From d9e64c01de283339f9d10201bcb185331e343c7a Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 8 Aug 2011 10:56:53 +0200 Subject: allow shared library building on ppc --- package/cyrus-sasl/patches/patch-config_ltconfig | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 package/cyrus-sasl/patches/patch-config_ltconfig diff --git a/package/cyrus-sasl/patches/patch-config_ltconfig b/package/cyrus-sasl/patches/patch-config_ltconfig new file mode 100644 index 000000000..7112c26e1 --- /dev/null +++ b/package/cyrus-sasl/patches/patch-config_ltconfig @@ -0,0 +1,20 @@ +--- cyrus-sasl-2.1.23.orig/config/ltconfig 2003-06-12 02:32:43.000000000 +0200 ++++ cyrus-sasl-2.1.23/config/ltconfig 2011-08-08 10:54:43.509265006 +0200 +@@ -2034,16 +2034,7 @@ linux-gnu*) + shlibpath_var=LD_LIBRARY_PATH + shlibpath_overrides_runpath=no + deplibs_check_method=pass_all +- +- if test -f /lib/ld.so.1; then +- dynamic_linker='GNU ld.so' +- else +- # Only the GNU ld.so supports shared libraries on MkLinux. +- case "$host_cpu" in +- powerpc*) dynamic_linker=no ;; +- *) dynamic_linker='Linux ld.so' ;; +- esac +- fi ++ dynamic_linker='Linux ld.so' + ;; + + netbsd*) -- cgit v1.2.3 From 31fb5bbcfe32d567284c5ef0b98b66921e0497b2 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 8 Aug 2011 14:14:44 +0200 Subject: disable some drivers --- package/sdl/Makefile | 2 ++ 1 file changed, 2 insertions(+) diff --git a/package/sdl/Makefile b/package/sdl/Makefile index e39b2f6a4..d36b9d55b 100644 --- a/package/sdl/Makefile +++ b/package/sdl/Makefile @@ -40,6 +40,8 @@ CONFIGURE_ARGS+= --disable-esd \ --enable-video-fbcon \ --disable-video-directfb \ --disable-video-opengl \ + --disable-video-ps2gs \ + --disable-video-ps3 \ --with-x libsdl-install: -- cgit v1.2.3 From 96d9f7612b66674d60f6fc37df647d363fd9dce2 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 8 Aug 2011 22:42:57 +0200 Subject: fix compile with uClibc, tested on rb532 --- jtools/Makefile | 1 + package/openjdk/Makefile | 6 +- package/openjdk/patches/cross-compile.patch | 53 ++++++++++++++ package/openjdk/patches/disable-backtrace.patch | 14 +++- package/openjdk/patches/inc-path.patch | 22 ++++++ package/openjdk/patches/uClibc-compat.patch | 92 +++++++++++++++++++++++++ 6 files changed, 185 insertions(+), 3 deletions(-) create mode 100644 package/openjdk/patches/cross-compile.patch create mode 100644 package/openjdk/patches/inc-path.patch create mode 100644 package/openjdk/patches/uClibc-compat.patch diff --git a/jtools/Makefile b/jtools/Makefile index 2ea44243a..7ddaf23eb 100644 --- a/jtools/Makefile +++ b/jtools/Makefile @@ -5,6 +5,7 @@ include $(TOPDIR)/rules.mk TARGETS:= ifneq ($(ADK_PACKAGE_OPENJDK),) +# jikes is for ant TARGETS+=fastjar gcj ecj jikes classpath jamvm ant openjdk endif diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index e297bca74..45194d4d9 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -24,7 +24,7 @@ PKG_SITES:= http://download.java.net/openjdk/jdk6/promoted/b22/ \ http://icedtea.classpath.org/download/drops/ \ http://icedtea.classpath.org/download/source/ -PKG_CFLINE_OPENJDK:= depends on ADK_TARGET_LIB_GLIBC || ADK_TARGET_LIB_EGLIBC && !ADK_TARGET_SYSTEM_LEMOTE_YEELONG +#PKG_CFLINE_OPENJDK:= depends on ADK_TARGET_LIB_GLIBC || ADK_TARGET_LIB_EGLIBC && !ADK_TARGET_SYSTEM_LEMOTE_YEELONG PKG_HOST_DEPENDS:= !darwin !cygwin !openbsd !netbsd !freebsd # autotools infrastructure for OpenJDK @@ -106,6 +106,10 @@ OPENJDK_NATIVE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAM TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) ALL_TARGET:= icedtea +# add include path for Xrender.h from staging directory +post-patch: + $(SED) "s#@ADK_TARGETDIR@#$(STAGING_TARGET_DIR)#" ${WRKDIST}/$(PKG_NAME)-$(PKG_VERSION)/jdk/make/sun/xawt/Makefile + do-extract: cd ${WRKDIST}; mkdir $(PKG_NAME)-$(PKG_VERSION); \ tar xzf $(TOPDIR)/dl/$(PKG_NAME)-$(PKG_VERSION)-src-$(PKG_EXTRAVER).tar.gz -C $(PKG_NAME)-$(PKG_VERSION) diff --git a/package/openjdk/patches/cross-compile.patch b/package/openjdk/patches/cross-compile.patch new file mode 100644 index 000000000..afc00b032 --- /dev/null +++ b/package/openjdk/patches/cross-compile.patch @@ -0,0 +1,53 @@ +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/sun/awt/Makefile 2011-02-28 17:06:11.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/jdk/make/sun/awt/Makefile 2011-08-07 17:00:37.676468717 +0200 +@@ -509,10 +509,7 @@ + # + + ifeq ($(PLATFORM), linux) +-CPPFLAGS += -I$(MOTIF_DIR)/include \ +- -I$(OPENWIN_HOME)/include \ +- -I$(OPENWIN_HOME)/include/X11/extensions \ +- -I$(PLATFORM_SRC)/native/$(PKGDIR)/font ++CPPFLAGS += -I$(PLATFORM_SRC)/native/$(PKGDIR)/font + endif + CPPFLAGS += -I$(SHARE_SRC)/native/$(PKGDIR)/debug \ + -I$(SHARE_SRC)/native/$(PKGDIR)/../font \ +@@ -535,10 +532,6 @@ + -I$(PLATFORM_SRC)/native/$(PKGDIR) \ + $(EVENT_MODEL) + +-ifeq ($(PLATFORM), linux) +-LDFLAGS += -L$(MOTIF_LIB) -L$(OPENWIN_LIB) +-endif +- + LDFLAGS += -L$(LIBDIR)/$(LIBARCH)/$(TSOBJDIR) \ + $(AWT_RUNPATH) + +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/sun/xawt/Makefile 2011-02-28 17:06:12.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/jdk/make/sun/xawt/Makefile 2011-08-07 18:31:08.635355054 +0200 +@@ -96,6 +96,10 @@ + + CPPFLAGS += -I$(CUPS_HEADERS_PATH) + ++ifeq ($(PLATFORM), linux) ++CPPFLAGS += -I@ADK_TARGETDIR@/usr/include/X11/extensions ++endif ++ + CPPFLAGS += -DXAWT -DXAWT_HACK \ + -I$(TEMPDIR)/../../sun.awt/awt/CClassHeaders \ + -I$(PLATFORM_SRC)/native/sun/awt \ +@@ -122,14 +126,6 @@ + -I$(SHARE_SRC)/native/sun/awt \ + -I$(PLATFORM_SRC)/native/sun/awt + +-ifeq ($(PLATFORM), linux) +-# Allows for builds on Debian GNU Linux, X11 is in a different place +- CPPFLAGS += -I/usr/X11R6/include/X11/extensions \ +- -I/usr/include/X11/extensions \ +- -I$(MOTIF_DIR)/include \ +- -I$(OPENWIN_HOME)/include +-endif +- + ifeq ($(PLATFORM), solaris) + CPPFLAGS += -I$(OPENWIN_HOME)/include/X11/extensions -I$(MOTIF_DIR)/include + endif diff --git a/package/openjdk/patches/disable-backtrace.patch b/package/openjdk/patches/disable-backtrace.patch index bd335a914..b54c95741 100644 --- a/package/openjdk/patches/disable-backtrace.patch +++ b/package/openjdk/patches/disable-backtrace.patch @@ -1,6 +1,16 @@ --- w-openjdk-6-1.orig/openjdk-6/jdk/src/solaris/native/sun/xawt/XToolkit.c 2011-02-28 17:06:50.000000000 +0100 -+++ w-openjdk-6-1/openjdk-6/jdk/src/solaris/native/sun/xawt/XToolkit.c 2011-04-10 22:33:28.481412674 +0200 -@@ -689,7 +689,7 @@ ++++ w-openjdk-6-1/openjdk-6/jdk/src/solaris/native/sun/xawt/XToolkit.c 2011-08-08 10:45:01.445330729 +0200 +@@ -27,9 +27,6 @@ + #include + #include + #include +-#ifdef __linux__ +-#include +-#endif + + #include + #include +@@ -689,7 +686,7 @@ return ret; } diff --git a/package/openjdk/patches/inc-path.patch b/package/openjdk/patches/inc-path.patch new file mode 100644 index 000000000..32aaa919e --- /dev/null +++ b/package/openjdk/patches/inc-path.patch @@ -0,0 +1,22 @@ +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/Defs.gmk 2011-02-28 17:06:10.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/jdk/make/common/Defs.gmk 2011-08-07 21:21:49.335286149 +0200 +@@ -173,7 +173,7 @@ + ifeq ($(DEVTOOLS_FT_DIR_EXISTS), true) + FREETYPE_HEADERS_PATH = $(DEVTOOLS_FT_DIR)/include + else +- FREETYPE_HEADERS_PATH = /usr/include ++ FREETYPE_HEADERS_PATH = /usr/include/disabled + endif + endif + endif +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-02-28 17:06:10.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-08-08 10:07:58.975256728 +0200 +@@ -170,7 +170,7 @@ + GCC29_COMPILER_PATH = $(JDK_DEVTOOLS_DIR)/$(PLATFORM)/gcc29/usr/ + endif + +-_CUPS_HEADERS_PATH=/usr/include ++_CUPS_HEADERS_PATH=/usr/include/disabled + + # Import JDK images allow for partial builds, components not built are + # imported (or copied from) these import areas when needed. diff --git a/package/openjdk/patches/uClibc-compat.patch b/package/openjdk/patches/uClibc-compat.patch new file mode 100644 index 000000000..1bdf56b5b --- /dev/null +++ b/package/openjdk/patches/uClibc-compat.patch @@ -0,0 +1,92 @@ +--- w-openjdk-6-1.orig/openjdk-6/hotspot/src/os/linux/vm/os_linux.cpp 2011-02-28 17:03:14.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/hotspot/src/os/linux/vm/os_linux.cpp 2011-08-07 14:30:00.195403776 +0200 +@@ -53,7 +53,6 @@ + # include + # include + # include +-# include + # include + # include + # include +@@ -553,9 +552,10 @@ + os::Linux::set_glibc_version(str); + } else { + // _CS_GNU_LIBC_VERSION is not supported, try gnu_get_libc_version() +- static char _gnu_libc_version[32]; +- jio_snprintf(_gnu_libc_version, sizeof(_gnu_libc_version), +- "glibc %s %s", gnu_get_libc_version(), gnu_get_libc_release()); ++ // static char _gnu_libc_version[32]; ++ // jio_snprintf(_gnu_libc_version, sizeof(_gnu_libc_version), ++ // "glibc %s %s", gnu_get_libc_version(), gnu_get_libc_release()); ++ static char _gnu_libc_version[32] = "2.12"; + os::Linux::set_glibc_version(_gnu_libc_version); + } + +@@ -2434,10 +2434,8 @@ + // If we are running with earlier version, which did not have symbol versions, + // we should use the base version. + void* os::Linux::libnuma_dlsym(void* handle, const char *name) { +- void *f = dlvsym(handle, name, "libnuma_1.1"); +- if (f == NULL) { +- f = dlsym(handle, name); +- } ++ void *f; ++ f = dlsym(handle, name); + return f; + } + +@@ -4446,7 +4444,21 @@ + // Linux doesn't yet have a (official) notion of processor sets, + // so just return the system wide load average. + int os::loadavg(double loadavg[], int nelem) { +- return ::getloadavg(loadavg, nelem); ++ FILE *LOADAVG; ++ double avg[3] = { 0.0, 0.0, 0.0 }; ++ int i, res = -1;; ++ ++ if ((LOADAVG = fopen("/proc/loadavg", "r"))) { ++ fscanf(LOADAVG, "%lf %lf %lf", &avg[0], &avg[1], &avg[2]); ++ res = 0; ++ fclose(LOADAVG); ++ } ++ ++ for (i = 0; (i < nelem) && (i < 3); i++) { ++ loadavg[i] = avg[i]; ++ } ++ ++ return res; + } + + void os::pause() { + +--- w-openjdk-6-1.orig/openjdk-6/hotspot/make/linux/platform_zero.in 2011-02-28 17:03:13.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/hotspot/make/linux/platform_zero.in 2011-08-07 13:56:56.875281880 +0200 +@@ -14,4 +14,4 @@ + + gnu_dis_arch = zero + +-sysdefs = -DLINUX -D_GNU_SOURCE -DCC_INTERP -DZERO -D@ZERO_ARCHDEF@ -DZERO_LIBARCH=\"@ZERO_LIBARCH@\" ++sysdefs = -DLINUX -D_GNU_SOURCE -DCC_INTERP -DZERO -D@ZERO_ARCHDEF@ -DZERO_LIBARCH=\"@ZERO_LIBARCH@\" -D__STDC_LIMIT_MACROS + +--- w-openjdk-6-1.orig/openjdk-6/hotspot/src/share/vm/utilities/globalDefinitions_gcc.hpp 2011-02-28 17:03:22.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/hotspot/src/share/vm/utilities/globalDefinitions_gcc.hpp 2011-08-07 12:32:09.325489647 +0200 +@@ -238,7 +238,7 @@ + #endif + inline int g_isnan(double f) { return isnand(f); } + #elif LINUX +-inline int g_isnan(float f) { return isnanf(f); } ++inline int g_isnan(float f) { return __isnanf(f); } + inline int g_isnan(double f) { return isnan(f); } + #else + #error "missing platform-specific definition here" +@@ -252,8 +252,8 @@ + + // Checking for finiteness + +-inline int g_isfinite(jfloat f) { return finite(f); } +-inline int g_isfinite(jdouble f) { return finite(f); } ++inline int g_isfinite(jfloat f) { return isfinite(f); } ++inline int g_isfinite(jdouble f) { return isfinite(f); } + + + // Wide characters -- cgit v1.2.3 From 11f9e374a5bba6dceb3eb80ac2ae65d74543d91a Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Tue, 9 Aug 2011 11:42:14 +0200 Subject: java uses $ORIGIN in RPATH of the binary. This patch from the mailinglist, seems to work fine. http://www.mail-archive.com/uclibc@uclibc.org/msg06444.html --- toolchain/uClibc/patches/rpath-origin.patch | 174 ++++++++++++++++++++++++++++ 1 file changed, 174 insertions(+) create mode 100644 toolchain/uClibc/patches/rpath-origin.patch diff --git a/toolchain/uClibc/patches/rpath-origin.patch b/toolchain/uClibc/patches/rpath-origin.patch new file mode 100644 index 000000000..c2bd2e8ab --- /dev/null +++ b/toolchain/uClibc/patches/rpath-origin.patch @@ -0,0 +1,174 @@ +diff -Nur uClibc-0.9.32.orig//ldso/ldso/dl-elf.c uClibc-0.9.32/ldso/ldso/dl-elf.c +--- uClibc-0.9.32.orig//ldso/ldso/dl-elf.c 2011-06-08 21:35:20.000000000 +0200 ++++ uClibc-0.9.32/ldso/ldso/dl-elf.c 2011-08-09 11:19:18.325314589 +0200 +@@ -133,53 +133,59 @@ + * in uClibc/ldso/util/ldd.c */ + static struct elf_resolve * + search_for_named_library(const char *name, int secure, const char *path_list, +- struct dyn_elf **rpnt) ++ struct dyn_elf **rpnt, const char *origin) + { +- char *path, *path_n, *mylibname; ++ char *mylibname; ++ const char *p, *pn; + struct elf_resolve *tpnt; +- int done; ++ int plen; + + if (path_list==NULL) + return NULL; + +- /* We need a writable copy of this string, but we don't +- * need this allocated permanently since we don't want +- * to leak memory, so use alloca to put path on the stack */ +- done = _dl_strlen(path_list); +- path = alloca(done + 1); +- + /* another bit of local storage */ + mylibname = alloca(2050); + +- _dl_memcpy(path, path_list, done+1); +- + /* Unlike ldd.c, don't bother to eliminate double //s */ + + /* Replace colons with zeros in path_list */ + /* : at the beginning or end of path maps to CWD */ + /* :: anywhere maps CWD */ + /* "" maps to CWD */ +- done = 0; +- path_n = path; +- do { +- if (*path == 0) { +- *path = ':'; +- done = 1; ++ for (p = path_list; p != NULL; p = pn) { ++ pn = _dl_strchr(p + 1, ':'); ++ if (pn != NULL) { ++ plen = pn - p; ++ pn++; ++ } else ++ plen = _dl_strlen(p); ++ ++ if (plen >= 7 && _dl_memcmp(p, "$ORIGIN", 7) == 0) { ++ int olen; ++ if (secure && plen != 7) ++ continue; ++ if (origin == NULL) ++ continue; ++ for (olen = _dl_strlen(origin) - 1; olen >= 0 && origin[olen] != '/'; olen--) ++ ; ++ if (olen <= 0) ++ continue; ++ _dl_memcpy(&mylibname[0], origin, olen); ++ _dl_memcpy(&mylibname[olen], p + 7, plen - 7); ++ mylibname[olen + plen - 7] = 0; ++ } else if (plen != 0) { ++ _dl_memcpy(mylibname, p, plen); ++ mylibname[plen] = 0; ++ } else { ++ _dl_strcpy(mylibname, "."); + } +- if (*path == ':') { +- *path = 0; +- if (*path_n) +- _dl_strcpy(mylibname, path_n); +- else +- _dl_strcpy(mylibname, "."); /* Assume current dir if empty path */ +- _dl_strcat(mylibname, "/"); +- _dl_strcat(mylibname, name); +- if ((tpnt = _dl_load_elf_shared_library(secure, rpnt, mylibname)) != NULL) +- return tpnt; +- path_n = path+1; +- } +- path++; +- } while (!done); ++ _dl_strcat(mylibname, "/"); ++ _dl_strcat(mylibname, name); ++ ++ tpnt = _dl_load_elf_shared_library(secure, rpnt, mylibname); ++ if (tpnt != NULL) ++ return tpnt; ++ } + return NULL; + } + +@@ -231,7 +237,7 @@ + if (pnt) { + pnt += (unsigned long) tpnt->dynamic_info[DT_STRTAB]; + _dl_if_debug_dprint("\tsearching RPATH='%s'\n", pnt); +- if ((tpnt1 = search_for_named_library(libname, secure, pnt, rpnt)) != NULL) ++ if ((tpnt1 = search_for_named_library(libname, secure, pnt, rpnt, tpnt->libname)) != NULL) + return tpnt1; + } + #endif +@@ -239,7 +245,7 @@ + /* Check in LD_{ELF_}LIBRARY_PATH, if specified and allowed */ + if (_dl_library_path) { + _dl_if_debug_dprint("\tsearching LD_LIBRARY_PATH='%s'\n", _dl_library_path); +- if ((tpnt1 = search_for_named_library(libname, secure, _dl_library_path, rpnt)) != NULL) ++ if ((tpnt1 = search_for_named_library(libname, secure, _dl_library_path, rpnt, NULL)) != NULL) + { + return tpnt1; + } +@@ -253,7 +259,7 @@ + if (pnt) { + pnt += (unsigned long) tpnt->dynamic_info[DT_STRTAB]; + _dl_if_debug_dprint("\tsearching RUNPATH='%s'\n", pnt); +- if ((tpnt1 = search_for_named_library(libname, secure, pnt, rpnt)) != NULL) ++ if ((tpnt1 = search_for_named_library(libname, secure, pnt, rpnt, NULL)) != NULL) + return tpnt1; + } + #endif +@@ -287,7 +293,7 @@ + /* Look for libraries wherever the shared library loader + * was installed */ + _dl_if_debug_dprint("\tsearching ldso dir='%s'\n", _dl_ldsopath); +- tpnt1 = search_for_named_library(libname, secure, _dl_ldsopath, rpnt); ++ tpnt1 = search_for_named_library(libname, secure, _dl_ldsopath, rpnt, NULL); + if (tpnt1 != NULL) + return tpnt1; + +@@ -300,7 +306,7 @@ + #ifndef __LDSO_CACHE_SUPPORT__ + ":" UCLIBC_RUNTIME_PREFIX "usr/X11R6/lib" + #endif +- , rpnt); ++ , rpnt, NULL); + if (tpnt1 != NULL) + return tpnt1; + +diff -Nur uClibc-0.9.32.orig//ldso/ldso/ldso.c uClibc-0.9.32/ldso/ldso/ldso.c +--- uClibc-0.9.32.orig//ldso/ldso/ldso.c 2011-06-08 21:35:20.000000000 +0200 ++++ uClibc-0.9.32/ldso/ldso/ldso.c 2011-08-09 11:15:04.135386129 +0200 +@@ -272,6 +272,20 @@ + } + } + ++static void _dl_setup_progname(const char *argv0) ++{ ++ char image[PATH_MAX]; ++ ssize_t s; ++ ++ s = _dl_readlink("/proc/self/exe", image, sizeof(image)); ++ if (s > 0 && image[0] == '/') { ++ image[s] = 0; ++ _dl_progname = _dl_strdup(image); ++ } else if (argv0) { ++ _dl_progname = argv0; ++ } ++} ++ + void _dl_get_ready_to_run(struct elf_resolve *tpnt, DL_LOADADDR_TYPE load_addr, + ElfW(auxv_t) auxvt[AT_EGID + 1], char **envp, + char **argv +@@ -321,9 +335,7 @@ + * been fixed up by now. Still no function calls outside of this + * library, since the dynamic resolver is not yet ready. + */ +- if (argv[0]) { +- _dl_progname = argv[0]; +- } ++ _dl_setup_progname(argv[0]); + + if (_start == (void *) auxvt[AT_ENTRY].a_un.a_val) { + _dl_dprintf(_dl_debug_file, "Standalone execution is not supported yet\n"); -- cgit v1.2.3 From f74d8a406d12c57550fea0cd4dbe967cd9f94eeb Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Tue, 9 Aug 2011 16:56:39 +0200 Subject: some powerpc fixes found via make bulk --- .../patch-lib_direct_ppcasm_memcpy_cachable_S | 11 + package/forked-daapd/Makefile | 7 +- package/gpsd/Makefile | 2 +- package/id3lib/Makefile | 2 +- package/microperl/files/uconfig.h.ppc | 4462 ++++++++++++++++++++ package/pcc-libs/Makefile | 2 +- package/pcc/Makefile | 3 +- target/config/Config.in | 2 +- target/ppc/uclibc.config | 2 +- 9 files changed, 4484 insertions(+), 9 deletions(-) create mode 100644 package/DirectFB/patches/patch-lib_direct_ppcasm_memcpy_cachable_S create mode 100644 package/microperl/files/uconfig.h.ppc diff --git a/package/DirectFB/patches/patch-lib_direct_ppcasm_memcpy_cachable_S b/package/DirectFB/patches/patch-lib_direct_ppcasm_memcpy_cachable_S new file mode 100644 index 000000000..5352a950c --- /dev/null +++ b/package/DirectFB/patches/patch-lib_direct_ppcasm_memcpy_cachable_S @@ -0,0 +1,11 @@ +--- DirectFB-1.4.11.orig/lib/direct/ppcasm_memcpy_cachable.S 2010-10-08 14:43:46.000000000 +0200 ++++ DirectFB-1.4.11/lib/direct/ppcasm_memcpy_cachable.S 2011-08-08 14:52:51.448015034 +0200 +@@ -34,8 +34,6 @@ + + #define __ASSEMBLY__ + +-#include +- + #if defined(CONFIG_8xx) || defined(CONFIG_403GCX) + #define L1_CACHE_LINE_SIZE 16 + #define LG_L1_CACHE_LINE_SIZE 4 diff --git a/package/forked-daapd/Makefile b/package/forked-daapd/Makefile index 7b11a7523..435a3c560 100644 --- a/package/forked-daapd/Makefile +++ b/package/forked-daapd/Makefile @@ -4,9 +4,9 @@ include $(TOPDIR)/rules.mk PKG_NAME:= forked-daapd -PKG_VERSION:= 0.16 +PKG_VERSION:= 0.18 PKG_RELEASE:= 1 -PKG_MD5SUM:= cc35619babefea35db9ee22e6f1d036b +PKG_MD5SUM:= b45aab5b60382ec3ada7e71cb1356b1d PKG_DESCR:= DAAPD server PKG_SECTION:= multimedia PKG_DEPENDS:= libunistring zlib libconfuse sqlite ffmpeg libgcrypt @@ -17,11 +17,14 @@ PKG_BUILDDEP+= mxml libevent libavl libantlr3c alsa-lib libgcrypt PKG_SITES:= http://alioth.debian.org/~jblache/forked-daapd/ PKG_CFLINE_FORKED_DAAPD:= select ADK_KERNEL_INOTIFY_USER +PKG_ARCH_DEPENDS:= !ppc include $(TOPDIR)/mk/package.mk $(eval $(call PKG_template,FORKED_DAAPD,forked-daapd,$(PKG_VERSION)-${PKG_RELEASE},${PKG_DEPENDS},${PKG_DESCR},${PKG_SECTION})) +#TARGET_LDFLAGS+= -lgcc + forked-daapd-install: $(INSTALL_DIR) $(IDIR_FORKED_DAAPD)/etc $(CP) ./files/forked-daapd.conf \ diff --git a/package/gpsd/Makefile b/package/gpsd/Makefile index 397460f67..19cd7c3f2 100644 --- a/package/gpsd/Makefile +++ b/package/gpsd/Makefile @@ -34,7 +34,7 @@ CONFIGURE_ENV+= EGREP="grep -E" \ CONFIGURE_ARGS+= --disable-dbus TARGET_CFLAGS+= -fPIC -LIBRARIES:=-nodefaultlibs -luClibc++ +LIBRARIES:=-nodefaultlibs -luClibc++ -lgcc ifeq ($(ADK_TOOLCHAIN_GCC_USE_SSP),y) LIBRARIES+=-lssp -lssp_nonshared endif diff --git a/package/id3lib/Makefile b/package/id3lib/Makefile index 370b40755..bcff710b1 100644 --- a/package/id3lib/Makefile +++ b/package/id3lib/Makefile @@ -23,7 +23,7 @@ $(eval $(call PKG_template,ID3LIB,id3lib,${PKG_VERSION}-${PKG_RELEASE},${PKG_DEP TARGET_CFLAGS+= -fPIC CONFIGURE_ARGS+= --enable-cxx-warnings=no -LIBRARIES:=-nodefaultlibs -luClibc++ -lz -lm -lc +LIBRARIES:=-nodefaultlibs -luClibc++ -lz -lm -lc -lgcc ifeq ($(ADK_TOOLCHAIN_GCC_USE_SSP),y) LIBRARIES+=-lssp -fstack-protector endif diff --git a/package/microperl/files/uconfig.h.ppc b/package/microperl/files/uconfig.h.ppc new file mode 100644 index 000000000..bfc1ab90b --- /dev/null +++ b/package/microperl/files/uconfig.h.ppc @@ -0,0 +1,4462 @@ +/* + * This file was produced by running the config_h.SH script, which + * gets its values from config.sh, which is generally produced by + * running Configure. + * + * Feel free to modify any of this as the need arises. Note, however, + * that running config_h.SH again will wipe out any changes you've made. + * For a more permanent change edit config.sh and rerun config_h.SH. + * + * $Id: Config_h.U,v 3.0.1.5 1997/02/28 14:57:43 ram Exp $ + */ + +/* + * Package name : perl5 + * Source directory : . + * Configuration time: Mon Sep 14 22:24:11 CEST 2009 + * Configured by : OpenADK + * Target system : linux linux 2.6.30.5 #4 smp fri sep 11 13:47:48 cest 2009 x86_64 unknown + */ + +#ifndef _config_h_ +#define _config_h_ + +/* LOC_SED: + * This symbol holds the complete pathname to the sed program. + */ +#define LOC_SED "/bin/sed" /**/ + +/* HAS_ALARM: + * This symbol, if defined, indicates that the alarm routine is + * available. + */ +#define HAS_ALARM /**/ + +/* HAS_BCMP: + * This symbol is defined if the bcmp() routine is available to + * compare blocks of memory. + */ +/*#define HAS_BCMP / **/ + +/* HAS_BCOPY: + * This symbol is defined if the bcopy() routine is available to + * copy blocks of memory. + */ +/*#define HAS_BCOPY / **/ + +/* HAS_BZERO: + * This symbol is defined if the bzero() routine is available to + * set a memory block to 0. + */ +/*#define HAS_BZERO / **/ + +/* HAS_CHOWN: + * This symbol, if defined, indicates that the chown routine is + * available. + */ +#define HAS_CHOWN /**/ + +/* HAS_CHROOT: + * This symbol, if defined, indicates that the chroot routine is + * available. + */ +#define HAS_CHROOT /**/ + +/* HAS_CHSIZE: + * This symbol, if defined, indicates that the chsize routine is available + * to truncate files. You might need a -lx to get this routine. + */ +/*#define HAS_CHSIZE / **/ + +/* HAS_CTERMID: + * This symbol, if defined, indicates that the ctermid routine is + * available to generate filename for terminal. + */ +#define HAS_CTERMID /**/ + +/* HAS_CUSERID: + * This symbol, if defined, indicates that the cuserid routine is + * available to get character login names. + */ +#define HAS_CUSERID /**/ + +/* HAS_DBL_DIG: + * This symbol, if defined, indicates that this system's + * or defines the symbol DBL_DIG, which is the number + * of significant digits in a double precision number. If this + * symbol is not defined, a guess of 15 is usually pretty good. + */ +#define HAS_DBL_DIG /* */ + +/* HAS_DIFFTIME: + * This symbol, if defined, indicates that the difftime routine is + * available. + */ +#define HAS_DIFFTIME /**/ + +/* HAS_DLERROR: + * This symbol, if defined, indicates that the dlerror routine is + * available to return a string describing the last error that + * occurred from a call to dlopen(), dlclose() or dlsym(). + */ +/*#define HAS_DLERROR / **/ + +/* HAS_DUP2: + * This symbol, if defined, indicates that the dup2 routine is + * available to duplicate file descriptors. + */ +#define HAS_DUP2 /**/ + +/* HAS_FCHMOD: + * This symbol, if defined, indicates that the fchmod routine is available + * to change mode of opened files. If unavailable, use chmod(). + */ +#define HAS_FCHMOD /**/ + +/* HAS_FCHOWN: + * This symbol, if defined, indicates that the fchown routine is available + * to change ownership of opened files. If unavailable, use chown(). + */ +#define HAS_FCHOWN /**/ + +/* HAS_FCNTL: + * This symbol, if defined, indicates to the C program that + * the fcntl() function exists. + */ +#define HAS_FCNTL /**/ + +/* HAS_FGETPOS: + * This symbol, if defined, indicates that the fgetpos routine is + * available to get the file position indicator, similar to ftell(). + */ +#define HAS_FGETPOS /**/ + +/* HAS_FLOCK: + * This symbol, if defined, indicates that the flock routine is + * available to do file locking. + */ +#define HAS_FLOCK /**/ + +/* HAS_FORK: + * This symbol, if defined, indicates that the fork routine is + * available. + */ +#define HAS_FORK /**/ + +/* HAS_FSETPOS: + * This symbol, if defined, indicates that the fsetpos routine is + * available to set the file position indicator, similar to fseek(). + */ +#define HAS_FSETPOS /**/ + +/* HAS_GETTIMEOFDAY: + * This symbol, if defined, indicates that the gettimeofday() system + * call is available for a sub-second accuracy clock. Usually, the file + * needs to be included (see I_SYS_RESOURCE). + * The type "Timeval" should be used to refer to "struct timeval". + */ +#define HAS_GETTIMEOFDAY /**/ +#ifdef HAS_GETTIMEOFDAY +#define Timeval struct timeval /* Structure used by gettimeofday() */ +#endif + +/* HAS_GETGROUPS: + * This symbol, if defined, indicates that the getgroups() routine is + * available to get the list of process groups. If unavailable, multiple + * groups are probably not supported. + */ +#define HAS_GETGROUPS /**/ + +/* HAS_GETLOGIN: + * This symbol, if defined, indicates that the getlogin routine is + * available to get the login name. + */ +#define HAS_GETLOGIN /**/ + +/* HAS_GETPGID: + * This symbol, if defined, indicates to the C program that + * the getpgid(pid) function is available to get the + * process group id. + */ +#define HAS_GETPGID /**/ + +/* HAS_GETPGRP2: + * This symbol, if defined, indicates that the getpgrp2() (as in DG/UX) + * routine is available to get the current process group. + */ +/*#define HAS_GETPGRP2 / **/ + +/* HAS_GETPPID: + * This symbol, if defined, indicates that the getppid routine is + * available to get the parent process ID. + */ +#define HAS_GETPPID /**/ + +/* HAS_GETPRIORITY: + * This symbol, if defined, indicates that the getpriority routine is + * available to get a process's priority. + */ +#define HAS_GETPRIORITY /**/ + +/* HAS_INET_ATON: + * This symbol, if defined, indicates to the C program that the + * inet_aton() function is available to parse IP address "dotted-quad" + * strings. + */ +#define HAS_INET_ATON /**/ + +/* HAS_KILLPG: + * This symbol, if defined, indicates that the killpg routine is available + * to kill process groups. If unavailable, you probably should use kill + * with a negative process number. + */ +#define HAS_KILLPG /**/ + +/* HAS_LINK: + * This symbol, if defined, indicates that the link routine is + * available to create hard links. + */ +#define HAS_LINK /**/ + +/* HAS_LOCALECONV: + * This symbol, if defined, indicates that the localeconv routine is + * available for numeric and monetary formatting conventions. + */ +#define HAS_LOCALECONV /**/ + +/* HAS_LOCKF: + * This symbol, if defined, indicates that the lockf routine is + * available to do file locking. + */ +#define HAS_LOCKF /**/ + +/* HAS_LSTAT: + * This symbol, if defined, indicates that the lstat routine is + * available to do file stats on symbolic links. + */ +#define HAS_LSTAT /**/ + +/* HAS_MBLEN: + * This symbol, if defined, indicates that the mblen routine is available + * to find the number of bytes in a multibye character. + */ +#define HAS_MBLEN /**/ + +/* HAS_MBSTOWCS: + * This symbol, if defined, indicates that the mbstowcs routine is + * available to covert a multibyte string into a wide character string. + */ +#define HAS_MBSTOWCS /**/ + +/* HAS_MBTOWC: + * This symbol, if defined, indicates that the mbtowc routine is available + * to covert a multibyte to a wide character. + */ +#define HAS_MBTOWC /**/ + +/* HAS_MEMCMP: + * This symbol, if defined, indicates that the memcmp routine is available + * to compare blocks of memory. + */ +#define HAS_MEMCMP /**/ + +/* HAS_MEMCPY: + * This symbol, if defined, indicates that the memcpy routine is available + * to copy blocks of memory. + */ +#define HAS_MEMCPY /**/ + +/* HAS_MEMMOVE: + * This symbol, if defined, indicates that the memmove routine is available + * to copy potentially overlapping blocks of memory. This should be used + * only when HAS_SAFE_BCOPY is not defined. If neither is there, roll your + * own version. + */ +#define HAS_MEMMOVE /**/ + +/* HAS_MEMSET: + * This symbol, if defined, indicates that the memset routine is available + * to set blocks of memory. + */ +#define HAS_MEMSET /**/ + +/* HAS_MKDIR: + * This symbol, if defined, indicates that the mkdir routine is available + * to create directories. Otherwise you should fork off a new process to + * exec /bin/mkdir. + */ +#define HAS_MKDIR /**/ + +/* HAS_MKFIFO: + * This symbol, if defined, indicates that the mkfifo routine is + * available to create FIFOs. Otherwise, mknod should be able to + * do it for you. However, if mkfifo is there, mknod might require + * super-user privileges which mkfifo will not. + */ +#define HAS_MKFIFO /**/ + +/* HAS_MKTIME: + * This symbol, if defined, indicates that the mktime routine is + * available. + */ +#define HAS_MKTIME /**/ + +/* HAS_MSYNC: + * This symbol, if defined, indicates that the msync system call is + * available to synchronize a mapped file. + */ +#define HAS_MSYNC /**/ + +/* HAS_MUNMAP: + * This symbol, if defined, indicates that the munmap system call is + * available to unmap a region, usually mapped by mmap(). + */ +#define HAS_MUNMAP /**/ + +/* HAS_NICE: + * This symbol, if defined, indicates that the nice routine is + * available. + */ +#define HAS_NICE /**/ + +/* HAS_PATHCONF: + * This symbol, if defined, indicates that pathconf() is available + * to determine file-system related limits and options associated + * with a given filename. + */ +/* HAS_FPATHCONF: + * This symbol, if defined, indicates that pathconf() is available + * to determine file-system related limits and options associated + * with a given open file descriptor. + */ +#define HAS_PATHCONF /**/ +#define HAS_FPATHCONF /**/ + +/* HAS_PAUSE: + * This symbol, if defined, indicates that the pause routine is + * available to suspend a process until a signal is received. + */ +#define HAS_PAUSE /**/ + +/* HAS_PIPE: + * This symbol, if defined, indicates that the pipe routine is + * available to create an inter-process channel. + */ +#define HAS_PIPE /**/ + +/* HAS_READDIR: + * This symbol, if defined, indicates that the readdir routine is + * available to read directory entries. You may have to include + * . See I_DIRENT. + */ +#define HAS_READDIR /**/ + +/* HAS_SEEKDIR: + * This symbol, if defined, indicates that the seekdir routine is + * available. You may have to include . See I_DIRENT. + */ +#define HAS_SEEKDIR /**/ + +/* HAS_TELLDIR: + * This symbol, if defined, indicates that the telldir routine is + * available. You may have to include . See I_DIRENT. + */ +#define HAS_TELLDIR /**/ + +/* HAS_REWINDDIR: + * This symbol, if defined, indicates that the rewinddir routine is + * available. You may have to include . See I_DIRENT. + */ +#define HAS_REWINDDIR /**/ + +/* HAS_READLINK: + * This symbol, if defined, indicates that the readlink routine is + * available to read the value of a symbolic link. + */ +#define HAS_READLINK /**/ + +/* HAS_RENAME: + * This symbol, if defined, indicates that the rename routine is available + * to rename files. Otherwise you should do the unlink(), link(), unlink() + * trick. + */ +#define HAS_RENAME /**/ + +/* HAS_RMDIR: + * This symbol, if defined, indicates that the rmdir routine is + * available to remove directories. Otherwise you should fork off a + * new process to exec /bin/rmdir. + */ +#define HAS_RMDIR /**/ + +/* HAS_SELECT: + * This symbol, if defined, indicates that the select routine is + * available to select active file descriptors. If the timeout field + * is used, may need to be included. + */ +#define HAS_SELECT /**/ + +/* HAS_SETEGID: + * This symbol, if defined, indicates that the setegid routine is available + * to change the effective gid of the current program. + */ +#define HAS_SETEGID /**/ + +/* HAS_SETEUID: + * This symbol, if defined, indicates that the seteuid routine is available + * to change the effective uid of the current program. + */ +#define HAS_SETEUID /**/ + +/* HAS_SETLINEBUF: + * This symbol, if defined, indicates that the setlinebuf routine is + * available to change stderr or stdout from block-buffered or unbuffered + * to a line-buffered mode. + */ +#define HAS_SETLINEBUF /**/ + +/* HAS_SETLOCALE: + * This symbol, if defined, indicates that the setlocale routine is + * available to handle locale-specific ctype implementations. + */ +#define HAS_SETLOCALE /**/ + +/* HAS_SETPGID: + * This symbol, if defined, indicates that the setpgid(pid, gpid) + * routine is available to set process group ID. + */ +#define HAS_SETPGID /**/ + +/* HAS_SETPGRP2: + * This symbol, if defined, indicates that the setpgrp2() (as in DG/UX) + * routine is available to set the current process group. + */ +/*#define HAS_SETPGRP2 / **/ + +/* HAS_SETPRIORITY: + * This symbol, if defined, indicates that the setpriority routine is + * available to set a process's priority. + */ +#define HAS_SETPRIORITY /**/ + +/* HAS_SETREGID: + * This symbol, if defined, indicates that the setregid routine is + * available to change the real and effective gid of the current + * process. + */ +/* HAS_SETRESGID: + * This symbol, if defined, indicates that the setresgid routine is + * available to change the real, effective and saved gid of the current + * process. + */ +#define HAS_SETREGID /**/ +#define HAS_SETRESGID /**/ + +/* HAS_SETREUID: + * This symbol, if defined, indicates that the setreuid routine is + * available to change the real and effective uid of the current + * process. + */ +/* HAS_SETRESUID: + * This symbol, if defined, indicates that the setresuid routine is + * available to change the real, effective and saved uid of the current + * process. + */ +#define HAS_SETREUID /**/ +#define HAS_SETRESUID /**/ + +/* HAS_SETRGID: + * This symbol, if defined, indicates that the setrgid routine is available + * to change the real gid of the current program. + */ +/*#define HAS_SETRGID / **/ + +/* HAS_SETRUID: + * This symbol, if defined, indicates that the setruid routine is available + * to change the real uid of the current program. + */ +/*#define HAS_SETRUID / **/ + +/* HAS_SETSID: + * This symbol, if defined, indicates that the setsid routine is + * available to set the process group ID. + */ +#define HAS_SETSID /**/ + +/* HAS_STRCHR: + * This symbol is defined to indicate that the strchr()/strrchr() + * functions are available for string searching. If not, try the + * index()/rindex() pair. + */ +/* HAS_INDEX: + * This symbol is defined to indicate that the index()/rindex() + * functions are available for string searching. + */ +#define HAS_STRCHR /**/ +/*#define HAS_INDEX / **/ + +/* HAS_STRCOLL: + * This symbol, if defined, indicates that the strcoll routine is + * available to compare strings using collating information. + */ +#define HAS_STRCOLL /**/ + +/* HAS_STRTOD: + * This symbol, if defined, indicates that the strtod routine is + * available to provide better numeric string conversion than atof(). + */ +#define HAS_STRTOD /**/ + +/* HAS_STRTOL: + * This symbol, if defined, indicates that the strtol routine is available + * to provide better numeric string conversion than atoi() and friends. + */ +#define HAS_STRTOL /**/ + +/* HAS_STRXFRM: + * This symbol, if defined, indicates that the strxfrm() routine is + * available to transform strings. + */ +#define HAS_STRXFRM /**/ + +/* HAS_SYMLINK: + * This symbol, if defined, indicates that the symlink routine is available + * to create symbolic links. + */ +#define HAS_SYMLINK /**/ + +/* HAS_SYSCALL: + * This symbol, if defined, indicates that the syscall routine is + * available to call arbitrary system calls. If undefined, that's tough. + */ +#define HAS_SYSCALL /**/ + +/* HAS_SYSCONF: + * This symbol, if defined, indicates that sysconf() is available + * to determine system related limits and options. + */ +#define HAS_SYSCONF /**/ + +/* HAS_SYSTEM: + * This symbol, if defined, indicates that the system routine is + * available to issue a shell command. + */ +#define HAS_SYSTEM /**/ + +/* HAS_TCGETPGRP: + * This symbol, if defined, indicates that the tcgetpgrp routine is + * available to get foreground process group ID. + */ +#define HAS_TCGETPGRP /**/ + +/* HAS_TCSETPGRP: + * This symbol, if defined, indicates that the tcsetpgrp routine is + * available to set foreground process group ID. + */ +#define HAS_TCSETPGRP /**/ + +/* HAS_TRUNCATE: + * This symbol, if defined, indicates that the truncate routine is + * available to truncate files. + */ +#define HAS_TRUNCATE /**/ + +/* HAS_TZNAME: + * This symbol, if defined, indicates that the tzname[] array is + * available to access timezone names. + */ +#define HAS_TZNAME /**/ + +/* HAS_UMASK: + * This symbol, if defined, indicates that the umask routine is + * available to set and get the value of the file creation mask. + */ +#define HAS_UMASK /**/ + +/* HAS_USLEEP: + * This symbol, if defined, indicates that the usleep routine is + * available to let the process sleep on a sub-second accuracy. + */ +#define HAS_USLEEP /**/ + +/* HAS_WAIT4: + * This symbol, if defined, indicates that wait4() exists. + */ +#define HAS_WAIT4 /**/ + +/* HAS_WAITPID: + * This symbol, if defined, indicates that the waitpid routine is + * available to wait for child process. + */ +#define HAS_WAITPID /**/ + +/* HAS_WCSTOMBS: + * This symbol, if defined, indicates that the wcstombs routine is + * available to convert wide character strings to multibyte strings. + */ +#define HAS_WCSTOMBS /**/ + +/* HAS_WCTOMB: + * This symbol, if defined, indicates that the wctomb routine is available + * to covert a wide character to a multibyte. + */ +#define HAS_WCTOMB /**/ + +/* I_ARPA_INET: + * This symbol, if defined, indicates to the C program that it should + * include to get inet_addr and friends declarations. + */ +#define I_ARPA_INET /**/ + +/* I_DBM: + * This symbol, if defined, indicates that exists and should + * be included. + */ +/* I_RPCSVC_DBM: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_DBM / **/ +/*#define I_RPCSVC_DBM / **/ + +/* I_DLFCN: + * This symbol, if defined, indicates that exists and should + * be included. + */ +#define I_DLFCN /**/ + +/* I_FCNTL: + * This manifest constant tells the C program to include . + */ +/*#define I_FCNTL / **/ + +/* I_FLOAT: + * This symbol, if defined, indicates to the C program that it should + * include to get definition of symbols like DBL_MAX or + * DBL_MIN, i.e. machine dependent floating point values. + */ +#define I_FLOAT /**/ + +/* I_GDBM: + * This symbol, if defined, indicates that exists and should + * be included. + */ +/*#define I_GDBM / **/ + +/* I_LIMITS: + * This symbol, if defined, indicates to the C program that it should + * include to get definition of symbols like WORD_BIT or + * LONG_MAX, i.e. machine dependant limitations. + */ +#define I_LIMITS /**/ + +/* I_LOCALE: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_LOCALE /**/ + +/* I_MATH: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_MATH /**/ + +/* I_MEMORY: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_MEMORY / **/ + +/* I_NET_ERRNO: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_NET_ERRNO / **/ + +/* I_NETINET_IN: + * This symbol, if defined, indicates to the C program that it should + * include . Otherwise, you may try . + */ +#define I_NETINET_IN /**/ + +/* I_SFIO: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_SFIO / **/ + +/* I_STDDEF: + * This symbol, if defined, indicates that exists and should + * be included. + */ +#define I_STDDEF /**/ + +/* I_STDLIB: + * This symbol, if defined, indicates that exists and should + * be included. + */ +#define I_STDLIB /**/ + +/* I_STRING: + * This symbol, if defined, indicates to the C program that it should + * include (USG systems) instead of (BSD systems). + */ +#define I_STRING /**/ + +/* I_SYS_DIR: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_DIR /**/ + +/* I_SYS_FILE: + * This symbol, if defined, indicates to the C program that it should + * include to get definition of R_OK and friends. + */ +#define I_SYS_FILE /**/ + +/* I_SYS_IOCTL: + * This symbol, if defined, indicates that exists and should + * be included. Otherwise, include or . + */ +/* I_SYS_SOCKIO: + * This symbol, if defined, indicates the should be included + * to get socket ioctl options, like SIOCATMARK. + */ +#define I_SYS_IOCTL /**/ +/*#define I_SYS_SOCKIO / **/ + +/* I_SYS_NDIR: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_SYS_NDIR / **/ + +/* I_SYS_PARAM: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_PARAM /**/ + +/* I_SYS_RESOURCE: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_RESOURCE /**/ + +/* I_SYS_SELECT: + * This symbol, if defined, indicates to the C program that it should + * include in order to get definition of struct timeval. + */ +#define I_SYS_SELECT /**/ + +/* I_SYS_STAT: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_STAT /**/ + +/* I_SYS_TIMES: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_TIMES /**/ + +/* I_SYS_TYPES: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_TYPES /**/ + +/* I_SYS_UN: + * This symbol, if defined, indicates to the C program that it should + * include to get UNIX domain socket definitions. + */ +#define I_SYS_UN /**/ + +/* I_SYS_WAIT: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_SYS_WAIT /**/ + +/* I_TERMIO: + * This symbol, if defined, indicates that the program should include + * rather than . There are also differences in + * the ioctl() calls that depend on the value of this symbol. + */ +/* I_TERMIOS: + * This symbol, if defined, indicates that the program should include + * the POSIX termios.h rather than sgtty.h or termio.h. + * There are also differences in the ioctl() calls that depend on the + * value of this symbol. + */ +/* I_SGTTY: + * This symbol, if defined, indicates that the program should include + * rather than . There are also differences in + * the ioctl() calls that depend on the value of this symbol. + */ +/*#define I_TERMIO / **/ +#define I_TERMIOS /**/ +/*#define I_SGTTY / **/ + +/* I_UNISTD: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_UNISTD /**/ + +/* I_UTIME: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_UTIME /**/ + +/* I_VALUES: + * This symbol, if defined, indicates to the C program that it should + * include to get definition of symbols like MINFLOAT or + * MAXLONG, i.e. machine dependant limitations. Probably, you + * should use instead, if it is available. + */ +#define I_VALUES /**/ + +/* I_VFORK: + * This symbol, if defined, indicates to the C program that it should + * include vfork.h. + */ +/*#define I_VFORK / **/ + +/* INTSIZE: + * This symbol contains the value of sizeof(int) so that the C + * preprocessor can make decisions based on it. + */ +/* LONGSIZE: + * This symbol contains the value of sizeof(long) so that the C + * preprocessor can make decisions based on it. + */ +/* SHORTSIZE: + * This symbol contains the value of sizeof(short) so that the C + * preprocessor can make decisions based on it. + */ +#define INTSIZE 4 /**/ +#define LONGSIZE 4 /**/ +#define SHORTSIZE 2 /**/ + +/* MULTIARCH: + * This symbol, if defined, signifies that the build + * process will produce some binary files that are going to be + * used in a cross-platform environment. This is the case for + * example with the NeXT "fat" binaries that contain executables + * for several CPUs. + */ +/*#define MULTIARCH / **/ + +/* HAS_QUAD: + * This symbol, if defined, tells that there's a 64-bit integer type, + * Quad_t, and its unsigned counterpar, Uquad_t. QUADKIND will be one + * of QUAD_IS_INT, QUAD_IS_LONG, QUAD_IS_LONG_LONG, or QUAD_IS_INT64_T. + */ +#define HAS_QUAD /**/ +#ifdef HAS_QUAD +# define Quad_t long /**/ +# define Uquad_t unsigned long /**/ +# define QUADKIND 3 /**/ +# define QUAD_IS_INT 1 +# define QUAD_IS_LONG 2 +# define QUAD_IS_LONG_LONG 3 +# define QUAD_IS_INT64_T 4 +#endif + +/* OSNAME: + * This symbol contains the name of the operating system, as determined + * by Configure. You shouldn't rely on it too much; the specific + * feature tests from Configure are generally more reliable. + */ +/* OSVERS: + * This symbol contains the version of the operating system, as determined + * by Configure. You shouldn't rely on it too much; the specific + * feature tests from Configure are generally more reliable. + */ +#define OSNAME "linux" /**/ +#define OSVERS "2.6.30.5" /**/ + +/* ARCHLIB: + * This variable, if defined, holds the name of the directory in + * which the user wants to put architecture-dependent public + * library files for perl5. It is most often a local directory + * such as /usr/local/lib. Programs using this variable must be + * prepared to deal with filename expansion. If ARCHLIB is the + * same as PRIVLIB, it is not defined, since presumably the + * program already searches PRIVLIB. + */ +/* ARCHLIB_EXP: + * This symbol contains the ~name expanded version of ARCHLIB, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +#define ARCHLIB "/usr/lib/perl5/5.10.0/powerpc-linux" /**/ +#define ARCHLIB_EXP "/usr/lib/perl5/5.10.0/powerpc-linux" /**/ + +/* ARCHNAME: + * This symbol holds a string representing the architecture name. + * It may be used to construct an architecture-dependant pathname + * where library files may be held under a private library, for + * instance. + */ +#define ARCHNAME "powerpc-linux" /**/ + +/* BIN: + * This symbol holds the path of the bin directory where the package will + * be installed. Program must be prepared to deal with ~name substitution. + */ +/* BIN_EXP: + * This symbol is the filename expanded version of the BIN symbol, for + * programs that do not want to deal with that at run-time. + */ +/* PERL_RELOCATABLE_INC: + * This symbol, if defined, indicates that we'd like to relocate entries + * in @INC at run time based on the location of the perl binary. + */ +#define BIN "/usr/bin" /**/ +#define BIN_EXP "/usr/bin" /**/ +#define PERL_RELOCATABLE_INC "undef" /**/ + +/* CAT2: + * This macro concatenates 2 tokens together. + */ +/* STRINGIFY: + * This macro surrounds its token with double quotes. + */ +#if 42 == 1 +#define CAT2(a,b) a/**/b +#define STRINGIFY(a) "a" + /* If you can get stringification with catify, tell me how! */ +#endif +#if 42 == 42 +#define PeRl_CaTiFy(a, b) a ## b +#define PeRl_StGiFy(a) #a +/* the additional level of indirection enables these macros to be + * used as arguments to other macros. See K&R 2nd ed., page 231. */ +#define CAT2(a,b) PeRl_CaTiFy(a,b) +#define StGiFy(a) PeRl_StGiFy(a) +#define STRINGIFY(a) PeRl_StGiFy(a) +#endif +#if 42 != 1 && 42 != 42 +# include "Bletch: How does this C preprocessor concatenate tokens?" +#endif + +/* CPPSTDIN: + * This symbol contains the first part of the string which will invoke + * the C preprocessor on the standard input and produce to standard + * output. Typical value of "cc -E" or "/lib/cpp", but it can also + * call a wrapper. See CPPRUN. + */ +/* CPPMINUS: + * This symbol contains the second part of the string which will invoke + * the C preprocessor on the standard input and produce to standard + * output. This symbol will have the value "-" if CPPSTDIN needs a minus + * to specify standard input, otherwise the value is "". + */ +/* CPPRUN: + * This symbol contains the string which will invoke a C preprocessor on + * the standard input and produce to standard output. It needs to end + * with CPPLAST, after all other preprocessor flags have been specified. + * The main difference with CPPSTDIN is that this program will never be a + * pointer to a shell wrapper, i.e. it will be empty if no preprocessor is + * available directly to the user. Note that it may well be different from + * the preprocessor used to compile the C program. + */ +/* CPPLAST: + * This symbol is intended to be used along with CPPRUN in the same manner + * symbol CPPMINUS is used with CPPSTDIN. It contains either "-" or "". + */ +#define CPPSTDIN "gcc -E" +#define CPPMINUS "-" +#define CPPRUN "gcc -E" +#define CPPLAST "-" + +/* HAS_ACCESS: + * This manifest constant lets the C program know that the access() + * system call is available to check for accessibility using real UID/GID. + * (always present on UNIX.) + */ +#define HAS_ACCESS /**/ + +/* HAS_ACCESSX: + * This symbol, if defined, indicates that the accessx routine is + * available to do extended access checks. + */ +/*#define HAS_ACCESSX / **/ + +/* HAS_ASCTIME_R: + * This symbol, if defined, indicates that the asctime_r routine + * is available to asctime re-entrantly. + */ +/* ASCTIME_R_PROTO: + * This symbol encodes the prototype of asctime_r. + * It is zero if d_asctime_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_asctime_r + * is defined. + */ +/*#define HAS_ASCTIME_R / **/ +#define ASCTIME_R_PROTO 0 /**/ + +/* HASATTRIBUTE_FORMAT: + * Can we handle GCC attribute for checking printf-style formats + */ +/* PRINTF_FORMAT_NULL_OK: + * Allows __printf__ format to be null when checking printf-style + */ +/* HASATTRIBUTE_MALLOC: + * Can we handle GCC attribute for malloc-style functions. + */ +/* HASATTRIBUTE_NONNULL: + * Can we handle GCC attribute for nonnull function parms. + */ +/* HASATTRIBUTE_NORETURN: + * Can we handle GCC attribute for functions that do not return + */ +/* HASATTRIBUTE_PURE: + * Can we handle GCC attribute for pure functions + */ +/* HASATTRIBUTE_UNUSED: + * Can we handle GCC attribute for unused variables and arguments + */ +/* HASATTRIBUTE_WARN_UNUSED_RESULT: + * Can we handle GCC attribute for warning on unused results + */ +#define HASATTRIBUTE_FORMAT /**/ +/*#define PRINTF_FORMAT_NULL_OK / **/ +#define HASATTRIBUTE_NORETURN /**/ +#define HASATTRIBUTE_MALLOC /**/ +#define HASATTRIBUTE_NONNULL /**/ +#define HASATTRIBUTE_PURE /**/ +#define HASATTRIBUTE_UNUSED /**/ +#define HASATTRIBUTE_WARN_UNUSED_RESULT /**/ + +/* HASCONST: + * This symbol, if defined, indicates that this C compiler knows about + * the const type. There is no need to actually test for that symbol + * within your programs. The mere use of the "const" keyword will + * trigger the necessary tests. + */ +#define HASCONST /**/ +#ifndef HASCONST +#define const +#endif + +/* HAS_CRYPT: + * This symbol, if defined, indicates that the crypt routine is available + * to encrypt passwords and the like. + */ +/*#define HAS_CRYPT / **/ + +/* HAS_CRYPT_R: + * This symbol, if defined, indicates that the crypt_r routine + * is available to crypt re-entrantly. + */ +/* CRYPT_R_PROTO: + * This symbol encodes the prototype of crypt_r. + * It is zero if d_crypt_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_crypt_r + * is defined. + */ +/*#define HAS_CRYPT_R / **/ +#define CRYPT_R_PROTO 0 /**/ + +/* HAS_CSH: + * This symbol, if defined, indicates that the C-shell exists. + */ +/* CSH: + * This symbol, if defined, contains the full pathname of csh. + */ +/*#define HAS_CSH / **/ +#ifdef HAS_CSH +#define CSH "csh" /**/ +#endif + +/* HAS_CTERMID_R: + * This symbol, if defined, indicates that the ctermid_r routine + * is available to ctermid re-entrantly. + */ +/* CTERMID_R_PROTO: + * This symbol encodes the prototype of ctermid_r. + * It is zero if d_ctermid_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_ctermid_r + * is defined. + */ +/*#define HAS_CTERMID_R / **/ +#define CTERMID_R_PROTO 0 /**/ + +/* HAS_CTIME_R: + * This symbol, if defined, indicates that the ctime_r routine + * is available to ctime re-entrantly. + */ +/* CTIME_R_PROTO: + * This symbol encodes the prototype of ctime_r. + * It is zero if d_ctime_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_ctime_r + * is defined. + */ +/*#define HAS_CTIME_R / **/ +#define CTIME_R_PROTO 0 /**/ + +/* SETUID_SCRIPTS_ARE_SECURE_NOW: + * This symbol, if defined, indicates that the bug that prevents + * setuid scripts from being secure is not present in this kernel. + */ +/* DOSUID: + * This symbol, if defined, indicates that the C program should + * check the script that it is executing for setuid/setgid bits, and + * attempt to emulate setuid/setgid on systems that have disabled + * setuid #! scripts because the kernel can't do it securely. + * It is up to the package designer to make sure that this emulation + * is done securely. Among other things, it should do an fstat on + * the script it just opened to make sure it really is a setuid/setgid + * script, it should make sure the arguments passed correspond exactly + * to the argument on the #! line, and it should not trust any + * subprocesses to which it must pass the filename rather than the + * file descriptor of the script to be executed. + */ +/*#define SETUID_SCRIPTS_ARE_SECURE_NOW / **/ +/*#define DOSUID / **/ + +/* HAS_DRAND48_R: + * This symbol, if defined, indicates that the drand48_r routine + * is available to drand48 re-entrantly. + */ +/* DRAND48_R_PROTO: + * This symbol encodes the prototype of drand48_r. + * It is zero if d_drand48_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_drand48_r + * is defined. + */ +/*#define HAS_DRAND48_R / **/ +#define DRAND48_R_PROTO 0 /**/ + +/* HAS_DRAND48_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the drand48() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern double drand48(void); + */ +#define HAS_DRAND48_PROTO /**/ + +/* HAS_EACCESS: + * This symbol, if defined, indicates that the eaccess routine is + * available to do extended access checks. + */ +/*#define HAS_EACCESS / **/ + +/* HAS_ENDGRENT: + * This symbol, if defined, indicates that the getgrent routine is + * available for finalizing sequential access of the group database. + */ +#define HAS_ENDGRENT /**/ + +/* HAS_ENDGRENT_R: + * This symbol, if defined, indicates that the endgrent_r routine + * is available to endgrent re-entrantly. + */ +/* ENDGRENT_R_PROTO: + * This symbol encodes the prototype of endgrent_r. + * It is zero if d_endgrent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endgrent_r + * is defined. + */ +/*#define HAS_ENDGRENT_R / **/ +#define ENDGRENT_R_PROTO 0 /**/ + +/* HAS_ENDHOSTENT: + * This symbol, if defined, indicates that the endhostent() routine is + * available to close whatever was being used for host queries. + */ +#define HAS_ENDHOSTENT /**/ + +/* HAS_ENDHOSTENT_R: + * This symbol, if defined, indicates that the endhostent_r routine + * is available to endhostent re-entrantly. + */ +/* ENDHOSTENT_R_PROTO: + * This symbol encodes the prototype of endhostent_r. + * It is zero if d_endhostent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endhostent_r + * is defined. + */ +/*#define HAS_ENDHOSTENT_R / **/ +#define ENDHOSTENT_R_PROTO 0 /**/ + +/* HAS_ENDNETENT: + * This symbol, if defined, indicates that the endnetent() routine is + * available to close whatever was being used for network queries. + */ +#define HAS_ENDNETENT /**/ + +/* HAS_ENDNETENT_R: + * This symbol, if defined, indicates that the endnetent_r routine + * is available to endnetent re-entrantly. + */ +/* ENDNETENT_R_PROTO: + * This symbol encodes the prototype of endnetent_r. + * It is zero if d_endnetent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endnetent_r + * is defined. + */ +/*#define HAS_ENDNETENT_R / **/ +#define ENDNETENT_R_PROTO 0 /**/ + +/* HAS_ENDPROTOENT: + * This symbol, if defined, indicates that the endprotoent() routine is + * available to close whatever was being used for protocol queries. + */ +#define HAS_ENDPROTOENT /**/ + +/* HAS_ENDPROTOENT_R: + * This symbol, if defined, indicates that the endprotoent_r routine + * is available to endprotoent re-entrantly. + */ +/* ENDPROTOENT_R_PROTO: + * This symbol encodes the prototype of endprotoent_r. + * It is zero if d_endprotoent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endprotoent_r + * is defined. + */ +/*#define HAS_ENDPROTOENT_R / **/ +#define ENDPROTOENT_R_PROTO 0 /**/ + +/* HAS_ENDPWENT: + * This symbol, if defined, indicates that the getgrent routine is + * available for finalizing sequential access of the passwd database. + */ +#define HAS_ENDPWENT /**/ + +/* HAS_ENDPWENT_R: + * This symbol, if defined, indicates that the endpwent_r routine + * is available to endpwent re-entrantly. + */ +/* ENDPWENT_R_PROTO: + * This symbol encodes the prototype of endpwent_r. + * It is zero if d_endpwent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endpwent_r + * is defined. + */ +/*#define HAS_ENDPWENT_R / **/ +#define ENDPWENT_R_PROTO 0 /**/ + +/* HAS_ENDSERVENT: + * This symbol, if defined, indicates that the endservent() routine is + * available to close whatever was being used for service queries. + */ +#define HAS_ENDSERVENT /**/ + +/* HAS_ENDSERVENT_R: + * This symbol, if defined, indicates that the endservent_r routine + * is available to endservent re-entrantly. + */ +/* ENDSERVENT_R_PROTO: + * This symbol encodes the prototype of endservent_r. + * It is zero if d_endservent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_endservent_r + * is defined. + */ +/*#define HAS_ENDSERVENT_R / **/ +#define ENDSERVENT_R_PROTO 0 /**/ + +/* FLEXFILENAMES: + * This symbol, if defined, indicates that the system supports filenames + * longer than 14 characters. + */ +#define FLEXFILENAMES /**/ + +/* HAS_GETGRENT: + * This symbol, if defined, indicates that the getgrent routine is + * available for sequential access of the group database. + */ +#define HAS_GETGRENT /**/ + +/* HAS_GETGRENT_R: + * This symbol, if defined, indicates that the getgrent_r routine + * is available to getgrent re-entrantly. + */ +/* GETGRENT_R_PROTO: + * This symbol encodes the prototype of getgrent_r. + * It is zero if d_getgrent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getgrent_r + * is defined. + */ +/*#define HAS_GETGRENT_R / **/ +#define GETGRENT_R_PROTO 0 /**/ + +/* HAS_GETGRGID_R: + * This symbol, if defined, indicates that the getgrgid_r routine + * is available to getgrgid re-entrantly. + */ +/* GETGRGID_R_PROTO: + * This symbol encodes the prototype of getgrgid_r. + * It is zero if d_getgrgid_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getgrgid_r + * is defined. + */ +/*#define HAS_GETGRGID_R / **/ +#define GETGRGID_R_PROTO 0 /**/ + +/* HAS_GETGRNAM_R: + * This symbol, if defined, indicates that the getgrnam_r routine + * is available to getgrnam re-entrantly. + */ +/* GETGRNAM_R_PROTO: + * This symbol encodes the prototype of getgrnam_r. + * It is zero if d_getgrnam_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getgrnam_r + * is defined. + */ +/*#define HAS_GETGRNAM_R / **/ +#define GETGRNAM_R_PROTO 0 /**/ + +/* HAS_GETHOSTBYADDR: + * This symbol, if defined, indicates that the gethostbyaddr() routine is + * available to look up hosts by their IP addresses. + */ +#define HAS_GETHOSTBYADDR /**/ + +/* HAS_GETHOSTBYNAME: + * This symbol, if defined, indicates that the gethostbyname() routine is + * available to look up host names in some data base or other. + */ +#define HAS_GETHOSTBYNAME /**/ + +/* HAS_GETHOSTENT: + * This symbol, if defined, indicates that the gethostent() routine is + * available to look up host names in some data base or another. + */ +#define HAS_GETHOSTENT /**/ + +/* HAS_GETHOSTNAME: + * This symbol, if defined, indicates that the C program may use the + * gethostname() routine to derive the host name. See also HAS_UNAME + * and PHOSTNAME. + */ +/* HAS_UNAME: + * This symbol, if defined, indicates that the C program may use the + * uname() routine to derive the host name. See also HAS_GETHOSTNAME + * and PHOSTNAME. + */ +/* PHOSTNAME: + * This symbol, if defined, indicates the command to feed to the + * popen() routine to derive the host name. See also HAS_GETHOSTNAME + * and HAS_UNAME. Note that the command uses a fully qualified path, + * so that it is safe even if used by a process with super-user + * privileges. + */ +/* HAS_PHOSTNAME: + * This symbol, if defined, indicates that the C program may use the + * contents of PHOSTNAME as a command to feed to the popen() routine + * to derive the host name. + */ +#define HAS_GETHOSTNAME /**/ +#define HAS_UNAME /**/ +/*#define HAS_PHOSTNAME / **/ +#ifdef HAS_PHOSTNAME +#define PHOSTNAME "/bin/hostname" /* How to get the host name */ +#endif + +/* HAS_GETHOSTBYADDR_R: + * This symbol, if defined, indicates that the gethostbyaddr_r routine + * is available to gethostbyaddr re-entrantly. + */ +/* GETHOSTBYADDR_R_PROTO: + * This symbol encodes the prototype of gethostbyaddr_r. + * It is zero if d_gethostbyaddr_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_gethostbyaddr_r + * is defined. + */ +/*#define HAS_GETHOSTBYADDR_R / **/ +#define GETHOSTBYADDR_R_PROTO 0 /**/ + +/* HAS_GETHOSTBYNAME_R: + * This symbol, if defined, indicates that the gethostbyname_r routine + * is available to gethostbyname re-entrantly. + */ +/* GETHOSTBYNAME_R_PROTO: + * This symbol encodes the prototype of gethostbyname_r. + * It is zero if d_gethostbyname_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_gethostbyname_r + * is defined. + */ +/*#define HAS_GETHOSTBYNAME_R / **/ +#define GETHOSTBYNAME_R_PROTO 0 /**/ + +/* HAS_GETHOSTENT_R: + * This symbol, if defined, indicates that the gethostent_r routine + * is available to gethostent re-entrantly. + */ +/* GETHOSTENT_R_PROTO: + * This symbol encodes the prototype of gethostent_r. + * It is zero if d_gethostent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_gethostent_r + * is defined. + */ +/*#define HAS_GETHOSTENT_R / **/ +#define GETHOSTENT_R_PROTO 0 /**/ + +/* HAS_GETHOST_PROTOS: + * This symbol, if defined, indicates that includes + * prototypes for gethostent(), gethostbyname(), and + * gethostbyaddr(). Otherwise, it is up to the program to guess + * them. See netdbtype.U for probing for various Netdb_xxx_t types. + */ +#define HAS_GETHOST_PROTOS /**/ + +/* HAS_GETLOGIN_R: + * This symbol, if defined, indicates that the getlogin_r routine + * is available to getlogin re-entrantly. + */ +/* GETLOGIN_R_PROTO: + * This symbol encodes the prototype of getlogin_r. + * It is zero if d_getlogin_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getlogin_r + * is defined. + */ +/*#define HAS_GETLOGIN_R / **/ +#define GETLOGIN_R_PROTO 0 /**/ + +/* HAS_GETNETBYADDR: + * This symbol, if defined, indicates that the getnetbyaddr() routine is + * available to look up networks by their IP addresses. + */ +#define HAS_GETNETBYADDR /**/ + +/* HAS_GETNETBYNAME: + * This symbol, if defined, indicates that the getnetbyname() routine is + * available to look up networks by their names. + */ +#define HAS_GETNETBYNAME /**/ + +/* HAS_GETNETENT: + * This symbol, if defined, indicates that the getnetent() routine is + * available to look up network names in some data base or another. + */ +#define HAS_GETNETENT /**/ + +/* HAS_GETNETBYADDR_R: + * This symbol, if defined, indicates that the getnetbyaddr_r routine + * is available to getnetbyaddr re-entrantly. + */ +/* GETNETBYADDR_R_PROTO: + * This symbol encodes the prototype of getnetbyaddr_r. + * It is zero if d_getnetbyaddr_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getnetbyaddr_r + * is defined. + */ +/*#define HAS_GETNETBYADDR_R / **/ +#define GETNETBYADDR_R_PROTO 0 /**/ + +/* HAS_GETNETBYNAME_R: + * This symbol, if defined, indicates that the getnetbyname_r routine + * is available to getnetbyname re-entrantly. + */ +/* GETNETBYNAME_R_PROTO: + * This symbol encodes the prototype of getnetbyname_r. + * It is zero if d_getnetbyname_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getnetbyname_r + * is defined. + */ +/*#define HAS_GETNETBYNAME_R / **/ +#define GETNETBYNAME_R_PROTO 0 /**/ + +/* HAS_GETNETENT_R: + * This symbol, if defined, indicates that the getnetent_r routine + * is available to getnetent re-entrantly. + */ +/* GETNETENT_R_PROTO: + * This symbol encodes the prototype of getnetent_r. + * It is zero if d_getnetent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getnetent_r + * is defined. + */ +/*#define HAS_GETNETENT_R / **/ +#define GETNETENT_R_PROTO 0 /**/ + +/* HAS_GETNET_PROTOS: + * This symbol, if defined, indicates that includes + * prototypes for getnetent(), getnetbyname(), and + * getnetbyaddr(). Otherwise, it is up to the program to guess + * them. See netdbtype.U for probing for various Netdb_xxx_t types. + */ +#define HAS_GETNET_PROTOS /**/ + +/* HAS_GETPROTOENT: + * This symbol, if defined, indicates that the getprotoent() routine is + * available to look up protocols in some data base or another. + */ +#define HAS_GETPROTOENT /**/ + +/* HAS_GETPGRP: + * This symbol, if defined, indicates that the getpgrp routine is + * available to get the current process group. + */ +/* USE_BSD_GETPGRP: + * This symbol, if defined, indicates that getpgrp needs one + * arguments whereas USG one needs none. + */ +#define HAS_GETPGRP /**/ +/*#define USE_BSD_GETPGRP / **/ + +/* HAS_GETPROTOBYNAME: + * This symbol, if defined, indicates that the getprotobyname() + * routine is available to look up protocols by their name. + */ +/* HAS_GETPROTOBYNUMBER: + * This symbol, if defined, indicates that the getprotobynumber() + * routine is available to look up protocols by their number. + */ +#define HAS_GETPROTOBYNAME /**/ +#define HAS_GETPROTOBYNUMBER /**/ + +/* HAS_GETPROTOBYNAME_R: + * This symbol, if defined, indicates that the getprotobyname_r routine + * is available to getprotobyname re-entrantly. + */ +/* GETPROTOBYNAME_R_PROTO: + * This symbol encodes the prototype of getprotobyname_r. + * It is zero if d_getprotobyname_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getprotobyname_r + * is defined. + */ +/*#define HAS_GETPROTOBYNAME_R / **/ +#define GETPROTOBYNAME_R_PROTO 0 /**/ + +/* HAS_GETPROTOBYNUMBER_R: + * This symbol, if defined, indicates that the getprotobynumber_r routine + * is available to getprotobynumber re-entrantly. + */ +/* GETPROTOBYNUMBER_R_PROTO: + * This symbol encodes the prototype of getprotobynumber_r. + * It is zero if d_getprotobynumber_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getprotobynumber_r + * is defined. + */ +/*#define HAS_GETPROTOBYNUMBER_R / **/ +#define GETPROTOBYNUMBER_R_PROTO 0 /**/ + +/* HAS_GETPROTOENT_R: + * This symbol, if defined, indicates that the getprotoent_r routine + * is available to getprotoent re-entrantly. + */ +/* GETPROTOENT_R_PROTO: + * This symbol encodes the prototype of getprotoent_r. + * It is zero if d_getprotoent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getprotoent_r + * is defined. + */ +/*#define HAS_GETPROTOENT_R / **/ +#define GETPROTOENT_R_PROTO 0 /**/ + +/* HAS_GETPROTO_PROTOS: + * This symbol, if defined, indicates that includes + * prototypes for getprotoent(), getprotobyname(), and + * getprotobyaddr(). Otherwise, it is up to the program to guess + * them. See netdbtype.U for probing for various Netdb_xxx_t types. + */ +#define HAS_GETPROTO_PROTOS /**/ + +/* HAS_GETPWENT: + * This symbol, if defined, indicates that the getpwent routine is + * available for sequential access of the passwd database. + * If this is not available, the older getpw() function may be available. + */ +#define HAS_GETPWENT /**/ + +/* HAS_GETPWENT_R: + * This symbol, if defined, indicates that the getpwent_r routine + * is available to getpwent re-entrantly. + */ +/* GETPWENT_R_PROTO: + * This symbol encodes the prototype of getpwent_r. + * It is zero if d_getpwent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getpwent_r + * is defined. + */ +/*#define HAS_GETPWENT_R / **/ +#define GETPWENT_R_PROTO 0 /**/ + +/* HAS_GETPWNAM_R: + * This symbol, if defined, indicates that the getpwnam_r routine + * is available to getpwnam re-entrantly. + */ +/* GETPWNAM_R_PROTO: + * This symbol encodes the prototype of getpwnam_r. + * It is zero if d_getpwnam_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getpwnam_r + * is defined. + */ +/*#define HAS_GETPWNAM_R / **/ +#define GETPWNAM_R_PROTO 0 /**/ + +/* HAS_GETPWUID_R: + * This symbol, if defined, indicates that the getpwuid_r routine + * is available to getpwuid re-entrantly. + */ +/* GETPWUID_R_PROTO: + * This symbol encodes the prototype of getpwuid_r. + * It is zero if d_getpwuid_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getpwuid_r + * is defined. + */ +/*#define HAS_GETPWUID_R / **/ +#define GETPWUID_R_PROTO 0 /**/ + +/* HAS_GETSERVENT: + * This symbol, if defined, indicates that the getservent() routine is + * available to look up network services in some data base or another. + */ +#define HAS_GETSERVENT /**/ + +/* HAS_GETSERVBYNAME_R: + * This symbol, if defined, indicates that the getservbyname_r routine + * is available to getservbyname re-entrantly. + */ +/* GETSERVBYNAME_R_PROTO: + * This symbol encodes the prototype of getservbyname_r. + * It is zero if d_getservbyname_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getservbyname_r + * is defined. + */ +/*#define HAS_GETSERVBYNAME_R / **/ +#define GETSERVBYNAME_R_PROTO 0 /**/ + +/* HAS_GETSERVBYPORT_R: + * This symbol, if defined, indicates that the getservbyport_r routine + * is available to getservbyport re-entrantly. + */ +/* GETSERVBYPORT_R_PROTO: + * This symbol encodes the prototype of getservbyport_r. + * It is zero if d_getservbyport_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getservbyport_r + * is defined. + */ +/*#define HAS_GETSERVBYPORT_R / **/ +#define GETSERVBYPORT_R_PROTO 0 /**/ + +/* HAS_GETSERVENT_R: + * This symbol, if defined, indicates that the getservent_r routine + * is available to getservent re-entrantly. + */ +/* GETSERVENT_R_PROTO: + * This symbol encodes the prototype of getservent_r. + * It is zero if d_getservent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getservent_r + * is defined. + */ +/*#define HAS_GETSERVENT_R / **/ +#define GETSERVENT_R_PROTO 0 /**/ + +/* HAS_GETSERV_PROTOS: + * This symbol, if defined, indicates that includes + * prototypes for getservent(), getservbyname(), and + * getservbyaddr(). Otherwise, it is up to the program to guess + * them. See netdbtype.U for probing for various Netdb_xxx_t types. + */ +#define HAS_GETSERV_PROTOS /**/ + +/* HAS_GETSPNAM_R: + * This symbol, if defined, indicates that the getspnam_r routine + * is available to getspnam re-entrantly. + */ +/* GETSPNAM_R_PROTO: + * This symbol encodes the prototype of getspnam_r. + * It is zero if d_getspnam_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_getspnam_r + * is defined. + */ +/*#define HAS_GETSPNAM_R / **/ +#define GETSPNAM_R_PROTO 0 /**/ + +/* HAS_GETSERVBYNAME: + * This symbol, if defined, indicates that the getservbyname() + * routine is available to look up services by their name. + */ +/* HAS_GETSERVBYPORT: + * This symbol, if defined, indicates that the getservbyport() + * routine is available to look up services by their port. + */ +#define HAS_GETSERVBYNAME /**/ +#define HAS_GETSERVBYPORT /**/ + +/* HAS_GMTIME_R: + * This symbol, if defined, indicates that the gmtime_r routine + * is available to gmtime re-entrantly. + */ +/* GMTIME_R_PROTO: + * This symbol encodes the prototype of gmtime_r. + * It is zero if d_gmtime_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_gmtime_r + * is defined. + */ +/*#define HAS_GMTIME_R / **/ +#define GMTIME_R_PROTO 0 /**/ + +/* HAS_HTONL: + * This symbol, if defined, indicates that the htonl() routine (and + * friends htons() ntohl() ntohs()) are available to do network + * order byte swapping. + */ +/* HAS_HTONS: + * This symbol, if defined, indicates that the htons() routine (and + * friends htonl() ntohl() ntohs()) are available to do network + * order byte swapping. + */ +/* HAS_NTOHL: + * This symbol, if defined, indicates that the ntohl() routine (and + * friends htonl() htons() ntohs()) are available to do network + * order byte swapping. + */ +/* HAS_NTOHS: + * This symbol, if defined, indicates that the ntohs() routine (and + * friends htonl() htons() ntohl()) are available to do network + * order byte swapping. + */ +#define HAS_HTONL /**/ +#define HAS_HTONS /**/ +#define HAS_NTOHL /**/ +#define HAS_NTOHS /**/ + +/* HAS_LOCALTIME_R: + * This symbol, if defined, indicates that the localtime_r routine + * is available to localtime re-entrantly. + */ +/* LOCALTIME_R_NEEDS_TZSET: + * Many libc's localtime_r implementations do not call tzset, + * making them differ from localtime(), and making timezone + * changes using $ENV{TZ} without explicitly calling tzset + * impossible. This symbol makes us call tzset before localtime_r + */ +/*#define LOCALTIME_R_NEEDS_TZSET / **/ +#ifdef LOCALTIME_R_NEEDS_TZSET +#define L_R_TZSET tzset(), +#else +#define L_R_TZSET +#endif + +/* LOCALTIME_R_PROTO: + * This symbol encodes the prototype of localtime_r. + * It is zero if d_localtime_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_localtime_r + * is defined. + */ +/*#define HAS_LOCALTIME_R / **/ +#define LOCALTIME_R_PROTO 0 /**/ + +/* HAS_LONG_DOUBLE: + * This symbol will be defined if the C compiler supports long + * doubles. + */ +/* LONG_DOUBLESIZE: + * This symbol contains the size of a long double, so that the + * C preprocessor can make decisions based on it. It is only + * defined if the system supports long doubles. + */ +#define HAS_LONG_DOUBLE /**/ +#ifdef HAS_LONG_DOUBLE +#define LONG_DOUBLESIZE 12 /**/ +#endif + +/* HAS_LONG_LONG: + * This symbol will be defined if the C compiler supports long long. + */ +/* LONGLONGSIZE: + * This symbol contains the size of a long long, so that the + * C preprocessor can make decisions based on it. It is only + * defined if the system supports long long. + */ +#define HAS_LONG_LONG /**/ +#ifdef HAS_LONG_LONG +#define LONGLONGSIZE 8 /**/ +#endif + +/* HAS_LSEEK_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the lseek() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern off_t lseek(int, off_t, int); + */ +#define HAS_LSEEK_PROTO /**/ + +/* HAS_MEMCHR: + * This symbol, if defined, indicates that the memchr routine is available + * to locate characters within a C string. + */ +#define HAS_MEMCHR /**/ + +/* HAS_MKSTEMP: + * This symbol, if defined, indicates that the mkstemp routine is + * available to exclusively create and open a uniquely named + * temporary file. + */ +#define HAS_MKSTEMP /**/ + +/* HAS_MMAP: + * This symbol, if defined, indicates that the mmap system call is + * available to map a file into memory. + */ +/* Mmap_t: + * This symbol holds the return type of the mmap() system call + * (and simultaneously the type of the first argument). + * Usually set to 'void *' or 'caddr_t'. + */ +#define HAS_MMAP /**/ +#define Mmap_t void * /**/ + +/* HAS_MSG: + * This symbol, if defined, indicates that the entire msg*(2) library is + * supported (IPC mechanism based on message queues). + */ +#define HAS_MSG /**/ + +/* HAS_POLL: + * This symbol, if defined, indicates that the poll routine is + * available to poll active file descriptors. You may safely + * include when both this symbol *and* I_POLL are defined. + */ +#define HAS_POLL /**/ + +/* OLD_PTHREAD_CREATE_JOINABLE: + * This symbol, if defined, indicates how to create pthread + * in joinable (aka undetached) state. NOTE: not defined + * if pthread.h already has defined PTHREAD_CREATE_JOINABLE + * (the new version of the constant). + * If defined, known values are PTHREAD_CREATE_UNDETACHED + * and __UNDETACHED. + */ +/*#define OLD_PTHREAD_CREATE_JOINABLE / **/ + +/* HAS_PTHREAD_ATFORK: + * This symbol, if defined, indicates that the pthread_atfork routine + * is available to setup fork handlers. + */ +/*#define HAS_PTHREAD_ATFORK / **/ + +/* HAS_PTHREAD_YIELD: + * This symbol, if defined, indicates that the pthread_yield + * routine is available to yield the execution of the current + * thread. sched_yield is preferable to pthread_yield. + */ +/* SCHED_YIELD: + * This symbol defines the way to yield the execution of + * the current thread. Known ways are sched_yield, + * pthread_yield, and pthread_yield with NULL. + */ +/* HAS_SCHED_YIELD: + * This symbol, if defined, indicates that the sched_yield + * routine is available to yield the execution of the current + * thread. sched_yield is preferable to pthread_yield. + */ +/*#define HAS_PTHREAD_YIELD / **/ +#define SCHED_YIELD sched_yield() /**/ +#define HAS_SCHED_YIELD /**/ + +/* HAS_RANDOM_R: + * This symbol, if defined, indicates that the random_r routine + * is available to random re-entrantly. + */ +/* RANDOM_R_PROTO: + * This symbol encodes the prototype of random_r. + * It is zero if d_random_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_random_r + * is defined. + */ +/*#define HAS_RANDOM_R / **/ +#define RANDOM_R_PROTO 0 /**/ + +/* HAS_READDIR64_R: + * This symbol, if defined, indicates that the readdir64_r routine + * is available to readdir64 re-entrantly. + */ +/* READDIR64_R_PROTO: + * This symbol encodes the prototype of readdir64_r. + * It is zero if d_readdir64_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_readdir64_r + * is defined. + */ +/*#define HAS_READDIR64_R / **/ +#define READDIR64_R_PROTO 0 /**/ + +/* HAS_READDIR_R: + * This symbol, if defined, indicates that the readdir_r routine + * is available to readdir re-entrantly. + */ +/* READDIR_R_PROTO: + * This symbol encodes the prototype of readdir_r. + * It is zero if d_readdir_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_readdir_r + * is defined. + */ +/*#define HAS_READDIR_R / **/ +#define READDIR_R_PROTO 0 /**/ + +/* HAS_SEM: + * This symbol, if defined, indicates that the entire sem*(2) library is + * supported. + */ +#define HAS_SEM /**/ + +/* HAS_SETGRENT: + * This symbol, if defined, indicates that the setgrent routine is + * available for initializing sequential access of the group database. + */ +#define HAS_SETGRENT /**/ + +/* HAS_SETGRENT_R: + * This symbol, if defined, indicates that the setgrent_r routine + * is available to setgrent re-entrantly. + */ +/* SETGRENT_R_PROTO: + * This symbol encodes the prototype of setgrent_r. + * It is zero if d_setgrent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setgrent_r + * is defined. + */ +/*#define HAS_SETGRENT_R / **/ +#define SETGRENT_R_PROTO 0 /**/ + +/* HAS_SETGROUPS: + * This symbol, if defined, indicates that the setgroups() routine is + * available to set the list of process groups. If unavailable, multiple + * groups are probably not supported. + */ +#define HAS_SETGROUPS /**/ + +/* HAS_SETHOSTENT: + * This symbol, if defined, indicates that the sethostent() routine is + * available. + */ +#define HAS_SETHOSTENT /**/ + +/* HAS_SETHOSTENT_R: + * This symbol, if defined, indicates that the sethostent_r routine + * is available to sethostent re-entrantly. + */ +/* SETHOSTENT_R_PROTO: + * This symbol encodes the prototype of sethostent_r. + * It is zero if d_sethostent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_sethostent_r + * is defined. + */ +/*#define HAS_SETHOSTENT_R / **/ +#define SETHOSTENT_R_PROTO 0 /**/ + +/* HAS_SETLOCALE_R: + * This symbol, if defined, indicates that the setlocale_r routine + * is available to setlocale re-entrantly. + */ +/* SETLOCALE_R_PROTO: + * This symbol encodes the prototype of setlocale_r. + * It is zero if d_setlocale_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setlocale_r + * is defined. + */ +/*#define HAS_SETLOCALE_R / **/ +#define SETLOCALE_R_PROTO 0 /**/ + +/* HAS_SETNETENT: + * This symbol, if defined, indicates that the setnetent() routine is + * available. + */ +#define HAS_SETNETENT /**/ + +/* HAS_SETNETENT_R: + * This symbol, if defined, indicates that the setnetent_r routine + * is available to setnetent re-entrantly. + */ +/* SETNETENT_R_PROTO: + * This symbol encodes the prototype of setnetent_r. + * It is zero if d_setnetent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setnetent_r + * is defined. + */ +/*#define HAS_SETNETENT_R / **/ +#define SETNETENT_R_PROTO 0 /**/ + +/* HAS_SETPROTOENT: + * This symbol, if defined, indicates that the setprotoent() routine is + * available. + */ +#define HAS_SETPROTOENT /**/ + +/* HAS_SETPGRP: + * This symbol, if defined, indicates that the setpgrp routine is + * available to set the current process group. + */ +/* USE_BSD_SETPGRP: + * This symbol, if defined, indicates that setpgrp needs two + * arguments whereas USG one needs none. See also HAS_SETPGID + * for a POSIX interface. + */ +#define HAS_SETPGRP /**/ +/*#define USE_BSD_SETPGRP / **/ + +/* HAS_SETPROTOENT_R: + * This symbol, if defined, indicates that the setprotoent_r routine + * is available to setprotoent re-entrantly. + */ +/* SETPROTOENT_R_PROTO: + * This symbol encodes the prototype of setprotoent_r. + * It is zero if d_setprotoent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setprotoent_r + * is defined. + */ +/*#define HAS_SETPROTOENT_R / **/ +#define SETPROTOENT_R_PROTO 0 /**/ + +/* HAS_SETPWENT: + * This symbol, if defined, indicates that the setpwent routine is + * available for initializing sequential access of the passwd database. + */ +#define HAS_SETPWENT /**/ + +/* HAS_SETPWENT_R: + * This symbol, if defined, indicates that the setpwent_r routine + * is available to setpwent re-entrantly. + */ +/* SETPWENT_R_PROTO: + * This symbol encodes the prototype of setpwent_r. + * It is zero if d_setpwent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setpwent_r + * is defined. + */ +/*#define HAS_SETPWENT_R / **/ +#define SETPWENT_R_PROTO 0 /**/ + +/* HAS_SETSERVENT: + * This symbol, if defined, indicates that the setservent() routine is + * available. + */ +#define HAS_SETSERVENT /**/ + +/* HAS_SETSERVENT_R: + * This symbol, if defined, indicates that the setservent_r routine + * is available to setservent re-entrantly. + */ +/* SETSERVENT_R_PROTO: + * This symbol encodes the prototype of setservent_r. + * It is zero if d_setservent_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_setservent_r + * is defined. + */ +/*#define HAS_SETSERVENT_R / **/ +#define SETSERVENT_R_PROTO 0 /**/ + +/* HAS_SETVBUF: + * This symbol, if defined, indicates that the setvbuf routine is + * available to change buffering on an open stdio stream. + * to a line-buffered mode. + */ +#define HAS_SETVBUF /**/ + +/* HAS_SHM: + * This symbol, if defined, indicates that the entire shm*(2) library is + * supported. + */ +#define HAS_SHM /**/ + +/* Shmat_t: + * This symbol holds the return type of the shmat() system call. + * Usually set to 'void *' or 'char *'. + */ +/* HAS_SHMAT_PROTOTYPE: + * This symbol, if defined, indicates that the sys/shm.h includes + * a prototype for shmat(). Otherwise, it is up to the program to + * guess one. Shmat_t shmat(int, Shmat_t, int) is a good guess, + * but not always right so it should be emitted by the program only + * when HAS_SHMAT_PROTOTYPE is not defined to avoid conflicting defs. + */ +#define Shmat_t void * /**/ +#define HAS_SHMAT_PROTOTYPE /**/ + +/* HAS_SOCKET: + * This symbol, if defined, indicates that the BSD socket interface is + * supported. + */ +/* HAS_SOCKETPAIR: + * This symbol, if defined, indicates that the BSD socketpair() call is + * supported. + */ +/* HAS_MSG_CTRUNC: + * This symbol, if defined, indicates that the MSG_CTRUNC is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +/* HAS_MSG_DONTROUTE: + * This symbol, if defined, indicates that the MSG_DONTROUTE is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +/* HAS_MSG_OOB: + * This symbol, if defined, indicates that the MSG_OOB is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +/* HAS_MSG_PEEK: + * This symbol, if defined, indicates that the MSG_PEEK is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +/* HAS_MSG_PROXY: + * This symbol, if defined, indicates that the MSG_PROXY is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +/* HAS_SCM_RIGHTS: + * This symbol, if defined, indicates that the SCM_RIGHTS is supported. + * Checking just with #ifdef might not be enough because this symbol + * has been known to be an enum. + */ +#define HAS_SOCKET /**/ +#define HAS_SOCKETPAIR /**/ +#define HAS_MSG_CTRUNC /**/ +#define HAS_MSG_DONTROUTE /**/ +#define HAS_MSG_OOB /**/ +#define HAS_MSG_PEEK /**/ +#define HAS_MSG_PROXY /**/ +#define HAS_SCM_RIGHTS /**/ + +/* HAS_SRAND48_R: + * This symbol, if defined, indicates that the srand48_r routine + * is available to srand48 re-entrantly. + */ +/* SRAND48_R_PROTO: + * This symbol encodes the prototype of srand48_r. + * It is zero if d_srand48_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_srand48_r + * is defined. + */ +/*#define HAS_SRAND48_R / **/ +#define SRAND48_R_PROTO 0 /**/ + +/* HAS_SRANDOM_R: + * This symbol, if defined, indicates that the srandom_r routine + * is available to srandom re-entrantly. + */ +/* SRANDOM_R_PROTO: + * This symbol encodes the prototype of srandom_r. + * It is zero if d_srandom_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_srandom_r + * is defined. + */ +/*#define HAS_SRANDOM_R / **/ +#define SRANDOM_R_PROTO 0 /**/ + +/* USE_STAT_BLOCKS: + * This symbol is defined if this system has a stat structure declaring + * st_blksize and st_blocks. + */ +#ifndef USE_STAT_BLOCKS +#define USE_STAT_BLOCKS /**/ +#endif + +/* USE_STRUCT_COPY: + * This symbol, if defined, indicates that this C compiler knows how + * to copy structures. If undefined, you'll need to use a block copy + * routine of some sort instead. + */ +#define USE_STRUCT_COPY /**/ + +/* HAS_STRERROR: + * This symbol, if defined, indicates that the strerror routine is + * available to translate error numbers to strings. See the writeup + * of Strerror() in this file before you try to define your own. + */ +/* HAS_SYS_ERRLIST: + * This symbol, if defined, indicates that the sys_errlist array is + * available to translate error numbers to strings. The extern int + * sys_nerr gives the size of that table. + */ +/* Strerror: + * This preprocessor symbol is defined as a macro if strerror() is + * not available to translate error numbers to strings but sys_errlist[] + * array is there. + */ +#define HAS_STRERROR /**/ +/*#define HAS_SYS_ERRLIST / **/ +#define Strerror(e) strerror(e) + +/* HAS_STRERROR_R: + * This symbol, if defined, indicates that the strerror_r routine + * is available to strerror re-entrantly. + */ +/* STRERROR_R_PROTO: + * This symbol encodes the prototype of strerror_r. + * It is zero if d_strerror_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_strerror_r + * is defined. + */ +/*#define HAS_STRERROR_R / **/ +#define STRERROR_R_PROTO 0 /**/ + +/* HAS_STRTOUL: + * This symbol, if defined, indicates that the strtoul routine is + * available to provide conversion of strings to unsigned long. + */ +#define HAS_STRTOUL /**/ + +/* HAS_TIME: + * This symbol, if defined, indicates that the time() routine exists. + */ +/* Time_t: + * This symbol holds the type returned by time(). It can be long, + * or time_t on BSD sites (in which case should be + * included). + */ +#define HAS_TIME /**/ +#define Time_t time_t /* Time type */ + +/* HAS_TIMES: + * This symbol, if defined, indicates that the times() routine exists. + * Note that this became obsolete on some systems (SUNOS), which now + * use getrusage(). It may be necessary to include . + */ +#define HAS_TIMES /**/ + +/* HAS_TMPNAM_R: + * This symbol, if defined, indicates that the tmpnam_r routine + * is available to tmpnam re-entrantly. + */ +/* TMPNAM_R_PROTO: + * This symbol encodes the prototype of tmpnam_r. + * It is zero if d_tmpnam_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_tmpnam_r + * is defined. + */ +/*#define HAS_TMPNAM_R / **/ +#define TMPNAM_R_PROTO 0 /**/ + +/* HAS_TTYNAME_R: + * This symbol, if defined, indicates that the ttyname_r routine + * is available to ttyname re-entrantly. + */ +/* TTYNAME_R_PROTO: + * This symbol encodes the prototype of ttyname_r. + * It is zero if d_ttyname_r is undef, and one of the + * REENTRANT_PROTO_T_ABC macros of reentr.h if d_ttyname_r + * is defined. + */ +/*#define HAS_TTYNAME_R / **/ +#define TTYNAME_R_PROTO 0 /**/ + +/* HAS_UNION_SEMUN: + * This symbol, if defined, indicates that the union semun is + * defined by including . If not, the user code + * probably needs to define it as: + * union semun { + * int val; + * struct semid_ds *buf; + * unsigned short *array; + * } + */ +/* USE_SEMCTL_SEMUN: + * This symbol, if defined, indicates that union semun is + * used for semctl IPC_STAT. + */ +/* USE_SEMCTL_SEMID_DS: + * This symbol, if defined, indicates that struct semid_ds * is + * used for semctl IPC_STAT. + */ +/*#define HAS_UNION_SEMUN / **/ +#define USE_SEMCTL_SEMUN /**/ +#define USE_SEMCTL_SEMID_DS /**/ + +/* HAS_VFORK: + * This symbol, if defined, indicates that vfork() exists. + */ +/*#define HAS_VFORK / **/ + +/* HAS_PSEUDOFORK: + * This symbol, if defined, indicates that an emulation of the + * fork routine is available. + */ +/*#define HAS_PSEUDOFORK / **/ + +/* Signal_t: + * This symbol's value is either "void" or "int", corresponding to the + * appropriate return type of a signal handler. Thus, you can declare + * a signal handler using "Signal_t (*handler)()", and define the + * handler using "Signal_t handler(sig)". + */ +#define Signal_t void /* Signal handler's return type */ + +/* HASVOLATILE: + * This symbol, if defined, indicates that this C compiler knows about + * the volatile declaration. + */ +#define HASVOLATILE /**/ +#ifndef HASVOLATILE +#define volatile +#endif + +/* Fpos_t: + * This symbol holds the type used to declare file positions in libc. + * It can be fpos_t, long, uint, etc... It may be necessary to include + * to get any typedef'ed information. + */ +#define Fpos_t fpos_t /* File position type */ + +/* Gid_t_f: + * This symbol defines the format string used for printing a Gid_t. + */ +#define Gid_t_f "lu" /**/ + +/* Gid_t_sign: + * This symbol holds the signedess of a Gid_t. + * 1 for unsigned, -1 for signed. + */ +#define Gid_t_sign 1 /* GID sign */ + +/* Gid_t_size: + * This symbol holds the size of a Gid_t in bytes. + */ +#define Gid_t_size 4 /* GID size */ + +/* Gid_t: + * This symbol holds the return type of getgid() and the type of + * argument to setrgid() and related functions. Typically, + * it is the type of group ids in the kernel. It can be int, ushort, + * gid_t, etc... It may be necessary to include to get + * any typedef'ed information. + */ +#define Gid_t gid_t /* Type for getgid(), etc... */ + +/* Groups_t: + * This symbol holds the type used for the second argument to + * getgroups() and setgroups(). Usually, this is the same as + * gidtype (gid_t) , but sometimes it isn't. + * It can be int, ushort, gid_t, etc... + * It may be necessary to include to get any + * typedef'ed information. This is only required if you have + * getgroups() or setgroups().. + */ +#if defined(HAS_GETGROUPS) || defined(HAS_SETGROUPS) +#define Groups_t gid_t /* Type for 2nd arg to [sg]etgroups() */ +#endif + +/* I_DIRENT: + * This symbol, if defined, indicates to the C program that it should + * include . Using this symbol also triggers the definition + * of the Direntry_t define which ends up being 'struct dirent' or + * 'struct direct' depending on the availability of . + */ +/* DIRNAMLEN: + * This symbol, if defined, indicates to the C program that the length + * of directory entry names is provided by a d_namlen field. Otherwise + * you need to do strlen() on the d_name field. + */ +/* Direntry_t: + * This symbol is set to 'struct direct' or 'struct dirent' depending on + * whether dirent is available or not. You should use this pseudo type to + * portably declare your directory entries. + */ +#define I_DIRENT /**/ +/*#define DIRNAMLEN / **/ +#define Direntry_t struct dirent + +/* I_GRP: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/* GRPASSWD: + * This symbol, if defined, indicates to the C program that struct group + * in contains gr_passwd. + */ +#define I_GRP /**/ +#define GRPASSWD /**/ + +/* I_MACH_CTHREADS: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_MACH_CTHREADS / **/ + +/* I_NDBM: + * This symbol, if defined, indicates that exists and should + * be included. + */ +/*#define I_NDBM / **/ + +/* I_NETDB: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_NETDB /**/ + +/* I_PTHREAD: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_PTHREAD /**/ + +/* I_PWD: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/* PWQUOTA: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_quota. + */ +/* PWAGE: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_age. + */ +/* PWCHANGE: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_change. + */ +/* PWCLASS: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_class. + */ +/* PWEXPIRE: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_expire. + */ +/* PWCOMMENT: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_comment. + */ +/* PWGECOS: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_gecos. + */ +/* PWPASSWD: + * This symbol, if defined, indicates to the C program that struct passwd + * contains pw_passwd. + */ +#define I_PWD /**/ +/*#define PWQUOTA / **/ +/*#define PWAGE / **/ +/*#define PWCHANGE / **/ +/*#define PWCLASS / **/ +/*#define PWEXPIRE / **/ +/*#define PWCOMMENT / **/ +#define PWGECOS /**/ +#define PWPASSWD /**/ + +/* I_SYS_ACCESS: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_SYS_ACCESS / **/ + +/* I_SYS_SECURITY: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/*#define I_SYS_SECURITY / **/ + +/* I_SYSUIO: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYSUIO /**/ + +/* I_STDARG: + * This symbol, if defined, indicates that exists and should + * be included. + */ +/* I_VARARGS: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_STDARG /**/ +/*#define I_VARARGS / **/ + +/* PERL_INC_VERSION_LIST: + * This variable specifies the list of subdirectories in over + * which perl.c:incpush() and lib/lib.pm will automatically + * search when adding directories to @INC, in a format suitable + * for a C initialization string. See the inc_version_list entry + * in Porting/Glossary for more details. + */ +/*#define PERL_INC_VERSION_LIST 0 / **/ + +/* INSTALL_USR_BIN_PERL: + * This symbol, if defined, indicates that Perl is to be installed + * also as /usr/bin/perl. + */ +/*#define INSTALL_USR_BIN_PERL / **/ + +/* Off_t: + * This symbol holds the type used to declare offsets in the kernel. + * It can be int, long, off_t, etc... It may be necessary to include + * to get any typedef'ed information. + */ +/* LSEEKSIZE: + * This symbol holds the number of bytes used by the Off_t. + */ +/* Off_t_size: + * This symbol holds the number of bytes used by the Off_t. + */ +#define Off_t off_t /* type */ +#define LSEEKSIZE 8 /* size */ +#define Off_t_size 8 /* size */ + +/* Free_t: + * This variable contains the return type of free(). It is usually + * void, but occasionally int. + */ +/* Malloc_t: + * This symbol is the type of pointer returned by malloc and realloc. + */ +#define Malloc_t void * /**/ +#define Free_t void /**/ + +/* PERL_MALLOC_WRAP: + * This symbol, if defined, indicates that we'd like malloc wrap checks. + */ +/*#define PERL_MALLOC_WRAP / **/ + +/* MYMALLOC: + * This symbol, if defined, indicates that we're using our own malloc. + */ +/*#define MYMALLOC / **/ + +/* Mode_t: + * This symbol holds the type used to declare file modes + * for systems calls. It is usually mode_t, but may be + * int or unsigned short. It may be necessary to include + * to get any typedef'ed information. + */ +#define Mode_t mode_t /* file mode parameter for system calls */ + +/* Netdb_host_t: + * This symbol holds the type used for the 1st argument + * to gethostbyaddr(). + */ +/* Netdb_hlen_t: + * This symbol holds the type used for the 2nd argument + * to gethostbyaddr(). + */ +/* Netdb_name_t: + * This symbol holds the type used for the argument to + * gethostbyname(). + */ +/* Netdb_net_t: + * This symbol holds the type used for the 1st argument to + * getnetbyaddr(). + */ +#define Netdb_host_t char * /**/ +#define Netdb_hlen_t size_t /**/ +#define Netdb_name_t const char * /**/ +#define Netdb_net_t in_addr_t /**/ + +/* PERL_OTHERLIBDIRS: + * This variable contains a colon-separated set of paths for the perl + * binary to search for additional library files or modules. + * These directories will be tacked to the end of @INC. + * Perl will automatically search below each path for version- + * and architecture-specific directories. See PERL_INC_VERSION_LIST + * for more details. + */ +/*#define PERL_OTHERLIBDIRS " " / **/ + +/* Pid_t: + * This symbol holds the type used to declare process ids in the kernel. + * It can be int, uint, pid_t, etc... It may be necessary to include + * to get any typedef'ed information. + */ +#define Pid_t pid_t /* PID type */ + +/* PRIVLIB: + * This symbol contains the name of the private library for this package. + * The library is private in the sense that it needn't be in anyone's + * execution path, but it should be accessible by the world. The program + * should be prepared to do ~ expansion. + */ +/* PRIVLIB_EXP: + * This symbol contains the ~name expanded version of PRIVLIB, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +#define PRIVLIB "/usr/lib/perl5/5.10.0" /**/ +#define PRIVLIB_EXP "/usr/lib/perl5/5.10.0" /**/ + +/* CAN_PROTOTYPE: + * If defined, this macro indicates that the C compiler can handle + * function prototypes. + */ +/* _: + * This macro is used to declare function parameters for folks who want + * to make declarations with prototypes using a different style than + * the above macros. Use double parentheses. For example: + * + * int main _((int argc, char *argv[])); + */ +#define CAN_PROTOTYPE /**/ +#ifdef CAN_PROTOTYPE +#define _(args) args +#else +#define _(args) () +#endif + +/* Select_fd_set_t: + * This symbol holds the type used for the 2nd, 3rd, and 4th + * arguments to select. Usually, this is 'fd_set *', if HAS_FD_SET + * is defined, and 'int *' otherwise. This is only useful if you + * have select(), of course. + */ +#define Select_fd_set_t fd_set * /**/ + +/* SH_PATH: + * This symbol contains the full pathname to the shell used on this + * on this system to execute Bourne shell scripts. Usually, this will be + * /bin/sh, though it's possible that some systems will have /bin/ksh, + * /bin/pdksh, /bin/ash, /bin/bash, or even something such as + * D:/bin/sh.exe. + */ +#define SH_PATH "/bin/sh" /**/ + +/* SIG_NAME: + * This symbol contains a list of signal names in order of + * signal number. This is intended + * to be used as a static array initialization, like this: + * char *sig_name[] = { SIG_NAME }; + * The signals in the list are separated with commas, and each signal + * is surrounded by double quotes. There is no leading SIG in the signal + * name, i.e. SIGQUIT is known as "QUIT". + * Gaps in the signal numbers (up to NSIG) are filled in with NUMnn, + * etc., where nn is the actual signal number (e.g. NUM37). + * The signal number for sig_name[i] is stored in sig_num[i]. + * The last element is 0 to terminate the list with a NULL. This + * corresponds to the 0 at the end of the sig_name_init list. + * Note that this variable is initialized from the sig_name_init, + * not from sig_name (which is unused). + */ +/* SIG_NUM: + * This symbol contains a list of signal numbers, in the same order as the + * SIG_NAME list. It is suitable for static array initialization, as in: + * int sig_num[] = { SIG_NUM }; + * The signals in the list are separated with commas, and the indices + * within that list and the SIG_NAME list match, so it's easy to compute + * the signal name from a number or vice versa at the price of a small + * dynamic linear lookup. + * Duplicates are allowed, but are moved to the end of the list. + * The signal number corresponding to sig_name[i] is sig_number[i]. + * if (i < NSIG) then sig_number[i] == i. + * The last element is 0, corresponding to the 0 at the end of + * the sig_name_init list. + * Note that this variable is initialized from the sig_num_init, + * not from sig_num (which is unused). + */ +/* SIG_SIZE: + * This variable contains the number of elements of the SIG_NAME + * and SIG_NUM arrays, excluding the final NULL entry. + */ +#define SIG_NAME "ZERO", "HUP", "INT", "QUIT", "ILL", "TRAP", "ABRT", "BUS", "FPE", "KILL", "USR1", "SEGV", "USR2", "PIPE", "ALRM", "TERM", "STKFLT", "CHLD", "CONT", "STOP", "TSTP", "TTIN", "TTOU", "URG", "XCPU", "XFSZ", "VTALRM", "PROF", "WINCH", "IO", "PWR", "SYS", "RTMIN", "NUM33", "NUM34", "NUM35", "NUM36", "NUM37", "NUM38", "NUM39", "NUM40", "NUM41", "NUM42", "NUM43", "NUM44", "NUM45", "NUM46", "NUM47", "NUM48", "NUM49", "NUM50", "NUM51", "NUM52", "NUM53", "NUM54", "NUM55", "NUM56", "NUM57", "NUM58", "NUM59", "NUM60", "NUM61", "NUM62", "NUM63", "RTMAX", "CLD", "IOT", "POLL", "UNUSED", 0 /**/ +#define SIG_NUM 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 17, 6, 29, 31, 0 /**/ +#define SIG_SIZE 69 /**/ + +/* SITEARCH: + * This symbol contains the name of the private library for this package. + * The library is private in the sense that it needn't be in anyone's + * execution path, but it should be accessible by the world. The program + * should be prepared to do ~ expansion. + * The standard distribution will put nothing in this directory. + * After perl has been installed, users may install their own local + * architecture-dependent modules in this directory with + * MakeMaker Makefile.PL + * or equivalent. See INSTALL for details. + */ +/* SITEARCH_EXP: + * This symbol contains the ~name expanded version of SITEARCH, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +#define SITEARCH "/usr/lib/perl5/site_perl/5.10.0/i686-linux" /**/ +#define SITEARCH_EXP "/usr/lib/perl5/site_perl/5.10.0/i686-linux" /**/ + +/* SITELIB: + * This symbol contains the name of the private library for this package. + * The library is private in the sense that it needn't be in anyone's + * execution path, but it should be accessible by the world. The program + * should be prepared to do ~ expansion. + * The standard distribution will put nothing in this directory. + * After perl has been installed, users may install their own local + * architecture-independent modules in this directory with + * MakeMaker Makefile.PL + * or equivalent. See INSTALL for details. + */ +/* SITELIB_EXP: + * This symbol contains the ~name expanded version of SITELIB, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +/* SITELIB_STEM: + * This define is SITELIB_EXP with any trailing version-specific component + * removed. The elements in inc_version_list (inc_version_list.U) can + * be tacked onto this variable to generate a list of directories to search. + */ +#define SITELIB "/usr/lib/perl5/site_perl/5.10.0" /**/ +#define SITELIB_EXP "/usr/lib/perl5/site_perl/5.10.0" /**/ +#define SITELIB_STEM "/usr/lib/perl5/site_perl" /**/ + +/* Size_t_size: + * This symbol holds the size of a Size_t in bytes. + */ +#define Size_t_size 4 /* */ + +/* Size_t: + * This symbol holds the type used to declare length parameters + * for string functions. It is usually size_t, but may be + * unsigned long, int, etc. It may be necessary to include + * to get any typedef'ed information. + */ +#define Size_t size_t /* length paramater for string functions */ + +/* Sock_size_t: + * This symbol holds the type used for the size argument of + * various socket calls (just the base type, not the pointer-to). + */ +#define Sock_size_t socklen_t /**/ + +/* STDCHAR: + * This symbol is defined to be the type of char used in stdio.h. + * It has the values "unsigned char" or "char". + */ +#define STDCHAR char /**/ + +/* Uid_t_f: + * This symbol defines the format string used for printing a Uid_t. + */ +#define Uid_t_f "lu" /**/ + +/* Uid_t_sign: + * This symbol holds the signedess of a Uid_t. + * 1 for unsigned, -1 for signed. + */ +#define Uid_t_sign 1 /* UID sign */ + +/* Uid_t_size: + * This symbol holds the size of a Uid_t in bytes. + */ +#define Uid_t_size 4 /* UID size */ + +/* Uid_t: + * This symbol holds the type used to declare user ids in the kernel. + * It can be int, ushort, uid_t, etc... It may be necessary to include + * to get any typedef'ed information. + */ +#define Uid_t uid_t /* UID type */ + +/* USE_ITHREADS: + * This symbol, if defined, indicates that Perl should be built to + * use the interpreter-based threading implementation. + */ +/* USE_5005THREADS: + * This symbol, if defined, indicates that Perl should be built to + * use the 5.005-based threading implementation. + * Only valid up to 5.8.x. + */ +/* OLD_PTHREADS_API: + * This symbol, if defined, indicates that Perl should + * be built to use the old draft POSIX threads API. + */ +/* USE_REENTRANT_API: + * This symbol, if defined, indicates that Perl should + * try to use the various _r versions of library functions. + * This is extremely experimental. + */ +/*#define USE_5005THREADS / **/ +/*#define USE_ITHREADS / **/ +#if defined(USE_5005THREADS) && !defined(USE_ITHREADS) +#define USE_THREADS /* until src is revised*/ +#endif +/*#define OLD_PTHREADS_API / **/ +/*#define USE_REENTRANT_API / **/ + +/* PERL_VENDORARCH: + * If defined, this symbol contains the name of a private library. + * The library is private in the sense that it needn't be in anyone's + * execution path, but it should be accessible by the world. + * It may have a ~ on the front. + * The standard distribution will put nothing in this directory. + * Vendors who distribute perl may wish to place their own + * architecture-dependent modules and extensions in this directory with + * MakeMaker Makefile.PL INSTALLDIRS=vendor + * or equivalent. See INSTALL for details. + */ +/* PERL_VENDORARCH_EXP: + * This symbol contains the ~name expanded version of PERL_VENDORARCH, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +/*#define PERL_VENDORARCH "" / **/ +/*#define PERL_VENDORARCH_EXP "" / **/ + +/* PERL_VENDORLIB_EXP: + * This symbol contains the ~name expanded version of VENDORLIB, to be used + * in programs that are not prepared to deal with ~ expansion at run-time. + */ +/* PERL_VENDORLIB_STEM: + * This define is PERL_VENDORLIB_EXP with any trailing version-specific component + * removed. The elements in inc_version_list (inc_version_list.U) can + * be tacked onto this variable to generate a list of directories to search. + */ +/*#define PERL_VENDORLIB_EXP "" / **/ +/*#define PERL_VENDORLIB_STEM "" / **/ + +/* VOIDFLAGS: + * This symbol indicates how much support of the void type is given by this + * compiler. What various bits mean: + * + * 1 = supports declaration of void + * 2 = supports arrays of pointers to functions returning void + * 4 = supports comparisons between pointers to void functions and + * addresses of void functions + * 8 = suports declaration of generic void pointers + * + * The package designer should define VOIDUSED to indicate the requirements + * of the package. This can be done either by #defining VOIDUSED before + * including config.h, or by defining defvoidused in Myinit.U. If the + * latter approach is taken, only those flags will be tested. If the + * level of void support necessary is not present, defines void to int. + */ +#ifndef VOIDUSED +#define VOIDUSED 15 +#endif +#define VOIDFLAGS 15 +#if (VOIDFLAGS & VOIDUSED) != VOIDUSED +#define void int /* is void to be avoided? */ +#define M_VOID /* Xenix strikes again */ +#endif + +/* USE_CROSS_COMPILE: + * This symbol, if defined, indicates that Perl is being cross-compiled. + */ +/* PERL_TARGETARCH: + * This symbol, if defined, indicates the target architecture + * Perl has been cross-compiled to. Undefined if not a cross-compile. + */ +#ifndef USE_CROSS_COMPILE +/*#define USE_CROSS_COMPILE / **/ +#define PERL_TARGETARCH "" /**/ +#endif + +/* MEM_ALIGNBYTES: + * This symbol contains the number of bytes required to align a + * double, or a long double when applicable. Usual values are 2, + * 4 and 8. The default is eight, for safety. + */ +#if defined(USE_CROSS_COMPILE) || defined(MULTIARCH) +# define MEM_ALIGNBYTES 8 +#else +#define MEM_ALIGNBYTES 4 +#endif + +/* BYTEORDER: + * This symbol holds the hexadecimal constant defined in byteorder, + * in a UV, i.e. 0x1234 or 0x4321 or 0x12345678, etc... + * If the compiler supports cross-compiling or multiple-architecture + * binaries (eg. on NeXT systems), use compiler-defined macros to + * determine the byte order. + * On NeXT 3.2 (and greater), you can build "Fat" Multiple Architecture + * Binaries (MAB) on either big endian or little endian machines. + * The endian-ness is available at compile-time. This only matters + * for perl, where the config.h can be generated and installed on + * one system, and used by a different architecture to build an + * extension. Older versions of NeXT that might not have + * defined either *_ENDIAN__ were all on Motorola 680x0 series, + * so the default case (for NeXT) is big endian to catch them. + * This might matter for NeXT 3.0. + */ +#if defined(USE_CROSS_COMPILE) || defined(MULTIARCH) +# ifdef __LITTLE_ENDIAN__ +# if LONGSIZE == 4 +# define BYTEORDER 0x1234 +# else +# if LONGSIZE == 8 +# define BYTEORDER 0x12345678 +# endif +# endif +# else +# ifdef __BIG_ENDIAN__ +# if LONGSIZE == 4 +# define BYTEORDER 0x4321 +# else +# if LONGSIZE == 8 +# define BYTEORDER 0x87654321 +# endif +# endif +# endif +# endif +# if !defined(BYTEORDER) && (defined(NeXT) || defined(__NeXT__)) +# define BYTEORDER 0x4321 +# endif +#else +#define BYTEORDER 0x1234 /* large digits for MSB */ +#endif /* NeXT */ + +/* CASTI32: + * This symbol is defined if the C compiler can cast negative + * or large floating point numbers to 32-bit ints. + */ +/*#define CASTI32 / **/ + +/* CASTNEGFLOAT: + * This symbol is defined if the C compiler can cast negative + * numbers to unsigned longs, ints and shorts. + */ +/* CASTFLAGS: + * This symbol contains flags that say what difficulties the compiler + * has casting odd floating values to unsigned long: + * 0 = ok + * 1 = couldn't cast < 0 + * 2 = couldn't cast >= 0x80000000 + * 4 = couldn't cast in argument expression list + */ +#define CASTNEGFLOAT /**/ +#define CASTFLAGS 0 /**/ + +/* VOID_CLOSEDIR: + * This symbol, if defined, indicates that the closedir() routine + * does not return a value. + */ +/*#define VOID_CLOSEDIR / **/ + +/* HAS_FD_SET: + * This symbol, when defined, indicates presence of the fd_set typedef + * in + */ +#define HAS_FD_SET /**/ + +/* Gconvert: + * This preprocessor macro is defined to convert a floating point + * number to a string without a trailing decimal point. This + * emulates the behavior of sprintf("%g"), but is sometimes much more + * efficient. If gconvert() is not available, but gcvt() drops the + * trailing decimal point, then gcvt() is used. If all else fails, + * a macro using sprintf("%g") is used. Arguments for the Gconvert + * macro are: value, number of digits, whether trailing zeros should + * be retained, and the output buffer. + * The usual values are: + * d_Gconvert='gconvert((x),(n),(t),(b))' + * d_Gconvert='gcvt((x),(n),(b))' + * d_Gconvert='sprintf((b),"%.*g",(n),(x))' + * The last two assume trailing zeros should not be kept. + */ +#define Gconvert(x,n,t,b) sprintf((b),"%.*g",(n),(x)) + +/* HAS_GETPAGESIZE: + * This symbol, if defined, indicates that the getpagesize system call + * is available to get system page size, which is the granularity of + * many memory management calls. + */ +#define HAS_GETPAGESIZE /**/ + +/* HAS_GNULIBC: + * This symbol, if defined, indicates to the C program that + * the GNU C library is being used. A better check is to use + * the __GLIBC__ and __GLIBC_MINOR__ symbols supplied with glibc. + */ +/*#define HAS_GNULIBC / **/ +#if defined(HAS_GNULIBC) && !defined(_GNU_SOURCE) +# define _GNU_SOURCE +#endif +/* HAS_ISASCII: + * This manifest constant lets the C program know that isascii + * is available. + */ +#define HAS_ISASCII /**/ + +/* HAS_LCHOWN: + * This symbol, if defined, indicates that the lchown routine is + * available to operate on a symbolic link (instead of following the + * link). + */ +#define HAS_LCHOWN /**/ + +/* HAS_OPEN3: + * This manifest constant lets the C program know that the three + * argument form of open(2) is available. + */ +#define HAS_OPEN3 /**/ + +/* HAS_SAFE_BCOPY: + * This symbol, if defined, indicates that the bcopy routine is available + * to copy potentially overlapping memory blocks. Normally, you should + * probably use memmove() or memcpy(). If neither is defined, roll your + * own version. + */ +/*#define HAS_SAFE_BCOPY / **/ + +/* HAS_SAFE_MEMCPY: + * This symbol, if defined, indicates that the memcpy routine is available + * to copy potentially overlapping memory blocks. If you need to + * copy overlapping memory blocks, you should check HAS_MEMMOVE and + * use memmove() instead, if available. + */ +/*#define HAS_SAFE_MEMCPY / **/ + +/* HAS_SANE_MEMCMP: + * This symbol, if defined, indicates that the memcmp routine is available + * and can be used to compare relative magnitudes of chars with their high + * bits set. If it is not defined, roll your own version. + */ +#define HAS_SANE_MEMCMP /**/ + +/* HAS_SIGACTION: + * This symbol, if defined, indicates that Vr4's sigaction() routine + * is available. + */ +#define HAS_SIGACTION /**/ + +/* HAS_SIGSETJMP: + * This variable indicates to the C program that the sigsetjmp() + * routine is available to save the calling process's registers + * and stack environment for later use by siglongjmp(), and + * to optionally save the process's signal mask. See + * Sigjmp_buf, Sigsetjmp, and Siglongjmp. + */ +/* Sigjmp_buf: + * This is the buffer type to be used with Sigsetjmp and Siglongjmp. + */ +/* Sigsetjmp: + * This macro is used in the same way as sigsetjmp(), but will invoke + * traditional setjmp() if sigsetjmp isn't available. + * See HAS_SIGSETJMP. + */ +/* Siglongjmp: + * This macro is used in the same way as siglongjmp(), but will invoke + * traditional longjmp() if siglongjmp isn't available. + * See HAS_SIGSETJMP. + */ +#define HAS_SIGSETJMP /**/ +#ifdef HAS_SIGSETJMP +#define Sigjmp_buf sigjmp_buf +#define Sigsetjmp(buf,save_mask) sigsetjmp((buf),(save_mask)) +#define Siglongjmp(buf,retval) siglongjmp((buf),(retval)) +#else +#define Sigjmp_buf jmp_buf +#define Sigsetjmp(buf,save_mask) setjmp((buf)) +#define Siglongjmp(buf,retval) longjmp((buf),(retval)) +#endif + +/* USE_STDIO_PTR: + * This symbol is defined if the _ptr and _cnt fields (or similar) + * of the stdio FILE structure can be used to access the stdio buffer + * for a file handle. If this is defined, then the FILE_ptr(fp) + * and FILE_cnt(fp) macros will also be defined and should be used + * to access these fields. + */ +/* FILE_ptr: + * This macro is used to access the _ptr field (or equivalent) of the + * FILE structure pointed to by its argument. This macro will always be + * defined if USE_STDIO_PTR is defined. + */ +/* STDIO_PTR_LVALUE: + * This symbol is defined if the FILE_ptr macro can be used as an + * lvalue. + */ +/* FILE_cnt: + * This macro is used to access the _cnt field (or equivalent) of the + * FILE structure pointed to by its argument. This macro will always be + * defined if USE_STDIO_PTR is defined. + */ +/* STDIO_CNT_LVALUE: + * This symbol is defined if the FILE_cnt macro can be used as an + * lvalue. + */ +/* STDIO_PTR_LVAL_SETS_CNT: + * This symbol is defined if using the FILE_ptr macro as an lvalue + * to increase the pointer by n has the side effect of decreasing the + * value of File_cnt(fp) by n. + */ +/* STDIO_PTR_LVAL_NOCHANGE_CNT: + * This symbol is defined if using the FILE_ptr macro as an lvalue + * to increase the pointer by n leaves File_cnt(fp) unchanged. + */ +/*#define USE_STDIO_PTR / **/ +#ifdef USE_STDIO_PTR +#define FILE_ptr(fp) ((fp)->_ptr) +/*#define STDIO_PTR_LVALUE / **/ +#define FILE_cnt(fp) ((fp)->_cnt) +/*#define STDIO_CNT_LVALUE / **/ +/*#define STDIO_PTR_LVAL_SETS_CNT / **/ +/*#define STDIO_PTR_LVAL_NOCHANGE_CNT / **/ +#endif + +/* USE_STDIO_BASE: + * This symbol is defined if the _base field (or similar) of the + * stdio FILE structure can be used to access the stdio buffer for + * a file handle. If this is defined, then the FILE_base(fp) macro + * will also be defined and should be used to access this field. + * Also, the FILE_bufsiz(fp) macro will be defined and should be used + * to determine the number of bytes in the buffer. USE_STDIO_BASE + * will never be defined unless USE_STDIO_PTR is. + */ +/* FILE_base: + * This macro is used to access the _base field (or equivalent) of the + * FILE structure pointed to by its argument. This macro will always be + * defined if USE_STDIO_BASE is defined. + */ +/* FILE_bufsiz: + * This macro is used to determine the number of bytes in the I/O + * buffer pointed to by _base field (or equivalent) of the FILE + * structure pointed to its argument. This macro will always be defined + * if USE_STDIO_BASE is defined. + */ +/*#define USE_STDIO_BASE / **/ +#ifdef USE_STDIO_BASE +#define FILE_base(fp) ((fp)->_base) +#define FILE_bufsiz(fp) ((fp)->_cnt + (fp)->_ptr - (fp)->_base) +#endif + +/* HAS_VPRINTF: + * This symbol, if defined, indicates that the vprintf routine is available + * to printf with a pointer to an argument list. If unavailable, you + * may need to write your own, probably in terms of _doprnt(). + */ +/* USE_CHAR_VSPRINTF: + * This symbol is defined if this system has vsprintf() returning type + * (char*). The trend seems to be to declare it as "int vsprintf()". It + * is up to the package author to declare vsprintf correctly based on the + * symbol. + */ +#define HAS_VPRINTF /**/ +/*#define USE_CHAR_VSPRINTF / **/ + +/* DOUBLESIZE: + * This symbol contains the size of a double, so that the C preprocessor + * can make decisions based on it. + */ +#define DOUBLESIZE 8 /**/ + +/* I_TIME: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/* I_SYS_TIME: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +/* I_SYS_TIME_KERNEL: + * This symbol, if defined, indicates to the C program that it should + * include with KERNEL defined. + */ +/* HAS_TM_TM_ZONE: + * This symbol, if defined, indicates to the C program that + * the struct tm has a tm_zone field. + */ +/* HAS_TM_TM_GMTOFF: + * This symbol, if defined, indicates to the C program that + * the struct tm has a tm_gmtoff field. + */ +#define I_TIME /**/ +#define I_SYS_TIME /**/ +/*#define I_SYS_TIME_KERNEL / **/ +#define HAS_TM_TM_ZONE /**/ +#define HAS_TM_TM_GMTOFF /**/ + +/* VAL_O_NONBLOCK: + * This symbol is to be used during open() or fcntl(F_SETFL) to turn on + * non-blocking I/O for the file descriptor. Note that there is no way + * back, i.e. you cannot turn it blocking again this way. If you wish to + * alternatively switch between blocking and non-blocking, use the + * ioctl(FIOSNBIO) call instead, but that is not supported by all devices. + */ +/* VAL_EAGAIN: + * This symbol holds the errno error code set by read() when no data was + * present on the non-blocking file descriptor. + */ +/* RD_NODATA: + * This symbol holds the return code from read() when no data is present + * on the non-blocking file descriptor. Be careful! If EOF_NONBLOCK is + * not defined, then you can't distinguish between no data and EOF by + * issuing a read(). You'll have to find another way to tell for sure! + */ +/* EOF_NONBLOCK: + * This symbol, if defined, indicates to the C program that a read() on + * a non-blocking file descriptor will return 0 on EOF, and not the value + * held in RD_NODATA (-1 usually, in that case!). + */ +#define VAL_O_NONBLOCK O_NONBLOCK +#define VAL_EAGAIN EAGAIN +#define RD_NODATA -1 +#define EOF_NONBLOCK + +/* PTRSIZE: + * This symbol contains the size of a pointer, so that the C preprocessor + * can make decisions based on it. It will be sizeof(void *) if + * the compiler supports (void *); otherwise it will be + * sizeof(char *). + */ +#define PTRSIZE 4 /**/ + +/* Drand01: + * This macro is to be used to generate uniformly distributed + * random numbers over the range [0., 1.[. You may have to supply + * an 'extern double drand48();' in your program since SunOS 4.1.3 + * doesn't provide you with anything relevant in its headers. + * See HAS_DRAND48_PROTO. + */ +/* Rand_seed_t: + * This symbol defines the type of the argument of the + * random seed function. + */ +/* seedDrand01: + * This symbol defines the macro to be used in seeding the + * random number generator (see Drand01). + */ +/* RANDBITS: + * This symbol indicates how many bits are produced by the + * function used to generate normalized random numbers. + * Values include 15, 16, 31, and 48. + */ +#define Drand01() drand48() /**/ +#define Rand_seed_t long /**/ +#define seedDrand01(x) srand48((Rand_seed_t)x) /**/ +#define RANDBITS 48 /**/ + +/* SSize_t: + * This symbol holds the type used by functions that return + * a count of bytes or an error condition. It must be a signed type. + * It is usually ssize_t, but may be long or int, etc. + * It may be necessary to include or + * to get any typedef'ed information. + * We will pick a type such that sizeof(SSize_t) == sizeof(Size_t). + */ +#define SSize_t ssize_t /* signed count of bytes */ + +/* EBCDIC: + * This symbol, if defined, indicates that this system uses + * EBCDIC encoding. + */ +/*#define EBCDIC / **/ + +/* HAS_ATOLF: + * This symbol, if defined, indicates that the atolf routine is + * available to convert strings into long doubles. + */ +/*#define HAS_ATOLF / **/ + +/* HAS_ATOLL: + * This symbol, if defined, indicates that the atoll routine is + * available to convert strings into long longs. + */ +#define HAS_ATOLL /**/ + +/* HAS__FWALK: + * This symbol, if defined, indicates that the _fwalk system call is + * available to apply a function to all the file handles. + */ +/*#define HAS__FWALK / **/ + +/* HAS_AINTL: + * This symbol, if defined, indicates that the aintl routine is + * available. If copysignl is also present we can emulate modfl. + */ +/*#define HAS_AINTL / **/ + +/* HAS_BUILTIN_CHOOSE_EXPR: + * Can we handle GCC builtin for compile-time ternary-like expressions + */ +/* HAS_BUILTIN_EXPECT: + * Can we handle GCC builtin for telling that certain values are more + * likely + */ +/*#define HAS_BUILTIN_EXPECT / **/ +#define HAS_BUILTIN_CHOOSE_EXPR /**/ + +/* HAS_C99_VARIADIC_MACROS: + * If defined, the compiler supports C99 variadic macros. + */ +#define HAS_C99_VARIADIC_MACROS /**/ + +/* HAS_CLASS: + * This symbol, if defined, indicates that the class routine is + * available to classify doubles. Available for example in AIX. + * The returned values are defined in and are: + * + * FP_PLUS_NORM Positive normalized, nonzero + * FP_MINUS_NORM Negative normalized, nonzero + * FP_PLUS_DENORM Positive denormalized, nonzero + * FP_MINUS_DENORM Negative denormalized, nonzero + * FP_PLUS_ZERO +0.0 + * FP_MINUS_ZERO -0.0 + * FP_PLUS_INF +INF + * FP_MINUS_INF -INF + * FP_NANS Signaling Not a Number (NaNS) + * FP_NANQ Quiet Not a Number (NaNQ) + */ +/*#define HAS_CLASS / **/ + +/* HAS_CLEARENV: + * This symbol, if defined, indicates that the clearenv () routine is + * available for use. + */ +#define HAS_CLEARENV /**/ + +/* HAS_STRUCT_CMSGHDR: + * This symbol, if defined, indicates that the struct cmsghdr + * is supported. + */ +#define HAS_STRUCT_CMSGHDR /**/ + +/* HAS_COPYSIGNL: + * This symbol, if defined, indicates that the copysignl routine is + * available. If aintl is also present we can emulate modfl. + */ +/*#define HAS_COPYSIGNL / **/ + +/* USE_CPLUSPLUS: + * This symbol, if defined, indicates that a C++ compiler was + * used to compiled Perl and will be used to compile extensions. + */ +/*#define USE_CPLUSPLUS / **/ + +/* HAS_DBMINIT_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the dbminit() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern int dbminit(char *); + */ +/*#define HAS_DBMINIT_PROTO / **/ + +/* HAS_DIR_DD_FD: + * This symbol, if defined, indicates that the the DIR* dirstream + * structure contains a member variable named dd_fd. + */ +/*#define HAS_DIR_DD_FD / **/ + +/* HAS_DIRFD: + * This manifest constant lets the C program know that dirfd + * is available. + */ +#define HAS_DIRFD /**/ + +/* DLSYM_NEEDS_UNDERSCORE: + * This symbol, if defined, indicates that we need to prepend an + * underscore to the symbol name before calling dlsym(). This only + * makes sense if you *have* dlsym, which we will presume is the + * case if you're using dl_dlopen.xs. + */ +/*#define DLSYM_NEEDS_UNDERSCORE / **/ + +/* HAS_FAST_STDIO: + * This symbol, if defined, indicates that the "fast stdio" + * is available to manipulate the stdio buffers directly. + */ +/*#define HAS_FAST_STDIO / **/ + +/* HAS_FCHDIR: + * This symbol, if defined, indicates that the fchdir routine is + * available to change directory using a file descriptor. + */ +#define HAS_FCHDIR /**/ + +/* FCNTL_CAN_LOCK: + * This symbol, if defined, indicates that fcntl() can be used + * for file locking. Normally on Unix systems this is defined. + * It may be undefined on VMS. + */ +#define FCNTL_CAN_LOCK /**/ + +/* HAS_FINITE: + * This symbol, if defined, indicates that the finite routine is + * available to check whether a double is finite (non-infinity non-NaN). + */ +/*#define HAS_FINITE / **/ + +/* HAS_FINITEL: + * This symbol, if defined, indicates that the finitel routine is + * available to check whether a long double is finite + * (non-infinity non-NaN). + */ +/*#define HAS_FINITEL / **/ + +/* HAS_FLOCK_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the flock() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern int flock(int, int); + */ +#define HAS_FLOCK_PROTO /**/ + +/* HAS_FP_CLASS: + * This symbol, if defined, indicates that the fp_class routine is + * available to classify doubles. Available for example in Digital UNIX. + * The returned values are defined in and are: + * + * FP_SNAN Signaling NaN (Not-a-Number) + * FP_QNAN Quiet NaN (Not-a-Number) + * FP_POS_INF +infinity + * FP_NEG_INF -infinity + * FP_POS_NORM Positive normalized + * FP_NEG_NORM Negative normalized + * FP_POS_DENORM Positive denormalized + * FP_NEG_DENORM Negative denormalized + * FP_POS_ZERO +0.0 (positive zero) + * FP_NEG_ZERO -0.0 (negative zero) + */ +/*#define HAS_FP_CLASS / **/ + +/* HAS_FPCLASS: + * This symbol, if defined, indicates that the fpclass routine is + * available to classify doubles. Available for example in Solaris/SVR4. + * The returned values are defined in and are: + * + * FP_SNAN signaling NaN + * FP_QNAN quiet NaN + * FP_NINF negative infinity + * FP_PINF positive infinity + * FP_NDENORM negative denormalized non-zero + * FP_PDENORM positive denormalized non-zero + * FP_NZERO negative zero + * FP_PZERO positive zero + * FP_NNORM negative normalized non-zero + * FP_PNORM positive normalized non-zero + */ +/*#define HAS_FPCLASS / **/ + +/* HAS_FPCLASSIFY: + * This symbol, if defined, indicates that the fpclassify routine is + * available to classify doubles. Available for example in HP-UX. + * The returned values are defined in and are + * + * FP_NORMAL Normalized + * FP_ZERO Zero + * FP_INFINITE Infinity + * FP_SUBNORMAL Denormalized + * FP_NAN NaN + * + */ +/*#define HAS_FPCLASSIFY / **/ + +/* HAS_FPCLASSL: + * This symbol, if defined, indicates that the fpclassl routine is + * available to classify long doubles. Available for example in IRIX. + * The returned values are defined in and are: + * + * FP_SNAN signaling NaN + * FP_QNAN quiet NaN + * FP_NINF negative infinity + * FP_PINF positive infinity + * FP_NDENORM negative denormalized non-zero + * FP_PDENORM positive denormalized non-zero + * FP_NZERO negative zero + * FP_PZERO positive zero + * FP_NNORM negative normalized non-zero + * FP_PNORM positive normalized non-zero + */ +/*#define HAS_FPCLASSL / **/ + +/* HAS_FPOS64_T: + * This symbol will be defined if the C compiler supports fpos64_t. + */ +/*#define HAS_FPOS64_T / **/ + +/* HAS_FREXPL: + * This symbol, if defined, indicates that the frexpl routine is + * available to break a long double floating-point number into + * a normalized fraction and an integral power of 2. + */ +/*#define HAS_FREXPL / **/ + +/* HAS_STRUCT_FS_DATA: + * This symbol, if defined, indicates that the struct fs_data + * to do statfs() is supported. + */ +/*#define HAS_STRUCT_FS_DATA / **/ + +/* HAS_FSEEKO: + * This symbol, if defined, indicates that the fseeko routine is + * available to fseek beyond 32 bits (useful for ILP32 hosts). + */ +#define HAS_FSEEKO /**/ + +/* HAS_FSTATFS: + * This symbol, if defined, indicates that the fstatfs routine is + * available to stat filesystems by file descriptors. + */ +#define HAS_FSTATFS /**/ + +/* HAS_FSYNC: + * This symbol, if defined, indicates that the fsync routine is + * available to write a file's modified data and attributes to + * permanent storage. + */ +#define HAS_FSYNC /**/ + +/* HAS_FTELLO: + * This symbol, if defined, indicates that the ftello routine is + * available to ftell beyond 32 bits (useful for ILP32 hosts). + */ +#define HAS_FTELLO /**/ + +/* HAS_FUTIMES: + * This symbol, if defined, indicates that the futimes routine is + * available to change file descriptor time stamps with struct timevals. + */ +/*#define HAS_FUTIMES / **/ + +/* HAS_GETCWD: + * This symbol, if defined, indicates that the getcwd routine is + * available to get the current working directory. + */ +#define HAS_GETCWD /**/ + +/* HAS_GETESPWNAM: + * This symbol, if defined, indicates that the getespwnam system call is + * available to retrieve enchanced (shadow) password entries by name. + */ +/*#define HAS_GETESPWNAM / **/ + +/* HAS_GETFSSTAT: + * This symbol, if defined, indicates that the getfsstat routine is + * available to stat filesystems in bulk. + */ +/*#define HAS_GETFSSTAT / **/ + +/* HAS_GETITIMER: + * This symbol, if defined, indicates that the getitimer routine is + * available to return interval timers. + */ +#define HAS_GETITIMER /**/ + +/* HAS_GETMNT: + * This symbol, if defined, indicates that the getmnt routine is + * available to get filesystem mount info by filename. + */ +/*#define HAS_GETMNT / **/ + +/* HAS_GETMNTENT: + * This symbol, if defined, indicates that the getmntent routine is + * available to iterate through mounted file systems to get their info. + */ +#define HAS_GETMNTENT /**/ + +/* HAS_GETPRPWNAM: + * This symbol, if defined, indicates that the getprpwnam system call is + * available to retrieve protected (shadow) password entries by name. + */ +/*#define HAS_GETPRPWNAM / **/ + +/* HAS_GETSPNAM: + * This symbol, if defined, indicates that the getspnam system call is + * available to retrieve SysV shadow password entries by name. + */ +#define HAS_GETSPNAM /**/ + +/* HAS_HASMNTOPT: + * This symbol, if defined, indicates that the hasmntopt routine is + * available to query the mount options of file systems. + */ +#define HAS_HASMNTOPT /**/ + +/* HAS_ILOGBL: + * This symbol, if defined, indicates that the ilogbl routine is + * available. If scalbnl is also present we can emulate frexpl. + */ +/*#define HAS_ILOGBL / **/ + +/* HAS_INT64_T: + * This symbol will defined if the C compiler supports int64_t. + * Usually the needs to be included, but sometimes + * is enough. + */ +#define HAS_INT64_T /**/ + +/* HAS_ISFINITE: + * This symbol, if defined, indicates that the isfinite routine is + * available to check whether a double is finite (non-infinity non-NaN). + */ +/*#define HAS_ISFINITE / **/ + +/* HAS_ISINF: + * This symbol, if defined, indicates that the isinf routine is + * available to check whether a double is an infinity. + */ +/*#define HAS_ISINF / **/ + +/* HAS_ISNAN: + * This symbol, if defined, indicates that the isnan routine is + * available to check whether a double is a NaN. + */ +/*#define HAS_ISNAN / **/ + +/* HAS_ISNANL: + * This symbol, if defined, indicates that the isnanl routine is + * available to check whether a long double is a NaN. + */ +/*#define HAS_ISNANL / **/ + +/* HAS_LDBL_DIG: + * This symbol, if defined, indicates that this system's + * or defines the symbol LDBL_DIG, which is the number + * of significant digits in a long double precision number. Unlike + * for DBL_DIG, there's no good guess for LDBL_DIG if it is undefined. + */ +#define HAS_LDBL_DIG /* */ + +/* LIBM_LIB_VERSION: + * This symbol, if defined, indicates that libm exports _LIB_VERSION + * and that math.h defines the enum to manipulate it. + */ +/*#define LIBM_LIB_VERSION / **/ + +/* HAS_MADVISE: + * This symbol, if defined, indicates that the madvise system call is + * available to map a file into memory. + */ +#define HAS_MADVISE /**/ + +/* HAS_MALLOC_SIZE: + * This symbol, if defined, indicates that the malloc_size + * routine is available for use. + */ +/*#define HAS_MALLOC_SIZE / **/ + +/* HAS_MALLOC_GOOD_SIZE: + * This symbol, if defined, indicates that the malloc_good_size + * routine is available for use. + */ +/*#define HAS_MALLOC_GOOD_SIZE / **/ + +/* HAS_MKDTEMP: + * This symbol, if defined, indicates that the mkdtemp routine is + * available to exclusively create a uniquely named temporary directory. + */ +#define HAS_MKDTEMP /**/ + +/* HAS_MKSTEMPS: + * This symbol, if defined, indicates that the mkstemps routine is + * available to excluslvely create and open a uniquely named + * (with a suffix) temporary file. + */ +/*#define HAS_MKSTEMPS / **/ + +/* HAS_MODFL: + * This symbol, if defined, indicates that the modfl routine is + * available to split a long double x into a fractional part f and + * an integer part i such that |f| < 1.0 and (f + i) = x. + */ +/* HAS_MODFL_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the modfl() function. Otherwise, it is up + * to the program to supply one. + */ +/* HAS_MODFL_POW32_BUG: + * This symbol, if defined, indicates that the modfl routine is + * broken for long doubles >= pow(2, 32). + * For example from 4294967303.150000 one would get 4294967302.000000 + * and 1.150000. The bug has been seen in certain versions of glibc, + * release 2.2.2 is known to be okay. + */ +/*#define HAS_MODFL / **/ +#define HAS_MODFL_PROTO /**/ +/*#define HAS_MODFL_POW32_BUG / **/ + +/* HAS_MPROTECT: + * This symbol, if defined, indicates that the mprotect system call is + * available to modify the access protection of a memory mapped file. + */ +#define HAS_MPROTECT /**/ + +/* HAS_STRUCT_MSGHDR: + * This symbol, if defined, indicates that the struct msghdr + * is supported. + */ +#define HAS_STRUCT_MSGHDR /**/ + +/* HAS_NL_LANGINFO: + * This symbol, if defined, indicates that the nl_langinfo routine is + * available to return local data. You will also need + * and therefore I_LANGINFO. + */ +#define HAS_NL_LANGINFO /**/ + +/* HAS_OFF64_T: + * This symbol will be defined if the C compiler supports off64_t. + */ +/*#define HAS_OFF64_T / **/ + +/* HAS_PROCSELFEXE: + * This symbol is defined if PROCSELFEXE_PATH is a symlink + * to the absolute pathname of the executing program. + */ +/* PROCSELFEXE_PATH: + * If HAS_PROCSELFEXE is defined this symbol is the filename + * of the symbolic link pointing to the absolute pathname of + * the executing program. + */ +/*#define HAS_PROCSELFEXE / **/ +#if defined(HAS_PROCSELFEXE) && !defined(PROCSELFEXE_PATH) +#define PROCSELFEXE_PATH /**/ +#endif + +/* HAS_PTHREAD_ATTR_SETSCOPE: + * This symbol, if defined, indicates that the pthread_attr_setscope + * system call is available to set the contention scope attribute of + * a thread attribute object. + */ +#define HAS_PTHREAD_ATTR_SETSCOPE /**/ + +/* HAS_READV: + * This symbol, if defined, indicates that the readv routine is + * available to do gather reads. You will also need + * and there I_SYSUIO. + */ +#define HAS_READV /**/ + +/* HAS_RECVMSG: + * This symbol, if defined, indicates that the recvmsg routine is + * available to send structured socket messages. + */ +#define HAS_RECVMSG /**/ + +/* HAS_SBRK_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the sbrk() function. Otherwise, it is up + * to the program to supply one. Good guesses are + * extern void* sbrk(int); + * extern void* sbrk(size_t); + */ +#define HAS_SBRK_PROTO /**/ + +/* HAS_SCALBNL: + * This symbol, if defined, indicates that the scalbnl routine is + * available. If ilogbl is also present we can emulate frexpl. + */ +/*#define HAS_SCALBNL / **/ + +/* HAS_SENDMSG: + * This symbol, if defined, indicates that the sendmsg routine is + * available to send structured socket messages. + */ +#define HAS_SENDMSG /**/ + +/* HAS_SETITIMER: + * This symbol, if defined, indicates that the setitimer routine is + * available to set interval timers. + */ +#define HAS_SETITIMER /**/ + +/* HAS_SETPROCTITLE: + * This symbol, if defined, indicates that the setproctitle routine is + * available to set process title. + */ +/*#define HAS_SETPROCTITLE / **/ + +/* USE_SFIO: + * This symbol, if defined, indicates that sfio should + * be used. + */ +/*#define USE_SFIO / **/ + +/* HAS_SIGNBIT: + * This symbol, if defined, indicates that the signbit routine is + * available to check if the given number has the sign bit set. + * This should include correct testing of -0.0. This will only be set + * if the signbit() routine is safe to use with the NV type used internally + * in perl. Users should call Perl_signbit(), which will be #defined to + * the system's signbit() function or macro if this symbol is defined. + */ +#define HAS_SIGNBIT /**/ + +/* HAS_SIGPROCMASK: + * This symbol, if defined, indicates that the sigprocmask + * system call is available to examine or change the signal mask + * of the calling process. + */ +#define HAS_SIGPROCMASK /**/ + +/* USE_SITECUSTOMIZE: + * This symbol, if defined, indicates that sitecustomize should + * be used. + */ +#ifndef USE_SITECUSTOMIZE +/*#define USE_SITECUSTOMIZE / **/ +#endif + +/* HAS_SNPRINTF: + * This symbol, if defined, indicates that the snprintf () library + * function is available for use. + */ +/* HAS_VSNPRINTF: + * This symbol, if defined, indicates that the vsnprintf () library + * function is available for use. + */ +#define HAS_SNPRINTF /**/ +#define HAS_VSNPRINTF /**/ + +/* HAS_SOCKATMARK: + * This symbol, if defined, indicates that the sockatmark routine is + * available to test whether a socket is at the out-of-band mark. + */ +/*#define HAS_SOCKATMARK / **/ + +/* HAS_SOCKATMARK_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the sockatmark() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern int sockatmark(int); + */ +/*#define HAS_SOCKATMARK_PROTO / **/ + +/* HAS_SOCKS5_INIT: + * This symbol, if defined, indicates that the socks5_init routine is + * available to initialize SOCKS 5. + */ +/*#define HAS_SOCKS5_INIT / **/ + +/* SPRINTF_RETURNS_STRLEN: + * This variable defines whether sprintf returns the length of the string + * (as per the ANSI spec). Some C libraries retain compatibility with + * pre-ANSI C and return a pointer to the passed in buffer; for these + * this variable will be undef. + */ +#define SPRINTF_RETURNS_STRLEN /**/ + +/* HAS_SQRTL: + * This symbol, if defined, indicates that the sqrtl routine is + * available to do long double square roots. + */ +/*#define HAS_SQRTL / **/ + +/* HAS_SETRESGID_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the setresgid() function. Otherwise, it is up + * to the program to supply one. Good guesses are + * extern int setresgid(uid_t ruid, uid_t euid, uid_t suid); + */ +/*#define HAS_SETRESGID_PROTO / **/ + +/* HAS_SETRESUID_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the setresuid() function. Otherwise, it is up + * to the program to supply one. Good guesses are + * extern int setresuid(uid_t ruid, uid_t euid, uid_t suid); + */ +/*#define HAS_SETRESUID_PROTO / **/ + +/* HAS_STRUCT_STATFS_F_FLAGS: + * This symbol, if defined, indicates that the struct statfs + * does have the f_flags member containing the mount flags of + * the filesystem containing the file. + * This kind of struct statfs is coming from (BSD 4.3), + * not from (SYSV). Older BSDs (like Ultrix) do not + * have statfs() and struct statfs, they have ustat() and getmnt() + * with struct ustat and struct fs_data. + */ +/*#define HAS_STRUCT_STATFS_F_FLAGS / **/ + +/* HAS_STRUCT_STATFS: + * This symbol, if defined, indicates that the struct statfs + * to do statfs() is supported. + */ +#define HAS_STRUCT_STATFS /**/ + +/* HAS_FSTATVFS: + * This symbol, if defined, indicates that the fstatvfs routine is + * available to stat filesystems by file descriptors. + */ +#define HAS_FSTATVFS /**/ + +/* HAS_STRFTIME: + * This symbol, if defined, indicates that the strftime routine is + * available to do time formatting. + */ +#define HAS_STRFTIME /**/ + +/* HAS_STRLCAT: + * This symbol, if defined, indicates that the strlcat () routine is + * available to do string concatenation. + */ +/*#define HAS_STRLCAT /* */ + +/* HAS_STRLCPY: + * This symbol, if defined, indicates that the strlcpy () routine is + * available to do string copying. + */ +/*#define HAS_STRLCPY /* */ + +/* HAS_STRTOLD: + * This symbol, if defined, indicates that the strtold routine is + * available to convert strings to long doubles. + */ +#define HAS_STRTOLD /**/ + +/* HAS_STRTOLL: + * This symbol, if defined, indicates that the strtoll routine is + * available to convert strings to long longs. + */ +#define HAS_STRTOLL /**/ + +/* HAS_STRTOQ: + * This symbol, if defined, indicates that the strtoq routine is + * available to convert strings to long longs (quads). + */ +/*#define HAS_STRTOQ / **/ + +/* HAS_STRTOULL: + * This symbol, if defined, indicates that the strtoull routine is + * available to convert strings to unsigned long longs. + */ +#define HAS_STRTOULL /**/ + +/* HAS_STRTOUQ: + * This symbol, if defined, indicates that the strtouq routine is + * available to convert strings to unsigned long longs (quads). + */ +/*#define HAS_STRTOUQ / **/ + +/* HAS_SYSCALL_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the syscall() function. Otherwise, it is up + * to the program to supply one. Good guesses are + * extern int syscall(int, ...); + * extern int syscall(long, ...); + */ +#define HAS_SYSCALL_PROTO /**/ + +/* HAS_TELLDIR_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the telldir() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern long telldir(DIR*); + */ +#define HAS_TELLDIR_PROTO /**/ + +/* U32_ALIGNMENT_REQUIRED: + * This symbol, if defined, indicates that you must access + * character data through U32-aligned pointers. + */ +#ifndef U32_ALIGNMENT_REQUIRED +#define U32_ALIGNMENT_REQUIRED /**/ +#endif + +/* HAS_UALARM: + * This symbol, if defined, indicates that the ualarm routine is + * available to do alarms with microsecond granularity. + */ +#define HAS_UALARM /**/ + +/* HAS_UNORDERED: + * This symbol, if defined, indicates that the unordered routine is + * available to check whether two doubles are unordered + * (effectively: whether either of them is NaN) + */ +/*#define HAS_UNORDERED / **/ + +/* HAS_UNSETENV: + * This symbol, if defined, indicates that the unsetenv () routine is + * available for use. + */ +#define HAS_UNSETENV /**/ + +/* HAS_USLEEP_PROTO: + * This symbol, if defined, indicates that the system provides + * a prototype for the usleep() function. Otherwise, it is up + * to the program to supply one. A good guess is + * extern int usleep(useconds_t); + */ +#define HAS_USLEEP_PROTO /**/ + +/* HAS_USTAT: + * This symbol, if defined, indicates that the ustat system call is + * available to query file system statistics by dev_t. + */ +/*#define HAS_USTAT / **/ + +/* HAS_WRITEV: + * This symbol, if defined, indicates that the writev routine is + * available to do scatter writes. + */ +#define HAS_WRITEV /**/ + +/* USE_DYNAMIC_LOADING: + * This symbol, if defined, indicates that dynamic loading of + * some sort is available. + */ +/*#define USE_DYNAMIC_LOADING / **/ + +/* FFLUSH_NULL: + * This symbol, if defined, tells that fflush(NULL) does flush + * all pending stdio output. + */ +/* FFLUSH_ALL: + * This symbol, if defined, tells that to flush + * all pending stdio output one must loop through all + * the stdio file handles stored in an array and fflush them. + * Note that if fflushNULL is defined, fflushall will not + * even be probed for and will be left undefined. + */ +/*#define FFLUSH_NULL / **/ +/*#define FFLUSH_ALL / **/ + +/* I_CRYPT: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_CRYPT /**/ + +/* DB_Prefix_t: + * This symbol contains the type of the prefix structure element + * in the header file. In older versions of DB, it was + * int, while in newer ones it is u_int32_t. + */ +/* DB_Hash_t: + * This symbol contains the type of the prefix structure element + * in the header file. In older versions of DB, it was + * int, while in newer ones it is size_t. + */ +/* DB_VERSION_MAJOR_CFG: + * This symbol, if defined, defines the major version number of + * Berkeley DB found in the header when Perl was configured. + */ +/* DB_VERSION_MINOR_CFG: + * This symbol, if defined, defines the minor version number of + * Berkeley DB found in the header when Perl was configured. + * For DB version 1 this is always 0. + */ +/* DB_VERSION_PATCH_CFG: + * This symbol, if defined, defines the patch version number of + * Berkeley DB found in the header when Perl was configured. + * For DB version 1 this is always 0. + */ +#define DB_Hash_t u_int32_t /**/ +#define DB_Prefix_t size_t /**/ +#define DB_VERSION_MAJOR_CFG /**/ +#define DB_VERSION_MINOR_CFG /**/ +#define DB_VERSION_PATCH_CFG /**/ + +/* I_FP: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_FP / **/ + +/* I_FP_CLASS: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_FP_CLASS / **/ + +/* I_IEEEFP: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_IEEEFP / **/ + +/* I_INTTYPES: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_INTTYPES /**/ + +/* I_LANGINFO: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_LANGINFO /**/ + +/* I_LIBUTIL: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_LIBUTIL / **/ + +/* I_MNTENT: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_MNTENT /**/ + +/* I_NETINET_TCP: + * This symbol, if defined, indicates to the C program that it should + * include . + */ +#define I_NETINET_TCP /**/ + +/* I_POLL: + * This symbol, if defined, indicates that exists and + * should be included. (see also HAS_POLL) + */ +#define I_POLL /**/ + +/* I_PROT: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_PROT / **/ + +/* I_SHADOW: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SHADOW /**/ + +/* I_SOCKS: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_SOCKS / **/ + +/* I_SUNMATH: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_SUNMATH / **/ + +/* I_SYSLOG: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYSLOG /**/ + +/* I_SYSMODE: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_SYSMODE / **/ + +/* I_SYS_MOUNT: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYS_MOUNT /**/ + +/* I_SYS_STATFS: + * This symbol, if defined, indicates that exists. + */ +#define I_SYS_STATFS /**/ + +/* I_SYS_STATVFS: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYS_STATVFS /**/ + +/* I_SYSUTSNAME: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYSUTSNAME /**/ + +/* I_SYS_VFS: + * This symbol, if defined, indicates that exists and + * should be included. + */ +#define I_SYS_VFS /**/ + +/* I_USTAT: + * This symbol, if defined, indicates that exists and + * should be included. + */ +/*#define I_USTAT / **/ + +/* PERL_PRIfldbl: + * This symbol, if defined, contains the string used by stdio to + * format long doubles (format 'f') for output. + */ +/* PERL_PRIgldbl: + * This symbol, if defined, contains the string used by stdio to + * format long doubles (format 'g') for output. + */ +/* PERL_PRIeldbl: + * This symbol, if defined, contains the string used by stdio to + * format long doubles (format 'e') for output. + */ +/* PERL_SCNfldbl: + * This symbol, if defined, contains the string used by stdio to + * format long doubles (format 'f') for input. + */ +#define PERL_PRIfldbl "Lf" /**/ +#define PERL_PRIgldbl "Lg" /**/ +#define PERL_PRIeldbl "Le" /**/ +#define PERL_SCNfldbl "Lf" /**/ + +/* PERL_MAD: + * This symbol, if defined, indicates that the Misc Attribution + * Declaration code should be conditionally compiled. + */ +/*#define PERL_MAD / **/ + +/* NEED_VA_COPY: + * This symbol, if defined, indicates that the system stores + * the variable argument list datatype, va_list, in a format + * that cannot be copied by simple assignment, so that some + * other means must be used when copying is required. + * As such systems vary in their provision (or non-provision) + * of copying mechanisms, handy.h defines a platform- + * independent macro, Perl_va_copy(src, dst), to do the job. + */ +#define NEED_VA_COPY /**/ + +/* IVTYPE: + * This symbol defines the C type used for Perl's IV. + */ +/* UVTYPE: + * This symbol defines the C type used for Perl's UV. + */ +/* I8TYPE: + * This symbol defines the C type used for Perl's I8. + */ +/* U8TYPE: + * This symbol defines the C type used for Perl's U8. + */ +/* I16TYPE: + * This symbol defines the C type used for Perl's I16. + */ +/* U16TYPE: + * This symbol defines the C type used for Perl's U16. + */ +/* I32TYPE: + * This symbol defines the C type used for Perl's I32. + */ +/* U32TYPE: + * This symbol defines the C type used for Perl's U32. + */ +/* I64TYPE: + * This symbol defines the C type used for Perl's I64. + */ +/* U64TYPE: + * This symbol defines the C type used for Perl's U64. + */ +/* NVTYPE: + * This symbol defines the C type used for Perl's NV. + */ +/* IVSIZE: + * This symbol contains the sizeof(IV). + */ +/* UVSIZE: + * This symbol contains the sizeof(UV). + */ +/* I8SIZE: + * This symbol contains the sizeof(I8). + */ +/* U8SIZE: + * This symbol contains the sizeof(U8). + */ +/* I16SIZE: + * This symbol contains the sizeof(I16). + */ +/* U16SIZE: + * This symbol contains the sizeof(U16). + */ +/* I32SIZE: + * This symbol contains the sizeof(I32). + */ +/* U32SIZE: + * This symbol contains the sizeof(U32). + */ +/* I64SIZE: + * This symbol contains the sizeof(I64). + */ +/* U64SIZE: + * This symbol contains the sizeof(U64). + */ +/* NVSIZE: + * This symbol contains the sizeof(NV). + */ +/* NV_PRESERVES_UV: + * This symbol, if defined, indicates that a variable of type NVTYPE + * can preserve all the bits of a variable of type UVTYPE. + */ +/* NV_PRESERVES_UV_BITS: + * This symbol contains the number of bits a variable of type NVTYPE + * can preserve of a variable of type UVTYPE. + */ +/* NV_ZERO_IS_ALLBITS_ZERO: + * This symbol, if defined, indicates that a variable of type NVTYPE + * stores 0.0 in memory as all bits zero. + */ +#define IVTYPE long /**/ +#define UVTYPE unsigned long /**/ +#define I8TYPE char /**/ +#define U8TYPE unsigned char /**/ +#define I16TYPE short /**/ +#define U16TYPE unsigned short /**/ +#define I32TYPE long /**/ +#define U32TYPE unsigned long /**/ +#ifdef HAS_QUAD +#define I64TYPE long long /**/ +#define U64TYPE unsigned long long /**/ +#endif +#define NVTYPE double /**/ +#define IVSIZE 4 /**/ +#define UVSIZE 4 /**/ +#define I8SIZE 1 /**/ +#define U8SIZE 1 /**/ +#define I16SIZE 2 /**/ +#define U16SIZE 2 /**/ +#define I32SIZE 4 /**/ +#define U32SIZE 4 /**/ +#ifdef HAS_QUAD +#define I64SIZE 8 /**/ +#define U64SIZE 8 /**/ +#endif +#define NVSIZE 8 /**/ +#define NV_PRESERVES_UV +#define NV_PRESERVES_UV_BITS 32 +#define NV_ZERO_IS_ALLBITS_ZERO +#if UVSIZE == 8 +# ifdef BYTEORDER +# if BYTEORDER == 0x1234 +# undef BYTEORDER +# define BYTEORDER 0x12345678 +# else +# if BYTEORDER == 0x4321 +# undef BYTEORDER +# define BYTEORDER 0x87654321 +# endif +# endif +# endif +#endif + +/* IVdf: + * This symbol defines the format string used for printing a Perl IV + * as a signed decimal integer. + */ +/* UVuf: + * This symbol defines the format string used for printing a Perl UV + * as an unsigned decimal integer. + */ +/* UVof: + * This symbol defines the format string used for printing a Perl UV + * as an unsigned octal integer. + */ +/* UVxf: + * This symbol defines the format string used for printing a Perl UV + * as an unsigned hexadecimal integer in lowercase abcdef. + */ +/* UVXf: + * This symbol defines the format string used for printing a Perl UV + * as an unsigned hexadecimal integer in uppercase ABCDEF. + */ +/* NVef: + * This symbol defines the format string used for printing a Perl NV + * using %e-ish floating point format. + */ +/* NVff: + * This symbol defines the format string used for printing a Perl NV + * using %f-ish floating point format. + */ +/* NVgf: + * This symbol defines the format string used for printing a Perl NV + * using %g-ish floating point format. + */ +#define IVdf "ld" /**/ +#define UVuf "lu" /**/ +#define UVof "lo" /**/ +#define UVxf "lx" /**/ +#define UVXf "lX" /**/ +#define NVef "e" /**/ +#define NVff "f" /**/ +#define NVgf "g" /**/ + +/* SELECT_MIN_BITS: + * This symbol holds the minimum number of bits operated by select. + * That is, if you do select(n, ...), how many bits at least will be + * cleared in the masks if some activity is detected. Usually this + * is either n or 32*ceil(n/32), especially many little-endians do + * the latter. This is only useful if you have select(), naturally. + */ +#define SELECT_MIN_BITS 32 /**/ + +/* STARTPERL: + * This variable contains the string to put in front of a perl + * script to make sure (one hopes) that it runs with perl and not + * some shell. + */ +#define STARTPERL "#!/usr/bin/perl" /**/ + +/* HAS_STDIO_STREAM_ARRAY: + * This symbol, if defined, tells that there is an array + * holding the stdio streams. + */ +/* STDIO_STREAM_ARRAY: + * This symbol tells the name of the array holding the stdio streams. + * Usual values include _iob, __iob, and __sF. + */ +/*#define HAS_STDIO_STREAM_ARRAY / **/ +#define STDIO_STREAM_ARRAY + +/* USE_64_BIT_INT: + * This symbol, if defined, indicates that 64-bit integers should + * be used when available. If not defined, the native integers + * will be employed (be they 32 or 64 bits). The minimal possible + * 64-bitness is used, just enough to get 64-bit integers into Perl. + * This may mean using for example "long longs", while your memory + * may still be limited to 2 gigabytes. + */ +/* USE_64_BIT_ALL: + * This symbol, if defined, indicates that 64-bit integers should + * be used when available. If not defined, the native integers + * will be used (be they 32 or 64 bits). The maximal possible + * 64-bitness is employed: LP64 or ILP64, meaning that you will + * be able to use more than 2 gigabytes of memory. This mode is + * even more binary incompatible than USE_64_BIT_INT. You may not + * be able to run the resulting executable in a 32-bit CPU at all or + * you may need at least to reboot your OS to 64-bit mode. + */ +#ifndef USE_64_BIT_INT +/*#define USE_64_BIT_INT / **/ +#endif + +#ifndef USE_64_BIT_ALL +/*#define USE_64_BIT_ALL / **/ +#endif + +/* USE_FAST_STDIO: + * This symbol, if defined, indicates that Perl should + * be built to use 'fast stdio'. + * Defaults to define in Perls 5.8 and earlier, to undef later. + */ +#ifndef USE_FAST_STDIO +/*#define USE_FAST_STDIO / **/ +#endif + +/* USE_LARGE_FILES: + * This symbol, if defined, indicates that large file support + * should be used when available. + */ +#ifndef USE_LARGE_FILES +#define USE_LARGE_FILES /**/ +#endif + +/* USE_LONG_DOUBLE: + * This symbol, if defined, indicates that long doubles should + * be used when available. + */ +#ifndef USE_LONG_DOUBLE +/*#define USE_LONG_DOUBLE / **/ +#endif + +/* USE_MORE_BITS: + * This symbol, if defined, indicates that 64-bit interfaces and + * long doubles should be used when available. + */ +#ifndef USE_MORE_BITS +/*#define USE_MORE_BITS / **/ +#endif + +/* MULTIPLICITY: + * This symbol, if defined, indicates that Perl should + * be built to use multiplicity. + */ +#ifndef MULTIPLICITY +/*#define MULTIPLICITY / **/ +#endif + +/* USE_PERLIO: + * This symbol, if defined, indicates that the PerlIO abstraction should + * be used throughout. If not defined, stdio should be + * used in a fully backward compatible manner. + */ +#ifndef USE_PERLIO +/*#define USE_PERLIO / **/ +#endif + +/* USE_SOCKS: + * This symbol, if defined, indicates that Perl should + * be built to use socks. + */ +#ifndef USE_SOCKS +/*#define USE_SOCKS / **/ +#endif + +#endif diff --git a/package/pcc-libs/Makefile b/package/pcc-libs/Makefile index 238348777..bce74cd8d 100644 --- a/package/pcc-libs/Makefile +++ b/package/pcc-libs/Makefile @@ -12,7 +12,7 @@ PKG_SECTION:= lang PKG_URL:= http://pcc.ludd.ltu.se/ PKG_SITES:= http://pcc.ludd.ltu.se/ftp/pub/pcc-releases/ -PKG_ARCH_DEPENDS:= !arm !cris !mips +PKG_ARCH_DEPENDS:= !arm !cris !mips !ppc DISTFILES:= ${PKG_NAME}-${PKG_VERSION}.tgz include $(TOPDIR)/mk/package.mk diff --git a/package/pcc/Makefile b/package/pcc/Makefile index 5eb9bfc68..d305c55a1 100644 --- a/package/pcc/Makefile +++ b/package/pcc/Makefile @@ -10,12 +10,11 @@ PKG_MD5SUM:= 6e5d851ee57fe58702fe4e80ecd1f852 PKG_DESCR:= Portable C Compiler PKG_SECTION:= lang PKG_DEPENDS:= pcc-libs -# binutils PKG_URL:= http://pcc.ludd.ltu.se/ PKG_SITES:= http://pcc.ludd.ltu.se/ftp/pub/pcc-releases/ PKG_NOPARALLEL:= 1 -PKG_ARCH_DEPENDS:= !arm !cris !mips +PKG_ARCH_DEPENDS:= !arm !cris !mips !ppc DISTFILES:= ${PKG_NAME}-${PKG_VERSION}.tgz include $(TOPDIR)/mk/package.mk diff --git a/target/config/Config.in b/target/config/Config.in index 5c38228b6..5e89eb8f6 100644 --- a/target/config/Config.in +++ b/target/config/Config.in @@ -264,7 +264,7 @@ config ADK_TARGET_CPU_ARCH default "arm" if ADK_LINUX_ARM && ADK_little default "armeb" if ADK_LINUX_ARM && ADK_big default "sparc" if ADK_LINUX_SPARC - default "powerpc" if ADK_CPU_PPC + default "ppc" if ADK_CPU_PPC config ADK_TARGET_ABI_CFLAGS string diff --git a/target/ppc/uclibc.config b/target/ppc/uclibc.config index e649d075e..11788e4c0 100644 --- a/target/ppc/uclibc.config +++ b/target/ppc/uclibc.config @@ -82,7 +82,7 @@ UCLIBC_CTOR_DTOR=y UCLIBC_HAS_THREADS_NATIVE=y UCLIBC_HAS_THREADS=y UCLIBC_HAS_TLS=y -# PTHREADS_DEBUG_SUPPORT is not set +PTHREADS_DEBUG_SUPPORT=y UCLIBC_HAS_SYSLOG=y UCLIBC_HAS_LFS=y # MALLOC is not set -- cgit v1.2.3 From 390eea03ce71b5c3a6dcb493812d744a8986c241 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Thu, 11 Aug 2011 15:13:48 +0200 Subject: qemu help --- target/ppc/Makefile | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/target/ppc/Makefile b/target/ppc/Makefile index a60d376a9..c643d6c5c 100644 --- a/target/ppc/Makefile +++ b/target/ppc/Makefile @@ -20,9 +20,17 @@ imageinstall: $(BIN_DIR)/$(INITRAMFS) @cp $(KERNEL) $(BIN_DIR)/$(TARGET_KERNEL) @echo 'The kernel file is: $(BIN_DIR)/${TARGET_KERNEL}' @echo 'The initramfs image is: ${BIN_DIR}/${INITRAMFS}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-ppc -M mac99 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' +endif endif ifeq ($(ADK_TARGET_FS),initramfs-piggyback) imageinstall: ${BUILD_DIR}/${INITRAMFS_PIGGYBACK} createinitramfs @cp $(KERNEL) $(BIN_DIR)/${TARGET_KERNEL} @echo 'The kernel+initramfs file is: $(BIN_DIR)/${TARGET_KERNEL}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-ppc -M mac99 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' +endif endif -- cgit v1.2.3 From 1eccc1842e2c6a0bce4c448320341f1aef1683b7 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 15 Aug 2011 12:12:44 +0200 Subject: cosmetic changes for jtools build --- jtools/ant/Makefile | 1 - jtools/ecj/Makefile | 5 ----- jtools/jamvm/Makefile | 10 +++++----- mk/build.mk | 2 +- mk/vars.mk | 1 + package/openjdk/Makefile | 2 +- 6 files changed, 8 insertions(+), 13 deletions(-) diff --git a/jtools/ant/Makefile b/jtools/ant/Makefile index 07da1f1a0..537668a21 100644 --- a/jtools/ant/Makefile +++ b/jtools/ant/Makefile @@ -20,7 +20,6 @@ $(WRKBUILD)/.compiled: ${WRKDIST}/.prepared cd $(WRKBUILD)/lib/optional; wget http://openadk.org/distfiles/junit-4.9b2.jar cp $(STAGING_JAVA_HOST_DIR)/usr/share/java/ecj.jar $(WRKBUILD)/lib/optional cd ${WRKBUILD}; export BOOTJAVAC_OPTS="-bootclasspath $(STAGING_JAVA_HOST_DIR)/usr/share/classpath/glibj.zip" \ - BOOTCLASSPATH="$(STAGING_JAVA_HOST_DIR)/usr/share/jamvm/classes.zip:$(STAGING_JAVA_HOST_DIR)/usr/share/classpath/glibj.zip" \ LD_LIBRARY_PATH=$(STAGING_JAVA_HOST_DIR)/usr/lib:$(STAGING_JAVA_HOST_DIR)/usr/lib64 \ JAVA_HOME=$(STAGING_JAVA_HOST_DIR)/usr/lib/jvm ; \ $(BASH) build.sh diff --git a/jtools/ecj/Makefile b/jtools/ecj/Makefile index c9e4559a7..af051f9b9 100644 --- a/jtools/ecj/Makefile +++ b/jtools/ecj/Makefile @@ -21,7 +21,6 @@ ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj: -o ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj.native \ --main=org.eclipse.jdt.internal.compiler.batch.Main \ $(TOPDIR)/jtools_build/gcc-$(GCJ_VER)/ecj.jar - #$(CP) $(TOPDIR)/jtools_build/gcc-$(GCJ_VER)/ecj.jar ${STAGING_JAVA_HOST_DIR}/usr/share/ecj.jar echo "env LD_LIBRARY_PATH=$(STAGING_JAVA_HOST_DIR)/usr/lib:$(STAGING_JAVA_HOST_DIR)/usr/lib64 ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj.native \$$@" > \ ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj chmod u+x ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj @@ -33,9 +32,5 @@ ${STAGING_JAVA_HOST_DIR}/usr/bin/ecj: echo "env LD_LIBRARY_PATH=$(STAGING_JAVA_HOST_DIR)/usr/lib:$(STAGING_JAVA_HOST_DIR)/usr/lib64 ${STAGING_JAVA_HOST_DIR}/usr/bin/gij.native \"\$$@\"" > \ ${STAGING_JAVA_HOST_DIR}/usr/bin/gij chmod u+x ${STAGING_JAVA_HOST_DIR}/usr/bin/gij - rm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/bin/java - rm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/jre/bin/java - cp ${STAGING_JAVA_HOST_DIR}/usr/bin/java ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/bin/java - cp ${STAGING_JAVA_HOST_DIR}/usr/bin/java ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/jre/bin/java include $(TOPDIR)/mk/tools.mk diff --git a/jtools/jamvm/Makefile b/jtools/jamvm/Makefile index defdbd713..a85b2d6c8 100644 --- a/jtools/jamvm/Makefile +++ b/jtools/jamvm/Makefile @@ -5,7 +5,7 @@ include $(TOPDIR)/rules.mk PKG_NAME:= jamvm PKG_VERSION:= 1.5.4 -PKG_RELEASE:= 1 +PKG_RELEASE:= 2 PKG_MD5SUM:= 63220327925ace13756ae334c55a3baa PKG_SITES:= ${MASTER_SITE_SOURCEFORGE:=jamvm/} @@ -23,7 +23,7 @@ $(WRKBUILD)/.configured: ${WRKDIST}/.prepared CC='${CC_FOR_BUILD}' \ CXX='${CXX_FOR_BUILD}' \ ./configure \ - --prefix=/usr \ + --prefix=$(STAGING_JAVA_HOST_DIR)/usr \ --with-classpath-install-dir=$(STAGING_JAVA_HOST_DIR)/usr touch $@ @@ -32,8 +32,8 @@ $(WRKBUILD)/.compiled: ${WRKDIST}/.configured touch $@ ${STAGING_JAVA_HOST_DIR}/usr/bin/jamvm: $(WRKBUILD)/.compiled - ${MAKE} -C ${WRKBUILD} DESTDIR=$(STAGING_JAVA_HOST_DIR) install $(MAKE_TRACE) - $(CP) ${STAGING_JAVA_HOST_DIR}/usr/bin/jamvm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/bin/java - $(CP) ${STAGING_JAVA_HOST_DIR}/usr/bin/jamvm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/jre/bin/java + ${MAKE} -C ${WRKBUILD} install $(MAKE_TRACE) + ln -sf ${STAGING_JAVA_HOST_DIR}/usr/bin/jamvm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/bin/java + ln -sf ${STAGING_JAVA_HOST_DIR}/usr/bin/jamvm ${STAGING_JAVA_HOST_DIR}/usr/lib/jvm/jre/bin/java include $(TOPDIR)/mk/tools.mk diff --git a/mk/build.mk b/mk/build.mk index cd50be90f..42ddebefb 100644 --- a/mk/build.mk +++ b/mk/build.mk @@ -266,7 +266,7 @@ ifeq ($(filter-out distclean,${MAKECMDGOALS}),) include ${TOPDIR}/mk/vars.mk else include $(TOPDIR)/prereq.mk -export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD +export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD CXX_FOR_BUILD endif all: menuconfig diff --git a/mk/vars.mk b/mk/vars.mk index 3776b57b4..2c7e1259a 100644 --- a/mk/vars.mk +++ b/mk/vars.mk @@ -136,6 +136,7 @@ TARGET_CONFIGURE_OPTS= PATH='${TARGET_PATH}' \ CROSS='$(TARGET_CROSS)' HOST_CONFIGURE_OPTS= CC_FOR_BUILD='${CC_FOR_BUILD}' \ + CXX_FOR_BUILD='${CXX_FOR_BUILD}' \ CPPFLAGS_FOR_BUILD='${CPPFLAGS_FOR_BUILD}' \ CFLAGS_FOR_BUILD='${CFLAGS_FOR_BUILD}' \ LDFLAGS_FOR_BUILD='${LDFLAGS_FOR_BUILD}' diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 45194d4d9..0e5d4852c 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -50,7 +50,7 @@ WRKSRC= ${WRKDIST}/${ICEDTEA_NAME}-${ICEDTEA_VERSION} PKG_SUBPKGS:= OPENJDK PKG_CHOICES_OPENJDK:= ZERO SHARK CACAO PKGCD_ZERO:= zero-assembly backend -PKGCD_SHARK:= JIT backend +PKGCD_SHARK:= Shark JIT backend PKGCB_SHARK:= llvm PKGCD_CACAO:= Cacao JIT backend PKGCD_JAMVM:= JamVM backend -- cgit v1.2.3 From 36c4d46389c888b948448b34284af1d7dfd60508 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 15 Aug 2011 12:18:17 +0200 Subject: fix compile for arm target --- jtools/Makefile | 2 +- jtools/qemu/Makefile | 32 ++++++++++++++++++++++++ mk/build.mk | 2 +- mk/vars.mk | 7 +++++- package/openjdk/Makefile | 2 ++ package/openjdk/patches/dlopen-RTLD_NOLOAD.patch | 13 ++++++++++ package/openjdk/patches/icedtea-arm-mkbc.patch | 26 +++++++++++++++++++ package/openjdk/patches/inc-path.patch | 31 +++++++++++++++-------- 8 files changed, 101 insertions(+), 14 deletions(-) create mode 100644 jtools/qemu/Makefile create mode 100644 package/openjdk/patches/dlopen-RTLD_NOLOAD.patch create mode 100644 package/openjdk/patches/icedtea-arm-mkbc.patch diff --git a/jtools/Makefile b/jtools/Makefile index 7ddaf23eb..728d46dac 100644 --- a/jtools/Makefile +++ b/jtools/Makefile @@ -6,7 +6,7 @@ include $(TOPDIR)/rules.mk TARGETS:= ifneq ($(ADK_PACKAGE_OPENJDK),) # jikes is for ant -TARGETS+=fastjar gcj ecj jikes classpath jamvm ant openjdk +TARGETS+=fastjar gcj ecj jikes classpath jamvm ant openjdk qemu endif TARGETS_INSTALL:=$(patsubst %,%-install,$(TARGETS)) diff --git a/jtools/qemu/Makefile b/jtools/qemu/Makefile new file mode 100644 index 000000000..bc2f89205 --- /dev/null +++ b/jtools/qemu/Makefile @@ -0,0 +1,32 @@ +# This file is part of the OpenADK project. OpenADK is copyrighted +# material, please see the LICENCE file in the top-level directory. + +include $(TOPDIR)/rules.mk + +PKG_NAME:= qemu +PKG_VERSION:= 0.14.1 +PKG_RELEASE:= 1 +PKG_MD5SUM:= b6c713a8db638e173af53a62d5178640 +PKG_SITES:= http://download.savannah.gnu.org/releases/qemu/ + +include ../rules.mk + +install: ${STAGING_JAVA_HOST_DIR}/usr/bin/qemu-arm + +$(WRKBUILD)/.configured: ${WRKDIST}/.prepared + (cd $(WRKBUILD); ./configure --prefix=/usr \ + --host-cc=$(CC_FOR_BUILD) \ + --disable-system \ + --disable-sdl \ + --target-list=arm-linux-user \ + ) + touch $@ + +$(WRKBUILD)/.compiled: ${WRKDIST}/.configured + ${MAKE} -C ${WRKBUILD} $(MAKE_TRACE) + touch $@ + +${STAGING_JAVA_HOST_DIR}/usr/bin/qemu-arm: $(WRKBUILD)/.compiled + ${MAKE} -C ${WRKBUILD} DESTDIR=$(STAGING_JAVA_HOST_DIR) install $(MAKE_TRACE) + +include $(TOPDIR)/mk/tools.mk diff --git a/mk/build.mk b/mk/build.mk index cd50be90f..854fdb19d 100644 --- a/mk/build.mk +++ b/mk/build.mk @@ -266,7 +266,7 @@ ifeq ($(filter-out distclean,${MAKECMDGOALS}),) include ${TOPDIR}/mk/vars.mk else include $(TOPDIR)/prereq.mk -export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD +export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD QEMU endif all: menuconfig diff --git a/mk/vars.mk b/mk/vars.mk index 3776b57b4..925635d01 100644 --- a/mk/vars.mk +++ b/mk/vars.mk @@ -47,6 +47,10 @@ TARGET_PATH= ${SCRIPT_DIR}:${TOOLS_DIR}:${STAGING_HOST_DIR}/bin:${STAGING_HOST_ REAL_GNU_TARGET_NAME= $(CPU_ARCH)-$(ADK_VENDOR)-linux-$(ADK_TARGET_SUFFIX) GNU_TARGET_NAME= $(CPU_ARCH)-$(ADK_VENDOR)-linux +ifeq ($(CPU_ARCH),arm) +QEMU:= qemu-arm +endif + ifeq ($(ADK_NATIVE),y) TARGET_CROSS:= TARGET_COMPILER_PREFIX?= @@ -138,7 +142,8 @@ TARGET_CONFIGURE_OPTS= PATH='${TARGET_PATH}' \ HOST_CONFIGURE_OPTS= CC_FOR_BUILD='${CC_FOR_BUILD}' \ CPPFLAGS_FOR_BUILD='${CPPFLAGS_FOR_BUILD}' \ CFLAGS_FOR_BUILD='${CFLAGS_FOR_BUILD}' \ - LDFLAGS_FOR_BUILD='${LDFLAGS_FOR_BUILD}' + LDFLAGS_FOR_BUILD='${LDFLAGS_FOR_BUILD}' \ + QEMU='$(QEMU)' PKG_SUFFIX:= $(strip $(subst ",, $(ADK_PACKAGE_SUFFIX))) diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 45194d4d9..2650341c5 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -26,6 +26,8 @@ PKG_SITES:= http://download.java.net/openjdk/jdk6/promoted/b22/ \ #PKG_CFLINE_OPENJDK:= depends on ADK_TARGET_LIB_GLIBC || ADK_TARGET_LIB_EGLIBC && !ADK_TARGET_SYSTEM_LEMOTE_YEELONG PKG_HOST_DEPENDS:= !darwin !cygwin !openbsd !netbsd !freebsd +PKG_ARCH_DEPENDS:= arm mips x86 x86_64 +PKG_SYSTEM_DEPENDS:= !lemote-yeelong !linksys-ag241 !fon-fon2100 # autotools infrastructure for OpenJDK ICEDTEA_NAME:= icedtea6 diff --git a/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch b/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch new file mode 100644 index 000000000..1baf3411b --- /dev/null +++ b/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch @@ -0,0 +1,13 @@ +the option RTLOD_NOLOAD is not portable. (not available in uClibc) +https://evolvis.org/scm/viewvc.php/jalimo/trunk/oe-overlay/packages/openjdk/openjdk-6-6b18-1.8/icedtea-jdk-RTLD_NOLOAD.patch?revision=840&view=markup&pathrev=867 +--- w-openjdk-6.orig/openjdk-6/jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c 2011-02-28 17:06:50.000000000 +0100 ++++ w-openjdk-6/openjdk-6/jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c 2011-08-10 14:41:26.700571862 +0200 +@@ -51,7 +51,7 @@ + { + const char *libName = (*env)->GetStringUTFChars(env, jLibName, NULL); + // look up existing handle only, do not load +- void *hModule = dlopen(libName, RTLD_NOLOAD); ++ void *hModule = dlopen(libName, RTLD_LAZY); + dprintf2("-handle for %s: %u\n", libName, hModule); + (*env)->ReleaseStringUTFChars(env, jLibName, libName); + return (jlong)hModule; diff --git a/package/openjdk/patches/icedtea-arm-mkbc.patch b/package/openjdk/patches/icedtea-arm-mkbc.patch new file mode 100644 index 000000000..1d481740f --- /dev/null +++ b/package/openjdk/patches/icedtea-arm-mkbc.patch @@ -0,0 +1,26 @@ +--- w-openjdk-6-1.orig/icedtea6-1.10/patches/arm.patch 2011-02-23 23:32:32.909601440 +0100 ++++ w-openjdk-6-1/icedtea6-1.10/patches/arm.patch 2011-08-09 20:05:56.721765260 +0200 +@@ -25,7 +25,7 @@ + + + +offsets_arm.s: mkoffsets + + @echo Generating assembler offsets +-+ ./mkoffsets > $@ +++ $(QEMU) ./mkoffsets > $@ + + + +bytecodes_arm.s: bytecodes_arm.def mkbc + + @echo Generatine ARM assembler bytecode sequences +@@ -33,12 +33,12 @@ + + + +mkbc: $(GAMMADIR)/tools/mkbc.c + + @echo Compiling mkbc tool +-+ $(CC_COMPILE) -o $@ $< $(COMPILE_DONE) +++ $(CC_FOR_BUILD) -o $@ $< $(COMPILE_DONE) + + + +mkoffsets: asm_helper.cpp + + @echo Compiling offset generator + + $(QUIETLY) $(REMOVE_TARGET) +-+ $(CC_COMPILE) -DSTATIC_OFFSETS -o $@ $< $(COMPILE_DONE) +++ $(CC_COMPILE) -static -DSTATIC_OFFSETS -o $@ $< $(COMPILE_DONE) + + + +endif + + diff --git a/package/openjdk/patches/inc-path.patch b/package/openjdk/patches/inc-path.patch index 32aaa919e..06c006685 100644 --- a/package/openjdk/patches/inc-path.patch +++ b/package/openjdk/patches/inc-path.patch @@ -1,14 +1,3 @@ ---- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/Defs.gmk 2011-02-28 17:06:10.000000000 +0100 -+++ w-openjdk-6-1/openjdk-6/jdk/make/common/Defs.gmk 2011-08-07 21:21:49.335286149 +0200 -@@ -173,7 +173,7 @@ - ifeq ($(DEVTOOLS_FT_DIR_EXISTS), true) - FREETYPE_HEADERS_PATH = $(DEVTOOLS_FT_DIR)/include - else -- FREETYPE_HEADERS_PATH = /usr/include -+ FREETYPE_HEADERS_PATH = /usr/include/disabled - endif - endif - endif --- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-02-28 17:06:10.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-08-08 10:07:58.975256728 +0200 @@ -170,7 +170,7 @@ @@ -20,3 +9,23 @@ # Import JDK images allow for partial builds, components not built are # imported (or copied from) these import areas when needed. +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/Defs.gmk 2011-02-28 17:06:10.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/jdk/make/common/Defs.gmk 2011-08-10 18:50:53.248017538 +0200 +@@ -156,7 +156,7 @@ + ifeq ($(DEVTOOLS_FT_DIR_EXISTS), true) + FREETYPE_LIB_PATH = $(DEVTOOLS_FT_DIR)/lib + else +- FREETYPE_LIB_PATH = /usr/lib ++ FREETYPE_LIB_PATH = /usr/lib/disabled + USING_SYSTEM_FT_LIB=true + endif + endif +@@ -173,7 +173,7 @@ + ifeq ($(DEVTOOLS_FT_DIR_EXISTS), true) + FREETYPE_HEADERS_PATH = $(DEVTOOLS_FT_DIR)/include + else +- FREETYPE_HEADERS_PATH = /usr/include ++ FREETYPE_HEADERS_PATH = /usr/include/disabled + endif + endif + endif -- cgit v1.2.3 From c228dba74d4b4536721f9537ad67ac70fd57afe0 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 15 Aug 2011 12:18:35 +0200 Subject: fix 64 bit build --- package/nss/Makefile | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/package/nss/Makefile b/package/nss/Makefile index 0c777b09b..7dcf8217d 100644 --- a/package/nss/Makefile +++ b/package/nss/Makefile @@ -29,7 +29,9 @@ $(eval $(call PKG_template,NSS,${PKG_NAME},$(PKG_VERSION)-${PKG_RELEASE},${PKG_D CONFIG_STYLE:= manual ifneq ($(ADK_LINUX_64),) -TARGET_CFLAGS+= -DUSE_64 -DNS_PTR_LE_32 +ifeq ($(ADK_LINUX_MIPS),y) +TARGET_CFLAGS+= -DNS_PTR_LE_32 +endif XAKE_FLAGS+= USE_64=1 endif -- cgit v1.2.3 From a749a1f34e0fe6d22e9858494cffac021c0034cc Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 17 Aug 2011 05:39:08 +0200 Subject: revert CXX_FOR_BUILD stuff, breaks gcj compile --- mk/build.mk | 2 +- mk/vars.mk | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/mk/build.mk b/mk/build.mk index 3e5d92e6f..854fdb19d 100644 --- a/mk/build.mk +++ b/mk/build.mk @@ -266,7 +266,7 @@ ifeq ($(filter-out distclean,${MAKECMDGOALS}),) include ${TOPDIR}/mk/vars.mk else include $(TOPDIR)/prereq.mk -export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD CXX_FOR_BUILD QEMU +export BASH MAKE LANGUAGE LC_ALL OStype PATH CC_FOR_BUILD QEMU endif all: menuconfig diff --git a/mk/vars.mk b/mk/vars.mk index 893416ab2..925635d01 100644 --- a/mk/vars.mk +++ b/mk/vars.mk @@ -140,7 +140,6 @@ TARGET_CONFIGURE_OPTS= PATH='${TARGET_PATH}' \ CROSS='$(TARGET_CROSS)' HOST_CONFIGURE_OPTS= CC_FOR_BUILD='${CC_FOR_BUILD}' \ - CXX_FOR_BUILD='${CXX_FOR_BUILD}' \ CPPFLAGS_FOR_BUILD='${CPPFLAGS_FOR_BUILD}' \ CFLAGS_FOR_BUILD='${CFLAGS_FOR_BUILD}' \ LDFLAGS_FOR_BUILD='${LDFLAGS_FOR_BUILD}' \ -- cgit v1.2.3 From 4c863c8a5d97ba758af95b153a99d80cf34216d1 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 17 Aug 2011 05:55:38 +0200 Subject: fix small bug, use architecture for filename qemu- --- scripts/update-sys | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/update-sys b/scripts/update-sys index bcfbfa84e..268184428 100755 --- a/scripts/update-sys +++ b/scripts/update-sys @@ -50,7 +50,7 @@ config $archsym EOF if [ "${system}" = "toolchain" -o "${system}" = "qemu" ];then - sys=${system}-$cpuarch + sys=${system}-$arch else sys=$system fi -- cgit v1.2.3 From 86dfed8c166fbbdf03985b46eb3c69b4ec1030b1 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 18:09:48 +0200 Subject: some kernels use LZMA, some XZ by default now. Check both tools. --- scripts/scan-tools.sh | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/scripts/scan-tools.sh b/scripts/scan-tools.sh index 8834940c7..4ffe44649 100644 --- a/scripts/scan-tools.sh +++ b/scripts/scan-tools.sh @@ -112,8 +112,14 @@ if ! which gzip >/dev/null 2>&1; then out=1 fi -if ! which lzma >/dev/null 2>&1 && ! which xz >/dev/null 2>&1; then - echo You must install lzma or xz-utils to continue. +if ! which lzma >/dev/null 2>&1; then + echo You must install lzma to continue. + echo + out=1 +fi + +if ! which xz >/dev/null 2>&1; then + echo You must install xz-utils to continue. echo out=1 fi -- cgit v1.2.3 From 26020e730fb30663e7a4acfaa0ba0274d6cbf0eb Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 18:10:35 +0200 Subject: remove from image and kernel filenames. they are implicitely known. --- mk/image.mk | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/mk/image.mk b/mk/image.mk index 24e31aa0b..8053ba43d 100644 --- a/mk/image.mk +++ b/mk/image.mk @@ -65,12 +65,12 @@ kernel-package: $(KERNEL) $(TRACE) target/$(ADK_TARGET_ARCH)-install-kernel-package $(PKG_INSTALL) $(KERNEL_PKG) $(MAKE_TRACE) -TARGET_KERNEL= ${ADK_TARGET_SYSTEM}-${CPU_ARCH}-${ADK_TARGET_FS}-kernel -INITRAMFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_ARCH}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS} -ROOTFSSQUASHFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_ARCH}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.img -ROOTFSTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_ARCH}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}+kernel.tar.gz -ROOTFSUSERTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_ARCH}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.tar.gz -INITRAMFS_PIGGYBACK= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_ARCH}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.cpio +TARGET_KERNEL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_FS}-kernel +INITRAMFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS} +ROOTFSSQUASHFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.img +ROOTFSTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}+kernel.tar.gz +ROOTFSUSERTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.tar.gz +INITRAMFS_PIGGYBACK= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.cpio ${BIN_DIR}/${ROOTFSTARBALL}: ${TARGET_DIR} kernel-package cd ${TARGET_DIR}; find . | sed -n '/^\.\//s///p' | \ -- cgit v1.2.3 From 9519af69775d89b379f83b5a6c72740a20d7b6ef Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 18:10:52 +0200 Subject: compile qemu for more archs --- jtools/qemu/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jtools/qemu/Makefile b/jtools/qemu/Makefile index bc2f89205..c83a6d987 100644 --- a/jtools/qemu/Makefile +++ b/jtools/qemu/Makefile @@ -18,7 +18,7 @@ $(WRKBUILD)/.configured: ${WRKDIST}/.prepared --host-cc=$(CC_FOR_BUILD) \ --disable-system \ --disable-sdl \ - --target-list=arm-linux-user \ + --target-list=arm-linux-user,i386-linux-user,mipsel-linux-user \ ) touch $@ -- cgit v1.2.3 From b83a99b16e9a89df4baa1c6cd6e33193a841c848 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 18:11:16 +0200 Subject: refresh kernel config --- target/arm/kernel.config | 113 +++++++++++++++++++++++++++++++++-------------- 1 file changed, 81 insertions(+), 32 deletions(-) diff --git a/target/arm/kernel.config b/target/arm/kernel.config index c602fdffa..d107d697a 100644 --- a/target/arm/kernel.config +++ b/target/arm/kernel.config @@ -1,15 +1,15 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.36 -# Sat Dec 25 17:40:46 2010 +# Linux/arm 2.6.39 Kernel Configuration +# Fri Aug 19 17:47:30 2011 # CONFIG_ARM=y CONFIG_SYS_SUPPORTS_APM_EMULATION=y CONFIG_GENERIC_GPIO=y # CONFIG_ARCH_USES_GETTIMEOFFSET is not set CONFIG_GENERIC_CLOCKEVENTS=y +CONFIG_KTIME_SCALAR=y CONFIG_HAVE_PROC_CPU=y -CONFIG_GENERIC_HARDIRQS=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y @@ -17,13 +17,15 @@ CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_HARDIRQS_SW_RESEND=y CONFIG_GENERIC_IRQ_PROBE=y CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_ARCH_HAS_CPU_IDLE_WAIT=y CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_NEED_DMA_MAP_STATE=y -CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y CONFIG_VECTORS_BASE=0xffff0000 +# CONFIG_ARM_PATCH_PHYS_VIRT is not set CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y +CONFIG_HAVE_IRQ_WORK=y # # General setup @@ -35,40 +37,47 @@ CONFIG_CROSS_COMPILE="" CONFIG_LOCALVERSION="" # CONFIG_LOCALVERSION_AUTO is not set CONFIG_HAVE_KERNEL_GZIP=y -CONFIG_HAVE_KERNEL_BZIP2=y CONFIG_HAVE_KERNEL_LZMA=y CONFIG_HAVE_KERNEL_LZO=y # CONFIG_KERNEL_GZIP is not set -# CONFIG_KERNEL_BZIP2 is not set CONFIG_KERNEL_LZMA=y # CONFIG_KERNEL_LZO is not set CONFIG_SYSVIPC=y CONFIG_SYSVIPC_SYSCTL=y # CONFIG_POSIX_MQUEUE is not set # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set +CONFIG_HAVE_GENERIC_HARDIRQS=y + +# +# IRQ subsystem +# +CONFIG_GENERIC_HARDIRQS=y +CONFIG_HAVE_SPARSE_IRQ=y +CONFIG_GENERIC_IRQ_SHOW=y +# CONFIG_SPARSE_IRQ is not set # # RCU Subsystem # -CONFIG_TREE_RCU=y -# CONFIG_TINY_RCU is not set +CONFIG_TINY_RCU=y +# CONFIG_PREEMPT_RCU is not set # CONFIG_RCU_TRACE is not set -CONFIG_RCU_FANOUT=32 -# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=17 # CONFIG_CGROUPS is not set -# CONFIG_SYSFS_DEPRECATED_V2 is not set -# CONFIG_RELAY is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set +# CONFIG_SYSFS_DEPRECATED is not set +# CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_UID16=y CONFIG_SYSCTL_SYSCALL=y # CONFIG_KALLSYMS is not set @@ -84,6 +93,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y CONFIG_HAVE_PERF_EVENTS=y CONFIG_PERF_USE_VMALLOC=y @@ -104,6 +114,7 @@ CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_REGS_AND_STACK_ACCESS_API=y CONFIG_HAVE_CLK=y +CONFIG_HAVE_DMA_API_DEBUG=y # # GCOV-based kernel profiling @@ -119,8 +130,6 @@ CONFIG_MODULE_FORCE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set # CONFIG_BLOCK is not set -# CONFIG_DEFAULT_CFQ is not set -# CONFIG_DEFAULT_NOOP is not set # CONFIG_INLINE_SPIN_TRYLOCK is not set # CONFIG_INLINE_SPIN_TRYLOCK_BH is not set # CONFIG_INLINE_SPIN_LOCK is not set @@ -150,13 +159,12 @@ CONFIG_INLINE_WRITE_UNLOCK=y CONFIG_INLINE_WRITE_UNLOCK_IRQ=y # CONFIG_INLINE_WRITE_UNLOCK_IRQRESTORE is not set # CONFIG_MUTEX_SPIN_ON_OWNER is not set -# CONFIG_FREEZER is not set +CONFIG_FREEZER=y # # System Type # CONFIG_MMU=y -# CONFIG_ARCH_AAEC2000 is not set # CONFIG_ARCH_INTEGRATOR is not set # CONFIG_ARCH_REALVIEW is not set # CONFIG_ARCH_VERSATILE is not set @@ -170,6 +178,7 @@ CONFIG_ARCH_AT91=y # CONFIG_ARCH_EP93XX is not set # CONFIG_ARCH_FOOTBRIDGE is not set # CONFIG_ARCH_MXC is not set +# CONFIG_ARCH_MXS is not set # CONFIG_ARCH_STMP3XXX is not set # CONFIG_ARCH_NETX is not set # CONFIG_ARCH_H720X is not set @@ -199,19 +208,20 @@ CONFIG_ARCH_AT91=y # CONFIG_ARCH_SA1100 is not set # CONFIG_ARCH_S3C2410 is not set # CONFIG_ARCH_S3C64XX is not set -# CONFIG_ARCH_S5P6440 is not set +# CONFIG_ARCH_S5P64X0 is not set # CONFIG_ARCH_S5P6442 is not set # CONFIG_ARCH_S5PC100 is not set # CONFIG_ARCH_S5PV210 is not set -# CONFIG_ARCH_S5PV310 is not set +# CONFIG_ARCH_EXYNOS4 is not set # CONFIG_ARCH_SHARK is not set -# CONFIG_ARCH_LH7A40X is not set +# CONFIG_ARCH_TCC_926 is not set # CONFIG_ARCH_U300 is not set # CONFIG_ARCH_U8500 is not set # CONFIG_ARCH_NOMADIK is not set # CONFIG_ARCH_DAVINCI is not set # CONFIG_ARCH_OMAP is not set # CONFIG_PLAT_SPEAR is not set +# CONFIG_ARCH_VT8500 is not set CONFIG_HAVE_AT91_USART3=y # @@ -256,6 +266,7 @@ CONFIG_AT91_PMC_UNIT=y # AT91 Feature Selections # # CONFIG_AT91_PROGRAMMABLE_CLOCKS is not set +# CONFIG_AT91_SLOW_CLOCK is not set CONFIG_AT91_TIMER_HZ=128 CONFIG_AT91_EARLY_DBGU=y # CONFIG_AT91_EARLY_USART0 is not set @@ -263,6 +274,10 @@ CONFIG_AT91_EARLY_DBGU=y # CONFIG_AT91_EARLY_USART2 is not set # CONFIG_AT91_EARLY_USART3 is not set +# +# System MMU +# + # # Processor Type # @@ -276,6 +291,7 @@ CONFIG_CPU_COPY_V4WB=y CONFIG_CPU_TLB_V4WBI=y CONFIG_CPU_CP15=y CONFIG_CPU_CP15_MMU=y +CONFIG_CPU_USE_DOMAINS=y # # Processor Features @@ -312,7 +328,6 @@ CONFIG_AEABI=y # CONFIG_ARCH_SPARSEMEM_DEFAULT is not set # CONFIG_ARCH_SELECT_MEMORY_MODEL is not set # CONFIG_HIGHMEM is not set -# CONFIG_SPARSE_IRQ is not set CONFIG_SELECT_MEMORY_MODEL=y CONFIG_FLATMEM_MANUAL=y CONFIG_FLATMEM=y @@ -320,15 +335,18 @@ CONFIG_FLAT_NODE_MEM_MAP=y CONFIG_HAVE_MEMBLOCK=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=999999 +# CONFIG_COMPACTION is not set # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y # CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 +CONFIG_NEED_PER_CPU_KM=y CONFIG_FORCE_MAX_ZONEORDER=11 # CONFIG_LEDS is not set CONFIG_ALIGNMENT_TRAP=y # CONFIG_UACCESS_WITH_MEMCPY is not set +# CONFIG_SECCOMP is not set # CONFIG_CC_STACKPROTECTOR is not set # CONFIG_DEPRECATED_PARAM_STRUCT is not set @@ -340,6 +358,7 @@ CONFIG_ZBOOT_ROM_BSS=0 CONFIG_CMDLINE="" # CONFIG_XIP_KERNEL is not set # CONFIG_KEXEC is not set +# CONFIG_CRASH_DUMP is not set # CONFIG_AUTO_ZRELADDR is not set # @@ -366,7 +385,13 @@ CONFIG_HAVE_AOUT=y # # Power management options # -# CONFIG_PM is not set +CONFIG_SUSPEND=y +CONFIG_SUSPEND_FREEZER=y +CONFIG_PM_SLEEP=y +# CONFIG_PM_RUNTIME is not set +CONFIG_PM=y +# CONFIG_PM_DEBUG is not set +# CONFIG_APM_EMULATION is not set CONFIG_ARCH_SUSPEND_POSSIBLE=y CONFIG_NET=y @@ -379,10 +404,9 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set -# CONFIG_NET_IPGRE is not set +# CONFIG_NET_IPGRE_DEMUX is not set # CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set @@ -423,6 +447,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -438,6 +463,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set # CONFIG_CAIF is not set +# CONFIG_CEPH_LIB is not set # # Device Drivers @@ -484,9 +510,12 @@ CONFIG_SCSI_MOD=y # Character devices # # CONFIG_VT is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set # CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers @@ -505,9 +534,8 @@ CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_TIMBERDALE is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set +# CONFIG_TTY_PRINTK is not set +# CONFIG_HVC_DCC is not set # CONFIG_IPMI_HANDLER is not set # CONFIG_HW_RANDOM is not set # CONFIG_R3964 is not set @@ -521,6 +549,10 @@ CONFIG_UNIX98_PTYS=y # PPS support # # CONFIG_PPS is not set + +# +# PPS generators support +# CONFIG_ARCH_REQUIRE_GPIOLIB=y CONFIG_GPIOLIB=y # CONFIG_GPIO_SYSFS is not set @@ -528,6 +560,7 @@ CONFIG_GPIOLIB=y # # Memory mapped GPIO expanders: # +# CONFIG_GPIO_BASIC_MMIO is not set # CONFIG_GPIO_IT8761E is not set # @@ -582,6 +615,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set +# CONFIG_NFC_DEVICES is not set # CONFIG_ACCESSIBILITY is not set CONFIG_RTC_LIB=y # CONFIG_RTC_CLASS is not set @@ -593,12 +627,15 @@ CONFIG_RTC_LIB=y # # File systems # +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set +# CONFIG_FANOTIFY is not set # CONFIG_QUOTA is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_QUOTACTL is not set # CONFIG_AUTOFS4_FS is not set # CONFIG_FUSE_FS is not set @@ -621,12 +658,12 @@ CONFIG_TMPFS=y # CONFIG_MISC_FILESYSTEMS is not set # CONFIG_NETWORK_FILESYSTEMS is not set # CONFIG_NLS is not set -# CONFIG_DLM is not set # # Kernel hacking # CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -635,18 +672,26 @@ CONFIG_MAGIC_SYSRQ=y # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set +# CONFIG_SPARSE_RCU_POINTER is not set # CONFIG_DEBUG_MEMORY_INIT is not set CONFIG_FRAME_POINTER=y -# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set CONFIG_HAVE_FUNCTION_TRACER=y +CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y +CONFIG_HAVE_DYNAMIC_FTRACE=y +CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y +CONFIG_HAVE_C_RECORDMCOUNT=y CONFIG_TRACING_SUPPORT=y # CONFIG_FTRACE is not set +# CONFIG_DMA_API_DEBUG is not set # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_TEST_KSTRTOX is not set +# CONFIG_STRICT_DEVMEM is not set # CONFIG_ARM_UNWIND is not set # CONFIG_DEBUG_USER is not set # CONFIG_OC_ETM is not set @@ -655,6 +700,7 @@ CONFIG_HAVE_ARCH_KGDB=y # Security options # # CONFIG_KEYS is not set +# CONFIG_SECURITY_DMESG_RESTRICT is not set # CONFIG_SECURITY is not set # CONFIG_SECURITYFS is not set CONFIG_DEFAULT_SECURITY_DAC=y @@ -679,8 +725,11 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y CONFIG_GENERIC_ATOMIC64=y +# CONFIG_AVERAGE is not set -- cgit v1.2.3 From 9637f7746433e32ce710f0094aee29eea994195f Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 18:11:35 +0200 Subject: more qemu archs for OpenJDK --- mk/vars.mk | 9 +++++++++ package/openjdk/Makefile | 6 +++++- .../openjdk/patches/shark-adlc-cross-compile.patch | 20 ++++++++++++++++++++ 3 files changed, 34 insertions(+), 1 deletion(-) create mode 100644 package/openjdk/patches/shark-adlc-cross-compile.patch diff --git a/mk/vars.mk b/mk/vars.mk index 925635d01..d4f64d068 100644 --- a/mk/vars.mk +++ b/mk/vars.mk @@ -50,6 +50,15 @@ GNU_TARGET_NAME= $(CPU_ARCH)-$(ADK_VENDOR)-linux ifeq ($(CPU_ARCH),arm) QEMU:= qemu-arm endif +ifeq ($(CPU_ARCH),mipsel) +QEMU:= qemu-mipsel +endif +ifeq ($(CPU_ARCH),i586) +QEMU:= qemu-i386 +endif +ifeq ($(CPU_ARCH),i686) +QEMU:= qemu-i386 +endif ifeq ($(ADK_NATIVE),y) TARGET_CROSS:= diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 62786add7..56097f6f8 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -52,7 +52,7 @@ WRKSRC= ${WRKDIST}/${ICEDTEA_NAME}-${ICEDTEA_VERSION} PKG_SUBPKGS:= OPENJDK PKG_CHOICES_OPENJDK:= ZERO SHARK CACAO PKGCD_ZERO:= zero-assembly backend -PKGCD_SHARK:= Shark JIT backend +PKGCD_SHARK:= Shark JIT backend (needs eglibc/glibc) PKGCB_SHARK:= llvm PKGCD_CACAO:= Cacao JIT backend PKGCD_JAMVM:= JamVM backend @@ -61,6 +61,7 @@ include $(TOPDIR)/mk/package.mk $(eval $(call PKG_template,OPENJDK,openjdk,$(PKG_VERSION)-${PKG_RELEASE},${PKG_DEPENDS},${PKG_DESCR},${PKG_SECTION})) + TARGET_CFLAGS:= $(filter-out -fhonour-copts,$(TARGET_CFLAGS)) BOOTSTRAPJDK:= ${STAGING_JAVA_HOST_DIR}/bootstrap-jdk @@ -110,6 +111,9 @@ ALL_TARGET:= icedtea # add include path for Xrender.h from staging directory post-patch: +ifeq ($(QEMU),) + $(error Fatal error: $$QEMU not set!) +endif $(SED) "s#@ADK_TARGETDIR@#$(STAGING_TARGET_DIR)#" ${WRKDIST}/$(PKG_NAME)-$(PKG_VERSION)/jdk/make/sun/xawt/Makefile do-extract: diff --git a/package/openjdk/patches/shark-adlc-cross-compile.patch b/package/openjdk/patches/shark-adlc-cross-compile.patch new file mode 100644 index 000000000..79670f9ac --- /dev/null +++ b/package/openjdk/patches/shark-adlc-cross-compile.patch @@ -0,0 +1,20 @@ +--- w-openjdk-6.orig/openjdk-6/hotspot/make/linux/makefiles/adlc.make 2011-02-28 17:03:13.000000000 +0100 ++++ w-openjdk-6/openjdk-6/hotspot/make/linux/makefiles/adlc.make 2011-08-17 13:05:55.317470977 +0200 +@@ -103,7 +103,7 @@ + + $(EXEC) : $(OBJECTS) + @echo Making adlc +- $(QUIETLY) $(LINK_NOPROF.CC) -o $(EXEC) $(OBJECTS) ++ $(QUIETLY) $(LINK_NOPROF.CC) -static -o $(EXEC) $(OBJECTS) + + # Random dependencies: + $(OBJECTS): opcodes.hpp classes.hpp adlc.hpp adlcVMDeps.hpp adlparse.hpp archDesc.hpp arena.hpp dict2.hpp filebuff.hpp forms.hpp formsopt.hpp formssel.hpp +@@ -170,7 +170,7 @@ + # + refresh_adfiles: $(EXEC) $(SOURCE.AD) $(ADLC_UPDATER) + @rm -rf $(TEMPDIR); mkdir $(TEMPDIR) +- $(QUIETLY) $(EXEC) $(ADLCFLAGS) $(SOURCE.AD) \ ++ $(QEMU) $(EXEC) $(ADLCFLAGS) $(SOURCE.AD) \ + -c$(TEMPDIR)/ad_$(Platform_arch_model).cpp -h$(TEMPDIR)/ad_$(Platform_arch_model).hpp -a$(TEMPDIR)/dfa_$(Platform_arch_model).cpp -v$(TEMPDIR)/adGlobals_$(Platform_arch_model).hpp \ + || { rm -rf $(TEMPDIR); exit 1; } + $(QUIETLY) ./$(ADLC_UPDATER) ad_$(Platform_arch_model).cpp $(TEMPDIR) $(OUTDIR) -- cgit v1.2.3 From b6fed3d8f011df89e166b673a2bbee6d7bdee734 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 19:46:02 +0200 Subject: use native ecj, comment some patches --- package/openjdk/Makefile | 2 + package/openjdk/patches/cross-compile.patch | 3 + package/openjdk/patches/disable-backtrace.patch | 3 + .../openjdk/patches/disable-freetype-check.patch | 5 +- package/openjdk/patches/disable-gamma.patch | 3 + package/openjdk/patches/dlopen-RTLD_NOLOAD.patch | 6 +- package/openjdk/patches/icedtea-arm-mkbc.patch | 3 + package/openjdk/patches/icedtea6-Makefile_in.patch | 78 ++++++++++++++++++++++ package/openjdk/patches/iconv.patch | 19 +----- package/openjdk/patches/inc-path.patch | 3 + package/openjdk/patches/llvm-headers.patch | 3 + package/openjdk/patches/openjdk-6_Makefile.patch | 16 +++++ .../patches/patch-icedtea6-1_10_Makefile_in | 78 ---------------------- package/openjdk/patches/patch-openjdk-6_Makefile | 13 ---- package/openjdk/patches/remove-libnsl.patch | 3 + .../openjdk/patches/shark-adlc-cross-compile.patch | 3 + package/openjdk/patches/uClibc-compat.patch | 4 ++ 17 files changed, 135 insertions(+), 110 deletions(-) create mode 100644 package/openjdk/patches/icedtea6-Makefile_in.patch create mode 100644 package/openjdk/patches/openjdk-6_Makefile.patch delete mode 100644 package/openjdk/patches/patch-icedtea6-1_10_Makefile_in delete mode 100644 package/openjdk/patches/patch-openjdk-6_Makefile diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 56097f6f8..ad8f29778 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -99,11 +99,13 @@ CONFIGURE_ARGS+= --disable-docs \ CONFIGURE_ENV+= PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin MAKE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ + ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ GCC_HONOUR_COPTS=s \ TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) OPENJDK_NATIVE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ + ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) diff --git a/package/openjdk/patches/cross-compile.patch b/package/openjdk/patches/cross-compile.patch index afc00b032..604b5d6cb 100644 --- a/package/openjdk/patches/cross-compile.patch +++ b/package/openjdk/patches/cross-compile.patch @@ -1,3 +1,6 @@ + + disable wrong pathes to /usr, fix cross-compile + --- w-openjdk-6-1.orig/openjdk-6/jdk/make/sun/awt/Makefile 2011-02-28 17:06:11.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/make/sun/awt/Makefile 2011-08-07 17:00:37.676468717 +0200 @@ -509,10 +509,7 @@ diff --git a/package/openjdk/patches/disable-backtrace.patch b/package/openjdk/patches/disable-backtrace.patch index b54c95741..f3d1424c1 100644 --- a/package/openjdk/patches/disable-backtrace.patch +++ b/package/openjdk/patches/disable-backtrace.patch @@ -1,3 +1,6 @@ + + uClibc does not have backtrace support right now. Disable it for now. + --- w-openjdk-6-1.orig/openjdk-6/jdk/src/solaris/native/sun/xawt/XToolkit.c 2011-02-28 17:06:50.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/src/solaris/native/sun/xawt/XToolkit.c 2011-08-08 10:45:01.445330729 +0200 @@ -27,9 +27,6 @@ diff --git a/package/openjdk/patches/disable-freetype-check.patch b/package/openjdk/patches/disable-freetype-check.patch index 5f5f6cf83..cde23910d 100644 --- a/package/openjdk/patches/disable-freetype-check.patch +++ b/package/openjdk/patches/disable-freetype-check.patch @@ -1,4 +1,7 @@ ---- w-openjdk-6-1.orig/openjdk-6.orig/jdk/make/common/shared/Sanity.gmk 2011-02-28 17:06:10.000000000 +0100 + + disable freetype sanity check, not cross-compile safe. + +--- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/shared/Sanity.gmk 2011-02-28 17:06:10.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/make/common/shared/Sanity.gmk 2011-04-05 14:05:29.691807661 +0200 @@ -793,7 +793,7 @@ # Check for availability of FreeType (OpenJDK specific) diff --git a/package/openjdk/patches/disable-gamma.patch b/package/openjdk/patches/disable-gamma.patch index 92a80b3be..5dc1b2723 100644 --- a/package/openjdk/patches/disable-gamma.patch +++ b/package/openjdk/patches/disable-gamma.patch @@ -1,3 +1,6 @@ + + Fails when cross-compilation is done, disable it. + --- w-openjdk-6-1.orig/openjdk-6/hotspot/make/linux/makefiles/buildtree.make 2011-02-28 17:03:13.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/hotspot/make/linux/makefiles/buildtree.make 2011-04-11 12:47:31.000000000 +0200 @@ -352,12 +352,8 @@ diff --git a/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch b/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch index 1baf3411b..cd228391b 100644 --- a/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch +++ b/package/openjdk/patches/dlopen-RTLD_NOLOAD.patch @@ -1,5 +1,7 @@ -the option RTLOD_NOLOAD is not portable. (not available in uClibc) -https://evolvis.org/scm/viewvc.php/jalimo/trunk/oe-overlay/packages/openjdk/openjdk-6-6b18-1.8/icedtea-jdk-RTLD_NOLOAD.patch?revision=840&view=markup&pathrev=867 + + the option RTLOD_NOLOAD is not portable. (not available in uClibc) + https://evolvis.org/scm/viewvc.php/jalimo/trunk/oe-overlay/packages/openjdk/openjdk-6-6b18-1.8/icedtea-jdk-RTLD_NOLOAD.patch?revision=840&view=markup&pathrev=867 + --- w-openjdk-6.orig/openjdk-6/jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c 2011-02-28 17:06:50.000000000 +0100 +++ w-openjdk-6/openjdk-6/jdk/src/solaris/native/sun/security/pkcs11/j2secmod_md.c 2011-08-10 14:41:26.700571862 +0200 @@ -51,7 +51,7 @@ diff --git a/package/openjdk/patches/icedtea-arm-mkbc.patch b/package/openjdk/patches/icedtea-arm-mkbc.patch index 1d481740f..9df3ebbf4 100644 --- a/package/openjdk/patches/icedtea-arm-mkbc.patch +++ b/package/openjdk/patches/icedtea-arm-mkbc.patch @@ -1,3 +1,6 @@ + + execute mkoffsets via Qemu and build mkbc with the host compiler. + --- w-openjdk-6-1.orig/icedtea6-1.10/patches/arm.patch 2011-02-23 23:32:32.909601440 +0100 +++ w-openjdk-6-1/icedtea6-1.10/patches/arm.patch 2011-08-09 20:05:56.721765260 +0200 @@ -25,7 +25,7 @@ diff --git a/package/openjdk/patches/icedtea6-Makefile_in.patch b/package/openjdk/patches/icedtea6-Makefile_in.patch new file mode 100644 index 000000000..193e008aa --- /dev/null +++ b/package/openjdk/patches/icedtea6-Makefile_in.patch @@ -0,0 +1,78 @@ +--- w-openjdk-6-1.orig/icedtea6-1.10/Makefile.in 2011-03-02 20:48:45.000000000 +0100 ++++ w-openjdk-6-1/icedtea6-1.10/Makefile.in 2011-04-02 23:33:17.000000000 +0200 +@@ -328,7 +328,7 @@ + am__untar = @am__untar@ + bindir = @bindir@ + build = @build@ +-build_alias = @build_alias@ ++build_alias = ${BUILD_ALIAS} + build_cpu = @build_cpu@ + build_os = @build_os@ + build_vendor = @build_vendor@ +@@ -339,7 +339,7 @@ + dvidir = @dvidir@ + exec_prefix = @exec_prefix@ + host = @host@ +-host_alias = @host_alias@ ++host_alias = ${HOST_ALIAS} + host_cpu = @host_cpu@ + host_os = @host_os@ + host_vendor = @host_vendor@ +@@ -362,7 +362,7 @@ + sharedstatedir = @sharedstatedir@ + srcdir = @srcdir@ + sysconfdir = @sysconfdir@ +-target_alias = @target_alias@ ++target_alias = ${TARGET_ALIAS} + top_build_prefix = @top_build_prefix@ + top_builddir = @top_builddir@ + top_srcdir = @top_srcdir@ +@@ -1329,7 +1329,7 @@ stamps/extract-openjdk.stamp: stamps/dow + @OPENJDK_SRC_DIR_FOUND_TRUE@ cp -pPR $(OPENJDK_SRC_DIR_LINK) $(OPENJDK_SRC_DIR) openjdk ; \ + @OPENJDK_SRC_DIR_FOUND_TRUE@ fi + @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ if ! test -d openjdk ; then \ +-@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPRl openjdk.hg openjdk ; \ ++@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPR openjdk.hg openjdk ; \ + @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ fi + @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ set -e ; \ + @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ if ! test -d openjdk ; \ +@@ -1576,7 +1576,7 @@ clean-overlay: + # FIXME (missing): Rename to clone-ecj. + stamps/extract-ecj.stamp: $(OPENJDK_TREE) + if ! test -d openjdk-ecj ; then \ +- cp -pPRl openjdk openjdk-ecj ; \ ++ cp -pPR openjdk openjdk-ecj ; \ + fi + mkdir -p stamps + touch stamps/extract-ecj.stamp +@@ -1642,11 +1642,15 @@ clean-patch-ecj: + # =========================== + + stamps/native-ecj.stamp: +- mkdir -p stamps ; \ +- if test "x$(GCJ)" != "xno"; then \ +- $(GCJ) $(IT_CFLAGS) -Wl,-Bsymbolic -findirect-dispatch -o native-ecj \ +- --main=org.eclipse.jdt.internal.compiler.batch.Main ${ECJ_JAR} ; \ +- fi ; \ ++ mkdir -p stamps ; \ ++ if test -n "${ADK_ECJ}" && test -x "${ADK_ECJ}"; then \ ++ ln -s "${ADK_ECJ}" native-ecj; \ ++ else \ ++ if test "x$(GCJ)" != "xno"; then \ ++ $(GCJ) $(IT_CFLAGS) -Wl,-Bsymbolic -findirect-dispatch -o native-ecj \ ++ --main=org.eclipse.jdt.internal.compiler.batch.Main ${ECJ_JAR} ; \ ++ fi ; \ ++ fi; \ + touch stamps/native-ecj.stamp + + clean-native-ecj: +@@ -2167,6 +2167,9 @@ + stamps/jamvm.stamp: $(OPENJDK_TREE) stamps/rt.stamp + @BUILD_JAMVM_TRUE@ cd jamvm/jamvm && \ + @BUILD_JAMVM_TRUE@ ./autogen.sh --with-java-runtime-library=openjdk \ ++@BUILD_JAMVM_TRUE@ --host=$(host_alias) \ ++@BUILD_JAMVM_TRUE@ --build=$(build_alias) \ ++@BUILD_JAMVM_TRUE@ --target=$(target_alias) \ + @BUILD_JAMVM_TRUE@ --prefix=$(abs_top_builddir)/jamvm/install ; \ + @BUILD_JAMVM_TRUE@ $(MAKE) ; \ + @BUILD_JAMVM_TRUE@ $(MAKE) install diff --git a/package/openjdk/patches/iconv.patch b/package/openjdk/patches/iconv.patch index 16a6946f6..b79971930 100644 --- a/package/openjdk/patches/iconv.patch +++ b/package/openjdk/patches/iconv.patch @@ -1,17 +1,6 @@ -diff -Nur w-openjdk-6.orig/openjdk-6/hotspot/make/linux/makefiles/gcc.make w-openjdk-6/openjdk-6/hotspot/make/linux/makefiles/gcc.make ---- w-openjdk-6.orig/openjdk-6/hotspot/make/linux/makefiles/gcc.make 2011-02-28 17:03:13.000000000 +0100 -+++ w-openjdk-6/openjdk-6/hotspot/make/linux/makefiles/gcc.make 2011-04-11 18:36:16.837665258 +0200 -@@ -108,9 +108,6 @@ - CFLAGS += -pipe - endif - --# Compiler warnings are treated as errors --WARNINGS_ARE_ERRORS = -Werror -- - # Except for a few acceptable ones - # Since GCC 4.3, -Wconversion has changed its meanings to warn these implicit - # conversions which might affect the values. To avoid that, we need to turn -diff -Nur w-openjdk-6.orig/openjdk-6/jdk/make/java/instrument/Makefile w-openjdk-6/openjdk-6/jdk/make/java/instrument/Makefile + + add required linker flags. + --- w-openjdk-6.orig/openjdk-6/jdk/make/java/instrument/Makefile 2011-02-28 17:06:10.000000000 +0100 +++ w-openjdk-6/openjdk-6/jdk/make/java/instrument/Makefile 2011-04-11 23:14:27.571411016 +0200 @@ -123,6 +123,8 @@ @@ -23,7 +12,6 @@ diff -Nur w-openjdk-6.orig/openjdk-6/jdk/make/java/instrument/Makefile w-openjdk # # Add to ambient vpath so we pick up the library files # -diff -Nur w-openjdk-6.orig/openjdk-6/jdk/make/java/npt/Makefile w-openjdk-6/openjdk-6/jdk/make/java/npt/Makefile --- w-openjdk-6.orig/openjdk-6/jdk/make/java/npt/Makefile 2011-02-28 17:06:11.000000000 +0100 +++ w-openjdk-6/openjdk-6/jdk/make/java/npt/Makefile 2011-04-11 23:14:07.017670197 +0200 @@ -65,6 +65,8 @@ @@ -35,7 +23,6 @@ diff -Nur w-openjdk-6.orig/openjdk-6/jdk/make/java/npt/Makefile w-openjdk-6/open # Add -export options to explicitly spell exported symbols ifeq ($(PLATFORM), windows) OTHER_LCF += -export:nptInitialize -export:nptTerminate -diff -Nur w-openjdk-6.orig/openjdk-6/jdk/make/sun/splashscreen/Makefile w-openjdk-6/openjdk-6/jdk/make/sun/splashscreen/Makefile --- w-openjdk-6.orig/openjdk-6/jdk/make/sun/splashscreen/Makefile 2011-02-28 17:06:12.000000000 +0100 +++ w-openjdk-6/openjdk-6/jdk/make/sun/splashscreen/Makefile 2011-04-11 23:15:07.221411030 +0200 @@ -55,6 +55,8 @@ diff --git a/package/openjdk/patches/inc-path.patch b/package/openjdk/patches/inc-path.patch index 06c006685..4a195f03e 100644 --- a/package/openjdk/patches/inc-path.patch +++ b/package/openjdk/patches/inc-path.patch @@ -1,3 +1,6 @@ + + disable wrong pathes for cross-compilation + --- w-openjdk-6-1.orig/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-02-28 17:06:10.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/make/common/shared/Defs-linux.gmk 2011-08-08 10:07:58.975256728 +0200 @@ -170,7 +170,7 @@ diff --git a/package/openjdk/patches/llvm-headers.patch b/package/openjdk/patches/llvm-headers.patch index d0f42146d..25dd137d9 100644 --- a/package/openjdk/patches/llvm-headers.patch +++ b/package/openjdk/patches/llvm-headers.patch @@ -1,3 +1,6 @@ + + fix wrong header path + --- w-openjdk-6.orig/openjdk-6/hotspot/src/share/vm/shark/llvmHeaders.hpp 2011-02-28 17:03:21.000000000 +0100 +++ w-openjdk-6/openjdk-6/hotspot/src/share/vm/shark/llvmHeaders.hpp 2011-04-29 18:07:20.171550601 +0200 @@ -43,7 +43,7 @@ diff --git a/package/openjdk/patches/openjdk-6_Makefile.patch b/package/openjdk/patches/openjdk-6_Makefile.patch new file mode 100644 index 000000000..4425eff7c --- /dev/null +++ b/package/openjdk/patches/openjdk-6_Makefile.patch @@ -0,0 +1,16 @@ + + TOPDIR is already used by build system, so always set it. + +--- w-openjdk-6-1.orig/openjdk-6/Makefile 2011-02-28 17:02:07.000000000 +0100 ++++ w-openjdk-6-1/openjdk-6/Makefile 2011-03-28 20:06:13.751809044 +0200 +@@ -25,9 +25,7 @@ + + BUILD_PARENT_DIRECTORY=. + +-ifndef TOPDIR +- TOPDIR:=. +-endif ++TOPDIR:=. + + ifndef JDK_TOPDIR + JDK_TOPDIR=$(TOPDIR)/jdk diff --git a/package/openjdk/patches/patch-icedtea6-1_10_Makefile_in b/package/openjdk/patches/patch-icedtea6-1_10_Makefile_in deleted file mode 100644 index 193e008aa..000000000 --- a/package/openjdk/patches/patch-icedtea6-1_10_Makefile_in +++ /dev/null @@ -1,78 +0,0 @@ ---- w-openjdk-6-1.orig/icedtea6-1.10/Makefile.in 2011-03-02 20:48:45.000000000 +0100 -+++ w-openjdk-6-1/icedtea6-1.10/Makefile.in 2011-04-02 23:33:17.000000000 +0200 -@@ -328,7 +328,7 @@ - am__untar = @am__untar@ - bindir = @bindir@ - build = @build@ --build_alias = @build_alias@ -+build_alias = ${BUILD_ALIAS} - build_cpu = @build_cpu@ - build_os = @build_os@ - build_vendor = @build_vendor@ -@@ -339,7 +339,7 @@ - dvidir = @dvidir@ - exec_prefix = @exec_prefix@ - host = @host@ --host_alias = @host_alias@ -+host_alias = ${HOST_ALIAS} - host_cpu = @host_cpu@ - host_os = @host_os@ - host_vendor = @host_vendor@ -@@ -362,7 +362,7 @@ - sharedstatedir = @sharedstatedir@ - srcdir = @srcdir@ - sysconfdir = @sysconfdir@ --target_alias = @target_alias@ -+target_alias = ${TARGET_ALIAS} - top_build_prefix = @top_build_prefix@ - top_builddir = @top_builddir@ - top_srcdir = @top_srcdir@ -@@ -1329,7 +1329,7 @@ stamps/extract-openjdk.stamp: stamps/dow - @OPENJDK_SRC_DIR_FOUND_TRUE@ cp -pPR $(OPENJDK_SRC_DIR_LINK) $(OPENJDK_SRC_DIR) openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ if ! test -d openjdk ; then \ --@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPRl openjdk.hg openjdk ; \ -+@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPR openjdk.hg openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ set -e ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ if ! test -d openjdk ; \ -@@ -1576,7 +1576,7 @@ clean-overlay: - # FIXME (missing): Rename to clone-ecj. - stamps/extract-ecj.stamp: $(OPENJDK_TREE) - if ! test -d openjdk-ecj ; then \ -- cp -pPRl openjdk openjdk-ecj ; \ -+ cp -pPR openjdk openjdk-ecj ; \ - fi - mkdir -p stamps - touch stamps/extract-ecj.stamp -@@ -1642,11 +1642,15 @@ clean-patch-ecj: - # =========================== - - stamps/native-ecj.stamp: -- mkdir -p stamps ; \ -- if test "x$(GCJ)" != "xno"; then \ -- $(GCJ) $(IT_CFLAGS) -Wl,-Bsymbolic -findirect-dispatch -o native-ecj \ -- --main=org.eclipse.jdt.internal.compiler.batch.Main ${ECJ_JAR} ; \ -- fi ; \ -+ mkdir -p stamps ; \ -+ if test -n "${ADK_ECJ}" && test -x "${ADK_ECJ}"; then \ -+ ln -s "${ADK_ECJ}" native-ecj; \ -+ else \ -+ if test "x$(GCJ)" != "xno"; then \ -+ $(GCJ) $(IT_CFLAGS) -Wl,-Bsymbolic -findirect-dispatch -o native-ecj \ -+ --main=org.eclipse.jdt.internal.compiler.batch.Main ${ECJ_JAR} ; \ -+ fi ; \ -+ fi; \ - touch stamps/native-ecj.stamp - - clean-native-ecj: -@@ -2167,6 +2167,9 @@ - stamps/jamvm.stamp: $(OPENJDK_TREE) stamps/rt.stamp - @BUILD_JAMVM_TRUE@ cd jamvm/jamvm && \ - @BUILD_JAMVM_TRUE@ ./autogen.sh --with-java-runtime-library=openjdk \ -+@BUILD_JAMVM_TRUE@ --host=$(host_alias) \ -+@BUILD_JAMVM_TRUE@ --build=$(build_alias) \ -+@BUILD_JAMVM_TRUE@ --target=$(target_alias) \ - @BUILD_JAMVM_TRUE@ --prefix=$(abs_top_builddir)/jamvm/install ; \ - @BUILD_JAMVM_TRUE@ $(MAKE) ; \ - @BUILD_JAMVM_TRUE@ $(MAKE) install diff --git a/package/openjdk/patches/patch-openjdk-6_Makefile b/package/openjdk/patches/patch-openjdk-6_Makefile deleted file mode 100644 index 2364d7ec0..000000000 --- a/package/openjdk/patches/patch-openjdk-6_Makefile +++ /dev/null @@ -1,13 +0,0 @@ ---- w-openjdk-6-1.orig/openjdk-6/Makefile 2011-02-28 17:02:07.000000000 +0100 -+++ w-openjdk-6-1/openjdk-6/Makefile 2011-03-28 20:06:13.751809044 +0200 -@@ -25,9 +25,7 @@ - - BUILD_PARENT_DIRECTORY=. - --ifndef TOPDIR -- TOPDIR:=. --endif -+TOPDIR:=. - - ifndef JDK_TOPDIR - JDK_TOPDIR=$(TOPDIR)/jdk diff --git a/package/openjdk/patches/remove-libnsl.patch b/package/openjdk/patches/remove-libnsl.patch index 9c086843e..965829fd6 100644 --- a/package/openjdk/patches/remove-libnsl.patch +++ b/package/openjdk/patches/remove-libnsl.patch @@ -1,3 +1,6 @@ + + remove libnsl from linking. + --- w-openjdk-6-1.orig/openjdk-6/jdk/make/java/hpi/hpi_common.gmk 2011-02-28 17:06:10.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/jdk/make/java/hpi/hpi_common.gmk 2011-04-10 20:05:01.417672476 +0200 @@ -86,5 +86,5 @@ diff --git a/package/openjdk/patches/shark-adlc-cross-compile.patch b/package/openjdk/patches/shark-adlc-cross-compile.patch index 79670f9ac..fc3b804ea 100644 --- a/package/openjdk/patches/shark-adlc-cross-compile.patch +++ b/package/openjdk/patches/shark-adlc-cross-compile.patch @@ -1,3 +1,6 @@ + + Execute adlc via Qemu. + --- w-openjdk-6.orig/openjdk-6/hotspot/make/linux/makefiles/adlc.make 2011-02-28 17:03:13.000000000 +0100 +++ w-openjdk-6/openjdk-6/hotspot/make/linux/makefiles/adlc.make 2011-08-17 13:05:55.317470977 +0200 @@ -103,7 +103,7 @@ diff --git a/package/openjdk/patches/uClibc-compat.patch b/package/openjdk/patches/uClibc-compat.patch index 1bdf56b5b..1cc16cbb1 100644 --- a/package/openjdk/patches/uClibc-compat.patch +++ b/package/openjdk/patches/uClibc-compat.patch @@ -1,3 +1,7 @@ + + some uClibc compatibility hacks. + Partly from https://evolvis.org/scm/viewvc.php/jalimo/trunk/oe-overlay/packages/openjdk/openjdk-6-6b18-1.8/ + --- w-openjdk-6-1.orig/openjdk-6/hotspot/src/os/linux/vm/os_linux.cpp 2011-02-28 17:03:14.000000000 +0100 +++ w-openjdk-6-1/openjdk-6/hotspot/src/os/linux/vm/os_linux.cpp 2011-08-07 14:30:00.195403776 +0200 @@ -53,7 +53,6 @@ -- cgit v1.2.3 From 8147baaa25d586d4402455a5176edb192083a2ea Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 19 Aug 2011 19:46:37 +0200 Subject: disable Werror in a single patch --- package/openjdk/patches/remove-Werror.patch | 15 +++++++++++++++ 1 file changed, 15 insertions(+) create mode 100644 package/openjdk/patches/remove-Werror.patch diff --git a/package/openjdk/patches/remove-Werror.patch b/package/openjdk/patches/remove-Werror.patch new file mode 100644 index 000000000..445165781 --- /dev/null +++ b/package/openjdk/patches/remove-Werror.patch @@ -0,0 +1,15 @@ + + disable -Werror + +--- w-openjdk-6.orig/openjdk-6/hotspot/make/linux/makefiles/gcc.make 2011-02-28 17:03:13.000000000 +0100 ++++ w-openjdk-6/openjdk-6/hotspot/make/linux/makefiles/gcc.make 2011-08-19 18:18:55.997423368 +0200 +@@ -108,9 +108,6 @@ + CFLAGS += -pipe + endif + +-# Compiler warnings are treated as errors +-WARNINGS_ARE_ERRORS = -Werror +- + # Except for a few acceptable ones + # Since GCC 4.3, -Wconversion has changed its meanings to warn these implicit + # conversions which might affect the values. To avoid that, we need to turn -- cgit v1.2.3 From 432ae1a94f4d543da3aa2ed226cd3c00e350e3c4 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Sun, 21 Aug 2011 10:28:27 +0200 Subject: use qemu to execute sizer binary, remove pregenerated stuff --- jtools/openjdk/files/sizes.32 | 790 --------------------------- jtools/openjdk/files/sizes.64 | 790 --------------------------- package/openjdk/Makefile | 4 - package/openjdk/patches/disable-sizers.patch | 12 - package/openjdk/patches/qemu-sizer.patch | 22 + 5 files changed, 22 insertions(+), 1596 deletions(-) delete mode 100644 jtools/openjdk/files/sizes.32 delete mode 100644 jtools/openjdk/files/sizes.64 delete mode 100644 package/openjdk/patches/disable-sizers.patch create mode 100644 package/openjdk/patches/qemu-sizer.patch diff --git a/jtools/openjdk/files/sizes.32 b/jtools/openjdk/files/sizes.32 deleted file mode 100644 index 2277d4039..000000000 --- a/jtools/openjdk/files/sizes.32 +++ /dev/null @@ -1,790 +0,0 @@ -long 4 -int 4 -short 2 -ptr 4 -Bool 4 -Atom 4 -Window 4 -Screen.ext_data 0 -Screen.display 4 -Screen.root 8 -Screen.width 12 -Screen.height 16 -Screen.mwidth 20 -Screen.mheight 24 -Screen.ndepths 28 -Screen.depths 32 -Screen.root_depth 36 -Screen.root_visual 40 -Screen.default_gc 44 -Screen.cmap 48 -Screen.white_pixel 52 -Screen.black_pixel 56 -Screen.max_maps 60 -Screen.min_maps 64 -Screen.backing_store 68 -Screen.save_unders 72 -Screen.root_input_mask 76 -Screen 80 -XMapRequestEvent.type 0 -XMapRequestEvent.serial 4 -XMapRequestEvent.send_event 8 -XMapRequestEvent.display 12 -XMapRequestEvent.parent 16 -XMapRequestEvent.window 20 -XMapRequestEvent 24 -AwtScreenData.numConfigs 0 -AwtScreenData.root 4 -AwtScreenData.whitepixel 8 -AwtScreenData.blackpixel 12 -AwtScreenData.defaultConfig 16 -AwtScreenData.configs 20 -AwtScreenData 24 -XIMPreeditCaretCallbackStruct.position 0 -XIMPreeditCaretCallbackStruct.direction 4 -XIMPreeditCaretCallbackStruct.style 8 -XIMPreeditCaretCallbackStruct 12 -XTimeCoord.time 0 -XTimeCoord.x 4 -XTimeCoord.y 6 -XTimeCoord 8 -XWindowChanges.x 0 -XWindowChanges.y 4 -XWindowChanges.width 8 -XWindowChanges.height 12 -XWindowChanges.border_width 16 -XWindowChanges.sibling 20 -XWindowChanges.stack_mode 24 -XWindowChanges 28 -XSelectionClearEvent.type 0 -XSelectionClearEvent.serial 4 -XSelectionClearEvent.send_event 8 -XSelectionClearEvent.display 12 -XSelectionClearEvent.window 16 -XSelectionClearEvent.selection 20 -XSelectionClearEvent.time 24 -XSelectionClearEvent 28 -XKeyboardControl.key_click_percent 0 -XKeyboardControl.bell_percent 4 -XKeyboardControl.bell_pitch 8 -XKeyboardControl.bell_duration 12 -XKeyboardControl.led 16 -XKeyboardControl.led_mode 20 -XKeyboardControl.key 24 -XKeyboardControl.auto_repeat_mode 28 -XKeyboardControl 32 -XIMStatusDrawCallbackStruct.type 0 -XIMStatusDrawCallbackStruct.data 4 -XIMStatusDrawCallbackStruct 8 -XOMCharSetList.charset_count 0 -XOMCharSetList.charset_list 4 -XOMCharSetList 8 -XOMFontInfo.num_font 0 -XOMFontInfo.font_struct_list 4 -XOMFontInfo.font_name_list 8 -XOMFontInfo 12 -XIMStringConversionCallbackStruct.position 0 -XIMStringConversionCallbackStruct.direction 4 -XIMStringConversionCallbackStruct.operation 8 -XIMStringConversionCallbackStruct.factor 10 -XIMStringConversionCallbackStruct.text 12 -XIMStringConversionCallbackStruct 16 -XCirculateEvent.type 0 -XCirculateEvent.serial 4 -XCirculateEvent.send_event 8 -XCirculateEvent.display 12 -XCirculateEvent.event 16 -XCirculateEvent.window 20 -XCirculateEvent.place 24 -XCirculateEvent 28 -XIMHotKeyTrigger.keysym 0 -XIMHotKeyTrigger.modifier 4 -XIMHotKeyTrigger.modifier_mask 8 -XIMHotKeyTrigger 12 -XExtData.number 0 -XExtData.next 4 -XExtData.free_private 8 -XExtData.private_data 12 -XExtData 16 -XTextProperty.value 0 -XTextProperty.encoding 4 -XTextProperty.format 8 -XTextProperty.nitems 12 -XTextProperty 16 -XColor.pixel 0 -XColor.red 4 -XColor.green 6 -XColor.blue 8 -XColor.flags 10 -XColor.pad 11 -XColor 12 -XGraphicsExposeEvent.type 0 -XGraphicsExposeEvent.serial 4 -XGraphicsExposeEvent.send_event 8 -XGraphicsExposeEvent.display 12 -XGraphicsExposeEvent.drawable 16 -XGraphicsExposeEvent.x 20 -XGraphicsExposeEvent.y 24 -XGraphicsExposeEvent.width 28 -XGraphicsExposeEvent.height 32 -XGraphicsExposeEvent.count 36 -XGraphicsExposeEvent.major_code 40 -XGraphicsExposeEvent.minor_code 44 -XGraphicsExposeEvent 48 -XStandardColormap.colormap 0 -XStandardColormap.red_max 4 -XStandardColormap.red_mult 8 -XStandardColormap.green_max 12 -XStandardColormap.green_mult 16 -XStandardColormap.blue_max 20 -XStandardColormap.blue_mult 24 -XStandardColormap.base_pixel 28 -XStandardColormap.visualid 32 -XStandardColormap.killid 36 -XStandardColormap 40 -XPropertyEvent.type 0 -XPropertyEvent.serial 4 -XPropertyEvent.send_event 8 -XPropertyEvent.display 12 -XPropertyEvent.window 16 -XPropertyEvent.atom 20 -XPropertyEvent.time 24 -XPropertyEvent.state 28 -XPropertyEvent 32 -ColorEntry.r 0 -ColorEntry.g 1 -ColorEntry.b 2 -ColorEntry.flags 3 -ColorEntry 4 -XResizeRequestEvent.type 0 -XResizeRequestEvent.serial 4 -XResizeRequestEvent.send_event 8 -XResizeRequestEvent.display 12 -XResizeRequestEvent.window 16 -XResizeRequestEvent.width 20 -XResizeRequestEvent.height 24 -XResizeRequestEvent 28 -XFontStruct.ext_data 0 -XFontStruct.fid 4 -XFontStruct.direction 8 -XFontStruct.min_char_or_byte2 12 -XFontStruct.max_char_or_byte2 16 -XFontStruct.min_byte1 20 -XFontStruct.max_byte1 24 -XFontStruct.all_chars_exist 28 -XFontStruct.n_properties 36 -XFontStruct.properties 40 -XFontStruct.min_bounds 44 -XFontStruct.max_bounds 56 -XFontStruct.per_char 68 -XFontStruct.ascent 72 -XFontStruct.descent 76 -XFontStruct 80 -XNoExposeEvent.type 0 -XNoExposeEvent.serial 4 -XNoExposeEvent.send_event 8 -XNoExposeEvent.display 12 -XNoExposeEvent.drawable 16 -XNoExposeEvent.major_code 20 -XNoExposeEvent.minor_code 24 -XNoExposeEvent 28 -XErrorEvent.type 0 -XErrorEvent.display 4 -XErrorEvent.resourceid 8 -XErrorEvent.serial 12 -XErrorEvent.error_code 16 -XErrorEvent.request_code 17 -XErrorEvent.minor_code 18 -XErrorEvent 20 -XArc.x 0 -XArc.y 2 -XArc.width 4 -XArc.height 6 -XArc.angle1 8 -XArc.angle2 10 -XArc 12 -XSelectionEvent.type 0 -XSelectionEvent.serial 4 -XSelectionEvent.send_event 8 -XSelectionEvent.display 12 -XSelectionEvent.requestor 16 -XSelectionEvent.selection 20 -XSelectionEvent.target 24 -XSelectionEvent.property 28 -XSelectionEvent.time 32 -XSelectionEvent 36 -XVisibilityEvent.type 0 -XVisibilityEvent.serial 4 -XVisibilityEvent.send_event 8 -XVisibilityEvent.display 12 -XVisibilityEvent.window 16 -XVisibilityEvent.state 20 -XVisibilityEvent 24 -XFontProp.name 0 -XFontProp.card32 4 -XFontProp 8 -XTextItem16.chars 0 -XTextItem16.nchars 4 -XTextItem16.delta 8 -XTextItem16.font 12 -XTextItem16 16 -XIMPreeditDrawCallbackStruct.caret 0 -XIMPreeditDrawCallbackStruct.chg_first 4 -XIMPreeditDrawCallbackStruct.chg_length 8 -XIMPreeditDrawCallbackStruct.text 12 -XIMPreeditDrawCallbackStruct 16 -XRectangle.x 0 -XRectangle.y 2 -XRectangle.width 4 -XRectangle.height 6 -XRectangle 8 -PropMwmHints.flags 0 -PropMwmHints.functions 4 -PropMwmHints.decorations 8 -PropMwmHints.inputMode 12 -PropMwmHints.status 16 -PropMwmHints 20 -XConfigureEvent.type 0 -XConfigureEvent.serial 4 -XConfigureEvent.send_event 8 -XConfigureEvent.display 12 -XConfigureEvent.event 16 -XConfigureEvent.window 20 -XConfigureEvent.x 24 -XConfigureEvent.y 28 -XConfigureEvent.width 32 -XConfigureEvent.height 36 -XConfigureEvent.border_width 40 -XConfigureEvent.above 44 -XConfigureEvent.override_redirect 48 -XConfigureEvent 52 -XClientMessageEvent.type 0 -XClientMessageEvent.serial 4 -XClientMessageEvent.send_event 8 -XClientMessageEvent.display 12 -XClientMessageEvent.window 16 -XClientMessageEvent.message_type 20 -XClientMessageEvent.format 24 -XClientMessageEvent.data 28 -XClientMessageEvent 48 -XIconSize.min_width 0 -XIconSize.min_height 4 -XIconSize.max_width 8 -XIconSize.max_height 12 -XIconSize.width_inc 16 -XIconSize.height_inc 20 -XIconSize 24 -XSegment.x1 0 -XSegment.y1 2 -XSegment.x2 4 -XSegment.y2 6 -XSegment 8 -XPoint.x 0 -XPoint.y 2 -XPoint 4 -XIMStringConversionText.length 0 -XIMStringConversionText.feedback 4 -XIMStringConversionText.encoding_is_wchar 8 -XIMStringConversionText.string 12 -XIMStringConversionText 16 -XPixmapFormatValues.depth 0 -XPixmapFormatValues.bits_per_pixel 4 -XPixmapFormatValues.scanline_pad 8 -XPixmapFormatValues 12 -XExposeEvent.type 0 -XExposeEvent.serial 4 -XExposeEvent.send_event 8 -XExposeEvent.display 12 -XExposeEvent.window 16 -XExposeEvent.x 20 -XExposeEvent.y 24 -XExposeEvent.width 28 -XExposeEvent.height 32 -XExposeEvent.count 36 -XExposeEvent 40 -XIMStyles.count_styles 0 -XIMStyles.supported_styles 4 -XIMStyles 8 -XSizeHints.flags 0 -XSizeHints.x 4 -XSizeHints.y 8 -XSizeHints.width 12 -XSizeHints.height 16 -XSizeHints.min_width 20 -XSizeHints.min_height 24 -XSizeHints.max_width 28 -XSizeHints.max_height 32 -XSizeHints.width_inc 36 -XSizeHints.height_inc 40 -XSizeHints.min_aspect.x 44 -XSizeHints.min_aspect.y 48 -XSizeHints.max_aspect.x 52 -XSizeHints.max_aspect.y 56 -XSizeHints.base_width 60 -XSizeHints.base_height 64 -XSizeHints.win_gravity 68 -XSizeHints 72 -XMappingEvent.type 0 -XMappingEvent.serial 4 -XMappingEvent.send_event 8 -XMappingEvent.display 12 -XMappingEvent.window 16 -XMappingEvent.request 20 -XMappingEvent.first_keycode 24 -XMappingEvent.count 28 -XMappingEvent 32 -XClassHint.res_name 0 -XClassHint.res_class 4 -XClassHint 8 -XmbTextItem.chars 0 -XmbTextItem.nchars 4 -XmbTextItem.delta 8 -XmbTextItem.font_set 12 -XmbTextItem 16 -XWindowAttributes.x 0 -XWindowAttributes.y 4 -XWindowAttributes.width 8 -XWindowAttributes.height 12 -XWindowAttributes.border_width 16 -XWindowAttributes.depth 20 -XWindowAttributes.visual 24 -XWindowAttributes.root 28 -XWindowAttributes.class 32 -XWindowAttributes.bit_gravity 36 -XWindowAttributes.win_gravity 40 -XWindowAttributes.backing_store 44 -XWindowAttributes.backing_planes 48 -XWindowAttributes.backing_pixel 52 -XWindowAttributes.save_under 56 -XWindowAttributes.colormap 60 -XWindowAttributes.map_installed 64 -XWindowAttributes.map_state 68 -XWindowAttributes.all_event_masks 72 -XWindowAttributes.your_event_mask 76 -XWindowAttributes.do_not_propagate_mask 80 -XWindowAttributes.override_redirect 84 -XWindowAttributes.screen 88 -XWindowAttributes 92 -XSetWindowAttributes.background_pixmap 0 -XSetWindowAttributes.background_pixel 4 -XSetWindowAttributes.border_pixmap 8 -XSetWindowAttributes.border_pixel 12 -XSetWindowAttributes.bit_gravity 16 -XSetWindowAttributes.win_gravity 20 -XSetWindowAttributes.backing_store 24 -XSetWindowAttributes.backing_planes 28 -XSetWindowAttributes.backing_pixel 32 -XSetWindowAttributes.save_under 36 -XSetWindowAttributes.event_mask 40 -XSetWindowAttributes.do_not_propagate_mask 44 -XSetWindowAttributes.override_redirect 48 -XSetWindowAttributes.colormap 52 -XSetWindowAttributes.cursor 56 -XSetWindowAttributes 60 -XOMOrientation.num_orientation 0 -XOMOrientation.orientation 4 -XOMOrientation 8 -Visual.ext_data 0 -Visual.visualid 4 -Visual.class 8 -Visual.red_mask 12 -Visual.green_mask 16 -Visual.blue_mask 20 -Visual.bits_per_rgb 24 -Visual.map_entries 28 -Visual 32 -XGravityEvent.type 0 -XGravityEvent.serial 4 -XGravityEvent.send_event 8 -XGravityEvent.display 12 -XGravityEvent.event 16 -XGravityEvent.window 20 -XGravityEvent.x 24 -XGravityEvent.y 28 -XGravityEvent 32 -XReparentEvent.type 0 -XReparentEvent.serial 4 -XReparentEvent.send_event 8 -XReparentEvent.display 12 -XReparentEvent.event 16 -XReparentEvent.window 20 -XReparentEvent.parent 24 -XReparentEvent.x 28 -XReparentEvent.y 32 -XReparentEvent.override_redirect 36 -XReparentEvent 40 -XCirculateRequestEvent.type 0 -XCirculateRequestEvent.serial 4 -XCirculateRequestEvent.send_event 8 -XCirculateRequestEvent.display 12 -XCirculateRequestEvent.parent 16 -XCirculateRequestEvent.window 20 -XCirculateRequestEvent.place 24 -XCirculateRequestEvent 28 -XKeyEvent.type 0 -XKeyEvent.serial 4 -XKeyEvent.send_event 8 -XKeyEvent.display 12 -XKeyEvent.window 16 -XKeyEvent.root 20 -XKeyEvent.subwindow 24 -XKeyEvent.time 28 -XKeyEvent.x 32 -XKeyEvent.y 36 -XKeyEvent.x_root 40 -XKeyEvent.y_root 44 -XKeyEvent.state 48 -XKeyEvent.keycode 52 -XKeyEvent.same_screen 56 -XKeyEvent 60 -XCharStruct.lbearing 0 -XCharStruct.rbearing 2 -XCharStruct.width 4 -XCharStruct.ascent 6 -XCharStruct.descent 8 -XCharStruct.attributes 10 -XCharStruct 12 -XModifierKeymap.max_keypermod 0 -XModifierKeymap.modifiermap 4 -XModifierKeymap 8 -XTextItem.chars 0 -XTextItem.nchars 4 -XTextItem.delta 8 -XTextItem.font 12 -XTextItem 16 -XdbeSwapInfo.swap_window 0 -XdbeSwapInfo.swap_action 4 -XdbeSwapInfo 8 -XImage.width 0 -XImage.height 4 -XImage.xoffset 8 -XImage.format 12 -XImage.data 16 -XImage.byte_order 20 -XImage.bitmap_unit 24 -XImage.bitmap_bit_order 28 -XImage.bitmap_pad 32 -XImage.depth 36 -XImage.bytes_per_line 40 -XImage.bits_per_pixel 44 -XImage.red_mask 48 -XImage.green_mask 52 -XImage.blue_mask 56 -XImage.obdata 60 -XImage.f.create_image 64 -XImage.f.destroy_image 68 -XImage.f.get_pixel 72 -XImage.f.put_pixel 76 -XImage.f.sub_image 80 -XImage.f.add_pixel 84 -XImage 88 -XChar2b.byte1 0 -XChar2b.byte2 1 -XChar2b 2 -XwcTextItem.chars 0 -XwcTextItem.nchars 4 -XwcTextItem.delta 8 -XwcTextItem.font_set 12 -XwcTextItem 16 -XUnmapEvent.type 0 -XUnmapEvent.serial 4 -XUnmapEvent.send_event 8 -XUnmapEvent.display 12 -XUnmapEvent.event 16 -XUnmapEvent.window 20 -XUnmapEvent.from_configure 24 -XUnmapEvent 28 -awtImageData.Depth 0 -awtImageData.wsImageFormat 4 -awtImageData.clrdata 16 -awtImageData.convert 48 -awtImageData 304 -XGCValues.function 0 -XGCValues.plane_mask 4 -XGCValues.foreground 8 -XGCValues.background 12 -XGCValues.line_width 16 -XGCValues.line_style 20 -XGCValues.cap_style 24 -XGCValues.join_style 28 -XGCValues.fill_style 32 -XGCValues.fill_rule 36 -XGCValues.arc_mode 40 -XGCValues.tile 44 -XGCValues.stipple 48 -XGCValues.ts_x_origin 52 -XGCValues.ts_y_origin 56 -XGCValues.font 60 -XGCValues.subwindow_mode 64 -XGCValues.graphics_exposures 68 -XGCValues.clip_x_origin 72 -XGCValues.clip_y_origin 76 -XGCValues.clip_mask 80 -XGCValues.dash_offset 84 -XGCValues.dashes 88 -XGCValues 92 -XFocusChangeEvent.type 0 -XFocusChangeEvent.serial 4 -XFocusChangeEvent.send_event 8 -XFocusChangeEvent.display 12 -XFocusChangeEvent.window 16 -XFocusChangeEvent.mode 20 -XFocusChangeEvent.detail 24 -XFocusChangeEvent 28 -XMapEvent.type 0 -XMapEvent.serial 4 -XMapEvent.send_event 8 -XMapEvent.display 12 -XMapEvent.event 16 -XMapEvent.window 20 -XMapEvent.override_redirect 24 -XMapEvent 28 -XIMHotKeyTriggers.num_hot_key 0 -XIMHotKeyTriggers.key 4 -XIMHotKeyTriggers 8 -XKeyboardState.key_click_percent 0 -XKeyboardState.bell_percent 4 -XKeyboardState.bell_pitch 8 -XKeyboardState.bell_duration 12 -XKeyboardState.led_mask 16 -XKeyboardState.global_auto_repeat 20 -XKeyboardState.auto_repeats 24 -XKeyboardState 56 -XMotionEvent.type 0 -XMotionEvent.serial 4 -XMotionEvent.send_event 8 -XMotionEvent.display 12 -XMotionEvent.window 16 -XMotionEvent.root 20 -XMotionEvent.subwindow 24 -XMotionEvent.time 28 -XMotionEvent.x 32 -XMotionEvent.y 36 -XMotionEvent.x_root 40 -XMotionEvent.y_root 44 -XMotionEvent.state 48 -XMotionEvent.is_hint 52 -XMotionEvent.same_screen 56 -XMotionEvent 60 -XIMPreeditStateNotifyCallbackStruct.state 0 -XIMPreeditStateNotifyCallbackStruct 4 -XAnyEvent.type 0 -XAnyEvent.serial 4 -XAnyEvent.send_event 8 -XAnyEvent.display 12 -XAnyEvent.window 16 -XAnyEvent 20 -XIMCallback.client_data 0 -XIMCallback.callback 4 -XIMCallback 8 -XVisualInfo.visual 0 -XVisualInfo.visualid 4 -XVisualInfo.screen 8 -XVisualInfo.depth 12 -XVisualInfo.class 16 -XVisualInfo.red_mask 20 -XVisualInfo.green_mask 24 -XVisualInfo.blue_mask 28 -XVisualInfo.colormap_size 32 -XVisualInfo.bits_per_rgb 36 -XVisualInfo 40 -XCreateWindowEvent.type 0 -XCreateWindowEvent.serial 4 -XCreateWindowEvent.send_event 8 -XCreateWindowEvent.display 12 -XCreateWindowEvent.parent 16 -XCreateWindowEvent.window 20 -XCreateWindowEvent.x 24 -XCreateWindowEvent.y 28 -XCreateWindowEvent.width 32 -XCreateWindowEvent.height 36 -XCreateWindowEvent.border_width 40 -XCreateWindowEvent.override_redirect 44 -XCreateWindowEvent 48 -XIMValuesList.count_values 0 -XIMValuesList.supported_values 4 -XIMValuesList 8 -XKeymapEvent.type 0 -XKeymapEvent.serial 4 -XKeymapEvent.send_event 8 -XKeymapEvent.display 12 -XKeymapEvent.window 16 -XKeymapEvent.key_vector 20 -XKeymapEvent 52 -XButtonEvent.type 0 -XButtonEvent.serial 4 -XButtonEvent.send_event 8 -XButtonEvent.display 12 -XButtonEvent.window 16 -XButtonEvent.root 20 -XButtonEvent.subwindow 24 -XButtonEvent.time 28 -XButtonEvent.x 32 -XButtonEvent.y 36 -XButtonEvent.x_root 40 -XButtonEvent.y_root 44 -XButtonEvent.state 48 -XButtonEvent.button 52 -XButtonEvent.same_screen 56 -XButtonEvent 60 -XWMHints.flags 0 -XWMHints.initial_state 8 -XWMHints.icon_pixmap 12 -XWMHints.icon_window 16 -XWMHints.icon_x 20 -XWMHints.icon_y 24 -XWMHints.icon_mask 28 -XWMHints.input 4 -XWMHints.window_group 32 -XWMHints 36 -ScreenFormat.ext_data 0 -ScreenFormat.depth 4 -ScreenFormat.bits_per_pixel 8 -ScreenFormat.scanline_pad 12 -ScreenFormat 16 -XCrossingEvent.type 0 -XCrossingEvent.serial 4 -XCrossingEvent.send_event 8 -XCrossingEvent.display 12 -XCrossingEvent.window 16 -XCrossingEvent.root 20 -XCrossingEvent.subwindow 24 -XCrossingEvent.time 28 -XCrossingEvent.x 32 -XCrossingEvent.y 36 -XCrossingEvent.x_root 40 -XCrossingEvent.y_root 44 -XCrossingEvent.mode 48 -XCrossingEvent.detail 52 -XCrossingEvent.same_screen 56 -XCrossingEvent.focus 60 -XCrossingEvent.state 64 -XCrossingEvent 68 -XConfigureRequestEvent.type 0 -XConfigureRequestEvent.serial 4 -XConfigureRequestEvent.send_event 8 -XConfigureRequestEvent.display 12 -XConfigureRequestEvent.parent 16 -XConfigureRequestEvent.window 20 -XConfigureRequestEvent.x 24 -XConfigureRequestEvent.y 28 -XConfigureRequestEvent.width 32 -XConfigureRequestEvent.height 36 -XConfigureRequestEvent.border_width 40 -XConfigureRequestEvent.above 44 -XConfigureRequestEvent.detail 48 -XConfigureRequestEvent.value_mask 52 -XConfigureRequestEvent 56 -XSelectionRequestEvent.type 0 -XSelectionRequestEvent.serial 4 -XSelectionRequestEvent.send_event 8 -XSelectionRequestEvent.display 12 -XSelectionRequestEvent.owner 16 -XSelectionRequestEvent.requestor 20 -XSelectionRequestEvent.selection 24 -XSelectionRequestEvent.target 28 -XSelectionRequestEvent.property 32 -XSelectionRequestEvent.time 36 -XSelectionRequestEvent 40 -XFontSetExtents.max_ink_extent 0 -XFontSetExtents.max_logical_extent 8 -XFontSetExtents 16 -XExtCodes.extension 0 -XExtCodes.major_opcode 4 -XExtCodes.first_event 8 -XExtCodes.first_error 12 -XExtCodes 16 -XHostAddress.family 0 -XHostAddress.length 4 -XHostAddress.address 8 -XHostAddress 12 -ColorData.awt_Colors 0 -ColorData.awt_numICMcolors 4 -ColorData.awt_icmLUT 8 -ColorData.awt_icmLUT2Colors 12 -ColorData.img_grays 16 -ColorData.img_clr_tbl 20 -ColorData.img_oda_red 24 -ColorData.img_oda_green 28 -ColorData.img_oda_blue 32 -ColorData.pGrayInverseLutData 36 -ColorData.screendata 40 -ColorData 44 -XColormapEvent.type 0 -XColormapEvent.serial 4 -XColormapEvent.send_event 8 -XColormapEvent.display 12 -XColormapEvent.window 16 -XColormapEvent.colormap 20 -XColormapEvent.new 24 -XColormapEvent.state 28 -XColormapEvent 32 -Depth.depth 0 -Depth.nvisuals 4 -Depth.visuals 8 -Depth 12 -XEvent.type 0 -XEvent.xany 0 -XEvent.xkey 0 -XEvent.xbutton 0 -XEvent.xmotion 0 -XEvent.xcrossing 0 -XEvent.xfocus 0 -XEvent.xexpose 0 -XEvent.xgraphicsexpose 0 -XEvent.xnoexpose 0 -XEvent.xvisibility 0 -XEvent.xcreatewindow 0 -XEvent.xdestroywindow 0 -XEvent.xunmap 0 -XEvent.xmap 0 -XEvent.xmaprequest 0 -XEvent.xreparent 0 -XEvent.xconfigure 0 -XEvent.xgravity 0 -XEvent.xresizerequest 0 -XEvent.xconfigurerequest 0 -XEvent.xcirculate 0 -XEvent.xcirculaterequest 0 -XEvent.xproperty 0 -XEvent.xselectionclear 0 -XEvent.xselectionrequest 0 -XEvent.xselection 0 -XEvent.xcolormap 0 -XEvent.xclient 0 -XEvent.xmapping 0 -XEvent.xerror 0 -XEvent.xkeymap 0 -XEvent.pad 0 -XEvent 96 -XDestroyWindowEvent.type 0 -XDestroyWindowEvent.serial 4 -XDestroyWindowEvent.send_event 8 -XDestroyWindowEvent.display 12 -XDestroyWindowEvent.event 16 -XDestroyWindowEvent.window 20 -XDestroyWindowEvent 24 -XComposeStatus.compose_ptr 0 -XComposeStatus.chars_matched 4 -XComposeStatus 8 -AwtGraphicsConfigData.awt_depth 0 -AwtGraphicsConfigData.awt_cmap 4 -AwtGraphicsConfigData.awt_visInfo 8 -AwtGraphicsConfigData.awt_num_colors 48 -AwtGraphicsConfigData.awtImage 52 -AwtGraphicsConfigData.AwtColorMatch 56 -AwtGraphicsConfigData.monoImage 60 -AwtGraphicsConfigData.monoPixmap 64 -AwtGraphicsConfigData.monoPixmapWidth 68 -AwtGraphicsConfigData.monoPixmapHeight 72 -AwtGraphicsConfigData.monoPixmapGC 76 -AwtGraphicsConfigData.pixelStride 80 -AwtGraphicsConfigData.color_data 84 -AwtGraphicsConfigData.glxInfo 88 -AwtGraphicsConfigData.isTranslucencySupported 92 -AwtGraphicsConfigData 96 -XIMText.length 0 -XIMText.feedback 4 -XIMText.encoding_is_wchar 8 -XIMText.string 12 -XIMText 16 diff --git a/jtools/openjdk/files/sizes.64 b/jtools/openjdk/files/sizes.64 deleted file mode 100644 index 9661f857f..000000000 --- a/jtools/openjdk/files/sizes.64 +++ /dev/null @@ -1,790 +0,0 @@ -long 8 -int 4 -short 2 -ptr 8 -Bool 4 -Atom 8 -Window 8 -Screen.ext_data 0 -Screen.display 8 -Screen.root 16 -Screen.width 24 -Screen.height 28 -Screen.mwidth 32 -Screen.mheight 36 -Screen.ndepths 40 -Screen.depths 48 -Screen.root_depth 56 -Screen.root_visual 64 -Screen.default_gc 72 -Screen.cmap 80 -Screen.white_pixel 88 -Screen.black_pixel 96 -Screen.max_maps 104 -Screen.min_maps 108 -Screen.backing_store 112 -Screen.save_unders 116 -Screen.root_input_mask 120 -Screen 128 -XMapRequestEvent.type 0 -XMapRequestEvent.serial 8 -XMapRequestEvent.send_event 16 -XMapRequestEvent.display 24 -XMapRequestEvent.parent 32 -XMapRequestEvent.window 40 -XMapRequestEvent 48 -AwtScreenData.numConfigs 0 -AwtScreenData.root 8 -AwtScreenData.whitepixel 16 -AwtScreenData.blackpixel 24 -AwtScreenData.defaultConfig 32 -AwtScreenData.configs 40 -AwtScreenData 48 -XIMPreeditCaretCallbackStruct.position 0 -XIMPreeditCaretCallbackStruct.direction 4 -XIMPreeditCaretCallbackStruct.style 8 -XIMPreeditCaretCallbackStruct 12 -XTimeCoord.time 0 -XTimeCoord.x 8 -XTimeCoord.y 10 -XTimeCoord 16 -XWindowChanges.x 0 -XWindowChanges.y 4 -XWindowChanges.width 8 -XWindowChanges.height 12 -XWindowChanges.border_width 16 -XWindowChanges.sibling 24 -XWindowChanges.stack_mode 32 -XWindowChanges 40 -XSelectionClearEvent.type 0 -XSelectionClearEvent.serial 8 -XSelectionClearEvent.send_event 16 -XSelectionClearEvent.display 24 -XSelectionClearEvent.window 32 -XSelectionClearEvent.selection 40 -XSelectionClearEvent.time 48 -XSelectionClearEvent 56 -XKeyboardControl.key_click_percent 0 -XKeyboardControl.bell_percent 4 -XKeyboardControl.bell_pitch 8 -XKeyboardControl.bell_duration 12 -XKeyboardControl.led 16 -XKeyboardControl.led_mode 20 -XKeyboardControl.key 24 -XKeyboardControl.auto_repeat_mode 28 -XKeyboardControl 32 -XIMStatusDrawCallbackStruct.type 0 -XIMStatusDrawCallbackStruct.data 8 -XIMStatusDrawCallbackStruct 16 -XOMCharSetList.charset_count 0 -XOMCharSetList.charset_list 8 -XOMCharSetList 16 -XOMFontInfo.num_font 0 -XOMFontInfo.font_struct_list 8 -XOMFontInfo.font_name_list 16 -XOMFontInfo 24 -XIMStringConversionCallbackStruct.position 0 -XIMStringConversionCallbackStruct.direction 4 -XIMStringConversionCallbackStruct.operation 8 -XIMStringConversionCallbackStruct.factor 10 -XIMStringConversionCallbackStruct.text 16 -XIMStringConversionCallbackStruct 24 -XCirculateEvent.type 0 -XCirculateEvent.serial 8 -XCirculateEvent.send_event 16 -XCirculateEvent.display 24 -XCirculateEvent.event 32 -XCirculateEvent.window 40 -XCirculateEvent.place 48 -XCirculateEvent 56 -XIMHotKeyTrigger.keysym 0 -XIMHotKeyTrigger.modifier 8 -XIMHotKeyTrigger.modifier_mask 12 -XIMHotKeyTrigger 16 -XExtData.number 0 -XExtData.next 8 -XExtData.free_private 16 -XExtData.private_data 24 -XExtData 32 -XTextProperty.value 0 -XTextProperty.encoding 8 -XTextProperty.format 16 -XTextProperty.nitems 24 -XTextProperty 32 -XColor.pixel 0 -XColor.red 8 -XColor.green 10 -XColor.blue 12 -XColor.flags 14 -XColor.pad 15 -XColor 16 -XGraphicsExposeEvent.type 0 -XGraphicsExposeEvent.serial 8 -XGraphicsExposeEvent.send_event 16 -XGraphicsExposeEvent.display 24 -XGraphicsExposeEvent.drawable 32 -XGraphicsExposeEvent.x 40 -XGraphicsExposeEvent.y 44 -XGraphicsExposeEvent.width 48 -XGraphicsExposeEvent.height 52 -XGraphicsExposeEvent.count 56 -XGraphicsExposeEvent.major_code 60 -XGraphicsExposeEvent.minor_code 64 -XGraphicsExposeEvent 72 -XStandardColormap.colormap 0 -XStandardColormap.red_max 8 -XStandardColormap.red_mult 16 -XStandardColormap.green_max 24 -XStandardColormap.green_mult 32 -XStandardColormap.blue_max 40 -XStandardColormap.blue_mult 48 -XStandardColormap.base_pixel 56 -XStandardColormap.visualid 64 -XStandardColormap.killid 72 -XStandardColormap 80 -XPropertyEvent.type 0 -XPropertyEvent.serial 8 -XPropertyEvent.send_event 16 -XPropertyEvent.display 24 -XPropertyEvent.window 32 -XPropertyEvent.atom 40 -XPropertyEvent.time 48 -XPropertyEvent.state 56 -XPropertyEvent 64 -ColorEntry.r 0 -ColorEntry.g 1 -ColorEntry.b 2 -ColorEntry.flags 3 -ColorEntry 4 -XResizeRequestEvent.type 0 -XResizeRequestEvent.serial 8 -XResizeRequestEvent.send_event 16 -XResizeRequestEvent.display 24 -XResizeRequestEvent.window 32 -XResizeRequestEvent.width 40 -XResizeRequestEvent.height 44 -XResizeRequestEvent 48 -XFontStruct.ext_data 0 -XFontStruct.fid 8 -XFontStruct.direction 16 -XFontStruct.min_char_or_byte2 20 -XFontStruct.max_char_or_byte2 24 -XFontStruct.min_byte1 28 -XFontStruct.max_byte1 32 -XFontStruct.all_chars_exist 36 -XFontStruct.n_properties 44 -XFontStruct.properties 48 -XFontStruct.min_bounds 56 -XFontStruct.max_bounds 68 -XFontStruct.per_char 80 -XFontStruct.ascent 88 -XFontStruct.descent 92 -XFontStruct 96 -XNoExposeEvent.type 0 -XNoExposeEvent.serial 8 -XNoExposeEvent.send_event 16 -XNoExposeEvent.display 24 -XNoExposeEvent.drawable 32 -XNoExposeEvent.major_code 40 -XNoExposeEvent.minor_code 44 -XNoExposeEvent 48 -XErrorEvent.type 0 -XErrorEvent.display 8 -XErrorEvent.resourceid 16 -XErrorEvent.serial 24 -XErrorEvent.error_code 32 -XErrorEvent.request_code 33 -XErrorEvent.minor_code 34 -XErrorEvent 40 -XArc.x 0 -XArc.y 2 -XArc.width 4 -XArc.height 6 -XArc.angle1 8 -XArc.angle2 10 -XArc 12 -XSelectionEvent.type 0 -XSelectionEvent.serial 8 -XSelectionEvent.send_event 16 -XSelectionEvent.display 24 -XSelectionEvent.requestor 32 -XSelectionEvent.selection 40 -XSelectionEvent.target 48 -XSelectionEvent.property 56 -XSelectionEvent.time 64 -XSelectionEvent 72 -XVisibilityEvent.type 0 -XVisibilityEvent.serial 8 -XVisibilityEvent.send_event 16 -XVisibilityEvent.display 24 -XVisibilityEvent.window 32 -XVisibilityEvent.state 40 -XVisibilityEvent 48 -XFontProp.name 0 -XFontProp.card32 8 -XFontProp 16 -XTextItem16.chars 0 -XTextItem16.nchars 8 -XTextItem16.delta 12 -XTextItem16.font 16 -XTextItem16 24 -XIMPreeditDrawCallbackStruct.caret 0 -XIMPreeditDrawCallbackStruct.chg_first 4 -XIMPreeditDrawCallbackStruct.chg_length 8 -XIMPreeditDrawCallbackStruct.text 16 -XIMPreeditDrawCallbackStruct 24 -XRectangle.x 0 -XRectangle.y 2 -XRectangle.width 4 -XRectangle.height 6 -XRectangle 8 -PropMwmHints.flags 0 -PropMwmHints.functions 8 -PropMwmHints.decorations 16 -PropMwmHints.inputMode 24 -PropMwmHints.status 32 -PropMwmHints 40 -XConfigureEvent.type 0 -XConfigureEvent.serial 8 -XConfigureEvent.send_event 16 -XConfigureEvent.display 24 -XConfigureEvent.event 32 -XConfigureEvent.window 40 -XConfigureEvent.x 48 -XConfigureEvent.y 52 -XConfigureEvent.width 56 -XConfigureEvent.height 60 -XConfigureEvent.border_width 64 -XConfigureEvent.above 72 -XConfigureEvent.override_redirect 80 -XConfigureEvent 88 -XClientMessageEvent.type 0 -XClientMessageEvent.serial 8 -XClientMessageEvent.send_event 16 -XClientMessageEvent.display 24 -XClientMessageEvent.window 32 -XClientMessageEvent.message_type 40 -XClientMessageEvent.format 48 -XClientMessageEvent.data 56 -XClientMessageEvent 96 -XIconSize.min_width 0 -XIconSize.min_height 4 -XIconSize.max_width 8 -XIconSize.max_height 12 -XIconSize.width_inc 16 -XIconSize.height_inc 20 -XIconSize 24 -XSegment.x1 0 -XSegment.y1 2 -XSegment.x2 4 -XSegment.y2 6 -XSegment 8 -XPoint.x 0 -XPoint.y 2 -XPoint 4 -XIMStringConversionText.length 0 -XIMStringConversionText.feedback 8 -XIMStringConversionText.encoding_is_wchar 16 -XIMStringConversionText.string 24 -XIMStringConversionText 32 -XPixmapFormatValues.depth 0 -XPixmapFormatValues.bits_per_pixel 4 -XPixmapFormatValues.scanline_pad 8 -XPixmapFormatValues 12 -XExposeEvent.type 0 -XExposeEvent.serial 8 -XExposeEvent.send_event 16 -XExposeEvent.display 24 -XExposeEvent.window 32 -XExposeEvent.x 40 -XExposeEvent.y 44 -XExposeEvent.width 48 -XExposeEvent.height 52 -XExposeEvent.count 56 -XExposeEvent 64 -XIMStyles.count_styles 0 -XIMStyles.supported_styles 8 -XIMStyles 16 -XSizeHints.flags 0 -XSizeHints.x 8 -XSizeHints.y 12 -XSizeHints.width 16 -XSizeHints.height 20 -XSizeHints.min_width 24 -XSizeHints.min_height 28 -XSizeHints.max_width 32 -XSizeHints.max_height 36 -XSizeHints.width_inc 40 -XSizeHints.height_inc 44 -XSizeHints.min_aspect.x 48 -XSizeHints.min_aspect.y 52 -XSizeHints.max_aspect.x 56 -XSizeHints.max_aspect.y 60 -XSizeHints.base_width 64 -XSizeHints.base_height 68 -XSizeHints.win_gravity 72 -XSizeHints 80 -XMappingEvent.type 0 -XMappingEvent.serial 8 -XMappingEvent.send_event 16 -XMappingEvent.display 24 -XMappingEvent.window 32 -XMappingEvent.request 40 -XMappingEvent.first_keycode 44 -XMappingEvent.count 48 -XMappingEvent 56 -XClassHint.res_name 0 -XClassHint.res_class 8 -XClassHint 16 -XmbTextItem.chars 0 -XmbTextItem.nchars 8 -XmbTextItem.delta 12 -XmbTextItem.font_set 16 -XmbTextItem 24 -XWindowAttributes.x 0 -XWindowAttributes.y 4 -XWindowAttributes.width 8 -XWindowAttributes.height 12 -XWindowAttributes.border_width 16 -XWindowAttributes.depth 20 -XWindowAttributes.visual 24 -XWindowAttributes.root 32 -XWindowAttributes.class 40 -XWindowAttributes.bit_gravity 44 -XWindowAttributes.win_gravity 48 -XWindowAttributes.backing_store 52 -XWindowAttributes.backing_planes 56 -XWindowAttributes.backing_pixel 64 -XWindowAttributes.save_under 72 -XWindowAttributes.colormap 80 -XWindowAttributes.map_installed 88 -XWindowAttributes.map_state 92 -XWindowAttributes.all_event_masks 96 -XWindowAttributes.your_event_mask 104 -XWindowAttributes.do_not_propagate_mask 112 -XWindowAttributes.override_redirect 120 -XWindowAttributes.screen 128 -XWindowAttributes 136 -XSetWindowAttributes.background_pixmap 0 -XSetWindowAttributes.background_pixel 8 -XSetWindowAttributes.border_pixmap 16 -XSetWindowAttributes.border_pixel 24 -XSetWindowAttributes.bit_gravity 32 -XSetWindowAttributes.win_gravity 36 -XSetWindowAttributes.backing_store 40 -XSetWindowAttributes.backing_planes 48 -XSetWindowAttributes.backing_pixel 56 -XSetWindowAttributes.save_under 64 -XSetWindowAttributes.event_mask 72 -XSetWindowAttributes.do_not_propagate_mask 80 -XSetWindowAttributes.override_redirect 88 -XSetWindowAttributes.colormap 96 -XSetWindowAttributes.cursor 104 -XSetWindowAttributes 112 -XOMOrientation.num_orientation 0 -XOMOrientation.orientation 8 -XOMOrientation 16 -Visual.ext_data 0 -Visual.visualid 8 -Visual.class 16 -Visual.red_mask 24 -Visual.green_mask 32 -Visual.blue_mask 40 -Visual.bits_per_rgb 48 -Visual.map_entries 52 -Visual 56 -XGravityEvent.type 0 -XGravityEvent.serial 8 -XGravityEvent.send_event 16 -XGravityEvent.display 24 -XGravityEvent.event 32 -XGravityEvent.window 40 -XGravityEvent.x 48 -XGravityEvent.y 52 -XGravityEvent 56 -XReparentEvent.type 0 -XReparentEvent.serial 8 -XReparentEvent.send_event 16 -XReparentEvent.display 24 -XReparentEvent.event 32 -XReparentEvent.window 40 -XReparentEvent.parent 48 -XReparentEvent.x 56 -XReparentEvent.y 60 -XReparentEvent.override_redirect 64 -XReparentEvent 72 -XCirculateRequestEvent.type 0 -XCirculateRequestEvent.serial 8 -XCirculateRequestEvent.send_event 16 -XCirculateRequestEvent.display 24 -XCirculateRequestEvent.parent 32 -XCirculateRequestEvent.window 40 -XCirculateRequestEvent.place 48 -XCirculateRequestEvent 56 -XKeyEvent.type 0 -XKeyEvent.serial 8 -XKeyEvent.send_event 16 -XKeyEvent.display 24 -XKeyEvent.window 32 -XKeyEvent.root 40 -XKeyEvent.subwindow 48 -XKeyEvent.time 56 -XKeyEvent.x 64 -XKeyEvent.y 68 -XKeyEvent.x_root 72 -XKeyEvent.y_root 76 -XKeyEvent.state 80 -XKeyEvent.keycode 84 -XKeyEvent.same_screen 88 -XKeyEvent 96 -XCharStruct.lbearing 0 -XCharStruct.rbearing 2 -XCharStruct.width 4 -XCharStruct.ascent 6 -XCharStruct.descent 8 -XCharStruct.attributes 10 -XCharStruct 12 -XModifierKeymap.max_keypermod 0 -XModifierKeymap.modifiermap 8 -XModifierKeymap 16 -XTextItem.chars 0 -XTextItem.nchars 8 -XTextItem.delta 12 -XTextItem.font 16 -XTextItem 24 -XdbeSwapInfo.swap_window 0 -XdbeSwapInfo.swap_action 8 -XdbeSwapInfo 16 -XImage.width 0 -XImage.height 4 -XImage.xoffset 8 -XImage.format 12 -XImage.data 16 -XImage.byte_order 24 -XImage.bitmap_unit 28 -XImage.bitmap_bit_order 32 -XImage.bitmap_pad 36 -XImage.depth 40 -XImage.bytes_per_line 44 -XImage.bits_per_pixel 48 -XImage.red_mask 56 -XImage.green_mask 64 -XImage.blue_mask 72 -XImage.obdata 80 -XImage.f.create_image 88 -XImage.f.destroy_image 96 -XImage.f.get_pixel 104 -XImage.f.put_pixel 112 -XImage.f.sub_image 120 -XImage.f.add_pixel 128 -XImage 136 -XChar2b.byte1 0 -XChar2b.byte2 1 -XChar2b 2 -XwcTextItem.chars 0 -XwcTextItem.nchars 8 -XwcTextItem.delta 12 -XwcTextItem.font_set 16 -XwcTextItem 24 -XUnmapEvent.type 0 -XUnmapEvent.serial 8 -XUnmapEvent.send_event 16 -XUnmapEvent.display 24 -XUnmapEvent.event 32 -XUnmapEvent.window 40 -XUnmapEvent.from_configure 48 -XUnmapEvent 56 -awtImageData.Depth 0 -awtImageData.wsImageFormat 4 -awtImageData.clrdata 16 -awtImageData.convert 48 -awtImageData 560 -XGCValues.function 0 -XGCValues.plane_mask 8 -XGCValues.foreground 16 -XGCValues.background 24 -XGCValues.line_width 32 -XGCValues.line_style 36 -XGCValues.cap_style 40 -XGCValues.join_style 44 -XGCValues.fill_style 48 -XGCValues.fill_rule 52 -XGCValues.arc_mode 56 -XGCValues.tile 64 -XGCValues.stipple 72 -XGCValues.ts_x_origin 80 -XGCValues.ts_y_origin 84 -XGCValues.font 88 -XGCValues.subwindow_mode 96 -XGCValues.graphics_exposures 100 -XGCValues.clip_x_origin 104 -XGCValues.clip_y_origin 108 -XGCValues.clip_mask 112 -XGCValues.dash_offset 120 -XGCValues.dashes 124 -XGCValues 128 -XFocusChangeEvent.type 0 -XFocusChangeEvent.serial 8 -XFocusChangeEvent.send_event 16 -XFocusChangeEvent.display 24 -XFocusChangeEvent.window 32 -XFocusChangeEvent.mode 40 -XFocusChangeEvent.detail 44 -XFocusChangeEvent 48 -XMapEvent.type 0 -XMapEvent.serial 8 -XMapEvent.send_event 16 -XMapEvent.display 24 -XMapEvent.event 32 -XMapEvent.window 40 -XMapEvent.override_redirect 48 -XMapEvent 56 -XIMHotKeyTriggers.num_hot_key 0 -XIMHotKeyTriggers.key 8 -XIMHotKeyTriggers 16 -XKeyboardState.key_click_percent 0 -XKeyboardState.bell_percent 4 -XKeyboardState.bell_pitch 8 -XKeyboardState.bell_duration 12 -XKeyboardState.led_mask 16 -XKeyboardState.global_auto_repeat 24 -XKeyboardState.auto_repeats 28 -XKeyboardState 64 -XMotionEvent.type 0 -XMotionEvent.serial 8 -XMotionEvent.send_event 16 -XMotionEvent.display 24 -XMotionEvent.window 32 -XMotionEvent.root 40 -XMotionEvent.subwindow 48 -XMotionEvent.time 56 -XMotionEvent.x 64 -XMotionEvent.y 68 -XMotionEvent.x_root 72 -XMotionEvent.y_root 76 -XMotionEvent.state 80 -XMotionEvent.is_hint 84 -XMotionEvent.same_screen 88 -XMotionEvent 96 -XIMPreeditStateNotifyCallbackStruct.state 0 -XIMPreeditStateNotifyCallbackStruct 8 -XAnyEvent.type 0 -XAnyEvent.serial 8 -XAnyEvent.send_event 16 -XAnyEvent.display 24 -XAnyEvent.window 32 -XAnyEvent 40 -XIMCallback.client_data 0 -XIMCallback.callback 8 -XIMCallback 16 -XVisualInfo.visual 0 -XVisualInfo.visualid 8 -XVisualInfo.screen 16 -XVisualInfo.depth 20 -XVisualInfo.class 24 -XVisualInfo.red_mask 32 -XVisualInfo.green_mask 40 -XVisualInfo.blue_mask 48 -XVisualInfo.colormap_size 56 -XVisualInfo.bits_per_rgb 60 -XVisualInfo 64 -XCreateWindowEvent.type 0 -XCreateWindowEvent.serial 8 -XCreateWindowEvent.send_event 16 -XCreateWindowEvent.display 24 -XCreateWindowEvent.parent 32 -XCreateWindowEvent.window 40 -XCreateWindowEvent.x 48 -XCreateWindowEvent.y 52 -XCreateWindowEvent.width 56 -XCreateWindowEvent.height 60 -XCreateWindowEvent.border_width 64 -XCreateWindowEvent.override_redirect 68 -XCreateWindowEvent 72 -XIMValuesList.count_values 0 -XIMValuesList.supported_values 8 -XIMValuesList 16 -XKeymapEvent.type 0 -XKeymapEvent.serial 8 -XKeymapEvent.send_event 16 -XKeymapEvent.display 24 -XKeymapEvent.window 32 -XKeymapEvent.key_vector 40 -XKeymapEvent 72 -XButtonEvent.type 0 -XButtonEvent.serial 8 -XButtonEvent.send_event 16 -XButtonEvent.display 24 -XButtonEvent.window 32 -XButtonEvent.root 40 -XButtonEvent.subwindow 48 -XButtonEvent.time 56 -XButtonEvent.x 64 -XButtonEvent.y 68 -XButtonEvent.x_root 72 -XButtonEvent.y_root 76 -XButtonEvent.state 80 -XButtonEvent.button 84 -XButtonEvent.same_screen 88 -XButtonEvent 96 -XWMHints.flags 0 -XWMHints.initial_state 12 -XWMHints.icon_pixmap 16 -XWMHints.icon_window 24 -XWMHints.icon_x 32 -XWMHints.icon_y 36 -XWMHints.icon_mask 40 -XWMHints.input 8 -XWMHints.window_group 48 -XWMHints 56 -ScreenFormat.ext_data 0 -ScreenFormat.depth 8 -ScreenFormat.bits_per_pixel 12 -ScreenFormat.scanline_pad 16 -ScreenFormat 24 -XCrossingEvent.type 0 -XCrossingEvent.serial 8 -XCrossingEvent.send_event 16 -XCrossingEvent.display 24 -XCrossingEvent.window 32 -XCrossingEvent.root 40 -XCrossingEvent.subwindow 48 -XCrossingEvent.time 56 -XCrossingEvent.x 64 -XCrossingEvent.y 68 -XCrossingEvent.x_root 72 -XCrossingEvent.y_root 76 -XCrossingEvent.mode 80 -XCrossingEvent.detail 84 -XCrossingEvent.same_screen 88 -XCrossingEvent.focus 92 -XCrossingEvent.state 96 -XCrossingEvent 104 -XConfigureRequestEvent.type 0 -XConfigureRequestEvent.serial 8 -XConfigureRequestEvent.send_event 16 -XConfigureRequestEvent.display 24 -XConfigureRequestEvent.parent 32 -XConfigureRequestEvent.window 40 -XConfigureRequestEvent.x 48 -XConfigureRequestEvent.y 52 -XConfigureRequestEvent.width 56 -XConfigureRequestEvent.height 60 -XConfigureRequestEvent.border_width 64 -XConfigureRequestEvent.above 72 -XConfigureRequestEvent.detail 80 -XConfigureRequestEvent.value_mask 88 -XConfigureRequestEvent 96 -XSelectionRequestEvent.type 0 -XSelectionRequestEvent.serial 8 -XSelectionRequestEvent.send_event 16 -XSelectionRequestEvent.display 24 -XSelectionRequestEvent.owner 32 -XSelectionRequestEvent.requestor 40 -XSelectionRequestEvent.selection 48 -XSelectionRequestEvent.target 56 -XSelectionRequestEvent.property 64 -XSelectionRequestEvent.time 72 -XSelectionRequestEvent 80 -XFontSetExtents.max_ink_extent 0 -XFontSetExtents.max_logical_extent 8 -XFontSetExtents 16 -XExtCodes.extension 0 -XExtCodes.major_opcode 4 -XExtCodes.first_event 8 -XExtCodes.first_error 12 -XExtCodes 16 -XHostAddress.family 0 -XHostAddress.length 4 -XHostAddress.address 8 -XHostAddress 16 -ColorData.awt_Colors 0 -ColorData.awt_numICMcolors 8 -ColorData.awt_icmLUT 16 -ColorData.awt_icmLUT2Colors 24 -ColorData.img_grays 32 -ColorData.img_clr_tbl 40 -ColorData.img_oda_red 48 -ColorData.img_oda_green 56 -ColorData.img_oda_blue 64 -ColorData.pGrayInverseLutData 72 -ColorData.screendata 80 -ColorData 88 -XColormapEvent.type 0 -XColormapEvent.serial 8 -XColormapEvent.send_event 16 -XColormapEvent.display 24 -XColormapEvent.window 32 -XColormapEvent.colormap 40 -XColormapEvent.new 48 -XColormapEvent.state 52 -XColormapEvent 56 -Depth.depth 0 -Depth.nvisuals 4 -Depth.visuals 8 -Depth 16 -XEvent.type 0 -XEvent.xany 0 -XEvent.xkey 0 -XEvent.xbutton 0 -XEvent.xmotion 0 -XEvent.xcrossing 0 -XEvent.xfocus 0 -XEvent.xexpose 0 -XEvent.xgraphicsexpose 0 -XEvent.xnoexpose 0 -XEvent.xvisibility 0 -XEvent.xcreatewindow 0 -XEvent.xdestroywindow 0 -XEvent.xunmap 0 -XEvent.xmap 0 -XEvent.xmaprequest 0 -XEvent.xreparent 0 -XEvent.xconfigure 0 -XEvent.xgravity 0 -XEvent.xresizerequest 0 -XEvent.xconfigurerequest 0 -XEvent.xcirculate 0 -XEvent.xcirculaterequest 0 -XEvent.xproperty 0 -XEvent.xselectionclear 0 -XEvent.xselectionrequest 0 -XEvent.xselection 0 -XEvent.xcolormap 0 -XEvent.xclient 0 -XEvent.xmapping 0 -XEvent.xerror 0 -XEvent.xkeymap 0 -XEvent.pad 0 -XEvent 192 -XDestroyWindowEvent.type 0 -XDestroyWindowEvent.serial 8 -XDestroyWindowEvent.send_event 16 -XDestroyWindowEvent.display 24 -XDestroyWindowEvent.event 32 -XDestroyWindowEvent.window 40 -XDestroyWindowEvent 48 -XComposeStatus.compose_ptr 0 -XComposeStatus.chars_matched 8 -XComposeStatus 16 -AwtGraphicsConfigData.awt_depth 0 -AwtGraphicsConfigData.awt_cmap 8 -AwtGraphicsConfigData.awt_visInfo 16 -AwtGraphicsConfigData.awt_num_colors 80 -AwtGraphicsConfigData.awtImage 88 -AwtGraphicsConfigData.AwtColorMatch 96 -AwtGraphicsConfigData.monoImage 104 -AwtGraphicsConfigData.monoPixmap 112 -AwtGraphicsConfigData.monoPixmapWidth 120 -AwtGraphicsConfigData.monoPixmapHeight 124 -AwtGraphicsConfigData.monoPixmapGC 128 -AwtGraphicsConfigData.pixelStride 136 -AwtGraphicsConfigData.color_data 144 -AwtGraphicsConfigData.glxInfo 152 -AwtGraphicsConfigData.isTranslucencySupported 160 -AwtGraphicsConfigData 168 -XIMText.length 0 -XIMText.feedback 8 -XIMText.encoding_is_wchar 16 -XIMText.string 24 -XIMText 32 diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index ad8f29778..1f8264f67 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -154,10 +154,6 @@ pre-configure: --with-gcj=$(STAGING_JAVA_HOST_DIR)/usr/bin/gcj \ --with-ecj-jar=$(STAGING_JAVA_HOST_DIR)/usr/share/java/ecj.jar \ --without-rhino ;\ - mkdir -p $(WRKBUILD)/generated/sun/awt/X11/generator/ ; \ - mkdir -p $(WRKBUILD)/openjdk.build/gensrc/sun/awt/X11/generator/ ; \ - cp $(TOPDIR)/jtools/openjdk/files/sizes.* $(WRKBUILD)/generated/sun/awt/X11/generator/; \ - cp $(TOPDIR)/jtools/openjdk/files/sizes.* $(WRKBUILD)/openjdk.build/gensrc/sun/awt/X11/generator/; \ env ${OPENJDK_NATIVE_ENV} $(MAKE) icedtea-ecj # fixup symlinks to bootstrap jdk ln -sf $(BOOTSTRAPJDK)/bin/java $(WRKBUILD)/openjdk.build-ecj/j2sdk-image/bin/java diff --git a/package/openjdk/patches/disable-sizers.patch b/package/openjdk/patches/disable-sizers.patch deleted file mode 100644 index 46325008c..000000000 --- a/package/openjdk/patches/disable-sizers.patch +++ /dev/null @@ -1,12 +0,0 @@ ---- w-openjdk-6.orig/openjdk-6/jdk/make/sun/xawt/Makefile 2011-02-28 17:06:12.000000000 +0100 -+++ w-openjdk-6/openjdk-6/jdk/make/sun/xawt/Makefile 2011-04-13 12:00:18.618922673 +0200 -@@ -237,7 +237,8 @@ - $(BOOT_JAVA_CMD) -cp $(WRAPPER_GENERATOR_TEMPDIR) WrapperGenerator \ - $(SIZER_DIR) $(XLIBTYPES) "sizer" $(subst .,,$(suffix $(basename $@))) - --$(SIZES): $(SIZERS) -+$(SIZES): -+ $(prep-target) - @if [ "$(DOHACK)$@" = "true$(PREDEFINED_SIZES)" ]; then \ - $(ECHO) COPYING $(PREDEFINED_SIZES_TMPL) into $@; \ - $(CP) $(PREDEFINED_SIZES_TMPL) $@; \ diff --git a/package/openjdk/patches/qemu-sizer.patch b/package/openjdk/patches/qemu-sizer.patch new file mode 100644 index 000000000..b0049e852 --- /dev/null +++ b/package/openjdk/patches/qemu-sizer.patch @@ -0,0 +1,22 @@ +--- w-openjdk-6.orig/openjdk-6/jdk/make/sun/xawt/Makefile 2011-02-28 17:06:12.000000000 +0100 ++++ w-openjdk-6/openjdk-6/jdk/make/sun/xawt/Makefile 2011-08-20 18:45:28.499240773 +0200 +@@ -225,7 +225,7 @@ + + $(SIZERS): $(SIZERS_C) + $(prep-target) +- $(CC) $(CFLAGS_$(subst .,,$(suffix $@))) $(CPPFLAGS) -o $@ $(SIZER)$(suffix $@).c ++ $(CC) -static $(CFLAGS_$(subst .,,$(suffix $@))) $(CPPFLAGS) -o $@ $(SIZER)$(suffix $@).c + + $(WRAPPER_GENERATOR_CLASS): $(WRAPPER_GENERATOR_JAVA) + $(prep-target) +@@ -243,8 +243,8 @@ + $(CP) $(PREDEFINED_SIZES_TMPL) $@; \ + $(CHMOD) +w $@;\ + else \ +- $(ECHO) GENERATING $@; \ +- $(WRAPPER_GENERATOR_DIR)/sizer$(suffix $@) > $@; \ ++ $(ECHO) GENERATING $@ via $(QEMU) $(WRAPPER_GENERATOR_DIR)/sizer..; \ ++ $(QEMU) $(WRAPPER_GENERATOR_DIR)/sizer$(suffix $@) > $@; \ + fi + @if [ "$(DOCOMPARE)$(suffix $@)" = "true.64" ]; then \ + $(ECHO) COMPARING $@ and $(STORED_SIZES_TMPL_$(PLATFORM)_$(LIBARCH)); \ -- cgit v1.2.3 From dcbfc98334c615ffd2dd05315a1aef936f65ad46 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Sun, 21 Aug 2011 11:49:58 +0200 Subject: cleanup duplicate environment variables, cosmetic changes --- package/openjdk/Makefile | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 1f8264f67..0cdea7b0d 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -24,7 +24,6 @@ PKG_SITES:= http://download.java.net/openjdk/jdk6/promoted/b22/ \ http://icedtea.classpath.org/download/drops/ \ http://icedtea.classpath.org/download/source/ -#PKG_CFLINE_OPENJDK:= depends on ADK_TARGET_LIB_GLIBC || ADK_TARGET_LIB_EGLIBC && !ADK_TARGET_SYSTEM_LEMOTE_YEELONG PKG_HOST_DEPENDS:= !darwin !cygwin !openbsd !netbsd !freebsd PKG_ARCH_DEPENDS:= arm mips x86 x86_64 PKG_SYSTEM_DEPENDS:= !lemote-yeelong !linksys-ag241 !fon-fon2100 @@ -55,7 +54,6 @@ PKGCD_ZERO:= zero-assembly backend PKGCD_SHARK:= Shark JIT backend (needs eglibc/glibc) PKGCB_SHARK:= llvm PKGCD_CACAO:= Cacao JIT backend -PKGCD_JAMVM:= JamVM backend include $(TOPDIR)/mk/package.mk @@ -75,9 +73,6 @@ endif ifeq ($(ADK_PACKAGE_OPENJDK_CACAO),y) CONFIGURE_BACKEND:= --enable-cacao endif -ifeq ($(ADK_PACKAGE_OPENJDK_JAMVM),y) -CONFIGURE_BACKEND:= --enable-jamvm -endif CONFIGURE_ARGS+= $(CONFIGURE_BACKEND) CONFIGURE_ARGS+= --disable-docs \ @@ -101,10 +96,10 @@ CONFIGURE_ENV+= PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET MAKE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ - GCC_HONOUR_COPTS=s \ + GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) -OPENJDK_NATIVE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ +#OPENJDK_NATIVE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ @@ -128,7 +123,7 @@ do-extract: pre-configure: cd ${WRKBUILD}; rm -rf config.{cache,status}; \ - export $(MAKE_ENV) ${OPENJDK_NATIVE_ENV} ; ./configure \ + export $(MAKE_ENV); ./configure \ ${CONFIGURE_TRIPLE} \ $(CONFIGURE_BACKEND) \ --prefix=/usr \ @@ -154,7 +149,7 @@ pre-configure: --with-gcj=$(STAGING_JAVA_HOST_DIR)/usr/bin/gcj \ --with-ecj-jar=$(STAGING_JAVA_HOST_DIR)/usr/share/java/ecj.jar \ --without-rhino ;\ - env ${OPENJDK_NATIVE_ENV} $(MAKE) icedtea-ecj + env ${MAKE_ENV} $(MAKE) icedtea-ecj # fixup symlinks to bootstrap jdk ln -sf $(BOOTSTRAPJDK)/bin/java $(WRKBUILD)/openjdk.build-ecj/j2sdk-image/bin/java ln -sf $(BOOTSTRAPJDK)/bin/javac $(WRKBUILD)/openjdk.build-ecj/j2sdk-image/bin/javac -- cgit v1.2.3 From 23c5e02a837eb148c87cf85309bdba6039022e2a Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 04:55:35 +0200 Subject: unify configure arguments --- package/openjdk/Makefile | 30 ++++++------------------------ 1 file changed, 6 insertions(+), 24 deletions(-) diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 0cdea7b0d..58f54c3ea 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -74,9 +74,7 @@ ifeq ($(ADK_PACKAGE_OPENJDK_CACAO),y) CONFIGURE_BACKEND:= --enable-cacao endif -CONFIGURE_ARGS+= $(CONFIGURE_BACKEND) -CONFIGURE_ARGS+= --disable-docs \ - --disable-bootstrap \ +CONFIGURE_COMMON:= --disable-docs \ --enable-openjdk-cross-compilation \ --with-openjdk-src-dir=$(WRKDIST)/$(PKG_NAME)-$(PKG_VERSION) \ --with-xalan2-jar=${WRKDIST}/${XALAN_NAME}_${XALAN_VERSION}/xalan.jar \ @@ -92,18 +90,16 @@ CONFIGURE_ARGS+= --disable-docs \ --with-gcj=$(STAGING_JAVA_HOST_DIR)/usr/bin/gcj \ --without-rhino +CONFIGURE_ARGS+= $(CONFIGURE_BACKEND) +CONFIGURE_ARGS+= $(CONFIGURE_COMMON) +CONFIGURE_ARGS+= --disable-bootstrap + CONFIGURE_ENV+= PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin MAKE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) - -#OPENJDK_NATIVE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ - ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ - PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ - GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ - TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) ALL_TARGET:= icedtea # add include path for Xrender.h from staging directory @@ -134,21 +130,7 @@ pre-configure: --localstatedir=/var \ --sysconfdir=/etc \ --enable-bootstrap \ - --enable-openjdk-cross-compilation \ - --with-openjdk-src-dir=$(WRKDIST)/$(PKG_NAME)-$(PKG_VERSION) \ - --with-xalan2-jar=${WRKDIST}/${XALAN_NAME}_${XALAN_VERSION}/xalan.jar \ - --with-xalan2-serializer-jar=${WRKDIST}/${XALAN_NAME}_${XALAN_VERSION}/serializer.jar \ - --with-xerces2-jar=${WRKDIST}/${XALAN_NAME}_${XALAN_VERSION}/xercesImpl.jar \ - --with-jdk-home=$(BOOTSTRAPJDK) \ - --with-java=$(BOOTSTRAPJDK)/bin/java \ - --with-javac=$(BOOTSTRAPJDK)/bin/javac \ - --with-javah=$(BOOTSTRAPJDK)/bin/javah \ - --with-jar=$(BOOTSTRAPJDK)/bin/jar \ - --with-rmic=$(BOOTSTRAPJDK)/bin/rmic \ - --with-native2ascii=$(BOOTSTRAPJDK)/bin/native2ascii \ - --with-gcj=$(STAGING_JAVA_HOST_DIR)/usr/bin/gcj \ - --with-ecj-jar=$(STAGING_JAVA_HOST_DIR)/usr/share/java/ecj.jar \ - --without-rhino ;\ + $(CONFIGURE_COMMON) ;\ env ${MAKE_ENV} $(MAKE) icedtea-ecj # fixup symlinks to bootstrap jdk ln -sf $(BOOTSTRAPJDK)/bin/java $(WRKBUILD)/openjdk.build-ecj/j2sdk-image/bin/java -- cgit v1.2.3 From f41e4877defd5be85457121c5fd9b923a943d8ed Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 06:26:22 +0200 Subject: fix the help for usb boot, root= is required for now --- target/mips/Makefile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/target/mips/Makefile b/target/mips/Makefile index 7fc44a976..5d606046f 100644 --- a/target/mips/Makefile +++ b/target/mips/Makefile @@ -135,7 +135,8 @@ imageinstall: $(BIN_DIR)/$(ROOTFSTARBALL) ifeq ($(ADK_TARGET_SYSTEM_LEMOTE_YEELONG),y) @echo "Startup the netbook and type del to enter PMON:" @echo "PMON> load /dev/fs/ext2@usb0/boot/kernel" - @echo "PMON> g console=tty no_auto_cmd" + @echo "PMON> g root=/dev/sdc1" + @echo "The root parameter have to be changed." endif endif ifeq ($(ADK_TARGET_FS),cf) -- cgit v1.2.3 From a2d86599cb6ba6fb5ca5c8cea98557a4e426df14 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 06:30:17 +0200 Subject: uClibc nowadays works for pagesize != 4kb, so lemote is supported --- target/config/Config.in | 1 - 1 file changed, 1 deletion(-) diff --git a/target/config/Config.in b/target/config/Config.in index 5e89eb8f6..38dca4b19 100644 --- a/target/config/Config.in +++ b/target/config/Config.in @@ -334,7 +334,6 @@ config ADK_TARGET_LIB_UCLIBC boolean select ADK_uclibc depends on \ - !ADK_TARGET_SYSTEM_LEMOTE_YEELONG && \ !ADK_LINUX_SPARC64 && \ !ADK_LINUX_PPC64 && \ !ADK_LINUX_NATIVE -- cgit v1.2.3 From ea1aef3da3e68a062f28718a3e697b3148eef1fe Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 06:31:02 +0200 Subject: allow FETCH_STYLE=manual to succeed. simplify fetch loop. --- mk/buildhlp.mk | 18 +++++++++++++++--- mk/fetch.mk | 7 ------- 2 files changed, 15 insertions(+), 10 deletions(-) diff --git a/mk/buildhlp.mk b/mk/buildhlp.mk index 3c79fc1e8..19b761f46 100644 --- a/mk/buildhlp.mk +++ b/mk/buildhlp.mk @@ -49,15 +49,27 @@ ifeq (${_CHECKSUM_COOKIE},) endif ifeq ($(EXTRACT_OVERRIDE),1) ${MAKE} do-extract -else +else ${EXTRACT_CMD} endif @${MAKE} post-extract $(MAKE_TRACE) touch $@ __use_generic_patch_target:=42 -else ifeq ($(strip ${_IN_PACKAGE}),1) -$(warning This package does not use the generic extraction and patch target; it's most likely to fail.) +else +include ${TOPDIR}/mk/fetch.mk +${WRKDIST}/.extract_done: ${_CHECKSUM_COOKIE} + $(MAKE) fetch +ifeq (${_CHECKSUM_COOKIE},) + rm -rf ${WRKDIST} ${WRKSRC} ${WRKBUILD} +endif +ifeq ($(EXTRACT_OVERRIDE),1) + ${MAKE} do-extract +else + ${EXTRACT_CMD} +endif + @${MAKE} post-extract $(MAKE_TRACE) + touch $@ endif ifeq ($(strip ${__use_generic_patch_target}),42) diff --git a/mk/fetch.mk b/mk/fetch.mk index 5c3edf918..a2590d467 100644 --- a/mk/fetch.mk +++ b/mk/fetch.mk @@ -59,14 +59,7 @@ endif define FETCH_template $(1): @fullname='$(1)'; \ - subname=$$$${fullname##$${DISTDIR}/}; \ filename=$$$${fullname##*/}; \ - i='$${LOCAL_DISTDIR}'; \ - if [[ -n $$$$i && -e $$$$i/$$$$subname ]]; then \ - cd "$$$$i"; \ - echo pax -rw "$$$$subname" '$${DISTDIR}/'; \ - exec pax -rw "$$$$subname" '$${DISTDIR}/'; \ - fi; \ mkdir -p "$$$${fullname%%/$$$$filename}"; \ cd "$$$${fullname%%/$$$$filename}"; \ for site in $${PKG_SITES} $${MASTER_SITE_BACKUP}; do \ -- cgit v1.2.3 From 2a8f18f0aa29136e8d5dce664de031336e531360 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 08:00:09 +0200 Subject: simplify patch, remove unused cruft --- package/openjdk/Makefile | 3 +- package/openjdk/patches/icedtea6-Makefile_in.patch | 46 ---------------------- 2 files changed, 1 insertion(+), 48 deletions(-) diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 58f54c3ea..347f3b01d 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -98,8 +98,7 @@ CONFIGURE_ENV+= PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET MAKE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ - GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) \ - TARGET_ALIAS=$(GNU_TARGET_NAME) BUILD_ALIAS=$(GNU_HOST_NAME) HOST_ALIAS=$(GNU_TARGET_NAME) + GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) ALL_TARGET:= icedtea # add include path for Xrender.h from staging directory diff --git a/package/openjdk/patches/icedtea6-Makefile_in.patch b/package/openjdk/patches/icedtea6-Makefile_in.patch index 193e008aa..7febd6cac 100644 --- a/package/openjdk/patches/icedtea6-Makefile_in.patch +++ b/package/openjdk/patches/icedtea6-Makefile_in.patch @@ -1,41 +1,5 @@ --- w-openjdk-6-1.orig/icedtea6-1.10/Makefile.in 2011-03-02 20:48:45.000000000 +0100 +++ w-openjdk-6-1/icedtea6-1.10/Makefile.in 2011-04-02 23:33:17.000000000 +0200 -@@ -328,7 +328,7 @@ - am__untar = @am__untar@ - bindir = @bindir@ - build = @build@ --build_alias = @build_alias@ -+build_alias = ${BUILD_ALIAS} - build_cpu = @build_cpu@ - build_os = @build_os@ - build_vendor = @build_vendor@ -@@ -339,7 +339,7 @@ - dvidir = @dvidir@ - exec_prefix = @exec_prefix@ - host = @host@ --host_alias = @host_alias@ -+host_alias = ${HOST_ALIAS} - host_cpu = @host_cpu@ - host_os = @host_os@ - host_vendor = @host_vendor@ -@@ -362,7 +362,7 @@ - sharedstatedir = @sharedstatedir@ - srcdir = @srcdir@ - sysconfdir = @sysconfdir@ --target_alias = @target_alias@ -+target_alias = ${TARGET_ALIAS} - top_build_prefix = @top_build_prefix@ - top_builddir = @top_builddir@ - top_srcdir = @top_srcdir@ -@@ -1329,7 +1329,7 @@ stamps/extract-openjdk.stamp: stamps/dow - @OPENJDK_SRC_DIR_FOUND_TRUE@ cp -pPR $(OPENJDK_SRC_DIR_LINK) $(OPENJDK_SRC_DIR) openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ if ! test -d openjdk ; then \ --@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPRl openjdk.hg openjdk ; \ -+@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPR openjdk.hg openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ set -e ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ if ! test -d openjdk ; \ @@ -1576,7 +1576,7 @@ clean-overlay: # FIXME (missing): Rename to clone-ecj. stamps/extract-ecj.stamp: $(OPENJDK_TREE) @@ -66,13 +30,3 @@ touch stamps/native-ecj.stamp clean-native-ecj: -@@ -2167,6 +2167,9 @@ - stamps/jamvm.stamp: $(OPENJDK_TREE) stamps/rt.stamp - @BUILD_JAMVM_TRUE@ cd jamvm/jamvm && \ - @BUILD_JAMVM_TRUE@ ./autogen.sh --with-java-runtime-library=openjdk \ -+@BUILD_JAMVM_TRUE@ --host=$(host_alias) \ -+@BUILD_JAMVM_TRUE@ --build=$(build_alias) \ -+@BUILD_JAMVM_TRUE@ --target=$(target_alias) \ - @BUILD_JAMVM_TRUE@ --prefix=$(abs_top_builddir)/jamvm/install ; \ - @BUILD_JAMVM_TRUE@ $(MAKE) ; \ - @BUILD_JAMVM_TRUE@ $(MAKE) install -- cgit v1.2.3 From ce867d683d2e8414bf95c307a34dae9e4df21623 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 08:40:05 +0200 Subject: implement submodel for foxboard lx. resolves duplicate full build for this systems --- mk/modules.mk | 4 +--- target/config/Config.in | 14 ++++++++++++++ target/cris/sys-available/foxboard-lx416 | 9 --------- target/cris/sys-available/foxboard-lx832 | 9 --------- target/linux/config/Config.in.block | 9 +++------ target/linux/config/Config.in.debug | 3 +-- target/linux/config/Config.in.fs | 3 +-- target/linux/config/Config.in.input | 3 +-- target/linux/config/Config.in.kernel | 18 +++++++++--------- target/linux/config/Config.in.netdevice | 6 ++---- target/linux/config/Config.in.usb | 15 +++++---------- 11 files changed, 37 insertions(+), 56 deletions(-) delete mode 100644 target/cris/sys-available/foxboard-lx416 delete mode 100644 target/cris/sys-available/foxboard-lx832 diff --git a/mk/modules.mk b/mk/modules.mk index c9819c697..e51732a4c 100644 --- a/mk/modules.mk +++ b/mk/modules.mk @@ -1180,13 +1180,11 @@ $(eval $(call KMOD_template,INPUT_EVDEV,input-evdev,\ # USB # -ifeq ($(ADK_TARGET_SYSTEM_FOXBOARD_LX832),) -ifeq ($(ADK_TARGET_SYSTEM_FOXBOARD_LX416),) +ifeq ($(ADK_TARGET_SYSTEM_FOXBOARD_LX),) $(eval $(call KMOD_template,USB,usb,\ $(MODULES_DIR)/kernel/drivers/usb/core/usbcore \ ,50)) endif -endif $(eval $(call KMOD_template,USB_EHCI_HCD,usb-ehci-hcd,\ $(MODULES_DIR)/kernel/drivers/usb/host/ehci-hcd \ diff --git a/target/config/Config.in b/target/config/Config.in index 38dca4b19..a15e42e27 100644 --- a/target/config/Config.in +++ b/target/config/Config.in @@ -73,6 +73,19 @@ config ADK_TARGET_ABI_N64 endchoice +# submodel support +choice +prompt "Foxboard LX Model" +depends on ADK_TARGET_SYSTEM_FOXBOARD_LX + +config ADK_TARGET_FOXBOARD_MODEL_LX416 + boolean "Foxboard LX 4x16" + +config ADK_TARGET_FOXBOARD_MODEL_LX832 + boolean "Foxboard LX 8x32" + +endchoice + choice prompt "Broadcom BCM47xx Model" depends on ADK_TARGET_SYSTEM_BROADCOM_BCM47XX @@ -302,6 +315,7 @@ config ADK_TARGET_CMDLINE default "console=ttyS0,115200 console=tty0" if ADK_TARGET_SYSTEM_IBM_X40 default "console=ttyS0,115200" if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D13 default "console=ttyS0,115200" if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D2 + default "console=ttyS0,115200" if ADK_TARGET_SYSTEM_FOXBOARD_LX default "" # c library diff --git a/target/cris/sys-available/foxboard-lx416 b/target/cris/sys-available/foxboard-lx416 deleted file mode 100644 index 2dce884c5..000000000 --- a/target/cris/sys-available/foxboard-lx416 +++ /dev/null @@ -1,9 +0,0 @@ -config ADK_TARGET_SYSTEM_FOXBOARD_LX416 - bool "FOX Board LX416" - select ADK_cris - select ADK_foxboard_lx416 - select ADK_TARGET_WITH_MTD - select ADK_TARGET_WITH_USB - help - Build a system for FOX Board LX416. - diff --git a/target/cris/sys-available/foxboard-lx832 b/target/cris/sys-available/foxboard-lx832 deleted file mode 100644 index a5e3de1e0..000000000 --- a/target/cris/sys-available/foxboard-lx832 +++ /dev/null @@ -1,9 +0,0 @@ -config ADK_TARGET_SYSTEM_FOXBOARD_LX832 - bool "FOX Board LX832" - select ADK_cris - select ADK_foxboard_lx832 - select ADK_TARGET_WITH_MTD - select ADK_TARGET_WITH_USB - help - Build a system for FOX Board LX832. - diff --git a/target/linux/config/Config.in.block b/target/linux/config/Config.in.block index 7e7d6cd9c..78e7b1bd5 100644 --- a/target/linux/config/Config.in.block +++ b/target/linux/config/Config.in.block @@ -274,8 +274,7 @@ config ADK_KPACKAGE_KMOD_BLK_DEV_MD tristate depends on !ADK_KERNEL_BLK_DEV_MD select ADK_KERNEL_MD - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX help config ADK_KERNEL_MD_RAID0 @@ -310,8 +309,7 @@ config ADK_KPACKAGE_KMOD_BLK_DEV_DM prompt "kmod-blk-dev-dm................... Device Mapper support" select ADK_KERNEL_MD depends on !ADK_KERNEL_BLK_DEV_DM - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX tristate help Device-mapper is a low level volume manager. It works by allowing @@ -359,8 +357,7 @@ config ADK_KPACKAGE_KMOD_BLK_DEV_DRBD tristate select ADK_KERNEL_BLK_DEV select ADK_KERNEL_CONNECTOR - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX help DRBD - http://www.drbd.org diff --git a/target/linux/config/Config.in.debug b/target/linux/config/Config.in.debug index 891a00c6e..0aed48de9 100644 --- a/target/linux/config/Config.in.debug +++ b/target/linux/config/Config.in.debug @@ -60,8 +60,7 @@ config ADK_KPACKAGE_KMOD_OPROFILE prompt "kernel support for oprofile" tristate select ADK_KERNEL_PROFILING - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help use oprofile package to make use of the kernel support. diff --git a/target/linux/config/Config.in.fs b/target/linux/config/Config.in.fs index ee2adc39f..60b331755 100644 --- a/target/linux/config/Config.in.fs +++ b/target/linux/config/Config.in.fs @@ -190,8 +190,7 @@ config ADK_KPACKAGE_KMOD_XFS_FS tristate select ADK_KERNEL_EXPORTFS depends on !ADK_KERNEL_XFS_FS - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help XFS is a high performance journaling filesystem which originated diff --git a/target/linux/config/Config.in.input b/target/linux/config/Config.in.input index 4a18af573..b8566e569 100644 --- a/target/linux/config/Config.in.input +++ b/target/linux/config/Config.in.input @@ -61,8 +61,7 @@ config ADK_KPACKAGE_KMOD_USB_HID select ADK_KERNEL_INPUT select ADK_KERNEL_HID select ADK_PACKAGE_KMOD_USB_CONTROLLER - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX depends on ADK_TARGET_WITH_USB default n diff --git a/target/linux/config/Config.in.kernel b/target/linux/config/Config.in.kernel index 0400d8db6..696f7afc9 100644 --- a/target/linux/config/Config.in.kernel +++ b/target/linux/config/Config.in.kernel @@ -3,21 +3,21 @@ config ADK_KERNEL_EXPERIMENTAL config ADK_KERNEL_ETRAX_MTD_SIZE hex - depends on ADK_TARGET_SYSTEM_FOXBOARD_LX416 || ADK_TARGET_SYSTEM_FOXBOARD_LX832 - default "0x00400000" if ADK_TARGET_SYSTEM_FOXBOARD_LX416 - default "0x00800000" if ADK_TARGET_SYSTEM_FOXBOARD_LX832 + depends on ADK_TARGET_SYSTEM_FOXBOARD_LX + default "0x00400000" if ADK_TARGET_FOXBOARD_MODEL_LX416 + default "0x00800000" if ADK_TARGET_FOXBOARD_MODEL_LX832 config ADK_KERNEL_ETRAX_DRAM_SIZE int - depends on ADK_TARGET_SYSTEM_FOXBOARD_LX416 || ADK_TARGET_SYSTEM_FOXBOARD_LX832 - default "16" if ADK_TARGET_SYSTEM_FOXBOARD_LX416 - default "32" if ADK_TARGET_SYSTEM_FOXBOARD_LX832 + depends on ADK_TARGET_SYSTEM_FOXBOARD_LX + default "16" if ADK_TARGET_FOXBOARD_MODEL_LX416 + default "32" if ADK_TARGET_FOXBOARD_MODEL_LX832 config ADK_KERNEL_ETRAX_DEF_R_SDRAM_TIMING hex - depends on ADK_TARGET_SYSTEM_FOXBOARD_LX416 || ADK_TARGET_SYSTEM_FOXBOARD_LX832 - default "0x80608002" if ADK_TARGET_SYSTEM_FOXBOARD_LX416 - default "0x80008002" if ADK_TARGET_SYSTEM_FOXBOARD_LX832 + depends on ADK_TARGET_SYSTEM_FOXBOARD_LX + default "0x80608002" if ADK_TARGET_FOXBOARD_MODEL_LX416 + default "0x80008002" if ADK_TARGET_FOXBOARD_MODEL_LX832 config ADK_KERNEL_BLK_DEV_INITRD boolean diff --git a/target/linux/config/Config.in.netdevice b/target/linux/config/Config.in.netdevice index 14820b810..b7ae9c655 100644 --- a/target/linux/config/Config.in.netdevice +++ b/target/linux/config/Config.in.netdevice @@ -373,8 +373,7 @@ config ADK_KPACKAGE_KMOD_RTL8187 prompt "kmod-rtl8187................. Realtek RTL8187/RTL8187B wireless cards" tristate depends on ADK_TARGET_WITH_USB - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help Driver for Realtek RTL8187/RTL8187B wireless chips. @@ -389,8 +388,7 @@ config ADK_KPACKAGE_KMOD_P54_USB select ADK_KPACKAGE_KMOD_MAC80211 select ADK_KPACKAGE_KMOD_CRC_CCITT depends on ADK_PACKAGE_KMOD_USB_CONTROLLER - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help Driver for Prism54 USB adaptors. diff --git a/target/linux/config/Config.in.usb b/target/linux/config/Config.in.usb index 2bc8d73db..ba004a59b 100644 --- a/target/linux/config/Config.in.usb +++ b/target/linux/config/Config.in.usb @@ -75,8 +75,7 @@ config ADK_KPACKAGE_KMOD_USB_UHCI_HCD depends on ADK_KPACKAGE_KMOD_USB depends on !ADK_KERNEL_USB_UHCI_HCD depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default y if ADK_TARGET_SYSTEM_IBM_X40 default y if ADK_NATIVE_SYSTEM_IBM_X40 default y if ADK_TARGET_SYSTEM_LEMOTE_YEELONG @@ -97,8 +96,7 @@ config ADK_KPACKAGE_KMOD_USB_OHCI_HCD select ADK_PACKAGE_KMOD_USB_CONTROLLER depends on ADK_KPACKAGE_KMOD_USB #depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX1C default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D2 default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D13 @@ -120,8 +118,7 @@ config ADK_KPACKAGE_KMOD_USB_ISP116X_HCD select ADK_PACKAGE_KMOD_USB_CONTROLLER depends on ADK_KPACKAGE_KMOD_USB depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help The ISP1160 and ISP1161 chips are USB host controllers. Enable this @@ -135,8 +132,7 @@ config ADK_KPACKAGE_KMOD_USB_SL811_HCD select ADK_PACKAGE_KMOD_USB_CONTROLLER depends on ADK_KPACKAGE_KMOD_USB depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help The SL811HS is a single-port USB controller that supports either @@ -151,8 +147,7 @@ config ADK_KPACKAGE_KMOD_USB_EHCI_HCD select ADK_PACKAGE_KMOD_USB_CONTROLLER depends on !ADK_KERNEL_USB_EHCI_HCD depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX832 - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX416 + depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX depends on ADK_KPACKAGE_KMOD_USB default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX1C default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D2 -- cgit v1.2.3 From 3c6574084fc00de09699604cda24c75cb616c874 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 09:55:30 +0200 Subject: refresh kernel config, enable WLAN symbol, enable USB by default --- target/cris/kernel.config | 96 +- target/cris/sys-available/foxboard-lx | 9 + target/linux/config/Config.in.netdevice | 2 +- target/linux/config/Config.in.usb | 3 +- target/linux/patches/2.6.39/cris.patch | 7665 +------------------------------ 5 files changed, 181 insertions(+), 7594 deletions(-) create mode 100644 target/cris/sys-available/foxboard-lx diff --git a/target/cris/kernel.config b/target/cris/kernel.config index 755927166..8fbd0d9c7 100644 --- a/target/cris/kernel.config +++ b/target/cris/kernel.config @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.36 -# Tue Dec 28 18:58:02 2010 +# Linux/cris 2.6.39 Kernel Configuration +# Mon Aug 22 09:21:47 2011 # CONFIG_MMU=y CONFIG_ZONE_DMA=y @@ -36,29 +36,36 @@ CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set +CONFIG_HAVE_GENERIC_HARDIRQS=y + +# +# IRQ subsystem +# +CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_IRQ_SHOW=y # # RCU Subsystem # -CONFIG_TREE_RCU=y -# CONFIG_TINY_RCU is not set +CONFIG_TINY_RCU=y +# CONFIG_PREEMPT_RCU is not set # CONFIG_RCU_TRACE is not set -CONFIG_RCU_FANOUT=32 -# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_CGROUPS is not set -# CONFIG_SYSFS_DEPRECATED_V2 is not set -# CONFIG_RELAY is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set +# CONFIG_SYSFS_DEPRECATED is not set +# CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_UID16=y CONFIG_SYSCTL_SYSCALL=y # CONFIG_KALLSYMS is not set @@ -74,6 +81,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y # # Kernel Performance Events And Counters @@ -148,7 +156,6 @@ CONFIG_INLINE_WRITE_UNLOCK_IRQ=y CONFIG_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set -CONFIG_GENERIC_HARDIRQS=y CONFIG_ETRAX_CMDLINE="" CONFIG_ETRAX_WATCHDOG=y # CONFIG_ETRAX_WATCHDOG_NICE_DOGGY is not set @@ -164,12 +171,14 @@ CONFIG_FLATMEM=y CONFIG_FLAT_NODE_MEM_MAP=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 +# CONFIG_COMPACTION is not set # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y # CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 +CONFIG_NEED_PER_CPU_KM=y # # Hardware setup @@ -183,6 +192,7 @@ CONFIG_ETRAX100LX_V2=y CONFIG_ETRAX_ARCH_V10=y # CONFIG_ETRAX_ARCH_V32 is not set CONFIG_ETRAX_DRAM_SIZE=16 +CONFIG_ETRAX_MTD_SIZE=0x00800000 CONFIG_ETRAX_FLASH_BUSWIDTH=2 CONFIG_ETRAX_NANDFLASH_BUSWIDTH=1 CONFIG_ETRAX_FLASH1_SIZE=0 @@ -232,10 +242,9 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set -# CONFIG_NET_IPGRE is not set +# CONFIG_NET_IPGRE_DEMUX is not set # CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set @@ -277,6 +286,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -287,11 +297,18 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IRDA is not set # CONFIG_BT is not set # CONFIG_AF_RXRPC is not set -# CONFIG_WIRELESS is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +# CONFIG_LIB80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set # CONFIG_CAIF is not set +# CONFIG_CEPH_LIB is not set # # Drivers for built-in interfaces @@ -354,9 +371,7 @@ CONFIG_DEVTMPFS_MOUNT=y CONFIG_MTD=y # CONFIG_MTD_DEBUG is not set # CONFIG_MTD_TESTS is not set -CONFIG_MTD_CONCAT=y CONFIG_MTD_PARTITIONS=y -CONFIG_MTD_ROOTFS_ROOT_DEV=y # CONFIG_MTD_REDBOOT_PARTS is not set # CONFIG_MTD_CMDLINE_PARTS is not set # CONFIG_MTD_AR7_PARTS is not set @@ -367,6 +382,7 @@ CONFIG_MTD_ROOTFS_ROOT_DEV=y CONFIG_MTD_CHAR=y CONFIG_MTD_BLKDEVS=y CONFIG_MTD_BLOCK=y +CONFIG_MTD_BLOCK_RO=y # CONFIG_FTL is not set # CONFIG_NFTL is not set # CONFIG_INFTL is not set @@ -411,6 +427,7 @@ CONFIG_MTD_CFI_UTIL=y CONFIG_MTD_COMPLEX_MAPPINGS=y # CONFIG_MTD_PHYSMAP is not set # CONFIG_MTD_PLATRAM is not set +# CONFIG_MTD_LATCH_ADDR is not set # # Self-contained MTD device drivers @@ -433,15 +450,21 @@ CONFIG_MTD_COMPLEX_MAPPINGS=y # LPDDR flash memory drivers # # CONFIG_MTD_LPDDR is not set - -# -# UBI - Unsorted block images -# # CONFIG_MTD_UBI is not set # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set + +# +# SCSI device support +# +CONFIG_SCSI_MOD=y +# CONFIG_RAID_ATTRS is not set +# CONFIG_SCSI is not set +# CONFIG_SCSI_DMA is not set +# CONFIG_SCSI_NETLINK is not set +# CONFIG_MEDIA_SUPPORT is not set CONFIG_NETDEVICES=y # CONFIG_DUMMY is not set # CONFIG_BONDING is not set @@ -449,9 +472,9 @@ CONFIG_NETDEVICES=y # CONFIG_EQUALIZER is not set # CONFIG_TUN is not set # CONFIG_VETH is not set +CONFIG_MII=y # CONFIG_PHYLIB is not set CONFIG_NET_ETHERNET=y -CONFIG_MII=y # CONFIG_ETHOC is not set # CONFIG_DNET is not set # CONFIG_IBM_NEW_EMAC_ZMII is not set @@ -464,7 +487,9 @@ CONFIG_MII=y # CONFIG_KS8851_MLL is not set # CONFIG_NETDEV_1000 is not set # CONFIG_NETDEV_10000 is not set -# CONFIG_WLAN is not set +CONFIG_WLAN=y +# CONFIG_USB_ZD1201 is not set +# CONFIG_HOSTAP is not set # # Enable WiMAX (Networking options) to see the WiMAX drivers @@ -507,9 +532,12 @@ CONFIG_MII=y # Character devices # # CONFIG_VT is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set # CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers @@ -522,9 +550,7 @@ CONFIG_MII=y # CONFIG_SERIAL_TIMBERDALE is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set +# CONFIG_TTY_PRINTK is not set # CONFIG_IPMI_HANDLER is not set # CONFIG_HW_RANDOM is not set # CONFIG_RTC is not set @@ -546,17 +572,18 @@ CONFIG_UNIX98_PTYS=y # CONFIG_EXT4_FS is not set # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set -# CONFIG_FS_POSIX_ACL is not set # CONFIG_XFS_FS is not set -# CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set # CONFIG_NILFS2_FS is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set +# CONFIG_FANOTIFY is not set # CONFIG_QUOTA is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_QUOTACTL is not set # CONFIG_AUTOFS4_FS is not set # CONFIG_FUSE_FS is not set @@ -599,7 +626,6 @@ CONFIG_TMPFS=y # CONFIG_PARTITION_ADVANCED is not set CONFIG_MSDOS_PARTITION=y # CONFIG_NLS is not set -# CONFIG_DLM is not set # CONFIG_SOUND is not set CONFIG_USB_SUPPORT=y # CONFIG_USB_ARCH_HAS_HCD is not set @@ -681,6 +707,7 @@ CONFIG_USB=y # CONFIG_USB_IOWARRIOR is not set # CONFIG_USB_TEST is not set # CONFIG_USB_ISIGHTFW is not set +# CONFIG_USB_YUREX is not set # CONFIG_USB_GADGET is not set # @@ -694,6 +721,7 @@ CONFIG_USB=y # # CONFIG_SYSTEM_PROFILER is not set CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -702,19 +730,22 @@ CONFIG_MAGIC_SYSRQ=y # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set +# CONFIG_SPARSE_RCU_POINTER is not set # CONFIG_DEBUG_MEMORY_INIT is not set -# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set +# CONFIG_TEST_KSTRTOX is not set # CONFIG_NO_SEGFAULT_TERMINATION is not set # # Security options # # CONFIG_KEYS is not set +# CONFIG_SECURITY_DMESG_RESTRICT is not set # CONFIG_SECURITY is not set # CONFIG_SECURITYFS is not set CONFIG_DEFAULT_SECURITY_DAC=y @@ -739,6 +770,9 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y +# CONFIG_AVERAGE is not set diff --git a/target/cris/sys-available/foxboard-lx b/target/cris/sys-available/foxboard-lx new file mode 100644 index 000000000..0b4c81c68 --- /dev/null +++ b/target/cris/sys-available/foxboard-lx @@ -0,0 +1,9 @@ +config ADK_TARGET_SYSTEM_FOXBOARD_LX + bool "FOX Board LX" + select ADK_cris + select ADK_foxboard_lx + select ADK_TARGET_WITH_MTD + select ADK_TARGET_WITH_USB + help + Build a system for FOX Board LX models. + diff --git a/target/linux/config/Config.in.netdevice b/target/linux/config/Config.in.netdevice index b7ae9c655..1a84f6bcc 100644 --- a/target/linux/config/Config.in.netdevice +++ b/target/linux/config/Config.in.netdevice @@ -244,6 +244,7 @@ config ADK_KPACKAGE_KMOD_R8169 endmenu config ADK_KERNEL_WIRELESS + select ADK_KERNEL_NETDEVICES boolean config ADK_KERNEL_WIRELESS_EXT @@ -388,7 +389,6 @@ config ADK_KPACKAGE_KMOD_P54_USB select ADK_KPACKAGE_KMOD_MAC80211 select ADK_KPACKAGE_KMOD_CRC_CCITT depends on ADK_PACKAGE_KMOD_USB_CONTROLLER - depends on !ADK_TARGET_SYSTEM_FOXBOARD_LX default n help Driver for Prism54 USB adaptors. diff --git a/target/linux/config/Config.in.usb b/target/linux/config/Config.in.usb index ba004a59b..f16ef7dab 100644 --- a/target/linux/config/Config.in.usb +++ b/target/linux/config/Config.in.usb @@ -30,7 +30,6 @@ config ADK_KPACKAGE_KMOD_USB tristate select ADK_KERNEL_NLS depends on !ADK_KERNEL_USB - #depends on !ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX1C default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D2 default y if ADK_TARGET_SYSTEM_PCENGINES_ALIX2D13 @@ -38,6 +37,7 @@ config ADK_KPACKAGE_KMOD_USB default y if ADK_NATIVE_SYSTEM_IBM_X40 default y if ADK_TARGET_SYSTEM_LEMOTE_YEELONG default y if ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 + default y if ADK_TARGET_SYSTEM_FOXBOARD_LX default n help Universal Serial Bus (USB) is a specification for a serial bus @@ -178,6 +178,7 @@ config ADK_KPACKAGE_KMOD_USB_EHCI_HCD config ADK_PACKAGE_KMOD_USB_CONTROLLER tristate default y if ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20 + default y if ADK_TARGET_SYSTEM_FOXBOARD_LX default n config ADK_KPACKAGE_KMOD_USB_ACM diff --git a/target/linux/patches/2.6.39/cris.patch b/target/linux/patches/2.6.39/cris.patch index f58391a5d..3bdc0acb8 100644 --- a/target/linux/patches/2.6.39/cris.patch +++ b/target/linux/patches/2.6.39/cris.patch @@ -1,6 +1,6 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/axisflashmap.c linux-2.6.39/arch/cris/arch-v10/drivers/axisflashmap.c --- linux-2.6.39.orig/arch/cris/arch-v10/drivers/axisflashmap.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/arch-v10/drivers/axisflashmap.c 2011-07-28 16:16:35.633425525 +0200 ++++ linux-2.6.39/arch/cris/arch-v10/drivers/axisflashmap.c 2011-08-22 08:58:55.057980882 +0200 @@ -113,7 +113,7 @@ /* If no partition-table was found, we use this default-set. */ @@ -146,443 +146,9 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/axisflashmap.c linux-2.6. return err; } -diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/axisflashmap.c.orig linux-2.6.39/arch/cris/arch-v10/drivers/axisflashmap.c.orig ---- linux-2.6.39.orig/arch/cris/arch-v10/drivers/axisflashmap.c.orig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/cris/arch-v10/drivers/axisflashmap.c.orig 2011-05-19 06:06:34.000000000 +0200 -@@ -0,0 +1,430 @@ -+/* -+ * Physical mapping layer for MTD using the Axis partitiontable format -+ * -+ * Copyright (c) 2001, 2002 Axis Communications AB -+ * -+ * This file is under the GPL. -+ * -+ * First partition is always sector 0 regardless of if we find a partitiontable -+ * or not. In the start of the next sector, there can be a partitiontable that -+ * tells us what other partitions to define. If there isn't, we use a default -+ * partition split defined below. -+ * -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include -+#include -+ -+#ifdef CONFIG_CRIS_LOW_MAP -+#define FLASH_UNCACHED_ADDR KSEG_8 -+#define FLASH_CACHED_ADDR KSEG_5 -+#else -+#define FLASH_UNCACHED_ADDR KSEG_E -+#define FLASH_CACHED_ADDR KSEG_F -+#endif -+ -+#if CONFIG_ETRAX_FLASH_BUSWIDTH==1 -+#define flash_data __u8 -+#elif CONFIG_ETRAX_FLASH_BUSWIDTH==2 -+#define flash_data __u16 -+#elif CONFIG_ETRAX_FLASH_BUSWIDTH==4 -+#define flash_data __u32 -+#endif -+ -+/* From head.S */ -+extern unsigned long romfs_start, romfs_length, romfs_in_flash; -+ -+/* The master mtd for the entire flash. */ -+struct mtd_info* axisflash_mtd = NULL; -+ -+/* Map driver functions. */ -+ -+static map_word flash_read(struct map_info *map, unsigned long ofs) -+{ -+ map_word tmp; -+ tmp.x[0] = *(flash_data *)(map->map_priv_1 + ofs); -+ return tmp; -+} -+ -+static void flash_copy_from(struct map_info *map, void *to, -+ unsigned long from, ssize_t len) -+{ -+ memcpy(to, (void *)(map->map_priv_1 + from), len); -+} -+ -+static void flash_write(struct map_info *map, map_word d, unsigned long adr) -+{ -+ *(flash_data *)(map->map_priv_1 + adr) = (flash_data)d.x[0]; -+} -+ -+/* -+ * The map for chip select e0. -+ * -+ * We run into tricky coherence situations if we mix cached with uncached -+ * accesses to we only use the uncached version here. -+ * -+ * The size field is the total size where the flash chips may be mapped on the -+ * chip select. MTD probes should find all devices there and it does not matter -+ * if there are unmapped gaps or aliases (mirrors of flash devices). The MTD -+ * probes will ignore them. -+ * -+ * The start address in map_priv_1 is in virtual memory so we cannot use -+ * MEM_CSE0_START but must rely on that FLASH_UNCACHED_ADDR is the start -+ * address of cse0. -+ */ -+static struct map_info map_cse0 = { -+ .name = "cse0", -+ .size = MEM_CSE0_SIZE, -+ .bankwidth = CONFIG_ETRAX_FLASH_BUSWIDTH, -+ .read = flash_read, -+ .copy_from = flash_copy_from, -+ .write = flash_write, -+ .map_priv_1 = FLASH_UNCACHED_ADDR -+}; -+ -+/* -+ * The map for chip select e1. -+ * -+ * If there was a gap between cse0 and cse1, map_priv_1 would get the wrong -+ * address, but there isn't. -+ */ -+static struct map_info map_cse1 = { -+ .name = "cse1", -+ .size = MEM_CSE1_SIZE, -+ .bankwidth = CONFIG_ETRAX_FLASH_BUSWIDTH, -+ .read = flash_read, -+ .copy_from = flash_copy_from, -+ .write = flash_write, -+ .map_priv_1 = FLASH_UNCACHED_ADDR + MEM_CSE0_SIZE -+}; -+ -+/* If no partition-table was found, we use this default-set. */ -+#define MAX_PARTITIONS 7 -+#define NUM_DEFAULT_PARTITIONS 3 -+ -+/* -+ * Default flash size is 2MB. CONFIG_ETRAX_PTABLE_SECTOR is most likely the -+ * size of one flash block and "filesystem"-partition needs 5 blocks to be able -+ * to use JFFS. -+ */ -+static struct mtd_partition axis_default_partitions[NUM_DEFAULT_PARTITIONS] = { -+ { -+ .name = "boot firmware", -+ .size = CONFIG_ETRAX_PTABLE_SECTOR, -+ .offset = 0 -+ }, -+ { -+ .name = "kernel", -+ .size = 0x200000 - (6 * CONFIG_ETRAX_PTABLE_SECTOR), -+ .offset = CONFIG_ETRAX_PTABLE_SECTOR -+ }, -+ { -+ .name = "filesystem", -+ .size = 5 * CONFIG_ETRAX_PTABLE_SECTOR, -+ .offset = 0x200000 - (5 * CONFIG_ETRAX_PTABLE_SECTOR) -+ } -+}; -+ -+/* Initialize the ones normally used. */ -+static struct mtd_partition axis_partitions[MAX_PARTITIONS] = { -+ { -+ .name = "part0", -+ .size = CONFIG_ETRAX_PTABLE_SECTOR, -+ .offset = 0 -+ }, -+ { -+ .name = "part1", -+ .size = 0, -+ .offset = 0 -+ }, -+ { -+ .name = "part2", -+ .size = 0, -+ .offset = 0 -+ }, -+ { -+ .name = "part3", -+ .size = 0, -+ .offset = 0 -+ }, -+ { -+ .name = "part4", -+ .size = 0, -+ .offset = 0 -+ }, -+ { -+ .name = "part5", -+ .size = 0, -+ .offset = 0 -+ }, -+ { -+ .name = "part6", -+ .size = 0, -+ .offset = 0 -+ }, -+}; -+ -+#ifdef CONFIG_ETRAX_AXISFLASHMAP_MTD0WHOLE -+/* Main flash device */ -+static struct mtd_partition main_partition = { -+ .name = "main", -+ .size = 0, -+ .offset = 0 -+}; -+#endif -+ -+/* -+ * Probe a chip select for AMD-compatible (JEDEC) or CFI-compatible flash -+ * chips in that order (because the amd_flash-driver is faster). -+ */ -+static struct mtd_info *probe_cs(struct map_info *map_cs) -+{ -+ struct mtd_info *mtd_cs = NULL; -+ -+ printk(KERN_INFO -+ "%s: Probing a 0x%08lx bytes large window at 0x%08lx.\n", -+ map_cs->name, map_cs->size, map_cs->map_priv_1); -+ -+#ifdef CONFIG_MTD_CFI -+ mtd_cs = do_map_probe("cfi_probe", map_cs); -+#endif -+#ifdef CONFIG_MTD_JEDECPROBE -+ if (!mtd_cs) -+ mtd_cs = do_map_probe("jedec_probe", map_cs); -+#endif -+ -+ return mtd_cs; -+} -+ -+/* -+ * Probe each chip select individually for flash chips. If there are chips on -+ * both cse0 and cse1, the mtd_info structs will be concatenated to one struct -+ * so that MTD partitions can cross chip boundries. -+ * -+ * The only known restriction to how you can mount your chips is that each -+ * chip select must hold similar flash chips. But you need external hardware -+ * to do that anyway and you can put totally different chips on cse0 and cse1 -+ * so it isn't really much of a restriction. -+ */ -+static struct mtd_info *flash_probe(void) -+{ -+ struct mtd_info *mtd_cse0; -+ struct mtd_info *mtd_cse1; -+ struct mtd_info *mtd_cse; -+ -+ mtd_cse0 = probe_cs(&map_cse0); -+ mtd_cse1 = probe_cs(&map_cse1); -+ -+ if (!mtd_cse0 && !mtd_cse1) { -+ /* No chip found. */ -+ return NULL; -+ } -+ -+ if (mtd_cse0 && mtd_cse1) { -+ struct mtd_info *mtds[] = { mtd_cse0, mtd_cse1 }; -+ -+ /* Since the concatenation layer adds a small overhead we -+ * could try to figure out if the chips in cse0 and cse1 are -+ * identical and reprobe the whole cse0+cse1 window. But since -+ * flash chips are slow, the overhead is relatively small. -+ * So we use the MTD concatenation layer instead of further -+ * complicating the probing procedure. -+ */ -+ mtd_cse = mtd_concat_create(mtds, ARRAY_SIZE(mtds), -+ "cse0+cse1"); -+ if (!mtd_cse) { -+ printk(KERN_ERR "%s and %s: Concatenation failed!\n", -+ map_cse0.name, map_cse1.name); -+ -+ /* The best we can do now is to only use what we found -+ * at cse0. -+ */ -+ mtd_cse = mtd_cse0; -+ map_destroy(mtd_cse1); -+ } -+ } else { -+ mtd_cse = mtd_cse0? mtd_cse0 : mtd_cse1; -+ } -+ -+ return mtd_cse; -+} -+ -+/* -+ * Probe the flash chip(s) and, if it succeeds, read the partition-table -+ * and register the partitions with MTD. -+ */ -+static int __init init_axis_flash(void) -+{ -+ struct mtd_info *mymtd; -+ int err = 0; -+ int pidx = 0; -+ struct partitiontable_head *ptable_head = NULL; -+ struct partitiontable_entry *ptable; -+ int use_default_ptable = 1; /* Until proven otherwise. */ -+ const char pmsg[] = " /dev/flash%d at 0x%08x, size 0x%08x\n"; -+ -+ if (!(mymtd = flash_probe())) { -+ /* There's no reason to use this module if no flash chip can -+ * be identified. Make sure that's understood. -+ */ -+ printk(KERN_INFO "axisflashmap: Found no flash chip.\n"); -+ } else { -+ printk(KERN_INFO "%s: 0x%08x bytes of flash memory.\n", -+ mymtd->name, mymtd->size); -+ axisflash_mtd = mymtd; -+ } -+ -+ if (mymtd) { -+ mymtd->owner = THIS_MODULE; -+ ptable_head = (struct partitiontable_head *)(FLASH_CACHED_ADDR + -+ CONFIG_ETRAX_PTABLE_SECTOR + -+ PARTITION_TABLE_OFFSET); -+ } -+ pidx++; /* First partition is always set to the default. */ -+ -+ if (ptable_head && (ptable_head->magic == PARTITION_TABLE_MAGIC) -+ && (ptable_head->size < -+ (MAX_PARTITIONS * sizeof(struct partitiontable_entry) + -+ PARTITIONTABLE_END_MARKER_SIZE)) -+ && (*(unsigned long*)((void*)ptable_head + sizeof(*ptable_head) + -+ ptable_head->size - -+ PARTITIONTABLE_END_MARKER_SIZE) -+ == PARTITIONTABLE_END_MARKER)) { -+ /* Looks like a start, sane length and end of a -+ * partition table, lets check csum etc. -+ */ -+ int ptable_ok = 0; -+ struct partitiontable_entry *max_addr = -+ (struct partitiontable_entry *) -+ ((unsigned long)ptable_head + sizeof(*ptable_head) + -+ ptable_head->size); -+ unsigned long offset = CONFIG_ETRAX_PTABLE_SECTOR; -+ unsigned char *p; -+ unsigned long csum = 0; -+ -+ ptable = (struct partitiontable_entry *) -+ ((unsigned long)ptable_head + sizeof(*ptable_head)); -+ -+ /* Lets be PARANOID, and check the checksum. */ -+ p = (unsigned char*) ptable; -+ -+ while (p <= (unsigned char*)max_addr) { -+ csum += *p++; -+ csum += *p++; -+ csum += *p++; -+ csum += *p++; -+ } -+ ptable_ok = (csum == ptable_head->checksum); -+ -+ /* Read the entries and use/show the info. */ -+ printk(KERN_INFO " Found a%s partition table at 0x%p-0x%p.\n", -+ (ptable_ok ? " valid" : "n invalid"), ptable_head, -+ max_addr); -+ -+ /* We have found a working bootblock. Now read the -+ * partition table. Scan the table. It ends when -+ * there is 0xffffffff, that is, empty flash. -+ */ -+ while (ptable_ok -+ && ptable->offset != 0xffffffff -+ && ptable < max_addr -+ && pidx < MAX_PARTITIONS) { -+ -+ axis_partitions[pidx].offset = offset + ptable->offset; -+ axis_partitions[pidx].size = ptable->size; -+ -+ printk(pmsg, pidx, axis_partitions[pidx].offset, -+ axis_partitions[pidx].size); -+ pidx++; -+ ptable++; -+ } -+ use_default_ptable = !ptable_ok; -+ } -+ -+ if (romfs_in_flash) { -+ /* Add an overlapping device for the root partition (romfs). */ -+ -+ axis_partitions[pidx].name = "romfs"; -+ axis_partitions[pidx].size = romfs_length; -+ axis_partitions[pidx].offset = romfs_start - FLASH_CACHED_ADDR; -+ axis_partitions[pidx].mask_flags |= MTD_WRITEABLE; -+ -+ printk(KERN_INFO -+ " Adding readonly flash partition for romfs image:\n"); -+ printk(pmsg, pidx, axis_partitions[pidx].offset, -+ axis_partitions[pidx].size); -+ pidx++; -+ } -+ -+#ifdef CONFIG_ETRAX_AXISFLASHMAP_MTD0WHOLE -+ if (mymtd) { -+ main_partition.size = mymtd->size; -+ err = add_mtd_partitions(mymtd, &main_partition, 1); -+ if (err) -+ panic("axisflashmap: Could not initialize " -+ "partition for whole main mtd device!\n"); -+ } -+#endif -+ -+ if (mymtd) { -+ if (use_default_ptable) { -+ printk(KERN_INFO " Using default partition table.\n"); -+ err = add_mtd_partitions(mymtd, axis_default_partitions, -+ NUM_DEFAULT_PARTITIONS); -+ } else { -+ err = add_mtd_partitions(mymtd, axis_partitions, pidx); -+ } -+ -+ if (err) -+ panic("axisflashmap could not add MTD partitions!\n"); -+ } -+ -+ if (!romfs_in_flash) { -+ /* Create an RAM device for the root partition (romfs). */ -+ -+#if !defined(CONFIG_MTD_MTDRAM) || (CONFIG_MTDRAM_TOTAL_SIZE != 0) || (CONFIG_MTDRAM_ABS_POS != 0) -+ /* No use trying to boot this kernel from RAM. Panic! */ -+ printk(KERN_EMERG "axisflashmap: Cannot create an MTD RAM " -+ "device due to kernel (mis)configuration!\n"); -+ panic("This kernel cannot boot from RAM!\n"); -+#else -+ struct mtd_info *mtd_ram; -+ -+ mtd_ram = kmalloc(sizeof(struct mtd_info), GFP_KERNEL); -+ if (!mtd_ram) -+ panic("axisflashmap couldn't allocate memory for " -+ "mtd_info!\n"); -+ -+ printk(KERN_INFO " Adding RAM partition for romfs image:\n"); -+ printk(pmsg, pidx, (unsigned)romfs_start, -+ (unsigned)romfs_length); -+ -+ err = mtdram_init_device(mtd_ram, -+ (void *)romfs_start, -+ romfs_length, -+ "romfs"); -+ if (err) -+ panic("axisflashmap could not initialize MTD RAM " -+ "device!\n"); -+#endif -+ } -+ return err; -+} -+ -+/* This adds the above to the kernels init-call chain. */ -+module_init(init_axis_flash); -+ -+EXPORT_SYMBOL(axisflash_mtd); diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/ds1302.c linux-2.6.39/arch/cris/arch-v10/drivers/ds1302.c --- linux-2.6.39.orig/arch/cris/arch-v10/drivers/ds1302.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/arch-v10/drivers/ds1302.c 2011-07-28 16:16:35.863415658 +0200 ++++ linux-2.6.39/arch/cris/arch-v10/drivers/ds1302.c 2011-08-22 08:58:55.157980341 +0200 @@ -22,6 +22,7 @@ #include #include @@ -617,7 +183,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/ds1302.c linux-2.6.39/arc } diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/gpio.c linux-2.6.39/arch/cris/arch-v10/drivers/gpio.c --- linux-2.6.39.orig/arch/cris/arch-v10/drivers/gpio.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/arch-v10/drivers/gpio.c 2011-07-28 16:16:36.023425394 +0200 ++++ linux-2.6.39/arch/cris/arch-v10/drivers/gpio.c 2011-08-22 08:58:55.227980067 +0200 @@ -20,6 +20,7 @@ #include #include @@ -653,7 +219,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/drivers/gpio.c linux-2.6.39/arch/ CRIS_LED_NETWORK_SET(0); diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/lib/hw_settings.S linux-2.6.39/arch/cris/arch-v10/lib/hw_settings.S --- linux-2.6.39.orig/arch/cris/arch-v10/lib/hw_settings.S 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/arch-v10/lib/hw_settings.S 2011-07-28 16:16:36.163758404 +0200 ++++ linux-2.6.39/arch/cris/arch-v10/lib/hw_settings.S 2011-08-22 08:58:55.287980084 +0200 @@ -58,3 +58,5 @@ .dword R_PORT_PB_SET .dword PB_SET_VALUE @@ -662,7 +228,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/lib/hw_settings.S linux-2.6.39/ar + .dword 0xdeadc0de diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/mm/init.c linux-2.6.39/arch/cris/arch-v10/mm/init.c --- linux-2.6.39.orig/arch/cris/arch-v10/mm/init.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/arch-v10/mm/init.c 2011-07-28 16:16:36.313421347 +0200 ++++ linux-2.6.39/arch/cris/arch-v10/mm/init.c 2011-08-22 08:58:55.347981214 +0200 @@ -184,6 +184,9 @@ free_area_init_node(0, zones_size, PAGE_OFFSET >> PAGE_SHIFT, 0); @@ -675,7 +241,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/arch-v10/mm/init.c linux-2.6.39/arch/cris/ * is called before any driver is initialized. diff -Nur linux-2.6.39.orig/arch/cris/boot/compressed/Makefile linux-2.6.39/arch/cris/boot/compressed/Makefile --- linux-2.6.39.orig/arch/cris/boot/compressed/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/boot/compressed/Makefile 2011-07-28 16:16:36.453421314 +0200 ++++ linux-2.6.39/arch/cris/boot/compressed/Makefile 2011-08-22 08:58:55.427980567 +0200 @@ -18,7 +18,7 @@ OBJECTS-$(CONFIG_ETRAX_ARCH_V32) = $(obj)/head_v32.o OBJECTS-$(CONFIG_ETRAX_ARCH_V10) = $(obj)/head_v10.o @@ -687,7 +253,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/boot/compressed/Makefile linux-2.6.39/arch cmd_image = cat $(obj)/decompress.bin $(obj)/piggy.gz > $@ diff -Nur linux-2.6.39.orig/arch/cris/boot/Makefile linux-2.6.39/arch/cris/boot/Makefile --- linux-2.6.39.orig/arch/cris/boot/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/boot/Makefile 2011-07-28 16:16:36.573671907 +0200 ++++ linux-2.6.39/arch/cris/boot/Makefile 2011-08-22 08:58:55.507980367 +0200 @@ -5,7 +5,7 @@ objcopyflags-$(CONFIG_ETRAX_ARCH_V10) += -R .note -R .comment objcopyflags-$(CONFIG_ETRAX_ARCH_V32) += --remove-section=.bss --remove-section=.note.gnu.build-id @@ -707,7 +273,7 @@ diff -Nur linux-2.6.39.orig/arch/cris/boot/Makefile linux-2.6.39/arch/cris/boot/ @cp $< $@ diff -Nur linux-2.6.39.orig/arch/cris/Kconfig linux-2.6.39/arch/cris/Kconfig --- linux-2.6.39.orig/arch/cris/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/Kconfig 2011-07-28 16:16:36.713417234 +0200 ++++ linux-2.6.39/arch/cris/Kconfig 2011-08-22 08:58:55.587980284 +0200 @@ -168,6 +168,12 @@ help Size of DRAM (decimal in MB) typically 2, 8 or 16. @@ -751,7126 +317,103 @@ diff -Nur linux-2.6.39.orig/arch/cris/Kconfig linux-2.6.39/arch/cris/Kconfig source "drivers/usb/Kconfig" source "drivers/uwb/Kconfig" -diff -Nur linux-2.6.39.orig/arch/cris/Kconfig.orig linux-2.6.39/arch/cris/Kconfig.orig ---- linux-2.6.39.orig/arch/cris/Kconfig.orig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/cris/Kconfig.orig 2011-05-19 06:06:34.000000000 +0200 -@@ -0,0 +1,690 @@ -+config MMU -+ bool -+ default y -+ -+config ZONE_DMA -+ bool -+ default y -+ -+config RWSEM_GENERIC_SPINLOCK -+ bool -+ default y -+ -+config RWSEM_XCHGADD_ALGORITHM -+ bool -+ -+config GENERIC_CMOS_UPDATE -+ def_bool y -+ -+config ARCH_USES_GETTIMEOFFSET -+ def_bool n -+ -+config GENERIC_IOMAP -+ bool -+ default y -+ -+config ARCH_HAS_ILOG2_U32 -+ bool -+ default n -+ -+config ARCH_HAS_ILOG2_U64 -+ bool -+ default n -+ -+config GENERIC_FIND_NEXT_BIT -+ bool -+ default y -+ -+config GENERIC_HWEIGHT -+ bool -+ default y -+ -+config GENERIC_CALIBRATE_DELAY -+ bool -+ default y -+ -+config NO_IOPORT -+ def_bool y -+ -+config FORCE_MAX_ZONEORDER -+ int -+ default 6 -+ -+config CRIS -+ bool -+ default y -+ select HAVE_IDE -+ select HAVE_GENERIC_HARDIRQS -+ select GENERIC_IRQ_SHOW -+ -+config HZ -+ int -+ default 100 -+ -+source "init/Kconfig" -+ -+source "kernel/Kconfig.freezer" -+ -+menu "General setup" -+ -+source "fs/Kconfig.binfmt" -+ -+config ETRAX_CMDLINE -+ string "Kernel command line" -+ default "root=/dev/mtdblock3" -+ help -+ Pass additional commands to the kernel. -+ -+config ETRAX_WATCHDOG -+ bool "Enable ETRAX watchdog" -+ help -+ Enable the built-in watchdog timer support on ETRAX based embedded -+ network computers. -+ -+config ETRAX_WATCHDOG_NICE_DOGGY -+ bool "Disable watchdog during Oops printouts" -+ depends on ETRAX_WATCHDOG -+ help -+ By enabling this you make sure that the watchdog does not bite while -+ printing oopses. Recommended for development systems but not for -+ production releases. -+ -+config ETRAX_FAST_TIMER -+ bool "Enable ETRAX fast timer API" -+ help -+ This options enables the API to a fast timer implementation using -+ timer1 to get sub jiffie resolution timers (primarily one-shot -+ timers). -+ This is needed if CONFIG_ETRAX_SERIAL_FAST_TIMER is enabled. -+ -+config ETRAX_KMALLOCED_MODULES -+ bool "Enable module allocation with kmalloc" -+ help -+ Enable module allocation with kmalloc instead of vmalloc. -+ -+config OOM_REBOOT -+ bool "Enable reboot at out of memory" -+ -+source "kernel/Kconfig.preempt" -+ -+source mm/Kconfig -+ -+endmenu -+ -+menu "Hardware setup" -+ -+choice -+ prompt "Processor type" -+ default ETRAX100LX -+ -+config ETRAX100LX -+ bool "ETRAX-100LX-v1" -+ select ARCH_USES_GETTIMEOFFSET -+ help -+ Support version 1 of the ETRAX 100LX. +diff -Nur linux-2.6.39.orig/arch/cris/Makefile linux-2.6.39/arch/cris/Makefile +--- linux-2.6.39.orig/arch/cris/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/cris/Makefile 2011-08-22 08:58:55.837980069 +0200 +@@ -40,10 +40,10 @@ + + LD = $(CROSS_COMPILE)ld -mcrislinux + +-OBJCOPYFLAGS := -O binary -R .note -R .comment -S ++OBJCOPYFLAGS := -O binary -R .bss -R .note -R .note.gnu.build-id -R .comment -S + + KBUILD_AFLAGS += -mlinux -march=$(arch-y) $(inc) +-KBUILD_CFLAGS += -mlinux -march=$(arch-y) -pipe $(inc) ++KBUILD_CFLAGS += -mlinux -march=$(arch-y) -pipe -fno-peephole2 $(inc) + KBUILD_CPPFLAGS += $(inc) + + ifdef CONFIG_FRAME_POINTER +diff -Nur linux-2.6.39.orig/arch/cris/mm/init.c linux-2.6.39/arch/cris/mm/init.c +--- linux-2.6.39.orig/arch/cris/mm/init.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/cris/mm/init.c 2011-08-22 08:58:55.897980391 +0200 +@@ -16,6 +16,7 @@ + DEFINE_PER_CPU(struct mmu_gather, mmu_gathers); + + unsigned long empty_zero_page; ++EXPORT_SYMBOL(empty_zero_page); + + extern char _stext, _edata, _etext; /* From linkerscript */ + extern char __init_begin, __init_end; +@@ -81,3 +82,10 @@ + printk (KERN_INFO "Freeing unused kernel memory: %luk freed\n", + (unsigned long)((&__init_end - &__init_begin) >> 10)); + } + -+config ETRAX100LX_V2 -+ bool "ETRAX-100LX-v2" -+ select ARCH_USES_GETTIMEOFFSET -+ help -+ Support version 2 of the ETRAX 100LX. ++#ifdef CONFIG_BLK_DEV_INITRD ++void free_initrd_mem(unsigned long start, unsigned long end) ++{ ++ return 0; ++} ++#endif +diff -Nur linux-2.6.39.orig/drivers/net/cris/eth_v10.c linux-2.6.39/drivers/net/cris/eth_v10.c +--- linux-2.6.39.orig/drivers/net/cris/eth_v10.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/cris/eth_v10.c 2011-08-22 08:58:55.987980420 +0200 +@@ -1714,7 +1714,7 @@ + static void + e100_netpoll(struct net_device* netdev) + { +- e100rxtx_interrupt(NETWORK_DMA_TX_IRQ_NBR, netdev, NULL); ++ e100rxtx_interrupt(NETWORK_DMA_TX_IRQ_NBR, netdev); + } + #endif + +diff -Nur linux-2.6.39.orig/drivers/tty/serial/crisv10.c linux-2.6.39/drivers/tty/serial/crisv10.c +--- linux-2.6.39.orig/drivers/tty/serial/crisv10.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/tty/serial/crisv10.c 2011-08-22 08:58:56.137981508 +0200 +@@ -26,6 +26,7 @@ + #include + #include + #include ++#include + #include + #include + #include +@@ -4430,6 +4431,7 @@ + #endif + }; + ++static struct class *rs_class; + static int __init rs_init(void) + { + int i; +@@ -4564,6 +4566,24 @@ + #endif + #endif /* CONFIG_SVINTO_SIM */ + ++ rs_class = class_create(THIS_MODULE, "rs_tty"); ++#ifdef CONFIG_ETRAX_SERIAL_PORT0 ++ device_create(rs_class, NULL, ++ MKDEV(TTY_MAJOR, 64), NULL, "ttyS0"); ++#endif ++#ifdef CONFIG_ETRAX_SERIAL_PORT1 ++ device_create(rs_class, NULL, ++ MKDEV(TTY_MAJOR, 65), NULL, "ttyS1"); ++#endif ++#ifdef CONFIG_ETRAX_SERIAL_PORT2 ++ device_create(rs_class, NULL, ++ MKDEV(TTY_MAJOR, 66), NULL, "ttyS2"); ++#endif ++#ifdef CONFIG_ETRAX_SERIAL_PORT3 ++ device_create(rs_class, NULL, ++ MKDEV(TTY_MAJOR, 67), NULL, "ttyS3"); ++#endif + -+config SVINTO_SIM -+ bool "ETRAX-100LX-for-xsim-simulator" -+ select ARCH_USES_GETTIMEOFFSET -+ help -+ Support the xsim ETRAX Simulator. -+ -+config ETRAXFS -+ bool "ETRAX-FS-V32" -+ help -+ Support CRIS V32. -+ -+config CRIS_MACH_ARTPEC3 -+ bool "ARTPEC-3" -+ help -+ Support Axis ARTPEC-3. -+ -+endchoice -+ -+config ETRAX_VCS_SIM -+ bool "VCS Simulator" -+ help -+ Setup hardware to be run in the VCS simulator. -+ -+config ETRAX_ARCH_V10 -+ bool -+ default y if ETRAX100LX || ETRAX100LX_V2 -+ default n if !(ETRAX100LX || ETRAX100LX_V2) -+ -+config ETRAX_ARCH_V32 -+ bool -+ default y if (ETRAXFS || CRIS_MACH_ARTPEC3) -+ default n if !(ETRAXFS || CRIS_MACH_ARTPEC3) -+ -+config ETRAX_DRAM_SIZE -+ int "DRAM size (dec, in MB)" -+ default "8" -+ help -+ Size of DRAM (decimal in MB) typically 2, 8 or 16. -+ -+config ETRAX_VMEM_SIZE -+ int "Video memory size (dec, in MB)" -+ depends on ETRAX_ARCH_V32 && !ETRAXFS -+ default 8 if !ETRAXFS -+ help -+ Size of Video accessible memory (decimal, in MB). -+ -+config ETRAX_FLASH_BUSWIDTH -+ int "Buswidth of NOR flash in bytes" -+ default "2" -+ help -+ Width in bytes of the NOR Flash bus (1, 2 or 4). Is usually 2. -+ -+config ETRAX_NANDFLASH_BUSWIDTH -+ int "Buswidth of NAND flash in bytes" -+ default "1" -+ help -+ Width in bytes of the NAND flash (1 or 2). -+ -+config ETRAX_FLASH1_SIZE -+ int "FLASH1 size (dec, in MB. 0 = Unknown)" -+ default "0" -+ -+choice -+ prompt "Product debug-port" -+ default ETRAX_DEBUG_PORT0 -+ -+config ETRAX_DEBUG_PORT0 -+ bool "Serial-0" -+ help -+ Choose a serial port for the ETRAX debug console. Default to -+ port 0. -+ -+config ETRAX_DEBUG_PORT1 -+ bool "Serial-1" -+ help -+ Use serial port 1 for the console. -+ -+config ETRAX_DEBUG_PORT2 -+ bool "Serial-2" -+ help -+ Use serial port 2 for the console. -+ -+config ETRAX_DEBUG_PORT3 -+ bool "Serial-3" -+ help -+ Use serial port 3 for the console. -+ -+config ETRAX_DEBUG_PORT_NULL -+ bool "disabled" -+ help -+ Disable serial-port debugging. -+ -+endchoice -+ -+choice -+ prompt "Kernel GDB port" -+ depends on ETRAX_KGDB -+ default ETRAX_KGDB_PORT0 -+ help -+ Choose a serial port for kernel debugging. NOTE: This port should -+ not be enabled under Drivers for built-in interfaces (as it has its -+ own initialization code) and should not be the same as the debug port. -+ -+config ETRAX_KGDB_PORT0 -+ bool "Serial-0" -+ help -+ Use serial port 0 for kernel debugging. -+ -+config ETRAX_KGDB_PORT1 -+ bool "Serial-1" -+ help -+ Use serial port 1 for kernel debugging. -+ -+config ETRAX_KGDB_PORT2 -+ bool "Serial-2" -+ help -+ Use serial port 2 for kernel debugging. -+ -+config ETRAX_KGDB_PORT3 -+ bool "Serial-3" -+ help -+ Use serial port 3 for kernel debugging. -+ -+endchoice -+ -+source arch/cris/arch-v10/Kconfig -+source arch/cris/arch-v32/Kconfig -+ -+endmenu -+ -+source "net/Kconfig" -+ -+# bring in ETRAX built-in drivers -+menu "Drivers for built-in interfaces" -+source arch/cris/arch-v10/drivers/Kconfig -+source arch/cris/arch-v32/drivers/Kconfig -+ -+config ETRAX_AXISFLASHMAP -+ bool "Axis flash-map support" -+ select MTD -+ select MTD_CFI -+ select MTD_CFI_AMDSTD -+ select MTD_JEDECPROBE if ETRAX_ARCH_V32 -+ select MTD_CHAR -+ select MTD_BLOCK -+ select MTD_PARTITIONS -+ select MTD_COMPLEX_MAPPINGS -+ help -+ This option enables MTD mapping of flash devices. Needed to use -+ flash memories. If unsure, say Y. -+ -+config ETRAX_RTC -+ bool "Real Time Clock support" -+ depends on ETRAX_I2C -+ help -+ Enables drivers for the Real-Time Clock battery-backed chips on -+ some products. The kernel reads the time when booting, and -+ the date can be set using ioctl(fd, RTC_SET_TIME, &rt) with rt a -+ rtc_time struct (see ) on the /dev/rtc -+ device. You can check the time with cat /proc/rtc, but -+ normal time reading should be done using libc function time and -+ friends. -+ -+choice -+ prompt "RTC chip" -+ depends on ETRAX_RTC -+ default ETRAX_DS1302 -+ -+config ETRAX_DS1302 -+ depends on ETRAX_ARCH_V10 -+ bool "DS1302" -+ help -+ Enables the driver for the DS1302 Real-Time Clock battery-backed -+ chip on some products. -+ -+config ETRAX_PCF8563 -+ bool "PCF8563" -+ help -+ Enables the driver for the PCF8563 Real-Time Clock battery-backed -+ chip on some products. -+ -+endchoice -+ -+config ETRAX_SYNCHRONOUS_SERIAL -+ bool "Synchronous serial-port support" -+ help -+ Select this to enable the synchronous serial port driver. -+ -+config ETRAX_SYNCHRONOUS_SERIAL_PORT0 -+ bool "Synchronous serial port 0 enabled" -+ depends on ETRAX_SYNCHRONOUS_SERIAL -+ help -+ Enabled synchronous serial port 0. -+ -+config ETRAX_SYNCHRONOUS_SERIAL0_DMA -+ bool "Enable DMA on synchronous serial port 0." -+ depends on ETRAX_SYNCHRONOUS_SERIAL_PORT0 -+ help -+ A synchronous serial port can run in manual or DMA mode. -+ Selecting this option will make it run in DMA mode. -+ -+config ETRAX_SYNCHRONOUS_SERIAL_PORT1 -+ bool "Synchronous serial port 1 enabled" -+ depends on ETRAX_SYNCHRONOUS_SERIAL && (ETRAXFS || ETRAX_ARCH_V10) -+ help -+ Enabled synchronous serial port 1. -+ -+config ETRAX_SYNCHRONOUS_SERIAL1_DMA -+ bool "Enable DMA on synchronous serial port 1." -+ depends on ETRAX_SYNCHRONOUS_SERIAL_PORT1 -+ help -+ A synchronous serial port can run in manual or DMA mode. -+ Selecting this option will make it run in DMA mode. -+ -+choice -+ prompt "Network LED behavior" -+ depends on ETRAX_ETHERNET -+ default ETRAX_NETWORK_LED_ON_WHEN_ACTIVITY -+ -+config ETRAX_NETWORK_LED_ON_WHEN_LINK -+ bool "LED_on_when_link" -+ help -+ Selecting LED_on_when_link will light the LED when there is a -+ connection and will flash off when there is activity. -+ -+ Selecting LED_on_when_activity will light the LED only when -+ there is activity. -+ -+ This setting will also affect the behaviour of other activity LEDs -+ e.g. Bluetooth. -+ -+config ETRAX_NETWORK_LED_ON_WHEN_ACTIVITY -+ bool "LED_on_when_activity" -+ help -+ Selecting LED_on_when_link will light the LED when there is a -+ connection and will flash off when there is activity. -+ -+ Selecting LED_on_when_activity will light the LED only when -+ there is activity. -+ -+ This setting will also affect the behaviour of other activity LEDs -+ e.g. Bluetooth. -+ -+endchoice -+ -+choice -+ prompt "Ser0 DMA out channel" -+ depends on ETRAX_SERIAL_PORT0 -+ default ETRAX_SERIAL_PORT0_DMA6_OUT if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT0_NO_DMA_OUT if ETRAX_ARCH_V10 -+ -+config ETRAX_SERIAL_PORT0_NO_DMA_OUT -+ bool "Ser0 uses no DMA for output" -+ help -+ Do not use DMA for ser0 output. -+ -+config ETRAX_SERIAL_PORT0_DMA6_OUT -+ bool "Ser0 uses DMA6 for output" -+ depends on ETRAXFS -+ help -+ Enables the DMA6 output channel for ser0 (ttyS0). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT0_DMA0_OUT -+ bool "Ser0 uses DMA0 for output" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA0 output channel for ser0 (ttyS0). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser0 DMA in channel " -+ depends on ETRAX_SERIAL_PORT0 -+ default ETRAX_SERIAL_PORT0_NO_DMA_IN if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT0_DMA7_IN if ETRAX_ARCH_V10 -+ help -+ What DMA channel to use for ser0. -+ -+config ETRAX_SERIAL_PORT0_NO_DMA_IN -+ bool "Ser0 uses no DMA for input" -+ help -+ Do not use DMA for ser0 input. -+ -+config ETRAX_SERIAL_PORT0_DMA7_IN -+ bool "Ser0 uses DMA7 for input" -+ depends on ETRAXFS -+ help -+ Enables the DMA7 input channel for ser0 (ttyS0). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT0_DMA1_IN -+ bool "Ser0 uses DMA1 for input" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA1 input channel for ser0 (ttyS0). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser1 DMA in channel " -+ depends on ETRAX_SERIAL_PORT1 -+ default ETRAX_SERIAL_PORT1_NO_DMA_IN if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT1_DMA9_IN if ETRAX_ARCH_V10 -+ help -+ What DMA channel to use for ser1. -+ -+config ETRAX_SERIAL_PORT1_NO_DMA_IN -+ bool "Ser1 uses no DMA for input" -+ help -+ Do not use DMA for ser1 input. -+ -+config ETRAX_SERIAL_PORT1_DMA5_IN -+ bool "Ser1 uses DMA5 for input" -+ depends on ETRAX_ARCH_V32 -+ help -+ Enables the DMA5 input channel for ser1 (ttyS1). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want this on, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT1_DMA9_IN -+ depends on ETRAX_ARCH_V10 -+ bool "Ser1 uses DMA9 for input" -+ -+endchoice -+ -+ -+choice -+ prompt "Ser1 DMA out channel" -+ depends on ETRAX_SERIAL_PORT1 -+ default ETRAX_SERIAL_PORT1_NO_DMA_OUT if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT1_DMA8_OUT if ETRAX_ARCH_V10 -+ help -+ What DMA channel to use for ser1. -+ -+config ETRAX_SERIAL_PORT1_NO_DMA_OUT -+ bool "Ser1 uses no DMA for output" -+ help -+ Do not use DMA for ser1 output. -+ -+config ETRAX_SERIAL_PORT1_DMA8_OUT -+ depends on ETRAX_ARCH_V10 -+ bool "Ser1 uses DMA8 for output" -+ -+config ETRAX_SERIAL_PORT1_DMA4_OUT -+ depends on ETRAX_ARCH_V32 -+ bool "Ser1 uses DMA4 for output" -+ help -+ Enables the DMA4 output channel for ser1 (ttyS1). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want this on, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser2 DMA out channel" -+ depends on ETRAX_SERIAL_PORT2 -+ default ETRAX_SERIAL_PORT2_NO_DMA_OUT if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT2_DMA2_OUT if ETRAX_ARCH_V10 -+ -+config ETRAX_SERIAL_PORT2_NO_DMA_OUT -+ bool "Ser2 uses no DMA for output" -+ help -+ Do not use DMA for ser2 output. -+ -+config ETRAX_SERIAL_PORT2_DMA2_OUT -+ bool "Ser2 uses DMA2 for output" -+ depends on ETRAXFS || ETRAX_ARCH_V10 -+ help -+ Enables the DMA2 output channel for ser2 (ttyS2). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT2_DMA6_OUT -+ bool "Ser2 uses DMA6 for output" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA6 output channel for ser2 (ttyS2). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser2 DMA in channel" -+ depends on ETRAX_SERIAL_PORT2 -+ default ETRAX_SERIAL_PORT2_NO_DMA_IN if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT2_DMA3_IN if ETRAX_ARCH_V10 -+ help -+ What DMA channel to use for ser2. -+ -+config ETRAX_SERIAL_PORT2_NO_DMA_IN -+ bool "Ser2 uses no DMA for input" -+ help -+ Do not use DMA for ser2 input. -+ -+config ETRAX_SERIAL_PORT2_DMA3_IN -+ bool "Ser2 uses DMA3 for input" -+ depends on ETRAXFS || ETRAX_ARCH_V10 -+ help -+ Enables the DMA3 input channel for ser2 (ttyS2). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT2_DMA7_IN -+ bool "Ser2 uses DMA7 for input" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA7 input channel for ser2 (ttyS2). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser3 DMA in channel" -+ depends on ETRAX_SERIAL_PORT3 -+ default ETRAX_SERIAL_PORT3_NO_DMA_IN if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT3_DMA5_IN if ETRAX_ARCH_V10 -+ help -+ What DMA channel to use for ser3. -+ -+config ETRAX_SERIAL_PORT3_NO_DMA_IN -+ bool "Ser3 uses no DMA for input" -+ help -+ Do not use DMA for ser3 input. -+ -+config ETRAX_SERIAL_PORT3_DMA5_IN -+ depends on ETRAX_ARCH_V10 -+ bool "DMA 5" -+ -+config ETRAX_SERIAL_PORT3_DMA9_IN -+ bool "Ser3 uses DMA9 for input" -+ depends on ETRAXFS -+ help -+ Enables the DMA9 input channel for ser3 (ttyS3). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT3_DMA3_IN -+ bool "Ser3 uses DMA3 for input" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA3 input channel for ser3 (ttyS3). -+ If you do not enable DMA, an interrupt for each character will be -+ used when receiving data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+choice -+ prompt "Ser3 DMA out channel" -+ depends on ETRAX_SERIAL_PORT3 -+ default ETRAX_SERIAL_PORT3_NO_DMA_OUT if ETRAX_ARCH_V32 -+ default ETRAX_SERIAL_PORT3_DMA4_OUT if ETRAX_ARCH_V10 -+ -+config ETRAX_SERIAL_PORT3_NO_DMA_OUT -+ bool "Ser3 uses no DMA for output" -+ help -+ Do not use DMA for ser3 output. -+ -+config ETRAX_SERIAL_PORT3_DMA4_OUT -+ depends on ETRAX_ARCH_V10 -+ bool "DMA 4" -+ -+config ETRAX_SERIAL_PORT3_DMA8_OUT -+ bool "Ser3 uses DMA8 for output" -+ depends on ETRAXFS -+ help -+ Enables the DMA8 output channel for ser3 (ttyS3). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+config ETRAX_SERIAL_PORT3_DMA2_OUT -+ bool "Ser3 uses DMA2 for output" -+ depends on CRIS_MACH_ARTPEC3 -+ help -+ Enables the DMA2 output channel for ser3 (ttyS3). -+ If you do not enable DMA, an interrupt for each character will be -+ used when transmitting data. -+ Normally you want to use DMA, unless you use the DMA channel for -+ something else. -+ -+endchoice -+ -+endmenu -+ -+source "drivers/base/Kconfig" -+ -+# standard linux drivers -+source "drivers/mtd/Kconfig" -+ -+source "drivers/parport/Kconfig" -+ -+source "drivers/pnp/Kconfig" -+ -+source "drivers/block/Kconfig" -+ -+source "drivers/ide/Kconfig" -+ -+source "drivers/net/Kconfig" -+ -+source "drivers/i2c/Kconfig" -+ -+source "drivers/rtc/Kconfig" -+ -+# -+# input before char - char/joystick depends on it. As does USB. -+# -+source "drivers/input/Kconfig" -+ -+source "drivers/char/Kconfig" -+ -+source "fs/Kconfig" -+ -+source "drivers/usb/Kconfig" -+ -+source "drivers/uwb/Kconfig" -+ -+source "drivers/staging/Kconfig" -+ -+source "arch/cris/Kconfig.debug" -+ -+source "security/Kconfig" -+ -+source "crypto/Kconfig" -+ -+source "lib/Kconfig" -diff -Nur linux-2.6.39.orig/arch/cris/Makefile linux-2.6.39/arch/cris/Makefile ---- linux-2.6.39.orig/arch/cris/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/Makefile 2011-07-28 16:16:36.883415879 +0200 -@@ -40,10 +40,10 @@ - - LD = $(CROSS_COMPILE)ld -mcrislinux - --OBJCOPYFLAGS := -O binary -R .note -R .comment -S -+OBJCOPYFLAGS := -O binary -R .bss -R .note -R .note.gnu.build-id -R .comment -S - - KBUILD_AFLAGS += -mlinux -march=$(arch-y) $(inc) --KBUILD_CFLAGS += -mlinux -march=$(arch-y) -pipe $(inc) -+KBUILD_CFLAGS += -mlinux -march=$(arch-y) -pipe -fno-peephole2 $(inc) - KBUILD_CPPFLAGS += $(inc) - - ifdef CONFIG_FRAME_POINTER -diff -Nur linux-2.6.39.orig/arch/cris/mm/init.c linux-2.6.39/arch/cris/mm/init.c ---- linux-2.6.39.orig/arch/cris/mm/init.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/cris/mm/init.c 2011-07-28 16:16:37.013424379 +0200 -@@ -16,6 +16,7 @@ - DEFINE_PER_CPU(struct mmu_gather, mmu_gathers); - - unsigned long empty_zero_page; -+EXPORT_SYMBOL(empty_zero_page); - - extern char _stext, _edata, _etext; /* From linkerscript */ - extern char __init_begin, __init_end; -@@ -81,3 +82,10 @@ - printk (KERN_INFO "Freeing unused kernel memory: %luk freed\n", - (unsigned long)((&__init_end - &__init_begin) >> 10)); - } -+ -+#ifdef CONFIG_BLK_DEV_INITRD -+void free_initrd_mem(unsigned long start, unsigned long end) -+{ -+ return 0; -+} -+#endif -diff -Nur linux-2.6.39.orig/drivers/net/cris/eth_v10.c linux-2.6.39/drivers/net/cris/eth_v10.c ---- linux-2.6.39.orig/drivers/net/cris/eth_v10.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/cris/eth_v10.c 2011-07-28 16:16:37.184155914 +0200 -@@ -1714,7 +1714,7 @@ - static void - e100_netpoll(struct net_device* netdev) - { -- e100rxtx_interrupt(NETWORK_DMA_TX_IRQ_NBR, netdev, NULL); -+ e100rxtx_interrupt(NETWORK_DMA_TX_IRQ_NBR, netdev); + return 0; } - #endif -diff -Nur linux-2.6.39.orig/drivers/net/cris/eth_v10.c.orig linux-2.6.39/drivers/net/cris/eth_v10.c.orig ---- linux-2.6.39.orig/drivers/net/cris/eth_v10.c.orig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/cris/eth_v10.c.orig 2011-05-19 06:06:34.000000000 +0200 -@@ -0,0 +1,1749 @@ -+/* -+ * e100net.c: A network driver for the ETRAX 100LX network controller. -+ * -+ * Copyright (c) 1998-2002 Axis Communications AB. -+ * -+ * The outline of this driver comes from skeleton.c. -+ * -+ */ -+ -+ -+#include -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include /* DMA and register descriptions */ -+#include /* CRIS_LED_* I/O functions */ -+#include -+#include -+#include -+#include -+#include -+#include -+ -+//#define ETHDEBUG -+#define D(x) -+ -+/* -+ * The name of the card. Is used for messages and in the requests for -+ * io regions, irqs and dma channels -+ */ -+ -+static const char* cardname = "ETRAX 100LX built-in ethernet controller"; -+ -+/* A default ethernet address. Highlevel SW will set the real one later */ -+ -+static struct sockaddr default_mac = { -+ 0, -+ { 0x00, 0x40, 0x8C, 0xCD, 0x00, 0x00 } -+}; -+ -+/* Information that need to be kept for each board. */ -+struct net_local { -+ struct mii_if_info mii_if; -+ -+ /* Tx control lock. This protects the transmit buffer ring -+ * state along with the "tx full" state of the driver. This -+ * means all netif_queue flow control actions are protected -+ * by this lock as well. -+ */ -+ spinlock_t lock; -+ -+ spinlock_t led_lock; /* Protect LED state */ -+ spinlock_t transceiver_lock; /* Protect transceiver state. */ -+}; -+ -+typedef struct etrax_eth_descr -+{ -+ etrax_dma_descr descr; -+ struct sk_buff* skb; -+} etrax_eth_descr; -+ -+/* Some transceivers requires special handling */ -+struct transceiver_ops -+{ -+ unsigned int oui; -+ void (*check_speed)(struct net_device* dev); -+ void (*check_duplex)(struct net_device* dev); -+}; -+ -+/* Duplex settings */ -+enum duplex -+{ -+ half, -+ full, -+ autoneg -+}; -+ -+/* Dma descriptors etc. */ -+ -+#define MAX_MEDIA_DATA_SIZE 1522 -+ -+#define MIN_PACKET_LEN 46 -+#define ETHER_HEAD_LEN 14 -+ -+/* -+** MDIO constants. -+*/ -+#define MDIO_START 0x1 -+#define MDIO_READ 0x2 -+#define MDIO_WRITE 0x1 -+#define MDIO_PREAMBLE 0xfffffffful -+ -+/* Broadcom specific */ -+#define MDIO_AUX_CTRL_STATUS_REG 0x18 -+#define MDIO_BC_FULL_DUPLEX_IND 0x1 -+#define MDIO_BC_SPEED 0x2 -+ -+/* TDK specific */ -+#define MDIO_TDK_DIAGNOSTIC_REG 18 -+#define MDIO_TDK_DIAGNOSTIC_RATE 0x400 -+#define MDIO_TDK_DIAGNOSTIC_DPLX 0x800 -+ -+/*Intel LXT972A specific*/ -+#define MDIO_INT_STATUS_REG_2 0x0011 -+#define MDIO_INT_FULL_DUPLEX_IND (1 << 9) -+#define MDIO_INT_SPEED (1 << 14) -+ -+/* Network flash constants */ -+#define NET_FLASH_TIME (HZ/50) /* 20 ms */ -+#define NET_FLASH_PAUSE (HZ/100) /* 10 ms */ -+#define NET_LINK_UP_CHECK_INTERVAL (2*HZ) /* 2 s */ -+#define NET_DUPLEX_CHECK_INTERVAL (2*HZ) /* 2 s */ -+ -+#define NO_NETWORK_ACTIVITY 0 -+#define NETWORK_ACTIVITY 1 -+ -+#define NBR_OF_RX_DESC 32 -+#define NBR_OF_TX_DESC 16 -+ -+/* Large packets are sent directly to upper layers while small packets are */ -+/* copied (to reduce memory waste). The following constant decides the breakpoint */ -+#define RX_COPYBREAK 256 -+ -+/* Due to a chip bug we need to flush the cache when descriptors are returned */ -+/* to the DMA. To decrease performance impact we return descriptors in chunks. */ -+/* The following constant determines the number of descriptors to return. */ -+#define RX_QUEUE_THRESHOLD NBR_OF_RX_DESC/2 -+ -+#define GET_BIT(bit,val) (((val) >> (bit)) & 0x01) -+ -+/* Define some macros to access ETRAX 100 registers */ -+#define SETF(var, reg, field, val) var = (var & ~IO_MASK_(reg##_, field##_)) | \ -+ IO_FIELD_(reg##_, field##_, val) -+#define SETS(var, reg, field, val) var = (var & ~IO_MASK_(reg##_, field##_)) | \ -+ IO_STATE_(reg##_, field##_, _##val) -+ -+static etrax_eth_descr *myNextRxDesc; /* Points to the next descriptor to -+ to be processed */ -+static etrax_eth_descr *myLastRxDesc; /* The last processed descriptor */ -+ -+static etrax_eth_descr RxDescList[NBR_OF_RX_DESC] __attribute__ ((aligned(32))); -+ -+static etrax_eth_descr* myFirstTxDesc; /* First packet not yet sent */ -+static etrax_eth_descr* myLastTxDesc; /* End of send queue */ -+static etrax_eth_descr* myNextTxDesc; /* Next descriptor to use */ -+static etrax_eth_descr TxDescList[NBR_OF_TX_DESC] __attribute__ ((aligned(32))); -+ -+static unsigned int network_rec_config_shadow = 0; -+ -+static unsigned int network_tr_ctrl_shadow = 0; -+ -+/* Network speed indication. */ -+static DEFINE_TIMER(speed_timer, NULL, 0, 0); -+static DEFINE_TIMER(clear_led_timer, NULL, 0, 0); -+static int current_speed; /* Speed read from transceiver */ -+static int current_speed_selection; /* Speed selected by user */ -+static unsigned long led_next_time; -+static int led_active; -+static int rx_queue_len; -+ -+/* Duplex */ -+static DEFINE_TIMER(duplex_timer, NULL, 0, 0); -+static int full_duplex; -+static enum duplex current_duplex; -+ -+/* Index to functions, as function prototypes. */ -+ -+static int etrax_ethernet_init(void); -+ -+static int e100_open(struct net_device *dev); -+static int e100_set_mac_address(struct net_device *dev, void *addr); -+static int e100_send_packet(struct sk_buff *skb, struct net_device *dev); -+static irqreturn_t e100rxtx_interrupt(int irq, void *dev_id); -+static irqreturn_t e100nw_interrupt(int irq, void *dev_id); -+static void e100_rx(struct net_device *dev); -+static int e100_close(struct net_device *dev); -+static int e100_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd); -+static int e100_set_config(struct net_device* dev, struct ifmap* map); -+static void e100_tx_timeout(struct net_device *dev); -+static struct net_device_stats *e100_get_stats(struct net_device *dev); -+static void set_multicast_list(struct net_device *dev); -+static void e100_hardware_send_packet(struct net_local* np, char *buf, int length); -+static void update_rx_stats(struct net_device_stats *); -+static void update_tx_stats(struct net_device_stats *); -+static int e100_probe_transceiver(struct net_device* dev); -+ -+static void e100_check_speed(unsigned long priv); -+static void e100_set_speed(struct net_device* dev, unsigned long speed); -+static void e100_check_duplex(unsigned long priv); -+static void e100_set_duplex(struct net_device* dev, enum duplex); -+static void e100_negotiate(struct net_device* dev); -+ -+static int e100_get_mdio_reg(struct net_device *dev, int phy_id, int location); -+static void e100_set_mdio_reg(struct net_device *dev, int phy_id, int location, int value); -+ -+static void e100_send_mdio_cmd(unsigned short cmd, int write_cmd); -+static void e100_send_mdio_bit(unsigned char bit); -+static unsigned char e100_receive_mdio_bit(void); -+static void e100_reset_transceiver(struct net_device* net); -+ -+static void e100_clear_network_leds(unsigned long dummy); -+static void e100_set_network_leds(int active); -+ -+static const struct ethtool_ops e100_ethtool_ops; -+#if defined(CONFIG_ETRAX_NO_PHY) -+static void dummy_check_speed(struct net_device* dev); -+static void dummy_check_duplex(struct net_device* dev); -+#else -+static void broadcom_check_speed(struct net_device* dev); -+static void broadcom_check_duplex(struct net_device* dev); -+static void tdk_check_speed(struct net_device* dev); -+static void tdk_check_duplex(struct net_device* dev); -+static void intel_check_speed(struct net_device* dev); -+static void intel_check_duplex(struct net_device* dev); -+static void generic_check_speed(struct net_device* dev); -+static void generic_check_duplex(struct net_device* dev); -+#endif -+#ifdef CONFIG_NET_POLL_CONTROLLER -+static void e100_netpoll(struct net_device* dev); -+#endif -+ -+static int autoneg_normal = 1; -+ -+struct transceiver_ops transceivers[] = -+{ -+#if defined(CONFIG_ETRAX_NO_PHY) -+ {0x0000, dummy_check_speed, dummy_check_duplex} /* Dummy */ -+#else -+ {0x1018, broadcom_check_speed, broadcom_check_duplex}, /* Broadcom */ -+ {0xC039, tdk_check_speed, tdk_check_duplex}, /* TDK 2120 */ -+ {0x039C, tdk_check_speed, tdk_check_duplex}, /* TDK 2120C */ -+ {0x04de, intel_check_speed, intel_check_duplex}, /* Intel LXT972A*/ -+ {0x0000, generic_check_speed, generic_check_duplex} /* Generic, must be last */ -+#endif -+}; -+ -+struct transceiver_ops* transceiver = &transceivers[0]; -+ -+static const struct net_device_ops e100_netdev_ops = { -+ .ndo_open = e100_open, -+ .ndo_stop = e100_close, -+ .ndo_start_xmit = e100_send_packet, -+ .ndo_tx_timeout = e100_tx_timeout, -+ .ndo_get_stats = e100_get_stats, -+ .ndo_set_multicast_list = set_multicast_list, -+ .ndo_do_ioctl = e100_ioctl, -+ .ndo_set_mac_address = e100_set_mac_address, -+ .ndo_validate_addr = eth_validate_addr, -+ .ndo_change_mtu = eth_change_mtu, -+ .ndo_set_config = e100_set_config, -+#ifdef CONFIG_NET_POLL_CONTROLLER -+ .ndo_poll_controller = e100_netpoll, -+#endif -+}; -+ -+#define tx_done(dev) (*R_DMA_CH0_CMD == 0) -+ -+/* -+ * Check for a network adaptor of this type, and return '0' if one exists. -+ * If dev->base_addr == 0, probe all likely locations. -+ * If dev->base_addr == 1, always return failure. -+ * If dev->base_addr == 2, allocate space for the device and return success -+ * (detachable devices only). -+ */ -+ -+static int __init -+etrax_ethernet_init(void) -+{ -+ struct net_device *dev; -+ struct net_local* np; -+ int i, err; -+ -+ printk(KERN_INFO -+ "ETRAX 100LX 10/100MBit ethernet v2.0 (c) 1998-2007 Axis Communications AB\n"); -+ -+ if (cris_request_io_interface(if_eth, cardname)) { -+ printk(KERN_CRIT "etrax_ethernet_init failed to get IO interface\n"); -+ return -EBUSY; -+ } -+ -+ dev = alloc_etherdev(sizeof(struct net_local)); -+ if (!dev) -+ return -ENOMEM; -+ -+ np = netdev_priv(dev); -+ -+ /* we do our own locking */ -+ dev->features |= NETIF_F_LLTX; -+ -+ dev->base_addr = (unsigned int)R_NETWORK_SA_0; /* just to have something to show */ -+ -+ /* now setup our etrax specific stuff */ -+ -+ dev->irq = NETWORK_DMA_RX_IRQ_NBR; /* we really use DMATX as well... */ -+ dev->dma = NETWORK_RX_DMA_NBR; -+ -+ /* fill in our handlers so the network layer can talk to us in the future */ -+ -+ dev->ethtool_ops = &e100_ethtool_ops; -+ dev->netdev_ops = &e100_netdev_ops; -+ -+ spin_lock_init(&np->lock); -+ spin_lock_init(&np->led_lock); -+ spin_lock_init(&np->transceiver_lock); -+ -+ /* Initialise the list of Etrax DMA-descriptors */ -+ -+ /* Initialise receive descriptors */ -+ -+ for (i = 0; i < NBR_OF_RX_DESC; i++) { -+ /* Allocate two extra cachelines to make sure that buffer used -+ * by DMA does not share cacheline with any other data (to -+ * avoid cache bug) -+ */ -+ RxDescList[i].skb = dev_alloc_skb(MAX_MEDIA_DATA_SIZE + 2 * L1_CACHE_BYTES); -+ if (!RxDescList[i].skb) -+ return -ENOMEM; -+ RxDescList[i].descr.ctrl = 0; -+ RxDescList[i].descr.sw_len = MAX_MEDIA_DATA_SIZE; -+ RxDescList[i].descr.next = virt_to_phys(&RxDescList[i + 1]); -+ RxDescList[i].descr.buf = L1_CACHE_ALIGN(virt_to_phys(RxDescList[i].skb->data)); -+ RxDescList[i].descr.status = 0; -+ RxDescList[i].descr.hw_len = 0; -+ prepare_rx_descriptor(&RxDescList[i].descr); -+ } -+ -+ RxDescList[NBR_OF_RX_DESC - 1].descr.ctrl = d_eol; -+ RxDescList[NBR_OF_RX_DESC - 1].descr.next = virt_to_phys(&RxDescList[0]); -+ rx_queue_len = 0; -+ -+ /* Initialize transmit descriptors */ -+ for (i = 0; i < NBR_OF_TX_DESC; i++) { -+ TxDescList[i].descr.ctrl = 0; -+ TxDescList[i].descr.sw_len = 0; -+ TxDescList[i].descr.next = virt_to_phys(&TxDescList[i + 1].descr); -+ TxDescList[i].descr.buf = 0; -+ TxDescList[i].descr.status = 0; -+ TxDescList[i].descr.hw_len = 0; -+ TxDescList[i].skb = 0; -+ } -+ -+ TxDescList[NBR_OF_TX_DESC - 1].descr.ctrl = d_eol; -+ TxDescList[NBR_OF_TX_DESC - 1].descr.next = virt_to_phys(&TxDescList[0].descr); -+ -+ /* Initialise initial pointers */ -+ -+ myNextRxDesc = &RxDescList[0]; -+ myLastRxDesc = &RxDescList[NBR_OF_RX_DESC - 1]; -+ myFirstTxDesc = &TxDescList[0]; -+ myNextTxDesc = &TxDescList[0]; -+ myLastTxDesc = &TxDescList[NBR_OF_TX_DESC - 1]; -+ -+ /* Register device */ -+ err = register_netdev(dev); -+ if (err) { -+ free_netdev(dev); -+ return err; -+ } -+ -+ /* set the default MAC address */ -+ -+ e100_set_mac_address(dev, &default_mac); -+ -+ /* Initialize speed indicator stuff. */ -+ -+ current_speed = 10; -+ current_speed_selection = 0; /* Auto */ -+ speed_timer.expires = jiffies + NET_LINK_UP_CHECK_INTERVAL; -+ speed_timer.data = (unsigned long)dev; -+ speed_timer.function = e100_check_speed; -+ -+ clear_led_timer.function = e100_clear_network_leds; -+ clear_led_timer.data = (unsigned long)dev; -+ -+ full_duplex = 0; -+ current_duplex = autoneg; -+ duplex_timer.expires = jiffies + NET_DUPLEX_CHECK_INTERVAL; -+ duplex_timer.data = (unsigned long)dev; -+ duplex_timer.function = e100_check_duplex; -+ -+ /* Initialize mii interface */ -+ np->mii_if.phy_id_mask = 0x1f; -+ np->mii_if.reg_num_mask = 0x1f; -+ np->mii_if.dev = dev; -+ np->mii_if.mdio_read = e100_get_mdio_reg; -+ np->mii_if.mdio_write = e100_set_mdio_reg; -+ -+ /* Initialize group address registers to make sure that no */ -+ /* unwanted addresses are matched */ -+ *R_NETWORK_GA_0 = 0x00000000; -+ *R_NETWORK_GA_1 = 0x00000000; -+ -+ /* Initialize next time the led can flash */ -+ led_next_time = jiffies; -+ return 0; -+} -+ -+/* set MAC address of the interface. called from the core after a -+ * SIOCSIFADDR ioctl, and from the bootup above. -+ */ -+ -+static int -+e100_set_mac_address(struct net_device *dev, void *p) -+{ -+ struct net_local *np = netdev_priv(dev); -+ struct sockaddr *addr = p; -+ -+ spin_lock(&np->lock); /* preemption protection */ -+ -+ /* remember it */ -+ -+ memcpy(dev->dev_addr, addr->sa_data, dev->addr_len); -+ -+ /* Write it to the hardware. -+ * Note the way the address is wrapped: -+ * *R_NETWORK_SA_0 = a0_0 | (a0_1 << 8) | (a0_2 << 16) | (a0_3 << 24); -+ * *R_NETWORK_SA_1 = a0_4 | (a0_5 << 8); -+ */ -+ -+ *R_NETWORK_SA_0 = dev->dev_addr[0] | (dev->dev_addr[1] << 8) | -+ (dev->dev_addr[2] << 16) | (dev->dev_addr[3] << 24); -+ *R_NETWORK_SA_1 = dev->dev_addr[4] | (dev->dev_addr[5] << 8); -+ *R_NETWORK_SA_2 = 0; -+ -+ /* show it in the log as well */ -+ -+ printk(KERN_INFO "%s: changed MAC to %pM\n", dev->name, dev->dev_addr); -+ -+ spin_unlock(&np->lock); -+ -+ return 0; -+} -+ -+/* -+ * Open/initialize the board. This is called (in the current kernel) -+ * sometime after booting when the 'ifconfig' program is run. -+ * -+ * This routine should set everything up anew at each open, even -+ * registers that "should" only need to be set once at boot, so that -+ * there is non-reboot way to recover if something goes wrong. -+ */ -+ -+static int -+e100_open(struct net_device *dev) -+{ -+ unsigned long flags; -+ -+ /* enable the MDIO output pin */ -+ -+ *R_NETWORK_MGM_CTRL = IO_STATE(R_NETWORK_MGM_CTRL, mdoe, enable); -+ -+ *R_IRQ_MASK0_CLR = -+ IO_STATE(R_IRQ_MASK0_CLR, overrun, clr) | -+ IO_STATE(R_IRQ_MASK0_CLR, underrun, clr) | -+ IO_STATE(R_IRQ_MASK0_CLR, excessive_col, clr); -+ -+ /* clear dma0 and 1 eop and descr irq masks */ -+ *R_IRQ_MASK2_CLR = -+ IO_STATE(R_IRQ_MASK2_CLR, dma0_descr, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma0_eop, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma1_descr, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma1_eop, clr); -+ -+ /* Reset and wait for the DMA channels */ -+ -+ RESET_DMA(NETWORK_TX_DMA_NBR); -+ RESET_DMA(NETWORK_RX_DMA_NBR); -+ WAIT_DMA(NETWORK_TX_DMA_NBR); -+ WAIT_DMA(NETWORK_RX_DMA_NBR); -+ -+ /* Initialise the etrax network controller */ -+ -+ /* allocate the irq corresponding to the receiving DMA */ -+ -+ if (request_irq(NETWORK_DMA_RX_IRQ_NBR, e100rxtx_interrupt, -+ IRQF_SAMPLE_RANDOM, cardname, (void *)dev)) { -+ goto grace_exit0; -+ } -+ -+ /* allocate the irq corresponding to the transmitting DMA */ -+ -+ if (request_irq(NETWORK_DMA_TX_IRQ_NBR, e100rxtx_interrupt, 0, -+ cardname, (void *)dev)) { -+ goto grace_exit1; -+ } -+ -+ /* allocate the irq corresponding to the network errors etc */ -+ -+ if (request_irq(NETWORK_STATUS_IRQ_NBR, e100nw_interrupt, 0, -+ cardname, (void *)dev)) { -+ goto grace_exit2; -+ } -+ -+ /* -+ * Always allocate the DMA channels after the IRQ, -+ * and clean up on failure. -+ */ -+ -+ if (cris_request_dma(NETWORK_TX_DMA_NBR, -+ cardname, -+ DMA_VERBOSE_ON_ERROR, -+ dma_eth)) { -+ goto grace_exit3; -+ } -+ -+ if (cris_request_dma(NETWORK_RX_DMA_NBR, -+ cardname, -+ DMA_VERBOSE_ON_ERROR, -+ dma_eth)) { -+ goto grace_exit4; -+ } -+ -+ /* give the HW an idea of what MAC address we want */ -+ -+ *R_NETWORK_SA_0 = dev->dev_addr[0] | (dev->dev_addr[1] << 8) | -+ (dev->dev_addr[2] << 16) | (dev->dev_addr[3] << 24); -+ *R_NETWORK_SA_1 = dev->dev_addr[4] | (dev->dev_addr[5] << 8); -+ *R_NETWORK_SA_2 = 0; -+ -+#if 0 -+ /* use promiscuous mode for testing */ -+ *R_NETWORK_GA_0 = 0xffffffff; -+ *R_NETWORK_GA_1 = 0xffffffff; -+ -+ *R_NETWORK_REC_CONFIG = 0xd; /* broadcast rec, individ. rec, ma0 enabled */ -+#else -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, max_size, size1522); -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, broadcast, receive); -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, ma0, enable); -+ SETF(network_rec_config_shadow, R_NETWORK_REC_CONFIG, duplex, full_duplex); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+#endif -+ -+ *R_NETWORK_GEN_CONFIG = -+ IO_STATE(R_NETWORK_GEN_CONFIG, phy, mii_clk) | -+ IO_STATE(R_NETWORK_GEN_CONFIG, enable, on); -+ -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, clr_error, clr); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, delay, none); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, cancel, dont); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, cd, enable); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, retry, enable); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, pad, enable); -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, crc, enable); -+ *R_NETWORK_TR_CTRL = network_tr_ctrl_shadow; -+ -+ local_irq_save(flags); -+ -+ /* enable the irq's for ethernet DMA */ -+ -+ *R_IRQ_MASK2_SET = -+ IO_STATE(R_IRQ_MASK2_SET, dma0_eop, set) | -+ IO_STATE(R_IRQ_MASK2_SET, dma1_eop, set); -+ -+ *R_IRQ_MASK0_SET = -+ IO_STATE(R_IRQ_MASK0_SET, overrun, set) | -+ IO_STATE(R_IRQ_MASK0_SET, underrun, set) | -+ IO_STATE(R_IRQ_MASK0_SET, excessive_col, set); -+ -+ /* make sure the irqs are cleared */ -+ -+ *R_DMA_CH0_CLR_INTR = IO_STATE(R_DMA_CH0_CLR_INTR, clr_eop, do); -+ *R_DMA_CH1_CLR_INTR = IO_STATE(R_DMA_CH1_CLR_INTR, clr_eop, do); -+ -+ /* make sure the rec and transmit error counters are cleared */ -+ -+ (void)*R_REC_COUNTERS; /* dummy read */ -+ (void)*R_TR_COUNTERS; /* dummy read */ -+ -+ /* start the receiving DMA channel so we can receive packets from now on */ -+ -+ *R_DMA_CH1_FIRST = virt_to_phys(myNextRxDesc); -+ *R_DMA_CH1_CMD = IO_STATE(R_DMA_CH1_CMD, cmd, start); -+ -+ /* Set up transmit DMA channel so it can be restarted later */ -+ -+ *R_DMA_CH0_FIRST = 0; -+ *R_DMA_CH0_DESCR = virt_to_phys(myLastTxDesc); -+ netif_start_queue(dev); -+ -+ local_irq_restore(flags); -+ -+ /* Probe for transceiver */ -+ if (e100_probe_transceiver(dev)) -+ goto grace_exit5; -+ -+ /* Start duplex/speed timers */ -+ add_timer(&speed_timer); -+ add_timer(&duplex_timer); -+ -+ /* We are now ready to accept transmit requeusts from -+ * the queueing layer of the networking. -+ */ -+ netif_carrier_on(dev); -+ -+ return 0; -+ -+grace_exit5: -+ cris_free_dma(NETWORK_RX_DMA_NBR, cardname); -+grace_exit4: -+ cris_free_dma(NETWORK_TX_DMA_NBR, cardname); -+grace_exit3: -+ free_irq(NETWORK_STATUS_IRQ_NBR, (void *)dev); -+grace_exit2: -+ free_irq(NETWORK_DMA_TX_IRQ_NBR, (void *)dev); -+grace_exit1: -+ free_irq(NETWORK_DMA_RX_IRQ_NBR, (void *)dev); -+grace_exit0: -+ return -EAGAIN; -+} -+ -+#if defined(CONFIG_ETRAX_NO_PHY) -+static void -+dummy_check_speed(struct net_device* dev) -+{ -+ current_speed = 100; -+} -+#else -+static void -+generic_check_speed(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_ADVERTISE); -+ if ((data & ADVERTISE_100FULL) || -+ (data & ADVERTISE_100HALF)) -+ current_speed = 100; -+ else -+ current_speed = 10; -+} -+ -+static void -+tdk_check_speed(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_TDK_DIAGNOSTIC_REG); -+ current_speed = (data & MDIO_TDK_DIAGNOSTIC_RATE ? 100 : 10); -+} -+ -+static void -+broadcom_check_speed(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_AUX_CTRL_STATUS_REG); -+ current_speed = (data & MDIO_BC_SPEED ? 100 : 10); -+} -+ -+static void -+intel_check_speed(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_INT_STATUS_REG_2); -+ current_speed = (data & MDIO_INT_SPEED ? 100 : 10); -+} -+#endif -+static void -+e100_check_speed(unsigned long priv) -+{ -+ struct net_device* dev = (struct net_device*)priv; -+ struct net_local *np = netdev_priv(dev); -+ static int led_initiated = 0; -+ unsigned long data; -+ int old_speed = current_speed; -+ -+ spin_lock(&np->transceiver_lock); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_BMSR); -+ if (!(data & BMSR_LSTATUS)) { -+ current_speed = 0; -+ } else { -+ transceiver->check_speed(dev); -+ } -+ -+ spin_lock(&np->led_lock); -+ if ((old_speed != current_speed) || !led_initiated) { -+ led_initiated = 1; -+ e100_set_network_leds(NO_NETWORK_ACTIVITY); -+ if (current_speed) -+ netif_carrier_on(dev); -+ else -+ netif_carrier_off(dev); -+ } -+ spin_unlock(&np->led_lock); -+ -+ /* Reinitialize the timer. */ -+ speed_timer.expires = jiffies + NET_LINK_UP_CHECK_INTERVAL; -+ add_timer(&speed_timer); -+ -+ spin_unlock(&np->transceiver_lock); -+} -+ -+static void -+e100_negotiate(struct net_device* dev) -+{ -+ struct net_local *np = netdev_priv(dev); -+ unsigned short data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MII_ADVERTISE); -+ -+ /* Discard old speed and duplex settings */ -+ data &= ~(ADVERTISE_100HALF | ADVERTISE_100FULL | -+ ADVERTISE_10HALF | ADVERTISE_10FULL); -+ -+ switch (current_speed_selection) { -+ case 10: -+ if (current_duplex == full) -+ data |= ADVERTISE_10FULL; -+ else if (current_duplex == half) -+ data |= ADVERTISE_10HALF; -+ else -+ data |= ADVERTISE_10HALF | ADVERTISE_10FULL; -+ break; -+ -+ case 100: -+ if (current_duplex == full) -+ data |= ADVERTISE_100FULL; -+ else if (current_duplex == half) -+ data |= ADVERTISE_100HALF; -+ else -+ data |= ADVERTISE_100HALF | ADVERTISE_100FULL; -+ break; -+ -+ case 0: /* Auto */ -+ if (current_duplex == full) -+ data |= ADVERTISE_100FULL | ADVERTISE_10FULL; -+ else if (current_duplex == half) -+ data |= ADVERTISE_100HALF | ADVERTISE_10HALF; -+ else -+ data |= ADVERTISE_10HALF | ADVERTISE_10FULL | -+ ADVERTISE_100HALF | ADVERTISE_100FULL; -+ break; -+ -+ default: /* assume autoneg speed and duplex */ -+ data |= ADVERTISE_10HALF | ADVERTISE_10FULL | -+ ADVERTISE_100HALF | ADVERTISE_100FULL; -+ break; -+ } -+ -+ e100_set_mdio_reg(dev, np->mii_if.phy_id, MII_ADVERTISE, data); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_BMCR); -+ if (autoneg_normal) { -+ /* Renegotiate with link partner */ -+ data |= BMCR_ANENABLE | BMCR_ANRESTART; -+ } else { -+ /* Don't negotiate speed or duplex */ -+ data &= ~(BMCR_ANENABLE | BMCR_ANRESTART); -+ -+ /* Set speed and duplex static */ -+ if (current_speed_selection == 10) -+ data &= ~BMCR_SPEED100; -+ else -+ data |= BMCR_SPEED100; -+ -+ if (current_duplex != full) -+ data &= ~BMCR_FULLDPLX; -+ else -+ data |= BMCR_FULLDPLX; -+ } -+ e100_set_mdio_reg(dev, np->mii_if.phy_id, MII_BMCR, data); -+} -+ -+static void -+e100_set_speed(struct net_device* dev, unsigned long speed) -+{ -+ struct net_local *np = netdev_priv(dev); -+ -+ spin_lock(&np->transceiver_lock); -+ if (speed != current_speed_selection) { -+ current_speed_selection = speed; -+ e100_negotiate(dev); -+ } -+ spin_unlock(&np->transceiver_lock); -+} -+ -+static void -+e100_check_duplex(unsigned long priv) -+{ -+ struct net_device *dev = (struct net_device *)priv; -+ struct net_local *np = netdev_priv(dev); -+ int old_duplex; -+ -+ spin_lock(&np->transceiver_lock); -+ old_duplex = full_duplex; -+ transceiver->check_duplex(dev); -+ if (old_duplex != full_duplex) { -+ /* Duplex changed */ -+ SETF(network_rec_config_shadow, R_NETWORK_REC_CONFIG, duplex, full_duplex); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+ } -+ -+ /* Reinitialize the timer. */ -+ duplex_timer.expires = jiffies + NET_DUPLEX_CHECK_INTERVAL; -+ add_timer(&duplex_timer); -+ np->mii_if.full_duplex = full_duplex; -+ spin_unlock(&np->transceiver_lock); -+} -+#if defined(CONFIG_ETRAX_NO_PHY) -+static void -+dummy_check_duplex(struct net_device* dev) -+{ -+ full_duplex = 1; -+} -+#else -+static void -+generic_check_duplex(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_ADVERTISE); -+ if ((data & ADVERTISE_10FULL) || -+ (data & ADVERTISE_100FULL)) -+ full_duplex = 1; -+ else -+ full_duplex = 0; -+} -+ -+static void -+tdk_check_duplex(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_TDK_DIAGNOSTIC_REG); -+ full_duplex = (data & MDIO_TDK_DIAGNOSTIC_DPLX) ? 1 : 0; -+} -+ -+static void -+broadcom_check_duplex(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_AUX_CTRL_STATUS_REG); -+ full_duplex = (data & MDIO_BC_FULL_DUPLEX_IND) ? 1 : 0; -+} -+ -+static void -+intel_check_duplex(struct net_device* dev) -+{ -+ unsigned long data; -+ struct net_local *np = netdev_priv(dev); -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, -+ MDIO_INT_STATUS_REG_2); -+ full_duplex = (data & MDIO_INT_FULL_DUPLEX_IND) ? 1 : 0; -+} -+#endif -+static void -+e100_set_duplex(struct net_device* dev, enum duplex new_duplex) -+{ -+ struct net_local *np = netdev_priv(dev); -+ -+ spin_lock(&np->transceiver_lock); -+ if (new_duplex != current_duplex) { -+ current_duplex = new_duplex; -+ e100_negotiate(dev); -+ } -+ spin_unlock(&np->transceiver_lock); -+} -+ -+static int -+e100_probe_transceiver(struct net_device* dev) -+{ -+ int ret = 0; -+ -+#if !defined(CONFIG_ETRAX_NO_PHY) -+ unsigned int phyid_high; -+ unsigned int phyid_low; -+ unsigned int oui; -+ struct transceiver_ops* ops = NULL; -+ struct net_local *np = netdev_priv(dev); -+ -+ spin_lock(&np->transceiver_lock); -+ -+ /* Probe MDIO physical address */ -+ for (np->mii_if.phy_id = 0; np->mii_if.phy_id <= 31; -+ np->mii_if.phy_id++) { -+ if (e100_get_mdio_reg(dev, -+ np->mii_if.phy_id, MII_BMSR) != 0xffff) -+ break; -+ } -+ if (np->mii_if.phy_id == 32) { -+ ret = -ENODEV; -+ goto out; -+ } -+ -+ /* Get manufacturer */ -+ phyid_high = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_PHYSID1); -+ phyid_low = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_PHYSID2); -+ oui = (phyid_high << 6) | (phyid_low >> 10); -+ -+ for (ops = &transceivers[0]; ops->oui; ops++) { -+ if (ops->oui == oui) -+ break; -+ } -+ transceiver = ops; -+out: -+ spin_unlock(&np->transceiver_lock); -+#endif -+ return ret; -+} -+ -+static int -+e100_get_mdio_reg(struct net_device *dev, int phy_id, int location) -+{ -+ unsigned short cmd; /* Data to be sent on MDIO port */ -+ int data; /* Data read from MDIO */ -+ int bitCounter; -+ -+ /* Start of frame, OP Code, Physical Address, Register Address */ -+ cmd = (MDIO_START << 14) | (MDIO_READ << 12) | (phy_id << 7) | -+ (location << 2); -+ -+ e100_send_mdio_cmd(cmd, 0); -+ -+ data = 0; -+ -+ /* Data... */ -+ for (bitCounter=15; bitCounter>=0 ; bitCounter--) { -+ data |= (e100_receive_mdio_bit() << bitCounter); -+ } -+ -+ return data; -+} -+ -+static void -+e100_set_mdio_reg(struct net_device *dev, int phy_id, int location, int value) -+{ -+ int bitCounter; -+ unsigned short cmd; -+ -+ cmd = (MDIO_START << 14) | (MDIO_WRITE << 12) | (phy_id << 7) | -+ (location << 2); -+ -+ e100_send_mdio_cmd(cmd, 1); -+ -+ /* Data... */ -+ for (bitCounter=15; bitCounter>=0 ; bitCounter--) { -+ e100_send_mdio_bit(GET_BIT(bitCounter, value)); -+ } -+ -+} -+ -+static void -+e100_send_mdio_cmd(unsigned short cmd, int write_cmd) -+{ -+ int bitCounter; -+ unsigned char data = 0x2; -+ -+ /* Preamble */ -+ for (bitCounter = 31; bitCounter>= 0; bitCounter--) -+ e100_send_mdio_bit(GET_BIT(bitCounter, MDIO_PREAMBLE)); -+ -+ for (bitCounter = 15; bitCounter >= 2; bitCounter--) -+ e100_send_mdio_bit(GET_BIT(bitCounter, cmd)); -+ -+ /* Turnaround */ -+ for (bitCounter = 1; bitCounter >= 0 ; bitCounter--) -+ if (write_cmd) -+ e100_send_mdio_bit(GET_BIT(bitCounter, data)); -+ else -+ e100_receive_mdio_bit(); -+} -+ -+static void -+e100_send_mdio_bit(unsigned char bit) -+{ -+ *R_NETWORK_MGM_CTRL = -+ IO_STATE(R_NETWORK_MGM_CTRL, mdoe, enable) | -+ IO_FIELD(R_NETWORK_MGM_CTRL, mdio, bit); -+ udelay(1); -+ *R_NETWORK_MGM_CTRL = -+ IO_STATE(R_NETWORK_MGM_CTRL, mdoe, enable) | -+ IO_MASK(R_NETWORK_MGM_CTRL, mdck) | -+ IO_FIELD(R_NETWORK_MGM_CTRL, mdio, bit); -+ udelay(1); -+} -+ -+static unsigned char -+e100_receive_mdio_bit() -+{ -+ unsigned char bit; -+ *R_NETWORK_MGM_CTRL = 0; -+ bit = IO_EXTRACT(R_NETWORK_STAT, mdio, *R_NETWORK_STAT); -+ udelay(1); -+ *R_NETWORK_MGM_CTRL = IO_MASK(R_NETWORK_MGM_CTRL, mdck); -+ udelay(1); -+ return bit; -+} -+ -+static void -+e100_reset_transceiver(struct net_device* dev) -+{ -+ struct net_local *np = netdev_priv(dev); -+ unsigned short cmd; -+ unsigned short data; -+ int bitCounter; -+ -+ data = e100_get_mdio_reg(dev, np->mii_if.phy_id, MII_BMCR); -+ -+ cmd = (MDIO_START << 14) | (MDIO_WRITE << 12) | (np->mii_if.phy_id << 7) | (MII_BMCR << 2); -+ -+ e100_send_mdio_cmd(cmd, 1); -+ -+ data |= 0x8000; -+ -+ for (bitCounter = 15; bitCounter >= 0 ; bitCounter--) { -+ e100_send_mdio_bit(GET_BIT(bitCounter, data)); -+ } -+} -+ -+/* Called by upper layers if they decide it took too long to complete -+ * sending a packet - we need to reset and stuff. -+ */ -+ -+static void -+e100_tx_timeout(struct net_device *dev) -+{ -+ struct net_local *np = netdev_priv(dev); -+ unsigned long flags; -+ -+ spin_lock_irqsave(&np->lock, flags); -+ -+ printk(KERN_WARNING "%s: transmit timed out, %s?\n", dev->name, -+ tx_done(dev) ? "IRQ problem" : "network cable problem"); -+ -+ /* remember we got an error */ -+ -+ dev->stats.tx_errors++; -+ -+ /* reset the TX DMA in case it has hung on something */ -+ -+ RESET_DMA(NETWORK_TX_DMA_NBR); -+ WAIT_DMA(NETWORK_TX_DMA_NBR); -+ -+ /* Reset the transceiver. */ -+ -+ e100_reset_transceiver(dev); -+ -+ /* and get rid of the packets that never got an interrupt */ -+ while (myFirstTxDesc != myNextTxDesc) { -+ dev_kfree_skb(myFirstTxDesc->skb); -+ myFirstTxDesc->skb = 0; -+ myFirstTxDesc = phys_to_virt(myFirstTxDesc->descr.next); -+ } -+ -+ /* Set up transmit DMA channel so it can be restarted later */ -+ *R_DMA_CH0_FIRST = 0; -+ *R_DMA_CH0_DESCR = virt_to_phys(myLastTxDesc); -+ -+ /* tell the upper layers we're ok again */ -+ -+ netif_wake_queue(dev); -+ spin_unlock_irqrestore(&np->lock, flags); -+} -+ -+ -+/* This will only be invoked if the driver is _not_ in XOFF state. -+ * What this means is that we need not check it, and that this -+ * invariant will hold if we make sure that the netif_*_queue() -+ * calls are done at the proper times. -+ */ -+ -+static int -+e100_send_packet(struct sk_buff *skb, struct net_device *dev) -+{ -+ struct net_local *np = netdev_priv(dev); -+ unsigned char *buf = skb->data; -+ unsigned long flags; -+ -+#ifdef ETHDEBUG -+ printk("send packet len %d\n", length); -+#endif -+ spin_lock_irqsave(&np->lock, flags); /* protect from tx_interrupt and ourself */ -+ -+ myNextTxDesc->skb = skb; -+ -+ dev->trans_start = jiffies; /* NETIF_F_LLTX driver :( */ -+ -+ e100_hardware_send_packet(np, buf, skb->len); -+ -+ myNextTxDesc = phys_to_virt(myNextTxDesc->descr.next); -+ -+ /* Stop queue if full */ -+ if (myNextTxDesc == myFirstTxDesc) { -+ netif_stop_queue(dev); -+ } -+ -+ spin_unlock_irqrestore(&np->lock, flags); -+ -+ return NETDEV_TX_OK; -+} -+ -+/* -+ * The typical workload of the driver: -+ * Handle the network interface interrupts. -+ */ -+ -+static irqreturn_t -+e100rxtx_interrupt(int irq, void *dev_id) -+{ -+ struct net_device *dev = (struct net_device *)dev_id; -+ struct net_local *np = netdev_priv(dev); -+ unsigned long irqbits; -+ -+ /* -+ * Note that both rx and tx interrupts are blocked at this point, -+ * regardless of which got us here. -+ */ -+ -+ irqbits = *R_IRQ_MASK2_RD; -+ -+ /* Handle received packets */ -+ if (irqbits & IO_STATE(R_IRQ_MASK2_RD, dma1_eop, active)) { -+ /* acknowledge the eop interrupt */ -+ -+ *R_DMA_CH1_CLR_INTR = IO_STATE(R_DMA_CH1_CLR_INTR, clr_eop, do); -+ -+ /* check if one or more complete packets were indeed received */ -+ -+ while ((*R_DMA_CH1_FIRST != virt_to_phys(myNextRxDesc)) && -+ (myNextRxDesc != myLastRxDesc)) { -+ /* Take out the buffer and give it to the OS, then -+ * allocate a new buffer to put a packet in. -+ */ -+ e100_rx(dev); -+ dev->stats.rx_packets++; -+ /* restart/continue on the channel, for safety */ -+ *R_DMA_CH1_CMD = IO_STATE(R_DMA_CH1_CMD, cmd, restart); -+ /* clear dma channel 1 eop/descr irq bits */ -+ *R_DMA_CH1_CLR_INTR = -+ IO_STATE(R_DMA_CH1_CLR_INTR, clr_eop, do) | -+ IO_STATE(R_DMA_CH1_CLR_INTR, clr_descr, do); -+ -+ /* now, we might have gotten another packet -+ so we have to loop back and check if so */ -+ } -+ } -+ -+ /* Report any packets that have been sent */ -+ while (virt_to_phys(myFirstTxDesc) != *R_DMA_CH0_FIRST && -+ (netif_queue_stopped(dev) || myFirstTxDesc != myNextTxDesc)) { -+ dev->stats.tx_bytes += myFirstTxDesc->skb->len; -+ dev->stats.tx_packets++; -+ -+ /* dma is ready with the transmission of the data in tx_skb, so now -+ we can release the skb memory */ -+ dev_kfree_skb_irq(myFirstTxDesc->skb); -+ myFirstTxDesc->skb = 0; -+ myFirstTxDesc = phys_to_virt(myFirstTxDesc->descr.next); -+ /* Wake up queue. */ -+ netif_wake_queue(dev); -+ } -+ -+ if (irqbits & IO_STATE(R_IRQ_MASK2_RD, dma0_eop, active)) { -+ /* acknowledge the eop interrupt. */ -+ *R_DMA_CH0_CLR_INTR = IO_STATE(R_DMA_CH0_CLR_INTR, clr_eop, do); -+ } -+ -+ return IRQ_HANDLED; -+} -+ -+static irqreturn_t -+e100nw_interrupt(int irq, void *dev_id) -+{ -+ struct net_device *dev = (struct net_device *)dev_id; -+ unsigned long irqbits = *R_IRQ_MASK0_RD; -+ -+ /* check for underrun irq */ -+ if (irqbits & IO_STATE(R_IRQ_MASK0_RD, underrun, active)) { -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, clr_error, clr); -+ *R_NETWORK_TR_CTRL = network_tr_ctrl_shadow; -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, clr_error, nop); -+ dev->stats.tx_errors++; -+ D(printk("ethernet receiver underrun!\n")); -+ } -+ -+ /* check for overrun irq */ -+ if (irqbits & IO_STATE(R_IRQ_MASK0_RD, overrun, active)) { -+ update_rx_stats(&dev->stats); /* this will ack the irq */ -+ D(printk("ethernet receiver overrun!\n")); -+ } -+ /* check for excessive collision irq */ -+ if (irqbits & IO_STATE(R_IRQ_MASK0_RD, excessive_col, active)) { -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, clr_error, clr); -+ *R_NETWORK_TR_CTRL = network_tr_ctrl_shadow; -+ SETS(network_tr_ctrl_shadow, R_NETWORK_TR_CTRL, clr_error, nop); -+ dev->stats.tx_errors++; -+ D(printk("ethernet excessive collisions!\n")); -+ } -+ return IRQ_HANDLED; -+} -+ -+/* We have a good packet(s), get it/them out of the buffers. */ -+static void -+e100_rx(struct net_device *dev) -+{ -+ struct sk_buff *skb; -+ int length = 0; -+ struct net_local *np = netdev_priv(dev); -+ unsigned char *skb_data_ptr; -+#ifdef ETHDEBUG -+ int i; -+#endif -+ etrax_eth_descr *prevRxDesc; /* The descriptor right before myNextRxDesc */ -+ spin_lock(&np->led_lock); -+ if (!led_active && time_after(jiffies, led_next_time)) { -+ /* light the network leds depending on the current speed. */ -+ e100_set_network_leds(NETWORK_ACTIVITY); -+ -+ /* Set the earliest time we may clear the LED */ -+ led_next_time = jiffies + NET_FLASH_TIME; -+ led_active = 1; -+ mod_timer(&clear_led_timer, jiffies + HZ/10); -+ } -+ spin_unlock(&np->led_lock); -+ -+ length = myNextRxDesc->descr.hw_len - 4; -+ dev->stats.rx_bytes += length; -+ -+#ifdef ETHDEBUG -+ printk("Got a packet of length %d:\n", length); -+ /* dump the first bytes in the packet */ -+ skb_data_ptr = (unsigned char *)phys_to_virt(myNextRxDesc->descr.buf); -+ for (i = 0; i < 8; i++) { -+ printk("%d: %.2x %.2x %.2x %.2x %.2x %.2x %.2x %.2x\n", i * 8, -+ skb_data_ptr[0],skb_data_ptr[1],skb_data_ptr[2],skb_data_ptr[3], -+ skb_data_ptr[4],skb_data_ptr[5],skb_data_ptr[6],skb_data_ptr[7]); -+ skb_data_ptr += 8; -+ } -+#endif -+ -+ if (length < RX_COPYBREAK) { -+ /* Small packet, copy data */ -+ skb = dev_alloc_skb(length - ETHER_HEAD_LEN); -+ if (!skb) { -+ dev->stats.rx_errors++; -+ printk(KERN_NOTICE "%s: Memory squeeze, dropping packet.\n", dev->name); -+ goto update_nextrxdesc; -+ } -+ -+ skb_put(skb, length - ETHER_HEAD_LEN); /* allocate room for the packet body */ -+ skb_data_ptr = skb_push(skb, ETHER_HEAD_LEN); /* allocate room for the header */ -+ -+#ifdef ETHDEBUG -+ printk("head = 0x%x, data = 0x%x, tail = 0x%x, end = 0x%x\n", -+ skb->head, skb->data, skb_tail_pointer(skb), -+ skb_end_pointer(skb)); -+ printk("copying packet to 0x%x.\n", skb_data_ptr); -+#endif -+ -+ memcpy(skb_data_ptr, phys_to_virt(myNextRxDesc->descr.buf), length); -+ } -+ else { -+ /* Large packet, send directly to upper layers and allocate new -+ * memory (aligned to cache line boundary to avoid bug). -+ * Before sending the skb to upper layers we must make sure -+ * that skb->data points to the aligned start of the packet. -+ */ -+ int align; -+ struct sk_buff *new_skb = dev_alloc_skb(MAX_MEDIA_DATA_SIZE + 2 * L1_CACHE_BYTES); -+ if (!new_skb) { -+ dev->stats.rx_errors++; -+ printk(KERN_NOTICE "%s: Memory squeeze, dropping packet.\n", dev->name); -+ goto update_nextrxdesc; -+ } -+ skb = myNextRxDesc->skb; -+ align = (int)phys_to_virt(myNextRxDesc->descr.buf) - (int)skb->data; -+ skb_put(skb, length + align); -+ skb_pull(skb, align); /* Remove alignment bytes */ -+ myNextRxDesc->skb = new_skb; -+ myNextRxDesc->descr.buf = L1_CACHE_ALIGN(virt_to_phys(myNextRxDesc->skb->data)); -+ } -+ -+ skb->protocol = eth_type_trans(skb, dev); -+ -+ /* Send the packet to the upper layers */ -+ netif_rx(skb); -+ -+ update_nextrxdesc: -+ /* Prepare for next packet */ -+ myNextRxDesc->descr.status = 0; -+ prevRxDesc = myNextRxDesc; -+ myNextRxDesc = phys_to_virt(myNextRxDesc->descr.next); -+ -+ rx_queue_len++; -+ -+ /* Check if descriptors should be returned */ -+ if (rx_queue_len == RX_QUEUE_THRESHOLD) { -+ flush_etrax_cache(); -+ prevRxDesc->descr.ctrl |= d_eol; -+ myLastRxDesc->descr.ctrl &= ~d_eol; -+ myLastRxDesc = prevRxDesc; -+ rx_queue_len = 0; -+ } -+} -+ -+/* The inverse routine to net_open(). */ -+static int -+e100_close(struct net_device *dev) -+{ -+ printk(KERN_INFO "Closing %s.\n", dev->name); -+ -+ netif_stop_queue(dev); -+ -+ *R_IRQ_MASK0_CLR = -+ IO_STATE(R_IRQ_MASK0_CLR, overrun, clr) | -+ IO_STATE(R_IRQ_MASK0_CLR, underrun, clr) | -+ IO_STATE(R_IRQ_MASK0_CLR, excessive_col, clr); -+ -+ *R_IRQ_MASK2_CLR = -+ IO_STATE(R_IRQ_MASK2_CLR, dma0_descr, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma0_eop, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma1_descr, clr) | -+ IO_STATE(R_IRQ_MASK2_CLR, dma1_eop, clr); -+ -+ /* Stop the receiver and the transmitter */ -+ -+ RESET_DMA(NETWORK_TX_DMA_NBR); -+ RESET_DMA(NETWORK_RX_DMA_NBR); -+ -+ /* Flush the Tx and disable Rx here. */ -+ -+ free_irq(NETWORK_DMA_RX_IRQ_NBR, (void *)dev); -+ free_irq(NETWORK_DMA_TX_IRQ_NBR, (void *)dev); -+ free_irq(NETWORK_STATUS_IRQ_NBR, (void *)dev); -+ -+ cris_free_dma(NETWORK_TX_DMA_NBR, cardname); -+ cris_free_dma(NETWORK_RX_DMA_NBR, cardname); -+ -+ /* Update the statistics here. */ -+ -+ update_rx_stats(&dev->stats); -+ update_tx_stats(&dev->stats); -+ -+ /* Stop speed/duplex timers */ -+ del_timer(&speed_timer); -+ del_timer(&duplex_timer); -+ -+ return 0; -+} -+ -+static int -+e100_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) -+{ -+ struct mii_ioctl_data *data = if_mii(ifr); -+ struct net_local *np = netdev_priv(dev); -+ int rc = 0; -+ int old_autoneg; -+ -+ spin_lock(&np->lock); /* Preempt protection */ -+ switch (cmd) { -+ /* The ioctls below should be considered obsolete but are */ -+ /* still present for compatibility with old scripts/apps */ -+ case SET_ETH_SPEED_10: /* 10 Mbps */ -+ e100_set_speed(dev, 10); -+ break; -+ case SET_ETH_SPEED_100: /* 100 Mbps */ -+ e100_set_speed(dev, 100); -+ break; -+ case SET_ETH_SPEED_AUTO: /* Auto-negotiate speed */ -+ e100_set_speed(dev, 0); -+ break; -+ case SET_ETH_DUPLEX_HALF: /* Half duplex */ -+ e100_set_duplex(dev, half); -+ break; -+ case SET_ETH_DUPLEX_FULL: /* Full duplex */ -+ e100_set_duplex(dev, full); -+ break; -+ case SET_ETH_DUPLEX_AUTO: /* Auto-negotiate duplex */ -+ e100_set_duplex(dev, autoneg); -+ break; -+ case SET_ETH_AUTONEG: -+ old_autoneg = autoneg_normal; -+ autoneg_normal = *(int*)data; -+ if (autoneg_normal != old_autoneg) -+ e100_negotiate(dev); -+ break; -+ default: -+ rc = generic_mii_ioctl(&np->mii_if, if_mii(ifr), -+ cmd, NULL); -+ break; -+ } -+ spin_unlock(&np->lock); -+ return rc; -+} -+ -+static int e100_get_settings(struct net_device *dev, -+ struct ethtool_cmd *cmd) -+{ -+ struct net_local *np = netdev_priv(dev); -+ int err; -+ -+ spin_lock_irq(&np->lock); -+ err = mii_ethtool_gset(&np->mii_if, cmd); -+ spin_unlock_irq(&np->lock); -+ -+ /* The PHY may support 1000baseT, but the Etrax100 does not. */ -+ cmd->supported &= ~(SUPPORTED_1000baseT_Half -+ | SUPPORTED_1000baseT_Full); -+ return err; -+} -+ -+static int e100_set_settings(struct net_device *dev, -+ struct ethtool_cmd *ecmd) -+{ -+ if (ecmd->autoneg == AUTONEG_ENABLE) { -+ e100_set_duplex(dev, autoneg); -+ e100_set_speed(dev, 0); -+ } else { -+ e100_set_duplex(dev, ecmd->duplex == DUPLEX_HALF ? half : full); -+ e100_set_speed(dev, ecmd->speed == SPEED_10 ? 10: 100); -+ } -+ -+ return 0; -+} -+ -+static void e100_get_drvinfo(struct net_device *dev, -+ struct ethtool_drvinfo *info) -+{ -+ strncpy(info->driver, "ETRAX 100LX", sizeof(info->driver) - 1); -+ strncpy(info->version, "$Revision: 1.31 $", sizeof(info->version) - 1); -+ strncpy(info->fw_version, "N/A", sizeof(info->fw_version) - 1); -+ strncpy(info->bus_info, "N/A", sizeof(info->bus_info) - 1); -+} -+ -+static int e100_nway_reset(struct net_device *dev) -+{ -+ if (current_duplex == autoneg && current_speed_selection == 0) -+ e100_negotiate(dev); -+ return 0; -+} -+ -+static const struct ethtool_ops e100_ethtool_ops = { -+ .get_settings = e100_get_settings, -+ .set_settings = e100_set_settings, -+ .get_drvinfo = e100_get_drvinfo, -+ .nway_reset = e100_nway_reset, -+ .get_link = ethtool_op_get_link, -+}; -+ -+static int -+e100_set_config(struct net_device *dev, struct ifmap *map) -+{ -+ struct net_local *np = netdev_priv(dev); -+ -+ spin_lock(&np->lock); /* Preempt protection */ -+ -+ switch(map->port) { -+ case IF_PORT_UNKNOWN: -+ /* Use autoneg */ -+ e100_set_speed(dev, 0); -+ e100_set_duplex(dev, autoneg); -+ break; -+ case IF_PORT_10BASET: -+ e100_set_speed(dev, 10); -+ e100_set_duplex(dev, autoneg); -+ break; -+ case IF_PORT_100BASET: -+ case IF_PORT_100BASETX: -+ e100_set_speed(dev, 100); -+ e100_set_duplex(dev, autoneg); -+ break; -+ case IF_PORT_100BASEFX: -+ case IF_PORT_10BASE2: -+ case IF_PORT_AUI: -+ spin_unlock(&np->lock); -+ return -EOPNOTSUPP; -+ break; -+ default: -+ printk(KERN_ERR "%s: Invalid media selected", dev->name); -+ spin_unlock(&np->lock); -+ return -EINVAL; -+ } -+ spin_unlock(&np->lock); -+ return 0; -+} -+ -+static void -+update_rx_stats(struct net_device_stats *es) -+{ -+ unsigned long r = *R_REC_COUNTERS; -+ /* update stats relevant to reception errors */ -+ es->rx_fifo_errors += IO_EXTRACT(R_REC_COUNTERS, congestion, r); -+ es->rx_crc_errors += IO_EXTRACT(R_REC_COUNTERS, crc_error, r); -+ es->rx_frame_errors += IO_EXTRACT(R_REC_COUNTERS, alignment_error, r); -+ es->rx_length_errors += IO_EXTRACT(R_REC_COUNTERS, oversize, r); -+} -+ -+static void -+update_tx_stats(struct net_device_stats *es) -+{ -+ unsigned long r = *R_TR_COUNTERS; -+ /* update stats relevant to transmission errors */ -+ es->collisions += -+ IO_EXTRACT(R_TR_COUNTERS, single_col, r) + -+ IO_EXTRACT(R_TR_COUNTERS, multiple_col, r); -+} -+ -+/* -+ * Get the current statistics. -+ * This may be called with the card open or closed. -+ */ -+static struct net_device_stats * -+e100_get_stats(struct net_device *dev) -+{ -+ struct net_local *lp = netdev_priv(dev); -+ unsigned long flags; -+ -+ spin_lock_irqsave(&lp->lock, flags); -+ -+ update_rx_stats(&dev->stats); -+ update_tx_stats(&dev->stats); -+ -+ spin_unlock_irqrestore(&lp->lock, flags); -+ return &dev->stats; -+} -+ -+/* -+ * Set or clear the multicast filter for this adaptor. -+ * num_addrs == -1 Promiscuous mode, receive all packets -+ * num_addrs == 0 Normal mode, clear multicast list -+ * num_addrs > 0 Multicast mode, receive normal and MC packets, -+ * and do best-effort filtering. -+ */ -+static void -+set_multicast_list(struct net_device *dev) -+{ -+ struct net_local *lp = netdev_priv(dev); -+ int num_addr = netdev_mc_count(dev); -+ unsigned long int lo_bits; -+ unsigned long int hi_bits; -+ -+ spin_lock(&lp->lock); -+ if (dev->flags & IFF_PROMISC) { -+ /* promiscuous mode */ -+ lo_bits = 0xfffffffful; -+ hi_bits = 0xfffffffful; -+ -+ /* Enable individual receive */ -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, individual, receive); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+ } else if (dev->flags & IFF_ALLMULTI) { -+ /* enable all multicasts */ -+ lo_bits = 0xfffffffful; -+ hi_bits = 0xfffffffful; -+ -+ /* Disable individual receive */ -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, individual, discard); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+ } else if (num_addr == 0) { -+ /* Normal, clear the mc list */ -+ lo_bits = 0x00000000ul; -+ hi_bits = 0x00000000ul; -+ -+ /* Disable individual receive */ -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, individual, discard); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+ } else { -+ /* MC mode, receive normal and MC packets */ -+ char hash_ix; -+ struct netdev_hw_addr *ha; -+ char *baddr; -+ -+ lo_bits = 0x00000000ul; -+ hi_bits = 0x00000000ul; -+ netdev_for_each_mc_addr(ha, dev) { -+ /* Calculate the hash index for the GA registers */ -+ -+ hash_ix = 0; -+ baddr = ha->addr; -+ hash_ix ^= (*baddr) & 0x3f; -+ hash_ix ^= ((*baddr) >> 6) & 0x03; -+ ++baddr; -+ hash_ix ^= ((*baddr) << 2) & 0x03c; -+ hash_ix ^= ((*baddr) >> 4) & 0xf; -+ ++baddr; -+ hash_ix ^= ((*baddr) << 4) & 0x30; -+ hash_ix ^= ((*baddr) >> 2) & 0x3f; -+ ++baddr; -+ hash_ix ^= (*baddr) & 0x3f; -+ hash_ix ^= ((*baddr) >> 6) & 0x03; -+ ++baddr; -+ hash_ix ^= ((*baddr) << 2) & 0x03c; -+ hash_ix ^= ((*baddr) >> 4) & 0xf; -+ ++baddr; -+ hash_ix ^= ((*baddr) << 4) & 0x30; -+ hash_ix ^= ((*baddr) >> 2) & 0x3f; -+ -+ hash_ix &= 0x3f; -+ -+ if (hash_ix >= 32) { -+ hi_bits |= (1 << (hash_ix-32)); -+ } else { -+ lo_bits |= (1 << hash_ix); -+ } -+ } -+ /* Disable individual receive */ -+ SETS(network_rec_config_shadow, R_NETWORK_REC_CONFIG, individual, discard); -+ *R_NETWORK_REC_CONFIG = network_rec_config_shadow; -+ } -+ *R_NETWORK_GA_0 = lo_bits; -+ *R_NETWORK_GA_1 = hi_bits; -+ spin_unlock(&lp->lock); -+} -+ -+void -+e100_hardware_send_packet(struct net_local *np, char *buf, int length) -+{ -+ D(printk("e100 send pack, buf 0x%x len %d\n", buf, length)); -+ -+ spin_lock(&np->led_lock); -+ if (!led_active && time_after(jiffies, led_next_time)) { -+ /* light the network leds depending on the current speed. */ -+ e100_set_network_leds(NETWORK_ACTIVITY); -+ -+ /* Set the earliest time we may clear the LED */ -+ led_next_time = jiffies + NET_FLASH_TIME; -+ led_active = 1; -+ mod_timer(&clear_led_timer, jiffies + HZ/10); -+ } -+ spin_unlock(&np->led_lock); -+ -+ /* configure the tx dma descriptor */ -+ myNextTxDesc->descr.sw_len = length; -+ myNextTxDesc->descr.ctrl = d_eop | d_eol | d_wait; -+ myNextTxDesc->descr.buf = virt_to_phys(buf); -+ -+ /* Move end of list */ -+ myLastTxDesc->descr.ctrl &= ~d_eol; -+ myLastTxDesc = myNextTxDesc; -+ -+ /* Restart DMA channel */ -+ *R_DMA_CH0_CMD = IO_STATE(R_DMA_CH0_CMD, cmd, restart); -+} -+ -+static void -+e100_clear_network_leds(unsigned long dummy) -+{ -+ struct net_device *dev = (struct net_device *)dummy; -+ struct net_local *np = netdev_priv(dev); -+ -+ spin_lock(&np->led_lock); -+ -+ if (led_active && time_after(jiffies, led_next_time)) { -+ e100_set_network_leds(NO_NETWORK_ACTIVITY); -+ -+ /* Set the earliest time we may set the LED */ -+ led_next_time = jiffies + NET_FLASH_PAUSE; -+ led_active = 0; -+ } -+ -+ spin_unlock(&np->led_lock); -+} -+ -+static void -+e100_set_network_leds(int active) -+{ -+#if defined(CONFIG_ETRAX_NETWORK_LED_ON_WHEN_LINK) -+ int light_leds = (active == NO_NETWORK_ACTIVITY); -+#elif defined(CONFIG_ETRAX_NETWORK_LED_ON_WHEN_ACTIVITY) -+ int light_leds = (active == NETWORK_ACTIVITY); -+#else -+#error "Define either CONFIG_ETRAX_NETWORK_LED_ON_WHEN_LINK or CONFIG_ETRAX_NETWORK_LED_ON_WHEN_ACTIVITY" -+#endif -+ -+ if (!current_speed) { -+ /* Make LED red, link is down */ -+ CRIS_LED_NETWORK_SET(CRIS_LED_OFF); -+ } else if (light_leds) { -+ if (current_speed == 10) { -+ CRIS_LED_NETWORK_SET(CRIS_LED_ORANGE); -+ } else { -+ CRIS_LED_NETWORK_SET(CRIS_LED_GREEN); -+ } -+ } else { -+ CRIS_LED_NETWORK_SET(CRIS_LED_OFF); -+ } -+} -+ -+#ifdef CONFIG_NET_POLL_CONTROLLER -+static void -+e100_netpoll(struct net_device* netdev) -+{ -+ e100rxtx_interrupt(NETWORK_DMA_TX_IRQ_NBR, netdev, NULL); -+} -+#endif -+ -+static int -+etrax_init_module(void) -+{ -+ return etrax_ethernet_init(); -+} -+ -+static int __init -+e100_boot_setup(char* str) -+{ -+ struct sockaddr sa = {0}; -+ int i; -+ -+ /* Parse the colon separated Ethernet station address */ -+ for (i = 0; i < ETH_ALEN; i++) { -+ unsigned int tmp; -+ if (sscanf(str + 3*i, "%2x", &tmp) != 1) { -+ printk(KERN_WARNING "Malformed station address"); -+ return 0; -+ } -+ sa.sa_data[i] = (char)tmp; -+ } -+ -+ default_mac = sa; -+ return 1; -+} -+ -+__setup("etrax100_eth=", e100_boot_setup); -+ -+module_init(etrax_init_module); -diff -Nur linux-2.6.39.orig/drivers/tty/serial/crisv10.c linux-2.6.39/drivers/tty/serial/crisv10.c ---- linux-2.6.39.orig/drivers/tty/serial/crisv10.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/tty/serial/crisv10.c 2011-07-28 16:27:57.623883501 +0200 -@@ -26,6 +26,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -4430,6 +4431,7 @@ - #endif - }; - -+static struct class *rs_class; - static int __init rs_init(void) - { - int i; -@@ -4564,6 +4566,24 @@ - #endif - #endif /* CONFIG_SVINTO_SIM */ - -+ rs_class = class_create(THIS_MODULE, "rs_tty"); -+#ifdef CONFIG_ETRAX_SERIAL_PORT0 -+ device_create(rs_class, NULL, -+ MKDEV(TTY_MAJOR, 64), NULL, "ttyS0"); -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT1 -+ device_create(rs_class, NULL, -+ MKDEV(TTY_MAJOR, 65), NULL, "ttyS1"); -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT2 -+ device_create(rs_class, NULL, -+ MKDEV(TTY_MAJOR, 66), NULL, "ttyS2"); -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT3 -+ device_create(rs_class, NULL, -+ MKDEV(TTY_MAJOR, 67), NULL, "ttyS3"); -+#endif -+ - return 0; - } - -diff -Nur linux-2.6.39.orig/drivers/tty/serial/crisv10.c.orig linux-2.6.39/drivers/tty/serial/crisv10.c.orig ---- linux-2.6.39.orig/drivers/tty/serial/crisv10.c.orig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/tty/serial/crisv10.c.orig 2011-05-19 06:06:34.000000000 +0200 -@@ -0,0 +1,4572 @@ -+/* -+ * Serial port driver for the ETRAX 100LX chip -+ * -+ * Copyright (C) 1998-2007 Axis Communications AB -+ * -+ * Many, many authors. Based once upon a time on serial.c for 16x50. -+ * -+ */ -+ -+static char *serial_version = "$Revision: 1.25 $"; -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include -+#include -+ -+#include -+ -+/* non-arch dependent serial structures are in linux/serial.h */ -+#include -+/* while we keep our own stuff (struct e100_serial) in a local .h file */ -+#include "crisv10.h" -+#include -+#include -+ -+#ifdef CONFIG_ETRAX_SERIAL_FAST_TIMER -+#ifndef CONFIG_ETRAX_FAST_TIMER -+#error "Enable FAST_TIMER to use SERIAL_FAST_TIMER" -+#endif -+#endif -+ -+#if defined(CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS) && \ -+ (CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS == 0) -+#error "RX_TIMEOUT_TICKS == 0 not allowed, use 1" -+#endif -+ -+#if defined(CONFIG_ETRAX_RS485_ON_PA) && defined(CONFIG_ETRAX_RS485_ON_PORT_G) -+#error "Disable either CONFIG_ETRAX_RS485_ON_PA or CONFIG_ETRAX_RS485_ON_PORT_G" -+#endif -+ -+/* -+ * All of the compatibilty code so we can compile serial.c against -+ * older kernels is hidden in serial_compat.h -+ */ -+#if defined(LOCAL_HEADERS) -+#include "serial_compat.h" -+#endif -+ -+struct tty_driver *serial_driver; -+ -+/* number of characters left in xmit buffer before we ask for more */ -+#define WAKEUP_CHARS 256 -+ -+//#define SERIAL_DEBUG_INTR -+//#define SERIAL_DEBUG_OPEN -+//#define SERIAL_DEBUG_FLOW -+//#define SERIAL_DEBUG_DATA -+//#define SERIAL_DEBUG_THROTTLE -+//#define SERIAL_DEBUG_IO /* Debug for Extra control and status pins */ -+//#define SERIAL_DEBUG_LINE 0 /* What serport we want to debug */ -+ -+/* Enable this to use serial interrupts to handle when you -+ expect the first received event on the serial port to -+ be an error, break or similar. Used to be able to flash IRMA -+ from eLinux */ -+#define SERIAL_HANDLE_EARLY_ERRORS -+ -+/* Currently 16 descriptors x 128 bytes = 2048 bytes */ -+#define SERIAL_DESCR_BUF_SIZE 256 -+ -+#define SERIAL_PRESCALE_BASE 3125000 /* 3.125MHz */ -+#define DEF_BAUD_BASE SERIAL_PRESCALE_BASE -+ -+/* We don't want to load the system with massive fast timer interrupt -+ * on high baudrates so limit it to 250 us (4kHz) */ -+#define MIN_FLUSH_TIME_USEC 250 -+ -+/* Add an x here to log a lot of timer stuff */ -+#define TIMERD(x) -+/* Debug details of interrupt handling */ -+#define DINTR1(x) /* irq on/off, errors */ -+#define DINTR2(x) /* tx and rx */ -+/* Debug flip buffer stuff */ -+#define DFLIP(x) -+/* Debug flow control and overview of data flow */ -+#define DFLOW(x) -+#define DBAUD(x) -+#define DLOG_INT_TRIG(x) -+ -+//#define DEBUG_LOG_INCLUDED -+#ifndef DEBUG_LOG_INCLUDED -+#define DEBUG_LOG(line, string, value) -+#else -+struct debug_log_info -+{ -+ unsigned long time; -+ unsigned long timer_data; -+// int line; -+ const char *string; -+ int value; -+}; -+#define DEBUG_LOG_SIZE 4096 -+ -+struct debug_log_info debug_log[DEBUG_LOG_SIZE]; -+int debug_log_pos = 0; -+ -+#define DEBUG_LOG(_line, _string, _value) do { \ -+ if ((_line) == SERIAL_DEBUG_LINE) {\ -+ debug_log_func(_line, _string, _value); \ -+ }\ -+}while(0) -+ -+void debug_log_func(int line, const char *string, int value) -+{ -+ if (debug_log_pos < DEBUG_LOG_SIZE) { -+ debug_log[debug_log_pos].time = jiffies; -+ debug_log[debug_log_pos].timer_data = *R_TIMER_DATA; -+// debug_log[debug_log_pos].line = line; -+ debug_log[debug_log_pos].string = string; -+ debug_log[debug_log_pos].value = value; -+ debug_log_pos++; -+ } -+ /*printk(string, value);*/ -+} -+#endif -+ -+#ifndef CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS -+/* Default number of timer ticks before flushing rx fifo -+ * When using "little data, low latency applications: use 0 -+ * When using "much data applications (PPP)" use ~5 -+ */ -+#define CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS 5 -+#endif -+ -+unsigned long timer_data_to_ns(unsigned long timer_data); -+ -+static void change_speed(struct e100_serial *info); -+static void rs_throttle(struct tty_struct * tty); -+static void rs_wait_until_sent(struct tty_struct *tty, int timeout); -+static int rs_write(struct tty_struct *tty, -+ const unsigned char *buf, int count); -+#ifdef CONFIG_ETRAX_RS485 -+static int e100_write_rs485(struct tty_struct *tty, -+ const unsigned char *buf, int count); -+#endif -+static int get_lsr_info(struct e100_serial *info, unsigned int *value); -+ -+ -+#define DEF_BAUD 115200 /* 115.2 kbit/s */ -+#define STD_FLAGS (ASYNC_BOOT_AUTOCONF | ASYNC_SKIP_TEST) -+#define DEF_RX 0x20 /* or SERIAL_CTRL_W >> 8 */ -+/* Default value of tx_ctrl register: has txd(bit 7)=1 (idle) as default */ -+#define DEF_TX 0x80 /* or SERIAL_CTRL_B */ -+ -+/* offsets from R_SERIALx_CTRL */ -+ -+#define REG_DATA 0 -+#define REG_DATA_STATUS32 0 /* this is the 32 bit register R_SERIALx_READ */ -+#define REG_TR_DATA 0 -+#define REG_STATUS 1 -+#define REG_TR_CTRL 1 -+#define REG_REC_CTRL 2 -+#define REG_BAUD 3 -+#define REG_XOFF 4 /* this is a 32 bit register */ -+ -+/* The bitfields are the same for all serial ports */ -+#define SER_RXD_MASK IO_MASK(R_SERIAL0_STATUS, rxd) -+#define SER_DATA_AVAIL_MASK IO_MASK(R_SERIAL0_STATUS, data_avail) -+#define SER_FRAMING_ERR_MASK IO_MASK(R_SERIAL0_STATUS, framing_err) -+#define SER_PAR_ERR_MASK IO_MASK(R_SERIAL0_STATUS, par_err) -+#define SER_OVERRUN_MASK IO_MASK(R_SERIAL0_STATUS, overrun) -+ -+#define SER_ERROR_MASK (SER_OVERRUN_MASK | SER_PAR_ERR_MASK | SER_FRAMING_ERR_MASK) -+ -+/* Values for info->errorcode */ -+#define ERRCODE_SET_BREAK (TTY_BREAK) -+#define ERRCODE_INSERT 0x100 -+#define ERRCODE_INSERT_BREAK (ERRCODE_INSERT | TTY_BREAK) -+ -+#define FORCE_EOP(info) *R_SET_EOP = 1U << info->iseteop; -+ -+/* -+ * General note regarding the use of IO_* macros in this file: -+ * -+ * We will use the bits defined for DMA channel 6 when using various -+ * IO_* macros (e.g. IO_STATE, IO_MASK, IO_EXTRACT) and _assume_ they are -+ * the same for all channels (which of course they are). -+ * -+ * We will also use the bits defined for serial port 0 when writing commands -+ * to the different ports, as these bits too are the same for all ports. -+ */ -+ -+ -+/* Mask for the irqs possibly enabled in R_IRQ_MASK1_RD etc. */ -+static const unsigned long e100_ser_int_mask = 0 -+#ifdef CONFIG_ETRAX_SERIAL_PORT0 -+| IO_MASK(R_IRQ_MASK1_RD, ser0_data) | IO_MASK(R_IRQ_MASK1_RD, ser0_ready) -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT1 -+| IO_MASK(R_IRQ_MASK1_RD, ser1_data) | IO_MASK(R_IRQ_MASK1_RD, ser1_ready) -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT2 -+| IO_MASK(R_IRQ_MASK1_RD, ser2_data) | IO_MASK(R_IRQ_MASK1_RD, ser2_ready) -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT3 -+| IO_MASK(R_IRQ_MASK1_RD, ser3_data) | IO_MASK(R_IRQ_MASK1_RD, ser3_ready) -+#endif -+; -+unsigned long r_alt_ser_baudrate_shadow = 0; -+ -+/* this is the data for the four serial ports in the etrax100 */ -+/* DMA2(ser2), DMA4(ser3), DMA6(ser0) or DMA8(ser1) */ -+/* R_DMA_CHx_CLR_INTR, R_DMA_CHx_FIRST, R_DMA_CHx_CMD */ -+ -+static struct e100_serial rs_table[] = { -+ { .baud = DEF_BAUD, -+ .ioport = (unsigned char *)R_SERIAL0_CTRL, -+ .irq = 1U << 12, /* uses DMA 6 and 7 */ -+ .oclrintradr = R_DMA_CH6_CLR_INTR, -+ .ofirstadr = R_DMA_CH6_FIRST, -+ .ocmdadr = R_DMA_CH6_CMD, -+ .ostatusadr = R_DMA_CH6_STATUS, -+ .iclrintradr = R_DMA_CH7_CLR_INTR, -+ .ifirstadr = R_DMA_CH7_FIRST, -+ .icmdadr = R_DMA_CH7_CMD, -+ .idescradr = R_DMA_CH7_DESCR, -+ .flags = STD_FLAGS, -+ .rx_ctrl = DEF_RX, -+ .tx_ctrl = DEF_TX, -+ .iseteop = 2, -+ .dma_owner = dma_ser0, -+ .io_if = if_serial_0, -+#ifdef CONFIG_ETRAX_SERIAL_PORT0 -+ .enabled = 1, -+#ifdef CONFIG_ETRAX_SERIAL_PORT0_DMA6_OUT -+ .dma_out_enabled = 1, -+ .dma_out_nbr = SER0_TX_DMA_NBR, -+ .dma_out_irq_nbr = SER0_DMA_TX_IRQ_NBR, -+ .dma_out_irq_flags = IRQF_DISABLED, -+ .dma_out_irq_description = "serial 0 dma tr", -+#else -+ .dma_out_enabled = 0, -+ .dma_out_nbr = UINT_MAX, -+ .dma_out_irq_nbr = 0, -+ .dma_out_irq_flags = 0, -+ .dma_out_irq_description = NULL, -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT0_DMA7_IN -+ .dma_in_enabled = 1, -+ .dma_in_nbr = SER0_RX_DMA_NBR, -+ .dma_in_irq_nbr = SER0_DMA_RX_IRQ_NBR, -+ .dma_in_irq_flags = IRQF_DISABLED, -+ .dma_in_irq_description = "serial 0 dma rec", -+#else -+ .dma_in_enabled = 0, -+ .dma_in_nbr = UINT_MAX, -+ .dma_in_irq_nbr = 0, -+ .dma_in_irq_flags = 0, -+ .dma_in_irq_description = NULL, -+#endif -+#else -+ .enabled = 0, -+ .io_if_description = NULL, -+ .dma_out_enabled = 0, -+ .dma_in_enabled = 0 -+#endif -+ -+}, /* ttyS0 */ -+#ifndef CONFIG_SVINTO_SIM -+ { .baud = DEF_BAUD, -+ .ioport = (unsigned char *)R_SERIAL1_CTRL, -+ .irq = 1U << 16, /* uses DMA 8 and 9 */ -+ .oclrintradr = R_DMA_CH8_CLR_INTR, -+ .ofirstadr = R_DMA_CH8_FIRST, -+ .ocmdadr = R_DMA_CH8_CMD, -+ .ostatusadr = R_DMA_CH8_STATUS, -+ .iclrintradr = R_DMA_CH9_CLR_INTR, -+ .ifirstadr = R_DMA_CH9_FIRST, -+ .icmdadr = R_DMA_CH9_CMD, -+ .idescradr = R_DMA_CH9_DESCR, -+ .flags = STD_FLAGS, -+ .rx_ctrl = DEF_RX, -+ .tx_ctrl = DEF_TX, -+ .iseteop = 3, -+ .dma_owner = dma_ser1, -+ .io_if = if_serial_1, -+#ifdef CONFIG_ETRAX_SERIAL_PORT1 -+ .enabled = 1, -+ .io_if_description = "ser1", -+#ifdef CONFIG_ETRAX_SERIAL_PORT1_DMA8_OUT -+ .dma_out_enabled = 1, -+ .dma_out_nbr = SER1_TX_DMA_NBR, -+ .dma_out_irq_nbr = SER1_DMA_TX_IRQ_NBR, -+ .dma_out_irq_flags = IRQF_DISABLED, -+ .dma_out_irq_description = "serial 1 dma tr", -+#else -+ .dma_out_enabled = 0, -+ .dma_out_nbr = UINT_MAX, -+ .dma_out_irq_nbr = 0, -+ .dma_out_irq_flags = 0, -+ .dma_out_irq_description = NULL, -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT1_DMA9_IN -+ .dma_in_enabled = 1, -+ .dma_in_nbr = SER1_RX_DMA_NBR, -+ .dma_in_irq_nbr = SER1_DMA_RX_IRQ_NBR, -+ .dma_in_irq_flags = IRQF_DISABLED, -+ .dma_in_irq_description = "serial 1 dma rec", -+#else -+ .dma_in_enabled = 0, -+ .dma_in_enabled = 0, -+ .dma_in_nbr = UINT_MAX, -+ .dma_in_irq_nbr = 0, -+ .dma_in_irq_flags = 0, -+ .dma_in_irq_description = NULL, -+#endif -+#else -+ .enabled = 0, -+ .io_if_description = NULL, -+ .dma_in_irq_nbr = 0, -+ .dma_out_enabled = 0, -+ .dma_in_enabled = 0 -+#endif -+}, /* ttyS1 */ -+ -+ { .baud = DEF_BAUD, -+ .ioport = (unsigned char *)R_SERIAL2_CTRL, -+ .irq = 1U << 4, /* uses DMA 2 and 3 */ -+ .oclrintradr = R_DMA_CH2_CLR_INTR, -+ .ofirstadr = R_DMA_CH2_FIRST, -+ .ocmdadr = R_DMA_CH2_CMD, -+ .ostatusadr = R_DMA_CH2_STATUS, -+ .iclrintradr = R_DMA_CH3_CLR_INTR, -+ .ifirstadr = R_DMA_CH3_FIRST, -+ .icmdadr = R_DMA_CH3_CMD, -+ .idescradr = R_DMA_CH3_DESCR, -+ .flags = STD_FLAGS, -+ .rx_ctrl = DEF_RX, -+ .tx_ctrl = DEF_TX, -+ .iseteop = 0, -+ .dma_owner = dma_ser2, -+ .io_if = if_serial_2, -+#ifdef CONFIG_ETRAX_SERIAL_PORT2 -+ .enabled = 1, -+ .io_if_description = "ser2", -+#ifdef CONFIG_ETRAX_SERIAL_PORT2_DMA2_OUT -+ .dma_out_enabled = 1, -+ .dma_out_nbr = SER2_TX_DMA_NBR, -+ .dma_out_irq_nbr = SER2_DMA_TX_IRQ_NBR, -+ .dma_out_irq_flags = IRQF_DISABLED, -+ .dma_out_irq_description = "serial 2 dma tr", -+#else -+ .dma_out_enabled = 0, -+ .dma_out_nbr = UINT_MAX, -+ .dma_out_irq_nbr = 0, -+ .dma_out_irq_flags = 0, -+ .dma_out_irq_description = NULL, -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT2_DMA3_IN -+ .dma_in_enabled = 1, -+ .dma_in_nbr = SER2_RX_DMA_NBR, -+ .dma_in_irq_nbr = SER2_DMA_RX_IRQ_NBR, -+ .dma_in_irq_flags = IRQF_DISABLED, -+ .dma_in_irq_description = "serial 2 dma rec", -+#else -+ .dma_in_enabled = 0, -+ .dma_in_nbr = UINT_MAX, -+ .dma_in_irq_nbr = 0, -+ .dma_in_irq_flags = 0, -+ .dma_in_irq_description = NULL, -+#endif -+#else -+ .enabled = 0, -+ .io_if_description = NULL, -+ .dma_out_enabled = 0, -+ .dma_in_enabled = 0 -+#endif -+ }, /* ttyS2 */ -+ -+ { .baud = DEF_BAUD, -+ .ioport = (unsigned char *)R_SERIAL3_CTRL, -+ .irq = 1U << 8, /* uses DMA 4 and 5 */ -+ .oclrintradr = R_DMA_CH4_CLR_INTR, -+ .ofirstadr = R_DMA_CH4_FIRST, -+ .ocmdadr = R_DMA_CH4_CMD, -+ .ostatusadr = R_DMA_CH4_STATUS, -+ .iclrintradr = R_DMA_CH5_CLR_INTR, -+ .ifirstadr = R_DMA_CH5_FIRST, -+ .icmdadr = R_DMA_CH5_CMD, -+ .idescradr = R_DMA_CH5_DESCR, -+ .flags = STD_FLAGS, -+ .rx_ctrl = DEF_RX, -+ .tx_ctrl = DEF_TX, -+ .iseteop = 1, -+ .dma_owner = dma_ser3, -+ .io_if = if_serial_3, -+#ifdef CONFIG_ETRAX_SERIAL_PORT3 -+ .enabled = 1, -+ .io_if_description = "ser3", -+#ifdef CONFIG_ETRAX_SERIAL_PORT3_DMA4_OUT -+ .dma_out_enabled = 1, -+ .dma_out_nbr = SER3_TX_DMA_NBR, -+ .dma_out_irq_nbr = SER3_DMA_TX_IRQ_NBR, -+ .dma_out_irq_flags = IRQF_DISABLED, -+ .dma_out_irq_description = "serial 3 dma tr", -+#else -+ .dma_out_enabled = 0, -+ .dma_out_nbr = UINT_MAX, -+ .dma_out_irq_nbr = 0, -+ .dma_out_irq_flags = 0, -+ .dma_out_irq_description = NULL, -+#endif -+#ifdef CONFIG_ETRAX_SERIAL_PORT3_DMA5_IN -+ .dma_in_enabled = 1, -+ .dma_in_nbr = SER3_RX_DMA_NBR, -+ .dma_in_irq_nbr = SER3_DMA_RX_IRQ_NBR, -+ .dma_in_irq_flags = IRQF_DISABLED, -+ .dma_in_irq_description = "serial 3 dma rec", -+#else -+ .dma_in_enabled = 0, -+ .dma_in_nbr = UINT_MAX, -+ .dma_in_irq_nbr = 0, -+ .dma_in_irq_flags = 0, -+ .dma_in_irq_description = NULL -+#endif -+#else -+ .enabled = 0, -+ .io_if_description = NULL, -+ .dma_out_enabled = 0, -+ .dma_in_enabled = 0 -+#endif -+ } /* ttyS3 */ -+#endif -+}; -+ -+ -+#define NR_PORTS (sizeof(rs_table)/sizeof(struct e100_serial)) -+ -+#ifdef CONFIG_ETRAX_SERIAL_FAST_TIMER -+static struct fast_timer fast_timers[NR_PORTS]; -+#endif -+ -+#ifdef CONFIG_ETRAX_SERIAL_PROC_ENTRY -+#define PROCSTAT(x) x -+struct ser_statistics_type { -+ int overrun_cnt; -+ int early_errors_cnt; -+ int ser_ints_ok_cnt; -+ int errors_cnt; -+ unsigned long int processing_flip; -+ unsigned long processing_flip_still_room; -+ unsigned long int timeout_flush_cnt; -+ int rx_dma_ints; -+ int tx_dma_ints; -+ int rx_tot; -+ int tx_tot; -+}; -+ -+static struct ser_statistics_type ser_stat[NR_PORTS]; -+ -+#else -+ -+#define PROCSTAT(x) -+ -+#endif /* CONFIG_ETRAX_SERIAL_PROC_ENTRY */ -+ -+/* RS-485 */ -+#if defined(CONFIG_ETRAX_RS485) -+#ifdef CONFIG_ETRAX_FAST_TIMER -+static struct fast_timer fast_timers_rs485[NR_PORTS]; -+#endif -+#if defined(CONFIG_ETRAX_RS485_ON_PA) -+static int rs485_pa_bit = CONFIG_ETRAX_RS485_ON_PA_BIT; -+#endif -+#if defined(CONFIG_ETRAX_RS485_ON_PORT_G) -+static int rs485_port_g_bit = CONFIG_ETRAX_RS485_ON_PORT_G_BIT; -+#endif -+#endif -+ -+/* Info and macros needed for each ports extra control/status signals. */ -+#define E100_STRUCT_PORT(line, pinname) \ -+ ((CONFIG_ETRAX_SER##line##_##pinname##_ON_PA_BIT >= 0)? \ -+ (R_PORT_PA_DATA): ( \ -+ (CONFIG_ETRAX_SER##line##_##pinname##_ON_PB_BIT >= 0)? \ -+ (R_PORT_PB_DATA):&dummy_ser[line])) -+ -+#define E100_STRUCT_SHADOW(line, pinname) \ -+ ((CONFIG_ETRAX_SER##line##_##pinname##_ON_PA_BIT >= 0)? \ -+ (&port_pa_data_shadow): ( \ -+ (CONFIG_ETRAX_SER##line##_##pinname##_ON_PB_BIT >= 0)? \ -+ (&port_pb_data_shadow):&dummy_ser[line])) -+#define E100_STRUCT_MASK(line, pinname) \ -+ ((CONFIG_ETRAX_SER##line##_##pinname##_ON_PA_BIT >= 0)? \ -+ (1<= 0)? \ -+ (1< 3.3V to RS-232 driver -> -12V on RS-232 level -+ * inactive = 1 -> 0V to RS-232 driver -> +12V on RS-232 level -+ * -+ * These macros returns the pin value: 0=0V, >=1 = 3.3V on ETRAX chip -+ */ -+ -+/* Output */ -+#define E100_RTS_GET(info) ((info)->rx_ctrl & E100_RTS_MASK) -+/* Input */ -+#define E100_CTS_GET(info) ((info)->ioport[REG_STATUS] & E100_CTS_MASK) -+ -+/* These are typically PA or PB and 0 means 0V, 1 means 3.3V */ -+/* Is an output */ -+#define E100_DTR_GET(info) ((*e100_modem_pins[(info)->line].dtr_shadow) & e100_modem_pins[(info)->line].dtr_mask) -+ -+/* Normally inputs */ -+#define E100_RI_GET(info) ((*e100_modem_pins[(info)->line].ri_port) & e100_modem_pins[(info)->line].ri_mask) -+#define E100_CD_GET(info) ((*e100_modem_pins[(info)->line].cd_port) & e100_modem_pins[(info)->line].cd_mask) -+ -+/* Input */ -+#define E100_DSR_GET(info) ((*e100_modem_pins[(info)->line].dsr_port) & e100_modem_pins[(info)->line].dsr_mask) -+ -+ -+/* -+ * tmp_buf is used as a temporary buffer by serial_write. We need to -+ * lock it in case the memcpy_fromfs blocks while swapping in a page, -+ * and some other program tries to do a serial write at the same time. -+ * Since the lock will only come under contention when the system is -+ * swapping and available memory is low, it makes sense to share one -+ * buffer across all the serial ports, since it significantly saves -+ * memory if large numbers of serial ports are open. -+ */ -+static unsigned char *tmp_buf; -+static DEFINE_MUTEX(tmp_buf_mutex); -+ -+/* Calculate the chartime depending on baudrate, numbor of bits etc. */ -+static void update_char_time(struct e100_serial * info) -+{ -+ tcflag_t cflags = info->port.tty->termios->c_cflag; -+ int bits; -+ -+ /* calc. number of bits / data byte */ -+ /* databits + startbit and 1 stopbit */ -+ if ((cflags & CSIZE) == CS7) -+ bits = 9; -+ else -+ bits = 10; -+ -+ if (cflags & CSTOPB) /* 2 stopbits ? */ -+ bits++; -+ -+ if (cflags & PARENB) /* parity bit ? */ -+ bits++; -+ -+ /* calc timeout */ -+ info->char_time_usec = ((bits * 1000000) / info->baud) + 1; -+ info->flush_time_usec = 4*info->char_time_usec; -+ if (info->flush_time_usec < MIN_FLUSH_TIME_USEC) -+ info->flush_time_usec = MIN_FLUSH_TIME_USEC; -+ -+} -+ -+/* -+ * This function maps from the Bxxxx defines in asm/termbits.h into real -+ * baud rates. -+ */ -+ -+static int -+cflag_to_baud(unsigned int cflag) -+{ -+ static int baud_table[] = { -+ 0, 50, 75, 110, 134, 150, 200, 300, 600, 1200, 1800, 2400, -+ 4800, 9600, 19200, 38400 }; -+ -+ static int ext_baud_table[] = { -+ 0, 57600, 115200, 230400, 460800, 921600, 1843200, 6250000, -+ 0, 0, 0, 0, 0, 0, 0, 0 }; -+ -+ if (cflag & CBAUDEX) -+ return ext_baud_table[(cflag & CBAUD) & ~CBAUDEX]; -+ else -+ return baud_table[cflag & CBAUD]; -+} -+ -+/* and this maps to an etrax100 hardware baud constant */ -+ -+static unsigned char -+cflag_to_etrax_baud(unsigned int cflag) -+{ -+ char retval; -+ -+ static char baud_table[] = { -+ -1, -1, -1, -1, -1, -1, -1, 0, 1, 2, -1, 3, 4, 5, 6, 7 }; -+ -+ static char ext_baud_table[] = { -+ -1, 8, 9, 10, 11, 12, 13, 14, -1, -1, -1, -1, -1, -1, -1, -1 }; -+ -+ if (cflag & CBAUDEX) -+ retval = ext_baud_table[(cflag & CBAUD) & ~CBAUDEX]; -+ else -+ retval = baud_table[cflag & CBAUD]; -+ -+ if (retval < 0) { -+ printk(KERN_WARNING "serdriver tried setting invalid baud rate, flags %x.\n", cflag); -+ retval = 5; /* choose default 9600 instead */ -+ } -+ -+ return retval | (retval << 4); /* choose same for both TX and RX */ -+} -+ -+ -+/* Various static support functions */ -+ -+/* Functions to set or clear DTR/RTS on the requested line */ -+/* It is complicated by the fact that RTS is a serial port register, while -+ * DTR might not be implemented in the HW at all, and if it is, it can be on -+ * any general port. -+ */ -+ -+ -+static inline void -+e100_dtr(struct e100_serial *info, int set) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ unsigned char mask = e100_modem_pins[info->line].dtr_mask; -+ -+#ifdef SERIAL_DEBUG_IO -+ printk("ser%i dtr %i mask: 0x%02X\n", info->line, set, mask); -+ printk("ser%i shadow before 0x%02X get: %i\n", -+ info->line, *e100_modem_pins[info->line].dtr_shadow, -+ E100_DTR_GET(info)); -+#endif -+ /* DTR is active low */ -+ { -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ *e100_modem_pins[info->line].dtr_shadow &= ~mask; -+ *e100_modem_pins[info->line].dtr_shadow |= (set ? 0 : mask); -+ *e100_modem_pins[info->line].dtr_port = *e100_modem_pins[info->line].dtr_shadow; -+ local_irq_restore(flags); -+ } -+ -+#ifdef SERIAL_DEBUG_IO -+ printk("ser%i shadow after 0x%02X get: %i\n", -+ info->line, *e100_modem_pins[info->line].dtr_shadow, -+ E100_DTR_GET(info)); -+#endif -+#endif -+} -+ -+/* set = 0 means 3.3V on the pin, bitvalue: 0=active, 1=inactive -+ * 0=0V , 1=3.3V -+ */ -+static inline void -+e100_rts(struct e100_serial *info, int set) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ unsigned long flags; -+ local_irq_save(flags); -+ info->rx_ctrl &= ~E100_RTS_MASK; -+ info->rx_ctrl |= (set ? 0 : E100_RTS_MASK); /* RTS is active low */ -+ info->ioport[REG_REC_CTRL] = info->rx_ctrl; -+ local_irq_restore(flags); -+#ifdef SERIAL_DEBUG_IO -+ printk("ser%i rts %i\n", info->line, set); -+#endif -+#endif -+} -+ -+ -+/* If this behaves as a modem, RI and CD is an output */ -+static inline void -+e100_ri_out(struct e100_serial *info, int set) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ /* RI is active low */ -+ { -+ unsigned char mask = e100_modem_pins[info->line].ri_mask; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ *e100_modem_pins[info->line].ri_shadow &= ~mask; -+ *e100_modem_pins[info->line].ri_shadow |= (set ? 0 : mask); -+ *e100_modem_pins[info->line].ri_port = *e100_modem_pins[info->line].ri_shadow; -+ local_irq_restore(flags); -+ } -+#endif -+} -+static inline void -+e100_cd_out(struct e100_serial *info, int set) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ /* CD is active low */ -+ { -+ unsigned char mask = e100_modem_pins[info->line].cd_mask; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ *e100_modem_pins[info->line].cd_shadow &= ~mask; -+ *e100_modem_pins[info->line].cd_shadow |= (set ? 0 : mask); -+ *e100_modem_pins[info->line].cd_port = *e100_modem_pins[info->line].cd_shadow; -+ local_irq_restore(flags); -+ } -+#endif -+} -+ -+static inline void -+e100_disable_rx(struct e100_serial *info) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ /* disable the receiver */ -+ info->ioport[REG_REC_CTRL] = -+ (info->rx_ctrl &= ~IO_MASK(R_SERIAL0_REC_CTRL, rec_enable)); -+#endif -+} -+ -+static inline void -+e100_enable_rx(struct e100_serial *info) -+{ -+#ifndef CONFIG_SVINTO_SIM -+ /* enable the receiver */ -+ info->ioport[REG_REC_CTRL] = -+ (info->rx_ctrl |= IO_MASK(R_SERIAL0_REC_CTRL, rec_enable)); -+#endif -+} -+ -+/* the rx DMA uses both the dma_descr and the dma_eop interrupts */ -+ -+static inline void -+e100_disable_rxdma_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("rxdma_irq(%d): 0\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ disable_rxdma_irq %i\n", info->line)); -+ *R_IRQ_MASK2_CLR = (info->irq << 2) | (info->irq << 3); -+} -+ -+static inline void -+e100_enable_rxdma_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("rxdma_irq(%d): 1\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ enable_rxdma_irq %i\n", info->line)); -+ *R_IRQ_MASK2_SET = (info->irq << 2) | (info->irq << 3); -+} -+ -+/* the tx DMA uses only dma_descr interrupt */ -+ -+static void e100_disable_txdma_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("txdma_irq(%d): 0\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ disable_txdma_irq %i\n", info->line)); -+ *R_IRQ_MASK2_CLR = info->irq; -+} -+ -+static void e100_enable_txdma_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("txdma_irq(%d): 1\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ enable_txdma_irq %i\n", info->line)); -+ *R_IRQ_MASK2_SET = info->irq; -+} -+ -+static void e100_disable_txdma_channel(struct e100_serial *info) -+{ -+ unsigned long flags; -+ -+ /* Disable output DMA channel for the serial port in question -+ * ( set to something other than serialX) -+ */ -+ local_irq_save(flags); -+ DFLOW(DEBUG_LOG(info->line, "disable_txdma_channel %i\n", info->line)); -+ if (info->line == 0) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma6)) == -+ IO_STATE(R_GEN_CONFIG, dma6, serial0)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma6); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma6, unused); -+ } -+ } else if (info->line == 1) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma8)) == -+ IO_STATE(R_GEN_CONFIG, dma8, serial1)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma8); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma8, usb); -+ } -+ } else if (info->line == 2) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma2)) == -+ IO_STATE(R_GEN_CONFIG, dma2, serial2)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma2); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma2, par0); -+ } -+ } else if (info->line == 3) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma4)) == -+ IO_STATE(R_GEN_CONFIG, dma4, serial3)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma4); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma4, par1); -+ } -+ } -+ *R_GEN_CONFIG = genconfig_shadow; -+ local_irq_restore(flags); -+} -+ -+ -+static void e100_enable_txdma_channel(struct e100_serial *info) -+{ -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ DFLOW(DEBUG_LOG(info->line, "enable_txdma_channel %i\n", info->line)); -+ /* Enable output DMA channel for the serial port in question */ -+ if (info->line == 0) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma6); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma6, serial0); -+ } else if (info->line == 1) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma8); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma8, serial1); -+ } else if (info->line == 2) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma2); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma2, serial2); -+ } else if (info->line == 3) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma4); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma4, serial3); -+ } -+ *R_GEN_CONFIG = genconfig_shadow; -+ local_irq_restore(flags); -+} -+ -+static void e100_disable_rxdma_channel(struct e100_serial *info) -+{ -+ unsigned long flags; -+ -+ /* Disable input DMA channel for the serial port in question -+ * ( set to something other than serialX) -+ */ -+ local_irq_save(flags); -+ if (info->line == 0) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma7)) == -+ IO_STATE(R_GEN_CONFIG, dma7, serial0)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma7); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma7, unused); -+ } -+ } else if (info->line == 1) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma9)) == -+ IO_STATE(R_GEN_CONFIG, dma9, serial1)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma9); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma9, usb); -+ } -+ } else if (info->line == 2) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma3)) == -+ IO_STATE(R_GEN_CONFIG, dma3, serial2)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma3); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma3, par0); -+ } -+ } else if (info->line == 3) { -+ if ((genconfig_shadow & IO_MASK(R_GEN_CONFIG, dma5)) == -+ IO_STATE(R_GEN_CONFIG, dma5, serial3)) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma5); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma5, par1); -+ } -+ } -+ *R_GEN_CONFIG = genconfig_shadow; -+ local_irq_restore(flags); -+} -+ -+ -+static void e100_enable_rxdma_channel(struct e100_serial *info) -+{ -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ /* Enable input DMA channel for the serial port in question */ -+ if (info->line == 0) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma7); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma7, serial0); -+ } else if (info->line == 1) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma9); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma9, serial1); -+ } else if (info->line == 2) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma3); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma3, serial2); -+ } else if (info->line == 3) { -+ genconfig_shadow &= ~IO_MASK(R_GEN_CONFIG, dma5); -+ genconfig_shadow |= IO_STATE(R_GEN_CONFIG, dma5, serial3); -+ } -+ *R_GEN_CONFIG = genconfig_shadow; -+ local_irq_restore(flags); -+} -+ -+#ifdef SERIAL_HANDLE_EARLY_ERRORS -+/* in order to detect and fix errors on the first byte -+ we have to use the serial interrupts as well. */ -+ -+static inline void -+e100_disable_serial_data_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("ser_irq(%d): 0\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ disable data_irq %i\n", info->line)); -+ *R_IRQ_MASK1_CLR = (1U << (8+2*info->line)); -+} -+ -+static inline void -+e100_enable_serial_data_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("ser_irq(%d): 1\n",info->line); -+ printk("**** %d = %d\n", -+ (8+2*info->line), -+ (1U << (8+2*info->line))); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ enable data_irq %i\n", info->line)); -+ *R_IRQ_MASK1_SET = (1U << (8+2*info->line)); -+} -+#endif -+ -+static inline void -+e100_disable_serial_tx_ready_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("ser_tx_irq(%d): 0\n",info->line); -+#endif -+ DINTR1(DEBUG_LOG(info->line,"IRQ disable ready_irq %i\n", info->line)); -+ *R_IRQ_MASK1_CLR = (1U << (8+1+2*info->line)); -+} -+ -+static inline void -+e100_enable_serial_tx_ready_irq(struct e100_serial *info) -+{ -+#ifdef SERIAL_DEBUG_INTR -+ printk("ser_tx_irq(%d): 1\n",info->line); -+ printk("**** %d = %d\n", -+ (8+1+2*info->line), -+ (1U << (8+1+2*info->line))); -+#endif -+ DINTR2(DEBUG_LOG(info->line,"IRQ enable ready_irq %i\n", info->line)); -+ *R_IRQ_MASK1_SET = (1U << (8+1+2*info->line)); -+} -+ -+static inline void e100_enable_rx_irq(struct e100_serial *info) -+{ -+ if (info->uses_dma_in) -+ e100_enable_rxdma_irq(info); -+ else -+ e100_enable_serial_data_irq(info); -+} -+static inline void e100_disable_rx_irq(struct e100_serial *info) -+{ -+ if (info->uses_dma_in) -+ e100_disable_rxdma_irq(info); -+ else -+ e100_disable_serial_data_irq(info); -+} -+ -+#if defined(CONFIG_ETRAX_RS485) -+/* Enable RS-485 mode on selected port. This is UGLY. */ -+static int -+e100_enable_rs485(struct tty_struct *tty, struct serial_rs485 *r) -+{ -+ struct e100_serial * info = (struct e100_serial *)tty->driver_data; -+ -+#if defined(CONFIG_ETRAX_RS485_ON_PA) -+ *R_PORT_PA_DATA = port_pa_data_shadow |= (1 << rs485_pa_bit); -+#endif -+#if defined(CONFIG_ETRAX_RS485_ON_PORT_G) -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ rs485_port_g_bit, 1); -+#endif -+#if defined(CONFIG_ETRAX_RS485_LTC1387) -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ CONFIG_ETRAX_RS485_LTC1387_DXEN_PORT_G_BIT, 1); -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ CONFIG_ETRAX_RS485_LTC1387_RXEN_PORT_G_BIT, 1); -+#endif -+ -+ info->rs485 = *r; -+ -+ /* Maximum delay before RTS equal to 1000 */ -+ if (info->rs485.delay_rts_before_send >= 1000) -+ info->rs485.delay_rts_before_send = 1000; -+ -+/* printk("rts: on send = %i, after = %i, enabled = %i", -+ info->rs485.rts_on_send, -+ info->rs485.rts_after_sent, -+ info->rs485.enabled -+ ); -+*/ -+ return 0; -+} -+ -+static int -+e100_write_rs485(struct tty_struct *tty, -+ const unsigned char *buf, int count) -+{ -+ struct e100_serial * info = (struct e100_serial *)tty->driver_data; -+ int old_value = (info->rs485.flags) & SER_RS485_ENABLED; -+ -+ /* rs485 is always implicitly enabled if we're using the ioctl() -+ * but it doesn't have to be set in the serial_rs485 -+ * (to be backward compatible with old apps) -+ * So we store, set and restore it. -+ */ -+ info->rs485.flags |= SER_RS485_ENABLED; -+ /* rs_write now deals with RS485 if enabled */ -+ count = rs_write(tty, buf, count); -+ if (!old_value) -+ info->rs485.flags &= ~(SER_RS485_ENABLED); -+ return count; -+} -+ -+#ifdef CONFIG_ETRAX_FAST_TIMER -+/* Timer function to toggle RTS when using FAST_TIMER */ -+static void rs485_toggle_rts_timer_function(unsigned long data) -+{ -+ struct e100_serial *info = (struct e100_serial *)data; -+ -+ fast_timers_rs485[info->line].function = NULL; -+ e100_rts(info, (info->rs485.flags & SER_RS485_RTS_AFTER_SEND)); -+#if defined(CONFIG_ETRAX_RS485_DISABLE_RECEIVER) -+ e100_enable_rx(info); -+ e100_enable_rx_irq(info); -+#endif -+} -+#endif -+#endif /* CONFIG_ETRAX_RS485 */ -+ -+/* -+ * ------------------------------------------------------------ -+ * rs_stop() and rs_start() -+ * -+ * This routines are called before setting or resetting tty->stopped. -+ * They enable or disable transmitter using the XOFF registers, as necessary. -+ * ------------------------------------------------------------ -+ */ -+ -+static void -+rs_stop(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ if (info) { -+ unsigned long flags; -+ unsigned long xoff; -+ -+ local_irq_save(flags); -+ DFLOW(DEBUG_LOG(info->line, "XOFF rs_stop xmit %i\n", -+ CIRC_CNT(info->xmit.head, -+ info->xmit.tail,SERIAL_XMIT_SIZE))); -+ -+ xoff = IO_FIELD(R_SERIAL0_XOFF, xoff_char, -+ STOP_CHAR(info->port.tty)); -+ xoff |= IO_STATE(R_SERIAL0_XOFF, tx_stop, stop); -+ if (tty->termios->c_iflag & IXON ) { -+ xoff |= IO_STATE(R_SERIAL0_XOFF, auto_xoff, enable); -+ } -+ -+ *((unsigned long *)&info->ioport[REG_XOFF]) = xoff; -+ local_irq_restore(flags); -+ } -+} -+ -+static void -+rs_start(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ if (info) { -+ unsigned long flags; -+ unsigned long xoff; -+ -+ local_irq_save(flags); -+ DFLOW(DEBUG_LOG(info->line, "XOFF rs_start xmit %i\n", -+ CIRC_CNT(info->xmit.head, -+ info->xmit.tail,SERIAL_XMIT_SIZE))); -+ xoff = IO_FIELD(R_SERIAL0_XOFF, xoff_char, STOP_CHAR(tty)); -+ xoff |= IO_STATE(R_SERIAL0_XOFF, tx_stop, enable); -+ if (tty->termios->c_iflag & IXON ) { -+ xoff |= IO_STATE(R_SERIAL0_XOFF, auto_xoff, enable); -+ } -+ -+ *((unsigned long *)&info->ioport[REG_XOFF]) = xoff; -+ if (!info->uses_dma_out && -+ info->xmit.head != info->xmit.tail && info->xmit.buf) -+ e100_enable_serial_tx_ready_irq(info); -+ -+ local_irq_restore(flags); -+ } -+} -+ -+/* -+ * ---------------------------------------------------------------------- -+ * -+ * Here starts the interrupt handling routines. All of the following -+ * subroutines are declared as inline and are folded into -+ * rs_interrupt(). They were separated out for readability's sake. -+ * -+ * Note: rs_interrupt() is a "fast" interrupt, which means that it -+ * runs with interrupts turned off. People who may want to modify -+ * rs_interrupt() should try to keep the interrupt handler as fast as -+ * possible. After you are done making modifications, it is not a bad -+ * idea to do: -+ * -+ * gcc -S -DKERNEL -Wall -Wstrict-prototypes -O6 -fomit-frame-pointer serial.c -+ * -+ * and look at the resulting assemble code in serial.s. -+ * -+ * - Ted Ts'o (tytso@mit.edu), 7-Mar-93 -+ * ----------------------------------------------------------------------- -+ */ -+ -+/* -+ * This routine is used by the interrupt handler to schedule -+ * processing in the software interrupt portion of the driver. -+ */ -+static void rs_sched_event(struct e100_serial *info, int event) -+{ -+ if (info->event & (1 << event)) -+ return; -+ info->event |= 1 << event; -+ schedule_work(&info->work); -+} -+ -+/* The output DMA channel is free - use it to send as many chars as possible -+ * NOTES: -+ * We don't pay attention to info->x_char, which means if the TTY wants to -+ * use XON/XOFF it will set info->x_char but we won't send any X char! -+ * -+ * To implement this, we'd just start a DMA send of 1 byte pointing at a -+ * buffer containing the X char, and skip updating xmit. We'd also have to -+ * check if the last sent char was the X char when we enter this function -+ * the next time, to avoid updating xmit with the sent X value. -+ */ -+ -+static void -+transmit_chars_dma(struct e100_serial *info) -+{ -+ unsigned int c, sentl; -+ struct etrax_dma_descr *descr; -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* This will output too little if tail is not 0 always since -+ * we don't reloop to send the other part. Anyway this SHOULD be a -+ * no-op - transmit_chars_dma would never really be called during sim -+ * since rs_write does not write into the xmit buffer then. -+ */ -+ if (info->xmit.tail) -+ printk("Error in serial.c:transmit_chars-dma(), tail!=0\n"); -+ if (info->xmit.head != info->xmit.tail) { -+ SIMCOUT(info->xmit.buf + info->xmit.tail, -+ CIRC_CNT(info->xmit.head, -+ info->xmit.tail, -+ SERIAL_XMIT_SIZE)); -+ info->xmit.head = info->xmit.tail; /* move back head */ -+ info->tr_running = 0; -+ } -+ return; -+#endif -+ /* acknowledge both dma_descr and dma_eop irq in R_DMA_CHx_CLR_INTR */ -+ *info->oclrintradr = -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_descr, do) | -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_eop, do); -+ -+#ifdef SERIAL_DEBUG_INTR -+ if (info->line == SERIAL_DEBUG_LINE) -+ printk("tc\n"); -+#endif -+ if (!info->tr_running) { -+ /* weirdo... we shouldn't get here! */ -+ printk(KERN_WARNING "Achtung: transmit_chars_dma with !tr_running\n"); -+ return; -+ } -+ -+ descr = &info->tr_descr; -+ -+ /* first get the amount of bytes sent during the last DMA transfer, -+ and update xmit accordingly */ -+ -+ /* if the stop bit was not set, all data has been sent */ -+ if (!(descr->status & d_stop)) { -+ sentl = descr->sw_len; -+ } else -+ /* otherwise we find the amount of data sent here */ -+ sentl = descr->hw_len; -+ -+ DFLOW(DEBUG_LOG(info->line, "TX %i done\n", sentl)); -+ -+ /* update stats */ -+ info->icount.tx += sentl; -+ -+ /* update xmit buffer */ -+ info->xmit.tail = (info->xmit.tail + sentl) & (SERIAL_XMIT_SIZE - 1); -+ -+ /* if there is only a few chars left in the buf, wake up the blocked -+ write if any */ -+ if (CIRC_CNT(info->xmit.head, -+ info->xmit.tail, -+ SERIAL_XMIT_SIZE) < WAKEUP_CHARS) -+ rs_sched_event(info, RS_EVENT_WRITE_WAKEUP); -+ -+ /* find out the largest amount of consecutive bytes we want to send now */ -+ -+ c = CIRC_CNT_TO_END(info->xmit.head, info->xmit.tail, SERIAL_XMIT_SIZE); -+ -+ /* Don't send all in one DMA transfer - divide it so we wake up -+ * application before all is sent -+ */ -+ -+ if (c >= 4*WAKEUP_CHARS) -+ c = c/2; -+ -+ if (c <= 0) { -+ /* our job here is done, don't schedule any new DMA transfer */ -+ info->tr_running = 0; -+ -+#if defined(CONFIG_ETRAX_RS485) && defined(CONFIG_ETRAX_FAST_TIMER) -+ if (info->rs485.flags & SER_RS485_ENABLED) { -+ /* Set a short timer to toggle RTS */ -+ start_one_shot_timer(&fast_timers_rs485[info->line], -+ rs485_toggle_rts_timer_function, -+ (unsigned long)info, -+ info->char_time_usec*2, -+ "RS-485"); -+ } -+#endif /* RS485 */ -+ return; -+ } -+ -+ /* ok we can schedule a dma send of c chars starting at info->xmit.tail */ -+ /* set up the descriptor correctly for output */ -+ DFLOW(DEBUG_LOG(info->line, "TX %i\n", c)); -+ descr->ctrl = d_int | d_eol | d_wait; /* Wait needed for tty_wait_until_sent() */ -+ descr->sw_len = c; -+ descr->buf = virt_to_phys(info->xmit.buf + info->xmit.tail); -+ descr->status = 0; -+ -+ *info->ofirstadr = virt_to_phys(descr); /* write to R_DMAx_FIRST */ -+ *info->ocmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, start); -+ -+ /* DMA is now running (hopefully) */ -+} /* transmit_chars_dma */ -+ -+static void -+start_transmit(struct e100_serial *info) -+{ -+#if 0 -+ if (info->line == SERIAL_DEBUG_LINE) -+ printk("x\n"); -+#endif -+ -+ info->tr_descr.sw_len = 0; -+ info->tr_descr.hw_len = 0; -+ info->tr_descr.status = 0; -+ info->tr_running = 1; -+ if (info->uses_dma_out) -+ transmit_chars_dma(info); -+ else -+ e100_enable_serial_tx_ready_irq(info); -+} /* start_transmit */ -+ -+#ifdef CONFIG_ETRAX_SERIAL_FAST_TIMER -+static int serial_fast_timer_started = 0; -+static int serial_fast_timer_expired = 0; -+static void flush_timeout_function(unsigned long data); -+#define START_FLUSH_FAST_TIMER_TIME(info, string, usec) {\ -+ unsigned long timer_flags; \ -+ local_irq_save(timer_flags); \ -+ if (fast_timers[info->line].function == NULL) { \ -+ serial_fast_timer_started++; \ -+ TIMERD(DEBUG_LOG(info->line, "start_timer %i ", info->line)); \ -+ TIMERD(DEBUG_LOG(info->line, "num started: %i\n", serial_fast_timer_started)); \ -+ start_one_shot_timer(&fast_timers[info->line], \ -+ flush_timeout_function, \ -+ (unsigned long)info, \ -+ (usec), \ -+ string); \ -+ } \ -+ else { \ -+ TIMERD(DEBUG_LOG(info->line, "timer %i already running\n", info->line)); \ -+ } \ -+ local_irq_restore(timer_flags); \ -+} -+#define START_FLUSH_FAST_TIMER(info, string) START_FLUSH_FAST_TIMER_TIME(info, string, info->flush_time_usec) -+ -+#else -+#define START_FLUSH_FAST_TIMER_TIME(info, string, usec) -+#define START_FLUSH_FAST_TIMER(info, string) -+#endif -+ -+static struct etrax_recv_buffer * -+alloc_recv_buffer(unsigned int size) -+{ -+ struct etrax_recv_buffer *buffer; -+ -+ if (!(buffer = kmalloc(sizeof *buffer + size, GFP_ATOMIC))) -+ return NULL; -+ -+ buffer->next = NULL; -+ buffer->length = 0; -+ buffer->error = TTY_NORMAL; -+ -+ return buffer; -+} -+ -+static void -+append_recv_buffer(struct e100_serial *info, struct etrax_recv_buffer *buffer) -+{ -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ -+ if (!info->first_recv_buffer) -+ info->first_recv_buffer = buffer; -+ else -+ info->last_recv_buffer->next = buffer; -+ -+ info->last_recv_buffer = buffer; -+ -+ info->recv_cnt += buffer->length; -+ if (info->recv_cnt > info->max_recv_cnt) -+ info->max_recv_cnt = info->recv_cnt; -+ -+ local_irq_restore(flags); -+} -+ -+static int -+add_char_and_flag(struct e100_serial *info, unsigned char data, unsigned char flag) -+{ -+ struct etrax_recv_buffer *buffer; -+ if (info->uses_dma_in) { -+ if (!(buffer = alloc_recv_buffer(4))) -+ return 0; -+ -+ buffer->length = 1; -+ buffer->error = flag; -+ buffer->buffer[0] = data; -+ -+ append_recv_buffer(info, buffer); -+ -+ info->icount.rx++; -+ } else { -+ struct tty_struct *tty = info->port.tty; -+ tty_insert_flip_char(tty, data, flag); -+ info->icount.rx++; -+ } -+ -+ return 1; -+} -+ -+static unsigned int handle_descr_data(struct e100_serial *info, -+ struct etrax_dma_descr *descr, -+ unsigned int recvl) -+{ -+ struct etrax_recv_buffer *buffer = phys_to_virt(descr->buf) - sizeof *buffer; -+ -+ if (info->recv_cnt + recvl > 65536) { -+ printk(KERN_CRIT -+ "%s: Too much pending incoming serial data! Dropping %u bytes.\n", __func__, recvl); -+ return 0; -+ } -+ -+ buffer->length = recvl; -+ -+ if (info->errorcode == ERRCODE_SET_BREAK) -+ buffer->error = TTY_BREAK; -+ info->errorcode = 0; -+ -+ append_recv_buffer(info, buffer); -+ -+ if (!(buffer = alloc_recv_buffer(SERIAL_DESCR_BUF_SIZE))) -+ panic("%s: Failed to allocate memory for receive buffer!\n", __func__); -+ -+ descr->buf = virt_to_phys(buffer->buffer); -+ -+ return recvl; -+} -+ -+static unsigned int handle_all_descr_data(struct e100_serial *info) -+{ -+ struct etrax_dma_descr *descr; -+ unsigned int recvl; -+ unsigned int ret = 0; -+ -+ while (1) -+ { -+ descr = &info->rec_descr[info->cur_rec_descr]; -+ -+ if (descr == phys_to_virt(*info->idescradr)) -+ break; -+ -+ if (++info->cur_rec_descr == SERIAL_RECV_DESCRIPTORS) -+ info->cur_rec_descr = 0; -+ -+ /* find out how many bytes were read */ -+ -+ /* if the eop bit was not set, all data has been received */ -+ if (!(descr->status & d_eop)) { -+ recvl = descr->sw_len; -+ } else { -+ /* otherwise we find the amount of data received here */ -+ recvl = descr->hw_len; -+ } -+ -+ /* Reset the status information */ -+ descr->status = 0; -+ -+ DFLOW( DEBUG_LOG(info->line, "RX %lu\n", recvl); -+ if (info->port.tty->stopped) { -+ unsigned char *buf = phys_to_virt(descr->buf); -+ DEBUG_LOG(info->line, "rx 0x%02X\n", buf[0]); -+ DEBUG_LOG(info->line, "rx 0x%02X\n", buf[1]); -+ DEBUG_LOG(info->line, "rx 0x%02X\n", buf[2]); -+ } -+ ); -+ -+ /* update stats */ -+ info->icount.rx += recvl; -+ -+ ret += handle_descr_data(info, descr, recvl); -+ } -+ -+ return ret; -+} -+ -+static void receive_chars_dma(struct e100_serial *info) -+{ -+ struct tty_struct *tty; -+ unsigned char rstat; -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* No receive in the simulator. Will probably be when the rest of -+ * the serial interface works, and this piece will just be removed. -+ */ -+ return; -+#endif -+ -+ /* Acknowledge both dma_descr and dma_eop irq in R_DMA_CHx_CLR_INTR */ -+ *info->iclrintradr = -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_descr, do) | -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_eop, do); -+ -+ tty = info->port.tty; -+ if (!tty) /* Something wrong... */ -+ return; -+ -+#ifdef SERIAL_HANDLE_EARLY_ERRORS -+ if (info->uses_dma_in) -+ e100_enable_serial_data_irq(info); -+#endif -+ -+ if (info->errorcode == ERRCODE_INSERT_BREAK) -+ add_char_and_flag(info, '\0', TTY_BREAK); -+ -+ handle_all_descr_data(info); -+ -+ /* Read the status register to detect errors */ -+ rstat = info->ioport[REG_STATUS]; -+ if (rstat & IO_MASK(R_SERIAL0_STATUS, xoff_detect) ) { -+ DFLOW(DEBUG_LOG(info->line, "XOFF detect stat %x\n", rstat)); -+ } -+ -+ if (rstat & SER_ERROR_MASK) { -+ /* If we got an error, we must reset it by reading the -+ * data_in field -+ */ -+ unsigned char data = info->ioport[REG_DATA]; -+ -+ PROCSTAT(ser_stat[info->line].errors_cnt++); -+ DEBUG_LOG(info->line, "#dERR: s d 0x%04X\n", -+ ((rstat & SER_ERROR_MASK) << 8) | data); -+ -+ if (rstat & SER_PAR_ERR_MASK) -+ add_char_and_flag(info, data, TTY_PARITY); -+ else if (rstat & SER_OVERRUN_MASK) -+ add_char_and_flag(info, data, TTY_OVERRUN); -+ else if (rstat & SER_FRAMING_ERR_MASK) -+ add_char_and_flag(info, data, TTY_FRAME); -+ } -+ -+ START_FLUSH_FAST_TIMER(info, "receive_chars"); -+ -+ /* Restart the receiving DMA */ -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, restart); -+} -+ -+static int start_recv_dma(struct e100_serial *info) -+{ -+ struct etrax_dma_descr *descr = info->rec_descr; -+ struct etrax_recv_buffer *buffer; -+ int i; -+ -+ /* Set up the receiving descriptors */ -+ for (i = 0; i < SERIAL_RECV_DESCRIPTORS; i++) { -+ if (!(buffer = alloc_recv_buffer(SERIAL_DESCR_BUF_SIZE))) -+ panic("%s: Failed to allocate memory for receive buffer!\n", __func__); -+ -+ descr[i].ctrl = d_int; -+ descr[i].buf = virt_to_phys(buffer->buffer); -+ descr[i].sw_len = SERIAL_DESCR_BUF_SIZE; -+ descr[i].hw_len = 0; -+ descr[i].status = 0; -+ descr[i].next = virt_to_phys(&descr[i+1]); -+ } -+ -+ /* Link the last descriptor to the first */ -+ descr[i-1].next = virt_to_phys(&descr[0]); -+ -+ /* Start with the first descriptor in the list */ -+ info->cur_rec_descr = 0; -+ -+ /* Start the DMA */ -+ *info->ifirstadr = virt_to_phys(&descr[info->cur_rec_descr]); -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, start); -+ -+ /* Input DMA should be running now */ -+ return 1; -+} -+ -+static void -+start_receive(struct e100_serial *info) -+{ -+#ifdef CONFIG_SVINTO_SIM -+ /* No receive in the simulator. Will probably be when the rest of -+ * the serial interface works, and this piece will just be removed. -+ */ -+ return; -+#endif -+ if (info->uses_dma_in) { -+ /* reset the input dma channel to be sure it works */ -+ -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, reset); -+ while (IO_EXTRACT(R_DMA_CH6_CMD, cmd, *info->icmdadr) == -+ IO_STATE_VALUE(R_DMA_CH6_CMD, cmd, reset)); -+ -+ start_recv_dma(info); -+ } -+} -+ -+ -+/* the bits in the MASK2 register are laid out like this: -+ DMAI_EOP DMAI_DESCR DMAO_EOP DMAO_DESCR -+ where I is the input channel and O is the output channel for the port. -+ info->irq is the bit number for the DMAO_DESCR so to check the others we -+ shift info->irq to the left. -+*/ -+ -+/* dma output channel interrupt handler -+ this interrupt is called from DMA2(ser2), DMA4(ser3), DMA6(ser0) or -+ DMA8(ser1) when they have finished a descriptor with the intr flag set. -+*/ -+ -+static irqreturn_t -+tr_interrupt(int irq, void *dev_id) -+{ -+ struct e100_serial *info; -+ unsigned long ireg; -+ int i; -+ int handled = 0; -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* No receive in the simulator. Will probably be when the rest of -+ * the serial interface works, and this piece will just be removed. -+ */ -+ { -+ const char *s = "What? tr_interrupt in simulator??\n"; -+ SIMCOUT(s,strlen(s)); -+ } -+ return IRQ_HANDLED; -+#endif -+ -+ /* find out the line that caused this irq and get it from rs_table */ -+ -+ ireg = *R_IRQ_MASK2_RD; /* get the active irq bits for the dma channels */ -+ -+ for (i = 0; i < NR_PORTS; i++) { -+ info = rs_table + i; -+ if (!info->enabled || !info->uses_dma_out) -+ continue; -+ /* check for dma_descr (don't need to check for dma_eop in output dma for serial */ -+ if (ireg & info->irq) { -+ handled = 1; -+ /* we can send a new dma bunch. make it so. */ -+ DINTR2(DEBUG_LOG(info->line, "tr_interrupt %i\n", i)); -+ /* Read jiffies_usec first, -+ * we want this time to be as late as possible -+ */ -+ PROCSTAT(ser_stat[info->line].tx_dma_ints++); -+ info->last_tx_active_usec = GET_JIFFIES_USEC(); -+ info->last_tx_active = jiffies; -+ transmit_chars_dma(info); -+ } -+ -+ /* FIXME: here we should really check for a change in the -+ status lines and if so call status_handle(info) */ -+ } -+ return IRQ_RETVAL(handled); -+} /* tr_interrupt */ -+ -+/* dma input channel interrupt handler */ -+ -+static irqreturn_t -+rec_interrupt(int irq, void *dev_id) -+{ -+ struct e100_serial *info; -+ unsigned long ireg; -+ int i; -+ int handled = 0; -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* No receive in the simulator. Will probably be when the rest of -+ * the serial interface works, and this piece will just be removed. -+ */ -+ { -+ const char *s = "What? rec_interrupt in simulator??\n"; -+ SIMCOUT(s,strlen(s)); -+ } -+ return IRQ_HANDLED; -+#endif -+ -+ /* find out the line that caused this irq and get it from rs_table */ -+ -+ ireg = *R_IRQ_MASK2_RD; /* get the active irq bits for the dma channels */ -+ -+ for (i = 0; i < NR_PORTS; i++) { -+ info = rs_table + i; -+ if (!info->enabled || !info->uses_dma_in) -+ continue; -+ /* check for both dma_eop and dma_descr for the input dma channel */ -+ if (ireg & ((info->irq << 2) | (info->irq << 3))) { -+ handled = 1; -+ /* we have received something */ -+ receive_chars_dma(info); -+ } -+ -+ /* FIXME: here we should really check for a change in the -+ status lines and if so call status_handle(info) */ -+ } -+ return IRQ_RETVAL(handled); -+} /* rec_interrupt */ -+ -+static int force_eop_if_needed(struct e100_serial *info) -+{ -+ /* We check data_avail bit to determine if data has -+ * arrived since last time -+ */ -+ unsigned char rstat = info->ioport[REG_STATUS]; -+ -+ /* error or datavail? */ -+ if (rstat & SER_ERROR_MASK) { -+ /* Some error has occurred. If there has been valid data, an -+ * EOP interrupt will be made automatically. If no data, the -+ * normal ser_interrupt should be enabled and handle it. -+ * So do nothing! -+ */ -+ DEBUG_LOG(info->line, "timeout err: rstat 0x%03X\n", -+ rstat | (info->line << 8)); -+ return 0; -+ } -+ -+ if (rstat & SER_DATA_AVAIL_MASK) { -+ /* Ok data, no error, count it */ -+ TIMERD(DEBUG_LOG(info->line, "timeout: rstat 0x%03X\n", -+ rstat | (info->line << 8))); -+ /* Read data to clear status flags */ -+ (void)info->ioport[REG_DATA]; -+ -+ info->forced_eop = 0; -+ START_FLUSH_FAST_TIMER(info, "magic"); -+ return 0; -+ } -+ -+ /* hit the timeout, force an EOP for the input -+ * dma channel if we haven't already -+ */ -+ if (!info->forced_eop) { -+ info->forced_eop = 1; -+ PROCSTAT(ser_stat[info->line].timeout_flush_cnt++); -+ TIMERD(DEBUG_LOG(info->line, "timeout EOP %i\n", info->line)); -+ FORCE_EOP(info); -+ } -+ -+ return 1; -+} -+ -+static void flush_to_flip_buffer(struct e100_serial *info) -+{ -+ struct tty_struct *tty; -+ struct etrax_recv_buffer *buffer; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ tty = info->port.tty; -+ -+ if (!tty) { -+ local_irq_restore(flags); -+ return; -+ } -+ -+ while ((buffer = info->first_recv_buffer) != NULL) { -+ unsigned int count = buffer->length; -+ -+ tty_insert_flip_string(tty, buffer->buffer, count); -+ info->recv_cnt -= count; -+ -+ if (count == buffer->length) { -+ info->first_recv_buffer = buffer->next; -+ kfree(buffer); -+ } else { -+ buffer->length -= count; -+ memmove(buffer->buffer, buffer->buffer + count, buffer->length); -+ buffer->error = TTY_NORMAL; -+ } -+ } -+ -+ if (!info->first_recv_buffer) -+ info->last_recv_buffer = NULL; -+ -+ local_irq_restore(flags); -+ -+ /* This includes a check for low-latency */ -+ tty_flip_buffer_push(tty); -+} -+ -+static void check_flush_timeout(struct e100_serial *info) -+{ -+ /* Flip what we've got (if we can) */ -+ flush_to_flip_buffer(info); -+ -+ /* We might need to flip later, but not to fast -+ * since the system is busy processing input... */ -+ if (info->first_recv_buffer) -+ START_FLUSH_FAST_TIMER_TIME(info, "flip", 2000); -+ -+ /* Force eop last, since data might have come while we're processing -+ * and if we started the slow timer above, we won't start a fast -+ * below. -+ */ -+ force_eop_if_needed(info); -+} -+ -+#ifdef CONFIG_ETRAX_SERIAL_FAST_TIMER -+static void flush_timeout_function(unsigned long data) -+{ -+ struct e100_serial *info = (struct e100_serial *)data; -+ -+ fast_timers[info->line].function = NULL; -+ serial_fast_timer_expired++; -+ TIMERD(DEBUG_LOG(info->line, "flush_timout %i ", info->line)); -+ TIMERD(DEBUG_LOG(info->line, "num expired: %i\n", serial_fast_timer_expired)); -+ check_flush_timeout(info); -+} -+ -+#else -+ -+/* dma fifo/buffer timeout handler -+ forces an end-of-packet for the dma input channel if no chars -+ have been received for CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS/100 s. -+*/ -+ -+static struct timer_list flush_timer; -+ -+static void -+timed_flush_handler(unsigned long ptr) -+{ -+ struct e100_serial *info; -+ int i; -+ -+#ifdef CONFIG_SVINTO_SIM -+ return; -+#endif -+ -+ for (i = 0; i < NR_PORTS; i++) { -+ info = rs_table + i; -+ if (info->uses_dma_in) -+ check_flush_timeout(info); -+ } -+ -+ /* restart flush timer */ -+ mod_timer(&flush_timer, jiffies + CONFIG_ETRAX_SERIAL_RX_TIMEOUT_TICKS); -+} -+#endif -+ -+#ifdef SERIAL_HANDLE_EARLY_ERRORS -+ -+/* If there is an error (ie break) when the DMA is running and -+ * there are no bytes in the fifo the DMA is stopped and we get no -+ * eop interrupt. Thus we have to monitor the first bytes on a DMA -+ * transfer, and if it is without error we can turn the serial -+ * interrupts off. -+ */ -+ -+/* -+BREAK handling on ETRAX 100: -+ETRAX will generate interrupt although there is no stop bit between the -+characters. -+ -+Depending on how long the break sequence is, the end of the breaksequence -+will look differently: -+| indicates start/end of a character. -+ -+B= Break character (0x00) with framing error. -+E= Error byte with parity error received after B characters. -+F= "Faked" valid byte received immediately after B characters. -+V= Valid byte -+ -+1. -+ B BL ___________________________ V -+.._|__________|__________| |valid data | -+ -+Multiple frame errors with data == 0x00 (B), -+the timing matches up "perfectly" so no extra ending char is detected. -+The RXD pin is 1 in the last interrupt, in that case -+we set info->errorcode = ERRCODE_INSERT_BREAK, but we can't really -+know if another byte will come and this really is case 2. below -+(e.g F=0xFF or 0xFE) -+If RXD pin is 0 we can expect another character (see 2. below). -+ -+ -+2. -+ -+ B B E or F__________________..__ V -+.._|__________|__________|______ | |valid data -+ "valid" or -+ parity error -+ -+Multiple frame errors with data == 0x00 (B), -+but the part of the break trigs is interpreted as a start bit (and possibly -+some 0 bits followed by a number of 1 bits and a stop bit). -+Depending on parity settings etc. this last character can be either -+a fake "valid" char (F) or have a parity error (E). -+ -+If the character is valid it will be put in the buffer, -+we set info->errorcode = ERRCODE_SET_BREAK so the receive interrupt -+will set the flags so the tty will handle it, -+if it's an error byte it will not be put in the buffer -+and we set info->errorcode = ERRCODE_INSERT_BREAK. -+ -+To distinguish a V byte in 1. from an F byte in 2. we keep a timestamp -+of the last faulty char (B) and compares it with the current time: -+If the time elapsed time is less then 2*char_time_usec we will assume -+it's a faked F char and not a Valid char and set -+info->errorcode = ERRCODE_SET_BREAK. -+ -+Flaws in the above solution: -+~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -+We use the timer to distinguish a F character from a V character, -+if a V character is to close after the break we might make the wrong decision. -+ -+TODO: The break will be delayed until an F or V character is received. -+ -+*/ -+ -+static -+struct e100_serial * handle_ser_rx_interrupt_no_dma(struct e100_serial *info) -+{ -+ unsigned long data_read; -+ struct tty_struct *tty = info->port.tty; -+ -+ if (!tty) { -+ printk("!NO TTY!\n"); -+ return info; -+ } -+ -+ /* Read data and status at the same time */ -+ data_read = *((unsigned long *)&info->ioport[REG_DATA_STATUS32]); -+more_data: -+ if (data_read & IO_MASK(R_SERIAL0_READ, xoff_detect) ) { -+ DFLOW(DEBUG_LOG(info->line, "XOFF detect\n", 0)); -+ } -+ DINTR2(DEBUG_LOG(info->line, "ser_rx %c\n", IO_EXTRACT(R_SERIAL0_READ, data_in, data_read))); -+ -+ if (data_read & ( IO_MASK(R_SERIAL0_READ, framing_err) | -+ IO_MASK(R_SERIAL0_READ, par_err) | -+ IO_MASK(R_SERIAL0_READ, overrun) )) { -+ /* An error */ -+ info->last_rx_active_usec = GET_JIFFIES_USEC(); -+ info->last_rx_active = jiffies; -+ DINTR1(DEBUG_LOG(info->line, "ser_rx err stat_data %04X\n", data_read)); -+ DLOG_INT_TRIG( -+ if (!log_int_trig1_pos) { -+ log_int_trig1_pos = log_int_pos; -+ log_int(rdpc(), 0, 0); -+ } -+ ); -+ -+ -+ if ( ((data_read & IO_MASK(R_SERIAL0_READ, data_in)) == 0) && -+ (data_read & IO_MASK(R_SERIAL0_READ, framing_err)) ) { -+ /* Most likely a break, but we get interrupts over and -+ * over again. -+ */ -+ -+ if (!info->break_detected_cnt) { -+ DEBUG_LOG(info->line, "#BRK start\n", 0); -+ } -+ if (data_read & IO_MASK(R_SERIAL0_READ, rxd)) { -+ /* The RX pin is high now, so the break -+ * must be over, but.... -+ * we can't really know if we will get another -+ * last byte ending the break or not. -+ * And we don't know if the byte (if any) will -+ * have an error or look valid. -+ */ -+ DEBUG_LOG(info->line, "# BL BRK\n", 0); -+ info->errorcode = ERRCODE_INSERT_BREAK; -+ } -+ info->break_detected_cnt++; -+ } else { -+ /* The error does not look like a break, but could be -+ * the end of one -+ */ -+ if (info->break_detected_cnt) { -+ DEBUG_LOG(info->line, "EBRK %i\n", info->break_detected_cnt); -+ info->errorcode = ERRCODE_INSERT_BREAK; -+ } else { -+ unsigned char data = IO_EXTRACT(R_SERIAL0_READ, -+ data_in, data_read); -+ char flag = TTY_NORMAL; -+ if (info->errorcode == ERRCODE_INSERT_BREAK) { -+ struct tty_struct *tty = info->port.tty; -+ tty_insert_flip_char(tty, 0, flag); -+ info->icount.rx++; -+ } -+ -+ if (data_read & IO_MASK(R_SERIAL0_READ, par_err)) { -+ info->icount.parity++; -+ flag = TTY_PARITY; -+ } else if (data_read & IO_MASK(R_SERIAL0_READ, overrun)) { -+ info->icount.overrun++; -+ flag = TTY_OVERRUN; -+ } else if (data_read & IO_MASK(R_SERIAL0_READ, framing_err)) { -+ info->icount.frame++; -+ flag = TTY_FRAME; -+ } -+ tty_insert_flip_char(tty, data, flag); -+ info->errorcode = 0; -+ } -+ info->break_detected_cnt = 0; -+ } -+ } else if (data_read & IO_MASK(R_SERIAL0_READ, data_avail)) { -+ /* No error */ -+ DLOG_INT_TRIG( -+ if (!log_int_trig1_pos) { -+ if (log_int_pos >= log_int_size) { -+ log_int_pos = 0; -+ } -+ log_int_trig0_pos = log_int_pos; -+ log_int(rdpc(), 0, 0); -+ } -+ ); -+ tty_insert_flip_char(tty, -+ IO_EXTRACT(R_SERIAL0_READ, data_in, data_read), -+ TTY_NORMAL); -+ } else { -+ DEBUG_LOG(info->line, "ser_rx int but no data_avail %08lX\n", data_read); -+ } -+ -+ -+ info->icount.rx++; -+ data_read = *((unsigned long *)&info->ioport[REG_DATA_STATUS32]); -+ if (data_read & IO_MASK(R_SERIAL0_READ, data_avail)) { -+ DEBUG_LOG(info->line, "ser_rx %c in loop\n", IO_EXTRACT(R_SERIAL0_READ, data_in, data_read)); -+ goto more_data; -+ } -+ -+ tty_flip_buffer_push(info->port.tty); -+ return info; -+} -+ -+static struct e100_serial* handle_ser_rx_interrupt(struct e100_serial *info) -+{ -+ unsigned char rstat; -+ -+#ifdef SERIAL_DEBUG_INTR -+ printk("Interrupt from serport %d\n", i); -+#endif -+/* DEBUG_LOG(info->line, "ser_interrupt stat %03X\n", rstat | (i << 8)); */ -+ if (!info->uses_dma_in) { -+ return handle_ser_rx_interrupt_no_dma(info); -+ } -+ /* DMA is used */ -+ rstat = info->ioport[REG_STATUS]; -+ if (rstat & IO_MASK(R_SERIAL0_STATUS, xoff_detect) ) { -+ DFLOW(DEBUG_LOG(info->line, "XOFF detect\n", 0)); -+ } -+ -+ if (rstat & SER_ERROR_MASK) { -+ unsigned char data; -+ -+ info->last_rx_active_usec = GET_JIFFIES_USEC(); -+ info->last_rx_active = jiffies; -+ /* If we got an error, we must reset it by reading the -+ * data_in field -+ */ -+ data = info->ioport[REG_DATA]; -+ DINTR1(DEBUG_LOG(info->line, "ser_rx! %c\n", data)); -+ DINTR1(DEBUG_LOG(info->line, "ser_rx err stat %02X\n", rstat)); -+ if (!data && (rstat & SER_FRAMING_ERR_MASK)) { -+ /* Most likely a break, but we get interrupts over and -+ * over again. -+ */ -+ -+ if (!info->break_detected_cnt) { -+ DEBUG_LOG(info->line, "#BRK start\n", 0); -+ } -+ if (rstat & SER_RXD_MASK) { -+ /* The RX pin is high now, so the break -+ * must be over, but.... -+ * we can't really know if we will get another -+ * last byte ending the break or not. -+ * And we don't know if the byte (if any) will -+ * have an error or look valid. -+ */ -+ DEBUG_LOG(info->line, "# BL BRK\n", 0); -+ info->errorcode = ERRCODE_INSERT_BREAK; -+ } -+ info->break_detected_cnt++; -+ } else { -+ /* The error does not look like a break, but could be -+ * the end of one -+ */ -+ if (info->break_detected_cnt) { -+ DEBUG_LOG(info->line, "EBRK %i\n", info->break_detected_cnt); -+ info->errorcode = ERRCODE_INSERT_BREAK; -+ } else { -+ if (info->errorcode == ERRCODE_INSERT_BREAK) { -+ info->icount.brk++; -+ add_char_and_flag(info, '\0', TTY_BREAK); -+ } -+ -+ if (rstat & SER_PAR_ERR_MASK) { -+ info->icount.parity++; -+ add_char_and_flag(info, data, TTY_PARITY); -+ } else if (rstat & SER_OVERRUN_MASK) { -+ info->icount.overrun++; -+ add_char_and_flag(info, data, TTY_OVERRUN); -+ } else if (rstat & SER_FRAMING_ERR_MASK) { -+ info->icount.frame++; -+ add_char_and_flag(info, data, TTY_FRAME); -+ } -+ -+ info->errorcode = 0; -+ } -+ info->break_detected_cnt = 0; -+ DEBUG_LOG(info->line, "#iERR s d %04X\n", -+ ((rstat & SER_ERROR_MASK) << 8) | data); -+ } -+ PROCSTAT(ser_stat[info->line].early_errors_cnt++); -+ } else { /* It was a valid byte, now let the DMA do the rest */ -+ unsigned long curr_time_u = GET_JIFFIES_USEC(); -+ unsigned long curr_time = jiffies; -+ -+ if (info->break_detected_cnt) { -+ /* Detect if this character is a new valid char or the -+ * last char in a break sequence: If LSBits are 0 and -+ * MSBits are high AND the time is close to the -+ * previous interrupt we should discard it. -+ */ -+ long elapsed_usec = -+ (curr_time - info->last_rx_active) * (1000000/HZ) + -+ curr_time_u - info->last_rx_active_usec; -+ if (elapsed_usec < 2*info->char_time_usec) { -+ DEBUG_LOG(info->line, "FBRK %i\n", info->line); -+ /* Report as BREAK (error) and let -+ * receive_chars_dma() handle it -+ */ -+ info->errorcode = ERRCODE_SET_BREAK; -+ } else { -+ DEBUG_LOG(info->line, "Not end of BRK (V)%i\n", info->line); -+ } -+ DEBUG_LOG(info->line, "num brk %i\n", info->break_detected_cnt); -+ } -+ -+#ifdef SERIAL_DEBUG_INTR -+ printk("** OK, disabling ser_interrupts\n"); -+#endif -+ e100_disable_serial_data_irq(info); -+ DINTR2(DEBUG_LOG(info->line, "ser_rx OK %d\n", info->line)); -+ info->break_detected_cnt = 0; -+ -+ PROCSTAT(ser_stat[info->line].ser_ints_ok_cnt++); -+ } -+ /* Restarting the DMA never hurts */ -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, restart); -+ START_FLUSH_FAST_TIMER(info, "ser_int"); -+ return info; -+} /* handle_ser_rx_interrupt */ -+ -+static void handle_ser_tx_interrupt(struct e100_serial *info) -+{ -+ unsigned long flags; -+ -+ if (info->x_char) { -+ unsigned char rstat; -+ DFLOW(DEBUG_LOG(info->line, "tx_int: xchar 0x%02X\n", info->x_char)); -+ local_irq_save(flags); -+ rstat = info->ioport[REG_STATUS]; -+ DFLOW(DEBUG_LOG(info->line, "stat %x\n", rstat)); -+ -+ info->ioport[REG_TR_DATA] = info->x_char; -+ info->icount.tx++; -+ info->x_char = 0; -+ /* We must enable since it is disabled in ser_interrupt */ -+ e100_enable_serial_tx_ready_irq(info); -+ local_irq_restore(flags); -+ return; -+ } -+ if (info->uses_dma_out) { -+ unsigned char rstat; -+ int i; -+ /* We only use normal tx interrupt when sending x_char */ -+ DFLOW(DEBUG_LOG(info->line, "tx_int: xchar sent\n", 0)); -+ local_irq_save(flags); -+ rstat = info->ioport[REG_STATUS]; -+ DFLOW(DEBUG_LOG(info->line, "stat %x\n", rstat)); -+ e100_disable_serial_tx_ready_irq(info); -+ if (info->port.tty->stopped) -+ rs_stop(info->port.tty); -+ /* Enable the DMA channel and tell it to continue */ -+ e100_enable_txdma_channel(info); -+ /* Wait 12 cycles before doing the DMA command */ -+ for(i = 6; i > 0; i--) -+ nop(); -+ -+ *info->ocmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, continue); -+ local_irq_restore(flags); -+ return; -+ } -+ /* Normal char-by-char interrupt */ -+ if (info->xmit.head == info->xmit.tail -+ || info->port.tty->stopped -+ || info->port.tty->hw_stopped) { -+ DFLOW(DEBUG_LOG(info->line, "tx_int: stopped %i\n", -+ info->port.tty->stopped)); -+ e100_disable_serial_tx_ready_irq(info); -+ info->tr_running = 0; -+ return; -+ } -+ DINTR2(DEBUG_LOG(info->line, "tx_int %c\n", info->xmit.buf[info->xmit.tail])); -+ /* Send a byte, rs485 timing is critical so turn of ints */ -+ local_irq_save(flags); -+ info->ioport[REG_TR_DATA] = info->xmit.buf[info->xmit.tail]; -+ info->xmit.tail = (info->xmit.tail + 1) & (SERIAL_XMIT_SIZE-1); -+ info->icount.tx++; -+ if (info->xmit.head == info->xmit.tail) { -+#if defined(CONFIG_ETRAX_RS485) && defined(CONFIG_ETRAX_FAST_TIMER) -+ if (info->rs485.flags & SER_RS485_ENABLED) { -+ /* Set a short timer to toggle RTS */ -+ start_one_shot_timer(&fast_timers_rs485[info->line], -+ rs485_toggle_rts_timer_function, -+ (unsigned long)info, -+ info->char_time_usec*2, -+ "RS-485"); -+ } -+#endif /* RS485 */ -+ info->last_tx_active_usec = GET_JIFFIES_USEC(); -+ info->last_tx_active = jiffies; -+ e100_disable_serial_tx_ready_irq(info); -+ info->tr_running = 0; -+ DFLOW(DEBUG_LOG(info->line, "tx_int: stop2\n", 0)); -+ } else { -+ /* We must enable since it is disabled in ser_interrupt */ -+ e100_enable_serial_tx_ready_irq(info); -+ } -+ local_irq_restore(flags); -+ -+ if (CIRC_CNT(info->xmit.head, -+ info->xmit.tail, -+ SERIAL_XMIT_SIZE) < WAKEUP_CHARS) -+ rs_sched_event(info, RS_EVENT_WRITE_WAKEUP); -+ -+} /* handle_ser_tx_interrupt */ -+ -+/* result of time measurements: -+ * RX duration 54-60 us when doing something, otherwise 6-9 us -+ * ser_int duration: just sending: 8-15 us normally, up to 73 us -+ */ -+static irqreturn_t -+ser_interrupt(int irq, void *dev_id) -+{ -+ static volatile int tx_started = 0; -+ struct e100_serial *info; -+ int i; -+ unsigned long flags; -+ unsigned long irq_mask1_rd; -+ unsigned long data_mask = (1 << (8+2*0)); /* ser0 data_avail */ -+ int handled = 0; -+ static volatile unsigned long reentered_ready_mask = 0; -+ -+ local_irq_save(flags); -+ irq_mask1_rd = *R_IRQ_MASK1_RD; -+ /* First handle all rx interrupts with ints disabled */ -+ info = rs_table; -+ irq_mask1_rd &= e100_ser_int_mask; -+ for (i = 0; i < NR_PORTS; i++) { -+ /* Which line caused the data irq? */ -+ if (irq_mask1_rd & data_mask) { -+ handled = 1; -+ handle_ser_rx_interrupt(info); -+ } -+ info += 1; -+ data_mask <<= 2; -+ } -+ /* Handle tx interrupts with interrupts enabled so we -+ * can take care of new data interrupts while transmitting -+ * We protect the tx part with the tx_started flag. -+ * We disable the tr_ready interrupts we are about to handle and -+ * unblock the serial interrupt so new serial interrupts may come. -+ * -+ * If we get a new interrupt: -+ * - it migth be due to synchronous serial ports. -+ * - serial irq will be blocked by general irq handler. -+ * - async data will be handled above (sync will be ignored). -+ * - tx_started flag will prevent us from trying to send again and -+ * we will exit fast - no need to unblock serial irq. -+ * - Next (sync) serial interrupt handler will be runned with -+ * disabled interrupt due to restore_flags() at end of function, -+ * so sync handler will not be preempted or reentered. -+ */ -+ if (!tx_started) { -+ unsigned long ready_mask; -+ unsigned long -+ tx_started = 1; -+ /* Only the tr_ready interrupts left */ -+ irq_mask1_rd &= (IO_MASK(R_IRQ_MASK1_RD, ser0_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser1_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser2_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser3_ready)); -+ while (irq_mask1_rd) { -+ /* Disable those we are about to handle */ -+ *R_IRQ_MASK1_CLR = irq_mask1_rd; -+ /* Unblock the serial interrupt */ -+ *R_VECT_MASK_SET = IO_STATE(R_VECT_MASK_SET, serial, set); -+ -+ local_irq_enable(); -+ ready_mask = (1 << (8+1+2*0)); /* ser0 tr_ready */ -+ info = rs_table; -+ for (i = 0; i < NR_PORTS; i++) { -+ /* Which line caused the ready irq? */ -+ if (irq_mask1_rd & ready_mask) { -+ handled = 1; -+ handle_ser_tx_interrupt(info); -+ } -+ info += 1; -+ ready_mask <<= 2; -+ } -+ /* handle_ser_tx_interrupt enables tr_ready interrupts */ -+ local_irq_disable(); -+ /* Handle reentered TX interrupt */ -+ irq_mask1_rd = reentered_ready_mask; -+ } -+ local_irq_disable(); -+ tx_started = 0; -+ } else { -+ unsigned long ready_mask; -+ ready_mask = irq_mask1_rd & (IO_MASK(R_IRQ_MASK1_RD, ser0_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser1_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser2_ready) | -+ IO_MASK(R_IRQ_MASK1_RD, ser3_ready)); -+ if (ready_mask) { -+ reentered_ready_mask |= ready_mask; -+ /* Disable those we are about to handle */ -+ *R_IRQ_MASK1_CLR = ready_mask; -+ DFLOW(DEBUG_LOG(SERIAL_DEBUG_LINE, "ser_int reentered with TX %X\n", ready_mask)); -+ } -+ } -+ -+ local_irq_restore(flags); -+ return IRQ_RETVAL(handled); -+} /* ser_interrupt */ -+#endif -+ -+/* -+ * ------------------------------------------------------------------- -+ * Here ends the serial interrupt routines. -+ * ------------------------------------------------------------------- -+ */ -+ -+/* -+ * This routine is used to handle the "bottom half" processing for the -+ * serial driver, known also the "software interrupt" processing. -+ * This processing is done at the kernel interrupt level, after the -+ * rs_interrupt() has returned, BUT WITH INTERRUPTS TURNED ON. This -+ * is where time-consuming activities which can not be done in the -+ * interrupt driver proper are done; the interrupt driver schedules -+ * them using rs_sched_event(), and they get done here. -+ */ -+static void -+do_softint(struct work_struct *work) -+{ -+ struct e100_serial *info; -+ struct tty_struct *tty; -+ -+ info = container_of(work, struct e100_serial, work); -+ -+ tty = info->port.tty; -+ if (!tty) -+ return; -+ -+ if (test_and_clear_bit(RS_EVENT_WRITE_WAKEUP, &info->event)) -+ tty_wakeup(tty); -+} -+ -+static int -+startup(struct e100_serial * info) -+{ -+ unsigned long flags; -+ unsigned long xmit_page; -+ int i; -+ -+ xmit_page = get_zeroed_page(GFP_KERNEL); -+ if (!xmit_page) -+ return -ENOMEM; -+ -+ local_irq_save(flags); -+ -+ /* if it was already initialized, skip this */ -+ -+ if (info->flags & ASYNC_INITIALIZED) { -+ local_irq_restore(flags); -+ free_page(xmit_page); -+ return 0; -+ } -+ -+ if (info->xmit.buf) -+ free_page(xmit_page); -+ else -+ info->xmit.buf = (unsigned char *) xmit_page; -+ -+#ifdef SERIAL_DEBUG_OPEN -+ printk("starting up ttyS%d (xmit_buf 0x%p)...\n", info->line, info->xmit.buf); -+#endif -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* Bits and pieces collected from below. Better to have them -+ in one ifdef:ed clause than to mix in a lot of ifdefs, -+ right? */ -+ if (info->port.tty) -+ clear_bit(TTY_IO_ERROR, &info->port.tty->flags); -+ -+ info->xmit.head = info->xmit.tail = 0; -+ info->first_recv_buffer = info->last_recv_buffer = NULL; -+ info->recv_cnt = info->max_recv_cnt = 0; -+ -+ for (i = 0; i < SERIAL_RECV_DESCRIPTORS; i++) -+ info->rec_descr[i].buf = NULL; -+ -+ /* No real action in the simulator, but may set info important -+ to ioctl. */ -+ change_speed(info); -+#else -+ -+ /* -+ * Clear the FIFO buffers and disable them -+ * (they will be reenabled in change_speed()) -+ */ -+ -+ /* -+ * Reset the DMA channels and make sure their interrupts are cleared -+ */ -+ -+ if (info->dma_in_enabled) { -+ info->uses_dma_in = 1; -+ e100_enable_rxdma_channel(info); -+ -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, reset); -+ -+ /* Wait until reset cycle is complete */ -+ while (IO_EXTRACT(R_DMA_CH6_CMD, cmd, *info->icmdadr) == -+ IO_STATE_VALUE(R_DMA_CH6_CMD, cmd, reset)); -+ -+ /* Make sure the irqs are cleared */ -+ *info->iclrintradr = -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_descr, do) | -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_eop, do); -+ } else { -+ e100_disable_rxdma_channel(info); -+ } -+ -+ if (info->dma_out_enabled) { -+ info->uses_dma_out = 1; -+ e100_enable_txdma_channel(info); -+ *info->ocmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, reset); -+ -+ while (IO_EXTRACT(R_DMA_CH6_CMD, cmd, *info->ocmdadr) == -+ IO_STATE_VALUE(R_DMA_CH6_CMD, cmd, reset)); -+ -+ /* Make sure the irqs are cleared */ -+ *info->oclrintradr = -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_descr, do) | -+ IO_STATE(R_DMA_CH6_CLR_INTR, clr_eop, do); -+ } else { -+ e100_disable_txdma_channel(info); -+ } -+ -+ if (info->port.tty) -+ clear_bit(TTY_IO_ERROR, &info->port.tty->flags); -+ -+ info->xmit.head = info->xmit.tail = 0; -+ info->first_recv_buffer = info->last_recv_buffer = NULL; -+ info->recv_cnt = info->max_recv_cnt = 0; -+ -+ for (i = 0; i < SERIAL_RECV_DESCRIPTORS; i++) -+ info->rec_descr[i].buf = 0; -+ -+ /* -+ * and set the speed and other flags of the serial port -+ * this will start the rx/tx as well -+ */ -+#ifdef SERIAL_HANDLE_EARLY_ERRORS -+ e100_enable_serial_data_irq(info); -+#endif -+ change_speed(info); -+ -+ /* dummy read to reset any serial errors */ -+ -+ (void)info->ioport[REG_DATA]; -+ -+ /* enable the interrupts */ -+ if (info->uses_dma_out) -+ e100_enable_txdma_irq(info); -+ -+ e100_enable_rx_irq(info); -+ -+ info->tr_running = 0; /* to be sure we don't lock up the transmitter */ -+ -+ /* setup the dma input descriptor and start dma */ -+ -+ start_receive(info); -+ -+ /* for safety, make sure the descriptors last result is 0 bytes written */ -+ -+ info->tr_descr.sw_len = 0; -+ info->tr_descr.hw_len = 0; -+ info->tr_descr.status = 0; -+ -+ /* enable RTS/DTR last */ -+ -+ e100_rts(info, 1); -+ e100_dtr(info, 1); -+ -+#endif /* CONFIG_SVINTO_SIM */ -+ -+ info->flags |= ASYNC_INITIALIZED; -+ -+ local_irq_restore(flags); -+ return 0; -+} -+ -+/* -+ * This routine will shutdown a serial port; interrupts are disabled, and -+ * DTR is dropped if the hangup on close termio flag is on. -+ */ -+static void -+shutdown(struct e100_serial * info) -+{ -+ unsigned long flags; -+ struct etrax_dma_descr *descr = info->rec_descr; -+ struct etrax_recv_buffer *buffer; -+ int i; -+ -+#ifndef CONFIG_SVINTO_SIM -+ /* shut down the transmitter and receiver */ -+ DFLOW(DEBUG_LOG(info->line, "shutdown %i\n", info->line)); -+ e100_disable_rx(info); -+ info->ioport[REG_TR_CTRL] = (info->tx_ctrl &= ~0x40); -+ -+ /* disable interrupts, reset dma channels */ -+ if (info->uses_dma_in) { -+ e100_disable_rxdma_irq(info); -+ *info->icmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, reset); -+ info->uses_dma_in = 0; -+ } else { -+ e100_disable_serial_data_irq(info); -+ } -+ -+ if (info->uses_dma_out) { -+ e100_disable_txdma_irq(info); -+ info->tr_running = 0; -+ *info->ocmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, reset); -+ info->uses_dma_out = 0; -+ } else { -+ e100_disable_serial_tx_ready_irq(info); -+ info->tr_running = 0; -+ } -+ -+#endif /* CONFIG_SVINTO_SIM */ -+ -+ if (!(info->flags & ASYNC_INITIALIZED)) -+ return; -+ -+#ifdef SERIAL_DEBUG_OPEN -+ printk("Shutting down serial port %d (irq %d)....\n", info->line, -+ info->irq); -+#endif -+ -+ local_irq_save(flags); -+ -+ if (info->xmit.buf) { -+ free_page((unsigned long)info->xmit.buf); -+ info->xmit.buf = NULL; -+ } -+ -+ for (i = 0; i < SERIAL_RECV_DESCRIPTORS; i++) -+ if (descr[i].buf) { -+ buffer = phys_to_virt(descr[i].buf) - sizeof *buffer; -+ kfree(buffer); -+ descr[i].buf = 0; -+ } -+ -+ if (!info->port.tty || (info->port.tty->termios->c_cflag & HUPCL)) { -+ /* hang up DTR and RTS if HUPCL is enabled */ -+ e100_dtr(info, 0); -+ e100_rts(info, 0); /* could check CRTSCTS before doing this */ -+ } -+ -+ if (info->port.tty) -+ set_bit(TTY_IO_ERROR, &info->port.tty->flags); -+ -+ info->flags &= ~ASYNC_INITIALIZED; -+ local_irq_restore(flags); -+} -+ -+ -+/* change baud rate and other assorted parameters */ -+ -+static void -+change_speed(struct e100_serial *info) -+{ -+ unsigned int cflag; -+ unsigned long xoff; -+ unsigned long flags; -+ /* first some safety checks */ -+ -+ if (!info->port.tty || !info->port.tty->termios) -+ return; -+ if (!info->ioport) -+ return; -+ -+ cflag = info->port.tty->termios->c_cflag; -+ -+ /* possibly, the tx/rx should be disabled first to do this safely */ -+ -+ /* change baud-rate and write it to the hardware */ -+ if ((info->flags & ASYNC_SPD_MASK) == ASYNC_SPD_CUST) { -+ /* Special baudrate */ -+ u32 mask = 0xFF << (info->line*8); /* Each port has 8 bits */ -+ unsigned long alt_source = -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_rec, normal) | -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_tr, normal); -+ /* R_ALT_SER_BAUDRATE selects the source */ -+ DBAUD(printk("Custom baudrate: baud_base/divisor %lu/%i\n", -+ (unsigned long)info->baud_base, info->custom_divisor)); -+ if (info->baud_base == SERIAL_PRESCALE_BASE) { -+ /* 0, 2-65535 (0=65536) */ -+ u16 divisor = info->custom_divisor; -+ /* R_SERIAL_PRESCALE (upper 16 bits of R_CLOCK_PRESCALE) */ -+ /* baudrate is 3.125MHz/custom_divisor */ -+ alt_source = -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_rec, prescale) | -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_tr, prescale); -+ alt_source = 0x11; -+ DBAUD(printk("Writing SERIAL_PRESCALE: divisor %i\n", divisor)); -+ *R_SERIAL_PRESCALE = divisor; -+ info->baud = SERIAL_PRESCALE_BASE/divisor; -+ } -+#ifdef CONFIG_ETRAX_EXTERN_PB6CLK_ENABLED -+ else if ((info->baud_base==CONFIG_ETRAX_EXTERN_PB6CLK_FREQ/8 && -+ info->custom_divisor == 1) || -+ (info->baud_base==CONFIG_ETRAX_EXTERN_PB6CLK_FREQ && -+ info->custom_divisor == 8)) { -+ /* ext_clk selected */ -+ alt_source = -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_rec, extern) | -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_tr, extern); -+ DBAUD(printk("using external baudrate: %lu\n", CONFIG_ETRAX_EXTERN_PB6CLK_FREQ/8)); -+ info->baud = CONFIG_ETRAX_EXTERN_PB6CLK_FREQ/8; -+ } -+#endif -+ else -+ { -+ /* Bad baudbase, we don't support using timer0 -+ * for baudrate. -+ */ -+ printk(KERN_WARNING "Bad baud_base/custom_divisor: %lu/%i\n", -+ (unsigned long)info->baud_base, info->custom_divisor); -+ } -+ r_alt_ser_baudrate_shadow &= ~mask; -+ r_alt_ser_baudrate_shadow |= (alt_source << (info->line*8)); -+ *R_ALT_SER_BAUDRATE = r_alt_ser_baudrate_shadow; -+ } else { -+ /* Normal baudrate */ -+ /* Make sure we use normal baudrate */ -+ u32 mask = 0xFF << (info->line*8); /* Each port has 8 bits */ -+ unsigned long alt_source = -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_rec, normal) | -+ IO_STATE(R_ALT_SER_BAUDRATE, ser0_tr, normal); -+ r_alt_ser_baudrate_shadow &= ~mask; -+ r_alt_ser_baudrate_shadow |= (alt_source << (info->line*8)); -+#ifndef CONFIG_SVINTO_SIM -+ *R_ALT_SER_BAUDRATE = r_alt_ser_baudrate_shadow; -+#endif /* CONFIG_SVINTO_SIM */ -+ -+ info->baud = cflag_to_baud(cflag); -+#ifndef CONFIG_SVINTO_SIM -+ info->ioport[REG_BAUD] = cflag_to_etrax_baud(cflag); -+#endif /* CONFIG_SVINTO_SIM */ -+ } -+ -+#ifndef CONFIG_SVINTO_SIM -+ /* start with default settings and then fill in changes */ -+ local_irq_save(flags); -+ /* 8 bit, no/even parity */ -+ info->rx_ctrl &= ~(IO_MASK(R_SERIAL0_REC_CTRL, rec_bitnr) | -+ IO_MASK(R_SERIAL0_REC_CTRL, rec_par_en) | -+ IO_MASK(R_SERIAL0_REC_CTRL, rec_par)); -+ -+ /* 8 bit, no/even parity, 1 stop bit, no cts */ -+ info->tx_ctrl &= ~(IO_MASK(R_SERIAL0_TR_CTRL, tr_bitnr) | -+ IO_MASK(R_SERIAL0_TR_CTRL, tr_par_en) | -+ IO_MASK(R_SERIAL0_TR_CTRL, tr_par) | -+ IO_MASK(R_SERIAL0_TR_CTRL, stop_bits) | -+ IO_MASK(R_SERIAL0_TR_CTRL, auto_cts)); -+ -+ if ((cflag & CSIZE) == CS7) { -+ /* set 7 bit mode */ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, tr_bitnr, tr_7bit); -+ info->rx_ctrl |= IO_STATE(R_SERIAL0_REC_CTRL, rec_bitnr, rec_7bit); -+ } -+ -+ if (cflag & CSTOPB) { -+ /* set 2 stop bit mode */ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, stop_bits, two_bits); -+ } -+ -+ if (cflag & PARENB) { -+ /* enable parity */ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, tr_par_en, enable); -+ info->rx_ctrl |= IO_STATE(R_SERIAL0_REC_CTRL, rec_par_en, enable); -+ } -+ -+ if (cflag & CMSPAR) { -+ /* enable stick parity, PARODD mean Mark which matches ETRAX */ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, tr_stick_par, stick); -+ info->rx_ctrl |= IO_STATE(R_SERIAL0_REC_CTRL, rec_stick_par, stick); -+ } -+ if (cflag & PARODD) { -+ /* set odd parity (or Mark if CMSPAR) */ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, tr_par, odd); -+ info->rx_ctrl |= IO_STATE(R_SERIAL0_REC_CTRL, rec_par, odd); -+ } -+ -+ if (cflag & CRTSCTS) { -+ /* enable automatic CTS handling */ -+ DFLOW(DEBUG_LOG(info->line, "FLOW auto_cts enabled\n", 0)); -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, auto_cts, active); -+ } -+ -+ /* make sure the tx and rx are enabled */ -+ -+ info->tx_ctrl |= IO_STATE(R_SERIAL0_TR_CTRL, tr_enable, enable); -+ info->rx_ctrl |= IO_STATE(R_SERIAL0_REC_CTRL, rec_enable, enable); -+ -+ /* actually write the control regs to the hardware */ -+ -+ info->ioport[REG_TR_CTRL] = info->tx_ctrl; -+ info->ioport[REG_REC_CTRL] = info->rx_ctrl; -+ xoff = IO_FIELD(R_SERIAL0_XOFF, xoff_char, STOP_CHAR(info->port.tty)); -+ xoff |= IO_STATE(R_SERIAL0_XOFF, tx_stop, enable); -+ if (info->port.tty->termios->c_iflag & IXON ) { -+ DFLOW(DEBUG_LOG(info->line, "FLOW XOFF enabled 0x%02X\n", -+ STOP_CHAR(info->port.tty))); -+ xoff |= IO_STATE(R_SERIAL0_XOFF, auto_xoff, enable); -+ } -+ -+ *((unsigned long *)&info->ioport[REG_XOFF]) = xoff; -+ local_irq_restore(flags); -+#endif /* !CONFIG_SVINTO_SIM */ -+ -+ update_char_time(info); -+ -+} /* change_speed */ -+ -+/* start transmitting chars NOW */ -+ -+static void -+rs_flush_chars(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ if (info->tr_running || -+ info->xmit.head == info->xmit.tail || -+ tty->stopped || -+ tty->hw_stopped || -+ !info->xmit.buf) -+ return; -+ -+#ifdef SERIAL_DEBUG_FLOW -+ printk("rs_flush_chars\n"); -+#endif -+ -+ /* this protection might not exactly be necessary here */ -+ -+ local_irq_save(flags); -+ start_transmit(info); -+ local_irq_restore(flags); -+} -+ -+static int rs_raw_write(struct tty_struct *tty, -+ const unsigned char *buf, int count) -+{ -+ int c, ret = 0; -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ /* first some sanity checks */ -+ -+ if (!tty || !info->xmit.buf || !tmp_buf) -+ return 0; -+ -+#ifdef SERIAL_DEBUG_DATA -+ if (info->line == SERIAL_DEBUG_LINE) -+ printk("rs_raw_write (%d), status %d\n", -+ count, info->ioport[REG_STATUS]); -+#endif -+ -+#ifdef CONFIG_SVINTO_SIM -+ /* Really simple. The output is here and now. */ -+ SIMCOUT(buf, count); -+ return count; -+#endif -+ local_save_flags(flags); -+ DFLOW(DEBUG_LOG(info->line, "write count %i ", count)); -+ DFLOW(DEBUG_LOG(info->line, "ldisc %i\n", tty->ldisc.chars_in_buffer(tty))); -+ -+ -+ /* The local_irq_disable/restore_flags pairs below are needed -+ * because the DMA interrupt handler moves the info->xmit values. -+ * the memcpy needs to be in the critical region unfortunately, -+ * because we need to read xmit values, memcpy, write xmit values -+ * in one atomic operation... this could perhaps be avoided by -+ * more clever design. -+ */ -+ local_irq_disable(); -+ while (count) { -+ c = CIRC_SPACE_TO_END(info->xmit.head, -+ info->xmit.tail, -+ SERIAL_XMIT_SIZE); -+ -+ if (count < c) -+ c = count; -+ if (c <= 0) -+ break; -+ -+ memcpy(info->xmit.buf + info->xmit.head, buf, c); -+ info->xmit.head = (info->xmit.head + c) & -+ (SERIAL_XMIT_SIZE-1); -+ buf += c; -+ count -= c; -+ ret += c; -+ } -+ local_irq_restore(flags); -+ -+ /* enable transmitter if not running, unless the tty is stopped -+ * this does not need IRQ protection since if tr_running == 0 -+ * the IRQ's are not running anyway for this port. -+ */ -+ DFLOW(DEBUG_LOG(info->line, "write ret %i\n", ret)); -+ -+ if (info->xmit.head != info->xmit.tail && -+ !tty->stopped && -+ !tty->hw_stopped && -+ !info->tr_running) { -+ start_transmit(info); -+ } -+ -+ return ret; -+} /* raw_raw_write() */ -+ -+static int -+rs_write(struct tty_struct *tty, -+ const unsigned char *buf, int count) -+{ -+#if defined(CONFIG_ETRAX_RS485) -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ -+ if (info->rs485.flags & SER_RS485_ENABLED) -+ { -+ /* If we are in RS-485 mode, we need to toggle RTS and disable -+ * the receiver before initiating a DMA transfer -+ */ -+#ifdef CONFIG_ETRAX_FAST_TIMER -+ /* Abort any started timer */ -+ fast_timers_rs485[info->line].function = NULL; -+ del_fast_timer(&fast_timers_rs485[info->line]); -+#endif -+ e100_rts(info, (info->rs485.flags & SER_RS485_RTS_ON_SEND)); -+#if defined(CONFIG_ETRAX_RS485_DISABLE_RECEIVER) -+ e100_disable_rx(info); -+ e100_enable_rx_irq(info); -+#endif -+ if ((info->rs485.flags & SER_RS485_RTS_BEFORE_SEND) && -+ (info->rs485.delay_rts_before_send > 0)) -+ msleep(info->rs485.delay_rts_before_send); -+ } -+#endif /* CONFIG_ETRAX_RS485 */ -+ -+ count = rs_raw_write(tty, buf, count); -+ -+#if defined(CONFIG_ETRAX_RS485) -+ if (info->rs485.flags & SER_RS485_ENABLED) -+ { -+ unsigned int val; -+ /* If we are in RS-485 mode the following has to be done: -+ * wait until DMA is ready -+ * wait on transmit shift register -+ * toggle RTS -+ * enable the receiver -+ */ -+ -+ /* Sleep until all sent */ -+ tty_wait_until_sent(tty, 0); -+#ifdef CONFIG_ETRAX_FAST_TIMER -+ /* Now sleep a little more so that shift register is empty */ -+ schedule_usleep(info->char_time_usec * 2); -+#endif -+ /* wait on transmit shift register */ -+ do{ -+ get_lsr_info(info, &val); -+ }while (!(val & TIOCSER_TEMT)); -+ -+ e100_rts(info, (info->rs485.flags & SER_RS485_RTS_AFTER_SEND)); -+ -+#if defined(CONFIG_ETRAX_RS485_DISABLE_RECEIVER) -+ e100_enable_rx(info); -+ e100_enable_rxdma_irq(info); -+#endif -+ } -+#endif /* CONFIG_ETRAX_RS485 */ -+ -+ return count; -+} /* rs_write */ -+ -+ -+/* how much space is available in the xmit buffer? */ -+ -+static int -+rs_write_room(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ -+ return CIRC_SPACE(info->xmit.head, info->xmit.tail, SERIAL_XMIT_SIZE); -+} -+ -+/* How many chars are in the xmit buffer? -+ * This does not include any chars in the transmitter FIFO. -+ * Use wait_until_sent for waiting for FIFO drain. -+ */ -+ -+static int -+rs_chars_in_buffer(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ -+ return CIRC_CNT(info->xmit.head, info->xmit.tail, SERIAL_XMIT_SIZE); -+} -+ -+/* discard everything in the xmit buffer */ -+ -+static void -+rs_flush_buffer(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ info->xmit.head = info->xmit.tail = 0; -+ local_irq_restore(flags); -+ -+ tty_wakeup(tty); -+} -+ -+/* -+ * This function is used to send a high-priority XON/XOFF character to -+ * the device -+ * -+ * Since we use DMA we don't check for info->x_char in transmit_chars_dma(), -+ * but we do it in handle_ser_tx_interrupt(). -+ * We disable DMA channel and enable tx ready interrupt and write the -+ * character when possible. -+ */ -+static void rs_send_xchar(struct tty_struct *tty, char ch) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ local_irq_save(flags); -+ if (info->uses_dma_out) { -+ /* Put the DMA on hold and disable the channel */ -+ *info->ocmdadr = IO_STATE(R_DMA_CH6_CMD, cmd, hold); -+ while (IO_EXTRACT(R_DMA_CH6_CMD, cmd, *info->ocmdadr) != -+ IO_STATE_VALUE(R_DMA_CH6_CMD, cmd, hold)); -+ e100_disable_txdma_channel(info); -+ } -+ -+ /* Must make sure transmitter is not stopped before we can transmit */ -+ if (tty->stopped) -+ rs_start(tty); -+ -+ /* Enable manual transmit interrupt and send from there */ -+ DFLOW(DEBUG_LOG(info->line, "rs_send_xchar 0x%02X\n", ch)); -+ info->x_char = ch; -+ e100_enable_serial_tx_ready_irq(info); -+ local_irq_restore(flags); -+} -+ -+/* -+ * ------------------------------------------------------------ -+ * rs_throttle() -+ * -+ * This routine is called by the upper-layer tty layer to signal that -+ * incoming characters should be throttled. -+ * ------------------------------------------------------------ -+ */ -+static void -+rs_throttle(struct tty_struct * tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+#ifdef SERIAL_DEBUG_THROTTLE -+ char buf[64]; -+ -+ printk("throttle %s: %lu....\n", tty_name(tty, buf), -+ (unsigned long)tty->ldisc.chars_in_buffer(tty)); -+#endif -+ DFLOW(DEBUG_LOG(info->line,"rs_throttle %lu\n", tty->ldisc.chars_in_buffer(tty))); -+ -+ /* Do RTS before XOFF since XOFF might take some time */ -+ if (tty->termios->c_cflag & CRTSCTS) { -+ /* Turn off RTS line */ -+ e100_rts(info, 0); -+ } -+ if (I_IXOFF(tty)) -+ rs_send_xchar(tty, STOP_CHAR(tty)); -+ -+} -+ -+static void -+rs_unthrottle(struct tty_struct * tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+#ifdef SERIAL_DEBUG_THROTTLE -+ char buf[64]; -+ -+ printk("unthrottle %s: %lu....\n", tty_name(tty, buf), -+ (unsigned long)tty->ldisc.chars_in_buffer(tty)); -+#endif -+ DFLOW(DEBUG_LOG(info->line,"rs_unthrottle ldisc %d\n", tty->ldisc.chars_in_buffer(tty))); -+ DFLOW(DEBUG_LOG(info->line,"rs_unthrottle flip.count: %i\n", tty->flip.count)); -+ /* Do RTS before XOFF since XOFF might take some time */ -+ if (tty->termios->c_cflag & CRTSCTS) { -+ /* Assert RTS line */ -+ e100_rts(info, 1); -+ } -+ -+ if (I_IXOFF(tty)) { -+ if (info->x_char) -+ info->x_char = 0; -+ else -+ rs_send_xchar(tty, START_CHAR(tty)); -+ } -+ -+} -+ -+/* -+ * ------------------------------------------------------------ -+ * rs_ioctl() and friends -+ * ------------------------------------------------------------ -+ */ -+ -+static int -+get_serial_info(struct e100_serial * info, -+ struct serial_struct * retinfo) -+{ -+ struct serial_struct tmp; -+ -+ /* this is all probably wrong, there are a lot of fields -+ * here that we don't have in e100_serial and maybe we -+ * should set them to something else than 0. -+ */ -+ -+ if (!retinfo) -+ return -EFAULT; -+ memset(&tmp, 0, sizeof(tmp)); -+ tmp.type = info->type; -+ tmp.line = info->line; -+ tmp.port = (int)info->ioport; -+ tmp.irq = info->irq; -+ tmp.flags = info->flags; -+ tmp.baud_base = info->baud_base; -+ tmp.close_delay = info->close_delay; -+ tmp.closing_wait = info->closing_wait; -+ tmp.custom_divisor = info->custom_divisor; -+ if (copy_to_user(retinfo, &tmp, sizeof(*retinfo))) -+ return -EFAULT; -+ return 0; -+} -+ -+static int -+set_serial_info(struct e100_serial *info, -+ struct serial_struct *new_info) -+{ -+ struct serial_struct new_serial; -+ struct e100_serial old_info; -+ int retval = 0; -+ -+ if (copy_from_user(&new_serial, new_info, sizeof(new_serial))) -+ return -EFAULT; -+ -+ old_info = *info; -+ -+ if (!capable(CAP_SYS_ADMIN)) { -+ if ((new_serial.type != info->type) || -+ (new_serial.close_delay != info->close_delay) || -+ ((new_serial.flags & ~ASYNC_USR_MASK) != -+ (info->flags & ~ASYNC_USR_MASK))) -+ return -EPERM; -+ info->flags = ((info->flags & ~ASYNC_USR_MASK) | -+ (new_serial.flags & ASYNC_USR_MASK)); -+ goto check_and_exit; -+ } -+ -+ if (info->count > 1) -+ return -EBUSY; -+ -+ /* -+ * OK, past this point, all the error checking has been done. -+ * At this point, we start making changes..... -+ */ -+ -+ info->baud_base = new_serial.baud_base; -+ info->flags = ((info->flags & ~ASYNC_FLAGS) | -+ (new_serial.flags & ASYNC_FLAGS)); -+ info->custom_divisor = new_serial.custom_divisor; -+ info->type = new_serial.type; -+ info->close_delay = new_serial.close_delay; -+ info->closing_wait = new_serial.closing_wait; -+ info->port.tty->low_latency = (info->flags & ASYNC_LOW_LATENCY) ? 1 : 0; -+ -+ check_and_exit: -+ if (info->flags & ASYNC_INITIALIZED) { -+ change_speed(info); -+ } else -+ retval = startup(info); -+ return retval; -+} -+ -+/* -+ * get_lsr_info - get line status register info -+ * -+ * Purpose: Let user call ioctl() to get info when the UART physically -+ * is emptied. On bus types like RS485, the transmitter must -+ * release the bus after transmitting. This must be done when -+ * the transmit shift register is empty, not be done when the -+ * transmit holding register is empty. This functionality -+ * allows an RS485 driver to be written in user space. -+ */ -+static int -+get_lsr_info(struct e100_serial * info, unsigned int *value) -+{ -+ unsigned int result = TIOCSER_TEMT; -+#ifndef CONFIG_SVINTO_SIM -+ unsigned long curr_time = jiffies; -+ unsigned long curr_time_usec = GET_JIFFIES_USEC(); -+ unsigned long elapsed_usec = -+ (curr_time - info->last_tx_active) * 1000000/HZ + -+ curr_time_usec - info->last_tx_active_usec; -+ -+ if (info->xmit.head != info->xmit.tail || -+ elapsed_usec < 2*info->char_time_usec) { -+ result = 0; -+ } -+#endif -+ -+ if (copy_to_user(value, &result, sizeof(int))) -+ return -EFAULT; -+ return 0; -+} -+ -+#ifdef SERIAL_DEBUG_IO -+struct state_str -+{ -+ int state; -+ const char *str; -+}; -+ -+const struct state_str control_state_str[] = { -+ {TIOCM_DTR, "DTR" }, -+ {TIOCM_RTS, "RTS"}, -+ {TIOCM_ST, "ST?" }, -+ {TIOCM_SR, "SR?" }, -+ {TIOCM_CTS, "CTS" }, -+ {TIOCM_CD, "CD" }, -+ {TIOCM_RI, "RI" }, -+ {TIOCM_DSR, "DSR" }, -+ {0, NULL } -+}; -+ -+char *get_control_state_str(int MLines, char *s) -+{ -+ int i = 0; -+ -+ s[0]='\0'; -+ while (control_state_str[i].str != NULL) { -+ if (MLines & control_state_str[i].state) { -+ if (s[0] != '\0') { -+ strcat(s, ", "); -+ } -+ strcat(s, control_state_str[i].str); -+ } -+ i++; -+ } -+ return s; -+} -+#endif -+ -+static int -+rs_break(struct tty_struct *tty, int break_state) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ if (!info->ioport) -+ return -EIO; -+ -+ local_irq_save(flags); -+ if (break_state == -1) { -+ /* Go to manual mode and set the txd pin to 0 */ -+ /* Clear bit 7 (txd) and 6 (tr_enable) */ -+ info->tx_ctrl &= 0x3F; -+ } else { -+ /* Set bit 7 (txd) and 6 (tr_enable) */ -+ info->tx_ctrl |= (0x80 | 0x40); -+ } -+ info->ioport[REG_TR_CTRL] = info->tx_ctrl; -+ local_irq_restore(flags); -+ return 0; -+} -+ -+static int -+rs_tiocmset(struct tty_struct *tty, unsigned int set, unsigned int clear) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ -+ if (clear & TIOCM_RTS) -+ e100_rts(info, 0); -+ if (clear & TIOCM_DTR) -+ e100_dtr(info, 0); -+ /* Handle FEMALE behaviour */ -+ if (clear & TIOCM_RI) -+ e100_ri_out(info, 0); -+ if (clear & TIOCM_CD) -+ e100_cd_out(info, 0); -+ -+ if (set & TIOCM_RTS) -+ e100_rts(info, 1); -+ if (set & TIOCM_DTR) -+ e100_dtr(info, 1); -+ /* Handle FEMALE behaviour */ -+ if (set & TIOCM_RI) -+ e100_ri_out(info, 1); -+ if (set & TIOCM_CD) -+ e100_cd_out(info, 1); -+ -+ local_irq_restore(flags); -+ return 0; -+} -+ -+static int -+rs_tiocmget(struct tty_struct *tty) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned int result; -+ unsigned long flags; -+ -+ local_irq_save(flags); -+ -+ result = -+ (!E100_RTS_GET(info) ? TIOCM_RTS : 0) -+ | (!E100_DTR_GET(info) ? TIOCM_DTR : 0) -+ | (!E100_RI_GET(info) ? TIOCM_RNG : 0) -+ | (!E100_DSR_GET(info) ? TIOCM_DSR : 0) -+ | (!E100_CD_GET(info) ? TIOCM_CAR : 0) -+ | (!E100_CTS_GET(info) ? TIOCM_CTS : 0); -+ -+ local_irq_restore(flags); -+ -+#ifdef SERIAL_DEBUG_IO -+ printk(KERN_DEBUG "ser%i: modem state: %i 0x%08X\n", -+ info->line, result, result); -+ { -+ char s[100]; -+ -+ get_control_state_str(result, s); -+ printk(KERN_DEBUG "state: %s\n", s); -+ } -+#endif -+ return result; -+ -+} -+ -+ -+static int -+rs_ioctl(struct tty_struct *tty, -+ unsigned int cmd, unsigned long arg) -+{ -+ struct e100_serial * info = (struct e100_serial *)tty->driver_data; -+ -+ if ((cmd != TIOCGSERIAL) && (cmd != TIOCSSERIAL) && -+ (cmd != TIOCSERCONFIG) && (cmd != TIOCSERGWILD) && -+ (cmd != TIOCSERSWILD) && (cmd != TIOCSERGSTRUCT)) { -+ if (tty->flags & (1 << TTY_IO_ERROR)) -+ return -EIO; -+ } -+ -+ switch (cmd) { -+ case TIOCGSERIAL: -+ return get_serial_info(info, -+ (struct serial_struct *) arg); -+ case TIOCSSERIAL: -+ return set_serial_info(info, -+ (struct serial_struct *) arg); -+ case TIOCSERGETLSR: /* Get line status register */ -+ return get_lsr_info(info, (unsigned int *) arg); -+ -+ case TIOCSERGSTRUCT: -+ if (copy_to_user((struct e100_serial *) arg, -+ info, sizeof(struct e100_serial))) -+ return -EFAULT; -+ return 0; -+ -+#if defined(CONFIG_ETRAX_RS485) -+ case TIOCSERSETRS485: -+ { -+ /* In this ioctl we still use the old structure -+ * rs485_control for backward compatibility -+ * (if we use serial_rs485, then old user-level code -+ * wouldn't work anymore...). -+ * The use of this ioctl is deprecated: use TIOCSRS485 -+ * instead.*/ -+ struct rs485_control rs485ctrl; -+ struct serial_rs485 rs485data; -+ printk(KERN_DEBUG "The use of this ioctl is deprecated. Use TIOCSRS485 instead\n"); -+ if (copy_from_user(&rs485ctrl, (struct rs485_control *)arg, -+ sizeof(rs485ctrl))) -+ return -EFAULT; -+ -+ rs485data.delay_rts_before_send = rs485ctrl.delay_rts_before_send; -+ rs485data.flags = 0; -+ if (rs485data.delay_rts_before_send != 0) -+ rs485data.flags |= SER_RS485_RTS_BEFORE_SEND; -+ else -+ rs485data.flags &= ~(SER_RS485_RTS_BEFORE_SEND); -+ -+ if (rs485ctrl.enabled) -+ rs485data.flags |= SER_RS485_ENABLED; -+ else -+ rs485data.flags &= ~(SER_RS485_ENABLED); -+ -+ if (rs485ctrl.rts_on_send) -+ rs485data.flags |= SER_RS485_RTS_ON_SEND; -+ else -+ rs485data.flags &= ~(SER_RS485_RTS_ON_SEND); -+ -+ if (rs485ctrl.rts_after_sent) -+ rs485data.flags |= SER_RS485_RTS_AFTER_SEND; -+ else -+ rs485data.flags &= ~(SER_RS485_RTS_AFTER_SEND); -+ -+ return e100_enable_rs485(tty, &rs485data); -+ } -+ -+ case TIOCSRS485: -+ { -+ /* This is the new version of TIOCSRS485, with new -+ * data structure serial_rs485 */ -+ struct serial_rs485 rs485data; -+ if (copy_from_user(&rs485data, (struct rs485_control *)arg, -+ sizeof(rs485data))) -+ return -EFAULT; -+ -+ return e100_enable_rs485(tty, &rs485data); -+ } -+ -+ case TIOCGRS485: -+ { -+ struct serial_rs485 *rs485data = -+ &(((struct e100_serial *)tty->driver_data)->rs485); -+ /* This is the ioctl to get RS485 data from user-space */ -+ if (copy_to_user((struct serial_rs485 *) arg, -+ rs485data, -+ sizeof(struct serial_rs485))) -+ return -EFAULT; -+ break; -+ } -+ -+ case TIOCSERWRRS485: -+ { -+ struct rs485_write rs485wr; -+ if (copy_from_user(&rs485wr, (struct rs485_write *)arg, -+ sizeof(rs485wr))) -+ return -EFAULT; -+ -+ return e100_write_rs485(tty, rs485wr.outc, rs485wr.outc_size); -+ } -+#endif -+ -+ default: -+ return -ENOIOCTLCMD; -+ } -+ return 0; -+} -+ -+static void -+rs_set_termios(struct tty_struct *tty, struct ktermios *old_termios) -+{ -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ -+ change_speed(info); -+ -+ /* Handle turning off CRTSCTS */ -+ if ((old_termios->c_cflag & CRTSCTS) && -+ !(tty->termios->c_cflag & CRTSCTS)) { -+ tty->hw_stopped = 0; -+ rs_start(tty); -+ } -+ -+} -+ -+/* -+ * ------------------------------------------------------------ -+ * rs_close() -+ * -+ * This routine is called when the serial port gets closed. First, we -+ * wait for the last remaining data to be sent. Then, we unlink its -+ * S structure from the interrupt chain if necessary, and we free -+ * that IRQ if nothing is left in the chain. -+ * ------------------------------------------------------------ -+ */ -+static void -+rs_close(struct tty_struct *tty, struct file * filp) -+{ -+ struct e100_serial * info = (struct e100_serial *)tty->driver_data; -+ unsigned long flags; -+ -+ if (!info) -+ return; -+ -+ /* interrupts are disabled for this entire function */ -+ -+ local_irq_save(flags); -+ -+ if (tty_hung_up_p(filp)) { -+ local_irq_restore(flags); -+ return; -+ } -+ -+#ifdef SERIAL_DEBUG_OPEN -+ printk("[%d] rs_close ttyS%d, count = %d\n", current->pid, -+ info->line, info->count); -+#endif -+ if ((tty->count == 1) && (info->count != 1)) { -+ /* -+ * Uh, oh. tty->count is 1, which means that the tty -+ * structure will be freed. Info->count should always -+ * be one in these conditions. If it's greater than -+ * one, we've got real problems, since it means the -+ * serial port won't be shutdown. -+ */ -+ printk(KERN_CRIT -+ "rs_close: bad serial port count; tty->count is 1, " -+ "info->count is %d\n", info->count); -+ info->count = 1; -+ } -+ if (--info->count < 0) { -+ printk(KERN_CRIT "rs_close: bad serial port count for ttyS%d: %d\n", -+ info->line, info->count); -+ info->count = 0; -+ } -+ if (info->count) { -+ local_irq_restore(flags); -+ return; -+ } -+ info->flags |= ASYNC_CLOSING; -+ /* -+ * Save the termios structure, since this port may have -+ * separate termios for callout and dialin. -+ */ -+ if (info->flags & ASYNC_NORMAL_ACTIVE) -+ info->normal_termios = *tty->termios; -+ /* -+ * Now we wait for the transmit buffer to clear; and we notify -+ * the line discipline to only process XON/XOFF characters. -+ */ -+ tty->closing = 1; -+ if (info->closing_wait != ASYNC_CLOSING_WAIT_NONE) -+ tty_wait_until_sent(tty, info->closing_wait); -+ /* -+ * At this point we stop accepting input. To do this, we -+ * disable the serial receiver and the DMA receive interrupt. -+ */ -+#ifdef SERIAL_HANDLE_EARLY_ERRORS -+ e100_disable_serial_data_irq(info); -+#endif -+ -+#ifndef CONFIG_SVINTO_SIM -+ e100_disable_rx(info); -+ e100_disable_rx_irq(info); -+ -+ if (info->flags & ASYNC_INITIALIZED) { -+ /* -+ * Before we drop DTR, make sure the UART transmitter -+ * has completely drained; this is especially -+ * important as we have a transmit FIFO! -+ */ -+ rs_wait_until_sent(tty, HZ); -+ } -+#endif -+ -+ shutdown(info); -+ rs_flush_buffer(tty); -+ tty_ldisc_flush(tty); -+ tty->closing = 0; -+ info->event = 0; -+ info->port.tty = NULL; -+ if (info->blocked_open) { -+ if (info->close_delay) -+ schedule_timeout_interruptible(info->close_delay); -+ wake_up_interruptible(&info->open_wait); -+ } -+ info->flags &= ~(ASYNC_NORMAL_ACTIVE|ASYNC_CLOSING); -+ wake_up_interruptible(&info->close_wait); -+ local_irq_restore(flags); -+ -+ /* port closed */ -+ -+#if defined(CONFIG_ETRAX_RS485) -+ if (info->rs485.flags & SER_RS485_ENABLED) { -+ info->rs485.flags &= ~(SER_RS485_ENABLED); -+#if defined(CONFIG_ETRAX_RS485_ON_PA) -+ *R_PORT_PA_DATA = port_pa_data_shadow &= ~(1 << rs485_pa_bit); -+#endif -+#if defined(CONFIG_ETRAX_RS485_ON_PORT_G) -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ rs485_port_g_bit, 0); -+#endif -+#if defined(CONFIG_ETRAX_RS485_LTC1387) -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ CONFIG_ETRAX_RS485_LTC1387_DXEN_PORT_G_BIT, 0); -+ REG_SHADOW_SET(R_PORT_G_DATA, port_g_data_shadow, -+ CONFIG_ETRAX_RS485_LTC1387_RXEN_PORT_G_BIT, 0); -+#endif -+ } -+#endif -+ -+ /* -+ * Release any allocated DMA irq's. -+ */ -+ if (info->dma_in_enabled) { -+ free_irq(info->dma_in_irq_nbr, info); -+ cris_free_dma(info->dma_in_nbr, info->dma_in_irq_description); -+ info->uses_dma_in = 0; -+#ifdef SERIAL_DEBUG_OPEN -+ printk(KERN_DEBUG "DMA irq '%s' freed\n", -+ info->dma_in_irq_description); -+#endif -+ } -+ if (info->dma_out_enabled) { -+ free_irq(info->dma_out_irq_nbr, info); -+ cris_free_dma(info->dma_out_nbr, info->dma_out_irq_description); -+ info->uses_dma_out = 0; -+#ifdef SERIAL_DEBUG_OPEN -+ printk(KERN_DEBUG "DMA irq '%s' freed\n", -+ info->dma_out_irq_description); -+#endif -+ } -+} -+ -+/* -+ * rs_wait_until_sent() --- wait until the transmitter is empty -+ */ -+static void rs_wait_until_sent(struct tty_struct *tty, int timeout) -+{ -+ unsigned long orig_jiffies; -+ struct e100_serial *info = (struct e100_serial *)tty->driver_data; -+ unsigned long curr_time = jiffies; -+ unsigned long curr_time_usec = GET_JIFFIES_USEC(); -+ long elapsed_usec = -+ (curr_time - info->last_tx_active) * (1000000/HZ) + -+ curr_time_usec - info->last_tx_active_usec; -+ -+ /* -+ * Check R_DMA_CHx_STATUS bit 0-6=number of available bytes in FIFO -+ * R_DMA_CHx_HWSW bit 31-16=nbr of bytes left in DMA buffer (0=64k) -+ */ -+ orig_jiffies = jiffies; -+ while (info->xmit.head != info->xmit.tail || /* More in send queue */ -+ (*info->ostatusadr & 0x007f) || /* more in FIFO */ -+ (elapsed_usec < 2*info->char_time_usec)) { -+ schedule_timeout_interruptible(1); -+ if (signal_pending(current)) -+ break; -+ if (timeout && time_after(jiffies, orig_jiffies + timeout)) -+ break; -+ curr_time = jiffies; -+ curr_time_usec = GET_JIFFIES_USEC(); -+ elapsed_usec = -+ (curr_time - info->last_tx_active) * (1000000/HZ) + -+ curr_time_usec - info->last_tx_active_usec; -+ } -+ set_current_state(TASK_RUNNING); -+} -+ -+/* -+ * rs_hangup() --- called by tty_hangup() when a hangup is signaled. -+ */ -+void -+rs_hangup(struct tty_struct *tty) -+{ -+ struct e100_serial * info = (struct e100_serial *)tty->driver_data; -+ -+ rs_flush_buffer(tty); -+ shutdown(info); -+ info->event = 0; -+ info->count = 0; -+ info->flags &= ~ASYNC_NORMAL_ACTIVE; -+ info->port.tty = NULL; -+ wake_up_interruptible(&info->open_wait); -+} -+ -+/* -+ * ------------------------------------------------------------ -+ * rs_open() and friends -+ * ------------------------------------------------------------ -+ */ -+static int -+block_til_ready(struct tty_struct *tty, struct file * filp, -+ struct e100_serial *info) -+{ -+ DECLARE_WAITQUEUE(wait, current); -+ unsigned long flags; -+ int retval; -+ int do_clocal = 0, extra_count = 0; -+ -+ /* -+ * If the device is in the middle of being closed, then block -+ * until it's done, and then try again. -+ */ -+ if (tty_hung_up_p(filp) || -+ (info->flags & ASYNC_CLOSING)) { -+ wait_event_interruptible_tty(info->close_wait, -+ !(info->flags & ASYNC_CLOSING)); -+#ifdef SERIAL_DO_RESTART -+ if (info->flags & ASYNC_HUP_NOTIFY) -+ return -EAGAIN; -+ else -+ return -ERESTARTSYS; -+#else -+ return -EAGAIN; -+#endif -+ } -+ -+ /* -+ * If non-blocking mode is set, or the port is not enabled, -+ * then make the check up front and then exit. -+ */ -+ if ((filp->f_flags & O_NONBLOCK) || -+ (tty->flags & (1 << TTY_IO_ERROR))) { -+ info->flags |= ASYNC_NORMAL_ACTIVE; -+ return 0; -+ } -+ -+ if (tty->termios->c_cflag & CLOCAL) { -+ do_clocal = 1; -+ } -+ -+ /* -+ * Block waiting for the carrier detect and the line to become -+ * free (i.e., not in use by the callout). While we are in -+ * this loop, info->count is dropped by one, so that -+ * rs_close() knows when to free things. We restore it upon -+ * exit, either normal or abnormal. -+ */ -+ retval = 0; -+ add_wait_queue(&info->open_wait, &wait); -+#ifdef SERIAL_DEBUG_OPEN -+ printk("block_til_ready before block: ttyS%d, count = %d\n", -+ info->line, info->count); -+#endif -+ local_irq_save(flags); -+ if (!tty_hung_up_p(filp)) { -+ extra_count++; -+ info->count--; -+ } -+ local_irq_restore(flags); -+ info->blocked_open++; -+ while (1) { -+ local_irq_save(flags); -+ /* assert RTS and DTR */ -+ e100_rts(info, 1); -+ e100_dtr(info, 1); -+ local_irq_restore(flags); -+ set_current_state(TASK_INTERRUPTIBLE); -+ if (tty_hung_up_p(filp) || -+ !(info->flags & ASYNC_INITIALIZED)) { -+#ifdef SERIAL_DO_RESTART -+ if (info->flags & ASYNC_HUP_NOTIFY) -+ retval = -EAGAIN; -+ else -+ retval = -ERESTARTSYS; -+#else -+ retval = -EAGAIN; -+#endif -+ break; -+ } -+ if (!(info->flags & ASYNC_CLOSING) && do_clocal) -+ /* && (do_clocal || DCD_IS_ASSERTED) */ -+ break; -+ if (signal_pending(current)) { -+ retval = -ERESTARTSYS; -+ break; -+ } -+#ifdef SERIAL_DEBUG_OPEN -+ printk("block_til_ready blocking: ttyS%d, count = %d\n", -+ info->line, info->count); -+#endif -+ tty_unlock(); -+ schedule(); -+ tty_lock(); -+ } -+ set_current_state(TASK_RUNNING); -+ remove_wait_queue(&info->open_wait, &wait); -+ if (extra_count) -+ info->count++; -+ info->blocked_open--; -+#ifdef SERIAL_DEBUG_OPEN -+ printk("block_til_ready after blocking: ttyS%d, count = %d\n", -+ info->line, info->count); -+#endif -+ if (retval) -+ return retval; -+ info->flags |= ASYNC_NORMAL_ACTIVE; -+ return 0; -+} -+ -+static void -+deinit_port(struct e100_serial *info) -+{ -+ if (info->dma_out_enabled) { -+ cris_free_dma(info->dma_out_nbr, info->dma_out_irq_description); -+ free_irq(info->dma_out_irq_nbr, info); -+ } -+ if (info->dma_in_enabled) { -+ cris_free_dma(info->dma_in_nbr, info->dma_in_irq_description); -+ free_irq(info->dma_in_irq_nbr, info); -+ } -+} -+ -+/* -+ * This routine is called whenever a serial port is opened. -+ * It performs the serial-specific initialization for the tty structure. -+ */ -+static int -+rs_open(struct tty_struct *tty, struct file * filp) -+{ -+ struct e100_serial *info; -+ int retval, line; -+ unsigned long page; -+ int allocated_resources = 0; -+ -+ /* find which port we want to open */ -+ line = tty->index; -+ -+ if (line < 0 || line >= NR_PORTS) -+ return -ENODEV; -+ -+ /* find the corresponding e100_serial struct in the table */ -+ info = rs_table + line; -+ -+ /* don't allow the opening of ports that are not enabled in the HW config */ -+ if (!info->enabled) -+ return -ENODEV; -+ -+#ifdef SERIAL_DEBUG_OPEN -+ printk("[%d] rs_open %s, count = %d\n", current->pid, tty->name, -+ info->count); -+#endif -+ -+ info->count++; -+ tty->driver_data = info; -+ info->port.tty = tty; -+ -+ info->port.tty->low_latency = (info->flags & ASYNC_LOW_LATENCY) ? 1 : 0; -+ -+ if (!tmp_buf) { -+ page = get_zeroed_page(GFP_KERNEL); -+ if (!page) { -+ return -ENOMEM; -+ } -+ if (tmp_buf) -+ free_page(page); -+ else -+ tmp_buf = (unsigned char *) page; -+ } -+ -+ /* -+ * If the port is in the middle of closing, bail out now -+ */ -+ if (tty_hung_up_p(filp) || -+ (info->flags & ASYNC_CLOSING)) { -+ wait_event_interruptible_tty(info->close_wait, -+ !(info->flags & ASYNC_CLOSING)); -+#ifdef SERIAL_DO_RESTART -+ return ((info->flags & ASYNC_HUP_NOTIFY) ? -+ -EAGAIN : -ERESTARTSYS); -+#else -+ return -EAGAIN; -+#endif -+ } -+ -+ /* -+ * If DMA is enabled try to allocate the irq's. -+ */ -+ if (info->count == 1) { -+ allocated_resources = 1; -+ if (info->dma_in_enabled) { -+ if (request_irq(info->dma_in_irq_nbr, -+ rec_interrupt, -+ info->dma_in_irq_flags, -+ info->dma_in_irq_description, -+ info)) { -+ printk(KERN_WARNING "DMA irq '%s' busy; " -+ "falling back to non-DMA mode\n", -+ info->dma_in_irq_description); -+ /* Make sure we never try to use DMA in */ -+ /* for the port again. */ -+ info->dma_in_enabled = 0; -+ } else if (cris_request_dma(info->dma_in_nbr, -+ info->dma_in_irq_description, -+ DMA_VERBOSE_ON_ERROR, -+ info->dma_owner)) { -+ free_irq(info->dma_in_irq_nbr, info); -+ printk(KERN_WARNING "DMA '%s' busy; " -+ "falling back to non-DMA mode\n", -+ info->dma_in_irq_description); -+ /* Make sure we never try to use DMA in */ -+ /* for the port again. */ -+ info->dma_in_enabled = 0; -+ } -+#ifdef SERIAL_DEBUG_OPEN -+ else -+ printk(KERN_DEBUG "DMA irq '%s' allocated\n", -+ info->dma_in_irq_description); -+#endif -+ } -+ if (info->dma_out_enabled) { -+ if (request_irq(info->dma_out_irq_nbr, -+ tr_interrupt, -+ info->dma_out_irq_flags, -+ info->dma_out_irq_description, -+ info)) { -+ printk(KERN_WARNING "DMA irq '%s' busy; " -+ "falling back to non-DMA mode\n", -+ info->dma_out_irq_description); -+ /* Make sure we never try to use DMA out */ -+ /* for the port again. */ -+ info->dma_out_enabled = 0; -+ } else if (cris_request_dma(info->dma_out_nbr, -+ info->dma_out_irq_description, -+ DMA_VERBOSE_ON_ERROR, -+ info->dma_owner)) { -+ free_irq(info->dma_out_irq_nbr, info); -+ printk(KERN_WARNING "DMA '%s' busy; " -+ "falling back to non-DMA mode\n", -+ info->dma_out_irq_description); -+ /* Make sure we never try to use DMA out */ -+ /* for the port again. */ -+ info->dma_out_enabled = 0; -+ } -+#ifdef SERIAL_DEBUG_OPEN -+ else -+ printk(KERN_DEBUG "DMA irq '%s' allocated\n", -+ info->dma_out_irq_description); -+#endif -+ } -+ } -+ -+ /* -+ * Start up the serial port -+ */ -+ -+ retval = startup(info); -+ if (retval) { -+ if (allocated_resources) -+ deinit_port(info); -+ -+ /* FIXME Decrease count info->count here too? */ -+ return retval; -+ } -+ -+ -+ retval = block_til_ready(tty, filp, info); -+ if (retval) { -+#ifdef SERIAL_DEBUG_OPEN -+ printk("rs_open returning after block_til_ready with %d\n", -+ retval); -+#endif -+ if (allocated_resources) -+ deinit_port(info); -+ -+ return retval; -+ } -+ -+ if ((info->count == 1) && (info->flags & ASYNC_SPLIT_TERMIOS)) { -+ *tty->termios = info->normal_termios; -+ change_speed(info); -+ } -+ -+#ifdef SERIAL_DEBUG_OPEN -+ printk("rs_open ttyS%d successful...\n", info->line); -+#endif -+ DLOG_INT_TRIG( log_int_pos = 0); -+ -+ DFLIP( if (info->line == SERIAL_DEBUG_LINE) { -+ info->icount.rx = 0; -+ } ); -+ -+ return 0; -+} -+ -+#ifdef CONFIG_PROC_FS -+/* -+ * /proc fs routines.... -+ */ -+ -+static void seq_line_info(struct seq_file *m, struct e100_serial *info) -+{ -+ unsigned long tmp; -+ -+ seq_printf(m, "%d: uart:E100 port:%lX irq:%d", -+ info->line, (unsigned long)info->ioport, info->irq); -+ -+ if (!info->ioport || (info->type == PORT_UNKNOWN)) { -+ seq_printf(m, "\n"); -+ return; -+ } -+ -+ seq_printf(m, " baud:%d", info->baud); -+ seq_printf(m, " tx:%lu rx:%lu", -+ (unsigned long)info->icount.tx, -+ (unsigned long)info->icount.rx); -+ tmp = CIRC_CNT(info->xmit.head, info->xmit.tail, SERIAL_XMIT_SIZE); -+ if (tmp) -+ seq_printf(m, " tx_pend:%lu/%lu", -+ (unsigned long)tmp, -+ (unsigned long)SERIAL_XMIT_SIZE); -+ -+ seq_printf(m, " rx_pend:%lu/%lu", -+ (unsigned long)info->recv_cnt, -+ (unsigned long)info->max_recv_cnt); -+ -+#if 1 -+ if (info->port.tty) { -+ if (info->port.tty->stopped) -+ seq_printf(m, " stopped:%i", -+ (int)info->port.tty->stopped); -+ if (info->port.tty->hw_stopped) -+ seq_printf(m, " hw_stopped:%i", -+ (int)info->port.tty->hw_stopped); -+ } -+ -+ { -+ unsigned char rstat = info->ioport[REG_STATUS]; -+ if (rstat & IO_MASK(R_SERIAL0_STATUS, xoff_detect)) -+ seq_printf(m, " xoff_detect:1"); -+ } -+ -+#endif -+ -+ if (info->icount.frame) -+ seq_printf(m, " fe:%lu", (unsigned long)info->icount.frame); -+ -+ if (info->icount.parity) -+ seq_printf(m, " pe:%lu", (unsigned long)info->icount.parity); -+ -+ if (info->icount.brk) -+ seq_printf(m, " brk:%lu", (unsigned long)info->icount.brk); -+ -+ if (info->icount.overrun) -+ seq_printf(m, " oe:%lu", (unsigned long)info->icount.overrun); -+ -+ /* -+ * Last thing is the RS-232 status lines -+ */ -+ if (!E100_RTS_GET(info)) -+ seq_puts(m, "|RTS"); -+ if (!E100_CTS_GET(info)) -+ seq_puts(m, "|CTS"); -+ if (!E100_DTR_GET(info)) -+ seq_puts(m, "|DTR"); -+ if (!E100_DSR_GET(info)) -+ seq_puts(m, "|DSR"); -+ if (!E100_CD_GET(info)) -+ seq_puts(m, "|CD"); -+ if (!E100_RI_GET(info)) -+ seq_puts(m, "|RI"); -+ seq_puts(m, "\n"); -+} -+ -+ -+static int crisv10_proc_show(struct seq_file *m, void *v) -+{ -+ int i; -+ -+ seq_printf(m, "serinfo:1.0 driver:%s\n", serial_version); -+ -+ for (i = 0; i < NR_PORTS; i++) { -+ if (!rs_table[i].enabled) -+ continue; -+ seq_line_info(m, &rs_table[i]); -+ } -+#ifdef DEBUG_LOG_INCLUDED -+ for (i = 0; i < debug_log_pos; i++) { -+ seq_printf(m, "%-4i %lu.%lu ", -+ i, debug_log[i].time, -+ timer_data_to_ns(debug_log[i].timer_data)); -+ seq_printf(m, debug_log[i].string, debug_log[i].value); -+ } -+ seq_printf(m, "debug_log %i/%i\n", i, DEBUG_LOG_SIZE); -+ debug_log_pos = 0; -+#endif -+ return 0; -+} -+ -+static int crisv10_proc_open(struct inode *inode, struct file *file) -+{ -+ return single_open(file, crisv10_proc_show, NULL); -+} -+ -+static const struct file_operations crisv10_proc_fops = { -+ .owner = THIS_MODULE, -+ .open = crisv10_proc_open, -+ .read = seq_read, -+ .llseek = seq_lseek, -+ .release = single_release, -+}; -+#endif -+ -+ -+/* Finally, routines used to initialize the serial driver. */ -+ -+static void show_serial_version(void) -+{ -+ printk(KERN_INFO -+ "ETRAX 100LX serial-driver %s, " -+ "(c) 2000-2004 Axis Communications AB\r\n", -+ &serial_version[11]); /* "$Revision: x.yy" */ -+} -+ -+/* rs_init inits the driver at boot (using the module_init chain) */ -+ -+static const struct tty_operations rs_ops = { -+ .open = rs_open, -+ .close = rs_close, -+ .write = rs_write, -+ .flush_chars = rs_flush_chars, -+ .write_room = rs_write_room, -+ .chars_in_buffer = rs_chars_in_buffer, -+ .flush_buffer = rs_flush_buffer, -+ .ioctl = rs_ioctl, -+ .throttle = rs_throttle, -+ .unthrottle = rs_unthrottle, -+ .set_termios = rs_set_termios, -+ .stop = rs_stop, -+ .start = rs_start, -+ .hangup = rs_hangup, -+ .break_ctl = rs_break, -+ .send_xchar = rs_send_xchar, -+ .wait_until_sent = rs_wait_until_sent, -+ .tiocmget = rs_tiocmget, -+ .tiocmset = rs_tiocmset, -+#ifdef CONFIG_PROC_FS -+ .proc_fops = &crisv10_proc_fops, -+#endif -+}; -+ -+static int __init rs_init(void) -+{ -+ int i; -+ struct e100_serial *info; -+ struct tty_driver *driver = alloc_tty_driver(NR_PORTS); -+ -+ if (!driver) -+ return -ENOMEM; -+ -+ show_serial_version(); -+ -+ /* Setup the timed flush handler system */ -+ -+#if !defined(CONFIG_ETRAX_SERIAL_FAST_TIMER) -+ setup_timer(&flush_timer, timed_flush_handler, 0); -+ mod_timer(&flush_timer, jiffies + 5); -+#endif -+ -+#if defined(CONFIG_ETRAX_RS485) -+#if defined(CONFIG_ETRAX_RS485_ON_PA) -+ if (cris_io_interface_allocate_pins(if_ser0, 'a', rs485_pa_bit, -+ rs485_pa_bit)) { -+ printk(KERN_CRIT "ETRAX100LX serial: Could not allocate " -+ "RS485 pin\n"); -+ put_tty_driver(driver); -+ return -EBUSY; -+ } -+#endif -+#if defined(CONFIG_ETRAX_RS485_ON_PORT_G) -+ if (cris_io_interface_allocate_pins(if_ser0, 'g', rs485_pa_bit, -+ rs485_port_g_bit)) { -+ printk(KERN_CRIT "ETRAX100LX serial: Could not allocate " -+ "RS485 pin\n"); -+ put_tty_driver(driver); -+ return -EBUSY; -+ } -+#endif -+#endif -+ -+ /* Initialize the tty_driver structure */ -+ -+ driver->driver_name = "serial"; -+ driver->name = "ttyS"; -+ driver->major = TTY_MAJOR; -+ driver->minor_start = 64; -+ driver->type = TTY_DRIVER_TYPE_SERIAL; -+ driver->subtype = SERIAL_TYPE_NORMAL; -+ driver->init_termios = tty_std_termios; -+ driver->init_termios.c_cflag = -+ B115200 | CS8 | CREAD | HUPCL | CLOCAL; /* is normally B9600 default... */ -+ driver->init_termios.c_ispeed = 115200; -+ driver->init_termios.c_ospeed = 115200; -+ driver->flags = TTY_DRIVER_REAL_RAW | TTY_DRIVER_DYNAMIC_DEV; -+ -+ tty_set_operations(driver, &rs_ops); -+ serial_driver = driver; -+ if (tty_register_driver(driver)) -+ panic("Couldn't register serial driver\n"); -+ /* do some initializing for the separate ports */ -+ -+ for (i = 0, info = rs_table; i < NR_PORTS; i++,info++) { -+ if (info->enabled) { -+ if (cris_request_io_interface(info->io_if, -+ info->io_if_description)) { -+ printk(KERN_CRIT "ETRAX100LX async serial: " -+ "Could not allocate IO pins for " -+ "%s, port %d\n", -+ info->io_if_description, i); -+ info->enabled = 0; -+ } -+ } -+ info->uses_dma_in = 0; -+ info->uses_dma_out = 0; -+ info->line = i; -+ info->port.tty = NULL; -+ info->type = PORT_ETRAX; -+ info->tr_running = 0; -+ info->forced_eop = 0; -+ info->baud_base = DEF_BAUD_BASE; -+ info->custom_divisor = 0; -+ info->flags = 0; -+ info->close_delay = 5*HZ/10; -+ info->closing_wait = 30*HZ; -+ info->x_char = 0; -+ info->event = 0; -+ info->count = 0; -+ info->blocked_open = 0; -+ info->normal_termios = driver->init_termios; -+ init_waitqueue_head(&info->open_wait); -+ init_waitqueue_head(&info->close_wait); -+ info->xmit.buf = NULL; -+ info->xmit.tail = info->xmit.head = 0; -+ info->first_recv_buffer = info->last_recv_buffer = NULL; -+ info->recv_cnt = info->max_recv_cnt = 0; -+ info->last_tx_active_usec = 0; -+ info->last_tx_active = 0; -+ -+#if defined(CONFIG_ETRAX_RS485) -+ /* Set sane defaults */ -+ info->rs485.flags &= ~(SER_RS485_RTS_ON_SEND); -+ info->rs485.flags |= SER_RS485_RTS_AFTER_SEND; -+ info->rs485.flags &= ~(SER_RS485_RTS_BEFORE_SEND); -+ info->rs485.delay_rts_before_send = 0; -+ info->rs485.flags &= ~(SER_RS485_ENABLED); -+#endif -+ INIT_WORK(&info->work, do_softint); -+ -+ if (info->enabled) { -+ printk(KERN_INFO "%s%d at %p is a builtin UART with DMA\n", -+ serial_driver->name, info->line, info->ioport); -+ } -+ } -+#ifdef CONFIG_ETRAX_FAST_TIMER -+#ifdef CONFIG_ETRAX_SERIAL_FAST_TIMER -+ memset(fast_timers, 0, sizeof(fast_timers)); -+#endif -+#ifdef CONFIG_ETRAX_RS485 -+ memset(fast_timers_rs485, 0, sizeof(fast_timers_rs485)); -+#endif -+ fast_timer_init(); -+#endif -+ -+#ifndef CONFIG_SVINTO_SIM -+#ifndef CONFIG_ETRAX_KGDB -+ /* Not needed in simulator. May only complicate stuff. */ -+ /* hook the irq's for DMA channel 6 and 7, serial output and input, and some more... */ -+ -+ if (request_irq(SERIAL_IRQ_NBR, ser_interrupt, -+ IRQF_SHARED | IRQF_DISABLED, "serial ", driver)) -+ panic("%s: Failed to request irq8", __func__); -+ -+#endif -+#endif /* CONFIG_SVINTO_SIM */ -+ -+ return 0; -+} -+ -+/* this makes sure that rs_init is called during kernel boot */ -+ -+module_init(rs_init); diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-cris-dbg.h linux-2.6.39/drivers/usb/host/hc-cris-dbg.h --- linux-2.6.39.orig/drivers/usb/host/hc-cris-dbg.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/usb/host/hc-cris-dbg.h 2011-07-28 16:16:37.503543830 +0200 ++++ linux-2.6.39/drivers/usb/host/hc-cris-dbg.h 2011-08-22 08:58:56.307980767 +0200 @@ -0,0 +1,146 @@ + +/* macros for debug output */ @@ -8020,7 +563,7 @@ diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-cris-dbg.h linux-2.6.39/drivers/ + }) diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-crisv10.c linux-2.6.39/drivers/usb/host/hc-crisv10.c --- linux-2.6.39.orig/drivers/usb/host/hc-crisv10.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/usb/host/hc-crisv10.c 2011-07-28 16:16:37.633441816 +0200 ++++ linux-2.6.39/drivers/usb/host/hc-crisv10.c 2011-08-22 08:58:56.397980354 +0200 @@ -0,0 +1,4801 @@ +/* + * @@ -12825,7 +5368,7 @@ diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-crisv10.c linux-2.6.39/drivers/u +module_exit(module_hcd_exit); diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-crisv10.h linux-2.6.39/drivers/usb/host/hc-crisv10.h --- linux-2.6.39.orig/drivers/usb/host/hc-crisv10.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/usb/host/hc-crisv10.h 2011-07-28 16:16:37.757174124 +0200 ++++ linux-2.6.39/drivers/usb/host/hc-crisv10.h 2011-08-22 08:58:56.467980502 +0200 @@ -0,0 +1,331 @@ +#ifndef __LINUX_ETRAX_USB_H +#define __LINUX_ETRAX_USB_H @@ -13160,7 +5703,7 @@ diff -Nur linux-2.6.39.orig/drivers/usb/host/hc-crisv10.h linux-2.6.39/drivers/u +#endif diff -Nur linux-2.6.39.orig/drivers/usb/host/Makefile linux-2.6.39/drivers/usb/host/Makefile --- linux-2.6.39.orig/drivers/usb/host/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/usb/host/Makefile 2011-07-28 16:16:37.863421513 +0200 ++++ linux-2.6.39/drivers/usb/host/Makefile 2011-08-22 08:58:56.527980204 +0200 @@ -32,6 +32,7 @@ obj-$(CONFIG_USB_R8A66597_HCD) += r8a66597-hcd.o obj-$(CONFIG_USB_ISP1760_HCD) += isp1760.o @@ -13171,7 +5714,7 @@ diff -Nur linux-2.6.39.orig/drivers/usb/host/Makefile linux-2.6.39/drivers/usb/h obj-$(CONFIG_USB_OCTEON2_COMMON) += octeon2-common.o diff -Nur linux-2.6.39.orig/drivers/usb/Makefile linux-2.6.39/drivers/usb/Makefile --- linux-2.6.39.orig/drivers/usb/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/usb/Makefile 2011-07-28 16:16:37.993659487 +0200 ++++ linux-2.6.39/drivers/usb/Makefile 2011-08-22 08:58:56.607990534 +0200 @@ -21,6 +21,7 @@ obj-$(CONFIG_USB_R8A66597_HCD) += host/ obj-$(CONFIG_USB_HWA_HCD) += host/ @@ -13182,7 +5725,7 @@ diff -Nur linux-2.6.39.orig/drivers/usb/Makefile linux-2.6.39/drivers/usb/Makefi obj-$(CONFIG_USB_C67X00_HCD) += c67x00/ diff -Nur linux-2.6.39.orig/lib/klist.c linux-2.6.39/lib/klist.c --- linux-2.6.39.orig/lib/klist.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/lib/klist.c 2011-07-28 16:16:38.103425277 +0200 ++++ linux-2.6.39/lib/klist.c 2011-08-22 08:58:56.667990229 +0200 @@ -60,7 +60,7 @@ { knode->n_klist = klist; -- cgit v1.2.3 From 1430d117c0fcfc9f3b954ebce078745fb172a826 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Mon, 22 Aug 2011 09:59:55 +0200 Subject: enable x86_64 --- jtools/qemu/Makefile | 2 +- mk/vars.mk | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/jtools/qemu/Makefile b/jtools/qemu/Makefile index c83a6d987..b6add732e 100644 --- a/jtools/qemu/Makefile +++ b/jtools/qemu/Makefile @@ -18,7 +18,7 @@ $(WRKBUILD)/.configured: ${WRKDIST}/.prepared --host-cc=$(CC_FOR_BUILD) \ --disable-system \ --disable-sdl \ - --target-list=arm-linux-user,i386-linux-user,mipsel-linux-user \ + --target-list=arm-linux-user,i386-linux-user,mipsel-linux-user,x86_64-linux-user \ ) touch $@ diff --git a/mk/vars.mk b/mk/vars.mk index d4f64d068..89d78be83 100644 --- a/mk/vars.mk +++ b/mk/vars.mk @@ -59,6 +59,9 @@ endif ifeq ($(CPU_ARCH),i686) QEMU:= qemu-i386 endif +ifeq ($(CPU_ARCH),x86_64) +QEMU:= qemu-x86_64 +endif ifeq ($(ADK_NATIVE),y) TARGET_CROSS:= -- cgit v1.2.3 From 31b8a0a342a4525e9540a25883d0600ce9d374dc Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Tue, 23 Aug 2011 14:26:33 +0200 Subject: finetune qemu-ppc support, usable now --- target/linux/config/Config.in.netdevice | 10 +++ target/ppc/Makefile | 6 +- target/ppc/kernel.config | 150 ++++++++++++++++++++------------ 3 files changed, 108 insertions(+), 58 deletions(-) diff --git a/target/linux/config/Config.in.netdevice b/target/linux/config/Config.in.netdevice index 14820b810..dad3fcb0f 100644 --- a/target/linux/config/Config.in.netdevice +++ b/target/linux/config/Config.in.netdevice @@ -87,6 +87,16 @@ config ADK_KERNEL_AR231X_ETHERNET default n help +config ADK_KERNEL_NE2K_PCI + boolean + select ADK_KERNEL_NETDEVICES + select ADK_KERNEL_NET_ETHERNET + select ADK_KERNEL_NET_PCI + select ADK_KERNEL_MII + default y if ADK_TARGET_SYSTEM_QEMU_PPC + default n + help + config ADK_KERNEL_KORINA boolean select ADK_KERNEL_NETDEVICES diff --git a/target/ppc/Makefile b/target/ppc/Makefile index c643d6c5c..1b225d657 100644 --- a/target/ppc/Makefile +++ b/target/ppc/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/mk/modules.mk include $(TOPDIR)/mk/kernel-build.mk include $(TOPDIR)/mk/image.mk -KERNEL:=$(LINUX_DIR)/arch/powerpc/boot/zImage +KERNEL:=$(LINUX_DIR)/vmlinux ifeq ($(ADK_TARGET_FS),archive) imageinstall: $(BIN_DIR)/$(ROOTFSTARBALL) @@ -22,7 +22,7 @@ imageinstall: $(BIN_DIR)/$(INITRAMFS) @echo 'The initramfs image is: ${BIN_DIR}/${INITRAMFS}' ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC),y) @echo "Start qemu with following command line:" - @echo 'qemu-system-ppc -M mac99 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' + @echo 'qemu-system-ppc -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' endif endif ifeq ($(ADK_TARGET_FS),initramfs-piggyback) @@ -31,6 +31,6 @@ imageinstall: ${BUILD_DIR}/${INITRAMFS_PIGGYBACK} createinitramfs @echo 'The kernel+initramfs file is: $(BIN_DIR)/${TARGET_KERNEL}' ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC),y) @echo "Start qemu with following command line:" - @echo 'qemu-system-ppc -M mac99 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' + @echo 'qemu-system-ppc -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' endif endif diff --git a/target/ppc/kernel.config b/target/ppc/kernel.config index e075fd4ba..d97b641cc 100644 --- a/target/ppc/kernel.config +++ b/target/ppc/kernel.config @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.36 -# Fri Nov 19 00:22:49 2010 +# Linux/powerpc 2.6.39 Kernel Configuration +# Tue Aug 23 14:16:21 2011 # # CONFIG_PPC64 is not set @@ -17,24 +17,23 @@ CONFIG_PPC_BOOK3S_32=y CONFIG_PPC_BOOK3S=y CONFIG_6xx=y CONFIG_PPC_FPU=y -# CONFIG_ALTIVEC is not set +CONFIG_ALTIVEC=y CONFIG_PPC_STD_MMU=y CONFIG_PPC_STD_MMU_32=y # CONFIG_PPC_MM_SLICES is not set CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set CONFIG_PPC32=y +CONFIG_32BIT=y CONFIG_WORD_SIZE=32 # CONFIG_ARCH_PHYS_ADDR_T_64BIT is not set +# CONFIG_ARCH_DMA_ADDR_T_64BIT is not set CONFIG_MMU=y CONFIG_GENERIC_CMOS_UPDATE=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y -CONFIG_GENERIC_HARDIRQS=y -CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y # CONFIG_HAVE_SETUP_PER_CPU_AREA is not set # CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set -CONFIG_IRQ_PER_CPU=y CONFIG_NR_IRQS=512 CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -44,6 +43,7 @@ CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_FIND_NEXT_BIT=y +CONFIG_GENERIC_FIND_BIT_LE=y # CONFIG_ARCH_NO_VIRT_TO_BUS is not set CONFIG_PPC=y CONFIG_EARLY_PRINTK=y @@ -62,6 +62,7 @@ CONFIG_ARCH_HIBERNATION_POSSIBLE=y CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y +CONFIG_HAVE_IRQ_WORK=y # # General setup @@ -78,30 +79,40 @@ CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set +CONFIG_HAVE_GENERIC_HARDIRQS=y + +# +# IRQ subsystem +# +CONFIG_GENERIC_HARDIRQS=y +CONFIG_HAVE_SPARSE_IRQ=y +CONFIG_GENERIC_IRQ_SHOW=y +CONFIG_GENERIC_IRQ_SHOW_LEVEL=y +# CONFIG_SPARSE_IRQ is not set # # RCU Subsystem # -CONFIG_TREE_RCU=y -# CONFIG_TINY_RCU is not set +CONFIG_TINY_RCU=y +# CONFIG_PREEMPT_RCU is not set # CONFIG_RCU_TRACE is not set -CONFIG_RCU_FANOUT=32 -# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=15 # CONFIG_CGROUPS is not set -# CONFIG_SYSFS_DEPRECATED_V2 is not set -# CONFIG_RELAY is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set +# CONFIG_SYSFS_DEPRECATED is not set +# CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_SYSCTL_SYSCALL=y # CONFIG_KALLSYMS is not set CONFIG_HOTPLUG=y @@ -117,6 +128,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y CONFIG_HAVE_PERF_EVENTS=y # @@ -215,6 +227,7 @@ CONFIG_PPC_PMAC=y # CONFIG_PPC_86xx is not set # CONFIG_EMBEDDED6xx is not set # CONFIG_AMIGAONE is not set +# CONFIG_KVM_GUEST is not set CONFIG_PPC_NATIVE=y CONFIG_PPC_OF_BOOT_TRAMPOLINE=y # CONFIG_UDBG_RTAS_CONSOLE is not set @@ -225,7 +238,7 @@ CONFIG_PPC_I8259=y CONFIG_PPC_RTAS=y CONFIG_RTAS_ERROR_LOGGING=y CONFIG_PPC_RTAS_DAEMON=y -CONFIG_RTAS_PROC=y +# CONFIG_RTAS_PROC is not set # CONFIG_MMIO_NVRAM is not set # CONFIG_MPIC_U3_HT_IRQS is not set CONFIG_PPC_MPC106=y @@ -233,7 +246,7 @@ CONFIG_PPC_MPC106=y # CONFIG_PPC_INDIRECT_IO is not set # CONFIG_GENERIC_IOMAP is not set # CONFIG_CPU_FREQ is not set -# CONFIG_PPC601_SYNC_FIX is not set +CONFIG_PPC601_SYNC_FIX=y # CONFIG_TAU is not set # CONFIG_FSL_ULI1575 is not set # CONFIG_SIMPLE_GPIO is not set @@ -264,7 +277,6 @@ CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set -# CONFIG_SPARSE_IRQ is not set CONFIG_MAX_ACTIVE_REGIONS=32 CONFIG_ARCH_FLATMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y @@ -275,6 +287,7 @@ CONFIG_FLAT_NODE_MEM_MAP=y CONFIG_HAVE_MEMBLOCK=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 +# CONFIG_COMPACTION is not set # CONFIG_MIGRATION is not set # CONFIG_PHYS_ADDR_T_64BIT is not set CONFIG_ZONE_DMA_FLAG=1 @@ -282,11 +295,13 @@ CONFIG_BOUNCE=y CONFIG_VIRT_TO_BUS=y # CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 +CONFIG_NEED_PER_CPU_KM=y CONFIG_PPC_4K_PAGES=y CONFIG_FORCE_MAX_ZONEORDER=11 -# CONFIG_CMDLINE_BOOL is not set +CONFIG_CMDLINE_BOOL=y +CONFIG_CMDLINE="console=ttyS0,9600 console=tty0" CONFIG_EXTRA_TARGETS="" -# CONFIG_PM is not set +# CONFIG_PM_RUNTIME is not set # CONFIG_SECCOMP is not set CONFIG_ISA_DMA_API=y @@ -310,6 +325,7 @@ CONFIG_ARCH_SUPPORTS_MSI=y # CONFIG_PCCARD is not set # CONFIG_HOTPLUG_PCI is not set # CONFIG_HAS_RAPIDIO is not set +# CONFIG_RAPIDIO is not set # # Advanced setup @@ -335,10 +351,9 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set -# CONFIG_NET_IPGRE is not set +# CONFIG_NET_IPGRE_DEMUX is not set # CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set @@ -379,6 +394,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -389,11 +405,18 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IRDA is not set # CONFIG_BT is not set # CONFIG_AF_RXRPC is not set -# CONFIG_WIRELESS is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +# CONFIG_LIB80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set # CONFIG_CAIF is not set +# CONFIG_CEPH_LIB is not set # # Device Drivers @@ -415,16 +438,19 @@ CONFIG_DTC=y CONFIG_OF=y # -# Flattened Device Tree and Open Firmware support +# Device Tree and Open Firmware support # # CONFIG_PROC_DEVICETREE is not set CONFIG_OF_FLATTREE=y +CONFIG_OF_EARLY_FLATTREE=y CONFIG_OF_DYNAMIC=y CONFIG_OF_ADDRESS=y CONFIG_OF_IRQ=y CONFIG_OF_DEVICE=y +CONFIG_OF_PCI=y # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set +# CONFIG_SENSORS_LIS3LV02D is not set # CONFIG_MISC_DEVICES is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -444,25 +470,19 @@ CONFIG_SCSI_MOD=y # # IEEE 1394 (FireWire) support # - -# -# You can enable one or both FireWire driver stacks. -# - -# -# The newer stack is recommended. -# # CONFIG_FIREWIRE is not set -# CONFIG_IEEE1394 is not set # CONFIG_FIREWIRE_NOSY is not set # CONFIG_I2O is not set CONFIG_MACINTOSH_DRIVERS=y -# CONFIG_ADB is not set -# CONFIG_ADB_CUDA is not set +CONFIG_ADB=y +CONFIG_ADB_CUDA=y # CONFIG_ADB_PMU is not set # CONFIG_PMAC_MEDIABAY is not set +# CONFIG_ADB_MACIO is not set +CONFIG_INPUT_ADBHID=y # CONFIG_MAC_EMUMOUSEBTN is not set # CONFIG_WINDFARM is not set +# CONFIG_ANSLCD is not set # CONFIG_PMAC_RACKMETER is not set # CONFIG_NETDEVICES is not set # CONFIG_ISDN is not set @@ -497,7 +517,15 @@ CONFIG_INPUT=y # # Hardware I/O ports # -# CONFIG_SERIO is not set +CONFIG_SERIO=y +# CONFIG_SERIO_I8042 is not set +# CONFIG_SERIO_SERPORT is not set +# CONFIG_SERIO_PCIPS2 is not set +# CONFIG_SERIO_LIBPS2 is not set +# CONFIG_SERIO_RAW is not set +# CONFIG_SERIO_XILINX_XPS_PS2 is not set +# CONFIG_SERIO_ALTERA_PS2 is not set +# CONFIG_SERIO_PS2MULT is not set # CONFIG_GAMEPORT is not set # @@ -508,20 +536,18 @@ CONFIG_VT=y CONFIG_VT_CONSOLE=y CONFIG_HW_CONSOLE=y # CONFIG_VT_HW_CONSOLE_BINDING is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set -# CONFIG_N_GSM is not set # CONFIG_NOZOMI is not set +# CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers # -CONFIG_SERIAL_8250=y -CONFIG_SERIAL_8250_CONSOLE=y -# CONFIG_SERIAL_8250_PCI is not set -CONFIG_SERIAL_8250_NR_UARTS=4 -CONFIG_SERIAL_8250_RUNTIME_UARTS=4 -# CONFIG_SERIAL_8250_EXTENDED is not set +# CONFIG_SERIAL_8250 is not set # # Non-8250 serial port support @@ -530,16 +556,15 @@ CONFIG_SERIAL_8250_RUNTIME_UARTS=4 # CONFIG_SERIAL_UARTLITE is not set CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y -# CONFIG_SERIAL_PMACZILOG is not set +CONFIG_SERIAL_PMACZILOG=y +CONFIG_SERIAL_PMACZILOG_TTYS=y +CONFIG_SERIAL_PMACZILOG_CONSOLE=y # CONFIG_SERIAL_JSM is not set -# CONFIG_SERIAL_OF_PLATFORM is not set # CONFIG_SERIAL_TIMBERDALE is not set -# CONFIG_SERIAL_GRLIB_GAISLER_APBUART is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set +# CONFIG_SERIAL_PCH_UART is not set +# CONFIG_TTY_PRINTK is not set # CONFIG_BRIQ_PANEL is not set # CONFIG_HVC_RTAS is not set # CONFIG_HVC_UDBG is not set @@ -559,6 +584,10 @@ CONFIG_DEVPORT=y # PPS support # # CONFIG_PPS is not set + +# +# PPS generators support +# CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set @@ -582,6 +611,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_AGP is not set # CONFIG_VGA_ARB is not set # CONFIG_DRM is not set +# CONFIG_STUB_POULSBO is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set # CONFIG_FB is not set @@ -605,6 +635,7 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set +# CONFIG_NFC_DEVICES is not set # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set # CONFIG_EDAC is not set @@ -661,17 +692,18 @@ CONFIG_RTC_DRV_M48T59=y # CONFIG_EXT4_FS is not set # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set -# CONFIG_FS_POSIX_ACL is not set # CONFIG_XFS_FS is not set -# CONFIG_OCFS2_FS is not set # CONFIG_BTRFS_FS is not set # CONFIG_NILFS2_FS is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set +# CONFIG_FANOTIFY is not set # CONFIG_QUOTA is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_QUOTACTL is not set # CONFIG_AUTOFS4_FS is not set # CONFIG_FUSE_FS is not set @@ -715,7 +747,6 @@ CONFIG_TMPFS=y CONFIG_MAC_PARTITION=y CONFIG_MSDOS_PARTITION=y # CONFIG_NLS is not set -# CONFIG_DLM is not set # CONFIG_BINARY_PRINTF is not set # @@ -730,16 +761,20 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y CONFIG_GENERIC_ATOMIC64=y +# CONFIG_AVERAGE is not set # # Kernel hacking # CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -748,11 +783,12 @@ CONFIG_FRAME_WARN=1024 # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set +# CONFIG_SPARSE_RCU_POINTER is not set CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_MEMORY_INIT is not set -# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set CONFIG_HAVE_FUNCTION_TRACER=y CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y @@ -764,16 +800,18 @@ CONFIG_TRACING_SUPPORT=y # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_TEST_KSTRTOX is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 -# CONFIG_BOOTX_TEXT is not set +CONFIG_BOOTX_TEXT=y # CONFIG_PPC_EARLY_DEBUG is not set # # Security options # # CONFIG_KEYS is not set +# CONFIG_SECURITY_DMESG_RESTRICT is not set # CONFIG_SECURITY is not set # CONFIG_SECURITYFS is not set CONFIG_DEFAULT_SECURITY_DAC=y @@ -864,6 +902,8 @@ CONFIG_CRYPTO=y # Random Number Generation # # CONFIG_CRYPTO_ANSI_CPRNG is not set +# CONFIG_CRYPTO_USER_API_HASH is not set +# CONFIG_CRYPTO_USER_API_SKCIPHER is not set # CONFIG_CRYPTO_HW is not set # -- cgit v1.2.3 From 0f664e8007ce59f13ae5c79cc4f88658b0c1338e Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 04:09:28 +0200 Subject: better ppc64 support, qemu still hangs @ returning from prom_init --- target/config/Config.in | 4 + target/ppc64/Makefile | 10 +- target/ppc64/kernel.config | 339 ++++++++++++++++++++++------------ target/ppc64/sys-available/qemu-ppc64 | 13 ++ toolchain/gcc/patches/no-lib64.patch | 48 +++-- 5 files changed, 283 insertions(+), 131 deletions(-) create mode 100644 target/ppc64/sys-available/qemu-ppc64 diff --git a/target/config/Config.in b/target/config/Config.in index a15e42e27..a5bbf06ef 100644 --- a/target/config/Config.in +++ b/target/config/Config.in @@ -249,6 +249,9 @@ config ADK_CPU_GEODE config ADK_CPU_PPC boolean +config ADK_CPU_PPC64 + boolean + config ADK_CPU_PENTIUM_M boolean @@ -278,6 +281,7 @@ config ADK_TARGET_CPU_ARCH default "armeb" if ADK_LINUX_ARM && ADK_big default "sparc" if ADK_LINUX_SPARC default "ppc" if ADK_CPU_PPC + default "ppc64" if ADK_CPU_PPC64 config ADK_TARGET_ABI_CFLAGS string diff --git a/target/ppc64/Makefile b/target/ppc64/Makefile index a60d376a9..0e9ac9547 100644 --- a/target/ppc64/Makefile +++ b/target/ppc64/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/mk/modules.mk include $(TOPDIR)/mk/kernel-build.mk include $(TOPDIR)/mk/image.mk -KERNEL:=$(LINUX_DIR)/arch/powerpc/boot/zImage +KERNEL:=$(LINUX_DIR)/vmlinux ifeq ($(ADK_TARGET_FS),archive) imageinstall: $(BIN_DIR)/$(ROOTFSTARBALL) @@ -20,9 +20,17 @@ imageinstall: $(BIN_DIR)/$(INITRAMFS) @cp $(KERNEL) $(BIN_DIR)/$(TARGET_KERNEL) @echo 'The kernel file is: $(BIN_DIR)/${TARGET_KERNEL}' @echo 'The initramfs image is: ${BIN_DIR}/${INITRAMFS}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC64),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-ppc64 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' +endif endif ifeq ($(ADK_TARGET_FS),initramfs-piggyback) imageinstall: ${BUILD_DIR}/${INITRAMFS_PIGGYBACK} createinitramfs @cp $(KERNEL) $(BIN_DIR)/${TARGET_KERNEL} @echo 'The kernel+initramfs file is: $(BIN_DIR)/${TARGET_KERNEL}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_PPC64),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-ppc64 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' +endif endif diff --git a/target/ppc64/kernel.config b/target/ppc64/kernel.config index e075fd4ba..0095cb373 100644 --- a/target/ppc64/kernel.config +++ b/target/ppc64/kernel.config @@ -1,40 +1,39 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.36 -# Fri Nov 19 00:22:49 2010 +# Linux/powerpc 2.6.39 Kernel Configuration +# Wed Aug 24 03:57:23 2011 # -# CONFIG_PPC64 is not set +CONFIG_PPC64=y # # Processor support # -CONFIG_PPC_BOOK3S_32=y -# CONFIG_PPC_85xx is not set -# CONFIG_PPC_8xx is not set -# CONFIG_40x is not set -# CONFIG_44x is not set -# CONFIG_E200 is not set +CONFIG_PPC_BOOK3S_64=y +# CONFIG_PPC_BOOK3E_64 is not set CONFIG_PPC_BOOK3S=y -CONFIG_6xx=y +# CONFIG_POWER4_ONLY is not set +CONFIG_POWER3=y +CONFIG_POWER4=y +# CONFIG_TUNE_CELL is not set CONFIG_PPC_FPU=y -# CONFIG_ALTIVEC is not set +CONFIG_ALTIVEC=y +# CONFIG_VSX is not set CONFIG_PPC_STD_MMU=y -CONFIG_PPC_STD_MMU_32=y +CONFIG_PPC_STD_MMU_64=y # CONFIG_PPC_MM_SLICES is not set +CONFIG_VIRT_CPU_ACCOUNTING=y CONFIG_PPC_HAVE_PMU_SUPPORT=y # CONFIG_SMP is not set -CONFIG_PPC32=y -CONFIG_WORD_SIZE=32 -# CONFIG_ARCH_PHYS_ADDR_T_64BIT is not set +CONFIG_64BIT=y +CONFIG_WORD_SIZE=64 +CONFIG_ARCH_PHYS_ADDR_T_64BIT=y +CONFIG_ARCH_DMA_ADDR_T_64BIT=y CONFIG_MMU=y CONFIG_GENERIC_CMOS_UPDATE=y CONFIG_GENERIC_TIME_VSYSCALL=y CONFIG_GENERIC_CLOCKEVENTS=y -CONFIG_GENERIC_HARDIRQS=y -CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y -# CONFIG_HAVE_SETUP_PER_CPU_AREA is not set -# CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK is not set -CONFIG_IRQ_PER_CPU=y +CONFIG_HAVE_SETUP_PER_CPU_AREA=y +CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK=y CONFIG_NR_IRQS=512 CONFIG_STACKTRACE_SUPPORT=y CONFIG_HAVE_LATENCYTOP_SUPPORT=y @@ -42,26 +41,32 @@ CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_LOCKDEP_SUPPORT=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_ARCH_HAS_ILOG2_U32=y +CONFIG_ARCH_HAS_ILOG2_U64=y CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_FIND_NEXT_BIT=y -# CONFIG_ARCH_NO_VIRT_TO_BUS is not set +CONFIG_GENERIC_FIND_BIT_LE=y +CONFIG_ARCH_NO_VIRT_TO_BUS=y CONFIG_PPC=y CONFIG_EARLY_PRINTK=y -CONFIG_GENERIC_NVRAM=y +CONFIG_COMPAT=y +CONFIG_SYSVIPC_COMPAT=y CONFIG_SCHED_OMIT_FRAME_POINTER=y CONFIG_ARCH_MAY_HAVE_PC_FDC=y CONFIG_PPC_OF=y -CONFIG_PPC_UDBG_16550=y -# CONFIG_GENERIC_TBSYNC is not set +# CONFIG_PPC_UDBG_16550 is not set +CONFIG_GENERIC_TBSYNC=y CONFIG_AUDIT_ARCH=y CONFIG_GENERIC_BUG=y # CONFIG_DEFAULT_UIMAGE is not set CONFIG_ARCH_HIBERNATION_POSSIBLE=y +CONFIG_ARCH_SUSPEND_POSSIBLE=y # CONFIG_PPC_DCR_NATIVE is not set # CONFIG_PPC_DCR_MMIO is not set +# CONFIG_PPC_OF_PLATFORM_PCI is not set CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y +CONFIG_HAVE_IRQ_WORK=y # # General setup @@ -78,37 +83,46 @@ CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set +CONFIG_HAVE_GENERIC_HARDIRQS=y + +# +# IRQ subsystem +# +CONFIG_GENERIC_HARDIRQS=y +CONFIG_HAVE_SPARSE_IRQ=y +CONFIG_GENERIC_IRQ_SHOW=y +CONFIG_GENERIC_IRQ_SHOW_LEVEL=y +# CONFIG_SPARSE_IRQ is not set # # RCU Subsystem # -CONFIG_TREE_RCU=y -# CONFIG_TINY_RCU is not set +CONFIG_TINY_RCU=y +# CONFIG_PREEMPT_RCU is not set # CONFIG_RCU_TRACE is not set -CONFIG_RCU_FANOUT=32 -# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=15 # CONFIG_CGROUPS is not set -# CONFIG_SYSFS_DEPRECATED_V2 is not set -# CONFIG_RELAY is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set +# CONFIG_SYSFS_DEPRECATED is not set +# CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_SYSCTL_SYSCALL=y # CONFIG_KALLSYMS is not set CONFIG_HOTPLUG=y CONFIG_PRINTK=y CONFIG_BUG=y # CONFIG_ELF_CORE is not set -CONFIG_PCSPKR_PLATFORM=y # CONFIG_BASE_FULL is not set CONFIG_FUTEX=y CONFIG_EPOLL=y @@ -117,6 +131,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y CONFIG_HAVE_PERF_EVENTS=y # @@ -134,6 +149,7 @@ CONFIG_SLAB=y CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y +CONFIG_HAVE_SYSCALL_WRAPPERS=y CONFIG_HAVE_IOREMAP_PROT=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y @@ -156,9 +172,9 @@ CONFIG_MODULE_FORCE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set +CONFIG_BLOCK_COMPAT=y # # IO Schedulers @@ -198,50 +214,47 @@ CONFIG_INLINE_WRITE_UNLOCK=y CONFIG_INLINE_WRITE_UNLOCK_IRQ=y # CONFIG_INLINE_WRITE_UNLOCK_IRQRESTORE is not set # CONFIG_MUTEX_SPIN_ON_OWNER is not set -# CONFIG_FREEZER is not set +CONFIG_FREEZER=y +CONFIG_PPC_MSI_BITMAP=y # # Platform support # -CONFIG_PPC_CHRP=y -# CONFIG_PPC_MPC512x is not set -# CONFIG_PPC_MPC52xx is not set +# CONFIG_PPC_PSERIES is not set +# CONFIG_PPC_ISERIES is not set CONFIG_PPC_PMAC=y +CONFIG_PPC_PMAC64=y +# CONFIG_PPC_MAPLE is not set +# CONFIG_PPC_PASEMI is not set +# CONFIG_PPC_PS3 is not set # CONFIG_PPC_CELL is not set # CONFIG_PPC_CELL_NATIVE is not set -# CONFIG_PPC_82xx is not set +# CONFIG_PPC_IBM_CELL_BLADE is not set +# CONFIG_PPC_CELLEB is not set +# CONFIG_PPC_CELL_QPACE is not set # CONFIG_PQ2ADS is not set -# CONFIG_PPC_83xx is not set -# CONFIG_PPC_86xx is not set -# CONFIG_EMBEDDED6xx is not set -# CONFIG_AMIGAONE is not set +# CONFIG_KVM_GUEST is not set CONFIG_PPC_NATIVE=y CONFIG_PPC_OF_BOOT_TRAMPOLINE=y -# CONFIG_UDBG_RTAS_CONSOLE is not set # CONFIG_IPIC is not set CONFIG_MPIC=y # CONFIG_MPIC_WEIRD is not set -CONFIG_PPC_I8259=y -CONFIG_PPC_RTAS=y -CONFIG_RTAS_ERROR_LOGGING=y -CONFIG_PPC_RTAS_DAEMON=y -CONFIG_RTAS_PROC=y +# CONFIG_PPC_I8259 is not set +CONFIG_U3_DART=y +# CONFIG_PPC_RTAS is not set # CONFIG_MMIO_NVRAM is not set -# CONFIG_MPIC_U3_HT_IRQS is not set -CONFIG_PPC_MPC106=y -# CONFIG_PPC_970_NAP is not set +CONFIG_MPIC_U3_HT_IRQS=y +# CONFIG_PPC_MPC106 is not set +CONFIG_PPC_970_NAP=y # CONFIG_PPC_INDIRECT_IO is not set # CONFIG_GENERIC_IOMAP is not set # CONFIG_CPU_FREQ is not set -# CONFIG_PPC601_SYNC_FIX is not set -# CONFIG_TAU is not set # CONFIG_FSL_ULI1575 is not set # CONFIG_SIMPLE_GPIO is not set # # Kernel options # -CONFIG_HIGHMEM=y # CONFIG_NO_HZ is not set # CONFIG_HIGH_RES_TIMERS is not set CONFIG_GENERIC_CLOCKEVENTS_BUILD=y @@ -255,75 +268,81 @@ CONFIG_PREEMPT_NONE=y # CONFIG_PREEMPT_VOLUNTARY is not set # CONFIG_PREEMPT is not set CONFIG_BINFMT_ELF=y +CONFIG_COMPAT_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set -# CONFIG_IOMMU_HELPER is not set +CONFIG_IOMMU_HELPER=y # CONFIG_SWIOTLB is not set CONFIG_ARCH_ENABLE_MEMORY_HOTPLUG=y CONFIG_ARCH_HAS_WALK_MEMORY=y CONFIG_ARCH_ENABLE_MEMORY_HOTREMOVE=y # CONFIG_KEXEC is not set # CONFIG_CRASH_DUMP is not set -# CONFIG_SPARSE_IRQ is not set -CONFIG_MAX_ACTIVE_REGIONS=32 +# CONFIG_NUMA is not set +CONFIG_MAX_ACTIVE_REGIONS=256 +CONFIG_ARCH_SELECT_MEMORY_MODEL=y CONFIG_ARCH_FLATMEM_ENABLE=y +CONFIG_ARCH_SPARSEMEM_ENABLE=y CONFIG_ARCH_POPULATES_NODE_MAP=y +CONFIG_SYS_SUPPORTS_HUGETLBFS=y CONFIG_SELECT_MEMORY_MODEL=y CONFIG_FLATMEM_MANUAL=y +# CONFIG_SPARSEMEM_MANUAL is not set CONFIG_FLATMEM=y CONFIG_FLAT_NODE_MEM_MAP=y +CONFIG_SPARSEMEM_VMEMMAP_ENABLE=y CONFIG_HAVE_MEMBLOCK=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 +# CONFIG_COMPACTION is not set # CONFIG_MIGRATION is not set -# CONFIG_PHYS_ADDR_T_64BIT is not set +CONFIG_PHYS_ADDR_T_64BIT=y CONFIG_ZONE_DMA_FLAG=1 CONFIG_BOUNCE=y -CONFIG_VIRT_TO_BUS=y # CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 +CONFIG_NEED_PER_CPU_KM=y +# CONFIG_PPC_HAS_HASH_64K is not set CONFIG_PPC_4K_PAGES=y -CONFIG_FORCE_MAX_ZONEORDER=11 -# CONFIG_CMDLINE_BOOL is not set +# CONFIG_PPC_64K_PAGES is not set +CONFIG_FORCE_MAX_ZONEORDER=13 +CONFIG_CMDLINE_BOOL=y +CONFIG_CMDLINE="console=ttyS0,9600 console=tty0" CONFIG_EXTRA_TARGETS="" -# CONFIG_PM is not set +CONFIG_ARCH_WANTS_FREEZER_CONTROL=y +CONFIG_SUSPEND=y +CONFIG_SUSPEND_FREEZER=y +CONFIG_PM_SLEEP=y +# CONFIG_PM_RUNTIME is not set +CONFIG_PM=y +# CONFIG_PM_DEBUG is not set # CONFIG_SECCOMP is not set CONFIG_ISA_DMA_API=y # # Bus options # -# CONFIG_ISA is not set CONFIG_ZONE_DMA=y -# CONFIG_NEED_DMA_MAP_STATE is not set +CONFIG_NEED_DMA_MAP_STATE=y CONFIG_NEED_SG_DMA_LENGTH=y CONFIG_GENERIC_ISA_DMA=y -CONFIG_PPC_INDIRECT_PCI=y +# CONFIG_PPC_INDIRECT_PCI is not set CONFIG_PCI=y CONFIG_PCI_DOMAINS=y CONFIG_PCI_SYSCALL=y # CONFIG_PCIEPORTBUS is not set CONFIG_ARCH_SUPPORTS_MSI=y -# CONFIG_PCI_MSI is not set +CONFIG_PCI_MSI=y # CONFIG_PCI_STUB is not set # CONFIG_PCI_IOV is not set # CONFIG_PCCARD is not set # CONFIG_HOTPLUG_PCI is not set # CONFIG_HAS_RAPIDIO is not set - -# -# Advanced setup -# -# CONFIG_ADVANCED_OPTIONS is not set - -# -# Default settings for advanced configuration options are used -# -CONFIG_LOWMEM_SIZE=0x30000000 -CONFIG_PAGE_OFFSET=0xc0000000 -CONFIG_KERNEL_START=0xc0000000 +# CONFIG_RAPIDIO is not set +# CONFIG_RELOCATABLE is not set +CONFIG_PAGE_OFFSET=0xc000000000000000 +CONFIG_KERNEL_START=0xc000000000000000 CONFIG_PHYSICAL_START=0x00000000 -CONFIG_TASK_SIZE=0xc0000000 CONFIG_NET=y # @@ -335,10 +354,9 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set -# CONFIG_NET_IPGRE is not set +# CONFIG_NET_IPGRE_DEMUX is not set # CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set @@ -379,6 +397,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -389,11 +408,18 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IRDA is not set # CONFIG_BT is not set # CONFIG_AF_RXRPC is not set -# CONFIG_WIRELESS is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +# CONFIG_LIB80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set # CONFIG_CAIF is not set +# CONFIG_CEPH_LIB is not set # # Device Drivers @@ -415,16 +441,19 @@ CONFIG_DTC=y CONFIG_OF=y # -# Flattened Device Tree and Open Firmware support +# Device Tree and Open Firmware support # # CONFIG_PROC_DEVICETREE is not set CONFIG_OF_FLATTREE=y +CONFIG_OF_EARLY_FLATTREE=y CONFIG_OF_DYNAMIC=y CONFIG_OF_ADDRESS=y CONFIG_OF_IRQ=y CONFIG_OF_DEVICE=y +CONFIG_OF_PCI=y # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set +# CONFIG_SENSORS_LIS3LV02D is not set # CONFIG_MISC_DEVICES is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -444,23 +473,13 @@ CONFIG_SCSI_MOD=y # # IEEE 1394 (FireWire) support # - -# -# You can enable one or both FireWire driver stacks. -# - -# -# The newer stack is recommended. -# # CONFIG_FIREWIRE is not set -# CONFIG_IEEE1394 is not set # CONFIG_FIREWIRE_NOSY is not set # CONFIG_I2O is not set CONFIG_MACINTOSH_DRIVERS=y -# CONFIG_ADB is not set -# CONFIG_ADB_CUDA is not set -# CONFIG_ADB_PMU is not set -# CONFIG_PMAC_MEDIABAY is not set +CONFIG_ADB_PMU=y +# CONFIG_ADB_PMU_LED is not set +CONFIG_PMAC_SMU=y # CONFIG_MAC_EMUMOUSEBTN is not set # CONFIG_WINDFARM is not set # CONFIG_PMAC_RACKMETER is not set @@ -497,7 +516,15 @@ CONFIG_INPUT=y # # Hardware I/O ports # -# CONFIG_SERIO is not set +CONFIG_SERIO=y +# CONFIG_SERIO_I8042 is not set +# CONFIG_SERIO_SERPORT is not set +# CONFIG_SERIO_PCIPS2 is not set +# CONFIG_SERIO_LIBPS2 is not set +# CONFIG_SERIO_RAW is not set +# CONFIG_SERIO_XILINX_XPS_PS2 is not set +# CONFIG_SERIO_ALTERA_PS2 is not set +# CONFIG_SERIO_PS2MULT is not set # CONFIG_GAMEPORT is not set # @@ -508,17 +535,20 @@ CONFIG_VT=y CONFIG_VT_CONSOLE=y CONFIG_HW_CONSOLE=y # CONFIG_VT_HW_CONSOLE_BINDING is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set -# CONFIG_N_GSM is not set # CONFIG_NOZOMI is not set +# CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers # CONFIG_SERIAL_8250=y CONFIG_SERIAL_8250_CONSOLE=y -# CONFIG_SERIAL_8250_PCI is not set +CONFIG_SERIAL_8250_PCI=y CONFIG_SERIAL_8250_NR_UARTS=4 CONFIG_SERIAL_8250_RUNTIME_UARTS=4 # CONFIG_SERIAL_8250_EXTENDED is not set @@ -527,28 +557,25 @@ CONFIG_SERIAL_8250_RUNTIME_UARTS=4 # Non-8250 serial port support # # CONFIG_SERIAL_MFD_HSU is not set -# CONFIG_SERIAL_UARTLITE is not set CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y -# CONFIG_SERIAL_PMACZILOG is not set +CONFIG_SERIAL_PMACZILOG=y +CONFIG_SERIAL_PMACZILOG_TTYS=y +CONFIG_SERIAL_PMACZILOG_CONSOLE=y # CONFIG_SERIAL_JSM is not set # CONFIG_SERIAL_OF_PLATFORM is not set # CONFIG_SERIAL_TIMBERDALE is not set -# CONFIG_SERIAL_GRLIB_GAISLER_APBUART is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set -# CONFIG_BRIQ_PANEL is not set -# CONFIG_HVC_RTAS is not set +# CONFIG_SERIAL_PCH_UART is not set +# CONFIG_TTY_PRINTK is not set # CONFIG_HVC_UDBG is not set # CONFIG_IPMI_HANDLER is not set # CONFIG_HW_RANDOM is not set -# CONFIG_NVRAM is not set # CONFIG_R3964 is not set # CONFIG_APPLICOM is not set # CONFIG_RAW_DRIVER is not set +# CONFIG_HANGCHECK_TIMER is not set # CONFIG_TCG_TPM is not set CONFIG_DEVPORT=y # CONFIG_RAMOOPS is not set @@ -559,6 +586,10 @@ CONFIG_DEVPORT=y # PPS support # # CONFIG_PPS is not set + +# +# PPS generators support +# CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set @@ -582,9 +613,63 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_AGP is not set # CONFIG_VGA_ARB is not set # CONFIG_DRM is not set +# CONFIG_STUB_POULSBO is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set -# CONFIG_FB is not set +CONFIG_FB=y +# CONFIG_FIRMWARE_EDID is not set +# CONFIG_FB_DDC is not set +# CONFIG_FB_BOOT_VESA_SUPPORT is not set +CONFIG_FB_CFB_FILLRECT=y +CONFIG_FB_CFB_COPYAREA=y +CONFIG_FB_CFB_IMAGEBLIT=y +# CONFIG_FB_CFB_REV_PIXELS_IN_BYTE is not set +# CONFIG_FB_SYS_FILLRECT is not set +# CONFIG_FB_SYS_COPYAREA is not set +# CONFIG_FB_SYS_IMAGEBLIT is not set +# CONFIG_FB_FOREIGN_ENDIAN is not set +# CONFIG_FB_SYS_FOPS is not set +# CONFIG_FB_WMT_GE_ROPS is not set +# CONFIG_FB_SVGALIB is not set +CONFIG_FB_MACMODES=y +# CONFIG_FB_BACKLIGHT is not set +# CONFIG_FB_MODE_HELPERS is not set +# CONFIG_FB_TILEBLITTING is not set + +# +# Frame buffer hardware drivers +# +# CONFIG_FB_CIRRUS is not set +# CONFIG_FB_PM2 is not set +# CONFIG_FB_CYBER2000 is not set +CONFIG_FB_OF=y +# CONFIG_FB_ASILIANT is not set +# CONFIG_FB_IMSTT is not set +# CONFIG_FB_VGA16 is not set +# CONFIG_FB_S1D13XXX is not set +# CONFIG_FB_NVIDIA is not set +# CONFIG_FB_RIVA is not set +# CONFIG_FB_MATROX is not set +# CONFIG_FB_RADEON is not set +# CONFIG_FB_ATY128 is not set +# CONFIG_FB_ATY is not set +# CONFIG_FB_S3 is not set +# CONFIG_FB_SAVAGE is not set +# CONFIG_FB_SIS is not set +# CONFIG_FB_NEOMAGIC is not set +# CONFIG_FB_KYRO is not set +# CONFIG_FB_3DFX is not set +# CONFIG_FB_VOODOO1 is not set +# CONFIG_FB_VT8623 is not set +# CONFIG_FB_TRIDENT is not set +# CONFIG_FB_ARK is not set +# CONFIG_FB_PM3 is not set +# CONFIG_FB_CARMINE is not set +# CONFIG_FB_IBM_GXT4500 is not set +# CONFIG_FB_VIRTUAL is not set +# CONFIG_FB_METRONOME is not set +# CONFIG_FB_MB862XX is not set +# CONFIG_FB_BROADSHEET is not set # CONFIG_BACKLIGHT_LCD_SUPPORT is not set # @@ -598,6 +683,13 @@ CONFIG_SSB_POSSIBLE=y CONFIG_VGA_CONSOLE=y # CONFIG_VGACON_SOFT_SCROLLBACK is not set CONFIG_DUMMY_CONSOLE=y +CONFIG_FRAMEBUFFER_CONSOLE=y +# CONFIG_FRAMEBUFFER_CONSOLE_DETECT_PRIMARY is not set +# CONFIG_FRAMEBUFFER_CONSOLE_ROTATION is not set +# CONFIG_FONTS is not set +CONFIG_FONT_8x8=y +CONFIG_FONT_8x16=y +# CONFIG_LOGO is not set # CONFIG_SOUND is not set # CONFIG_HID_SUPPORT is not set # CONFIG_USB_SUPPORT is not set @@ -605,6 +697,7 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set +# CONFIG_NFC_DEVICES is not set # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set # CONFIG_EDAC is not set @@ -661,17 +754,19 @@ CONFIG_RTC_DRV_M48T59=y # CONFIG_EXT4_FS is not set # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set -# CONFIG_FS_POSIX_ACL is not set # CONFIG_XFS_FS is not set -# CONFIG_OCFS2_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_BTRFS_FS is not set # CONFIG_NILFS2_FS is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set +# CONFIG_FANOTIFY is not set # CONFIG_QUOTA is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_QUOTACTL is not set # CONFIG_AUTOFS4_FS is not set # CONFIG_FUSE_FS is not set @@ -703,6 +798,7 @@ CONFIG_PROC_SYSCTL=y CONFIG_SYSFS=y CONFIG_TMPFS=y # CONFIG_TMPFS_POSIX_ACL is not set +# CONFIG_HUGETLBFS is not set # CONFIG_HUGETLB_PAGE is not set # CONFIG_CONFIGFS_FS is not set # CONFIG_MISC_FILESYSTEMS is not set @@ -715,7 +811,6 @@ CONFIG_TMPFS=y CONFIG_MAC_PARTITION=y CONFIG_MSDOS_PARTITION=y # CONFIG_NLS is not set -# CONFIG_DLM is not set # CONFIG_BINARY_PRINTF is not set # @@ -730,16 +825,19 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y -CONFIG_GENERIC_ATOMIC64=y +# CONFIG_AVERAGE is not set # # Kernel hacking # CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -748,11 +846,12 @@ CONFIG_FRAME_WARN=1024 # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set +# CONFIG_SPARSE_RCU_POINTER is not set CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_MEMORY_INIT is not set -# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set CONFIG_HAVE_FUNCTION_TRACER=y CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y @@ -764,16 +863,18 @@ CONFIG_TRACING_SUPPORT=y # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_TEST_KSTRTOX is not set # CONFIG_PPC_DISABLE_WERROR is not set CONFIG_PPC_WERROR=y CONFIG_PRINT_STACK_DEPTH=64 -# CONFIG_BOOTX_TEXT is not set +CONFIG_BOOTX_TEXT=y # CONFIG_PPC_EARLY_DEBUG is not set # # Security options # # CONFIG_KEYS is not set +# CONFIG_SECURITY_DMESG_RESTRICT is not set # CONFIG_SECURITY is not set # CONFIG_SECURITYFS is not set CONFIG_DEFAULT_SECURITY_DAC=y @@ -864,6 +965,8 @@ CONFIG_CRYPTO=y # Random Number Generation # # CONFIG_CRYPTO_ANSI_CPRNG is not set +# CONFIG_CRYPTO_USER_API_HASH is not set +# CONFIG_CRYPTO_USER_API_SKCIPHER is not set # CONFIG_CRYPTO_HW is not set # diff --git a/target/ppc64/sys-available/qemu-ppc64 b/target/ppc64/sys-available/qemu-ppc64 new file mode 100644 index 000000000..cb559267e --- /dev/null +++ b/target/ppc64/sys-available/qemu-ppc64 @@ -0,0 +1,13 @@ +config ADK_TARGET_SYSTEM_QEMU_PPC64 + bool "Qemu Emulator" + select ADK_ppc64 + select ADK_qemu_ppc64 + select ADK_CPU_PPC64 + select ADK_HARDWARE_QEMU + select ADK_TARGET_WITH_VGA + select ADK_TARGET_WITH_INPUT + select ADK_TARGET_WITH_PCI + select ADK_TARGET_WITH_HDD + help + Support for Qemu Emulator (PPC64). + diff --git a/toolchain/gcc/patches/no-lib64.patch b/toolchain/gcc/patches/no-lib64.patch index 5ad91ea50..5fc1225e1 100644 --- a/toolchain/gcc/patches/no-lib64.patch +++ b/toolchain/gcc/patches/no-lib64.patch @@ -1,6 +1,6 @@ -diff -Nur gcc-4.5.2.orig/gcc/config/i386/linux64.h gcc-4.5.2/gcc/config/i386/linux64.h ---- gcc-4.5.2.orig/gcc/config/i386/linux64.h 2010-03-24 21:44:48.000000000 +0100 -+++ gcc-4.5.2/gcc/config/i386/linux64.h 2011-04-23 22:49:31.087660410 +0200 +diff -Nur gcc-4.5.3.orig/gcc/config/i386/linux64.h gcc-4.5.3/gcc/config/i386/linux64.h +--- gcc-4.5.3.orig/gcc/config/i386/linux64.h 2010-03-24 21:44:48.000000000 +0100 ++++ gcc-4.5.3/gcc/config/i386/linux64.h 2011-08-24 01:58:27.000000000 +0200 @@ -59,7 +59,7 @@ done. */ @@ -10,9 +10,9 @@ diff -Nur gcc-4.5.2.orig/gcc/config/i386/linux64.h gcc-4.5.2/gcc/config/i386/lin #if TARGET_64BIT_DEFAULT #define SPEC_32 "m32" -diff -Nur gcc-4.5.2.orig/gcc/config/i386/t-linux64 gcc-4.5.2/gcc/config/i386/t-linux64 ---- gcc-4.5.2.orig/gcc/config/i386/t-linux64 2009-04-21 21:03:23.000000000 +0200 -+++ gcc-4.5.2/gcc/config/i386/t-linux64 2011-04-23 22:49:31.107660436 +0200 +diff -Nur gcc-4.5.3.orig/gcc/config/i386/t-linux64 gcc-4.5.3/gcc/config/i386/t-linux64 +--- gcc-4.5.3.orig/gcc/config/i386/t-linux64 2009-04-21 21:03:23.000000000 +0200 ++++ gcc-4.5.3/gcc/config/i386/t-linux64 2011-08-24 01:58:27.000000000 +0200 @@ -25,7 +25,7 @@ MULTILIB_OPTIONS = m64/m32 @@ -22,9 +22,9 @@ diff -Nur gcc-4.5.2.orig/gcc/config/i386/t-linux64 gcc-4.5.2/gcc/config/i386/t-l LIBGCC = stmp-multilib INSTALL_LIBGCC = install-multilib -diff -Nur gcc-4.5.2.orig/gcc/config/mips/linux64.h gcc-4.5.2/gcc/config/mips/linux64.h ---- gcc-4.5.2.orig/gcc/config/mips/linux64.h 2009-02-20 16:20:38.000000000 +0100 -+++ gcc-4.5.2/gcc/config/mips/linux64.h 2011-04-23 22:50:17.267672629 +0200 +diff -Nur gcc-4.5.3.orig/gcc/config/mips/linux64.h gcc-4.5.3/gcc/config/mips/linux64.h +--- gcc-4.5.3.orig/gcc/config/mips/linux64.h 2009-02-20 16:20:38.000000000 +0100 ++++ gcc-4.5.3/gcc/config/mips/linux64.h 2011-08-24 01:58:27.000000000 +0200 @@ -36,9 +36,9 @@ %{profile:-lc_p} %{!profile:-lc}}" @@ -38,9 +38,9 @@ diff -Nur gcc-4.5.2.orig/gcc/config/mips/linux64.h gcc-4.5.2/gcc/config/mips/lin #define LINUX_DYNAMIC_LINKERN32 \ CHOOSE_DYNAMIC_LINKER (GLIBC_DYNAMIC_LINKERN32, UCLIBC_DYNAMIC_LINKERN32) -diff -Nur gcc-4.5.2.orig/gcc/config/mips/t-linux64 gcc-4.5.2/gcc/config/mips/t-linux64 ---- gcc-4.5.2.orig/gcc/config/mips/t-linux64 2009-04-21 21:03:23.000000000 +0200 -+++ gcc-4.5.2/gcc/config/mips/t-linux64 2011-04-23 22:49:31.207663770 +0200 +diff -Nur gcc-4.5.3.orig/gcc/config/mips/t-linux64 gcc-4.5.3/gcc/config/mips/t-linux64 +--- gcc-4.5.3.orig/gcc/config/mips/t-linux64 2009-04-21 21:03:23.000000000 +0200 ++++ gcc-4.5.3/gcc/config/mips/t-linux64 2011-08-24 01:58:27.000000000 +0200 @@ -18,7 +18,7 @@ MULTILIB_OPTIONS = mabi=n32/mabi=32/mabi=64 @@ -50,3 +50,27 @@ diff -Nur gcc-4.5.2.orig/gcc/config/mips/t-linux64 gcc-4.5.2/gcc/config/mips/t-l EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o crtbeginS.o crtendS.o crtbeginT.o +diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/linux64.h gcc-4.5.3/gcc/config/rs6000/linux64.h +--- gcc-4.5.3.orig/gcc/config/rs6000/linux64.h 2010-11-17 07:09:53.000000000 +0100 ++++ gcc-4.5.3/gcc/config/rs6000/linux64.h 2011-08-24 02:01:35.000000000 +0200 +@@ -341,7 +341,7 @@ + #define LINK_OS_DEFAULT_SPEC "%(link_os_linux)" + + #define GLIBC_DYNAMIC_LINKER32 "/lib/ld.so.1" +-#define GLIBC_DYNAMIC_LINKER64 "/lib64/ld64.so.1" ++#define GLIBC_DYNAMIC_LINKER64 "/lib/ld64.so.1" + #define UCLIBC_DYNAMIC_LINKER32 "/lib/ld-uClibc.so.0" + #define UCLIBC_DYNAMIC_LINKER64 "/lib/ld64-uClibc.so.0" + #if UCLIBC_DEFAULT +diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/t-linux64 gcc-4.5.3/gcc/config/rs6000/t-linux64 +--- gcc-4.5.3.orig/gcc/config/rs6000/t-linux64 2009-04-21 21:03:23.000000000 +0200 ++++ gcc-4.5.3/gcc/config/rs6000/t-linux64 2011-08-24 02:00:50.000000000 +0200 +@@ -36,7 +36,7 @@ + MULTILIB_EXTRA_OPTS = fPIC mstrict-align + MULTILIB_EXCEPTIONS = m64/msoft-float + MULTILIB_EXCLUSIONS = m64/!m32/msoft-float +-MULTILIB_OSDIRNAMES = ../lib64 $(if $(wildcard $(shell echo $(SYSTEM_HEADER_DIR))/../../usr/lib32),../lib32,../lib) nof ++MULTILIB_OSDIRNAMES = ../lib $(if $(wildcard $(shell echo $(SYSTEM_HEADER_DIR))/../../usr/lib32),../lib32,../lib) nof + MULTILIB_MATCHES = $(MULTILIB_MATCHES_FLOAT) + + softfp_wrap_start := '\#ifndef __powerpc64__' -- cgit v1.2.3 From c39e8b5f6441ae3a9ba351bd5e3c2d31e0371415 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 05:38:26 +0200 Subject: add qemu sparc support --- mk/image.mk | 9 ++ target/config/Config.in | 1 + target/sparc/Makefile | 8 ++ target/sparc/kernel.config | 167 +++++++++++++++++++++++++++++++--- target/sparc/sys-available/qemu-sparc | 13 +++ 5 files changed, 183 insertions(+), 15 deletions(-) create mode 100644 target/sparc/sys-available/qemu-sparc diff --git a/mk/image.mk b/mk/image.mk index 8053ba43d..185164c22 100644 --- a/mk/image.mk +++ b/mk/image.mk @@ -65,12 +65,21 @@ kernel-package: $(KERNEL) $(TRACE) target/$(ADK_TARGET_ARCH)-install-kernel-package $(PKG_INSTALL) $(KERNEL_PKG) $(MAKE_TRACE) +ifeq ($(ADK_HARDWARE_QEMU),y) +TARGET_KERNEL= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_FS}-kernel +INITRAMFS= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_LIBC}-${ADK_TARGET_FS} +ROOTFSSQUASHFS= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.img +ROOTFSTARBALL= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}+kernel.tar.gz +ROOTFSUSERTARBALL= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.tar.gz +INITRAMFS_PIGGYBACK= ${ADK_TARGET_SYSTEM}-$(CPU_ARCH)-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.cpio +else TARGET_KERNEL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_FS}-kernel INITRAMFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS} ROOTFSSQUASHFS= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.img ROOTFSTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}+kernel.tar.gz ROOTFSUSERTARBALL= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.tar.gz INITRAMFS_PIGGYBACK= ${ADK_TARGET_SYSTEM}-${ADK_TARGET_LIBC}-${ADK_TARGET_FS}.cpio +endif ${BIN_DIR}/${ROOTFSTARBALL}: ${TARGET_DIR} kernel-package cd ${TARGET_DIR}; find . | sed -n '/^\.\//s///p' | \ diff --git a/target/config/Config.in b/target/config/Config.in index a5bbf06ef..62bcbf071 100644 --- a/target/config/Config.in +++ b/target/config/Config.in @@ -371,6 +371,7 @@ config ADK_TARGET_LIB_EGLIBC ADK_LINUX_MIPS64EL || \ ADK_LINUX_PPC || \ ADK_LINUX_PPC64 || \ + ADK_LINUX_SPARC || \ ADK_LINUX_SPARC64 || \ ADK_LINUX_X86 || \ ADK_LINUX_X86_64 diff --git a/target/sparc/Makefile b/target/sparc/Makefile index 39212d52e..5fe97c12a 100644 --- a/target/sparc/Makefile +++ b/target/sparc/Makefile @@ -20,9 +20,17 @@ imageinstall: $(BIN_DIR)/$(INITRAMFS) @cp $(KERNEL) $(BIN_DIR)/$(TARGET_KERNEL) @echo 'The kernel file is: $(BIN_DIR)/${TARGET_KERNEL}' @echo 'The initramfs image is: ${BIN_DIR}/${INITRAMFS}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_SPARC),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-sparc -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' +endif endif ifeq ($(ADK_TARGET_FS),initramfs-piggyback) imageinstall: ${BUILD_DIR}/${INITRAMFS_PIGGYBACK} createinitramfs @cp $(KERNEL) $(BIN_DIR)/${TARGET_KERNEL} @echo 'The kernel+initramfs file is: $(BIN_DIR)/${TARGET_KERNEL}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_SPARC),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-sparc -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' +endif endif diff --git a/target/sparc/kernel.config b/target/sparc/kernel.config index 47f75db63..7f48a15da 100644 --- a/target/sparc/kernel.config +++ b/target/sparc/kernel.config @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux/sparc 2.6.39-rc7 Kernel Configuration -# Sat May 21 13:52:37 2011 +# Linux/sparc 2.6.39 Kernel Configuration +# Wed Aug 24 05:35:52 2011 # # CONFIG_64BIT is not set CONFIG_SPARC=y @@ -250,6 +250,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ATM is not set # CONFIG_L2TP is not set # CONFIG_BRIDGE is not set +# CONFIG_NET_DSA is not set # CONFIG_VLAN_8021Q is not set # CONFIG_DECNET is not set # CONFIG_LLC2 is not set @@ -304,6 +305,7 @@ CONFIG_OF=y # CONFIG_OF_PROMTREE=y CONFIG_OF_DEVICE=y +CONFIG_OF_NET=y # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set # CONFIG_SENSORS_LIS3LV02D is not set @@ -316,11 +318,90 @@ CONFIG_HAVE_IDE=y # CONFIG_SCSI_MOD=y # CONFIG_RAID_ATTRS is not set -# CONFIG_SCSI is not set -# CONFIG_SCSI_DMA is not set +CONFIG_SCSI=y +CONFIG_SCSI_DMA=y +# CONFIG_SCSI_TGT is not set # CONFIG_SCSI_NETLINK is not set +# CONFIG_SCSI_PROC_FS is not set + +# +# SCSI support type (disk, tape, CD-ROM) +# +# CONFIG_BLK_DEV_SD is not set +# CONFIG_CHR_DEV_ST is not set +# CONFIG_CHR_DEV_OSST is not set +# CONFIG_BLK_DEV_SR is not set +# CONFIG_CHR_DEV_SG is not set +# CONFIG_CHR_DEV_SCH is not set +# CONFIG_SCSI_MULTI_LUN is not set +# CONFIG_SCSI_CONSTANTS is not set +# CONFIG_SCSI_LOGGING is not set +# CONFIG_SCSI_SCAN_ASYNC is not set +CONFIG_SCSI_WAIT_SCAN=m + +# +# SCSI Transports +# +CONFIG_SCSI_SPI_ATTRS=y +# CONFIG_SCSI_FC_ATTRS is not set +# CONFIG_SCSI_ISCSI_ATTRS is not set +# CONFIG_SCSI_SAS_ATTRS is not set +# CONFIG_SCSI_SAS_LIBSAS is not set +# CONFIG_SCSI_SRP_ATTRS is not set +CONFIG_SCSI_LOWLEVEL=y +# CONFIG_ISCSI_TCP is not set +# CONFIG_ISCSI_BOOT_SYSFS is not set +# CONFIG_SCSI_CXGB3_ISCSI is not set +# CONFIG_SCSI_CXGB4_ISCSI is not set +# CONFIG_SCSI_BNX2_ISCSI is not set +# CONFIG_SCSI_BNX2X_FCOE is not set +# CONFIG_BE2ISCSI is not set +# CONFIG_BLK_DEV_3W_XXXX_RAID is not set +# CONFIG_SCSI_HPSA is not set +# CONFIG_SCSI_3W_9XXX is not set +# CONFIG_SCSI_3W_SAS is not set +# CONFIG_SCSI_ACARD is not set +# CONFIG_SCSI_AACRAID is not set +# CONFIG_SCSI_AIC7XXX is not set +# CONFIG_SCSI_AIC7XXX_OLD is not set +# CONFIG_SCSI_AIC79XX is not set +# CONFIG_SCSI_AIC94XX is not set +# CONFIG_SCSI_MVSAS is not set +# CONFIG_SCSI_ARCMSR is not set +# CONFIG_MEGARAID_NEWGEN is not set +# CONFIG_MEGARAID_LEGACY is not set +# CONFIG_MEGARAID_SAS is not set +# CONFIG_SCSI_MPT2SAS is not set +# CONFIG_SCSI_HPTIOP is not set +# CONFIG_LIBFC is not set +# CONFIG_LIBFCOE is not set +# CONFIG_FCOE is not set +# CONFIG_SCSI_DMX3191D is not set +# CONFIG_SCSI_FUTURE_DOMAIN is not set +# CONFIG_SCSI_IPS is not set +# CONFIG_SCSI_INITIO is not set +# CONFIG_SCSI_INIA100 is not set +# CONFIG_SCSI_STEX is not set +# CONFIG_SCSI_SYM53C8XX_2 is not set +# CONFIG_SCSI_QLOGIC_1280 is not set +# CONFIG_SCSI_QLOGICPTI is not set +# CONFIG_SCSI_QLA_FC is not set +# CONFIG_SCSI_QLA_ISCSI is not set +# CONFIG_SCSI_LPFC is not set +# CONFIG_SCSI_DC395x is not set +# CONFIG_SCSI_DC390T is not set +# CONFIG_SCSI_NSP32 is not set +# CONFIG_SCSI_DEBUG is not set +CONFIG_SCSI_SUNESP=y +# CONFIG_SCSI_PMCRAID is not set +# CONFIG_SCSI_PM8001 is not set +# CONFIG_SCSI_SRP is not set +# CONFIG_SCSI_BFA_FC is not set +# CONFIG_SCSI_DH is not set +# CONFIG_SCSI_OSD_INITIATOR is not set # CONFIG_ATA is not set # CONFIG_MD is not set +# CONFIG_TARGET_CORE is not set # CONFIG_FUSION is not set # @@ -329,7 +410,62 @@ CONFIG_SCSI_MOD=y # CONFIG_FIREWIRE is not set # CONFIG_FIREWIRE_NOSY is not set # CONFIG_I2O is not set -# CONFIG_NETDEVICES is not set +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_MACVLAN is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set +# CONFIG_VETH is not set +# CONFIG_ARCNET is not set +# CONFIG_MII is not set +# CONFIG_PHYLIB is not set +CONFIG_NET_ETHERNET=y +CONFIG_SUNLANCE=y +# CONFIG_HAPPYMEAL is not set +# CONFIG_SUNBMAC is not set +# CONFIG_SUNQE is not set +# CONFIG_SUNGEM is not set +# CONFIG_CASSINI is not set +# CONFIG_NET_VENDOR_3COM is not set +# CONFIG_ETHOC is not set +# CONFIG_GRETH is not set +# CONFIG_DNET is not set +# CONFIG_NET_TULIP is not set +# CONFIG_HP100 is not set +# CONFIG_IBM_NEW_EMAC_ZMII is not set +# CONFIG_IBM_NEW_EMAC_RGMII is not set +# CONFIG_IBM_NEW_EMAC_TAH is not set +# CONFIG_IBM_NEW_EMAC_EMAC4 is not set +# CONFIG_IBM_NEW_EMAC_NO_FLOW_CTRL is not set +# CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set +# CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set +# CONFIG_NET_PCI is not set +# CONFIG_B44 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_ATL2 is not set +# CONFIG_NETDEV_1000 is not set +# CONFIG_NETDEV_10000 is not set +# CONFIG_TR is not set +# CONFIG_WLAN is not set + +# +# Enable WiMAX (Networking options) to see the WiMAX drivers +# +# CONFIG_WAN is not set + +# +# CAIF transport drivers +# +# CONFIG_FDDI is not set +# CONFIG_HIPPI is not set +# CONFIG_PPP is not set +# CONFIG_SLIP is not set +# CONFIG_NET_FC is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set +# CONFIG_VMXNET3 is not set # CONFIG_ISDN is not set # CONFIG_PHONE is not set @@ -384,25 +520,20 @@ CONFIG_UNIX98_PTYS=y # # Serial drivers # -CONFIG_SERIAL_8250=y -CONFIG_SERIAL_8250_CONSOLE=y -# CONFIG_SERIAL_8250_PCI is not set -CONFIG_SERIAL_8250_NR_UARTS=4 -CONFIG_SERIAL_8250_RUNTIME_UARTS=4 -# CONFIG_SERIAL_8250_EXTENDED is not set +# CONFIG_SERIAL_8250 is not set # # Non-8250 serial port support # # CONFIG_SERIAL_MFD_HSU is not set CONFIG_SERIAL_SUNCORE=y -# CONFIG_SERIAL_SUNZILOG is not set +CONFIG_SERIAL_SUNZILOG=y +CONFIG_SERIAL_SUNZILOG_CONSOLE=y # CONFIG_SERIAL_SUNSU is not set # CONFIG_SERIAL_SUNSAB is not set CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_JSM is not set -# CONFIG_SERIAL_OF_PLATFORM is not set # CONFIG_SERIAL_TIMBERDALE is not set # CONFIG_SERIAL_GRLIB_GAISLER_APBUART is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set @@ -535,9 +666,10 @@ CONFIG_RTC_DRV_M48T59=y # CONFIG_XFS_FS is not set # CONFIG_BTRFS_FS is not set # CONFIG_NILFS2_FS is not set -# CONFIG_FS_POSIX_ACL is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set # CONFIG_FANOTIFY is not set @@ -712,6 +844,11 @@ CONFIG_CRYPTO=y # CONFIG_CRYPTO_USER_API_HASH is not set # CONFIG_CRYPTO_USER_API_SKCIPHER is not set # CONFIG_CRYPTO_HW is not set + +# +# OCF Configuration +# +# CONFIG_OCF_OCF is not set # CONFIG_BINARY_PRINTF is not set # diff --git a/target/sparc/sys-available/qemu-sparc b/target/sparc/sys-available/qemu-sparc new file mode 100644 index 000000000..0a20db581 --- /dev/null +++ b/target/sparc/sys-available/qemu-sparc @@ -0,0 +1,13 @@ +config ADK_TARGET_SYSTEM_QEMU_SPARC + bool "Qemu Emulator" + select ADK_sparc + select ADK_qemu_sparc + select ADK_CPU_SPARC_V8 + select ADK_HARDWARE_QEMU + select ADK_TARGET_WITH_VGA + select ADK_TARGET_WITH_INPUT + select ADK_TARGET_WITH_PCI + select ADK_TARGET_WITH_HDD + help + Support for Qemu Emulator (SPARC). + -- cgit v1.2.3 From 0e930c133951dffe8c933fe02f67e72fec57dc8d Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 06:08:24 +0200 Subject: sync patch with OpenWrt, combine both targets (rb411/rb433) --- mk/rootfs.mk | 2 +- package/adkinstall/Makefile | 5 +- target/linux/Config.in | 1 + target/linux/config/Config.in.flash | 3 +- target/linux/config/Config.in.netdevice | 3 +- target/linux/config/Config.in.spi | 14 + target/linux/patches/2.6.39/rb4xx.patch | 36530 ++++++++++++++++++----------- target/mips/Makefile | 6 +- target/mips/kernel.config | 212 +- target/mips/sys-available/mikrotik-rb411 | 13 - target/mips/sys-available/mikrotik-rb433 | 13 - target/mips/sys-available/mikrotik-rb4xx | 15 + 12 files changed, 23402 insertions(+), 13415 deletions(-) create mode 100644 target/linux/config/Config.in.spi delete mode 100644 target/mips/sys-available/mikrotik-rb411 delete mode 100644 target/mips/sys-available/mikrotik-rb433 create mode 100644 target/mips/sys-available/mikrotik-rb4xx diff --git a/mk/rootfs.mk b/mk/rootfs.mk index 241a237fa..5080944e6 100644 --- a/mk/rootfs.mk +++ b/mk/rootfs.mk @@ -17,7 +17,7 @@ ROOTFS:= root=/dev/sda2 MTDDEV:= root=/dev/mtdblock1 endif -ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB433),y) +ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB4XX),y) MTDDEV:= root=/dev/mtdblock2 endif diff --git a/package/adkinstall/Makefile b/package/adkinstall/Makefile index 6aae012f8..a4ab0d8eb 100644 --- a/package/adkinstall/Makefile +++ b/package/adkinstall/Makefile @@ -36,10 +36,7 @@ else ifeq ($(ADK_TARGET_SYSTEM_ACMESYSTEMS_FOXG20),y) else ifeq ($(ADK_TARGET_SYSTEM_LEMOTE_YEELONG),y) ${INSTALL_BIN} ./src/adkinstall.yeelong \ $(IDIR_ADKINSTALL)/sbin/adkinstall -else ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB411),y) - ${INSTALL_BIN} ./src/adkinstall.rb4xx \ - $(IDIR_ADKINSTALL)/sbin/adkinstall -else ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB433),y) +else ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB4XX),y) ${INSTALL_BIN} ./src/adkinstall.rb4xx \ $(IDIR_ADKINSTALL)/sbin/adkinstall else diff --git a/target/linux/Config.in b/target/linux/Config.in index cf4890059..7b52a3003 100644 --- a/target/linux/Config.in +++ b/target/linux/Config.in @@ -20,5 +20,6 @@ source target/linux/config/Config.in.misc source target/linux/config/Config.in.mips source target/linux/config/Config.in.lib source target/linux/config/Config.in.pm +source target/linux/config/Config.in.spi source target/linux/config/Config.in.kvm source target/linux/config/Config.in.debug diff --git a/target/linux/config/Config.in.flash b/target/linux/config/Config.in.flash index 4d9bf6828..3e2898617 100644 --- a/target/linux/config/Config.in.flash +++ b/target/linux/config/Config.in.flash @@ -43,8 +43,7 @@ config ADK_KERNEL_MTD_CFI_ADV_OPTIONS config ADK_KERNEL_MTD_NAND_RB4XX boolean - default y if ADK_TARGET_SYSTEM_MIKROTIK_RB411 - default y if ADK_TARGET_SYSTEM_MIKROTIK_RB433 + default y if ADK_TARGET_SYSTEM_MIKROTIK_RB4XX default n config ADK_KERNEL_MTD_AR7_PARTS diff --git a/target/linux/config/Config.in.netdevice b/target/linux/config/Config.in.netdevice index 1a84f6bcc..cd90f3af2 100644 --- a/target/linux/config/Config.in.netdevice +++ b/target/linux/config/Config.in.netdevice @@ -104,8 +104,7 @@ config ADK_KERNEL_AG71XX select ADK_KERNEL_NET_PCI select ADK_KERNEL_MII select ADK_KERNEL_NETDEV_1000 - default y if ADK_TARGET_SYSTEM_MIKROTIK_RB411 - default y if ADK_TARGET_SYSTEM_MIKROTIK_RB433 + default y if ADK_TARGET_SYSTEM_MIKROTIK_RB4XX default n help diff --git a/target/linux/config/Config.in.spi b/target/linux/config/Config.in.spi new file mode 100644 index 000000000..a141f8231 --- /dev/null +++ b/target/linux/config/Config.in.spi @@ -0,0 +1,14 @@ +config ADK_KERNEL_SPI + boolean + +config ADK_KERNEL_SPI_AR71XX + select ADK_KERNEL_SPI + boolean + +config ADK_KERNEL_SPI_RB4XX + select ADK_KERNEL_SPI + boolean + +config ADK_KERNEL_SPI_RB4XX_CPLD + select ADK_KERNEL_SPI + boolean diff --git a/target/linux/patches/2.6.39/rb4xx.patch b/target/linux/patches/2.6.39/rb4xx.patch index 1739221bf..49fd204d7 100644 --- a/target/linux/patches/2.6.39/rb4xx.patch +++ b/target/linux/patches/2.6.39/rb4xx.patch @@ -1,548 +1,223 @@ -diff -Nur linux-2.6.39.orig/arch/mips/Kconfig linux-2.6.39/arch/mips/Kconfig ---- linux-2.6.39.orig/arch/mips/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/Kconfig 2011-05-27 14:36:50.000000000 +0200 -@@ -84,6 +84,23 @@ - help - Support for the Atheros AR71XX/AR724X/AR913X SoCs. - -+config ATHEROS_AR71XX -+ bool "Atheros AR71xx based boards" -+ select CEVT_R4K -+ select CSRC_R4K -+ select DMA_NONCOHERENT -+ select HW_HAS_PCI -+ select IRQ_CPU -+ select ARCH_REQUIRE_GPIOLIB -+ select SYS_HAS_CPU_MIPS32_R1 -+ select SYS_HAS_CPU_MIPS32_R2 -+ select SYS_SUPPORTS_32BIT_KERNEL -+ select SYS_SUPPORTS_BIG_ENDIAN -+ select SYS_HAS_EARLY_PRINTK -+ select MIPS_MACHINE -+ help -+ Support for Atheros AR71xx based boards. +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/ar71xx.c linux-2.6.39/arch/mips/ar71xx/ar71xx.c +--- linux-2.6.39.orig/arch/mips/ar71xx/ar71xx.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/ar71xx.c 2011-08-24 02:41:55.227990426 +0200 +@@ -0,0 +1,230 @@ ++/* ++ * AR71xx SoC routines ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + - config BCM47XX - bool "Broadcom BCM47XX based boards" - select CEVT_R4K -@@ -740,6 +757,7 @@ - - source "arch/mips/alchemy/Kconfig" - source "arch/mips/ath79/Kconfig" -+source "arch/mips/ar71xx/Kconfig" - source "arch/mips/bcm63xx/Kconfig" - source "arch/mips/jazz/Kconfig" - source "arch/mips/jz4740/Kconfig" -diff -Nur linux-2.6.39.orig/arch/mips/Makefile linux-2.6.39/arch/mips/Makefile ---- linux-2.6.39.orig/arch/mips/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/Makefile 2011-05-27 14:36:50.000000000 +0200 -@@ -158,6 +158,13 @@ - endif - cflags-$(CONFIG_CAVIUM_CN63XXP1) += -Wa,-mfix-cn63xxp1 - -+# -+# Atheros AR71xx -+# -+core-$(CONFIG_ATHEROS_AR71XX) += arch/mips/ar71xx/ -+cflags-$(CONFIG_ATHEROS_AR71XX) += -I$(srctree)/arch/mips/include/asm/mach-ar71xx -+load-$(CONFIG_ATHEROS_AR71XX) += 0xffffffff80060000 ++#include ++#include ++#include ++#include ++#include + - cflags-$(CONFIG_CPU_R4000_WORKAROUNDS) += $(call cc-option,-mfix-r4000,) - cflags-$(CONFIG_CPU_R4400_WORKAROUNDS) += $(call cc-option,-mfix-r4400,) - cflags-$(CONFIG_CPU_DADDI_WORKAROUNDS) += $(call cc-option,-mno-daddi,) -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/Kconfig linux-2.6.39/arch/mips/ar71xx/Kconfig ---- linux-2.6.39.orig/arch/mips/ar71xx/Kconfig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/Kconfig 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,264 @@ -+if ATHEROS_AR71XX ++#include + -+menu "Atheros AR71xx machine selection" ++static DEFINE_MUTEX(ar71xx_flash_mutex); ++static DEFINE_SPINLOCK(ar71xx_device_lock); + -+config AR71XX_MACH_AP81 -+ bool "Atheros AP81 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++void __iomem *ar71xx_ddr_base; ++EXPORT_SYMBOL_GPL(ar71xx_ddr_base); + -+config AR71XX_MACH_AP83 -+ bool "Atheros AP83 board support" -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++void __iomem *ar71xx_pll_base; ++EXPORT_SYMBOL_GPL(ar71xx_pll_base); + -+config AR71XX_MACH_DIR_600_A1 -+ bool "D-Link DIR-600 rev. A1 support" -+ select AR71XX_DEV_AP91_ETH -+ select AR71XX_DEV_AP91_PCI if PCI -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_NVRAM -+ default n ++void __iomem *ar71xx_reset_base; ++EXPORT_SYMBOL_GPL(ar71xx_reset_base); + -+config AR71XX_MACH_DIR_615_C1 -+ bool "D-Link DIR-615 rev. C1 support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_NVRAM -+ default n ++void __iomem *ar71xx_gpio_base; ++EXPORT_SYMBOL_GPL(ar71xx_gpio_base); + -+config AR71XX_MACH_DIR_825_B1 -+ bool "D-Link DIR-825 rev. B1 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AP94_PCI if PCI -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++void __iomem *ar71xx_usb_ctrl_base; ++EXPORT_SYMBOL_GPL(ar71xx_usb_ctrl_base); + -+config AR71XX_MACH_PB42 -+ bool "Atheros PB42 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_PB42_PCI if PCI -+ default n ++void ar71xx_device_stop(u32 mask) ++{ ++ unsigned long flags; ++ u32 mask_inv; ++ u32 t; + -+config AR71XX_MACH_PB44 -+ bool "Atheros PB44 board support" -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_PB42_PCI if PCI -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR71XX_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR71XX_RESET_REG_RESET_MODULE, t | mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_PB92 -+ bool "Atheros PB92 board support" -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_PB9X_PCI if PCI -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ mask_inv = mask & RESET_MODULE_USB_OHCI_DLL_7240; ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); ++ t |= mask; ++ t &= ~mask_inv; ++ ar71xx_reset_wr(AR724X_RESET_REG_RESET_MODULE, t); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_AW_NR580 -+ bool "AzureWave AW-NR580 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_PB42_PCI if PCI -+ select AR71XX_DEV_LEDS_GPIO -+ default n ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR91XX_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR91XX_RESET_REG_RESET_MODULE, t | mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_WZR_HP_G300NH -+ bool "Buffalo WZR-HP-G300NH board support" -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default y ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR933X_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR933X_RESET_REG_RESET_MODULE, t | mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_WP543 -+ bool "Compex WP543/WPJ543 board support" -+ select MYLOADER -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_PB42_PCI if PCI -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR934X_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR934X_RESET_REG_RESET_MODULE, t | mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_WRT160NL -+ bool "Linksys WRT160NL board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ select AR71XX_NVRAM -+ default n ++ default: ++ BUG(); ++ } ++} ++EXPORT_SYMBOL_GPL(ar71xx_device_stop); + -+config AR71XX_MACH_WRT400N -+ bool "Linksys WRT400N board support" -+ select AR71XX_DEV_AP94_PCI if PCI -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n ++void ar71xx_device_start(u32 mask) ++{ ++ unsigned long flags; ++ u32 mask_inv; ++ u32 t; + -+config AR71XX_MACH_RB4XX -+ bool "MikroTik RouterBOARD 4xx series support" -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR71XX_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR71XX_RESET_REG_RESET_MODULE, t & ~mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_RB750 -+ bool "MikroTik RouterBOARD 750 support" -+ select AR71XX_DEV_AP91_ETH -+ default n ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ mask_inv = mask & RESET_MODULE_USB_OHCI_DLL_7240; ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); ++ t &= ~mask; ++ t |= mask_inv; ++ ar71xx_reset_wr(AR724X_RESET_REG_RESET_MODULE, t); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_WNDR3700 -+ bool "NETGEAR WNDR3700 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AP94_PCI if PCI -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR91XX_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR91XX_RESET_REG_RESET_MODULE, t & ~mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_WNR2000 -+ bool "NETGEAR WNR2000 board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR933X_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR933X_RESET_REG_RESET_MODULE, t & ~mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; + -+config AR71XX_MACH_MZK_W04NU -+ bool "Planex MZK-W04NU board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n -+ -+config AR71XX_MACH_MZK_W300NH -+ bool "Planex MZK-W300NH board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n -+ -+config AR71XX_MACH_NBG460N -+ bool "Zyxel NBG460N/550N/550NH board support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n -+ -+config AR71XX_MACH_TL_WR741ND -+ bool "TP-LINK TL-WR741ND support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AP91_ETH -+ select AR71XX_DEV_AP91_PCI if PCI -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n -+ -+config AR71XX_MACH_TL_WR841N_V1 -+ bool "TP-LINK TL-WR841N v1 support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_PB42_PCI if PCI -+ select AR71XX_DEV_DSA -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n -+ -+config AR71XX_MACH_TL_WR941ND -+ bool "TP-LINK TL-WR941ND support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_DSA -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ default n -+ -+config AR71XX_MACH_TL_WR1043ND -+ bool "TP-LINK TL-WR1043ND support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_USB -+ default n -+ -+config AR71XX_MACH_TEW_632BRP -+ bool "TRENDnet TEW-632BRP support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AR913X_WMAC -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_NVRAM -+ default n -+ -+config AR71XX_MACH_UBNT -+ bool "Ubiquiti AR71xx based boards support" -+ select AR71XX_DEV_M25P80 -+ select AR71XX_DEV_AP91_PCI if PCI -+ select AR71XX_DEV_GPIO_BUTTONS -+ select AR71XX_DEV_LEDS_GPIO -+ select AR71XX_DEV_PB42_PCI if PCI -+ select AR71XX_DEV_USB -+ default n -+ -+endmenu -+ -+config AR71XX_DEV_M25P80 -+ def_bool n -+ -+config AR71XX_DEV_AP91_PCI -+ def_bool n -+ -+config AR71XX_DEV_AP91_ETH -+ def_bool n -+ -+config AR71XX_DEV_AP94_PCI -+ def_bool n -+ -+config AR71XX_DEV_AR913X_WMAC -+ def_bool n -+ -+config AR71XX_DEV_DSA -+ def_bool n -+ -+config AR71XX_DEV_GPIO_BUTTONS -+ def_bool n -+ -+config AR71XX_DEV_LEDS_GPIO -+ def_bool n -+ -+config AR71XX_DEV_PB42_PCI -+ def_bool n -+ -+config AR71XX_DEV_PB9X_PCI -+ def_bool n -+ -+config AR71XX_DEV_USB -+ def_bool n -+ -+config AR71XX_NVRAM -+ def_bool n -+ -+endif -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/Makefile linux-2.6.39/arch/mips/ar71xx/Makefile ---- linux-2.6.39.orig/arch/mips/ar71xx/Makefile 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/Makefile 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,54 @@ -+# -+# Makefile for the Atheros AR71xx SoC specific parts of the kernel -+# -+# Copyright (C) 2008-2009 Gabor Juhos -+# Copyright (C) 2008 Imre Kaloz -+# -+# This program is free software; you can redistribute it and/or modify it -+# under the terms of the GNU General Public License version 2 as published -+# by the Free Software Foundation. -+ -+obj-y := prom.o irq.o setup.o devices.o gpio.o ar71xx.o -+ -+obj-$(CONFIG_EARLY_PRINTK) += early_printk.o -+obj-$(CONFIG_PCI) += pci.o -+ -+obj-$(CONFIG_AR71XX_DEV_AP91_ETH) += dev-ap91-eth.o -+obj-$(CONFIG_AR71XX_DEV_AP91_PCI) += dev-ap91-pci.o -+obj-$(CONFIG_AR71XX_DEV_AP94_PCI) += dev-ap94-pci.o -+obj-$(CONFIG_AR71XX_DEV_AR913X_WMAC) += dev-ar913x-wmac.o -+obj-$(CONFIG_AR71XX_DEV_DSA) += dev-dsa.o -+obj-$(CONFIG_AR71XX_DEV_GPIO_BUTTONS) += dev-gpio-buttons.o -+obj-$(CONFIG_AR71XX_DEV_LEDS_GPIO) += dev-leds-gpio.o -+obj-$(CONFIG_AR71XX_DEV_M25P80) += dev-m25p80.o -+obj-$(CONFIG_AR71XX_DEV_PB42_PCI) += dev-pb42-pci.o -+obj-$(CONFIG_AR71XX_DEV_PB9X_PCI) += dev-pb9x-pci.o -+obj-$(CONFIG_AR71XX_DEV_USB) += dev-usb.o -+ -+obj-$(CONFIG_AR71XX_NVRAM) += nvram.o -+ -+obj-$(CONFIG_AR71XX_MACH_AP81) += mach-ap81.o -+obj-$(CONFIG_AR71XX_MACH_AP83) += mach-ap83.o -+obj-$(CONFIG_AR71XX_MACH_AW_NR580) += mach-aw-nr580.o -+obj-$(CONFIG_AR71XX_MACH_DIR_600_A1) += mach-dir-600-a1.o -+obj-$(CONFIG_AR71XX_MACH_DIR_615_C1) += mach-dir-615-c1.o -+obj-$(CONFIG_AR71XX_MACH_DIR_825_B1) += mach-dir-825-b1.o -+obj-$(CONFIG_AR71XX_MACH_MZK_W04NU) += mach-mzk-w04nu.o -+obj-$(CONFIG_AR71XX_MACH_MZK_W300NH) += mach-mzk-w300nh.o -+obj-$(CONFIG_AR71XX_MACH_NBG460N) += mach-nbg460n.o -+obj-$(CONFIG_AR71XX_MACH_PB42) += mach-pb42.o -+obj-$(CONFIG_AR71XX_MACH_PB44) += mach-pb44.o -+obj-$(CONFIG_AR71XX_MACH_PB92) += mach-pb92.o -+obj-$(CONFIG_AR71XX_MACH_RB4XX) += mach-rb4xx.o -+obj-$(CONFIG_AR71XX_MACH_RB750) += mach-rb750.o -+obj-$(CONFIG_AR71XX_MACH_TEW_632BRP) += mach-tew-632brp.o -+obj-$(CONFIG_AR71XX_MACH_TL_WR741ND) += mach-tl-wr741nd.o -+obj-$(CONFIG_AR71XX_MACH_TL_WR841N_V1) += mach-tl-wr841n.o -+obj-$(CONFIG_AR71XX_MACH_TL_WR941ND) += mach-tl-wr941nd.o -+obj-$(CONFIG_AR71XX_MACH_TL_WR1043ND) += mach-tl-wr1043nd.o -+obj-$(CONFIG_AR71XX_MACH_UBNT) += mach-ubnt.o -+obj-$(CONFIG_AR71XX_MACH_WNDR3700) += mach-wndr3700.o -+obj-$(CONFIG_AR71XX_MACH_WNR2000) += mach-wnr2000.o -+obj-$(CONFIG_AR71XX_MACH_WP543) += mach-wp543.o -+obj-$(CONFIG_AR71XX_MACH_WRT160NL) += mach-wrt160nl.o -+obj-$(CONFIG_AR71XX_MACH_WRT400N) += mach-wrt400n.o -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/ar71xx.c linux-2.6.39/arch/mips/ar71xx/ar71xx.c ---- linux-2.6.39.orig/arch/mips/ar71xx/ar71xx.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/ar71xx.c 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,177 @@ -+/* -+ * AR71xx SoC routines -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include -+#include -+#include -+#include -+ -+#include -+ -+static DEFINE_MUTEX(ar71xx_flash_mutex); -+ -+void __iomem *ar71xx_ddr_base; -+EXPORT_SYMBOL_GPL(ar71xx_ddr_base); -+ -+void __iomem *ar71xx_pll_base; -+EXPORT_SYMBOL_GPL(ar71xx_pll_base); -+ -+void __iomem *ar71xx_reset_base; -+EXPORT_SYMBOL_GPL(ar71xx_reset_base); -+ -+void __iomem *ar71xx_gpio_base; -+EXPORT_SYMBOL_GPL(ar71xx_gpio_base); -+ -+void __iomem *ar71xx_usb_ctrl_base; -+EXPORT_SYMBOL_GPL(ar71xx_usb_ctrl_base); -+ -+void ar71xx_device_stop(u32 mask) -+{ -+ unsigned long flags; -+ u32 mask_inv; -+ u32 t; -+ -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR71XX_RESET_REG_RESET_MODULE); -+ ar71xx_reset_wr(AR71XX_RESET_REG_RESET_MODULE, t | mask); -+ local_irq_restore(flags); -+ break; -+ -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ mask_inv = mask & RESET_MODULE_USB_OHCI_DLL_7240; -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); -+ t |= mask; -+ t &= ~mask_inv; -+ ar71xx_reset_wr(AR724X_RESET_REG_RESET_MODULE, t); -+ local_irq_restore(flags); -+ break; -+ -+ case AR71XX_SOC_AR9130: -+ case AR71XX_SOC_AR9132: -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR91XX_RESET_REG_RESET_MODULE); -+ ar71xx_reset_wr(AR91XX_RESET_REG_RESET_MODULE, t | mask); -+ local_irq_restore(flags); ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR934X_RESET_REG_RESET_MODULE); ++ ar71xx_reset_wr(AR934X_RESET_REG_RESET_MODULE, t & ~mask); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); + break; + + default: + BUG(); + } +} -+EXPORT_SYMBOL_GPL(ar71xx_device_stop); ++EXPORT_SYMBOL_GPL(ar71xx_device_start); + -+void ar71xx_device_start(u32 mask) ++int ar71xx_device_stopped(u32 mask) +{ + unsigned long flags; -+ u32 mask_inv; + u32 t; + + switch (ar71xx_soc) { + case AR71XX_SOC_AR7130: + case AR71XX_SOC_AR7141: + case AR71XX_SOC_AR7161: -+ local_irq_save(flags); ++ spin_lock_irqsave(&ar71xx_device_lock, flags); + t = ar71xx_reset_rr(AR71XX_RESET_REG_RESET_MODULE); -+ ar71xx_reset_wr(AR71XX_RESET_REG_RESET_MODULE, t & ~mask); -+ local_irq_restore(flags); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); + break; + + case AR71XX_SOC_AR7240: + case AR71XX_SOC_AR7241: + case AR71XX_SOC_AR7242: -+ mask_inv = mask & RESET_MODULE_USB_OHCI_DLL_7240; -+ local_irq_save(flags); ++ spin_lock_irqsave(&ar71xx_device_lock, flags); + t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); -+ t &= ~mask; -+ t |= mask_inv; -+ ar71xx_reset_wr(AR724X_RESET_REG_RESET_MODULE, t); -+ local_irq_restore(flags); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); + break; + + case AR71XX_SOC_AR9130: + case AR71XX_SOC_AR9132: -+ local_irq_save(flags); ++ spin_lock_irqsave(&ar71xx_device_lock, flags); + t = ar71xx_reset_rr(AR91XX_RESET_REG_RESET_MODULE); -+ ar71xx_reset_wr(AR91XX_RESET_REG_RESET_MODULE, t & ~mask); -+ local_irq_restore(flags); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; ++ ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR933X_RESET_REG_RESET_MODULE); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); ++ break; ++ ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ spin_lock_irqsave(&ar71xx_device_lock, flags); ++ t = ar71xx_reset_rr(AR934X_RESET_REG_RESET_MODULE); ++ spin_unlock_irqrestore(&ar71xx_device_lock, flags); + break; + + default: + BUG(); + } ++ ++ return ((t & mask) == mask); +} -+EXPORT_SYMBOL_GPL(ar71xx_device_start); ++EXPORT_SYMBOL_GPL(ar71xx_device_stopped); + -+int ar71xx_device_stopped(u32 mask) ++void ar71xx_ddr_flush(u32 reg) +{ -+ unsigned long flags; -+ u32 t; -+ -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR71XX_RESET_REG_RESET_MODULE); -+ local_irq_restore(flags); -+ break; -+ -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); -+ local_irq_restore(flags); -+ break; -+ -+ case AR71XX_SOC_AR9130: -+ case AR71XX_SOC_AR9132: -+ local_irq_save(flags); -+ t = ar71xx_reset_rr(AR91XX_RESET_REG_RESET_MODULE); -+ local_irq_restore(flags); -+ break; -+ -+ default: -+ BUG(); -+ } -+ -+ return ((t & mask) == mask); -+} -+EXPORT_SYMBOL_GPL(ar71xx_device_stopped); -+ -+void ar71xx_ddr_flush(u32 reg) -+{ -+ ar71xx_ddr_wr(reg, 1); -+ while ((ar71xx_ddr_rr(reg) & 0x1)); ++ ar71xx_ddr_wr(reg, 1); ++ while ((ar71xx_ddr_rr(reg) & 0x1)) ++ ; + + ar71xx_ddr_wr(reg, 1); -+ while ((ar71xx_ddr_rr(reg) & 0x1)); ++ while ((ar71xx_ddr_rr(reg) & 0x1)) ++ ; +} +EXPORT_SYMBOL_GPL(ar71xx_ddr_flush); + @@ -557,111 +232,10 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/ar71xx.c linux-2.6.39/arch/mips/ar7 + mutex_unlock(&ar71xx_flash_mutex); +} +EXPORT_SYMBOL_GPL(ar71xx_flash_release); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-eth.c linux-2.6.39/arch/mips/ar71xx/dev-ap91-eth.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-eth.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-eth.c 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,70 @@ -+/* -+ * Atheros AP91 reference board ethernet initialization -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include "devices.h" -+#include "dev-dsa.h" -+#include "dev-ap91-eth.h" -+ -+static struct dsa_chip_data ap91_dsa_chip = { -+ .port_names[0] = "cpu", -+ .port_names[1] = "lan1", -+ .port_names[2] = "lan2", -+ .port_names[3] = "lan3", -+ .port_names[4] = "lan4", -+}; -+ -+static struct dsa_platform_data ap91_dsa_data = { -+ .nr_chips = 1, -+ .chip = &ap91_dsa_chip, -+}; -+ -+static void ap91_eth_set_port_name(unsigned port, const char *name) -+{ -+ if (port < 1 || port > 5) -+ return; -+ -+ if (name) -+ ap91_dsa_chip.port_names[port] = (char *) name; -+} -+ -+void __init ap91_eth_init(u8 *mac_addr, const char *port_names[]) -+{ -+ if (mac_addr) -+ ar71xx_set_mac_base(mac_addr); -+ -+ if (port_names) { -+ int i; -+ -+ for (i = 0; i < AP91_ETH_NUM_PORT_NAMES; i++) -+ ap91_eth_set_port_name(i + 1, port_names[i]); -+ } -+ -+ /* WAN port */ -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.fifo_cfg1 = 0x0fff0000; -+ ar71xx_eth0_data.fifo_cfg2 = 0x00001fff; -+ ar71xx_eth0_data.fifo_cfg3 = 0x008001ff; -+ -+ /* LAN ports */ -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.speed = SPEED_1000; -+ ar71xx_eth1_data.duplex = DUPLEX_FULL; -+ ar71xx_eth1_data.fifo_cfg1 = 0x0fff0000; -+ ar71xx_eth1_data.fifo_cfg2 = 0x00001fff; -+ ar71xx_eth1_data.fifo_cfg3 = 0x008001ff; -+ -+ ar71xx_add_device_mdio(0x0); -+ ar71xx_add_device_eth(1); -+ ar71xx_add_device_eth(0); -+ -+ ar71xx_add_device_dsa(1, &ap91_dsa_data); -+} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-eth.h linux-2.6.39/arch/mips/ar71xx/dev-ap91-eth.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-eth.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-eth.h 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,23 @@ -+/* -+ * Atheros AP91 reference board ethernet initialization -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#ifndef _AR71XX_DEV_AP91_ETH_H -+#define _AR71XX_DEV_AP91_ETH_H -+ -+#define AP91_ETH_NUM_PORT_NAMES 4 -+ -+#if defined(CONFIG_AR71XX_DEV_AP91_ETH) -+void ap91_eth_init(u8 *mac_addr, const char *port_names[]) __init; -+#else -+static inline void ap91_eth_init(u8 *mac_addr) { } -+#endif -+ -+#endif /* _AR71XX_DEV_AP91_ETH_H */ -+ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.c --- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.c 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,114 @@ ++++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.c 2011-08-24 02:41:55.277990824 +0200 +@@ -0,0 +1,71 @@ +/* + * Atheros AP91 reference board PCI initialization + * @@ -680,10 +254,12 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c linux-2.6.39/arch/mi +#include + +#include "dev-ap91-pci.h" ++#include "pci-ath9k-fixup.h" + -+static struct ath9k_platform_data ap91_wmac_data; ++static struct ath9k_platform_data ap91_wmac_data = { ++ .led_pin = -1, ++}; +static char ap91_wmac_mac[6]; -+static int ap91_pci_fixup_enabled; + +static struct ar71xx_pci_irq ap91_pci_irqs[] __initdata = { + { @@ -695,7 +271,7 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c linux-2.6.39/arch/mi + +static int ap91_pci_plat_dev_init(struct pci_dev *dev) +{ -+ switch(PCI_SLOT(dev->devfn)) { ++ switch (PCI_SLOT(dev->devfn)) { + case 0: + dev->dev.platform_data = &ap91_wmac_data; + break; @@ -704,61 +280,16 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c linux-2.6.39/arch/mi + return 0; +} + -+static void ap91_pci_fixup(struct pci_dev *dev) ++__init void ap91_pci_setup_wmac_led_pin(int pin) +{ -+ void __iomem *mem; -+ u16 *cal_data; -+ u16 cmd; -+ u32 val; -+ -+ if (!ap91_pci_fixup_enabled) -+ return; -+ -+ printk(KERN_INFO "PCI: fixup device %s\n", pci_name(dev)); -+ -+ cal_data = ap91_wmac_data.eeprom_data; -+ if (*cal_data != 0xa55a) { -+ printk(KERN_ERR "PCI: no calibration data found for %s\n", -+ pci_name(dev)); -+ return; -+ } -+ -+ mem = ioremap(AR71XX_PCI_MEM_BASE, 0x10000); -+ if (!mem) { -+ printk(KERN_ERR "PCI: ioremap error for device %s\n", -+ pci_name(dev)); -+ return; -+ } -+ -+ /* Setup the PCI device to allow access to the internal registers */ -+ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, 0xffff); -+ pci_read_config_word(dev, PCI_COMMAND, &cmd); -+ cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; -+ pci_write_config_word(dev, PCI_COMMAND, cmd); -+ -+ /* set pointer to first reg address */ -+ cal_data += 3; -+ while (*cal_data != 0xffff) { -+ u32 reg; -+ reg = *cal_data++; -+ val = *cal_data++; -+ val |= (*cal_data++) << 16; -+ -+ __raw_writel(val, mem + reg); -+ udelay(100); -+ } -+ -+ pci_read_config_dword(dev, PCI_VENDOR_ID, &val); -+ dev->vendor = val & 0xffff; -+ dev->device = (val >> 16) & 0xffff; -+ -+ pci_read_config_dword(dev, PCI_CLASS_REVISION, &val); -+ dev->revision = val & 0xff; -+ dev->class = val >> 8; /* upper 3 bytes */ ++ ap91_wmac_data.led_pin = pin; ++} + -+ iounmap(mem); ++__init void ap91_pci_setup_wmac_gpio(u32 mask, u32 val) ++{ ++ ap91_wmac_data.gpio_mask = mask; ++ ap91_wmac_data.gpio_val = val; +} -+DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_ATHEROS, PCI_ANY_ID, ap91_pci_fixup); + +void __init ap91_pci_init(u8 *cal_data, u8 *mac_addr) +{ @@ -774,12 +305,12 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.c linux-2.6.39/arch/mi + ar71xx_pci_plat_dev_init = ap91_pci_plat_dev_init; + ar71xx_pci_init(ARRAY_SIZE(ap91_pci_irqs), ap91_pci_irqs); + -+ ap91_pci_fixup_enabled = 1; ++ pci_enable_ath9k_fixup(0, ap91_wmac_data.eeprom_data); +} diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.h linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.h --- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.h 2011-05-27 14:36:50.000000000 +0200 -@@ -0,0 +1,21 @@ ++++ linux-2.6.39/arch/mips/ar71xx/dev-ap91-pci.h 2011-08-24 02:41:55.287981779 +0200 +@@ -0,0 +1,25 @@ +/* + * Atheros AP91 reference board PCI initialization + * @@ -795,16 +326,20 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap91-pci.h linux-2.6.39/arch/mi + +#if defined(CONFIG_AR71XX_DEV_AP91_PCI) +void ap91_pci_init(u8 *cal_data, u8 *mac_addr) __init; ++void ap91_pci_setup_wmac_led_pin(int pin) __init; ++void ap91_pci_setup_wmac_gpio(u32 mask, u32 val) __init; +#else +static inline void ap91_pci_init(u8 *cal_data, u8 *mac_addr) { } ++static inline void ap91_pci_setup_wmac_led_pin(int pin) { } ++static inline void ap91_pci_setup_wmac_gpio(u32 mask, u32 gpio) { } +#endif + +#endif /* _AR71XX_DEV_AP91_PCI_H */ + diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.c linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.c --- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,159 @@ ++++ linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.c 2011-08-24 02:41:55.287981779 +0200 +@@ -0,0 +1,109 @@ +/* + * Atheros AP94 reference board PCI initialization + * @@ -823,28 +358,32 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.c linux-2.6.39/arch/mi +#include + +#include "dev-ap94-pci.h" ++#include "pci-ath9k-fixup.h" + -+static struct ath9k_platform_data ap94_wmac0_data; -+static struct ath9k_platform_data ap94_wmac1_data; ++static struct ath9k_platform_data ap94_wmac0_data = { ++ .led_pin = -1, ++}; ++static struct ath9k_platform_data ap94_wmac1_data = { ++ .led_pin = -1, ++}; +static char ap94_wmac0_mac[6]; +static char ap94_wmac1_mac[6]; -+static int ap94_pci_fixup_enabled; + +static struct ar71xx_pci_irq ap94_pci_irqs[] __initdata = { -+ { -+ .slot = 0, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV0, -+ }, { -+ .slot = 1, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV1, -+ } ++ { ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, ++ }, { ++ .slot = 1, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV1, ++ } +}; + +static int ap94_pci_plat_dev_init(struct pci_dev *dev) +{ -+ switch(PCI_SLOT(dev->devfn)) { ++ switch (PCI_SLOT(dev->devfn)) { + case 17: + dev->dev.platform_data = &ap94_wmac0_data; + break; @@ -857,85 +396,30 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.c linux-2.6.39/arch/mi + return 0; +} + -+static void ap94_pci_fixup(struct pci_dev *dev) ++__init void ap94_pci_setup_wmac_led_pin(unsigned wmac, int pin) +{ -+ void __iomem *mem; -+ u16 *cal_data; -+ u16 cmd; -+ u32 bar0; -+ u32 val; -+ -+ if (!ap94_pci_fixup_enabled) -+ return; -+ -+ switch (PCI_SLOT(dev->devfn)) { -+ case 17: -+ cal_data = ap94_wmac0_data.eeprom_data; ++ switch (wmac) { ++ case 0: ++ ap94_wmac0_data.led_pin = pin; + break; -+ case 18: -+ cal_data = ap94_wmac1_data.eeprom_data; ++ case 1: ++ ap94_wmac1_data.led_pin = pin; + break; -+ default: -+ return; -+ } -+ -+ if (*cal_data != 0xa55a) { -+ printk(KERN_ERR "PCI: no calibration data found for %s\n", -+ pci_name(dev)); -+ return; -+ } -+ -+ mem = ioremap(AR71XX_PCI_MEM_BASE, 0x10000); -+ if (!mem) { -+ printk(KERN_ERR "PCI: ioremap error for device %s\n", -+ pci_name(dev)); -+ return; -+ } -+ -+ printk(KERN_INFO "PCI: fixup device %s\n", pci_name(dev)); -+ -+ pci_read_config_dword(dev, PCI_BASE_ADDRESS_0, &bar0); -+ -+ /* Setup the PCI device to allow access to the internal registers */ -+ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, AR71XX_PCI_MEM_BASE); -+ pci_read_config_word(dev, PCI_COMMAND, &cmd); -+ cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; -+ pci_write_config_word(dev, PCI_COMMAND, cmd); -+ -+ /* set pointer to first reg address */ -+ cal_data += 3; -+ while (*cal_data != 0xffff) { -+ u32 reg; -+ reg = *cal_data++; -+ val = *cal_data++; -+ val |= (*cal_data++) << 16; -+ -+ __raw_writel(val, mem + reg); -+ udelay(100); + } -+ -+ pci_read_config_dword(dev, PCI_VENDOR_ID, &val); -+ dev->vendor = val & 0xffff; -+ dev->device = (val >> 16) & 0xffff; -+ -+ pci_read_config_dword(dev, PCI_CLASS_REVISION, &val); -+ dev->revision = val & 0xff; -+ dev->class = val >> 8; /* upper 3 bytes */ -+ -+ pci_read_config_word(dev, PCI_COMMAND, &cmd); -+ cmd &= ~(PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY); -+ pci_write_config_word(dev, PCI_COMMAND, cmd); -+ -+ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, bar0); -+ -+ iounmap(mem); +} -+DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_ATHEROS, PCI_ANY_ID, ap94_pci_fixup); + -+void __init ap94_pci_enable_quirk_wndr3700(void) ++__init void ap94_pci_setup_wmac_gpio(unsigned wmac, u32 mask, u32 val) +{ -+ ap94_wmac0_data.quirk_wndr3700 = 1; -+ ap94_wmac1_data.quirk_wndr3700 = 1; ++ switch (wmac) { ++ case 0: ++ ap94_wmac0_data.gpio_mask = mask; ++ ap94_wmac0_data.gpio_val = val; ++ break; ++ case 1: ++ ap94_wmac1_data.gpio_mask = mask; ++ ap94_wmac1_data.gpio_val = val; ++ break; ++ } +} + +void __init ap94_pci_init(u8 *cal_data0, u8 *mac_addr0, @@ -962,12 +446,13 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.c linux-2.6.39/arch/mi + ar71xx_pci_plat_dev_init = ap94_pci_plat_dev_init; + ar71xx_pci_init(ARRAY_SIZE(ap94_pci_irqs), ap94_pci_irqs); + -+ ap94_pci_fixup_enabled = 1; ++ pci_enable_ath9k_fixup(17, ap94_wmac0_data.eeprom_data); ++ pci_enable_ath9k_fixup(18, ap94_wmac1_data.eeprom_data); +} diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.h linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.h --- linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,28 @@ ++++ linux-2.6.39/arch/mips/ar71xx/dev-ap94-pci.h 2011-08-24 02:41:55.287981779 +0200 +@@ -0,0 +1,31 @@ +/* + * Atheros AP94 reference board PCI initialization + * @@ -985,28 +470,32 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ap94-pci.h linux-2.6.39/arch/mi +void ap94_pci_init(u8 *cal_data0, u8 *mac_addr0, + u8 *cal_data1, u8 *mac_addr1) __init; + -+void ap94_pci_enable_quirk_wndr3700(void) __init; ++void ap94_pci_setup_wmac_led_pin(unsigned wmac, int pin) __init; ++void ap94_pci_setup_wmac_gpio(unsigned wmac, u32 mask, u32 val) __init; + +#else +static inline void ap94_pci_init(u8 *cal_data0, u8 *mac_addr0, + u8 *cal_data1, u8 *mac_addr1) {} + -+static inline void ap94_pci_enable_quirk_wndr3700(void) {} ++static inline void ap94_pci_setup_wmac_led_pin(unsigned wmac, int pin) {} ++static inline void ap94_pci_setup_wmac_gpio(unsigned wmac, ++ u32 mask, u32 val) {} +#endif + +#endif /* _AR71XX_DEV_AP94_PCI_H */ + -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.c linux-2.6.39/arch/mips/ar71xx/dev-ar913x-wmac.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ar913x-wmac.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,68 @@ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar9xxx-wmac.c linux-2.6.39/arch/mips/ar71xx/dev-ar9xxx-wmac.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-ar9xxx-wmac.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-ar9xxx-wmac.c 2011-08-24 02:41:55.287981779 +0200 +@@ -0,0 +1,154 @@ +/* -+ * Atheros AR913x SoC built-in WMAC device support ++ * Atheros AR9XXX SoCs built-in WMAC device support + * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan + * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.15/2.6.31 BSP + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -1022,15 +511,18 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.c linux-2.6.39/arch + +#include + -+#include "dev-ar913x-wmac.h" ++#include "dev-ar9xxx-wmac.h" ++ ++#define MHZ_25 (25 * 1000 * 1000) + -+static struct ath9k_platform_data ar913x_wmac_data; -+static char ar913x_wmac_mac[6]; ++static struct ath9k_platform_data ar9xxx_wmac_data = { ++ .led_pin = -1, ++}; ++static char ar9xxx_wmac_mac[6]; + -+static struct resource ar913x_wmac_resources[] = { ++static struct resource ar9xxx_wmac_resources[] = { + { -+ .start = AR91XX_WMAC_BASE, -+ .end = AR91XX_WMAC_BASE + AR91XX_WMAC_SIZE - 1, ++ /* .start and .end fields are filled dynamically */ + .flags = IORESOURCE_MEM, + }, { + .start = AR71XX_CPU_IRQ_IP2, @@ -1039,90 +531,234 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.c linux-2.6.39/arch + }, +}; + -+static struct platform_device ar913x_wmac_device = { ++static struct platform_device ar9xxx_wmac_device = { + .name = "ath9k", + .id = -1, -+ .resource = ar913x_wmac_resources, -+ .num_resources = ARRAY_SIZE(ar913x_wmac_resources), ++ .resource = ar9xxx_wmac_resources, ++ .num_resources = ARRAY_SIZE(ar9xxx_wmac_resources), + .dev = { -+ .platform_data = &ar913x_wmac_data, ++ .platform_data = &ar9xxx_wmac_data, + }, +}; + -+void __init ar913x_add_device_wmac(u8 *cal_data, u8 *mac_addr) ++static void ar913x_wmac_init(void) +{ -+ if (cal_data) -+ memcpy(ar913x_wmac_data.eeprom_data, cal_data, -+ sizeof(ar913x_wmac_data.eeprom_data)); -+ -+ if (mac_addr) { -+ memcpy(ar913x_wmac_mac, mac_addr, sizeof(ar913x_wmac_mac)); -+ ar913x_wmac_data.macaddr = ar913x_wmac_mac; -+ } -+ + ar71xx_device_stop(RESET_MODULE_AMBA2WMAC); + mdelay(10); + + ar71xx_device_start(RESET_MODULE_AMBA2WMAC); + mdelay(10); + -+ platform_device_register(&ar913x_wmac_device); ++ ar9xxx_wmac_resources[0].start = AR91XX_WMAC_BASE; ++ ar9xxx_wmac_resources[0].end = AR91XX_WMAC_BASE + AR91XX_WMAC_SIZE - 1; +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.h linux-2.6.39/arch/mips/ar71xx/dev-ar913x-wmac.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-ar913x-wmac.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-ar913x-wmac.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,19 @@ -+/* -+ * Atheros AR913x SoC built-in WMAC device support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ + -+#ifndef _AR71XX_DEV_AR913X_WMAC_H -+#define _AR71XX_DEV_AR913X_WMAC_H ++static int ar933x_r1_get_wmac_revision(void) ++{ ++ return ar71xx_soc_rev; ++} + -+void ar913x_add_device_wmac(u8 *cal_data, u8 *mac_addr) __init; ++static int ar933x_wmac_reset(void) ++{ ++ unsigned retries = 0; + -+#endif /* _AR71XX_DEV_AR913X_WMAC_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.c linux-2.6.39/arch/mips/ar71xx/dev-dsa.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-dsa.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,50 @@ -+/* -+ * Atheros AR71xx DSA switch device support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ ar71xx_device_stop(AR933X_RESET_WMAC); ++ ar71xx_device_start(AR933X_RESET_WMAC); + -+#include -+#include ++ while (1) { ++ u32 bootstrap; + -+#include ++ bootstrap = ar71xx_reset_rr(AR933X_RESET_REG_BOOTSTRAP); ++ if ((bootstrap & AR933X_BOOTSTRAP_EEPBUSY) == 0) ++ return 0; + -+#include "devices.h" -+#include "dev-dsa.h" ++ if (retries > 20) ++ break; + -+static struct platform_device ar71xx_dsa_switch_device = { -+ .name = "dsa", -+ .id = 0, -+}; ++ udelay(10000); ++ retries++; ++ } + -+void __init ar71xx_add_device_dsa(unsigned int id, -+ struct dsa_platform_data *d) -+{ -+ int i; ++ pr_err("ar93xx: WMAC reset timed out"); ++ return -ETIMEDOUT; ++} ++ ++static void ar933x_wmac_init(void) ++{ ++ ar9xxx_wmac_device.name = "ar933x_wmac"; ++ ar9xxx_wmac_resources[0].start = AR933X_WMAC_BASE; ++ ar9xxx_wmac_resources[0].end = AR933X_WMAC_BASE + AR933X_WMAC_SIZE - 1; ++ if (ar71xx_ref_freq == MHZ_25) ++ ar9xxx_wmac_data.is_clk_25mhz = true; ++ ++ if (ar71xx_soc_rev == 1) ++ ar9xxx_wmac_data.get_mac_revision = ar933x_r1_get_wmac_revision; ++ ++ ar9xxx_wmac_data.external_reset = ar933x_wmac_reset; ++ ++ ar933x_wmac_reset(); ++} ++ ++static void ar934x_wmac_init(void) ++{ ++ ar9xxx_wmac_device.name = "ar934x_wmac"; ++ ar9xxx_wmac_resources[0].start = AR934X_WMAC_BASE; ++ ar9xxx_wmac_resources[0].end = AR934X_WMAC_BASE + AR934X_WMAC_SIZE - 1; ++ if (ar71xx_ref_freq == MHZ_25) ++ ar9xxx_wmac_data.is_clk_25mhz = true; ++} ++ ++void __init ar9xxx_add_device_wmac(u8 *cal_data, u8 *mac_addr) ++{ ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ ar913x_wmac_init(); ++ break; ++ ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ar933x_wmac_init(); ++ break; ++ ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ar934x_wmac_init(); ++ break; ++ ++ default: ++ BUG(); ++ } ++ ++ if (cal_data) ++ memcpy(ar9xxx_wmac_data.eeprom_data, cal_data, ++ sizeof(ar9xxx_wmac_data.eeprom_data)); ++ ++ if (mac_addr) { ++ memcpy(ar9xxx_wmac_mac, mac_addr, sizeof(ar9xxx_wmac_mac)); ++ ar9xxx_wmac_data.macaddr = ar9xxx_wmac_mac; ++ } ++ ++ platform_device_register(&ar9xxx_wmac_device); ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-ar9xxx-wmac.h linux-2.6.39/arch/mips/ar71xx/dev-ar9xxx-wmac.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-ar9xxx-wmac.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-ar9xxx-wmac.h 2011-08-24 02:41:55.297981663 +0200 +@@ -0,0 +1,20 @@ ++/* ++ * Atheros AR9XXX SoCs built-in WMAC device support ++ * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros 2.6.15/2.6.31 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#ifndef _AR71XX_DEV_AR9XXX_WMAC_H ++#define _AR71XX_DEV_AR9XXX_WMAC_H ++ ++void ar9xxx_add_device_wmac(u8 *cal_data, u8 *mac_addr) __init; ++ ++#endif /* _AR71XX_DEV_AR9XXX_WMAC_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-db120-pci.c linux-2.6.39/arch/mips/ar71xx/dev-db120-pci.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-db120-pci.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-db120-pci.c 2011-08-24 02:41:55.317990461 +0200 +@@ -0,0 +1,31 @@ ++/* ++ * Atheros db120 reference board PCI initialization ++ * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * ++ * Parts of this file are based on Atheros linux 2.6.31 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++ ++#include ++#include ++ ++#include "dev-db120-pci.h" ++ ++static struct ar71xx_pci_irq db120_pci_irqs[] __initdata = { ++ { ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, ++ } ++}; ++ ++void __init db120_pci_init(void) ++{ ++ ar71xx_pci_init(ARRAY_SIZE(db120_pci_irqs), db120_pci_irqs); ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-db120-pci.h linux-2.6.39/arch/mips/ar71xx/dev-db120-pci.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-db120-pci.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-db120-pci.h 2011-08-24 02:41:55.327990934 +0200 +@@ -0,0 +1,22 @@ ++/* ++ * Atheros DB120 reference board PCI initialization ++ * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * ++ * Parts of this file are based on Atheros linux 2.6.31 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#ifndef _AR71XX_DEV_DB120_PCI_H ++#define _AR71XX_DEV_DB120_PCI_H ++ ++#if defined(CONFIG_AR71XX_DEV_DB120_PCI) ++void db120_pci_init(void); ++#else ++static inline void db120_pci_init(void) { } ++#endif ++ ++#endif /* _AR71XX_DEV_DB120_PCI_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.c linux-2.6.39/arch/mips/ar71xx/dev-dsa.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-dsa.c 2011-08-24 02:41:55.337990441 +0200 +@@ -0,0 +1,50 @@ ++/* ++ * Atheros AR71xx DSA switch device support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++ ++#include ++ ++#include "devices.h" ++#include "dev-dsa.h" ++ ++static struct platform_device ar71xx_dsa_switch_device = { ++ .name = "dsa", ++ .id = 0, ++}; ++ ++void __init ar71xx_add_device_dsa(unsigned int id, ++ struct dsa_platform_data *d) ++{ ++ int i; + + switch (id) { + case 0: @@ -1147,7 +783,7 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.c linux-2.6.39/arch/mips/ar +} diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.h linux-2.6.39/arch/mips/ar71xx/dev-dsa.h --- linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-dsa.h 2011-05-27 14:36:51.000000000 +0200 ++++ linux-2.6.39/arch/mips/ar71xx/dev-dsa.h 2011-08-24 02:41:55.347990727 +0200 @@ -0,0 +1,20 @@ +/* + * Atheros AR71xx DSA switch device support @@ -1171,7 +807,7 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-dsa.h linux-2.6.39/arch/mips/ar +#endif /* _AR71XX_DEV_DSA_H */ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.c --- linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.c 2011-05-27 14:36:51.000000000 +0200 ++++ linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.c 2011-08-24 02:41:55.347990727 +0200 @@ -0,0 +1,58 @@ +/* + * Atheros AR71xx GPIO button support @@ -1185,18 +821,19 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c linux-2.6.39/arc + */ + +#include "linux/init.h" ++#include "linux/slab.h" +#include + +#include "dev-gpio-buttons.h" + -+void __init ar71xx_add_device_gpio_buttons(int id, -+ unsigned poll_interval, -+ unsigned nbuttons, -+ struct gpio_button *buttons) ++void __init ar71xx_register_gpio_keys_polled(int id, ++ unsigned poll_interval, ++ unsigned nbuttons, ++ struct gpio_keys_button *buttons) +{ + struct platform_device *pdev; -+ struct gpio_buttons_platform_data pdata; -+ struct gpio_button *p; ++ struct gpio_keys_platform_data pdata; ++ struct gpio_keys_button *p; + int err; + + p = kmalloc(nbuttons * sizeof(*p), GFP_KERNEL); @@ -1205,7 +842,7 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c linux-2.6.39/arc + + memcpy(p, buttons, nbuttons * sizeof(*p)); + -+ pdev = platform_device_alloc("gpio-buttons", id); ++ pdev = platform_device_alloc("gpio-keys-polled", id); + if (!pdev) + goto err_free_buttons; + @@ -1218,7 +855,6 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c linux-2.6.39/arc + if (err) + goto err_put_pdev; + -+ + err = platform_device_add(pdev); + if (err) + goto err_put_pdev; @@ -1233,8 +869,8 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.c linux-2.6.39/arc +} diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.h linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.h --- linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,25 @@ ++++ linux-2.6.39/arch/mips/ar71xx/dev-gpio-buttons.h 2011-08-24 02:41:55.347990727 +0200 +@@ -0,0 +1,23 @@ +/* + * Atheros AR71xx GPIO button support + * @@ -1250,1169 +886,1121 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-gpio-buttons.h linux-2.6.39/arc +#define _AR71XX_DEV_GPIO_BUTTONS_H + +#include -+#include -+ -+#include ++#include + -+void ar71xx_add_device_gpio_buttons(int id, -+ unsigned poll_interval, -+ unsigned nbuttons, -+ struct gpio_button *buttons) __init; ++void ar71xx_register_gpio_keys_polled(int id, ++ unsigned poll_interval, ++ unsigned nbuttons, ++ struct gpio_keys_button *buttons); + +#endif /* _AR71XX_DEV_GPIO_BUTTONS_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.c linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,57 @@ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/devices.c linux-2.6.39/arch/mips/ar71xx/devices.c +--- linux-2.6.39.orig/arch/mips/ar71xx/devices.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/devices.c 2011-08-24 02:41:55.347990727 +0200 +@@ -0,0 +1,765 @@ +/* -+ * Atheros AR71xx GPIO LED device support ++ * Atheros AR71xx SoC platform devices + * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan + * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.31 BSP + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include +#include ++#include ++#include +#include -+#include -+ -+#include "dev-leds-gpio.h" -+ -+void __init ar71xx_add_device_leds_gpio(int id, unsigned num_leds, -+ struct gpio_led *leds) -+{ -+ struct platform_device *pdev; -+ struct gpio_led_platform_data pdata; -+ struct gpio_led *p; -+ int err; ++#include + -+ p = kmalloc(num_leds * sizeof(*p), GFP_KERNEL); -+ if (!p) -+ return; ++#include ++#include + -+ memcpy(p, leds, num_leds * sizeof(*p)); ++#include "devices.h" + -+ pdev = platform_device_alloc("leds-gpio", id); -+ if (!pdev) -+ goto err_free_leds; ++unsigned char ar71xx_mac_base[ETH_ALEN] __initdata; + -+ memset(&pdata, 0, sizeof(pdata)); -+ pdata.num_leds = num_leds; -+ pdata.leds = p; ++static struct resource ar71xx_uart_resources[] = { ++ { ++ .start = AR71XX_UART_BASE, ++ .end = AR71XX_UART_BASE + AR71XX_UART_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; + -+ err = platform_device_add_data(pdev, &pdata, sizeof(pdata)); -+ if (err) -+ goto err_put_pdev; ++#define AR71XX_UART_FLAGS (UPF_BOOT_AUTOCONF | UPF_SKIP_TEST | UPF_IOREMAP) ++static struct plat_serial8250_port ar71xx_uart_data[] = { ++ { ++ .mapbase = AR71XX_UART_BASE, ++ .irq = AR71XX_MISC_IRQ_UART, ++ .flags = AR71XX_UART_FLAGS, ++ .iotype = UPIO_MEM32, ++ .regshift = 2, ++ }, { ++ /* terminating entry */ ++ } ++}; + -+ err = platform_device_add(pdev); -+ if (err) -+ goto err_put_pdev; ++static struct platform_device ar71xx_uart_device = { ++ .name = "serial8250", ++ .id = PLAT8250_DEV_PLATFORM, ++ .resource = ar71xx_uart_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_uart_resources), ++ .dev = { ++ .platform_data = ar71xx_uart_data ++ }, ++}; + -+ return; ++static struct resource ar933x_uart_resources[] = { ++ { ++ .start = AR933X_UART_BASE, ++ .end = AR933X_UART_BASE + AR71XX_UART_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++ { ++ .start = AR71XX_MISC_IRQ_UART, ++ .end = AR71XX_MISC_IRQ_UART, ++ .flags = IORESOURCE_IRQ, ++ }, ++}; + -+err_put_pdev: -+ platform_device_put(pdev); ++static struct ar933x_uart_platform_data ar933x_uart_data; ++static struct platform_device ar933x_uart_device = { ++ .name = "ar933x-uart", ++ .id = -1, ++ .resource = ar933x_uart_resources, ++ .num_resources = ARRAY_SIZE(ar933x_uart_resources), ++ .dev = { ++ .platform_data = &ar933x_uart_data, ++ }, ++}; + -+err_free_leds: -+ kfree(p); -+} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.h linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,21 @@ -+/* -+ * Atheros AR71xx GPIO LED device support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++void __init ar71xx_add_device_uart(void) ++{ ++ struct platform_device *pdev; + -+#ifndef _AR71XX_DEV_LEDS_GPIO_H -+#define _AR71XX_DEV_LEDS_GPIO_H ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ pdev = &ar71xx_uart_device; ++ ar71xx_uart_data[0].uartclk = ar71xx_ahb_freq; ++ break; + -+#include ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ pdev = &ar933x_uart_device; ++ ar933x_uart_data.uartclk = ar71xx_ref_freq; ++ break; + -+void ar71xx_add_device_leds_gpio(int id, -+ unsigned num_leds, -+ struct gpio_led *leds) __init; ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ pdev = &ar71xx_uart_device; ++ ar71xx_uart_data[0].uartclk = ar71xx_ref_freq; ++ break; + -+#endif /* _AR71XX_DEV_LEDS_GPIO_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.c linux-2.6.39/arch/mips/ar71xx/dev-m25p80.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-m25p80.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,30 @@ -+/* -+ * Copyright (C) 2009 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ default: ++ BUG(); ++ } + -+#include -+#include -+#include ++ platform_device_register(pdev); ++} + -+#include "devices.h" -+#include "dev-m25p80.h" -+ -+static struct spi_board_info ar71xx_spi_info[] = { ++static struct resource ar71xx_mdio_resources[] = { + { -+ .bus_num = 0, -+ .chip_select = 0, -+ .max_speed_hz = 25000000, -+ .modalias = "m25p80", ++ .name = "mdio_base", ++ .flags = IORESOURCE_MEM, ++ .start = AR71XX_GE0_BASE, ++ .end = AR71XX_GE0_BASE + 0x200 - 1, + } +}; + -+void __init ar71xx_add_device_m25p80(struct flash_platform_data *pdata) -+{ -+ ar71xx_spi_info[0].platform_data = pdata; -+ ar71xx_add_device_spi(NULL, ar71xx_spi_info, -+ ARRAY_SIZE(ar71xx_spi_info)); -+} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.h linux-2.6.39/arch/mips/ar71xx/dev-m25p80.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-m25p80.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,16 @@ -+/* -+ * Copyright (C) 2009 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++static struct ag71xx_mdio_platform_data ar71xx_mdio_data; + -+#ifndef _AR71XX_DEV_M25P80_H -+#define _AR71XX_DEV_M25P80_H ++struct platform_device ar71xx_mdio_device = { ++ .name = "ag71xx-mdio", ++ .id = -1, ++ .resource = ar71xx_mdio_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_mdio_resources), ++ .dev = { ++ .platform_data = &ar71xx_mdio_data, ++ }, ++}; + -+#include ++static void ar71xx_set_pll(u32 cfg_reg, u32 pll_reg, u32 pll_val, u32 shift) ++{ ++ void __iomem *base; ++ u32 t; + -+void ar71xx_add_device_m25p80(struct flash_platform_data *pdata) __init; ++ base = ioremap_nocache(AR71XX_PLL_BASE, AR71XX_PLL_SIZE); + -+#endif /* _AR71XX_DEV_M25P80_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.c linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,40 @@ -+/* -+ * Atheros PB42 reference board PCI initialization -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ t = __raw_readl(base + cfg_reg); ++ t &= ~(3 << shift); ++ t |= (2 << shift); ++ __raw_writel(t, base + cfg_reg); ++ udelay(100); + -+#include ++ __raw_writel(pll_val, base + pll_reg); + -+#include -+#include ++ t |= (3 << shift); ++ __raw_writel(t, base + cfg_reg); ++ udelay(100); + -+#include "dev-pb42-pci.h" ++ t &= ~(3 << shift); ++ __raw_writel(t, base + cfg_reg); ++ udelay(100); + -+static struct ar71xx_pci_irq pb42_pci_irqs[] __initdata = { -+ { -+ .slot = 0, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV0, -+ }, { -+ .slot = 1, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV1, -+ }, { -+ .slot = 2, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV2, -+ } -+}; ++ printk(KERN_DEBUG "ar71xx: pll_reg %#x: %#x\n", ++ (unsigned int)(base + pll_reg), __raw_readl(base + pll_reg)); + -+void __init pb42_pci_init(void) -+{ -+ ar71xx_pci_init(ARRAY_SIZE(pb42_pci_irqs), pb42_pci_irqs); ++ iounmap(base); +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.h linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,21 @@ -+/* -+ * Atheros PB42 reference board PCI initialization -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ + -+#ifndef _AR71XX_DEV_PB42_PCI_H -+#define _AR71XX_DEV_PB42_PCI_H ++void __init ar71xx_add_device_mdio(u32 phy_mask) ++{ ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7240: ++ ar71xx_mdio_data.is_ar7240 = 1; ++ break; ++ case AR71XX_SOC_AR7241: ++ ar71xx_mdio_data.is_ar7240 = 1; ++ ar71xx_mdio_resources[0].start = AR71XX_GE1_BASE; ++ ar71xx_mdio_resources[0].end = AR71XX_GE1_BASE + 0x200 - 1; ++ break; ++ case AR71XX_SOC_AR7242: ++ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, ++ AR7242_PLL_REG_ETH0_INT_CLOCK, 0x62000000, ++ AR71XX_ETH0_PLL_SHIFT); ++ break; ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ar71xx_mdio_data.is_ar7240 = 1; ++ ar71xx_mdio_resources[0].start = AR71XX_GE1_BASE; ++ ar71xx_mdio_resources[0].end = AR71XX_GE1_BASE + 0x200 - 1; ++ break; ++ default: ++ break; ++ } + -+#if defined(CONFIG_AR71XX_DEV_PB42_PCI) -+void pb42_pci_init(void) __init; -+#else -+static inline void pb42_pci_init(void) { } -+#endif ++ ar71xx_mdio_data.phy_mask = phy_mask; + -+#endif /* _AR71XX_DEV_PB42_PCI_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.c linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,33 @@ -+/* -+ * Atheros PB9x reference board PCI initialization -+ * -+ * Copyright (C) 2010 Felix Fietkau -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ platform_device_register(&ar71xx_mdio_device); ++} + -+#include ++struct ar71xx_eth_pll_data ar71xx_eth0_pll_data; ++struct ar71xx_eth_pll_data ar71xx_eth1_pll_data; + -+#include -+#include ++static u32 ar71xx_get_eth_pll(unsigned int mac, int speed) ++{ ++ struct ar71xx_eth_pll_data *pll_data; ++ u32 pll_val; + -+#include "dev-pb9x-pci.h" ++ switch (mac) { ++ case 0: ++ pll_data = &ar71xx_eth0_pll_data; ++ break; ++ case 1: ++ pll_data = &ar71xx_eth1_pll_data; ++ break; ++ default: ++ BUG(); ++ } + -+static struct ar71xx_pci_irq pb9x_pci_irqs[] __initdata = { -+ { -+ .slot = 0, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV0, ++ switch (speed) { ++ case SPEED_10: ++ pll_val = pll_data->pll_10; ++ break; ++ case SPEED_100: ++ pll_val = pll_data->pll_100; ++ break; ++ case SPEED_1000: ++ pll_val = pll_data->pll_1000; ++ break; ++ default: ++ BUG(); + } -+}; + -+void __init pb9x_pci_init(void) -+{ -+ ar71xx_pci_init(ARRAY_SIZE(pb9x_pci_irqs), pb9x_pci_irqs); ++ return pll_val; +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.h linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,22 @@ -+/* -+ * Atheros PB9x reference board PCI initialization -+ * -+ * Copyright (C) 2010 Felix Fietkau -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#ifndef _AR71XX_DEV_PB9X_PCI_H -+#define _AR71XX_DEV_PB9X_PCI_H + -+#if defined(CONFIG_AR71XX_DEV_PB9X_PCI) -+void pb9x_pci_init(void) __init; -+#else -+static inline void pb9x_pci_init(void) { } -+#endif ++static void ar71xx_set_pll_ge0(int speed) ++{ ++ u32 val = ar71xx_get_eth_pll(0, speed); + -+#endif /* _AR71XX_DEV_PB9X_PCI_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.c linux-2.6.39/arch/mips/ar71xx/dev-usb.c ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-usb.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,181 @@ -+/* -+ * Atheros AR71xx USB host device support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, AR71XX_PLL_REG_ETH0_INT_CLOCK, ++ val, AR71XX_ETH0_PLL_SHIFT); ++} + -+#include -+#include -+#include -+#include -+#include ++static void ar71xx_set_pll_ge1(int speed) ++{ ++ u32 val = ar71xx_get_eth_pll(1, speed); + -+#include -+#include ++ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, AR71XX_PLL_REG_ETH1_INT_CLOCK, ++ val, AR71XX_ETH1_PLL_SHIFT); ++} + -+#include "dev-usb.h" ++static void ar724x_set_pll_ge0(int speed) ++{ ++ /* TODO */ ++} + -+/* -+ * OHCI (USB full speed host controller) -+ */ -+static struct resource ar71xx_ohci_resources[] = { -+ [0] = { -+ .start = AR71XX_OHCI_BASE, -+ .end = AR71XX_OHCI_BASE + AR71XX_OHCI_SIZE - 1, ++static void ar724x_set_pll_ge1(int speed) ++{ ++ /* TODO */ ++} ++ ++static void ar7242_set_pll_ge0(int speed) ++{ ++ u32 val = ar71xx_get_eth_pll(0, speed); ++ ++ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, AR7242_PLL_REG_ETH0_INT_CLOCK, ++ val, AR71XX_ETH0_PLL_SHIFT); ++} ++ ++static void ar91xx_set_pll_ge0(int speed) ++{ ++ u32 val = ar71xx_get_eth_pll(0, speed); ++ ++ ar71xx_set_pll(AR91XX_PLL_REG_ETH_CONFIG, AR91XX_PLL_REG_ETH0_INT_CLOCK, ++ val, AR91XX_ETH0_PLL_SHIFT); ++} ++ ++static void ar91xx_set_pll_ge1(int speed) ++{ ++ u32 val = ar71xx_get_eth_pll(1, speed); ++ ++ ar71xx_set_pll(AR91XX_PLL_REG_ETH_CONFIG, AR91XX_PLL_REG_ETH1_INT_CLOCK, ++ val, AR91XX_ETH1_PLL_SHIFT); ++} ++ ++static void ar933x_set_pll_ge0(int speed) ++{ ++ /* TODO */ ++} ++ ++static void ar933x_set_pll_ge1(int speed) ++{ ++ /* TODO */ ++} ++ ++static void ar71xx_ddr_flush_ge0(void) ++{ ++ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_GE0); ++} ++ ++static void ar71xx_ddr_flush_ge1(void) ++{ ++ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_GE1); ++} ++ ++static void ar724x_ddr_flush_ge0(void) ++{ ++ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_GE0); ++} ++ ++static void ar724x_ddr_flush_ge1(void) ++{ ++ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_GE1); ++} ++ ++static void ar91xx_ddr_flush_ge0(void) ++{ ++ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_GE0); ++} ++ ++static void ar91xx_ddr_flush_ge1(void) ++{ ++ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_GE1); ++} ++ ++static void ar933x_ddr_flush_ge0(void) ++{ ++ ar71xx_ddr_flush(AR933X_DDR_REG_FLUSH_GE0); ++} ++ ++static void ar933x_ddr_flush_ge1(void) ++{ ++ ar71xx_ddr_flush(AR933X_DDR_REG_FLUSH_GE1); ++} ++ ++static struct resource ar71xx_eth0_resources[] = { ++ { ++ .name = "mac_base", + .flags = IORESOURCE_MEM, -+ }, -+ [1] = { -+ .start = AR71XX_MISC_IRQ_OHCI, -+ .end = AR71XX_MISC_IRQ_OHCI, ++ .start = AR71XX_GE0_BASE, ++ .end = AR71XX_GE0_BASE + 0x200 - 1, ++ }, { ++ .name = "mii_ctrl", ++ .flags = IORESOURCE_MEM, ++ .start = AR71XX_MII_BASE + MII_REG_MII0_CTRL, ++ .end = AR71XX_MII_BASE + MII_REG_MII0_CTRL + 3, ++ }, { ++ .name = "mac_irq", + .flags = IORESOURCE_IRQ, ++ .start = AR71XX_CPU_IRQ_GE0, ++ .end = AR71XX_CPU_IRQ_GE0, + }, +}; + -+static struct resource ar7240_ohci_resources[] = { -+ [0] = { -+ .start = AR7240_OHCI_BASE, -+ .end = AR7240_OHCI_BASE + AR7240_OHCI_SIZE - 1, -+ .flags = IORESOURCE_MEM, -+ }, -+ [1] = { -+ .start = AR71XX_CPU_IRQ_USB, -+ .end = AR71XX_CPU_IRQ_USB, -+ .flags = IORESOURCE_IRQ, -+ }, ++struct ag71xx_platform_data ar71xx_eth0_data = { ++ .reset_bit = RESET_MODULE_GE0_MAC, +}; + -+static u64 ar71xx_ohci_dmamask = DMA_BIT_MASK(32); -+static struct platform_device ar71xx_ohci_device = { -+ .name = "ar71xx-ohci", -+ .id = -1, -+ .resource = ar71xx_ohci_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_ohci_resources), ++struct platform_device ar71xx_eth0_device = { ++ .name = "ag71xx", ++ .id = 0, ++ .resource = ar71xx_eth0_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_eth0_resources), + .dev = { -+ .dma_mask = &ar71xx_ohci_dmamask, -+ .coherent_dma_mask = DMA_BIT_MASK(32), ++ .platform_data = &ar71xx_eth0_data, + }, +}; + -+/* -+ * EHCI (USB full speed host controller) -+ */ -+static struct resource ar71xx_ehci_resources[] = { -+ [0] = { -+ .start = AR71XX_EHCI_BASE, -+ .end = AR71XX_EHCI_BASE + AR71XX_EHCI_SIZE - 1, ++static struct resource ar71xx_eth1_resources[] = { ++ { ++ .name = "mac_base", + .flags = IORESOURCE_MEM, -+ }, -+ [1] = { -+ .start = AR71XX_CPU_IRQ_USB, -+ .end = AR71XX_CPU_IRQ_USB, ++ .start = AR71XX_GE1_BASE, ++ .end = AR71XX_GE1_BASE + 0x200 - 1, ++ }, { ++ .name = "mii_ctrl", ++ .flags = IORESOURCE_MEM, ++ .start = AR71XX_MII_BASE + MII_REG_MII1_CTRL, ++ .end = AR71XX_MII_BASE + MII_REG_MII1_CTRL + 3, ++ }, { ++ .name = "mac_irq", + .flags = IORESOURCE_IRQ, ++ .start = AR71XX_CPU_IRQ_GE1, ++ .end = AR71XX_CPU_IRQ_GE1, + }, +}; + -+static u64 ar71xx_ehci_dmamask = DMA_BIT_MASK(32); -+static struct ar71xx_ehci_platform_data ar71xx_ehci_data; ++struct ag71xx_platform_data ar71xx_eth1_data = { ++ .reset_bit = RESET_MODULE_GE1_MAC, ++}; + -+static struct platform_device ar71xx_ehci_device = { -+ .name = "ar71xx-ehci", -+ .id = -1, -+ .resource = ar71xx_ehci_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_ehci_resources), ++struct platform_device ar71xx_eth1_device = { ++ .name = "ag71xx", ++ .id = 1, ++ .resource = ar71xx_eth1_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_eth1_resources), + .dev = { -+ .dma_mask = &ar71xx_ehci_dmamask, -+ .coherent_dma_mask = DMA_BIT_MASK(32), -+ .platform_data = &ar71xx_ehci_data, ++ .platform_data = &ar71xx_eth1_data, + }, +}; + -+#define AR71XX_USB_RESET_MASK \ -+ (RESET_MODULE_USB_HOST | RESET_MODULE_USB_PHY \ -+ | RESET_MODULE_USB_OHCI_DLL) -+ -+#define AR7240_USB_RESET_MASK \ -+ (RESET_MODULE_USB_HOST | RESET_MODULE_USB_OHCI_DLL_7240) -+ -+static void __init ar71xx_usb_setup(void) -+{ -+ ar71xx_device_stop(AR71XX_USB_RESET_MASK); -+ mdelay(1000); -+ ar71xx_device_start(AR71XX_USB_RESET_MASK); ++#define AR71XX_PLL_VAL_1000 0x00110000 ++#define AR71XX_PLL_VAL_100 0x00001099 ++#define AR71XX_PLL_VAL_10 0x00991099 + -+ /* Turning on the Buff and Desc swap bits */ -+ ar71xx_usb_ctrl_wr(USB_CTRL_REG_CONFIG, 0xf0000); ++#define AR724X_PLL_VAL_1000 0x00110000 ++#define AR724X_PLL_VAL_100 0x00001099 ++#define AR724X_PLL_VAL_10 0x00991099 + -+ /* WAR for HW bug. Here it adjusts the duration between two SOFS */ -+ ar71xx_usb_ctrl_wr(USB_CTRL_REG_FLADJ, 0x20c00); ++#define AR7242_PLL_VAL_1000 0x1c000000 ++#define AR7242_PLL_VAL_100 0x00000101 ++#define AR7242_PLL_VAL_10 0x00001616 + -+ mdelay(900); ++#define AR91XX_PLL_VAL_1000 0x1a000000 ++#define AR91XX_PLL_VAL_100 0x13000a44 ++#define AR91XX_PLL_VAL_10 0x00441099 + -+ platform_device_register(&ar71xx_ohci_device); -+ platform_device_register(&ar71xx_ehci_device); -+} ++#define AR933X_PLL_VAL_1000 0x00110000 ++#define AR933X_PLL_VAL_100 0x00001099 ++#define AR933X_PLL_VAL_10 0x00991099 + -+static void __init ar7240_usb_setup(void) ++static void __init ar71xx_init_eth_pll_data(unsigned int id) +{ -+ ar71xx_device_stop(AR7240_USB_RESET_MASK); -+ mdelay(1000); -+ ar71xx_device_start(AR7240_USB_RESET_MASK); -+ -+ /* WAR for HW bug. Here it adjusts the duration between two SOFS */ -+ ar71xx_usb_ctrl_wr(USB_CTRL_REG_FLADJ, 0x3); ++ struct ar71xx_eth_pll_data *pll_data; ++ u32 pll_10, pll_100, pll_1000; + -+ if (ar71xx_soc == AR71XX_SOC_AR7241 || ar71xx_soc == AR71XX_SOC_AR7242) { -+ ar71xx_ehci_data.is_ar91xx = 1; -+ ar71xx_ehci_device.resource = ar7240_ohci_resources; -+ ar71xx_ehci_device.num_resources = ARRAY_SIZE(ar7240_ohci_resources); -+ platform_device_register(&ar71xx_ehci_device); -+ } else { -+ ar71xx_ohci_device.resource = ar7240_ohci_resources; -+ ar71xx_ohci_device.num_resources = ARRAY_SIZE(ar7240_ohci_resources); -+ platform_device_register(&ar71xx_ohci_device); ++ switch (id) { ++ case 0: ++ pll_data = &ar71xx_eth0_pll_data; ++ break; ++ case 1: ++ pll_data = &ar71xx_eth1_pll_data; ++ break; ++ default: ++ BUG(); + } -+} -+ -+static void __init ar91xx_usb_setup(void) -+{ -+ ar71xx_device_stop(RESET_MODULE_USBSUS_OVERRIDE); -+ mdelay(10); + -+ ar71xx_device_start(RESET_MODULE_USB_HOST); -+ mdelay(10); -+ -+ ar71xx_device_start(RESET_MODULE_USB_PHY); -+ mdelay(10); -+ -+ ar71xx_ehci_data.is_ar91xx = 1; -+ platform_device_register(&ar71xx_ehci_device); -+} -+ -+void __init ar71xx_add_device_usb(void) -+{ + switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ pll_10 = AR71XX_PLL_VAL_10; ++ pll_100 = AR71XX_PLL_VAL_100; ++ pll_1000 = AR71XX_PLL_VAL_1000; ++ break; ++ + case AR71XX_SOC_AR7240: + case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ar7240_usb_setup(); ++ pll_10 = AR724X_PLL_VAL_10; ++ pll_100 = AR724X_PLL_VAL_100; ++ pll_1000 = AR724X_PLL_VAL_1000; + break; + -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ ar71xx_usb_setup(); ++ case AR71XX_SOC_AR7242: ++ pll_10 = AR7242_PLL_VAL_10; ++ pll_100 = AR7242_PLL_VAL_100; ++ pll_1000 = AR7242_PLL_VAL_1000; + break; + + case AR71XX_SOC_AR9130: + case AR71XX_SOC_AR9132: -+ ar91xx_usb_setup(); -+ break; ++ pll_10 = AR91XX_PLL_VAL_10; ++ pll_100 = AR91XX_PLL_VAL_100; ++ pll_1000 = AR91XX_PLL_VAL_1000; ++ break; ++ ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ pll_10 = AR933X_PLL_VAL_10; ++ pll_100 = AR933X_PLL_VAL_100; ++ pll_1000 = AR933X_PLL_VAL_1000; ++ break; + + default: + BUG(); + } -+} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.h linux-2.6.39/arch/mips/ar71xx/dev-usb.h ---- linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/dev-usb.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,17 @@ -+/* -+ * Atheros AR71xx USB host device support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#ifndef _AR71XX_DEV_USB_H -+#define _AR71XX_DEV_USB_H -+ -+void ar71xx_add_device_usb(void) __init; -+ -+#endif /* _AR71XX_DEV_USB_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/devices.c linux-2.6.39/arch/mips/ar71xx/devices.c ---- linux-2.6.39.orig/arch/mips/ar71xx/devices.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/devices.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,575 @@ -+/* -+ * Atheros AR71xx SoC platform devices -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include + -+#include -+ -+#include "devices.h" -+ -+static u8 ar71xx_mac_base[ETH_ALEN] __initdata; -+ -+static struct resource ar71xx_uart_resources[] = { -+ { -+ .start = AR71XX_UART_BASE, -+ .end = AR71XX_UART_BASE + AR71XX_UART_SIZE - 1, -+ .flags = IORESOURCE_MEM, -+ }, -+}; -+ -+#define AR71XX_UART_FLAGS (UPF_BOOT_AUTOCONF | UPF_SKIP_TEST | UPF_IOREMAP) -+static struct plat_serial8250_port ar71xx_uart_data[] = { -+ { -+ .mapbase = AR71XX_UART_BASE, -+ .irq = AR71XX_MISC_IRQ_UART, -+ .flags = AR71XX_UART_FLAGS, -+ .iotype = UPIO_MEM32, -+ .regshift = 2, -+ }, { -+ /* terminating entry */ -+ } -+}; ++ if (!pll_data->pll_10) ++ pll_data->pll_10 = pll_10; + -+static struct platform_device ar71xx_uart_device = { -+ .name = "serial8250", -+ .id = PLAT8250_DEV_PLATFORM, -+ .resource = ar71xx_uart_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_uart_resources), -+ .dev = { -+ .platform_data = ar71xx_uart_data -+ }, -+}; ++ if (!pll_data->pll_100) ++ pll_data->pll_100 = pll_100; + -+void __init ar71xx_add_device_uart(void) -+{ -+ ar71xx_uart_data[0].uartclk = ar71xx_ahb_freq; -+ platform_device_register(&ar71xx_uart_device); ++ if (!pll_data->pll_1000) ++ pll_data->pll_1000 = pll_1000; +} + -+static struct resource ar71xx_mdio_resources[] = { -+ { -+ .name = "mdio_base", -+ .flags = IORESOURCE_MEM, -+ .start = AR71XX_GE0_BASE, -+ .end = AR71XX_GE0_BASE + 0x200 - 1, -+ } -+}; -+ -+static struct ag71xx_mdio_platform_data ar71xx_mdio_data; ++static int ar71xx_eth_instance __initdata; ++void __init ar71xx_add_device_eth(unsigned int id) ++{ ++ struct platform_device *pdev; ++ struct ag71xx_platform_data *pdata; + -+struct platform_device ar71xx_mdio_device = { -+ .name = "ag71xx-mdio", -+ .id = -1, -+ .resource = ar71xx_mdio_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_mdio_resources), -+ .dev = { -+ .platform_data = &ar71xx_mdio_data, -+ }, -+}; ++ ar71xx_init_eth_pll_data(id); + -+void __init ar71xx_add_device_mdio(u32 phy_mask) -+{ -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ar71xx_mdio_data.is_ar7240 = 1; ++ switch (id) { ++ case 0: ++ switch (ar71xx_eth0_data.phy_if_mode) { ++ case PHY_INTERFACE_MODE_MII: ++ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_MII; ++ break; ++ case PHY_INTERFACE_MODE_GMII: ++ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_GMII; ++ break; ++ case PHY_INTERFACE_MODE_RGMII: ++ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_RGMII; ++ break; ++ case PHY_INTERFACE_MODE_RMII: ++ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_RMII; ++ break; ++ default: ++ printk(KERN_ERR "ar71xx: invalid PHY interface mode " ++ "for eth0\n"); ++ return; ++ } ++ pdev = &ar71xx_eth0_device; + break; -+ default: ++ case 1: ++ switch (ar71xx_eth1_data.phy_if_mode) { ++ case PHY_INTERFACE_MODE_RMII: ++ ar71xx_eth1_data.mii_if = MII1_CTRL_IF_RMII; ++ break; ++ case PHY_INTERFACE_MODE_RGMII: ++ ar71xx_eth1_data.mii_if = MII1_CTRL_IF_RGMII; ++ break; ++ default: ++ printk(KERN_ERR "ar71xx: invalid PHY interface mode " ++ "for eth1\n"); ++ return; ++ } ++ pdev = &ar71xx_eth1_device; + break; ++ default: ++ printk(KERN_ERR "ar71xx: invalid ethernet id %d\n", id); ++ return; + } + -+ ar71xx_mdio_data.phy_mask = phy_mask; -+ -+ platform_device_register(&ar71xx_mdio_device); -+} -+ -+static void ar71xx_set_pll(u32 cfg_reg, u32 pll_reg, u32 pll_val, u32 shift) -+{ -+ void __iomem *base; -+ u32 t; -+ -+ base = ioremap_nocache(AR71XX_PLL_BASE, AR71XX_PLL_SIZE); ++ pdata = pdev->dev.platform_data; + -+ t = __raw_readl(base + cfg_reg); -+ t &= ~(3 << shift); -+ t |= (2 << shift); -+ __raw_writel(t, base + cfg_reg); -+ udelay(100); ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ pdata->ddr_flush = id ? ar71xx_ddr_flush_ge1 ++ : ar71xx_ddr_flush_ge0; ++ pdata->set_pll = id ? ar71xx_set_pll_ge1 ++ : ar71xx_set_pll_ge0; ++ break; + -+ __raw_writel(pll_val, base + pll_reg); ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ pdata->ddr_flush = id ? ar71xx_ddr_flush_ge1 ++ : ar71xx_ddr_flush_ge0; ++ pdata->set_pll = id ? ar71xx_set_pll_ge1 ++ : ar71xx_set_pll_ge0; ++ pdata->has_gbit = 1; ++ break; + -+ t |= (3 << shift); -+ __raw_writel(t, base + cfg_reg); -+ udelay(100); ++ case AR71XX_SOC_AR7242: ++ ar71xx_eth0_data.reset_bit |= AR724X_RESET_GE0_MDIO | ++ RESET_MODULE_GE0_PHY; ++ ar71xx_eth1_data.reset_bit |= AR724X_RESET_GE1_MDIO | ++ RESET_MODULE_GE1_PHY; ++ pdata->ddr_flush = id ? ar724x_ddr_flush_ge1 ++ : ar724x_ddr_flush_ge0; ++ pdata->set_pll = id ? ar724x_set_pll_ge1 ++ : ar7242_set_pll_ge0; ++ pdata->has_gbit = 1; ++ pdata->is_ar724x = 1; + -+ t &= ~(3 << shift); -+ __raw_writel(t, base + cfg_reg); -+ udelay(100); ++ if (!pdata->fifo_cfg1) ++ pdata->fifo_cfg1 = 0x0010ffff; ++ if (!pdata->fifo_cfg2) ++ pdata->fifo_cfg2 = 0x015500aa; ++ if (!pdata->fifo_cfg3) ++ pdata->fifo_cfg3 = 0x01f00140; ++ break; + -+ printk(KERN_DEBUG "ar71xx: pll_reg %#x: %#x\n", -+ (unsigned int)(base + pll_reg), __raw_readl(base + pll_reg)); ++ case AR71XX_SOC_AR7241: ++ ar71xx_eth0_data.reset_bit |= AR724X_RESET_GE0_MDIO; ++ ar71xx_eth1_data.reset_bit |= AR724X_RESET_GE1_MDIO; ++ /* fall through */ ++ case AR71XX_SOC_AR7240: ++ ar71xx_eth0_data.reset_bit |= RESET_MODULE_GE0_PHY; ++ ar71xx_eth1_data.reset_bit |= RESET_MODULE_GE1_PHY; ++ pdata->ddr_flush = id ? ar724x_ddr_flush_ge1 ++ : ar724x_ddr_flush_ge0; ++ pdata->set_pll = id ? ar724x_set_pll_ge1 ++ : ar724x_set_pll_ge0; ++ pdata->is_ar724x = 1; ++ if (ar71xx_soc == AR71XX_SOC_AR7240) ++ pdata->is_ar7240 = 1; ++ ++ if (!pdata->fifo_cfg1) ++ pdata->fifo_cfg1 = 0x0010ffff; ++ if (!pdata->fifo_cfg2) ++ pdata->fifo_cfg2 = 0x015500aa; ++ if (!pdata->fifo_cfg3) ++ pdata->fifo_cfg3 = 0x01f00140; ++ break; + -+ iounmap(base); -+} ++ case AR71XX_SOC_AR9130: ++ pdata->ddr_flush = id ? ar91xx_ddr_flush_ge1 ++ : ar91xx_ddr_flush_ge0; ++ pdata->set_pll = id ? ar91xx_set_pll_ge1 ++ : ar91xx_set_pll_ge0; ++ pdata->is_ar91xx = 1; ++ break; + -+struct ar71xx_eth_pll_data ar71xx_eth0_pll_data; -+struct ar71xx_eth_pll_data ar71xx_eth1_pll_data; ++ case AR71XX_SOC_AR9132: ++ pdata->ddr_flush = id ? ar91xx_ddr_flush_ge1 ++ : ar91xx_ddr_flush_ge0; ++ pdata->set_pll = id ? ar91xx_set_pll_ge1 ++ : ar91xx_set_pll_ge0; ++ pdata->is_ar91xx = 1; ++ pdata->has_gbit = 1; ++ break; + -+static u32 ar71xx_get_eth_pll(unsigned int mac, int speed) -+{ -+ struct ar71xx_eth_pll_data *pll_data; -+ u32 pll_val; ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ar71xx_eth0_data.reset_bit = AR933X_RESET_GE0_MAC | ++ AR933X_RESET_GE0_MDIO; ++ ar71xx_eth1_data.reset_bit = AR933X_RESET_GE1_MAC | ++ AR933X_RESET_GE1_MDIO; ++ pdata->ddr_flush = id ? ar933x_ddr_flush_ge1 ++ : ar933x_ddr_flush_ge0; ++ pdata->set_pll = id ? ar933x_set_pll_ge1 ++ : ar933x_set_pll_ge0; ++ pdata->has_gbit = 1; ++ pdata->is_ar724x = 1; + -+ switch (mac) { -+ case 0: -+ pll_data = &ar71xx_eth0_pll_data; -+ break; -+ case 1: -+ pll_data = &ar71xx_eth1_pll_data; ++ if (!pdata->fifo_cfg1) ++ pdata->fifo_cfg1 = 0x0010ffff; ++ if (!pdata->fifo_cfg2) ++ pdata->fifo_cfg2 = 0x015500aa; ++ if (!pdata->fifo_cfg3) ++ pdata->fifo_cfg3 = 0x01f00140; + break; ++ + default: + BUG(); + } + -+ switch (speed) { -+ case SPEED_10: -+ pll_val = pll_data->pll_10; -+ break; -+ case SPEED_100: -+ pll_val = pll_data->pll_100; -+ break; -+ case SPEED_1000: -+ pll_val = pll_data->pll_1000; -+ break; ++ switch (pdata->phy_if_mode) { ++ case PHY_INTERFACE_MODE_GMII: ++ case PHY_INTERFACE_MODE_RGMII: ++ if (!pdata->has_gbit) { ++ printk(KERN_ERR "ar71xx: no gbit available on eth%d\n", ++ id); ++ return; ++ } ++ /* fallthrough */ + default: -+ BUG(); ++ break; + } + -+ return pll_val; -+} ++ if (!is_valid_ether_addr(pdata->mac_addr)) { ++ random_ether_addr(pdata->mac_addr); ++ printk(KERN_DEBUG ++ "ar71xx: using random MAC address for eth%d\n", ++ ar71xx_eth_instance); ++ } + -+static void ar71xx_set_pll_ge0(int speed) -+{ -+ u32 val = ar71xx_get_eth_pll(0, speed); ++ if (pdata->mii_bus_dev == NULL) ++ pdata->mii_bus_dev = &ar71xx_mdio_device.dev; + -+ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, AR71XX_PLL_REG_ETH0_INT_CLOCK, -+ val, AR71XX_ETH0_PLL_SHIFT); -+} ++ /* Reset the device */ ++ ar71xx_device_stop(pdata->reset_bit); ++ mdelay(100); + -+static void ar71xx_set_pll_ge1(int speed) -+{ -+ u32 val = ar71xx_get_eth_pll(1, speed); ++ ar71xx_device_start(pdata->reset_bit); ++ mdelay(100); + -+ ar71xx_set_pll(AR71XX_PLL_REG_SEC_CONFIG, AR71XX_PLL_REG_ETH1_INT_CLOCK, -+ val, AR71XX_ETH1_PLL_SHIFT); ++ platform_device_register(pdev); ++ ar71xx_eth_instance++; +} + -+static void ar724x_set_pll_ge0(int speed) ++static struct resource ar71xx_spi_resources[] = { ++ [0] = { ++ .start = AR71XX_SPI_BASE, ++ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; ++ ++static struct platform_device ar71xx_spi_device = { ++ .name = "ar71xx-spi", ++ .id = -1, ++ .resource = ar71xx_spi_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_spi_resources), ++}; ++ ++void __init ar71xx_add_device_spi(struct ar71xx_spi_platform_data *pdata, ++ struct spi_board_info const *info, ++ unsigned n) +{ -+ /* TODO */ ++ spi_register_board_info(info, n); ++ ar71xx_spi_device.dev.platform_data = pdata; ++ platform_device_register(&ar71xx_spi_device); +} + -+static void ar724x_set_pll_ge1(int speed) ++void __init ar71xx_add_device_wdt(void) +{ -+ /* TODO */ ++ platform_device_register_simple("ar71xx-wdt", -1, NULL, 0); +} + -+static void ar91xx_set_pll_ge0(int speed) ++void __init ar71xx_set_mac_base(unsigned char *mac) +{ -+ u32 val = ar71xx_get_eth_pll(0, speed); -+ -+ ar71xx_set_pll(AR91XX_PLL_REG_ETH_CONFIG, AR91XX_PLL_REG_ETH0_INT_CLOCK, -+ val, AR91XX_ETH0_PLL_SHIFT); ++ memcpy(ar71xx_mac_base, mac, ETH_ALEN); +} + -+static void ar91xx_set_pll_ge1(int speed) ++void __init ar71xx_parse_mac_addr(char *mac_str) +{ -+ u32 val = ar71xx_get_eth_pll(1, speed); ++ u8 tmp[ETH_ALEN]; ++ int t; + -+ ar71xx_set_pll(AR91XX_PLL_REG_ETH_CONFIG, AR91XX_PLL_REG_ETH1_INT_CLOCK, -+ val, AR91XX_ETH1_PLL_SHIFT); -+} ++ t = sscanf(mac_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx", ++ &tmp[0], &tmp[1], &tmp[2], &tmp[3], &tmp[4], &tmp[5]); + -+static void ar71xx_ddr_flush_ge0(void) -+{ -+ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_GE0); -+} ++ if (t != ETH_ALEN) ++ t = sscanf(mac_str, "%02hhx.%02hhx.%02hhx.%02hhx.%02hhx.%02hhx", ++ &tmp[0], &tmp[1], &tmp[2], &tmp[3], &tmp[4], &tmp[5]); + -+static void ar71xx_ddr_flush_ge1(void) -+{ -+ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_GE1); ++ if (t == ETH_ALEN) ++ ar71xx_set_mac_base(tmp); ++ else ++ printk(KERN_DEBUG "ar71xx: failed to parse mac address " ++ "\"%s\"\n", mac_str); +} + -+static void ar724x_ddr_flush_ge0(void) ++static int __init ar71xx_ethaddr_setup(char *str) +{ -+ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_GE0); ++ ar71xx_parse_mac_addr(str); ++ return 1; +} ++__setup("ethaddr=", ar71xx_ethaddr_setup); + -+static void ar724x_ddr_flush_ge1(void) ++static int __init ar71xx_kmac_setup(char *str) +{ -+ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_GE1); ++ ar71xx_parse_mac_addr(str); ++ return 1; +} ++__setup("kmac=", ar71xx_kmac_setup); + -+static void ar91xx_ddr_flush_ge0(void) ++void __init ar71xx_init_mac(unsigned char *dst, const unsigned char *src, ++ unsigned offset) +{ -+ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_GE0); -+} ++ u32 t; + -+static void ar91xx_ddr_flush_ge1(void) -+{ -+ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_GE1); ++ if (!is_valid_ether_addr(src)) { ++ memset(dst, '\0', ETH_ALEN); ++ return; ++ } ++ ++ t = (((u32) src[3]) << 16) + (((u32) src[4]) << 8) + ((u32) src[5]); ++ t += offset; ++ ++ dst[0] = src[0]; ++ dst[1] = src[1]; ++ dst[2] = src[2]; ++ dst[3] = (t >> 16) & 0xff; ++ dst[4] = (t >> 8) & 0xff; ++ dst[5] = t & 0xff; +} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/devices.h linux-2.6.39/arch/mips/ar71xx/devices.h +--- linux-2.6.39.orig/arch/mips/ar71xx/devices.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/devices.h 2011-08-24 02:41:55.347990727 +0200 +@@ -0,0 +1,50 @@ ++/* ++ * Atheros AR71xx SoC device definitions ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+static struct resource ar71xx_eth0_resources[] = { -+ { -+ .name = "mac_base", -+ .flags = IORESOURCE_MEM, -+ .start = AR71XX_GE0_BASE, -+ .end = AR71XX_GE0_BASE + 0x200 - 1, -+ }, { -+ .name = "mii_ctrl", -+ .flags = IORESOURCE_MEM, -+ .start = AR71XX_MII_BASE + MII_REG_MII0_CTRL, -+ .end = AR71XX_MII_BASE + MII_REG_MII0_CTRL + 3, -+ }, { -+ .name = "mac_irq", -+ .flags = IORESOURCE_IRQ, -+ .start = AR71XX_CPU_IRQ_GE0, -+ .end = AR71XX_CPU_IRQ_GE0, -+ }, -+}; ++#ifndef __AR71XX_DEVICES_H ++#define __AR71XX_DEVICES_H + -+struct ag71xx_platform_data ar71xx_eth0_data = { -+ .reset_bit = RESET_MODULE_GE0_MAC, -+}; ++#include + -+struct platform_device ar71xx_eth0_device = { -+ .name = "ag71xx", -+ .id = 0, -+ .resource = ar71xx_eth0_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_eth0_resources), -+ .dev = { -+ .platform_data = &ar71xx_eth0_data, -+ }, -+}; ++struct platform_device; + -+static struct resource ar71xx_eth1_resources[] = { -+ { -+ .name = "mac_base", -+ .flags = IORESOURCE_MEM, -+ .start = AR71XX_GE1_BASE, -+ .end = AR71XX_GE1_BASE + 0x200 - 1, -+ }, { -+ .name = "mii_ctrl", -+ .flags = IORESOURCE_MEM, -+ .start = AR71XX_MII_BASE + MII_REG_MII1_CTRL, -+ .end = AR71XX_MII_BASE + MII_REG_MII1_CTRL + 3, -+ }, { -+ .name = "mac_irq", -+ .flags = IORESOURCE_IRQ, -+ .start = AR71XX_CPU_IRQ_GE1, -+ .end = AR71XX_CPU_IRQ_GE1, -+ }, -+}; ++void ar71xx_add_device_spi(struct ar71xx_spi_platform_data *pdata, ++ struct spi_board_info const *info, ++ unsigned n) __init; + -+struct ag71xx_platform_data ar71xx_eth1_data = { -+ .reset_bit = RESET_MODULE_GE1_MAC, -+}; ++extern unsigned char ar71xx_mac_base[] __initdata; ++void ar71xx_parse_mac_addr(char *mac_str) __init; ++void ar71xx_init_mac(unsigned char *dst, const unsigned char *src, ++ unsigned offset) __init; + -+struct platform_device ar71xx_eth1_device = { -+ .name = "ag71xx", -+ .id = 1, -+ .resource = ar71xx_eth1_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_eth1_resources), -+ .dev = { -+ .platform_data = &ar71xx_eth1_data, -+ }, ++struct ar71xx_eth_pll_data { ++ u32 pll_10; ++ u32 pll_100; ++ u32 pll_1000; +}; + -+#define AR71XX_PLL_VAL_1000 0x00110000 -+#define AR71XX_PLL_VAL_100 0x00001099 -+#define AR71XX_PLL_VAL_10 0x00991099 -+ -+#define AR724X_PLL_VAL_1000 0x00110000 -+#define AR724X_PLL_VAL_100 0x00001099 -+#define AR724X_PLL_VAL_10 0x00991099 ++extern struct ar71xx_eth_pll_data ar71xx_eth0_pll_data; ++extern struct ar71xx_eth_pll_data ar71xx_eth1_pll_data; + -+#define AR91XX_PLL_VAL_1000 0x1a000000 -+#define AR91XX_PLL_VAL_100 0x13000a44 -+#define AR91XX_PLL_VAL_10 0x00441099 ++extern struct ag71xx_platform_data ar71xx_eth0_data; ++extern struct ag71xx_platform_data ar71xx_eth1_data; ++extern struct platform_device ar71xx_eth0_device; ++extern struct platform_device ar71xx_eth1_device; ++void ar71xx_add_device_eth(unsigned int id) __init; + -+static void __init ar71xx_init_eth_pll_data(unsigned int id) -+{ -+ struct ar71xx_eth_pll_data *pll_data; -+ u32 pll_10, pll_100, pll_1000; ++extern struct platform_device ar71xx_mdio_device; ++void ar71xx_add_device_mdio(u32 phy_mask) __init; + -+ switch (id) { -+ case 0: -+ pll_data = &ar71xx_eth0_pll_data; -+ break; -+ case 1: -+ pll_data = &ar71xx_eth1_pll_data; -+ break; -+ default: -+ BUG(); -+ } ++void ar71xx_add_device_uart(void) __init; + -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ pll_10 = AR71XX_PLL_VAL_10; -+ pll_100 = AR71XX_PLL_VAL_100; -+ pll_1000 = AR71XX_PLL_VAL_1000; -+ break; ++void ar71xx_add_device_wdt(void) __init; + -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ pll_10 = AR724X_PLL_VAL_10; -+ pll_100 = AR724X_PLL_VAL_100; -+ pll_1000 = AR724X_PLL_VAL_1000; -+ break; -+ -+ case AR71XX_SOC_AR9130: -+ case AR71XX_SOC_AR9132: -+ pll_10 = AR91XX_PLL_VAL_10; -+ pll_100 = AR91XX_PLL_VAL_100; -+ pll_1000 = AR91XX_PLL_VAL_1000; -+ break; -+ default: -+ BUG(); -+ } -+ -+ if (!pll_data->pll_10) -+ pll_data->pll_10 = pll_10; ++#endif /* __AR71XX_DEVICES_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.c linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.c 2011-08-24 02:41:55.347990727 +0200 +@@ -0,0 +1,57 @@ ++/* ++ * Atheros AR71xx GPIO LED device support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ if (!pll_data->pll_100) -+ pll_data->pll_100 = pll_100; ++#include ++#include ++#include + -+ if (!pll_data->pll_1000) -+ pll_data->pll_1000 = pll_1000; -+} ++#include "dev-leds-gpio.h" + -+static int ar71xx_eth_instance __initdata; -+void __init ar71xx_add_device_eth(unsigned int id) ++void __init ar71xx_add_device_leds_gpio(int id, unsigned num_leds, ++ struct gpio_led *leds) +{ + struct platform_device *pdev; -+ struct ag71xx_platform_data *pdata; -+ -+ ar71xx_init_eth_pll_data(id); ++ struct gpio_led_platform_data pdata; ++ struct gpio_led *p; ++ int err; + -+ switch (id) { -+ case 0: -+ switch (ar71xx_eth0_data.phy_if_mode) { -+ case PHY_INTERFACE_MODE_MII: -+ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_MII; -+ break; -+ case PHY_INTERFACE_MODE_GMII: -+ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_GMII; -+ break; -+ case PHY_INTERFACE_MODE_RGMII: -+ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_RGMII; -+ break; -+ case PHY_INTERFACE_MODE_RMII: -+ ar71xx_eth0_data.mii_if = MII0_CTRL_IF_RMII; -+ break; -+ default: -+ printk(KERN_ERR "ar71xx: invalid PHY interface mode " -+ "for eth0\n"); -+ return; -+ } -+ pdev = &ar71xx_eth0_device; -+ break; -+ case 1: -+ switch (ar71xx_eth1_data.phy_if_mode) { -+ case PHY_INTERFACE_MODE_RMII: -+ ar71xx_eth1_data.mii_if = MII1_CTRL_IF_RMII; -+ break; -+ case PHY_INTERFACE_MODE_RGMII: -+ ar71xx_eth1_data.mii_if = MII1_CTRL_IF_RGMII; -+ break; -+ default: -+ printk(KERN_ERR "ar71xx: invalid PHY interface mode " -+ "for eth1\n"); -+ return; -+ } -+ pdev = &ar71xx_eth1_device; -+ break; -+ default: -+ printk(KERN_ERR "ar71xx: invalid ethernet id %d\n", id); ++ p = kmalloc(num_leds * sizeof(*p), GFP_KERNEL); ++ if (!p) + return; -+ } + -+ pdata = pdev->dev.platform_data; ++ memcpy(p, leds, num_leds * sizeof(*p)); + -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ pdata->ddr_flush = id ? ar71xx_ddr_flush_ge1 -+ : ar71xx_ddr_flush_ge0; -+ pdata->set_pll = id ? ar71xx_set_pll_ge1 -+ : ar71xx_set_pll_ge0; -+ break; ++ pdev = platform_device_alloc("leds-gpio", id); ++ if (!pdev) ++ goto err_free_leds; + -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ pdata->ddr_flush = id ? ar71xx_ddr_flush_ge1 -+ : ar71xx_ddr_flush_ge0; -+ pdata->set_pll = id ? ar71xx_set_pll_ge1 -+ : ar71xx_set_pll_ge0; -+ pdata->has_gbit = 1; -+ break; ++ memset(&pdata, 0, sizeof(pdata)); ++ pdata.num_leds = num_leds; ++ pdata.leds = p; + -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ar71xx_eth0_data.reset_bit |= AR724X_RESET_GE0_MDIO; -+ ar71xx_eth1_data.reset_bit |= AR724X_RESET_GE1_MDIO; -+ /* fall through */ -+ case AR71XX_SOC_AR7240: -+ pdata->ddr_flush = id ? ar724x_ddr_flush_ge1 -+ : ar724x_ddr_flush_ge0; -+ pdata->set_pll = id ? ar724x_set_pll_ge1 -+ : ar724x_set_pll_ge0; -+ pdata->is_ar724x = 1; -+ break; ++ err = platform_device_add_data(pdev, &pdata, sizeof(pdata)); ++ if (err) ++ goto err_put_pdev; + -+ case AR71XX_SOC_AR9130: -+ pdata->ddr_flush = id ? ar91xx_ddr_flush_ge1 -+ : ar91xx_ddr_flush_ge0; -+ pdata->set_pll = id ? ar91xx_set_pll_ge1 -+ : ar91xx_set_pll_ge0; -+ pdata->is_ar91xx = 1; -+ break; ++ err = platform_device_add(pdev); ++ if (err) ++ goto err_put_pdev; + -+ case AR71XX_SOC_AR9132: -+ pdata->ddr_flush = id ? ar91xx_ddr_flush_ge1 -+ : ar91xx_ddr_flush_ge0; -+ pdata->set_pll = id ? ar91xx_set_pll_ge1 -+ : ar91xx_set_pll_ge0; -+ pdata->is_ar91xx = 1; -+ pdata->has_gbit = 1; -+ break; ++ return; + -+ default: -+ BUG(); -+ } ++err_put_pdev: ++ platform_device_put(pdev); + -+ switch (pdata->phy_if_mode) { -+ case PHY_INTERFACE_MODE_GMII: -+ case PHY_INTERFACE_MODE_RGMII: -+ if (!pdata->has_gbit) { -+ printk(KERN_ERR "ar71xx: no gbit available on eth%d\n", -+ id); -+ return; -+ } -+ /* fallthrough */ -+ default: -+ break; -+ } ++err_free_leds: ++ kfree(p); ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.h linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-leds-gpio.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-leds-gpio.h 2011-08-24 02:41:55.367990903 +0200 +@@ -0,0 +1,21 @@ ++/* ++ * Atheros AR71xx GPIO LED device support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ if (is_valid_ether_addr(ar71xx_mac_base)) { -+ memcpy(pdata->mac_addr, ar71xx_mac_base, ETH_ALEN); -+ pdata->mac_addr[5] += ar71xx_eth_instance; -+ } else { -+ random_ether_addr(pdata->mac_addr); -+ printk(KERN_DEBUG -+ "ar71xx: using random MAC address for eth%d\n", -+ ar71xx_eth_instance); -+ } ++#ifndef _AR71XX_DEV_LEDS_GPIO_H ++#define _AR71XX_DEV_LEDS_GPIO_H + -+ if (pdata->mii_bus_dev == NULL) -+ pdata->mii_bus_dev = &ar71xx_mdio_device.dev; ++#include + -+ /* Reset the device */ -+ ar71xx_device_stop(pdata->reset_bit); -+ mdelay(100); ++void ar71xx_add_device_leds_gpio(int id, ++ unsigned num_leds, ++ struct gpio_led *leds) __init; + -+ ar71xx_device_start(pdata->reset_bit); -+ mdelay(100); ++#endif /* _AR71XX_DEV_LEDS_GPIO_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.c linux-2.6.39/arch/mips/ar71xx/dev-m25p80.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-m25p80.c 2011-08-24 02:41:55.367990903 +0200 +@@ -0,0 +1,30 @@ ++/* ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ platform_device_register(pdev); -+ ar71xx_eth_instance++; -+} ++#include ++#include ++#include + -+static struct resource ar71xx_spi_resources[] = { -+ [0] = { -+ .start = AR71XX_SPI_BASE, -+ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, -+ .flags = IORESOURCE_MEM, -+ }, -+}; ++#include "devices.h" ++#include "dev-m25p80.h" + -+static struct platform_device ar71xx_spi_device = { -+ .name = "ar71xx-spi", -+ .id = -1, -+ .resource = ar71xx_spi_resources, -+ .num_resources = ARRAY_SIZE(ar71xx_spi_resources), ++static struct spi_board_info ar71xx_spi_info[] = { ++ { ++ .bus_num = 0, ++ .chip_select = 0, ++ .max_speed_hz = 25000000, ++ .modalias = "m25p80", ++ } +}; + -+void __init ar71xx_add_device_spi(struct ar71xx_spi_platform_data *pdata, -+ struct spi_board_info const *info, -+ unsigned n) ++void __init ar71xx_add_device_m25p80(struct flash_platform_data *pdata) +{ -+ spi_register_board_info(info, n); -+ ar71xx_spi_device.dev.platform_data = pdata; -+ platform_device_register(&ar71xx_spi_device); ++ ar71xx_spi_info[0].platform_data = pdata; ++ ar71xx_add_device_spi(NULL, ar71xx_spi_info, ++ ARRAY_SIZE(ar71xx_spi_info)); +} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.h linux-2.6.39/arch/mips/ar71xx/dev-m25p80.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-m25p80.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-m25p80.h 2011-08-24 02:41:55.377990515 +0200 +@@ -0,0 +1,16 @@ ++/* ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+void __init ar71xx_add_device_wdt(void) -+{ -+ platform_device_register_simple("ar71xx-wdt", -1, NULL, 0); -+} -+ -+void __init ar71xx_set_mac_base(unsigned char *mac) -+{ -+ memcpy(ar71xx_mac_base, mac, ETH_ALEN); -+} -+ -+void __init ar71xx_parse_mac_addr(char *mac_str) -+{ -+ u8 tmp[ETH_ALEN]; -+ int t; -+ -+ t = sscanf(mac_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx", -+ &tmp[0], &tmp[1], &tmp[2], &tmp[3], &tmp[4], &tmp[5]); -+ -+ if (t != ETH_ALEN) -+ t = sscanf(mac_str, "%02hhx.%02hhx.%02hhx.%02hhx.%02hhx.%02hhx", -+ &tmp[0], &tmp[1], &tmp[2], &tmp[3], &tmp[4], &tmp[5]); ++#ifndef _AR71XX_DEV_M25P80_H ++#define _AR71XX_DEV_M25P80_H + -+ if (t == ETH_ALEN) -+ ar71xx_set_mac_base(tmp); -+ else -+ printk(KERN_DEBUG "ar71xx: failed to parse mac address " -+ "\"%s\"\n", mac_str); -+} ++#include + -+static int __init ar71xx_ethaddr_setup(char *str) -+{ -+ ar71xx_parse_mac_addr(str); -+ return 1; -+} -+__setup("ethaddr=", ar71xx_ethaddr_setup); ++void ar71xx_add_device_m25p80(struct flash_platform_data *pdata) __init; + -+static int __init ar71xx_kmac_setup(char *str) -+{ -+ ar71xx_parse_mac_addr(str); -+ return 1; -+} -+__setup("kmac=", ar71xx_kmac_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/devices.h linux-2.6.39/arch/mips/ar71xx/devices.h ---- linux-2.6.39.orig/arch/mips/ar71xx/devices.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/devices.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,48 @@ ++#endif /* _AR71XX_DEV_M25P80_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.c linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.c 2011-08-24 02:41:55.377990515 +0200 +@@ -0,0 +1,40 @@ +/* -+ * Atheros AR71xx SoC device definitions ++ * Atheros PB42 reference board PCI initialization + * + * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#ifndef __AR71XX_DEVICES_H -+#define __AR71XX_DEVICES_H -+ -+#include -+ -+struct platform_device; ++#include + -+void ar71xx_add_device_spi(struct ar71xx_spi_platform_data *pdata, -+ struct spi_board_info const *info, -+ unsigned n) __init; ++#include ++#include + -+void ar71xx_set_mac_base(unsigned char *mac) __init; -+void ar71xx_parse_mac_addr(char *mac_str) __init; ++#include "dev-pb42-pci.h" + -+struct ar71xx_eth_pll_data { -+ u32 pll_10; -+ u32 pll_100; -+ u32 pll_1000; ++static struct ar71xx_pci_irq pb42_pci_irqs[] __initdata = { ++ { ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, ++ }, { ++ .slot = 1, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV1, ++ }, { ++ .slot = 2, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV2, ++ } +}; + -+extern struct ar71xx_eth_pll_data ar71xx_eth0_pll_data; -+extern struct ar71xx_eth_pll_data ar71xx_eth1_pll_data; -+ -+extern struct ag71xx_platform_data ar71xx_eth0_data; -+extern struct ag71xx_platform_data ar71xx_eth1_data; -+extern struct platform_device ar71xx_eth0_device; -+extern struct platform_device ar71xx_eth1_device; -+void ar71xx_add_device_eth(unsigned int id) __init; -+ -+extern struct platform_device ar71xx_mdio_device; -+void ar71xx_add_device_mdio(u32 phy_mask) __init; ++void __init pb42_pci_init(void) ++{ ++ ar71xx_pci_init(ARRAY_SIZE(pb42_pci_irqs), pb42_pci_irqs); ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.h linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb42-pci.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-pb42-pci.h 2011-08-24 02:41:55.387991243 +0200 +@@ -0,0 +1,21 @@ ++/* ++ * Atheros PB42 reference board PCI initialization ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+void ar71xx_add_device_uart(void) __init; ++#ifndef _AR71XX_DEV_PB42_PCI_H ++#define _AR71XX_DEV_PB42_PCI_H + -+void ar71xx_add_device_wdt(void) __init; ++#if defined(CONFIG_AR71XX_DEV_PB42_PCI) ++void pb42_pci_init(void) __init; ++#else ++static inline void pb42_pci_init(void) { } ++#endif + -+#endif /* __AR71XX_DEVICES_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/early_printk.c linux-2.6.39/arch/mips/ar71xx/early_printk.c ---- linux-2.6.39.orig/arch/mips/ar71xx/early_printk.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/early_printk.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,30 @@ ++#endif /* _AR71XX_DEV_PB42_PCI_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.c linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.c 2011-08-24 02:41:55.387991243 +0200 +@@ -0,0 +1,33 @@ +/* -+ * Atheros AR71xx SoC early printk support ++ * Atheros PB9x reference board PCI initialization + * ++ * Copyright (C) 2010 Felix Fietkau + * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include ++#include + +#include ++#include + -+#define UART_READ(r) \ -+ __raw_readl((void __iomem *)(KSEG1ADDR(AR71XX_UART_BASE) + 4 * (r))) ++#include "dev-pb9x-pci.h" + -+#define UART_WRITE(r, v) \ -+ __raw_writel((v), (void __iomem *)(KSEG1ADDR(AR71XX_UART_BASE) + 4*(r))) ++static struct ar71xx_pci_irq pb9x_pci_irqs[] __initdata = { ++ { ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, ++ } ++}; + -+void prom_putchar(unsigned char ch) ++void __init pb9x_pci_init(void) +{ -+ while (((UART_READ(UART_LSR)) & UART_LSR_THRE) == 0); -+ UART_WRITE(UART_TX, ch); -+ while (((UART_READ(UART_LSR)) & UART_LSR_THRE) == 0); ++ ar71xx_pci_init(ARRAY_SIZE(pb9x_pci_irqs), pb9x_pci_irqs); +} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.h linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-pb9x-pci.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-pb9x-pci.h 2011-08-24 02:41:55.387991243 +0200 +@@ -0,0 +1,22 @@ ++/* ++ * Atheros PB9x reference board PCI initialization ++ * ++ * Copyright (C) 2010 Felix Fietkau ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/gpio.c linux-2.6.39/arch/mips/ar71xx/gpio.c ---- linux-2.6.39.orig/arch/mips/ar71xx/gpio.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/gpio.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,182 @@ ++#ifndef _AR71XX_DEV_PB9X_PCI_H ++#define _AR71XX_DEV_PB9X_PCI_H ++ ++#if defined(CONFIG_AR71XX_DEV_PB9X_PCI) ++void pb9x_pci_init(void) __init; ++#else ++static inline void pb9x_pci_init(void) { } ++#endif ++ ++#endif /* _AR71XX_DEV_PB9X_PCI_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.c linux-2.6.39/arch/mips/ar71xx/dev-usb.c +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-usb.c 2011-08-24 02:41:55.417990329 +0200 +@@ -0,0 +1,199 @@ +/* -+ * Atheros AR71xx SoC GPIO API support ++ * Atheros AR71xx USB host device support + * -+ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. @@ -2420,36 +2008,358 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/gpio.c linux-2.6.39/arch/mips/ar71x + +#include +#include -+#include -+#include -+#include -+#include -+#include -+#include ++#include ++#include ++#include + +#include ++#include + -+static DEFINE_SPINLOCK(ar71xx_gpio_lock); ++#include "dev-usb.h" + -+unsigned long ar71xx_gpio_count; -+EXPORT_SYMBOL(ar71xx_gpio_count); ++/* ++ * OHCI (USB full speed host controller) ++ */ ++static struct resource ar71xx_ohci_resources[] = { ++ [0] = { ++ .start = AR71XX_OHCI_BASE, ++ .end = AR71XX_OHCI_BASE + AR71XX_OHCI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++ [1] = { ++ .start = AR71XX_MISC_IRQ_OHCI, ++ .end = AR71XX_MISC_IRQ_OHCI, ++ .flags = IORESOURCE_IRQ, ++ }, ++}; + -+void __ar71xx_gpio_set_value(unsigned gpio, int value) -+{ -+ void __iomem *base = ar71xx_gpio_base; ++static struct resource ar7240_ohci_resources[] = { ++ [0] = { ++ .start = AR7240_OHCI_BASE, ++ .end = AR7240_OHCI_BASE + AR7240_OHCI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++ [1] = { ++ .start = AR71XX_CPU_IRQ_USB, ++ .end = AR71XX_CPU_IRQ_USB, ++ .flags = IORESOURCE_IRQ, ++ }, ++}; + -+ if (value) -+ __raw_writel(1 << gpio, base + GPIO_REG_SET); -+ else -+ __raw_writel(1 << gpio, base + GPIO_REG_CLEAR); -+} -+EXPORT_SYMBOL(__ar71xx_gpio_set_value); ++static u64 ar71xx_ohci_dmamask = DMA_BIT_MASK(32); ++static struct platform_device ar71xx_ohci_device = { ++ .name = "ar71xx-ohci", ++ .id = -1, ++ .resource = ar71xx_ohci_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_ohci_resources), ++ .dev = { ++ .dma_mask = &ar71xx_ohci_dmamask, ++ .coherent_dma_mask = DMA_BIT_MASK(32), ++ }, ++}; + -+int __ar71xx_gpio_get_value(unsigned gpio) -+{ -+ return (__raw_readl(ar71xx_gpio_base + GPIO_REG_IN) >> gpio) & 1; -+} -+EXPORT_SYMBOL(__ar71xx_gpio_get_value); ++/* ++ * EHCI (USB high/full speed host controller) ++ */ ++static struct resource ar71xx_ehci_resources[] = { ++ [0] = { ++ .start = AR71XX_EHCI_BASE, ++ .end = AR71XX_EHCI_BASE + AR71XX_EHCI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++ [1] = { ++ .start = AR71XX_CPU_IRQ_USB, ++ .end = AR71XX_CPU_IRQ_USB, ++ .flags = IORESOURCE_IRQ, ++ }, ++}; ++ ++static u64 ar71xx_ehci_dmamask = DMA_BIT_MASK(32); ++static struct ar71xx_ehci_platform_data ar71xx_ehci_data; ++ ++static struct platform_device ar71xx_ehci_device = { ++ .name = "ar71xx-ehci", ++ .id = -1, ++ .resource = ar71xx_ehci_resources, ++ .num_resources = ARRAY_SIZE(ar71xx_ehci_resources), ++ .dev = { ++ .dma_mask = &ar71xx_ehci_dmamask, ++ .coherent_dma_mask = DMA_BIT_MASK(32), ++ .platform_data = &ar71xx_ehci_data, ++ }, ++}; ++ ++#define AR71XX_USB_RESET_MASK \ ++ (RESET_MODULE_USB_HOST | RESET_MODULE_USB_PHY \ ++ | RESET_MODULE_USB_OHCI_DLL) ++ ++#define AR7240_USB_RESET_MASK \ ++ (RESET_MODULE_USB_HOST | RESET_MODULE_USB_OHCI_DLL_7240) ++ ++static void __init ar71xx_usb_setup(void) ++{ ++ ar71xx_device_stop(AR71XX_USB_RESET_MASK); ++ mdelay(1000); ++ ar71xx_device_start(AR71XX_USB_RESET_MASK); ++ ++ /* Turning on the Buff and Desc swap bits */ ++ ar71xx_usb_ctrl_wr(USB_CTRL_REG_CONFIG, 0xf0000); ++ ++ /* WAR for HW bug. Here it adjusts the duration between two SOFS */ ++ ar71xx_usb_ctrl_wr(USB_CTRL_REG_FLADJ, 0x20c00); ++ ++ mdelay(900); ++ ++ platform_device_register(&ar71xx_ohci_device); ++ platform_device_register(&ar71xx_ehci_device); ++} ++ ++static void __init ar7240_usb_setup(void) ++{ ++ ar71xx_device_stop(AR7240_USB_RESET_MASK); ++ mdelay(1000); ++ ar71xx_device_start(AR7240_USB_RESET_MASK); ++ ++ /* WAR for HW bug. Here it adjusts the duration between two SOFS */ ++ ar71xx_usb_ctrl_wr(USB_CTRL_REG_FLADJ, 0x3); ++ ++ ar71xx_ohci_device.resource = ar7240_ohci_resources; ++ ar71xx_ohci_device.num_resources = ARRAY_SIZE(ar7240_ohci_resources); ++ platform_device_register(&ar71xx_ohci_device); ++} ++ ++static void __init ar7241_usb_setup(void) ++{ ++ ar71xx_device_start(AR724X_RESET_USBSUS_OVERRIDE); ++ mdelay(10); ++ ++ ar71xx_device_start(AR724X_RESET_USB_HOST); ++ mdelay(10); ++ ++ ar71xx_device_start(AR724X_RESET_USB_PHY); ++ mdelay(10); ++ ++ ar71xx_ehci_data.is_ar91xx = 1; ++ ar71xx_ehci_device.resource = ar7240_ohci_resources; ++ ar71xx_ehci_device.num_resources = ARRAY_SIZE(ar7240_ohci_resources); ++ platform_device_register(&ar71xx_ehci_device); ++} ++ ++static void __init ar91xx_usb_setup(void) ++{ ++ ar71xx_device_stop(RESET_MODULE_USBSUS_OVERRIDE); ++ mdelay(10); ++ ++ ar71xx_device_start(RESET_MODULE_USB_HOST); ++ mdelay(10); ++ ++ ar71xx_device_start(RESET_MODULE_USB_PHY); ++ mdelay(10); ++ ++ ar71xx_ehci_data.is_ar91xx = 1; ++ platform_device_register(&ar71xx_ehci_device); ++} ++ ++void __init ar71xx_add_device_usb(void) ++{ ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7240: ++ ar7240_usb_setup(); ++ break; ++ ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ ar7241_usb_setup(); ++ break; ++ ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ ar71xx_usb_setup(); ++ break; ++ ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ar91xx_usb_setup(); ++ break; ++ ++ default: ++ BUG(); ++ } ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.h linux-2.6.39/arch/mips/ar71xx/dev-usb.h +--- linux-2.6.39.orig/arch/mips/ar71xx/dev-usb.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/dev-usb.h 2011-08-24 02:41:55.427989786 +0200 +@@ -0,0 +1,17 @@ ++/* ++ * Atheros AR71xx USB host device support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#ifndef _AR71XX_DEV_USB_H ++#define _AR71XX_DEV_USB_H ++ ++void ar71xx_add_device_usb(void) __init; ++ ++#endif /* _AR71XX_DEV_USB_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/early_printk.c linux-2.6.39/arch/mips/ar71xx/early_printk.c +--- linux-2.6.39.orig/arch/mips/ar71xx/early_printk.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/early_printk.c 2011-08-24 02:41:55.427989786 +0200 +@@ -0,0 +1,96 @@ ++/* ++ * Atheros AR7xxx/AR9xxx SoC early printk support ++ * ++ * Copyright (C) 2008-2011 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++static void (*_prom_putchar) (unsigned char); ++ ++static inline void prom_putchar_wait(void __iomem *reg, u32 mask, u32 val) ++{ ++ u32 t; ++ ++ do { ++ t = __raw_readl(reg); ++ if ((t & mask) == val) ++ break; ++ } while (1); ++} ++ ++static void prom_putchar_ar71xx(unsigned char ch) ++{ ++ void __iomem *base = (void __iomem *)(KSEG1ADDR(AR71XX_UART_BASE)); ++ ++ prom_putchar_wait(base + UART_LSR * 4, UART_LSR_THRE, UART_LSR_THRE); ++ __raw_writel(ch, base + UART_TX * 4); ++ prom_putchar_wait(base + UART_LSR * 4, UART_LSR_THRE, UART_LSR_THRE); ++} ++ ++static void prom_putchar_ar933x(unsigned char ch) ++{ ++ void __iomem *base = (void __iomem *)(KSEG1ADDR(AR933X_UART_BASE)); ++ ++ prom_putchar_wait(base + AR933X_UART_DATA_REG, AR933X_UART_DATA_TX_CSR, ++ AR933X_UART_DATA_TX_CSR); ++ __raw_writel(AR933X_UART_DATA_TX_CSR | ch, base + AR933X_UART_DATA_REG); ++ prom_putchar_wait(base + AR933X_UART_DATA_REG, AR933X_UART_DATA_TX_CSR, ++ AR933X_UART_DATA_TX_CSR); ++} ++ ++static void prom_putchar_dummy(unsigned char ch) ++{ ++ /* nothing to do */ ++} ++ ++static void prom_putchar_init(void) ++{ ++ void __iomem *base; ++ u32 id; ++ ++ base = (void __iomem *)(KSEG1ADDR(AR71XX_RESET_BASE)); ++ id = __raw_readl(base + AR71XX_RESET_REG_REV_ID); ++ id &= REV_ID_MAJOR_MASK; ++ ++ switch (id) { ++ case REV_ID_MAJOR_AR71XX: ++ case REV_ID_MAJOR_AR7240: ++ case REV_ID_MAJOR_AR7241: ++ case REV_ID_MAJOR_AR7242: ++ case REV_ID_MAJOR_AR913X: ++ case REV_ID_MAJOR_AR9341: ++ case REV_ID_MAJOR_AR9342: ++ case REV_ID_MAJOR_AR9344: ++ _prom_putchar = prom_putchar_ar71xx; ++ break; ++ ++ case REV_ID_MAJOR_AR9330: ++ case REV_ID_MAJOR_AR9331: ++ _prom_putchar = prom_putchar_ar933x; ++ break; ++ ++ default: ++ _prom_putchar = prom_putchar_dummy; ++ break; ++ } ++} ++ ++void prom_putchar(unsigned char ch) ++{ ++ if (!_prom_putchar) ++ prom_putchar_init(); ++ ++ _prom_putchar(ch); ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/gpio.c linux-2.6.39/arch/mips/ar71xx/gpio.c +--- linux-2.6.39.orig/arch/mips/ar71xx/gpio.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/gpio.c 2011-08-24 02:41:55.457989607 +0200 +@@ -0,0 +1,193 @@ ++/* ++ * Atheros AR7XXX/AR9XXX SoC GPIO API support ++ * ++ * Copyright (C) 2008-2011 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++ ++static DEFINE_SPINLOCK(ar71xx_gpio_lock); ++ ++unsigned long ar71xx_gpio_count; ++EXPORT_SYMBOL(ar71xx_gpio_count); ++ ++void __ar71xx_gpio_set_value(unsigned gpio, int value) ++{ ++ void __iomem *base = ar71xx_gpio_base; ++ ++ if (value) ++ __raw_writel(1 << gpio, base + GPIO_REG_SET); ++ else ++ __raw_writel(1 << gpio, base + GPIO_REG_CLEAR); ++} ++EXPORT_SYMBOL(__ar71xx_gpio_set_value); ++ ++int __ar71xx_gpio_get_value(unsigned gpio) ++{ ++ return (__raw_readl(ar71xx_gpio_base + GPIO_REG_IN) >> gpio) & 1; ++} ++EXPORT_SYMBOL(__ar71xx_gpio_get_value); + +static int ar71xx_gpio_get_value(struct gpio_chip *chip, unsigned offset) +{ @@ -2581,6 +2491,17 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/gpio.c linux-2.6.39/arch/mips/ar71x + ar71xx_gpio_chip.ngpio = AR91XX_GPIO_COUNT; + break; + ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ar71xx_gpio_chip.ngpio = AR933X_GPIO_COUNT; ++ break; ++ ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ar71xx_gpio_chip.ngpio = AR934X_GPIO_COUNT; ++ break; ++ + default: + BUG(); + } @@ -2591,15 +2512,17 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/gpio.c linux-2.6.39/arch/mips/ar71x +} diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx/irq.c --- linux-2.6.39.orig/arch/mips/ar71xx/irq.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/irq.c 2011-06-01 13:50:58.000000000 +0200 -@@ -0,0 +1,293 @@ ++++ linux-2.6.39/arch/mips/ar71xx/irq.c 2011-08-24 02:41:55.457989607 +0200 +@@ -0,0 +1,377 @@ +/* + * Atheros AR71xx SoC specific interrupt handling + * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan + * Copyright (C) 2008-2010 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.31 BSP + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -2616,8 +2539,6 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + +#include + -+static int ip2_flush_reg; -+ +static void ar71xx_gpio_irq_dispatch(void) +{ + void __iomem *base = ar71xx_gpio_base; @@ -2634,13 +2555,12 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + +static void ar71xx_gpio_irq_unmask(struct irq_data *d) +{ ++ unsigned int irq = d->irq - AR71XX_GPIO_IRQ_BASE; + void __iomem *base = ar71xx_gpio_base; + u32 t; + -+ d->irq -= AR71XX_GPIO_IRQ_BASE; -+ + t = __raw_readl(base + GPIO_REG_INT_ENABLE); -+ __raw_writel(t | (1 << d->irq), base + GPIO_REG_INT_ENABLE); ++ __raw_writel(t | (1 << irq), base + GPIO_REG_INT_ENABLE); + + /* flush write */ + (void) __raw_readl(base + GPIO_REG_INT_ENABLE); @@ -2648,34 +2568,22 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + +static void ar71xx_gpio_irq_mask(struct irq_data *d) +{ ++ unsigned int irq = d->irq - AR71XX_GPIO_IRQ_BASE; + void __iomem *base = ar71xx_gpio_base; + u32 t; + -+ d->irq -= AR71XX_GPIO_IRQ_BASE; -+ + t = __raw_readl(base + GPIO_REG_INT_ENABLE); -+ __raw_writel(t & ~(1 << d->irq), base + GPIO_REG_INT_ENABLE); ++ __raw_writel(t & ~(1 << irq), base + GPIO_REG_INT_ENABLE); + + /* flush write */ + (void) __raw_readl(base + GPIO_REG_INT_ENABLE); +} + -+#if 0 -+static int ar71xx_gpio_irq_set_type(unsigned int irq, unsigned int flow_type) -+{ -+ /* TODO: implement */ -+ return 0; -+} -+#else -+#define ar71xx_gpio_irq_set_type NULL -+#endif -+ +static struct irq_chip ar71xx_gpio_irq_chip = { + .name = "AR71XX GPIO", -+ .irq_unmask = ar71xx_gpio_irq_unmask, -+ .irq_mask = ar71xx_gpio_irq_mask, ++ .irq_unmask = ar71xx_gpio_irq_unmask, ++ .irq_mask = ar71xx_gpio_irq_mask, + .irq_mask_ack = ar71xx_gpio_irq_mask, -+ .irq_set_type = ar71xx_gpio_irq_set_type, +}; + +static struct irqaction ar71xx_gpio_irqaction = { @@ -2683,7 +2591,6 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + .name = "cascade [AR71XX GPIO]", +}; + -+#define GPIO_IRQ_INIT_STATUS (IRQ_LEVEL | IRQ_TYPE_LEVEL_HIGH) +#define GPIO_INT_ALL 0xffff + +static void __init ar71xx_gpio_irq_init(void) @@ -2701,10 +2608,9 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + __raw_writel(GPIO_INT_ALL, base + GPIO_REG_INT_POLARITY); + + for (i = AR71XX_GPIO_IRQ_BASE; -+ i < AR71XX_GPIO_IRQ_BASE + AR71XX_GPIO_IRQ_COUNT; i++) { ++ i < AR71XX_GPIO_IRQ_BASE + AR71XX_GPIO_IRQ_COUNT; i++) + irq_set_chip_and_handler(i, &ar71xx_gpio_irq_chip, + handle_level_irq); -+ } + + setup_irq(AR71XX_MISC_IRQ_GPIO, &ar71xx_gpio_irqaction); +} @@ -2740,19 +2646,33 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + else if (pending & MISC_INT_WDOG) + do_IRQ(AR71XX_MISC_IRQ_WDOG); + ++ else if (pending & MISC_INT_TIMER2) ++ do_IRQ(AR71XX_MISC_IRQ_TIMER2); ++ ++ else if (pending & MISC_INT_TIMER3) ++ do_IRQ(AR71XX_MISC_IRQ_TIMER3); ++ ++ else if (pending & MISC_INT_TIMER4) ++ do_IRQ(AR71XX_MISC_IRQ_TIMER4); ++ ++ else if (pending & MISC_INT_DDR_PERF) ++ do_IRQ(AR71XX_MISC_IRQ_DDR_PERF); ++ ++ else if (pending & MISC_INT_ENET_LINK) ++ do_IRQ(AR71XX_MISC_IRQ_ENET_LINK); ++ + else + spurious_interrupt(); +} + +static void ar71xx_misc_irq_unmask(struct irq_data *d) +{ ++ unsigned int irq = d->irq - AR71XX_MISC_IRQ_BASE; + void __iomem *base = ar71xx_reset_base; + u32 t; + -+ d->irq -= AR71XX_MISC_IRQ_BASE; -+ + t = __raw_readl(base + AR71XX_RESET_REG_MISC_INT_ENABLE); -+ __raw_writel(t | (1 << d->irq), base + AR71XX_RESET_REG_MISC_INT_ENABLE); ++ __raw_writel(t | (1 << irq), base + AR71XX_RESET_REG_MISC_INT_ENABLE); + + /* flush write */ + (void) __raw_readl(base + AR71XX_RESET_REG_MISC_INT_ENABLE); @@ -2760,25 +2680,23 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + +static void ar71xx_misc_irq_mask(struct irq_data *d) +{ ++ unsigned int irq = d->irq - AR71XX_MISC_IRQ_BASE; + void __iomem *base = ar71xx_reset_base; + u32 t; + -+ d->irq -= AR71XX_MISC_IRQ_BASE; -+ + t = __raw_readl(base + AR71XX_RESET_REG_MISC_INT_ENABLE); -+ __raw_writel(t & ~(1 << d->irq), base + AR71XX_RESET_REG_MISC_INT_ENABLE); ++ __raw_writel(t & ~(1 << irq), base + AR71XX_RESET_REG_MISC_INT_ENABLE); + + /* flush write */ + (void) __raw_readl(base + AR71XX_RESET_REG_MISC_INT_ENABLE); +} + -+static void ar724x_misc_irq_ack(unsigned int irq) ++static void ar724x_misc_irq_ack(struct irq_data *d) +{ ++ unsigned int irq = d->irq - AR71XX_MISC_IRQ_BASE; + void __iomem *base = ar71xx_reset_base; + u32 t; + -+ irq -= AR71XX_MISC_IRQ_BASE; -+ + t = __raw_readl(base + AR71XX_RESET_REG_MISC_INT_STATUS); + __raw_writel(t & ~(1 << irq), base + AR71XX_RESET_REG_MISC_INT_STATUS); + @@ -2788,8 +2706,8 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + +static struct irq_chip ar71xx_misc_irq_chip = { + .name = "AR71XX MISC", -+ .irq_unmask = ar71xx_misc_irq_unmask, -+ .irq_mask = ar71xx_misc_irq_mask, ++ .irq_unmask = ar71xx_misc_irq_unmask, ++ .irq_mask = ar71xx_misc_irq_mask, +}; + +static struct irqaction ar71xx_misc_irqaction = { @@ -2809,6 +2727,11 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + case AR71XX_SOC_AR7240: + case AR71XX_SOC_AR7241: + case AR71XX_SOC_AR7242: ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: + ar71xx_misc_irq_chip.irq_ack = ar724x_misc_irq_ack; + break; + default: @@ -2817,14 +2740,82 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + } + + for (i = AR71XX_MISC_IRQ_BASE; -+ i < AR71XX_MISC_IRQ_BASE + AR71XX_MISC_IRQ_COUNT; i++) { ++ i < AR71XX_MISC_IRQ_BASE + AR71XX_MISC_IRQ_COUNT; i++) + irq_set_chip_and_handler(i, &ar71xx_misc_irq_chip, + handle_level_irq); -+ } + + setup_irq(AR71XX_CPU_IRQ_MISC, &ar71xx_misc_irqaction); +} + ++/* ++ * The IP2/IP3 lines are tied to a PCI/WMAC/USB device. Drivers for ++ * these devices typically allocate coherent DMA memory, however the ++ * DMA controller may still have some unsynchronized data in the FIFO. ++ * Issue a flush in the handlers to ensure that the driver sees ++ * the update. ++ */ ++static void ar71xx_ip2_handler(void) ++{ ++ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_PCI); ++ do_IRQ(AR71XX_CPU_IRQ_IP2); ++} ++ ++static void ar724x_ip2_handler(void) ++{ ++ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_PCIE); ++ do_IRQ(AR71XX_CPU_IRQ_IP2); ++} ++ ++static void ar913x_ip2_handler(void) ++{ ++ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_WMAC); ++ do_IRQ(AR71XX_CPU_IRQ_IP2); ++} ++ ++static void ar933x_ip2_handler(void) ++{ ++ ar71xx_ddr_flush(AR933X_DDR_REG_FLUSH_WMAC); ++ do_IRQ(AR71XX_CPU_IRQ_IP2); ++} ++ ++static void ar934x_ip2_handler(void) ++{ ++ ar71xx_ddr_flush(AR934X_DDR_REG_FLUSH_PCIE); ++ do_IRQ(AR71XX_CPU_IRQ_IP2); ++} ++ ++static void ar71xx_ip3_handler(void) ++{ ++ ar71xx_ddr_flush(AR71XX_DDR_REG_FLUSH_USB); ++ do_IRQ(AR71XX_CPU_IRQ_USB); ++} ++ ++static void ar724x_ip3_handler(void) ++{ ++ ar71xx_ddr_flush(AR724X_DDR_REG_FLUSH_USB); ++ do_IRQ(AR71XX_CPU_IRQ_USB); ++} ++ ++static void ar913x_ip3_handler(void) ++{ ++ ar71xx_ddr_flush(AR91XX_DDR_REG_FLUSH_USB); ++ do_IRQ(AR71XX_CPU_IRQ_USB); ++} ++ ++static void ar933x_ip3_handler(void) ++{ ++ ar71xx_ddr_flush(AR933X_DDR_REG_FLUSH_USB); ++ do_IRQ(AR71XX_CPU_IRQ_USB); ++} ++ ++static void ar934x_ip3_handler(void) ++{ ++ do_IRQ(AR71XX_CPU_IRQ_USB); ++} ++ ++static void (*ip2_handler)(void); ++static void (*ip3_handler)(void); ++ +asmlinkage void plat_irq_dispatch(void) +{ + unsigned long pending; @@ -2834,17 +2825,8 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + if (pending & STATUSF_IP7) + do_IRQ(AR71XX_CPU_IRQ_TIMER); + -+ else if (pending & STATUSF_IP2) { -+ /* -+ * This IRQ is meant for a PCI device. Drivers for PCI devices -+ * typically allocate coherent DMA memory for the descriptor -+ * ring, however the DMA controller may still have some -+ * unsynchronized data in the FIFO. -+ * Issue a flush here to ensure that the driver sees the update. -+ */ -+ ar71xx_ddr_flush(ip2_flush_reg); -+ do_IRQ(AR71XX_CPU_IRQ_IP2); -+ } ++ else if (pending & STATUSF_IP2) ++ ip2_handler(); + + else if (pending & STATUSF_IP4) + do_IRQ(AR71XX_CPU_IRQ_GE0); @@ -2853,31 +2835,54 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + do_IRQ(AR71XX_CPU_IRQ_GE1); + + else if (pending & STATUSF_IP3) -+ do_IRQ(AR71XX_CPU_IRQ_USB); ++ ip3_handler(); + + else if (pending & STATUSF_IP6) + ar71xx_misc_irq_dispatch(); + -+ else -+ spurious_interrupt(); ++ spurious_interrupt(); +} + +void __init arch_init_irq(void) +{ -+ switch(ar71xx_soc) { ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ ip2_handler = ar71xx_ip2_handler; ++ ip3_handler = ar71xx_ip3_handler; ++ break; ++ + case AR71XX_SOC_AR7240: + case AR71XX_SOC_AR7241: + case AR71XX_SOC_AR7242: -+ ip2_flush_reg = AR724X_DDR_REG_FLUSH_PCIE; ++ ip2_handler = ar724x_ip2_handler; ++ ip3_handler = ar724x_ip3_handler; + break; ++ + case AR71XX_SOC_AR9130: + case AR71XX_SOC_AR9132: -+ ip2_flush_reg = AR91XX_DDR_REG_FLUSH_WMAC; ++ ip2_handler = ar913x_ip2_handler; ++ ip3_handler = ar913x_ip3_handler; + break; -+ default: -+ ip2_flush_reg = AR71XX_DDR_REG_FLUSH_PCI; ++ ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ip2_handler = ar933x_ip2_handler; ++ ip3_handler = ar933x_ip3_handler; ++ break; ++ ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ip2_handler = ar934x_ip2_handler; ++ ip3_handler = ar934x_ip3_handler; + break; ++ ++ default: ++ BUG(); + } ++ + mips_cpu_irq_init(); + + ar71xx_misc_irq_init(); @@ -2886,429 +2891,688 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/irq.c linux-2.6.39/arch/mips/ar71xx + + ar71xx_gpio_irq_init(); +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap81.c linux-2.6.39/arch/mips/ar71xx/mach-ap81.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap81.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-ap81.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,140 @@ -+/* -+ * Atheros AP81 board support -+ * -+ * Copyright (C) 2009 Gabor Juhos -+ * Copyright (C) 2009 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include -+#include +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/Kconfig linux-2.6.39/arch/mips/ar71xx/Kconfig +--- linux-2.6.39.orig/arch/mips/ar71xx/Kconfig 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/Kconfig 2011-08-24 04:20:27.209240389 +0200 +@@ -0,0 +1,420 @@ ++if ATHEROS_AR71XX + -+#include ++menu "Atheros AR71xx machine selection" + -+#include "machtype.h" -+#include "devices.h" -+#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" -+#include "dev-gpio-buttons.h" -+#include "dev-leds-gpio.h" -+#include "dev-usb.h" ++config AR71XX_MACH_AP81 ++ bool "Atheros AP81 board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+#define AP81_GPIO_LED_STATUS 1 -+#define AP81_GPIO_LED_AOSS 3 -+#define AP81_GPIO_LED_WLAN 6 -+#define AP81_GPIO_LED_POWER 14 ++config AR71XX_MACH_AP83 ++ bool "Atheros AP83 board support" ++ select SOC_AR913X ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+#define AP81_GPIO_BTN_SW4 12 -+#define AP81_GPIO_BTN_SW1 21 ++config AR71XX_MACH_AP96 ++ bool "Atheros AP96 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP94_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+#define AP81_BUTTONS_POLL_INTERVAL 20 ++config AR71XX_MACH_AP121 ++ bool "Atheros AP121 board support" ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ select AR71XX_DEV_AR9XXX_WMAC ++ select SOC_AR933X ++ default n + -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition ap81_partitions[] = { -+ { -+ .name = "u-boot", -+ .offset = 0, -+ .size = 0x040000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "u-boot-env", -+ .offset = 0x040000, -+ .size = 0x010000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x050000, -+ .size = 0x500000, -+ } , { -+ .name = "uImage", -+ .offset = 0x550000, -+ .size = 0x100000, -+ } , { -+ .name = "ART", -+ .offset = 0x650000, -+ .size = 0x1b0000, -+ .mask_flags = MTD_WRITEABLE, -+ } -+}; -+#endif /* CONFIG_MTD_PARTITIONS */ ++config AR71XX_MACH_DB120 ++ bool "Atheros DB120 board support" ++ select SOC_AR934X ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_DB120_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+static struct flash_platform_data ap81_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = ap81_partitions, -+ .nr_parts = ARRAY_SIZE(ap81_partitions), -+#endif -+}; ++config AR71XX_MACH_DIR_600_A1 ++ bool "D-Link DIR-600 rev. A1 support" ++ select SOC_AR724X ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_NVRAM ++ default n + -+static struct gpio_led ap81_leds_gpio[] __initdata = { -+ { -+ .name = "ap81:green:status", -+ .gpio = AP81_GPIO_LED_STATUS, -+ .active_low = 1, -+ }, { -+ .name = "ap81:amber:aoss", -+ .gpio = AP81_GPIO_LED_AOSS, -+ .active_low = 1, -+ }, { -+ .name = "ap81:green:wlan", -+ .gpio = AP81_GPIO_LED_WLAN, -+ .active_low = 1, -+ }, { -+ .name = "ap81:green:power", -+ .gpio = AP81_GPIO_LED_POWER, -+ .active_low = 1, -+ } -+}; ++config AR71XX_MACH_DIR_615_C1 ++ bool "D-Link DIR-615 rev. C1 support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_NVRAM ++ default n + -+static struct gpio_button ap81_gpio_buttons[] __initdata = { -+ { -+ .desc = "sw1", -+ .type = EV_KEY, -+ .code = BTN_0, -+ .threshold = 3, -+ .gpio = AP81_GPIO_BTN_SW1, -+ .active_low = 1, -+ } , { -+ .desc = "sw4", -+ .type = EV_KEY, -+ .code = BTN_1, -+ .threshold = 3, -+ .gpio = AP81_GPIO_BTN_SW4, -+ .active_low = 1, -+ } -+}; ++config AR71XX_MACH_DIR_825_B1 ++ bool "D-Link DIR-825 rev. B1 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP94_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+static void __init ap81_setup(void) -+{ -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++config AR71XX_MACH_JA76PF ++ bool "jjPlus JA76PF board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+ ar71xx_set_mac_base(eeprom); -+ ar71xx_add_device_mdio(0x0); ++config AR71XX_MACH_JWAP003 ++ bool "jjPlus JWAP003 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_USB ++ default n + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.has_ar8216 = 1; ++config AR71XX_MACH_PB42 ++ bool "Atheros PB42 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ default n + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++config AR71XX_MACH_PB44 ++ bool "Atheros PB44 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+ ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); ++config AR71XX_MACH_PB92 ++ bool "Atheros PB92 board support" ++ select SOC_AR724X ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB9X_PCI if PCI ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+ ar71xx_add_device_usb(); ++config AR71XX_MACH_AW_NR580 ++ bool "AzureWave AW-NR580 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_LEDS_GPIO ++ default n + -+ ar71xx_add_device_m25p80(&ap81_flash_data); ++config AR71XX_MACH_WZR_HP_AG300H ++ bool "Buffalo WZR-HP-AG300H board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap81_leds_gpio), -+ ap81_leds_gpio); ++config AR71XX_MACH_WZR_HP_G300NH ++ bool "Buffalo WZR-HP-G300NH board support" ++ select SOC_AR913X ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ select RTL8366_SMI ++ default n + -+ ar71xx_add_device_gpio_buttons(-1, AP81_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(ap81_gpio_buttons), -+ ap81_gpio_buttons); ++config AR71XX_MACH_WP543 ++ bool "Compex WP543/WPJ543 board support" ++ select SOC_AR71XX ++ select MYLOADER ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n + -+ ar913x_add_device_wmac(eeprom, NULL); -+} ++config AR71XX_MACH_WRT160NL ++ bool "Linksys WRT160NL board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ select AR71XX_NVRAM ++ default n + -+MIPS_MACHINE(AR71XX_MACH_AP81, "AP81", "Atheros AP81", ap81_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap83.c linux-2.6.39/arch/mips/ar71xx/mach-ap83.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap83.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-ap83.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,266 @@ ++config AR71XX_MACH_WRT400N ++ bool "Linksys WRT400N board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_AP94_PCI if PCI ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_RB4XX ++ bool "MikroTik RouterBOARD 4xx series support" ++ select SOC_AR71XX ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_RB750 ++ bool "MikroTik RouterBOARD 750 support" ++ select SOC_AR724X ++ default n ++ ++config AR71XX_MACH_WNDR3700 ++ bool "NETGEAR WNDR3700 board support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP94_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_WNR2000 ++ bool "NETGEAR WNR2000 board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_MZK_W04NU ++ bool "Planex MZK-W04NU board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_MZK_W300NH ++ bool "Planex MZK-W300NH board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_NBG460N ++ bool "Zyxel NBG460N/550N/550NH board support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_MR3X20 ++ bool "TP-LINK TL-MR3220/3420 support" ++ select SOC_AR724X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_TL_WA901ND ++ bool "TP-LINK TL-WA901ND support" ++ select SOC_AR724X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_WA901ND_V2 ++ bool "TP-LINK TL-WA901ND v2 support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_WR741ND ++ bool "TP-LINK TL-WR741ND support" ++ select SOC_AR724X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_WR841N_V1 ++ bool "TP-LINK TL-WR841N v1 support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_DSA ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_WR941ND ++ bool "TP-LINK TL-WR941ND support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_DSA ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_TL_WR1043ND ++ bool "TP-LINK TL-WR1043ND support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_TEW_632BRP ++ bool "TRENDnet TEW-632BRP support" ++ select SOC_AR913X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AR9XXX_WMAC ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_NVRAM ++ default n ++ ++config AR71XX_MACH_UBNT ++ bool "Ubiquiti AR71xx based boards support" ++ select SOC_AR71XX ++ select SOC_AR724X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ select AR71XX_DEV_PB42_PCI if PCI ++ select AR71XX_DEV_USB ++ default n ++ ++config AR71XX_MACH_EAP7660D ++ bool "Senao EAP7660D support" ++ select SOC_AR71XX ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++config AR71XX_MACH_ZCN_1523H ++ bool "Zcomax ZCN-1523H support" ++ select SOC_AR724X ++ select AR71XX_DEV_M25P80 ++ select AR71XX_DEV_AP91_PCI if PCI ++ select AR71XX_DEV_GPIO_BUTTONS ++ select AR71XX_DEV_LEDS_GPIO ++ default n ++ ++endmenu ++ ++config SOC_AR71XX ++ bool ++ select USB_ARCH_HAS_EHCI ++ select USB_ARCH_HAS_OHCI ++ ++config SOC_AR724X ++ bool ++ select USB_ARCH_HAS_EHCI ++ select USB_ARCH_HAS_OHCI ++ ++config SOC_AR913X ++ bool ++ select USB_ARCH_HAS_EHCI ++ ++config SOC_AR934X ++ bool ++ select USB_ARCH_HAS_EHCI ++ ++config AR71XX_DEV_M25P80 ++ def_bool n ++ ++config AR71XX_DEV_AP91_PCI ++ select AR71XX_PCI_ATH9K_FIXUP ++ def_bool n ++ ++config AR71XX_DEV_AP94_PCI ++ select AR71XX_PCI_ATH9K_FIXUP ++ def_bool n ++ ++config AR71XX_DEV_AR9XXX_WMAC ++ def_bool n ++ ++config AR71XX_DEV_DB120_PCI ++ select AR71XX_PCI_ATH9K_FIXUP ++ def_bool n ++ ++config AR71XX_DEV_DSA ++ def_bool n ++ ++config AR71XX_DEV_GPIO_BUTTONS ++ def_bool n ++ ++config AR71XX_DEV_LEDS_GPIO ++ def_bool n ++ ++config AR71XX_DEV_PB42_PCI ++ def_bool n ++ ++config AR71XX_DEV_PB9X_PCI ++ def_bool n ++ ++config AR71XX_DEV_USB ++ def_bool n ++ ++config AR71XX_NVRAM ++ def_bool n ++ ++config AR71XX_PCI_ATH9K_FIXUP ++ def_bool n ++ ++config SOC_AR933X ++ bool ++ select USB_ARCH_HAS_EHCI ++ ++endif +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap121.c linux-2.6.39/arch/mips/ar71xx/mach-ap121.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap121.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ap121.c 2011-08-24 02:41:55.477989660 +0200 +@@ -0,0 +1,245 @@ +/* -+ * Atheros AP83 board support ++ * Atheros AP121 board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2011 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include +#include +#include -+#include -+#include -+#include -+ -+#include -+#include ++#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "dev-m25p80.h" +#include "dev-usb.h" + -+#define AP83_GPIO_LED_WLAN 6 -+#define AP83_GPIO_LED_POWER 14 -+#define AP83_GPIO_LED_JUMPSTART 15 -+#define AP83_GPIO_BTN_JUMPSTART 12 -+#define AP83_GPIO_BTN_RESET 21 ++#define AP121_GPIO_LED_WLAN 0 ++#define AP121_GPIO_LED_USB 1 + -+#define AP83_050_GPIO_VSC7385_CS 1 -+#define AP83_050_GPIO_VSC7385_MISO 3 -+#define AP83_050_GPIO_VSC7385_MOSI 16 -+#define AP83_050_GPIO_VSC7385_SCK 17 ++#define AP121_GPIO_BTN_JUMPSTART 11 ++#define AP121_GPIO_BTN_RESET 12 ++ ++#define AP121_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define AP121_KEYS_DEBOUNCE_INTERVAL (3 * AP121_KEYS_POLL_INTERVAL) ++ ++#define AP121_MAC0_OFFSET 0x0000 ++#define AP121_MAC1_OFFSET 0x0006 ++#define AP121_CALDATA_OFFSET 0x1000 ++#define AP121_WMAC_MAC_OFFSET 0x1002 + -+#define AP83_BUTTONS_POLL_INTERVAL 20 ++#define AP121_MINI_GPIO_LED_WLAN 0 ++#define AP121_MINI_GPIO_BTN_JUMPSTART 12 ++#define AP121_MINI_GPIO_BTN_RESET 11 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition ap83_flash_partitions[] = { ++static struct mtd_partition ap121_parts[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x040000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "u-boot-env", -+ .offset = 0x040000, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "kernel", -+ .offset = 0x060000, -+ .size = 0x140000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x1a0000, -+ .size = 0x650000, -+ } , { -+ .name = "art", -+ .offset = 0x7f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x060000, -+ .size = 0x790000, -+ } -+}; -+#endif /* CONFIG_MTD_PARTITIONS */ -+ -+static struct ar91xx_flash_platform_data ap83_flash_data = { -+ .width = 2, -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = ap83_flash_partitions, -+ .nr_parts = ARRAY_SIZE(ap83_flash_partitions), -+#endif ++ }, ++ { ++ .name = "rootfs", ++ .offset = 0x010000, ++ .size = 0x130000, ++ }, ++ { ++ .name = "uImage", ++ .offset = 0x140000, ++ .size = 0x0a0000, ++ }, ++ { ++ .name = "NVRAM", ++ .offset = 0x1e0000, ++ .size = 0x010000, ++ }, ++ { ++ .name = "ART", ++ .offset = 0x1f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, +}; ++#define ap121_nr_parts ARRAY_SIZE(ap121_parts) + -+static struct resource ap83_flash_resources[] = { -+ [0] = { -+ .start = AR71XX_SPI_BASE, -+ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, -+ .flags = IORESOURCE_MEM, ++static struct mtd_partition ap121_mini_parts[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, ++ { ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, ++ { ++ .name = "rootfs", ++ .offset = 0x050000, ++ .size = 0x2b0000, ++ }, ++ { ++ .name = "uImage", ++ .offset = 0x300000, ++ .size = 0x0e0000, ++ }, ++ { ++ .name = "NVRAM", ++ .offset = 0x3e0000, ++ .size = 0x010000, ++ }, ++ { ++ .name = "ART", ++ .offset = 0x3f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, + }, +}; + -+static struct platform_device ap83_flash_device = { -+ .name = "ar91xx-flash", -+ .id = -1, -+ .resource = ap83_flash_resources, -+ .num_resources = ARRAY_SIZE(ap83_flash_resources), -+ .dev = { -+ .platform_data = &ap83_flash_data, -+ } ++#define ap121_mini_nr_parts ARRAY_SIZE(ap121_parts) ++ ++#else ++#define ap121_parts NULL ++#define ap121_nr_parts 0 ++#define ap121_mini_parts NULL ++#define ap121_mini_nr_parts 0 ++#endif /* CONFIG_MTD_PARTITIONS */ ++ ++static struct flash_platform_data ap121_flash_data = { ++ .parts = ap121_parts, ++ .nr_parts = ap121_nr_parts, +}; + -+static struct gpio_led ap83_leds_gpio[] __initdata = { ++static struct gpio_led ap121_leds_gpio[] __initdata = { + { -+ .name = "ap83:green:jumpstart", -+ .gpio = AP83_GPIO_LED_JUMPSTART, -+ .active_low = 0, -+ }, { -+ .name = "ap83:green:power", -+ .gpio = AP83_GPIO_LED_POWER, ++ .name = "ap121:green:usb", ++ .gpio = AP121_GPIO_LED_USB, + .active_low = 0, -+ }, { -+ .name = "ap83:green:wlan", -+ .gpio = AP83_GPIO_LED_WLAN, ++ }, ++ { ++ .name = "ap121:green:wlan", ++ .gpio = AP121_GPIO_LED_WLAN, + .active_low = 0, + }, +}; + -+static struct gpio_button ap83_gpio_buttons[] __initdata = { ++static struct gpio_keys_button ap121_gpio_keys[] __initdata = { + { -+ .desc = "soft_reset", ++ .desc = "jumpstart button", + .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = AP83_GPIO_BTN_RESET, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = AP121_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP121_GPIO_BTN_JUMPSTART, + .active_low = 1, -+ } , { -+ .desc = "jumpstart", ++ }, ++ { ++ .desc = "reset button", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = AP83_GPIO_BTN_JUMPSTART, ++ .code = KEY_RESTART, ++ .debounce_interval = AP121_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP121_GPIO_BTN_RESET, + .active_low = 1, + } +}; + -+static struct resource ap83_040_spi_resources[] = { -+ [0] = { -+ .start = AR71XX_SPI_BASE, -+ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, -+ .flags = IORESOURCE_MEM, ++static struct gpio_led ap121_mini_leds_gpio[] __initdata = { ++ { ++ .name = "ap121:green:wlan", ++ .gpio = AP121_MINI_GPIO_LED_WLAN, ++ .active_low = 0, + }, +}; + -+static struct platform_device ap83_040_spi_device = { -+ .name = "ap83-spi", -+ .id = 0, -+ .resource = ap83_040_spi_resources, -+ .num_resources = ARRAY_SIZE(ap83_040_spi_resources), -+}; -+ -+static struct spi_gpio_platform_data ap83_050_spi_data = { -+ .miso = AP83_050_GPIO_VSC7385_MISO, -+ .mosi = AP83_050_GPIO_VSC7385_MOSI, -+ .sck = AP83_050_GPIO_VSC7385_SCK, -+ .num_chipselect = 1, -+}; -+ -+static struct platform_device ap83_050_spi_device = { -+ .name = "spi_gpio", -+ .id = 0, -+ .dev = { -+ .platform_data = &ap83_050_spi_data, -+ } -+}; -+ -+static void ap83_vsc7385_reset(void) -+{ -+ ar71xx_device_stop(RESET_MODULE_GE1_PHY); -+ udelay(10); -+ ar71xx_device_start(RESET_MODULE_GE1_PHY); -+ mdelay(50); -+} -+ -+static struct vsc7385_platform_data ap83_vsc7385_data = { -+ .reset = ap83_vsc7385_reset, -+ .ucode_name = "vsc7385_ucode_ap83.bin", -+ .mac_cfg = { -+ .tx_ipg = 6, -+ .bit2 = 0, -+ .clk_sel = 3, ++static struct gpio_keys_button ap121_mini_gpio_keys[] __initdata = { ++ { ++ .desc = "jumpstart button", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = AP121_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP121_MINI_GPIO_BTN_JUMPSTART, ++ .active_low = 1, + }, -+}; -+ -+static struct spi_board_info ap83_spi_info[] = { + { -+ .bus_num = 0, -+ .chip_select = 0, -+ .max_speed_hz = 25000000, -+ .modalias = "spi-vsc7385", -+ .platform_data = &ap83_vsc7385_data, -+ .controller_data = (void *) AP83_050_GPIO_VSC7385_CS, ++ .desc = "reset button", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = AP121_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP121_MINI_GPIO_BTN_RESET, ++ .active_low = 1, + } +}; + -+static void __init ap83_generic_setup(void) ++static void __init ap121_common_setup(void) +{ -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ -+ ar71xx_set_mac_base(eeprom); ++ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); + -+ ar71xx_add_device_mdio(0xfffffffe); ++ ar71xx_add_device_m25p80(&ap121_flash_data); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.phy_mask = 0x1; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, art + AP121_MAC0_OFFSET, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, art + AP121_MAC1_OFFSET, 0); + -+ ar71xx_add_device_eth(0); ++ /* WAN port */ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(4); + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ /* LAN ports */ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; + ar71xx_eth1_data.speed = SPEED_1000; + ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_eth1_data.has_ar7240_switch = 1; + -+ ar71xx_eth1_pll_data.pll_1000 = 0x1f000000; -+ ++ ar71xx_add_device_mdio(0x0); + ar71xx_add_device_eth(1); ++ ar71xx_add_device_eth(0); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap83_leds_gpio), -+ ap83_leds_gpio); -+ -+ ar71xx_add_device_gpio_buttons(-1, AP83_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(ap83_gpio_buttons), -+ ap83_gpio_buttons); -+ -+ ar71xx_add_device_usb(); -+ -+ ar913x_add_device_wmac(eeprom, NULL); -+ -+ platform_device_register(&ap83_flash_device); -+ -+ spi_register_board_info(ap83_spi_info, ARRAY_SIZE(ap83_spi_info)); ++ ar9xxx_add_device_wmac(art + AP121_CALDATA_OFFSET, ++ art + AP121_WMAC_MAC_OFFSET); +} + -+static void __init ap83_040_setup(void) ++static void __init ap121_setup(void) +{ -+ ap83_flash_data.is_shared=1; -+ ap83_generic_setup(); -+ platform_device_register(&ap83_040_spi_device); -+} ++ ap121_flash_data.parts = ap121_parts; ++ ap121_flash_data.nr_parts = ap121_nr_parts; + -+static void __init ap83_050_setup(void) -+{ -+ ap83_generic_setup(); -+ platform_device_register(&ap83_050_spi_device); ++ ap121_common_setup(); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap121_leds_gpio), ++ ap121_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, AP121_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ap121_gpio_keys), ++ ap121_gpio_keys); ++ ++ ar71xx_add_device_usb(); +} + -+static void __init ap83_setup(void) ++static void __init ap121_mini_setup(void) +{ -+ u8 *board_id = (u8 *) KSEG1ADDR(0x1fff1244); -+ unsigned int board_version; ++ ap121_flash_data.parts = ap121_mini_parts; ++ ap121_flash_data.nr_parts = ap121_mini_nr_parts; + -+ board_version = (unsigned int)(board_id[0] - '0'); -+ board_version += ((unsigned int)(board_id[1] - '0')) * 10; ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap121_mini_leds_gpio), ++ ap121_mini_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, AP121_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ap121_mini_gpio_keys), ++ ap121_mini_gpio_keys); + -+ switch (board_version) { -+ case 40: -+ ap83_040_setup(); -+ break; -+ case 50: -+ ap83_050_setup(); -+ break; -+ default: -+ printk(KERN_WARNING "AP83-%03u board is not yet supported\n", -+ board_version); -+ } ++ ap121_common_setup(); +} + -+MIPS_MACHINE(AR71XX_MACH_AP83, "AP83", "Atheros AP83", ap83_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-aw-nr580.c linux-2.6.39/arch/mips/ar71xx/mach-aw-nr580.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-aw-nr580.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-aw-nr580.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,101 @@ ++MIPS_MACHINE(AR71XX_MACH_AP121, "AP121", "Atheros AP121", ++ ap121_setup); ++ ++MIPS_MACHINE(AR71XX_MACH_AP121_MINI, "AP121-MINI", "Atheros AP121-MINI", ++ ap121_mini_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap81.c linux-2.6.39/arch/mips/ar71xx/mach-ap81.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap81.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ap81.c 2011-08-24 02:41:55.477989660 +0200 +@@ -0,0 +1,142 @@ +/* -+ * AzureWave AW-NR580 board support ++ * Atheros AP81 board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2009 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -3318,616 +3582,703 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-aw-nr580.c linux-2.6.39/arch/m +#include +#include + -+#include +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" -+#include "dev-pb42-pci.h" +#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define AW_NR580_GPIO_LED_READY_RED 0 -+#define AW_NR580_GPIO_LED_WLAN 1 -+#define AW_NR580_GPIO_LED_READY_GREEN 2 -+#define AW_NR580_GPIO_LED_WPS_GREEN 4 -+#define AW_NR580_GPIO_LED_WPS_AMBER 5 ++#define AP81_GPIO_LED_STATUS 1 ++#define AP81_GPIO_LED_AOSS 3 ++#define AP81_GPIO_LED_WLAN 6 ++#define AP81_GPIO_LED_POWER 14 + -+#define AW_NR580_GPIO_BTN_WPS 3 -+#define AW_NR580_GPIO_BTN_RESET 11 ++#define AP81_GPIO_BTN_SW4 12 ++#define AP81_GPIO_BTN_SW1 21 + -+#define AW_NR580_BUTTONS_POLL_INTERVAL 20 ++#define AP81_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define AP81_KEYS_DEBOUNCE_INTERVAL (3 * AP81_KEYS_POLL_INTERVAL) + -+static struct gpio_led aw_nr580_leds_gpio[] __initdata = { ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition ap81_partitions[] = { + { -+ .name = "aw-nr580:red:ready", -+ .gpio = AW_NR580_GPIO_LED_READY_RED, -+ .active_low = 0, -+ }, { -+ .name = "aw-nr580:green:ready", -+ .gpio = AW_NR580_GPIO_LED_READY_GREEN, -+ .active_low = 0, ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, + }, { -+ .name = "aw-nr580:green:wps", -+ .gpio = AW_NR580_GPIO_LED_WPS_GREEN, -+ .active_low = 0, ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, + }, { -+ .name = "aw-nr580:amber:wps", -+ .gpio = AW_NR580_GPIO_LED_WPS_AMBER, -+ .active_low = 0, ++ .name = "rootfs", ++ .offset = 0x050000, ++ .size = 0x500000, + }, { -+ .name = "aw-nr580:green:wlan", -+ .gpio = AW_NR580_GPIO_LED_WLAN, -+ .active_low = 0, ++ .name = "uImage", ++ .offset = 0x550000, ++ .size = 0x100000, ++ }, { ++ .name = "ART", ++ .offset = 0x650000, ++ .size = 0x1b0000, ++ .mask_flags = MTD_WRITEABLE, + } +}; ++#endif /* CONFIG_MTD_PARTITIONS */ ++ ++static struct flash_platform_data ap81_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = ap81_partitions, ++ .nr_parts = ARRAY_SIZE(ap81_partitions), ++#endif ++}; + -+static struct gpio_button aw_nr580_gpio_buttons[] __initdata = { ++static struct gpio_led ap81_leds_gpio[] __initdata = { + { -+ .desc = "reset", ++ .name = "ap81:green:status", ++ .gpio = AP81_GPIO_LED_STATUS, ++ .active_low = 1, ++ }, { ++ .name = "ap81:amber:aoss", ++ .gpio = AP81_GPIO_LED_AOSS, ++ .active_low = 1, ++ }, { ++ .name = "ap81:green:wlan", ++ .gpio = AP81_GPIO_LED_WLAN, ++ .active_low = 1, ++ }, { ++ .name = "ap81:green:power", ++ .gpio = AP81_GPIO_LED_POWER, ++ .active_low = 1, ++ } ++}; ++ ++static struct gpio_keys_button ap81_gpio_keys[] __initdata = { ++ { ++ .desc = "sw1", + .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = AW_NR580_GPIO_BTN_RESET, ++ .code = BTN_0, ++ .debounce_interval = AP81_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP81_GPIO_BTN_SW1, + .active_low = 1, + }, { -+ .desc = "wps", ++ .desc = "sw4", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = AW_NR580_GPIO_BTN_WPS, ++ .code = BTN_1, ++ .debounce_interval = AP81_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP81_GPIO_BTN_SW4, + .active_low = 1, + } +}; + -+static void __init aw_nr580_setup(void) ++static void __init ap81_setup(void) +{ ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ + ar71xx_add_device_mdio(0x0); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, eeprom, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; + ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.has_ar8216 = 1; ++ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, eeprom, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + + ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ pb42_pci_init(); ++ ar71xx_add_device_usb(); + -+ ar71xx_add_device_m25p80(NULL); ++ ar71xx_add_device_m25p80(&ap81_flash_data); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(aw_nr580_leds_gpio), -+ aw_nr580_leds_gpio); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap81_leds_gpio), ++ ap81_leds_gpio); + -+ ar71xx_add_device_gpio_buttons(-1, AW_NR580_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(aw_nr580_gpio_buttons), -+ aw_nr580_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, AP81_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ap81_gpio_keys), ++ ap81_gpio_keys); ++ ++ ar9xxx_add_device_wmac(eeprom, NULL); +} + -+MIPS_MACHINE(AR71XX_MACH_AW_NR580, "AW-NR580", "AzureWave AW-NR580", -+ aw_nr580_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-600-a1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-600-a1.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-600-a1.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-dir-600-a1.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,138 @@ ++MIPS_MACHINE(AR71XX_MACH_AP81, "AP81", "Atheros AP81", ap81_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap83.c linux-2.6.39/arch/mips/ar71xx/mach-ap83.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap83.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ap83.c 2011-08-24 02:41:55.477989660 +0200 +@@ -0,0 +1,267 @@ +/* -+ * D-Link DIR-600 rev. A1 board support ++ * Atheros AP83 board support + * -+ * Copyright (C) 2010 Gabor Juhos ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include ++#include +#include +#include ++#include ++#include ++#include + +#include ++#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-m25p80.h" -+#include "dev-ap91-eth.h" -+#include "dev-ap91-pci.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "nvram.h" -+ -+#define DIR_600_A1_GPIO_LED_WPS 0 -+#define DIR_600_A1_GPIO_LED_POWER_AMBER 1 -+#define DIR_600_A1_GPIO_LED_POWER_GREEN 6 ++#include "dev-usb.h" + -+#define DIR_600_A1_GPIO_BTN_RESET 8 -+#define DIR_600_A1_GPIO_BTN_WPS 12 ++#define AP83_GPIO_LED_WLAN 6 ++#define AP83_GPIO_LED_POWER 14 ++#define AP83_GPIO_LED_JUMPSTART 15 ++#define AP83_GPIO_BTN_JUMPSTART 12 ++#define AP83_GPIO_BTN_RESET 21 + -+#define DIR_600_A1_BUTTONS_POLL_INTERVAL 20 ++#define AP83_050_GPIO_VSC7385_CS 1 ++#define AP83_050_GPIO_VSC7385_MISO 3 ++#define AP83_050_GPIO_VSC7385_MOSI 16 ++#define AP83_050_GPIO_VSC7385_SCK 17 + -+#define DIR_600_A1_NVRAM_ADDR 0x1f030000 -+#define DIR_600_A1_NVRAM_SIZE 0x10000 ++#define AP83_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define AP83_KEYS_DEBOUNCE_INTERVAL (3 * AP83_KEYS_POLL_INTERVAL) + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition dir_600_a1_partitions[] = { ++static struct mtd_partition ap83_flash_partitions[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x030000, ++ .size = 0x040000, + .mask_flags = MTD_WRITEABLE, + }, { -+ .name = "nvram", -+ .offset = 0x030000, -+ .size = 0x010000, ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, + }, { + .name = "kernel", -+ .offset = 0x040000, -+ .size = 0x0e0000, ++ .offset = 0x060000, ++ .size = 0x140000, + }, { + .name = "rootfs", -+ .offset = 0x120000, -+ .size = 0x2c0000, -+ }, { -+ .name = "mac", -+ .offset = 0x3e0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, ++ .offset = 0x1a0000, ++ .size = 0x650000, + }, { + .name = "art", -+ .offset = 0x3f0000, ++ .offset = 0x7f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, + }, { + .name = "firmware", -+ .offset = 0x040000, -+ .size = 0x3a0000, ++ .offset = 0x060000, ++ .size = 0x790000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data dir_600_a1_flash_data = { ++static struct ar91xx_flash_platform_data ap83_flash_data = { ++ .width = 2, +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = dir_600_a1_partitions, -+ .nr_parts = ARRAY_SIZE(dir_600_a1_partitions), ++ .parts = ap83_flash_partitions, ++ .nr_parts = ARRAY_SIZE(ap83_flash_partitions), +#endif +}; + -+static struct gpio_led dir_600_a1_leds_gpio[] __initdata = { ++static struct resource ap83_flash_resources[] = { ++ [0] = { ++ .start = AR71XX_SPI_BASE, ++ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; ++ ++static struct platform_device ap83_flash_device = { ++ .name = "ar91xx-flash", ++ .id = -1, ++ .resource = ap83_flash_resources, ++ .num_resources = ARRAY_SIZE(ap83_flash_resources), ++ .dev = { ++ .platform_data = &ap83_flash_data, ++ } ++}; ++ ++static struct gpio_led ap83_leds_gpio[] __initdata = { + { -+ .name = "dir-600-a1:green:power", -+ .gpio = DIR_600_A1_GPIO_LED_POWER_GREEN, ++ .name = "ap83:green:jumpstart", ++ .gpio = AP83_GPIO_LED_JUMPSTART, ++ .active_low = 0, + }, { -+ .name = "dir-600-a1:amber:power", -+ .gpio = DIR_600_A1_GPIO_LED_POWER_AMBER, ++ .name = "ap83:green:power", ++ .gpio = AP83_GPIO_LED_POWER, ++ .active_low = 0, + }, { -+ .name = "dir-600-a1:blue:wps", -+ .gpio = DIR_600_A1_GPIO_LED_WPS, -+ .active_low = 1, -+ } ++ .name = "ap83:green:wlan", ++ .gpio = AP83_GPIO_LED_WLAN, ++ .active_low = 0, ++ }, +}; + -+static struct gpio_button dir_600_a1_gpio_buttons[] __initdata = { ++static struct gpio_keys_button ap83_gpio_keys[] __initdata = { + { -+ .desc = "reset", ++ .desc = "soft_reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = DIR_600_A1_GPIO_BTN_RESET, ++ .debounce_interval = AP83_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP83_GPIO_BTN_RESET, + .active_low = 1, + }, { -+ .desc = "wps", ++ .desc = "jumpstart", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = DIR_600_A1_GPIO_BTN_WPS, ++ .debounce_interval = AP83_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP83_GPIO_BTN_JUMPSTART, + .active_low = 1, + } +}; + -+static void __init dir_600_a1_setup(void) -+{ -+ const char *nvram = (char *) KSEG1ADDR(DIR_600_A1_NVRAM_ADDR); -+ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); -+ u8 mac_buff[6]; -+ u8 *mac = NULL; -+ -+ if (nvram_parse_mac_addr(nvram, DIR_600_A1_NVRAM_SIZE, -+ "lan_mac=", mac_buff) == 0) -+ mac = mac_buff; ++static struct resource ap83_040_spi_resources[] = { ++ [0] = { ++ .start = AR71XX_SPI_BASE, ++ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; + -+ ar71xx_add_device_m25p80(&dir_600_a1_flash_data); ++static struct platform_device ap83_040_spi_device = { ++ .name = "ap83-spi", ++ .id = 0, ++ .resource = ap83_040_spi_resources, ++ .num_resources = ARRAY_SIZE(ap83_040_spi_resources), ++}; + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir_600_a1_leds_gpio), -+ dir_600_a1_leds_gpio); ++static struct spi_gpio_platform_data ap83_050_spi_data = { ++ .miso = AP83_050_GPIO_VSC7385_MISO, ++ .mosi = AP83_050_GPIO_VSC7385_MOSI, ++ .sck = AP83_050_GPIO_VSC7385_SCK, ++ .num_chipselect = 1, ++}; + -+ ar71xx_add_device_gpio_buttons(-1, DIR_600_A1_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(dir_600_a1_gpio_buttons), -+ dir_600_a1_gpio_buttons); ++static struct platform_device ap83_050_spi_device = { ++ .name = "spi_gpio", ++ .id = 0, ++ .dev = { ++ .platform_data = &ap83_050_spi_data, ++ } ++}; + -+ ap91_eth_init(mac, NULL); -+ ap91_pci_init(ee, mac); ++static void ap83_vsc7385_reset(void) ++{ ++ ar71xx_device_stop(RESET_MODULE_GE1_PHY); ++ udelay(10); ++ ar71xx_device_start(RESET_MODULE_GE1_PHY); ++ mdelay(50); +} + -+MIPS_MACHINE(AR71XX_MACH_DIR_600_A1, "DIR-600-A1", "D-Link DIR-600 rev. A1", -+ dir_600_a1_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-615-c1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-615-c1.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-615-c1.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-dir-615-c1.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,173 @@ -+/* -+ * D-Link DIR-615 rev C1 board support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published ++static struct vsc7385_platform_data ap83_vsc7385_data = { ++ .reset = ap83_vsc7385_reset, ++ .ucode_name = "vsc7385_ucode_ap83.bin", ++ .mac_cfg = { ++ .tx_ipg = 6, ++ .bit2 = 0, ++ .clk_sel = 3, ++ }, ++}; ++ ++static struct spi_board_info ap83_spi_info[] = { ++ { ++ .bus_num = 0, ++ .chip_select = 0, ++ .max_speed_hz = 25000000, ++ .modalias = "spi-vsc7385", ++ .platform_data = &ap83_vsc7385_data, ++ .controller_data = (void *) AP83_050_GPIO_VSC7385_CS, ++ } ++}; ++ ++static void __init ap83_generic_setup(void) ++{ ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ ++ ar71xx_add_device_mdio(0xfffffffe); ++ ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, eeprom, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = 0x1; ++ ++ ar71xx_add_device_eth(0); ++ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, eeprom, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ++ ar71xx_eth1_pll_data.pll_1000 = 0x1f000000; ++ ++ ar71xx_add_device_eth(1); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap83_leds_gpio), ++ ap83_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, AP83_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ap83_gpio_keys), ++ ap83_gpio_keys); ++ ++ ar71xx_add_device_usb(); ++ ++ ar9xxx_add_device_wmac(eeprom, NULL); ++ ++ platform_device_register(&ap83_flash_device); ++ ++ spi_register_board_info(ap83_spi_info, ARRAY_SIZE(ap83_spi_info)); ++} ++ ++static void __init ap83_040_setup(void) ++{ ++ ap83_flash_data.is_shared = 1; ++ ap83_generic_setup(); ++ platform_device_register(&ap83_040_spi_device); ++} ++ ++static void __init ap83_050_setup(void) ++{ ++ ap83_generic_setup(); ++ platform_device_register(&ap83_050_spi_device); ++} ++ ++static void __init ap83_setup(void) ++{ ++ u8 *board_id = (u8 *) KSEG1ADDR(0x1fff1244); ++ unsigned int board_version; ++ ++ board_version = (unsigned int)(board_id[0] - '0'); ++ board_version += ((unsigned int)(board_id[1] - '0')) * 10; ++ ++ switch (board_version) { ++ case 40: ++ ap83_040_setup(); ++ break; ++ case 50: ++ ap83_050_setup(); ++ break; ++ default: ++ printk(KERN_WARNING "AP83-%03u board is not yet supported\n", ++ board_version); ++ } ++} ++ ++MIPS_MACHINE(AR71XX_MACH_AP83, "AP83", "Atheros AP83", ap83_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ap96.c linux-2.6.39/arch/mips/ar71xx/mach-ap96.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ap96.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ap96.c 2011-08-24 02:41:55.477989660 +0200 +@@ -0,0 +1,180 @@ ++/* ++ * Atheros AP96 board support ++ * ++ * Copyright (C) 2009 Marco Porsch ++ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2010 Atheros Communications ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include +#include +#include ++#include + +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ap94-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "nvram.h" -+ -+#define DIR_615C1_GPIO_LED_ORANGE_STATUS 1 /* ORANGE:STATUS:TRICOLOR */ -+#define DIR_615C1_GPIO_LED_BLUE_WPS 3 /* BLUE:WPS */ -+#define DIR_615C1_GPIO_LED_GREEN_WAN 4 /* GREEN:WAN:TRICOLOR */ -+#define DIR_615C1_GPIO_LED_GREEN_WANCPU 5 /* GREEN:WAN:CPU:TRICOLOR */ -+#define DIR_615C1_GPIO_LED_GREEN_WLAN 6 /* GREEN:WLAN */ -+#define DIR_615C1_GPIO_LED_GREEN_STATUS 14 /* GREEN:STATUS:TRICOLOR */ -+#define DIR_615C1_GPIO_LED_ORANGE_WAN 15 /* ORANGE:WAN:TRICOLOR */ ++#include "dev-usb.h" + -+/* buttons may need refinement */ ++#define AP96_GPIO_LED_12_GREEN 0 ++#define AP96_GPIO_LED_3_GREEN 1 ++#define AP96_GPIO_LED_2_GREEN 2 ++#define AP96_GPIO_LED_WPS_GREEN 4 ++#define AP96_GPIO_LED_5_GREEN 5 ++#define AP96_GPIO_LED_4_ORANGE 6 + -+#define DIR_615C1_GPIO_BTN_WPS 12 -+#define DIR_615C1_GPIO_BTN_RESET 21 ++/* Reset button - next to the power connector */ ++#define AP96_GPIO_BTN_RESET 3 ++/* WPS button - next to a led on right */ ++#define AP96_GPIO_BTN_WPS 8 + -+#define DIR_615C1_BUTTONS_POLL_INTERVAL 20 ++#define AP96_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define AP96_KEYS_DEBOUNCE_INTERVAL (3 * AP96_KEYS_POLL_INTERVAL) + -+#define DIR_615C1_CONFIG_ADDR 0x1f020000 -+#define DIR_615C1_CONFIG_SIZE 0x10000 ++#define AP96_WMAC0_MAC_OFFSET 0x120c ++#define AP96_WMAC1_MAC_OFFSET 0x520c ++#define AP96_CALDATA0_OFFSET 0x1000 ++#define AP96_CALDATA1_OFFSET 0x5000 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition dir_615c1_partitions[] = { ++static struct mtd_partition ap96_partitions[] = { + { -+ .name = "u-boot", ++ .name = "uboot", + .offset = 0, -+ .size = 0x020000, ++ .size = 0x030000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "config", -+ .offset = 0x020000, -+ .size = 0x010000, -+ } , { -+ .name = "kernel", ++ }, { ++ .name = "env", + .offset = 0x030000, -+ .size = 0x0d0000, -+ } , { ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { + .name = "rootfs", -+ .offset = 0x100000, -+ .size = 0x2f0000, -+ } , { -+ .name = "art", -+ .offset = 0x3f0000, ++ .offset = 0x040000, ++ .size = 0x600000, ++ }, { ++ .name = "uImage", ++ .offset = 0x640000, ++ .size = 0x1b0000, ++ }, { ++ .name = "caldata", ++ .offset = 0x7f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x030000, -+ .size = 0x3c0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data dir_615c1_flash_data = { ++static struct flash_platform_data ap96_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = dir_615c1_partitions, -+ .nr_parts = ARRAY_SIZE(dir_615c1_partitions), ++ .parts = ap96_partitions, ++ .nr_parts = ARRAY_SIZE(ap96_partitions), +#endif +}; + -+static struct gpio_led dir_615c1_leds_gpio[] __initdata = { ++/* ++ * AP96 has 12 unlabeled leds in the front; these are numbered from 1 to 12 ++ * below (from left to right on the board). Led 1 seems to be on whenever the ++ * board is powered. Led 11 shows LAN link activity actity. Led 3 is orange; ++ * others are green. ++ * ++ * In addition, there is one led next to a button on the right side for WPS. ++ */ ++static struct gpio_led ap96_leds_gpio[] __initdata = { + { -+ .name = "dir-615c1:orange:status", -+ .gpio = DIR_615C1_GPIO_LED_ORANGE_STATUS, ++ .name = "ap96:green:led2", ++ .gpio = AP96_GPIO_LED_2_GREEN, + .active_low = 1, + }, { -+ .name = "dir-615c1:blue:wps", -+ .gpio = DIR_615C1_GPIO_LED_BLUE_WPS, ++ .name = "ap96:green:led3", ++ .gpio = AP96_GPIO_LED_3_GREEN, + .active_low = 1, + }, { -+ .name = "dir-615c1:green:wan", -+ .gpio = DIR_615C1_GPIO_LED_GREEN_WAN, ++ .name = "ap96:orange:led4", ++ .gpio = AP96_GPIO_LED_4_ORANGE, + .active_low = 1, + }, { -+ .name = "dir-615c1:green:wancpu", -+ .gpio = DIR_615C1_GPIO_LED_GREEN_WANCPU, -+ .active_low = 1, -+ }, { -+ .name = "dir-615c1:green:wlan", -+ .gpio = DIR_615C1_GPIO_LED_GREEN_WLAN, ++ .name = "ap96:green:led5", ++ .gpio = AP96_GPIO_LED_5_GREEN, + .active_low = 1, -+ }, { -+ .name = "dir-615c1:green:status", -+ .gpio = DIR_615C1_GPIO_LED_GREEN_STATUS, -+ .active_low = 1, + }, { -+ .name = "dir-615c1:orange:wan", -+ .gpio = DIR_615C1_GPIO_LED_ORANGE_WAN, ++ .name = "ap96:green:led12", ++ .gpio = AP96_GPIO_LED_12_GREEN, ++ .active_low = 1, ++ }, { /* next to a button on right */ ++ .name = "ap96:green:wps", ++ .gpio = AP96_GPIO_LED_WPS_GREEN, + .active_low = 1, + } -+ +}; + -+static struct gpio_button dir_615c1_gpio_buttons[] __initdata = { ++static struct gpio_keys_button ap96_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = DIR_615C1_GPIO_BTN_RESET, ++ .debounce_interval = AP96_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP96_GPIO_BTN_RESET, ++ .active_low = 1, + }, { + .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = DIR_615C1_GPIO_BTN_WPS, ++ .debounce_interval = AP96_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AP96_GPIO_BTN_WPS, ++ .active_low = 1, + } +}; + -+#define DIR_615C1_LAN_PHYMASK BIT(0) -+#define DIR_615C1_WAN_PHYMASK BIT(4) -+#define DIR_615C1_MDIO_MASK (~(DIR_615C1_LAN_PHYMASK | \ -+ DIR_615C1_WAN_PHYMASK)) ++#define AP96_WAN_PHYMASK 0x10 ++#define AP96_LAN_PHYMASK 0x0f + -+static void __init dir_615c1_setup(void) ++static void __init ap96_setup(void) +{ -+ const char *config = (char *) KSEG1ADDR(DIR_615C1_CONFIG_ADDR); -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ u8 mac[6]; -+ u8 *wlan_mac = NULL; ++ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); + -+ if (nvram_parse_mac_addr(config, DIR_615C1_CONFIG_SIZE, -+ "lan_mac=", mac) == 0) { -+ ar71xx_set_mac_base(mac); -+ wlan_mac = mac; -+ } ++ ar71xx_add_device_mdio(~(AP96_WAN_PHYMASK | AP96_LAN_PHYMASK)); + -+ ar71xx_add_device_mdio(DIR_615C1_MDIO_MASK); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, art, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = AP96_LAN_PHYMASK; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.phy_mask = DIR_615C1_LAN_PHYMASK; ++ ar71xx_add_device_eth(0); + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = DIR_615C1_WAN_PHYMASK; ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, art, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = AP96_WAN_PHYMASK; ++ ++ ar71xx_eth1_pll_data.pll_1000 = 0x1f000000; + -+ ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_m25p80(&dir_615c1_flash_data); ++ ar71xx_add_device_usb(); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir_615c1_leds_gpio), -+ dir_615c1_leds_gpio); ++ ar71xx_add_device_m25p80(&ap96_flash_data); + -+ ar71xx_add_device_gpio_buttons(-1, DIR_615C1_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(dir_615c1_gpio_buttons), -+ dir_615c1_gpio_buttons); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ap96_leds_gpio), ++ ap96_leds_gpio); + -+ ar913x_add_device_wmac(eeprom, wlan_mac); ++ ar71xx_register_gpio_keys_polled(-1, AP96_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ap96_gpio_keys), ++ ap96_gpio_keys); ++ ++ ap94_pci_init(art + AP96_CALDATA0_OFFSET, ++ art + AP96_WMAC0_MAC_OFFSET, ++ art + AP96_CALDATA1_OFFSET, ++ art + AP96_WMAC1_MAC_OFFSET); +} + -+MIPS_MACHINE(AR71XX_MACH_DIR_615_C1, "DIR-615-C1", "D-Link DIR-615 rev. C1", -+ dir_615c1_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-825-b1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-825-b1.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-825-b1.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-dir-825-b1.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,192 @@ ++MIPS_MACHINE(AR71XX_MACH_AP96, "AP96", "Atheros AP96", ap96_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-aw-nr580.c linux-2.6.39/arch/mips/ar71xx/mach-aw-nr580.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-aw-nr580.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-aw-nr580.c 2011-08-24 02:41:55.487989871 +0200 +@@ -0,0 +1,102 @@ +/* -+ * D-Link DIR-825 rev. B1 board support -+ * -+ * Copyright (C) 2009 Lukas Kuna, Evkanet, s.r.o. ++ * AzureWave AW-NR580 board support + * -+ * based on mach-wndr3700.c ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include +#include +#include -+#include -+#include + ++#include +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ap94-pci.h" +#include "dev-gpio-buttons.h" ++#include "dev-pb42-pci.h" +#include "dev-leds-gpio.h" -+#include "dev-usb.h" -+ -+#define DIR825B1_GPIO_LED_BLUE_USB 0 -+#define DIR825B1_GPIO_LED_ORANGE_POWER 1 -+#define DIR825B1_GPIO_LED_BLUE_POWER 2 -+#define DIR825B1_GPIO_LED_BLUE_POWERSAVE 4 -+#define DIR825B1_GPIO_LED_ORANGE_PLANET 6 -+#define DIR825B1_GPIO_LED_BLUE_PLANET 11 -+ -+#define DIR825B1_GPIO_BTN_RESET 3 -+#define DIR825B1_GPIO_BTN_POWERSAVE 8 + -+#define DIR825B1_GPIO_RTL8366_SDA 5 -+#define DIR825B1_GPIO_RTL8366_SCK 7 -+ -+#define DIR825B1_BUTTONS_POLL_INTERVAL 20 ++#define AW_NR580_GPIO_LED_READY_RED 0 ++#define AW_NR580_GPIO_LED_WLAN 1 ++#define AW_NR580_GPIO_LED_READY_GREEN 2 ++#define AW_NR580_GPIO_LED_WPS_GREEN 4 ++#define AW_NR580_GPIO_LED_WPS_AMBER 5 + -+#define DIR825B1_CAL_LOCATION_0 0x1f661000 -+#define DIR825B1_CAL_LOCATION_1 0x1f665000 ++#define AW_NR580_GPIO_BTN_WPS 3 ++#define AW_NR580_GPIO_BTN_RESET 11 + -+#define DIR825B1_MAC_LOCATION_0 0x2ffa81b8 -+#define DIR825B1_MAC_LOCATION_1 0x2ffa8370 ++#define AW_NR580_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define AW_NR580_KEYS_DEBOUNCE_INTERVAL (3 * AW_NR580_KEYS_POLL_INTERVAL) + -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition dir825b1_partitions[] = { ++static struct gpio_led aw_nr580_leds_gpio[] __initdata = { + { -+ .name = "uboot", -+ .offset = 0, -+ .size = 0x040000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "config", -+ .offset = 0x040000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x050000, -+ .size = 0x610000, -+ } , { -+ .name = "caldata", -+ .offset = 0x660000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "unknown", -+ .offset = 0x670000, -+ .size = 0x190000, -+ .mask_flags = MTD_WRITEABLE, -+ } -+}; -+#endif /* CONFIG_MTD_PARTITIONS */ -+ -+static struct flash_platform_data dir825b1_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = dir825b1_partitions, -+ .nr_parts = ARRAY_SIZE(dir825b1_partitions), -+#endif -+}; -+ -+static struct gpio_led dir825b1_leds_gpio[] __initdata = { -+ { -+ .name = "dir825b1:blue:usb", -+ .gpio = DIR825B1_GPIO_LED_BLUE_USB, -+ .active_low = 1, -+ }, { -+ .name = "dir825b1:orange:power", -+ .gpio = DIR825B1_GPIO_LED_ORANGE_POWER, -+ .active_low = 1, ++ .name = "aw-nr580:red:ready", ++ .gpio = AW_NR580_GPIO_LED_READY_RED, ++ .active_low = 0, + }, { -+ .name = "dir825b1:blue:power", -+ .gpio = DIR825B1_GPIO_LED_BLUE_POWER, -+ .active_low = 1, ++ .name = "aw-nr580:green:ready", ++ .gpio = AW_NR580_GPIO_LED_READY_GREEN, ++ .active_low = 0, + }, { -+ .name = "dir825b1:blue:powersave", -+ .gpio = DIR825B1_GPIO_LED_BLUE_POWERSAVE, -+ .active_low = 1, ++ .name = "aw-nr580:green:wps", ++ .gpio = AW_NR580_GPIO_LED_WPS_GREEN, ++ .active_low = 0, + }, { -+ .name = "dir825b1:orange:planet", -+ .gpio = DIR825B1_GPIO_LED_ORANGE_PLANET, -+ .active_low = 1, ++ .name = "aw-nr580:amber:wps", ++ .gpio = AW_NR580_GPIO_LED_WPS_AMBER, ++ .active_low = 0, + }, { -+ .name = "dir825b1:blue:planet", -+ .gpio = DIR825B1_GPIO_LED_BLUE_PLANET, -+ .active_low = 1, ++ .name = "aw-nr580:green:wlan", ++ .gpio = AW_NR580_GPIO_LED_WLAN, ++ .active_low = 0, + } +}; + -+static struct gpio_button dir825b1_gpio_buttons[] __initdata = { ++static struct gpio_keys_button aw_nr580_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = DIR825B1_GPIO_BTN_RESET, ++ .debounce_interval = AW_NR580_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AW_NR580_GPIO_BTN_RESET, + .active_low = 1, -+ } , { -+ .desc = "powersave", ++ }, { ++ .desc = "wps", + .type = EV_KEY, -+ .code = BTN_1, -+ .threshold = 3, -+ .gpio = DIR825B1_GPIO_BTN_POWERSAVE, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = AW_NR580_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = AW_NR580_GPIO_BTN_WPS, + .active_low = 1, + } +}; + -+static struct rtl8366s_platform_data dir825b1_rtl8366s_data = { -+ .gpio_sda = DIR825B1_GPIO_RTL8366_SDA, -+ .gpio_sck = DIR825B1_GPIO_RTL8366_SCK, -+}; -+ -+static struct platform_device dir825b1_rtl8366s_device = { -+ .name = RTL8366S_DRIVER_NAME, -+ .id = -1, -+ .dev = { -+ .platform_data = &dir825b1_rtl8366s_data, -+ } -+}; -+ -+static void __init dir825b1_setup(void) ++static void __init aw_nr580_setup(void) +{ -+ u8 mac[6], i; -+ -+ memcpy(mac, (u8*)KSEG1ADDR(DIR825B1_MAC_LOCATION_1), 6); -+ for(i = 5; i >= 3; i--) -+ if(++mac[i] != 0x00) break; -+ -+ ar71xx_set_mac_base(mac); -+ + ar71xx_add_device_mdio(0x0); + -+ ar71xx_eth0_data.mii_bus_dev = &dir825b1_rtl8366s_device.dev; -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_pll_data.pll_1000 = 0x11110000; -+ -+ ar71xx_eth1_data.mii_bus_dev = &dir825b1_rtl8366s_device.dev; -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth1_data.phy_mask = 0x10; -+ ar71xx_eth1_pll_data.pll_1000 = 0x11110000; + + ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); -+ -+ ar71xx_add_device_m25p80(&dir825b1_flash_data); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir825b1_leds_gpio), -+ dir825b1_leds_gpio); + -+ ar71xx_add_device_gpio_buttons(-1, DIR825B1_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(dir825b1_gpio_buttons), -+ dir825b1_gpio_buttons); ++ pb42_pci_init(); + -+ ar71xx_add_device_usb(); ++ ar71xx_add_device_m25p80(NULL); + -+ platform_device_register(&dir825b1_rtl8366s_device); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(aw_nr580_leds_gpio), ++ aw_nr580_leds_gpio); + -+ ap94_pci_init((u8 *) KSEG1ADDR(DIR825B1_CAL_LOCATION_0), -+ (u8 *) KSEG1ADDR(DIR825B1_MAC_LOCATION_0), -+ (u8 *) KSEG1ADDR(DIR825B1_CAL_LOCATION_1), -+ (u8 *) KSEG1ADDR(DIR825B1_MAC_LOCATION_1)); ++ ar71xx_register_gpio_keys_polled(-1, AW_NR580_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(aw_nr580_gpio_keys), ++ aw_nr580_gpio_keys); +} + -+MIPS_MACHINE(AR71XX_MACH_DIR_825_B1, "DIR-825-B1", "D-Link DIR-825 rev. B1", -+ dir825b1_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w04nu.c linux-2.6.39/arch/mips/ar71xx/mach-mzk-w04nu.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w04nu.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-mzk-w04nu.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,165 @@ ++MIPS_MACHINE(AR71XX_MACH_AW_NR580, "AW-NR580", "AzureWave AW-NR580", ++ aw_nr580_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-db120.c linux-2.6.39/arch/mips/ar71xx/mach-db120.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-db120.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-db120.c 2011-08-24 02:41:55.487989871 +0200 +@@ -0,0 +1,134 @@ +/* -+ * Planex MZK-W04NU board support ++ * Atheros DB120 board (WASP SoC) support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -3941,163 +4292,131 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w04nu.c linux-2.6.39/arch/ + +#include "machtype.h" +#include "devices.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-m25p80.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "dev-m25p80.h" +#include "dev-usb.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-db120-pci.h" + -+#define MZK_W04NU_GPIO_LED_USB 0 -+#define MZK_W04NU_GPIO_LED_STATUS 1 -+#define MZK_W04NU_GPIO_LED_WPS 3 -+#define MZK_W04NU_GPIO_LED_WLAN 6 -+#define MZK_W04NU_GPIO_LED_AP 15 -+#define MZK_W04NU_GPIO_LED_ROUTER 16 ++#define DB120_GPIO_LED_USB 11 ++#define DB120_GPIO_LED_WLAN_5G 12 ++#define DB120_GPIO_LED_WLAN_2G 13 ++#define DB120_GPIO_LED_STATUS 14 ++#define DB120_GPIO_LED_WPS 15 + -+#define MZK_W04NU_GPIO_BTN_APROUTER 5 -+#define MZK_W04NU_GPIO_BTN_WPS 12 -+#define MZK_W04NU_GPIO_BTN_RESET 21 ++#define DB120_GPIO_BTN_SW1 16 + -+#define MZK_W04NU_BUTTONS_POLL_INTERVAL 20 ++#define DB120_CALDATA_OFFSET 0x1000 ++#define DB120_WMAC_MAC_OFFSET 0x1002 ++ ++#define DB120_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define DB120_KEYS_DEBOUNCE_INTERVAL (3 * DB120_KEYS_POLL_INTERVAL) + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition mzk_w04nu_partitions[] = { ++static struct mtd_partition db120_partitions[] = { + { + .name = "u-boot", + .offset = 0, + .size = 0x040000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "u-boot-env", + .offset = 0x040000, + .size = 0x010000, -+ } , { -+ .name = "kernel", -+ .offset = 0x050000, -+ .size = 0x160000, -+ } , { ++ }, { + .name = "rootfs", -+ .offset = 0x1b0000, ++ .offset = 0x050000, + .size = 0x630000, -+ } , { -+ .name = "art", -+ .offset = 0x7e0000, -+ .size = 0x020000, ++ }, { ++ .name = "uImage", ++ .offset = 0x680000, ++ .size = 0x160000, ++ }, { ++ .name = "NVRAM", ++ .offset = 0x7E0000, ++ .size = 0x010000, ++ }, { ++ .name = "ART", ++ .offset = 0x7F0000, ++ .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x050000, -+ .size = 0x790000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data mzk_w04nu_flash_data = { ++static struct flash_platform_data db120_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = mzk_w04nu_partitions, -+ .nr_parts = ARRAY_SIZE(mzk_w04nu_partitions), ++ .parts = db120_partitions, ++ .nr_parts = ARRAY_SIZE(db120_partitions), +#endif +}; + -+static struct gpio_led mzk_w04nu_leds_gpio[] __initdata = { ++static struct gpio_led db120_leds_gpio[] __initdata = { + { -+ .name = "mzk-w04nu:green:status", -+ .gpio = MZK_W04NU_GPIO_LED_STATUS, -+ .active_low = 1, -+ }, { -+ .name = "mzk-w04nu:blue:wps", -+ .gpio = MZK_W04NU_GPIO_LED_WPS, ++ .name = "db120:green:status", ++ .gpio = DB120_GPIO_LED_STATUS, + .active_low = 1, + }, { -+ .name = "mzk-w04nu:green:wlan", -+ .gpio = MZK_W04NU_GPIO_LED_WLAN, ++ .name = "db120:green:wps", ++ .gpio = DB120_GPIO_LED_WPS, + .active_low = 1, + }, { -+ .name = "mzk-w04nu:green:usb", -+ .gpio = MZK_W04NU_GPIO_LED_USB, ++ .name = "db120:green:wlan-5g", ++ .gpio = DB120_GPIO_LED_WLAN_5G, + .active_low = 1, + }, { -+ .name = "mzk-w04nu:green:ap", -+ .gpio = MZK_W04NU_GPIO_LED_AP, ++ .name = "db120:green:wlan-2g", ++ .gpio = DB120_GPIO_LED_WLAN_2G, + .active_low = 1, + }, { -+ .name = "mzk-w04nu:green:router", -+ .gpio = MZK_W04NU_GPIO_LED_ROUTER, ++ .name = "db120:green:usb", ++ .gpio = DB120_GPIO_LED_USB, + .active_low = 1, + } +}; + -+static struct gpio_button mzk_w04nu_gpio_buttons[] __initdata = { ++static struct gpio_keys_button db120_gpio_keys[] __initdata = { + { -+ .desc = "reset", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = MZK_W04NU_GPIO_BTN_RESET, -+ .active_low = 1, -+ }, { -+ .desc = "wps", ++ .desc = "sw1", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = MZK_W04NU_GPIO_BTN_WPS, ++ .code = BTN_0, ++ .debounce_interval = DB120_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DB120_GPIO_BTN_SW1, + .active_low = 1, -+ }, { -+ .desc = "aprouter", -+ .type = EV_KEY, -+ .code = BTN_2, -+ .threshold = 3, -+ .gpio = MZK_W04NU_GPIO_BTN_APROUTER, -+ .active_low = 0, + } +}; + -+#define MZK_W04NU_WAN_PHYMASK BIT(4) -+#define MZK_W04NU_MDIO_MASK (~MZK_W04NU_WAN_PHYMASK) -+ -+static void __init mzk_w04nu_setup(void) ++static void __init db120_setup(void) +{ -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ -+ ar71xx_set_mac_base(eeprom); -+ -+ ar71xx_add_device_mdio(MZK_W04NU_MDIO_MASK); -+ -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.has_ar8216 = 1; ++ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = MZK_W04NU_WAN_PHYMASK; ++ ar71xx_add_device_usb(); + -+ ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); ++ ar71xx_add_device_m25p80(&db120_flash_data); + -+ ar71xx_add_device_m25p80(&mzk_w04nu_flash_data); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(db120_leds_gpio), ++ db120_leds_gpio); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(mzk_w04nu_leds_gpio), -+ mzk_w04nu_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, DB120_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(db120_gpio_keys), ++ db120_gpio_keys); + -+ ar71xx_add_device_gpio_buttons(-1, MZK_W04NU_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(mzk_w04nu_gpio_buttons), -+ mzk_w04nu_gpio_buttons); -+ ar71xx_add_device_usb(); ++ ar9xxx_add_device_wmac(art + DB120_CALDATA_OFFSET, ++ art + DB120_WMAC_MAC_OFFSET); + -+ ar913x_add_device_wmac(eeprom, NULL); ++ db120_pci_init(); +} + -+MIPS_MACHINE(AR71XX_MACH_MZK_W04NU, "MZK-W04NU", "Planex MZK-W04NU", -+ mzk_w04nu_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w300nh.c linux-2.6.39/arch/mips/ar71xx/mach-mzk-w300nh.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w300nh.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-mzk-w300nh.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,158 @@ ++MIPS_MACHINE(AR71XX_MACH_DB120, "DB120", "Atheros DB120", db120_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-600-a1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-600-a1.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-600-a1.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-dir-600-a1.c 2011-08-24 02:41:55.487989871 +0200 +@@ -0,0 +1,159 @@ +/* -+ * Planex MZK-W300NH board support ++ * D-Link DIR-600 rev. A1 board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -4112,1641 +4431,1772 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w300nh.c linux-2.6.39/arch +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ap91-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "nvram.h" + -+#define MZK_W300NH_GPIO_LED_STATUS 1 -+#define MZK_W300NH_GPIO_LED_WPS 3 -+#define MZK_W300NH_GPIO_LED_WLAN 6 -+#define MZK_W300NH_GPIO_LED_AP 15 -+#define MZK_W300NH_GPIO_LED_ROUTER 16 ++#define DIR_600_A1_GPIO_LED_WPS 0 ++#define DIR_600_A1_GPIO_LED_POWER_AMBER 1 ++#define DIR_600_A1_GPIO_LED_POWER_GREEN 6 + -+#define MZK_W300NH_GPIO_BTN_APROUTER 5 -+#define MZK_W300NH_GPIO_BTN_WPS 12 -+#define MZK_W300NH_GPIO_BTN_RESET 21 ++#define DIR_600_A1_GPIO_BTN_RESET 8 ++#define DIR_600_A1_GPIO_BTN_WPS 12 + -+#define MZK_W04NU_BUTTONS_POLL_INTERVAL 20 ++#define DIR_600_A1_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define DIR_600_A1_KEYS_DEBOUNCE_INTERVAL (3 * DIR_600_A1_KEYS_POLL_INTERVAL) ++ ++#define DIR_600_A1_NVRAM_ADDR 0x1f030000 ++#define DIR_600_A1_NVRAM_SIZE 0x10000 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition mzk_w300nh_partitions[] = { ++static struct mtd_partition dir_600_a1_partitions[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x040000, ++ .size = 0x030000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "u-boot-env", -+ .offset = 0x040000, ++ }, { ++ .name = "nvram", ++ .offset = 0x030000, + .size = 0x010000, -+ } , { ++ }, { + .name = "kernel", -+ .offset = 0x050000, -+ .size = 0x160000, -+ } , { ++ .offset = 0x040000, ++ .size = 0x0e0000, ++ }, { + .name = "rootfs", -+ .offset = 0x1b0000, -+ .size = 0x630000, -+ } , { ++ .offset = 0x120000, ++ .size = 0x2c0000, ++ }, { ++ .name = "mac", ++ .offset = 0x3e0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { + .name = "art", -+ .offset = 0x7e0000, -+ .size = 0x020000, ++ .offset = 0x3f0000, ++ .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "firmware", -+ .offset = 0x050000, -+ .size = 0x790000, ++ .offset = 0x040000, ++ .size = 0x3a0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data mzk_w300nh_flash_data = { ++static struct flash_platform_data dir_600_a1_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = mzk_w300nh_partitions, -+ .nr_parts = ARRAY_SIZE(mzk_w300nh_partitions), ++ .parts = dir_600_a1_partitions, ++ .nr_parts = ARRAY_SIZE(dir_600_a1_partitions), +#endif +}; + -+static struct gpio_led mzk_w300nh_leds_gpio[] __initdata = { ++static struct gpio_led dir_600_a1_leds_gpio[] __initdata = { + { -+ .name = "mzk-w300nh:green:status", -+ .gpio = MZK_W300NH_GPIO_LED_STATUS, -+ .active_low = 1, -+ }, { -+ .name = "mzk-w300nh:blue:wps", -+ .gpio = MZK_W300NH_GPIO_LED_WPS, -+ .active_low = 1, -+ }, { -+ .name = "mzk-w300nh:green:wlan", -+ .gpio = MZK_W300NH_GPIO_LED_WLAN, -+ .active_low = 1, ++ .name = "dir-600-a1:green:power", ++ .gpio = DIR_600_A1_GPIO_LED_POWER_GREEN, + }, { -+ .name = "mzk-w300nh:green:ap", -+ .gpio = MZK_W300NH_GPIO_LED_AP, -+ .active_low = 1, ++ .name = "dir-600-a1:amber:power", ++ .gpio = DIR_600_A1_GPIO_LED_POWER_AMBER, + }, { -+ .name = "mzk-w300nh:green:router", -+ .gpio = MZK_W300NH_GPIO_LED_ROUTER, ++ .name = "dir-600-a1:blue:wps", ++ .gpio = DIR_600_A1_GPIO_LED_WPS, + .active_low = 1, + } +}; + -+static struct gpio_button mzk_w300nh_gpio_buttons[] __initdata = { ++static struct gpio_keys_button dir_600_a1_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = MZK_W300NH_GPIO_BTN_RESET, ++ .debounce_interval = DIR_600_A1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR_600_A1_GPIO_BTN_RESET, + .active_low = 1, + }, { + .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = MZK_W300NH_GPIO_BTN_WPS, ++ .debounce_interval = DIR_600_A1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR_600_A1_GPIO_BTN_WPS, + .active_low = 1, -+ }, { -+ .desc = "aprouter", -+ .type = EV_KEY, -+ .code = BTN_2, -+ .threshold = 3, -+ .gpio = MZK_W300NH_GPIO_BTN_APROUTER, -+ .active_low = 0, + } +}; + -+#define MZK_W300NH_WAN_PHYMASK BIT(4) -+#define MZK_W300NH_MDIO_MASK (~MZK_W300NH_WAN_PHYMASK) -+ -+static void __init mzk_w300nh_setup(void) ++static void __init dir_600_a1_setup(void) +{ -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ const char *nvram = (char *) KSEG1ADDR(DIR_600_A1_NVRAM_ADDR); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); ++ u8 mac_buff[6]; ++ u8 *mac = NULL; ++ ++ if (nvram_parse_mac_addr(nvram, DIR_600_A1_NVRAM_SIZE, ++ "lan_mac=", mac_buff) == 0) { ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac_buff, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac_buff, 1); ++ mac = mac_buff; ++ } + -+ ar71xx_set_mac_base(eeprom); ++ ar71xx_add_device_m25p80(&dir_600_a1_flash_data); + -+ ar71xx_add_device_mdio(MZK_W300NH_MDIO_MASK); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir_600_a1_leds_gpio), ++ dir_600_a1_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, DIR_600_A1_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(dir_600_a1_gpio_keys), ++ dir_600_a1_gpio_keys); + ++ ar71xx_eth1_data.has_ar7240_switch = 1; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ ++ /* WAN port */ + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; + ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.has_ar8216 = 1; ++ ar71xx_eth0_data.phy_mask = BIT(4); + ++ /* LAN ports */ + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = MZK_W300NH_WAN_PHYMASK; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ ar71xx_add_device_eth(0); ++ ar71xx_add_device_mdio(0x0); + ar71xx_add_device_eth(1); ++ ar71xx_add_device_eth(0); + -+ ar71xx_add_device_m25p80(&mzk_w300nh_flash_data); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(mzk_w300nh_leds_gpio), -+ mzk_w300nh_leds_gpio); -+ -+ ar71xx_add_device_gpio_buttons(-1, MZK_W04NU_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(mzk_w300nh_gpio_buttons), -+ mzk_w300nh_gpio_buttons); -+ ar913x_add_device_wmac(eeprom, NULL); ++ ap91_pci_init(ee, mac); +} + -+MIPS_MACHINE(AR71XX_MACH_MZK_W300NH, "MZK-W300NH", "Planex MZK-W300NH", -+ mzk_w300nh_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-nbg460n.c linux-2.6.39/arch/mips/ar71xx/mach-nbg460n.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-nbg460n.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-nbg460n.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,222 @@ ++MIPS_MACHINE(AR71XX_MACH_DIR_600_A1, "DIR-600-A1", "D-Link DIR-600 rev. A1", ++ dir_600_a1_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-615-c1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-615-c1.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-615-c1.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-dir-615-c1.c 2011-08-24 02:41:55.487989871 +0200 +@@ -0,0 +1,175 @@ +/* -+ * Zyxel NBG 460N/550N/550NH board support -+ * -+ * Copyright (C) 2010 Michael Kurz ++ * D-Link DIR-615 rev C1 board support + * -+ * based on mach-tl-wr1043nd.c ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include +#include +#include -+#include -+#include -+ -+#include -+#include -+#include + +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "nvram.h" + -+/* LEDs */ -+#define NBG460N_GPIO_LED_WPS 3 -+#define NBG460N_GPIO_LED_WAN 6 -+#define NBG460N_GPIO_LED_POWER 14 -+#define NBG460N_GPIO_LED_WLAN 15 ++#define DIR_615C1_GPIO_LED_ORANGE_STATUS 1 /* ORANGE:STATUS:TRICOLOR */ ++#define DIR_615C1_GPIO_LED_BLUE_WPS 3 /* BLUE:WPS */ ++#define DIR_615C1_GPIO_LED_GREEN_WAN 4 /* GREEN:WAN:TRICOLOR */ ++#define DIR_615C1_GPIO_LED_GREEN_WANCPU 5 /* GREEN:WAN:CPU:TRICOLOR */ ++#define DIR_615C1_GPIO_LED_GREEN_WLAN 6 /* GREEN:WLAN */ ++#define DIR_615C1_GPIO_LED_GREEN_STATUS 14 /* GREEN:STATUS:TRICOLOR */ ++#define DIR_615C1_GPIO_LED_ORANGE_WAN 15 /* ORANGE:WAN:TRICOLOR */ + -+/* Buttons */ -+#define NBG460N_GPIO_BTN_WPS 12 -+#define NBG460N_GPIO_BTN_RESET 21 -+#define NBG460N_BUTTONS_POLL_INTERVAL 20 ++/* buttons may need refinement */ + -+/* RTC chip PCF8563 I2C interface */ -+#define NBG460N_GPIO_PCF8563_SDA 8 -+#define NBG460N_GPIO_PCF8563_SCK 7 ++#define DIR_615C1_GPIO_BTN_WPS 12 ++#define DIR_615C1_GPIO_BTN_RESET 21 + -+/* Switch configuration I2C interface */ -+#define NBG460N_GPIO_RTL8366_SDA 16 -+#define NBG460N_GPIO_RTL8366_SCK 18 ++#define DIR_615C1_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define DIR_615C1_KEYS_DEBOUNCE_INTERVAL (3 * DIR_615C1_KEYS_POLL_INTERVAL) ++ ++#define DIR_615C1_CONFIG_ADDR 0x1f020000 ++#define DIR_615C1_CONFIG_SIZE 0x10000 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition nbg460n_partitions[] = { ++static struct mtd_partition dir_615c1_partitions[] = { + { -+ .name = "Bootbase", ++ .name = "u-boot", + .offset = 0, -+ .size = 0x010000, ++ .size = 0x020000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "U-Boot Config", -+ .offset = 0x010000, -+ .size = 0x030000, -+ } , { -+ .name = "U-Boot", -+ .offset = 0x040000, -+ .size = 0x030000, -+ } , { -+ .name = "linux", -+ .offset = 0x070000, ++ }, { ++ .name = "config", ++ .offset = 0x020000, ++ .size = 0x010000, ++ }, { ++ .name = "kernel", ++ .offset = 0x030000, + .size = 0x0e0000, -+ } , { ++ }, { + .name = "rootfs", -+ .offset = 0x150000, -+ .size = 0x2a0000, -+ } , { -+ .name = "CalibData", ++ .offset = 0x110000, ++ .size = 0x2e0000, ++ }, { ++ .name = "art", + .offset = 0x3f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "firmware", -+ .offset = 0x070000, -+ .size = 0x380000, ++ .offset = 0x030000, ++ .size = 0x3c0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data nbg460n_flash_data = { ++static struct flash_platform_data dir_615c1_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = nbg460n_partitions, -+ .nr_parts = ARRAY_SIZE(nbg460n_partitions), ++ .parts = dir_615c1_partitions, ++ .nr_parts = ARRAY_SIZE(dir_615c1_partitions), +#endif +}; + -+static struct gpio_led nbg460n_leds_gpio[] __initdata = { ++static struct gpio_led dir_615c1_leds_gpio[] __initdata = { + { -+ .name = "nbg460n:green:power", -+ .gpio = NBG460N_GPIO_LED_POWER, -+ .active_low = 0, -+ .default_trigger = "default-on", ++ .name = "dir-615c1:orange:status", ++ .gpio = DIR_615C1_GPIO_LED_ORANGE_STATUS, ++ .active_low = 1, + }, { -+ .name = "nbg460n:green:wps", -+ .gpio = NBG460N_GPIO_LED_WPS, -+ .active_low = 0, ++ .name = "dir-615c1:blue:wps", ++ .gpio = DIR_615C1_GPIO_LED_BLUE_WPS, ++ .active_low = 1, + }, { -+ .name = "nbg460n:green:wlan", -+ .gpio = NBG460N_GPIO_LED_WLAN, -+ .active_low = 0, ++ .name = "dir-615c1:green:wan", ++ .gpio = DIR_615C1_GPIO_LED_GREEN_WAN, ++ .active_low = 1, + }, { -+ /* Not really for controlling the LED, -+ when set low the LED blinks uncontrollable */ -+ .name = "nbg460n:green:wan", -+ .gpio = NBG460N_GPIO_LED_WAN, -+ .active_low = 0, ++ .name = "dir-615c1:green:wancpu", ++ .gpio = DIR_615C1_GPIO_LED_GREEN_WANCPU, ++ .active_low = 1, ++ }, { ++ .name = "dir-615c1:green:wlan", ++ .gpio = DIR_615C1_GPIO_LED_GREEN_WLAN, ++ .active_low = 1, ++ }, { ++ .name = "dir-615c1:green:status", ++ .gpio = DIR_615C1_GPIO_LED_GREEN_STATUS, ++ .active_low = 1, ++ }, { ++ .name = "dir-615c1:orange:wan", ++ .gpio = DIR_615C1_GPIO_LED_ORANGE_WAN, ++ .active_low = 1, + } ++ +}; + -+static struct gpio_button nbg460n_gpio_buttons[] __initdata = { ++static struct gpio_keys_button dir_615c1_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = NBG460N_GPIO_BTN_RESET, -+ .active_low = 1, ++ .debounce_interval = DIR_615C1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR_615C1_GPIO_BTN_RESET, + }, { + .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = NBG460N_GPIO_BTN_WPS, -+ .active_low = 1, ++ .debounce_interval = DIR_615C1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR_615C1_GPIO_BTN_WPS, + } +}; + -+static struct i2c_gpio_platform_data nbg460n_i2c_device_platdata = { -+ .sda_pin = NBG460N_GPIO_PCF8563_SDA, -+ .scl_pin = NBG460N_GPIO_PCF8563_SCK, -+ .udelay = 10, -+}; -+ -+static struct platform_device nbg460n_i2c_device = { -+ .name = "i2c-gpio", -+ .id = -1, -+ .num_resources = 0, -+ .resource = NULL, -+ .dev = { -+ .platform_data = &nbg460n_i2c_device_platdata, -+ }, -+}; -+ -+static struct i2c_board_info nbg460n_i2c_devs[] __initdata = { -+ { -+ I2C_BOARD_INFO("pcf8563", 0x51), -+ }, -+}; ++#define DIR_615C1_LAN_PHYMASK BIT(0) ++#define DIR_615C1_WAN_PHYMASK BIT(4) ++#define DIR_615C1_MDIO_MASK (~(DIR_615C1_LAN_PHYMASK | \ ++ DIR_615C1_WAN_PHYMASK)) + -+static void __devinit nbg460n_i2c_init(void) ++static void __init dir_615c1_setup(void) +{ -+ /* The gpio interface */ -+ platform_device_register(&nbg460n_i2c_device); -+ /* I2C devices */ -+ i2c_register_board_info(0, nbg460n_i2c_devs, -+ ARRAY_SIZE(nbg460n_i2c_devs)); -+} -+ -+ -+static struct rtl8366s_platform_data nbg460n_rtl8366s_data = { -+ .gpio_sda = NBG460N_GPIO_RTL8366_SDA, -+ .gpio_sck = NBG460N_GPIO_RTL8366_SCK, -+}; ++ const char *config = (char *) KSEG1ADDR(DIR_615C1_CONFIG_ADDR); ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ u8 mac[6]; ++ u8 *wlan_mac = NULL; + -+static struct platform_device nbg460n_rtl8366s_device = { -+ .name = RTL8366S_DRIVER_NAME, -+ .id = -1, -+ .dev = { -+ .platform_data = &nbg460n_rtl8366s_data, ++ if (nvram_parse_mac_addr(config, DIR_615C1_CONFIG_SIZE, ++ "lan_mac=", mac) == 0) { ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ wlan_mac = mac; + } -+}; + -+static void __init nbg460n_setup(void) -+{ -+ /* end of bootloader sector contains mac address*/ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1fc0fff8); -+ /* last sector contains wlan calib data */ -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ ar71xx_add_device_mdio(DIR_615C1_MDIO_MASK); + -+ ar71xx_set_mac_base(mac); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.phy_mask = DIR_615C1_LAN_PHYMASK; + -+ /* LAN Port */ -+ ar71xx_eth0_data.mii_bus_dev = &nbg460n_rtl8366s_device.dev; -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.speed = SPEED_1000; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ -+ /* WAN Port */ -+ ar71xx_eth1_data.mii_bus_dev = &nbg460n_rtl8366s_device.dev; -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = DIR_615C1_WAN_PHYMASK; + + ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ /* register the switch phy */ -+ platform_device_register(&nbg460n_rtl8366s_device); -+ -+ /* register flash */ -+ ar71xx_add_device_m25p80(&nbg460n_flash_data); -+ -+ ar913x_add_device_wmac(eeprom, mac); ++ ar71xx_add_device_m25p80(&dir_615c1_flash_data); + -+ /* register RTC chip */ -+ nbg460n_i2c_init(); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir_615c1_leds_gpio), ++ dir_615c1_leds_gpio); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(nbg460n_leds_gpio), -+ nbg460n_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, DIR_615C1_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(dir_615c1_gpio_keys), ++ dir_615c1_gpio_keys); + -+ ar71xx_add_device_gpio_buttons(-1, NBG460N_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(nbg460n_gpio_buttons), -+ nbg460n_gpio_buttons); ++ ar9xxx_add_device_wmac(eeprom, wlan_mac); +} + -+MIPS_MACHINE(AR71XX_MACH_NBG460N, "NBG460N", "Zyxel NBG460N/550N/550NH", nbg460n_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb42.c linux-2.6.39/arch/mips/ar71xx/mach-pb42.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb42.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-pb42.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,71 @@ ++MIPS_MACHINE(AR71XX_MACH_DIR_615_C1, "DIR-615-C1", "D-Link DIR-615 rev. C1", ++ dir_615c1_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-825-b1.c linux-2.6.39/arch/mips/ar71xx/mach-dir-825-b1.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-dir-825-b1.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-dir-825-b1.c 2011-08-24 02:41:55.487989871 +0200 +@@ -0,0 +1,198 @@ +/* -+ * Atheros PB42 board support ++ * D-Link DIR-825 rev. B1 board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009 Lukas Kuna, Evkanet, s.r.o. ++ * ++ * based on mach-wndr3700.c + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include ++#include ++#include ++#include ++#include ++ +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" ++#include "dev-ap94-pci.h" +#include "dev-gpio-buttons.h" -+#include "dev-pb42-pci.h" ++#include "dev-leds-gpio.h" +#include "dev-usb.h" + -+#define PB42_BUTTONS_POLL_INTERVAL 20 ++#define DIR825B1_GPIO_LED_BLUE_USB 0 ++#define DIR825B1_GPIO_LED_ORANGE_POWER 1 ++#define DIR825B1_GPIO_LED_BLUE_POWER 2 ++#define DIR825B1_GPIO_LED_BLUE_WPS 4 ++#define DIR825B1_GPIO_LED_ORANGE_PLANET 6 ++#define DIR825B1_GPIO_LED_BLUE_PLANET 11 ++ ++#define DIR825B1_GPIO_BTN_RESET 3 ++#define DIR825B1_GPIO_BTN_WPS 8 + -+#define PB42_GPIO_BTN_SW4 8 -+#define PB42_GPIO_BTN_SW5 3 ++#define DIR825B1_GPIO_RTL8366_SDA 5 ++#define DIR825B1_GPIO_RTL8366_SCK 7 ++ ++#define DIR825B1_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define DIR825B1_KEYS_DEBOUNCE_INTERVAL (3 * DIR825B1_KEYS_POLL_INTERVAL) ++ ++#define DIR825B1_CAL_LOCATION_0 0x1f661000 ++#define DIR825B1_CAL_LOCATION_1 0x1f665000 ++ ++#define DIR825B1_MAC_LOCATION_0 0x2ffa81b8 ++#define DIR825B1_MAC_LOCATION_1 0x2ffa8370 ++ ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition dir825b1_partitions[] = { ++ { ++ .name = "uboot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "config", ++ .offset = 0x040000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x050000, ++ .size = 0x610000, ++ }, { ++ .name = "caldata", ++ .offset = 0x660000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "unknown", ++ .offset = 0x670000, ++ .size = 0x190000, ++ .mask_flags = MTD_WRITEABLE, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ ++ ++static struct flash_platform_data dir825b1_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = dir825b1_partitions, ++ .nr_parts = ARRAY_SIZE(dir825b1_partitions), ++#endif ++}; + -+static struct gpio_button pb42_gpio_buttons[] __initdata = { ++static struct gpio_led dir825b1_leds_gpio[] __initdata = { + { -+ .desc = "sw4", ++ .name = "dir825b1:blue:usb", ++ .gpio = DIR825B1_GPIO_LED_BLUE_USB, ++ .active_low = 1, ++ }, { ++ .name = "dir825b1:orange:power", ++ .gpio = DIR825B1_GPIO_LED_ORANGE_POWER, ++ .active_low = 1, ++ }, { ++ .name = "dir825b1:blue:power", ++ .gpio = DIR825B1_GPIO_LED_BLUE_POWER, ++ .active_low = 1, ++ }, { ++ .name = "dir825b1:blue:wps", ++ .gpio = DIR825B1_GPIO_LED_BLUE_WPS, ++ .active_low = 1, ++ }, { ++ .name = "dir825b1:orange:planet", ++ .gpio = DIR825B1_GPIO_LED_ORANGE_PLANET, ++ .active_low = 1, ++ }, { ++ .name = "dir825b1:blue:planet", ++ .gpio = DIR825B1_GPIO_LED_BLUE_PLANET, ++ .active_low = 1, ++ } ++}; ++ ++static struct gpio_keys_button dir825b1_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", + .type = EV_KEY, -+ .code = BTN_0, -+ .threshold = 3, -+ .gpio = PB42_GPIO_BTN_SW4, ++ .code = KEY_RESTART, ++ .debounce_interval = DIR825B1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR825B1_GPIO_BTN_RESET, + .active_low = 1, -+ } , { -+ .desc = "sw5", ++ }, { ++ .desc = "wps", + .type = EV_KEY, -+ .code = BTN_1, -+ .threshold = 3, -+ .gpio = PB42_GPIO_BTN_SW5, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = DIR825B1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = DIR825B1_GPIO_BTN_WPS, + .active_low = 1, + } +}; + -+#define PB42_WAN_PHYMASK BIT(20) -+#define PB42_LAN_PHYMASK (BIT(16) | BIT(17) | BIT(18) | BIT(19)) -+#define PB42_MDIO_PHYMASK (PB42_LAN_PHYMASK | PB42_WAN_PHYMASK) ++static struct rtl8366_initval dir825b1_rtl8366s_initvals[] = { ++ { .reg = 0x06, .val = 0x0108 }, ++}; + -+static void __init pb42_init(void) ++static struct rtl8366_platform_data dir825b1_rtl8366s_data = { ++ .gpio_sda = DIR825B1_GPIO_RTL8366_SDA, ++ .gpio_sck = DIR825B1_GPIO_RTL8366_SCK, ++ .num_initvals = ARRAY_SIZE(dir825b1_rtl8366s_initvals), ++ .initvals = dir825b1_rtl8366s_initvals, ++}; ++ ++static struct platform_device dir825b1_rtl8366s_device = { ++ .name = RTL8366S_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &dir825b1_rtl8366s_data, ++ } ++}; ++ ++static void __init dir825b1_setup(void) +{ -+ ar71xx_add_device_m25p80(NULL); ++ u8 *mac = (u8 *) KSEG1ADDR(DIR825B1_MAC_LOCATION_1); + -+ ar71xx_add_device_mdio(~PB42_MDIO_PHYMASK); ++ ar71xx_add_device_mdio(0x0); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = PB42_WAN_PHYMASK; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 1); ++ ar71xx_eth0_data.mii_bus_dev = &dir825b1_rtl8366s_device.dev; ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_pll_data.pll_1000 = 0x11110000; + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.speed = SPEED_100; -+ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 2); ++ ar71xx_eth1_data.mii_bus_dev = &dir825b1_rtl8366s_device.dev; ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = 0x10; ++ ar71xx_eth1_pll_data.pll_1000 = 0x11110000; + + ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_gpio_buttons(-1, PB42_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(pb42_gpio_buttons), -+ pb42_gpio_buttons); ++ ar71xx_add_device_m25p80(&dir825b1_flash_data); + -+ pb42_pci_init(); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(dir825b1_leds_gpio), ++ dir825b1_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, DIR825B1_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(dir825b1_gpio_keys), ++ dir825b1_gpio_keys); ++ ++ ar71xx_add_device_usb(); ++ ++ platform_device_register(&dir825b1_rtl8366s_device); ++ ++ ap94_pci_setup_wmac_led_pin(0, 5); ++ ap94_pci_setup_wmac_led_pin(1, 5); ++ ++ ap94_pci_init((u8 *) KSEG1ADDR(DIR825B1_CAL_LOCATION_0), ++ (u8 *) KSEG1ADDR(DIR825B1_MAC_LOCATION_0), ++ (u8 *) KSEG1ADDR(DIR825B1_CAL_LOCATION_1), ++ (u8 *) KSEG1ADDR(DIR825B1_MAC_LOCATION_1)); +} + -+MIPS_MACHINE(AR71XX_MACH_PB42, "PB42", "Atheros PB42", pb42_init); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb44.c linux-2.6.39/arch/mips/ar71xx/mach-pb44.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb44.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-pb44.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,207 @@ ++MIPS_MACHINE(AR71XX_MACH_DIR_825_B1, "DIR-825-B1", "D-Link DIR-825 rev. B1", ++ dir825b1_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-eap7660d.c linux-2.6.39/arch/mips/ar71xx/mach-eap7660d.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-eap7660d.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-eap7660d.c 2011-08-24 02:41:55.497990784 +0200 +@@ -0,0 +1,180 @@ +/* -+ * Atheros PB44 board support ++ * Senao EAP7660D board support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2010 Daniel Golle ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include ++#include ++#include +#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ +#include ++#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-pb42-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "dev-usb.h" ++#include "dev-m25p80.h" + -+#define PB44_PCF8757_VSC7395_CS 0 -+#define PB44_PCF8757_STEREO_CS 1 -+#define PB44_PCF8757_SLIC_CS0 2 -+#define PB44_PCF8757_SLIC_TEST 3 -+#define PB44_PCF8757_SLIC_INT0 4 -+#define PB44_PCF8757_SLIC_INT1 5 -+#define PB44_PCF8757_SW_RESET 6 -+#define PB44_PCF8757_SW_JUMP 8 -+#define PB44_PCF8757_LED_JUMP1 9 -+#define PB44_PCF8757_LED_JUMP2 10 -+#define PB44_PCF8757_TP24 11 -+#define PB44_PCF8757_TP25 12 -+#define PB44_PCF8757_TP26 13 -+#define PB44_PCF8757_TP27 14 -+#define PB44_PCF8757_TP28 15 ++#define EAP7660D_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define EAP7660D_KEYS_DEBOUNCE_INTERVAL (3 * EAP7660D_KEYS_POLL_INTERVAL) ++ ++#define EAP7660D_GPIO_DS4 7 ++#define EAP7660D_GPIO_DS5 2 ++#define EAP7660D_GPIO_DS7 0 ++#define EAP7660D_GPIO_DS8 4 ++#define EAP7660D_GPIO_SW1 3 ++#define EAP7660D_GPIO_SW3 8 ++#define EAP7660D_PHYMASK BIT(20) ++#define EAP7660D_BOARDCONFIG 0x1F7F0000 ++#define EAP7660D_GBIC_MAC_OFFSET 0x1000 ++#define EAP7660D_WMAC0_MAC_OFFSET 0x1010 ++#define EAP7660D_WMAC1_MAC_OFFSET 0x1016 ++#define EAP7660D_WMAC0_CALDATA_OFFSET 0x2000 ++#define EAP7660D_WMAC1_CALDATA_OFFSET 0x3000 ++ ++static struct ath5k_platform_data eap7660d_wmac0_data; ++static struct ath5k_platform_data eap7660d_wmac1_data; ++static char eap7660d_wmac0_mac[6]; ++static char eap7660d_wmac1_mac[6]; ++static u16 eap7660d_wmac0_eeprom[ATH5K_PLAT_EEP_MAX_WORDS]; ++static u16 eap7660d_wmac1_eeprom[ATH5K_PLAT_EEP_MAX_WORDS]; ++ ++#ifdef CONFIG_PCI ++static struct ar71xx_pci_irq eap7660d_pci_irqs[] __initdata = { ++ { ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, ++ }, { ++ .slot = 1, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV1, ++ } ++}; + -+#define PB44_GPIO_I2C_SCL 0 -+#define PB44_GPIO_I2C_SDA 1 ++static int eap7660d_pci_plat_dev_init(struct pci_dev *dev) ++{ ++ switch (PCI_SLOT(dev->devfn)) { ++ case 17: ++ dev->dev.platform_data = &eap7660d_wmac0_data; ++ break; + -+#define PB44_GPIO_EXP_BASE 16 -+#define PB44_GPIO_VSC7395_CS (PB44_GPIO_EXP_BASE + PB44_PCF8757_VSC7395_CS) -+#define PB44_GPIO_SW_RESET (PB44_GPIO_EXP_BASE + PB44_PCF8757_SW_RESET) -+#define PB44_GPIO_SW_JUMP (PB44_GPIO_EXP_BASE + PB44_PCF8757_SW_JUMP) -+#define PB44_GPIO_LED_JUMP1 (PB44_GPIO_EXP_BASE + PB44_PCF8757_LED_JUMP1) -+#define PB44_GPIO_LED_JUMP2 (PB44_GPIO_EXP_BASE + PB44_PCF8757_LED_JUMP2) ++ case 18: ++ dev->dev.platform_data = &eap7660d_wmac1_data; ++ break; ++ } + -+static struct i2c_gpio_platform_data pb44_i2c_gpio_data = { -+ .sda_pin = PB44_GPIO_I2C_SDA, -+ .scl_pin = PB44_GPIO_I2C_SCL, -+}; ++ return 0; ++} + -+static struct platform_device pb44_i2c_gpio_device = { -+ .name = "i2c-gpio", -+ .id = 0, -+ .dev = { -+ .platform_data = &pb44_i2c_gpio_data, ++void __init eap7660d_pci_init(u8 *cal_data0, u8 *mac_addr0, ++ u8 *cal_data1, u8 *mac_addr1) ++{ ++ if (cal_data0 && *cal_data0 == 0xa55a) { ++ memcpy(eap7660d_wmac0_eeprom, cal_data0, ++ ATH5K_PLAT_EEP_MAX_WORDS); ++ eap7660d_wmac0_data.eeprom_data = eap7660d_wmac0_eeprom; + } -+}; + -+static struct pcf857x_platform_data pb44_pcf857x_data = { -+ .gpio_base = PB44_GPIO_EXP_BASE, -+}; ++ if (cal_data1 && *cal_data1 == 0xa55a) { ++ memcpy(eap7660d_wmac1_eeprom, cal_data1, ++ ATH5K_PLAT_EEP_MAX_WORDS); ++ eap7660d_wmac1_data.eeprom_data = eap7660d_wmac1_eeprom; ++ } + -+static struct i2c_board_info pb44_i2c_board_info[] __initdata = { ++ if (mac_addr0) { ++ memcpy(eap7660d_wmac0_mac, mac_addr0, ++ sizeof(eap7660d_wmac0_mac)); ++ eap7660d_wmac0_data.macaddr = eap7660d_wmac0_mac; ++ } ++ ++ if (mac_addr1) { ++ memcpy(eap7660d_wmac1_mac, mac_addr1, ++ sizeof(eap7660d_wmac1_mac)); ++ eap7660d_wmac1_data.macaddr = eap7660d_wmac1_mac; ++ } ++ ++ ar71xx_pci_plat_dev_init = eap7660d_pci_plat_dev_init; ++ ar71xx_pci_init(ARRAY_SIZE(eap7660d_pci_irqs), eap7660d_pci_irqs); ++} ++#else ++static inline void eap7660d_pci_init(u8 *cal_data0, u8 *mac_addr0, ++ u8 *cal_data1, u8 *mac_addr1) ++{ ++} ++#endif /* CONFIG_PCI */ ++ ++static struct gpio_led eap7660d_leds_gpio[] __initdata = { + { -+ I2C_BOARD_INFO("pcf8575", 0x20), -+ .platform_data = &pb44_pcf857x_data, ++ .name = "eap7660d:green:ds8", ++ .gpio = EAP7660D_GPIO_DS8, ++ .active_low = 0, + }, -+}; -+ -+static struct gpio_led pb44_leds_gpio[] __initdata = { + { -+ .name = "pb44:amber:jump1", -+ .gpio = PB44_GPIO_LED_JUMP1, -+ .active_low = 1, -+ }, { -+ .name = "pb44:green:jump2", -+ .gpio = PB44_GPIO_LED_JUMP2, -+ .active_low = 1, ++ .name = "eap7660d:green:ds5", ++ .gpio = EAP7660D_GPIO_DS5, ++ .active_low = 0, ++ }, ++ { ++ .name = "eap7660d:green:ds7", ++ .gpio = EAP7660D_GPIO_DS7, ++ .active_low = 0, + }, ++ { ++ .name = "eap7660d:green:ds4", ++ .gpio = EAP7660D_GPIO_DS4, ++ .active_low = 0, ++ } +}; + -+static struct gpio_button pb44_gpio_buttons[] __initdata = { ++static struct gpio_keys_button eap7660d_gpio_keys[] __initdata = { + { -+ .desc = "soft_reset", ++ .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = PB44_GPIO_SW_RESET, ++ .debounce_interval = EAP7660D_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = EAP7660D_GPIO_SW1, + .active_low = 1, -+ } , { -+ .desc = "jumpstart", ++ }, ++ { ++ .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = PB44_GPIO_SW_JUMP, ++ .debounce_interval = EAP7660D_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = EAP7660D_GPIO_SW3, + .active_low = 1, + } +}; + -+static void pb44_vsc7395_reset(void) ++static void __init eap7660d_setup(void) +{ -+ ar71xx_device_stop(RESET_MODULE_GE1_PHY); -+ udelay(10); -+ ar71xx_device_start(RESET_MODULE_GE1_PHY); -+ mdelay(50); -+} ++ u8 *boardconfig = (u8 *) KSEG1ADDR(EAP7660D_BOARDCONFIG); + -+static struct vsc7385_platform_data pb44_vsc7395_data = { -+ .reset = pb44_vsc7395_reset, -+ .ucode_name = "vsc7395_ucode_pb44.bin", -+ .mac_cfg = { -+ .tx_ipg = 6, -+ .bit2 = 1, -+ .clk_sel = 0, -+ }, -+}; ++ ar71xx_add_device_mdio(~EAP7660D_PHYMASK); + -+static struct spi_board_info pb44_spi_info[] = { ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ++ boardconfig + EAP7660D_GBIC_MAC_OFFSET, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = EAP7660D_PHYMASK; ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_m25p80(NULL); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(eap7660d_leds_gpio), ++ eap7660d_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, EAP7660D_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(eap7660d_gpio_keys), ++ eap7660d_gpio_keys); ++ eap7660d_pci_init(boardconfig + EAP7660D_WMAC0_CALDATA_OFFSET, ++ boardconfig + EAP7660D_WMAC0_MAC_OFFSET, ++ boardconfig + EAP7660D_WMAC1_CALDATA_OFFSET, ++ boardconfig + EAP7660D_WMAC1_MAC_OFFSET); ++}; ++ ++MIPS_MACHINE(AR71XX_MACH_EAP7660D, "EAP7660D", "Senao EAP7660D", ++ eap7660d_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ja76pf.c linux-2.6.39/arch/mips/ar71xx/mach-ja76pf.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ja76pf.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ja76pf.c 2011-08-24 02:41:55.517989552 +0200 +@@ -0,0 +1,102 @@ ++/* ++ * jjPlus JA76PF board support ++ */ ++ ++#include ++#include ++#include ++#include ++ ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-gpio-buttons.h" ++#include "dev-pb42-pci.h" ++#include "dev-usb.h" ++#include "dev-leds-gpio.h" ++ ++#define JA76PF_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define JA76PF_KEYS_DEBOUNCE_INTERVAL (3 * JA76PF_KEYS_POLL_INTERVAL) ++ ++#define JA76PF_GPIO_I2C_SCL 0 ++#define JA76PF_GPIO_I2C_SDA 1 ++#define JA76PF_GPIO_LED_1 5 ++#define JA76PF_GPIO_LED_2 4 ++#define JA76PF_GPIO_LED_3 3 ++#define JA76PF_GPIO_BTN_RESET 11 ++ ++static struct gpio_led ja76pf_leds_gpio[] __initdata = { + { -+ .bus_num = 0, -+ .chip_select = 0, -+ .max_speed_hz = 25000000, -+ .modalias = "m25p80", ++ .name = "ja76pf:green:led1", ++ .gpio = JA76PF_GPIO_LED_1, ++ .active_low = 1, + }, { -+ .bus_num = 0, -+ .chip_select = 1, -+ .max_speed_hz = 25000000, -+ .modalias = "spi-vsc7385", -+ .platform_data = &pb44_vsc7395_data, -+ .controller_data = (void *) PB44_GPIO_VSC7395_CS, -+ }, ++ .name = "ja76pf:green:led2", ++ .gpio = JA76PF_GPIO_LED_2, ++ .active_low = 1, ++ }, { ++ .name = "ja76pf:green:led3", ++ .gpio = JA76PF_GPIO_LED_3, ++ .active_low = 1, ++ } +}; + -+static struct resource pb44_spi_resources[] = { -+ [0] = { -+ .start = AR71XX_SPI_BASE, -+ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, -+ .flags = IORESOURCE_MEM, -+ }, ++static struct gpio_keys_button ja76pf_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = JA76PF_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = JA76PF_GPIO_BTN_RESET, ++ .active_low = 1, ++ } +}; + -+static struct ar71xx_spi_platform_data pb44_spi_data = { -+ .bus_num = 0, -+ .num_chipselect = 2, ++static struct i2c_gpio_platform_data ja76pf_i2c_gpio_data = { ++ .sda_pin = JA76PF_GPIO_I2C_SDA, ++ .scl_pin = JA76PF_GPIO_I2C_SCL, +}; + -+static struct platform_device pb44_spi_device = { -+ .name = "pb44-spi", -+ .id = -1, -+ .resource = pb44_spi_resources, -+ .num_resources = ARRAY_SIZE(pb44_spi_resources), ++static struct platform_device ja76pf_i2c_gpio_device = { ++ .name = "i2c-gpio", ++ .id = 0, + .dev = { -+ .platform_data = &pb44_spi_data, -+ }, ++ .platform_data = &ja76pf_i2c_gpio_data, ++ } +}; + -+#define PB44_WAN_PHYMASK BIT(0) -+#define PB44_LAN_PHYMASK 0 -+#define PB44_MDIO_PHYMASK (PB44_LAN_PHYMASK | PB44_WAN_PHYMASK) ++#define JA76PF_WAN_PHYMASK (1 << 4) ++#define JA76PF_LAN_PHYMASK ((1 << 0) | (1 << 1) | (1 << 2) | (1 < 3)) ++#define JA76PF_MDIO_PHYMASK (JA76PF_LAN_PHYMASK | JA76PF_WAN_PHYMASK) + -+static void __init pb44_init(void) ++static void __init ja76pf_init(void) +{ -+ ar71xx_add_device_mdio(~PB44_MDIO_PHYMASK); ++ ar71xx_add_device_m25p80(NULL); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.phy_mask = PB44_WAN_PHYMASK; ++ ar71xx_add_device_mdio(~JA76PF_MDIO_PHYMASK); + -+ ar71xx_add_device_eth(0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = JA76PF_LAN_PHYMASK; + + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = JA76PF_WAN_PHYMASK; + ar71xx_eth1_data.speed = SPEED_1000; + ar71xx_eth1_data.duplex = DUPLEX_FULL; -+ ar71xx_eth1_pll_data.pll_1000 = 0x110000; + ++ ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_usb(); -+ -+ pb42_pci_init(); -+ -+ i2c_register_board_info(0, pb44_i2c_board_info, -+ ARRAY_SIZE(pb44_i2c_board_info)); -+ -+ platform_device_register(&pb44_i2c_gpio_device); ++ platform_device_register(&ja76pf_i2c_gpio_device); + -+ spi_register_board_info(pb44_spi_info, ARRAY_SIZE(pb44_spi_info)); -+ platform_device_register(&pb44_spi_device); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ja76pf_leds_gpio), ++ ja76pf_leds_gpio); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(pb44_leds_gpio), -+ pb44_leds_gpio); ++ ar71xx_register_gpio_keys_polled(-1, JA76PF_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ja76pf_gpio_keys), ++ ja76pf_gpio_keys); + -+ ar71xx_add_device_gpio_buttons(-1, 20, ARRAY_SIZE(pb44_gpio_buttons), -+ pb44_gpio_buttons); ++ ar71xx_add_device_usb(); ++ pb42_pci_init(); +} + -+MIPS_MACHINE(AR71XX_MACH_PB44, "PB44", "Atheros PB44", pb44_init); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb92.c linux-2.6.39/arch/mips/ar71xx/mach-pb92.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb92.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-pb92.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,109 @@ ++MIPS_MACHINE(AR71XX_MACH_JA76PF, "JA76PF", "jjPlus JA76PF", ja76pf_init); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-jwap003.c linux-2.6.39/arch/mips/ar71xx/mach-jwap003.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-jwap003.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-jwap003.c 2011-08-24 02:41:55.517989552 +0200 +@@ -0,0 +1,83 @@ +/* -+ * Atheros PB92 board support -+ * -+ * Copyright (C) 2010 Felix Fietkau -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * jjPlus JWAP003 board support + * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. + */ + -+#include -+#include +#include ++#include ++#include ++#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" +#include "dev-gpio-buttons.h" -+#include "dev-pb9x-pci.h" ++#include "dev-pb42-pci.h" +#include "dev-usb.h" + -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition pb92_partitions[] = { ++#define JWAP003_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define JWAP003_KEYS_DEBOUNCE_INTERVAL (3 * JWAP003_KEYS_POLL_INTERVAL) ++ ++#define JWAP003_GPIO_WPS 11 ++#define JWAP003_GPIO_I2C_SCL 0 ++#define JWAP003_GPIO_I2C_SDA 1 ++ ++static struct gpio_keys_button jwap003_gpio_keys[] __initdata = { + { -+ .name = "u-boot", -+ .offset = 0, -+ .size = 0x040000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "u-boot-env", -+ .offset = 0x040000, -+ .size = 0x010000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x050000, -+ .size = 0x2b0000, -+ } , { -+ .name = "uImage", -+ .offset = 0x300000, -+ .size = 0x0e0000, -+ } , { -+ .name = "ART", -+ .offset = 0x3e0000, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = JWAP003_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = JWAP003_GPIO_WPS, ++ .active_low = 1, + } +}; -+#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data pb92_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = pb92_partitions, -+ .nr_parts = ARRAY_SIZE(pb92_partitions), -+#endif ++static struct i2c_gpio_platform_data jwap003_i2c_gpio_data = { ++ .sda_pin = JWAP003_GPIO_I2C_SDA, ++ .scl_pin = JWAP003_GPIO_I2C_SCL, +}; + -+ -+#define PB92_BUTTONS_POLL_INTERVAL 20 -+ -+#define PB92_GPIO_BTN_SW4 8 -+#define PB92_GPIO_BTN_SW5 3 -+ -+static struct gpio_button pb92_gpio_buttons[] __initdata = { -+ { -+ .desc = "sw4", -+ .type = EV_KEY, -+ .code = BTN_0, -+ .threshold = 3, -+ .gpio = PB92_GPIO_BTN_SW4, -+ .active_low = 1, -+ } , { -+ .desc = "sw5", -+ .type = EV_KEY, -+ .code = BTN_1, -+ .threshold = 3, -+ .gpio = PB92_GPIO_BTN_SW5, -+ .active_low = 1, ++static struct platform_device jwap003_i2c_gpio_device = { ++ .name = "i2c-gpio", ++ .id = 0, ++ .dev = { ++ .platform_data = &jwap003_i2c_gpio_data, + } +}; + -+static void __init pb92_init(void) ++#define JWAP003_WAN_PHYMASK BIT(0) ++#define JWAP003_LAN_PHYMASK BIT(4) ++ ++static void __init jwap003_init(void) +{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1fff0000); ++ ar71xx_add_device_m25p80(NULL); + -+ ar71xx_set_mac_base(mac); -+ ar71xx_add_device_m25p80(&pb92_flash_data); ++ ar71xx_add_device_mdio(0x0); + -+ ar71xx_add_device_mdio(~0); + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.phy_mask = JWAP003_WAN_PHYMASK; ++ ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.has_ar8216 = 1; + + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.phy_mask = JWAP003_LAN_PHYMASK; ++ ar71xx_eth1_data.speed = SPEED_100; + ar71xx_eth1_data.duplex = DUPLEX_FULL; + + ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_gpio_buttons(-1, PB92_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(pb92_gpio_buttons), -+ pb92_gpio_buttons); ++ platform_device_register(&jwap003_i2c_gpio_device); + -+ pb9x_pci_init(); ++ ar71xx_add_device_usb(); ++ ++ ar71xx_register_gpio_keys_polled(-1, JWAP003_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(jwap003_gpio_keys), ++ jwap003_gpio_keys); ++ ++ pb42_pci_init(); +} + -+MIPS_MACHINE(AR71XX_MACH_PB92, "PB92", "Atheros PB92", pb92_init); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-rb4xx.c linux-2.6.39/arch/mips/ar71xx/mach-rb4xx.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-rb4xx.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-rb4xx.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,290 @@ ++MIPS_MACHINE(AR71XX_MACH_JWAP003, "JWAP003", "jjPlus JWAP003", jwap003_init); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w04nu.c linux-2.6.39/arch/mips/ar71xx/mach-mzk-w04nu.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w04nu.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-mzk-w04nu.c 2011-08-24 02:41:55.517989552 +0200 +@@ -0,0 +1,166 @@ +/* -+ * MikroTik RouterBOARD 4xx series support ++ * Planex MZK-W04NU board support + * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include -+#include -+#include ++#include ++#include + +#include -+#include + +#include "machtype.h" +#include "devices.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "dev-m25p80.h" +#include "dev-usb.h" + -+#define RB4XX_GPIO_USER_LED 4 -+#define RB4XX_GPIO_RESET_SWITCH 7 -+ -+#define RB4XX_BUTTONS_POLL_INTERVAL 20 -+ -+static struct gpio_led rb4xx_leds_gpio[] __initdata = { -+ { -+ .name = "rb4xx:yellow:user", -+ .gpio = RB4XX_GPIO_USER_LED, -+ .active_low = 0, -+ }, -+}; ++#define MZK_W04NU_GPIO_LED_USB 0 ++#define MZK_W04NU_GPIO_LED_STATUS 1 ++#define MZK_W04NU_GPIO_LED_WPS 3 ++#define MZK_W04NU_GPIO_LED_WLAN 6 ++#define MZK_W04NU_GPIO_LED_AP 15 ++#define MZK_W04NU_GPIO_LED_ROUTER 16 + -+static struct gpio_button rb4xx_gpio_buttons[] __initdata = { -+ { -+ .desc = "reset_switch", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = RB4XX_GPIO_RESET_SWITCH, -+ .active_low = 1, -+ } -+}; ++#define MZK_W04NU_GPIO_BTN_APROUTER 5 ++#define MZK_W04NU_GPIO_BTN_WPS 12 ++#define MZK_W04NU_GPIO_BTN_RESET 21 + -+static struct platform_device rb4xx_nand_device = { -+ .name = "rb4xx-nand", -+ .id = -1, -+}; ++#define MZK_W04NU_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define MZK_W04NU_KEYS_DEBOUNCE_INTERVAL (3 * MZK_W04NU_KEYS_POLL_INTERVAL) + -+static struct ar71xx_pci_irq rb4xx_pci_irqs[] __initdata = { ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition mzk_w04nu_partitions[] = { + { -+ .slot = 0, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV2, ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, + }, { -+ .slot = 1, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV0, ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, + }, { -+ .slot = 1, -+ .pin = 2, -+ .irq = AR71XX_PCI_IRQ_DEV1, ++ .name = "kernel", ++ .offset = 0x050000, ++ .size = 0x160000, + }, { -+ .slot = 2, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV1, ++ .name = "rootfs", ++ .offset = 0x1b0000, ++ .size = 0x630000, + }, { -+ .slot = 3, -+ .pin = 1, -+ .irq = AR71XX_PCI_IRQ_DEV2, ++ .name = "art", ++ .offset = 0x7e0000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x050000, ++ .size = 0x790000, + } +}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#if 0 -+/* -+ * SPI device support is experimental -+ */ -+static struct flash_platform_data rb4xx_flash_data = { -+ .type = "pm25lv512", ++static struct flash_platform_data mzk_w04nu_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = mzk_w04nu_partitions, ++ .nr_parts = ARRAY_SIZE(mzk_w04nu_partitions), ++#endif +}; + -+static struct spi_board_info rb4xx_spi_info[] = { ++static struct gpio_led mzk_w04nu_leds_gpio[] __initdata = { + { -+ .bus_num = 0, -+ .chip_select = 0, -+ .max_speed_hz = 25000000, -+ .modalias = "m25p80", -+ .platform_data = &rb4xx_flash_data, ++ .name = "mzk-w04nu:green:status", ++ .gpio = MZK_W04NU_GPIO_LED_STATUS, ++ .active_low = 1, ++ }, { ++ .name = "mzk-w04nu:blue:wps", ++ .gpio = MZK_W04NU_GPIO_LED_WPS, ++ .active_low = 1, ++ }, { ++ .name = "mzk-w04nu:green:wlan", ++ .gpio = MZK_W04NU_GPIO_LED_WLAN, ++ .active_low = 1, ++ }, { ++ .name = "mzk-w04nu:green:usb", ++ .gpio = MZK_W04NU_GPIO_LED_USB, ++ .active_low = 1, ++ }, { ++ .name = "mzk-w04nu:green:ap", ++ .gpio = MZK_W04NU_GPIO_LED_AP, ++ .active_low = 1, ++ }, { ++ .name = "mzk-w04nu:green:router", ++ .gpio = MZK_W04NU_GPIO_LED_ROUTER, ++ .active_low = 1, + } +}; + -+static struct mmc_spi_platform_data rb433_mmc_data = { -+ .ocr_mask = MMC_VDD_32_33 | MMC_VDD_33_34, -+}; -+ -+static struct spi_board_info rb433_spi_info[] = { ++static struct gpio_keys_button mzk_w04nu_gpio_keys[] __initdata = { + { -+ .bus_num = 0, -+ .chip_select = 0, -+ .max_speed_hz = 25000000, -+ .modalias = "m25p80", -+ .platform_data = &rb433_flash_data, ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = MZK_W04NU_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W04NU_GPIO_BTN_RESET, ++ .active_low = 1, + }, { -+ .bus_num = 0, -+ .chip_select = 2, -+ .max_speed_hz = 25000000, -+ .modalias = "mmc_spi", -+ .platform_data = &rb433_mmc_data, -+ } -+}; -+ -+static u32 rb433_spi_get_ioc_base(u8 chip_select, int cs_high, int is_on) -+{ -+ u32 ret; -+ -+ if (is_on == AR71XX_SPI_CS_INACTIVE) { -+ ret = SPI_IOC_CS0 | SPI_IOC_CS1; -+ } else { -+ if (cs_high) { -+ ret = SPI_IOC_CS0 | SPI_IOC_CS1; -+ } else { -+ if ((chip_select ^ 2) == 0) -+ ret = SPI_IOC_CS1 ^ (SPI_IOC_CS0 | SPI_IOC_CS1); -+ else -+ ret = SPI_IOC_CS0 ^ (SPI_IOC_CS0 | SPI_IOC_CS1); -+ } ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = MZK_W04NU_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W04NU_GPIO_BTN_WPS, ++ .active_low = 1, ++ }, { ++ .desc = "aprouter", ++ .type = EV_KEY, ++ .code = BTN_2, ++ .debounce_interval = MZK_W04NU_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W04NU_GPIO_BTN_APROUTER, ++ .active_low = 0, + } -+ -+ return ret; -+} -+ -+struct ar71xx_spi_platform_data rb433_spi_data = { -+ .bus_num = 0, -+ .num_chipselect = 3, -+ .get_ioc_base = rb433_spi_get_ioc_base, +}; + -+static void rb4xx_add_device_spi(void) -+{ -+ ar71xx_add_device_spi(NULL, rb4xx_spi_info, ARRAY_SIZE(rb4xx_spi_info)); -+} -+ -+static void rb433_add_device_spi(void) -+{ -+ ar71xx_add_device_spi(&rb433_spi_data, rb433_spi_info, -+ ARRAY_SIZE(rb433_spi_info)); -+} -+#else -+static inline void rb4xx_add_device_spi(void) {} -+static inline void rb433_add_device_spi(void) {} -+#endif -+ -+static void __init rb4xx_generic_setup(void) -+{ -+ ar71xx_gpio_function_enable(AR71XX_GPIO_FUNC_SPI_CS1_EN | -+ AR71XX_GPIO_FUNC_SPI_CS2_EN); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(rb4xx_leds_gpio), -+ rb4xx_leds_gpio); -+ -+ ar71xx_add_device_gpio_buttons(-1, RB4XX_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(rb4xx_gpio_buttons), -+ rb4xx_gpio_buttons); -+ -+ platform_device_register(&rb4xx_nand_device); -+} -+ -+static void __init rb411_setup(void) -+{ -+ rb4xx_generic_setup(); -+ rb4xx_add_device_spi(); -+ -+ ar71xx_add_device_mdio(0xfffffffc); -+ -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = 0x00000003; -+ -+ ar71xx_add_device_eth(0); -+ -+ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_RB_411, "411", "MikroTik RouterBOARD 411/A/AH", -+ rb411_setup); -+ -+static void __init rb411u_setup(void) -+{ -+ rb411_setup(); -+ ar71xx_add_device_usb(); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_RB_411U, "411U", "MikroTik RouterBOARD 411U", -+ rb411u_setup); ++#define MZK_W04NU_WAN_PHYMASK BIT(4) ++#define MZK_W04NU_MDIO_MASK (~MZK_W04NU_WAN_PHYMASK) + -+static void __init rb433_setup(void) ++static void __init mzk_w04nu_setup(void) +{ -+ rb4xx_generic_setup(); -+ rb433_add_device_spi(); ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ ar71xx_add_device_mdio(0xffffffe9); ++ ar71xx_add_device_mdio(MZK_W04NU_MDIO_MASK); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, eeprom, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; + ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.has_ar8216 = 1; + ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, eeprom, 1); + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x00000010; ++ ar71xx_eth1_data.phy_mask = MZK_W04NU_WAN_PHYMASK; + -+ ar71xx_add_device_eth(1); + ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); -+} ++ ar71xx_add_device_m25p80(&mzk_w04nu_flash_data); + -+MIPS_MACHINE(AR71XX_MACH_RB_433, "433", "MikroTik RouterBOARD 433/AH", -+ rb433_setup); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(mzk_w04nu_leds_gpio), ++ mzk_w04nu_leds_gpio); + -+static void __init rb433u_setup(void) -+{ -+ rb433_setup(); ++ ar71xx_register_gpio_keys_polled(-1, MZK_W04NU_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(mzk_w04nu_gpio_keys), ++ mzk_w04nu_gpio_keys); + ar71xx_add_device_usb(); ++ ++ ar9xxx_add_device_wmac(eeprom, NULL); +} + -+MIPS_MACHINE(AR71XX_MACH_RB_433U, "433U", "MikroTik RouterBOARD 433UAH", -+ rb433u_setup); ++MIPS_MACHINE(AR71XX_MACH_MZK_W04NU, "MZK-W04NU", "Planex MZK-W04NU", ++ mzk_w04nu_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w300nh.c linux-2.6.39/arch/mips/ar71xx/mach-mzk-w300nh.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-mzk-w300nh.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-mzk-w300nh.c 2011-08-24 02:41:55.527982711 +0200 +@@ -0,0 +1,159 @@ ++/* ++ * Planex MZK-W300NH board support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+static void __init rb450_generic_setup(int gige) -+{ -+ rb4xx_generic_setup(); -+ rb4xx_add_device_spi(); ++#include ++#include + -+ ar71xx_add_device_mdio(0xffffffe0); ++#include + -+ ar71xx_eth0_data.phy_if_mode = (gige) ? PHY_INTERFACE_MODE_RGMII : PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = (gige) ? (1 << 0) : 0; -+ ar71xx_eth0_data.speed = (gige) ? SPEED_1000 : SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" + -+ ar71xx_eth1_data.phy_if_mode = (gige) ? PHY_INTERFACE_MODE_RGMII : PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x00000010; ++#define MZK_W300NH_GPIO_LED_STATUS 1 ++#define MZK_W300NH_GPIO_LED_WPS 3 ++#define MZK_W300NH_GPIO_LED_WLAN 6 ++#define MZK_W300NH_GPIO_LED_AP 15 ++#define MZK_W300NH_GPIO_LED_ROUTER 16 + -+ ar71xx_add_device_eth(1); -+ ar71xx_add_device_eth(0); -+} ++#define MZK_W300NH_GPIO_BTN_APROUTER 5 ++#define MZK_W300NH_GPIO_BTN_WPS 12 ++#define MZK_W300NH_GPIO_BTN_RESET 21 + -+static void __init rb450_setup(void) -+{ -+ rb450_generic_setup(0); -+} ++#define MZK_W300NH_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define MZK_W300NH_KEYS_DEBOUNCE_INTERVAL (3 * MZK_W300NH_KEYS_POLL_INTERVAL) + -+MIPS_MACHINE(AR71XX_MACH_RB_450, "450", "MikroTik RouterBOARD 450", -+ rb450_setup); -+ -+static void __init rb450g_setup(void) -+{ -+ rb450_generic_setup(1); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_RB_450G, "450G", "MikroTik RouterBOARD 450G", -+ rb450g_setup); -+ -+static void __init rb493_setup(void) -+{ -+ rb4xx_generic_setup(); -+ rb4xx_add_device_spi(); -+ -+ ar71xx_add_device_mdio(0x3fffff00); -+ -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x00000001; -+ -+ ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); -+ -+ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_RB_493, "493", "MikroTik RouterBOARD 493/AH", -+ rb493_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-rb750.c linux-2.6.39/arch/mips/ar71xx/mach-rb750.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-rb750.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-rb750.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,133 @@ -+/* -+ * MikroTik RouterBOARD 750 support -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include -+#include -+#include ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition mzk_w300nh_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, ++ }, { ++ .name = "kernel", ++ .offset = 0x050000, ++ .size = 0x160000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x1b0000, ++ .size = 0x630000, ++ }, { ++ .name = "art", ++ .offset = 0x7e0000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x050000, ++ .size = 0x790000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#include "machtype.h" -+#include "dev-ap91-eth.h" ++static struct flash_platform_data mzk_w300nh_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = mzk_w300nh_partitions, ++ .nr_parts = ARRAY_SIZE(mzk_w300nh_partitions), ++#endif ++}; + -+static struct rb750_led_data rb750_leds[] = { ++static struct gpio_led mzk_w300nh_leds_gpio[] __initdata = { + { -+ .name = "rb750:green:act", -+ .mask = RB750_LED_ACT, -+ .active_low = 1, -+ }, { -+ .name = "rb750:green:port1", -+ .mask = RB750_LED_PORT5, ++ .name = "mzk-w300nh:green:status", ++ .gpio = MZK_W300NH_GPIO_LED_STATUS, + .active_low = 1, + }, { -+ .name = "rb750:green:port2", -+ .mask = RB750_LED_PORT4, ++ .name = "mzk-w300nh:blue:wps", ++ .gpio = MZK_W300NH_GPIO_LED_WPS, + .active_low = 1, + }, { -+ .name = "rb750:green:port3", -+ .mask = RB750_LED_PORT3, ++ .name = "mzk-w300nh:green:wlan", ++ .gpio = MZK_W300NH_GPIO_LED_WLAN, + .active_low = 1, + }, { -+ .name = "rb750:green:port4", -+ .mask = RB750_LED_PORT2, ++ .name = "mzk-w300nh:green:ap", ++ .gpio = MZK_W300NH_GPIO_LED_AP, + .active_low = 1, + }, { -+ .name = "rb750:green:port5", -+ .mask = RB750_LED_PORT1, ++ .name = "mzk-w300nh:green:router", ++ .gpio = MZK_W300NH_GPIO_LED_ROUTER, + .active_low = 1, + } +}; + -+static struct rb750_led_platform_data rb750_leds_data = { -+ .num_leds = ARRAY_SIZE(rb750_leds), -+ .leds = rb750_leds, -+}; -+ -+static struct platform_device rb750_leds_device = { -+ .name = "leds-rb750", -+ .dev = { -+ .platform_data = &rb750_leds_data, ++static struct gpio_keys_button mzk_w300nh_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = MZK_W300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W300NH_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = MZK_W300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W300NH_GPIO_BTN_WPS, ++ .active_low = 1, ++ }, { ++ .desc = "aprouter", ++ .type = EV_KEY, ++ .code = BTN_2, ++ .debounce_interval = MZK_W300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = MZK_W300NH_GPIO_BTN_APROUTER, ++ .active_low = 0, + } +}; + -+static const char *rb750_port_names[AP91_ETH_NUM_PORT_NAMES] __initdata = { -+ "port5", -+ "port4", -+ "port3", -+ "port2", -+}; -+ -+static struct platform_device rb750_nand_device = { -+ .name = "rb750-nand", -+ .id = -1, -+}; ++#define MZK_W300NH_WAN_PHYMASK BIT(4) ++#define MZK_W300NH_MDIO_MASK (~MZK_W300NH_WAN_PHYMASK) + -+int rb750_latch_change(u32 mask_clr, u32 mask_set) ++static void __init mzk_w300nh_setup(void) +{ -+ static DEFINE_SPINLOCK(lock); -+ static u32 latch_set = RB750_LED_BITS | RB750_LVC573_LE; -+ static u32 latch_oe; -+ static u32 latch_clr; -+ unsigned long flags; -+ u32 t; -+ int ret = 0; -+ -+ spin_lock_irqsave(&lock, flags); -+ -+ if ((mask_clr & BIT(31)) != 0 && -+ (latch_set & RB750_LVC573_LE) == 0) { -+ goto unlock; -+ } -+ -+ latch_set = (latch_set | mask_set) & ~mask_clr; -+ latch_clr = (latch_clr | mask_clr) & ~mask_set; -+ -+ if (latch_oe == 0) -+ latch_oe = __raw_readl(ar71xx_gpio_base + GPIO_REG_OE); -+ -+ if (likely(latch_set & RB750_LVC573_LE)) { -+ void __iomem *base = ar71xx_gpio_base; ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ t = __raw_readl(base + GPIO_REG_OE); -+ t |= mask_clr | latch_oe | mask_set; ++ ar71xx_add_device_mdio(MZK_W300NH_MDIO_MASK); + -+ __raw_writel(t, base + GPIO_REG_OE); -+ __raw_writel(latch_clr, base + GPIO_REG_CLEAR); -+ __raw_writel(latch_set, base + GPIO_REG_SET); -+ } else if (mask_clr & RB750_LVC573_LE) { -+ void __iomem *base = ar71xx_gpio_base; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, eeprom, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.has_ar8216 = 1; + -+ latch_oe = __raw_readl(base + GPIO_REG_OE); -+ __raw_writel(RB750_LVC573_LE, base + GPIO_REG_CLEAR); -+ /* flush write */ -+ __raw_readl(base + GPIO_REG_CLEAR); -+ } ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, eeprom, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = MZK_W300NH_WAN_PHYMASK; + -+ ret = 1; ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ unlock: -+ spin_unlock_irqrestore(&lock, flags); -+ return ret; -+} -+EXPORT_SYMBOL_GPL(rb750_latch_change); ++ ar71xx_add_device_m25p80(&mzk_w300nh_flash_data); + -+static void __init rb750_setup(void) -+{ -+ ar71xx_gpio_function_disable(AR724X_GPIO_FUNC_ETH_SWITCH_LED0_EN | -+ AR724X_GPIO_FUNC_ETH_SWITCH_LED1_EN | -+ AR724X_GPIO_FUNC_ETH_SWITCH_LED2_EN | -+ AR724X_GPIO_FUNC_ETH_SWITCH_LED3_EN | -+ AR724X_GPIO_FUNC_ETH_SWITCH_LED4_EN); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(mzk_w300nh_leds_gpio), ++ mzk_w300nh_leds_gpio); + -+ ap91_eth_init(NULL, rb750_port_names); -+ platform_device_register(&rb750_leds_device); -+ platform_device_register(&rb750_nand_device); ++ ar71xx_register_gpio_keys_polled(-1, MZK_W300NH_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(mzk_w300nh_gpio_keys), ++ mzk_w300nh_gpio_keys); ++ ar9xxx_add_device_wmac(eeprom, NULL); +} + -+MIPS_MACHINE(AR71XX_MACH_RB_750, "750i", "MikroTik RouterBOARD 750", -+ rb750_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tew-632brp.c linux-2.6.39/arch/mips/ar71xx/mach-tew-632brp.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-tew-632brp.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-tew-632brp.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,149 @@ ++MIPS_MACHINE(AR71XX_MACH_MZK_W300NH, "MZK-W300NH", "Planex MZK-W300NH", ++ mzk_w300nh_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-nbg460n.c linux-2.6.39/arch/mips/ar71xx/mach-nbg460n.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-nbg460n.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-nbg460n.c 2011-08-24 02:41:55.537990605 +0200 +@@ -0,0 +1,225 @@ +/* -+ * TrendNET TEW-632BRP board support ++ * Zyxel NBG 460N/550N/550NH board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2010 Michael Kurz ++ * ++ * based on mach-tl-wr1043nd.c + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include +#include +#include ++#include ++#include ++ ++#include ++#include ++#include + +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "nvram.h" + -+#define TEW_632BRP_GPIO_LED_STATUS 1 -+#define TEW_632BRP_GPIO_LED_WPS 3 -+#define TEW_632BRP_GPIO_LED_WLAN 6 -+#define TEW_632BRP_GPIO_BTN_WPS 12 -+#define TEW_632BRP_GPIO_BTN_RESET 21 ++/* LEDs */ ++#define NBG460N_GPIO_LED_WPS 3 ++#define NBG460N_GPIO_LED_WAN 6 ++#define NBG460N_GPIO_LED_POWER 14 ++#define NBG460N_GPIO_LED_WLAN 15 ++ ++/* Buttons */ ++#define NBG460N_GPIO_BTN_WPS 12 ++#define NBG460N_GPIO_BTN_RESET 21 + -+#define TEW_632BRP_BUTTONS_POLL_INTERVAL 20 ++#define NBG460N_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define NBG460N_KEYS_DEBOUNCE_INTERVAL (3 * NBG460N_KEYS_POLL_INTERVAL) + -+#define TEW_632BRP_CONFIG_ADDR 0x1f020000 -+#define TEW_632BRP_CONFIG_SIZE 0x10000 ++/* RTC chip PCF8563 I2C interface */ ++#define NBG460N_GPIO_PCF8563_SDA 8 ++#define NBG460N_GPIO_PCF8563_SCK 7 ++ ++/* Switch configuration I2C interface */ ++#define NBG460N_GPIO_RTL8366_SDA 16 ++#define NBG460N_GPIO_RTL8366_SCK 18 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition tew_632brp_partitions[] = { ++static struct mtd_partition nbg460n_partitions[] = { + { -+ .name = "u-boot", ++ .name = "Bootbase", + .offset = 0, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "config", -+ .offset = 0x020000, + .size = 0x010000, -+ } , { -+ .name = "kernel", -+ .offset = 0x030000, -+ .size = 0x0d0000, -+ } , { ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "U-Boot Config", ++ .offset = 0x010000, ++ .size = 0x030000, ++ }, { ++ .name = "U-Boot", ++ .offset = 0x040000, ++ .size = 0x030000, ++ }, { ++ .name = "linux", ++ .offset = 0x070000, ++ .size = 0x0e0000, ++ }, { + .name = "rootfs", -+ .offset = 0x100000, -+ .size = 0x2f0000, -+ } , { -+ .name = "art", ++ .offset = 0x150000, ++ .size = 0x2a0000, ++ }, { ++ .name = "CalibData", + .offset = 0x3f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "firmware", -+ .offset = 0x030000, -+ .size = 0x3c0000, ++ .offset = 0x070000, ++ .size = 0x380000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data tew_632brp_flash_data = { ++static struct flash_platform_data nbg460n_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = tew_632brp_partitions, -+ .nr_parts = ARRAY_SIZE(tew_632brp_partitions), ++ .parts = nbg460n_partitions, ++ .nr_parts = ARRAY_SIZE(nbg460n_partitions), +#endif +}; + -+static struct gpio_led tew_632brp_leds_gpio[] __initdata = { ++static struct gpio_led nbg460n_leds_gpio[] __initdata = { + { -+ .name = "tew-632brp:green:status", -+ .gpio = TEW_632BRP_GPIO_LED_STATUS, -+ .active_low = 1, ++ .name = "nbg460n:green:power", ++ .gpio = NBG460N_GPIO_LED_POWER, ++ .active_low = 0, ++ .default_trigger = "default-on", + }, { -+ .name = "tew-632brp:blue:wps", -+ .gpio = TEW_632BRP_GPIO_LED_WPS, -+ .active_low = 1, ++ .name = "nbg460n:green:wps", ++ .gpio = NBG460N_GPIO_LED_WPS, ++ .active_low = 0, + }, { -+ .name = "tew-632brp:green:wlan", -+ .gpio = TEW_632BRP_GPIO_LED_WLAN, -+ .active_low = 1, ++ .name = "nbg460n:green:wlan", ++ .gpio = NBG460N_GPIO_LED_WLAN, ++ .active_low = 0, ++ }, { ++ /* Not really for controlling the LED, ++ when set low the LED blinks uncontrollable */ ++ .name = "nbg460n:green:wan", ++ .gpio = NBG460N_GPIO_LED_WAN, ++ .active_low = 0, + } +}; + -+static struct gpio_button tew_632brp_gpio_buttons[] __initdata = { ++static struct gpio_keys_button nbg460n_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = TEW_632BRP_GPIO_BTN_RESET, ++ .debounce_interval = NBG460N_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = NBG460N_GPIO_BTN_RESET, ++ .active_low = 1, + }, { + .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = TEW_632BRP_GPIO_BTN_WPS, ++ .debounce_interval = NBG460N_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = NBG460N_GPIO_BTN_WPS, ++ .active_low = 1, + } +}; + -+#define TEW_632BRP_LAN_PHYMASK BIT(0) -+#define TEW_632BRP_WAN_PHYMASK BIT(4) -+#define TEW_632BRP_MDIO_MASK (~(TEW_632BRP_LAN_PHYMASK | \ -+ TEW_632BRP_WAN_PHYMASK)) ++static struct i2c_gpio_platform_data nbg460n_i2c_device_platdata = { ++ .sda_pin = NBG460N_GPIO_PCF8563_SDA, ++ .scl_pin = NBG460N_GPIO_PCF8563_SCK, ++ .udelay = 10, ++}; + -+static void __init tew_632brp_setup(void) ++static struct platform_device nbg460n_i2c_device = { ++ .name = "i2c-gpio", ++ .id = -1, ++ .num_resources = 0, ++ .resource = NULL, ++ .dev = { ++ .platform_data = &nbg460n_i2c_device_platdata, ++ }, ++}; ++ ++static struct i2c_board_info nbg460n_i2c_devs[] __initdata = { ++ { ++ I2C_BOARD_INFO("pcf8563", 0x51), ++ }, ++}; ++ ++static void __devinit nbg460n_i2c_init(void) +{ -+ const char *config = (char *) KSEG1ADDR(TEW_632BRP_CONFIG_ADDR); -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ u8 mac[6]; -+ u8 *wlan_mac = NULL; ++ /* The gpio interface */ ++ platform_device_register(&nbg460n_i2c_device); ++ /* I2C devices */ ++ i2c_register_board_info(0, nbg460n_i2c_devs, ++ ARRAY_SIZE(nbg460n_i2c_devs)); ++} + -+ if (nvram_parse_mac_addr(config, TEW_632BRP_CONFIG_SIZE, -+ "lan_mac=", mac) == 0) { -+ ar71xx_set_mac_base(mac); -+ wlan_mac = mac; ++ ++static struct rtl8366_platform_data nbg460n_rtl8366s_data = { ++ .gpio_sda = NBG460N_GPIO_RTL8366_SDA, ++ .gpio_sck = NBG460N_GPIO_RTL8366_SCK, ++}; ++ ++static struct platform_device nbg460n_rtl8366s_device = { ++ .name = RTL8366S_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &nbg460n_rtl8366s_data, + } ++}; + -+ ar71xx_add_device_mdio(TEW_632BRP_MDIO_MASK); ++static void __init nbg460n_setup(void) ++{ ++ /* end of bootloader sector contains mac address */ ++ u8 *mac = (u8 *) KSEG1ADDR(0x1fc0fff8); ++ /* last sector contains wlan calib data */ ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.phy_mask = TEW_632BRP_LAN_PHYMASK; ++ /* LAN Port */ ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.mii_bus_dev = &nbg460n_rtl8366s_device.dev; ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = TEW_632BRP_WAN_PHYMASK; ++ /* WAN Port */ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ ar71xx_eth1_data.mii_bus_dev = &nbg460n_rtl8366s_device.dev; ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + + ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_m25p80(&tew_632brp_flash_data); ++ /* register the switch phy */ ++ platform_device_register(&nbg460n_rtl8366s_device); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tew_632brp_leds_gpio), -+ tew_632brp_leds_gpio); ++ /* register flash */ ++ ar71xx_add_device_m25p80(&nbg460n_flash_data); ++ ++ ar9xxx_add_device_wmac(eeprom, mac); ++ ++ /* register RTC chip */ ++ nbg460n_i2c_init(); + -+ ar71xx_add_device_gpio_buttons(-1, TEW_632BRP_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(tew_632brp_gpio_buttons), -+ tew_632brp_gpio_buttons); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(nbg460n_leds_gpio), ++ nbg460n_leds_gpio); + -+ ar913x_add_device_wmac(eeprom, wlan_mac); ++ ar71xx_register_gpio_keys_polled(-1, NBG460N_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(nbg460n_gpio_keys), ++ nbg460n_gpio_keys); +} + -+MIPS_MACHINE(AR71XX_MACH_TEW_632BRP, "TEW-632BRP", "TRENDnet TEW-632BRP", -+ tew_632brp_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr1043nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr1043nd.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr1043nd.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr1043nd.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,156 @@ ++MIPS_MACHINE(AR71XX_MACH_NBG460N, "NBG460N", "Zyxel NBG460N/550N/550NH", ++ nbg460n_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb42.c linux-2.6.39/arch/mips/ar71xx/mach-pb42.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb42.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-pb42.c 2011-08-24 02:41:55.537990605 +0200 +@@ -0,0 +1,74 @@ +/* -+ * TP-LINK TL-WR1043ND board support ++ * Atheros PB42 board support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include +#include + +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" +#include "dev-gpio-buttons.h" -+#include "dev-leds-gpio.h" ++#include "dev-pb42-pci.h" +#include "dev-usb.h" + -+#define TL_WR1043ND_GPIO_LED_USB 1 -+#define TL_WR1043ND_GPIO_LED_SYSTEM 2 -+#define TL_WR1043ND_GPIO_LED_QSS 5 -+#define TL_WR1043ND_GPIO_LED_WLAN 9 -+ -+#define TL_WR1043ND_GPIO_BTN_RESET 3 -+#define TL_WR1043ND_GPIO_BTN_QSS 7 -+ -+#define TL_WR1043ND_GPIO_RTL8366_SDA 18 -+#define TL_WR1043ND_GPIO_RTL8366_SCK 19 -+ -+#define TL_WR1043ND_BUTTONS_POLL_INTERVAL 20 -+ -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition tl_wr1043nd_partitions[] = { -+ { -+ .name = "u-boot", -+ .offset = 0, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "kernel", -+ .offset = 0x020000, -+ .size = 0x140000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x160000, -+ .size = 0x690000, -+ } , { -+ .name = "art", -+ .offset = 0x7f0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x020000, -+ .size = 0x7d0000, -+ } -+}; -+#endif /* CONFIG_MTD_PARTITIONS */ -+ -+static struct flash_platform_data tl_wr1043nd_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = tl_wr1043nd_partitions, -+ .nr_parts = ARRAY_SIZE(tl_wr1043nd_partitions), -+#endif -+}; ++#define PB42_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define PB42_KEYS_DEBOUNCE_INTERVAL (3 * PB42_KEYS_POLL_INTERVAL) + -+static struct gpio_led tl_wr1043nd_leds_gpio[] __initdata = { -+ { -+ .name = "tl-wr1043nd:green:usb", -+ .gpio = TL_WR1043ND_GPIO_LED_USB, -+ .active_low = 1, -+ }, { -+ .name = "tl-wr1043nd:green:system", -+ .gpio = TL_WR1043ND_GPIO_LED_SYSTEM, -+ .active_low = 1, -+ }, { -+ .name = "tl-wr1043nd:green:qss", -+ .gpio = TL_WR1043ND_GPIO_LED_QSS, -+ .active_low = 0, -+ }, { -+ .name = "tl-wr1043nd:green:wlan", -+ .gpio = TL_WR1043ND_GPIO_LED_WLAN, -+ .active_low = 1, -+ } -+}; ++#define PB42_GPIO_BTN_SW4 8 ++#define PB42_GPIO_BTN_SW5 3 + -+static struct gpio_button tl_wr1043nd_gpio_buttons[] __initdata = { ++static struct gpio_keys_button pb42_gpio_keys[] __initdata = { + { -+ .desc = "reset", ++ .desc = "sw4", + .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = TL_WR1043ND_GPIO_BTN_RESET, ++ .code = BTN_0, ++ .debounce_interval = PB42_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB42_GPIO_BTN_SW4, + .active_low = 1, + }, { -+ .desc = "qss", ++ .desc = "sw5", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = TL_WR1043ND_GPIO_BTN_QSS, ++ .code = BTN_1, ++ .debounce_interval = PB42_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB42_GPIO_BTN_SW5, + .active_low = 1, + } +}; + -+static struct rtl8366rb_platform_data tl_wr1043nd_rtl8366rb_data = { -+ .gpio_sda = TL_WR1043ND_GPIO_RTL8366_SDA, -+ .gpio_sck = TL_WR1043ND_GPIO_RTL8366_SCK, -+}; -+ -+static struct platform_device tl_wr1043nd_rtl8366rb_device = { -+ .name = RTL8366RB_DRIVER_NAME, -+ .id = -1, -+ .dev = { -+ .platform_data = &tl_wr1043nd_rtl8366rb_data, -+ } -+}; ++#define PB42_WAN_PHYMASK BIT(20) ++#define PB42_LAN_PHYMASK (BIT(16) | BIT(17) | BIT(18) | BIT(19)) ++#define PB42_MDIO_PHYMASK (PB42_LAN_PHYMASK | PB42_WAN_PHYMASK) + -+static void __init tl_wr1043nd_setup(void) ++static void __init pb42_init(void) +{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ ar71xx_add_device_m25p80(NULL); + -+ ar71xx_set_mac_base(mac); ++ ar71xx_add_device_mdio(~PB42_MDIO_PHYMASK); + -+ ar71xx_eth0_data.mii_bus_dev = &tl_wr1043nd_rtl8366rb_device.dev; -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.speed = SPEED_1000; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_pll_data.pll_1000 = 0x1a000000; -+ -+ ar71xx_add_device_eth(0); -+ -+ ar71xx_add_device_usb(); -+ -+ ar71xx_add_device_m25p80(&tl_wr1043nd_flash_data); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = PB42_WAN_PHYMASK; + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr1043nd_leds_gpio), -+ tl_wr1043nd_leds_gpio); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_100; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ platform_device_register(&tl_wr1043nd_rtl8366rb_device); ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ ar71xx_add_device_gpio_buttons(-1, TL_WR1043ND_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(tl_wr1043nd_gpio_buttons), -+ tl_wr1043nd_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, PB42_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(pb42_gpio_keys), ++ pb42_gpio_keys); + -+ ar913x_add_device_wmac(eeprom, mac); ++ pb42_pci_init(); +} + -+MIPS_MACHINE(AR71XX_MACH_TL_WR1043ND, "TL-WR1043ND", "TP-LINK TL-WR1043ND", -+ tl_wr1043nd_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr741nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr741nd.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr741nd.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr741nd.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,115 @@ ++MIPS_MACHINE(AR71XX_MACH_PB42, "PB42", "Atheros PB42", pb42_init); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb44.c linux-2.6.39/arch/mips/ar71xx/mach-pb44.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb44.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-pb44.c 2011-08-24 02:41:55.537990605 +0200 +@@ -0,0 +1,213 @@ +/* -+ * TP-LINK TL-WR741ND board support ++ * Atheros PB44 board support + * -+ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include + +#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-m25p80.h" -+#include "dev-ap91-eth.h" -+#include "dev-ap91-pci.h" ++#include "dev-pb42-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define TL_WR741ND_GPIO_LED_QSS 0 -+#define TL_WR741ND_GPIO_LED_SYSTEM 1 ++#define PB44_PCF8757_VSC7395_CS 0 ++#define PB44_PCF8757_STEREO_CS 1 ++#define PB44_PCF8757_SLIC_CS0 2 ++#define PB44_PCF8757_SLIC_TEST 3 ++#define PB44_PCF8757_SLIC_INT0 4 ++#define PB44_PCF8757_SLIC_INT1 5 ++#define PB44_PCF8757_SW_RESET 6 ++#define PB44_PCF8757_SW_JUMP 8 ++#define PB44_PCF8757_LED_JUMP1 9 ++#define PB44_PCF8757_LED_JUMP2 10 ++#define PB44_PCF8757_TP24 11 ++#define PB44_PCF8757_TP25 12 ++#define PB44_PCF8757_TP26 13 ++#define PB44_PCF8757_TP27 14 ++#define PB44_PCF8757_TP28 15 + -+#define TL_WR741ND_GPIO_BTN_RESET 11 -+#define TL_WR741ND_GPIO_BTN_QSS 12 ++#define PB44_GPIO_I2C_SCL 0 ++#define PB44_GPIO_I2C_SDA 1 + -+#define TL_WR741ND_BUTTONS_POLL_INTERVAL 20 ++#define PB44_GPIO_EXP_BASE 16 ++#define PB44_GPIO_VSC7395_CS (PB44_GPIO_EXP_BASE + PB44_PCF8757_VSC7395_CS) ++#define PB44_GPIO_SW_RESET (PB44_GPIO_EXP_BASE + PB44_PCF8757_SW_RESET) ++#define PB44_GPIO_SW_JUMP (PB44_GPIO_EXP_BASE + PB44_PCF8757_SW_JUMP) ++#define PB44_GPIO_LED_JUMP1 (PB44_GPIO_EXP_BASE + PB44_PCF8757_LED_JUMP1) ++#define PB44_GPIO_LED_JUMP2 (PB44_GPIO_EXP_BASE + PB44_PCF8757_LED_JUMP2) + -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition tl_wr741nd_partitions[] = { -+ { -+ .name = "u-boot", -+ .offset = 0, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "kernel", -+ .offset = 0x020000, -+ .size = 0x140000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x160000, -+ .size = 0x290000, -+ } , { -+ .name = "art", -+ .offset = 0x3f0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x020000, -+ .size = 0x3d0000, ++#define PB44_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define PB44_KEYS_DEBOUNCE_INTERVAL (3 * PB44_KEYS_POLL_INTERVAL) ++ ++static struct i2c_gpio_platform_data pb44_i2c_gpio_data = { ++ .sda_pin = PB44_GPIO_I2C_SDA, ++ .scl_pin = PB44_GPIO_I2C_SCL, ++}; ++ ++static struct platform_device pb44_i2c_gpio_device = { ++ .name = "i2c-gpio", ++ .id = 0, ++ .dev = { ++ .platform_data = &pb44_i2c_gpio_data, + } +}; -+#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data tl_wr741nd_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = tl_wr741nd_partitions, -+ .nr_parts = ARRAY_SIZE(tl_wr741nd_partitions), -+#endif ++static struct pcf857x_platform_data pb44_pcf857x_data = { ++ .gpio_base = PB44_GPIO_EXP_BASE, +}; + -+static struct gpio_led tl_wr741nd_leds_gpio[] __initdata = { ++static struct i2c_board_info pb44_i2c_board_info[] __initdata = { + { -+ .name = "tl-wr741nd:green:system", -+ .gpio = TL_WR741ND_GPIO_LED_SYSTEM, ++ I2C_BOARD_INFO("pcf8575", 0x20), ++ .platform_data = &pb44_pcf857x_data, ++ }, ++}; ++ ++static struct gpio_led pb44_leds_gpio[] __initdata = { ++ { ++ .name = "pb44:amber:jump1", ++ .gpio = PB44_GPIO_LED_JUMP1, + .active_low = 1, + }, { -+ .name = "tl-wr741nd:green:qss", -+ .gpio = TL_WR741ND_GPIO_LED_QSS, ++ .name = "pb44:green:jump2", ++ .gpio = PB44_GPIO_LED_JUMP2, + .active_low = 1, -+ } ++ }, +}; + -+static struct gpio_button tl_wr741nd_gpio_buttons[] __initdata = { ++static struct gpio_keys_button pb44_gpio_keys[] __initdata = { + { -+ .desc = "reset", ++ .desc = "soft_reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = TL_WR741ND_GPIO_BTN_RESET, ++ .debounce_interval = PB44_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB44_GPIO_SW_RESET, + .active_low = 1, + }, { -+ .desc = "qss", ++ .desc = "jumpstart", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = TL_WR741ND_GPIO_BTN_QSS, ++ .debounce_interval = PB44_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB44_GPIO_SW_JUMP, + .active_low = 1, + } +}; + -+static void __init tl_wr741nd_setup(void) ++static void pb44_vsc7395_reset(void) +{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); -+ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); ++ ar71xx_device_stop(RESET_MODULE_GE1_PHY); ++ udelay(10); ++ ar71xx_device_start(RESET_MODULE_GE1_PHY); ++ mdelay(50); ++} + -+ ar71xx_add_device_m25p80(&tl_wr741nd_flash_data); ++static struct vsc7385_platform_data pb44_vsc7395_data = { ++ .reset = pb44_vsc7395_reset, ++ .ucode_name = "vsc7395_ucode_pb44.bin", ++ .mac_cfg = { ++ .tx_ipg = 6, ++ .bit2 = 1, ++ .clk_sel = 0, ++ }, ++}; + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr741nd_leds_gpio), -+ tl_wr741nd_leds_gpio); ++static struct spi_board_info pb44_spi_info[] = { ++ { ++ .bus_num = 0, ++ .chip_select = 0, ++ .max_speed_hz = 25000000, ++ .modalias = "m25p80", ++ }, { ++ .bus_num = 0, ++ .chip_select = 1, ++ .max_speed_hz = 25000000, ++ .modalias = "spi-vsc7385", ++ .platform_data = &pb44_vsc7395_data, ++ .controller_data = (void *) PB44_GPIO_VSC7395_CS, ++ }, ++}; ++ ++static struct resource pb44_spi_resources[] = { ++ [0] = { ++ .start = AR71XX_SPI_BASE, ++ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; + -+ ar71xx_add_device_gpio_buttons(-1, TL_WR741ND_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(tl_wr741nd_gpio_buttons), -+ tl_wr741nd_gpio_buttons); ++static struct ar71xx_spi_platform_data pb44_spi_data = { ++ .bus_num = 0, ++ .num_chipselect = 2, ++}; + -+ ap91_eth_init(mac, NULL); -+ ap91_pci_init(ee, mac); ++static struct platform_device pb44_spi_device = { ++ .name = "pb44-spi", ++ .id = -1, ++ .resource = pb44_spi_resources, ++ .num_resources = ARRAY_SIZE(pb44_spi_resources), ++ .dev = { ++ .platform_data = &pb44_spi_data, ++ }, ++}; ++ ++#define PB44_WAN_PHYMASK BIT(0) ++#define PB44_LAN_PHYMASK 0 ++#define PB44_MDIO_PHYMASK (PB44_LAN_PHYMASK | PB44_WAN_PHYMASK) ++ ++static void __init pb44_init(void) ++{ ++ ar71xx_add_device_mdio(~PB44_MDIO_PHYMASK); ++ ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = PB44_WAN_PHYMASK; ++ ++ ar71xx_add_device_eth(0); ++ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_eth1_pll_data.pll_1000 = 0x110000; ++ ++ ar71xx_add_device_eth(1); ++ ++ ar71xx_add_device_usb(); ++ ++ pb42_pci_init(); ++ ++ i2c_register_board_info(0, pb44_i2c_board_info, ++ ARRAY_SIZE(pb44_i2c_board_info)); ++ ++ platform_device_register(&pb44_i2c_gpio_device); ++ ++ spi_register_board_info(pb44_spi_info, ARRAY_SIZE(pb44_spi_info)); ++ platform_device_register(&pb44_spi_device); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(pb44_leds_gpio), ++ pb44_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, PB44_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(pb44_gpio_keys), ++ pb44_gpio_keys); +} -+MIPS_MACHINE(AR71XX_MACH_TL_WR741ND, "TL-WR741ND", "TP-LINK TL-WR741ND", -+ tl_wr741nd_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr841n.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr841n.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr841n.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr841n.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,143 @@ ++ ++MIPS_MACHINE(AR71XX_MACH_PB44, "PB44", "Atheros PB44", pb44_init); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-pb92.c linux-2.6.39/arch/mips/ar71xx/mach-pb92.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-pb92.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-pb92.c 2011-08-24 02:41:55.567991163 +0200 +@@ -0,0 +1,105 @@ +/* -+ * TP-LINK TL-WR841N board support ++ * Atheros PB92 board support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2010 Felix Fietkau ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -5755,577 +6205,453 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr841n.c linux-2.6.39/arch/ + +#include +#include -+ +#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-dsa.h" +#include "dev-m25p80.h" +#include "dev-gpio-buttons.h" -+#include "dev-pb42-pci.h" -+#include "dev-leds-gpio.h" -+ -+#define TL_WR841ND_V1_GPIO_LED_SYSTEM 2 -+#define TL_WR841ND_V1_GPIO_LED_QSS_GREEN 4 -+#define TL_WR841ND_V1_GPIO_LED_QSS_RED 5 -+ -+#define TL_WR841ND_V1_GPIO_BTN_RESET 3 -+#define TL_WR841ND_V1_GPIO_BTN_QSS 7 -+ -+#define TL_WR841ND_V1_BUTTONS_POLL_INTERVAL 20 ++#include "dev-pb9x-pci.h" ++#include "dev-usb.h" + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition tl_wr841n_v1_partitions[] = { ++static struct mtd_partition pb92_partitions[] = { + { -+ .name = "redboot", ++ .name = "u-boot", + .offset = 0, -+ .size = 0x020000, ++ .size = 0x040000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "kernel", -+ .offset = 0x020000, -+ .size = 0x140000, -+ } , { ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, ++ }, { + .name = "rootfs", -+ .offset = 0x160000, -+ .size = 0x280000, -+ } , { -+ .name = "config", ++ .offset = 0x050000, ++ .size = 0x2b0000, ++ }, { ++ .name = "uImage", ++ .offset = 0x300000, ++ .size = 0x0e0000, ++ }, { ++ .name = "ART", + .offset = 0x3e0000, + .size = 0x020000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x020000, -+ .size = 0x3c0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data tl_wr841n_v1_flash_data = { ++static struct flash_platform_data pb92_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = tl_wr841n_v1_partitions, -+ .nr_parts = ARRAY_SIZE(tl_wr841n_v1_partitions), ++ .parts = pb92_partitions, ++ .nr_parts = ARRAY_SIZE(pb92_partitions), +#endif +}; + -+static struct gpio_led tl_wr841n_v1_leds_gpio[] __initdata = { -+ { -+ .name = "tl-wr841n:green:system", -+ .gpio = TL_WR841ND_V1_GPIO_LED_SYSTEM, -+ .active_low = 1, -+ }, { -+ .name = "tl-wr841n:red:qss", -+ .gpio = TL_WR841ND_V1_GPIO_LED_QSS_RED, -+ }, { -+ .name = "tl-wr841n:green:qss", -+ .gpio = TL_WR841ND_V1_GPIO_LED_QSS_GREEN, -+ } -+}; ++#define PB92_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define PB92_KEYS_DEBOUNCE_INTERVAL (3 * PB92_KEYS_POLL_INTERVAL) ++ ++#define PB92_GPIO_BTN_SW4 8 ++#define PB92_GPIO_BTN_SW5 3 + -+static struct gpio_button tl_wr841n_v1_gpio_buttons[] __initdata = { ++static struct gpio_keys_button pb92_gpio_keys[] __initdata = { + { -+ .desc = "reset", ++ .desc = "sw4", + .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = TL_WR841ND_V1_GPIO_BTN_RESET, ++ .code = BTN_0, ++ .debounce_interval = PB92_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB92_GPIO_BTN_SW4, + .active_low = 1, + }, { -+ .desc = "qss", ++ .desc = "sw5", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = TL_WR841ND_V1_GPIO_BTN_QSS, ++ .code = BTN_1, ++ .debounce_interval = PB92_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = PB92_GPIO_BTN_SW5, + .active_low = 1, + } +}; + -+static struct dsa_chip_data tl_wr841n_v1_dsa_chip = { -+ .port_names[0] = "wan", -+ .port_names[1] = "lan1", -+ .port_names[2] = "lan2", -+ .port_names[3] = "lan3", -+ .port_names[4] = "lan4", -+ .port_names[5] = "cpu", -+}; -+ -+static struct dsa_platform_data tl_wr841n_v1_dsa_data = { -+ .nr_chips = 1, -+ .chip = &tl_wr841n_v1_dsa_chip, -+}; -+ -+static void __init tl_wr841n_v1_setup(void) ++static void __init pb92_init(void) +{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); -+ -+ ar71xx_set_mac_base(mac); ++ u8 *mac = (u8 *) KSEG1ADDR(0x1fff0000); + -+ ar71xx_add_device_mdio(0x0); ++ ar71xx_add_device_m25p80(&pb92_flash_data); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_add_device_mdio(~BIT(0)); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; + ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(0); + + ar71xx_add_device_eth(0); + -+ ar71xx_add_device_dsa(0, &tl_wr841n_v1_dsa_data); -+ -+ ar71xx_add_device_m25p80(&tl_wr841n_v1_flash_data); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr841n_v1_leds_gpio), -+ tl_wr841n_v1_leds_gpio); -+ -+ ar71xx_add_device_gpio_buttons(-1, TL_WR841ND_V1_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(tl_wr841n_v1_gpio_buttons), -+ tl_wr841n_v1_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, PB92_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(pb92_gpio_keys), ++ pb92_gpio_keys); + -+ pb42_pci_init(); ++ pb9x_pci_init(); +} + -+MIPS_MACHINE(AR71XX_MACH_TL_WR841N_V1, "TL-WR841N-v1.5", "TP-LINK TL-WR841N v1", -+ tl_wr841n_v1_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr941nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr941nd.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr941nd.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr941nd.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,142 @@ ++MIPS_MACHINE(AR71XX_MACH_PB92, "PB92", "Atheros PB92", pb92_init); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-rb4xx.c linux-2.6.39/arch/mips/ar71xx/mach-rb4xx.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-rb4xx.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-rb4xx.c 2011-08-24 02:41:55.567991163 +0200 +@@ -0,0 +1,344 @@ +/* -+ * TP-LINK TL-WR941ND board support ++ * MikroTik RouterBOARD 4xx series support + * -+ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include ++#include ++#include ++#include ++#include ++#include +#include +#include + +#include ++#include ++#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-dsa.h" -+#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define TL_WR941ND_GPIO_LED_SYSTEM 2 -+#define TL_WR941ND_GPIO_LED_QSS_RED 4 -+#define TL_WR941ND_GPIO_LED_QSS_GREEN 5 ++#define RB4XX_GPIO_USER_LED 4 ++#define RB4XX_GPIO_RESET_SWITCH 7 + -+#define TL_WR941ND_GPIO_BTN_RESET 3 -+#define TL_WR941ND_GPIO_BTN_QSS 7 ++#define RB4XX_GPIO_CPLD_BASE 32 ++#define RB4XX_GPIO_CPLD_LED1 (RB4XX_GPIO_CPLD_BASE + CPLD_GPIO_nLED1) ++#define RB4XX_GPIO_CPLD_LED2 (RB4XX_GPIO_CPLD_BASE + CPLD_GPIO_nLED2) ++#define RB4XX_GPIO_CPLD_LED3 (RB4XX_GPIO_CPLD_BASE + CPLD_GPIO_nLED3) ++#define RB4XX_GPIO_CPLD_LED4 (RB4XX_GPIO_CPLD_BASE + CPLD_GPIO_nLED4) ++#define RB4XX_GPIO_CPLD_LED5 (RB4XX_GPIO_CPLD_BASE + CPLD_GPIO_nLED5) + -+#define TL_WR941ND_BUTTONS_POLL_INTERVAL 20 ++#define RB4XX_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define RB4XX_KEYS_DEBOUNCE_INTERVAL (3 * RB4XX_KEYS_POLL_INTERVAL) + -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition tl_wr941nd_partitions[] = { ++static struct gpio_led rb4xx_leds_gpio[] __initdata = { + { -+ .name = "u-boot", -+ .offset = 0, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "kernel", -+ .offset = 0x020000, -+ .size = 0x140000, -+ } , { -+ .name = "rootfs", -+ .offset = 0x160000, -+ .size = 0x290000, -+ } , { -+ .name = "art", -+ .offset = 0x3f0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "firmware", -+ .offset = 0x020000, -+ .size = 0x3d0000, ++ .name = "rb4xx:yellow:user", ++ .gpio = RB4XX_GPIO_USER_LED, ++ .active_low = 0, ++ }, { ++ .name = "rb4xx:green:led1", ++ .gpio = RB4XX_GPIO_CPLD_LED1, ++ .active_low = 1, ++ }, { ++ .name = "rb4xx:green:led2", ++ .gpio = RB4XX_GPIO_CPLD_LED2, ++ .active_low = 1, ++ }, { ++ .name = "rb4xx:green:led3", ++ .gpio = RB4XX_GPIO_CPLD_LED3, ++ .active_low = 1, ++ }, { ++ .name = "rb4xx:green:led4", ++ .gpio = RB4XX_GPIO_CPLD_LED4, ++ .active_low = 1, ++ }, { ++ .name = "rb4xx:green:led5", ++ .gpio = RB4XX_GPIO_CPLD_LED5, ++ .active_low = 0, ++ }, ++}; ++ ++static struct gpio_keys_button rb4xx_gpio_keys[] __initdata = { ++ { ++ .desc = "reset_switch", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = RB4XX_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = RB4XX_GPIO_RESET_SWITCH, ++ .active_low = 1, + } +}; -+#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data tl_wr941nd_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = tl_wr941nd_partitions, -+ .nr_parts = ARRAY_SIZE(tl_wr941nd_partitions), -+#endif ++static struct platform_device rb4xx_nand_device = { ++ .name = "rb4xx-nand", ++ .id = -1, +}; + -+static struct gpio_led tl_wr941nd_leds_gpio[] __initdata = { ++static struct ar71xx_pci_irq rb4xx_pci_irqs[] __initdata = { + { -+ .name = "tl-wr941nd:green:system", -+ .gpio = TL_WR941ND_GPIO_LED_SYSTEM, -+ .active_low = 1, ++ .slot = 0, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV2, + }, { -+ .name = "tl-wr941nd:red:qss", -+ .gpio = TL_WR941ND_GPIO_LED_QSS_RED, ++ .slot = 1, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV0, + }, { -+ .name = "tl-wr941nd:green:qss", -+ .gpio = TL_WR941ND_GPIO_LED_QSS_GREEN, ++ .slot = 1, ++ .pin = 2, ++ .irq = AR71XX_PCI_IRQ_DEV1, ++ }, { ++ .slot = 2, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV1, ++ }, { ++ .slot = 3, ++ .pin = 1, ++ .irq = AR71XX_PCI_IRQ_DEV2, + } +}; + -+static struct gpio_button tl_wr941nd_gpio_buttons[] __initdata = { ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition rb4xx_partitions[] = { + { -+ .desc = "reset", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = TL_WR941ND_GPIO_BTN_RESET, -+ .active_low = 1, ++ .name = "routerboot", ++ .offset = 0, ++ .size = 0x0b000, ++ .mask_flags = MTD_WRITEABLE, + }, { -+ .desc = "qss", -+ .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = TL_WR941ND_GPIO_BTN_QSS, -+ .active_low = 1, ++ .name = "hard_config", ++ .offset = 0x0b000, ++ .size = 0x01000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "bios", ++ .offset = 0x0d000, ++ .size = 0x02000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "soft_config", ++ .offset = 0x0f000, ++ .size = 0x01000, + } +}; ++#define rb4xx_num_partitions ARRAY_SIZE(rb4xx_partitions) ++#else /* CONFIG_MTD_PARTITIONS */ ++#define rb4xx_partitions NULL ++#define rb4xx_num_partitions 0 ++#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct dsa_chip_data tl_wr941nd_dsa_chip = { -+ .port_names[0] = "wan", -+ .port_names[1] = "lan1", -+ .port_names[2] = "lan2", -+ .port_names[3] = "lan3", -+ .port_names[4] = "lan4", -+ .port_names[5] = "cpu", ++static struct flash_platform_data rb4xx_flash_data = { ++ .type = "pm25lv512", ++ .parts = rb4xx_partitions, ++ .nr_parts = rb4xx_num_partitions, +}; + -+static struct dsa_platform_data tl_wr941nd_dsa_data = { -+ .nr_chips = 1, -+ .chip = &tl_wr941nd_dsa_chip, ++static struct rb4xx_cpld_platform_data rb4xx_cpld_data = { ++ .gpio_base = RB4XX_GPIO_CPLD_BASE, +}; + -+static void __init tl_wr941nd_setup(void) -+{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ -+ ar71xx_set_mac_base(mac); ++static struct mmc_spi_platform_data rb4xx_mmc_data = { ++ .ocr_mask = MMC_VDD_32_33 | MMC_VDD_33_34, ++}; + -+ ar71xx_add_device_mdio(0x0); ++static struct spi_board_info rb4xx_spi_info[] = { ++ { ++ .bus_num = 0, ++ .chip_select = 0, ++ .max_speed_hz = 25000000, ++ .modalias = "m25p80", ++ .platform_data = &rb4xx_flash_data, ++ }, { ++ .bus_num = 0, ++ .chip_select = 1, ++ .max_speed_hz = 25000000, ++ .modalias = "spi-rb4xx-cpld", ++ .platform_data = &rb4xx_cpld_data, ++ } ++}; + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ -+ ar71xx_add_device_eth(0); -+ ar71xx_add_device_dsa(0, &tl_wr941nd_dsa_data); -+ -+ ar71xx_add_device_m25p80(&tl_wr941nd_flash_data); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr941nd_leds_gpio), -+ tl_wr941nd_leds_gpio); -+ -+ ar71xx_add_device_gpio_buttons(-1, TL_WR941ND_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(tl_wr941nd_gpio_buttons), -+ tl_wr941nd_gpio_buttons); -+ ar913x_add_device_wmac(eeprom, mac); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_TL_WR941ND, "TL-WR941ND", "TP-LINK TL-WR941ND", -+ tl_wr941nd_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ubnt.c linux-2.6.39/arch/mips/ar71xx/mach-ubnt.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-ubnt.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-ubnt.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,281 @@ -+/* -+ * Ubiquiti RouterStation support -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * Copyright (C) 2008 Ubiquiti -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include -+ -+#include "machtype.h" -+#include "devices.h" -+#include "dev-m25p80.h" -+#include "dev-ap91-pci.h" -+#include "dev-gpio-buttons.h" -+#include "dev-pb42-pci.h" -+#include "dev-leds-gpio.h" -+#include "dev-usb.h" -+ -+#define UBNT_RS_GPIO_LED_RF 2 -+#define UBNT_RS_GPIO_SW4 8 -+ -+#define UBNT_LS_SR71_GPIO_LED_D25 0 -+#define UBNT_LS_SR71_GPIO_LED_D26 1 -+#define UBNT_LS_SR71_GPIO_LED_D24 2 -+#define UBNT_LS_SR71_GPIO_LED_D23 4 -+#define UBNT_LS_SR71_GPIO_LED_D22 5 -+#define UBNT_LS_SR71_GPIO_LED_D27 6 -+#define UBNT_LS_SR71_GPIO_LED_D28 7 -+ -+#define UBNT_M_GPIO_LED_L1 0 -+#define UBNT_M_GPIO_LED_L2 1 -+#define UBNT_M_GPIO_LED_L3 11 -+#define UBNT_M_GPIO_LED_L4 7 -+#define UBNT_M_GPIO_BTN_RESET 12 -+ -+#define UBNT_BUTTONS_POLL_INTERVAL 20 -+ -+static struct gpio_led ubnt_rs_leds_gpio[] __initdata = { -+ { -+ .name = "ubnt:green:rf", -+ .gpio = UBNT_RS_GPIO_LED_RF, -+ .active_low = 0, -+ } -+}; -+ -+static struct gpio_led ubnt_ls_sr71_leds_gpio[] __initdata = { ++static struct spi_board_info rb4xx_microsd_info[] = { + { -+ .name = "ubnt:green:d22", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D22, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:d23", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D23, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:d24", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D24, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:red:d25", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D25, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:red:d26", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D26, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:d27", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D27, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:d28", -+ .gpio = UBNT_LS_SR71_GPIO_LED_D28, -+ .active_low = 0, ++ .bus_num = 0, ++ .chip_select = 2, ++ .max_speed_hz = 25000000, ++ .modalias = "mmc_spi", ++ .platform_data = &rb4xx_mmc_data, + } +}; + -+static struct gpio_led ubnt_m_leds_gpio[] __initdata = { -+ { -+ .name = "ubnt:red:link1", -+ .gpio = UBNT_M_GPIO_LED_L1, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:orange:link2", -+ .gpio = UBNT_M_GPIO_LED_L2, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:link3", -+ .gpio = UBNT_M_GPIO_LED_L3, -+ .active_low = 0, -+ }, { -+ .name = "ubnt:green:link4", -+ .gpio = UBNT_M_GPIO_LED_L4, -+ .active_low = 0, -+ } -+}; + -+static struct gpio_button ubnt_gpio_buttons[] __initdata = { ++static struct resource rb4xx_spi_resources[] = { + { -+ .desc = "sw4", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = UBNT_RS_GPIO_SW4, -+ .active_low = 1, -+ } ++ .start = AR71XX_SPI_BASE, ++ .end = AR71XX_SPI_BASE + AR71XX_SPI_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, +}; + -+static struct gpio_button ubnt_m_gpio_buttons[] __initdata = { -+ { -+ .desc = "reset", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = UBNT_M_GPIO_BTN_RESET, -+ .active_low = 1, -+ } ++static struct platform_device rb4xx_spi_device = { ++ .name = "rb4xx-spi", ++ .id = -1, ++ .resource = rb4xx_spi_resources, ++ .num_resources = ARRAY_SIZE(rb4xx_spi_resources), +}; + -+static void __init ubnt_generic_setup(void) ++static void __init rb4xx_generic_setup(void) +{ -+ ar71xx_add_device_m25p80(NULL); ++ ar71xx_gpio_function_enable(AR71XX_GPIO_FUNC_SPI_CS1_EN | ++ AR71XX_GPIO_FUNC_SPI_CS2_EN); + -+ ar71xx_add_device_gpio_buttons(-1, UBNT_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(ubnt_gpio_buttons), -+ ubnt_gpio_buttons); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(rb4xx_leds_gpio), ++ rb4xx_leds_gpio); + -+ pb42_pci_init(); -+} ++ ar71xx_register_gpio_keys_polled(-1, RB4XX_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(rb4xx_gpio_keys), ++ rb4xx_gpio_keys); + -+#define UBNT_RS_WAN_PHYMASK (1 << 20) -+#define UBNT_RS_LAN_PHYMASK ((1 << 16) | (1 << 17) | (1 << 18) | (1 << 19)) ++ spi_register_board_info(rb4xx_spi_info, ARRAY_SIZE(rb4xx_spi_info)); ++ platform_device_register(&rb4xx_spi_device); ++ platform_device_register(&rb4xx_nand_device); ++} + -+static void __init ubnt_rs_setup(void) ++static void __init rb411_setup(void) +{ -+ ubnt_generic_setup(); ++ rb4xx_generic_setup(); ++ spi_register_board_info(rb4xx_microsd_info, ++ ARRAY_SIZE(rb4xx_microsd_info)); + -+ ar71xx_add_device_mdio(~(UBNT_RS_WAN_PHYMASK | UBNT_RS_LAN_PHYMASK)); ++ ar71xx_add_device_mdio(0xfffffffc); + ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = UBNT_RS_WAN_PHYMASK; -+ -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.speed = SPEED_100; -+ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = 0x00000003; + + ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); + -+ ar71xx_add_device_usb(); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_rs_leds_gpio), -+ ubnt_rs_leds_gpio); ++ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); +} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_RS, "UBNT-RS", "Ubiquiti RouterStation", -+ ubnt_rs_setup); ++MIPS_MACHINE(AR71XX_MACH_RB_411, "411", "MikroTik RouterBOARD 411/A/AH", ++ rb411_setup); ++ ++static void __init rb411u_setup(void) ++{ ++ rb411_setup(); ++ ar71xx_add_device_usb(); ++} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_AR71XX, "Ubiquiti AR71xx-based board", -+ "Ubiquiti RouterStation", ubnt_rs_setup); ++MIPS_MACHINE(AR71XX_MACH_RB_411U, "411U", "MikroTik RouterBOARD 411U", ++ rb411u_setup); + -+#define UBNT_RSPRO_WAN_PHYMASK (1 << 4) -+#define UBNT_RSPRO_LAN_PHYMASK ((1 << 0) | (1 << 1) | (1 << 2) | (1 << 3)) ++#define RB433_LAN_PHYMASK BIT(0) ++#define RB433_WAN_PHYMASK BIT(4) ++#define RB433_MDIO_PHYMASK (RB433_LAN_PHYMASK | RB433_WAN_PHYMASK) + -+static void __init ubnt_rspro_setup(void) ++static void __init rb433_setup(void) +{ -+ ubnt_generic_setup(); ++ rb4xx_generic_setup(); ++ spi_register_board_info(rb4xx_microsd_info, ++ ARRAY_SIZE(rb4xx_microsd_info)); + -+ ar71xx_add_device_mdio(~(UBNT_RSPRO_WAN_PHYMASK | UBNT_RSPRO_LAN_PHYMASK)); ++ ar71xx_add_device_mdio(~RB433_MDIO_PHYMASK); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.phy_mask = UBNT_RSPRO_WAN_PHYMASK; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 1); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = RB433_LAN_PHYMASK; + -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth1_data.phy_mask = UBNT_RSPRO_LAN_PHYMASK; -+ ar71xx_eth1_data.speed = SPEED_1000; -+ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = RB433_WAN_PHYMASK; + -+ ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); ++ ar71xx_add_device_eth(0); + -+ ar71xx_add_device_usb(); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_rs_leds_gpio), -+ ubnt_rs_leds_gpio); ++ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); +} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_RSPRO, "UBNT-RSPRO", "Ubiquiti RouterStation Pro", -+ ubnt_rspro_setup); ++MIPS_MACHINE(AR71XX_MACH_RB_433, "433", "MikroTik RouterBOARD 433/AH", ++ rb433_setup); + -+static void __init ubnt_lsx_setup(void) ++static void __init rb433u_setup(void) +{ -+ ubnt_generic_setup(); ++ rb433_setup(); ++ ar71xx_add_device_usb(); +} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_LSX, "UBNT-LSX", "Ubiquiti LSX", ubnt_lsx_setup); ++MIPS_MACHINE(AR71XX_MACH_RB_433U, "433U", "MikroTik RouterBOARD 433UAH", ++ rb433u_setup); + -+#define UBNT_LSSR71_PHY_MASK (1 << 1) ++#define RB450_LAN_PHYMASK BIT(0) ++#define RB450_WAN_PHYMASK BIT(4) ++#define RB450_MDIO_PHYMASK (RB450_LAN_PHYMASK | RB450_WAN_PHYMASK) + -+static void __init ubnt_lssr71_setup(void) ++static void __init rb450_generic_setup(int gige) +{ -+ ubnt_generic_setup(); ++ rb4xx_generic_setup(); ++ ar71xx_add_device_mdio(~RB450_MDIO_PHYMASK); + -+ ar71xx_add_device_mdio(~UBNT_LSSR71_PHY_MASK); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 1); ++ ar71xx_eth0_data.phy_if_mode = (gige) ? ++ PHY_INTERFACE_MODE_RGMII : PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = RB450_LAN_PHYMASK; + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = UBNT_LSSR71_PHY_MASK; ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth1_data.phy_if_mode = (gige) ? ++ PHY_INTERFACE_MODE_RGMII : PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = RB450_WAN_PHYMASK; + ++ ar71xx_add_device_eth(1); + ar71xx_add_device_eth(0); ++} + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_ls_sr71_leds_gpio), -+ ubnt_ls_sr71_leds_gpio); ++static void __init rb450_setup(void) ++{ ++ rb450_generic_setup(0); +} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_LSSR71, "UBNT-LS-SR71", "Ubiquiti LS-SR71", -+ ubnt_lssr71_setup); ++MIPS_MACHINE(AR71XX_MACH_RB_450, "450", "MikroTik RouterBOARD 450", ++ rb450_setup); + -+static void __init ubnt_m_setup(void) ++static void __init rb450g_setup(void) +{ -+ u8 *mac = (u8 *) KSEG1ADDR(0x1fff0000); -+ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); ++ rb450_generic_setup(1); ++ spi_register_board_info(rb4xx_microsd_info, ++ ARRAY_SIZE(rb4xx_microsd_info)); ++} + -+ ar71xx_set_mac_base(mac); ++MIPS_MACHINE(AR71XX_MACH_RB_450G, "450G", "MikroTik RouterBOARD 450G", ++ rb450g_setup); + -+ ar71xx_add_device_m25p80(NULL); ++static void __init rb493_setup(void) ++{ ++ rb4xx_generic_setup(); + -+ ar71xx_add_device_mdio(~0); ++ ar71xx_add_device_mdio(0x3fffff00); + ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; + ar71xx_eth0_data.speed = SPEED_100; + ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.fifo_cfg1 = 0x0010ffff; -+ ar71xx_eth0_data.fifo_cfg2 = 0x015500aa; -+ ar71xx_eth0_data.fifo_cfg3 = 0x01f00140; -+ -+ ar71xx_add_device_eth(0); -+ -+ ap91_pci_init(ee, NULL); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_m_leds_gpio), -+ ubnt_m_leds_gpio); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = 0x00000001; + -+ ar71xx_add_device_gpio_buttons(-1, UBNT_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(ubnt_m_gpio_buttons), -+ ubnt_m_gpio_buttons); -+} ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+static void __init ubnt_rocket_m_setup(void) -+{ -+ ubnt_m_setup(); -+ ar71xx_add_device_usb(); ++ ar71xx_pci_init(ARRAY_SIZE(rb4xx_pci_irqs), rb4xx_pci_irqs); +} + -+MIPS_MACHINE(AR71XX_MACH_UBNT_BULLET_M, "UBNT-BM", "Ubiquiti Bullet M", -+ ubnt_m_setup); -+MIPS_MACHINE(AR71XX_MACH_UBNT_ROCKET_M, "UBNT-RM", "Ubiquiti Rocket M", -+ ubnt_rocket_m_setup); -+ -+/* TODO detect the second ethernet port and use one -+ init function for all Ubiquiti MIMO series products */ -+static void __init ubnt_nano_m_setup(void) -+{ -+ ubnt_m_setup(); -+ -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.speed = SPEED_1000; -+ ar71xx_eth1_data.duplex = DUPLEX_FULL; -+ ar71xx_eth1_data.fifo_cfg1 = 0x0010ffff; -+ ar71xx_eth1_data.fifo_cfg2 = 0x015500aa; -+ ar71xx_eth1_data.fifo_cfg3 = 0x01f00140; -+ -+ ar71xx_add_device_eth(1); -+} -+ -+MIPS_MACHINE(AR71XX_MACH_UBNT_NANO_M, "UBNT-NM", "Ubiquiti Nanostation M", -+ ubnt_nano_m_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wndr3700.c linux-2.6.39/arch/mips/ar71xx/mach-wndr3700.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wndr3700.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wndr3700.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,209 @@ ++MIPS_MACHINE(AR71XX_MACH_RB_493, "493", "MikroTik RouterBOARD 493/AH", ++ rb493_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-rb750.c linux-2.6.39/arch/mips/ar71xx/mach-rb750.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-rb750.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-rb750.c 2011-08-24 02:41:55.567991163 +0200 +@@ -0,0 +1,144 @@ +/* -+ * Netgear WNDR3700 board support ++ * MikroTik RouterBOARD 750 support + * -+ * Copyright (C) 2009 Marco Porsch -+ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -6333,213 +6659,148 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wndr3700.c linux-2.6.39/arch/m + */ + +#include -+#include -+#include -+#include -+#include -+ +#include ++#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-m25p80.h" -+#include "dev-ap94-pci.h" -+#include "dev-gpio-buttons.h" -+#include "dev-leds-gpio.h" -+#include "dev-usb.h" -+ -+#define WNDR3700_GPIO_LED_WPS_ORANGE 0 -+#define WNDR3700_GPIO_LED_POWER_ORANGE 1 -+#define WNDR3700_GPIO_LED_POWER_GREEN 2 -+#define WNDR3700_GPIO_LED_WPS_GREEN 4 -+#define WNDR3700_GPIO_LED_WAN_GREEN 6 -+ -+#define WNDR3700_GPIO_BTN_WPS 3 -+#define WNDR3700_GPIO_BTN_RESET 8 -+#define WNDR3700_GPIO_BTN_WIFI 11 -+ -+#define WNDR3700_GPIO_RTL8366_SDA 5 -+#define WNDR3700_GPIO_RTL8366_SCK 7 -+ -+#define WNDR3700_BUTTONS_POLL_INTERVAL 20 -+ -+#define WNDR3700_WMAC0_MAC_OFFSET 0 -+#define WNDR3700_WMAC1_MAC_OFFSET 0xc -+#define WNDR3700_CALDATA0_OFFSET 0x1000 -+#define WNDR3700_CALDATA1_OFFSET 0x5000 -+ -+#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition wndr3700_partitions[] = { -+ { -+ .name = "uboot", -+ .offset = 0, -+ .size = 0x050000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "env", -+ .offset = 0x050000, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "rootfs", -+ .offset = 0x070000, -+ .size = 0x720000, -+ } , { -+ .name = "config", -+ .offset = 0x790000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "config_bak", -+ .offset = 0x7a0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "pot", -+ .offset = 0x7b0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "traffic_meter", -+ .offset = 0x7c0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "language", -+ .offset = 0x7d0000, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "caldata", -+ .offset = 0x7f0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } -+}; -+#endif /* CONFIG_MTD_PARTITIONS */ -+ -+static struct flash_platform_data wndr3700_flash_data = { -+#ifdef CONFIG_MTD_PARTITIONS -+ .parts = wndr3700_partitions, -+ .nr_parts = ARRAY_SIZE(wndr3700_partitions), -+#endif -+}; + -+static struct gpio_led wndr3700_leds_gpio[] __initdata = { ++static struct rb750_led_data rb750_leds[] = { + { -+ .name = "wndr3700:green:power", -+ .gpio = WNDR3700_GPIO_LED_POWER_GREEN, ++ .name = "rb750:green:act", ++ .mask = RB750_LED_ACT, + .active_low = 1, + }, { -+ .name = "wndr3700:orange:power", -+ .gpio = WNDR3700_GPIO_LED_POWER_ORANGE, ++ .name = "rb750:green:port1", ++ .mask = RB750_LED_PORT5, + .active_low = 1, + }, { -+ .name = "wndr3700:green:wps", -+ .gpio = WNDR3700_GPIO_LED_WPS_GREEN, ++ .name = "rb750:green:port2", ++ .mask = RB750_LED_PORT4, + .active_low = 1, + }, { -+ .name = "wndr3700:orange:wps", -+ .gpio = WNDR3700_GPIO_LED_WPS_ORANGE, ++ .name = "rb750:green:port3", ++ .mask = RB750_LED_PORT3, + .active_low = 1, + }, { -+ .name = "wndr3700:green:wan", -+ .gpio = WNDR3700_GPIO_LED_WAN_GREEN, -+ .active_low = 1, -+ } -+}; -+ -+static struct gpio_button wndr3700_gpio_buttons[] __initdata = { -+ { -+ .desc = "reset", -+ .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = WNDR3700_GPIO_BTN_RESET, ++ .name = "rb750:green:port4", ++ .mask = RB750_LED_PORT2, + .active_low = 1, + }, { -+ .desc = "wps", -+ .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = WNDR3700_GPIO_BTN_WPS, -+ .active_low = 1, -+ } , { -+ .desc = "wifi", -+ .type = EV_KEY, -+ .code = BTN_2, -+ .threshold = 3, -+ .gpio = WNDR3700_GPIO_BTN_WIFI, ++ .name = "rb750:green:port5", ++ .mask = RB750_LED_PORT1, + .active_low = 1, + } +}; + -+static struct rtl8366s_platform_data wndr3700_rtl8366s_data = { -+ .gpio_sda = WNDR3700_GPIO_RTL8366_SDA, -+ .gpio_sck = WNDR3700_GPIO_RTL8366_SCK, ++static struct rb750_led_platform_data rb750_leds_data = { ++ .num_leds = ARRAY_SIZE(rb750_leds), ++ .leds = rb750_leds, +}; + -+static struct platform_device wndr3700_rtl8366s_device = { -+ .name = RTL8366S_DRIVER_NAME, -+ .id = -1, -+ .dev = { -+ .platform_data = &wndr3700_rtl8366s_data, ++static struct platform_device rb750_leds_device = { ++ .name = "leds-rb750", ++ .dev = { ++ .platform_data = &rb750_leds_data, + } +}; + -+static void __init wndr3700_setup(void) ++static struct platform_device rb750_nand_device = { ++ .name = "rb750-nand", ++ .id = -1, ++}; ++ ++int rb750_latch_change(u32 mask_clr, u32 mask_set) +{ -+ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); ++ static DEFINE_SPINLOCK(lock); ++ static u32 latch_set = RB750_LED_BITS | RB750_LVC573_LE; ++ static u32 latch_oe; ++ static u32 latch_clr; ++ unsigned long flags; ++ u32 t; ++ int ret = 0; + -+ ar71xx_set_mac_base(art); ++ spin_lock_irqsave(&lock, flags); + -+ ar71xx_eth0_pll_data.pll_1000 = 0x11110000; -+ ar71xx_eth0_data.mii_bus_dev = &wndr3700_rtl8366s_device.dev; -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth0_data.speed = SPEED_1000; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ if ((mask_clr & BIT(31)) != 0 && ++ (latch_set & RB750_LVC573_LE) == 0) { ++ goto unlock; ++ } + -+ ar71xx_eth1_pll_data.pll_1000 = 0x11110000; -+ ar71xx_eth1_data.mii_bus_dev = &wndr3700_rtl8366s_device.dev; -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++ latch_set = (latch_set | mask_set) & ~mask_clr; ++ latch_clr = (latch_clr | mask_clr) & ~mask_set; + -+ ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); ++ if (latch_oe == 0) ++ latch_oe = __raw_readl(ar71xx_gpio_base + GPIO_REG_OE); + -+ ar71xx_add_device_usb(); ++ if (likely(latch_set & RB750_LVC573_LE)) { ++ void __iomem *base = ar71xx_gpio_base; + -+ ar71xx_add_device_m25p80(&wndr3700_flash_data); ++ t = __raw_readl(base + GPIO_REG_OE); ++ t |= mask_clr | latch_oe | mask_set; + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wndr3700_leds_gpio), -+ wndr3700_leds_gpio); ++ __raw_writel(t, base + GPIO_REG_OE); ++ __raw_writel(latch_clr, base + GPIO_REG_CLEAR); ++ __raw_writel(latch_set, base + GPIO_REG_SET); ++ } else if (mask_clr & RB750_LVC573_LE) { ++ void __iomem *base = ar71xx_gpio_base; + -+ ar71xx_add_device_gpio_buttons(-1, WNDR3700_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wndr3700_gpio_buttons), -+ wndr3700_gpio_buttons); ++ latch_oe = __raw_readl(base + GPIO_REG_OE); ++ __raw_writel(RB750_LVC573_LE, base + GPIO_REG_CLEAR); ++ /* flush write */ ++ __raw_readl(base + GPIO_REG_CLEAR); ++ } + -+ platform_device_register(&wndr3700_rtl8366s_device); -+ platform_device_register_simple("wndr3700-led-usb", -1, NULL, 0); ++ ret = 1; + -+ ap94_pci_enable_quirk_wndr3700(); -+ ap94_pci_init(art + WNDR3700_CALDATA0_OFFSET, -+ art + WNDR3700_WMAC0_MAC_OFFSET, -+ art + WNDR3700_CALDATA1_OFFSET, -+ art + WNDR3700_WMAC1_MAC_OFFSET); ++unlock: ++ spin_unlock_irqrestore(&lock, flags); ++ return ret; +} ++EXPORT_SYMBOL_GPL(rb750_latch_change); + -+MIPS_MACHINE(AR71XX_MACH_WNDR3700, "WNDR3700", "NETGEAR WNDR3700", -+ wndr3700_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wnr2000.c linux-2.6.39/arch/mips/ar71xx/mach-wnr2000.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wnr2000.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wnr2000.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,148 @@ ++static void __init rb750_setup(void) ++{ ++ ar71xx_gpio_function_disable(AR724X_GPIO_FUNC_ETH_SWITCH_LED0_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED1_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED2_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED3_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED4_EN); ++ ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ar71xx_mac_base, 1); ++ ++ /* WAN port */ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(4); ++ ++ /* LAN ports */ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_eth1_data.has_ar7240_switch = 1; ++ ++ ar71xx_add_device_mdio(0x0); ++ ar71xx_add_device_eth(1); ++ ar71xx_add_device_eth(0); ++ ++ platform_device_register(&rb750_leds_device); ++ platform_device_register(&rb750_nand_device); ++} ++ ++MIPS_MACHINE(AR71XX_MACH_RB_750, "750i", "MikroTik RouterBOARD 750", ++ rb750_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tew-632brp.c linux-2.6.39/arch/mips/ar71xx/mach-tew-632brp.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tew-632brp.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tew-632brp.c 2011-08-24 02:41:55.577989822 +0200 +@@ -0,0 +1,151 @@ +/* -+ * NETGEAR WNR2000 board support ++ * TrendNET TEW-632BRP board support + * + * Copyright (C) 2008-2009 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz -+ * Copyright (C) 2008-2009 Andy Boyett + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -6554,149 +6815,153 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wnr2000.c linux-2.6.39/arch/mi +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "nvram.h" + -+#define WNR2000_GPIO_LED_PWR_GREEN 14 -+#define WNR2000_GPIO_LED_PWR_AMBER 7 -+#define WNR2000_GPIO_LED_WPS 4 -+#define WNR2000_GPIO_LED_WLAN 6 -+#define WNR2000_GPIO_BTN_RESET 21 -+#define WNR2000_GPIO_BTN_WPS 8 ++#define TEW_632BRP_GPIO_LED_STATUS 1 ++#define TEW_632BRP_GPIO_LED_WPS 3 ++#define TEW_632BRP_GPIO_LED_WLAN 6 ++#define TEW_632BRP_GPIO_BTN_WPS 12 ++#define TEW_632BRP_GPIO_BTN_RESET 21 + -+#define WNR2000_BUTTONS_POLL_INTERVAL 20 ++#define TEW_632BRP_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TEW_632BRP_KEYS_DEBOUNCE_INTERVAL (3 * TEW_632BRP_KEYS_POLL_INTERVAL) ++ ++#define TEW_632BRP_CONFIG_ADDR 0x1f020000 ++#define TEW_632BRP_CONFIG_SIZE 0x10000 + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition wnr2000_partitions[] = { ++static struct mtd_partition tew_632brp_partitions[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x040000, ++ .size = 0x020000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "u-boot-env", -+ .offset = 0x040000, ++ }, { ++ .name = "config", ++ .offset = 0x020000, + .size = 0x010000, -+ } , { ++ }, { ++ .name = "kernel", ++ .offset = 0x030000, ++ .size = 0x0e0000, ++ }, { + .name = "rootfs", -+ .offset = 0x050000, -+ .size = 0x240000, -+ } , { -+ .name = "user-config", -+ .offset = 0x290000, -+ .size = 0x010000, -+ } , { -+ .name = "uImage", -+ .offset = 0x2a0000, -+ .size = 0x120000, -+ } , { -+ .name = "language_table", -+ .offset = 0x3c0000, -+ .size = 0x020000, -+ } , { -+ .name = "rootfs_checksum", -+ .offset = 0x3e0000, -+ .size = 0x010000, -+ } , { ++ .offset = 0x110000, ++ .size = 0x2e0000, ++ }, { + .name = "art", + .offset = 0x3f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x030000, ++ .size = 0x3c0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data wnr2000_flash_data = { ++static struct flash_platform_data tew_632brp_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = wnr2000_partitions, -+ .nr_parts = ARRAY_SIZE(wnr2000_partitions), ++ .parts = tew_632brp_partitions, ++ .nr_parts = ARRAY_SIZE(tew_632brp_partitions), +#endif +}; + -+static struct gpio_led wnr2000_leds_gpio[] __initdata = { ++static struct gpio_led tew_632brp_leds_gpio[] __initdata = { + { -+ .name = "wnr2000:green:power", -+ .gpio = WNR2000_GPIO_LED_PWR_GREEN, -+ .active_low = 1, -+ }, { -+ .name = "wnr2000:amber:power", -+ .gpio = WNR2000_GPIO_LED_PWR_AMBER, ++ .name = "tew-632brp:green:status", ++ .gpio = TEW_632BRP_GPIO_LED_STATUS, + .active_low = 1, + }, { -+ .name = "wnr2000:green:wps", -+ .gpio = WNR2000_GPIO_LED_WPS, ++ .name = "tew-632brp:blue:wps", ++ .gpio = TEW_632BRP_GPIO_LED_WPS, + .active_low = 1, + }, { -+ .name = "wnr2000:blue:wlan", -+ .gpio = WNR2000_GPIO_LED_WLAN, ++ .name = "tew-632brp:green:wlan", ++ .gpio = TEW_632BRP_GPIO_LED_WLAN, + .active_low = 1, + } +}; + -+static struct gpio_button wnr2000_gpio_buttons[] __initdata = { ++static struct gpio_keys_button tew_632brp_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = WNR2000_GPIO_BTN_RESET, ++ .debounce_interval = TEW_632BRP_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TEW_632BRP_GPIO_BTN_RESET, + }, { + .desc = "wps", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = WNR2000_GPIO_BTN_WPS, ++ .debounce_interval = TEW_632BRP_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TEW_632BRP_GPIO_BTN_WPS, + } +}; + -+static void __init wnr2000_setup(void) ++#define TEW_632BRP_LAN_PHYMASK BIT(0) ++#define TEW_632BRP_WAN_PHYMASK BIT(4) ++#define TEW_632BRP_MDIO_MASK (~(TEW_632BRP_LAN_PHYMASK | \ ++ TEW_632BRP_WAN_PHYMASK)) ++ ++static void __init tew_632brp_setup(void) +{ ++ const char *config = (char *) KSEG1ADDR(TEW_632BRP_CONFIG_ADDR); + u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ u8 mac[6]; ++ u8 *wlan_mac = NULL; + -+ ar71xx_set_mac_base(eeprom); -+ ar71xx_add_device_mdio(0x0); ++ if (nvram_parse_mac_addr(config, TEW_632BRP_CONFIG_SIZE, ++ "lan_mac=", mac) == 0) { ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ wlan_mac = mac; ++ } ++ ++ ar71xx_add_device_mdio(TEW_632BRP_MDIO_MASK); + + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ ar71xx_eth0_data.has_ar8216 = 1; ++ ar71xx_eth0_data.phy_mask = TEW_632BRP_LAN_PHYMASK; + + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++ ar71xx_eth1_data.phy_mask = TEW_632BRP_WAN_PHYMASK; + + ar71xx_add_device_eth(0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_m25p80(&wnr2000_flash_data); -+ -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wnr2000_leds_gpio), -+ wnr2000_leds_gpio); ++ ar71xx_add_device_m25p80(&tew_632brp_flash_data); + -+ ar71xx_add_device_gpio_buttons(-1, WNR2000_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wnr2000_gpio_buttons), -+ wnr2000_gpio_buttons); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tew_632brp_leds_gpio), ++ tew_632brp_leds_gpio); + ++ ar71xx_register_gpio_keys_polled(-1, TEW_632BRP_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tew_632brp_gpio_keys), ++ tew_632brp_gpio_keys); + -+ ar913x_add_device_wmac(eeprom, NULL); ++ ar9xxx_add_device_wmac(eeprom, wlan_mac); +} + -+MIPS_MACHINE(AR71XX_MACH_WNR2000, "WNR2000", "NETGEAR WNR2000", wnr2000_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wp543.c linux-2.6.39/arch/mips/ar71xx/mach-wp543.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wp543.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wp543.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,99 @@ ++MIPS_MACHINE(AR71XX_MACH_TEW_632BRP, "TEW-632BRP", "TRENDnet TEW-632BRP", ++ tew_632brp_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-mr3x20.c linux-2.6.39/arch/mips/ar71xx/mach-tl-mr3x20.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-mr3x20.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-mr3x20.c 2011-08-24 02:41:55.577989822 +0200 +@@ -0,0 +1,166 @@ +/* -+ * Compex WP543/WPJ543 board support ++ * TP-LINK TL-MR3220/3420 board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + ++#include +#include +#include + @@ -6705,94 +6970,162 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wp543.c linux-2.6.39/arch/mips +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-pb42-pci.h" ++#include "dev-ap91-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" +#include "dev-usb.h" + -+#define WP543_GPIO_SW6 2 -+#define WP543_GPIO_LED_1 3 -+#define WP543_GPIO_LED_2 4 -+#define WP543_GPIO_LED_WLAN 5 -+#define WP543_GPIO_LED_CONN 6 -+#define WP543_GPIO_LED_DIAG 7 -+#define WP543_GPIO_SW4 8 ++#define TL_MR3X20_GPIO_LED_QSS 0 ++#define TL_MR3X20_GPIO_LED_SYSTEM 1 ++#define TL_MR3X20_GPIO_LED_3G 8 + -+#define WP543_BUTTONS_POLL_INTERVAL 20 ++#define TL_MR3X20_GPIO_BTN_RESET 11 ++#define TL_MR3X20_GPIO_BTN_QSS 12 + -+static struct gpio_led wp543_leds_gpio[] __initdata = { ++#define TL_MR3X20_GPIO_USB_POWER 6 ++ ++#define TL_MR3X20_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_MR3X20_KEYS_DEBOUNCE_INTERVAL (3 * TL_MR3X20_KEYS_POLL_INTERVAL) ++ ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition tl_mr3x20_partitions[] = { + { -+ .name = "wp543:green:led1", -+ .gpio = WP543_GPIO_LED_1, -+ .active_low = 1, ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, + }, { -+ .name = "wp543:green:led2", -+ .gpio = WP543_GPIO_LED_2, -+ .active_low = 1, ++ .name = "kernel", ++ .offset = 0x020000, ++ .size = 0x140000, + }, { -+ .name = "wp543:green:wlan", -+ .gpio = WP543_GPIO_LED_WLAN, ++ .name = "rootfs", ++ .offset = 0x160000, ++ .size = 0x290000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x020000, ++ .size = 0x3d0000, ++ } ++}; ++#define tl_mr3x20_num_partitions ARRAY_SIZE(tl_mr3x20_partitions) ++#else ++#define tl_mr3x20_partitions NULL ++#define tl_mr3x20_num_partitions 0 ++#endif /* CONFIG_MTD_PARTITIONS */ ++ ++static struct flash_platform_data tl_mr3x20_flash_data = { ++ .parts = tl_mr3x20_partitions, ++ .nr_parts = tl_mr3x20_num_partitions, ++}; ++ ++static struct gpio_led tl_mr3x20_leds_gpio[] __initdata = { ++ { ++ .name = "tl-mr3x20:green:system", ++ .gpio = TL_MR3X20_GPIO_LED_SYSTEM, + .active_low = 1, + }, { -+ .name = "wp543:green:conn", -+ .gpio = WP543_GPIO_LED_CONN, ++ .name = "tl-mr3x20:green:qss", ++ .gpio = TL_MR3X20_GPIO_LED_QSS, + .active_low = 1, + }, { -+ .name = "wp543:green:diag", -+ .gpio = WP543_GPIO_LED_DIAG, ++ .name = "tl-mr3x20:green:3g", ++ .gpio = TL_MR3X20_GPIO_LED_3G, + .active_low = 1, + } +}; + -+static struct gpio_button wp543_gpio_buttons[] __initdata = { ++static struct gpio_keys_button tl_mr3x20_gpio_keys[] __initdata = { + { -+ .desc = "sw6", ++ .desc = "reset", + .type = EV_KEY, -+ .code = BTN_0, -+ .threshold = 3, -+ .gpio = WP543_GPIO_SW6, ++ .code = KEY_RESTART, ++ .debounce_interval = TL_MR3X20_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_MR3X20_GPIO_BTN_RESET, ++ .active_low = 1, + }, { -+ .desc = "sw4", ++ .desc = "qss", + .type = EV_KEY, -+ .code = BTN_1, -+ .threshold = 3, -+ .gpio = WP543_GPIO_SW4, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = TL_MR3X20_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_MR3X20_GPIO_BTN_QSS, ++ .active_low = 1, + } +}; + -+static void __init wp543_setup(void) ++static void __init tl_mr3x20_setup(void) +{ -+ ar71xx_add_device_m25p80(NULL); ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + -+ ar71xx_add_device_mdio(0xfffffff7); ++ /* enable power for the USB port */ ++ gpio_request(TL_MR3X20_GPIO_USB_POWER, "USB power"); ++ gpio_direction_output(TL_MR3X20_GPIO_USB_POWER, 1); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; -+ ar71xx_eth0_data.phy_mask = 0x08; -+ ar71xx_eth0_data.reset_bit = RESET_MODULE_GE0_MAC | -+ RESET_MODULE_GE0_PHY; ++ ar71xx_add_device_m25p80(&tl_mr3x20_flash_data); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_mr3x20_leds_gpio), ++ tl_mr3x20_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, TL_MR3X20_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_mr3x20_gpio_keys), ++ tl_mr3x20_gpio_keys); ++ ++ ar71xx_eth1_data.has_ar7240_switch = 1; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ ++ /* WAN port */ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(4); ++ ++ /* LAN ports */ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ++ ar71xx_add_device_mdio(0x0); ++ ar71xx_add_device_eth(1); + ar71xx_add_device_eth(0); + + ar71xx_add_device_usb(); + -+ pb42_pci_init(); ++ ap91_pci_init(ee, mac); ++} + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wp543_leds_gpio), -+ wp543_leds_gpio); ++static void __init tl_mr3220_setup(void) ++{ ++ tl_mr3x20_setup(); ++ ap91_pci_setup_wmac_led_pin(1); ++} ++ ++MIPS_MACHINE(AR71XX_MACH_TL_MR3220, "TL-MR3220", "TP-LINK TL-MR3220", ++ tl_mr3220_setup); + -+ ar71xx_add_device_gpio_buttons(-1, WP543_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wp543_gpio_buttons), -+ wp543_gpio_buttons); ++static void __init tl_mr3420_setup(void) ++{ ++ tl_mr3x20_setup(); ++ ap91_pci_setup_wmac_led_pin(0); +} + -+MIPS_MACHINE(AR71XX_MACH_WP543, "WP543", "Compex WP543", wp543_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt160nl.c linux-2.6.39/arch/mips/ar71xx/mach-wrt160nl.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt160nl.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wrt160nl.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,158 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_MR3420, "TL-MR3420", "TP-LINK TL-MR3420", ++ tl_mr3420_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wa901nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wa901nd.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wa901nd.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wa901nd.c 2011-08-24 02:41:55.587990766 +0200 +@@ -0,0 +1,130 @@ +/* -+ * Linksys WRT160NL board support ++ * TP-LINK TL-WA901ND board support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2010 Pieter Hollants + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -6807,155 +7140,127 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt160nl.c linux-2.6.39/arch/m +#include "machtype.h" +#include "devices.h" +#include "dev-m25p80.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-ap91-pci.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" -+#include "dev-usb.h" -+#include "nvram.h" + -+#define WRT160NL_GPIO_LED_POWER 14 -+#define WRT160NL_GPIO_LED_WPS_AMBER 9 -+#define WRT160NL_GPIO_LED_WPS_BLUE 8 -+#define WRT160NL_GPIO_LED_WLAN 6 ++#define TL_WA901ND_GPIO_LED_QSS 0 ++#define TL_WA901ND_GPIO_LED_SYSTEM 1 + -+#define WRT160NL_GPIO_BTN_WPS 7 -+#define WRT160NL_GPIO_BTN_RESET 21 ++#define TL_WA901ND_GPIO_BTN_RESET 11 ++#define TL_WA901ND_GPIO_BTN_QSS 12 + -+#define WRT160NL_BUTTONS_POLL_INTERVAL 20 -+ -+#define WRT160NL_NVRAM_ADDR 0x1f7e0000 -+#define WRT160NL_NVRAM_SIZE 0x10000 ++#define TL_WA901ND_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WA901ND_KEYS_DEBOUNCE_INTERVAL (3 * TL_WA901ND_KEYS_POLL_INTERVAL) + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition wrt160nl_partitions[] = { ++static struct mtd_partition tl_wa901nd_partitions[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x040000, ++ .size = 0x020000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "kernel", -+ .offset = 0x040000, -+ .size = 0x0e0000, -+ } , { -+ .name = "filesytem", -+ .offset = 0x120000, -+ .size = 0x6c0000, -+ } , { -+ .name = "nvram", -+ .offset = 0x7e0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "ART", -+ .offset = 0x7f0000, ++ .offset = 0x020000, ++ .size = 0x140000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x160000, ++ .size = 0x290000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "firmware", -+ .offset = 0x040000, -+ .size = 0x7a0000, ++ .offset = 0x020000, ++ .size = 0x3d0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data wrt160nl_flash_data = { ++static struct flash_platform_data tl_wa901nd_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = wrt160nl_partitions, -+ .nr_parts = ARRAY_SIZE(wrt160nl_partitions), ++ .parts = tl_wa901nd_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wa901nd_partitions), +#endif +}; + -+static struct gpio_led wrt160nl_leds_gpio[] __initdata = { ++static struct gpio_led tl_wa901nd_leds_gpio[] __initdata = { + { -+ .name = "wrt160nl:blue:power", -+ .gpio = WRT160NL_GPIO_LED_POWER, -+ .active_low = 1, -+ .default_trigger = "default-on", -+ }, { -+ .name = "wrt160nl:amber:wps", -+ .gpio = WRT160NL_GPIO_LED_WPS_AMBER, -+ .active_low = 1, -+ }, { -+ .name = "wrt160nl:blue:wps", -+ .gpio = WRT160NL_GPIO_LED_WPS_BLUE, ++ .name = "tl-wa901nd:green:system", ++ .gpio = TL_WA901ND_GPIO_LED_SYSTEM, + .active_low = 1, + }, { -+ .name = "wrt160nl:blue:wlan", -+ .gpio = WRT160NL_GPIO_LED_WLAN, ++ .name = "tl-wa901nd:green:qss", ++ .gpio = TL_WA901ND_GPIO_LED_QSS, + .active_low = 1, + } +}; + -+static struct gpio_button wrt160nl_gpio_buttons[] __initdata = { ++static struct gpio_keys_button tl_wa901nd_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, -+ .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = WRT160NL_GPIO_BTN_RESET, ++ .code = BTN_0, ++ .debounce_interval = TL_WA901ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WA901ND_GPIO_BTN_RESET, + .active_low = 1, + }, { -+ .desc = "wps", ++ .desc = "qss", + .type = EV_KEY, -+ .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = WRT160NL_GPIO_BTN_WPS, ++ .code = BTN_1, ++ .debounce_interval = TL_WA901ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WA901ND_GPIO_BTN_QSS, + .active_low = 1, + } +}; + -+static void __init wrt160nl_setup(void) ++static void __init tl_wa901nd_setup(void) +{ -+ const char *nvram = (char *) KSEG1ADDR(WRT160NL_NVRAM_ADDR); -+ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); -+ u8 mac[6]; -+ -+ if (nvram_parse_mac_addr(nvram, WRT160NL_NVRAM_SIZE, -+ "lan_hwaddr=", mac) == 0) -+ ar71xx_set_mac_base(mac); -+ -+ ar71xx_add_device_mdio(0x0); -+ -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.phy_mask = 0x01; ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + ++ /* ++ * ar71xx_eth0 would be the WAN port, but is not connected on ++ * the TL-WA901ND. ar71xx_eth1 connects to the internal switch chip, ++ * however we have a single LAN port only. ++ */ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 0); + ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; ++ ar71xx_eth1_data.has_ar7240_switch = 1; + -+ ar71xx_add_device_eth(0); ++ ar71xx_add_device_mdio(0x0); + ar71xx_add_device_eth(1); + -+ ar71xx_add_device_m25p80(&wrt160nl_flash_data); -+ -+ ar71xx_add_device_usb(); -+ -+ if (nvram_parse_mac_addr(nvram, WRT160NL_NVRAM_SIZE, -+ "wl0_hwaddr=", mac) == 0) -+ ar913x_add_device_wmac(eeprom, mac); -+ else -+ ar913x_add_device_wmac(eeprom, NULL); ++ ar71xx_add_device_m25p80(&tl_wa901nd_flash_data); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wrt160nl_leds_gpio), -+ wrt160nl_leds_gpio); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wa901nd_leds_gpio), ++ tl_wa901nd_leds_gpio); + -+ ar71xx_add_device_gpio_buttons(-1, WRT160NL_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wrt160nl_gpio_buttons), -+ wrt160nl_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, TL_WA901ND_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wa901nd_gpio_keys), ++ tl_wa901nd_gpio_keys); + ++ ap91_pci_init(ee, mac); +} + -+MIPS_MACHINE(AR71XX_MACH_WRT160NL, "WRT160NL", "Linksys WRT160NL", -+ wrt160nl_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt400n.c linux-2.6.39/arch/mips/ar71xx/mach-wrt400n.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt400n.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wrt400n.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,168 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_WA901ND, "TL-WA901ND", "TP-LINK TL-WA901ND", ++ tl_wa901nd_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wa901nd-v2.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wa901nd-v2.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wa901nd-v2.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wa901nd-v2.c 2011-08-24 02:41:55.587990766 +0200 +@@ -0,0 +1,132 @@ +/* -+ * Linksys WRT400N board support ++ * TP-LINK TL-WA901ND v2 board support + * + * Copyright (C) 2009-2010 Gabor Juhos -+ * Copyright (C) 2009 Imre Kaloz ++ * Copyright (C) 2010 Pieter Hollants ++ * Copyright (C) 2011 Jonathan Bennett + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published @@ -6969,574 +7274,424 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt400n.c linux-2.6.39/arch/mi + +#include "machtype.h" +#include "devices.h" -+#include "dev-ap94-pci.h" +#include "dev-m25p80.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" ++#include "dev-ar9xxx-wmac.h" + -+#define WRT400N_GPIO_LED_ORANGE 5 -+#define WRT400N_GPIO_LED_GREEN 4 -+#define WRT400N_GPIO_LED_POWER 1 -+#define WRT400N_GPIO_LED_WLAN 0 -+ -+#define WRT400N_GPIO_BTN_RESET 8 -+#define WRT400N_GPIO_BTN_WLSEC 3 ++#define TL_WA901ND_V2_GPIO_LED_QSS 4 ++#define TL_WA901ND_V2_GPIO_LED_SYSTEM 2 ++#define TL_WA901ND_V2_GPIO_LED_WLAN 9 + -+#define WRT400N_BUTTONS_POLL_INTERVAL 20 + -+#define WRT400N_MAC_ADDR_OFFSET 0x120c -+#define WRT400N_CALDATA0_OFFSET 0x1000 -+#define WRT400N_CALDATA1_OFFSET 0x5000 ++#define TL_WA901ND_V2_GPIO_BTN_RESET 3 ++#define TL_WA901ND_V2_GPIO_BTN_QSS 7 + ++#define TL_WA901ND_V2_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WA901ND_V2_KEYS_DEBOUNCE_INTERVAL \ ++ (3 * TL_WA901ND_V2_KEYS_POLL_INTERVAL) +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition wrt400n_partitions[] = { ++static struct mtd_partition tl_wa901nd_v2_partitions[] = { + { -+ .name = "uboot", ++ .name = "u-boot", + .offset = 0, -+ .size = 0x030000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "env", -+ .offset = 0x030000, -+ .size = 0x010000, ++ .size = 0x020000, + .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "linux", -+ .offset = 0x040000, ++ }, { ++ .name = "kernel", ++ .offset = 0x020000, + .size = 0x140000, -+ } , { ++ }, { + .name = "rootfs", -+ .offset = 0x180000, -+ .size = 0x630000, -+ } , { -+ .name = "nvram", -+ .offset = 0x7b0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "factory", -+ .offset = 0x7c0000, -+ .size = 0x010000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "language", -+ .offset = 0x7d0000, -+ .size = 0x020000, -+ .mask_flags = MTD_WRITEABLE, -+ } , { -+ .name = "caldata", -+ .offset = 0x7f0000, ++ .offset = 0x160000, ++ .size = 0x290000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, + .size = 0x010000, + .mask_flags = MTD_WRITEABLE, -+ } , { ++ }, { + .name = "firmware", -+ .offset = 0x040000, -+ .size = 0x770000, ++ .offset = 0x020000, ++ .size = 0x3d0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct flash_platform_data wrt400n_flash_data = { ++static struct flash_platform_data tl_wa901nd_v2_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = wrt400n_partitions, -+ .nr_parts = ARRAY_SIZE(wrt400n_partitions), ++ .parts = tl_wa901nd_v2_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wa901nd_v2_partitions), +#endif +}; + -+static struct gpio_led wrt400n_leds_gpio[] __initdata = { ++static struct gpio_led tl_wa901nd_v2_leds_gpio[] __initdata = { + { -+ .name = "wrt400n:green:status", -+ .gpio = WRT400N_GPIO_LED_GREEN, -+ .active_low = 1, -+ }, { -+ .name = "wrt400n:amber:aoss", -+ .gpio = WRT400N_GPIO_LED_ORANGE, ++ .name = "tl-wa901nd-v2:green:system", ++ .gpio = TL_WA901ND_V2_GPIO_LED_SYSTEM, + .active_low = 1, + }, { -+ .name = "wrt400n:green:wlan", -+ .gpio = WRT400N_GPIO_LED_WLAN, -+ .active_low = 1, ++ .name = "tl-wa901nd-v2:green:qss", ++ .gpio = TL_WA901ND_V2_GPIO_LED_QSS, + }, { -+ .name = "wrt400n:green:power", -+ .gpio = WRT400N_GPIO_LED_POWER, ++ .name = "tl-wa901nd-v2:green:wlan", ++ .gpio = TL_WA901ND_V2_GPIO_LED_WLAN, + .active_low = 1, + } +}; + -+static struct gpio_button wrt400n_gpio_buttons[] __initdata = { ++static struct gpio_keys_button tl_wa901nd_v2_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = WRT400N_GPIO_BTN_RESET, ++ .debounce_interval = TL_WA901ND_V2_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WA901ND_V2_GPIO_BTN_RESET, + .active_low = 1, -+ } , { -+ .desc = "wlsec", ++ }, { ++ .desc = "qss", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = WRT400N_GPIO_BTN_WLSEC, ++ .debounce_interval = TL_WA901ND_V2_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WA901ND_V2_GPIO_BTN_QSS, + .active_low = 1, + } +}; + -+static void __init wrt400n_setup(void) ++static void __init tl_wa901nd_v2_setup(void) +{ -+ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); -+ u8 mac[6]; -+ int i; -+ -+ memcpy(mac, art + WRT400N_MAC_ADDR_OFFSET, 6); -+ for (i = 5; i >= 3; i--) -+ if (++mac[i] != 0x00) break; ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ ar71xx_set_mac_base(mac); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); + ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = 0x00001000; + ar71xx_add_device_mdio(0x0); + -+ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth0_data.speed = SPEED_100; -+ ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; -+ ar71xx_eth1_data.phy_mask = 0x10; -+ ++ ar71xx_eth0_data.reset_bit = RESET_MODULE_GE0_MAC | ++ RESET_MODULE_GE0_PHY; + ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); + -+ ar71xx_add_device_m25p80(&wrt400n_flash_data); ++ ar71xx_add_device_m25p80(&tl_wa901nd_v2_flash_data); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wrt400n_leds_gpio), -+ wrt400n_leds_gpio); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wa901nd_v2_leds_gpio), ++ tl_wa901nd_v2_leds_gpio); + -+ ar71xx_add_device_gpio_buttons(-1, WRT400N_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wrt400n_gpio_buttons), -+ wrt400n_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, TL_WA901ND_V2_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wa901nd_v2_gpio_keys), ++ tl_wa901nd_v2_gpio_keys); + -+ ap94_pci_init(art + WRT400N_CALDATA0_OFFSET, NULL, -+ art + WRT400N_CALDATA1_OFFSET, NULL); ++ ar9xxx_add_device_wmac(eeprom, mac); +} + -+MIPS_MACHINE(AR71XX_MACH_WRT400N, "WRT400N", "Linksys WRT400N", wrt400n_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-g300nh.c linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-g300nh.c ---- linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-g300nh.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-g300nh.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,265 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_WA901ND_V2, "TL-WA901ND-v2", ++ "TP-LINK TL-WA901ND v2", tl_wa901nd_v2_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr1043nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr1043nd.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr1043nd.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr1043nd.c 2011-08-24 02:41:55.587990766 +0200 +@@ -0,0 +1,156 @@ +/* -+ * Buffalo WZR-HP-G300NH board support ++ * TP-LINK TL-WR1043ND board support + * -+ * Copyright (C) 2010 Gabor Juhos ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include +#include +#include -+#include -+#include -+ -+#include ++#include ++#include +#include -+#include + +#include "machtype.h" +#include "devices.h" -+#include "dev-ar913x-wmac.h" ++#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" +#include "dev-gpio-buttons.h" +#include "dev-leds-gpio.h" +#include "dev-usb.h" + -+#define WZRHPG300NH_GPIO_LED_USB 0 -+#define WZRHPG300NH_GPIO_LED_DIAG 1 -+#define WZRHPG300NH_GPIO_LED_WIRELESS 6 -+#define WZRHPG300NH_GPIO_LED_SECURITY 17 -+#define WZRHPG300NH_GPIO_LED_ROUTER 18 -+ -+#define WZRHPG300NH_GPIO_RTL8366_SDA 19 -+#define WZRHPG300NH_GPIO_RTL8366_SCK 20 -+ -+#define WZRHPG300NH_GPIO_74HC153_S0 9 -+#define WZRHPG300NH_GPIO_74HC153_S1 11 -+#define WZRHPG300NH_GPIO_74HC153_1Y 12 -+#define WZRHPG300NH_GPIO_74HC153_2Y 14 ++#define TL_WR1043ND_GPIO_LED_USB 1 ++#define TL_WR1043ND_GPIO_LED_SYSTEM 2 ++#define TL_WR1043ND_GPIO_LED_QSS 5 ++#define TL_WR1043ND_GPIO_LED_WLAN 9 + -+#define WZRHPG300NH_GPIO_EXP_BASE 32 -+#define WZRHPG300NH_GPIO_BTN_AOSS (WZRHPG300NH_GPIO_EXP_BASE + 0) -+#define WZRHPG300NH_GPIO_BTN_RESET (WZRHPG300NH_GPIO_EXP_BASE + 1) -+#define WZRHPG300NH_GPIO_BTN_ROUTER_ON (WZRHPG300NH_GPIO_EXP_BASE + 2) -+#define WZRHPG300NH_GPIO_BTN_QOS_ON (WZRHPG300NH_GPIO_EXP_BASE + 3) -+#define WZRHPG300NH_GPIO_BTN_USB (WZRHPG300NH_GPIO_EXP_BASE + 5) -+#define WZRHPG300NH_GPIO_BTN_ROUTER_AUTO (WZRHPG300NH_GPIO_EXP_BASE + 6) -+#define WZRHPG300NH_GPIO_BTN_QOS_OFF (WZRHPG300NH_GPIO_EXP_BASE + 7) ++#define TL_WR1043ND_GPIO_BTN_RESET 3 ++#define TL_WR1043ND_GPIO_BTN_QSS 7 + -+#define WZRHPG300NH_BUTTONS_POLL_INTERVAL 20 ++#define TL_WR1043ND_GPIO_RTL8366_SDA 18 ++#define TL_WR1043ND_GPIO_RTL8366_SCK 19 + -+#define WZRHPG300NH_MAC_OFFSET 0x20c ++#define TL_WR1043ND_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WR1043ND_KEYS_DEBOUNCE_INTERVAL (3 * TL_WR1043ND_KEYS_POLL_INTERVAL) + +#ifdef CONFIG_MTD_PARTITIONS -+static struct mtd_partition wzrhpg300nh_flash_partitions[] = { ++static struct mtd_partition tl_wr1043nd_partitions[] = { + { + .name = "u-boot", + .offset = 0, -+ .size = 0x0040000, -+ .mask_flags = MTD_WRITEABLE, -+ }, { -+ .name = "u-boot-env", -+ .offset = 0x0040000, -+ .size = 0x0020000, ++ .size = 0x020000, + .mask_flags = MTD_WRITEABLE, + }, { + .name = "kernel", -+ .offset = 0x0060000, -+ .size = 0x0100000, ++ .offset = 0x020000, ++ .size = 0x140000, + }, { + .name = "rootfs", -+ .offset = 0x0160000, -+ .size = 0x1e60000, -+ }, { -+ .name = "user_property", -+ .offset = 0x1fc0000, -+ .size = 0x0020000, -+ .mask_flags = MTD_WRITEABLE, ++ .offset = 0x160000, ++ .size = 0x690000, + }, { + .name = "art", -+ .offset = 0x1fe0000, -+ .size = 0x0020000, ++ .offset = 0x7f0000, ++ .size = 0x010000, + .mask_flags = MTD_WRITEABLE, + }, { + .name = "firmware", -+ .offset = 0x0060000, -+ .size = 0x1f60000, ++ .offset = 0x020000, ++ .size = 0x7d0000, + } +}; +#endif /* CONFIG_MTD_PARTITIONS */ + -+static struct ar91xx_flash_platform_data wzrhpg300nh_flash_data = { -+ .width = 2, ++static struct flash_platform_data tl_wr1043nd_flash_data = { +#ifdef CONFIG_MTD_PARTITIONS -+ .parts = wzrhpg300nh_flash_partitions, -+ .nr_parts = ARRAY_SIZE(wzrhpg300nh_flash_partitions), ++ .parts = tl_wr1043nd_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wr1043nd_partitions), +#endif +}; + -+#define WZRHPG300NH_FLASH_BASE 0x1e000000 -+#define WZRHPG300NH_FLASH_SIZE (32 * 1024 * 1024) -+ -+static struct resource wzrhpg300nh_flash_resources[] = { -+ [0] = { -+ .start = WZRHPG300NH_FLASH_BASE, -+ .end = WZRHPG300NH_FLASH_BASE + WZRHPG300NH_FLASH_SIZE - 1, -+ .flags = IORESOURCE_MEM, -+ }, -+}; -+ -+static struct platform_device wzrhpg300nh_flash_device = { -+ .name = "ar91xx-flash", -+ .id = -1, -+ .resource = wzrhpg300nh_flash_resources, -+ .num_resources = ARRAY_SIZE(wzrhpg300nh_flash_resources), -+ .dev = { -+ .platform_data = &wzrhpg300nh_flash_data, -+ } -+}; -+ -+static struct gpio_led wzrhpg300nh_leds_gpio[] __initdata = { ++static struct gpio_led tl_wr1043nd_leds_gpio[] __initdata = { + { -+ .name = "wzr-hp-g300nh:orange:security", -+ .gpio = WZRHPG300NH_GPIO_LED_SECURITY, ++ .name = "tl-wr1043nd:green:usb", ++ .gpio = TL_WR1043ND_GPIO_LED_USB, + .active_low = 1, + }, { -+ .name = "wzr-hp-g300nh:green:wireless", -+ .gpio = WZRHPG300NH_GPIO_LED_WIRELESS, -+ .active_low = 1, -+ }, { -+ .name = "wzr-hp-g300nh:green:router", -+ .gpio = WZRHPG300NH_GPIO_LED_ROUTER, ++ .name = "tl-wr1043nd:green:system", ++ .gpio = TL_WR1043ND_GPIO_LED_SYSTEM, + .active_low = 1, + }, { -+ .name = "wzr-hp-g300nh:red:diag", -+ .gpio = WZRHPG300NH_GPIO_LED_DIAG, -+ .active_low = 1, ++ .name = "tl-wr1043nd:green:qss", ++ .gpio = TL_WR1043ND_GPIO_LED_QSS, ++ .active_low = 0, + }, { -+ .name = "wzr-hp-g300nh:blue:usb", -+ .gpio = WZRHPG300NH_GPIO_LED_USB, ++ .name = "tl-wr1043nd:green:wlan", ++ .gpio = TL_WR1043ND_GPIO_LED_WLAN, + .active_low = 1, + } +}; + -+static struct gpio_button wzrhpg300nh_gpio_buttons[] __initdata = { ++static struct gpio_keys_button tl_wr1043nd_gpio_keys[] __initdata = { + { + .desc = "reset", + .type = EV_KEY, + .code = KEY_RESTART, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_RESET, ++ .debounce_interval = TL_WR1043ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR1043ND_GPIO_BTN_RESET, + .active_low = 1, + }, { -+ .desc = "aoss", ++ .desc = "qss", + .type = EV_KEY, + .code = KEY_WPS_BUTTON, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_AOSS, -+ .active_low = 1, -+ }, { -+ .desc = "usb", -+ .type = EV_KEY, -+ .code = BTN_2, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_USB, ++ .debounce_interval = TL_WR1043ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR1043ND_GPIO_BTN_QSS, + .active_low = 1, -+ }, { -+ .desc = "qos_on", -+ .type = EV_KEY, -+ .code = BTN_3, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_QOS_ON, -+ .active_low = 0, -+ }, { -+ .desc = "qos_off", -+ .type = EV_KEY, -+ .code = BTN_4, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_QOS_OFF, -+ .active_low = 0, -+ }, { -+ .desc = "router_on", -+ .type = EV_KEY, -+ .code = BTN_5, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_ROUTER_ON, -+ .active_low = 0, -+ }, { -+ .desc = "router_auto", -+ .type = EV_KEY, -+ .code = BTN_6, -+ .threshold = 3, -+ .gpio = WZRHPG300NH_GPIO_BTN_ROUTER_AUTO, -+ .active_low = 0, -+ } -+}; -+ -+static struct nxp_74hc153_platform_data wzrhpg300nh_74hc153_data = { -+ .gpio_base = WZRHPG300NH_GPIO_EXP_BASE, -+ .gpio_pin_s0 = WZRHPG300NH_GPIO_74HC153_S0, -+ .gpio_pin_s1 = WZRHPG300NH_GPIO_74HC153_S1, -+ .gpio_pin_1y = WZRHPG300NH_GPIO_74HC153_1Y, -+ .gpio_pin_2y = WZRHPG300NH_GPIO_74HC153_2Y, -+}; -+ -+static struct platform_device wzrhpg300nh_74hc153_device = { -+ .name = NXP_74HC153_DRIVER_NAME, -+ .id = -1, -+ .dev = { -+ .platform_data = &wzrhpg300nh_74hc153_data, + } +}; + -+static struct rtl8366s_platform_data wzrhpg300nh_rtl8366s_data = { -+ .gpio_sda = WZRHPG300NH_GPIO_RTL8366_SDA, -+ .gpio_sck = WZRHPG300NH_GPIO_RTL8366_SCK, ++static struct rtl8366_platform_data tl_wr1043nd_rtl8366rb_data = { ++ .gpio_sda = TL_WR1043ND_GPIO_RTL8366_SDA, ++ .gpio_sck = TL_WR1043ND_GPIO_RTL8366_SCK, +}; + -+static struct platform_device wzrhpg300nh_rtl8366s_device = { -+ .name = RTL8366S_DRIVER_NAME, ++static struct platform_device tl_wr1043nd_rtl8366rb_device = { ++ .name = RTL8366RB_DRIVER_NAME, + .id = -1, + .dev = { -+ .platform_data = &wzrhpg300nh_rtl8366s_data, ++ .platform_data = &tl_wr1043nd_rtl8366rb_data, + } +}; + -+static void __init wzrhpg300nh_setup(void) ++static void __init tl_wr1043nd_setup(void) +{ ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); + u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ ar71xx_set_mac_base(eeprom + WZRHPG300NH_MAC_OFFSET); -+ -+ ar71xx_eth0_pll_data.pll_1000 = 0x1e000100; -+ ar71xx_eth0_data.mii_bus_dev = &wzrhpg300nh_rtl8366s_device.dev; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.mii_bus_dev = &tl_wr1043nd_rtl8366rb_device.dev; + ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; + ar71xx_eth0_data.speed = SPEED_1000; + ar71xx_eth0_data.duplex = DUPLEX_FULL; -+ -+ ar71xx_eth1_pll_data.pll_1000 = 0x1e000100; -+ ar71xx_eth1_data.mii_bus_dev = &wzrhpg300nh_rtl8366s_device.dev; -+ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; -+ ar71xx_eth1_data.phy_mask = 0x10; ++ ar71xx_eth0_pll_data.pll_1000 = 0x1a000000; + + ar71xx_add_device_eth(0); -+ ar71xx_add_device_eth(1); + + ar71xx_add_device_usb(); -+ ar913x_add_device_wmac(eeprom, NULL); + -+ platform_device_register(&wzrhpg300nh_74hc153_device); -+ platform_device_register(&wzrhpg300nh_flash_device); -+ platform_device_register(&wzrhpg300nh_rtl8366s_device); ++ ar71xx_add_device_m25p80(&tl_wr1043nd_flash_data); + -+ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wzrhpg300nh_leds_gpio), -+ wzrhpg300nh_leds_gpio); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr1043nd_leds_gpio), ++ tl_wr1043nd_leds_gpio); ++ ++ platform_device_register(&tl_wr1043nd_rtl8366rb_device); + -+ ar71xx_add_device_gpio_buttons(-1, WZRHPG300NH_BUTTONS_POLL_INTERVAL, -+ ARRAY_SIZE(wzrhpg300nh_gpio_buttons), -+ wzrhpg300nh_gpio_buttons); ++ ar71xx_register_gpio_keys_polled(-1, TL_WR1043ND_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wr1043nd_gpio_keys), ++ tl_wr1043nd_gpio_keys); + ++ ar9xxx_add_device_wmac(eeprom, mac); +} + -+MIPS_MACHINE(AR71XX_MACH_WZR_HP_G300NH, "WZR-HP-G300NH", -+ "Buffalo WZR-HP-G300NH", wzrhpg300nh_setup); -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/machtype.h linux-2.6.39/arch/mips/ar71xx/machtype.h ---- linux-2.6.39.orig/arch/mips/ar71xx/machtype.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/machtype.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,60 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_WR1043ND, "TL-WR1043ND", "TP-LINK TL-WR1043ND", ++ tl_wr1043nd_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr741nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr741nd.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr741nd.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr741nd.c 2011-08-24 02:41:55.587990766 +0200 +@@ -0,0 +1,135 @@ +/* -+ * Atheros AR71xx machine type definitions ++ * TP-LINK TL-WR741ND board support + * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009-2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#ifndef _AR71XX_MACHTYPE_H -+#define _AR71XX_MACHTYPE_H ++#include ++#include + -+#include ++#include + -+enum ar71xx_mach_type { -+ AR71XX_MACH_GENERIC = 0, -+ AR71XX_MACH_AP81, /* Atheros AP81 */ -+ AR71XX_MACH_AP83, /* Atheros AP83 */ -+ AR71XX_MACH_AW_NR580, /* AzureWave AW-NR580 */ -+ AR71XX_MACH_DIR_600_A1, /* D-Link DIR-600 rev. A1 */ -+ AR71XX_MACH_DIR_615_C1, /* D-Link DIR-615 rev. C1 */ -+ AR71XX_MACH_DIR_825_B1, /* D-Link DIR-825 rev. B1 */ -+ AR71XX_MACH_RB_411, /* MikroTik RouterBOARD 411/411A/411AH */ -+ AR71XX_MACH_RB_411U, /* MikroTik RouterBOARD 411U */ -+ AR71XX_MACH_RB_433, /* MikroTik RouterBOARD 433/433AH */ -+ AR71XX_MACH_RB_433U, /* MikroTik RouterBOARD 433UAH */ -+ AR71XX_MACH_RB_450, /* MikroTik RouterBOARD 450 */ -+ AR71XX_MACH_RB_450G, /* MikroTik RouterBOARD 450G */ -+ AR71XX_MACH_RB_493, /* Mikrotik RouterBOARD 493/493AH */ -+ AR71XX_MACH_RB_750, /* MikroTik RouterBOARD 750 */ -+ AR71XX_MACH_PB42, /* Atheros PB42 */ -+ AR71XX_MACH_PB44, /* Atheros PB44 */ -+ AR71XX_MACH_PB92, /* Atheros PB92 */ -+ AR71XX_MACH_MZK_W04NU, /* Planex MZK-W04NU */ -+ AR71XX_MACH_MZK_W300NH, /* Planex MZK-W300NH */ -+ AR71XX_MACH_NBG460N, /* Zyxel NBG460N/550N/550NH */ -+ AR71XX_MACH_TEW_632BRP, /* TRENDnet TEW-632BRP */ -+ AR71XX_MACH_TL_WR741ND, /* TP-LINK TL-WR741ND */ -+ AR71XX_MACH_TL_WR841N_V1, /* TP-LINK TL-WR841N v1 */ -+ AR71XX_MACH_TL_WR941ND, /* TP-LINK TL-WR941ND */ -+ AR71XX_MACH_TL_WR1043ND, /* TP-LINK TL-WR1041ND */ -+ AR71XX_MACH_UBNT_LSSR71, /* Ubiquiti LS-SR71 */ -+ AR71XX_MACH_UBNT_LSX, /* Ubiquiti LSX */ -+ AR71XX_MACH_UBNT_RS, /* Ubiquiti RouterStation */ -+ AR71XX_MACH_UBNT_AR71XX, /* Ubiquiti AR71xx-based board */ -+ AR71XX_MACH_UBNT_RSPRO, /* Ubiquiti RouterStation Pro */ -+ AR71XX_MACH_UBNT_BULLET_M, /* Ubiquiti Bullet M */ -+ AR71XX_MACH_UBNT_ROCKET_M, /* Ubiquiti Rocket M */ -+ AR71XX_MACH_UBNT_NANO_M, /* Ubiquiti NanoStation M */ -+ AR71XX_MACH_WNDR3700, /* NETGEAR WNDR3700 */ -+ AR71XX_MACH_WNR2000, /* NETGEAR WNR2000 */ -+ AR71XX_MACH_WP543, /* Compex WP543 */ -+ AR71XX_MACH_WRT160NL, /* Linksys WRT160NL */ -+ AR71XX_MACH_WRT400N, /* Linksys WRT400N */ -+ AR71XX_MACH_WZR_HP_G300NH, /* Buffalo WZR-HP-G300NH */ ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ap91-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++ ++#define TL_WR741ND_GPIO_LED_QSS 0 ++#define TL_WR741ND_GPIO_LED_SYSTEM 1 ++ ++#define TL_WR741ND_GPIO_BTN_RESET 11 ++#define TL_WR741ND_GPIO_BTN_QSS 12 ++ ++#define TL_WR741ND_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WR741ND_KEYS_DEBOUNCE_INTERVAL (3 * TL_WR741ND_KEYS_POLL_INTERVAL) ++ ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition tl_wr741nd_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x020000, ++ .size = 0x140000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x160000, ++ .size = 0x290000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x020000, ++ .size = 0x3d0000, ++ } +}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#endif /* _AR71XX_MACHTYPE_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/nvram.c linux-2.6.39/arch/mips/ar71xx/nvram.c ---- linux-2.6.39.orig/arch/mips/ar71xx/nvram.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/nvram.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,75 @@ -+/* -+ * Atheros AR71xx minimal nvram support -+ * -+ * Copyright (C) 2009 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++static struct flash_platform_data tl_wr741nd_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = tl_wr741nd_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wr741nd_partitions), ++#endif ++}; + -+#include -+#include -+#include -+#include -+#include ++static struct gpio_led tl_wr741nd_leds_gpio[] __initdata = { ++ { ++ .name = "tl-wr741nd:green:system", ++ .gpio = TL_WR741ND_GPIO_LED_SYSTEM, ++ .active_low = 1, ++ }, { ++ .name = "tl-wr741nd:green:qss", ++ .gpio = TL_WR741ND_GPIO_LED_QSS, ++ .active_low = 1, ++ } ++}; + -+#include "nvram.h" ++static struct gpio_keys_button tl_wr741nd_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = TL_WR741ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR741ND_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "qss", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = TL_WR741ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR741ND_GPIO_BTN_QSS, ++ .active_low = 1, ++ } ++}; + -+char *nvram_find_var(const char *name, const char *buf, unsigned buf_len) ++static void __init tl_wr741nd_setup(void) +{ -+ unsigned len = strlen(name); -+ char *cur, *last; ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + -+ if (buf_len == 0 || len == 0) -+ return NULL; ++ ar71xx_add_device_m25p80(&tl_wr741nd_flash_data); + -+ if (buf_len < len) -+ return NULL; ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr741nd_leds_gpio), ++ tl_wr741nd_leds_gpio); + -+ if (len == 1) -+ return memchr(buf, (int) *name, buf_len); ++ ar71xx_register_gpio_keys_polled(-1, TL_WR741ND_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wr741nd_gpio_keys), ++ tl_wr741nd_gpio_keys); + -+ last = (char *) buf + buf_len - len; -+ for (cur = (char *) buf; cur <= last; cur++) -+ if (cur[0] == name[0] && memcmp(cur, name, len) == 0) -+ return cur + len; -+ -+ return NULL; -+} -+ -+int nvram_parse_mac_addr(const char *nvram, unsigned nvram_len, -+ const char *name, char *mac) -+{ -+ char *buf; -+ char *mac_str; -+ int ret; -+ int t; -+ -+ buf = vmalloc(nvram_len); -+ if (!buf) -+ return -ENOMEM; -+ -+ memcpy(buf, nvram, nvram_len); -+ buf[nvram_len - 1] = '\0'; ++ ar71xx_eth1_data.has_ar7240_switch = 1; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); + -+ mac_str = nvram_find_var(name, buf, nvram_len); -+ if (!mac_str) { -+ ret = -EINVAL; -+ goto free; -+ } ++ /* WAN port */ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(4); + -+ t = sscanf(mac_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx", -+ &mac[0], &mac[1], &mac[2], &mac[3], &mac[4], &mac[5]); ++ /* LAN ports */ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ if (t != 6) { -+ ret = -EINVAL; -+ goto free; -+ } ++ ar71xx_add_device_mdio(0x0); ++ ar71xx_add_device_eth(1); ++ ar71xx_add_device_eth(0); + -+ ret = 0; ++ ap91_pci_setup_wmac_led_pin(1); + -+ free: -+ vfree(buf); -+ return ret; ++ ap91_pci_init(ee, mac); +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/nvram.h linux-2.6.39/arch/mips/ar71xx/nvram.h ---- linux-2.6.39.orig/arch/mips/ar71xx/nvram.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/nvram.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,19 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_WR741ND, "TL-WR741ND", "TP-LINK TL-WR741ND", ++ tl_wr741nd_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr841n.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr841n.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr841n.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr841n.c 2011-08-24 02:41:55.597982750 +0200 +@@ -0,0 +1,144 @@ +/* -+ * Atheros AR71xx minimal nvram support ++ * TP-LINK TL-WR841N board support + * + * Copyright (C) 2009 Gabor Juhos + * @@ -7545,7553 +7700,8833 @@ diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/nvram.h linux-2.6.39/arch/mips/ar71 + * by the Free Software Foundation. + */ + -+#ifndef _AR71XX_NVRAM_H -+#define _AR71XX_NVRAM_H -+ -+char *nvram_find_var(const char *name, const char *buf, -+ unsigned buf_len) __init; -+int nvram_parse_mac_addr(const char *nvram, unsigned nvram_len, -+ const char *name, char *mac) __init; ++#include ++#include + -+#endif /* _AR71XX_NVRAM_H */ -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/pci.c linux-2.6.39/arch/mips/ar71xx/pci.c ---- linux-2.6.39.orig/arch/mips/ar71xx/pci.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/pci.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,93 @@ -+/* -+ * Atheros AR71xx PCI setup code -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++#include + -+#include ++#include "machtype.h" ++#include "devices.h" ++#include "dev-dsa.h" ++#include "dev-m25p80.h" ++#include "dev-gpio-buttons.h" ++#include "dev-pb42-pci.h" ++#include "dev-leds-gpio.h" + -+#include ++#define TL_WR841ND_V1_GPIO_LED_SYSTEM 2 ++#define TL_WR841ND_V1_GPIO_LED_QSS_GREEN 4 ++#define TL_WR841ND_V1_GPIO_LED_QSS_RED 5 + -+#include -+#include ++#define TL_WR841ND_V1_GPIO_BTN_RESET 3 ++#define TL_WR841ND_V1_GPIO_BTN_QSS 7 + -+unsigned ar71xx_pci_nr_irqs __initdata; -+struct ar71xx_pci_irq *ar71xx_pci_irq_map __initdata; ++#define TL_WR841ND_V1_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WR841ND_V1_KEYS_DEBOUNCE_INTERVAL \ ++ (3 * TL_WR841ND_V1_KEYS_POLL_INTERVAL) + -+int (*ar71xx_pci_plat_dev_init)(struct pci_dev *dev); ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition tl_wr841n_v1_partitions[] = { ++ { ++ .name = "redboot", ++ .offset = 0, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x020000, ++ .size = 0x140000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x160000, ++ .size = 0x280000, ++ }, { ++ .name = "config", ++ .offset = 0x3e0000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x020000, ++ .size = 0x3c0000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+static int ar71xx_be_handler(struct pt_regs *regs, int is_fixup) -+{ -+ int err = 0; ++static struct flash_platform_data tl_wr841n_v1_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = tl_wr841n_v1_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wr841n_v1_partitions), ++#endif ++}; + -+ err = ar71xx_pci_be_handler(is_fixup); ++static struct gpio_led tl_wr841n_v1_leds_gpio[] __initdata = { ++ { ++ .name = "tl-wr841n:green:system", ++ .gpio = TL_WR841ND_V1_GPIO_LED_SYSTEM, ++ .active_low = 1, ++ }, { ++ .name = "tl-wr841n:red:qss", ++ .gpio = TL_WR841ND_V1_GPIO_LED_QSS_RED, ++ }, { ++ .name = "tl-wr841n:green:qss", ++ .gpio = TL_WR841ND_V1_GPIO_LED_QSS_GREEN, ++ } ++}; + -+ return (is_fixup && !err) ? MIPS_BE_FIXUP : MIPS_BE_FATAL; -+} ++static struct gpio_keys_button tl_wr841n_v1_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = TL_WR841ND_V1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR841ND_V1_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "qss", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = TL_WR841ND_V1_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR841ND_V1_GPIO_BTN_QSS, ++ .active_low = 1, ++ } ++}; + -+int pcibios_plat_dev_init(struct pci_dev *dev) -+{ -+ if (ar71xx_pci_plat_dev_init) -+ return ar71xx_pci_plat_dev_init(dev); ++static struct dsa_chip_data tl_wr841n_v1_dsa_chip = { ++ .port_names[0] = "wan", ++ .port_names[1] = "lan1", ++ .port_names[2] = "lan2", ++ .port_names[3] = "lan3", ++ .port_names[4] = "lan4", ++ .port_names[5] = "cpu", ++}; + -+ return 0; -+} ++static struct dsa_platform_data tl_wr841n_v1_dsa_data = { ++ .nr_chips = 1, ++ .chip = &tl_wr841n_v1_dsa_chip, ++}; + -+int __init pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, uint8_t pin) ++static void __init tl_wr841n_v1_setup(void) +{ -+ int ret = 0; -+ -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ ret = ar71xx_pcibios_map_irq(dev, slot, pin); -+ break; -+ -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ret = ar724x_pcibios_map_irq(dev, slot, pin); -+ break; ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); + -+ default: -+ break; -+ } ++ ar71xx_add_device_mdio(0x0); + -+ return ret; -+} ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+int __init ar71xx_pci_init(unsigned nr_irqs, struct ar71xx_pci_irq *map) -+{ -+ int ret = 0; ++ ar71xx_add_device_eth(0); + -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ board_be_handler = ar71xx_be_handler; -+ ret = ar71xx_pcibios_init(); -+ break; ++ ar71xx_add_device_dsa(0, &tl_wr841n_v1_dsa_data); + -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ret = ar724x_pcibios_init(); -+ break; ++ ar71xx_add_device_m25p80(&tl_wr841n_v1_flash_data); + -+ default: -+ return 0; -+ } ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr841n_v1_leds_gpio), ++ tl_wr841n_v1_leds_gpio); + -+ ar71xx_pci_nr_irqs = nr_irqs; -+ ar71xx_pci_irq_map = map; ++ ar71xx_register_gpio_keys_polled(-1, TL_WR841ND_V1_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wr841n_v1_gpio_keys), ++ tl_wr841n_v1_gpio_keys); + -+ return ret; ++ pb42_pci_init(); +} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/prom.c linux-2.6.39/arch/mips/ar71xx/prom.c ---- linux-2.6.39.orig/arch/mips/ar71xx/prom.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/prom.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,105 @@ ++ ++MIPS_MACHINE(AR71XX_MACH_TL_WR841N_V1, "TL-WR841N-v1.5", "TP-LINK TL-WR841N v1", ++ tl_wr841n_v1_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr941nd.c linux-2.6.39/arch/mips/ar71xx/mach-tl-wr941nd.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-tl-wr941nd.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-tl-wr941nd.c 2011-08-24 02:41:55.597982750 +0200 +@@ -0,0 +1,147 @@ +/* -+ * Atheros AR71xx SoC specific prom routines ++ * TP-LINK TL-WR941ND board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009-2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include -+ -+#include -+#include ++#include ++#include + +#include + -+static inline int is_valid_ram_addr(void *addr) -+{ -+ if (((u32) addr > KSEG0) && -+ ((u32) addr < (KSEG0 + AR71XX_MEM_SIZE_MAX))) -+ return 1; -+ -+ if (((u32) addr > KSEG1) && -+ ((u32) addr < (KSEG1 + AR71XX_MEM_SIZE_MAX))) -+ return 1; -+ -+ return 0; -+} ++#include "machtype.h" ++#include "devices.h" ++#include "dev-dsa.h" ++#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" + -+static void __init ar71xx_prom_append_cmdline(const char *name, -+ const char *value) -+{ -+ char buf[COMMAND_LINE_SIZE]; ++#define TL_WR941ND_GPIO_LED_SYSTEM 2 ++#define TL_WR941ND_GPIO_LED_QSS_RED 4 ++#define TL_WR941ND_GPIO_LED_QSS_GREEN 5 ++#define TL_WR941ND_GPIO_LED_WLAN 9 + -+ snprintf(buf, sizeof(buf), " %s=%s", name, value); -+ strlcat(arcs_cmdline, buf, sizeof(arcs_cmdline)); -+} ++#define TL_WR941ND_GPIO_BTN_RESET 3 ++#define TL_WR941ND_GPIO_BTN_QSS 7 + -+static void __init ar71xx_prom_find_env(char **envp, const char *name) -+{ -+ int len = strlen(name); -+ char **p; ++#define TL_WR941ND_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define TL_WR941ND_KEYS_DEBOUNCE_INTERVAL (3 * TL_WR941ND_KEYS_POLL_INTERVAL) + -+ if (!is_valid_ram_addr(envp)) -+ return; ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition tl_wr941nd_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x020000, ++ .size = 0x140000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x160000, ++ .size = 0x290000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x020000, ++ .size = 0x3d0000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+ for (p = envp; is_valid_ram_addr(*p); p++) { -+ if (strncmp(name, *p, len) == 0 && (*p)[len] == '=') { -+ ar71xx_prom_append_cmdline(name, *p + len + 1); -+ break; -+ } ++static struct flash_platform_data tl_wr941nd_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = tl_wr941nd_partitions, ++ .nr_parts = ARRAY_SIZE(tl_wr941nd_partitions), ++#endif ++}; + -+ /* RedBoot env comes in pointer pairs - key, value */ -+ if (strncmp(name, *p, len) == 0 && (*p)[len] == 0) -+ if (is_valid_ram_addr(*(++p))) { -+ ar71xx_prom_append_cmdline(name, *p); -+ break; -+ } ++static struct gpio_led tl_wr941nd_leds_gpio[] __initdata = { ++ { ++ .name = "tl-wr941nd:green:system", ++ .gpio = TL_WR941ND_GPIO_LED_SYSTEM, ++ .active_low = 1, ++ }, { ++ .name = "tl-wr941nd:red:qss", ++ .gpio = TL_WR941ND_GPIO_LED_QSS_RED, ++ }, { ++ .name = "tl-wr941nd:green:qss", ++ .gpio = TL_WR941ND_GPIO_LED_QSS_GREEN, ++ }, { ++ .name = "tl-wr941nd:green:wlan", ++ .gpio = TL_WR941ND_GPIO_LED_WLAN, ++ .active_low = 1, + } -+} ++}; + -+static int inline ar71xx_use__image_cmdline(void) { return 0; } ++static struct gpio_keys_button tl_wr941nd_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = TL_WR941ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR941ND_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "qss", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = TL_WR941ND_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = TL_WR941ND_GPIO_BTN_QSS, ++ .active_low = 1, ++ } ++}; + -+static __init void ar71xx_prom_init_cmdline(int argc, char **argv) -+{ -+ int i; ++static struct dsa_chip_data tl_wr941nd_dsa_chip = { ++ .port_names[0] = "wan", ++ .port_names[1] = "lan1", ++ .port_names[2] = "lan2", ++ .port_names[3] = "lan3", ++ .port_names[4] = "lan4", ++ .port_names[5] = "cpu", ++}; + -+ if (ar71xx_use__image_cmdline()) -+ return; ++static struct dsa_platform_data tl_wr941nd_dsa_data = { ++ .nr_chips = 1, ++ .chip = &tl_wr941nd_dsa_chip, ++}; + -+ if (!is_valid_ram_addr(argv)) -+ return; ++static void __init tl_wr941nd_setup(void) ++{ ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f01fc00); ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+ for (i = 0; i < argc; i++) -+ if (is_valid_ram_addr(argv[i])) { -+ strlcat(arcs_cmdline, " ", sizeof(arcs_cmdline)); -+ strlcat(arcs_cmdline, argv[i], sizeof(arcs_cmdline)); -+ } -+} ++ ar71xx_add_device_mdio(0x0); + -+void __init prom_init(void) -+{ -+ char **envp; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+ printk(KERN_DEBUG "prom: fw_arg0=%08x, fw_arg1=%08x, " -+ "fw_arg2=%08x, fw_arg3=%08x\n", -+ (unsigned int)fw_arg0, (unsigned int)fw_arg1, -+ (unsigned int)fw_arg2, (unsigned int)fw_arg3); ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_dsa(0, &tl_wr941nd_dsa_data); + ++ ar71xx_add_device_m25p80(&tl_wr941nd_flash_data); + -+ ar71xx_prom_init_cmdline(fw_arg0, (char **)fw_arg1); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(tl_wr941nd_leds_gpio), ++ tl_wr941nd_leds_gpio); + -+ envp = (char **)fw_arg2; -+ ar71xx_prom_find_env(envp, "board"); ++ ar71xx_register_gpio_keys_polled(-1, TL_WR941ND_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(tl_wr941nd_gpio_keys), ++ tl_wr941nd_gpio_keys); ++ ar9xxx_add_device_wmac(eeprom, mac); +} + -+void __init prom_free_prom_memory(void) -+{ -+ /* We do not have to prom memory to free */ -+} -diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/setup.c linux-2.6.39/arch/mips/ar71xx/setup.c ---- linux-2.6.39.orig/arch/mips/ar71xx/setup.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/ar71xx/setup.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,310 @@ ++MIPS_MACHINE(AR71XX_MACH_TL_WR941ND, "TL-WR941ND", "TP-LINK TL-WR941ND", ++ tl_wr941nd_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/machtype.h linux-2.6.39/arch/mips/ar71xx/machtype.h +--- linux-2.6.39.orig/arch/mips/ar71xx/machtype.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/machtype.h 2011-08-24 02:41:55.597982750 +0200 +@@ -0,0 +1,75 @@ +/* -+ * Atheros AR71xx SoC specific setup ++ * Atheros AR71xx machine type definitions + * -+ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008-2010 Gabor Juhos + * Copyright (C) 2008 Imre Kaloz + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include ++#ifndef _AR71XX_MACHTYPE_H ++#define _AR71XX_MACHTYPE_H + -+#include -+#include /* for mips_hpt_frequency */ -+#include /* for _machine_{restart,halt} */ +#include + ++enum ar71xx_mach_type { ++ AR71XX_MACH_GENERIC = 0, ++ AR71XX_MACH_AP121, /* Atheros AP121 */ ++ AR71XX_MACH_AP121_MINI, /* Atheros AP121-MINI */ ++ AR71XX_MACH_AP81, /* Atheros AP81 */ ++ AR71XX_MACH_AP83, /* Atheros AP83 */ ++ AR71XX_MACH_AW_NR580, /* AzureWave AW-NR580 */ ++ AR71XX_MACH_DIR_600_A1, /* D-Link DIR-600 rev. A1 */ ++ AR71XX_MACH_DIR_615_C1, /* D-Link DIR-615 rev. C1 */ ++ AR71XX_MACH_DIR_825_B1, /* D-Link DIR-825 rev. B1 */ ++ AR71XX_MACH_JA76PF, /* jjPlus JA76PF */ ++ AR71XX_MACH_JWAP003, /* jjPlus JWAP003 */ ++ AR71XX_MACH_RB_411, /* MikroTik RouterBOARD 411/411A/411AH */ ++ AR71XX_MACH_RB_411U, /* MikroTik RouterBOARD 411U */ ++ AR71XX_MACH_RB_433, /* MikroTik RouterBOARD 433/433AH */ ++ AR71XX_MACH_RB_433U, /* MikroTik RouterBOARD 433UAH */ ++ AR71XX_MACH_RB_450, /* MikroTik RouterBOARD 450 */ ++ AR71XX_MACH_RB_450G, /* MikroTik RouterBOARD 450G */ ++ AR71XX_MACH_RB_493, /* Mikrotik RouterBOARD 493/493AH */ ++ AR71XX_MACH_RB_750, /* MikroTik RouterBOARD 750 */ ++ AR71XX_MACH_PB42, /* Atheros PB42 */ ++ AR71XX_MACH_PB44, /* Atheros PB44 */ ++ AR71XX_MACH_PB92, /* Atheros PB92 */ ++ AR71XX_MACH_MZK_W04NU, /* Planex MZK-W04NU */ ++ AR71XX_MACH_MZK_W300NH, /* Planex MZK-W300NH */ ++ AR71XX_MACH_NBG460N, /* Zyxel NBG460N/550N/550NH */ ++ AR71XX_MACH_TEW_632BRP, /* TRENDnet TEW-632BRP */ ++ AR71XX_MACH_TL_MR3220, /* TP-LINK TL-MR3220 */ ++ AR71XX_MACH_TL_MR3420, /* TP-LINK TL-MR3420 */ ++ AR71XX_MACH_TL_WA901ND, /* TP-LINK TL-WA901ND */ ++ AR71XX_MACH_TL_WA901ND_V2, /* TP-LINK TL-WA901ND v2 */ ++ AR71XX_MACH_TL_WR741ND, /* TP-LINK TL-WR741ND */ ++ AR71XX_MACH_TL_WR841N_V1, /* TP-LINK TL-WR841N v1 */ ++ AR71XX_MACH_TL_WR941ND, /* TP-LINK TL-WR941ND */ ++ AR71XX_MACH_TL_WR1043ND, /* TP-LINK TL-WR1041ND */ ++ AR71XX_MACH_UBNT_LSSR71, /* Ubiquiti LS-SR71 */ ++ AR71XX_MACH_UBNT_LSX, /* Ubiquiti LSX */ ++ AR71XX_MACH_UBNT_RS, /* Ubiquiti RouterStation */ ++ AR71XX_MACH_UBNT_RSPRO, /* Ubiquiti RouterStation Pro */ ++ AR71XX_MACH_UBNT_BULLET_M, /* Ubiquiti Bullet M */ ++ AR71XX_MACH_UBNT_ROCKET_M, /* Ubiquiti Rocket M */ ++ AR71XX_MACH_UBNT_NANO_M, /* Ubiquiti NanoStation M */ ++ AR71XX_MACH_WNDR3700, /* NETGEAR WNDR3700 */ ++ AR71XX_MACH_WNDR3700V2, /* NETGEAR WNDR3700v2 */ ++ AR71XX_MACH_WNR2000, /* NETGEAR WNR2000 */ ++ AR71XX_MACH_WP543, /* Compex WP543 */ ++ AR71XX_MACH_WRT160NL, /* Linksys WRT160NL */ ++ AR71XX_MACH_WRT400N, /* Linksys WRT400N */ ++ AR71XX_MACH_WZR_HP_AG300H, /* Buffalo WZR-HP-AG300H */ ++ AR71XX_MACH_WZR_HP_G300NH, /* Buffalo WZR-HP-G300NH */ ++ AR71XX_MACH_EAP7660D, /* Senao EAP7660D */ ++ AR71XX_MACH_ZCN_1523H_2, /* Zcomax ZCN-1523H-2-xx */ ++ AR71XX_MACH_ZCN_1523H_5, /* Zcomax ZCN-1523H-5-xx */ ++ AR71XX_MACH_AP96, /* Atheros AP96 */ ++ AR71XX_MACH_UBNT_UNIFI, /* Unifi */ ++ AR71XX_MACH_DB120, /* Atheros DB120 (AR934x based) */ ++}; ++ ++#endif /* _AR71XX_MACHTYPE_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-ubnt.c linux-2.6.39/arch/mips/ar71xx/mach-ubnt.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-ubnt.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-ubnt.c 2011-08-24 02:41:55.597982750 +0200 +@@ -0,0 +1,333 @@ ++/* ++ * Ubiquiti RouterStation support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2008 Ubiquiti ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ +#include + +#include "machtype.h" +#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ap91-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-pb42-pci.h" ++#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define AR71XX_SYS_TYPE_LEN 64 -+#define AR71XX_BASE_FREQ 40000000 -+#define AR91XX_BASE_FREQ 5000000 -+#define AR724X_BASE_FREQ 5000000 -+ -+u32 ar71xx_cpu_freq; -+EXPORT_SYMBOL_GPL(ar71xx_cpu_freq); ++#define UBNT_RS_GPIO_LED_RF 2 ++#define UBNT_RS_GPIO_SW4 8 + -+u32 ar71xx_ahb_freq; -+EXPORT_SYMBOL_GPL(ar71xx_ahb_freq); ++#define UBNT_LS_SR71_GPIO_LED_D25 0 ++#define UBNT_LS_SR71_GPIO_LED_D26 1 ++#define UBNT_LS_SR71_GPIO_LED_D24 2 ++#define UBNT_LS_SR71_GPIO_LED_D23 4 ++#define UBNT_LS_SR71_GPIO_LED_D22 5 ++#define UBNT_LS_SR71_GPIO_LED_D27 6 ++#define UBNT_LS_SR71_GPIO_LED_D28 7 + -+u32 ar71xx_ddr_freq; -+EXPORT_SYMBOL_GPL(ar71xx_ddr_freq); -+ -+enum ar71xx_soc_type ar71xx_soc; -+EXPORT_SYMBOL_GPL(ar71xx_soc); ++#define UBNT_M_GPIO_LED_L1 0 ++#define UBNT_M_GPIO_LED_L2 1 ++#define UBNT_M_GPIO_LED_L3 11 ++#define UBNT_M_GPIO_LED_L4 7 ++#define UBNT_M_GPIO_BTN_RESET 12 + -+static char ar71xx_sys_type[AR71XX_SYS_TYPE_LEN]; ++#define UBNT_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define UBNT_KEYS_DEBOUNCE_INTERVAL (3 * UBNT_KEYS_POLL_INTERVAL) + -+static void ar71xx_restart(char *command) -+{ -+ ar71xx_device_stop(RESET_MODULE_FULL_CHIP); -+ for (;;) -+ if (cpu_wait) -+ cpu_wait(); -+} ++static struct gpio_led ubnt_rs_leds_gpio[] __initdata = { ++ { ++ .name = "ubnt:green:rf", ++ .gpio = UBNT_RS_GPIO_LED_RF, ++ .active_low = 0, ++ } ++}; + -+static void ar71xx_halt(void) -+{ -+ while (1) -+ cpu_wait(); -+} ++static struct gpio_led ubnt_ls_sr71_leds_gpio[] __initdata = { ++ { ++ .name = "ubnt:green:d22", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D22, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:d23", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D23, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:d24", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D24, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:red:d25", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D25, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:red:d26", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D26, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:d27", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D27, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:d28", ++ .gpio = UBNT_LS_SR71_GPIO_LED_D28, ++ .active_low = 0, ++ } ++}; + -+static void __init ar71xx_detect_mem_size(void) -+{ -+ unsigned long size; ++static struct gpio_led ubnt_m_leds_gpio[] __initdata = { ++ { ++ .name = "ubnt:red:link1", ++ .gpio = UBNT_M_GPIO_LED_L1, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:orange:link2", ++ .gpio = UBNT_M_GPIO_LED_L2, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:link3", ++ .gpio = UBNT_M_GPIO_LED_L3, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:link4", ++ .gpio = UBNT_M_GPIO_LED_L4, ++ .active_low = 0, ++ } ++}; + -+ for (size = AR71XX_MEM_SIZE_MIN; size < AR71XX_MEM_SIZE_MAX; -+ size <<= 1 ) { -+ if (!memcmp(ar71xx_detect_mem_size, -+ ar71xx_detect_mem_size + size, 1024)) -+ break; ++static struct gpio_keys_button ubnt_gpio_keys[] __initdata = { ++ { ++ .desc = "sw4", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = UBNT_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = UBNT_RS_GPIO_SW4, ++ .active_low = 1, + } ++}; + -+ add_memory_region(0, size, BOOT_MEM_RAM); -+} ++static struct gpio_keys_button ubnt_m_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = UBNT_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = UBNT_M_GPIO_BTN_RESET, ++ .active_low = 1, ++ } ++}; + -+static void __init ar71xx_detect_sys_type(void) ++static void __init ubnt_generic_setup(void) +{ -+ char *chip = "????"; -+ u32 id; -+ u32 major; -+ u32 minor; -+ u32 rev = 0; ++ ar71xx_add_device_m25p80(NULL); + -+ id = ar71xx_reset_rr(AR71XX_RESET_REG_REV_ID); -+ major = id & REV_ID_MAJOR_MASK; ++ ar71xx_register_gpio_keys_polled(-1, UBNT_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ubnt_gpio_keys), ++ ubnt_gpio_keys); + -+ switch (major) { -+ case REV_ID_MAJOR_AR71XX: -+ minor = id & AR71XX_REV_ID_MINOR_MASK; -+ rev = id >> AR71XX_REV_ID_REVISION_SHIFT; -+ rev &= AR71XX_REV_ID_REVISION_MASK; -+ switch (minor) { -+ case AR71XX_REV_ID_MINOR_AR7130: -+ ar71xx_soc = AR71XX_SOC_AR7130; -+ chip = "7130"; -+ break; ++ pb42_pci_init(); ++} + -+ case AR71XX_REV_ID_MINOR_AR7141: -+ ar71xx_soc = AR71XX_SOC_AR7141; -+ chip = "7141"; -+ break; ++/* ++ * There is Secondary MAC address duplicate problem with some UBNT HW batches. ++ * Do not increase Secondary MAC address by 1 but do workaround ++ * with 'Locally Administrated' bit. ++ */ ++static void __init ubnt_init_secondary_mac(unsigned char *mac_base) ++{ ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac_base, 0); ++ ar71xx_eth1_data.mac_addr[0] |= 0x02; ++} + -+ case AR71XX_REV_ID_MINOR_AR7161: -+ ar71xx_soc = AR71XX_SOC_AR7161; -+ chip = "7161"; -+ break; -+ } -+ break; ++#define UBNT_RS_WAN_PHYMASK BIT(20) ++#define UBNT_RS_LAN_PHYMASK (BIT(16) | BIT(17) | BIT(18) | BIT(19)) + -+ case REV_ID_MAJOR_AR7240: -+ ar71xx_soc = AR71XX_SOC_AR7240; -+ chip = "7240"; -+ rev = (id & AR724X_REV_ID_REVISION_MASK); -+ break; ++static void __init ubnt_rs_setup(void) ++{ ++ ubnt_generic_setup(); + -+ case REV_ID_MAJOR_AR7241: -+ ar71xx_soc = AR71XX_SOC_AR7241; -+ chip = "7241"; -+ rev = (id & AR724X_REV_ID_REVISION_MASK); -+ break; ++ ar71xx_add_device_mdio(~(UBNT_RS_WAN_PHYMASK | UBNT_RS_LAN_PHYMASK)); + -+ case REV_ID_MAJOR_AR7242: -+ ar71xx_soc = AR71XX_SOC_AR7242; -+ chip = "7242"; -+ rev = (id & AR724X_REV_ID_REVISION_MASK); -+ break; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = UBNT_RS_WAN_PHYMASK; + -+ case REV_ID_MAJOR_AR913X: -+ minor = id & AR91XX_REV_ID_MINOR_MASK; -+ rev = id >> AR91XX_REV_ID_REVISION_SHIFT; -+ rev &= AR91XX_REV_ID_REVISION_MASK; -+ switch (minor) { -+ case AR91XX_REV_ID_MINOR_AR9130: -+ ar71xx_soc = AR71XX_SOC_AR9130; -+ chip = "9130"; -+ break; ++ ubnt_init_secondary_mac(ar71xx_mac_base); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_100; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ case AR91XX_REV_ID_MINOR_AR9132: -+ ar71xx_soc = AR71XX_SOC_AR9132; -+ chip = "9132"; -+ break; -+ } -+ break; ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ default: -+ panic("ar71xx: unknown chip id:0x%08x\n", id); -+ } ++ ar71xx_add_device_usb(); + -+ sprintf(ar71xx_sys_type, "Atheros AR%s rev %u", chip, rev); ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_rs_leds_gpio), ++ ubnt_rs_leds_gpio); +} + -+static void __init ar91xx_detect_sys_frequency(void) ++MIPS_MACHINE(AR71XX_MACH_UBNT_RS, "UBNT-RS", "Ubiquiti RouterStation", ++ ubnt_rs_setup); ++ ++#define UBNT_RSPRO_WAN_PHYMASK BIT(4) ++#define UBNT_RSPRO_LAN_PHYMASK (BIT(0) | BIT(1) | BIT(2) | BIT(3)) ++ ++static void __init ubnt_rspro_setup(void) +{ -+ u32 pll; -+ u32 freq; -+ u32 div; ++ ubnt_generic_setup(); + -+ pll = ar71xx_pll_rr(AR91XX_PLL_REG_CPU_CONFIG); ++ ar71xx_add_device_mdio(~(UBNT_RSPRO_WAN_PHYMASK | ++ UBNT_RSPRO_LAN_PHYMASK)); + -+ div = ((pll >> AR91XX_PLL_DIV_SHIFT) & AR91XX_PLL_DIV_MASK); -+ freq = div * AR91XX_BASE_FREQ; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.phy_mask = UBNT_RSPRO_WAN_PHYMASK; + -+ ar71xx_cpu_freq = freq; ++ ubnt_init_secondary_mac(ar71xx_mac_base); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = UBNT_RSPRO_LAN_PHYMASK; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ div = ((pll >> AR91XX_DDR_DIV_SHIFT) & AR91XX_DDR_DIV_MASK) + 1; -+ ar71xx_ddr_freq = freq / div; ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ div = (((pll >> AR91XX_AHB_DIV_SHIFT) & AR91XX_AHB_DIV_MASK) + 1) * 2; -+ ar71xx_ahb_freq = ar71xx_cpu_freq / div; ++ ar71xx_add_device_usb(); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_rs_leds_gpio), ++ ubnt_rs_leds_gpio); +} + -+static void __init ar71xx_detect_sys_frequency(void) ++MIPS_MACHINE(AR71XX_MACH_UBNT_RSPRO, "UBNT-RSPRO", "Ubiquiti RouterStation Pro", ++ ubnt_rspro_setup); ++ ++static void __init ubnt_lsx_setup(void) +{ -+ u32 pll; -+ u32 freq; -+ u32 div; ++ ubnt_generic_setup(); ++} + -+ pll = ar71xx_pll_rr(AR71XX_PLL_REG_CPU_CONFIG); ++MIPS_MACHINE(AR71XX_MACH_UBNT_LSX, "UBNT-LSX", "Ubiquiti LSX", ubnt_lsx_setup); + -+ div = ((pll >> AR71XX_PLL_DIV_SHIFT) & AR71XX_PLL_DIV_MASK) + 1; -+ freq = div * AR71XX_BASE_FREQ; ++#define UBNT_LSSR71_PHY_MASK BIT(1) + -+ div = ((pll >> AR71XX_CPU_DIV_SHIFT) & AR71XX_CPU_DIV_MASK) + 1; -+ ar71xx_cpu_freq = freq / div; ++static void __init ubnt_lssr71_setup(void) ++{ ++ ubnt_generic_setup(); + -+ div = ((pll >> AR71XX_DDR_DIV_SHIFT) & AR71XX_DDR_DIV_MASK) + 1; -+ ar71xx_ddr_freq = freq / div; ++ ar71xx_add_device_mdio(~UBNT_LSSR71_PHY_MASK); + -+ div = (((pll >> AR71XX_AHB_DIV_SHIFT) & AR71XX_AHB_DIV_MASK) + 1) * 2; -+ ar71xx_ahb_freq = ar71xx_cpu_freq / div; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = UBNT_LSSR71_PHY_MASK; ++ ++ ar71xx_add_device_eth(0); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_ls_sr71_leds_gpio), ++ ubnt_ls_sr71_leds_gpio); +} + -+static void __init ar724x_detect_sys_frequency(void) ++MIPS_MACHINE(AR71XX_MACH_UBNT_LSSR71, "UBNT-LS-SR71", "Ubiquiti LS-SR71", ++ ubnt_lssr71_setup); ++ ++#define UBNT_M_WAN_PHYMASK BIT(4) ++ ++static void __init ubnt_m_setup(void) +{ -+ u32 pll; -+ u32 freq; -+ u32 div; ++ u8 *mac1 = (u8 *) KSEG1ADDR(0x1fff0000); ++ u8 *mac2 = (u8 *) KSEG1ADDR(0x1fff0000 + ETH_ALEN); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + -+ pll = ar71xx_pll_rr(AR724X_PLL_REG_CPU_CONFIG); ++ ar71xx_add_device_m25p80(NULL); + -+ div = ((pll >> AR724X_PLL_DIV_SHIFT) & AR724X_PLL_DIV_MASK); -+ freq = div * AR724X_BASE_FREQ; ++ ar71xx_add_device_mdio(~UBNT_M_WAN_PHYMASK); + -+ div = ((pll >> AR724X_PLL_REF_DIV_SHIFT) & AR724X_PLL_REF_DIV_MASK); -+ freq *= div; -+ -+ ar71xx_cpu_freq = freq; -+ -+ div = ((pll >> AR724X_DDR_DIV_SHIFT) & AR724X_DDR_DIV_MASK) + 1; -+ ar71xx_ddr_freq = freq / div; -+ -+ div = (((pll >> AR724X_AHB_DIV_SHIFT) & AR724X_AHB_DIV_MASK) + 1) * 2; -+ ar71xx_ahb_freq = ar71xx_cpu_freq / div; -+} ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac1, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac2, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = UBNT_M_WAN_PHYMASK; + -+static void __init detect_sys_frequency(void) -+{ -+ switch (ar71xx_soc) { -+ case AR71XX_SOC_AR7130: -+ case AR71XX_SOC_AR7141: -+ case AR71XX_SOC_AR7161: -+ ar71xx_detect_sys_frequency(); -+ break; ++ ar71xx_add_device_eth(0); + -+ case AR71XX_SOC_AR7240: -+ case AR71XX_SOC_AR7241: -+ case AR71XX_SOC_AR7242: -+ ar724x_detect_sys_frequency(); -+ break; ++ ap91_pci_init(ee, NULL); + -+ case AR71XX_SOC_AR9130: -+ case AR71XX_SOC_AR9132: -+ ar91xx_detect_sys_frequency(); -+ break; ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_m_leds_gpio), ++ ubnt_m_leds_gpio); + -+ default: -+ BUG(); -+ } ++ ar71xx_register_gpio_keys_polled(-1, UBNT_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(ubnt_m_gpio_keys), ++ ubnt_m_gpio_keys); +} + -+const char *get_system_type(void) ++static void __init ubnt_rocket_m_setup(void) +{ -+ return ar71xx_sys_type; ++ ubnt_m_setup(); ++ ar71xx_add_device_usb(); +} + -+unsigned int __cpuinit get_c0_compare_irq(void) -+{ -+ return CP0_LEGACY_COMPARE_IRQ; -+} ++MIPS_MACHINE(AR71XX_MACH_UBNT_BULLET_M, "UBNT-BM", "Ubiquiti Bullet M", ++ ubnt_m_setup); ++MIPS_MACHINE(AR71XX_MACH_UBNT_ROCKET_M, "UBNT-RM", "Ubiquiti Rocket M", ++ ubnt_rocket_m_setup); + -+void __init plat_mem_setup(void) ++/* TODO detect the second ethernet port and use one ++ init function for all Ubiquiti MIMO series products */ ++static void __init ubnt_nano_m_setup(void) +{ -+ set_io_port_base(KSEG1); -+ -+ ar71xx_ddr_base = ioremap_nocache(AR71XX_DDR_CTRL_BASE, -+ AR71XX_DDR_CTRL_SIZE); -+ -+ ar71xx_pll_base = ioremap_nocache(AR71XX_PLL_BASE, -+ AR71XX_PLL_SIZE); -+ -+ ar71xx_reset_base = ioremap_nocache(AR71XX_RESET_BASE, -+ AR71XX_RESET_SIZE); -+ -+ ar71xx_gpio_base = ioremap_nocache(AR71XX_GPIO_BASE, AR71XX_GPIO_SIZE); ++ ubnt_m_setup(); + -+ ar71xx_usb_ctrl_base = ioremap_nocache(AR71XX_USB_CTRL_BASE, -+ AR71XX_USB_CTRL_SIZE); ++ ar71xx_eth1_data.has_ar7240_switch = 1; ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ ar71xx_detect_mem_size(); -+ ar71xx_detect_sys_type(); -+ detect_sys_frequency(); ++ ar71xx_add_device_eth(1); ++} + -+ printk(KERN_INFO -+ "%s, CPU:%u.%03u MHz, AHB:%u.%03u MHz, DDR:%u.%03u MHz\n", -+ ar71xx_sys_type, -+ ar71xx_cpu_freq / 1000000, (ar71xx_cpu_freq / 1000) % 1000, -+ ar71xx_ahb_freq / 1000000, (ar71xx_ahb_freq / 1000) % 1000, -+ ar71xx_ddr_freq / 1000000, (ar71xx_ddr_freq / 1000) % 1000); ++MIPS_MACHINE(AR71XX_MACH_UBNT_NANO_M, "UBNT-NM", "Ubiquiti Nanostation M", ++ ubnt_nano_m_setup); + -+ _machine_restart = ar71xx_restart; -+ _machine_halt = ar71xx_halt; -+ pm_power_off = ar71xx_halt; -+} ++static struct gpio_led ubnt_unifi_leds_gpio[] __initdata = { ++ { ++ .name = "ubnt:orange:dome", ++ .gpio = 1, ++ .active_low = 0, ++ }, { ++ .name = "ubnt:green:dome", ++ .gpio = 0, ++ .active_low = 0, ++ } ++}; + -+void __init plat_time_init(void) ++static void __init ubnt_unifi_setup(void) +{ -+ mips_hpt_frequency = ar71xx_cpu_freq / 2; -+} ++ u8 *mac = (u8 *) KSEG1ADDR(0x1fff0000); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + -+__setup("board=", mips_machtype_setup); ++ ar71xx_add_device_m25p80(NULL); + -+static int __init ar71xx_machine_setup(void) -+{ -+ ar71xx_gpio_init(); ++ ar71xx_add_device_mdio(~UBNT_M_WAN_PHYMASK); + -+ ar71xx_add_device_uart(); -+ ar71xx_add_device_wdt(); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = UBNT_M_WAN_PHYMASK; + -+ mips_machine_setup(); -+ return 0; -+} ++ ar71xx_add_device_eth(0); + -+arch_initcall(ar71xx_machine_setup); ++ ap91_pci_init(ee, NULL); + -+static void __init ar71xx_generic_init(void) -+{ -+ /* Nothing to do */ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(ubnt_unifi_leds_gpio), ++ ubnt_unifi_leds_gpio); +} + -+MIPS_MACHINE(AR71XX_MACH_GENERIC, "Generic", "Generic AR71xx board", -+ ar71xx_generic_init); -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar71xx.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar71xx.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar71xx.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar71xx.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,514 @@ ++MIPS_MACHINE(AR71XX_MACH_UBNT_UNIFI, "UBNT-XM", "Ubiquiti UniFi", ++ ubnt_unifi_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wndr3700.c linux-2.6.39/arch/mips/ar71xx/mach-wndr3700.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wndr3700.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wndr3700.c 2011-08-24 02:41:55.607980283 +0200 +@@ -0,0 +1,290 @@ +/* -+ * Atheros AR71xx SoC specific definitions -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Netgear WNDR3700 board support + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2009 Marco Porsch ++ * Copyright (C) 2009-2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#ifndef __ASM_MACH_AR71XX_H -+#define __ASM_MACH_AR71XX_H -+ -+#include -+#include -+#include -+#include -+ -+#ifndef __ASSEMBLER__ -+ -+#define AR71XX_PCI_MEM_BASE 0x10000000 -+#define AR71XX_PCI_MEM_SIZE 0x08000000 -+#define AR71XX_APB_BASE 0x18000000 -+#define AR71XX_GE0_BASE 0x19000000 -+#define AR71XX_GE0_SIZE 0x01000000 -+#define AR71XX_GE1_BASE 0x1a000000 -+#define AR71XX_GE1_SIZE 0x01000000 -+#define AR71XX_EHCI_BASE 0x1b000000 -+#define AR71XX_EHCI_SIZE 0x01000000 -+#define AR71XX_OHCI_BASE 0x1c000000 -+#define AR71XX_OHCI_SIZE 0x01000000 -+#define AR7240_OHCI_BASE 0x1b000000 -+#define AR7240_OHCI_SIZE 0x01000000 -+#define AR71XX_SPI_BASE 0x1f000000 -+#define AR71XX_SPI_SIZE 0x01000000 -+ -+#define AR71XX_DDR_CTRL_BASE (AR71XX_APB_BASE + 0x00000000) -+#define AR71XX_DDR_CTRL_SIZE 0x10000 -+#define AR71XX_CPU_BASE (AR71XX_APB_BASE + 0x00010000) -+#define AR71XX_UART_BASE (AR71XX_APB_BASE + 0x00020000) -+#define AR71XX_UART_SIZE 0x10000 -+#define AR71XX_USB_CTRL_BASE (AR71XX_APB_BASE + 0x00030000) -+#define AR71XX_USB_CTRL_SIZE 0x10000 -+#define AR71XX_GPIO_BASE (AR71XX_APB_BASE + 0x00040000) -+#define AR71XX_GPIO_SIZE 0x10000 -+#define AR71XX_PLL_BASE (AR71XX_APB_BASE + 0x00050000) -+#define AR71XX_PLL_SIZE 0x10000 -+#define AR71XX_RESET_BASE (AR71XX_APB_BASE + 0x00060000) -+#define AR71XX_RESET_SIZE 0x10000 -+#define AR71XX_MII_BASE (AR71XX_APB_BASE + 0x00070000) -+#define AR71XX_MII_SIZE 0x10000 -+#define AR71XX_SLIC_BASE (AR71XX_APB_BASE + 0x00090000) -+#define AR71XX_SLIC_SIZE 0x10000 -+#define AR71XX_DMA_BASE (AR71XX_APB_BASE + 0x000A0000) -+#define AR71XX_DMA_SIZE 0x10000 -+#define AR71XX_STEREO_BASE (AR71XX_APB_BASE + 0x000B0000) -+#define AR71XX_STEREO_SIZE 0x10000 -+ -+#define AR724X_PCI_CRP_BASE (AR71XX_APB_BASE + 0x000C0000) -+#define AR724X_PCI_CRP_SIZE 0x100 -+ -+#define AR724X_PCI_CTRL_BASE (AR71XX_APB_BASE + 0x000F0000) -+#define AR724X_PCI_CTRL_SIZE 0x100 -+ -+#define AR91XX_WMAC_BASE (AR71XX_APB_BASE + 0x000C0000) -+#define AR91XX_WMAC_SIZE 0x30000 -+ -+#define AR71XX_MEM_SIZE_MIN 0x0200000 -+#define AR71XX_MEM_SIZE_MAX 0x10000000 ++#include ++#include ++#include ++#include ++#include + -+#define AR71XX_CPU_IRQ_BASE 0 -+#define AR71XX_MISC_IRQ_BASE 8 -+#define AR71XX_MISC_IRQ_COUNT 8 -+#define AR71XX_GPIO_IRQ_BASE 16 -+#define AR71XX_GPIO_IRQ_COUNT 32 -+#define AR71XX_PCI_IRQ_BASE 48 -+#define AR71XX_PCI_IRQ_COUNT 8 ++#include + -+#define AR71XX_CPU_IRQ_IP2 (AR71XX_CPU_IRQ_BASE + 2) -+#define AR71XX_CPU_IRQ_USB (AR71XX_CPU_IRQ_BASE + 3) -+#define AR71XX_CPU_IRQ_GE0 (AR71XX_CPU_IRQ_BASE + 4) -+#define AR71XX_CPU_IRQ_GE1 (AR71XX_CPU_IRQ_BASE + 5) -+#define AR71XX_CPU_IRQ_MISC (AR71XX_CPU_IRQ_BASE + 6) -+#define AR71XX_CPU_IRQ_TIMER (AR71XX_CPU_IRQ_BASE + 7) ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ap94-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define AR71XX_MISC_IRQ_TIMER (AR71XX_MISC_IRQ_BASE + 0) -+#define AR71XX_MISC_IRQ_ERROR (AR71XX_MISC_IRQ_BASE + 1) -+#define AR71XX_MISC_IRQ_GPIO (AR71XX_MISC_IRQ_BASE + 2) -+#define AR71XX_MISC_IRQ_UART (AR71XX_MISC_IRQ_BASE + 3) -+#define AR71XX_MISC_IRQ_WDOG (AR71XX_MISC_IRQ_BASE + 4) -+#define AR71XX_MISC_IRQ_PERFC (AR71XX_MISC_IRQ_BASE + 5) -+#define AR71XX_MISC_IRQ_OHCI (AR71XX_MISC_IRQ_BASE + 6) -+#define AR71XX_MISC_IRQ_DMA (AR71XX_MISC_IRQ_BASE + 7) ++#define WNDR3700_GPIO_LED_WPS_ORANGE 0 ++#define WNDR3700_GPIO_LED_POWER_ORANGE 1 ++#define WNDR3700_GPIO_LED_POWER_GREEN 2 ++#define WNDR3700_GPIO_LED_WPS_GREEN 4 ++#define WNDR3700_GPIO_LED_WAN_GREEN 6 + -+#define AR71XX_GPIO_IRQ(_x) (AR71XX_GPIO_IRQ_BASE + (_x)) ++#define WNDR3700_GPIO_BTN_WPS 3 ++#define WNDR3700_GPIO_BTN_RESET 8 ++#define WNDR3700_GPIO_BTN_WIFI 11 + -+#define AR71XX_PCI_IRQ_DEV0 (AR71XX_PCI_IRQ_BASE + 0) -+#define AR71XX_PCI_IRQ_DEV1 (AR71XX_PCI_IRQ_BASE + 1) -+#define AR71XX_PCI_IRQ_DEV2 (AR71XX_PCI_IRQ_BASE + 2) -+#define AR71XX_PCI_IRQ_CORE (AR71XX_PCI_IRQ_BASE + 4) ++#define WNDR3700_GPIO_RTL8366_SDA 5 ++#define WNDR3700_GPIO_RTL8366_SCK 7 + -+extern u32 ar71xx_ahb_freq; -+extern u32 ar71xx_cpu_freq; -+extern u32 ar71xx_ddr_freq; ++#define WNDR3700_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WNDR3700_KEYS_DEBOUNCE_INTERVAL (3 * WNDR3700_KEYS_POLL_INTERVAL) + -+enum ar71xx_soc_type { -+ AR71XX_SOC_UNKNOWN, -+ AR71XX_SOC_AR7130, -+ AR71XX_SOC_AR7141, -+ AR71XX_SOC_AR7161, -+ AR71XX_SOC_AR7240, -+ AR71XX_SOC_AR7241, -+ AR71XX_SOC_AR7242, -+ AR71XX_SOC_AR9130, -+ AR71XX_SOC_AR9132 -+}; ++#define WNDR3700_ETH0_MAC_OFFSET 0 ++#define WNDR3700_ETH1_MAC_OFFSET 0x6 + -+extern enum ar71xx_soc_type ar71xx_soc; ++#define WNDR3700_WMAC0_MAC_OFFSET 0 ++#define WNDR3700_WMAC1_MAC_OFFSET 0xc ++#define WNDR3700_CALDATA0_OFFSET 0x1000 ++#define WNDR3700_CALDATA1_OFFSET 0x5000 + -+/* -+ * PLL block -+ */ -+#define AR71XX_PLL_REG_CPU_CONFIG 0x00 -+#define AR71XX_PLL_REG_SEC_CONFIG 0x04 -+#define AR71XX_PLL_REG_ETH0_INT_CLOCK 0x10 -+#define AR71XX_PLL_REG_ETH1_INT_CLOCK 0x14 ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wndr3700_partitions[] = { ++ { ++ .name = "uboot", ++ .offset = 0, ++ .size = 0x050000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "env", ++ .offset = 0x050000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "rootfs", ++ .offset = 0x070000, ++ .size = 0x720000, ++ }, { ++ .name = "config", ++ .offset = 0x790000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "config_bak", ++ .offset = 0x7a0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "pot", ++ .offset = 0x7b0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "traffic_meter", ++ .offset = 0x7c0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "language", ++ .offset = 0x7d0000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "caldata", ++ .offset = 0x7f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ } ++}; + -+#define AR71XX_PLL_DIV_SHIFT 3 -+#define AR71XX_PLL_DIV_MASK 0x1f -+#define AR71XX_CPU_DIV_SHIFT 16 -+#define AR71XX_CPU_DIV_MASK 0x3 -+#define AR71XX_DDR_DIV_SHIFT 18 -+#define AR71XX_DDR_DIV_MASK 0x3 -+#define AR71XX_AHB_DIV_SHIFT 20 -+#define AR71XX_AHB_DIV_MASK 0x7 ++static struct mtd_partition wndr3700v2_partitions[] = { ++ { ++ .name = "uboot", ++ .offset = 0, ++ .size = 0x050000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "env", ++ .offset = 0x050000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "rootfs", ++ .offset = 0x070000, ++ .size = 0xe40000, ++ }, { ++ .name = "config", ++ .offset = 0xeb0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "config_bak", ++ .offset = 0xec0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "pot", ++ .offset = 0xed0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "traffic_meter", ++ .offset = 0xee0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "language", ++ .offset = 0xef0000, ++ .size = 0x100000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "caldata", ++ .offset = 0xff0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ } ++}; ++#define wndr3700_num_partitions ARRAY_SIZE(wndr3700_partitions) ++#define wndr3700v2_num_partitions ARRAY_SIZE(wndr3700v2_partitions) ++#else ++#define wndr3700_partitions NULL ++#define wndr3700_num_partitions 0 ++#define wndr3700v2_partitions NULL ++#define wndr3700v2_num_partitions 0 ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#define AR71XX_ETH0_PLL_SHIFT 17 -+#define AR71XX_ETH1_PLL_SHIFT 19 ++static struct flash_platform_data wndr3700_flash_data; + -+#define AR724X_PLL_REG_CPU_CONFIG 0x00 -+#define AR724X_PLL_REG_PCIE_CONFIG 0x18 ++static struct gpio_led wndr3700_leds_gpio[] __initdata = { ++ { ++ .name = "wndr3700:green:power", ++ .gpio = WNDR3700_GPIO_LED_POWER_GREEN, ++ .active_low = 1, ++ }, { ++ .name = "wndr3700:orange:power", ++ .gpio = WNDR3700_GPIO_LED_POWER_ORANGE, ++ .active_low = 1, ++ }, { ++ .name = "wndr3700:green:wps", ++ .gpio = WNDR3700_GPIO_LED_WPS_GREEN, ++ .active_low = 1, ++ }, { ++ .name = "wndr3700:orange:wps", ++ .gpio = WNDR3700_GPIO_LED_WPS_ORANGE, ++ .active_low = 1, ++ }, { ++ .name = "wndr3700:green:wan", ++ .gpio = WNDR3700_GPIO_LED_WAN_GREEN, ++ .active_low = 1, ++ } ++}; + -+#define AR724X_PLL_DIV_SHIFT 0 -+#define AR724X_PLL_DIV_MASK 0x3ff -+#define AR724X_PLL_REF_DIV_SHIFT 10 -+#define AR724X_PLL_REF_DIV_MASK 0xf -+#define AR724X_AHB_DIV_SHIFT 19 -+#define AR724X_AHB_DIV_MASK 0x1 -+#define AR724X_DDR_DIV_SHIFT 22 -+#define AR724X_DDR_DIV_MASK 0x3 ++static struct gpio_keys_button wndr3700_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WNDR3700_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WNDR3700_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WNDR3700_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WNDR3700_GPIO_BTN_WPS, ++ .active_low = 1, ++ }, { ++ .desc = "wifi", ++ .type = EV_KEY, ++ .code = BTN_2, ++ .debounce_interval = WNDR3700_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WNDR3700_GPIO_BTN_WIFI, ++ .active_low = 1, ++ } ++}; + -+#define AR91XX_PLL_REG_CPU_CONFIG 0x00 -+#define AR91XX_PLL_REG_ETH_CONFIG 0x04 -+#define AR91XX_PLL_REG_ETH0_INT_CLOCK 0x14 -+#define AR91XX_PLL_REG_ETH1_INT_CLOCK 0x18 ++static struct rtl8366_platform_data wndr3700_rtl8366s_data = { ++ .gpio_sda = WNDR3700_GPIO_RTL8366_SDA, ++ .gpio_sck = WNDR3700_GPIO_RTL8366_SCK, ++}; + -+#define AR91XX_PLL_DIV_SHIFT 0 -+#define AR91XX_PLL_DIV_MASK 0x3ff -+#define AR91XX_DDR_DIV_SHIFT 22 -+#define AR91XX_DDR_DIV_MASK 0x3 -+#define AR91XX_AHB_DIV_SHIFT 19 -+#define AR91XX_AHB_DIV_MASK 0x1 ++static struct platform_device wndr3700_rtl8366s_device = { ++ .name = RTL8366S_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &wndr3700_rtl8366s_data, ++ } ++}; + -+#define AR91XX_ETH0_PLL_SHIFT 20 -+#define AR91XX_ETH1_PLL_SHIFT 22 ++static void __init wndr3700_common_setup(void) ++{ ++ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); + -+extern void __iomem *ar71xx_pll_base; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ++ art + WNDR3700_ETH0_MAC_OFFSET, 0); ++ ar71xx_eth0_pll_data.pll_1000 = 0x11110000; ++ ar71xx_eth0_data.mii_bus_dev = &wndr3700_rtl8366s_device.dev; ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+static inline void ar71xx_pll_wr(unsigned reg, u32 val) -+{ -+ __raw_writel(val, ar71xx_pll_base + reg); -+} ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, ++ art + WNDR3700_ETH1_MAC_OFFSET, 0); ++ ar71xx_eth1_pll_data.pll_1000 = 0x11110000; ++ ar71xx_eth1_data.mii_bus_dev = &wndr3700_rtl8366s_device.dev; ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + -+static inline u32 ar71xx_pll_rr(unsigned reg) -+{ -+ return __raw_readl(ar71xx_pll_base + reg); -+} ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+/* -+ * USB_CONFIG block -+ */ -+#define USB_CTRL_REG_FLADJ 0x00 -+#define USB_CTRL_REG_CONFIG 0x04 ++ ar71xx_add_device_usb(); + -+extern void __iomem *ar71xx_usb_ctrl_base; ++ ar71xx_add_device_m25p80(&wndr3700_flash_data); + -+static inline void ar71xx_usb_ctrl_wr(unsigned reg, u32 val) ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wndr3700_leds_gpio), ++ wndr3700_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, WNDR3700_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wndr3700_gpio_keys), ++ wndr3700_gpio_keys); ++ ++ platform_device_register(&wndr3700_rtl8366s_device); ++ platform_device_register_simple("wndr3700-led-usb", -1, NULL, 0); ++ ++ ap94_pci_setup_wmac_led_pin(0, 5); ++ ap94_pci_setup_wmac_led_pin(1, 5); ++ ++ /* 2.4 GHz uses the first fixed antenna group (1, 0, 1, 0) */ ++ ap94_pci_setup_wmac_gpio(0, (0xf << 6), (0xa << 6)); ++ ++ /* 5 GHz uses the second fixed antenna group (0, 1, 1, 0) */ ++ ap94_pci_setup_wmac_gpio(1, (0xf << 6), (0x6 << 6)); ++ ++ ap94_pci_init(art + WNDR3700_CALDATA0_OFFSET, ++ art + WNDR3700_WMAC0_MAC_OFFSET, ++ art + WNDR3700_CALDATA1_OFFSET, ++ art + WNDR3700_WMAC1_MAC_OFFSET); ++} ++ ++static void __init wndr3700_setup(void) +{ -+ __raw_writel(val, ar71xx_usb_ctrl_base + reg); ++ wndr3700_flash_data.parts = wndr3700_partitions, ++ wndr3700_flash_data.nr_parts = wndr3700_num_partitions, ++ wndr3700_common_setup(); +} + -+static inline u32 ar71xx_usb_ctrl_rr(unsigned reg) ++MIPS_MACHINE(AR71XX_MACH_WNDR3700, "WNDR3700", "NETGEAR WNDR3700", ++ wndr3700_setup); ++ ++static void __init wndr3700v2_setup(void) +{ -+ return __raw_readl(ar71xx_usb_ctrl_base + reg); ++ wndr3700_flash_data.parts = wndr3700v2_partitions, ++ wndr3700_flash_data.nr_parts = wndr3700v2_num_partitions, ++ wndr3700_common_setup(); +} + ++MIPS_MACHINE(AR71XX_MACH_WNDR3700V2, "WNDR3700v2", "NETGEAR WNDR3700v2", ++ wndr3700v2_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wnr2000.c linux-2.6.39/arch/mips/ar71xx/mach-wnr2000.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wnr2000.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wnr2000.c 2011-08-24 02:41:55.617990333 +0200 +@@ -0,0 +1,150 @@ +/* -+ * GPIO block ++ * NETGEAR WNR2000 board support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2008-2009 Andy Boyett ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ -+#define GPIO_REG_OE 0x00 -+#define GPIO_REG_IN 0x04 -+#define GPIO_REG_OUT 0x08 -+#define GPIO_REG_SET 0x0c -+#define GPIO_REG_CLEAR 0x10 -+#define GPIO_REG_INT_MODE 0x14 -+#define GPIO_REG_INT_TYPE 0x18 -+#define GPIO_REG_INT_POLARITY 0x1c -+#define GPIO_REG_INT_PENDING 0x20 -+#define GPIO_REG_INT_ENABLE 0x24 -+#define GPIO_REG_FUNC 0x28 + -+#define AR71XX_GPIO_FUNC_STEREO_EN BIT(17) -+#define AR71XX_GPIO_FUNC_SLIC_EN BIT(16) -+#define AR71XX_GPIO_FUNC_SPI_CS2_EN BIT(13) -+#define AR71XX_GPIO_FUNC_SPI_CS1_EN BIT(12) -+#define AR71XX_GPIO_FUNC_UART_EN BIT(8) -+#define AR71XX_GPIO_FUNC_USB_OC_EN BIT(4) -+#define AR71XX_GPIO_FUNC_USB_CLK_EN BIT(0) ++#include ++#include + -+#define AR71XX_GPIO_COUNT 16 ++#include + -+#define AR724X_GPIO_FUNC_GE0_MII_CLK_EN BIT(19) -+#define AR724X_GPIO_FUNC_SPI_EN BIT(18) -+#define AR724X_GPIO_FUNC_SPI_CS_EN2 BIT(14) -+#define AR724X_GPIO_FUNC_SPI_CS_EN1 BIT(13) -+#define AR724X_GPIO_FUNC_CLK_OBS5_EN BIT(12) -+#define AR724X_GPIO_FUNC_CLK_OBS4_EN BIT(11) -+#define AR724X_GPIO_FUNC_CLK_OBS3_EN BIT(10) -+#define AR724X_GPIO_FUNC_CLK_OBS2_EN BIT(9) -+#define AR724X_GPIO_FUNC_CLK_OBS1_EN BIT(8) -+#define AR724X_GPIO_FUNC_ETH_SWITCH_LED4_EN BIT(7) -+#define AR724X_GPIO_FUNC_ETH_SWITCH_LED3_EN BIT(6) -+#define AR724X_GPIO_FUNC_ETH_SWITCH_LED2_EN BIT(5) -+#define AR724X_GPIO_FUNC_ETH_SWITCH_LED1_EN BIT(4) -+#define AR724X_GPIO_FUNC_ETH_SWITCH_LED0_EN BIT(3) -+#define AR724X_GPIO_FUNC_UART_RTS_CTS_EN BIT(2) -+#define AR724X_GPIO_FUNC_UART_EN BIT(1) -+#define AR724X_GPIO_FUNC_JTAG_DISABLE BIT(0) ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" + -+#define AR724X_GPIO_COUNT 18 ++#define WNR2000_GPIO_LED_PWR_GREEN 14 ++#define WNR2000_GPIO_LED_PWR_AMBER 7 ++#define WNR2000_GPIO_LED_WPS 4 ++#define WNR2000_GPIO_LED_WLAN 6 ++#define WNR2000_GPIO_BTN_RESET 21 ++#define WNR2000_GPIO_BTN_WPS 8 + -+#define AR91XX_GPIO_FUNC_WMAC_LED_EN BIT(22) -+#define AR91XX_GPIO_FUNC_EXP_PORT_CS_EN BIT(21) -+#define AR91XX_GPIO_FUNC_I2S_REFCLKEN BIT(20) -+#define AR91XX_GPIO_FUNC_I2S_MCKEN BIT(19) -+#define AR91XX_GPIO_FUNC_I2S1_EN BIT(18) -+#define AR91XX_GPIO_FUNC_I2S0_EN BIT(17) -+#define AR91XX_GPIO_FUNC_SLIC_EN BIT(16) -+#define AR91XX_GPIO_FUNC_UART_RTSCTS_EN BIT(9) -+#define AR91XX_GPIO_FUNC_UART_EN BIT(8) -+#define AR91XX_GPIO_FUNC_USB_CLK_EN BIT(4) ++#define WNR2000_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WNR2000_KEYS_DEBOUNCE_INTERVAL (3 * WNR2000_KEYS_POLL_INTERVAL) + -+#define AR91XX_GPIO_COUNT 22 ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wnr2000_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x050000, ++ .size = 0x240000, ++ }, { ++ .name = "user-config", ++ .offset = 0x290000, ++ .size = 0x010000, ++ }, { ++ .name = "uImage", ++ .offset = 0x2a0000, ++ .size = 0x120000, ++ }, { ++ .name = "language_table", ++ .offset = 0x3c0000, ++ .size = 0x020000, ++ }, { ++ .name = "rootfs_checksum", ++ .offset = 0x3e0000, ++ .size = 0x010000, ++ }, { ++ .name = "art", ++ .offset = 0x3f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+extern void __iomem *ar71xx_gpio_base; ++static struct flash_platform_data wnr2000_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = wnr2000_partitions, ++ .nr_parts = ARRAY_SIZE(wnr2000_partitions), ++#endif ++}; + -+static inline void ar71xx_gpio_wr(unsigned reg, u32 value) -+{ -+ __raw_writel(value, ar71xx_gpio_base + reg); -+} ++static struct gpio_led wnr2000_leds_gpio[] __initdata = { ++ { ++ .name = "wnr2000:green:power", ++ .gpio = WNR2000_GPIO_LED_PWR_GREEN, ++ .active_low = 1, ++ }, { ++ .name = "wnr2000:amber:power", ++ .gpio = WNR2000_GPIO_LED_PWR_AMBER, ++ .active_low = 1, ++ }, { ++ .name = "wnr2000:green:wps", ++ .gpio = WNR2000_GPIO_LED_WPS, ++ .active_low = 1, ++ }, { ++ .name = "wnr2000:blue:wlan", ++ .gpio = WNR2000_GPIO_LED_WLAN, ++ .active_low = 1, ++ } ++}; + -+static inline u32 ar71xx_gpio_rr(unsigned reg) ++static struct gpio_keys_button wnr2000_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WNR2000_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WNR2000_GPIO_BTN_RESET, ++ }, { ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WNR2000_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WNR2000_GPIO_BTN_WPS, ++ } ++}; ++ ++static void __init wnr2000_setup(void) +{ -+ return __raw_readl(ar71xx_gpio_base + reg); -+} ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); + -+void ar71xx_gpio_init(void) __init; -+void ar71xx_gpio_function_enable(u32 mask); -+void ar71xx_gpio_function_disable(u32 mask); -+void ar71xx_gpio_function_setup(u32 set, u32 clear); ++ ar71xx_add_device_mdio(0x0); + -+/* -+ * DDR_CTRL block -+ */ -+#define AR71XX_DDR_REG_PCI_WIN0 0x7c -+#define AR71XX_DDR_REG_PCI_WIN1 0x80 -+#define AR71XX_DDR_REG_PCI_WIN2 0x84 -+#define AR71XX_DDR_REG_PCI_WIN3 0x88 -+#define AR71XX_DDR_REG_PCI_WIN4 0x8c -+#define AR71XX_DDR_REG_PCI_WIN5 0x90 -+#define AR71XX_DDR_REG_PCI_WIN6 0x94 -+#define AR71XX_DDR_REG_PCI_WIN7 0x98 -+#define AR71XX_DDR_REG_FLUSH_GE0 0x9c -+#define AR71XX_DDR_REG_FLUSH_GE1 0xa0 -+#define AR71XX_DDR_REG_FLUSH_USB 0xa4 -+#define AR71XX_DDR_REG_FLUSH_PCI 0xa8 ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, eeprom, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.has_ar8216 = 1; + -+#define AR724X_DDR_REG_FLUSH_GE0 0x7c -+#define AR724X_DDR_REG_FLUSH_GE1 0x80 -+#define AR724X_DDR_REG_FLUSH_USB 0x84 -+#define AR724X_DDR_REG_FLUSH_PCIE 0x88 ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, eeprom, 1); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + -+#define AR91XX_DDR_REG_FLUSH_GE0 0x7c -+#define AR91XX_DDR_REG_FLUSH_GE1 0x80 -+#define AR91XX_DDR_REG_FLUSH_USB 0x84 -+#define AR91XX_DDR_REG_FLUSH_WMAC 0x88 ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+#define PCI_WIN0_OFFS 0x10000000 -+#define PCI_WIN1_OFFS 0x11000000 -+#define PCI_WIN2_OFFS 0x12000000 -+#define PCI_WIN3_OFFS 0x13000000 -+#define PCI_WIN4_OFFS 0x14000000 -+#define PCI_WIN5_OFFS 0x15000000 -+#define PCI_WIN6_OFFS 0x16000000 -+#define PCI_WIN7_OFFS 0x07000000 ++ ar71xx_add_device_m25p80(&wnr2000_flash_data); + -+extern void __iomem *ar71xx_ddr_base; ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wnr2000_leds_gpio), ++ wnr2000_leds_gpio); + -+static inline void ar71xx_ddr_wr(unsigned reg, u32 val) -+{ -+ __raw_writel(val, ar71xx_ddr_base + reg); -+} ++ ar71xx_register_gpio_keys_polled(-1, WNR2000_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wnr2000_gpio_keys), ++ wnr2000_gpio_keys); + -+static inline u32 ar71xx_ddr_rr(unsigned reg) -+{ -+ return __raw_readl(ar71xx_ddr_base + reg); -+} + -+void ar71xx_ddr_flush(u32 reg); ++ ar9xxx_add_device_wmac(eeprom, NULL); ++} + ++MIPS_MACHINE(AR71XX_MACH_WNR2000, "WNR2000", "NETGEAR WNR2000", wnr2000_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wp543.c linux-2.6.39/arch/mips/ar71xx/mach-wp543.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wp543.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wp543.c 2011-08-24 02:41:55.617990333 +0200 +@@ -0,0 +1,101 @@ +/* -+ * PCI block ++ * Compex WP543/WPJ543 board support ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ -+#define AR71XX_PCI_CFG_BASE (AR71XX_PCI_MEM_BASE + PCI_WIN7_OFFS + 0x10000) -+#define AR71XX_PCI_CFG_SIZE 0x100 -+ -+#define PCI_REG_CRP_AD_CBE 0x00 -+#define PCI_REG_CRP_WRDATA 0x04 -+#define PCI_REG_CRP_RDDATA 0x08 -+#define PCI_REG_CFG_AD 0x0c -+#define PCI_REG_CFG_CBE 0x10 -+#define PCI_REG_CFG_WRDATA 0x14 -+#define PCI_REG_CFG_RDDATA 0x18 -+#define PCI_REG_PCI_ERR 0x1c -+#define PCI_REG_PCI_ERR_ADDR 0x20 -+#define PCI_REG_AHB_ERR 0x24 -+#define PCI_REG_AHB_ERR_ADDR 0x28 + -+#define PCI_CRP_CMD_WRITE 0x00010000 -+#define PCI_CRP_CMD_READ 0x00000000 -+#define PCI_CFG_CMD_READ 0x0000000a -+#define PCI_CFG_CMD_WRITE 0x0000000b -+ -+#define PCI_IDSEL_ADL_START 17 ++#include ++#include + -+#define AR724X_PCI_CFG_BASE (AR71XX_PCI_MEM_BASE + 0x4000000) -+#define AR724X_PCI_CFG_SIZE 0x1000 ++#include + -+#define AR724X_PCI_REG_APP 0x00 -+#define AR724X_PCI_REG_RESET 0x18 -+#define AR724X_PCI_REG_INT_STATUS 0x4c -+#define AR724X_PCI_REG_INT_MASK 0x50 ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-pb42-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+#define AR724X_PCI_APP_LTSSM_ENABLE BIT(0) -+#define AR724X_PCI_RESET_LINK_UP BIT(0) ++#define WP543_GPIO_SW6 2 ++#define WP543_GPIO_LED_1 3 ++#define WP543_GPIO_LED_2 4 ++#define WP543_GPIO_LED_WLAN 5 ++#define WP543_GPIO_LED_CONN 6 ++#define WP543_GPIO_LED_DIAG 7 ++#define WP543_GPIO_SW4 8 + -+#define AR724X_PCI_INT_DEV0 BIT(14) ++#define WP543_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WP543_KEYS_DEBOUNCE_INTERVAL (3 * WP543_KEYS_POLL_INTERVAL) + -+/* -+ * RESET block -+ */ -+#define AR71XX_RESET_REG_TIMER 0x00 -+#define AR71XX_RESET_REG_TIMER_RELOAD 0x04 -+#define AR71XX_RESET_REG_WDOG_CTRL 0x08 -+#define AR71XX_RESET_REG_WDOG 0x0c -+#define AR71XX_RESET_REG_MISC_INT_STATUS 0x10 -+#define AR71XX_RESET_REG_MISC_INT_ENABLE 0x14 -+#define AR71XX_RESET_REG_PCI_INT_STATUS 0x18 -+#define AR71XX_RESET_REG_PCI_INT_ENABLE 0x1c -+#define AR71XX_RESET_REG_GLOBAL_INT_STATUS 0x20 -+#define AR71XX_RESET_REG_RESET_MODULE 0x24 -+#define AR71XX_RESET_REG_PERFC_CTRL 0x2c -+#define AR71XX_RESET_REG_PERFC0 0x30 -+#define AR71XX_RESET_REG_PERFC1 0x34 -+#define AR71XX_RESET_REG_REV_ID 0x90 -+ -+#define AR91XX_RESET_REG_GLOBAL_INT_STATUS 0x18 -+#define AR91XX_RESET_REG_RESET_MODULE 0x1c -+#define AR91XX_RESET_REG_PERF_CTRL 0x20 -+#define AR91XX_RESET_REG_PERFC0 0x24 -+#define AR91XX_RESET_REG_PERFC1 0x28 -+ -+#define AR724X_RESET_REG_RESET_MODULE 0x1c -+ -+#define WDOG_CTRL_LAST_RESET BIT(31) -+#define WDOG_CTRL_ACTION_MASK 3 -+#define WDOG_CTRL_ACTION_NONE 0 /* no action */ -+#define WDOG_CTRL_ACTION_GPI 1 /* general purpose interrupt */ -+#define WDOG_CTRL_ACTION_NMI 2 /* NMI */ -+#define WDOG_CTRL_ACTION_FCR 3 /* full chip reset */ -+ -+#define MISC_INT_DMA BIT(7) -+#define MISC_INT_OHCI BIT(6) -+#define MISC_INT_PERFC BIT(5) -+#define MISC_INT_WDOG BIT(4) -+#define MISC_INT_UART BIT(3) -+#define MISC_INT_GPIO BIT(2) -+#define MISC_INT_ERROR BIT(1) -+#define MISC_INT_TIMER BIT(0) -+ -+#define PCI_INT_CORE BIT(4) -+#define PCI_INT_DEV2 BIT(2) -+#define PCI_INT_DEV1 BIT(1) -+#define PCI_INT_DEV0 BIT(0) -+ -+#define RESET_MODULE_EXTERNAL BIT(28) -+#define RESET_MODULE_FULL_CHIP BIT(24) -+#define RESET_MODULE_AMBA2WMAC BIT(22) -+#define RESET_MODULE_CPU_NMI BIT(21) -+#define RESET_MODULE_CPU_COLD BIT(20) -+#define RESET_MODULE_DMA BIT(19) -+#define RESET_MODULE_SLIC BIT(18) -+#define RESET_MODULE_STEREO BIT(17) -+#define RESET_MODULE_DDR BIT(16) -+#define RESET_MODULE_GE1_MAC BIT(13) -+#define RESET_MODULE_GE1_PHY BIT(12) -+#define RESET_MODULE_USBSUS_OVERRIDE BIT(10) -+#define RESET_MODULE_GE0_MAC BIT(9) -+#define RESET_MODULE_GE0_PHY BIT(8) -+#define RESET_MODULE_USB_OHCI_DLL BIT(6) -+#define RESET_MODULE_USB_HOST BIT(5) -+#define RESET_MODULE_USB_PHY BIT(4) -+#define RESET_MODULE_USB_OHCI_DLL_7240 BIT(3) -+#define RESET_MODULE_PCI_BUS BIT(1) -+#define RESET_MODULE_PCI_CORE BIT(0) -+ -+#define AR724X_RESET_GE1_MDIO BIT(23) -+#define AR724X_RESET_GE0_MDIO BIT(22) -+#define AR724X_RESET_PCIE_PHY_SERIAL BIT(10) -+#define AR724X_RESET_PCIE_PHY BIT(7) -+#define AR724X_RESET_PCIE BIT(6) -+ -+#define REV_ID_MAJOR_MASK 0xfff0 -+#define REV_ID_MAJOR_AR71XX 0x00a0 -+#define REV_ID_MAJOR_AR913X 0x00b0 -+#define REV_ID_MAJOR_AR7240 0x00c0 -+#define REV_ID_MAJOR_AR7241 0x0100 -+#define REV_ID_MAJOR_AR7242 0x1100 -+ -+#define AR71XX_REV_ID_MINOR_MASK 0x3 -+#define AR71XX_REV_ID_MINOR_AR7130 0x0 -+#define AR71XX_REV_ID_MINOR_AR7141 0x1 -+#define AR71XX_REV_ID_MINOR_AR7161 0x2 -+#define AR71XX_REV_ID_REVISION_MASK 0x3 -+#define AR71XX_REV_ID_REVISION_SHIFT 2 -+ -+#define AR91XX_REV_ID_MINOR_MASK 0x3 -+#define AR91XX_REV_ID_MINOR_AR9130 0x0 -+#define AR91XX_REV_ID_MINOR_AR9132 0x1 -+#define AR91XX_REV_ID_REVISION_MASK 0x3 -+#define AR91XX_REV_ID_REVISION_SHIFT 2 -+ -+#define AR724X_REV_ID_REVISION_MASK 0x3 -+ -+extern void __iomem *ar71xx_reset_base; ++static struct gpio_led wp543_leds_gpio[] __initdata = { ++ { ++ .name = "wp543:green:led1", ++ .gpio = WP543_GPIO_LED_1, ++ .active_low = 1, ++ }, { ++ .name = "wp543:green:led2", ++ .gpio = WP543_GPIO_LED_2, ++ .active_low = 1, ++ }, { ++ .name = "wp543:green:wlan", ++ .gpio = WP543_GPIO_LED_WLAN, ++ .active_low = 1, ++ }, { ++ .name = "wp543:green:conn", ++ .gpio = WP543_GPIO_LED_CONN, ++ .active_low = 1, ++ }, { ++ .name = "wp543:green:diag", ++ .gpio = WP543_GPIO_LED_DIAG, ++ .active_low = 1, ++ } ++}; + -+static inline void ar71xx_reset_wr(unsigned reg, u32 val) -+{ -+ __raw_writel(val, ar71xx_reset_base + reg); -+} ++static struct gpio_keys_button wp543_gpio_keys[] __initdata = { ++ { ++ .desc = "sw6", ++ .type = EV_KEY, ++ .code = BTN_0, ++ .debounce_interval = WP543_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WP543_GPIO_SW6, ++ }, { ++ .desc = "sw4", ++ .type = EV_KEY, ++ .code = BTN_1, ++ .debounce_interval = WP543_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WP543_GPIO_SW4, ++ } ++}; + -+static inline u32 ar71xx_reset_rr(unsigned reg) ++static void __init wp543_setup(void) +{ -+ return __raw_readl(ar71xx_reset_base + reg); -+} -+ -+void ar71xx_device_stop(u32 mask); -+void ar71xx_device_start(u32 mask); -+int ar71xx_device_stopped(u32 mask); -+ -+/* -+ * SPI block -+ */ -+#define SPI_REG_FS 0x00 /* Function Select */ -+#define SPI_REG_CTRL 0x04 /* SPI Control */ -+#define SPI_REG_IOC 0x08 /* SPI I/O Control */ -+#define SPI_REG_RDS 0x0c /* Read Data Shift */ -+ -+#define SPI_FS_GPIO BIT(0) /* Enable GPIO mode */ -+ -+#define SPI_CTRL_RD BIT(6) /* Remap Disable */ -+#define SPI_CTRL_DIV_MASK 0x3f ++ ar71xx_add_device_m25p80(NULL); + -+#define SPI_IOC_DO BIT(0) /* Data Out pin */ -+#define SPI_IOC_CLK BIT(8) /* CLK pin */ -+#define SPI_IOC_CS(n) BIT(16 + (n)) -+#define SPI_IOC_CS0 SPI_IOC_CS(0) -+#define SPI_IOC_CS1 SPI_IOC_CS(1) -+#define SPI_IOC_CS2 SPI_IOC_CS(2) -+#define SPI_IOC_CS_ALL (SPI_IOC_CS0 | SPI_IOC_CS1 | SPI_IOC_CS2) ++ ar71xx_add_device_mdio(0xfffffff7); + -+void ar71xx_flash_acquire(void); -+void ar71xx_flash_release(void); ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, ar71xx_mac_base, 0); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_MII; ++ ar71xx_eth0_data.phy_mask = 0x08; ++ ar71xx_eth0_data.reset_bit = RESET_MODULE_GE0_MAC | ++ RESET_MODULE_GE0_PHY; ++ ar71xx_add_device_eth(0); + -+/* -+ * MII_CTRL block -+ */ -+#define MII_REG_MII0_CTRL 0x00 -+#define MII_REG_MII1_CTRL 0x04 ++ ar71xx_add_device_usb(); + -+#define MII0_CTRL_IF_GMII 0 -+#define MII0_CTRL_IF_MII 1 -+#define MII0_CTRL_IF_RGMII 2 -+#define MII0_CTRL_IF_RMII 3 ++ pb42_pci_init(); + -+#define MII1_CTRL_IF_RGMII 0 -+#define MII1_CTRL_IF_RMII 1 ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wp543_leds_gpio), ++ wp543_leds_gpio); + -+#endif /* __ASSEMBLER__ */ ++ ar71xx_register_gpio_keys_polled(-1, WP543_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wp543_gpio_keys), ++ wp543_gpio_keys); ++} + -+#endif /* __ASM_MACH_AR71XX_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,26 @@ ++MIPS_MACHINE(AR71XX_MACH_WP543, "WP543", "Compex WP543", wp543_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt160nl.c linux-2.6.39/arch/mips/ar71xx/mach-wrt160nl.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt160nl.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wrt160nl.c 2011-08-24 02:41:55.617990333 +0200 +@@ -0,0 +1,161 @@ +/* -+ * AR91xx parallel flash driver platform data definitions ++ * Linksys WRT160NL board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#ifndef __AR91XX_FLASH_H -+#define __AR91XX_FLASH_H ++#include ++#include + -+struct mtd_partition; ++#include + -+struct ar91xx_flash_platform_data { -+ unsigned int width; -+ u8 is_shared:1; -+#ifdef CONFIG_MTD_PARTITIONS -+ unsigned int nr_parts; -+ struct mtd_partition *parts; -+#endif -+}; ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++#include "dev-usb.h" ++#include "nvram.h" + -+#endif /* __AR91XX_FLASH_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,56 @@ -+/* -+ * Atheros AR71xx specific CPU feature overrides -+ * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This file was derived from: include/asm-mips/cpu-features.h -+ * Copyright (C) 2003, 2004 Ralf Baechle -+ * Copyright (C) 2004 Maciej W. Rozycki -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ * -+ */ -+#ifndef __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H -+#define __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H ++#define WRT160NL_GPIO_LED_POWER 14 ++#define WRT160NL_GPIO_LED_WPS_AMBER 9 ++#define WRT160NL_GPIO_LED_WPS_BLUE 8 ++#define WRT160NL_GPIO_LED_WLAN 6 + -+#define cpu_has_tlb 1 -+#define cpu_has_4kex 1 -+#define cpu_has_3k_cache 0 -+#define cpu_has_4k_cache 1 -+#define cpu_has_tx39_cache 0 -+#define cpu_has_sb1_cache 0 -+#define cpu_has_fpu 0 -+#define cpu_has_32fpr 0 -+#define cpu_has_counter 1 -+#define cpu_has_watch 1 -+#define cpu_has_divec 1 ++#define WRT160NL_GPIO_BTN_WPS 7 ++#define WRT160NL_GPIO_BTN_RESET 21 + -+#define cpu_has_prefetch 1 -+#define cpu_has_ejtag 1 -+#define cpu_has_llsc 1 ++#define WRT160NL_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WRT160NL_KEYS_DEBOUNCE_INTERVAL (3 * WRT160NL_KEYS_POLL_INTERVAL) + -+#define cpu_has_mips16 1 -+#define cpu_has_mdmx 0 -+#define cpu_has_mips3d 0 -+#define cpu_has_smartmips 0 -+ -+#define cpu_has_mips32r1 1 -+#define cpu_has_mips32r2 1 -+#define cpu_has_mips64r1 0 -+#define cpu_has_mips64r2 0 ++#define WRT160NL_NVRAM_ADDR 0x1f7e0000 ++#define WRT160NL_NVRAM_SIZE 0x10000 + -+#define cpu_has_dsp 0 -+#define cpu_has_mipsmt 0 ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wrt160nl_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x040000, ++ .size = 0x0e0000, ++ }, { ++ .name = "filesytem", ++ .offset = 0x120000, ++ .size = 0x6c0000, ++ }, { ++ .name = "nvram", ++ .offset = 0x7e0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "ART", ++ .offset = 0x7f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x040000, ++ .size = 0x7a0000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#define cpu_has_64bits 0 -+#define cpu_has_64bit_zero_reg 0 -+#define cpu_has_64bit_gp_regs 0 -+#define cpu_has_64bit_addresses 0 ++static struct flash_platform_data wrt160nl_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = wrt160nl_partitions, ++ .nr_parts = ARRAY_SIZE(wrt160nl_partitions), ++#endif ++}; + -+#define cpu_dcache_line_size() 32 -+#define cpu_icache_line_size() 32 ++static struct gpio_led wrt160nl_leds_gpio[] __initdata = { ++ { ++ .name = "wrt160nl:blue:power", ++ .gpio = WRT160NL_GPIO_LED_POWER, ++ .active_low = 1, ++ .default_trigger = "default-on", ++ }, { ++ .name = "wrt160nl:amber:wps", ++ .gpio = WRT160NL_GPIO_LED_WPS_AMBER, ++ .active_low = 1, ++ }, { ++ .name = "wrt160nl:blue:wps", ++ .gpio = WRT160NL_GPIO_LED_WPS_BLUE, ++ .active_low = 1, ++ }, { ++ .name = "wrt160nl:blue:wlan", ++ .gpio = WRT160NL_GPIO_LED_WLAN, ++ .active_low = 1, ++ } ++}; + -+#endif /* __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/gpio.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/gpio.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/gpio.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/gpio.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,53 @@ -+/* -+ * Atheros AR71xx GPIO API definitions -+ * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ * -+ */ ++static struct gpio_keys_button wrt160nl_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WRT160NL_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WRT160NL_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "wps", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WRT160NL_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WRT160NL_GPIO_BTN_WPS, ++ .active_low = 1, ++ } ++}; + -+#ifndef __ASM_MACH_AR71XX_GPIO_H -+#define __ASM_MACH_AR71XX_GPIO_H ++static void __init wrt160nl_setup(void) ++{ ++ const char *nvram = (char *) KSEG1ADDR(WRT160NL_NVRAM_ADDR); ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ u8 mac[6]; + -+#define ARCH_NR_GPIOS 64 -+#include ++ if (nvram_parse_mac_addr(nvram, WRT160NL_NVRAM_SIZE, ++ "lan_hwaddr=", mac) == 0) { ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); ++ } + -+#include ++ ar71xx_add_device_mdio(0x0); + -+extern unsigned long ar71xx_gpio_count; -+extern void __ar71xx_gpio_set_value(unsigned gpio, int value); -+extern int __ar71xx_gpio_get_value(unsigned gpio); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.phy_mask = 0x01; + -+static inline int gpio_to_irq(unsigned gpio) -+{ -+ return AR71XX_GPIO_IRQ(gpio); -+} ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + -+static inline int irq_to_gpio(unsigned irq) -+{ -+ return irq - AR71XX_GPIO_IRQ_BASE; -+} ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+static inline int gpio_get_value(unsigned gpio) -+{ -+ if (gpio < ar71xx_gpio_count) -+ return __ar71xx_gpio_get_value(gpio); ++ ar71xx_add_device_m25p80(&wrt160nl_flash_data); + -+ return __gpio_get_value(gpio); -+} ++ ar71xx_add_device_usb(); + -+static inline void gpio_set_value(unsigned gpio, int value) -+{ -+ if (gpio < ar71xx_gpio_count) -+ __ar71xx_gpio_set_value(gpio, value); ++ if (nvram_parse_mac_addr(nvram, WRT160NL_NVRAM_SIZE, ++ "wl0_hwaddr=", mac) == 0) ++ ar9xxx_add_device_wmac(eeprom, mac); + else -+ __gpio_set_value(gpio, value); -+} -+ -+#define gpio_cansleep __gpio_cansleep ++ ar9xxx_add_device_wmac(eeprom, NULL); + -+#endif /* __ASM_MACH_AR71XX_GPIO_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/irq.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/irq.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/irq.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/irq.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,17 @@ -+/* -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+#ifndef __ASM_MACH_AR71XX_IRQ_H -+#define __ASM_MACH_AR71XX_IRQ_H ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wrt160nl_leds_gpio), ++ wrt160nl_leds_gpio); + -+#define MIPS_CPU_IRQ_BASE 0 -+#define NR_IRQS 56 ++ ar71xx_register_gpio_keys_polled(-1, WRT160NL_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wrt160nl_gpio_keys), ++ wrt160nl_gpio_keys); + -+#include_next ++} + -+#endif /* __ASM_MACH_AR71XX_IRQ_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,32 @@ ++MIPS_MACHINE(AR71XX_MACH_WRT160NL, "WRT160NL", "Linksys WRT160NL", ++ wrt160nl_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt400n.c linux-2.6.39/arch/mips/ar71xx/mach-wrt400n.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wrt400n.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wrt400n.c 2011-08-24 02:41:55.617990333 +0200 +@@ -0,0 +1,164 @@ +/* -+ * Atheros AR71xx specific kernel entry setup ++ * Linksys WRT400N board support + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2009-2010 Gabor Juhos ++ * Copyright (C) 2009 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. -+ * + */ -+#ifndef __ASM_MACH_AR71XX_KERNEL_ENTRY_H -+#define __ASM_MACH_AR71XX_KERNEL_ENTRY_H + -+ /* -+ * Some bootloaders set the 'Kseg0 coherency algorithm' to -+ * 'Cacheable, noncoherent, write-through, no write allocate' -+ * and this cause performance issues. Let's go and change it to -+ * 'Cacheable, noncoherent, write-back, write allocate' -+ */ -+ .macro kernel_entry_setup -+ mfc0 t0, CP0_CONFIG -+ li t1, ~CONF_CM_CMASK -+ and t0, t1 -+ ori t0, CONF_CM_CACHABLE_NONCOHERENT -+ mtc0 t0, CP0_CONFIG -+ nop -+ .endm ++#include ++#include + -+ .macro smp_slave_setup -+ .endm ++#include + -+#endif /* __ASM_MACH_AR71XX_KERNEL_ENTRY_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mach-rb750.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mach-rb750.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mach-rb750.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mach-rb750.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,66 @@ -+/* -+ * MikroTik RouterBOARD 750 definitions -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+#ifndef _MACH_RB750_H -+#define _MACH_RB750_H ++#include "machtype.h" ++#include "devices.h" ++#include "dev-ap94-pci.h" ++#include "dev-m25p80.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" + -+#include ++#define WRT400N_GPIO_LED_ORANGE 5 ++#define WRT400N_GPIO_LED_GREEN 4 ++#define WRT400N_GPIO_LED_POWER 1 ++#define WRT400N_GPIO_LED_WLAN 0 + -+#define RB750_GPIO_LVC573_LE 0 /* Latch enable on LVC573 */ -+#define RB750_GPIO_NAND_IO0 1 /* NAND I/O 0 */ -+#define RB750_GPIO_NAND_IO1 2 /* NAND I/O 1 */ -+#define RB750_GPIO_NAND_IO2 3 /* NAND I/O 2 */ -+#define RB750_GPIO_NAND_IO3 4 /* NAND I/O 3 */ -+#define RB750_GPIO_NAND_IO4 5 /* NAND I/O 4 */ -+#define RB750_GPIO_NAND_IO5 6 /* NAND I/O 5 */ -+#define RB750_GPIO_NAND_IO6 7 /* NAND I/O 6 */ -+#define RB750_GPIO_NAND_IO7 8 /* NAND I/O 7 */ -+#define RB750_GPIO_NAND_NCE 11 /* NAND Chip Enable (active low) */ -+#define RB750_GPIO_NAND_RDY 12 /* NAND Ready */ -+#define RB750_GPIO_NAND_CLE 14 /* NAND Command Latch Enable */ -+#define RB750_GPIO_NAND_ALE 15 /* NAND Address Latch Enable */ -+#define RB750_GPIO_NAND_NRE 16 /* NAND Read Enable (active low) */ -+#define RB750_GPIO_NAND_NWE 17 /* NAND Write Enable (active low) */ ++#define WRT400N_GPIO_BTN_RESET 8 ++#define WRT400N_GPIO_BTN_WLSEC 3 + -+#define RB750_GPIO_BTN_RESET 1 -+#define RB750_GPIO_SPI_CS0 2 -+#define RB750_GPIO_LED_ACT 12 -+#define RB750_GPIO_LED_PORT1 13 -+#define RB750_GPIO_LED_PORT2 14 -+#define RB750_GPIO_LED_PORT3 15 -+#define RB750_GPIO_LED_PORT4 16 -+#define RB750_GPIO_LED_PORT5 17 ++#define WRT400N_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WRT400N_KEYS_DEBOUNE_INTERVAL (3 * WRT400N_KEYS_POLL_INTERVAL) + -+#define RB750_LED_ACT BIT(RB750_GPIO_LED_ACT) -+#define RB750_LED_PORT1 BIT(RB750_GPIO_LED_PORT1) -+#define RB750_LED_PORT2 BIT(RB750_GPIO_LED_PORT2) -+#define RB750_LED_PORT3 BIT(RB750_GPIO_LED_PORT3) -+#define RB750_LED_PORT4 BIT(RB750_GPIO_LED_PORT4) -+#define RB750_LED_PORT5 BIT(RB750_GPIO_LED_PORT5) ++#define WRT400N_MAC_ADDR_OFFSET 0x120c ++#define WRT400N_CALDATA0_OFFSET 0x1000 ++#define WRT400N_CALDATA1_OFFSET 0x5000 + -+#define RB750_LVC573_LE BIT(RB750_GPIO_LVC573_LE) ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wrt400n_partitions[] = { ++ { ++ .name = "uboot", ++ .offset = 0, ++ .size = 0x030000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "env", ++ .offset = 0x030000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "linux", ++ .offset = 0x040000, ++ .size = 0x140000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x180000, ++ .size = 0x630000, ++ }, { ++ .name = "nvram", ++ .offset = 0x7b0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "factory", ++ .offset = 0x7c0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "language", ++ .offset = 0x7d0000, ++ .size = 0x020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "caldata", ++ .offset = 0x7f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x040000, ++ .size = 0x770000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+#define RB750_LED_BITS (RB750_LED_PORT1 | RB750_LED_PORT2 | RB750_LED_PORT3 | \ -+ RB750_LED_PORT4 | RB750_LED_PORT5 | RB750_LED_ACT) ++static struct flash_platform_data wrt400n_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = wrt400n_partitions, ++ .nr_parts = ARRAY_SIZE(wrt400n_partitions), ++#endif ++}; + -+struct rb750_led_data { -+ char *name; -+ char *default_trigger; -+ u32 mask; -+ int active_low; ++static struct gpio_led wrt400n_leds_gpio[] __initdata = { ++ { ++ .name = "wrt400n:green:status", ++ .gpio = WRT400N_GPIO_LED_GREEN, ++ .active_low = 1, ++ }, { ++ .name = "wrt400n:amber:aoss", ++ .gpio = WRT400N_GPIO_LED_ORANGE, ++ .active_low = 1, ++ }, { ++ .name = "wrt400n:green:wlan", ++ .gpio = WRT400N_GPIO_LED_WLAN, ++ .active_low = 1, ++ }, { ++ .name = "wrt400n:green:power", ++ .gpio = WRT400N_GPIO_LED_POWER, ++ .active_low = 1, ++ } +}; + -+struct rb750_led_platform_data { -+ int num_leds; -+ struct rb750_led_data *leds; ++static struct gpio_keys_button wrt400n_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WRT400N_KEYS_DEBOUNE_INTERVAL, ++ .gpio = WRT400N_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "wlsec", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WRT400N_KEYS_DEBOUNE_INTERVAL, ++ .gpio = WRT400N_GPIO_BTN_WLSEC, ++ .active_low = 1, ++ } +}; + -+int rb750_latch_change(u32 mask_clr, u32 mask_set); ++static void __init wrt400n_setup(void) ++{ ++ u8 *art = (u8 *) KSEG1ADDR(0x1fff0000); ++ u8 *mac = art + WRT400N_MAC_ADDR_OFFSET; + -+#endif /* _MACH_RB750_H */ -\ No newline at end of file -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mangle-port.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mangle-port.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mangle-port.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mangle-port.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,45 @@ -+/* -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This file was derived from: inlude/asm-mips/mach-generic/mangle-port.h -+ * Copyright (C) 2003, 2004 Ralf Baechle -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ ar71xx_add_device_mdio(0x0); + -+#ifndef __ASM_MACH_AR71XX_MANGLE_PORT_H -+#define __ASM_MACH_AR71XX_MANGLE_PORT_H ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 1); ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+#define __swizzle_addr_b(port) ((port) ^ 3) -+#define __swizzle_addr_w(port) ((port) ^ 2) -+#define __swizzle_addr_l(port) (port) -+#define __swizzle_addr_q(port) (port) ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 2); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + -+#if defined(CONFIG_SWAP_IO_SPACE) ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+# define ioswabb(a, x) (x) -+# define __mem_ioswabb(a, x) (x) -+# define ioswabw(a, x) le16_to_cpu(x) -+# define __mem_ioswabw(a, x) (x) -+# define ioswabl(a, x) le32_to_cpu(x) -+# define __mem_ioswabl(a, x) (x) -+# define ioswabq(a, x) le64_to_cpu(x) -+# define __mem_ioswabq(a, x) (x) ++ ar71xx_add_device_m25p80(&wrt400n_flash_data); + -+#else ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wrt400n_leds_gpio), ++ wrt400n_leds_gpio); + -+# define ioswabb(a, x) (x) -+# define __mem_ioswabb(a, x) (x) -+# define ioswabw(a, x) (x) -+# define __mem_ioswabw(a, x) cpu_to_le16(x) -+# define ioswabl(a, x) (x) -+# define __mem_ioswabl(a, x) cpu_to_le32(x) -+# define ioswabq(a, x) (x) -+# define __mem_ioswabq(a, x) cpu_to_le64(x) ++ ar71xx_register_gpio_keys_polled(-1, WRT400N_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wrt400n_gpio_keys), ++ wrt400n_gpio_keys); + -+#endif ++ ap94_pci_init(art + WRT400N_CALDATA0_OFFSET, NULL, ++ art + WRT400N_CALDATA1_OFFSET, NULL); ++} + -+#endif /* __ASM_MACH_AR71XX_MANGLE_PORT_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/pci.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/pci.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/pci.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/pci.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,39 @@ ++MIPS_MACHINE(AR71XX_MACH_WRT400N, "WRT400N", "Linksys WRT400N", wrt400n_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-ag300h.c linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-ag300h.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-ag300h.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-ag300h.c 2011-08-24 02:41:55.628193451 +0200 +@@ -0,0 +1,231 @@ +/* -+ * Atheros AR71xx SoC specific PCI definitions ++ * Buffalo WZR-HP-AG300H board support + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2011 Felix Fietkau + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#ifndef __ASM_MACH_AR71XX_PCI_H -+#define __ASM_MACH_AR71XX_PCI_H ++#include ++#include ++#include ++#include + -+struct pci_dev; ++#include ++#include ++#include + -+struct ar71xx_pci_irq { -+ int irq; -+ u8 slot; -+ u8 pin; ++#include "machtype.h" ++#include "devices.h" ++#include "dev-ap94-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++#include "dev-m25p80.h" ++#include "dev-usb.h" ++ ++#define WZRHPAG300H_MAC_OFFSET 0x20c ++#define WZRHPAG300H_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL (3 * WZRHPAG300H_KEYS_POLL_INTERVAL) ++ ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wzrhpag300h_flash_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x0040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x0040000, ++ .size = 0x0010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "art", ++ .offset = 0x0050000, ++ .size = 0x0010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x0060000, ++ .size = 0x0100000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x0160000, ++ .size = 0x1e90000, ++ }, { ++ .name = "user_property", ++ .offset = 0x1ff0000, ++ .size = 0x0010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x0060000, ++ .size = 0x1f90000, ++ } +}; + -+extern int (*ar71xx_pci_plat_dev_init)(struct pci_dev *dev); -+extern unsigned ar71xx_pci_nr_irqs __initdata; -+extern struct ar71xx_pci_irq *ar71xx_pci_irq_map __initdata; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+int ar71xx_pcibios_map_irq(const struct pci_dev *dev, -+ uint8_t slot, uint8_t pin) __init; -+int ar71xx_pcibios_init(void) __init; ++static struct mtd_info *concat_devs[2] = { NULL, NULL }; ++static struct work_struct mtd_concat_work; + -+int ar71xx_pci_be_handler(int is_fixup); ++static void mtd_concat_add_work(struct work_struct *work) ++{ ++ struct mtd_info *mtd; + -+int ar724x_pcibios_map_irq(const struct pci_dev *dev, -+ uint8_t slot, uint8_t pin) __init; -+int ar724x_pcibios_init(void) __init; ++ mtd = mtd_concat_create(concat_devs, ARRAY_SIZE(concat_devs), "flash"); + -+int ar71xx_pci_init(unsigned nr_irqs, struct ar71xx_pci_irq *map) __init; ++#ifdef CONFIG_MTD_PARTITIONS ++ add_mtd_partitions(mtd, wzrhpag300h_flash_partitions, ++ ARRAY_SIZE(wzrhpag300h_flash_partitions)); ++#else ++ add_mtd_device(mtd); ++#endif ++} + -+#endif /* __ASM_MACH_AR71XX_PCI_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/platform.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/platform.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/platform.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/platform.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,61 @@ -+/* -+ * Atheros AR71xx SoC specific platform data definitions -+ * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++static void mtd_concat_add(struct mtd_info *mtd) ++{ ++ static bool registered = false; + -+#ifndef __ASM_MACH_AR71XX_PLATFORM_H -+#define __ASM_MACH_AR71XX_PLATFORM_H ++ if (registered) ++ return; + -+#include -+#include -+#include -+#include ++ if (!strcmp(mtd->name, "spi0.0")) ++ concat_devs[0] = mtd; ++ else if (!strcmp(mtd->name, "spi0.1")) ++ concat_devs[1] = mtd; ++ else ++ return; + -+struct ag71xx_platform_data { -+ phy_interface_t phy_if_mode; -+ u32 phy_mask; -+ int speed; -+ int duplex; -+ u32 reset_bit; -+ u32 mii_if; -+ u8 mac_addr[ETH_ALEN]; -+ struct device *mii_bus_dev; ++ if (!concat_devs[0] || !concat_devs[1]) ++ return; + -+ u8 has_gbit:1; -+ u8 is_ar91xx:1; -+ u8 is_ar724x:1; -+ u8 has_ar8216:1; ++ registered = true; ++ INIT_WORK(&mtd_concat_work, mtd_concat_add_work); ++ schedule_work(&mtd_concat_work); ++} ++ ++static void mtd_concat_remove(struct mtd_info *mtd) ++{ ++} + -+ void (* ddr_flush)(void); -+ void (* set_pll)(int speed); ++static void add_mtd_concat_notifier(void) ++{ ++ static struct mtd_notifier not = { ++ .add = mtd_concat_add, ++ .remove = mtd_concat_remove, ++ }; + -+ u32 fifo_cfg1; -+ u32 fifo_cfg2; -+ u32 fifo_cfg3; -+}; ++ register_mtd_user(¬); ++} + -+struct ag71xx_mdio_platform_data { -+ u32 phy_mask; -+ int is_ar7240; ++static struct gpio_led wzrhpag300h_leds_gpio[] __initdata = { ++ { ++ .name = "wzr-hp-ag300h:red:diag", ++ .gpio = 1, ++ .active_low = 1, ++ }, +}; + -+struct ar71xx_ehci_platform_data { -+ u8 is_ar91xx; ++ ++static struct gpio_keys_button wzrhpag300h_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = 11, ++ .active_low = 1, ++ }, { ++ .desc = "usb", ++ .type = EV_KEY, ++ .code = BTN_2, ++ .debounce_interval = WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = 3, ++ .active_low = 1, ++ }, { ++ .desc = "aoss", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = 5, ++ .active_low = 1, ++ }, { ++ .desc = "router_auto", ++ .type = EV_KEY, ++ .code = BTN_6, ++ .debounce_interval = WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = 6, ++ .active_low = 1, ++ }, { ++ .desc = "router_off", ++ .type = EV_KEY, ++ .code = BTN_5, ++ .debounce_interval = WZRHPAG300H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = 7, ++ .active_low = 1, ++ } +}; + -+struct ar71xx_spi_platform_data { -+ unsigned bus_num; -+ unsigned num_chipselect; -+ u32 (*get_ioc_base)(u8 chip_select, int cs_high, int is_on); ++static struct spi_board_info ar71xx_spi_info[] = { ++ { ++ .bus_num = 0, ++ .chip_select = 0, ++ .max_speed_hz = 25000000, ++ .modalias = "m25p80", ++ }, ++ { ++ .bus_num = 0, ++ .chip_select = 1, ++ .max_speed_hz = 25000000, ++ .modalias = "m25p80", ++ } +}; + -+#define AR71XX_SPI_CS_INACTIVE 0 -+#define AR71XX_SPI_CS_ACTIVE 1 ++static void __init wzrhpag300h_setup(void) ++{ ++ u8 *eeprom1 = (u8 *) KSEG1ADDR(0x1f051000); ++ u8 *eeprom2 = (u8 *) KSEG1ADDR(0x1f055000); ++ u8 *mac1 = eeprom1 + WZRHPAG300H_MAC_OFFSET; ++ u8 *mac2 = eeprom2 + WZRHPAG300H_MAC_OFFSET; + -+#endif /* __ASM_MACH_AR71XX_PLATFORM_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/war.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/war.h ---- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/war.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/war.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,25 @@ -+/* -+ * 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) 2002, 2004, 2007 by Ralf Baechle -+ */ -+#ifndef __ASM_MACH_AR71XX_WAR_H -+#define __ASM_MACH_AR71XX_WAR_H ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac1, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac2, 1); + -+#define R4600_V1_INDEX_ICACHEOP_WAR 0 -+#define R4600_V1_HIT_CACHEOP_WAR 0 -+#define R4600_V2_HIT_CACHEOP_WAR 0 -+#define R5432_CP0_INTERRUPT_WAR 0 -+#define BCM1250_M3_WAR 0 -+#define SIBYTE_1956_WAR 0 -+#define MIPS4K_ICACHE_REFILL_WAR 0 -+#define MIPS_CACHE_SYNC_WAR 0 -+#define TX49XX_ICACHE_INDEX_INV_WAR 0 -+#define RM9000_CDEX_SMP_WAR 0 -+#define ICACHE_REFILLS_WORKAROUND_WAR 0 -+#define R10000_LLSC_WAR 0 -+#define MIPS34K_MISSED_ITLB_WAR 0 ++ ar71xx_add_device_mdio(~(BIT(0) | BIT(4))); + -+#endif /* __ASM_MACH_AR71XX_WAR_H */ -diff -Nur linux-2.6.39.orig/arch/mips/include/asm/time.h linux-2.6.39/arch/mips/include/asm/time.h ---- linux-2.6.39.orig/arch/mips/include/asm/time.h 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/include/asm/time.h 2011-05-27 14:36:51.000000000 +0200 -@@ -52,6 +52,7 @@ - */ - #ifdef CONFIG_CEVT_R4K_LIB - extern unsigned int __weak get_c0_compare_int(void); -+extern unsigned int __weak get_c0_compare_irq(void); - extern int r4k_clockevent_init(void); - #endif - -diff -Nur linux-2.6.39.orig/arch/mips/kernel/Makefile linux-2.6.39/arch/mips/kernel/Makefile ---- linux-2.6.39.orig/arch/mips/kernel/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/kernel/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -94,6 +94,7 @@ - - obj-$(CONFIG_KEXEC) += machine_kexec.o relocate_kernel.o - obj-$(CONFIG_EARLY_PRINTK) += early_printk.o -+obj-$(CONFIG_MIPS_MACHINE) += mips_machine.o - obj-$(CONFIG_SPINLOCK_TEST) += spinlock_test.o - obj-$(CONFIG_MIPS_MACHINE) += mips_machine.o - -diff -Nur linux-2.6.39.orig/arch/mips/kernel/traps.c linux-2.6.39/arch/mips/kernel/traps.c ---- linux-2.6.39.orig/arch/mips/kernel/traps.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/kernel/traps.c 2011-05-27 14:36:51.000000000 +0200 -@@ -46,6 +46,7 @@ - #include - #include - #include -+#include - #include - #include - #include -@@ -1576,6 +1577,8 @@ - if (cpu_has_mips_r2) { - cp0_compare_irq_shift = CAUSEB_TI - CAUSEB_IP; - cp0_compare_irq = (read_c0_intctl() >> INTCTLB_IPTI) & 7; -+ if (get_c0_compare_irq) -+ cp0_compare_irq = get_c0_compare_irq(); - cp0_perfcount_irq = (read_c0_intctl() >> INTCTLB_IPPCI) & 7; - if (cp0_perfcount_irq == cp0_compare_irq) - cp0_perfcount_irq = -1; -diff -Nur linux-2.6.39.orig/arch/mips/pci/Makefile linux-2.6.39/arch/mips/pci/Makefile ---- linux-2.6.39.orig/arch/mips/pci/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/arch/mips/pci/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -18,6 +18,7 @@ - obj-$(CONFIG_BCM47XX) += pci-bcm47xx.o - obj-$(CONFIG_BCM63XX) += pci-bcm63xx.o fixup-bcm63xx.o \ - ops-bcm63xx.o -+obj-$(CONFIG_ATHEROS_AR71XX) += pci-ar71xx.o pci-ar724x.o - - # - # These are still pretty much in the old state, watch, go blind. -diff -Nur linux-2.6.39.orig/arch/mips/pci/pci-ar71xx.c linux-2.6.39/arch/mips/pci/pci-ar71xx.c ---- linux-2.6.39.orig/arch/mips/pci/pci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/pci/pci-ar71xx.c 2011-06-01 14:02:22.000000000 +0200 -@@ -0,0 +1,408 @@ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; ++ ar71xx_eth0_data.phy_mask = BIT(0); ++ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = BIT(4); ++ ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); ++ ++ ar71xx_add_device_usb(); ++ gpio_request(2, "usb"); ++ gpio_direction_output(2, 1); ++ ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wzrhpag300h_leds_gpio), ++ wzrhpag300h_leds_gpio); ++ ++ ar71xx_register_gpio_keys_polled(-1, WZRHPAG300H_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wzrhpag300h_gpio_keys), ++ wzrhpag300h_gpio_keys); ++ ++ ar71xx_add_device_spi(NULL, ar71xx_spi_info, ++ ARRAY_SIZE(ar71xx_spi_info)); ++ ++ add_mtd_concat_notifier(); ++ ++ ap94_pci_init(eeprom1, mac1, eeprom2, mac2); ++} ++ ++MIPS_MACHINE(AR71XX_MACH_WZR_HP_AG300H, "WZR-HP-AG300H", ++ "Buffalo WZR-HP-AG300H", wzrhpag300h_setup); ++ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-g300nh.c linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-g300nh.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-wzr-hp-g300nh.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-wzr-hp-g300nh.c 2011-08-24 02:41:55.649418561 +0200 +@@ -0,0 +1,292 @@ +/* -+ * Atheros AR71xx PCI host controller driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Buffalo WZR-HP-G300NH board support + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include -+#include -+#include -+#include ++#include ++#include ++#include ++#include ++#include + ++#include +#include -+#include -+ -+#undef DEBUG -+#ifdef DEBUG -+#define DBG(fmt, args...) printk(KERN_DEBUG fmt, ## args) -+#else -+#define DBG(fmt, args...) -+#endif -+ -+#define AR71XX_PCI_DELAY 100 /* msecs */ -+ -+#if 0 -+#define PCI_IDSEL_BASE PCI_IDSEL_ADL_START -+#else -+#define PCI_IDSEL_BASE 0 -+#endif ++#include + -+static void __iomem *ar71xx_pcicfg_base; -+static DEFINE_SPINLOCK(ar71xx_pci_lock); -+static int ar71xx_pci_fixup_enable; ++#include "machtype.h" ++#include "devices.h" ++#include "dev-ar9xxx-wmac.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" ++#include "dev-usb.h" + -+static inline void ar71xx_pci_delay(void) -+{ -+ mdelay(AR71XX_PCI_DELAY); -+} ++#define WZRHPG300NH_GPIO_LED_USB 0 ++#define WZRHPG300NH_GPIO_LED_DIAG 1 ++#define WZRHPG300NH_GPIO_LED_WIRELESS 6 ++#define WZRHPG300NH_GPIO_LED_SECURITY 17 ++#define WZRHPG300NH_GPIO_LED_ROUTER 18 + -+/* Byte lane enable bits */ -+static u8 ble_table[4][4] = { -+ {0x0, 0xf, 0xf, 0xf}, -+ {0xe, 0xd, 0xb, 0x7}, -+ {0xc, 0xf, 0x3, 0xf}, -+ {0xf, 0xf, 0xf, 0xf}, -+}; ++#define WZRHPG300NH_GPIO_RTL8366_SDA 19 ++#define WZRHPG300NH_GPIO_RTL8366_SCK 20 + -+static inline u32 ar71xx_pci_get_ble(int where, int size, int local) -+{ -+ u32 t; ++#define WZRHPG300NH_GPIO_74HC153_S0 9 ++#define WZRHPG300NH_GPIO_74HC153_S1 11 ++#define WZRHPG300NH_GPIO_74HC153_1Y 12 ++#define WZRHPG300NH_GPIO_74HC153_2Y 14 + -+ t = ble_table[size & 3][where & 3]; -+ BUG_ON(t == 0xf); -+ t <<= (local) ? 20 : 4; -+ return t; -+} ++#define WZRHPG300NH_GPIO_EXP_BASE 32 ++#define WZRHPG300NH_GPIO_BTN_AOSS (WZRHPG300NH_GPIO_EXP_BASE + 0) ++#define WZRHPG300NH_GPIO_BTN_RESET (WZRHPG300NH_GPIO_EXP_BASE + 1) ++#define WZRHPG300NH_GPIO_BTN_ROUTER_ON (WZRHPG300NH_GPIO_EXP_BASE + 2) ++#define WZRHPG300NH_GPIO_BTN_QOS_ON (WZRHPG300NH_GPIO_EXP_BASE + 3) ++#define WZRHPG300NH_GPIO_BTN_USB (WZRHPG300NH_GPIO_EXP_BASE + 5) ++#define WZRHPG300NH_GPIO_BTN_ROUTER_AUTO (WZRHPG300NH_GPIO_EXP_BASE + 6) ++#define WZRHPG300NH_GPIO_BTN_QOS_OFF (WZRHPG300NH_GPIO_EXP_BASE + 7) + -+static inline u32 ar71xx_pci_bus_addr(struct pci_bus *bus, unsigned int devfn, -+ int where) -+{ -+ u32 ret; ++#define WZRHPG300NH_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL (3 * WZRHPG300NH_KEYS_POLL_INTERVAL) + -+ if (!bus->number) { -+ /* type 0 */ -+ ret = (1 << (PCI_IDSEL_BASE + PCI_SLOT(devfn))) -+ | (PCI_FUNC(devfn) << 8) | (where & ~3); -+ } else { -+ /* type 1 */ -+ ret = (bus->number << 16) | (PCI_SLOT(devfn) << 11) -+ | (PCI_FUNC(devfn) << 8) | (where & ~3) | 1; -+ } ++#define WZRHPG300NH_MAC_OFFSET 0x20c + -+ return ret; -+} ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition wzrhpg300nh_flash_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x0040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x0040000, ++ .size = 0x0020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = 0x0060000, ++ .size = 0x0100000, ++ }, { ++ .name = "rootfs", ++ .offset = 0x0160000, ++ .size = 0x1e60000, ++ }, { ++ .name = "user_property", ++ .offset = 0x1fc0000, ++ .size = 0x0020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "art", ++ .offset = 0x1fe0000, ++ .size = 0x0020000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x0060000, ++ .size = 0x1f60000, ++ } ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+int ar71xx_pci_be_handler(int is_fixup) -+{ -+ void __iomem *base = ar71xx_pcicfg_base; -+ u32 pci_err; -+ u32 ahb_err; ++static struct ar91xx_flash_platform_data wzrhpg300nh_flash_data = { ++ .width = 2, ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = wzrhpg300nh_flash_partitions, ++ .nr_parts = ARRAY_SIZE(wzrhpg300nh_flash_partitions), ++#endif ++}; + -+ pci_err = __raw_readl(base + PCI_REG_PCI_ERR) & 3; -+ if (pci_err) { -+ if (!is_fixup) -+ printk(KERN_ALERT "PCI error %d at PCI addr 0x%x\n", -+ pci_err, -+ __raw_readl(base + PCI_REG_PCI_ERR_ADDR)); ++#define WZRHPG300NH_FLASH_BASE 0x1e000000 ++#define WZRHPG300NH_FLASH_SIZE (32 * 1024 * 1024) + -+ __raw_writel(pci_err, base + PCI_REG_PCI_ERR); -+ } ++static struct resource wzrhpg300nh_flash_resources[] = { ++ [0] = { ++ .start = WZRHPG300NH_FLASH_BASE, ++ .end = WZRHPG300NH_FLASH_BASE + WZRHPG300NH_FLASH_SIZE - 1, ++ .flags = IORESOURCE_MEM, ++ }, ++}; + -+ ahb_err = __raw_readl(base + PCI_REG_AHB_ERR) & 1; -+ if (ahb_err) { -+ if (!is_fixup) -+ printk(KERN_ALERT "AHB error at AHB address 0x%x\n", -+ __raw_readl(base + PCI_REG_AHB_ERR_ADDR)); ++static struct platform_device wzrhpg300nh_flash_device = { ++ .name = "ar91xx-flash", ++ .id = -1, ++ .resource = wzrhpg300nh_flash_resources, ++ .num_resources = ARRAY_SIZE(wzrhpg300nh_flash_resources), ++ .dev = { ++ .platform_data = &wzrhpg300nh_flash_data, ++ } ++}; + -+ __raw_writel(ahb_err, base + PCI_REG_AHB_ERR); ++static struct gpio_led wzrhpg300nh_leds_gpio[] __initdata = { ++ { ++ .name = "wzr-hp-g300nh:orange:security", ++ .gpio = WZRHPG300NH_GPIO_LED_SECURITY, ++ .active_low = 1, ++ }, { ++ .name = "wzr-hp-g300nh:green:wireless", ++ .gpio = WZRHPG300NH_GPIO_LED_WIRELESS, ++ .active_low = 1, ++ }, { ++ .name = "wzr-hp-g300nh:green:router", ++ .gpio = WZRHPG300NH_GPIO_LED_ROUTER, ++ .active_low = 1, ++ }, { ++ .name = "wzr-hp-g300nh:red:diag", ++ .gpio = WZRHPG300NH_GPIO_LED_DIAG, ++ .active_low = 1, ++ }, { ++ .name = "wzr-hp-g300nh:blue:usb", ++ .gpio = WZRHPG300NH_GPIO_LED_USB, ++ .active_low = 1, + } ++}; + -+ return ((ahb_err | pci_err) ? 1 : 0); -+} ++static struct gpio_keys_button wzrhpg300nh_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_RESET, ++ .active_low = 1, ++ }, { ++ .desc = "aoss", ++ .type = EV_KEY, ++ .code = KEY_WPS_BUTTON, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_AOSS, ++ .active_low = 1, ++ }, { ++ .desc = "usb", ++ .type = EV_KEY, ++ .code = BTN_2, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_USB, ++ .active_low = 1, ++ }, { ++ .desc = "qos_on", ++ .type = EV_KEY, ++ .code = BTN_3, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_QOS_ON, ++ .active_low = 0, ++ }, { ++ .desc = "qos_off", ++ .type = EV_KEY, ++ .code = BTN_4, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_QOS_OFF, ++ .active_low = 0, ++ }, { ++ .desc = "router_on", ++ .type = EV_KEY, ++ .code = BTN_5, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_ROUTER_ON, ++ .active_low = 0, ++ }, { ++ .desc = "router_auto", ++ .type = EV_KEY, ++ .code = BTN_6, ++ .debounce_interval = WZRHPG300NH_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = WZRHPG300NH_GPIO_BTN_ROUTER_AUTO, ++ .active_low = 0, ++ } ++}; + -+static inline int ar71xx_pci_set_cfgaddr(struct pci_bus *bus, -+ unsigned int devfn, int where, int size, u32 cmd) -+{ -+ void __iomem *base = ar71xx_pcicfg_base; -+ u32 addr; ++static struct nxp_74hc153_platform_data wzrhpg300nh_74hc153_data = { ++ .gpio_base = WZRHPG300NH_GPIO_EXP_BASE, ++ .gpio_pin_s0 = WZRHPG300NH_GPIO_74HC153_S0, ++ .gpio_pin_s1 = WZRHPG300NH_GPIO_74HC153_S1, ++ .gpio_pin_1y = WZRHPG300NH_GPIO_74HC153_1Y, ++ .gpio_pin_2y = WZRHPG300NH_GPIO_74HC153_2Y, ++}; + -+ addr = ar71xx_pci_bus_addr(bus, devfn, where); ++static struct platform_device wzrhpg300nh_74hc153_device = { ++ .name = NXP_74HC153_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &wzrhpg300nh_74hc153_data, ++ } ++}; + -+ DBG("PCI: set cfgaddr: %02x:%02x.%01x/%02x:%01d, addr=%08x\n", -+ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), -+ where, size, addr); ++static struct rtl8366_platform_data wzrhpg300nh_rtl8366_data = { ++ .gpio_sda = WZRHPG300NH_GPIO_RTL8366_SDA, ++ .gpio_sck = WZRHPG300NH_GPIO_RTL8366_SCK, ++}; + -+ __raw_writel(addr, base + PCI_REG_CFG_AD); -+ __raw_writel(cmd | ar71xx_pci_get_ble(where, size, 0), -+ base + PCI_REG_CFG_CBE); ++static struct platform_device wzrhpg300nh_rtl8366s_device = { ++ .name = RTL8366S_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &wzrhpg300nh_rtl8366_data, ++ } ++}; + -+ return ar71xx_pci_be_handler(1); -+} ++static struct platform_device wzrhpg300nh_rtl8366rb_device = { ++ .name = RTL8366RB_DRIVER_NAME, ++ .id = -1, ++ .dev = { ++ .platform_data = &wzrhpg300nh_rtl8366_data, ++ } ++}; + -+static int ar71xx_pci_read_config(struct pci_bus *bus, unsigned int devfn, -+ int where, int size, u32 *value) ++static void __init wzrhpg300nh_setup(void) +{ -+ void __iomem *base = ar71xx_pcicfg_base; -+ static u32 mask[8] = {0, 0xff, 0xffff, 0, 0xffffffff, 0, 0, 0}; -+ unsigned long flags; -+ u32 data; -+ int ret; ++ u8 *eeprom = (u8 *) KSEG1ADDR(0x1fff1000); ++ u8 *mac = eeprom + WZRHPG300NH_MAC_OFFSET; ++ bool hasrtl8366rb = false; + -+ ret = PCIBIOS_SUCCESSFUL; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); + -+ DBG("PCI: read config: %02x:%02x.%01x/%02x:%01d\n", bus->number, -+ PCI_SLOT(devfn), PCI_FUNC(devfn), where, size); ++ if (rtl8366_smi_detect(&wzrhpg300nh_rtl8366_data) == RTL8366_TYPE_RB) ++ hasrtl8366rb = true; + -+ spin_lock_irqsave(&ar71xx_pci_lock, flags); ++ if (hasrtl8366rb) { ++ ar71xx_eth0_pll_data.pll_1000 = 0x1f000000; ++ ar71xx_eth0_data.mii_bus_dev = &wzrhpg300nh_rtl8366rb_device.dev; ++ ar71xx_eth1_pll_data.pll_1000 = 0x100; ++ ar71xx_eth1_data.mii_bus_dev = &wzrhpg300nh_rtl8366rb_device.dev; ++ } else { ++ ar71xx_eth0_pll_data.pll_1000 = 0x1e000100; ++ ar71xx_eth0_data.mii_bus_dev = &wzrhpg300nh_rtl8366s_device.dev; ++ ar71xx_eth1_pll_data.pll_1000 = 0x1e000100; ++ ar71xx_eth1_data.mii_bus_dev = &wzrhpg300nh_rtl8366s_device.dev; ++ } + -+ if (bus->number == 0 && devfn == 0) { -+ u32 t; ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth0_data.speed = SPEED_1000; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+ t = PCI_CRP_CMD_READ | (where & ~3); ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RGMII; ++ ar71xx_eth1_data.phy_mask = 0x10; + -+ __raw_writel(t, base + PCI_REG_CRP_AD_CBE); -+ data = __raw_readl(base + PCI_REG_CRP_RDDATA); ++ ar71xx_add_device_eth(0); ++ ar71xx_add_device_eth(1); + -+ DBG("PCI: rd local cfg, ad_cbe:%08x, data:%08x\n", t, data); ++ ar71xx_add_device_usb(); ++ ar9xxx_add_device_wmac(eeprom, NULL); + -+ } else { -+ int err; ++ platform_device_register(&wzrhpg300nh_74hc153_device); ++ platform_device_register(&wzrhpg300nh_flash_device); + -+ err = ar71xx_pci_set_cfgaddr(bus, devfn, where, size, -+ PCI_CFG_CMD_READ); ++ if (hasrtl8366rb) ++ platform_device_register(&wzrhpg300nh_rtl8366rb_device); ++ else ++ platform_device_register(&wzrhpg300nh_rtl8366s_device); + -+ if (err == 0) { -+ data = __raw_readl(base + PCI_REG_CFG_RDDATA); -+ } else { -+ ret = PCIBIOS_DEVICE_NOT_FOUND; -+ data = ~0; -+ } -+ } ++ ar71xx_add_device_leds_gpio(-1, ARRAY_SIZE(wzrhpg300nh_leds_gpio), ++ wzrhpg300nh_leds_gpio); + -+ spin_unlock_irqrestore(&ar71xx_pci_lock, flags); ++ ar71xx_register_gpio_keys_polled(-1, WZRHPG300NH_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(wzrhpg300nh_gpio_keys), ++ wzrhpg300nh_gpio_keys); + -+ DBG("PCI: read config: data=%08x raw=%08x\n", -+ (data >> (8 * (where & 3))) & mask[size & 7], data); ++} + -+ *value = (data >> (8 * (where & 3))) & mask[size & 7]; ++MIPS_MACHINE(AR71XX_MACH_WZR_HP_G300NH, "WZR-HP-G300NH", ++ "Buffalo WZR-HP-G300NH", wzrhpg300nh_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/mach-zcn-1523h.c linux-2.6.39/arch/mips/ar71xx/mach-zcn-1523h.c +--- linux-2.6.39.orig/arch/mips/ar71xx/mach-zcn-1523h.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/mach-zcn-1523h.c 2011-08-24 02:41:55.649418561 +0200 +@@ -0,0 +1,214 @@ ++/* ++ * Zcomax ZCN-1523H-2-8/5-16 board support ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ return ret; -+} ++#include ++#include + -+static int ar71xx_pci_write_config(struct pci_bus *bus, unsigned int devfn, -+ int where, int size, u32 value) -+{ -+ void __iomem *base = ar71xx_pcicfg_base; -+ unsigned long flags; -+ int ret; ++#include + -+ DBG("PCI: write config: %02x:%02x.%01x/%02x:%01d value=%08x\n", -+ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), -+ where, size, value); -+ -+ value = value << (8 * (where & 3)); -+ ret = PCIBIOS_SUCCESSFUL; -+ -+ spin_lock_irqsave(&ar71xx_pci_lock, flags); -+ if (bus->number == 0 && devfn == 0) { -+ u32 t; ++#include "machtype.h" ++#include "devices.h" ++#include "dev-m25p80.h" ++#include "dev-ap91-pci.h" ++#include "dev-gpio-buttons.h" ++#include "dev-leds-gpio.h" + -+ t = PCI_CRP_CMD_WRITE | (where & ~3); -+ t |= ar71xx_pci_get_ble(where, size, 1); ++#define ZCN_1523H_GPIO_BTN_RESET 0 ++#define ZCN_1523H_GPIO_LED_INIT 11 ++#define ZCN_1523H_GPIO_LED_LAN1 17 + -+ DBG("PCI: wr local cfg, ad_cbe:%08x, value:%08x\n", t, value); ++#define ZCN_1523H_2_GPIO_LED_WEAK 13 ++#define ZCN_1523H_2_GPIO_LED_MEDIUM 14 ++#define ZCN_1523H_2_GPIO_LED_STRONG 15 + -+ __raw_writel(t, base + PCI_REG_CRP_AD_CBE); -+ __raw_writel(value, base + PCI_REG_CRP_WRDATA); -+ } else { -+ int err; ++#define ZCN_1523H_5_GPIO_LED_UNKNOWN 1 ++#define ZCN_1523H_5_GPIO_LED_LAN2 13 ++#define ZCN_1523H_5_GPIO_LED_WEAK 14 ++#define ZCN_1523H_5_GPIO_LED_MEDIUM 15 ++#define ZCN_1523H_5_GPIO_LED_STRONG 16 + -+ err = ar71xx_pci_set_cfgaddr(bus, devfn, where, size, -+ PCI_CFG_CMD_WRITE); ++#define ZCN_1523H_KEYS_POLL_INTERVAL 20 /* msecs */ ++#define ZCN_1523H_KEYS_DEBOUNCE_INTERVAL (3 * ZCN_1523H_KEYS_POLL_INTERVAL) + -+ if (err == 0) -+ __raw_writel(value, base + PCI_REG_CFG_WRDATA); -+ else -+ ret = PCIBIOS_DEVICE_NOT_FOUND; ++#ifdef CONFIG_MTD_PARTITIONS ++static struct mtd_partition zcn_1523h_partitions[] = { ++ { ++ .name = "u-boot", ++ .offset = 0, ++ .size = 0x040000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "u-boot-env", ++ .offset = 0x040000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "rootfs", ++ .offset = 0x050000, ++ .size = 0x610000, ++ }, { ++ .name = "kernel", ++ .offset = 0x660000, ++ .size = 0x170000, ++ }, { ++ .name = "configure", ++ .offset = 0x7d0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "mfg", ++ .offset = 0x7e0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "eeprom", ++ .offset = 0x7f0000, ++ .size = 0x010000, ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "firmware", ++ .offset = 0x050000, ++ .size = 0x780000, + } -+ spin_unlock_irqrestore(&ar71xx_pci_lock, flags); -+ -+ return ret; -+} -+ -+static void ar71xx_pci_fixup(struct pci_dev *dev) -+{ -+ u32 t; -+ -+ if (!ar71xx_pci_fixup_enable) -+ return; -+ -+ if (dev->bus->number != 0 || dev->devfn != 0) -+ return; -+ -+ DBG("PCI: fixup host controller %s (%04x:%04x)\n", pci_name(dev), -+ dev->vendor, dev->device); -+ -+ /* setup COMMAND register */ -+ t = PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | PCI_COMMAND_INVALIDATE -+ | PCI_COMMAND_PARITY | PCI_COMMAND_SERR | PCI_COMMAND_FAST_BACK; -+ -+ pci_write_config_word(dev, PCI_COMMAND, t); -+} -+DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, ar71xx_pci_fixup); -+ -+int __init ar71xx_pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, -+ uint8_t pin) -+{ -+ int irq = -1; -+ int i; -+ -+ slot -= PCI_IDSEL_ADL_START - PCI_IDSEL_BASE; -+ -+ for (i = 0; i < ar71xx_pci_nr_irqs; i++) { -+ struct ar71xx_pci_irq *entry; ++}; ++#endif /* CONFIG_MTD_PARTITIONS */ + -+ entry = &ar71xx_pci_irq_map[i]; -+ if (entry->slot == slot && entry->pin == pin) { -+ irq = entry->irq; -+ break; -+ } -+ } ++static struct flash_platform_data zcn_1523h_flash_data = { ++#ifdef CONFIG_MTD_PARTITIONS ++ .parts = zcn_1523h_partitions, ++ .nr_parts = ARRAY_SIZE(zcn_1523h_partitions), ++#endif ++}; + -+ if (irq < 0) { -+ printk(KERN_ALERT "PCI: no irq found for pin%u@%s\n", -+ pin, pci_name((struct pci_dev *)dev)); -+ } else { -+ printk(KERN_INFO "PCI: mapping irq %d to pin%u@%s\n", -+ irq, pin, pci_name((struct pci_dev *)dev)); ++static struct gpio_keys_button zcn_1523h_gpio_keys[] __initdata = { ++ { ++ .desc = "reset", ++ .type = EV_KEY, ++ .code = KEY_RESTART, ++ .debounce_interval = ZCN_1523H_KEYS_DEBOUNCE_INTERVAL, ++ .gpio = ZCN_1523H_GPIO_BTN_RESET, ++ .active_low = 1, + } -+ -+ return irq; -+} -+ -+static struct pci_ops ar71xx_pci_ops = { -+ .read = ar71xx_pci_read_config, -+ .write = ar71xx_pci_write_config, +}; + -+static struct resource ar71xx_pci_io_resource = { -+ .name = "PCI IO space", -+ .start = 0, -+ .end = 0, -+ .flags = IORESOURCE_IO, ++static struct gpio_led zcn_1523h_leds_gpio[] __initdata = { ++ { ++ .name = "zcn-1523h:amber:init", ++ .gpio = ZCN_1523H_GPIO_LED_INIT, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:green:lan1", ++ .gpio = ZCN_1523H_GPIO_LED_LAN1, ++ .active_low = 1, ++ } +}; + -+static struct resource ar71xx_pci_mem_resource = { -+ .name = "PCI memory space", -+ .start = AR71XX_PCI_MEM_BASE, -+ .end = AR71XX_PCI_MEM_BASE + AR71XX_PCI_MEM_SIZE - 1, -+ .flags = IORESOURCE_MEM ++static struct gpio_led zcn_1523h_2_leds_gpio[] __initdata = { ++ { ++ .name = "zcn-1523h:red:weak", ++ .gpio = ZCN_1523H_2_GPIO_LED_WEAK, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:amber:medium", ++ .gpio = ZCN_1523H_2_GPIO_LED_MEDIUM, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:green:strong", ++ .gpio = ZCN_1523H_2_GPIO_LED_STRONG, ++ .active_low = 1, ++ } +}; + -+static struct pci_controller ar71xx_pci_controller = { -+ .pci_ops = &ar71xx_pci_ops, -+ .mem_resource = &ar71xx_pci_mem_resource, -+ .io_resource = &ar71xx_pci_io_resource, ++static struct gpio_led zcn_1523h_5_leds_gpio[] __initdata = { ++ { ++ .name = "zcn-1523h:red:weak", ++ .gpio = ZCN_1523H_5_GPIO_LED_WEAK, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:amber:medium", ++ .gpio = ZCN_1523H_5_GPIO_LED_MEDIUM, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:green:strong", ++ .gpio = ZCN_1523H_5_GPIO_LED_STRONG, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:green:lan2", ++ .gpio = ZCN_1523H_5_GPIO_LED_LAN2, ++ .active_low = 1, ++ }, { ++ .name = "zcn-1523h:amber:unknown", ++ .gpio = ZCN_1523H_5_GPIO_LED_UNKNOWN, ++ } +}; + -+static void ar71xx_pci_irq_handler(unsigned int irq, struct irq_desc *desc) ++static void __init zcn_1523h_generic_setup(void) +{ -+ void __iomem *base = ar71xx_reset_base; -+ u32 pending; -+ -+ pending = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_STATUS) & -+ __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ u8 *mac = (u8 *) KSEG1ADDR(0x1f7e0004); ++ u8 *ee = (u8 *) KSEG1ADDR(0x1fff1000); + -+ if (pending & PCI_INT_DEV0) -+ generic_handle_irq(AR71XX_PCI_IRQ_DEV0); ++ ar71xx_gpio_function_disable(AR724X_GPIO_FUNC_ETH_SWITCH_LED0_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED1_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED2_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED3_EN | ++ AR724X_GPIO_FUNC_ETH_SWITCH_LED4_EN); + -+ else if (pending & PCI_INT_DEV1) -+ generic_handle_irq(AR71XX_PCI_IRQ_DEV1); ++ ar71xx_add_device_m25p80(&zcn_1523h_flash_data); + -+ else if (pending & PCI_INT_DEV2) -+ generic_handle_irq(AR71XX_PCI_IRQ_DEV2); ++ ar71xx_add_device_leds_gpio(0, ARRAY_SIZE(zcn_1523h_leds_gpio), ++ zcn_1523h_leds_gpio); + -+ else if (pending & PCI_INT_CORE) -+ generic_handle_irq(AR71XX_PCI_IRQ_CORE); ++ ar71xx_register_gpio_keys_polled(-1, ZCN_1523H_KEYS_POLL_INTERVAL, ++ ARRAY_SIZE(zcn_1523h_gpio_keys), ++ zcn_1523h_gpio_keys); + -+ else -+ spurious_interrupt(); -+} ++ ap91_pci_init(ee, mac); + -+static void ar71xx_pci_irq_unmask(struct irq_data *d) -+{ -+ void __iomem *base = ar71xx_reset_base; -+ u32 t; ++ ar71xx_init_mac(ar71xx_eth0_data.mac_addr, mac, 0); ++ ar71xx_init_mac(ar71xx_eth1_data.mac_addr, mac, 1); + -+ d->irq -= AR71XX_PCI_IRQ_BASE; ++ /* LAN1 port */ ++ ar71xx_eth0_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth0_data.speed = SPEED_100; ++ ar71xx_eth0_data.duplex = DUPLEX_FULL; + -+ t = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); -+ __raw_writel(t | (1 << d->irq), base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ /* LAN2 port */ ++ ar71xx_eth1_data.phy_if_mode = PHY_INTERFACE_MODE_RMII; ++ ar71xx_eth1_data.speed = SPEED_1000; ++ ar71xx_eth1_data.duplex = DUPLEX_FULL; + -+ /* flush write */ -+ (void) __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ ar71xx_add_device_mdio(0x0); ++ ar71xx_add_device_eth(0); +} + -+static void ar71xx_pci_irq_mask(struct irq_data *d) ++static void __init zcn_1523h_2_setup(void) +{ -+ void __iomem *base = ar71xx_reset_base; -+ u32 t; ++ zcn_1523h_generic_setup(); ++ ap91_pci_setup_wmac_gpio(BIT(9), 0); + -+ d->irq -= AR71XX_PCI_IRQ_BASE; -+ -+ t = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); -+ __raw_writel(t & ~(1 << d->irq), base + AR71XX_RESET_REG_PCI_INT_ENABLE); -+ -+ /* flush write */ -+ (void) __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ ar71xx_add_device_leds_gpio(1, ARRAY_SIZE(zcn_1523h_2_leds_gpio), ++ zcn_1523h_2_leds_gpio); +} + -+static struct irq_chip ar71xx_pci_irq_chip = { -+ .name = "AR71XX PCI ", -+ .irq_mask = ar71xx_pci_irq_mask, -+ .irq_unmask = ar71xx_pci_irq_unmask, -+ .irq_mask_ack = ar71xx_pci_irq_mask, -+}; ++MIPS_MACHINE(AR71XX_MACH_ZCN_1523H_2, "ZCN-1523H-2", "Zcomax ZCN-1523H-2", ++ zcn_1523h_2_setup); + -+static void __init ar71xx_pci_irq_init(void) ++static void __init zcn_1523h_5_setup(void) +{ -+ void __iomem *base = ar71xx_reset_base; -+ int i; -+ -+ __raw_writel(0, base + AR71XX_RESET_REG_PCI_INT_ENABLE); -+ __raw_writel(0, base + AR71XX_RESET_REG_PCI_INT_STATUS); -+ -+ for (i = AR71XX_PCI_IRQ_BASE; -+ i < AR71XX_PCI_IRQ_BASE + AR71XX_PCI_IRQ_COUNT; i++) { -+ irq_set_chip_and_handler(i, &ar71xx_pci_irq_chip, -+ handle_level_irq); -+ } ++ zcn_1523h_generic_setup(); ++ ap91_pci_setup_wmac_gpio(BIT(8), 0); + -+ irq_set_chained_handler(AR71XX_CPU_IRQ_IP2, ar71xx_pci_irq_handler); ++ ar71xx_add_device_leds_gpio(1, ARRAY_SIZE(zcn_1523h_5_leds_gpio), ++ zcn_1523h_5_leds_gpio); ++ ar71xx_add_device_eth(1); +} + -+int __init ar71xx_pcibios_init(void) -+{ -+ void __iomem *ddr_base = ar71xx_ddr_base; -+ -+ ar71xx_device_stop(RESET_MODULE_PCI_BUS | RESET_MODULE_PCI_CORE); -+ ar71xx_pci_delay(); ++MIPS_MACHINE(AR71XX_MACH_ZCN_1523H_5, "ZCN-1523H-5", "Zcomax ZCN-1523H-5", ++ zcn_1523h_5_setup); +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/Makefile linux-2.6.39/arch/mips/ar71xx/Makefile +--- linux-2.6.39.orig/arch/mips/ar71xx/Makefile 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/Makefile 2011-08-24 02:41:55.677990354 +0200 +@@ -0,0 +1,67 @@ ++# ++# Makefile for the Atheros AR71xx SoC specific parts of the kernel ++# ++# Copyright (C) 2008-2009 Gabor Juhos ++# Copyright (C) 2008 Imre Kaloz ++# ++# This program is free software; you can redistribute it and/or modify it ++# under the terms of the GNU General Public License version 2 as published ++# by the Free Software Foundation. + -+ ar71xx_device_start(RESET_MODULE_PCI_BUS | RESET_MODULE_PCI_CORE); -+ ar71xx_pci_delay(); ++obj-y := prom.o irq.o setup.o devices.o gpio.o ar71xx.o + -+ ar71xx_pcicfg_base = ioremap_nocache(AR71XX_PCI_CFG_BASE, -+ AR71XX_PCI_CFG_SIZE); -+ if (ar71xx_pcicfg_base == NULL) -+ return -ENOMEM; ++obj-$(CONFIG_EARLY_PRINTK) += early_printk.o ++obj-$(CONFIG_PCI) += pci.o + -+ __raw_writel(PCI_WIN0_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN0); -+ __raw_writel(PCI_WIN1_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN1); -+ __raw_writel(PCI_WIN2_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN2); -+ __raw_writel(PCI_WIN3_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN3); -+ __raw_writel(PCI_WIN4_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN4); -+ __raw_writel(PCI_WIN5_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN5); -+ __raw_writel(PCI_WIN6_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN6); -+ __raw_writel(PCI_WIN7_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN7); -+ -+ ar71xx_pci_delay(); -+ -+ /* clear bus errors */ -+ (void)ar71xx_pci_be_handler(1); ++obj-$(CONFIG_AR71XX_DEV_AP91_PCI) += dev-ap91-pci.o ++obj-$(CONFIG_AR71XX_DEV_AP94_PCI) += dev-ap94-pci.o ++obj-$(CONFIG_AR71XX_DEV_AR9XXX_WMAC) += dev-ar9xxx-wmac.o ++obj-$(CONFIG_AR71XX_DEV_DB120_PCI) += dev-db120-pci.o ++obj-$(CONFIG_AR71XX_DEV_DSA) += dev-dsa.o ++obj-$(CONFIG_AR71XX_DEV_GPIO_BUTTONS) += dev-gpio-buttons.o ++obj-$(CONFIG_AR71XX_DEV_LEDS_GPIO) += dev-leds-gpio.o ++obj-$(CONFIG_AR71XX_DEV_M25P80) += dev-m25p80.o ++obj-$(CONFIG_AR71XX_DEV_PB42_PCI) += dev-pb42-pci.o ++obj-$(CONFIG_AR71XX_DEV_PB9X_PCI) += dev-pb9x-pci.o ++obj-$(CONFIG_AR71XX_DEV_USB) += dev-usb.o + -+ ar71xx_pci_fixup_enable = 1; -+ ar71xx_pci_irq_init(); -+ register_pci_controller(&ar71xx_pci_controller); ++obj-$(CONFIG_AR71XX_NVRAM) += nvram.o ++obj-$(CONFIG_AR71XX_PCI_ATH9K_FIXUP) += pci-ath9k-fixup.o + -+ return 0; -+} -diff -Nur linux-2.6.39.orig/arch/mips/pci/pci-ar724x.c linux-2.6.39/arch/mips/pci/pci-ar724x.c ---- linux-2.6.39.orig/arch/mips/pci/pci-ar724x.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/arch/mips/pci/pci-ar724x.c 2011-06-01 14:02:22.000000000 +0200 -@@ -0,0 +1,394 @@ ++obj-$(CONFIG_AR71XX_MACH_AP121) += mach-ap121.o ++obj-$(CONFIG_AR71XX_MACH_AP81) += mach-ap81.o ++obj-$(CONFIG_AR71XX_MACH_AP83) += mach-ap83.o ++obj-$(CONFIG_AR71XX_MACH_AP96) += mach-ap96.o ++obj-$(CONFIG_AR71XX_MACH_AW_NR580) += mach-aw-nr580.o ++obj-$(CONFIG_AR71XX_MACH_DB120) += mach-db120.o ++obj-$(CONFIG_AR71XX_MACH_DIR_600_A1) += mach-dir-600-a1.o ++obj-$(CONFIG_AR71XX_MACH_DIR_615_C1) += mach-dir-615-c1.o ++obj-$(CONFIG_AR71XX_MACH_DIR_825_B1) += mach-dir-825-b1.o ++obj-$(CONFIG_AR71XX_MACH_EAP7660D) += mach-eap7660d.o ++obj-$(CONFIG_AR71XX_MACH_JA76PF) += mach-ja76pf.o ++obj-$(CONFIG_AR71XX_MACH_JWAP003) += mach-jwap003.o ++obj-$(CONFIG_AR71XX_MACH_MZK_W04NU) += mach-mzk-w04nu.o ++obj-$(CONFIG_AR71XX_MACH_MZK_W300NH) += mach-mzk-w300nh.o ++obj-$(CONFIG_AR71XX_MACH_NBG460N) += mach-nbg460n.o ++obj-$(CONFIG_AR71XX_MACH_PB42) += mach-pb42.o ++obj-$(CONFIG_AR71XX_MACH_PB44) += mach-pb44.o ++obj-$(CONFIG_AR71XX_MACH_PB92) += mach-pb92.o ++obj-$(CONFIG_AR71XX_MACH_RB4XX) += mach-rb4xx.o ++obj-$(CONFIG_AR71XX_MACH_RB750) += mach-rb750.o ++obj-$(CONFIG_AR71XX_MACH_TEW_632BRP) += mach-tew-632brp.o ++obj-$(CONFIG_AR71XX_MACH_TL_MR3X20) += mach-tl-mr3x20.o ++obj-$(CONFIG_AR71XX_MACH_TL_WA901ND) += mach-tl-wa901nd.o ++obj-$(CONFIG_AR71XX_MACH_TL_WA901ND_V2) += mach-tl-wa901nd-v2.o ++obj-$(CONFIG_AR71XX_MACH_TL_WR741ND) += mach-tl-wr741nd.o ++obj-$(CONFIG_AR71XX_MACH_TL_WR841N_V1) += mach-tl-wr841n.o ++obj-$(CONFIG_AR71XX_MACH_TL_WR941ND) += mach-tl-wr941nd.o ++obj-$(CONFIG_AR71XX_MACH_TL_WR1043ND) += mach-tl-wr1043nd.o ++obj-$(CONFIG_AR71XX_MACH_UBNT) += mach-ubnt.o ++obj-$(CONFIG_AR71XX_MACH_WNDR3700) += mach-wndr3700.o ++obj-$(CONFIG_AR71XX_MACH_WNR2000) += mach-wnr2000.o ++obj-$(CONFIG_AR71XX_MACH_WP543) += mach-wp543.o ++obj-$(CONFIG_AR71XX_MACH_WRT160NL) += mach-wrt160nl.o ++obj-$(CONFIG_AR71XX_MACH_WRT400N) += mach-wrt400n.o ++obj-$(CONFIG_AR71XX_MACH_WZR_HP_G300NH) += mach-wzr-hp-g300nh.o ++obj-$(CONFIG_AR71XX_MACH_WZR_HP_AG300H) += mach-wzr-hp-ag300h.o ++obj-$(CONFIG_AR71XX_MACH_ZCN_1523H) += mach-zcn-1523h.o +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/nvram.c linux-2.6.39/arch/mips/ar71xx/nvram.c +--- linux-2.6.39.orig/arch/mips/ar71xx/nvram.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/nvram.c 2011-08-24 02:41:55.677990354 +0200 +@@ -0,0 +1,75 @@ +/* -+ * Atheros AR724x PCI host controller driver -+ * -+ * Copyright (C) 2009-2010 Gabor Juhos ++ * Atheros AR71xx minimal nvram support + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include ++#include ++#include ++#include ++#include ++#include + -+#undef DEBUG -+#ifdef DEBUG -+#define DBG(fmt, args...) printk(KERN_INFO fmt, ## args) -+#else -+#define DBG(fmt, args...) -+#endif ++#include "nvram.h" + -+static void __iomem *ar724x_pci_localcfg_base; -+static void __iomem *ar724x_pci_devcfg_base; -+static void __iomem *ar724x_pci_ctrl_base; -+static int ar724x_pci_fixup_enable; ++char *nvram_find_var(const char *name, const char *buf, unsigned buf_len) ++{ ++ unsigned len = strlen(name); ++ char *cur, *last; + -+static DEFINE_SPINLOCK(ar724x_pci_lock); ++ if (buf_len == 0 || len == 0) ++ return NULL; + -+static void ar724x_pci_read(void __iomem *base, int where, int size, u32 *value) -+{ -+ unsigned long flags; -+ u32 data; ++ if (buf_len < len) ++ return NULL; + -+ spin_lock_irqsave(&ar724x_pci_lock, flags); -+ data = __raw_readl(base + (where & ~3)); ++ if (len == 1) ++ return memchr(buf, (int) *name, buf_len); + -+ switch (size) { -+ case 1: -+ if (where & 1) -+ data >>= 8; -+ if (where & 2) -+ data >>= 16; -+ data &= 0xFF; -+ break; -+ case 2: -+ if (where & 2) -+ data >>= 16; -+ data &= 0xFFFF; -+ break; -+ } ++ last = (char *) buf + buf_len - len; ++ for (cur = (char *) buf; cur <= last; cur++) ++ if (cur[0] == name[0] && memcmp(cur, name, len) == 0) ++ return cur + len; + -+ *value = data; -+ spin_unlock_irqrestore(&ar724x_pci_lock, flags); ++ return NULL; +} + -+static void ar724x_pci_write(void __iomem *base, int where, int size, u32 value) ++int nvram_parse_mac_addr(const char *nvram, unsigned nvram_len, ++ const char *name, char *mac) +{ -+ unsigned long flags; -+ u32 data; -+ int s; ++ char *buf; ++ char *mac_str; ++ int ret; ++ int t; + -+ spin_lock_irqsave(&ar724x_pci_lock, flags); -+ data = __raw_readl(base + (where & ~3)); ++ buf = vmalloc(nvram_len); ++ if (!buf) ++ return -ENOMEM; + -+ switch (size) { -+ case 1: -+ s = ((where & 3) << 3); -+ data &= ~(0xFF << s); -+ data |= ((value & 0xFF) << s); -+ break; -+ case 2: -+ s = ((where & 2) << 3); -+ data &= ~(0xFFFF << s); -+ data |= ((value & 0xFFFF) << s); -+ break; -+ case 4: -+ data = value; -+ break; ++ memcpy(buf, nvram, nvram_len); ++ buf[nvram_len - 1] = '\0'; ++ ++ mac_str = nvram_find_var(name, buf, nvram_len); ++ if (!mac_str) { ++ ret = -EINVAL; ++ goto free; + } + -+ __raw_writel(data, base + (where & ~3)); -+ /* flush write */ -+ (void)__raw_readl(base + (where & ~3)); -+ spin_unlock_irqrestore(&ar724x_pci_lock, flags); -+} ++ t = sscanf(mac_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx", ++ &mac[0], &mac[1], &mac[2], &mac[3], &mac[4], &mac[5]); + -+static int ar724x_pci_read_config(struct pci_bus *bus, unsigned int devfn, -+ int where, int size, u32 *value) -+{ ++ if (t != 6) { ++ ret = -EINVAL; ++ goto free; ++ } + -+ if (bus->number != 0 || devfn != 0) -+ return PCIBIOS_DEVICE_NOT_FOUND; ++ ret = 0; + -+ ar724x_pci_read(ar724x_pci_devcfg_base, where, size, value); ++free: ++ vfree(buf); ++ return ret; ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/nvram.h linux-2.6.39/arch/mips/ar71xx/nvram.h +--- linux-2.6.39.orig/arch/mips/ar71xx/nvram.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/nvram.h 2011-08-24 02:41:55.687991145 +0200 +@@ -0,0 +1,19 @@ ++/* ++ * Atheros AR71xx minimal nvram support ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ DBG("PCI: read config: %02x:%02x.%01x/%02x:%01d, value=%08x\n", -+ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), -+ where, size, *value); ++#ifndef _AR71XX_NVRAM_H ++#define _AR71XX_NVRAM_H + -+ /* -+ * WAR for BAR issue - We are unable to access the PCI device space -+ * if we set the BAR with proper base address -+ */ -+ if ((where == 0x10) && (size == 4)) { -+ if (ar71xx_soc == AR71XX_SOC_AR7240) -+ ar724x_pci_write(ar724x_pci_devcfg_base, where, size, 0xffff); -+ else -+ ar724x_pci_write(ar724x_pci_devcfg_base, where, size, 0x1000ffff); -+ } ++char *nvram_find_var(const char *name, const char *buf, ++ unsigned buf_len) __init; ++int nvram_parse_mac_addr(const char *nvram, unsigned nvram_len, ++ const char *name, char *mac) __init; + -+ return PCIBIOS_SUCCESSFUL; -+} ++#endif /* _AR71XX_NVRAM_H */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/pci-ath9k-fixup.c linux-2.6.39/arch/mips/ar71xx/pci-ath9k-fixup.c +--- linux-2.6.39.orig/arch/mips/ar71xx/pci-ath9k-fixup.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/pci-ath9k-fixup.c 2011-08-24 02:41:55.697990606 +0200 +@@ -0,0 +1,123 @@ ++/* ++ * Atheros AP94 reference board PCI initialization ++ * ++ * Copyright (C) 2009-2010 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+static int ar724x_pci_write_config(struct pci_bus *bus, unsigned int devfn, -+ int where, int size, u32 value) -+{ -+ if (bus->number != 0 || devfn != 0) -+ return PCIBIOS_DEVICE_NOT_FOUND; ++#include ++#include + -+ DBG("PCI: write config: %02x:%02x.%01x/%02x:%01d, value=%08x\n", -+ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), -+ where, size, value); ++#include ++#include + -+ ar724x_pci_write(ar724x_pci_devcfg_base, where, size, value); ++struct ath9k_fixup { ++ u16 *cal_data; ++ unsigned slot; ++}; + -+ return PCIBIOS_SUCCESSFUL; -+} ++static int ath9k_num_fixups; ++static struct ath9k_fixup ath9k_fixups[2]; + -+static void ar724x_pci_fixup(struct pci_dev *dev) ++static void ath9k_pci_fixup(struct pci_dev *dev) +{ ++ void __iomem *mem; ++ u16 *cal_data = NULL; + u16 cmd; ++ u32 bar0; ++ u32 val; ++ unsigned i; + -+ if (!ar724x_pci_fixup_enable) ++ for (i = 0; i < ath9k_num_fixups; i++) { ++ if (ath9k_fixups[i].cal_data == NULL) ++ continue; ++ ++ if (ath9k_fixups[i].slot != PCI_SLOT(dev->devfn)) ++ continue; ++ ++ cal_data = ath9k_fixups[i].cal_data; ++ break; ++ } ++ ++ if (cal_data == NULL) + return; + -+ if (dev->bus->number != 0 || dev->devfn != 0) ++ if (*cal_data != 0xa55a) { ++ pr_err("pci %s: invalid calibration data\n", pci_name(dev)); + return; ++ } + -+ /* setup COMMAND register */ -+ pci_read_config_word(dev, PCI_COMMAND, &cmd); -+ cmd |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | -+ PCI_COMMAND_INVALIDATE | PCI_COMMAND_PARITY | PCI_COMMAND_SERR | -+ PCI_COMMAND_FAST_BACK; ++ pr_info("pci %s: fixup device configuration\n", pci_name(dev)); + -+ pci_write_config_word(dev, PCI_COMMAND, cmd); -+} -+DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, ar724x_pci_fixup); ++ mem = ioremap(AR71XX_PCI_MEM_BASE, 0x10000); ++ if (!mem) { ++ pr_err("pci %s: ioremap error\n", pci_name(dev)); ++ return; ++ } + -+int __init ar724x_pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, -+ uint8_t pin) -+{ -+ int irq = -1; -+ int i; ++ pci_read_config_dword(dev, PCI_BASE_ADDRESS_0, &bar0); + -+ for (i = 0; i < ar71xx_pci_nr_irqs; i++) { -+ struct ar71xx_pci_irq *entry; -+ entry = &ar71xx_pci_irq_map[i]; ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7161: ++ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, ++ AR71XX_PCI_MEM_BASE); ++ break; ++ case AR71XX_SOC_AR7240: ++ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, 0xffff); ++ break; + -+ if (entry->slot == slot && entry->pin == pin) { -+ irq = entry->irq; -+ break; -+ } ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, 0x1000ffff); ++ break; ++ ++ default: ++ BUG(); + } + -+ if (irq < 0) -+ printk(KERN_ALERT "PCI: no irq found for pin%u@%s\n", -+ pin, pci_name((struct pci_dev *)dev)); -+ else -+ printk(KERN_INFO "PCI: mapping irq %d to pin%u@%s\n", -+ irq, pin, pci_name((struct pci_dev *)dev)); ++ pci_read_config_word(dev, PCI_COMMAND, &cmd); ++ cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY; ++ pci_write_config_word(dev, PCI_COMMAND, cmd); + -+ return irq; -+} ++ /* set pointer to first reg address */ ++ cal_data += 3; ++ while (*cal_data != 0xffff) { ++ u32 reg; ++ reg = *cal_data++; ++ val = *cal_data++; ++ val |= (*cal_data++) << 16; + -+static struct pci_ops ar724x_pci_ops = { -+ .read = ar724x_pci_read_config, -+ .write = ar724x_pci_write_config, -+}; ++ __raw_writel(val, mem + reg); ++ udelay(100); ++ } + -+static struct resource ar724x_pci_io_resource = { -+ .name = "PCI IO space", -+ .start = 0, -+ .end = 0, -+ .flags = IORESOURCE_IO, -+}; ++ pci_read_config_dword(dev, PCI_VENDOR_ID, &val); ++ dev->vendor = val & 0xffff; ++ dev->device = (val >> 16) & 0xffff; + -+static struct resource ar724x_pci_mem_resource = { -+ .name = "PCI memory space", -+ .start = AR71XX_PCI_MEM_BASE, -+ .end = AR71XX_PCI_MEM_BASE + AR71XX_PCI_MEM_SIZE - 1, -+ .flags = IORESOURCE_MEM -+}; ++ pci_read_config_dword(dev, PCI_CLASS_REVISION, &val); ++ dev->revision = val & 0xff; ++ dev->class = val >> 8; /* upper 3 bytes */ + -+static struct pci_controller ar724x_pci_controller = { -+ .pci_ops = &ar724x_pci_ops, -+ .mem_resource = &ar724x_pci_mem_resource, -+ .io_resource = &ar724x_pci_io_resource, -+}; ++ pci_read_config_word(dev, PCI_COMMAND, &cmd); ++ cmd &= ~(PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY); ++ pci_write_config_word(dev, PCI_COMMAND, cmd); + -+static void __init ar724x_pci_reset(void) -+{ -+ ar71xx_device_stop(AR724X_RESET_PCIE); -+ ar71xx_device_stop(AR724X_RESET_PCIE_PHY); -+ ar71xx_device_stop(AR724X_RESET_PCIE_PHY_SERIAL); -+ udelay(100); ++ pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, bar0); + -+ ar71xx_device_start(AR724X_RESET_PCIE_PHY_SERIAL); -+ udelay(100); -+ ar71xx_device_start(AR724X_RESET_PCIE_PHY); -+ ar71xx_device_start(AR724X_RESET_PCIE); ++ iounmap(mem); +} ++DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_ATHEROS, PCI_ANY_ID, ath9k_pci_fixup); + -+static int __init ar724x_pci_setup(void) ++void __init pci_enable_ath9k_fixup(unsigned slot, u16 *cal_data) +{ -+ void __iomem *base = ar724x_pci_ctrl_base; -+ u32 t; ++ if (ath9k_num_fixups >= ARRAY_SIZE(ath9k_fixups)) ++ return; + -+ /* setup COMMAND register */ -+ t = PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | PCI_COMMAND_INVALIDATE | -+ PCI_COMMAND_PARITY|PCI_COMMAND_SERR|PCI_COMMAND_FAST_BACK; ++ ath9k_fixups[ath9k_num_fixups].slot = slot; ++ ath9k_fixups[ath9k_num_fixups].cal_data = cal_data; ++ ath9k_num_fixups++; ++} +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/pci-ath9k-fixup.h linux-2.6.39/arch/mips/ar71xx/pci-ath9k-fixup.h +--- linux-2.6.39.orig/arch/mips/ar71xx/pci-ath9k-fixup.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/pci-ath9k-fixup.h 2011-08-24 02:41:55.697990606 +0200 +@@ -0,0 +1,6 @@ ++#ifndef _PCI_ATH9K_FIXUP ++#define _PCI_ATH9K_FIXUP + -+ ar724x_pci_write(ar724x_pci_localcfg_base, PCI_COMMAND, 4, t); -+ ar724x_pci_write(ar724x_pci_localcfg_base, 0x20, 4, 0x1ff01000); -+ ar724x_pci_write(ar724x_pci_localcfg_base, 0x24, 4, 0x1ff01000); ++void pci_enable_ath9k_fixup(unsigned slot, u16 *cal_data) __init; + -+ t = __raw_readl(base + AR724X_PCI_REG_RESET); -+ if (t != 0x7) { -+ udelay(100000); -+ __raw_writel(0, base + AR724X_PCI_REG_RESET); -+ udelay(100); -+ __raw_writel(4, base + AR724X_PCI_REG_RESET); -+ udelay(100000); -+ } ++#endif /* _PCI_ATH9K_FIXUP */ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/pci.c linux-2.6.39/arch/mips/ar71xx/pci.c +--- linux-2.6.39.orig/arch/mips/ar71xx/pci.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/pci.c 2011-08-24 02:41:55.697990606 +0200 +@@ -0,0 +1,97 @@ ++/* ++ * Atheros AR71xx PCI setup code ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ if (ar71xx_soc == AR71XX_SOC_AR7240) -+ t = AR724X_PCI_APP_LTSSM_ENABLE; -+ else -+ t = 0x1ffc1; -+ __raw_writel(t, base + AR724X_PCI_REG_APP); -+ /* flush write */ -+ (void) __raw_readl(base + AR724X_PCI_REG_APP); -+ udelay(1000); ++#include + -+ t = __raw_readl(base + AR724X_PCI_REG_RESET); -+ if ((t & AR724X_PCI_RESET_LINK_UP) == 0x0) { -+ printk(KERN_WARNING "PCI: no PCIe module found\n"); -+ return -ENODEV; -+ } ++#include + -+ if (ar71xx_soc == AR71XX_SOC_AR7241 || ar71xx_soc == AR71XX_SOC_AR7242) { -+ t = __raw_readl(base + AR724X_PCI_REG_APP); -+ t |= BIT(16); -+ __raw_writel(t, base + AR724X_PCI_REG_APP); -+ } ++#include ++#include + -+ return 0; -+} ++unsigned ar71xx_pci_nr_irqs __initdata; ++struct ar71xx_pci_irq *ar71xx_pci_irq_map __initdata; + -+static void ar724x_pci_irq_handler(unsigned int irq, struct irq_desc *desc) -+{ -+ void __iomem *base = ar724x_pci_ctrl_base; -+ u32 pending; ++int (*ar71xx_pci_plat_dev_init)(struct pci_dev *dev); + -+ pending = __raw_readl(base + AR724X_PCI_REG_INT_STATUS) & -+ __raw_readl(base + AR724X_PCI_REG_INT_MASK); ++static int ar71xx_be_handler(struct pt_regs *regs, int is_fixup) ++{ ++ int err = 0; + -+ if (pending & AR724X_PCI_INT_DEV0) -+ generic_handle_irq(AR71XX_PCI_IRQ_DEV0); ++ err = ar71xx_pci_be_handler(is_fixup); + -+ else -+ spurious_interrupt(); ++ return (is_fixup && !err) ? MIPS_BE_FIXUP : MIPS_BE_FATAL; +} + -+static void ar724x_pci_irq_unmask(struct irq_data *d) ++int pcibios_plat_dev_init(struct pci_dev *dev) +{ -+ void __iomem *base = ar724x_pci_ctrl_base; -+ u32 t; -+ -+ switch (d->irq) { -+ case AR71XX_PCI_IRQ_DEV0: -+ d->irq -= AR71XX_PCI_IRQ_BASE; ++ if (ar71xx_pci_plat_dev_init) ++ return ar71xx_pci_plat_dev_init(dev); + -+ t = __raw_readl(base + AR724X_PCI_REG_INT_MASK); -+ __raw_writel(t | AR724X_PCI_INT_DEV0, -+ base + AR724X_PCI_REG_INT_MASK); -+ /* flush write */ -+ (void) __raw_readl(base + AR724X_PCI_REG_INT_MASK); -+ } ++ return 0; +} + -+static void ar724x_pci_irq_mask(struct irq_data *d) ++int __init pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, uint8_t pin) +{ -+ void __iomem *base = ar724x_pci_ctrl_base; -+ u32 t; -+ -+ switch (d->irq) { -+ case AR71XX_PCI_IRQ_DEV0: -+ d->irq -= AR71XX_PCI_IRQ_BASE; -+ -+ t = __raw_readl(base + AR724X_PCI_REG_INT_MASK); -+ __raw_writel(t & ~AR724X_PCI_INT_DEV0, -+ base + AR724X_PCI_REG_INT_MASK); ++ int ret = 0; + -+ /* flush write */ -+ (void) __raw_readl(base + AR724X_PCI_REG_INT_MASK); ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ ret = ar71xx_pcibios_map_irq(dev, slot, pin); ++ break; + -+ t = __raw_readl(base + AR724X_PCI_REG_INT_STATUS); -+ __raw_writel(t | AR724X_PCI_INT_DEV0, -+ base + AR724X_PCI_REG_INT_STATUS); ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ret = ar724x_pcibios_map_irq(dev, slot, pin); ++ break; + -+ /* flush write */ -+ (void) __raw_readl(base + AR724X_PCI_REG_INT_STATUS); ++ default: ++ break; + } -+} + -+static struct irq_chip ar724x_pci_irq_chip = { -+ .name = "AR724X PCI ", -+ .irq_mask = ar724x_pci_irq_mask, -+ .irq_unmask = ar724x_pci_irq_unmask, -+ .irq_mask_ack = ar724x_pci_irq_mask, -+}; ++ return ret; ++} + -+static void __init ar724x_pci_irq_init(void) ++int __init ar71xx_pci_init(unsigned nr_irqs, struct ar71xx_pci_irq *map) +{ -+ void __iomem *base = ar724x_pci_ctrl_base; -+ u32 t; -+ int i; ++ int ret = 0; + -+ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); -+ if (t & (AR724X_RESET_PCIE | AR724X_RESET_PCIE_PHY | -+ AR724X_RESET_PCIE_PHY_SERIAL)) { -+ return; -+ } ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ board_be_handler = ar71xx_be_handler; ++ ret = ar71xx_pcibios_init(); ++ break; + -+ __raw_writel(0, base + AR724X_PCI_REG_INT_MASK); -+ __raw_writel(0, base + AR724X_PCI_REG_INT_STATUS); ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ret = ar724x_pcibios_init(); ++ break; + -+ for (i = AR71XX_PCI_IRQ_BASE; -+ i < AR71XX_PCI_IRQ_BASE + AR71XX_PCI_IRQ_COUNT; i++) { -+ irq_set_chip_and_handler(i, &ar724x_pci_irq_chip, -+ handle_level_irq); ++ default: ++ return 0; + } + -+ irq_set_chained_handler(AR71XX_CPU_IRQ_IP2, ar724x_pci_irq_handler); -+} -+ -+int __init ar724x_pcibios_init(void) -+{ -+ int ret = -ENOMEM; -+ -+ ar724x_pci_localcfg_base = ioremap_nocache(AR724X_PCI_CRP_BASE, -+ AR724X_PCI_CRP_SIZE); -+ if (ar724x_pci_localcfg_base == NULL) -+ goto err; -+ -+ ar724x_pci_devcfg_base = ioremap_nocache(AR724X_PCI_CFG_BASE, -+ AR724X_PCI_CFG_SIZE); -+ if (ar724x_pci_devcfg_base == NULL) -+ goto err_unmap_localcfg; -+ -+ ar724x_pci_ctrl_base = ioremap_nocache(AR724X_PCI_CTRL_BASE, -+ AR724X_PCI_CTRL_SIZE); -+ if (ar724x_pci_ctrl_base == NULL) -+ goto err_unmap_devcfg; -+ -+ ar724x_pci_reset(); -+ ret = ar724x_pci_setup(); -+ if (ret) -+ goto err_unmap_ctrl; -+ -+ ar724x_pci_fixup_enable = 1; -+ ar724x_pci_irq_init(); -+ register_pci_controller(&ar724x_pci_controller); -+ -+ return 0; ++ ar71xx_pci_nr_irqs = nr_irqs; ++ ar71xx_pci_irq_map = map; + -+ err_unmap_ctrl: -+ iounmap(ar724x_pci_ctrl_base); -+ err_unmap_devcfg: -+ iounmap(ar724x_pci_devcfg_base); -+ err_unmap_localcfg: -+ iounmap(ar724x_pci_localcfg_base); -+ err: + return ret; +} -diff -Nur linux-2.6.39.orig/drivers/char/Kconfig linux-2.6.39/drivers/char/Kconfig ---- linux-2.6.39.orig/drivers/char/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/char/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -511,6 +511,14 @@ - pc8736x_gpio drivers. If those drivers are built as - modules, this one will be too, named nsc_gpio - -+config GPIO_DEVICE -+ tristate "GPIO device support" -+ depends on GENERIC_GPIO -+ help -+ Say Y to enable Linux GPIO device support. This allows control of -+ GPIO pins using a character device -+ -+ - config RAW_DRIVER - tristate "RAW driver (/dev/raw/rawN)" - depends on BLOCK -diff -Nur linux-2.6.39.orig/drivers/char/Makefile linux-2.6.39/drivers/char/Makefile ---- linux-2.6.39.orig/drivers/char/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/char/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -47,6 +47,7 @@ - obj-$(CONFIG_SCx200_GPIO) += scx200_gpio.o - obj-$(CONFIG_PC8736x_GPIO) += pc8736x_gpio.o - obj-$(CONFIG_NSC_GPIO) += nsc_gpio.o -+obj-$(CONFIG_GPIO_DEVICE) += gpio_dev.o - obj-$(CONFIG_GPIO_TB0219) += tb0219.o - obj-$(CONFIG_TELCLOCK) += tlclk.o - -diff -Nur linux-2.6.39.orig/drivers/gpio/nxp_74hc153.c linux-2.6.39/drivers/gpio/nxp_74hc153.c ---- linux-2.6.39.orig/drivers/gpio/nxp_74hc153.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/gpio/nxp_74hc153.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,246 @@ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/prom.c linux-2.6.39/arch/mips/ar71xx/prom.c +--- linux-2.6.39.orig/arch/mips/ar71xx/prom.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/prom.c 2011-08-24 02:41:55.737990425 +0200 +@@ -0,0 +1,189 @@ +/* -+ * NXP 74HC153 - Dual 4-input multiplexer GPIO driver ++ * Atheros AR71xx SoC specific prom routines + * -+ * Copyright (C) 2010 Gabor Juhos ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * -+ * This program is free software; you can redistribute 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 free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + -+#include ++#include +#include -+#include -+#include -+#include ++#include ++#include + -+#define NXP_74HC153_NUM_GPIOS 8 -+#define NXP_74HC153_S0_MASK 0x1 -+#define NXP_74HC153_S1_MASK 0x2 -+#define NXP_74HC153_BANK_MASK 0x4 ++#include ++#include ++#include + -+struct nxp_74hc153_chip { -+ struct device *parent; -+ struct gpio_chip gpio_chip; -+ struct mutex lock; -+}; ++#include + -+static struct nxp_74hc153_chip *gpio_to_nxp(struct gpio_chip *gc) ++static inline int is_valid_ram_addr(void *addr) +{ -+ return container_of(gc, struct nxp_74hc153_chip, gpio_chip); -+} ++ if (((u32) addr > KSEG0) && ++ ((u32) addr < (KSEG0 + AR71XX_MEM_SIZE_MAX))) ++ return 1; ++ ++ if (((u32) addr > KSEG1) && ++ ((u32) addr < (KSEG1 + AR71XX_MEM_SIZE_MAX))) ++ return 1; + -+static int nxp_74hc153_direction_input(struct gpio_chip *gc, unsigned offset) -+{ + return 0; +} + -+static int nxp_74hc153_direction_output(struct gpio_chip *gc, -+ unsigned offset, int val) ++static void __init ar71xx_prom_append_cmdline(const char *name, ++ const char *value) +{ -+ return -EINVAL; ++ char buf[COMMAND_LINE_SIZE]; ++ ++ snprintf(buf, sizeof(buf), " %s=%s", name, value); ++ strlcat(arcs_cmdline, buf, sizeof(arcs_cmdline)); +} + -+static int nxp_74hc153_get_value(struct gpio_chip *gc, unsigned offset) ++static const char * __init ar71xx_prom_find_env(char **envp, const char *name) +{ -+ struct nxp_74hc153_chip *nxp; -+ struct nxp_74hc153_platform_data *pdata; -+ unsigned s0; -+ unsigned s1; -+ unsigned pin; -+ int ret; ++ const char *ret = NULL; ++ int len; ++ char **p; + -+ nxp = gpio_to_nxp(gc); -+ pdata = nxp->parent->platform_data; ++ if (!is_valid_ram_addr(envp)) ++ return NULL; + -+ s0 = !!(offset & NXP_74HC153_S0_MASK); -+ s1 = !!(offset & NXP_74HC153_S1_MASK); -+ pin = (offset & NXP_74HC153_BANK_MASK) ? pdata->gpio_pin_2y -+ : pdata->gpio_pin_1y; ++ len = strlen(name); ++ for (p = envp; is_valid_ram_addr(*p); p++) { ++ if (strncmp(name, *p, len) == 0 && (*p)[len] == '=') { ++ ret = *p + len + 1; ++ break; ++ } + -+ mutex_lock(&nxp->lock); -+ gpio_set_value(pdata->gpio_pin_s0, s0); -+ gpio_set_value(pdata->gpio_pin_s1, s1); -+ ret = gpio_get_value(pin); -+ mutex_unlock(&nxp->lock); ++ /* RedBoot env comes in pointer pairs - key, value */ ++ if (strncmp(name, *p, len) == 0 && (*p)[len] == 0) ++ if (is_valid_ram_addr(*(++p))) { ++ ret = *p; ++ break; ++ } ++ } + + return ret; +} + -+static void nxp_74hc153_set_value(struct gpio_chip *gc, -+ unsigned offset, int val) -+{ -+ /* not supported */ -+} -+ -+static int __devinit nxp_74hc153_probe(struct platform_device *pdev) ++static int __init ar71xx_prom_init_myloader(void) +{ -+ struct nxp_74hc153_platform_data *pdata; -+ struct nxp_74hc153_chip *nxp; -+ struct gpio_chip *gc; -+ int err; ++ struct myloader_info *mylo; ++ char mac_buf[32]; ++ char *mac; + -+ pdata = pdev->dev.platform_data; -+ if (pdata == NULL) { -+ dev_dbg(&pdev->dev, "no platform data specified\n"); -+ return -EINVAL; -+ } ++ mylo = myloader_get_info(); ++ if (!mylo) ++ return 0; + -+ nxp = kzalloc(sizeof(struct nxp_74hc153_chip), GFP_KERNEL); -+ if (nxp == NULL) { -+ dev_err(&pdev->dev, "no memory for private data\n"); -+ return -ENOMEM; ++ switch (mylo->did) { ++ case DEVID_COMPEX_WP543: ++ ar71xx_prom_append_cmdline("board", "WP543"); ++ break; ++ default: ++ printk(KERN_WARNING "prom: unknown device id: %x\n", ++ mylo->did); ++ return 0; + } + -+ err = gpio_request(pdata->gpio_pin_s0, dev_name(&pdev->dev)); -+ if (err) { -+ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", -+ pdata->gpio_pin_s0, err); -+ goto err_free_nxp; -+ } ++ mac = mylo->macs[0]; ++ snprintf(mac_buf, sizeof(mac_buf), "%02x:%02x:%02x:%02x:%02x:%02x", ++ mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]); + -+ err = gpio_request(pdata->gpio_pin_s1, dev_name(&pdev->dev)); -+ if (err) { -+ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", -+ pdata->gpio_pin_s1, err); -+ goto err_free_s0; -+ } ++ ar71xx_prom_append_cmdline("ethaddr", mac_buf); + -+ err = gpio_request(pdata->gpio_pin_1y, dev_name(&pdev->dev)); -+ if (err) { -+ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", -+ pdata->gpio_pin_1y, err); -+ goto err_free_s1; -+ } ++ return 1; ++} + -+ err = gpio_request(pdata->gpio_pin_2y, dev_name(&pdev->dev)); -+ if (err) { -+ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", -+ pdata->gpio_pin_2y, err); -+ goto err_free_1y; -+ } ++#ifdef CONFIG_IMAGE_CMDLINE_HACK ++extern char __image_cmdline[]; + -+ err = gpio_direction_output(pdata->gpio_pin_s0, 0); -+ if (err) { -+ dev_err(&pdev->dev, -+ "unable to set direction of gpio %u, err=%d\n", -+ pdata->gpio_pin_s0, err); -+ goto err_free_2y; -+ } ++static int __init ar71xx_use__image_cmdline(void) ++{ ++ char *p = __image_cmdline; ++ int replace = 0; + -+ err = gpio_direction_output(pdata->gpio_pin_s1, 0); -+ if (err) { -+ dev_err(&pdev->dev, -+ "unable to set direction of gpio %u, err=%d\n", -+ pdata->gpio_pin_s1, err); -+ goto err_free_2y; ++ if (*p == '-') { ++ replace = 1; ++ p++; + } + -+ err = gpio_direction_input(pdata->gpio_pin_1y); -+ if (err) { -+ dev_err(&pdev->dev, -+ "unable to set direction of gpio %u, err=%d\n", -+ pdata->gpio_pin_1y, err); -+ goto err_free_2y; -+ } ++ if (*p == '\0') ++ return 0; + -+ err = gpio_direction_input(pdata->gpio_pin_2y); -+ if (err) { -+ dev_err(&pdev->dev, -+ "unable to set direction of gpio %u, err=%d\n", -+ pdata->gpio_pin_2y, err); -+ goto err_free_2y; ++ if (replace) { ++ strlcpy(arcs_cmdline, p, sizeof(arcs_cmdline)); ++ } else { ++ strlcat(arcs_cmdline, " ", sizeof(arcs_cmdline)); ++ strlcat(arcs_cmdline, p, sizeof(arcs_cmdline)); + } + -+ nxp->parent = &pdev->dev; -+ mutex_init(&nxp->lock); -+ -+ gc = &nxp->gpio_chip; -+ -+ gc->direction_input = nxp_74hc153_direction_input; -+ gc->direction_output = nxp_74hc153_direction_output; -+ gc->get = nxp_74hc153_get_value; -+ gc->set = nxp_74hc153_set_value; -+ gc->can_sleep = 1; ++ return 1; ++} ++#else ++static inline int ar71xx_use__image_cmdline(void) { return 0; } ++#endif + -+ gc->base = pdata->gpio_base; -+ gc->ngpio = NXP_74HC153_NUM_GPIOS; -+ gc->label = dev_name(nxp->parent); -+ gc->dev = nxp->parent; -+ gc->owner = THIS_MODULE; ++static __init void ar71xx_prom_init_cmdline(int argc, char **argv) ++{ ++ int i; + -+ err = gpiochip_add(&nxp->gpio_chip); -+ if (err) { -+ dev_err(&pdev->dev, "unable to add gpio chip, err=%d\n", err); -+ goto err_free_2y; -+ } ++ if (ar71xx_use__image_cmdline()) ++ return; + -+ platform_set_drvdata(pdev, nxp); -+ return 0; ++ if (!is_valid_ram_addr(argv)) ++ return; + -+ err_free_2y: -+ gpio_free(pdata->gpio_pin_2y); -+ err_free_1y: -+ gpio_free(pdata->gpio_pin_1y); -+ err_free_s1: -+ gpio_free(pdata->gpio_pin_s1); -+ err_free_s0: -+ gpio_free(pdata->gpio_pin_s0); -+ err_free_nxp: -+ kfree(nxp); -+ return err; ++ for (i = 0; i < argc; i++) ++ if (is_valid_ram_addr(argv[i])) { ++ strlcat(arcs_cmdline, " ", sizeof(arcs_cmdline)); ++ strlcat(arcs_cmdline, argv[i], sizeof(arcs_cmdline)); ++ } +} + -+static int nxp_74hc153_remove(struct platform_device *pdev) ++void __init prom_init(void) +{ -+ struct nxp_74hc153_chip *nxp = platform_get_drvdata(pdev); -+ struct nxp_74hc153_platform_data *pdata = pdev->dev.platform_data; ++ const char *env; ++ char **envp; + -+ if (nxp) { -+ int err; ++ printk(KERN_DEBUG "prom: fw_arg0=%08x, fw_arg1=%08x, " ++ "fw_arg2=%08x, fw_arg3=%08x\n", ++ (unsigned int)fw_arg0, (unsigned int)fw_arg1, ++ (unsigned int)fw_arg2, (unsigned int)fw_arg3); + -+ err = gpiochip_remove(&nxp->gpio_chip); -+ if (err) { -+ dev_err(&pdev->dev, -+ "unable to remove gpio chip, err=%d\n", -+ err); -+ return err; -+ } + -+ gpio_free(pdata->gpio_pin_2y); -+ gpio_free(pdata->gpio_pin_1y); -+ gpio_free(pdata->gpio_pin_s1); -+ gpio_free(pdata->gpio_pin_s0); ++ if (ar71xx_prom_init_myloader()) ++ return; + -+ kfree(nxp); -+ platform_set_drvdata(pdev, NULL); ++ ar71xx_prom_init_cmdline(fw_arg0, (char **)fw_arg1); ++ ++ envp = (char **)fw_arg2; ++ if (!strstr(arcs_cmdline, "ethaddr=")) { ++ env = ar71xx_prom_find_env(envp, "ethaddr"); ++ if (env) ++ ar71xx_prom_append_cmdline("ethaddr", env); + } + -+ return 0; -+} ++ if (!strstr(arcs_cmdline, "board=")) { ++ env = ar71xx_prom_find_env(envp, "board"); ++ if (env) { ++ /* Workaround for buggy bootloaders */ ++ if (strcmp(env, "RouterStation") == 0 || ++ strcmp(env, "Ubiquiti AR71xx-based board") == 0) ++ env = "UBNT-RS"; + -+static struct platform_driver nxp_74hc153_driver = { -+ .probe = nxp_74hc153_probe, -+ .remove = __devexit_p(nxp_74hc153_remove), -+ .driver = { -+ .name = NXP_74HC153_DRIVER_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++ if (strcmp(env, "RouterStation PRO") == 0) ++ env = "UBNT-RSPRO"; + -+static int __init nxp_74hc153_init(void) -+{ -+ return platform_driver_register(&nxp_74hc153_driver); ++ ar71xx_prom_append_cmdline("board", env); ++ } ++ } +} -+subsys_initcall(nxp_74hc153_init); + -+static void __exit nxp_74hc153_exit(void) ++void __init prom_free_prom_memory(void) +{ -+ platform_driver_unregister(&nxp_74hc153_driver); ++ /* We do not have to prom memory to free */ +} -+module_exit(nxp_74hc153_exit); -+ -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_DESCRIPTION("GPIO expander driver for NXP 74HC153"); -+MODULE_LICENSE("GPL v2"); -+MODULE_ALIAS("platform:" NXP_74HC153_DRIVER_NAME); -diff -Nur linux-2.6.39.orig/drivers/input/misc/Kconfig linux-2.6.39/drivers/input/misc/Kconfig ---- linux-2.6.39.orig/drivers/input/misc/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/input/misc/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -467,4 +467,20 @@ - To compile this driver as a module, choose M here: the - module will be called xen-kbdfront. - -+config INPUT_GPIO_BUTTONS -+ tristate "Polled GPIO buttons interface" -+ depends on GENERIC_GPIO -+ select INPUT_POLLDEV -+ help -+ This driver implements support for buttons connected -+ to GPIO pins of various CPUs (and some other chips). -+ -+ Say Y here if your device has buttons connected -+ directly to such GPIO pins. Your board-specific -+ setup logic must also provide a platform device, -+ with configuration data saying which GPIOs are used. -+ -+ To compile this driver as a module, choose M here: the -+ module will be called gpio-buttons. -+ - endif -diff -Nur linux-2.6.39.orig/drivers/input/misc/Makefile linux-2.6.39/drivers/input/misc/Makefile ---- linux-2.6.39.orig/drivers/input/misc/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/input/misc/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -44,4 +44,5 @@ - obj-$(CONFIG_INPUT_WM831X_ON) += wm831x-on.o - obj-$(CONFIG_INPUT_XEN_KBDDEV_FRONTEND) += xen-kbdfront.o - obj-$(CONFIG_INPUT_YEALINK) += yealink.o -+obj-$(CONFIG_INPUT_GPIO_BUTTONS) += gpio_buttons.o - -diff -Nur linux-2.6.39.orig/drivers/input/misc/gpio_buttons.c linux-2.6.39/drivers/input/misc/gpio_buttons.c ---- linux-2.6.39.orig/drivers/input/misc/gpio_buttons.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/input/misc/gpio_buttons.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,216 @@ +diff -Nur linux-2.6.39.orig/arch/mips/ar71xx/setup.c linux-2.6.39/arch/mips/ar71xx/setup.c +--- linux-2.6.39.orig/arch/mips/ar71xx/setup.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/ar71xx/setup.c 2011-08-24 02:41:55.737990425 +0200 +@@ -0,0 +1,446 @@ +/* -+ * Driver for buttons on GPIO lines not capable of generating interrupts -+ * -+ * Copyright (C) 2007-2010 Gabor Juhos -+ * Copyright (C) 2010 Nuno Goncalves -+ * -+ * This file was based on: /drivers/input/misc/cobalt_btns.c -+ * Copyright (C) 2007 Yoichi Yuasa ++ * Atheros AR71xx SoC specific setup + * -+ * also was based on: /drivers/input/keyboard/gpio_keys.c -+ * Copyright 2005 Phil Blundell ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. ++ * Parts of this file are based on Atheros 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.31 BSP + * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + +#include -+#include +#include -+#include ++#include + -+#include -+#include -+#include -+#include ++#include ++#include /* for mips_hpt_frequency */ ++#include /* for _machine_{restart,halt} */ ++#include + -+#include ++#include + -+#include ++#include "machtype.h" ++#include "devices.h" + -+#define DRV_NAME "gpio-buttons" -+#define DRV_VERSION "0.1.2" -+#define PFX DRV_NAME ": " ++#define AR71XX_SYS_TYPE_LEN 64 + -+struct gpio_button_data { -+ int last_state; -+ int count; -+}; ++u32 ar71xx_cpu_freq; ++EXPORT_SYMBOL_GPL(ar71xx_cpu_freq); + -+struct gpio_buttons_dev { -+ struct input_polled_dev *poll_dev; -+ struct gpio_buttons_platform_data *pdata; -+ struct gpio_button_data *data; -+}; ++u32 ar71xx_ahb_freq; ++EXPORT_SYMBOL_GPL(ar71xx_ahb_freq); + -+static void gpio_buttons_poll(struct input_polled_dev *dev) -+{ -+ struct gpio_buttons_dev *bdev = dev->private; -+ struct gpio_buttons_platform_data *pdata = bdev->pdata; -+ struct input_dev *input = dev->input; -+ int i; ++u32 ar71xx_ddr_freq; ++EXPORT_SYMBOL_GPL(ar71xx_ddr_freq); + -+ for (i = 0; i < bdev->pdata->nbuttons; i++) { -+ struct gpio_button *button = &pdata->buttons[i]; -+ unsigned int type = button->type ?: EV_KEY; -+ int state; ++u32 ar71xx_ref_freq; ++EXPORT_SYMBOL_GPL(ar71xx_ref_freq); + -+ if (bdev->data[i].count < button->threshold) { -+ bdev->data[i].count++; -+ continue; -+ } ++enum ar71xx_soc_type ar71xx_soc; ++EXPORT_SYMBOL_GPL(ar71xx_soc); + -+ state = gpio_get_value(button->gpio) ? 1 : 0; -+ if (state != bdev->data[i].last_state) { -+ input_event(input, type, button->code, -+ !!(state ^ button->active_low)); -+ input_sync(input); -+ bdev->data[i].count = 0; -+ bdev->data[i].last_state = state; -+ } -+ } ++u32 ar71xx_soc_rev; ++EXPORT_SYMBOL_GPL(ar71xx_soc_rev); ++ ++static char ar71xx_sys_type[AR71XX_SYS_TYPE_LEN]; ++ ++static void ar71xx_restart(char *command) ++{ ++ ar71xx_device_stop(RESET_MODULE_FULL_CHIP); ++ for (;;) ++ if (cpu_wait) ++ cpu_wait(); +} + -+static int __devinit gpio_buttons_probe(struct platform_device *pdev) ++static void ar71xx_halt(void) +{ -+ struct gpio_buttons_platform_data *pdata = pdev->dev.platform_data; -+ struct gpio_buttons_dev *bdev; -+ struct input_polled_dev *poll_dev; -+ struct input_dev *input; -+ int error, i; ++ while (1) ++ cpu_wait(); ++} + -+ if (!pdata) -+ return -ENXIO; ++static void __init ar71xx_detect_mem_size(void) ++{ ++ unsigned long size; + -+ bdev = kzalloc(sizeof(struct gpio_buttons_dev) + -+ sizeof(struct gpio_button_data) * pdata->nbuttons, -+ GFP_KERNEL); -+ if (!bdev) { -+ printk(KERN_ERR DRV_NAME "no memory for device\n"); -+ return -ENOMEM; ++ for (size = AR71XX_MEM_SIZE_MIN; size < AR71XX_MEM_SIZE_MAX; ++ size <<= 1) { ++ if (!memcmp(ar71xx_detect_mem_size, ++ ar71xx_detect_mem_size + size, 1024)) ++ break; + } + -+ bdev->data = (struct gpio_button_data *) &bdev[1]; ++ add_memory_region(0, size, BOOT_MEM_RAM); ++} + -+ poll_dev = input_allocate_polled_device(); -+ if (!poll_dev) { -+ printk(KERN_ERR DRV_NAME "no memory for polled device\n"); -+ error = -ENOMEM; -+ goto err_free_bdev; -+ } ++static void __init ar71xx_detect_sys_type(void) ++{ ++ char *chip = "????"; ++ u32 id; ++ u32 major; ++ u32 minor; ++ u32 rev = 0; ++ ++ id = ar71xx_reset_rr(AR71XX_RESET_REG_REV_ID); ++ major = id & REV_ID_MAJOR_MASK; ++ ++ switch (major) { ++ case REV_ID_MAJOR_AR71XX: ++ minor = id & AR71XX_REV_ID_MINOR_MASK; ++ rev = id >> AR71XX_REV_ID_REVISION_SHIFT; ++ rev &= AR71XX_REV_ID_REVISION_MASK; ++ switch (minor) { ++ case AR71XX_REV_ID_MINOR_AR7130: ++ ar71xx_soc = AR71XX_SOC_AR7130; ++ chip = "7130"; ++ break; ++ ++ case AR71XX_REV_ID_MINOR_AR7141: ++ ar71xx_soc = AR71XX_SOC_AR7141; ++ chip = "7141"; ++ break; + -+ poll_dev->private = bdev; -+ poll_dev->poll = gpio_buttons_poll; -+ poll_dev->poll_interval = pdata->poll_interval; ++ case AR71XX_REV_ID_MINOR_AR7161: ++ ar71xx_soc = AR71XX_SOC_AR7161; ++ chip = "7161"; ++ break; ++ } ++ break; + -+ input = poll_dev->input; ++ case REV_ID_MAJOR_AR7240: ++ ar71xx_soc = AR71XX_SOC_AR7240; ++ chip = "7240"; ++ rev = id & AR724X_REV_ID_REVISION_MASK; ++ break; + -+ input->evbit[0] = BIT(EV_KEY); -+ input->name = pdev->name; -+ input->phys = "gpio-buttons/input0"; -+ input->dev.parent = &pdev->dev; ++ case REV_ID_MAJOR_AR7241: ++ ar71xx_soc = AR71XX_SOC_AR7241; ++ chip = "7241"; ++ rev = id & AR724X_REV_ID_REVISION_MASK; ++ break; + -+ input->id.bustype = BUS_HOST; -+ input->id.vendor = 0x0001; -+ input->id.product = 0x0001; -+ input->id.version = 0x0100; ++ case REV_ID_MAJOR_AR7242: ++ ar71xx_soc = AR71XX_SOC_AR7242; ++ chip = "7242"; ++ rev = id & AR724X_REV_ID_REVISION_MASK; ++ break; + -+ for (i = 0; i < pdata->nbuttons; i++) { -+ struct gpio_button *button = &pdata->buttons[i]; -+ unsigned int gpio = button->gpio; -+ unsigned int type = button->type ?: EV_KEY; ++ case REV_ID_MAJOR_AR913X: ++ minor = id & AR91XX_REV_ID_MINOR_MASK; ++ rev = id >> AR91XX_REV_ID_REVISION_SHIFT; ++ rev &= AR91XX_REV_ID_REVISION_MASK; ++ switch (minor) { ++ case AR91XX_REV_ID_MINOR_AR9130: ++ ar71xx_soc = AR71XX_SOC_AR9130; ++ chip = "9130"; ++ break; + -+ error = gpio_request(gpio, button->desc ? -+ button->desc : DRV_NAME); -+ if (error) { -+ printk(KERN_ERR PFX "unable to claim gpio %u, " -+ "error %d\n", gpio, error); -+ goto err_free_gpio; ++ case AR91XX_REV_ID_MINOR_AR9132: ++ ar71xx_soc = AR71XX_SOC_AR9132; ++ chip = "9132"; ++ break; + } ++ break; + -+ error = gpio_direction_input(gpio); -+ if (error) { -+ printk(KERN_ERR PFX "unable to set direction on " -+ "gpio %u, error %d\n", gpio, error); -+ goto err_free_gpio; -+ } ++ case REV_ID_MAJOR_AR9330: ++ ar71xx_soc = AR71XX_SOC_AR9330; ++ chip = "9330"; ++ rev = id & AR933X_REV_ID_REVISION_MASK; ++ break; + -+ input_set_capability(input, type, button->code); -+ bdev->data[i].last_state = gpio_get_value(button->gpio) ? 1 : 0; -+ } ++ case REV_ID_MAJOR_AR9331: ++ ar71xx_soc = AR71XX_SOC_AR9331; ++ chip = "9331"; ++ rev = id & AR933X_REV_ID_REVISION_MASK; ++ break; ++ ++ case REV_ID_MAJOR_AR9342: ++ ar71xx_soc = AR71XX_SOC_AR9342; ++ chip = "9342"; ++ rev = id & AR934X_REV_ID_REVISION_MASK; ++ break; + -+ bdev->poll_dev = poll_dev; -+ bdev->pdata = pdata; -+ platform_set_drvdata(pdev, bdev); ++ case REV_ID_MAJOR_AR9344: ++ ar71xx_soc = AR71XX_SOC_AR9344; ++ chip = "9344"; ++ rev = id & AR934X_REV_ID_REVISION_MASK; ++ break; + -+ error = input_register_polled_device(poll_dev); -+ if (error) { -+ printk(KERN_ERR PFX "unable to register polled device, " -+ "error %d\n", error); -+ goto err_free_gpio; ++ default: ++ panic("ar71xx: unknown chip id:0x%08x\n", id); + } + -+ return 0; ++ ar71xx_soc_rev = rev; + -+err_free_gpio: -+ for (i = i - 1; i >= 0; i--) -+ gpio_free(pdata->buttons[i].gpio); ++ sprintf(ar71xx_sys_type, "Atheros AR%s rev %u", chip, rev); ++ pr_info("SoC: %s\n", ar71xx_sys_type); ++} + -+ input_free_polled_device(poll_dev); ++static void __init ar934x_detect_sys_frequency(void) ++{ ++ u32 pll, out_div, ref_div, nint, frac, clk_ctrl, postdiv; + -+err_free_bdev: -+ kfree(bdev); ++ if (ar71xx_reset_rr(AR934X_RESET_REG_BOOTSTRAP) & AR934X_REF_CLK_40) ++ ar71xx_ref_freq = 40 * 1000 * 1000; ++ else ++ ar71xx_ref_freq = 25 * 1000 * 1000; ++ ++ clk_ctrl = ar71xx_pll_rr(AR934X_PLL_REG_DDR_CTRL_CLOCK); ++ ++ pll = ar71xx_pll_rr(AR934X_PLL_REG_CPU_CONFIG); ++ out_div = AR934X_CPU_PLL_CFG_OUTDIV_GET(pll); ++ ref_div = AR934X_CPU_PLL_CFG_REFDIV_GET(pll); ++ nint = AR934X_CPU_PLL_CFG_NINT_GET(pll); ++ frac = AR934X_CPU_PLL_CFG_NFRAC_GET(pll); ++ postdiv = AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_GET(clk_ctrl); ++ ar71xx_cpu_freq = ((nint * ar71xx_ref_freq / ref_div) >> out_div) / ++ (postdiv + 1); ++ ++ out_div = AR934X_DDR_PLL_CFG_OUTDIV_GET(pll); ++ ref_div = AR934X_DDR_PLL_CFG_REFDIV_GET(pll); ++ nint = AR934X_DDR_PLL_CFG_NINT_GET(pll); ++ frac = AR934X_DDR_PLL_CFG_NFRAC_GET(pll); ++ postdiv = AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_GET(clk_ctrl); ++ ar71xx_ddr_freq = ((nint * ar71xx_ref_freq / ref_div) >> out_div) / ++ (postdiv + 1); ++ ++ postdiv = AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_GET(clk_ctrl); ++ ++ if (AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_GET(clk_ctrl)) { ++ ar71xx_ahb_freq = ar71xx_ddr_freq / (postdiv + 1); ++ } else { ++ ar71xx_ahb_freq = ar71xx_cpu_freq / (postdiv + 1); ++ } + -+ platform_set_drvdata(pdev, NULL); -+ return error; +} + -+static int __devexit gpio_buttons_remove(struct platform_device *pdev) ++static void __init ar91xx_detect_sys_frequency(void) +{ -+ struct gpio_buttons_dev *bdev = platform_get_drvdata(pdev); -+ struct gpio_buttons_platform_data *pdata = bdev->pdata; -+ int i; -+ -+ input_unregister_polled_device(bdev->poll_dev); ++ u32 pll; ++ u32 freq; ++ u32 div; + -+ for (i = 0; i < pdata->nbuttons; i++) -+ gpio_free(pdata->buttons[i].gpio); ++ ar71xx_ref_freq = 5 * 1000 * 1000; + -+ input_free_polled_device(bdev->poll_dev); ++ pll = ar71xx_pll_rr(AR91XX_PLL_REG_CPU_CONFIG); + -+ kfree(bdev); -+ platform_set_drvdata(pdev, NULL); ++ div = ((pll >> AR91XX_PLL_DIV_SHIFT) & AR91XX_PLL_DIV_MASK); ++ freq = div * ar71xx_ref_freq; + -+ return 0; -+} ++ ar71xx_cpu_freq = freq; + -+static struct platform_driver gpio_buttons_driver = { -+ .probe = gpio_buttons_probe, -+ .remove = __devexit_p(gpio_buttons_remove), -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++ div = ((pll >> AR91XX_DDR_DIV_SHIFT) & AR91XX_DDR_DIV_MASK) + 1; ++ ar71xx_ddr_freq = freq / div; + -+static int __init gpio_buttons_init(void) -+{ -+ printk(KERN_INFO DRV_NAME " driver version " DRV_VERSION "\n"); -+ return platform_driver_register(&gpio_buttons_driver); ++ div = (((pll >> AR91XX_AHB_DIV_SHIFT) & AR91XX_AHB_DIV_MASK) + 1) * 2; ++ ar71xx_ahb_freq = ar71xx_cpu_freq / div; +} + -+static void __exit gpio_buttons_exit(void) ++static void __init ar71xx_detect_sys_frequency(void) +{ -+ platform_driver_unregister(&gpio_buttons_driver); -+} -+ -+module_init(gpio_buttons_init); -+module_exit(gpio_buttons_exit); ++ u32 pll; ++ u32 freq; ++ u32 div; + -+MODULE_LICENSE("GPL"); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_VERSION(DRV_VERSION); -+MODULE_DESCRIPTION("Polled buttons driver for CPU GPIOs"); ++ ar71xx_ref_freq = 40 * 1000 * 1000; + -diff -Nur linux-2.6.39.orig/drivers/leds/leds-rb750.c linux-2.6.39/drivers/leds/leds-rb750.c ---- linux-2.6.39.orig/drivers/leds/leds-rb750.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/leds/leds-rb750.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,140 @@ -+/* -+ * LED driver for the RouterBOARD 750 -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. -+ * -+ */ -+#include -+#include -+#include -+#include ++ pll = ar71xx_pll_rr(AR71XX_PLL_REG_CPU_CONFIG); + -+#include ++ div = ((pll >> AR71XX_PLL_DIV_SHIFT) & AR71XX_PLL_DIV_MASK) + 1; ++ freq = div * ar71xx_ref_freq; + -+#define DRV_NAME "leds-rb750" ++ div = ((pll >> AR71XX_CPU_DIV_SHIFT) & AR71XX_CPU_DIV_MASK) + 1; ++ ar71xx_cpu_freq = freq / div; + -+struct rb750_led_dev { -+ struct led_classdev cdev; -+ u32 mask; -+ int active_low; -+}; -+ -+struct rb750_led_drvdata { -+ struct rb750_led_dev *led_devs; -+ int num_leds; -+}; ++ div = ((pll >> AR71XX_DDR_DIV_SHIFT) & AR71XX_DDR_DIV_MASK) + 1; ++ ar71xx_ddr_freq = freq / div; + -+static inline struct rb750_led_dev *to_rbled(struct led_classdev *led_cdev) -+{ -+ return (struct rb750_led_dev *)container_of(led_cdev, -+ struct rb750_led_dev, cdev); ++ div = (((pll >> AR71XX_AHB_DIV_SHIFT) & AR71XX_AHB_DIV_MASK) + 1) * 2; ++ ar71xx_ahb_freq = ar71xx_cpu_freq / div; +} + -+static void rb750_led_brightness_set(struct led_classdev *led_cdev, -+ enum led_brightness value) ++static void __init ar724x_detect_sys_frequency(void) +{ -+ struct rb750_led_dev *rbled = to_rbled(led_cdev); -+ int level; ++ u32 pll; ++ u32 freq; ++ u32 div; + -+ level = (value == LED_OFF) ? 0 : 1; -+ level ^= rbled->active_low; ++ ar71xx_ref_freq = 5 * 1000 * 1000; + -+ if (level) -+ rb750_latch_change(0, rbled->mask); -+ else -+ rb750_latch_change(rbled->mask, 0); ++ pll = ar71xx_pll_rr(AR724X_PLL_REG_CPU_CONFIG); ++ ++ div = ((pll >> AR724X_PLL_DIV_SHIFT) & AR724X_PLL_DIV_MASK); ++ freq = div * ar71xx_ref_freq; ++ ++ div = ((pll >> AR724X_PLL_REF_DIV_SHIFT) & AR724X_PLL_REF_DIV_MASK); ++ freq *= div; ++ ++ ar71xx_cpu_freq = freq; ++ ++ div = ((pll >> AR724X_DDR_DIV_SHIFT) & AR724X_DDR_DIV_MASK) + 1; ++ ar71xx_ddr_freq = freq / div; ++ ++ div = (((pll >> AR724X_AHB_DIV_SHIFT) & AR724X_AHB_DIV_MASK) + 1) * 2; ++ ar71xx_ahb_freq = ar71xx_cpu_freq / div; +} + -+static int __devinit rb750_led_probe(struct platform_device *pdev) ++static void __init ar933x_detect_sys_frequency(void) +{ -+ struct rb750_led_platform_data *pdata; -+ struct rb750_led_drvdata *drvdata; -+ int ret = 0; -+ int i; -+ -+ pdata = pdev->dev.platform_data; -+ if (!pdata) -+ return -EINVAL; ++ u32 clock_ctrl; ++ u32 cpu_config; ++ u32 freq; ++ u32 t; + -+ drvdata = kzalloc(sizeof(struct rb750_led_drvdata) + -+ sizeof(struct rb750_led_dev) * pdata->num_leds, -+ GFP_KERNEL); -+ if (!drvdata) -+ return -ENOMEM; ++ t = ar71xx_reset_rr(AR933X_RESET_REG_BOOTSTRAP); ++ if (t & AR933X_BOOTSTRAP_REF_CLK_40) ++ ar71xx_ref_freq = (40 * 1000 * 1000); ++ else ++ ar71xx_ref_freq = (25 * 1000 * 1000); + -+ drvdata->num_leds = pdata->num_leds; -+ drvdata->led_devs = (struct rb750_led_dev *) &drvdata[1]; ++ clock_ctrl = ar71xx_pll_rr(AR933X_PLL_CLOCK_CTRL_REG); ++ if (clock_ctrl & AR933X_PLL_CLOCK_CTRL_BYPASS) { ++ ar71xx_cpu_freq = ar71xx_ref_freq; ++ ar71xx_ahb_freq = ar71xx_ref_freq; ++ ar71xx_ddr_freq = ar71xx_ref_freq; ++ } else { ++ cpu_config = ar71xx_pll_rr(AR933X_PLL_CPU_CONFIG_REG); + -+ for (i = 0; i < drvdata->num_leds; i++) { -+ struct rb750_led_dev *rbled = &drvdata->led_devs[i]; -+ struct rb750_led_data *led_data = &pdata->leds[i]; ++ t = (cpu_config >> AR933X_PLL_CPU_CONFIG_REFDIV_SHIFT) & ++ AR933X_PLL_CPU_CONFIG_REFDIV_MASK; ++ freq = ar71xx_ref_freq / t; + -+ rbled->cdev.name = led_data->name; -+ rbled->cdev.default_trigger = led_data->default_trigger; -+ rbled->cdev.brightness_set = rb750_led_brightness_set; -+ rbled->cdev.brightness = LED_OFF; ++ t = (cpu_config >> AR933X_PLL_CPU_CONFIG_NINT_SHIFT) & ++ AR933X_PLL_CPU_CONFIG_NINT_MASK; ++ freq *= t; + -+ rbled->mask = led_data->mask; -+ rbled->active_low = !!led_data->active_low; ++ t = (cpu_config >> AR933X_PLL_CPU_CONFIG_OUTDIV_SHIFT) & ++ AR933X_PLL_CPU_CONFIG_OUTDIV_MASK; ++ if (t == 0) ++ t = 1; + -+ ret = led_classdev_register(&pdev->dev, &rbled->cdev); -+ if (ret) -+ goto err; -+ } ++ freq >>= t; + -+ platform_set_drvdata(pdev, drvdata); -+ return 0; ++ t = ((clock_ctrl >> AR933X_PLL_CLOCK_CTRL_CPU_DIV_SHIFT) & ++ AR933X_PLL_CLOCK_CTRL_CPU_DIV_MASK) + 1; ++ ar71xx_cpu_freq = freq / t; + -+ err: -+ for (i = i - 1; i >= 0; i--) -+ led_classdev_unregister(&drvdata->led_devs[i].cdev); ++ t = ((clock_ctrl >> AR933X_PLL_CLOCK_CTRL_DDR_DIV_SHIFT) & ++ AR933X_PLL_CLOCK_CTRL_DDR_DIV_MASK) + 1; ++ ar71xx_ddr_freq = freq / t; + -+ kfree(drvdata); -+ return ret; ++ t = ((clock_ctrl >> AR933X_PLL_CLOCK_CTRL_AHB_DIV_SHIFT) & ++ AR933X_PLL_CLOCK_CTRL_AHB_DIV_MASK) + 1; ++ ar71xx_ahb_freq = freq / t; ++ } +} + -+static int __devexit rb750_led_remove(struct platform_device *pdev) ++static void __init detect_sys_frequency(void) +{ -+ struct rb750_led_drvdata *drvdata; -+ int i; ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ ar71xx_detect_sys_frequency(); ++ break; + -+ drvdata = platform_get_drvdata(pdev); -+ for (i = 0; i < drvdata->num_leds; i++) -+ led_classdev_unregister(&drvdata->led_devs[i].cdev); ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ ar724x_detect_sys_frequency(); ++ break; + -+ kfree(drvdata); -+ return 0; -+} ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ ar91xx_detect_sys_frequency(); ++ break; + -+static struct platform_driver rb750_led_driver = { -+ .probe = rb750_led_probe, -+ .remove = __devexit_p(rb750_led_remove), -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ ar933x_detect_sys_frequency(); ++ break; + -+MODULE_ALIAS("platform:leds-rb750"); ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ ar934x_detect_sys_frequency(); ++ break; ++ default: ++ BUG(); ++ } ++} + -+static int __init rb750_led_init(void) ++const char *get_system_type(void) +{ -+ return platform_driver_register(&rb750_led_driver); ++ return ar71xx_sys_type; +} + -+static void __exit rb750_led_exit(void) ++unsigned int __cpuinit get_c0_compare_irq(void) +{ -+ platform_driver_unregister(&rb750_led_driver); ++ return CP0_LEGACY_COMPARE_IRQ; +} + -+module_init(rb750_led_init); -+module_exit(rb750_led_exit); ++void __init plat_mem_setup(void) ++{ ++ set_io_port_base(KSEG1); + -+MODULE_DESCRIPTION(DRV_NAME); -+MODULE_DESCRIPTION("LED driver for the RouterBOARD 750"); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/leds/leds-wndr3700-usb.c linux-2.6.39/drivers/leds/leds-wndr3700-usb.c ---- linux-2.6.39.orig/drivers/leds/leds-wndr3700-usb.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/leds/leds-wndr3700-usb.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,75 @@ -+/* -+ * USB LED driver for the NETGEAR WNDR3700 -+ * -+ * Copyright (C) 2009 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ ar71xx_ddr_base = ioremap_nocache(AR71XX_DDR_CTRL_BASE, ++ AR71XX_DDR_CTRL_SIZE); + -+#include -+#include -+#include ++ ar71xx_pll_base = ioremap_nocache(AR71XX_PLL_BASE, ++ AR71XX_PLL_SIZE); + -+#include ++ ar71xx_reset_base = ioremap_nocache(AR71XX_RESET_BASE, ++ AR71XX_RESET_SIZE); + -+#define DRIVER_NAME "wndr3700-led-usb" ++ ar71xx_gpio_base = ioremap_nocache(AR71XX_GPIO_BASE, AR71XX_GPIO_SIZE); + -+static void wndr3700_usb_led_set(struct led_classdev *cdev, -+ enum led_brightness brightness) -+{ -+ if (brightness) -+ ar71xx_device_start(RESET_MODULE_GE1_PHY); -+ else -+ ar71xx_device_stop(RESET_MODULE_GE1_PHY); ++ ar71xx_usb_ctrl_base = ioremap_nocache(AR71XX_USB_CTRL_BASE, ++ AR71XX_USB_CTRL_SIZE); ++ ++ ar71xx_detect_mem_size(); ++ ar71xx_detect_sys_type(); ++ detect_sys_frequency(); ++ ++ pr_info("Clocks: CPU:%u.%03uMHz, DDR:%u.%03uMHz, AHB:%u.%03uMHz, " ++ "Ref:%u.%03uMHz", ++ ar71xx_cpu_freq / 1000000, (ar71xx_cpu_freq / 1000) % 1000, ++ ar71xx_ddr_freq / 1000000, (ar71xx_ddr_freq / 1000) % 1000, ++ ar71xx_ahb_freq / 1000000, (ar71xx_ahb_freq / 1000) % 1000, ++ ar71xx_ref_freq / 1000000, (ar71xx_ref_freq / 1000) % 1000); ++ ++ _machine_restart = ar71xx_restart; ++ _machine_halt = ar71xx_halt; ++ pm_power_off = ar71xx_halt; +} + -+static enum led_brightness wndr3700_usb_led_get(struct led_classdev *cdev) ++void __init plat_time_init(void) +{ -+ return ar71xx_device_stopped(RESET_MODULE_GE1_PHY) ? LED_OFF : LED_FULL; ++ mips_hpt_frequency = ar71xx_cpu_freq / 2; +} + -+static struct led_classdev wndr3700_usb_led = { -+ .name = "wndr3700:green:usb", -+ .brightness_set = wndr3700_usb_led_set, -+ .brightness_get = wndr3700_usb_led_get, -+}; ++__setup("board=", mips_machtype_setup); + -+static int __devinit wndr3700_usb_led_probe(struct platform_device *pdev) ++static int __init ar71xx_machine_setup(void) +{ -+ return led_classdev_register(&pdev->dev, &wndr3700_usb_led); -+} ++ ar71xx_gpio_init(); + -+static int __devexit wndr3700_usb_led_remove(struct platform_device *pdev) -+{ -+ led_classdev_unregister(&wndr3700_usb_led); ++ ar71xx_add_device_uart(); ++ ar71xx_add_device_wdt(); ++ ++ mips_machine_setup(); + return 0; +} + -+static struct platform_driver wndr3700_usb_led_driver = { -+ .probe = wndr3700_usb_led_probe, -+ .remove = __devexit_p(wndr3700_usb_led_remove), -+ .driver = { -+ .name = DRIVER_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++arch_initcall(ar71xx_machine_setup); + -+static int __init wndr3700_usb_led_init(void) ++static void __init ar71xx_generic_init(void) +{ -+ return platform_driver_register(&wndr3700_usb_led_driver); ++ /* Nothing to do */ +} + -+static void __exit wndr3700_usb_led_exit(void) ++MIPS_MACHINE(AR71XX_MACH_GENERIC, "Generic", "Generic AR71xx board", ++ ar71xx_generic_init); +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/checksum.h linux-2.6.39/arch/mips/include/asm/checksum.h +--- linux-2.6.39.orig/arch/mips/include/asm/checksum.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/include/asm/checksum.h 2011-08-24 05:53:21.109231561 +0200 +@@ -12,6 +12,7 @@ + #define _ASM_CHECKSUM_H + + #include ++#include + + #include + +@@ -104,26 +105,30 @@ + const unsigned int *stop = word + ihl; + unsigned int csum; + int carry; ++ unsigned int w; + +- csum = word[0]; +- csum += word[1]; +- carry = (csum < word[1]); ++ csum = __get_unaligned_cpu32(word++); ++ ++ w = __get_unaligned_cpu32(word++); ++ csum += w; ++ carry = (csum < w); + csum += carry; + +- csum += word[2]; +- carry = (csum < word[2]); ++ w = __get_unaligned_cpu32(word++); ++ csum += w; ++ carry = (csum < w); + csum += carry; + +- csum += word[3]; +- carry = (csum < word[3]); ++ w = __get_unaligned_cpu32(word++); ++ csum += w; ++ carry = (csum < w); + csum += carry; + +- word += 4; + do { +- csum += *word; +- carry = (csum < *word); ++ w = __get_unaligned_cpu32(word++); ++ csum += w; ++ carry = (csum < w); + csum += carry; +- word++; + } while (word != stop); + + return csum_fold(csum); +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/fw/myloader/myloader.h linux-2.6.39/arch/mips/include/asm/fw/myloader/myloader.h +--- linux-2.6.39.orig/arch/mips/include/asm/fw/myloader/myloader.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/fw/myloader/myloader.h 2011-04-27 12:19:21.887662064 +0200 +@@ -0,0 +1,34 @@ ++/* ++ * Compex's MyLoader specific definitions ++ * ++ * Copyright (C) 2006-2008 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ ++ ++#ifndef _ASM_MIPS_FW_MYLOADER_H ++#define _ASM_MIPS_FW_MYLOADER_H ++ ++#include ++ ++struct myloader_info { ++ uint32_t vid; ++ uint32_t did; ++ uint32_t svid; ++ uint32_t sdid; ++ uint8_t macs[MYLO_ETHADDR_COUNT][6]; ++}; ++ ++#ifdef CONFIG_MYLOADER ++extern struct myloader_info *myloader_get_info(void) __init; ++#else ++static inline struct myloader_info *myloader_get_info(void) +{ -+ platform_driver_unregister(&wndr3700_usb_led_driver); ++ return NULL; +} ++#endif /* CONFIG_MYLOADER */ + -+module_init(wndr3700_usb_led_init); -+module_exit(wndr3700_usb_led_exit); -+ -+MODULE_DESCRIPTION("USB LED driver for the NETGEAR WNDR3700"); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_LICENSE("GPL v2"); -+MODULE_ALIAS("platform:" DRIVER_NAME); -diff -Nur linux-2.6.39.orig/drivers/mtd/maps/Kconfig linux-2.6.39/drivers/mtd/maps/Kconfig ---- linux-2.6.39.orig/drivers/mtd/maps/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/mtd/maps/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -260,6 +260,13 @@ - Support for parsing CFE image tag and creating MTD partitions on - Broadcom BCM63xx boards. - -+config MTD_AR91XX_FLASH -+ tristate "Atheros AR91xx parallel flash support" -+ depends on ATHEROS_AR71XX -+ select MTD_COMPLEX_MAPPINGS -+ help -+ Parallel flash driver for the Atheros AR91xx based boards. -+ - config MTD_DILNETPC - tristate "CFI Flash device mapped on DIL/Net PC" - depends on X86 && MTD_PARTITIONS && MTD_CFI_INTELEXT && BROKEN -diff -Nur linux-2.6.39.orig/drivers/mtd/maps/Makefile linux-2.6.39/drivers/mtd/maps/Makefile ---- linux-2.6.39.orig/drivers/mtd/maps/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/mtd/maps/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -7,6 +7,7 @@ - endif - - # Chip mappings -+obj-$(CONFIG_MTD_AR91XX_FLASH) += ar91xx_flash.o - obj-$(CONFIG_MTD_CDB89712) += cdb89712.o - obj-$(CONFIG_MTD_ARM_INTEGRATOR)+= integrator-flash.o - obj-$(CONFIG_MTD_CFI_FLAGADM) += cfi_flagadm.o -diff -Nur linux-2.6.39.orig/drivers/mtd/maps/ar91xx_flash.c linux-2.6.39/drivers/mtd/maps/ar91xx_flash.c ---- linux-2.6.39.orig/drivers/mtd/maps/ar91xx_flash.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/mtd/maps/ar91xx_flash.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,310 @@ ++#endif /* _ASM_MIPS_FW_MYLOADER_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar71xx.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar71xx.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar71xx.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar71xx.h 2011-08-06 09:32:36.758018150 +0200 +@@ -0,0 +1,769 @@ +/* -+ * Parallel flash driver for the Atheros AR91xx SoC ++ * Atheros AR71xx SoC specific definitions + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. ++ * Parts of this file are based on Atheros 2.6.15 BSP ++ * Parts of this file are based on Atheros 2.6.31 BSP + * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + -+#include ++#ifndef __ASM_MACH_AR71XX_H ++#define __ASM_MACH_AR71XX_H ++ +#include -+#include +#include -+#include -+#include -+#include -+#include -+#include -+#include +#include ++#include + -+#include -+#include -+ -+#define DRV_NAME "ar91xx-flash" -+ -+struct ar91xx_flash_info { -+ struct mtd_info *mtd; -+ struct map_info map; -+#ifdef CONFIG_MTD_PARTITIONS -+ int nr_parts; -+ struct mtd_partition *parts; -+#endif -+}; ++#ifndef __ASSEMBLER__ + -+static map_word ar91xx_flash_read(struct map_info *map, unsigned long ofs) -+{ -+ map_word val; ++#define AR71XX_PCI_MEM_BASE 0x10000000 ++#define AR71XX_PCI_MEM_SIZE 0x08000000 ++#define AR71XX_APB_BASE 0x18000000 ++#define AR71XX_GE0_BASE 0x19000000 ++#define AR71XX_GE0_SIZE 0x01000000 ++#define AR71XX_GE1_BASE 0x1a000000 ++#define AR71XX_GE1_SIZE 0x01000000 ++#define AR71XX_EHCI_BASE 0x1b000000 ++#define AR71XX_EHCI_SIZE 0x01000000 ++#define AR71XX_OHCI_BASE 0x1c000000 ++#define AR71XX_OHCI_SIZE 0x01000000 ++#define AR7240_OHCI_BASE 0x1b000000 ++#define AR7240_OHCI_SIZE 0x01000000 ++#define AR71XX_SPI_BASE 0x1f000000 ++#define AR71XX_SPI_SIZE 0x01000000 + -+ if (map_bankwidth_is_1(map)) -+ val.x[0] = __raw_readb(map->virt + (ofs ^ 3)); -+ else if (map_bankwidth_is_2(map)) -+ val.x[0] = __raw_readw(map->virt + (ofs ^ 2)); -+ else -+ val = map_word_ff(map); ++#define AR71XX_DDR_CTRL_BASE (AR71XX_APB_BASE + 0x00000000) ++#define AR71XX_DDR_CTRL_SIZE 0x10000 ++#define AR71XX_CPU_BASE (AR71XX_APB_BASE + 0x00010000) ++#define AR71XX_UART_BASE (AR71XX_APB_BASE + 0x00020000) ++#define AR71XX_UART_SIZE 0x10000 ++#define AR71XX_USB_CTRL_BASE (AR71XX_APB_BASE + 0x00030000) ++#define AR71XX_USB_CTRL_SIZE 0x10000 ++#define AR71XX_GPIO_BASE (AR71XX_APB_BASE + 0x00040000) ++#define AR71XX_GPIO_SIZE 0x10000 ++#define AR71XX_PLL_BASE (AR71XX_APB_BASE + 0x00050000) ++#define AR71XX_PLL_SIZE 0x10000 ++#define AR71XX_RESET_BASE (AR71XX_APB_BASE + 0x00060000) ++#define AR71XX_RESET_SIZE 0x10000 ++#define AR71XX_MII_BASE (AR71XX_APB_BASE + 0x00070000) ++#define AR71XX_MII_SIZE 0x10000 ++#define AR71XX_SLIC_BASE (AR71XX_APB_BASE + 0x00090000) ++#define AR71XX_SLIC_SIZE 0x10000 ++#define AR71XX_DMA_BASE (AR71XX_APB_BASE + 0x000A0000) ++#define AR71XX_DMA_SIZE 0x10000 ++#define AR71XX_STEREO_BASE (AR71XX_APB_BASE + 0x000B0000) ++#define AR71XX_STEREO_SIZE 0x10000 + -+ return val; -+} ++#define AR724X_PCI_CRP_BASE (AR71XX_APB_BASE + 0x000C0000) ++#define AR724X_PCI_CRP_SIZE 0x100 + -+static void ar91xx_flash_write(struct map_info *map, map_word d, -+ unsigned long ofs) -+{ -+ if (map_bankwidth_is_1(map)) -+ __raw_writeb(d.x[0], map->virt + (ofs ^ 3)); -+ else if (map_bankwidth_is_2(map)) -+ __raw_writew(d.x[0], map->virt + (ofs ^ 2)); ++#define AR724X_PCI_CTRL_BASE (AR71XX_APB_BASE + 0x000F0000) ++#define AR724X_PCI_CTRL_SIZE 0x100 + -+ mb(); -+} ++#define AR91XX_WMAC_BASE (AR71XX_APB_BASE + 0x000C0000) ++#define AR91XX_WMAC_SIZE 0x30000 + -+static map_word ar91xx_flash_read_lock(struct map_info *map, unsigned long ofs) -+{ -+ map_word ret; ++#define AR933X_UART_BASE (AR71XX_APB_BASE + 0x00020000) ++#define AR933X_UART_SIZE 0x14 ++#define AR933X_WMAC_BASE (AR71XX_APB_BASE + 0x00100000) ++#define AR933X_WMAC_SIZE 0x20000 + -+ ar71xx_flash_acquire(); -+ ret = ar91xx_flash_read(map, ofs); -+ ar71xx_flash_release(); ++#define AR934X_WMAC_BASE (AR71XX_APB_BASE + 0x00100000) ++#define AR934X_WMAC_SIZE 0x20000 + -+ return ret; -+} ++#define AR71XX_MEM_SIZE_MIN 0x0200000 ++#define AR71XX_MEM_SIZE_MAX 0x10000000 + -+static void ar91xx_flash_write_lock(struct map_info *map, map_word d, -+ unsigned long ofs) -+{ -+ ar71xx_flash_acquire(); -+ ar91xx_flash_write(map, d, ofs); -+ ar71xx_flash_release(); -+} ++#define AR71XX_CPU_IRQ_BASE 0 ++#define AR71XX_MISC_IRQ_BASE 8 ++#define AR71XX_MISC_IRQ_COUNT 32 ++#define AR71XX_GPIO_IRQ_BASE 40 ++#define AR71XX_GPIO_IRQ_COUNT 32 ++#define AR71XX_PCI_IRQ_BASE 72 ++#define AR71XX_PCI_IRQ_COUNT 8 + -+static void ar91xx_flash_copy_from_lock(struct map_info *map, void *to, -+ unsigned long from, ssize_t len) -+{ -+ ar71xx_flash_acquire(); -+ inline_map_copy_from(map, to, from, len); -+ ar71xx_flash_release(); -+} ++#define AR71XX_CPU_IRQ_IP2 (AR71XX_CPU_IRQ_BASE + 2) ++#define AR71XX_CPU_IRQ_USB (AR71XX_CPU_IRQ_BASE + 3) ++#define AR71XX_CPU_IRQ_GE0 (AR71XX_CPU_IRQ_BASE + 4) ++#define AR71XX_CPU_IRQ_GE1 (AR71XX_CPU_IRQ_BASE + 5) ++#define AR71XX_CPU_IRQ_MISC (AR71XX_CPU_IRQ_BASE + 6) ++#define AR71XX_CPU_IRQ_TIMER (AR71XX_CPU_IRQ_BASE + 7) + -+static void ar91xx_flash_copy_to_lock(struct map_info *map, unsigned long to, -+ const void *from, ssize_t len) -+{ -+ ar71xx_flash_acquire(); -+ inline_map_copy_to(map, to, from, len); -+ ar71xx_flash_release(); -+} ++#define AR71XX_MISC_IRQ_TIMER (AR71XX_MISC_IRQ_BASE + 0) ++#define AR71XX_MISC_IRQ_ERROR (AR71XX_MISC_IRQ_BASE + 1) ++#define AR71XX_MISC_IRQ_GPIO (AR71XX_MISC_IRQ_BASE + 2) ++#define AR71XX_MISC_IRQ_UART (AR71XX_MISC_IRQ_BASE + 3) ++#define AR71XX_MISC_IRQ_WDOG (AR71XX_MISC_IRQ_BASE + 4) ++#define AR71XX_MISC_IRQ_PERFC (AR71XX_MISC_IRQ_BASE + 5) ++#define AR71XX_MISC_IRQ_OHCI (AR71XX_MISC_IRQ_BASE + 6) ++#define AR71XX_MISC_IRQ_DMA (AR71XX_MISC_IRQ_BASE + 7) ++#define AR71XX_MISC_IRQ_TIMER2 (AR71XX_MISC_IRQ_BASE + 8) ++#define AR71XX_MISC_IRQ_TIMER3 (AR71XX_MISC_IRQ_BASE + 9) ++#define AR71XX_MISC_IRQ_TIMER4 (AR71XX_MISC_IRQ_BASE + 10) ++#define AR71XX_MISC_IRQ_DDR_PERF (AR71XX_MISC_IRQ_BASE + 11) ++#define AR71XX_MISC_IRQ_ENET_LINK (AR71XX_MISC_IRQ_BASE + 12) + -+static int ar91xx_flash_remove(struct platform_device *pdev) -+{ -+ struct ar91xx_flash_platform_data *pdata; -+ struct ar91xx_flash_info *info; ++#define AR71XX_GPIO_IRQ(_x) (AR71XX_GPIO_IRQ_BASE + (_x)) + -+ info = platform_get_drvdata(pdev); -+ if (info == NULL) -+ return 0; ++#define AR71XX_PCI_IRQ_DEV0 (AR71XX_PCI_IRQ_BASE + 0) ++#define AR71XX_PCI_IRQ_DEV1 (AR71XX_PCI_IRQ_BASE + 1) ++#define AR71XX_PCI_IRQ_DEV2 (AR71XX_PCI_IRQ_BASE + 2) ++#define AR71XX_PCI_IRQ_CORE (AR71XX_PCI_IRQ_BASE + 4) + -+ platform_set_drvdata(pdev, NULL); ++extern u32 ar71xx_ahb_freq; ++extern u32 ar71xx_cpu_freq; ++extern u32 ar71xx_ddr_freq; ++extern u32 ar71xx_ref_freq; + -+ if (info->mtd == NULL) -+ return 0; ++enum ar71xx_soc_type { ++ AR71XX_SOC_UNKNOWN, ++ AR71XX_SOC_AR7130, ++ AR71XX_SOC_AR7141, ++ AR71XX_SOC_AR7161, ++ AR71XX_SOC_AR7240, ++ AR71XX_SOC_AR7241, ++ AR71XX_SOC_AR7242, ++ AR71XX_SOC_AR9130, ++ AR71XX_SOC_AR9132, ++ AR71XX_SOC_AR9330, ++ AR71XX_SOC_AR9331, ++ AR71XX_SOC_AR9341, ++ AR71XX_SOC_AR9342, ++ AR71XX_SOC_AR9344, ++}; ++extern u32 ar71xx_soc_rev; + -+ pdata = pdev->dev.platform_data; -+#ifdef CONFIG_MTD_PARTITIONS -+ if (info->nr_parts) { -+ del_mtd_partitions(info->mtd); -+ kfree(info->parts); -+ } else if (pdata->nr_parts) { -+ del_mtd_partitions(info->mtd); -+ } else { -+ del_mtd_device(info->mtd); -+ } -+#else -+ del_mtd_device(info->mtd); -+#endif -+ map_destroy(info->mtd); ++extern enum ar71xx_soc_type ar71xx_soc; + -+ return 0; -+} ++/* ++ * PLL block ++ */ ++#define AR71XX_PLL_REG_CPU_CONFIG 0x00 ++#define AR71XX_PLL_REG_SEC_CONFIG 0x04 ++#define AR71XX_PLL_REG_ETH0_INT_CLOCK 0x10 ++#define AR71XX_PLL_REG_ETH1_INT_CLOCK 0x14 + -+static const char *rom_probe_types[] = { "cfi_probe", "jedec_probe", NULL }; -+#ifdef CONFIG_MTD_PARTITIONS -+static const char *part_probe_types[] = { "cmdlinepart", "RedBoot", NULL }; -+#endif ++#define AR71XX_PLL_DIV_SHIFT 3 ++#define AR71XX_PLL_DIV_MASK 0x1f ++#define AR71XX_CPU_DIV_SHIFT 16 ++#define AR71XX_CPU_DIV_MASK 0x3 ++#define AR71XX_DDR_DIV_SHIFT 18 ++#define AR71XX_DDR_DIV_MASK 0x3 ++#define AR71XX_AHB_DIV_SHIFT 20 ++#define AR71XX_AHB_DIV_MASK 0x7 + -+static int ar91xx_flash_probe(struct platform_device *pdev) -+{ -+ struct ar91xx_flash_platform_data *pdata; -+ struct ar91xx_flash_info *info; -+ struct resource *res; -+ struct resource *region; -+ const char **probe_type; -+ int err = 0; ++#define AR71XX_ETH0_PLL_SHIFT 17 ++#define AR71XX_ETH1_PLL_SHIFT 19 + -+ pdata = pdev->dev.platform_data; -+ if (pdata == NULL) -+ return -EINVAL; ++#define AR724X_PLL_REG_CPU_CONFIG 0x00 ++#define AR724X_PLL_REG_PCIE_CONFIG 0x18 + -+ info = devm_kzalloc(&pdev->dev, sizeof(struct ar91xx_flash_info), -+ GFP_KERNEL); -+ if (info == NULL) { -+ err = -ENOMEM; -+ goto err_out; -+ } ++#define AR724X_PLL_DIV_SHIFT 0 ++#define AR724X_PLL_DIV_MASK 0x3ff ++#define AR724X_PLL_REF_DIV_SHIFT 10 ++#define AR724X_PLL_REF_DIV_MASK 0xf ++#define AR724X_AHB_DIV_SHIFT 19 ++#define AR724X_AHB_DIV_MASK 0x1 ++#define AR724X_DDR_DIV_SHIFT 22 ++#define AR724X_DDR_DIV_MASK 0x3 + -+ platform_set_drvdata(pdev, info); ++#define AR7242_PLL_REG_ETH0_INT_CLOCK 0x2c + -+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (res == NULL) { -+ err = -ENOENT; -+ goto err_out; -+ } ++#define AR91XX_PLL_REG_CPU_CONFIG 0x00 ++#define AR91XX_PLL_REG_ETH_CONFIG 0x04 ++#define AR91XX_PLL_REG_ETH0_INT_CLOCK 0x14 ++#define AR91XX_PLL_REG_ETH1_INT_CLOCK 0x18 + -+ dev_info(&pdev->dev, "%.8llx at %.8llx\n", -+ (unsigned long long)(res->end - res->start + 1), -+ (unsigned long long)res->start); ++#define AR91XX_PLL_DIV_SHIFT 0 ++#define AR91XX_PLL_DIV_MASK 0x3ff ++#define AR91XX_DDR_DIV_SHIFT 22 ++#define AR91XX_DDR_DIV_MASK 0x3 ++#define AR91XX_AHB_DIV_SHIFT 19 ++#define AR91XX_AHB_DIV_MASK 0x1 + -+ region = devm_request_mem_region(&pdev->dev, -+ res->start, res->end - res->start + 1, -+ dev_name(&pdev->dev)); -+ if (region == NULL) { -+ dev_err(&pdev->dev, "could not reserve memory region\n"); -+ err = -ENOMEM; -+ goto err_out; -+ } ++#define AR91XX_ETH0_PLL_SHIFT 20 ++#define AR91XX_ETH1_PLL_SHIFT 22 + -+ info->map.name = dev_name(&pdev->dev); -+ info->map.phys = res->start; -+ info->map.size = res->end - res->start + 1; -+ info->map.bankwidth = pdata->width; ++#define AR933X_PLL_CPU_CONFIG_REG 0x00 ++#define AR933X_PLL_CLOCK_CTRL_REG 0x08 + -+ info->map.virt = devm_ioremap(&pdev->dev, info->map.phys, -+ info->map.size); -+ if (info->map.virt == NULL) { -+ dev_err(&pdev->dev, "failed to ioremap flash region\n"); -+ err = -EIO; -+ goto err_out; -+ } ++#define AR933X_PLL_CPU_CONFIG_NINT_SHIFT 10 ++#define AR933X_PLL_CPU_CONFIG_NINT_MASK 0x3f ++#define AR933X_PLL_CPU_CONFIG_REFDIV_SHIFT 16 ++#define AR933X_PLL_CPU_CONFIG_REFDIV_MASK 0x1f ++#define AR933X_PLL_CPU_CONFIG_OUTDIV_SHIFT 23 ++#define AR933X_PLL_CPU_CONFIG_OUTDIV_MASK 0x7 + -+ simple_map_init(&info->map); -+ if (pdata->is_shared) { -+ info->map.read = ar91xx_flash_read_lock; -+ info->map.write = ar91xx_flash_write_lock; -+ info->map.copy_from = ar91xx_flash_copy_from_lock; -+ info->map.copy_to = ar91xx_flash_copy_to_lock; -+ } else { -+ info->map.read = ar91xx_flash_read; -+ info->map.write = ar91xx_flash_write; -+ } ++#define AR933X_PLL_CLOCK_CTRL_BYPASS BIT(2) ++#define AR933X_PLL_CLOCK_CTRL_CPU_DIV_SHIFT 5 ++#define AR933X_PLL_CLOCK_CTRL_CPU_DIV_MASK 0x3 ++#define AR933X_PLL_CLOCK_CTRL_DDR_DIV_SHIFT 10 ++#define AR933X_PLL_CLOCK_CTRL_DDR_DIV_MASK 0x3 ++#define AR933X_PLL_CLOCK_CTRL_AHB_DIV_SHIFT 15 ++#define AR933X_PLL_CLOCK_CTRL_AHB_DIV_MASK 0x7 + -+ probe_type = rom_probe_types; -+ for (; info->mtd == NULL && *probe_type != NULL; probe_type++) -+ info->mtd = do_map_probe(*probe_type, &info->map); ++#define AR934X_PLL_REG_CPU_CONFIG 0x00 ++#define AR934X_PLL_REG_DDR_CTRL_CLOCK 0x8 + -+ if (info->mtd == NULL) { -+ dev_err(&pdev->dev, "map_probe failed\n"); -+ err = -ENXIO; -+ goto err_out; -+ } ++#define AR934X_CPU_PLL_CFG_OUTDIV_MSB 21 ++#define AR934X_CPU_PLL_CFG_OUTDIV_LSB 19 ++#define AR934X_CPU_PLL_CFG_OUTDIV_MASK 0x00380000 + -+ info->mtd->owner = THIS_MODULE; ++#define AR934X_CPU_PLL_CFG_OUTDIV_GET(x) \ ++ (((x) & AR934X_CPU_PLL_CFG_OUTDIV_MASK) >> \ ++ AR934X_CPU_PLL_CFG_OUTDIV_LSB) + -+#ifdef CONFIG_MTD_PARTITIONS -+ if (pdata->nr_parts) { -+ dev_info(&pdev->dev, "using static partition mapping\n"); -+ add_mtd_partitions(info->mtd, pdata->parts, pdata->nr_parts); -+ return 0; -+ } ++#define AR934X_DDR_PLL_CFG_OUTDIV_MSB 25 ++#define AR934X_DDR_PLL_CFG_OUTDIV_LSB 23 ++#define AR934X_DDR_PLL_CFG_OUTDIV_MASK 0x03800000 + -+ err = parse_mtd_partitions(info->mtd, part_probe_types, -+ &info->parts, 0); -+ if (err > 0) { -+ add_mtd_partitions(info->mtd, info->parts, err); -+ return 0; -+ } -+#endif ++#define AR934X_DDR_PLL_CFG_OUTDIV_GET(x) \ ++ (((x) & AR934X_DDR_PLL_CFG_OUTDIV_MASK) >> \ ++ AR934X_DDR_PLL_CFG_OUTDIV_LSB) + -+ add_mtd_device(info->mtd); -+ return 0; ++#define AR934X_DDR_PLL_CFG_OUTDIV_SET(x) \ ++ (((x) << AR934X_DDR_PLL_CFG_OUTDIV_LSB) & \ ++ AR934X_DDR_PLL_CFG_OUTDIV_MASK) + -+ err_out: -+ ar91xx_flash_remove(pdev); -+ return err; -+} ++#define AR934X_CPU_PLL_CFG_REFDIV_MSB 16 ++#define AR934X_CPU_PLL_CFG_REFDIV_LSB 12 ++#define AR934X_CPU_PLL_CFG_REFDIV_MASK 0x0001f000 + -+#ifdef CONFIG_PM -+static int ar91xx_flash_suspend(struct platform_device *dev, pm_message_t state) -+{ -+ struct ar91xx_flash_info *info = platform_get_drvdata(dev); -+ int ret = 0; ++#define AR934X_CPU_PLL_CFG_REFDIV_GET(x) \ ++ (((x) & AR934X_CPU_PLL_CFG_REFDIV_MASK) >> \ ++ AR934X_CPU_PLL_CFG_REFDIV_LSB) + -+ if (info->mtd->suspend) -+ ret = info->mtd->suspend(info->mtd); ++#define AR934X_CPU_PLL_CFG_REFDIV_SET(x) \ ++ (((x) << AR934X_CPU_PLL_CFG_REFDIV_LSB) & \ ++ AR934X_CPU_PLL_CFG_REFDIV_MASK) + -+ if (ret) -+ goto fail; ++#define AR934X_CPU_PLL_CFG_REFDIV_RESET 2 + -+ return 0; ++#define AR934X_CPU_PLL_CFG_NINT_MSB 11 ++#define AR934X_CPU_PLL_CFG_NINT_LSB 6 ++#define AR934X_CPU_PLL_CFG_NINT_MASK 0x00000fc0 + -+ fail: -+ if (info->mtd->suspend) { -+ BUG_ON(!info->mtd->resume); -+ info->mtd->resume(info->mtd); -+ } ++#define AR934X_CPU_PLL_CFG_NINT_GET(x) \ ++ (((x) & AR934X_CPU_PLL_CFG_NINT_MASK) >> \ ++ AR934X_CPU_PLL_CFG_NINT_LSB) + -+ return ret; -+} ++#define AR934X_CPU_PLL_CFG_NINT_SET(x) \ ++ (((x) << AR934X_CPU_PLL_CFG_NINT_LSB) & \ ++ AR934X_CPU_PLL_CFG_NINT_MASK) + -+static int ar91xx_flash_resume(struct platform_device *pdev) -+{ -+ struct ar91xx_flash_info *info = platform_get_drvdata(pdev); ++#define AR934X_CPU_PLL_CFG_NINT_RESET 20 + -+ if (info->mtd->resume) -+ info->mtd->resume(info->mtd); ++#define AR934X_CPU_PLL_CFG_NFRAC_MSB 5 ++#define AR934X_CPU_PLL_CFG_NFRAC_LSB 0 ++#define AR934X_CPU_PLL_CFG_NFRAC_MASK 0x0000003f + -+ return 0; -+} ++#define AR934X_CPU_PLL_CFG_NFRAC_GET(x) \ ++ (((x) & AR934X_CPU_PLL_CFG_NFRAC_MASK) >> \ ++ AR934X_CPU_PLL_CFG_NFRAC_LSB) + -+static void ar91xx_flash_shutdown(struct platform_device *pdev) -+{ -+ struct ar91xx_flash_info *info = platform_get_drvdata(pdev); ++#define AR934X_CPU_PLL_CFG_NFRAC_SET(x) \ ++ (((x) << AR934X_CPU_PLL_CFG_NFRAC_LSB) & \ ++ AR934X_CPU_PLL_CFG_NFRAC_MASK) + -+ if (info->mtd->suspend && info->mtd->resume) -+ if (info->mtd->suspend(info->mtd) == 0) -+ info->mtd->resume(info->mtd); -+} -+#else -+#define ar91xx_flash_suspend NULL -+#define ar91xx_flash_resume NULL -+#define ar91xx_flash_shutdown NULL -+#endif ++#define AR934X_DDR_PLL_CFG_REFDIV_MSB 20 ++#define AR934X_DDR_PLL_CFG_REFDIV_LSB 16 ++#define AR934X_DDR_PLL_CFG_REFDIV_MASK 0x001f0000 + -+static struct platform_driver ar91xx_flash_driver = { -+ .probe = ar91xx_flash_probe, -+ .remove = ar91xx_flash_remove, -+ .suspend = ar91xx_flash_suspend, -+ .resume = ar91xx_flash_resume, -+ .shutdown = ar91xx_flash_shutdown, -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++#define AR934X_DDR_PLL_CFG_REFDIV_GET(x) \ ++ (((x) & AR934X_DDR_PLL_CFG_REFDIV_MASK) >> \ ++ AR934X_DDR_PLL_CFG_REFDIV_LSB) + -+static int __init ar91xx_flash_init(void) -+{ -+ return platform_driver_register(&ar91xx_flash_driver); -+} ++#define AR934X_DDR_PLL_CFG_REFDIV_SET(x) \ ++ (((x) << AR934X_DDR_PLL_CFG_REFDIV_LSB) & \ ++ AR934X_DDR_PLL_CFG_REFDIV_MASK) + -+static void __exit ar91xx_flash_exit(void) -+{ -+ platform_driver_unregister(&ar91xx_flash_driver); -+} ++#define AR934X_DDR_PLL_CFG_REFDIV_RESET 2 + -+module_init(ar91xx_flash_init); -+module_exit(ar91xx_flash_exit); ++#define AR934X_DDR_PLL_CFG_NINT_MSB 15 ++#define AR934X_DDR_PLL_CFG_NINT_LSB 10 ++#define AR934X_DDR_PLL_CFG_NINT_MASK 0x0000fc00 + -+MODULE_LICENSE("GPL v2"); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_DESCRIPTION("Parallel flash driver for the Atheros AR91xx SoC"); -+MODULE_ALIAS("platform:" DRV_NAME); -diff -Nur linux-2.6.39.orig/drivers/mtd/nand/Kconfig linux-2.6.39/drivers/mtd/nand/Kconfig ---- linux-2.6.39.orig/drivers/mtd/nand/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/mtd/nand/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -531,4 +531,8 @@ - Enables support for NAND Flash chips on the ST Microelectronics - Flexible Static Memory Controller (FSMC) - -+config MTD_NAND_RB4XX -+ tristate "NAND flash driver for RouterBoard 4xx series" -+ depends on MTD_NAND && AR71XX_MACH_RB4XX ++#define AR934X_DDR_PLL_CFG_NINT_GET(x) \ ++ (((x) & AR934X_DDR_PLL_CFG_NINT_MASK) >> \ ++ AR934X_DDR_PLL_CFG_NINT_LSB) + - endif # MTD_NAND -diff -Nur linux-2.6.39.orig/drivers/mtd/nand/Makefile linux-2.6.39/drivers/mtd/nand/Makefile ---- linux-2.6.39.orig/drivers/mtd/nand/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/mtd/nand/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -34,6 +34,7 @@ - obj-$(CONFIG_MTD_NAND_PXA3xx) += pxa3xx_nand.o - obj-$(CONFIG_MTD_NAND_TMIO) += tmio_nand.o - obj-$(CONFIG_MTD_NAND_PLATFORM) += plat_nand.o -+obj-$(CONFIG_MTD_NAND_RB4XX) += rb4xx_nand.o - obj-$(CONFIG_MTD_ALAUDA) += alauda.o - obj-$(CONFIG_MTD_NAND_PASEMI) += pasemi_nand.o - obj-$(CONFIG_MTD_NAND_ORION) += orion_nand.o -diff -Nur linux-2.6.39.orig/drivers/mtd/nand/rb4xx_nand.c linux-2.6.39/drivers/mtd/nand/rb4xx_nand.c ---- linux-2.6.39.orig/drivers/mtd/nand/rb4xx_nand.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/mtd/nand/rb4xx_nand.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,513 @@ -+/* -+ * NAND flash driver for the MikroTik RouterBoard 4xx series -+ * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This file was based on the driver for Linux 2.6.22 published by -+ * MikroTik for their RouterBoard 4xx series devices. -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++#define AR934X_DDR_PLL_CFG_NINT_SET(x) \ ++ (((x) << AR934X_DDR_PLL_CFG_NINT_LSB) & \ ++ AR934X_DDR_PLL_CFG_NINT_MASK) + -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include ++#define AR934X_DDR_PLL_CFG_NINT_RESET 20 + -+#include ++#define AR934X_DDR_PLL_CFG_NFRAC_MSB 9 ++#define AR934X_DDR_PLL_CFG_NFRAC_LSB 0 ++#define AR934X_DDR_PLL_CFG_NFRAC_MASK 0x000003ff + -+#define DRV_NAME "rb4xx-nand" -+#define DRV_VERSION "0.1.10" -+#define DRV_DESC "NAND flash driver for RouterBoard 4xx series" ++#define AR934X_DDR_PLL_CFG_NFRAC_GET(x) \ ++ (((x) & AR934X_DDR_PLL_CFG_NFRAC_MASK) >> \ ++ AR934X_DDR_PLL_CFG_NFRAC_LSB) + -+#define USE_FAST_READ 1 -+#define USE_FAST_WRITE 1 -+#undef RB4XX_NAND_DEBUG ++#define AR934X_DDR_PLL_CFG_NFRAC_SET(x) \ ++ (((x) << AR934X_DDR_PLL_CFG_NFRAC_LSB) & \ ++ AR934X_DDR_PLL_CFG_NFRAC_MASK) + -+#ifdef RB4XX_NAND_DEBUG -+#define DBG(fmt, arg...) printk(KERN_DEBUG DRV_NAME ": " fmt, ## arg) -+#else -+#define DBG(fmt, arg...) do {} while (0) -+#endif ++#define AR934X_DDR_PLL_CFG_NFRAC_RESET 512 + -+#define RB4XX_NAND_GPIO_RDY 5 -+#define RB4XX_FLASH_HZ 33333334 -+#define RB4XX_NAND_HZ 33333334 ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_MSB 19 ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_LSB 15 ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_MASK 0x000f8000 + -+#define SPI_CTRL_FASTEST 0x40 -+#define SPI_CTRL_SAFE 0x43 /* 25 MHz for AHB 200 MHz */ -+#define SBIT_IOC_BASE SPI_IOC_CS1 -+#define SBIT_IOC_DO_SHIFT 0 -+#define SBIT_IOC_DO (1u << SBIT_IOC_DO_SHIFT) -+#define SBIT_IOC_DO2_SHIFT 18 -+#define SBIT_IOC_DO2 (1u << SBIT_IOC_DO2_SHIFT) -+ -+#define CPLD_CMD_WRITE_MULT 0x08 /* send cmd, n x send data, read data */ -+#define CPLD_CMD_WRITE_CFG 0x09 /* send cmd, n x send cfg */ -+#define CPLD_CMD_READ_MULT 0x0a /* send cmd, send idle, n x read data */ -+#define CPLD_CMD_READ_FAST 0x0b /* send cmd, 4 x idle, n x read data */ -+ -+#define CFG_BIT_nCE 0x80 -+#define CFG_BIT_CLE 0x40 -+#define CFG_BIT_ALE 0x20 -+#define CFG_BIT_FAN 0x10 -+#define CFG_BIT_nLED4 0x08 -+#define CFG_BIT_nLED3 0x04 -+#define CFG_BIT_nLED2 0x02 -+#define CFG_BIT_nLED1 0x01 -+ -+#define CFG_BIT_nLEDS \ -+ (CFG_BIT_nLED1 | CFG_BIT_nLED2 | CFG_BIT_nLED3 | CFG_BIT_nLED4) ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_GET(x) \ ++ (((x) & AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_MASK) >> \ ++ AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_LSB) + -+struct rb4xx_nand_info { -+ struct nand_chip chip; -+ struct mtd_info mtd; -+}; ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_SET(x) \ ++ (((x) << AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_LSB) & \ ++ AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_MASK) + -+/* -+ * We need to use the OLD Yaffs-1 OOB layout, otherwise the RB bootloader -+ * will not be able to find the kernel that we load. -+ */ -+static struct nand_ecclayout rb4xx_nand_ecclayout = { -+ .eccbytes = 6, -+ .eccpos = { 8, 9, 10, 13, 14, 15 }, -+ .oobavail = 9, -+ .oobfree = { { 0, 4 }, { 6, 2 }, { 11, 2 }, { 4, 1 } } -+}; ++#define AR934X_CPU_DDR_CLK_CTRL_AHB_POST_DIV_RESET 0 + -+static struct mtd_partition rb4xx_nand_partitions[] = { -+ { -+ .name = "booter", -+ .offset = 0, -+ .size = (256 * 1024), -+ .mask_flags = MTD_WRITEABLE, -+ }, -+ { -+ .name = "kernel", -+ .offset = (256 * 1024), -+ .size = (4 * 1024 * 1024) - (256 * 1024), -+ }, -+ { -+ .name = "rootfs", -+ .offset = MTDPART_OFS_NXTBLK, -+ .size = (1024*1024*64) - (1024*256) - (4 * 1024 * 1024) -+ }, -+ { -+ .name = "cfgfs", -+ .offset = (1024*1024*64) - (1024*256), -+ .size = (1024*256), -+ }, -+}; ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_MSB 14 ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_LSB 10 ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_MASK 0x00007c00 + -+#if USE_FAST_READ -+#define SPI_NDATA_BASE 0x00800000 -+static unsigned spi_ctrl_fread = SPI_CTRL_SAFE; -+static unsigned spi_ctrl_flash = SPI_CTRL_SAFE; -+extern unsigned mips_hpt_frequency; -+#endif ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_GET(x) \ ++ (((x) & AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_MASK) >> \ ++ AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_LSB) + -+static inline unsigned rb4xx_spi_rreg(unsigned r) -+{ -+ return __raw_readl((void * __iomem)(KSEG1ADDR(AR71XX_SPI_BASE) + r)); -+} ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_SET(x) \ ++ (((x) << AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_LSB) & \ ++ AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_MASK) + -+static inline void rb4xx_spi_wreg(unsigned r, unsigned v) -+{ -+ __raw_writel(v, (void * __iomem)(KSEG1ADDR(AR71XX_SPI_BASE) + r)); -+} ++#define AR934X_CPU_DDR_CLK_CTRL_DDR_POST_DIV_RESET 0 + -+static inline void do_spi_clk(int bit) -+{ -+ unsigned bval = SBIT_IOC_BASE | (bit & 1); ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_MSB 9 ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_LSB 5 ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_MASK 0x000003e0 + -+ rb4xx_spi_wreg(SPI_REG_IOC, bval); -+ rb4xx_spi_wreg(SPI_REG_IOC, bval | SPI_IOC_CLK); -+} ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_GET(x) \ ++ (((x) & AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_MASK) >> \ ++ AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_LSB) + -+static void do_spi_byte(uint8_t byte) -+{ -+ do_spi_clk(byte >> 7); -+ do_spi_clk(byte >> 6); -+ do_spi_clk(byte >> 5); -+ do_spi_clk(byte >> 4); -+ do_spi_clk(byte >> 3); -+ do_spi_clk(byte >> 2); -+ do_spi_clk(byte >> 1); -+ do_spi_clk(byte); ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_SET(x) \ ++ (((x) << AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_LSB) & \ ++ AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_MASK) + -+ DBG("spi_byte sent 0x%02x got 0x%x\n", -+ byte, rb4xx_spi_rreg(SPI_REG_RDS)); -+} ++#define AR934X_CPU_DDR_CLK_CTRL_CPU_POST_DIV_RESET 0 + -+#if USE_FAST_WRITE -+static inline void do_spi_clk_fast(int bit1, int bit2) -+{ -+ unsigned bval = (SBIT_IOC_BASE | -+ ((bit1 << SBIT_IOC_DO_SHIFT) & SBIT_IOC_DO) | -+ ((bit2 << SBIT_IOC_DO2_SHIFT) & SBIT_IOC_DO2)); ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_MSB 24 ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_LSB 24 ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_MASK 0x01000000 + -+ rb4xx_spi_wreg(SPI_REG_IOC, bval); -+ rb4xx_spi_wreg(SPI_REG_IOC, bval | SPI_IOC_CLK); -+} ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_GET(x) \ ++ (((x) & AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_MASK) >> \ ++ AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_LSB) + -+static inline void do_spi_byte_fast(uint8_t byte) -+{ -+ do_spi_clk_fast(byte >> 7, byte >> 6); -+ do_spi_clk_fast(byte >> 5, byte >> 4); -+ do_spi_clk_fast(byte >> 3, byte >> 2); -+ do_spi_clk_fast(byte >> 1, byte >> 0); ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_SET(x) \ ++ (((x) << AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_LSB) & \ ++ AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_MASK) + -+ DBG("spi_byte_fast sent 0x%02x got 0x%x\n", -+ byte, rb4xx_spi_rreg(SPI_REG_RDS)); -+} -+#else -+static inline void do_spi_byte_fast(uint8_t byte) ++#define AR934X_CPU_DDR_CLK_CTRL_AHBCLK_FROM_DDRPLL_RESET 1 ++ ++extern void __iomem *ar71xx_pll_base; ++ ++static inline void ar71xx_pll_wr(unsigned reg, u32 val) +{ -+ do_spi_byte(byte); ++ __raw_writel(val, ar71xx_pll_base + reg); +} -+#endif /* USE_FAST_WRITE */ + -+static int do_spi_cmd(unsigned cmd, unsigned sendCnt, const uint8_t *sendData, -+ unsigned recvCnt, uint8_t *recvData, -+ const uint8_t *verifyData, int fastWrite) ++static inline u32 ar71xx_pll_rr(unsigned reg) +{ -+ unsigned i; -+ -+ DBG("SPI cmd 0x%x send %u recv %u\n", cmd, sendCnt, recvCnt); -+ -+ rb4xx_spi_wreg(SPI_REG_FS, SPI_FS_GPIO); -+ rb4xx_spi_wreg(SPI_REG_CTRL, SPI_CTRL_FASTEST); ++ return __raw_readl(ar71xx_pll_base + reg); ++} + -+ do_spi_byte(cmd); -+#if 0 -+ if (cmd == CPLD_CMD_READ_FAST) { -+ do_spi_byte(0x80); -+ do_spi_byte(0); -+ do_spi_byte(0); -+ } -+#endif -+ for (i = 0; i < sendCnt; ++i) { -+ if (fastWrite) -+ do_spi_byte_fast(sendData[i]); -+ else -+ do_spi_byte(sendData[i]); -+ } -+ -+ for (i = 0; i < recvCnt; ++i) { -+ if (fastWrite) -+ do_spi_byte_fast(0); -+ else -+ do_spi_byte(0); -+ -+ if (recvData) { -+ recvData[i] = rb4xx_spi_rreg(SPI_REG_RDS) & 0xff; -+ } else if (verifyData) { -+ if (verifyData[i] != (rb4xx_spi_rreg(SPI_REG_RDS) -+ & 0xff)) -+ break; -+ } -+ } -+ -+ rb4xx_spi_wreg(SPI_REG_IOC, SBIT_IOC_BASE | SPI_IOC_CS0); -+ rb4xx_spi_wreg(SPI_REG_CTRL, spi_ctrl_flash); -+ rb4xx_spi_wreg(SPI_REG_FS, 0); -+ -+ return i == recvCnt; -+} ++/* ++ * USB_CONFIG block ++ */ ++#define USB_CTRL_REG_FLADJ 0x00 ++#define USB_CTRL_REG_CONFIG 0x04 + -+static int got_write = 1; ++extern void __iomem *ar71xx_usb_ctrl_base; + -+static void rb4xx_nand_write_data(const uint8_t *byte, unsigned cnt) ++static inline void ar71xx_usb_ctrl_wr(unsigned reg, u32 val) +{ -+ do_spi_cmd(CPLD_CMD_WRITE_MULT, cnt, byte, 1, NULL, NULL, 1); -+ got_write = 1; ++ __raw_writel(val, ar71xx_usb_ctrl_base + reg); +} + -+static void rb4xx_nand_write_byte(uint8_t byte) ++static inline u32 ar71xx_usb_ctrl_rr(unsigned reg) +{ -+ rb4xx_nand_write_data(&byte, 1); ++ return __raw_readl(ar71xx_usb_ctrl_base + reg); +} + -+#if USE_FAST_READ -+static uint8_t *rb4xx_nand_read_getaddr(unsigned cnt) -+{ -+ static unsigned nboffset = 0x100000; -+ unsigned addr; ++/* ++ * GPIO block ++ */ ++#define GPIO_REG_OE 0x00 ++#define GPIO_REG_IN 0x04 ++#define GPIO_REG_OUT 0x08 ++#define GPIO_REG_SET 0x0c ++#define GPIO_REG_CLEAR 0x10 ++#define GPIO_REG_INT_MODE 0x14 ++#define GPIO_REG_INT_TYPE 0x18 ++#define GPIO_REG_INT_POLARITY 0x1c ++#define GPIO_REG_INT_PENDING 0x20 ++#define GPIO_REG_INT_ENABLE 0x24 ++#define GPIO_REG_FUNC 0x28 + -+ if (got_write) { -+ nboffset = (nboffset + 31) & ~31; -+ if (nboffset >= 0x100000) /* 1MB */ -+ nboffset = 0; ++#define AR71XX_GPIO_FUNC_STEREO_EN BIT(17) ++#define AR71XX_GPIO_FUNC_SLIC_EN BIT(16) ++#define AR71XX_GPIO_FUNC_SPI_CS2_EN BIT(13) ++#define AR71XX_GPIO_FUNC_SPI_CS1_EN BIT(12) ++#define AR71XX_GPIO_FUNC_UART_EN BIT(8) ++#define AR71XX_GPIO_FUNC_USB_OC_EN BIT(4) ++#define AR71XX_GPIO_FUNC_USB_CLK_EN BIT(0) + -+ got_write = 0; -+ rb4xx_spi_wreg(SPI_REG_FS, SPI_FS_GPIO); -+ rb4xx_spi_wreg(SPI_REG_CTRL, spi_ctrl_fread); -+ rb4xx_spi_wreg(SPI_REG_FS, 0); -+ } ++#define AR71XX_GPIO_COUNT 16 + -+ addr = KSEG1ADDR(AR71XX_SPI_BASE + SPI_NDATA_BASE) + nboffset; -+ DBG("rb4xx_nand_read_getaddr 0x%x cnt 0x%x\n", addr, cnt); ++#define AR724X_GPIO_FUNC_GE0_MII_CLK_EN BIT(19) ++#define AR724X_GPIO_FUNC_SPI_EN BIT(18) ++#define AR724X_GPIO_FUNC_SPI_CS_EN2 BIT(14) ++#define AR724X_GPIO_FUNC_SPI_CS_EN1 BIT(13) ++#define AR724X_GPIO_FUNC_CLK_OBS5_EN BIT(12) ++#define AR724X_GPIO_FUNC_CLK_OBS4_EN BIT(11) ++#define AR724X_GPIO_FUNC_CLK_OBS3_EN BIT(10) ++#define AR724X_GPIO_FUNC_CLK_OBS2_EN BIT(9) ++#define AR724X_GPIO_FUNC_CLK_OBS1_EN BIT(8) ++#define AR724X_GPIO_FUNC_ETH_SWITCH_LED4_EN BIT(7) ++#define AR724X_GPIO_FUNC_ETH_SWITCH_LED3_EN BIT(6) ++#define AR724X_GPIO_FUNC_ETH_SWITCH_LED2_EN BIT(5) ++#define AR724X_GPIO_FUNC_ETH_SWITCH_LED1_EN BIT(4) ++#define AR724X_GPIO_FUNC_ETH_SWITCH_LED0_EN BIT(3) ++#define AR724X_GPIO_FUNC_UART_RTS_CTS_EN BIT(2) ++#define AR724X_GPIO_FUNC_UART_EN BIT(1) ++#define AR724X_GPIO_FUNC_JTAG_DISABLE BIT(0) + -+ nboffset += cnt; -+ return (uint8_t *)addr; -+} ++#define AR724X_GPIO_COUNT 18 + -+static void rb4xx_nand_read_data(uint8_t *buf, unsigned cnt) -+{ -+ unsigned size32 = cnt & ~31; -+ unsigned remain = cnt & 31; ++#define AR91XX_GPIO_FUNC_WMAC_LED_EN BIT(22) ++#define AR91XX_GPIO_FUNC_EXP_PORT_CS_EN BIT(21) ++#define AR91XX_GPIO_FUNC_I2S_REFCLKEN BIT(20) ++#define AR91XX_GPIO_FUNC_I2S_MCKEN BIT(19) ++#define AR91XX_GPIO_FUNC_I2S1_EN BIT(18) ++#define AR91XX_GPIO_FUNC_I2S0_EN BIT(17) ++#define AR91XX_GPIO_FUNC_SLIC_EN BIT(16) ++#define AR91XX_GPIO_FUNC_UART_RTSCTS_EN BIT(9) ++#define AR91XX_GPIO_FUNC_UART_EN BIT(8) ++#define AR91XX_GPIO_FUNC_USB_CLK_EN BIT(4) + -+ if (size32) { -+ uint8_t *addr = rb4xx_nand_read_getaddr(size32); -+ memcpy(buf, (void *)addr, size32); -+ } ++#define AR91XX_GPIO_COUNT 22 + -+ if (remain) { -+ do_spi_cmd(CPLD_CMD_READ_MULT, 1, buf, remain, -+ buf + size32, NULL, 0); -+ } -+} ++#define AR933X_GPIO_COUNT 30 + -+static int rb4xx_nand_verify_data(const uint8_t *buf, unsigned cnt) -+{ -+ unsigned size32 = cnt & ~31; -+ unsigned remain = cnt & 31; ++#define AR934X_GPIO_FUNC_SPI_CS_1_EN BIT(14) ++#define AR934X_GPIO_FUNC_SPI_CS_0_EN BIT(13) + -+ if (size32) { -+ uint8_t *addr = rb4xx_nand_read_getaddr(size32); -+ if (memcmp(buf, (void *)addr, size32) != 0) -+ return 0; -+ } ++#define AR934X_GPIO_COUNT 32 ++#define AR934X_GPIO_FUNC_DDR_DQOE_EN BIT(17) + -+ if (remain) { -+ return do_spi_cmd(CPLD_CMD_READ_MULT, 1, buf, remain, -+ NULL, buf + size32, 0); -+ } -+ return 1; -+} -+#else /* USE_FAST_READ */ -+static void rb4xx_nand_read_data(uint8_t *buf, unsigned cnt) -+{ -+ do_spi_cmd(CPLD_CMD_READ_MULT, 1, buf, cnt, buf, NULL, 0); -+} ++extern void __iomem *ar71xx_gpio_base; + -+static int rb4xx_nand_verify_data(const uint8_t *buf, unsigned cnt) ++static inline void ar71xx_gpio_wr(unsigned reg, u32 value) +{ -+ return do_spi_cmd(CPLD_CMD_READ_MULT, 1, buf, cnt, NULL, buf, 0); ++ __raw_writel(value, ar71xx_gpio_base + reg); +} -+#endif /* USE_FAST_READ */ + -+static void rb4xx_nand_write_cfg(uint8_t byte) ++static inline u32 ar71xx_gpio_rr(unsigned reg) +{ -+ do_spi_cmd(CPLD_CMD_WRITE_CFG, 1, &byte, 0, NULL, NULL, 0); -+ got_write = 1; ++ return __raw_readl(ar71xx_gpio_base + reg); +} + -+static int rb4xx_nand_dev_ready(struct mtd_info *mtd) -+{ -+ return gpio_get_value(RB4XX_NAND_GPIO_RDY); -+} ++void ar71xx_gpio_init(void) __init; ++void ar71xx_gpio_function_enable(u32 mask); ++void ar71xx_gpio_function_disable(u32 mask); ++void ar71xx_gpio_function_setup(u32 set, u32 clear); + -+static void rb4xx_nand_cmd_ctrl(struct mtd_info *mtd, int cmd, -+ unsigned int ctrl) -+{ -+ if (ctrl & NAND_CTRL_CHANGE) { -+ uint8_t cfg = CFG_BIT_nLEDS; ++/* ++ * DDR_CTRL block ++ */ ++#define AR71XX_DDR_REG_PCI_WIN0 0x7c ++#define AR71XX_DDR_REG_PCI_WIN1 0x80 ++#define AR71XX_DDR_REG_PCI_WIN2 0x84 ++#define AR71XX_DDR_REG_PCI_WIN3 0x88 ++#define AR71XX_DDR_REG_PCI_WIN4 0x8c ++#define AR71XX_DDR_REG_PCI_WIN5 0x90 ++#define AR71XX_DDR_REG_PCI_WIN6 0x94 ++#define AR71XX_DDR_REG_PCI_WIN7 0x98 ++#define AR71XX_DDR_REG_FLUSH_GE0 0x9c ++#define AR71XX_DDR_REG_FLUSH_GE1 0xa0 ++#define AR71XX_DDR_REG_FLUSH_USB 0xa4 ++#define AR71XX_DDR_REG_FLUSH_PCI 0xa8 + -+ cfg |= (ctrl & NAND_CLE) ? CFG_BIT_CLE : 0; -+ cfg |= (ctrl & NAND_ALE) ? CFG_BIT_ALE : 0; -+ cfg |= (ctrl & NAND_NCE) ? 0 : CFG_BIT_nCE; ++#define AR724X_DDR_REG_FLUSH_GE0 0x7c ++#define AR724X_DDR_REG_FLUSH_GE1 0x80 ++#define AR724X_DDR_REG_FLUSH_USB 0x84 ++#define AR724X_DDR_REG_FLUSH_PCIE 0x88 + -+ rb4xx_nand_write_cfg(cfg); -+ } ++#define AR91XX_DDR_REG_FLUSH_GE0 0x7c ++#define AR91XX_DDR_REG_FLUSH_GE1 0x80 ++#define AR91XX_DDR_REG_FLUSH_USB 0x84 ++#define AR91XX_DDR_REG_FLUSH_WMAC 0x88 + -+ if (cmd != NAND_CMD_NONE) -+ rb4xx_nand_write_byte(cmd); -+} ++#define AR933X_DDR_REG_FLUSH_GE0 0x7c ++#define AR933X_DDR_REG_FLUSH_GE1 0x80 ++#define AR933X_DDR_REG_FLUSH_USB 0x84 ++#define AR933X_DDR_REG_FLUSH_WMAC 0x88 + -+static uint8_t rb4xx_nand_read_byte(struct mtd_info *mtd) -+{ -+ uint8_t byte = 0; ++#define AR934X_DDR_REG_FLUSH_GE0 0x9c ++#define AR934X_DDR_REG_FLUSH_GE1 0xa0 ++#define AR934X_DDR_REG_FLUSH_USB 0xa4 ++#define AR934X_DDR_REG_FLUSH_PCIE 0xa8 + -+ rb4xx_nand_read_data(&byte, 1); -+ return byte; -+} + -+static void rb4xx_nand_write_buf(struct mtd_info *mtd, const uint8_t *buf, -+ int len) -+{ -+ rb4xx_nand_write_data(buf, len); -+} ++#define PCI_WIN0_OFFS 0x10000000 ++#define PCI_WIN1_OFFS 0x11000000 ++#define PCI_WIN2_OFFS 0x12000000 ++#define PCI_WIN3_OFFS 0x13000000 ++#define PCI_WIN4_OFFS 0x14000000 ++#define PCI_WIN5_OFFS 0x15000000 ++#define PCI_WIN6_OFFS 0x16000000 ++#define PCI_WIN7_OFFS 0x07000000 + -+static void rb4xx_nand_read_buf(struct mtd_info *mtd, uint8_t *buf, -+ int len) ++extern void __iomem *ar71xx_ddr_base; ++ ++static inline void ar71xx_ddr_wr(unsigned reg, u32 val) +{ -+ rb4xx_nand_read_data(buf, len); ++ __raw_writel(val, ar71xx_ddr_base + reg); +} + -+static int rb4xx_nand_verify_buf(struct mtd_info *mtd, const uint8_t *buf, -+ int len) ++static inline u32 ar71xx_ddr_rr(unsigned reg) +{ -+ if (!rb4xx_nand_verify_data(buf, len)) -+ return -EFAULT; -+ -+ return 0; ++ return __raw_readl(ar71xx_ddr_base + reg); +} + -+static unsigned get_spi_ctrl(unsigned hz_max, const char *name) -+{ -+ unsigned div; ++void ar71xx_ddr_flush(u32 reg); + -+ div = (ar71xx_ahb_freq - 1) / (2 * hz_max); -+ /* -+ * CPU has a bug at (div == 0) - first bit read is random -+ */ -+ if (div == 0) -+ ++div; ++/* ++ * PCI block ++ */ ++#define AR71XX_PCI_CFG_BASE (AR71XX_PCI_MEM_BASE + PCI_WIN7_OFFS + 0x10000) ++#define AR71XX_PCI_CFG_SIZE 0x100 + -+ if (name) { -+ unsigned ahb_khz = (ar71xx_ahb_freq + 500) / 1000; -+ unsigned div_real = 2 * (div + 1); -+ printk(KERN_INFO "%s SPI clock %u kHz (AHB %u kHz / %u)\n", -+ name, -+ ahb_khz / div_real, -+ ahb_khz, div_real); -+ } ++#define PCI_REG_CRP_AD_CBE 0x00 ++#define PCI_REG_CRP_WRDATA 0x04 ++#define PCI_REG_CRP_RDDATA 0x08 ++#define PCI_REG_CFG_AD 0x0c ++#define PCI_REG_CFG_CBE 0x10 ++#define PCI_REG_CFG_WRDATA 0x14 ++#define PCI_REG_CFG_RDDATA 0x18 ++#define PCI_REG_PCI_ERR 0x1c ++#define PCI_REG_PCI_ERR_ADDR 0x20 ++#define PCI_REG_AHB_ERR 0x24 ++#define PCI_REG_AHB_ERR_ADDR 0x28 + -+ return SPI_CTRL_FASTEST + div; -+} ++#define PCI_CRP_CMD_WRITE 0x00010000 ++#define PCI_CRP_CMD_READ 0x00000000 ++#define PCI_CFG_CMD_READ 0x0000000a ++#define PCI_CFG_CMD_WRITE 0x0000000b + -+static int __init rb4xx_nand_probe(struct platform_device *pdev) -+{ -+ struct rb4xx_nand_info *info; -+ int ret; ++#define PCI_IDSEL_ADL_START 17 + -+ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); ++#define AR724X_PCI_CFG_BASE (AR71XX_PCI_MEM_BASE + 0x4000000) ++#define AR724X_PCI_CFG_SIZE 0x1000 + -+ ret = gpio_request(RB4XX_NAND_GPIO_RDY, "NAND RDY"); -+ if (ret) { -+ printk(KERN_ERR "rb4xx-nand: gpio request failed\n"); -+ return ret; -+ } ++#define AR724X_PCI_REG_APP 0x00 ++#define AR724X_PCI_REG_RESET 0x18 ++#define AR724X_PCI_REG_INT_STATUS 0x4c ++#define AR724X_PCI_REG_INT_MASK 0x50 + -+ ret = gpio_direction_input(RB4XX_NAND_GPIO_RDY); -+ if (ret) { -+ printk(KERN_ERR "rb4xx-nand: unable to set input mode " -+ "on gpio%d\n", RB4XX_NAND_GPIO_RDY); -+ goto err_free_gpio; -+ } ++#define AR724X_PCI_APP_LTSSM_ENABLE BIT(0) ++#define AR724X_PCI_RESET_LINK_UP BIT(0) + -+ info = kzalloc(sizeof(*info), GFP_KERNEL); -+ if (!info) { -+ printk(KERN_ERR "rb4xx-nand: no memory for private data\n"); -+ ret = -ENOMEM; -+ goto err_free_gpio; -+ } ++#define AR724X_PCI_INT_DEV0 BIT(14) + -+#if USE_FAST_READ -+ spi_ctrl_fread = get_spi_ctrl(RB4XX_NAND_HZ, "NAND"); -+#endif -+ spi_ctrl_flash = get_spi_ctrl(RB4XX_FLASH_HZ, "FLASH"); ++/* ++ * RESET block ++ */ ++#define AR71XX_RESET_REG_TIMER 0x00 ++#define AR71XX_RESET_REG_TIMER_RELOAD 0x04 ++#define AR71XX_RESET_REG_WDOG_CTRL 0x08 ++#define AR71XX_RESET_REG_WDOG 0x0c ++#define AR71XX_RESET_REG_MISC_INT_STATUS 0x10 ++#define AR71XX_RESET_REG_MISC_INT_ENABLE 0x14 ++#define AR71XX_RESET_REG_PCI_INT_STATUS 0x18 ++#define AR71XX_RESET_REG_PCI_INT_ENABLE 0x1c ++#define AR71XX_RESET_REG_GLOBAL_INT_STATUS 0x20 ++#define AR71XX_RESET_REG_RESET_MODULE 0x24 ++#define AR71XX_RESET_REG_PERFC_CTRL 0x2c ++#define AR71XX_RESET_REG_PERFC0 0x30 ++#define AR71XX_RESET_REG_PERFC1 0x34 ++#define AR71XX_RESET_REG_REV_ID 0x90 + -+ rb4xx_nand_write_cfg(CFG_BIT_nLEDS | CFG_BIT_nCE); ++#define AR91XX_RESET_REG_GLOBAL_INT_STATUS 0x18 ++#define AR91XX_RESET_REG_RESET_MODULE 0x1c ++#define AR91XX_RESET_REG_PERF_CTRL 0x20 ++#define AR91XX_RESET_REG_PERFC0 0x24 ++#define AR91XX_RESET_REG_PERFC1 0x28 + -+ info->chip.priv = &info; -+ info->mtd.priv = &info->chip; -+ info->mtd.owner = THIS_MODULE; ++#define AR724X_RESET_REG_RESET_MODULE 0x1c + -+ info->chip.cmd_ctrl = rb4xx_nand_cmd_ctrl; -+ info->chip.dev_ready = rb4xx_nand_dev_ready; -+ info->chip.read_byte = rb4xx_nand_read_byte; -+ info->chip.write_buf = rb4xx_nand_write_buf; -+ info->chip.read_buf = rb4xx_nand_read_buf; -+ info->chip.verify_buf = rb4xx_nand_verify_buf; ++#define AR933X_RESET_REG_RESET_MODULE 0x1c ++#define AR933X_RESET_REG_BOOTSTRAP 0xac ++#define AR933X_BOOTSTRAP_EEPBUSY BIT(4) ++#define AR933X_BOOTSTRAP_REF_CLK_40 BIT(0) + -+ info->chip.chip_delay = 25; -+ info->chip.ecc.mode = NAND_ECC_SOFT; -+ info->chip.options |= NAND_NO_AUTOINCR; ++#define AR934X_RESET_REG_RESET_MODULE 0x1c ++#define AR934X_RESET_REG_BOOTSTRAP 0xb0 ++/* 0 - 25MHz 1 - 40 MHz */ ++#define AR934X_REF_CLK_40 (1 << 4) + -+ platform_set_drvdata(pdev, info); ++#define WDOG_CTRL_LAST_RESET BIT(31) ++#define WDOG_CTRL_ACTION_MASK 3 ++#define WDOG_CTRL_ACTION_NONE 0 /* no action */ ++#define WDOG_CTRL_ACTION_GPI 1 /* general purpose interrupt */ ++#define WDOG_CTRL_ACTION_NMI 2 /* NMI */ ++#define WDOG_CTRL_ACTION_FCR 3 /* full chip reset */ + -+ ret = nand_scan_ident(&info->mtd, 1, NULL); -+ if (ret) { -+ ret = -ENXIO; -+ goto err_free_info; -+ } ++#define MISC_INT_ENET_LINK BIT(12) ++#define MISC_INT_DDR_PERF BIT(11) ++#define MISC_INT_TIMER4 BIT(10) ++#define MISC_INT_TIMER3 BIT(9) ++#define MISC_INT_TIMER2 BIT(8) ++#define MISC_INT_DMA BIT(7) ++#define MISC_INT_OHCI BIT(6) ++#define MISC_INT_PERFC BIT(5) ++#define MISC_INT_WDOG BIT(4) ++#define MISC_INT_UART BIT(3) ++#define MISC_INT_GPIO BIT(2) ++#define MISC_INT_ERROR BIT(1) ++#define MISC_INT_TIMER BIT(0) + -+ if (info->mtd.writesize == 512) -+ info->chip.ecc.layout = &rb4xx_nand_ecclayout; ++#define PCI_INT_CORE BIT(4) ++#define PCI_INT_DEV2 BIT(2) ++#define PCI_INT_DEV1 BIT(1) ++#define PCI_INT_DEV0 BIT(0) + -+ ret = nand_scan_tail(&info->mtd); -+ if (ret) { -+ return -ENXIO; -+ goto err_set_drvdata; -+ } ++#define RESET_MODULE_EXTERNAL BIT(28) ++#define RESET_MODULE_FULL_CHIP BIT(24) ++#define RESET_MODULE_AMBA2WMAC BIT(22) ++#define RESET_MODULE_CPU_NMI BIT(21) ++#define RESET_MODULE_CPU_COLD BIT(20) ++#define RESET_MODULE_DMA BIT(19) ++#define RESET_MODULE_SLIC BIT(18) ++#define RESET_MODULE_STEREO BIT(17) ++#define RESET_MODULE_DDR BIT(16) ++#define RESET_MODULE_GE1_MAC BIT(13) ++#define RESET_MODULE_GE1_PHY BIT(12) ++#define RESET_MODULE_USBSUS_OVERRIDE BIT(10) ++#define RESET_MODULE_GE0_MAC BIT(9) ++#define RESET_MODULE_GE0_PHY BIT(8) ++#define RESET_MODULE_USB_OHCI_DLL BIT(6) ++#define RESET_MODULE_USB_HOST BIT(5) ++#define RESET_MODULE_USB_PHY BIT(4) ++#define RESET_MODULE_USB_OHCI_DLL_7240 BIT(3) ++#define RESET_MODULE_PCI_BUS BIT(1) ++#define RESET_MODULE_PCI_CORE BIT(0) + -+#ifdef CONFIG_MTD_PARTITIONS -+ ret = add_mtd_partitions(&info->mtd, rb4xx_nand_partitions, -+ ARRAY_SIZE(rb4xx_nand_partitions)); -+#else -+ ret = add_mtd_device(&info->mtd); -+#endif -+ if (ret) -+ goto err_release_nand; ++#define AR724X_RESET_GE1_MDIO BIT(23) ++#define AR724X_RESET_GE0_MDIO BIT(22) ++#define AR724X_RESET_PCIE_PHY_SERIAL BIT(10) ++#define AR724X_RESET_PCIE_PHY BIT(7) ++#define AR724X_RESET_PCIE BIT(6) ++#define AR724X_RESET_USB_HOST BIT(5) ++#define AR724X_RESET_USB_PHY BIT(4) ++#define AR724X_RESET_USBSUS_OVERRIDE BIT(3) + -+ return 0; ++#define AR933X_RESET_WMAC BIT(11) ++#define AR933X_RESET_GE1_MDIO BIT(23) ++#define AR933X_RESET_GE0_MDIO BIT(22) ++#define AR933X_RESET_GE1_MAC BIT(13) ++#define AR933X_RESET_GE0_MAC BIT(9) + -+err_release_nand: -+ nand_release(&info->mtd); -+err_set_drvdata: -+ platform_set_drvdata(pdev, NULL); -+err_free_info: -+ kfree(info); -+err_free_gpio: -+ gpio_free(RB4XX_NAND_GPIO_RDY); -+ return ret; -+} ++#define REV_ID_MAJOR_MASK 0xfff0 ++#define REV_ID_MAJOR_AR71XX 0x00a0 ++#define REV_ID_MAJOR_AR913X 0x00b0 ++#define REV_ID_MAJOR_AR7240 0x00c0 ++#define REV_ID_MAJOR_AR7241 0x0100 ++#define REV_ID_MAJOR_AR7242 0x1100 ++#define REV_ID_MAJOR_AR9330 0x0110 ++#define REV_ID_MAJOR_AR9331 0x1110 ++#define REV_ID_MAJOR_AR9341 0x0120 ++#define REV_ID_MAJOR_AR9342 0x1120 ++#define REV_ID_MAJOR_AR9344 0x2120 + -+static int __devexit rb4xx_nand_remove(struct platform_device *pdev) -+{ -+ struct rb4xx_nand_info *info = platform_get_drvdata(pdev); ++#define AR71XX_REV_ID_MINOR_MASK 0x3 ++#define AR71XX_REV_ID_MINOR_AR7130 0x0 ++#define AR71XX_REV_ID_MINOR_AR7141 0x1 ++#define AR71XX_REV_ID_MINOR_AR7161 0x2 ++#define AR71XX_REV_ID_REVISION_MASK 0x3 ++#define AR71XX_REV_ID_REVISION_SHIFT 2 + -+ nand_release(&info->mtd); -+ platform_set_drvdata(pdev, NULL); -+ kfree(info); ++#define AR91XX_REV_ID_MINOR_MASK 0x3 ++#define AR91XX_REV_ID_MINOR_AR9130 0x0 ++#define AR91XX_REV_ID_MINOR_AR9132 0x1 ++#define AR91XX_REV_ID_REVISION_MASK 0x3 ++#define AR91XX_REV_ID_REVISION_SHIFT 2 + -+ return 0; -+} ++#define AR724X_REV_ID_REVISION_MASK 0x3 + -+static struct platform_driver rb4xx_nand_driver = { -+ .probe = rb4xx_nand_probe, -+ .remove = __devexit_p(rb4xx_nand_remove), -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; ++#define AR933X_REV_ID_REVISION_MASK 0xf + -+static int __init rb4xx_nand_init(void) ++#define AR934X_REV_ID_REVISION_MASK 0xf ++ ++extern void __iomem *ar71xx_reset_base; ++ ++static inline void ar71xx_reset_wr(unsigned reg, u32 val) +{ -+ return platform_driver_register(&rb4xx_nand_driver); ++ __raw_writel(val, ar71xx_reset_base + reg); +} + -+static void __exit rb4xx_nand_exit(void) ++static inline u32 ar71xx_reset_rr(unsigned reg) +{ -+ platform_driver_unregister(&rb4xx_nand_driver); ++ return __raw_readl(ar71xx_reset_base + reg); +} + -+module_init(rb4xx_nand_init); -+module_exit(rb4xx_nand_exit); ++void ar71xx_device_stop(u32 mask); ++void ar71xx_device_start(u32 mask); ++int ar71xx_device_stopped(u32 mask); + -+MODULE_DESCRIPTION(DRV_DESC); -+MODULE_VERSION(DRV_VERSION); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_AUTHOR("Imre Kaloz "); -+MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/mtd/nand/rb750_nand.c linux-2.6.39/drivers/mtd/nand/rb750_nand.c ---- linux-2.6.39.orig/drivers/mtd/nand/rb750_nand.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/mtd/nand/rb750_nand.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,360 @@ +/* -+ * NAND flash driver for the MikroTik RouterBOARD 750 ++ * SPI block ++ */ ++#define SPI_REG_FS 0x00 /* Function Select */ ++#define SPI_REG_CTRL 0x04 /* SPI Control */ ++#define SPI_REG_IOC 0x08 /* SPI I/O Control */ ++#define SPI_REG_RDS 0x0c /* Read Data Shift */ ++ ++#define SPI_FS_GPIO BIT(0) /* Enable GPIO mode */ ++ ++#define SPI_CTRL_RD BIT(6) /* Remap Disable */ ++#define SPI_CTRL_DIV_MASK 0x3f ++ ++#define SPI_IOC_DO BIT(0) /* Data Out pin */ ++#define SPI_IOC_CLK BIT(8) /* CLK pin */ ++#define SPI_IOC_CS(n) BIT(16 + (n)) ++#define SPI_IOC_CS0 SPI_IOC_CS(0) ++#define SPI_IOC_CS1 SPI_IOC_CS(1) ++#define SPI_IOC_CS2 SPI_IOC_CS(2) ++#define SPI_IOC_CS_ALL (SPI_IOC_CS0 | SPI_IOC_CS1 | SPI_IOC_CS2) ++ ++void ar71xx_flash_acquire(void); ++void ar71xx_flash_release(void); ++ ++/* ++ * MII_CTRL block ++ */ ++#define MII_REG_MII0_CTRL 0x00 ++#define MII_REG_MII1_CTRL 0x04 ++ ++#define MII0_CTRL_IF_GMII 0 ++#define MII0_CTRL_IF_MII 1 ++#define MII0_CTRL_IF_RGMII 2 ++#define MII0_CTRL_IF_RMII 3 ++ ++#define MII1_CTRL_IF_RGMII 0 ++#define MII1_CTRL_IF_RMII 1 ++ ++#endif /* __ASSEMBLER__ */ ++ ++#endif /* __ASM_MACH_AR71XX_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar91xx_flash.h 2011-04-27 12:19:21.867661560 +0200 +@@ -0,0 +1,26 @@ ++/* ++ * AR91xx parallel flash driver platform data definitions + * -+ * Copyright (C) 2010 Gabor Juhos ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+#include -+#include -+#include ++#ifndef __AR91XX_FLASH_H ++#define __AR91XX_FLASH_H + -+#include -+#include ++struct mtd_partition; + -+#define DRV_NAME "rb750-nand" -+#define DRV_VERSION "0.1.0" -+#define DRV_DESC "NAND flash driver for the RouterBOARD 750" ++struct ar91xx_flash_platform_data { ++ unsigned int width; ++ u8 is_shared:1; ++#ifdef CONFIG_MTD_PARTITIONS ++ unsigned int nr_parts; ++ struct mtd_partition *parts; ++#endif ++}; + -+#define RB750_NAND_IO0 BIT(RB750_GPIO_NAND_IO0) -+#define RB750_NAND_ALE BIT(RB750_GPIO_NAND_ALE) -+#define RB750_NAND_CLE BIT(RB750_GPIO_NAND_CLE) -+#define RB750_NAND_NRE BIT(RB750_GPIO_NAND_NRE) -+#define RB750_NAND_NWE BIT(RB750_GPIO_NAND_NWE) -+#define RB750_NAND_RDY BIT(RB750_GPIO_NAND_RDY) -+#define RB750_NAND_NCE BIT(RB750_GPIO_NAND_NCE) ++#endif /* __AR91XX_FLASH_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar933x_uart.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar933x_uart.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar933x_uart.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar933x_uart.h 2011-08-06 09:32:36.758018150 +0200 +@@ -0,0 +1,67 @@ ++/* ++ * Atheros AR933X UART defines ++ * ++ * Copyright (C) 2011 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+#define RB750_NAND_DATA_SHIFT 1 -+#define RB750_NAND_DATA_BITS (0xff << RB750_NAND_DATA_SHIFT) -+#define RB750_NAND_INPUT_BITS (RB750_NAND_DATA_BITS | RB750_NAND_RDY) -+#define RB750_NAND_OUTPUT_BITS (RB750_NAND_ALE | RB750_NAND_CLE | \ -+ RB750_NAND_NRE | RB750_NAND_NWE | \ -+ RB750_NAND_NCE) ++#ifndef __AR933X_UART_H ++#define __AR933X_UART_H ++ ++#define AR933X_UART_REGS_SIZE 20 ++#define AR933X_UART_FIFO_SIZE 16 ++ ++#define AR933X_UART_DATA_REG 0x00 ++#define AR933X_UART_CS_REG 0x04 ++#define AR933X_UART_CLOCK_REG 0x08 ++#define AR933X_UART_INT_REG 0x0c ++#define AR933X_UART_INT_EN_REG 0x10 ++ ++#define AR933X_UART_DATA_TX_RX_MASK 0xff ++#define AR933X_UART_DATA_RX_CSR BIT(8) ++#define AR933X_UART_DATA_TX_CSR BIT(9) ++ ++#define AR933X_UART_CS_PARITY_S 0 ++#define AR933X_UART_CS_PARITY_M 0x3 ++#define AR933X_UART_CS_PARITY_NONE 0 ++#define AR933X_UART_CS_PARITY_ODD 1 ++#define AR933X_UART_CS_PARITY_EVEN 2 ++#define AR933X_UART_CS_IF_MODE_S 2 ++#define AR933X_UART_CS_IF_MODE_M 0x3 ++#define AR933X_UART_CS_IF_MODE_NONE 0 ++#define AR933X_UART_CS_IF_MODE_DTE 1 ++#define AR933X_UART_CS_IF_MODE_DCE 2 ++#define AR933X_UART_CS_FLOW_CTRL_S 4 ++#define AR933X_UART_CS_FLOW_CTRL_M 0x3 ++#define AR933X_UART_CS_DMA_EN BIT(6) ++#define AR933X_UART_CS_TX_READY_ORIDE BIT(7) ++#define AR933X_UART_CS_RX_READY_ORIDE BIT(8) ++#define AR933X_UART_CS_TX_READY BIT(9) ++#define AR933X_UART_CS_RX_BREAK BIT(10) ++#define AR933X_UART_CS_TX_BREAK BIT(11) ++#define AR933X_UART_CS_HOST_INT BIT(12) ++#define AR933X_UART_CS_HOST_INT_EN BIT(13) ++#define AR933X_UART_CS_TX_BUSY BIT(14) ++#define AR933X_UART_CS_RX_BUSY BIT(15) ++ ++#define AR933X_UART_CLOCK_STEP_M 0xffff ++#define AR933X_UART_CLOCK_SCALE_M 0xfff ++#define AR933X_UART_CLOCK_SCALE_S 16 ++#define AR933X_UART_CLOCK_STEP_M 0xffff ++ ++#define AR933X_UART_INT_RX_VALID BIT(0) ++#define AR933X_UART_INT_TX_READY BIT(1) ++#define AR933X_UART_INT_RX_FRAMING_ERR BIT(2) ++#define AR933X_UART_INT_RX_OFLOW_ERR BIT(3) ++#define AR933X_UART_INT_TX_OFLOW_ERR BIT(4) ++#define AR933X_UART_INT_RX_PARITY_ERR BIT(5) ++#define AR933X_UART_INT_RX_BREAK_ON BIT(6) ++#define AR933X_UART_INT_RX_BREAK_OFF BIT(7) ++#define AR933X_UART_INT_RX_FULL BIT(8) ++#define AR933X_UART_INT_TX_EMPTY BIT(9) ++#define AR933X_UART_INT_ALLINTS 0x3ff ++ ++#endif /* __AR933X_UART_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar933x_uart_platform.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar933x_uart_platform.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/ar933x_uart_platform.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/ar933x_uart_platform.h 2011-08-06 09:32:36.758018150 +0200 +@@ -0,0 +1,18 @@ ++/* ++ * Platform data definition for Atheros AR933X UART ++ * ++ * Copyright (C) 2011 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+struct rb750_nand_info { -+ struct nand_chip chip; -+ struct mtd_info mtd; ++#ifndef _AR933X_UART_PLATFORM_H ++#define _AR933X_UART_PLATFORM_H ++ ++struct ar933x_uart_platform_data { ++ unsigned uartclk; +}; + ++#endif /* _AR933X_UART_PLATFORM_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/cpu-feature-overrides.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,56 @@ +/* -+ * We need to use the OLD Yaffs-1 OOB layout, otherwise the RB bootloader -+ * will not be able to find the kernel that we load. ++ * Atheros AR71xx specific CPU feature overrides ++ * ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This file was derived from: include/asm-mips/cpu-features.h ++ * Copyright (C) 2003, 2004 Ralf Baechle ++ * Copyright (C) 2004 Maciej W. Rozycki ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * + */ -+static struct nand_ecclayout rb750_nand_ecclayout = { -+ .eccbytes = 6, -+ .eccpos = { 8, 9, 10, 13, 14, 15 }, -+ .oobavail = 9, -+ .oobfree = { { 0, 4 }, { 6, 2 }, { 11, 2 }, { 4, 1 } } -+}; -+ -+static struct mtd_partition rb750_nand_partitions[] = { -+ { -+ .name = "booter", -+ .offset = 0, -+ .size = (256 * 1024), -+ .mask_flags = MTD_WRITEABLE, -+ }, { -+ .name = "kernel", -+ .offset = (256 * 1024), -+ .size = (4 * 1024 * 1024) - (256 * 1024), -+ }, { -+ .name = "rootfs", -+ .offset = MTDPART_OFS_NXTBLK, -+ .size = MTDPART_SIZ_FULL, -+ }, -+}; -+ -+static void rb750_nand_write(const u8 *buf, unsigned len) -+{ -+ void __iomem *base = ar71xx_gpio_base; -+ u32 out; -+ unsigned i; ++#ifndef __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H ++#define __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H + -+ /* set data lines to output mode */ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) | RB750_NAND_DATA_BITS, -+ base + GPIO_REG_OE); ++#define cpu_has_tlb 1 ++#define cpu_has_4kex 1 ++#define cpu_has_3k_cache 0 ++#define cpu_has_4k_cache 1 ++#define cpu_has_tx39_cache 0 ++#define cpu_has_sb1_cache 0 ++#define cpu_has_fpu 0 ++#define cpu_has_32fpr 0 ++#define cpu_has_counter 1 ++#define cpu_has_watch 1 ++#define cpu_has_divec 1 + -+ out = __raw_readl(base + GPIO_REG_OUT); -+ out &= ~(RB750_NAND_DATA_BITS | RB750_NAND_NWE); -+ for (i = 0; i != len; i++) { -+ u32 data; ++#define cpu_has_prefetch 1 ++#define cpu_has_ejtag 1 ++#define cpu_has_llsc 1 + -+ data = buf[i]; -+ data <<= RB750_NAND_DATA_SHIFT; -+ data |= out; -+ __raw_writel(data, base + GPIO_REG_OUT); ++#define cpu_has_mips16 1 ++#define cpu_has_mdmx 0 ++#define cpu_has_mips3d 0 ++#define cpu_has_smartmips 0 + -+ __raw_writel(data | RB750_NAND_NWE, base + GPIO_REG_OUT); -+ /* flush write */ -+ __raw_readl(base + GPIO_REG_OUT); -+ } ++#define cpu_has_mips32r1 1 ++#define cpu_has_mips32r2 1 ++#define cpu_has_mips64r1 0 ++#define cpu_has_mips64r2 0 + -+ /* set data lines to input mode */ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) & ~RB750_NAND_DATA_BITS, -+ base + GPIO_REG_OE); -+ /* flush write */ -+ __raw_readl(base + GPIO_REG_OE); -+} ++#define cpu_has_dsp 0 ++#define cpu_has_mipsmt 0 + -+static int rb750_nand_read_verify(u8 *read_buf, unsigned len, -+ const u8 *verify_buf) -+{ -+ void __iomem *base = ar71xx_gpio_base; -+ unsigned i; ++#define cpu_has_64bits 0 ++#define cpu_has_64bit_zero_reg 0 ++#define cpu_has_64bit_gp_regs 0 ++#define cpu_has_64bit_addresses 0 + -+ for (i = 0; i < len; i++) { -+ u8 data; ++#define cpu_dcache_line_size() 32 ++#define cpu_icache_line_size() 32 + -+ /* activate RE line */ -+ __raw_writel(RB750_NAND_NRE, base + GPIO_REG_CLEAR); -+ /* flush write */ -+ __raw_readl(base + GPIO_REG_CLEAR); ++#endif /* __ASM_MACH_AR71XX_CPU_FEATURE_OVERRIDES_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/gpio.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/gpio.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/gpio.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/gpio.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,53 @@ ++/* ++ * Atheros AR71xx GPIO API definitions ++ * ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ + -+ /* read input lines */ -+ data = __raw_readl(base + GPIO_REG_IN) >> RB750_NAND_DATA_SHIFT; ++#ifndef __ASM_MACH_AR71XX_GPIO_H ++#define __ASM_MACH_AR71XX_GPIO_H + -+ /* deactivate RE line */ -+ __raw_writel(RB750_NAND_NRE, base + GPIO_REG_SET); ++#define ARCH_NR_GPIOS 64 ++#include + -+ if (read_buf) -+ read_buf[i] = data; -+ else if (verify_buf && verify_buf[i] != data) -+ return -EFAULT; -+ } ++#include + -+ return 0; -+} ++extern unsigned long ar71xx_gpio_count; ++extern void __ar71xx_gpio_set_value(unsigned gpio, int value); ++extern int __ar71xx_gpio_get_value(unsigned gpio); + -+static void rb750_nand_select_chip(struct mtd_info *mtd, int chip) ++static inline int gpio_to_irq(unsigned gpio) +{ -+ void __iomem *base = ar71xx_gpio_base; -+ u32 func; -+ -+ func = __raw_readl(base + GPIO_REG_FUNC); -+ if (chip >= 0) { -+ /* disable latch */ -+ rb750_latch_change(RB750_LVC573_LE, 0); -+ -+ /* disable alternate functions */ -+ ar71xx_gpio_function_setup(AR724X_GPIO_FUNC_JTAG_DISABLE, -+ AR724X_GPIO_FUNC_SPI_EN); -+ -+ /* set input mode for data lines */ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) & -+ ~RB750_NAND_INPUT_BITS, -+ base + GPIO_REG_OE); -+ -+ /* deactivate RE and WE lines */ -+ __raw_writel(RB750_NAND_NRE | RB750_NAND_NWE, -+ base + GPIO_REG_SET); -+ /* flush write */ -+ (void) __raw_readl(base + GPIO_REG_SET); -+ -+ /* activate CE line */ -+ __raw_writel(RB750_NAND_NCE, base + GPIO_REG_CLEAR); -+ } else { -+ /* deactivate CE line */ -+ __raw_writel(RB750_NAND_NCE, base + GPIO_REG_SET); -+ /* flush write */ -+ (void) __raw_readl(base + GPIO_REG_SET); -+ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) | -+ RB750_NAND_IO0 | RB750_NAND_RDY, -+ base + GPIO_REG_OE); -+ -+ /* restore alternate functions */ -+ ar71xx_gpio_function_setup(AR724X_GPIO_FUNC_SPI_EN, -+ AR724X_GPIO_FUNC_JTAG_DISABLE); -+ -+ /* enable latch */ -+ rb750_latch_change(0, RB750_LVC573_LE); -+ } ++ return AR71XX_GPIO_IRQ(gpio); +} + -+static int rb750_nand_dev_ready(struct mtd_info *mtd) ++static inline int irq_to_gpio(unsigned irq) +{ -+ void __iomem *base = ar71xx_gpio_base; -+ -+ return !!(__raw_readl(base + GPIO_REG_IN) & RB750_NAND_RDY); ++ return irq - AR71XX_GPIO_IRQ_BASE; +} + -+static void rb750_nand_cmd_ctrl(struct mtd_info *mtd, int cmd, -+ unsigned int ctrl) ++static inline int gpio_get_value(unsigned gpio) +{ -+ if (ctrl & NAND_CTRL_CHANGE) { -+ void __iomem *base = ar71xx_gpio_base; -+ u32 t; -+ -+ t = __raw_readl(base + GPIO_REG_OUT); -+ -+ t &= ~(RB750_NAND_CLE | RB750_NAND_ALE); -+ t |= (ctrl & NAND_CLE) ? RB750_NAND_CLE : 0; -+ t |= (ctrl & NAND_ALE) ? RB750_NAND_ALE : 0; -+ -+ __raw_writel(t, base + GPIO_REG_OUT); -+ /* flush write */ -+ __raw_readl(base + GPIO_REG_OUT); -+ } ++ if (gpio < ar71xx_gpio_count) ++ return __ar71xx_gpio_get_value(gpio); + -+ if (cmd != NAND_CMD_NONE) { -+ u8 t = cmd; -+ rb750_nand_write(&t, 1); -+ } ++ return __gpio_get_value(gpio); +} + -+static u8 rb750_nand_read_byte(struct mtd_info *mtd) ++static inline void gpio_set_value(unsigned gpio, int value) +{ -+ u8 data = 0; -+ rb750_nand_read_verify(&data, 1, NULL); -+ return data; ++ if (gpio < ar71xx_gpio_count) ++ __ar71xx_gpio_set_value(gpio, value); ++ else ++ __gpio_set_value(gpio, value); +} + -+static void rb750_nand_read_buf(struct mtd_info *mtd, u8 *buf, int len) -+{ -+ rb750_nand_read_verify(buf, len, NULL); -+} ++#define gpio_cansleep __gpio_cansleep + -+static void rb750_nand_write_buf(struct mtd_info *mtd, const u8 *buf, int len) -+{ -+ rb750_nand_write(buf, len); -+} ++#endif /* __ASM_MACH_AR71XX_GPIO_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/irq.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/irq.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/irq.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/irq.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,17 @@ ++/* ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++#ifndef __ASM_MACH_AR71XX_IRQ_H ++#define __ASM_MACH_AR71XX_IRQ_H + -+static int rb750_nand_verify_buf(struct mtd_info *mtd, const u8 *buf, int len) -+{ -+ return rb750_nand_read_verify(NULL, len, buf); -+} ++#define MIPS_CPU_IRQ_BASE 0 ++#define NR_IRQS 80 + -+static void __init rb750_nand_gpio_init(void) -+{ -+ void __iomem *base = ar71xx_gpio_base; -+ u32 out; ++#include_next + -+ out = __raw_readl(base + GPIO_REG_OUT); ++#endif /* __ASM_MACH_AR71XX_IRQ_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/kernel-entry-init.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,32 @@ ++/* ++ * Atheros AR71xx specific kernel entry setup ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ ++#ifndef __ASM_MACH_AR71XX_KERNEL_ENTRY_H ++#define __ASM_MACH_AR71XX_KERNEL_ENTRY_H + -+ /* setup output levels */ -+ __raw_writel(RB750_NAND_NCE | RB750_NAND_NRE | RB750_NAND_NWE, -+ base + GPIO_REG_SET); ++ /* ++ * Some bootloaders set the 'Kseg0 coherency algorithm' to ++ * 'Cacheable, noncoherent, write-through, no write allocate' ++ * and this cause performance issues. Let's go and change it to ++ * 'Cacheable, noncoherent, write-back, write allocate' ++ */ ++ .macro kernel_entry_setup ++ mfc0 t0, CP0_CONFIG ++ li t1, ~CONF_CM_CMASK ++ and t0, t1 ++ ori t0, CONF_CM_CACHABLE_NONCOHERENT ++ mtc0 t0, CP0_CONFIG ++ nop ++ .endm + -+ __raw_writel(RB750_NAND_ALE | RB750_NAND_CLE, -+ base + GPIO_REG_CLEAR); ++ .macro smp_slave_setup ++ .endm + -+ /* setup input lines */ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) & ~(RB750_NAND_INPUT_BITS), -+ base + GPIO_REG_OE); ++#endif /* __ASM_MACH_AR71XX_KERNEL_ENTRY_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mach-rb750.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mach-rb750.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mach-rb750.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mach-rb750.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,66 @@ ++/* ++ * MikroTik RouterBOARD 750 definitions ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++#ifndef _MACH_RB750_H ++#define _MACH_RB750_H + -+ /* setup output lines */ -+ __raw_writel(__raw_readl(base + GPIO_REG_OE) | RB750_NAND_OUTPUT_BITS, -+ base + GPIO_REG_OE); ++#include + -+ rb750_latch_change(~out & RB750_NAND_IO0, out & RB750_NAND_IO0); -+} ++#define RB750_GPIO_LVC573_LE 0 /* Latch enable on LVC573 */ ++#define RB750_GPIO_NAND_IO0 1 /* NAND I/O 0 */ ++#define RB750_GPIO_NAND_IO1 2 /* NAND I/O 1 */ ++#define RB750_GPIO_NAND_IO2 3 /* NAND I/O 2 */ ++#define RB750_GPIO_NAND_IO3 4 /* NAND I/O 3 */ ++#define RB750_GPIO_NAND_IO4 5 /* NAND I/O 4 */ ++#define RB750_GPIO_NAND_IO5 6 /* NAND I/O 5 */ ++#define RB750_GPIO_NAND_IO6 7 /* NAND I/O 6 */ ++#define RB750_GPIO_NAND_IO7 8 /* NAND I/O 7 */ ++#define RB750_GPIO_NAND_NCE 11 /* NAND Chip Enable (active low) */ ++#define RB750_GPIO_NAND_RDY 12 /* NAND Ready */ ++#define RB750_GPIO_NAND_CLE 14 /* NAND Command Latch Enable */ ++#define RB750_GPIO_NAND_ALE 15 /* NAND Address Latch Enable */ ++#define RB750_GPIO_NAND_NRE 16 /* NAND Read Enable (active low) */ ++#define RB750_GPIO_NAND_NWE 17 /* NAND Write Enable (active low) */ + -+static int __init rb750_nand_probe(struct platform_device *pdev) -+{ -+ struct rb750_nand_info *info; -+ int ret; ++#define RB750_GPIO_BTN_RESET 1 ++#define RB750_GPIO_SPI_CS0 2 ++#define RB750_GPIO_LED_ACT 12 ++#define RB750_GPIO_LED_PORT1 13 ++#define RB750_GPIO_LED_PORT2 14 ++#define RB750_GPIO_LED_PORT3 15 ++#define RB750_GPIO_LED_PORT4 16 ++#define RB750_GPIO_LED_PORT5 17 + -+ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); ++#define RB750_LED_ACT BIT(RB750_GPIO_LED_ACT) ++#define RB750_LED_PORT1 BIT(RB750_GPIO_LED_PORT1) ++#define RB750_LED_PORT2 BIT(RB750_GPIO_LED_PORT2) ++#define RB750_LED_PORT3 BIT(RB750_GPIO_LED_PORT3) ++#define RB750_LED_PORT4 BIT(RB750_GPIO_LED_PORT4) ++#define RB750_LED_PORT5 BIT(RB750_GPIO_LED_PORT5) + -+ rb750_nand_gpio_init(); ++#define RB750_LVC573_LE BIT(RB750_GPIO_LVC573_LE) + -+ info = kzalloc(sizeof(*info), GFP_KERNEL); -+ if (!info) -+ return -ENOMEM; ++#define RB750_LED_BITS (RB750_LED_PORT1 | RB750_LED_PORT2 | RB750_LED_PORT3 | \ ++ RB750_LED_PORT4 | RB750_LED_PORT5 | RB750_LED_ACT) + -+ info->chip.priv = &info; -+ info->mtd.priv = &info->chip; -+ info->mtd.owner = THIS_MODULE; ++struct rb750_led_data { ++ char *name; ++ char *default_trigger; ++ u32 mask; ++ int active_low; ++}; + -+ info->chip.select_chip = rb750_nand_select_chip; -+ info->chip.cmd_ctrl = rb750_nand_cmd_ctrl; -+ info->chip.dev_ready = rb750_nand_dev_ready; -+ info->chip.read_byte = rb750_nand_read_byte; -+ info->chip.write_buf = rb750_nand_write_buf; -+ info->chip.read_buf = rb750_nand_read_buf; -+ info->chip.verify_buf = rb750_nand_verify_buf; ++struct rb750_led_platform_data { ++ int num_leds; ++ struct rb750_led_data *leds; ++}; + -+ info->chip.chip_delay = 25; -+ info->chip.ecc.mode = NAND_ECC_SOFT; -+ info->chip.options |= NAND_NO_AUTOINCR; ++int rb750_latch_change(u32 mask_clr, u32 mask_set); + -+ platform_set_drvdata(pdev, info); ++#endif /* _MACH_RB750_H */ +\ No newline at end of file +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mangle-port.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mangle-port.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/mangle-port.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/mangle-port.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,45 @@ ++/* ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This file was derived from: inlude/asm-mips/mach-generic/mangle-port.h ++ * Copyright (C) 2003, 2004 Ralf Baechle ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ ret = nand_scan_ident(&info->mtd, 1); -+ if (ret) { -+ ret = -ENXIO; -+ goto err_free_info; -+ } ++#ifndef __ASM_MACH_AR71XX_MANGLE_PORT_H ++#define __ASM_MACH_AR71XX_MANGLE_PORT_H + -+ if (info->mtd.writesize == 512) -+ info->chip.ecc.layout = &rb750_nand_ecclayout; ++#define __swizzle_addr_b(port) ((port) ^ 3) ++#define __swizzle_addr_w(port) ((port) ^ 2) ++#define __swizzle_addr_l(port) (port) ++#define __swizzle_addr_q(port) (port) + -+ ret = nand_scan_tail(&info->mtd); -+ if (ret) { -+ return -ENXIO; -+ goto err_set_drvdata; -+ } ++#if defined(CONFIG_SWAP_IO_SPACE) ++ ++# define ioswabb(a, x) (x) ++# define __mem_ioswabb(a, x) (x) ++# define ioswabw(a, x) le16_to_cpu(x) ++# define __mem_ioswabw(a, x) (x) ++# define ioswabl(a, x) le32_to_cpu(x) ++# define __mem_ioswabl(a, x) (x) ++# define ioswabq(a, x) le64_to_cpu(x) ++# define __mem_ioswabq(a, x) (x) + -+#ifdef CONFIG_MTD_PARTITIONS -+ ret = add_mtd_partitions(&info->mtd, rb750_nand_partitions, -+ ARRAY_SIZE(rb750_nand_partitions)); +#else -+ ret = add_mtd_device(&info->mtd); -+#endif -+ if (ret) -+ goto err_release_nand; + -+ return 0; ++# define ioswabb(a, x) (x) ++# define __mem_ioswabb(a, x) (x) ++# define ioswabw(a, x) (x) ++# define __mem_ioswabw(a, x) cpu_to_le16(x) ++# define ioswabl(a, x) (x) ++# define __mem_ioswabl(a, x) cpu_to_le32(x) ++# define ioswabq(a, x) (x) ++# define __mem_ioswabq(a, x) cpu_to_le64(x) + -+ err_release_nand: -+ nand_release(&info->mtd); -+ err_set_drvdata: -+ platform_set_drvdata(pdev, NULL); -+ err_free_info: -+ kfree(info); -+ return ret; -+} ++#endif + -+static int __devexit rb750_nand_remove(struct platform_device *pdev) -+{ -+ struct rb750_nand_info *info = platform_get_drvdata(pdev); ++#endif /* __ASM_MACH_AR71XX_MANGLE_PORT_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/pci.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/pci.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/pci.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/pci.h 2011-04-27 12:19:21.877661867 +0200 +@@ -0,0 +1,46 @@ ++/* ++ * Atheros AR71xx SoC specific PCI definitions ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ nand_release(&info->mtd); -+ platform_set_drvdata(pdev, NULL); -+ kfree(info); ++#ifndef __ASM_MACH_AR71XX_PCI_H ++#define __ASM_MACH_AR71XX_PCI_H + -+ return 0; -+} ++struct pci_dev; + -+static struct platform_driver rb750_nand_driver = { -+ .probe = rb750_nand_probe, -+ .remove = __devexit_p(rb750_nand_remove), -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, ++struct ar71xx_pci_irq { ++ int irq; ++ u8 slot; ++ u8 pin; +}; + -+static int __init rb750_nand_init(void) -+{ -+ return platform_driver_register(&rb750_nand_driver); -+} ++#ifdef CONFIG_PCI ++extern int (*ar71xx_pci_plat_dev_init)(struct pci_dev *dev); ++extern unsigned ar71xx_pci_nr_irqs __initdata; ++extern struct ar71xx_pci_irq *ar71xx_pci_irq_map __initdata; + -+static void __exit rb750_nand_exit(void) ++int ar71xx_pcibios_map_irq(const struct pci_dev *dev, ++ uint8_t slot, uint8_t pin) __init; ++int ar71xx_pcibios_init(void) __init; ++ ++int ar71xx_pci_be_handler(int is_fixup); ++ ++int ar724x_pcibios_map_irq(const struct pci_dev *dev, ++ uint8_t slot, uint8_t pin) __init; ++int ar724x_pcibios_init(void) __init; ++ ++int ar71xx_pci_init(unsigned nr_irqs, struct ar71xx_pci_irq *map) __init; ++#else ++static inline int ar71xx_pci_init(unsigned nr_irqs, struct ar71xx_pci_irq *map) +{ -+ platform_driver_unregister(&rb750_nand_driver); ++ return 0; +} ++#endif + -+module_init(rb750_nand_init); -+module_exit(rb750_nand_exit); -+ -+MODULE_DESCRIPTION(DRV_DESC); -+MODULE_VERSION(DRV_VERSION); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/mtd/wrt160nl_part.c linux-2.6.39/drivers/mtd/wrt160nl_part.c ---- linux-2.6.39.orig/drivers/mtd/wrt160nl_part.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/mtd/wrt160nl_part.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,181 @@ ++#endif /* __ASM_MACH_AR71XX_PCI_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/platform.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/platform.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/platform.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/platform.h 2011-08-22 07:40:11.890481646 +0200 +@@ -0,0 +1,63 @@ +/* -+ * Copyright (C) 2009 Christian Daniel -+ * Copyright (C) 2009 Gabor Juhos ++ * Atheros AR71xx SoC specific platform data definitions + * -+ * 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -+ * -+ * TRX flash partition table. -+ * Based on ar7 map by Felix Fietkau ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + -+#include -+#include -+#include -+ -+#include -+#include ++#ifndef __ASM_MACH_AR71XX_PLATFORM_H ++#define __ASM_MACH_AR71XX_PLATFORM_H + -+struct cybertan_header { -+ char magic[4]; -+ u8 res1[4]; -+ char fw_date[3]; -+ char fw_ver[3]; -+ char id[4]; -+ char hw_ver; -+ char unused; -+ u8 flags[2]; -+ u8 res2[10]; -+}; ++#include ++#include ++#include ++#include + -+#define TRX_PARTS 6 -+#define TRX_MAGIC 0x30524448 -+#define TRX_MAX_OFFSET 3 ++struct ag71xx_platform_data { ++ phy_interface_t phy_if_mode; ++ u32 phy_mask; ++ int speed; ++ int duplex; ++ u32 reset_bit; ++ u32 mii_if; ++ u8 mac_addr[ETH_ALEN]; ++ struct device *mii_bus_dev; + -+struct trx_header { -+ uint32_t magic; /* "HDR0" */ -+ uint32_t len; /* Length of file including header */ -+ uint32_t crc32; /* 32-bit CRC from flag_version to end of file */ -+ uint32_t flag_version; /* 0:15 flags, 16:31 version */ -+ uint32_t offsets[TRX_MAX_OFFSET]; /* Offsets of partitions from start of header */ -+}; ++ u8 has_gbit:1; ++ u8 is_ar91xx:1; ++ u8 is_ar7240:1; ++ u8 is_ar724x:1; ++ u8 has_ar8216:1; ++ u8 has_ar7240_switch:1; + -+#define IH_MAGIC 0x27051956 /* Image Magic Number */ -+#define IH_NMLEN 32 /* Image Name Length */ ++ void (*ddr_flush)(void); ++ void (*set_pll)(int speed); + -+struct uimage_header { -+ uint32_t ih_magic; /* Image Header Magic Number */ -+ uint32_t ih_hcrc; /* Image Header CRC Checksum */ -+ uint32_t ih_time; /* Image Creation Timestamp */ -+ uint32_t ih_size; /* Image Data Size */ -+ uint32_t ih_load; /* Data» Load Address */ -+ uint32_t ih_ep; /* Entry Point Address */ -+ uint32_t ih_dcrc; /* Image Data CRC Checksum */ -+ uint8_t ih_os; /* Operating System */ -+ uint8_t ih_arch; /* CPU architecture */ -+ uint8_t ih_type; /* Image Type */ -+ uint8_t ih_comp; /* Compression Type */ -+ uint8_t ih_name[IH_NMLEN]; /* Image Name */ ++ u32 fifo_cfg1; ++ u32 fifo_cfg2; ++ u32 fifo_cfg3; +}; + -+struct wrt160nl_header { -+ struct cybertan_header cybertan; -+ struct trx_header trx; -+ struct uimage_header uimage; -+} __attribute__ ((packed)); -+ -+static struct mtd_partition trx_parts[TRX_PARTS]; -+ -+static int wrt160nl_parse_partitions(struct mtd_info *master, -+ struct mtd_partition **pparts, -+ unsigned long origin) -+{ -+ struct wrt160nl_header *header; -+ struct trx_header *theader; -+ struct uimage_header *uheader; -+ size_t retlen; -+ unsigned int kernel_len; -+ int ret; -+ -+ header = vmalloc(sizeof(*header)); -+ if (!header) { -+ return -ENOMEM; -+ goto out; -+ } -+ -+ ret = master->read(master, 4 * master->erasesize, sizeof(*header), -+ &retlen, (void *) header); -+ if (ret) -+ goto free_hdr; -+ -+ if (retlen != sizeof(*header)) { -+ ret = -EIO; -+ goto free_hdr; -+ } -+ -+ if (strncmp(header->cybertan.magic, "NL16", 4) != 0) { -+ printk(KERN_NOTICE "%s: no WRT160NL signature found\n", -+ master->name); -+ goto free_hdr; -+ } -+ -+ theader = &header->trx; -+ if (le32_to_cpu(theader->magic) != TRX_MAGIC) { -+ printk(KERN_NOTICE "%s: no TRX header found\n", master->name); -+ goto free_hdr; -+ } -+ -+ uheader = &header->uimage; -+ if (uheader->ih_magic != IH_MAGIC) { -+ printk(KERN_NOTICE "%s: no uImage found\n", master->name); -+ goto free_hdr; -+ } -+ -+ kernel_len = le32_to_cpu(theader->offsets[1]) + sizeof(struct cybertan_header); -+ -+ trx_parts[0].name = "u-boot"; -+ trx_parts[0].offset = 0; -+ trx_parts[0].size = 4 * master->erasesize; -+ trx_parts[0].mask_flags = MTD_WRITEABLE; -+ -+ trx_parts[1].name = "kernel"; -+ trx_parts[1].offset = trx_parts[0].offset + trx_parts[0].size; -+ trx_parts[1].size = kernel_len; -+ trx_parts[1].mask_flags = 0; -+ -+ trx_parts[2].name = "rootfs"; -+ trx_parts[2].offset = trx_parts[1].offset + trx_parts[1].size; -+ trx_parts[2].size = master->size - 6 * master->erasesize - trx_parts[1].size; -+ trx_parts[2].mask_flags = 0; -+ -+ trx_parts[3].name = "nvram"; -+ trx_parts[3].offset = master->size - 2 * master->erasesize; -+ trx_parts[3].size = master->erasesize; -+ trx_parts[3].mask_flags = MTD_WRITEABLE; ++struct ag71xx_mdio_platform_data { ++ u32 phy_mask; ++ int is_ar7240; ++}; + -+ trx_parts[4].name = "art"; -+ trx_parts[4].offset = master->size - master->erasesize; -+ trx_parts[4].size = master->erasesize; -+ trx_parts[4].mask_flags = MTD_WRITEABLE; ++struct ar71xx_ehci_platform_data { ++ u8 is_ar91xx; ++}; + -+ trx_parts[5].name = "firmware"; -+ trx_parts[5].offset = 4 * master->erasesize; -+ trx_parts[5].size = master->size - 6 * master->erasesize; -+ trx_parts[5].mask_flags = 0; ++struct ar71xx_spi_platform_data { ++ unsigned bus_num; ++ unsigned num_chipselect; ++ u32 (*get_ioc_base)(u8 chip_select, int cs_high, int is_on); ++}; + -+ *pparts = trx_parts; -+ ret = TRX_PARTS; ++#define AR71XX_SPI_CS_INACTIVE 0 ++#define AR71XX_SPI_CS_ACTIVE 1 + -+ free_hdr: -+ vfree(header); -+ out: -+ return ret; -+} ++#endif /* __ASM_MACH_AR71XX_PLATFORM_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/rb4xx_cpld.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/rb4xx_cpld.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/rb4xx_cpld.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/rb4xx_cpld.h 2011-04-27 12:19:21.867661560 +0200 +@@ -0,0 +1,48 @@ ++/* ++ * SPI driver definitions for the CPLD chip on the Mikrotik RB4xx boards ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This file was based on the patches for Linux 2.6.27.39 published by ++ * MikroTik for their RouterBoard 4xx series devices. ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+static struct mtd_part_parser wrt160nl_parser = { -+ .owner = THIS_MODULE, -+ .parse_fn = wrt160nl_parse_partitions, -+ .name = "wrt160nl", ++#define CPLD_GPIO_nLED1 0 ++#define CPLD_GPIO_nLED2 1 ++#define CPLD_GPIO_nLED3 2 ++#define CPLD_GPIO_nLED4 3 ++#define CPLD_GPIO_FAN 4 ++#define CPLD_GPIO_ALE 5 ++#define CPLD_GPIO_CLE 6 ++#define CPLD_GPIO_nCE 7 ++#define CPLD_GPIO_nLED5 8 ++ ++#define CPLD_NUM_GPIOS 9 ++ ++#define CPLD_CFG_nLED1 BIT(CPLD_GPIO_nLED1) ++#define CPLD_CFG_nLED2 BIT(CPLD_GPIO_nLED2) ++#define CPLD_CFG_nLED3 BIT(CPLD_GPIO_nLED3) ++#define CPLD_CFG_nLED4 BIT(CPLD_GPIO_nLED4) ++#define CPLD_CFG_FAN BIT(CPLD_GPIO_FAN) ++#define CPLD_CFG_ALE BIT(CPLD_GPIO_ALE) ++#define CPLD_CFG_CLE BIT(CPLD_GPIO_CLE) ++#define CPLD_CFG_nCE BIT(CPLD_GPIO_nCE) ++#define CPLD_CFG_nLED5 BIT(CPLD_GPIO_nLED5) ++ ++struct rb4xx_cpld_platform_data { ++ unsigned gpio_base; +}; + -+static int __init wrt160nl_parser_init(void) -+{ -+ return register_mtd_parser(&wrt160nl_parser); -+} ++extern int rb4xx_cpld_change_cfg(unsigned mask, unsigned value); ++extern int rb4xx_cpld_read(unsigned char *rx_buf, ++ const unsigned char *verify_buf, ++ unsigned cnt); ++extern int rb4xx_cpld_read_from(unsigned addr, ++ unsigned char *rx_buf, ++ const unsigned char *verify_buf, ++ unsigned cnt); ++extern int rb4xx_cpld_write(const unsigned char *buf, unsigned count); +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/war.h linux-2.6.39/arch/mips/include/asm/mach-ar71xx/war.h +--- linux-2.6.39.orig/arch/mips/include/asm/mach-ar71xx/war.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/include/asm/mach-ar71xx/war.h 2011-04-27 12:19:21.867661560 +0200 +@@ -0,0 +1,25 @@ ++/* ++ * 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) 2002, 2004, 2007 by Ralf Baechle ++ */ ++#ifndef __ASM_MACH_AR71XX_WAR_H ++#define __ASM_MACH_AR71XX_WAR_H + -+module_init(wrt160nl_parser_init); ++#define R4600_V1_INDEX_ICACHEOP_WAR 0 ++#define R4600_V1_HIT_CACHEOP_WAR 0 ++#define R4600_V2_HIT_CACHEOP_WAR 0 ++#define R5432_CP0_INTERRUPT_WAR 0 ++#define BCM1250_M3_WAR 0 ++#define SIBYTE_1956_WAR 0 ++#define MIPS4K_ICACHE_REFILL_WAR 0 ++#define MIPS_CACHE_SYNC_WAR 0 ++#define TX49XX_ICACHE_INDEX_INV_WAR 0 ++#define RM9000_CDEX_SMP_WAR 0 ++#define ICACHE_REFILLS_WORKAROUND_WAR 0 ++#define R10000_LLSC_WAR 0 ++#define MIPS34K_MISSED_ITLB_WAR 0 + -+MODULE_LICENSE("GPL"); -+MODULE_AUTHOR("Christian Daniel "); -diff -Nur linux-2.6.39.orig/drivers/net/Kconfig linux-2.6.39/drivers/net/Kconfig ---- linux-2.6.39.orig/drivers/net/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -2071,6 +2071,8 @@ ++#endif /* __ASM_MACH_AR71XX_WAR_H */ +diff -Nur linux-2.6.39.orig/arch/mips/include/asm/time.h linux-2.6.39/arch/mips/include/asm/time.h +--- linux-2.6.39.orig/arch/mips/include/asm/time.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/include/asm/time.h 2011-08-24 05:53:05.239228886 +0200 +@@ -52,6 +52,7 @@ + */ + #ifdef CONFIG_CEVT_R4K_LIB + extern unsigned int __weak get_c0_compare_int(void); ++extern unsigned int __weak get_c0_compare_irq(void); + extern int r4k_clockevent_init(void); + #endif - The safe and default value for this is N. +diff -Nur linux-2.6.39.orig/arch/mips/Kconfig linux-2.6.39/arch/mips/Kconfig +--- linux-2.6.39.orig/arch/mips/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/Kconfig 2011-08-24 02:42:39.969240338 +0200 +@@ -84,6 +84,23 @@ + help + Support for the Atheros AR71XX/AR724X/AR913X SoCs. -+source drivers/net/ag71xx/Kconfig ++config ATHEROS_AR71XX ++ bool "Atheros AR71xx based boards" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select ARCH_REQUIRE_GPIOLIB ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_HAS_EARLY_PRINTK ++ select MIPS_MACHINE ++ help ++ Support for Atheros AR71xx based boards. + - config DL2K - tristate "DL2000/TC902x-based Gigabit Ethernet support" - depends on PCI -diff -Nur linux-2.6.39.orig/drivers/net/Makefile linux-2.6.39/drivers/net/Makefile ---- linux-2.6.39.orig/drivers/net/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -112,6 +112,7 @@ - # end link order section - # + config BCM47XX + bool "Broadcom BCM47XX based boards" + select CEVT_R4K +@@ -739,6 +756,7 @@ + endchoice -+obj-$(CONFIG_AG71XX) += ag71xx/ - obj-$(CONFIG_SUNDANCE) += sundance.o - obj-$(CONFIG_HAMACHI) += hamachi.o - obj-$(CONFIG_NET) += Space.o loopback.o -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/Kconfig linux-2.6.39/drivers/net/ag71xx/Kconfig ---- linux-2.6.39.orig/drivers/net/ag71xx/Kconfig 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,33 @@ -+config AG71XX -+ tristate "Atheros AR71xx built-in ethernet mac support" -+ depends on ATHEROS_AR71XX -+ select PHYLIB -+ help -+ If you wish to compile a kernel for AR71xx/91xx and enable -+ ethernet support, then you should always answer Y to this. + source "arch/mips/alchemy/Kconfig" ++source "arch/mips/ar71xx/Kconfig" + source "arch/mips/ath79/Kconfig" + source "arch/mips/bcm63xx/Kconfig" + source "arch/mips/jazz/Kconfig" +@@ -907,6 +925,9 @@ + config MIPS_DISABLE_OBSOLETE_IDE + bool + ++config MYLOADER ++ bool + -+if AG71XX + config SYNC_R4K + bool + +diff -Nur linux-2.6.39.orig/arch/mips/Kconfig.orig linux-2.6.39/arch/mips/Kconfig.orig +--- linux-2.6.39.orig/arch/mips/Kconfig.orig 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/Kconfig.orig 2011-08-22 16:21:32.077979816 +0200 +@@ -0,0 +1,2472 @@ ++config MIPS ++ bool ++ default y ++ select HAVE_GENERIC_DMA_COHERENT ++ select HAVE_IDE ++ select HAVE_OPROFILE ++ select HAVE_IRQ_WORK ++ select HAVE_PERF_EVENTS ++ select PERF_USE_VMALLOC ++ select HAVE_ARCH_KGDB ++ select HAVE_FUNCTION_TRACER ++ select HAVE_FUNCTION_TRACE_MCOUNT_TEST ++ select HAVE_DYNAMIC_FTRACE ++ select HAVE_FTRACE_MCOUNT_RECORD ++ select HAVE_C_RECORDMCOUNT ++ select HAVE_FUNCTION_GRAPH_TRACER ++ select HAVE_KPROBES ++ select HAVE_KRETPROBES ++ select RTC_LIB if !MACH_LOONGSON ++ select GENERIC_ATOMIC64 if !64BIT ++ select HAVE_DMA_ATTRS ++ select HAVE_DMA_API_DEBUG ++ select HAVE_GENERIC_HARDIRQS ++ select GENERIC_IRQ_PROBE ++ select GENERIC_IRQ_SHOW ++ select HAVE_ARCH_JUMP_LABEL ++ ++menu "Machine selection" ++ ++config ZONE_DMA ++ bool ++ ++choice ++ prompt "System type" ++ default SGI_IP22 ++ ++config MIPS_ALCHEMY ++ bool "Alchemy processor based machines" ++ select 64BIT_PHYS_ADDR ++ select CEVT_R4K_LIB ++ select CSRC_R4K_LIB ++ select IRQ_CPU ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_APM_EMULATION ++ select GENERIC_GPIO ++ select ARCH_WANT_OPTIONAL_GPIOLIB ++ select SYS_SUPPORTS_ZBOOT ++ ++config AR7 ++ bool "Texas Instruments AR7" ++ select BOOT_ELF32 ++ select DMA_NONCOHERENT ++ select CEVT_R4K ++ select CSRC_R4K ++ select IRQ_CPU ++ select NO_EXCEPT_FILL ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SYS_SUPPORTS_ZBOOT_UART16550 ++ select ARCH_REQUIRE_GPIOLIB ++ select GCD ++ select VLYNQ ++ help ++ Support for the Texas Instruments AR7 System-on-a-Chip ++ family: TNETD7100, 7200 and 7300. + -+config AG71XX_DEBUG -+ bool "Atheros AR71xx built-in ethernet driver debugging" -+ default n ++config ATH79 ++ bool "Atheros AR71XX/AR724X/AR913X based boards" ++ select ARCH_REQUIRE_GPIOLIB ++ select BOOT_RAW ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select MIPS_MACHINE ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN + help -+ Atheros AR71xx built-in ethernet driver debugging messages. ++ Support for the Atheros AR71XX/AR724X/AR913X SoCs. + -+config AG71XX_DEBUG_FS -+ bool "Atheros AR71xx built-in ethernet driver debugfs support" -+ depends on DEBUG_FS -+ default n ++config ATHEROS_AR71XX ++ bool "Atheros AR71xx based boards" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select ARCH_REQUIRE_GPIOLIB ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_HAS_EARLY_PRINTK ++ select MIPS_MACHINE + help -+ Say Y, if you need access to various statistics provided by -+ the ag71xx driver. ++ Support for Atheros AR71xx based boards. + -+config AG71XX_AR8216_SUPPORT -+ bool "special support for the Atheros AR8216 switch" -+ default n -+ default y if AR71XX_MACH_WNR2000 || AR71XX_MACH_MZK_W04NU ++config BCM47XX ++ bool "Broadcom BCM47XX based boards" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SSB ++ select SSB_DRIVER_MIPS ++ select SSB_DRIVER_EXTIF ++ select SSB_EMBEDDED ++ select SSB_B43_PCI_BRIDGE if PCI ++ select SSB_PCICORE_HOSTMODE if PCI ++ select GENERIC_GPIO ++ select SYS_HAS_EARLY_PRINTK ++ select CFE + help -+ Say 'y' here if you want to enable special support for the -+ Atheros AR8216 switch found on some boards. ++ Support for BCM47XX based boards + -+endif -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/Makefile linux-2.6.39/drivers/net/ag71xx/Makefile ---- linux-2.6.39.orig/drivers/net/ag71xx/Makefile 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,14 @@ -+# -+# Makefile for the Atheros AR71xx built-in ethernet macs -+# ++config BCM63XX ++ bool "Broadcom BCM63XX based boards" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_HAS_EARLY_PRINTK ++ select SWAP_IO_SPACE ++ select ARCH_REQUIRE_GPIOLIB ++ help ++ Support for BCM63XX based boards + -+ag71xx-y += ag71xx_main.o -+ag71xx-y += ag71xx_ethtool.o -+ag71xx-y += ag71xx_phy.o -+ag71xx-y += ag71xx_mdio.o ++config MIPS_COBALT ++ bool "Cobalt Server" ++ select CEVT_R4K ++ select CSRC_R4K ++ select CEVT_GT641XX ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select I8253 ++ select I8259 ++ select IRQ_CPU ++ select IRQ_GT641XX ++ select PCI_GT64XXX_PCI0 ++ select PCI ++ select SYS_HAS_CPU_NEVADA ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN + -+ag71xx-$(CONFIG_AG71XX_DEBUG_FS) += ag71xx_debugfs.o -+ag71xx-$(CONFIG_AG71XX_AR8216_SUPPORT) += ag71xx_ar8216.o ++config MACH_DECSTATION ++ bool "DECstations" ++ select BOOT_ELF32 ++ select CEVT_DS1287 ++ select CEVT_R4K ++ select CSRC_IOASIC ++ select CSRC_R4K ++ select CPU_DADDI_WORKAROUNDS if 64BIT ++ select CPU_R4000_WORKAROUNDS if 64BIT ++ select CPU_R4400_WORKAROUNDS if 64BIT ++ select DMA_NONCOHERENT ++ select NO_IOPORT ++ select IRQ_CPU ++ select SYS_HAS_CPU_R3000 ++ select SYS_HAS_CPU_R4X00 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL if EXPERIMENTAL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SYS_SUPPORTS_128HZ ++ select SYS_SUPPORTS_256HZ ++ select SYS_SUPPORTS_1024HZ ++ help ++ This enables support for DEC's MIPS based workstations. For details ++ see the Linux/MIPS FAQ on and the ++ DECstation porting pages on . + -+obj-$(CONFIG_AG71XX) += ag71xx.o ++ If you have one of the following DECstation Models you definitely ++ want to choose R4xx0 for the CPU Type: + -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx.h linux-2.6.39/drivers/net/ag71xx/ag71xx.h ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,500 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++ DECstation 5000/50 ++ DECstation 5000/150 ++ DECstation 5000/260 ++ DECsystem 5900/260 + -+#ifndef __AG71XX_H -+#define __AG71XX_H ++ otherwise choose R3000. + -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include ++config MACH_JAZZ ++ bool "Jazz family of machines" ++ select ARC ++ select ARC32 ++ select ARCH_MAY_HAVE_PC_FDC ++ select CEVT_R4K ++ select CSRC_R4K ++ select DEFAULT_SGI_PARTITION if CPU_BIG_ENDIAN ++ select GENERIC_ISA_DMA ++ select IRQ_CPU ++ select I8253 ++ select I8259 ++ select ISA ++ select SYS_HAS_CPU_R4X00 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL if EXPERIMENTAL ++ select SYS_SUPPORTS_100HZ ++ help ++ This a family of machines based on the MIPS R4030 chipset which was ++ used by several vendors to build RISC/os and Windows NT workstations. ++ Members include the Acer PICA, MIPS Magnum 4000, MIPS Millennium and ++ Olivetti M700-10 workstations. + -+#include ++config MACH_JZ4740 ++ bool "Ingenic JZ4740 based machines" ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select GENERIC_GPIO ++ select ARCH_REQUIRE_GPIOLIB ++ select SYS_HAS_EARLY_PRINTK ++ select HAVE_PWM ++ select HAVE_CLK + -+#include -+#include ++config LASAT ++ bool "LASAT Networks platforms" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select SYS_HAS_EARLY_PRINTK ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select PCI_GT64XXX_PCI0 ++ select MIPS_NILE4 ++ select R5000_CPU_SCACHE ++ select SYS_HAS_CPU_R5000 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL if BROKEN ++ select SYS_SUPPORTS_LITTLE_ENDIAN + -+#define ETH_FCS_LEN 4 ++config MACH_LOONGSON ++ bool "Loongson family of machines" ++ select SYS_SUPPORTS_ZBOOT ++ help ++ This enables the support of Loongson family of machines. ++ ++ Loongson is a family of general-purpose MIPS-compatible CPUs. ++ developed at Institute of Computing Technology (ICT), ++ Chinese Academy of Sciences (CAS) in the People's Republic ++ of China. The chief architect is Professor Weiwu Hu. ++ ++config MIPS_MALTA ++ bool "MIPS Malta board" ++ select ARCH_MAY_HAVE_PC_FDC ++ select BOOT_ELF32 ++ select BOOT_RAW ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select GENERIC_ISA_DMA ++ select IRQ_CPU ++ select IRQ_GIC ++ select HW_HAS_PCI ++ select I8253 ++ select I8259 ++ select MIPS_BOARDS_GEN ++ select MIPS_BONITO64 ++ select MIPS_CPU_SCACHE ++ select PCI_GT64XXX_PCI0 ++ select MIPS_MSC ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_HAS_CPU_MIPS64_R1 ++ select SYS_HAS_CPU_NEVADA ++ select SYS_HAS_CPU_RM7000 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SYS_SUPPORTS_MIPS_CMP ++ select SYS_SUPPORTS_MULTITHREADING ++ select SYS_SUPPORTS_SMARTMIPS ++ select SYS_SUPPORTS_ZBOOT ++ help ++ This enables support for the MIPS Technologies Malta evaluation ++ board. + -+#define AG71XX_DRV_NAME "ag71xx" -+#define AG71XX_DRV_VERSION "0.5.35" ++config MIPS_SIM ++ bool 'MIPS simulator (MIPSsim)' ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select SYS_HAS_EARLY_PRINTK ++ select IRQ_CPU ++ select BOOT_RAW ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_MULTITHREADING ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ help ++ This option enables support for MIPS Technologies MIPSsim software ++ emulator. + -+#define AG71XX_NAPI_WEIGHT 64 -+#define AG71XX_OOM_REFILL (1 + HZ/10) ++config NEC_MARKEINS ++ bool "NEC EMMA2RH Mark-eins board" ++ select SOC_EMMA2RH ++ select HW_HAS_PCI ++ help ++ This enables support for the NEC Electronics Mark-eins boards. + -+#define AG71XX_INT_ERR (AG71XX_INT_RX_BE | AG71XX_INT_TX_BE) -+#define AG71XX_INT_TX (AG71XX_INT_TX_PS) -+#define AG71XX_INT_RX (AG71XX_INT_RX_PR | AG71XX_INT_RX_OF) ++config MACH_VR41XX ++ bool "NEC VR4100 series based machines" ++ select CEVT_R4K ++ select CSRC_R4K ++ select SYS_HAS_CPU_VR41XX ++ select ARCH_REQUIRE_GPIOLIB + -+#define AG71XX_INT_POLL (AG71XX_INT_RX | AG71XX_INT_TX) -+#define AG71XX_INT_INIT (AG71XX_INT_ERR | AG71XX_INT_POLL) ++config NXP_STB220 ++ bool "NXP STB220 board" ++ select SOC_PNX833X ++ help ++ Support for NXP Semiconductors STB220 Development Board. + -+#define AG71XX_TX_FIFO_LEN 2048 -+#define AG71XX_TX_MTU_LEN 1536 -+#define AG71XX_RX_PKT_RESERVE 64 -+#define AG71XX_RX_PKT_SIZE \ -+ (AG71XX_RX_PKT_RESERVE + ETH_HLEN + ETH_FRAME_LEN + ETH_FCS_LEN) ++config NXP_STB225 ++ bool "NXP 225 board" ++ select SOC_PNX833X ++ select SOC_PNX8335 ++ help ++ Support for NXP Semiconductors STB225 Development Board. + -+#define AG71XX_TX_RING_SIZE 64 -+#define AG71XX_TX_THRES_STOP (AG71XX_TX_RING_SIZE - 4) -+#define AG71XX_TX_THRES_WAKEUP \ -+ (AG71XX_TX_RING_SIZE - (AG71XX_TX_RING_SIZE / 4)) ++config PNX8550_JBS ++ bool "NXP PNX8550 based JBS board" ++ select PNX8550 ++ select SYS_SUPPORTS_LITTLE_ENDIAN + -+#define AG71XX_RX_RING_SIZE 128 ++config PNX8550_STB810 ++ bool "NXP PNX8550 based STB810 board" ++ select PNX8550 ++ select SYS_SUPPORTS_LITTLE_ENDIAN + -+#ifdef CONFIG_AG71XX_DEBUG -+#define DBG(fmt, args...) printk(KERN_DEBUG fmt, ## args) -+#else -+#define DBG(fmt, args...) do {} while (0) -+#endif ++config PMC_MSP ++ bool "PMC-Sierra MSP chipsets" ++ depends on EXPERIMENTAL ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select SWAP_IO_SPACE ++ select NO_EXCEPT_FILL ++ select BOOT_RAW ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select IRQ_CPU ++ select SERIAL_8250 ++ select SERIAL_8250_CONSOLE ++ help ++ This adds support for the PMC-Sierra family of Multi-Service ++ Processor System-On-A-Chips. These parts include a number ++ of integrated peripherals, interfaces and DSPs in addition to ++ a variety of MIPS cores. + -+#define ag71xx_assert(_cond) \ -+do { \ -+ if (_cond) \ -+ break; \ -+ printk("%s,%d: assertion failed\n", __FILE__, __LINE__); \ -+ BUG(); \ -+} while (0) ++config PMC_YOSEMITE ++ bool "PMC-Sierra Yosemite eval board" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_COHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select IRQ_CPU_RM7K ++ select IRQ_CPU_RM9K ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_RM9000 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_SMP ++ help ++ Yosemite is an evaluation board for the RM9000x2 processor ++ manufactured by PMC-Sierra. + -+struct ag71xx_desc { -+ u32 data; -+ u32 ctrl; -+#define DESC_EMPTY BIT(31) -+#define DESC_MORE BIT(24) -+#define DESC_PKTLEN_M 0xfff -+ u32 next; -+ u32 pad; -+} __attribute__((aligned(4))); ++config POWERTV ++ bool "Cisco PowerTV" ++ select BOOT_ELF32 ++ select CEVT_R4K ++ select CPU_MIPSR2_IRQ_VI ++ select CPU_MIPSR2_IRQ_EI ++ select CSRC_POWERTV ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select USB_OHCI_LITTLE_ENDIAN ++ help ++ This enables support for the Cisco PowerTV Platform. + -+struct ag71xx_buf { -+ struct sk_buff *skb; -+ struct ag71xx_desc *desc; -+ dma_addr_t dma_addr; -+ u32 pad; -+}; ++config SGI_IP22 ++ bool "SGI IP22 (Indy/Indigo2)" ++ select ARC ++ select ARC32 ++ select BOOT_ELF32 ++ select CEVT_R4K ++ select CSRC_R4K ++ select DEFAULT_SGI_PARTITION ++ select DMA_NONCOHERENT ++ select HW_HAS_EISA ++ select I8253 ++ select I8259 ++ select IP22_CPU_SCACHE ++ select IRQ_CPU ++ select GENERIC_ISA_DMA_SUPPORT_BROKEN ++ select SGI_HAS_I8042 ++ select SGI_HAS_INDYDOG ++ select SGI_HAS_HAL2 ++ select SGI_HAS_SEEQ ++ select SGI_HAS_WD93 ++ select SGI_HAS_ZILOG ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_R4X00 ++ select SYS_HAS_CPU_R5000 ++ # ++ # Disable EARLY_PRINTK for now since it leads to overwritten prom ++ # memory during early boot on some machines. ++ # ++ # See http://www.linux-mips.org/cgi-bin/mesg.cgi?a=linux-mips&i=20091119164009.GA15038%40deprecation.cyrius.com ++ # for a more details discussion ++ # ++ # select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ help ++ This are the SGI Indy, Challenge S and Indigo2, as well as certain ++ OEM variants like the Tandem CMN B006S. To compile a Linux kernel ++ that runs on these, say Y here. ++ ++config SGI_IP27 ++ bool "SGI IP27 (Origin200/2000)" ++ select ARC ++ select ARC64 ++ select BOOT_ELF64 ++ select DEFAULT_SGI_PARTITION ++ select DMA_COHERENT ++ select SYS_HAS_EARLY_PRINTK ++ select HW_HAS_PCI ++ select NR_CPUS_DEFAULT_64 ++ select SYS_HAS_CPU_R10000 ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_NUMA ++ select SYS_SUPPORTS_SMP ++ help ++ This are the SGI Origin 200, Origin 2000 and Onyx 2 Graphics ++ workstations. To compile a Linux kernel that runs on these, say Y ++ here. ++ ++config SGI_IP28 ++ bool "SGI IP28 (Indigo2 R10k) (EXPERIMENTAL)" ++ depends on EXPERIMENTAL ++ select ARC ++ select ARC64 ++ select BOOT_ELF64 ++ select CEVT_R4K ++ select CSRC_R4K ++ select DEFAULT_SGI_PARTITION ++ select DMA_NONCOHERENT ++ select GENERIC_ISA_DMA_SUPPORT_BROKEN ++ select IRQ_CPU ++ select HW_HAS_EISA ++ select I8253 ++ select I8259 ++ select SGI_HAS_I8042 ++ select SGI_HAS_INDYDOG ++ select SGI_HAS_HAL2 ++ select SGI_HAS_SEEQ ++ select SGI_HAS_WD93 ++ select SGI_HAS_ZILOG ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_R10000 ++ # ++ # Disable EARLY_PRINTK for now since it leads to overwritten prom ++ # memory during early boot on some machines. ++ # ++ # See http://www.linux-mips.org/cgi-bin/mesg.cgi?a=linux-mips&i=20091119164009.GA15038%40deprecation.cyrius.com ++ # for a more details discussion ++ # ++ # select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ help ++ This is the SGI Indigo2 with R10000 processor. To compile a Linux ++ kernel that runs on these, say Y here. ++ ++config SGI_IP32 ++ bool "SGI IP32 (O2)" ++ select ARC ++ select ARC32 ++ select BOOT_ELF32 ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select R5000_CPU_SCACHE ++ select RM7000_CPU_SCACHE ++ select SYS_HAS_CPU_R5000 ++ select SYS_HAS_CPU_R10000 if BROKEN ++ select SYS_HAS_CPU_RM7000 ++ select SYS_HAS_CPU_NEVADA ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ help ++ If you want this kernel to run on SGI O2 workstation, say Y here. ++ ++config SIBYTE_CRHINE ++ bool "Sibyte BCM91120C-CRhine" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select SIBYTE_BCM1120 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_CARMEL ++ bool "Sibyte BCM91120x-Carmel" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select SIBYTE_BCM1120 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_CRHONE ++ bool "Sibyte BCM91125C-CRhone" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select SIBYTE_BCM1125 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_RHONE ++ bool "Sibyte BCM91125E-Rhone" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select SIBYTE_BCM1125H ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_SWARM ++ bool "Sibyte BCM91250A-SWARM" ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select HAVE_PATA_PLATFORM ++ select NR_CPUS_DEFAULT_2 ++ select SIBYTE_SB1250 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select ZONE_DMA32 if 64BIT ++ ++config SIBYTE_LITTLESUR ++ bool "Sibyte BCM91250C2-LittleSur" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select HAVE_PATA_PLATFORM ++ select NR_CPUS_DEFAULT_2 ++ select SIBYTE_SB1250 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_SENTOSA ++ bool "Sibyte BCM91250E-Sentosa" ++ depends on EXPERIMENTAL ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select NR_CPUS_DEFAULT_2 ++ select SIBYTE_SB1250 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ ++config SIBYTE_BIGSUR ++ bool "Sibyte BCM91480B-BigSur" ++ select BOOT_ELF32 ++ select DMA_COHERENT ++ select NR_CPUS_DEFAULT_4 ++ select SIBYTE_BCM1x80 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_SB1 ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select ZONE_DMA32 if 64BIT ++ ++config SNI_RM ++ bool "SNI RM200/300/400" ++ select ARC if CPU_LITTLE_ENDIAN ++ select ARC32 if CPU_LITTLE_ENDIAN ++ select SNIPROM if CPU_BIG_ENDIAN ++ select ARCH_MAY_HAVE_PC_FDC ++ select BOOT_ELF32 ++ select CEVT_R4K ++ select CSRC_R4K ++ select DEFAULT_SGI_PARTITION if CPU_BIG_ENDIAN ++ select DMA_NONCOHERENT ++ select GENERIC_ISA_DMA ++ select HW_HAS_EISA ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select I8253 ++ select I8259 ++ select ISA ++ select SWAP_IO_SPACE if CPU_BIG_ENDIAN ++ select SYS_HAS_CPU_R4X00 ++ select SYS_HAS_CPU_R5000 ++ select SYS_HAS_CPU_R10000 ++ select R5000_CPU_SCACHE ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL if EXPERIMENTAL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ help ++ The SNI RM200/300/400 are MIPS-based machines manufactured by ++ Siemens Nixdorf Informationssysteme (SNI), parent company of Pyramid ++ Technology and now in turn merged with Fujitsu. Say Y here to ++ support this machine type. + -+struct ag71xx_ring { -+ struct ag71xx_buf *buf; -+ u8 *descs_cpu; -+ dma_addr_t descs_dma; -+ unsigned int desc_size; -+ unsigned int curr; -+ unsigned int dirty; -+ unsigned int size; -+}; ++config MACH_TX39XX ++ bool "Toshiba TX39 series based machines" + -+struct ag71xx_mdio { -+ struct mii_bus *mii_bus; -+ int mii_irq[PHY_MAX_ADDR]; -+ void __iomem *mdio_base; -+ struct ag71xx_mdio_platform_data *pdata; -+}; ++config MACH_TX49XX ++ bool "Toshiba TX49 series based machines" + -+struct ag71xx_int_stats { -+ unsigned long rx_pr; -+ unsigned long rx_be; -+ unsigned long rx_of; -+ unsigned long tx_ps; -+ unsigned long tx_be; -+ unsigned long tx_ur; -+ unsigned long total; -+}; ++config MIKROTIK_RB532 ++ bool "Mikrotik RB532 boards" ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select IRQ_CPU ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SWAP_IO_SPACE ++ select BOOT_RAW ++ select ARCH_REQUIRE_GPIOLIB ++ help ++ Support the Mikrotik(tm) RouterBoard 532 series, ++ based on the IDT RC32434 SoC. + -+struct ag71xx_napi_stats { -+ unsigned long napi_calls; -+ unsigned long rx_count; -+ unsigned long rx_packets; -+ unsigned long rx_packets_max; -+ unsigned long tx_count; -+ unsigned long tx_packets; -+ unsigned long tx_packets_max; ++config WR_PPMC ++ bool "Wind River PPMC board" ++ select CEVT_R4K ++ select CSRC_R4K ++ select IRQ_CPU ++ select BOOT_ELF32 ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select PCI_GT64XXX_PCI0 ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_HAS_CPU_MIPS64_R1 ++ select SYS_HAS_CPU_NEVADA ++ select SYS_HAS_CPU_RM7000 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ help ++ This enables support for the Wind River MIPS32 4KC PPMC evaluation ++ board, which is based on GT64120 bridge chip. + -+ unsigned long rx[AG71XX_NAPI_WEIGHT + 1]; -+ unsigned long tx[AG71XX_NAPI_WEIGHT + 1]; -+}; ++config CAVIUM_OCTEON_SIMULATOR ++ bool "Cavium Networks Octeon Simulator" ++ select CEVT_R4K ++ select 64BIT_PHYS_ADDR ++ select DMA_COHERENT ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_HOTPLUG_CPU ++ select SYS_HAS_CPU_CAVIUM_OCTEON ++ help ++ The Octeon simulator is software performance model of the Cavium ++ Octeon Processor. It supports simulating Octeon processors on x86 ++ hardware. + -+struct ag71xx_debug { -+ struct dentry *debugfs_dir; -+ struct dentry *debugfs_int_stats; -+ struct dentry *debugfs_napi_stats; ++config CAVIUM_OCTEON_REFERENCE_BOARD ++ bool "Cavium Networks Octeon reference board" ++ select CEVT_R4K ++ select 64BIT_PHYS_ADDR ++ select DMA_COHERENT ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select SYS_SUPPORTS_HIGHMEM ++ select SYS_SUPPORTS_HOTPLUG_CPU ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_HAS_CPU_CAVIUM_OCTEON ++ select SWAP_IO_SPACE ++ select HW_HAS_PCI ++ select ARCH_SUPPORTS_MSI ++ select ZONE_DMA32 ++ select USB_ARCH_HAS_OHCI ++ select USB_ARCH_HAS_EHCI ++ help ++ This option supports all of the Octeon reference boards from Cavium ++ Networks. It builds a kernel that dynamically determines the Octeon ++ CPU type and supports all known board reference implementations. ++ Some of the supported boards are: ++ EBT3000 ++ EBH3000 ++ EBH3100 ++ Thunder ++ Kodama ++ Hikari ++ Say Y here for most Octeon reference boards. ++ ++endchoice ++ ++source "arch/mips/alchemy/Kconfig" ++source "arch/mips/ar71xx/Kconfig" ++source "arch/mips/ath79/Kconfig" ++source "arch/mips/bcm63xx/Kconfig" ++source "arch/mips/jazz/Kconfig" ++source "arch/mips/jz4740/Kconfig" ++source "arch/mips/lasat/Kconfig" ++source "arch/mips/pmc-sierra/Kconfig" ++source "arch/mips/powertv/Kconfig" ++source "arch/mips/sgi-ip27/Kconfig" ++source "arch/mips/sibyte/Kconfig" ++source "arch/mips/txx9/Kconfig" ++source "arch/mips/vr41xx/Kconfig" ++source "arch/mips/cavium-octeon/Kconfig" ++source "arch/mips/loongson/Kconfig" + -+ struct ag71xx_int_stats int_stats; -+ struct ag71xx_napi_stats napi_stats; -+}; ++endmenu + -+struct ag71xx { -+ void __iomem *mac_base; -+ void __iomem *mii_ctrl; ++config RWSEM_GENERIC_SPINLOCK ++ bool ++ default y + -+ spinlock_t lock; -+ struct platform_device *pdev; -+ struct net_device *dev; -+ struct napi_struct napi; -+ u32 msg_enable; ++config RWSEM_XCHGADD_ALGORITHM ++ bool + -+ struct ag71xx_ring rx_ring; -+ struct ag71xx_ring tx_ring; ++config ARCH_HAS_ILOG2_U32 ++ bool ++ default n + -+ struct mii_bus *mii_bus; -+ struct phy_device *phy_dev; ++config ARCH_HAS_ILOG2_U64 ++ bool ++ default n + -+ unsigned int link; -+ unsigned int speed; -+ int duplex; ++config ARCH_SUPPORTS_OPROFILE ++ bool ++ default y if !MIPS_MT_SMTC + -+ struct work_struct restart_work; -+ struct timer_list oom_timer; ++config GENERIC_FIND_NEXT_BIT ++ bool ++ default y + -+#ifdef CONFIG_AG71XX_DEBUG_FS -+ struct ag71xx_debug debug; -+#endif -+}; ++config GENERIC_FIND_BIT_LE ++ bool ++ default y + -+extern struct ethtool_ops ag71xx_ethtool_ops; -+void ag71xx_link_adjust(struct ag71xx *ag); ++config GENERIC_HWEIGHT ++ bool ++ default y + -+int ag71xx_mdio_driver_init(void) __init; -+void ag71xx_mdio_driver_exit(void); ++config GENERIC_CALIBRATE_DELAY ++ bool ++ default y + -+int ag71xx_phy_connect(struct ag71xx *ag); -+void ag71xx_phy_disconnect(struct ag71xx *ag); -+void ag71xx_phy_start(struct ag71xx *ag); -+void ag71xx_phy_stop(struct ag71xx *ag); ++config GENERIC_CLOCKEVENTS ++ bool ++ default y + -+static inline struct ag71xx_platform_data *ag71xx_get_pdata(struct ag71xx *ag) -+{ -+ return ag->pdev->dev.platform_data; -+} ++config GENERIC_CMOS_UPDATE ++ bool ++ default y + -+static inline int ag71xx_desc_empty(struct ag71xx_desc *desc) -+{ -+ return ((desc->ctrl & DESC_EMPTY) != 0); -+} ++config SCHED_OMIT_FRAME_POINTER ++ bool ++ default y + -+static inline int ag71xx_desc_pktlen(struct ag71xx_desc *desc) -+{ -+ return (desc->ctrl & DESC_PKTLEN_M); -+} ++# ++# Select some configuration options automatically based on user selections. ++# ++config ARC ++ bool + -+/* Register offsets */ -+#define AG71XX_REG_MAC_CFG1 0x0000 -+#define AG71XX_REG_MAC_CFG2 0x0004 -+#define AG71XX_REG_MAC_IPG 0x0008 -+#define AG71XX_REG_MAC_HDX 0x000c -+#define AG71XX_REG_MAC_MFL 0x0010 -+#define AG71XX_REG_MII_CFG 0x0020 -+#define AG71XX_REG_MII_CMD 0x0024 -+#define AG71XX_REG_MII_ADDR 0x0028 -+#define AG71XX_REG_MII_CTRL 0x002c -+#define AG71XX_REG_MII_STATUS 0x0030 -+#define AG71XX_REG_MII_IND 0x0034 -+#define AG71XX_REG_MAC_IFCTL 0x0038 -+#define AG71XX_REG_MAC_ADDR1 0x0040 -+#define AG71XX_REG_MAC_ADDR2 0x0044 -+#define AG71XX_REG_FIFO_CFG0 0x0048 -+#define AG71XX_REG_FIFO_CFG1 0x004c -+#define AG71XX_REG_FIFO_CFG2 0x0050 -+#define AG71XX_REG_FIFO_CFG3 0x0054 -+#define AG71XX_REG_FIFO_CFG4 0x0058 -+#define AG71XX_REG_FIFO_CFG5 0x005c -+#define AG71XX_REG_FIFO_RAM0 0x0060 -+#define AG71XX_REG_FIFO_RAM1 0x0064 -+#define AG71XX_REG_FIFO_RAM2 0x0068 -+#define AG71XX_REG_FIFO_RAM3 0x006c -+#define AG71XX_REG_FIFO_RAM4 0x0070 -+#define AG71XX_REG_FIFO_RAM5 0x0074 -+#define AG71XX_REG_FIFO_RAM6 0x0078 -+#define AG71XX_REG_FIFO_RAM7 0x007c ++config ARCH_MAY_HAVE_PC_FDC ++ bool + -+#define AG71XX_REG_TX_CTRL 0x0180 -+#define AG71XX_REG_TX_DESC 0x0184 -+#define AG71XX_REG_TX_STATUS 0x0188 -+#define AG71XX_REG_RX_CTRL 0x018c -+#define AG71XX_REG_RX_DESC 0x0190 -+#define AG71XX_REG_RX_STATUS 0x0194 -+#define AG71XX_REG_INT_ENABLE 0x0198 -+#define AG71XX_REG_INT_STATUS 0x019c ++config BOOT_RAW ++ bool + -+#define MAC_CFG1_TXE BIT(0) /* Tx Enable */ -+#define MAC_CFG1_STX BIT(1) /* Synchronize Tx Enable */ -+#define MAC_CFG1_RXE BIT(2) /* Rx Enable */ -+#define MAC_CFG1_SRX BIT(3) /* Synchronize Rx Enable */ -+#define MAC_CFG1_TFC BIT(4) /* Tx Flow Control Enable */ -+#define MAC_CFG1_RFC BIT(5) /* Rx Flow Control Enable */ -+#define MAC_CFG1_LB BIT(8) /* Loopback mode */ -+#define MAC_CFG1_SR BIT(31) /* Soft Reset */ ++config CEVT_BCM1480 ++ bool + -+#define MAC_CFG2_FDX BIT(0) -+#define MAC_CFG2_CRC_EN BIT(1) -+#define MAC_CFG2_PAD_CRC_EN BIT(2) -+#define MAC_CFG2_LEN_CHECK BIT(4) -+#define MAC_CFG2_HUGE_FRAME_EN BIT(5) -+#define MAC_CFG2_IF_1000 BIT(9) -+#define MAC_CFG2_IF_10_100 BIT(8) ++config CEVT_DS1287 ++ bool + -+#define FIFO_CFG0_WTM BIT(0) /* Watermark Module */ -+#define FIFO_CFG0_RXS BIT(1) /* Rx System Module */ -+#define FIFO_CFG0_RXF BIT(2) /* Rx Fabric Module */ -+#define FIFO_CFG0_TXS BIT(3) /* Tx System Module */ -+#define FIFO_CFG0_TXF BIT(4) /* Tx Fabric Module */ -+#define FIFO_CFG0_ALL (FIFO_CFG0_WTM | FIFO_CFG0_RXS | FIFO_CFG0_RXF \ -+ | FIFO_CFG0_TXS | FIFO_CFG0_TXF) ++config CEVT_GT641XX ++ bool + -+#define FIFO_CFG0_ENABLE_SHIFT 8 ++config CEVT_R4K_LIB ++ bool + -+#define FIFO_CFG4_DE BIT(0) /* Drop Event */ -+#define FIFO_CFG4_DV BIT(1) /* RX_DV Event */ -+#define FIFO_CFG4_FC BIT(2) /* False Carrier */ -+#define FIFO_CFG4_CE BIT(3) /* Code Error */ -+#define FIFO_CFG4_CR BIT(4) /* CRC error */ -+#define FIFO_CFG4_LM BIT(5) /* Length Mismatch */ -+#define FIFO_CFG4_LO BIT(6) /* Length out of range */ -+#define FIFO_CFG4_OK BIT(7) /* Packet is OK */ -+#define FIFO_CFG4_MC BIT(8) /* Multicast Packet */ -+#define FIFO_CFG4_BC BIT(9) /* Broadcast Packet */ -+#define FIFO_CFG4_DR BIT(10) /* Dribble */ -+#define FIFO_CFG4_LE BIT(11) /* Long Event */ -+#define FIFO_CFG4_CF BIT(12) /* Control Frame */ -+#define FIFO_CFG4_PF BIT(13) /* Pause Frame */ -+#define FIFO_CFG4_UO BIT(14) /* Unsupported Opcode */ -+#define FIFO_CFG4_VT BIT(15) /* VLAN tag detected */ -+#define FIFO_CFG4_FT BIT(16) /* Frame Truncated */ -+#define FIFO_CFG4_UC BIT(17) /* Unicast Packet */ ++config CEVT_R4K ++ select CEVT_R4K_LIB ++ bool + -+#define FIFO_CFG5_DE BIT(0) /* Drop Event */ -+#define FIFO_CFG5_DV BIT(1) /* RX_DV Event */ -+#define FIFO_CFG5_FC BIT(2) /* False Carrier */ -+#define FIFO_CFG5_CE BIT(3) /* Code Error */ -+#define FIFO_CFG5_LM BIT(4) /* Length Mismatch */ -+#define FIFO_CFG5_LO BIT(5) /* Length Out of Range */ -+#define FIFO_CFG5_OK BIT(6) /* Packet is OK */ -+#define FIFO_CFG5_MC BIT(7) /* Multicast Packet */ -+#define FIFO_CFG5_BC BIT(8) /* Broadcast Packet */ -+#define FIFO_CFG5_DR BIT(9) /* Dribble */ -+#define FIFO_CFG5_CF BIT(10) /* Control Frame */ -+#define FIFO_CFG5_PF BIT(11) /* Pause Frame */ -+#define FIFO_CFG5_UO BIT(12) /* Unsupported Opcode */ -+#define FIFO_CFG5_VT BIT(13) /* VLAN tag detected */ -+#define FIFO_CFG5_LE BIT(14) /* Long Event */ -+#define FIFO_CFG5_FT BIT(15) /* Frame Truncated */ -+#define FIFO_CFG5_16 BIT(16) /* unknown */ -+#define FIFO_CFG5_17 BIT(17) /* unknown */ -+#define FIFO_CFG5_SF BIT(18) /* Short Frame */ -+#define FIFO_CFG5_BM BIT(19) /* Byte Mode */ ++config CEVT_SB1250 ++ bool + -+#define AG71XX_INT_TX_PS BIT(0) -+#define AG71XX_INT_TX_UR BIT(1) -+#define AG71XX_INT_TX_BE BIT(3) -+#define AG71XX_INT_RX_PR BIT(4) -+#define AG71XX_INT_RX_OF BIT(6) -+#define AG71XX_INT_RX_BE BIT(7) ++config CEVT_TXX9 ++ bool + -+#define MAC_IFCTL_SPEED BIT(16) ++config CSRC_BCM1480 ++ bool + -+#define MII_CFG_CLK_DIV_4 0 -+#define MII_CFG_CLK_DIV_6 2 -+#define MII_CFG_CLK_DIV_8 3 -+#define MII_CFG_CLK_DIV_10 4 -+#define MII_CFG_CLK_DIV_14 5 -+#define MII_CFG_CLK_DIV_20 6 -+#define MII_CFG_CLK_DIV_28 7 -+#define MII_CFG_RESET BIT(31) ++config CSRC_IOASIC ++ bool + -+#define MII_CMD_WRITE 0x0 -+#define MII_CMD_READ 0x1 -+#define MII_ADDR_SHIFT 8 -+#define MII_IND_BUSY BIT(0) -+#define MII_IND_INVALID BIT(2) ++config CSRC_POWERTV ++ bool + -+#define TX_CTRL_TXE BIT(0) /* Tx Enable */ ++config CSRC_R4K_LIB ++ bool + -+#define TX_STATUS_PS BIT(0) /* Packet Sent */ -+#define TX_STATUS_UR BIT(1) /* Tx Underrun */ -+#define TX_STATUS_BE BIT(3) /* Bus Error */ ++config CSRC_R4K ++ select CSRC_R4K_LIB ++ bool + -+#define RX_CTRL_RXE BIT(0) /* Rx Enable */ ++config CSRC_SB1250 ++ bool + -+#define RX_STATUS_PR BIT(0) /* Packet Received */ -+#define RX_STATUS_OF BIT(2) /* Rx Overflow */ -+#define RX_STATUS_BE BIT(3) /* Bus Error */ ++config GPIO_TXX9 ++ select GENERIC_GPIO ++ select ARCH_REQUIRE_GPIOLIB ++ bool + -+#define MII_CTRL_IF_MASK 3 -+#define MII_CTRL_SPEED_SHIFT 4 -+#define MII_CTRL_SPEED_MASK 3 -+#define MII_CTRL_SPEED_10 0 -+#define MII_CTRL_SPEED_100 1 -+#define MII_CTRL_SPEED_1000 2 ++config CFE ++ bool + -+static inline void ag71xx_check_reg_offset(struct ag71xx *ag, unsigned reg) -+{ -+ switch (reg) { -+ case AG71XX_REG_MAC_CFG1 ... AG71XX_REG_MAC_MFL: -+ case AG71XX_REG_MAC_IFCTL ... AG71XX_REG_INT_STATUS: -+ break; ++config ARCH_DMA_ADDR_T_64BIT ++ def_bool (HIGHMEM && 64BIT_PHYS_ADDR) || 64BIT + -+ default: -+ BUG(); -+ } -+} ++config DMA_COHERENT ++ bool + -+static inline void ag71xx_wr(struct ag71xx *ag, unsigned reg, u32 value) -+{ -+ ag71xx_check_reg_offset(ag, reg); ++config DMA_NONCOHERENT ++ bool ++ select NEED_DMA_MAP_STATE + -+ __raw_writel(value, ag->mac_base + reg); -+ /* flush write */ -+ (void) __raw_readl(ag->mac_base + reg); -+} ++config NEED_DMA_MAP_STATE ++ bool + -+static inline u32 ag71xx_rr(struct ag71xx *ag, unsigned reg) -+{ -+ ag71xx_check_reg_offset(ag, reg); ++config SYS_HAS_EARLY_PRINTK ++ bool + -+ return __raw_readl(ag->mac_base + reg); -+} ++config HOTPLUG_CPU ++ bool "Support for hot-pluggable CPUs" ++ depends on SMP && HOTPLUG && SYS_SUPPORTS_HOTPLUG_CPU ++ help ++ Say Y here to allow turning CPUs off and on. CPUs can be ++ controlled through /sys/devices/system/cpu. ++ (Note: power management support will enable this option ++ automatically on SMP systems. ) ++ Say N if you want to disable CPU hotplug. + -+static inline void ag71xx_sb(struct ag71xx *ag, unsigned reg, u32 mask) -+{ -+ void __iomem *r; ++config SYS_SUPPORTS_HOTPLUG_CPU ++ bool + -+ ag71xx_check_reg_offset(ag, reg); ++config I8259 ++ bool + -+ r = ag->mac_base + reg; -+ __raw_writel(__raw_readl(r) | mask, r); -+ /* flush write */ -+ (void)__raw_readl(r); -+} ++config MIPS_BONITO64 ++ bool + -+static inline void ag71xx_cb(struct ag71xx *ag, unsigned reg, u32 mask) -+{ -+ void __iomem *r; ++config MIPS_MSC ++ bool + -+ ag71xx_check_reg_offset(ag, reg); ++config MIPS_NILE4 ++ bool + -+ r = ag->mac_base + reg; -+ __raw_writel(__raw_readl(r) & ~mask, r); -+ /* flush write */ -+ (void) __raw_readl(r); -+} ++config MIPS_DISABLE_OBSOLETE_IDE ++ bool + -+static inline void ag71xx_int_enable(struct ag71xx *ag, u32 ints) -+{ -+ ag71xx_sb(ag, AG71XX_REG_INT_ENABLE, ints); -+} ++config SYNC_R4K ++ bool + -+static inline void ag71xx_int_disable(struct ag71xx *ag, u32 ints) -+{ -+ ag71xx_cb(ag, AG71XX_REG_INT_ENABLE, ints); -+} ++config MIPS_MACHINE ++ def_bool n + -+static inline void ag71xx_mii_ctrl_wr(struct ag71xx *ag, u32 value) -+{ -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++config NO_IOPORT ++ def_bool n + -+ if (pdata->is_ar724x) -+ return; ++config GENERIC_ISA_DMA ++ bool ++ select ZONE_DMA if GENERIC_ISA_DMA_SUPPORT_BROKEN=n ++ select ISA_DMA_API + -+ __raw_writel(value, ag->mii_ctrl); ++config GENERIC_ISA_DMA_SUPPORT_BROKEN ++ bool ++ select GENERIC_ISA_DMA + -+ /* flush write */ -+ __raw_readl(ag->mii_ctrl); -+} ++config ISA_DMA_API ++ bool + -+static inline u32 ag71xx_mii_ctrl_rr(struct ag71xx *ag) -+{ -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++config GENERIC_GPIO ++ bool + -+ if (pdata->is_ar724x) -+ return 0xffffffff; ++# ++# Endianess selection. Sufficiently obscure so many users don't know what to ++# answer,so we try hard to limit the available choices. Also the use of a ++# choice statement should be more obvious to the user. ++# ++choice ++ prompt "Endianess selection" ++ help ++ Some MIPS machines can be configured for either little or big endian ++ byte order. These modes require different kernels and a different ++ Linux distribution. In general there is one preferred byteorder for a ++ particular system but some systems are just as commonly used in the ++ one or the other endianness. ++ ++config CPU_BIG_ENDIAN ++ bool "Big endian" ++ depends on SYS_SUPPORTS_BIG_ENDIAN ++ ++config CPU_LITTLE_ENDIAN ++ bool "Little endian" ++ depends on SYS_SUPPORTS_LITTLE_ENDIAN ++ help + -+ return __raw_readl(ag->mii_ctrl); -+} ++endchoice + -+static void inline ag71xx_mii_ctrl_set_if(struct ag71xx *ag, -+ unsigned int mii_if) -+{ -+ u32 t; ++config EXPORT_UASM ++ bool + -+ t = ag71xx_mii_ctrl_rr(ag); -+ t &= ~(MII_CTRL_IF_MASK); -+ t |= (mii_if & MII_CTRL_IF_MASK); -+ ag71xx_mii_ctrl_wr(ag, t); -+} ++config SYS_SUPPORTS_APM_EMULATION ++ bool + -+static void inline ag71xx_mii_ctrl_set_speed(struct ag71xx *ag, -+ unsigned int speed) -+{ -+ u32 t; ++config SYS_SUPPORTS_BIG_ENDIAN ++ bool + -+ t = ag71xx_mii_ctrl_rr(ag); -+ t &= ~(MII_CTRL_SPEED_MASK << MII_CTRL_SPEED_SHIFT); -+ t |= (speed & MII_CTRL_SPEED_MASK) << MII_CTRL_SPEED_SHIFT; -+ ag71xx_mii_ctrl_wr(ag, t); -+} ++config SYS_SUPPORTS_LITTLE_ENDIAN ++ bool + -+#ifdef CONFIG_AG71XX_AR8216_SUPPORT -+void ag71xx_add_ar8216_header(struct ag71xx *ag, struct sk_buff *skb); -+int ag71xx_remove_ar8216_header(struct ag71xx *ag, struct sk_buff *skb, -+ int pktlen); -+static inline int ag71xx_has_ar8216(struct ag71xx *ag) -+{ -+ return ag71xx_get_pdata(ag)->has_ar8216; -+} -+#else -+static inline void ag71xx_add_ar8216_header(struct ag71xx *ag, -+ struct sk_buff *skb) -+{ -+} ++config SYS_SUPPORTS_HUGETLBFS ++ bool ++ depends on CPU_SUPPORTS_HUGEPAGES && 64BIT ++ default y + -+static inline int ag71xx_remove_ar8216_header(struct ag71xx *ag, -+ struct sk_buff *skb, -+ int pktlen) -+{ -+ return 0; -+} -+static inline int ag71xx_has_ar8216(struct ag71xx *ag) -+{ -+ return 0; -+} -+#endif ++config IRQ_CPU ++ bool + -+#ifdef CONFIG_AG71XX_DEBUG_FS -+int ag71xx_debugfs_root_init(void); -+void ag71xx_debugfs_root_exit(void); -+int ag71xx_debugfs_init(struct ag71xx *ag); -+void ag71xx_debugfs_exit(struct ag71xx *ag); -+void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, u32 status); -+void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, int rx, int tx); -+#else -+static inline int ag71xx_debugfs_root_init(void) { return 0; } -+static inline void ag71xx_debugfs_root_exit(void) {} -+static inline int ag71xx_debugfs_init(struct ag71xx *ag) { return 0; } -+static inline void ag71xx_debugfs_exit(struct ag71xx *ag) {} -+static inline void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, -+ u32 status) {} -+static inline void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, -+ int rx, int tx) {} -+#endif /* CONFIG_AG71XX_DEBUG_FS */ ++config IRQ_CPU_RM7K ++ bool + -+#endif /* _AG71XX_H */ -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar8216.c linux-2.6.39/drivers/net/ag71xx/ag71xx_ar8216.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar8216.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_ar8216.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,44 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * Special support for the Atheros ar8216 switch chip -+ * -+ * Copyright (C) 2009-2010 Gabor Juhos -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++config IRQ_CPU_RM9K ++ bool + -+#include "ag71xx.h" ++config IRQ_MSP_SLP ++ bool + -+#define AR8216_PACKET_TYPE_MASK 0xf -+#define AR8216_PACKET_TYPE_NORMAL 0 ++config IRQ_MSP_CIC ++ bool + -+#define AR8216_HEADER_LEN 2 ++config IRQ_TXX9 ++ bool + -+void ag71xx_add_ar8216_header(struct ag71xx *ag, struct sk_buff *skb) -+{ -+ skb_push(skb, AR8216_HEADER_LEN); -+ skb->data[0] = 0x10; -+ skb->data[1] = 0x80; -+} ++config IRQ_GT641XX ++ bool + -+int ag71xx_remove_ar8216_header(struct ag71xx *ag, struct sk_buff *skb, -+ int pktlen) -+{ -+ u8 type; ++config IRQ_GIC ++ bool + -+ type = skb->data[1] & AR8216_PACKET_TYPE_MASK; -+ switch (type) { -+ case AR8216_PACKET_TYPE_NORMAL: -+ break; ++config MIPS_BOARDS_GEN ++ bool + -+ default: -+ return -EINVAL; -+ } ++config PCI_GT64XXX_PCI0 ++ bool + -+ skb_pull(skb, AR8216_HEADER_LEN); -+ return 0; -+} -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_debugfs.c linux-2.6.39/drivers/net/ag71xx/ag71xx_debugfs.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_debugfs.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_debugfs.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,197 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++config NO_EXCEPT_FILL ++ bool + -+#include ++config MIPS_RM9122 ++ bool ++ select SERIAL_RM9000 + -+#include "ag71xx.h" ++config SOC_EMMA2RH ++ bool ++ select CEVT_R4K ++ select CSRC_R4K ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SWAP_IO_SPACE ++ select SYS_HAS_CPU_R5500 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_BIG_ENDIAN + -+static struct dentry *ag71xx_debugfs_root; ++config SOC_PNX833X ++ bool ++ select CEVT_R4K ++ select CSRC_R4K ++ select IRQ_CPU ++ select DMA_NONCOHERENT ++ select SYS_HAS_CPU_MIPS32_R2 ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select SYS_SUPPORTS_LITTLE_ENDIAN ++ select SYS_SUPPORTS_BIG_ENDIAN ++ select GENERIC_GPIO ++ select CPU_MIPSR2_IRQ_VI + -+static int ag71xx_debugfs_generic_open(struct inode *inode, struct file *file) -+{ -+ file->private_data = inode->i_private; -+ return 0; -+} ++config SOC_PNX8335 ++ bool ++ select SOC_PNX833X + -+void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, u32 status) -+{ -+ if (status) -+ ag->debug.int_stats.total++; -+ if (status & AG71XX_INT_TX_PS) -+ ag->debug.int_stats.tx_ps++; -+ if (status & AG71XX_INT_TX_UR) -+ ag->debug.int_stats.tx_ur++; -+ if (status & AG71XX_INT_TX_BE) -+ ag->debug.int_stats.tx_be++; -+ if (status & AG71XX_INT_RX_PR) -+ ag->debug.int_stats.rx_pr++; -+ if (status & AG71XX_INT_RX_OF) -+ ag->debug.int_stats.rx_of++; -+ if (status & AG71XX_INT_RX_BE) -+ ag->debug.int_stats.rx_be++; -+} ++config PNX8550 ++ bool ++ select SOC_PNX8550 + -+static ssize_t read_file_int_stats(struct file *file, char __user *user_buf, -+ size_t count, loff_t *ppos) -+{ -+#define PR_INT_STAT(_label, _field) \ -+ len += snprintf(buf + len, sizeof(buf) - len, \ -+ "%20s: %10lu\n", _label, ag->debug.int_stats._field); ++config SOC_PNX8550 ++ bool ++ select DMA_NONCOHERENT ++ select HW_HAS_PCI ++ select SYS_HAS_CPU_MIPS32_R1 ++ select SYS_HAS_EARLY_PRINTK ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select GENERIC_GPIO + -+ struct ag71xx *ag = file->private_data; -+ char buf[256]; -+ unsigned int len = 0; ++config SWAP_IO_SPACE ++ bool + -+ PR_INT_STAT("TX Packet Sent", tx_ps); -+ PR_INT_STAT("TX Underrun", tx_ur); -+ PR_INT_STAT("TX Bus Error", tx_be); -+ PR_INT_STAT("RX Packet Received", rx_pr); -+ PR_INT_STAT("RX Overflow", rx_of); -+ PR_INT_STAT("RX Bus Error", rx_be); -+ len += snprintf(buf + len, sizeof(buf) - len, "\n"); -+ PR_INT_STAT("Total", total); ++config SERIAL_RM9000 ++ bool + -+ return simple_read_from_buffer(user_buf, count, ppos, buf, len); -+#undef PR_INT_STAT -+} ++config SGI_HAS_INDYDOG ++ bool + -+static const struct file_operations ag71xx_fops_int_stats = { -+ .open = ag71xx_debugfs_generic_open, -+ .read = read_file_int_stats, -+ .owner = THIS_MODULE -+}; ++config SGI_HAS_HAL2 ++ bool + -+void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, int rx, int tx) -+{ -+ struct ag71xx_napi_stats *stats = &ag->debug.napi_stats; ++config SGI_HAS_SEEQ ++ bool + -+ if (rx) { -+ stats->rx_count++; -+ stats->rx_packets += rx; -+ if (rx <= AG71XX_NAPI_WEIGHT) -+ stats->rx[rx]++; -+ if (rx > stats->rx_packets_max) -+ stats->rx_packets_max = rx; -+ } ++config SGI_HAS_WD93 ++ bool + -+ if (tx) { -+ stats->tx_count++; -+ stats->tx_packets += tx; -+ if (tx <= AG71XX_NAPI_WEIGHT) -+ stats->tx[tx]++; -+ if (tx > stats->tx_packets_max) -+ stats->tx_packets_max = tx; -+ } -+} ++config SGI_HAS_ZILOG ++ bool + -+static ssize_t read_file_napi_stats(struct file *file, char __user *user_buf, -+ size_t count, loff_t *ppos) -+{ -+ struct ag71xx *ag = file->private_data; -+ struct ag71xx_napi_stats *stats = &ag->debug.napi_stats; -+ char buf[2048]; -+ unsigned int len = 0; -+ unsigned long rx_avg = 0; -+ unsigned long tx_avg = 0; -+ int i; ++config SGI_HAS_I8042 ++ bool + -+ if (stats->rx_count) -+ rx_avg = stats->rx_packets / stats->rx_count; ++config DEFAULT_SGI_PARTITION ++ bool + -+ if (stats->tx_count) -+ tx_avg = stats->tx_packets / stats->tx_count; ++config ARC32 ++ bool + -+ len += snprintf(buf + len, sizeof(buf) - len, "%3s %10s %10s\n", -+ "len", "rx", "tx"); ++config SNIPROM ++ bool + -+ for (i = 1; i <= AG71XX_NAPI_WEIGHT; i++) -+ len += snprintf(buf + len, sizeof(buf) - len, -+ "%3d: %10lu %10lu\n", -+ i, stats->rx[i], stats->tx[i]); ++config BOOT_ELF32 ++ bool + -+ len += snprintf(buf + len, sizeof(buf) - len, "\n"); ++config MIPS_L1_CACHE_SHIFT ++ int ++ default "4" if MACH_DECSTATION || MIKROTIK_RB532 || PMC_MSP4200_EVAL ++ default "6" if MIPS_CPU_SCACHE ++ default "7" if SGI_IP22 || SGI_IP27 || SGI_IP28 || SNI_RM || CPU_CAVIUM_OCTEON ++ default "5" + -+ len += snprintf(buf + len, sizeof(buf) - len, "%3s: %10lu %10lu\n", -+ "sum", stats->rx_count, stats->tx_count); -+ len += snprintf(buf + len, sizeof(buf) - len, "%3s: %10lu %10lu\n", -+ "avg", rx_avg, tx_avg); -+ len += snprintf(buf + len, sizeof(buf) - len, "%3s: %10lu %10lu\n", -+ "max", stats->rx_packets_max, stats->tx_packets_max); -+ len += snprintf(buf + len, sizeof(buf) - len, "%3s: %10lu %10lu\n", -+ "pkt", stats->rx_packets, stats->tx_packets); ++config HAVE_STD_PC_SERIAL_PORT ++ bool + -+ return simple_read_from_buffer(user_buf, count, ppos, buf, len); -+} ++config ARC_CONSOLE ++ bool "ARC console support" ++ depends on SGI_IP22 || SGI_IP28 || (SNI_RM && CPU_LITTLE_ENDIAN) + -+static const struct file_operations ag71xx_fops_napi_stats = { -+ .open = ag71xx_debugfs_generic_open, -+ .read = read_file_napi_stats, -+ .owner = THIS_MODULE -+}; ++config ARC_MEMORY ++ bool ++ depends on MACH_JAZZ || SNI_RM || SGI_IP32 ++ default y + -+void ag71xx_debugfs_exit(struct ag71xx *ag) -+{ -+ debugfs_remove(ag->debug.debugfs_napi_stats); -+ debugfs_remove(ag->debug.debugfs_int_stats); -+ debugfs_remove(ag->debug.debugfs_dir); -+} ++config ARC_PROMLIB ++ bool ++ depends on MACH_JAZZ || SNI_RM || SGI_IP22 || SGI_IP28 || SGI_IP32 ++ default y + -+int ag71xx_debugfs_init(struct ag71xx *ag) -+{ -+ ag->debug.debugfs_dir = debugfs_create_dir(ag->dev->name, -+ ag71xx_debugfs_root); -+ if (!ag->debug.debugfs_dir) -+ goto err; ++config ARC64 ++ bool + -+ ag->debug.debugfs_int_stats = -+ debugfs_create_file("int_stats", -+ S_IRUGO, -+ ag->debug.debugfs_dir, -+ ag, -+ &ag71xx_fops_int_stats); -+ if (!ag->debug.debugfs_int_stats) -+ goto err; ++config BOOT_ELF64 ++ bool + -+ ag->debug.debugfs_napi_stats = -+ debugfs_create_file("napi_stats", -+ S_IRUGO, -+ ag->debug.debugfs_dir, -+ ag, -+ &ag71xx_fops_napi_stats); -+ if (!ag->debug.debugfs_napi_stats) -+ goto err; ++menu "CPU selection" + -+ return 0; ++choice ++ prompt "CPU type" ++ default CPU_R4X00 + -+ err: -+ ag71xx_debugfs_exit(ag); -+ return -ENOMEM; -+} ++config CPU_LOONGSON2E ++ bool "Loongson 2E" ++ depends on SYS_HAS_CPU_LOONGSON2E ++ select CPU_LOONGSON2 ++ help ++ The Loongson 2E processor implements the MIPS III instruction set ++ with many extensions. + -+int ag71xx_debugfs_root_init(void) -+{ -+ if (ag71xx_debugfs_root) -+ return -EBUSY; ++ It has an internal FPGA northbridge, which is compatible to ++ bonito64. + -+ ag71xx_debugfs_root = debugfs_create_dir(KBUILD_MODNAME, NULL); -+ if (!ag71xx_debugfs_root) -+ return -ENOENT; ++config CPU_LOONGSON2F ++ bool "Loongson 2F" ++ depends on SYS_HAS_CPU_LOONGSON2F ++ select CPU_LOONGSON2 ++ select GENERIC_GPIO ++ select ARCH_REQUIRE_GPIOLIB ++ help ++ The Loongson 2F processor implements the MIPS III instruction set ++ with many extensions. ++ ++ Loongson2F have built-in DDR2 and PCIX controller. The PCIX controller ++ have a similar programming interface with FPGA northbridge used in ++ Loongson2E. ++ ++config CPU_MIPS32_R1 ++ bool "MIPS32 Release 1" ++ depends on SYS_HAS_CPU_MIPS32_R1 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ help ++ Choose this option to build a kernel for release 1 or later of the ++ MIPS32 architecture. Most modern embedded systems with a 32-bit ++ MIPS processor are based on a MIPS32 processor. If you know the ++ specific type of processor in your system, choose those that one ++ otherwise CPU_MIPS32_R1 is a safe bet for any MIPS32 system. ++ Release 2 of the MIPS32 architecture is available since several ++ years so chances are you even have a MIPS32 Release 2 processor ++ in which case you should choose CPU_MIPS32_R2 instead for better ++ performance. ++ ++config CPU_MIPS32_R2 ++ bool "MIPS32 Release 2" ++ depends on SYS_HAS_CPU_MIPS32_R2 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ help ++ Choose this option to build a kernel for release 2 or later of the ++ MIPS32 architecture. Most modern embedded systems with a 32-bit ++ MIPS processor are based on a MIPS32 processor. If you know the ++ specific type of processor in your system, choose those that one ++ otherwise CPU_MIPS32_R1 is a safe bet for any MIPS32 system. ++ ++config CPU_MIPS64_R1 ++ bool "MIPS64 Release 1" ++ depends on SYS_HAS_CPU_MIPS64_R1 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ select CPU_SUPPORTS_HUGEPAGES ++ help ++ Choose this option to build a kernel for release 1 or later of the ++ MIPS64 architecture. Many modern embedded systems with a 64-bit ++ MIPS processor are based on a MIPS64 processor. If you know the ++ specific type of processor in your system, choose those that one ++ otherwise CPU_MIPS64_R1 is a safe bet for any MIPS64 system. ++ Release 2 of the MIPS64 architecture is available since several ++ years so chances are you even have a MIPS64 Release 2 processor ++ in which case you should choose CPU_MIPS64_R2 instead for better ++ performance. ++ ++config CPU_MIPS64_R2 ++ bool "MIPS64 Release 2" ++ depends on SYS_HAS_CPU_MIPS64_R2 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ select CPU_SUPPORTS_HUGEPAGES ++ help ++ Choose this option to build a kernel for release 2 or later of the ++ MIPS64 architecture. Many modern embedded systems with a 64-bit ++ MIPS processor are based on a MIPS64 processor. If you know the ++ specific type of processor in your system, choose those that one ++ otherwise CPU_MIPS64_R1 is a safe bet for any MIPS64 system. ++ ++config CPU_R3000 ++ bool "R3000" ++ depends on SYS_HAS_CPU_R3000 ++ select CPU_HAS_WB ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ help ++ Please make sure to pick the right CPU type. Linux/MIPS is not ++ designed to be generic, i.e. Kernels compiled for R3000 CPUs will ++ *not* work on R4000 machines and vice versa. However, since most ++ of the supported machines have an R4000 (or similar) CPU, R4x00 ++ might be a safe bet. If the resulting kernel does not work, ++ try to recompile with R3000. ++ ++config CPU_TX39XX ++ bool "R39XX" ++ depends on SYS_HAS_CPU_TX39XX ++ select CPU_SUPPORTS_32BIT_KERNEL ++ ++config CPU_VR41XX ++ bool "R41xx" ++ depends on SYS_HAS_CPU_VR41XX ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ The options selects support for the NEC VR4100 series of processors. ++ Only choose this option if you have one of these processors as a ++ kernel built with this option will not run on any other type of ++ processor or vice versa. ++ ++config CPU_R4300 ++ bool "R4300" ++ depends on SYS_HAS_CPU_R4300 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ MIPS Technologies R4300-series processors. + -+ return 0; -+} ++config CPU_R4X00 ++ bool "R4x00" ++ depends on SYS_HAS_CPU_R4X00 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ MIPS Technologies R4000-series processors other than 4300, including ++ the R4000, R4400, R4600, and 4700. ++ ++config CPU_TX49XX ++ bool "R49XX" ++ depends on SYS_HAS_CPU_TX49XX ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ ++config CPU_R5000 ++ bool "R5000" ++ depends on SYS_HAS_CPU_R5000 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ MIPS Technologies R5000-series processors other than the Nevada. ++ ++config CPU_R5432 ++ bool "R5432" ++ depends on SYS_HAS_CPU_R5432 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ ++config CPU_R5500 ++ bool "R5500" ++ depends on SYS_HAS_CPU_R5500 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HUGEPAGES ++ help ++ NEC VR5500 and VR5500A series processors implement 64-bit MIPS IV ++ instruction set. ++ ++config CPU_R6000 ++ bool "R6000" ++ depends on EXPERIMENTAL ++ depends on SYS_HAS_CPU_R6000 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ help ++ MIPS Technologies R6000 and R6000A series processors. Note these ++ processors are extremely rare and the support for them is incomplete. ++ ++config CPU_NEVADA ++ bool "RM52xx" ++ depends on SYS_HAS_CPU_NEVADA ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ QED / PMC-Sierra RM52xx-series ("Nevada") processors. ++ ++config CPU_R8000 ++ bool "R8000" ++ depends on EXPERIMENTAL ++ depends on SYS_HAS_CPU_R8000 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_64BIT_KERNEL ++ help ++ MIPS Technologies R8000 processors. Note these processors are ++ uncommon and the support for them is incomplete. ++ ++config CPU_R10000 ++ bool "R10000" ++ depends on SYS_HAS_CPU_R10000 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ help ++ MIPS Technologies R10000-series processors. ++ ++config CPU_RM7000 ++ bool "RM7000" ++ depends on SYS_HAS_CPU_RM7000 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ ++config CPU_RM9000 ++ bool "RM9000" ++ depends on SYS_HAS_CPU_RM9000 ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ select WEAK_ORDERING ++ ++config CPU_SB1 ++ bool "SB1" ++ depends on SYS_HAS_CPU_SB1 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ select WEAK_ORDERING ++ ++config CPU_CAVIUM_OCTEON ++ bool "Cavium Octeon processor" ++ depends on SYS_HAS_CPU_CAVIUM_OCTEON ++ select CPU_HAS_PREFETCH ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select SYS_SUPPORTS_SMP ++ select NR_CPUS_DEFAULT_16 ++ select WEAK_ORDERING ++ select CPU_SUPPORTS_HIGHMEM ++ select CPU_SUPPORTS_HUGEPAGES ++ help ++ The Cavium Octeon processor is a highly integrated chip containing ++ many ethernet hardware widgets for networking tasks. The processor ++ can have up to 16 Mips64v2 cores and 8 integrated gigabit ethernets. ++ Full details can be found at http://www.caviumnetworks.com. ++ ++config CPU_BMIPS3300 ++ bool "BMIPS3300" ++ depends on SYS_HAS_CPU_BMIPS3300 ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SWAP_IO_SPACE ++ select SYS_SUPPORTS_32BIT_KERNEL ++ select WEAK_ORDERING ++ help ++ Broadcom BMIPS3300 processors. + -+void ag71xx_debugfs_root_exit(void) -+{ -+ debugfs_remove(ag71xx_debugfs_root); -+ ag71xx_debugfs_root = NULL; -+} -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ethtool.c linux-2.6.39/drivers/net/ag71xx/ag71xx_ethtool.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ethtool.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_ethtool.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,71 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++config CPU_BMIPS4350 ++ bool "BMIPS4350" ++ depends on SYS_HAS_CPU_BMIPS4350 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SWAP_IO_SPACE ++ select SYS_SUPPORTS_SMP ++ select SYS_SUPPORTS_HOTPLUG_CPU ++ select WEAK_ORDERING ++ help ++ Broadcom BMIPS4350 ("VIPER") processors. + -+#include "ag71xx.h" ++config CPU_BMIPS4380 ++ bool "BMIPS4380" ++ depends on SYS_HAS_CPU_BMIPS4380 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SWAP_IO_SPACE ++ select SYS_SUPPORTS_SMP ++ select SYS_SUPPORTS_HOTPLUG_CPU ++ select WEAK_ORDERING ++ help ++ Broadcom BMIPS4380 processors. + -+static int ag71xx_ethtool_get_settings(struct net_device *dev, -+ struct ethtool_cmd *cmd) -+{ -+ struct ag71xx *ag = netdev_priv(dev); -+ struct phy_device *phydev = ag->phy_dev; ++config CPU_BMIPS5000 ++ bool "BMIPS5000" ++ depends on SYS_HAS_CPU_BMIPS5000 ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM ++ select DMA_NONCOHERENT ++ select IRQ_CPU ++ select SWAP_IO_SPACE ++ select SYS_SUPPORTS_SMP ++ select SYS_SUPPORTS_HOTPLUG_CPU ++ select WEAK_ORDERING ++ help ++ Broadcom BMIPS5000 processors. + -+ if (!phydev) -+ return -ENODEV; ++endchoice + -+ return phy_ethtool_gset(phydev, cmd); -+} ++if CPU_LOONGSON2F ++config CPU_NOP_WORKAROUNDS ++ bool + -+static int ag71xx_ethtool_set_settings(struct net_device *dev, -+ struct ethtool_cmd *cmd) -+{ -+ struct ag71xx *ag = netdev_priv(dev); -+ struct phy_device *phydev = ag->phy_dev; ++config CPU_JUMP_WORKAROUNDS ++ bool + -+ if (!phydev) -+ return -ENODEV; ++config CPU_LOONGSON2F_WORKAROUNDS ++ bool "Loongson 2F Workarounds" ++ default y ++ select CPU_NOP_WORKAROUNDS ++ select CPU_JUMP_WORKAROUNDS ++ help ++ Loongson 2F01 / 2F02 processors have the NOP & JUMP issues which ++ require workarounds. Without workarounds the system may hang ++ unexpectedly. For more information please refer to the gas ++ -mfix-loongson2f-nop and -mfix-loongson2f-jump options. + -+ return phy_ethtool_sset(phydev, cmd); -+} ++ Loongson 2F03 and later have fixed these issues and no workarounds ++ are needed. The workarounds have no significant side effect on them ++ but may decrease the performance of the system so this option should ++ be disabled unless the kernel is intended to be run on 2F01 or 2F02 ++ systems. + -+static void ag71xx_ethtool_get_drvinfo(struct net_device *dev, -+ struct ethtool_drvinfo *info) -+{ -+ struct ag71xx *ag = netdev_priv(dev); ++ If unsure, please say Y. ++endif # CPU_LOONGSON2F + -+ strcpy(info->driver, ag->pdev->dev.driver->name); -+ strcpy(info->version, AG71XX_DRV_VERSION); -+ strcpy(info->bus_info, dev_name(&ag->pdev->dev)); -+} ++config SYS_SUPPORTS_ZBOOT ++ bool ++ select HAVE_KERNEL_GZIP ++ select HAVE_KERNEL_BZIP2 ++ select HAVE_KERNEL_LZMA ++ select HAVE_KERNEL_LZO + -+static u32 ag71xx_ethtool_get_msglevel(struct net_device *dev) -+{ -+ struct ag71xx *ag = netdev_priv(dev); ++config SYS_SUPPORTS_ZBOOT_UART16550 ++ bool ++ select SYS_SUPPORTS_ZBOOT + -+ return ag->msg_enable; -+} ++config CPU_LOONGSON2 ++ bool ++ select CPU_SUPPORTS_32BIT_KERNEL ++ select CPU_SUPPORTS_64BIT_KERNEL ++ select CPU_SUPPORTS_HIGHMEM + -+static void ag71xx_ethtool_set_msglevel(struct net_device *dev, u32 msg_level) -+{ -+ struct ag71xx *ag = netdev_priv(dev); ++config SYS_HAS_CPU_LOONGSON2E ++ bool + -+ ag->msg_enable = msg_level; -+} ++config SYS_HAS_CPU_LOONGSON2F ++ bool ++ select CPU_SUPPORTS_CPUFREQ ++ select CPU_SUPPORTS_ADDRWINCFG if 64BIT ++ select CPU_SUPPORTS_UNCACHED_ACCELERATED + -+struct ethtool_ops ag71xx_ethtool_ops = { -+ .set_settings = ag71xx_ethtool_set_settings, -+ .get_settings = ag71xx_ethtool_get_settings, -+ .get_drvinfo = ag71xx_ethtool_get_drvinfo, -+ .get_msglevel = ag71xx_ethtool_get_msglevel, -+ .set_msglevel = ag71xx_ethtool_set_msglevel, -+ .get_link = ethtool_op_get_link, -+}; -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_main.c linux-2.6.39/drivers/net/ag71xx/ag71xx_main.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_main.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_main.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,1184 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++config SYS_HAS_CPU_MIPS32_R1 ++ bool + -+#include "ag71xx.h" ++config SYS_HAS_CPU_MIPS32_R2 ++ bool + -+#define AG71XX_DEFAULT_MSG_ENABLE \ -+ ( NETIF_MSG_DRV \ -+ | NETIF_MSG_PROBE \ -+ | NETIF_MSG_LINK \ -+ | NETIF_MSG_TIMER \ -+ | NETIF_MSG_IFDOWN \ -+ | NETIF_MSG_IFUP \ -+ | NETIF_MSG_RX_ERR \ -+ | NETIF_MSG_TX_ERR ) ++config SYS_HAS_CPU_MIPS64_R1 ++ bool + -+static int ag71xx_msg_level = -1; ++config SYS_HAS_CPU_MIPS64_R2 ++ bool + -+module_param_named(msg_level, ag71xx_msg_level, int, 0); -+MODULE_PARM_DESC(msg_level, "Message level (-1=defaults,0=none,...,16=all)"); ++config SYS_HAS_CPU_R3000 ++ bool + -+static void ag71xx_dump_dma_regs(struct ag71xx *ag) -+{ -+ DBG("%s: dma_tx_ctrl=%08x, dma_tx_desc=%08x, dma_tx_status=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_TX_CTRL), -+ ag71xx_rr(ag, AG71XX_REG_TX_DESC), -+ ag71xx_rr(ag, AG71XX_REG_TX_STATUS)); ++config SYS_HAS_CPU_TX39XX ++ bool + -+ DBG("%s: dma_rx_ctrl=%08x, dma_rx_desc=%08x, dma_rx_status=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_RX_CTRL), -+ ag71xx_rr(ag, AG71XX_REG_RX_DESC), -+ ag71xx_rr(ag, AG71XX_REG_RX_STATUS)); -+} ++config SYS_HAS_CPU_VR41XX ++ bool + -+static void ag71xx_dump_regs(struct ag71xx *ag) -+{ -+ DBG("%s: mac_cfg1=%08x, mac_cfg2=%08x, ipg=%08x, hdx=%08x, mfl=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_MAC_CFG1), -+ ag71xx_rr(ag, AG71XX_REG_MAC_CFG2), -+ ag71xx_rr(ag, AG71XX_REG_MAC_IPG), -+ ag71xx_rr(ag, AG71XX_REG_MAC_HDX), -+ ag71xx_rr(ag, AG71XX_REG_MAC_MFL)); -+ DBG("%s: mac_ifctl=%08x, mac_addr1=%08x, mac_addr2=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL), -+ ag71xx_rr(ag, AG71XX_REG_MAC_ADDR1), -+ ag71xx_rr(ag, AG71XX_REG_MAC_ADDR2)); -+ DBG("%s: fifo_cfg0=%08x, fifo_cfg1=%08x, fifo_cfg2=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG0), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG1), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG2)); -+ DBG("%s: fifo_cfg3=%08x, fifo_cfg4=%08x, fifo_cfg5=%08x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG3), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG4), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5)); -+} ++config SYS_HAS_CPU_R4300 ++ bool + -+static inline void ag71xx_dump_intr(struct ag71xx *ag, char *label, u32 intr) -+{ -+ DBG("%s: %s intr=%08x %s%s%s%s%s%s\n", -+ ag->dev->name, label, intr, -+ (intr & AG71XX_INT_TX_PS) ? "TXPS " : "", -+ (intr & AG71XX_INT_TX_UR) ? "TXUR " : "", -+ (intr & AG71XX_INT_TX_BE) ? "TXBE " : "", -+ (intr & AG71XX_INT_RX_PR) ? "RXPR " : "", -+ (intr & AG71XX_INT_RX_OF) ? "RXOF " : "", -+ (intr & AG71XX_INT_RX_BE) ? "RXBE " : ""); -+} ++config SYS_HAS_CPU_R4X00 ++ bool + -+static void ag71xx_ring_free(struct ag71xx_ring *ring) -+{ -+ kfree(ring->buf); ++config SYS_HAS_CPU_TX49XX ++ bool + -+ if (ring->descs_cpu) -+ dma_free_coherent(NULL, ring->size * ring->desc_size, -+ ring->descs_cpu, ring->descs_dma); -+} ++config SYS_HAS_CPU_R5000 ++ bool + -+static int ag71xx_ring_alloc(struct ag71xx_ring *ring, unsigned int size) -+{ -+ int err; -+ int i; ++config SYS_HAS_CPU_R5432 ++ bool + -+ ring->desc_size = sizeof(struct ag71xx_desc); -+ if (ring->desc_size % cache_line_size()) { -+ DBG("ag71xx: ring %p, desc size %u rounded to %u\n", -+ ring, ring->desc_size, -+ roundup(ring->desc_size, cache_line_size())); -+ ring->desc_size = roundup(ring->desc_size, cache_line_size()); -+ } ++config SYS_HAS_CPU_R5500 ++ bool + -+ ring->descs_cpu = dma_alloc_coherent(NULL, size * ring->desc_size, -+ &ring->descs_dma, GFP_ATOMIC); -+ if (!ring->descs_cpu) { -+ err = -ENOMEM; -+ goto err; -+ } ++config SYS_HAS_CPU_R6000 ++ bool + -+ ring->size = size; ++config SYS_HAS_CPU_NEVADA ++ bool + -+ ring->buf = kzalloc(size * sizeof(*ring->buf), GFP_KERNEL); -+ if (!ring->buf) { -+ err = -ENOMEM; -+ goto err; -+ } ++config SYS_HAS_CPU_R8000 ++ bool + -+ for (i = 0; i < size; i++) { -+ ring->buf[i].desc = (struct ag71xx_desc *)&ring->descs_cpu[i * ring->desc_size]; -+ DBG("ag71xx: ring %p, desc %d at %p\n", -+ ring, i, ring->buf[i].desc); -+ } ++config SYS_HAS_CPU_R10000 ++ bool + -+ return 0; ++config SYS_HAS_CPU_RM7000 ++ bool + -+ err: -+ return err; -+} ++config SYS_HAS_CPU_RM9000 ++ bool + -+static void ag71xx_ring_tx_clean(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->tx_ring; -+ struct net_device *dev = ag->dev; ++config SYS_HAS_CPU_SB1 ++ bool + -+ while (ring->curr != ring->dirty) { -+ u32 i = ring->dirty % AG71XX_TX_RING_SIZE; ++config SYS_HAS_CPU_CAVIUM_OCTEON ++ bool + -+ if (!ag71xx_desc_empty(ring->buf[i].desc)) { -+ ring->buf[i].desc->ctrl = 0; -+ dev->stats.tx_errors++; -+ } ++config SYS_HAS_CPU_BMIPS3300 ++ bool + -+ if (ring->buf[i].skb) -+ dev_kfree_skb_any(ring->buf[i].skb); ++config SYS_HAS_CPU_BMIPS4350 ++ bool + -+ ring->buf[i].skb = NULL; ++config SYS_HAS_CPU_BMIPS4380 ++ bool + -+ ring->dirty++; -+ } ++config SYS_HAS_CPU_BMIPS5000 ++ bool + -+ /* flush descriptors */ -+ wmb(); ++# ++# CPU may reorder R->R, R->W, W->R, W->W ++# Reordering beyond LL and SC is handled in WEAK_REORDERING_BEYOND_LLSC ++# ++config WEAK_ORDERING ++ bool + -+} ++# ++# CPU may reorder reads and writes beyond LL/SC ++# CPU may reorder R->LL, R->LL, W->LL, W->LL, R->SC, R->SC, W->SC, W->SC ++# ++config WEAK_REORDERING_BEYOND_LLSC ++ bool ++endmenu + -+static void ag71xx_ring_tx_init(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->tx_ring; -+ int i; ++# ++# These two indicate any level of the MIPS32 and MIPS64 architecture ++# ++config CPU_MIPS32 ++ bool ++ default y if CPU_MIPS32_R1 || CPU_MIPS32_R2 + -+ for (i = 0; i < AG71XX_TX_RING_SIZE; i++) { -+ ring->buf[i].desc->next = (u32) (ring->descs_dma + -+ ring->desc_size * ((i + 1) % AG71XX_TX_RING_SIZE)); ++config CPU_MIPS64 ++ bool ++ default y if CPU_MIPS64_R1 || CPU_MIPS64_R2 + -+ ring->buf[i].desc->ctrl = DESC_EMPTY; -+ ring->buf[i].skb = NULL; -+ } ++# ++# These two indicate the revision of the architecture, either Release 1 or Release 2 ++# ++config CPU_MIPSR1 ++ bool ++ default y if CPU_MIPS32_R1 || CPU_MIPS64_R1 ++ ++config CPU_MIPSR2 ++ bool ++ default y if CPU_MIPS32_R2 || CPU_MIPS64_R2 || CPU_CAVIUM_OCTEON ++ ++config SYS_SUPPORTS_32BIT_KERNEL ++ bool ++config SYS_SUPPORTS_64BIT_KERNEL ++ bool ++config CPU_SUPPORTS_32BIT_KERNEL ++ bool ++config CPU_SUPPORTS_64BIT_KERNEL ++ bool ++config CPU_SUPPORTS_CPUFREQ ++ bool ++config CPU_SUPPORTS_ADDRWINCFG ++ bool ++config CPU_SUPPORTS_HUGEPAGES ++ bool ++config CPU_SUPPORTS_UNCACHED_ACCELERATED ++ bool ++config MIPS_PGD_C0_CONTEXT ++ bool ++ default y if 64BIT && CPU_MIPSR2 + -+ /* flush descriptors */ -+ wmb(); ++# ++# Set to y for ptrace access to watch registers. ++# ++config HARDWARE_WATCHPOINTS ++ bool ++ default y if CPU_MIPSR1 || CPU_MIPSR2 + -+ ring->curr = 0; -+ ring->dirty = 0; -+} ++menu "Kernel type" + -+static void ag71xx_ring_rx_clean(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->rx_ring; -+ int i; ++choice + -+ if (!ring->buf) -+ return; ++ prompt "Kernel code model" ++ help ++ You should only select this option if you have a workload that ++ actually benefits from 64-bit processing or if your machine has ++ large memory. You will only be presented a single option in this ++ menu if your system does not support both 32-bit and 64-bit kernels. ++ ++config 32BIT ++ bool "32-bit kernel" ++ depends on CPU_SUPPORTS_32BIT_KERNEL && SYS_SUPPORTS_32BIT_KERNEL ++ select TRAD_SIGNALS ++ help ++ Select this option if you want to build a 32-bit kernel. ++config 64BIT ++ bool "64-bit kernel" ++ depends on CPU_SUPPORTS_64BIT_KERNEL && SYS_SUPPORTS_64BIT_KERNEL ++ select HAVE_SYSCALL_WRAPPERS ++ help ++ Select this option if you want to build a 64-bit kernel. + -+ for (i = 0; i < AG71XX_RX_RING_SIZE; i++) -+ if (ring->buf[i].skb) { -+ dma_unmap_single(&ag->dev->dev, ring->buf[i].dma_addr, -+ AG71XX_RX_PKT_SIZE, DMA_FROM_DEVICE); -+ kfree_skb(ring->buf[i].skb); -+ } -+} ++endchoice + -+static int ag71xx_rx_reserve(struct ag71xx *ag) -+{ -+ int reserve = 0; ++choice ++ prompt "Kernel page size" ++ default PAGE_SIZE_4KB + -+ if (ag71xx_get_pdata(ag)->is_ar724x) { -+ if (!ag71xx_has_ar8216(ag)) -+ reserve = 2; ++config PAGE_SIZE_4KB ++ bool "4kB" ++ depends on !CPU_LOONGSON2 ++ help ++ This option select the standard 4kB Linux page size. On some ++ R3000-family processors this is the only available page size. Using ++ 4kB page size will minimize memory consumption and is therefore ++ recommended for low memory systems. ++ ++config PAGE_SIZE_8KB ++ bool "8kB" ++ depends on (EXPERIMENTAL && CPU_R8000) || CPU_CAVIUM_OCTEON ++ help ++ Using 8kB page size will result in higher performance kernel at ++ the price of higher memory consumption. This option is available ++ only on R8000 and cnMIPS processors. Note that you will need a ++ suitable Linux distribution to support this. ++ ++config PAGE_SIZE_16KB ++ bool "16kB" ++ depends on !CPU_R3000 && !CPU_TX39XX ++ help ++ Using 16kB page size will result in higher performance kernel at ++ the price of higher memory consumption. This option is available on ++ all non-R3000 family processors. Note that you will need a suitable ++ Linux distribution to support this. ++ ++config PAGE_SIZE_32KB ++ bool "32kB" ++ depends on CPU_CAVIUM_OCTEON ++ help ++ Using 32kB page size will result in higher performance kernel at ++ the price of higher memory consumption. This option is available ++ only on cnMIPS cores. Note that you will need a suitable Linux ++ distribution to support this. ++ ++config PAGE_SIZE_64KB ++ bool "64kB" ++ depends on EXPERIMENTAL && !CPU_R3000 && !CPU_TX39XX ++ help ++ Using 64kB page size will result in higher performance kernel at ++ the price of higher memory consumption. This option is available on ++ all non-R3000 family processor. Not that at the time of this ++ writing this option is still high experimental. ++ ++endchoice ++ ++config FORCE_MAX_ZONEORDER ++ int "Maximum zone order" ++ range 13 64 if SYS_SUPPORTS_HUGETLBFS && PAGE_SIZE_32KB ++ default "13" if SYS_SUPPORTS_HUGETLBFS && PAGE_SIZE_32KB ++ range 12 64 if SYS_SUPPORTS_HUGETLBFS && PAGE_SIZE_16KB ++ default "12" if SYS_SUPPORTS_HUGETLBFS && PAGE_SIZE_16KB ++ range 11 64 ++ default "11" ++ help ++ The kernel memory allocator divides physically contiguous memory ++ blocks into "zones", where each zone is a power of two number of ++ pages. This option selects the largest power of two that the kernel ++ keeps in the memory allocator. If you need to allocate very large ++ blocks of physically contiguous memory, then you may need to ++ increase this value. + -+ if (ag->phy_dev) -+ reserve += 4 - (ag->phy_dev->pkt_align % 4); ++ This config option is actually maximum order plus one. For example, ++ a value of 11 means that the largest free memory block is 2^10 pages. + -+ reserve %= 4; -+ } ++ The page size is not necessarily 4KB. Keep this in mind ++ when choosing a value for this option. + -+ return reserve + AG71XX_RX_PKT_RESERVE; -+} ++config BOARD_SCACHE ++ bool + ++config IP22_CPU_SCACHE ++ bool ++ select BOARD_SCACHE + -+static int ag71xx_ring_rx_init(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->rx_ring; -+ unsigned int reserve = ag71xx_rx_reserve(ag); -+ unsigned int i; -+ int ret; ++# ++# Support for a MIPS32 / MIPS64 style S-caches ++# ++config MIPS_CPU_SCACHE ++ bool ++ select BOARD_SCACHE + -+ ret = 0; -+ for (i = 0; i < AG71XX_RX_RING_SIZE; i++) { -+ ring->buf[i].desc->next = (u32) (ring->descs_dma + -+ ring->desc_size * ((i + 1) % AG71XX_RX_RING_SIZE)); ++config R5000_CPU_SCACHE ++ bool ++ select BOARD_SCACHE + -+ DBG("ag71xx: RX desc at %p, next is %08x\n", -+ ring->buf[i].desc, -+ ring->buf[i].desc->next); -+ } ++config RM7000_CPU_SCACHE ++ bool ++ select BOARD_SCACHE + -+ for (i = 0; i < AG71XX_RX_RING_SIZE; i++) { -+ struct sk_buff *skb; -+ dma_addr_t dma_addr; ++config SIBYTE_DMA_PAGEOPS ++ bool "Use DMA to clear/copy pages" ++ depends on CPU_SB1 ++ help ++ Instead of using the CPU to zero and copy pages, use a Data Mover ++ channel. These DMA channels are otherwise unused by the standard ++ SiByte Linux port. Seems to give a small performance benefit. + -+ skb = dev_alloc_skb(AG71XX_RX_PKT_SIZE + reserve); -+ if (!skb) { -+ ret = -ENOMEM; -+ break; -+ } ++config CPU_HAS_PREFETCH ++ bool + -+ skb->dev = ag->dev; -+ skb_reserve(skb, reserve); ++choice ++ prompt "MIPS MT options" + -+ dma_addr = dma_map_single(&ag->dev->dev, skb->data, -+ AG71XX_RX_PKT_SIZE, -+ DMA_FROM_DEVICE); -+ ring->buf[i].skb = skb; -+ ring->buf[i].dma_addr = dma_addr; -+ ring->buf[i].desc->data = (u32) dma_addr; -+ ring->buf[i].desc->ctrl = DESC_EMPTY; -+ } ++config MIPS_MT_DISABLED ++ bool "Disable multithreading support." ++ help ++ Use this option if your workload can't take advantage of ++ MIPS hardware multithreading support. On systems that don't have ++ the option of an MT-enabled processor this option will be the only ++ option in this menu. ++ ++config MIPS_MT_SMP ++ bool "Use 1 TC on each available VPE for SMP" ++ depends on SYS_SUPPORTS_MULTITHREADING ++ select CPU_MIPSR2_IRQ_VI ++ select CPU_MIPSR2_IRQ_EI ++ select MIPS_MT ++ select NR_CPUS_DEFAULT_2 ++ select SMP ++ select SYS_SUPPORTS_SCHED_SMT if SMP ++ select SYS_SUPPORTS_SMP ++ select SMP_UP ++ help ++ This is a kernel model which is known a VSMP but lately has been ++ marketesed into SMVP. ++ Virtual SMP uses the processor's VPEs to implement virtual ++ processors. In currently available configuration of the 34K processor ++ this allows for a dual processor. Both processors will share the same ++ primary caches; each will obtain the half of the TLB for it's own ++ exclusive use. For a layman this model can be described as similar to ++ what Intel calls Hyperthreading. ++ ++ For further information see http://www.linux-mips.org/wiki/34K#VSMP ++ ++config MIPS_MT_SMTC ++ bool "SMTC: Use all TCs on all VPEs for SMP" ++ depends on CPU_MIPS32_R2 ++ #depends on CPU_MIPS64_R2 # once there is hardware ... ++ depends on SYS_SUPPORTS_MULTITHREADING ++ select CPU_MIPSR2_IRQ_VI ++ select CPU_MIPSR2_IRQ_EI ++ select MIPS_MT ++ select NR_CPUS_DEFAULT_8 ++ select SMP ++ select SYS_SUPPORTS_SMP ++ select SMP_UP ++ help ++ This is a kernel model which is known a SMTC or lately has been ++ marketesed into SMVP. ++ is presenting the available TC's of the core as processors to Linux. ++ On currently available 34K processors this means a Linux system will ++ see up to 5 processors. The implementation of the SMTC kernel differs ++ significantly from VSMP and cannot efficiently coexist in the same ++ kernel binary so the choice between VSMP and SMTC is a compile time ++ decision. + -+ /* flush descriptors */ -+ wmb(); ++ For further information see http://www.linux-mips.org/wiki/34K#SMTC + -+ ring->curr = 0; -+ ring->dirty = 0; ++endchoice + -+ return ret; -+} ++config MIPS_MT ++ bool + -+static int ag71xx_ring_rx_refill(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->rx_ring; -+ unsigned int reserve = ag71xx_rx_reserve(ag); -+ unsigned int count; ++config SCHED_SMT ++ bool "SMT (multithreading) scheduler support" ++ depends on SYS_SUPPORTS_SCHED_SMT ++ default n ++ help ++ SMT scheduler support improves the CPU scheduler's decision making ++ when dealing with MIPS MT enabled cores at a cost of slightly ++ increased overhead in some places. If unsure say N here. + -+ count = 0; -+ for (; ring->curr - ring->dirty > 0; ring->dirty++) { -+ unsigned int i; ++config SYS_SUPPORTS_SCHED_SMT ++ bool + -+ i = ring->dirty % AG71XX_RX_RING_SIZE; + -+ if (ring->buf[i].skb == NULL) { -+ dma_addr_t dma_addr; -+ struct sk_buff *skb; ++config SYS_SUPPORTS_MULTITHREADING ++ bool + -+ skb = dev_alloc_skb(AG71XX_RX_PKT_SIZE + reserve); -+ if (skb == NULL) -+ break; ++config MIPS_MT_FPAFF ++ bool "Dynamic FPU affinity for FP-intensive threads" ++ default y ++ depends on MIPS_MT_SMP || MIPS_MT_SMTC ++ ++config MIPS_VPE_LOADER ++ bool "VPE loader support." ++ depends on SYS_SUPPORTS_MULTITHREADING ++ select CPU_MIPSR2_IRQ_VI ++ select CPU_MIPSR2_IRQ_EI ++ select MIPS_MT ++ help ++ Includes a loader for loading an elf relocatable object ++ onto another VPE and running it. + -+ skb_reserve(skb, reserve); -+ skb->dev = ag->dev; ++config MIPS_MT_SMTC_IM_BACKSTOP ++ bool "Use per-TC register bits as backstop for inhibited IM bits" ++ depends on MIPS_MT_SMTC ++ default n ++ help ++ To support multiple TC microthreads acting as "CPUs" within ++ a VPE, VPE-wide interrupt mask bits must be specially manipulated ++ during interrupt handling. To support legacy drivers and interrupt ++ controller management code, SMTC has a "backstop" to track and ++ if necessary restore the interrupt mask. This has some performance ++ impact on interrupt service overhead. ++ ++config MIPS_MT_SMTC_IRQAFF ++ bool "Support IRQ affinity API" ++ depends on MIPS_MT_SMTC ++ default n ++ help ++ Enables SMP IRQ affinity API (/proc/irq/*/smp_affinity, etc.) ++ for SMTC Linux kernel. Requires platform support, of which ++ an example can be found in the MIPS kernel i8259 and Malta ++ platform code. Adds some overhead to interrupt dispatch, and ++ should be used only if you know what you are doing. ++ ++config MIPS_VPE_LOADER_TOM ++ bool "Load VPE program into memory hidden from linux" ++ depends on MIPS_VPE_LOADER ++ default y ++ help ++ The loader can use memory that is present but has been hidden from ++ Linux using the kernel command line option "mem=xxMB". It's up to ++ you to ensure the amount you put in the option and the space your ++ program requires is less or equal to the amount physically present. ++ ++# this should possibly be in drivers/char, but it is rather cpu related. Hmmm ++config MIPS_VPE_APSP_API ++ bool "Enable support for AP/SP API (RTLX)" ++ depends on MIPS_VPE_LOADER ++ help + -+ dma_addr = dma_map_single(&ag->dev->dev, skb->data, -+ AG71XX_RX_PKT_SIZE, -+ DMA_FROM_DEVICE); ++config MIPS_APSP_KSPD ++ bool "Enable KSPD" ++ depends on MIPS_VPE_APSP_API ++ default y ++ help ++ KSPD is a kernel daemon that accepts syscall requests from the SP ++ side, actions them and returns the results. It also handles the ++ "exit" syscall notifying other kernel modules the SP program is ++ exiting. You probably want to say yes here. ++ ++config MIPS_CMP ++ bool "MIPS CMP framework support" ++ depends on SYS_SUPPORTS_MIPS_CMP ++ select SYNC_R4K ++ select SYS_SUPPORTS_SMP ++ select SYS_SUPPORTS_SCHED_SMT if SMP ++ select WEAK_ORDERING ++ default n ++ help ++ This is a placeholder option for the GCMP work. It will need to ++ be handled differently... + -+ ring->buf[i].skb = skb; -+ ring->buf[i].dma_addr = dma_addr; -+ ring->buf[i].desc->data = (u32) dma_addr; -+ } ++config SB1_PASS_1_WORKAROUNDS ++ bool ++ depends on CPU_SB1_PASS_1 ++ default y + -+ ring->buf[i].desc->ctrl = DESC_EMPTY; -+ count++; -+ } ++config SB1_PASS_2_WORKAROUNDS ++ bool ++ depends on CPU_SB1 && (CPU_SB1_PASS_2_2 || CPU_SB1_PASS_2) ++ default y + -+ /* flush descriptors */ -+ wmb(); ++config SB1_PASS_2_1_WORKAROUNDS ++ bool ++ depends on CPU_SB1 && CPU_SB1_PASS_2 ++ default y + -+ DBG("%s: %u rx descriptors refilled\n", ag->dev->name, count); ++config 64BIT_PHYS_ADDR ++ bool + -+ return count; -+} ++config ARCH_PHYS_ADDR_T_64BIT ++ def_bool 64BIT_PHYS_ADDR + -+static int ag71xx_rings_init(struct ag71xx *ag) -+{ -+ int ret; ++config CPU_HAS_SMARTMIPS ++ depends on SYS_SUPPORTS_SMARTMIPS ++ bool "Support for the SmartMIPS ASE" ++ help ++ SmartMIPS is a extension of the MIPS32 architecture aimed at ++ increased security at both hardware and software level for ++ smartcards. Enabling this option will allow proper use of the ++ SmartMIPS instructions by Linux applications. However a kernel with ++ this option will not work on a MIPS core without SmartMIPS core. If ++ you don't know you probably don't have SmartMIPS and should say N ++ here. + -+ ret = ag71xx_ring_alloc(&ag->tx_ring, AG71XX_TX_RING_SIZE); -+ if (ret) -+ return ret; ++config CPU_HAS_WB ++ bool + -+ ag71xx_ring_tx_init(ag); ++# ++# Vectored interrupt mode is an R2 feature ++# ++config CPU_MIPSR2_IRQ_VI ++ bool + -+ ret = ag71xx_ring_alloc(&ag->rx_ring, AG71XX_RX_RING_SIZE); -+ if (ret) -+ return ret; ++# ++# Extended interrupt mode is an R2 feature ++# ++config CPU_MIPSR2_IRQ_EI ++ bool + -+ ret = ag71xx_ring_rx_init(ag); -+ return ret; -+} ++config CPU_HAS_SYNC ++ bool ++ depends on !CPU_R3000 ++ default y + -+static void ag71xx_rings_cleanup(struct ag71xx *ag) -+{ -+ ag71xx_ring_rx_clean(ag); -+ ag71xx_ring_free(&ag->rx_ring); ++config GENERIC_CLOCKEVENTS_BROADCAST ++ bool + -+ ag71xx_ring_tx_clean(ag); -+ ag71xx_ring_free(&ag->tx_ring); -+} ++# ++# CPU non-features ++# ++config CPU_DADDI_WORKAROUNDS ++ bool + -+static unsigned char *ag71xx_speed_str(struct ag71xx *ag) -+{ -+ switch (ag->speed) { -+ case SPEED_1000: -+ return "1000"; -+ case SPEED_100: -+ return "100"; -+ case SPEED_10: -+ return "10"; -+ } ++config CPU_R4000_WORKAROUNDS ++ bool ++ select CPU_R4400_WORKAROUNDS + -+ return "?"; -+} ++config CPU_R4400_WORKAROUNDS ++ bool + -+void ag71xx_link_adjust(struct ag71xx *ag) -+{ -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); -+ u32 cfg2; -+ u32 ifctl; -+ u32 fifo5; -+ u32 mii_speed; ++# ++# - Highmem only makes sense for the 32-bit kernel. ++# - The current highmem code will only work properly on physically indexed ++# caches such as R3000, SB1, R7000 or those that look like they're virtually ++# indexed such as R4000/R4400 SC and MC versions or R10000. So for the ++# moment we protect the user and offer the highmem option only on machines ++# where it's known to be safe. This will not offer highmem on a few systems ++# such as MIPS32 and MIPS64 CPUs which may have virtual and physically ++# indexed CPUs but we're playing safe. ++# - We use SYS_SUPPORTS_HIGHMEM to offer highmem only for systems where we ++# know they might have memory configurations that could make use of highmem ++# support. ++# ++config HIGHMEM ++ bool "High Memory Support" ++ depends on 32BIT && CPU_SUPPORTS_HIGHMEM && SYS_SUPPORTS_HIGHMEM + -+ if (!ag->link) { -+ netif_carrier_off(ag->dev); -+ if (netif_msg_link(ag)) -+ printk(KERN_INFO "%s: link down\n", ag->dev->name); -+ return; -+ } ++config CPU_SUPPORTS_HIGHMEM ++ bool + -+ cfg2 = ag71xx_rr(ag, AG71XX_REG_MAC_CFG2); -+ cfg2 &= ~(MAC_CFG2_IF_1000 | MAC_CFG2_IF_10_100 | MAC_CFG2_FDX); -+ cfg2 |= (ag->duplex) ? MAC_CFG2_FDX : 0; ++config SYS_SUPPORTS_HIGHMEM ++ bool + -+ ifctl = ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL); -+ ifctl &= ~(MAC_IFCTL_SPEED); ++config SYS_SUPPORTS_SMARTMIPS ++ bool + -+ fifo5 = ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5); -+ fifo5 &= ~FIFO_CFG5_BM; ++config ARCH_FLATMEM_ENABLE ++ def_bool y ++ depends on !NUMA && !CPU_LOONGSON2 + -+ switch (ag->speed) { -+ case SPEED_1000: -+ mii_speed = MII_CTRL_SPEED_1000; -+ cfg2 |= MAC_CFG2_IF_1000; -+ fifo5 |= FIFO_CFG5_BM; -+ break; -+ case SPEED_100: -+ mii_speed = MII_CTRL_SPEED_100; -+ cfg2 |= MAC_CFG2_IF_10_100; -+ ifctl |= MAC_IFCTL_SPEED; -+ break; -+ case SPEED_10: -+ mii_speed = MII_CTRL_SPEED_10; -+ cfg2 |= MAC_CFG2_IF_10_100; -+ break; -+ default: -+ BUG(); -+ return; -+ } ++config ARCH_DISCONTIGMEM_ENABLE ++ bool ++ default y if SGI_IP27 ++ help ++ Say Y to support efficient handling of discontiguous physical memory, ++ for architectures which are either NUMA (Non-Uniform Memory Access) ++ or have huge holes in the physical address space for other reasons. ++ See for more. + -+ if (pdata->is_ar91xx) -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, 0x00780fff); -+ else if (pdata->is_ar724x) -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, pdata->fifo_cfg3); -+ else -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, 0x008001ff); ++config ARCH_POPULATES_NODE_MAP ++ def_bool y + -+ if (pdata->set_pll) -+ pdata->set_pll(ag->speed); ++config ARCH_SPARSEMEM_ENABLE ++ bool ++ select SPARSEMEM_STATIC + -+ ag71xx_mii_ctrl_set_speed(ag, mii_speed); ++config NUMA ++ bool "NUMA Support" ++ depends on SYS_SUPPORTS_NUMA ++ help ++ Say Y to compile the kernel to support NUMA (Non-Uniform Memory ++ Access). This option improves performance on systems with more ++ than two nodes; on two node systems it is generally better to ++ leave it disabled; on single node systems disable this option ++ disabled. ++ ++config SYS_SUPPORTS_NUMA ++ bool ++ ++config NODES_SHIFT ++ int ++ default "6" ++ depends on NEED_MULTIPLE_NODES ++ ++config HW_PERF_EVENTS ++ bool "Enable hardware performance counter support for perf events" ++ depends on PERF_EVENTS && !MIPS_MT_SMTC && OPROFILE=n && CPU_MIPS32 ++ default y ++ help ++ Enable hardware performance counter support for perf events. If ++ disabled, perf events will use software events only. + -+ ag71xx_wr(ag, AG71XX_REG_MAC_CFG2, cfg2); -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG5, fifo5); -+ ag71xx_wr(ag, AG71XX_REG_MAC_IFCTL, ifctl); ++source "mm/Kconfig" + -+ netif_carrier_on(ag->dev); -+ if (netif_msg_link(ag)) -+ printk(KERN_INFO "%s: link up (%sMbps/%s duplex)\n", -+ ag->dev->name, -+ ag71xx_speed_str(ag), -+ (DUPLEX_FULL == ag->duplex) ? "Full" : "Half"); ++config SMP ++ bool "Multi-Processing support" ++ depends on SYS_SUPPORTS_SMP ++ select IRQ_PER_CPU ++ select USE_GENERIC_SMP_HELPERS ++ help ++ This enables support for systems with more than one CPU. If you have ++ a system with only one CPU, like most personal computers, say N. If ++ you have a system with more than one CPU, say Y. + -+ DBG("%s: fifo_cfg0=%#x, fifo_cfg1=%#x, fifo_cfg2=%#x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG0), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG1), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG2)); ++ If you say N here, the kernel will run on single and multiprocessor ++ machines, but will use only one CPU of a multiprocessor machine. If ++ you say Y here, the kernel will run on many, but not all, ++ singleprocessor machines. On a singleprocessor machine, the kernel ++ will run faster if you say N here. + -+ DBG("%s: fifo_cfg3=%#x, fifo_cfg4=%#x, fifo_cfg5=%#x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG3), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG4), -+ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5)); ++ People using multiprocessor machines who say Y here should also say ++ Y to "Enhanced Real Time Clock Support", below. + -+ DBG("%s: mac_cfg2=%#x, mac_ifctl=%#x, mii_ctrl=%#x\n", -+ ag->dev->name, -+ ag71xx_rr(ag, AG71XX_REG_MAC_CFG2), -+ ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL), -+ ag71xx_mii_ctrl_rr(ag)); -+} ++ See also the SMP-HOWTO available at ++ . + -+static void ag71xx_hw_set_macaddr(struct ag71xx *ag, unsigned char *mac) -+{ -+ u32 t; ++ If you don't know what to do here, say N. + -+ t = (((u32) mac[5]) << 24) | (((u32) mac[4]) << 16) -+ | (((u32) mac[3]) << 8) | ((u32) mac[2]); ++config SMP_UP ++ bool + -+ ag71xx_wr(ag, AG71XX_REG_MAC_ADDR1, t); ++config SYS_SUPPORTS_MIPS_CMP ++ bool + -+ t = (((u32) mac[1]) << 24) | (((u32) mac[0]) << 16); -+ ag71xx_wr(ag, AG71XX_REG_MAC_ADDR2, t); -+} ++config SYS_SUPPORTS_SMP ++ bool + -+static void ag71xx_dma_reset(struct ag71xx *ag) -+{ -+ u32 val; -+ int i; ++config NR_CPUS_DEFAULT_1 ++ bool + -+ ag71xx_dump_dma_regs(ag); ++config NR_CPUS_DEFAULT_2 ++ bool + -+ /* stop RX and TX */ -+ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, 0); -+ ag71xx_wr(ag, AG71XX_REG_TX_CTRL, 0); ++config NR_CPUS_DEFAULT_4 ++ bool + -+ /* clear descriptor addresses */ -+ ag71xx_wr(ag, AG71XX_REG_TX_DESC, 0); -+ ag71xx_wr(ag, AG71XX_REG_RX_DESC, 0); ++config NR_CPUS_DEFAULT_8 ++ bool + -+ /* clear pending RX/TX interrupts */ -+ for (i = 0; i < 256; i++) { -+ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_PR); -+ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_PS); -+ } ++config NR_CPUS_DEFAULT_16 ++ bool + -+ /* clear pending errors */ -+ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_BE | RX_STATUS_OF); -+ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_BE | TX_STATUS_UR); ++config NR_CPUS_DEFAULT_32 ++ bool + -+ val = ag71xx_rr(ag, AG71XX_REG_RX_STATUS); -+ if (val) -+ printk(KERN_ALERT "%s: unable to clear DMA Rx status: %08x\n", -+ ag->dev->name, val); ++config NR_CPUS_DEFAULT_64 ++ bool + -+ val = ag71xx_rr(ag, AG71XX_REG_TX_STATUS); ++config NR_CPUS ++ int "Maximum number of CPUs (2-64)" ++ range 1 64 if NR_CPUS_DEFAULT_1 ++ depends on SMP ++ default "1" if NR_CPUS_DEFAULT_1 ++ default "2" if NR_CPUS_DEFAULT_2 ++ default "4" if NR_CPUS_DEFAULT_4 ++ default "8" if NR_CPUS_DEFAULT_8 ++ default "16" if NR_CPUS_DEFAULT_16 ++ default "32" if NR_CPUS_DEFAULT_32 ++ default "64" if NR_CPUS_DEFAULT_64 ++ help ++ This allows you to specify the maximum number of CPUs which this ++ kernel will support. The maximum supported value is 32 for 32-bit ++ kernel and 64 for 64-bit kernels; the minimum value which makes ++ sense is 1 for Qemu (useful only for kernel debugging purposes) ++ and 2 for all others. + -+ /* mask out reserved bits */ -+ val &= ~0xff000000; ++ This is purely to save memory - each supported CPU adds ++ approximately eight kilobytes to the kernel image. For best ++ performance should round up your number of processors to the next ++ power of two. + -+ if (val) -+ printk(KERN_ALERT "%s: unable to clear DMA Tx status: %08x\n", -+ ag->dev->name, val); ++source "kernel/time/Kconfig" + -+ ag71xx_dump_dma_regs(ag); -+} ++# ++# Timer Interrupt Frequency Configuration ++# + -+#define MAC_CFG1_INIT (MAC_CFG1_RXE | MAC_CFG1_TXE | \ -+ MAC_CFG1_SRX | MAC_CFG1_STX) ++choice ++ prompt "Timer frequency" ++ default HZ_250 ++ help ++ Allows the configuration of the timer frequency. + -+#define FIFO_CFG0_INIT (FIFO_CFG0_ALL << FIFO_CFG0_ENABLE_SHIFT) ++ config HZ_48 ++ bool "48 HZ" if SYS_SUPPORTS_48HZ || SYS_SUPPORTS_ARBIT_HZ + -+#define FIFO_CFG4_INIT (FIFO_CFG4_DE | FIFO_CFG4_DV | FIFO_CFG4_FC | \ -+ FIFO_CFG4_CE | FIFO_CFG4_CR | FIFO_CFG4_LM | \ -+ FIFO_CFG4_LO | FIFO_CFG4_OK | FIFO_CFG4_MC | \ -+ FIFO_CFG4_BC | FIFO_CFG4_DR | FIFO_CFG4_LE | \ -+ FIFO_CFG4_CF | FIFO_CFG4_PF | FIFO_CFG4_UO | \ -+ FIFO_CFG4_VT) ++ config HZ_100 ++ bool "100 HZ" if SYS_SUPPORTS_100HZ || SYS_SUPPORTS_ARBIT_HZ + -+#define FIFO_CFG5_INIT (FIFO_CFG5_DE | FIFO_CFG5_DV | FIFO_CFG5_FC | \ -+ FIFO_CFG5_CE | FIFO_CFG5_LO | FIFO_CFG5_OK | \ -+ FIFO_CFG5_MC | FIFO_CFG5_BC | FIFO_CFG5_DR | \ -+ FIFO_CFG5_CF | FIFO_CFG5_PF | FIFO_CFG5_VT | \ -+ FIFO_CFG5_LE | FIFO_CFG5_FT | FIFO_CFG5_16 | \ -+ FIFO_CFG5_17 | FIFO_CFG5_SF) ++ config HZ_128 ++ bool "128 HZ" if SYS_SUPPORTS_128HZ || SYS_SUPPORTS_ARBIT_HZ + -+static void ag71xx_hw_init(struct ag71xx *ag) -+{ -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ config HZ_250 ++ bool "250 HZ" if SYS_SUPPORTS_250HZ || SYS_SUPPORTS_ARBIT_HZ + -+ ag71xx_sb(ag, AG71XX_REG_MAC_CFG1, MAC_CFG1_SR); -+ udelay(20); ++ config HZ_256 ++ bool "256 HZ" if SYS_SUPPORTS_256HZ || SYS_SUPPORTS_ARBIT_HZ + -+ ar71xx_device_stop(pdata->reset_bit); -+ mdelay(100); -+ ar71xx_device_start(pdata->reset_bit); -+ mdelay(100); ++ config HZ_1000 ++ bool "1000 HZ" if SYS_SUPPORTS_1000HZ || SYS_SUPPORTS_ARBIT_HZ + -+ /* setup MAC configuration registers */ -+ if (pdata->is_ar724x) -+ ag71xx_wr(ag, AG71XX_REG_MAC_CFG1, -+ MAC_CFG1_INIT | MAC_CFG1_TFC | MAC_CFG1_RFC); -+ else -+ ag71xx_wr(ag, AG71XX_REG_MAC_CFG1, MAC_CFG1_INIT); ++ config HZ_1024 ++ bool "1024 HZ" if SYS_SUPPORTS_1024HZ || SYS_SUPPORTS_ARBIT_HZ + -+ ag71xx_sb(ag, AG71XX_REG_MAC_CFG2, -+ MAC_CFG2_PAD_CRC_EN | MAC_CFG2_LEN_CHECK); ++endchoice + -+ /* setup max frame length */ -+ ag71xx_wr(ag, AG71XX_REG_MAC_MFL, AG71XX_TX_MTU_LEN); ++config SYS_SUPPORTS_48HZ ++ bool + -+ /* setup MII interface type */ -+ ag71xx_mii_ctrl_set_if(ag, pdata->mii_if); ++config SYS_SUPPORTS_100HZ ++ bool + -+ /* setup FIFO configuration registers */ -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG0, FIFO_CFG0_INIT); -+ if (pdata->is_ar724x) { -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG1, pdata->fifo_cfg1); -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG2, pdata->fifo_cfg2); -+ } else { -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG1, 0x0fff0000); -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG2, 0x00001fff); -+ } -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG4, FIFO_CFG4_INIT); -+ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG5, FIFO_CFG5_INIT); ++config SYS_SUPPORTS_128HZ ++ bool + -+ ag71xx_dma_reset(ag); -+} ++config SYS_SUPPORTS_250HZ ++ bool + -+static void ag71xx_hw_start(struct ag71xx *ag) -+{ -+ /* start RX engine */ -+ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, RX_CTRL_RXE); ++config SYS_SUPPORTS_256HZ ++ bool + -+ /* enable interrupts */ -+ ag71xx_wr(ag, AG71XX_REG_INT_ENABLE, AG71XX_INT_INIT); -+} ++config SYS_SUPPORTS_1000HZ ++ bool + -+static void ag71xx_hw_stop(struct ag71xx *ag) -+{ -+ /* disable all interrupts */ -+ ag71xx_wr(ag, AG71XX_REG_INT_ENABLE, 0); ++config SYS_SUPPORTS_1024HZ ++ bool + -+ ag71xx_dma_reset(ag); -+} ++config SYS_SUPPORTS_ARBIT_HZ ++ bool ++ default y if !SYS_SUPPORTS_48HZ && !SYS_SUPPORTS_100HZ && \ ++ !SYS_SUPPORTS_128HZ && !SYS_SUPPORTS_250HZ && \ ++ !SYS_SUPPORTS_256HZ && !SYS_SUPPORTS_1000HZ && \ ++ !SYS_SUPPORTS_1024HZ + -+static int ag71xx_open(struct net_device *dev) -+{ -+ struct ag71xx *ag = netdev_priv(dev); -+ int ret; ++config HZ ++ int ++ default 48 if HZ_48 ++ default 100 if HZ_100 ++ default 128 if HZ_128 ++ default 250 if HZ_250 ++ default 256 if HZ_256 ++ default 1000 if HZ_1000 ++ default 1024 if HZ_1024 + -+ ret = ag71xx_rings_init(ag); -+ if (ret) -+ goto err; ++source "kernel/Kconfig.preempt" + -+ napi_enable(&ag->napi); ++config MIPS_INSANE_LARGE ++ bool "Support for large 64-bit configurations" ++ depends on CPU_R10000 && 64BIT ++ help ++ MIPS R10000 does support a 44 bit / 16TB address space as opposed to ++ previous 64-bit processors which only supported 40 bit / 1TB. If you ++ need processes of more than 1TB virtual address space, say Y here. ++ This will result in additional memory usage, so it is not ++ recommended for normal users. ++ ++config KEXEC ++ bool "Kexec system call (EXPERIMENTAL)" ++ depends on EXPERIMENTAL ++ help ++ kexec is a system call that implements the ability to shutdown your ++ current kernel, and to start another kernel. It is like a reboot ++ but it is independent of the system firmware. And like a reboot ++ you can start any kernel with it, not just Linux. ++ ++ The name comes from the similarity to the exec system call. ++ ++ It is an ongoing process to be certain the hardware in a machine ++ is properly shutdown, so do not be surprised if this code does not ++ initially work for you. It may help to enable device hotplugging ++ support. As of this writing the exact hardware interface is ++ strongly in flux, so no good recommendation can be made. ++ ++config SECCOMP ++ bool "Enable seccomp to safely compute untrusted bytecode" ++ depends on PROC_FS ++ default y ++ help ++ This kernel feature is useful for number crunching applications ++ that may need to compute untrusted bytecode during their ++ execution. By using pipes or other transports made available to ++ the process as file descriptors supporting the read/write ++ syscalls, it's possible to isolate those applications in ++ their own address space using seccomp. Once seccomp is ++ enabled via /proc//seccomp, it cannot be disabled ++ and the task is only allowed to execute a few safe syscalls ++ defined by each seccomp mode. ++ ++ If unsure, say Y. Only embedded should say N here. ++ ++config USE_OF ++ bool "Flattened Device Tree support" ++ select OF ++ select OF_EARLY_FLATTREE ++ help ++ Include support for flattened device tree machine descriptions. + -+ netif_carrier_off(dev); -+ ag71xx_phy_start(ag); ++endmenu + -+ ag71xx_wr(ag, AG71XX_REG_TX_DESC, ag->tx_ring.descs_dma); -+ ag71xx_wr(ag, AG71XX_REG_RX_DESC, ag->rx_ring.descs_dma); ++config LOCKDEP_SUPPORT ++ bool ++ default y + -+ ag71xx_hw_set_macaddr(ag, dev->dev_addr); ++config STACKTRACE_SUPPORT ++ bool ++ default y + -+ ag71xx_hw_start(ag); ++source "init/Kconfig" + -+ netif_start_queue(dev); ++source "kernel/Kconfig.freezer" + -+ return 0; ++menu "Bus options (PCI, PCMCIA, EISA, ISA, TC)" + -+ err: -+ ag71xx_rings_cleanup(ag); -+ return ret; -+} ++config HW_HAS_EISA ++ bool ++config HW_HAS_PCI ++ bool + -+static int ag71xx_stop(struct net_device *dev) -+{ -+ struct ag71xx *ag = netdev_priv(dev); -+ unsigned long flags; ++config PCI ++ bool "Support for PCI controller" ++ depends on HW_HAS_PCI ++ select PCI_DOMAINS ++ help ++ Find out whether you have a PCI motherboard. PCI is the name of a ++ bus system, i.e. the way the CPU talks to the other stuff inside ++ your box. Other bus systems are ISA, EISA, or VESA. If you have PCI, ++ say Y, otherwise N. + -+ netif_carrier_off(dev); -+ ag71xx_phy_stop(ag); ++config PCI_DOMAINS ++ bool + -+ spin_lock_irqsave(&ag->lock, flags); ++source "drivers/pci/Kconfig" + -+ netif_stop_queue(dev); ++# ++# ISA support is now enabled via select. Too many systems still have the one ++# or other ISA chip on the board that users don't know about so don't expect ++# users to choose the right thing ... ++# ++config ISA ++ bool + -+ ag71xx_hw_stop(ag); ++config EISA ++ bool "EISA support" ++ depends on HW_HAS_EISA ++ select ISA ++ select GENERIC_ISA_DMA ++ ---help--- ++ The Extended Industry Standard Architecture (EISA) bus was ++ developed as an open alternative to the IBM MicroChannel bus. + -+ napi_disable(&ag->napi); -+ del_timer_sync(&ag->oom_timer); ++ The EISA bus provided some of the features of the IBM MicroChannel ++ bus while maintaining backward compatibility with cards made for ++ the older ISA bus. The EISA bus saw limited use between 1988 and ++ 1995 when it was made obsolete by the PCI bus. + -+ spin_unlock_irqrestore(&ag->lock, flags); ++ Say Y here if you are building a kernel for an EISA-based machine. + -+ ag71xx_rings_cleanup(ag); ++ Otherwise, say N. + -+ return 0; -+} ++source "drivers/eisa/Kconfig" + -+static netdev_tx_t ag71xx_hard_start_xmit(struct sk_buff *skb, -+ struct net_device *dev) -+{ -+ struct ag71xx *ag = netdev_priv(dev); -+ struct ag71xx_ring *ring = &ag->tx_ring; -+ struct ag71xx_desc *desc; -+ dma_addr_t dma_addr; -+ int i; ++config TC ++ bool "TURBOchannel support" ++ depends on MACH_DECSTATION ++ help ++ TURBOchannel is a DEC (now Compaq (now HP)) bus for Alpha and MIPS ++ processors. TURBOchannel programming specifications are available ++ at: ++ ++ and: ++ ++ Linux driver support status is documented at: ++ ++ ++#config ACCESSBUS ++# bool "Access.Bus support" ++# depends on TC ++ ++config MMU ++ bool ++ default y + -+ i = ring->curr % AG71XX_TX_RING_SIZE; -+ desc = ring->buf[i].desc; ++config I8253 ++ bool ++ select MIPS_EXTERNAL_TIMER + -+ if (!ag71xx_desc_empty(desc)) -+ goto err_drop; ++config ZONE_DMA32 ++ bool + -+ if (ag71xx_has_ar8216(ag)) -+ ag71xx_add_ar8216_header(ag, skb); ++source "drivers/pcmcia/Kconfig" + -+ if (skb->len <= 0) { -+ DBG("%s: packet len is too small\n", ag->dev->name); -+ goto err_drop; -+ } ++source "drivers/pci/hotplug/Kconfig" + -+ dma_addr = dma_map_single(&dev->dev, skb->data, skb->len, -+ DMA_TO_DEVICE); ++config RAPIDIO ++ bool "RapidIO support" ++ depends on PCI ++ default n ++ help ++ If you say Y here, the kernel will include drivers and ++ infrastructure code to support RapidIO interconnect devices. + -+ ring->buf[i].skb = skb; ++source "drivers/rapidio/Kconfig" + -+ /* setup descriptor fields */ -+ desc->data = (u32) dma_addr; -+ desc->ctrl = (skb->len & DESC_PKTLEN_M); ++endmenu + -+ /* flush descriptor */ -+ wmb(); ++menu "Executable file formats" + -+ ring->curr++; -+ if (ring->curr == (ring->dirty + AG71XX_TX_THRES_STOP)) { -+ DBG("%s: tx queue full\n", ag->dev->name); -+ netif_stop_queue(dev); -+ } ++source "fs/Kconfig.binfmt" + -+ DBG("%s: packet injected into TX queue\n", ag->dev->name); ++config TRAD_SIGNALS ++ bool + -+ /* enable TX engine */ -+ ag71xx_wr(ag, AG71XX_REG_TX_CTRL, TX_CTRL_TXE); ++config MIPS32_COMPAT ++ bool "Kernel support for Linux/MIPS 32-bit binary compatibility" ++ depends on 64BIT ++ help ++ Select this option if you want Linux/MIPS 32-bit binary ++ compatibility. Since all software available for Linux/MIPS is ++ currently 32-bit you should say Y here. + -+ return NETDEV_TX_OK; ++config COMPAT ++ bool ++ depends on MIPS32_COMPAT ++ default y + -+ err_drop: -+ dev->stats.tx_dropped++; ++config SYSVIPC_COMPAT ++ bool ++ depends on COMPAT && SYSVIPC ++ default y + -+ dev_kfree_skb(skb); -+ return NETDEV_TX_OK; -+} ++config MIPS32_O32 ++ bool "Kernel support for o32 binaries" ++ depends on MIPS32_COMPAT ++ help ++ Select this option if you want to run o32 binaries. These are pure ++ 32-bit binaries as used by the 32-bit Linux/MIPS port. Most of ++ existing binaries are in this format. + -+static int ag71xx_do_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) -+{ -+ struct mii_ioctl_data *data = (struct mii_ioctl_data *) &ifr->ifr_data; -+ struct ag71xx *ag = netdev_priv(dev); -+ int ret; ++ If unsure, say Y. + -+ switch (cmd) { -+ case SIOCETHTOOL: -+ if (ag->phy_dev == NULL) -+ break; ++config MIPS32_N32 ++ bool "Kernel support for n32 binaries" ++ depends on MIPS32_COMPAT ++ help ++ Select this option if you want to run n32 binaries. These are ++ 64-bit binaries using 32-bit quantities for addressing and certain ++ data that would normally be 64-bit. They are used in special ++ cases. + -+ spin_lock_irq(&ag->lock); -+ ret = phy_ethtool_ioctl(ag->phy_dev, (void *) ifr->ifr_data); -+ spin_unlock_irq(&ag->lock); -+ return ret; ++ If unsure, say N. + -+ case SIOCSIFHWADDR: -+ if (copy_from_user -+ (dev->dev_addr, ifr->ifr_data, sizeof(dev->dev_addr))) -+ return -EFAULT; -+ return 0; ++config BINFMT_ELF32 ++ bool ++ default y if MIPS32_O32 || MIPS32_N32 + -+ case SIOCGIFHWADDR: -+ if (copy_to_user -+ (ifr->ifr_data, dev->dev_addr, sizeof(dev->dev_addr))) -+ return -EFAULT; -+ return 0; ++endmenu + -+ case SIOCGMIIPHY: -+ case SIOCGMIIREG: -+ case SIOCSMIIREG: -+ if (ag->phy_dev == NULL) -+ break; ++menu "Power management options" + -+ return phy_mii_ioctl(ag->phy_dev, data, cmd); ++config ARCH_HIBERNATION_POSSIBLE ++ def_bool y ++ depends on SYS_SUPPORTS_HOTPLUG_CPU || !SMP + -+ default: -+ break; -+ } ++config ARCH_SUSPEND_POSSIBLE ++ def_bool y ++ depends on SYS_SUPPORTS_HOTPLUG_CPU || !SMP + -+ return -EOPNOTSUPP; -+} ++source "kernel/power/Kconfig" + -+static void ag71xx_oom_timer_handler(unsigned long data) -+{ -+ struct net_device *dev = (struct net_device *) data; -+ struct ag71xx *ag = netdev_priv(dev); ++endmenu + -+ napi_schedule(&ag->napi); -+} ++source "arch/mips/kernel/cpufreq/Kconfig" + -+static void ag71xx_tx_timeout(struct net_device *dev) -+{ -+ struct ag71xx *ag = netdev_priv(dev); ++source "net/Kconfig" + -+ if (netif_msg_tx_err(ag)) -+ printk(KERN_DEBUG "%s: tx timeout\n", ag->dev->name); ++source "drivers/Kconfig" + -+ schedule_work(&ag->restart_work); -+} ++source "fs/Kconfig" + -+static void ag71xx_restart_work_func(struct work_struct *work) -+{ -+ struct ag71xx *ag = container_of(work, struct ag71xx, restart_work); ++source "arch/mips/Kconfig.debug" + -+ ag71xx_stop(ag->dev); -+ ag71xx_open(ag->dev); -+} ++source "security/Kconfig" + -+static int ag71xx_tx_packets(struct ag71xx *ag) -+{ -+ struct ag71xx_ring *ring = &ag->tx_ring; -+ int sent; ++source "crypto/Kconfig" + -+ DBG("%s: processing TX ring\n", ag->dev->name); ++menuconfig VIRTUALIZATION ++ bool "Virtualization" ++ default n ++ ---help--- ++ Say Y here to get to see options for using your Linux host to run other ++ operating systems inside virtual machines (guests). ++ This option alone does not add any kernel code. + -+ sent = 0; -+ while (ring->dirty != ring->curr) { -+ unsigned int i = ring->dirty % AG71XX_TX_RING_SIZE; -+ struct ag71xx_desc *desc = ring->buf[i].desc; -+ struct sk_buff *skb = ring->buf[i].skb; ++ If you say N, all options in this submenu will be skipped and disabled. + -+ if (!ag71xx_desc_empty(desc)) -+ break; ++if VIRTUALIZATION + -+ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_PS); ++source drivers/virtio/Kconfig + -+ ag->dev->stats.tx_bytes += skb->len; -+ ag->dev->stats.tx_packets++; ++endif # VIRTUALIZATION + -+ dev_kfree_skb_any(skb); -+ ring->buf[i].skb = NULL; ++source "lib/Kconfig" +diff -Nur linux-2.6.39.orig/arch/mips/kernel/traps.c linux-2.6.39/arch/mips/kernel/traps.c +--- linux-2.6.39.orig/arch/mips/kernel/traps.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/kernel/traps.c 2011-08-24 05:53:05.179230891 +0200 +@@ -54,6 +54,7 @@ + #include + #include + #include ++#include + + extern void check_wait(void); + extern asmlinkage void r4k_wait(void); +@@ -1576,6 +1577,8 @@ + if (cpu_has_mips_r2) { + cp0_compare_irq_shift = CAUSEB_TI - CAUSEB_IP; + cp0_compare_irq = (read_c0_intctl() >> INTCTLB_IPTI) & 7; ++ if (get_c0_compare_irq) ++ cp0_compare_irq = get_c0_compare_irq(); + cp0_perfcount_irq = (read_c0_intctl() >> INTCTLB_IPPCI) & 7; + if (cp0_perfcount_irq == cp0_compare_irq) + cp0_perfcount_irq = -1; +diff -Nur linux-2.6.39.orig/arch/mips/Makefile linux-2.6.39/arch/mips/Makefile +--- linux-2.6.39.orig/arch/mips/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/Makefile 2011-08-24 02:42:39.917989402 +0200 +@@ -158,6 +158,13 @@ + endif + cflags-$(CONFIG_CAVIUM_CN63XXP1) += -Wa,-mfix-cn63xxp1 + ++# ++# Atheros AR71xx ++# ++core-$(CONFIG_ATHEROS_AR71XX) += arch/mips/ar71xx/ ++cflags-$(CONFIG_ATHEROS_AR71XX) += -I$(srctree)/arch/mips/include/asm/mach-ar71xx ++load-$(CONFIG_ATHEROS_AR71XX) += 0xffffffff80060000 + -+ ring->dirty++; -+ sent++; -+ } + cflags-$(CONFIG_CPU_R4000_WORKAROUNDS) += $(call cc-option,-mfix-r4000,) + cflags-$(CONFIG_CPU_R4400_WORKAROUNDS) += $(call cc-option,-mfix-r4400,) + cflags-$(CONFIG_CPU_DADDI_WORKAROUNDS) += $(call cc-option,-mno-daddi,) +@@ -174,6 +181,7 @@ + # + libs-$(CONFIG_ARC) += arch/mips/fw/arc/ + libs-$(CONFIG_CFE) += arch/mips/fw/cfe/ ++libs-$(CONFIG_MYLOADER) += arch/mips/fw/myloader/ + libs-$(CONFIG_SNIPROM) += arch/mips/fw/sni/ + libs-y += arch/mips/fw/lib/ + +diff -Nur linux-2.6.39.orig/arch/mips/pci/Makefile linux-2.6.39/arch/mips/pci/Makefile +--- linux-2.6.39.orig/arch/mips/pci/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/arch/mips/pci/Makefile 2011-08-22 16:21:37.437981205 +0200 +@@ -18,6 +18,7 @@ + obj-$(CONFIG_BCM47XX) += pci-bcm47xx.o + obj-$(CONFIG_BCM63XX) += pci-bcm63xx.o fixup-bcm63xx.o \ + ops-bcm63xx.o ++obj-$(CONFIG_ATHEROS_AR71XX) += pci-ar71xx.o pci-ar724x.o + + # + # These are still pretty much in the old state, watch, go blind. +diff -Nur linux-2.6.39.orig/arch/mips/pci/pci-ar71xx.c linux-2.6.39/arch/mips/pci/pci-ar71xx.c +--- linux-2.6.39.orig/arch/mips/pci/pci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/pci/pci-ar71xx.c 2011-08-06 09:32:37.098016752 +0200 +@@ -0,0 +1,415 @@ ++/* ++ * Atheros AR71xx PCI host controller driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ DBG("%s: %d packets sent out\n", ag->dev->name, sent); ++#include ++#include ++#include ++#include ++#include ++#include ++#include + -+ if ((ring->curr - ring->dirty) < AG71XX_TX_THRES_WAKEUP) -+ netif_wake_queue(ag->dev); ++#include ++#include + -+ return sent; -+} ++#undef DEBUG ++#ifdef DEBUG ++#define DBG(fmt, args...) printk(KERN_DEBUG fmt, ## args) ++#else ++#define DBG(fmt, args...) ++#endif + -+static int ag71xx_rx_packets(struct ag71xx *ag, int limit) -+{ -+ struct net_device *dev = ag->dev; -+ struct ag71xx_ring *ring = &ag->rx_ring; -+ int done = 0; ++#define AR71XX_PCI_DELAY 100 /* msecs */ + -+ DBG("%s: rx packets, limit=%d, curr=%u, dirty=%u\n", -+ dev->name, limit, ring->curr, ring->dirty); ++#if 0 ++#define PCI_IDSEL_BASE PCI_IDSEL_ADL_START ++#else ++#define PCI_IDSEL_BASE 0 ++#endif + -+ while (done < limit) { -+ unsigned int i = ring->curr % AG71XX_RX_RING_SIZE; -+ struct ag71xx_desc *desc = ring->buf[i].desc; -+ struct sk_buff *skb; -+ int pktlen; -+ int err = 0; ++static void __iomem *ar71xx_pcicfg_base; ++static DEFINE_SPINLOCK(ar71xx_pci_lock); ++static int ar71xx_pci_fixup_enable; + -+ if (ag71xx_desc_empty(desc)) -+ break; ++static inline void ar71xx_pci_delay(void) ++{ ++ mdelay(AR71XX_PCI_DELAY); ++} + -+ if ((ring->dirty + AG71XX_RX_RING_SIZE) == ring->curr) { -+ ag71xx_assert(0); -+ break; -+ } ++/* Byte lane enable bits */ ++static u8 ble_table[4][4] = { ++ {0x0, 0xf, 0xf, 0xf}, ++ {0xe, 0xd, 0xb, 0x7}, ++ {0xc, 0xf, 0x3, 0xf}, ++ {0xf, 0xf, 0xf, 0xf}, ++}; + -+ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_PR); ++static inline u32 ar71xx_pci_get_ble(int where, int size, int local) ++{ ++ u32 t; + -+ skb = ring->buf[i].skb; -+ pktlen = ag71xx_desc_pktlen(desc); -+ pktlen -= ETH_FCS_LEN; ++ t = ble_table[size & 3][where & 3]; ++ BUG_ON(t == 0xf); ++ t <<= (local) ? 20 : 4; ++ return t; ++} + -+ dma_unmap_single(&dev->dev, ring->buf[i].dma_addr, -+ AG71XX_RX_PKT_SIZE, DMA_FROM_DEVICE); ++static inline u32 ar71xx_pci_bus_addr(struct pci_bus *bus, unsigned int devfn, ++ int where) ++{ ++ u32 ret; + -+ dev->last_rx = jiffies; -+ dev->stats.rx_packets++; -+ dev->stats.rx_bytes += pktlen; ++ if (!bus->number) { ++ /* type 0 */ ++ ret = (1 << (PCI_IDSEL_BASE + PCI_SLOT(devfn))) ++ | (PCI_FUNC(devfn) << 8) | (where & ~3); ++ } else { ++ /* type 1 */ ++ ret = (bus->number << 16) | (PCI_SLOT(devfn) << 11) ++ | (PCI_FUNC(devfn) << 8) | (where & ~3) | 1; ++ } + -+ skb_put(skb, pktlen); -+ if (ag71xx_has_ar8216(ag)) -+ err = ag71xx_remove_ar8216_header(ag, skb, pktlen); ++ return ret; ++} + -+ if (err) { -+ dev->stats.rx_dropped++; -+ kfree_skb(skb); -+ } else { -+ skb->dev = dev; -+ skb->ip_summed = CHECKSUM_NONE; -+ if (ag->phy_dev) { -+ ag->phy_dev->netif_receive_skb(skb); -+ } else { -+ skb->protocol = eth_type_trans(skb, dev); -+ netif_receive_skb(skb); -+ } -+ } ++int ar71xx_pci_be_handler(int is_fixup) ++{ ++ void __iomem *base = ar71xx_pcicfg_base; ++ u32 pci_err; ++ u32 ahb_err; + -+ ring->buf[i].skb = NULL; -+ done++; ++ pci_err = __raw_readl(base + PCI_REG_PCI_ERR) & 3; ++ if (pci_err) { ++ if (!is_fixup) ++ printk(KERN_ALERT "PCI error %d at PCI addr 0x%x\n", ++ pci_err, ++ __raw_readl(base + PCI_REG_PCI_ERR_ADDR)); + -+ ring->curr++; ++ __raw_writel(pci_err, base + PCI_REG_PCI_ERR); + } + -+ ag71xx_ring_rx_refill(ag); ++ ahb_err = __raw_readl(base + PCI_REG_AHB_ERR) & 1; ++ if (ahb_err) { ++ if (!is_fixup) ++ printk(KERN_ALERT "AHB error at AHB address 0x%x\n", ++ __raw_readl(base + PCI_REG_AHB_ERR_ADDR)); + -+ DBG("%s: rx finish, curr=%u, dirty=%u, done=%d\n", -+ dev->name, ring->curr, ring->dirty, done); ++ __raw_writel(ahb_err, base + PCI_REG_AHB_ERR); ++ } + -+ return done; ++ return (ahb_err | pci_err) ? 1 : 0; +} + -+static int ag71xx_poll(struct napi_struct *napi, int limit) ++static inline int ar71xx_pci_set_cfgaddr(struct pci_bus *bus, ++ unsigned int devfn, int where, int size, u32 cmd) +{ -+ struct ag71xx *ag = container_of(napi, struct ag71xx, napi); -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); -+ struct net_device *dev = ag->dev; -+ struct ag71xx_ring *rx_ring; -+ unsigned long flags; -+ u32 status; -+ int tx_done; -+ int rx_done; -+ -+ pdata->ddr_flush(); -+ tx_done = ag71xx_tx_packets(ag); -+ -+ DBG("%s: processing RX ring\n", dev->name); -+ rx_done = ag71xx_rx_packets(ag, limit); -+ -+ ag71xx_debugfs_update_napi_stats(ag, rx_done, tx_done); ++ void __iomem *base = ar71xx_pcicfg_base; ++ u32 addr; + -+ rx_ring = &ag->rx_ring; -+ if (rx_ring->buf[rx_ring->dirty % AG71XX_RX_RING_SIZE].skb == NULL) -+ goto oom; ++ addr = ar71xx_pci_bus_addr(bus, devfn, where); + -+ status = ag71xx_rr(ag, AG71XX_REG_RX_STATUS); -+ if (unlikely(status & RX_STATUS_OF)) { -+ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_OF); -+ dev->stats.rx_fifo_errors++; ++ DBG("PCI: set cfgaddr: %02x:%02x.%01x/%02x:%01d, addr=%08x\n", ++ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), ++ where, size, addr); + -+ /* restart RX */ -+ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, RX_CTRL_RXE); -+ } ++ __raw_writel(addr, base + PCI_REG_CFG_AD); ++ __raw_writel(cmd | ar71xx_pci_get_ble(where, size, 0), ++ base + PCI_REG_CFG_CBE); + -+ if (rx_done < limit) { -+ if (status & RX_STATUS_PR) -+ goto more; ++ return ar71xx_pci_be_handler(1); ++} + -+ status = ag71xx_rr(ag, AG71XX_REG_TX_STATUS); -+ if (status & TX_STATUS_PS) -+ goto more; ++static int ar71xx_pci_read_config(struct pci_bus *bus, unsigned int devfn, ++ int where, int size, u32 *value) ++{ ++ void __iomem *base = ar71xx_pcicfg_base; ++ static u32 mask[8] = {0, 0xff, 0xffff, 0, 0xffffffff, 0, 0, 0}; ++ unsigned long flags; ++ u32 data; ++ int retry = 0; ++ int ret; + -+ DBG("%s: disable polling mode, rx=%d, tx=%d,limit=%d\n", -+ dev->name, rx_done, tx_done, limit); ++ ret = PCIBIOS_SUCCESSFUL; + -+ napi_complete(napi); ++ DBG("PCI: read config: %02x:%02x.%01x/%02x:%01d\n", bus->number, ++ PCI_SLOT(devfn), PCI_FUNC(devfn), where, size); + -+ /* enable interrupts */ -+ spin_lock_irqsave(&ag->lock, flags); -+ ag71xx_int_enable(ag, AG71XX_INT_POLL); -+ spin_unlock_irqrestore(&ag->lock, flags); -+ return rx_done; -+ } ++retry: ++ spin_lock_irqsave(&ar71xx_pci_lock, flags); + -+ more: -+ DBG("%s: stay in polling mode, rx=%d, tx=%d, limit=%d\n", -+ dev->name, rx_done, tx_done, limit); -+ return rx_done; ++ if (bus->number == 0 && devfn == 0) { ++ u32 t; + -+ oom: -+ if (netif_msg_rx_err(ag)) -+ printk(KERN_DEBUG "%s: out of memory\n", dev->name); ++ t = PCI_CRP_CMD_READ | (where & ~3); + -+ mod_timer(&ag->oom_timer, jiffies + AG71XX_OOM_REFILL); -+ napi_complete(napi); -+ return 0; -+} ++ __raw_writel(t, base + PCI_REG_CRP_AD_CBE); ++ data = __raw_readl(base + PCI_REG_CRP_RDDATA); + -+static irqreturn_t ag71xx_interrupt(int irq, void *dev_id) -+{ -+ struct net_device *dev = dev_id; -+ struct ag71xx *ag = netdev_priv(dev); -+ u32 status; ++ DBG("PCI: rd local cfg, ad_cbe:%08x, data:%08x\n", t, data); + -+ status = ag71xx_rr(ag, AG71XX_REG_INT_STATUS); -+ ag71xx_dump_intr(ag, "raw", status); ++ } else { ++ int err; + -+ if (unlikely(!status)) -+ return IRQ_NONE; ++ err = ar71xx_pci_set_cfgaddr(bus, devfn, where, size, ++ PCI_CFG_CMD_READ); + -+ if (unlikely(status & AG71XX_INT_ERR)) { -+ if (status & AG71XX_INT_TX_BE) { -+ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_BE); -+ dev_err(&dev->dev, "TX BUS error\n"); -+ } -+ if (status & AG71XX_INT_RX_BE) { -+ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_BE); -+ dev_err(&dev->dev, "RX BUS error\n"); ++ if (err == 0) { ++ data = __raw_readl(base + PCI_REG_CFG_RDDATA); ++ } else { ++ ret = PCIBIOS_DEVICE_NOT_FOUND; ++ data = ~0; + } + } + -+ if (likely(status & AG71XX_INT_POLL)) { -+ ag71xx_int_disable(ag, AG71XX_INT_POLL); -+ DBG("%s: enable polling mode\n", dev->name); -+ napi_schedule(&ag->napi); -+ } ++ spin_unlock_irqrestore(&ar71xx_pci_lock, flags); + -+ ag71xx_debugfs_update_int_stats(ag, status); ++ DBG("PCI: read config: data=%08x raw=%08x\n", ++ (data >> (8 * (where & 3))) & mask[size & 7], data); + -+ return IRQ_HANDLED; -+} ++ *value = (data >> (8 * (where & 3))) & mask[size & 7]; + -+static void ag71xx_set_multicast_list(struct net_device *dev) -+{ -+ /* TODO */ -+} ++ /* ++ * PCI controller bug: sometimes reads to the PCI_COMMAND register ++ * return 0xffff, even though the PCI trace shows the correct value. ++ * Work around this by retrying reads to this register ++ */ ++ if (where == PCI_COMMAND && (*value & 0xffff) == 0xffff && retry++ < 2) ++ goto retry; + -+#ifdef CONFIG_NET_POLL_CONTROLLER -+/* -+ * Polling 'interrupt' - used by things like netconsole to send skbs -+ * without having to re-enable interrupts. It's not called while -+ * the interrupt routine is executing. -+ */ -+static void ag71xx_netpoll(struct net_device *dev) -+{ -+ disable_irq(dev->irq); -+ ag71xx_interrupt(dev->irq, dev); -+ enable_irq(dev->irq); ++ return ret; +} -+#endif -+ -+static const struct net_device_ops ag71xx_netdev_ops = { -+ .ndo_open = ag71xx_open, -+ .ndo_stop = ag71xx_stop, -+ .ndo_start_xmit = ag71xx_hard_start_xmit, -+ .ndo_set_multicast_list = ag71xx_set_multicast_list, -+ .ndo_do_ioctl = ag71xx_do_ioctl, -+ .ndo_tx_timeout = ag71xx_tx_timeout, -+ .ndo_change_mtu = eth_change_mtu, -+ .ndo_set_mac_address = eth_mac_addr, -+ .ndo_validate_addr = eth_validate_addr, -+#ifdef CONFIG_NET_POLL_CONTROLLER -+ .ndo_poll_controller = ag71xx_netpoll, -+#endif -+}; + -+static int __init ag71xx_probe(struct platform_device *pdev) ++static int ar71xx_pci_write_config(struct pci_bus *bus, unsigned int devfn, ++ int where, int size, u32 value) +{ -+ struct net_device *dev; -+ struct resource *res; -+ struct ag71xx *ag; -+ struct ag71xx_platform_data *pdata; -+ int err; ++ void __iomem *base = ar71xx_pcicfg_base; ++ unsigned long flags; ++ int ret; + -+ pdata = pdev->dev.platform_data; -+ if (!pdata) { -+ dev_err(&pdev->dev, "no platform data specified\n"); -+ err = -ENXIO; -+ goto err_out; -+ } ++ DBG("PCI: write config: %02x:%02x.%01x/%02x:%01d value=%08x\n", ++ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), ++ where, size, value); + -+ if (pdata->mii_bus_dev == NULL) { -+ dev_err(&pdev->dev, "no MII bus device specified\n"); -+ err = -EINVAL; -+ goto err_out; -+ } ++ value = value << (8 * (where & 3)); ++ ret = PCIBIOS_SUCCESSFUL; + -+ dev = alloc_etherdev(sizeof(*ag)); -+ if (!dev) { -+ dev_err(&pdev->dev, "alloc_etherdev failed\n"); -+ err = -ENOMEM; -+ goto err_out; -+ } ++ spin_lock_irqsave(&ar71xx_pci_lock, flags); ++ if (bus->number == 0 && devfn == 0) { ++ u32 t; + -+ SET_NETDEV_DEV(dev, &pdev->dev); ++ t = PCI_CRP_CMD_WRITE | (where & ~3); ++ t |= ar71xx_pci_get_ble(where, size, 1); + -+ ag = netdev_priv(dev); -+ ag->pdev = pdev; -+ ag->dev = dev; -+ ag->msg_enable = netif_msg_init(ag71xx_msg_level, -+ AG71XX_DEFAULT_MSG_ENABLE); -+ spin_lock_init(&ag->lock); ++ DBG("PCI: wr local cfg, ad_cbe:%08x, value:%08x\n", t, value); + -+ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "mac_base"); -+ if (!res) { -+ dev_err(&pdev->dev, "no mac_base resource found\n"); -+ err = -ENXIO; -+ goto err_out; -+ } ++ __raw_writel(t, base + PCI_REG_CRP_AD_CBE); ++ __raw_writel(value, base + PCI_REG_CRP_WRDATA); ++ } else { ++ int err; + -+ ag->mac_base = ioremap_nocache(res->start, res->end - res->start + 1); -+ if (!ag->mac_base) { -+ dev_err(&pdev->dev, "unable to ioremap mac_base\n"); -+ err = -ENOMEM; -+ goto err_free_dev; -+ } ++ err = ar71xx_pci_set_cfgaddr(bus, devfn, where, size, ++ PCI_CFG_CMD_WRITE); + -+ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "mii_ctrl"); -+ if (!res) { -+ dev_err(&pdev->dev, "no mii_ctrl resource found\n"); -+ err = -ENXIO; -+ goto err_unmap_base; ++ if (err == 0) ++ __raw_writel(value, base + PCI_REG_CFG_WRDATA); ++ else ++ ret = PCIBIOS_DEVICE_NOT_FOUND; + } ++ spin_unlock_irqrestore(&ar71xx_pci_lock, flags); + -+ ag->mii_ctrl = ioremap_nocache(res->start, res->end - res->start + 1); -+ if (!ag->mii_ctrl) { -+ dev_err(&pdev->dev, "unable to ioremap mii_ctrl\n"); -+ err = -ENOMEM; -+ goto err_unmap_base; -+ } ++ return ret; ++} + -+ dev->irq = platform_get_irq(pdev, 0); -+ err = request_irq(dev->irq, ag71xx_interrupt, -+ IRQF_DISABLED | IRQF_SAMPLE_RANDOM, -+ dev->name, dev); -+ if (err) { -+ dev_err(&pdev->dev, "unable to request IRQ %d\n", dev->irq); -+ goto err_unmap_mii_ctrl; -+ } ++static void ar71xx_pci_fixup(struct pci_dev *dev) ++{ ++ u32 t; + -+ dev->base_addr = (unsigned long)ag->mac_base; -+ dev->netdev_ops = &ag71xx_netdev_ops; -+ dev->ethtool_ops = &ag71xx_ethtool_ops; ++ if (!ar71xx_pci_fixup_enable) ++ return; + -+ INIT_WORK(&ag->restart_work, ag71xx_restart_work_func); ++ if (dev->bus->number != 0 || dev->devfn != 0) ++ return; + -+ init_timer(&ag->oom_timer); -+ ag->oom_timer.data = (unsigned long) dev; -+ ag->oom_timer.function = ag71xx_oom_timer_handler; ++ DBG("PCI: fixup host controller %s (%04x:%04x)\n", pci_name(dev), ++ dev->vendor, dev->device); + -+ memcpy(dev->dev_addr, pdata->mac_addr, ETH_ALEN); ++ /* setup COMMAND register */ ++ t = PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | PCI_COMMAND_INVALIDATE ++ | PCI_COMMAND_PARITY | PCI_COMMAND_SERR | PCI_COMMAND_FAST_BACK; + -+ netif_napi_add(dev, &ag->napi, ag71xx_poll, AG71XX_NAPI_WEIGHT); ++ pci_write_config_word(dev, PCI_COMMAND, t); ++} ++DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, ar71xx_pci_fixup); + -+ err = register_netdev(dev); -+ if (err) { -+ dev_err(&pdev->dev, "unable to register net device\n"); -+ goto err_free_irq; ++int __init ar71xx_pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, ++ uint8_t pin) ++{ ++ int irq = -1; ++ int i; ++ ++ slot -= PCI_IDSEL_ADL_START - PCI_IDSEL_BASE; ++ ++ for (i = 0; i < ar71xx_pci_nr_irqs; i++) { ++ struct ar71xx_pci_irq *entry; ++ ++ entry = &ar71xx_pci_irq_map[i]; ++ if (entry->slot == slot && entry->pin == pin) { ++ irq = entry->irq; ++ break; ++ } + } + -+ printk(KERN_INFO "%s: Atheros AG71xx at 0x%08lx, irq %d\n", -+ dev->name, dev->base_addr, dev->irq); ++ if (irq < 0) { ++ printk(KERN_ALERT "PCI: no irq found for pin%u@%s\n", ++ pin, pci_name((struct pci_dev *)dev)); ++ } else { ++ printk(KERN_INFO "PCI: mapping irq %d to pin%u@%s\n", ++ irq, pin, pci_name((struct pci_dev *)dev)); ++ } + -+ ag71xx_dump_regs(ag); ++ return irq; ++} + -+ ag71xx_hw_init(ag); ++static struct pci_ops ar71xx_pci_ops = { ++ .read = ar71xx_pci_read_config, ++ .write = ar71xx_pci_write_config, ++}; + -+ ag71xx_dump_regs(ag); ++static struct resource ar71xx_pci_io_resource = { ++ .name = "PCI IO space", ++ .start = 0, ++ .end = 0, ++ .flags = IORESOURCE_IO, ++}; + -+ err = ag71xx_phy_connect(ag); -+ if (err) -+ goto err_unregister_netdev; ++static struct resource ar71xx_pci_mem_resource = { ++ .name = "PCI memory space", ++ .start = AR71XX_PCI_MEM_BASE, ++ .end = AR71XX_PCI_MEM_BASE + AR71XX_PCI_MEM_SIZE - 1, ++ .flags = IORESOURCE_MEM ++}; + -+ err = ag71xx_debugfs_init(ag); -+ if (err) -+ goto err_phy_disconnect; ++static struct pci_controller ar71xx_pci_controller = { ++ .pci_ops = &ar71xx_pci_ops, ++ .mem_resource = &ar71xx_pci_mem_resource, ++ .io_resource = &ar71xx_pci_io_resource, ++}; + -+ platform_set_drvdata(pdev, dev); ++static void ar71xx_pci_irq_handler(unsigned int irq, struct irq_desc *desc) ++{ ++ void __iomem *base = ar71xx_reset_base; ++ u32 pending; + -+ return 0; ++ pending = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_STATUS) & ++ __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); + -+ err_phy_disconnect: -+ ag71xx_phy_disconnect(ag); -+ err_unregister_netdev: -+ unregister_netdev(dev); -+ err_free_irq: -+ free_irq(dev->irq, dev); -+ err_unmap_mii_ctrl: -+ iounmap(ag->mii_ctrl); -+ err_unmap_base: -+ iounmap(ag->mac_base); -+ err_free_dev: -+ kfree(dev); -+ err_out: -+ platform_set_drvdata(pdev, NULL); -+ return err; ++ if (pending & PCI_INT_DEV0) ++ generic_handle_irq(AR71XX_PCI_IRQ_DEV0); ++ ++ else if (pending & PCI_INT_DEV1) ++ generic_handle_irq(AR71XX_PCI_IRQ_DEV1); ++ ++ else if (pending & PCI_INT_DEV2) ++ generic_handle_irq(AR71XX_PCI_IRQ_DEV2); ++ ++ else if (pending & PCI_INT_CORE) ++ generic_handle_irq(AR71XX_PCI_IRQ_CORE); ++ ++ else ++ spurious_interrupt(); +} + -+static int __exit ag71xx_remove(struct platform_device *pdev) ++static void ar71xx_pci_irq_unmask(struct irq_data *d) +{ -+ struct net_device *dev = platform_get_drvdata(pdev); ++ unsigned int irq = d->irq - AR71XX_PCI_IRQ_BASE; ++ void __iomem *base = ar71xx_reset_base; ++ u32 t; + -+ if (dev) { -+ struct ag71xx *ag = netdev_priv(dev); ++ t = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ __raw_writel(t | (1 << irq), base + AR71XX_RESET_REG_PCI_INT_ENABLE); + -+ ag71xx_debugfs_exit(ag); -+ ag71xx_phy_disconnect(ag); -+ unregister_netdev(dev); -+ free_irq(dev->irq, dev); -+ iounmap(ag->mii_ctrl); -+ iounmap(ag->mac_base); -+ kfree(dev); -+ platform_set_drvdata(pdev, NULL); -+ } ++ /* flush write */ ++ (void) __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++} + -+ return 0; ++static void ar71xx_pci_irq_mask(struct irq_data *d) ++{ ++ unsigned int irq = d->irq - AR71XX_PCI_IRQ_BASE; ++ void __iomem *base = ar71xx_reset_base; ++ u32 t; ++ ++ t = __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ __raw_writel(t & ~(1 << irq), base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ ++ /* flush write */ ++ (void) __raw_readl(base + AR71XX_RESET_REG_PCI_INT_ENABLE); +} + -+static struct platform_driver ag71xx_driver = { -+ .probe = ag71xx_probe, -+ .remove = __exit_p(ag71xx_remove), -+ .driver = { -+ .name = AG71XX_DRV_NAME, -+ } ++static struct irq_chip ar71xx_pci_irq_chip = { ++ .name = "AR71XX PCI ", ++ .irq_mask = ar71xx_pci_irq_mask, ++ .irq_unmask = ar71xx_pci_irq_unmask, ++ .irq_mask_ack = ar71xx_pci_irq_mask, +}; + -+static int __init ag71xx_module_init(void) ++static void __init ar71xx_pci_irq_init(void) +{ -+ int ret; -+ -+ ret = ag71xx_debugfs_root_init(); -+ if (ret) -+ goto err_out; -+ -+ ret = ag71xx_mdio_driver_init(); -+ if (ret) -+ goto err_debugfs_exit; ++ void __iomem *base = ar71xx_reset_base; ++ int i; + -+ ret = platform_driver_register(&ag71xx_driver); -+ if (ret) -+ goto err_mdio_exit; ++ __raw_writel(0, base + AR71XX_RESET_REG_PCI_INT_ENABLE); ++ __raw_writel(0, base + AR71XX_RESET_REG_PCI_INT_STATUS); + -+ return 0; ++ for (i = AR71XX_PCI_IRQ_BASE; ++ i < AR71XX_PCI_IRQ_BASE + AR71XX_PCI_IRQ_COUNT; i++) ++ irq_set_chip_and_handler(i, &ar71xx_pci_irq_chip, ++ handle_level_irq); + -+ err_mdio_exit: -+ ag71xx_mdio_driver_exit(); -+ err_debugfs_exit: -+ ag71xx_debugfs_root_exit(); -+ err_out: -+ return ret; ++ irq_set_chained_handler(AR71XX_CPU_IRQ_IP2, ar71xx_pci_irq_handler); +} + -+static void __exit ag71xx_module_exit(void) ++int __init ar71xx_pcibios_init(void) +{ -+ platform_driver_unregister(&ag71xx_driver); -+ ag71xx_mdio_driver_exit(); -+ ag71xx_debugfs_root_exit(); -+} ++ void __iomem *ddr_base = ar71xx_ddr_base; + -+module_init(ag71xx_module_init); -+module_exit(ag71xx_module_exit); ++ ar71xx_device_stop(RESET_MODULE_PCI_BUS | RESET_MODULE_PCI_CORE); ++ ar71xx_pci_delay(); + -+MODULE_VERSION(AG71XX_DRV_VERSION); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_AUTHOR("Imre Kaloz "); -+MODULE_LICENSE("GPL v2"); -+MODULE_ALIAS("platform:" AG71XX_DRV_NAME); -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_mdio.c linux-2.6.39/drivers/net/ag71xx/ag71xx_mdio.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_mdio.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_mdio.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,243 @@ ++ ar71xx_device_start(RESET_MODULE_PCI_BUS | RESET_MODULE_PCI_CORE); ++ ar71xx_pci_delay(); ++ ++ ar71xx_pcicfg_base = ioremap_nocache(AR71XX_PCI_CFG_BASE, ++ AR71XX_PCI_CFG_SIZE); ++ if (ar71xx_pcicfg_base == NULL) ++ return -ENOMEM; ++ ++ __raw_writel(PCI_WIN0_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN0); ++ __raw_writel(PCI_WIN1_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN1); ++ __raw_writel(PCI_WIN2_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN2); ++ __raw_writel(PCI_WIN3_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN3); ++ __raw_writel(PCI_WIN4_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN4); ++ __raw_writel(PCI_WIN5_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN5); ++ __raw_writel(PCI_WIN6_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN6); ++ __raw_writel(PCI_WIN7_OFFS, ddr_base + AR71XX_DDR_REG_PCI_WIN7); ++ ++ ar71xx_pci_delay(); ++ ++ /* clear bus errors */ ++ (void)ar71xx_pci_be_handler(1); ++ ++ ar71xx_pci_fixup_enable = 1; ++ ar71xx_pci_irq_init(); ++ register_pci_controller(&ar71xx_pci_controller); ++ ++ return 0; ++} +diff -Nur linux-2.6.39.orig/arch/mips/pci/pci-ar724x.c linux-2.6.39/arch/mips/pci/pci-ar724x.c +--- linux-2.6.39.orig/arch/mips/pci/pci-ar724x.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/arch/mips/pci/pci-ar724x.c 2011-08-06 09:32:37.088017079 +0200 +@@ -0,0 +1,389 @@ +/* -+ * Atheros AR71xx built-in ethernet mac driver ++ * Atheros AR724x PCI host controller driver + * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009-2010 Gabor Juhos + * -+ * Based on Atheros' AG7100 driver ++ * Parts of this file are based on Atheros' 2.6.15 BSP + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 as published + * by the Free Software Foundation. + */ + -+#include "ag71xx.h" ++#include ++#include ++#include ++#include ++#include ++#include ++#include + -+#define AG71XX_MDIO_RETRY 1000 -+#define AG71XX_MDIO_DELAY 5 ++#include ++#include + -+static inline void ag71xx_mdio_wr(struct ag71xx_mdio *am, unsigned reg, -+ u32 value) -+{ -+ void __iomem *r; ++#undef DEBUG ++#ifdef DEBUG ++#define DBG(fmt, args...) printk(KERN_INFO fmt, ## args) ++#else ++#define DBG(fmt, args...) ++#endif + -+ r = am->mdio_base + reg; -+ __raw_writel(value, r); ++static void __iomem *ar724x_pci_localcfg_base; ++static void __iomem *ar724x_pci_devcfg_base; ++static void __iomem *ar724x_pci_ctrl_base; ++static int ar724x_pci_fixup_enable; + -+ /* flush write */ -+ (void) __raw_readl(r); -+} ++static DEFINE_SPINLOCK(ar724x_pci_lock); + -+static inline u32 ag71xx_mdio_rr(struct ag71xx_mdio *am, unsigned reg) ++static void ar724x_pci_read(void __iomem *base, int where, int size, u32 *value) +{ -+ return __raw_readl(am->mdio_base + reg); -+} ++ unsigned long flags; ++ u32 data; + -+static void ag71xx_mdio_dump_regs(struct ag71xx_mdio *am) -+{ -+ DBG("%s: mii_cfg=%08x, mii_cmd=%08x, mii_addr=%08x\n", -+ am->mii_bus->name, -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_CFG), -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_CMD), -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_ADDR)); -+ DBG("%s: mii_ctrl=%08x, mii_status=%08x, mii_ind=%08x\n", -+ am->mii_bus->name, -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_CTRL), -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_STATUS), -+ ag71xx_mdio_rr(am, AG71XX_REG_MII_IND)); ++ spin_lock_irqsave(&ar724x_pci_lock, flags); ++ data = __raw_readl(base + (where & ~3)); ++ ++ switch (size) { ++ case 1: ++ if (where & 1) ++ data >>= 8; ++ if (where & 2) ++ data >>= 16; ++ data &= 0xFF; ++ break; ++ case 2: ++ if (where & 2) ++ data >>= 16; ++ data &= 0xFFFF; ++ break; ++ } ++ ++ *value = data; ++ spin_unlock_irqrestore(&ar724x_pci_lock, flags); +} + -+static int ag71xx_mdio_mii_read(struct ag71xx_mdio *am, int addr, int reg) ++static void ar724x_pci_write(void __iomem *base, int where, int size, u32 value) +{ -+ int ret; -+ int i; ++ unsigned long flags; ++ u32 data; ++ int s; + -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_WRITE); -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_ADDR, -+ ((addr & 0xff) << MII_ADDR_SHIFT) | (reg & 0xff)); -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_READ); ++ spin_lock_irqsave(&ar724x_pci_lock, flags); ++ data = __raw_readl(base + (where & ~3)); + -+ i = AG71XX_MDIO_RETRY; -+ while (ag71xx_mdio_rr(am, AG71XX_REG_MII_IND) & MII_IND_BUSY) { -+ if (i-- == 0) { -+ printk(KERN_ERR "%s: mii_read timed out\n", -+ am->mii_bus->name); -+ ret = 0xffff; -+ goto out; -+ } -+ udelay(AG71XX_MDIO_DELAY); ++ switch (size) { ++ case 1: ++ s = ((where & 3) << 3); ++ data &= ~(0xFF << s); ++ data |= ((value & 0xFF) << s); ++ break; ++ case 2: ++ s = ((where & 2) << 3); ++ data &= ~(0xFFFF << s); ++ data |= ((value & 0xFFFF) << s); ++ break; ++ case 4: ++ data = value; ++ break; + } + -+ ret = ag71xx_mdio_rr(am, AG71XX_REG_MII_STATUS) & 0xffff; -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_WRITE); -+ -+ DBG("mii_read: addr=%04x, reg=%04x, value=%04x\n", addr, reg, ret); -+ -+ out: -+ return ret; ++ __raw_writel(data, base + (where & ~3)); ++ /* flush write */ ++ (void)__raw_readl(base + (where & ~3)); ++ spin_unlock_irqrestore(&ar724x_pci_lock, flags); +} + -+static void ag71xx_mdio_mii_write(struct ag71xx_mdio *am, -+ int addr, int reg, u16 val) ++static int ar724x_pci_read_config(struct pci_bus *bus, unsigned int devfn, ++ int where, int size, u32 *value) +{ -+ int i; + -+ DBG("mii_write: addr=%04x, reg=%04x, value=%04x\n", addr, reg, val); ++ if (bus->number != 0 || devfn != 0) ++ return PCIBIOS_DEVICE_NOT_FOUND; + -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_ADDR, -+ ((addr & 0xff) << MII_ADDR_SHIFT) | (reg & 0xff)); -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CTRL, val); ++ ar724x_pci_read(ar724x_pci_devcfg_base, where, size, value); + -+ i = AG71XX_MDIO_RETRY; -+ while (ag71xx_mdio_rr(am, AG71XX_REG_MII_IND) & MII_IND_BUSY) { -+ if (i-- == 0) { -+ printk(KERN_ERR "%s: mii_write timed out\n", -+ am->mii_bus->name); -+ break; -+ } -+ udelay(AG71XX_MDIO_DELAY); ++ DBG("PCI: read config: %02x:%02x.%01x/%02x:%01d, value=%08x\n", ++ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), ++ where, size, *value); ++ ++ /* ++ * WAR for BAR issue - We are unable to access the PCI device space ++ * if we set the BAR with proper base address ++ */ ++ if ((where == 0x10) && (size == 4)) { ++ u32 val; ++ val = (ar71xx_soc == AR71XX_SOC_AR7240) ? 0xffff : 0x1000ffff; ++ ar724x_pci_write(ar724x_pci_devcfg_base, where, size, val); + } ++ ++ return PCIBIOS_SUCCESSFUL; +} + -+static int ag71xx_mdio_reset(struct mii_bus *bus) ++static int ar724x_pci_write_config(struct pci_bus *bus, unsigned int devfn, ++ int where, int size, u32 value) +{ -+ struct ag71xx_mdio *am = bus->priv; -+ u32 t; -+ -+ if (am->pdata->is_ar7240) -+ t = MII_CFG_CLK_DIV_6; -+ else -+ t = MII_CFG_CLK_DIV_28; ++ if (bus->number != 0 || devfn != 0) ++ return PCIBIOS_DEVICE_NOT_FOUND; + -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CFG, t | MII_CFG_RESET); -+ udelay(100); ++ DBG("PCI: write config: %02x:%02x.%01x/%02x:%01d, value=%08x\n", ++ bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn), ++ where, size, value); + -+ ag71xx_mdio_wr(am, AG71XX_REG_MII_CFG, t); -+ udelay(100); ++ ar724x_pci_write(ar724x_pci_devcfg_base, where, size, value); + -+ return 0; ++ return PCIBIOS_SUCCESSFUL; +} + -+static int ag71xx_mdio_read(struct mii_bus *bus, int addr, int reg) ++static void ar724x_pci_fixup(struct pci_dev *dev) +{ -+ struct ag71xx_mdio *am = bus->priv; ++ u16 cmd; + -+ return ag71xx_mdio_mii_read(am, addr, reg); -+} ++ if (!ar724x_pci_fixup_enable) ++ return; + -+static int ag71xx_mdio_write(struct mii_bus *bus, int addr, int reg, u16 val) -+{ -+ struct ag71xx_mdio *am = bus->priv; ++ if (dev->bus->number != 0 || dev->devfn != 0) ++ return; + -+ ag71xx_mdio_mii_write(am, addr, reg, val); -+ return 0; ++ /* setup COMMAND register */ ++ pci_read_config_word(dev, PCI_COMMAND, &cmd); ++ cmd |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | ++ PCI_COMMAND_INVALIDATE | PCI_COMMAND_PARITY | PCI_COMMAND_SERR | ++ PCI_COMMAND_FAST_BACK; ++ ++ pci_write_config_word(dev, PCI_COMMAND, cmd); +} ++DECLARE_PCI_FIXUP_EARLY(PCI_ANY_ID, PCI_ANY_ID, ar724x_pci_fixup); + -+static int __init ag71xx_mdio_probe(struct platform_device *pdev) ++int __init ar724x_pcibios_map_irq(const struct pci_dev *dev, uint8_t slot, ++ uint8_t pin) +{ -+ struct ag71xx_mdio_platform_data *pdata; -+ struct ag71xx_mdio *am; -+ struct resource *res; ++ int irq = -1; + int i; -+ int err; -+ -+ pdata = pdev->dev.platform_data; -+ if (!pdata) { -+ dev_err(&pdev->dev, "no platform data specified\n"); -+ return -EINVAL; -+ } -+ -+ am = kzalloc(sizeof(*am), GFP_KERNEL); -+ if (!am) { -+ err = -ENOMEM; -+ goto err_out; -+ } + -+ am->pdata = pdata; ++ for (i = 0; i < ar71xx_pci_nr_irqs; i++) { ++ struct ar71xx_pci_irq *entry; ++ entry = &ar71xx_pci_irq_map[i]; + -+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (!res) { -+ dev_err(&pdev->dev, "no iomem resource found\n"); -+ err = -ENXIO; -+ goto err_out; ++ if (entry->slot == slot && entry->pin == pin) { ++ irq = entry->irq; ++ break; ++ } + } + -+ am->mdio_base = ioremap_nocache(res->start, res->end - res->start + 1); -+ if (!am->mdio_base) { -+ dev_err(&pdev->dev, "unable to ioremap registers\n"); -+ err = -ENOMEM; -+ goto err_free_mdio; -+ } ++ if (irq < 0) ++ printk(KERN_ALERT "PCI: no irq found for pin%u@%s\n", ++ pin, pci_name((struct pci_dev *)dev)); ++ else ++ printk(KERN_INFO "PCI: mapping irq %d to pin%u@%s\n", ++ irq, pin, pci_name((struct pci_dev *)dev)); + -+ am->mii_bus = mdiobus_alloc(); -+ if (am->mii_bus == NULL) { -+ err = -ENOMEM; -+ goto err_iounmap; -+ } ++ return irq; ++} + -+ am->mii_bus->name = "ag71xx_mdio"; -+ am->mii_bus->read = ag71xx_mdio_read; -+ am->mii_bus->write = ag71xx_mdio_write; -+ am->mii_bus->reset = ag71xx_mdio_reset; -+ am->mii_bus->irq = am->mii_irq; -+ am->mii_bus->priv = am; -+ am->mii_bus->parent = &pdev->dev; -+ snprintf(am->mii_bus->id, MII_BUS_ID_SIZE, "%s", dev_name(&pdev->dev)); -+ am->mii_bus->phy_mask = pdata->phy_mask; ++static struct pci_ops ar724x_pci_ops = { ++ .read = ar724x_pci_read_config, ++ .write = ar724x_pci_write_config, ++}; + -+ for (i = 0; i < PHY_MAX_ADDR; i++) -+ am->mii_irq[i] = PHY_POLL; ++static struct resource ar724x_pci_io_resource = { ++ .name = "PCI IO space", ++ .start = 0, ++ .end = 0, ++ .flags = IORESOURCE_IO, ++}; + -+ ag71xx_mdio_wr(am, AG71XX_REG_MAC_CFG1, 0); ++static struct resource ar724x_pci_mem_resource = { ++ .name = "PCI memory space", ++ .start = AR71XX_PCI_MEM_BASE, ++ .end = AR71XX_PCI_MEM_BASE + AR71XX_PCI_MEM_SIZE - 1, ++ .flags = IORESOURCE_MEM ++}; + -+ err = mdiobus_register(am->mii_bus); -+ if (err) -+ goto err_free_bus; -+ -+ ag71xx_mdio_dump_regs(am); ++static struct pci_controller ar724x_pci_controller = { ++ .pci_ops = &ar724x_pci_ops, ++ .mem_resource = &ar724x_pci_mem_resource, ++ .io_resource = &ar724x_pci_io_resource, ++}; + -+ platform_set_drvdata(pdev, am); -+ return 0; ++static void __init ar724x_pci_reset(void) ++{ ++ ar71xx_device_stop(AR724X_RESET_PCIE); ++ ar71xx_device_stop(AR724X_RESET_PCIE_PHY); ++ ar71xx_device_stop(AR724X_RESET_PCIE_PHY_SERIAL); ++ udelay(100); + -+ err_free_bus: -+ mdiobus_free(am->mii_bus); -+ err_iounmap: -+ iounmap(am->mdio_base); -+ err_free_mdio: -+ kfree(am); -+ err_out: -+ return err; ++ ar71xx_device_start(AR724X_RESET_PCIE_PHY_SERIAL); ++ udelay(100); ++ ar71xx_device_start(AR724X_RESET_PCIE_PHY); ++ ar71xx_device_start(AR724X_RESET_PCIE); +} + -+static int __exit ag71xx_mdio_remove(struct platform_device *pdev) ++static int __init ar724x_pci_setup(void) +{ -+ struct ag71xx_mdio *am = platform_get_drvdata(pdev); ++ void __iomem *base = ar724x_pci_ctrl_base; ++ u32 t; + -+ if (am) { -+ mdiobus_unregister(am->mii_bus); -+ mdiobus_free(am->mii_bus); -+ iounmap(am->mdio_base); -+ kfree(am); -+ platform_set_drvdata(pdev, NULL); ++ /* setup COMMAND register */ ++ t = PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | PCI_COMMAND_INVALIDATE | ++ PCI_COMMAND_PARITY|PCI_COMMAND_SERR|PCI_COMMAND_FAST_BACK; ++ ++ ar724x_pci_write(ar724x_pci_localcfg_base, PCI_COMMAND, 4, t); ++ ar724x_pci_write(ar724x_pci_localcfg_base, 0x20, 4, 0x1ff01000); ++ ar724x_pci_write(ar724x_pci_localcfg_base, 0x24, 4, 0x1ff01000); ++ ++ t = __raw_readl(base + AR724X_PCI_REG_RESET); ++ if (t != 0x7) { ++ udelay(100000); ++ __raw_writel(0, base + AR724X_PCI_REG_RESET); ++ udelay(100); ++ __raw_writel(4, base + AR724X_PCI_REG_RESET); ++ udelay(100000); + } + -+ return 0; -+} ++ if (ar71xx_soc == AR71XX_SOC_AR7240) ++ t = AR724X_PCI_APP_LTSSM_ENABLE; ++ else ++ t = 0x1ffc1; ++ __raw_writel(t, base + AR724X_PCI_REG_APP); ++ /* flush write */ ++ (void) __raw_readl(base + AR724X_PCI_REG_APP); ++ udelay(1000); + -+static struct platform_driver ag71xx_mdio_driver = { -+ .probe = ag71xx_mdio_probe, -+ .remove = __exit_p(ag71xx_mdio_remove), -+ .driver = { -+ .name = "ag71xx-mdio", ++ t = __raw_readl(base + AR724X_PCI_REG_RESET); ++ if ((t & AR724X_PCI_RESET_LINK_UP) == 0x0) { ++ printk(KERN_WARNING "PCI: no PCIe module found\n"); ++ return -ENODEV; + } -+}; + -+int ag71xx_mdio_driver_init(void) -+{ -+ return platform_driver_register(&ag71xx_mdio_driver); -+} ++ if (ar71xx_soc == AR71XX_SOC_AR7241 || ++ ar71xx_soc == AR71XX_SOC_AR7242) { ++ t = __raw_readl(base + AR724X_PCI_REG_APP); ++ t |= BIT(16); ++ __raw_writel(t, base + AR724X_PCI_REG_APP); ++ } + -+void ag71xx_mdio_driver_exit(void) -+{ -+ platform_driver_unregister(&ag71xx_mdio_driver); ++ return 0; +} -diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_phy.c linux-2.6.39/drivers/net/ag71xx/ag71xx_phy.c ---- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_phy.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/net/ag71xx/ag71xx_phy.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,213 @@ -+/* -+ * Atheros AR71xx built-in ethernet mac driver -+ * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Based on Atheros' AG7100 driver -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ -+ -+#include "ag71xx.h" + -+static void ag71xx_phy_link_adjust(struct net_device *dev) ++static void ar724x_pci_irq_handler(unsigned int irq, struct irq_desc *desc) +{ -+ struct ag71xx *ag = netdev_priv(dev); -+ struct phy_device *phydev = ag->phy_dev; -+ unsigned long flags; -+ int status_change = 0; -+ -+ spin_lock_irqsave(&ag->lock, flags); -+ -+ if (phydev->link) { -+ if (ag->duplex != phydev->duplex -+ || ag->speed != phydev->speed) { -+ status_change = 1; -+ } -+ } -+ -+ if (phydev->link != ag->link) -+ status_change = 1; ++ void __iomem *base = ar724x_pci_ctrl_base; ++ u32 pending; + -+ ag->link = phydev->link; -+ ag->duplex = phydev->duplex; -+ ag->speed = phydev->speed; ++ pending = __raw_readl(base + AR724X_PCI_REG_INT_STATUS) & ++ __raw_readl(base + AR724X_PCI_REG_INT_MASK); + -+ if (status_change) -+ ag71xx_link_adjust(ag); ++ if (pending & AR724X_PCI_INT_DEV0) ++ generic_handle_irq(AR71XX_PCI_IRQ_DEV0); + -+ spin_unlock_irqrestore(&ag->lock, flags); ++ else ++ spurious_interrupt(); +} + -+void ag71xx_phy_start(struct ag71xx *ag) ++static void ar724x_pci_irq_unmask(struct irq_data *d) +{ -+ if (ag->phy_dev) { -+ phy_start(ag->phy_dev); -+ } else { -+ ag->link = 1; -+ ag71xx_link_adjust(ag); ++ void __iomem *base = ar724x_pci_ctrl_base; ++ u32 t; ++ ++ switch (d->irq) { ++ case AR71XX_PCI_IRQ_DEV0: ++ t = __raw_readl(base + AR724X_PCI_REG_INT_MASK); ++ __raw_writel(t | AR724X_PCI_INT_DEV0, ++ base + AR724X_PCI_REG_INT_MASK); ++ /* flush write */ ++ (void) __raw_readl(base + AR724X_PCI_REG_INT_MASK); + } +} + -+void ag71xx_phy_stop(struct ag71xx *ag) ++static void ar724x_pci_irq_mask(struct irq_data *d) +{ -+ if (ag->phy_dev) { -+ phy_stop(ag->phy_dev); -+ } else { -+ ag->link = 0; -+ ag71xx_link_adjust(ag); ++ void __iomem *base = ar724x_pci_ctrl_base; ++ u32 t; ++ ++ switch (d->irq) { ++ case AR71XX_PCI_IRQ_DEV0: ++ t = __raw_readl(base + AR724X_PCI_REG_INT_MASK); ++ __raw_writel(t & ~AR724X_PCI_INT_DEV0, ++ base + AR724X_PCI_REG_INT_MASK); ++ ++ /* flush write */ ++ (void) __raw_readl(base + AR724X_PCI_REG_INT_MASK); ++ ++ t = __raw_readl(base + AR724X_PCI_REG_INT_STATUS); ++ __raw_writel(t | AR724X_PCI_INT_DEV0, ++ base + AR724X_PCI_REG_INT_STATUS); ++ ++ /* flush write */ ++ (void) __raw_readl(base + AR724X_PCI_REG_INT_STATUS); + } +} + -+static int ag71xx_phy_connect_fixed(struct ag71xx *ag) ++static struct irq_chip ar724x_pci_irq_chip = { ++ .name = "AR724X PCI ", ++ .irq_mask = ar724x_pci_irq_mask, ++ .irq_unmask = ar724x_pci_irq_unmask, ++ .irq_mask_ack = ar724x_pci_irq_mask, ++}; ++ ++static void __init ar724x_pci_irq_init(void) +{ -+ struct net_device *dev = ag->dev; -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); -+ int ret = 0; ++ void __iomem *base = ar724x_pci_ctrl_base; ++ u32 t; ++ int i; + -+ /* use fixed settings */ -+ switch (pdata->speed) { -+ case SPEED_10: -+ case SPEED_100: -+ case SPEED_1000: -+ break; -+ default: -+ printk(KERN_ERR "%s: invalid speed specified\n", dev->name); -+ ret = -EINVAL; -+ break; ++ t = ar71xx_reset_rr(AR724X_RESET_REG_RESET_MODULE); ++ if (t & (AR724X_RESET_PCIE | AR724X_RESET_PCIE_PHY | ++ AR724X_RESET_PCIE_PHY_SERIAL)) { ++ return; + } + -+ printk(KERN_DEBUG "%s: using fixed link parameters\n", dev->name); ++ __raw_writel(0, base + AR724X_PCI_REG_INT_MASK); ++ __raw_writel(0, base + AR724X_PCI_REG_INT_STATUS); + -+ ag->duplex = pdata->duplex; -+ ag->speed = pdata->speed; ++ for (i = AR71XX_PCI_IRQ_BASE; ++ i < AR71XX_PCI_IRQ_BASE + AR71XX_PCI_IRQ_COUNT; i++) ++ irq_set_chip_and_handler(i, &ar724x_pci_irq_chip, ++ handle_level_irq); + -+ return ret; ++ irq_set_chained_handler(AR71XX_CPU_IRQ_IP2, ar724x_pci_irq_handler); +} + -+static int ag71xx_phy_connect_multi(struct ag71xx *ag) ++int __init ar724x_pcibios_init(void) +{ -+ struct net_device *dev = ag->dev; -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); -+ struct phy_device *phydev = NULL; -+ int phy_addr; -+ int ret = 0; ++ int ret = -ENOMEM; + -+ for (phy_addr = 0; phy_addr < PHY_MAX_ADDR; phy_addr++) { -+ if (!(pdata->phy_mask & (1 << phy_addr))) -+ continue; ++ ar724x_pci_localcfg_base = ioremap_nocache(AR724X_PCI_CRP_BASE, ++ AR724X_PCI_CRP_SIZE); ++ if (ar724x_pci_localcfg_base == NULL) ++ goto err; + -+ if (ag->mii_bus->phy_map[phy_addr] == NULL) -+ continue; ++ ar724x_pci_devcfg_base = ioremap_nocache(AR724X_PCI_CFG_BASE, ++ AR724X_PCI_CFG_SIZE); ++ if (ar724x_pci_devcfg_base == NULL) ++ goto err_unmap_localcfg; + -+ DBG("%s: PHY found at %s, uid=%08x\n", -+ dev->name, -+ dev_name(&ag->mii_bus->phy_map[phy_addr]->dev), -+ ag->mii_bus->phy_map[phy_addr]->phy_id); ++ ar724x_pci_ctrl_base = ioremap_nocache(AR724X_PCI_CTRL_BASE, ++ AR724X_PCI_CTRL_SIZE); ++ if (ar724x_pci_ctrl_base == NULL) ++ goto err_unmap_devcfg; + -+ if (phydev == NULL) -+ phydev = ag->mii_bus->phy_map[phy_addr]; -+ } ++ ar724x_pci_reset(); ++ ret = ar724x_pci_setup(); ++ if (ret) ++ goto err_unmap_ctrl; + -+ if (!phydev) { -+ printk(KERN_ERR "%s: no PHY found with phy_mask=%08x\n", -+ dev->name, pdata->phy_mask); -+ return -ENODEV; -+ } ++ ar724x_pci_fixup_enable = 1; ++ ar724x_pci_irq_init(); ++ register_pci_controller(&ar724x_pci_controller); + -+ ag->phy_dev = phy_connect(dev, dev_name(&phydev->dev), -+ &ag71xx_phy_link_adjust, 0, -+ pdata->phy_if_mode); -+ -+ if (IS_ERR(ag->phy_dev)) { -+ printk(KERN_ERR "%s: could not connect to PHY at %s\n", -+ dev->name, dev_name(&phydev->dev)); -+ return PTR_ERR(ag->phy_dev); -+ } ++ return 0; + -+ /* mask with MAC supported features */ -+ if (pdata->has_gbit) -+ phydev->supported &= PHY_GBIT_FEATURES; -+ else -+ phydev->supported &= PHY_BASIC_FEATURES; ++err_unmap_ctrl: ++ iounmap(ar724x_pci_ctrl_base); ++err_unmap_devcfg: ++ iounmap(ar724x_pci_devcfg_base); ++err_unmap_localcfg: ++ iounmap(ar724x_pci_localcfg_base); ++err: ++ return ret; ++} +diff -Nur linux-2.6.39.orig/drivers/gpio/nxp_74hc153.c linux-2.6.39/drivers/gpio/nxp_74hc153.c +--- linux-2.6.39.orig/drivers/gpio/nxp_74hc153.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/gpio/nxp_74hc153.c 2011-04-27 12:19:22.327664626 +0200 +@@ -0,0 +1,247 @@ ++/* ++ * NXP 74HC153 - Dual 4-input multiplexer GPIO driver ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ */ + -+ phydev->advertising = phydev->supported; ++#include ++#include ++#include ++#include ++#include ++#include + -+ printk(KERN_DEBUG "%s: connected to PHY at %s [uid=%08x, driver=%s]\n", -+ dev->name, dev_name(&phydev->dev), -+ phydev->phy_id, phydev->drv->name); ++#define NXP_74HC153_NUM_GPIOS 8 ++#define NXP_74HC153_S0_MASK 0x1 ++#define NXP_74HC153_S1_MASK 0x2 ++#define NXP_74HC153_BANK_MASK 0x4 + -+ ag->link = 0; -+ ag->speed = 0; -+ ag->duplex = -1; ++struct nxp_74hc153_chip { ++ struct device *parent; ++ struct gpio_chip gpio_chip; ++ struct mutex lock; ++}; + -+ return ret; ++static struct nxp_74hc153_chip *gpio_to_nxp(struct gpio_chip *gc) ++{ ++ return container_of(gc, struct nxp_74hc153_chip, gpio_chip); +} + -+static int dev_is_class(struct device *dev, void *class) ++static int nxp_74hc153_direction_input(struct gpio_chip *gc, unsigned offset) +{ -+ if (dev->class != NULL && !strcmp(dev->class->name, class)) -+ return 1; -+ + return 0; +} + -+static struct device *dev_find_class(struct device *parent, char *class) ++static int nxp_74hc153_direction_output(struct gpio_chip *gc, ++ unsigned offset, int val) +{ -+ if (dev_is_class(parent, class)) { -+ get_device(parent); -+ return parent; -+ } -+ -+ return device_find_child(parent, class, dev_is_class); ++ return -EINVAL; +} + -+static struct mii_bus *dev_to_mii_bus(struct device *dev) ++static int nxp_74hc153_get_value(struct gpio_chip *gc, unsigned offset) +{ -+ struct device *d; ++ struct nxp_74hc153_chip *nxp; ++ struct nxp_74hc153_platform_data *pdata; ++ unsigned s0; ++ unsigned s1; ++ unsigned pin; ++ int ret; + -+ d = dev_find_class(dev, "mdio_bus"); -+ if (d != NULL) { -+ struct mii_bus *bus; ++ nxp = gpio_to_nxp(gc); ++ pdata = nxp->parent->platform_data; + -+ bus = to_mii_bus(d); -+ put_device(d); ++ s0 = !!(offset & NXP_74HC153_S0_MASK); ++ s1 = !!(offset & NXP_74HC153_S1_MASK); ++ pin = (offset & NXP_74HC153_BANK_MASK) ? pdata->gpio_pin_2y ++ : pdata->gpio_pin_1y; + -+ return bus; -+ } ++ mutex_lock(&nxp->lock); ++ gpio_set_value(pdata->gpio_pin_s0, s0); ++ gpio_set_value(pdata->gpio_pin_s1, s1); ++ ret = gpio_get_value(pin); ++ mutex_unlock(&nxp->lock); + -+ return NULL; ++ return ret; +} + -+int ag71xx_phy_connect(struct ag71xx *ag) ++static void nxp_74hc153_set_value(struct gpio_chip *gc, ++ unsigned offset, int val) +{ -+ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ /* not supported */ ++} + -+ ag->mii_bus = dev_to_mii_bus(pdata->mii_bus_dev); -+ if (ag->mii_bus == NULL) { -+ printk(KERN_ERR "%s: unable to find MII bus on device '%s'\n", -+ ag->dev->name, dev_name(pdata->mii_bus_dev)); -+ return -ENODEV; -+ } ++static int __devinit nxp_74hc153_probe(struct platform_device *pdev) ++{ ++ struct nxp_74hc153_platform_data *pdata; ++ struct nxp_74hc153_chip *nxp; ++ struct gpio_chip *gc; ++ int err; + -+ /* Reset the mdio bus explicitly */ -+ if (ag->mii_bus->reset) { -+ mutex_lock(&ag->mii_bus->mdio_lock); -+ ag->mii_bus->reset(ag->mii_bus); -+ mutex_unlock(&ag->mii_bus->mdio_lock); ++ pdata = pdev->dev.platform_data; ++ if (pdata == NULL) { ++ dev_dbg(&pdev->dev, "no platform data specified\n"); ++ return -EINVAL; + } + -+ if (pdata->phy_mask) -+ return ag71xx_phy_connect_multi(ag); ++ nxp = kzalloc(sizeof(struct nxp_74hc153_chip), GFP_KERNEL); ++ if (nxp == NULL) { ++ dev_err(&pdev->dev, "no memory for private data\n"); ++ return -ENOMEM; ++ } + -+ return ag71xx_phy_connect_fixed(ag); -+} ++ err = gpio_request(pdata->gpio_pin_s0, dev_name(&pdev->dev)); ++ if (err) { ++ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", ++ pdata->gpio_pin_s0, err); ++ goto err_free_nxp; ++ } + -+void ag71xx_phy_disconnect(struct ag71xx *ag) -+{ -+ if (ag->phy_dev) -+ phy_disconnect(ag->phy_dev); -+} -diff -Nur linux-2.6.39.orig/drivers/net/phy/Kconfig linux-2.6.39/drivers/net/phy/Kconfig ---- linux-2.6.39.orig/drivers/net/phy/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/phy/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -91,6 +91,10 @@ - ---help--- - Supports the KSZ9021, VSC8201, KS8001 PHYs. - -+config IP175C_PHY -+ tristate "Driver for IC+ IP175C/IP178C switches" -+ select SWCONFIG ++ err = gpio_request(pdata->gpio_pin_s1, dev_name(&pdev->dev)); ++ if (err) { ++ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", ++ pdata->gpio_pin_s1, err); ++ goto err_free_s0; ++ } + - config FIXED_PHY - bool "Driver for MDIO Bus/PHY emulation with fixed speed/link PHYs" - depends on PHYLIB=y -diff -Nur linux-2.6.39.orig/drivers/net/phy/phy.c linux-2.6.39/drivers/net/phy/phy.c ---- linux-2.6.39.orig/drivers/net/phy/phy.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/phy/phy.c 2011-05-27 14:36:51.000000000 +0200 -@@ -297,6 +297,50 @@ - } - EXPORT_SYMBOL(phy_ethtool_gset); - -+int phy_ethtool_ioctl(struct phy_device *phydev, void *useraddr) -+{ -+ u32 cmd; -+ int tmp; -+ struct ethtool_cmd ecmd = { ETHTOOL_GSET }; -+ struct ethtool_value edata = { ETHTOOL_GLINK }; ++ err = gpio_request(pdata->gpio_pin_1y, dev_name(&pdev->dev)); ++ if (err) { ++ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", ++ pdata->gpio_pin_1y, err); ++ goto err_free_s1; ++ } + -+ if (get_user(cmd, (u32 *) useraddr)) -+ return -EFAULT; ++ err = gpio_request(pdata->gpio_pin_2y, dev_name(&pdev->dev)); ++ if (err) { ++ dev_err(&pdev->dev, "unable to claim gpio %u, err=%d\n", ++ pdata->gpio_pin_2y, err); ++ goto err_free_1y; ++ } + -+ switch (cmd) { -+ case ETHTOOL_GSET: -+ phy_ethtool_gset(phydev, &ecmd); -+ if (copy_to_user(useraddr, &ecmd, sizeof(ecmd))) -+ return -EFAULT; -+ return 0; ++ err = gpio_direction_output(pdata->gpio_pin_s0, 0); ++ if (err) { ++ dev_err(&pdev->dev, ++ "unable to set direction of gpio %u, err=%d\n", ++ pdata->gpio_pin_s0, err); ++ goto err_free_2y; ++ } + -+ case ETHTOOL_SSET: -+ if (copy_from_user(&ecmd, useraddr, sizeof(ecmd))) -+ return -EFAULT; -+ return phy_ethtool_sset(phydev, &ecmd); ++ err = gpio_direction_output(pdata->gpio_pin_s1, 0); ++ if (err) { ++ dev_err(&pdev->dev, ++ "unable to set direction of gpio %u, err=%d\n", ++ pdata->gpio_pin_s1, err); ++ goto err_free_2y; ++ } + -+ case ETHTOOL_NWAY_RST: -+ /* if autoneg is off, it's an error */ -+ tmp = phy_read(phydev, MII_BMCR); -+ if (tmp & BMCR_ANENABLE) { -+ tmp |= (BMCR_ANRESTART); -+ phy_write(phydev, MII_BMCR, tmp); -+ return 0; -+ } -+ return -EINVAL; ++ err = gpio_direction_input(pdata->gpio_pin_1y); ++ if (err) { ++ dev_err(&pdev->dev, ++ "unable to set direction of gpio %u, err=%d\n", ++ pdata->gpio_pin_1y, err); ++ goto err_free_2y; ++ } + -+ case ETHTOOL_GLINK: -+ edata.data = (phy_read(phydev, -+ MII_BMSR) & BMSR_LSTATUS) ? 1 : 0; -+ if (copy_to_user(useraddr, &edata, sizeof(edata))) -+ return -EFAULT; -+ return 0; ++ err = gpio_direction_input(pdata->gpio_pin_2y); ++ if (err) { ++ dev_err(&pdev->dev, ++ "unable to set direction of gpio %u, err=%d\n", ++ pdata->gpio_pin_2y, err); ++ goto err_free_2y; + } + -+ return -EOPNOTSUPP; -+} -+EXPORT_SYMBOL(phy_ethtool_ioctl); ++ nxp->parent = &pdev->dev; ++ mutex_init(&nxp->lock); + - /** - * phy_mii_ioctl - generic PHY MII ioctl interface - * @phydev: the phy_device struct -@@ -472,7 +516,7 @@ - int idx; - - idx = phy_find_setting(phydev->speed, phydev->duplex); -- ++ gc = &nxp->gpio_chip; + - idx++; - - idx = phy_find_valid(idx, phydev->supported); -diff -Nur linux-2.6.39.orig/drivers/net/phy/phy_device.c linux-2.6.39/drivers/net/phy/phy_device.c ---- linux-2.6.39.orig/drivers/net/phy/phy_device.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/net/phy/phy_device.c 2011-05-27 14:36:51.000000000 +0200 -@@ -149,6 +149,19 @@ - } - EXPORT_SYMBOL(phy_scan_fixups); - -+static int generic_receive_skb(struct sk_buff *skb) -+{ -+ skb->protocol = eth_type_trans(skb, skb->dev); -+ return netif_receive_skb(skb); ++ gc->direction_input = nxp_74hc153_direction_input; ++ gc->direction_output = nxp_74hc153_direction_output; ++ gc->get = nxp_74hc153_get_value; ++ gc->set = nxp_74hc153_set_value; ++ gc->can_sleep = 1; ++ ++ gc->base = pdata->gpio_base; ++ gc->ngpio = NXP_74HC153_NUM_GPIOS; ++ gc->label = dev_name(nxp->parent); ++ gc->dev = nxp->parent; ++ gc->owner = THIS_MODULE; ++ ++ err = gpiochip_add(&nxp->gpio_chip); ++ if (err) { ++ dev_err(&pdev->dev, "unable to add gpio chip, err=%d\n", err); ++ goto err_free_2y; ++ } ++ ++ platform_set_drvdata(pdev, nxp); ++ return 0; ++ ++err_free_2y: ++ gpio_free(pdata->gpio_pin_2y); ++err_free_1y: ++ gpio_free(pdata->gpio_pin_1y); ++err_free_s1: ++ gpio_free(pdata->gpio_pin_s1); ++err_free_s0: ++ gpio_free(pdata->gpio_pin_s0); ++err_free_nxp: ++ kfree(nxp); ++ return err; +} + -+static int generic_rx(struct sk_buff *skb) ++static int nxp_74hc153_remove(struct platform_device *pdev) +{ -+ skb->protocol = eth_type_trans(skb, skb->dev); -+ return netif_rx(skb); ++ struct nxp_74hc153_chip *nxp = platform_get_drvdata(pdev); ++ struct nxp_74hc153_platform_data *pdata = pdev->dev.platform_data; ++ ++ if (nxp) { ++ int err; ++ ++ err = gpiochip_remove(&nxp->gpio_chip); ++ if (err) { ++ dev_err(&pdev->dev, ++ "unable to remove gpio chip, err=%d\n", ++ err); ++ return err; ++ } ++ ++ gpio_free(pdata->gpio_pin_2y); ++ gpio_free(pdata->gpio_pin_1y); ++ gpio_free(pdata->gpio_pin_s1); ++ gpio_free(pdata->gpio_pin_s0); ++ ++ kfree(nxp); ++ platform_set_drvdata(pdev, NULL); ++ } ++ ++ return 0; +} + ++static struct platform_driver nxp_74hc153_driver = { ++ .probe = nxp_74hc153_probe, ++ .remove = __devexit_p(nxp_74hc153_remove), ++ .driver = { ++ .name = NXP_74HC153_DRIVER_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init nxp_74hc153_init(void) ++{ ++ return platform_driver_register(&nxp_74hc153_driver); ++} ++subsys_initcall(nxp_74hc153_init); + - static struct phy_device* phy_device_create(struct mii_bus *bus, - int addr, int phy_id) - { -@@ -180,6 +193,8 @@ - dev_set_name(&dev->dev, PHY_ID_FMT, bus->id, addr); - - dev->state = PHY_DOWN; -+ dev->netif_receive_skb = &generic_receive_skb; -+ dev->netif_rx = &generic_rx; - - mutex_init(&dev->lock); - INIT_DELAYED_WORK(&dev->state_queue, phy_state_machine); -diff -Nur linux-2.6.39.orig/drivers/spi/Kconfig linux-2.6.39/drivers/spi/Kconfig ---- linux-2.6.39.orig/drivers/spi/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/spi/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -67,6 +67,13 @@ - This enables support for the SPI controller present on the - Atheros AR71XX/AR724X/AR913X SoCs. - -+config SPI_AR71XX -+ tristate "Atheros AR71xx SPI Controller" -+ depends on SPI_MASTER && ATHEROS_AR71XX -+ select SPI_BITBANG -+ help -+ This is the SPI contoller driver for Atheros AR71xx. ++static void __exit nxp_74hc153_exit(void) ++{ ++ platform_driver_unregister(&nxp_74hc153_driver); ++} ++module_exit(nxp_74hc153_exit); + - config SPI_ATMEL - tristate "Atmel SPI Controller" - depends on (ARCH_AT91 || AVR32) -diff -Nur linux-2.6.39.orig/drivers/spi/Makefile linux-2.6.39/drivers/spi/Makefile ---- linux-2.6.39.orig/drivers/spi/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/spi/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -11,6 +11,7 @@ - # SPI master controller drivers (bus) - obj-$(CONFIG_SPI_ALTERA) += spi_altera.o - obj-$(CONFIG_SPI_ATMEL) += atmel_spi.o -+obj-$(CONFIG_SPI_AR71XX) += ar71xx_spi.o - obj-$(CONFIG_SPI_ATH79) += ath79_spi.o - obj-$(CONFIG_SPI_BFIN) += spi_bfin5xx.o - obj-$(CONFIG_SPI_BITBANG) += spi_bitbang.o -diff -Nur linux-2.6.39.orig/drivers/spi/ap83_spi.c linux-2.6.39/drivers/spi/ap83_spi.c ---- linux-2.6.39.orig/drivers/spi/ap83_spi.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/spi/ap83_spi.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,282 @@ ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_DESCRIPTION("GPIO expander driver for NXP 74HC153"); ++MODULE_LICENSE("GPL v2"); ++MODULE_ALIAS("platform:" NXP_74HC153_DRIVER_NAME); +diff -Nur linux-2.6.39.orig/drivers/leds/leds-rb750.c linux-2.6.39/drivers/leds/leds-rb750.c +--- linux-2.6.39.orig/drivers/leds/leds-rb750.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/leds/leds-rb750.c 2011-04-27 12:19:22.267661616 +0200 +@@ -0,0 +1,141 @@ +/* -+ * Atheros AP83 board specific SPI Controller driver ++ * LED driver for the RouterBOARD 750 + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2010 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + */ -+ +#include +#include -+#include -+#include -+#include +#include -+#include -+#include -+#include -+#include -+#include -+ -+#include -+#include -+ -+#define DRV_DESC "Atheros AP83 board SPI Controller driver" -+#define DRV_VERSION "0.1.0" -+#define DRV_NAME "ap83-spi" ++#include ++#include + -+#define AP83_SPI_CLK_HIGH (1 << 23) -+#define AP83_SPI_CLK_LOW 0 -+#define AP83_SPI_MOSI_HIGH (1 << 22) -+#define AP83_SPI_MOSI_LOW 0 ++#include + -+#define AP83_SPI_GPIO_CS 1 -+#define AP83_SPI_GPIO_MISO 3 ++#define DRV_NAME "leds-rb750" + -+struct ap83_spi { -+ struct spi_bitbang bitbang; -+ void __iomem *base; -+ u32 addr; ++struct rb750_led_dev { ++ struct led_classdev cdev; ++ u32 mask; ++ int active_low; ++}; + -+ struct platform_device *pdev; ++struct rb750_led_drvdata { ++ struct rb750_led_dev *led_devs; ++ int num_leds; +}; + -+static inline u32 ap83_spi_rr(struct ap83_spi *sp, u32 reg) ++static inline struct rb750_led_dev *to_rbled(struct led_classdev *led_cdev) +{ -+ return __raw_readl(sp->base + reg); ++ return (struct rb750_led_dev *)container_of(led_cdev, ++ struct rb750_led_dev, cdev); +} + -+static inline struct ap83_spi *spidev_to_sp(struct spi_device *spi) ++static void rb750_led_brightness_set(struct led_classdev *led_cdev, ++ enum led_brightness value) +{ -+ return spi_master_get_devdata(spi->master); ++ struct rb750_led_dev *rbled = to_rbled(led_cdev); ++ int level; ++ ++ level = (value == LED_OFF) ? 0 : 1; ++ level ^= rbled->active_low; ++ ++ if (level) ++ rb750_latch_change(0, rbled->mask); ++ else ++ rb750_latch_change(rbled->mask, 0); +} + -+static inline void setsck(struct spi_device *spi, int val) ++static int __devinit rb750_led_probe(struct platform_device *pdev) +{ -+ struct ap83_spi *sp = spidev_to_sp(spi); ++ struct rb750_led_platform_data *pdata; ++ struct rb750_led_drvdata *drvdata; ++ int ret = 0; ++ int i; + -+ if (val) -+ sp->addr |= AP83_SPI_CLK_HIGH; -+ else -+ sp->addr &= ~AP83_SPI_CLK_HIGH; ++ pdata = pdev->dev.platform_data; ++ if (!pdata) ++ return -EINVAL; + -+ dev_dbg(&spi->dev, "addr=%08x, SCK set to %s\n", -+ sp->addr, (val) ? "HIGH" : "LOW"); ++ drvdata = kzalloc(sizeof(struct rb750_led_drvdata) + ++ sizeof(struct rb750_led_dev) * pdata->num_leds, ++ GFP_KERNEL); ++ if (!drvdata) ++ return -ENOMEM; + -+ ap83_spi_rr(sp, sp->addr); -+} ++ drvdata->num_leds = pdata->num_leds; ++ drvdata->led_devs = (struct rb750_led_dev *) &drvdata[1]; + -+static inline void setmosi(struct spi_device *spi, int val) -+{ -+ struct ap83_spi *sp = spidev_to_sp(spi); ++ for (i = 0; i < drvdata->num_leds; i++) { ++ struct rb750_led_dev *rbled = &drvdata->led_devs[i]; ++ struct rb750_led_data *led_data = &pdata->leds[i]; + -+ if (val) -+ sp->addr |= AP83_SPI_MOSI_HIGH; -+ else -+ sp->addr &= ~AP83_SPI_MOSI_HIGH; ++ rbled->cdev.name = led_data->name; ++ rbled->cdev.default_trigger = led_data->default_trigger; ++ rbled->cdev.brightness_set = rb750_led_brightness_set; ++ rbled->cdev.brightness = LED_OFF; + -+ dev_dbg(&spi->dev, "addr=%08x, MOSI set to %s\n", -+ sp->addr, (val) ? "HIGH" : "LOW"); ++ rbled->mask = led_data->mask; ++ rbled->active_low = !!led_data->active_low; + -+ ap83_spi_rr(sp, sp->addr); -+} ++ ret = led_classdev_register(&pdev->dev, &rbled->cdev); ++ if (ret) ++ goto err; ++ } + -+static inline u32 getmiso(struct spi_device *spi) -+{ -+ u32 ret; ++ platform_set_drvdata(pdev, drvdata); ++ return 0; + -+ ret = gpio_get_value(AP83_SPI_GPIO_MISO) ? 1 : 0; -+ dev_dbg(&spi->dev, "get MISO: %d\n", ret); ++err: ++ for (i = i - 1; i >= 0; i--) ++ led_classdev_unregister(&drvdata->led_devs[i].cdev); + ++ kfree(drvdata); + return ret; +} + -+static inline void do_spidelay(struct spi_device *spi, unsigned nsecs) -+{ -+ ndelay(nsecs); -+} -+ -+static void ap83_spi_chipselect(struct spi_device *spi, int on) ++static int __devexit rb750_led_remove(struct platform_device *pdev) +{ -+ struct ap83_spi *sp = spidev_to_sp(spi); ++ struct rb750_led_drvdata *drvdata; ++ int i; + -+ dev_dbg(&spi->dev, "set CS to %d\n", (on) ? 0 : 1); ++ drvdata = platform_get_drvdata(pdev); ++ for (i = 0; i < drvdata->num_leds; i++) ++ led_classdev_unregister(&drvdata->led_devs[i].cdev); + -+ if (on) { -+ ar71xx_flash_acquire(); ++ kfree(drvdata); ++ return 0; ++} + -+ sp->addr = 0; -+ ap83_spi_rr(sp, sp->addr); -+ -+ gpio_set_value(AP83_SPI_GPIO_CS, 0); -+ } else { -+ gpio_set_value(AP83_SPI_GPIO_CS, 1); -+ ar71xx_flash_release(); -+ } -+} -+ -+#define spidelay(nsecs) \ -+ do { \ -+ /* Steal the spi_device pointer from our caller. \ -+ * The bitbang-API should probably get fixed here... */ \ -+ do_spidelay(spi, nsecs); \ -+ } while (0) -+ -+#define EXPAND_BITBANG_TXRX -+#include -+ -+static u32 ap83_spi_txrx_mode0(struct spi_device *spi, -+ unsigned nsecs, u32 word, u8 bits) -+{ -+ dev_dbg(&spi->dev, "TXRX0 word=%08x, bits=%u\n", word, bits); -+ return bitbang_txrx_be_cpha0(spi, nsecs, 0, word, bits); -+} ++static struct platform_driver rb750_led_driver = { ++ .probe = rb750_led_probe, ++ .remove = __devexit_p(rb750_led_remove), ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; + -+static u32 ap83_spi_txrx_mode1(struct spi_device *spi, -+ unsigned nsecs, u32 word, u8 bits) -+{ -+ dev_dbg(&spi->dev, "TXRX1 word=%08x, bits=%u\n", word, bits); -+ return bitbang_txrx_be_cpha1(spi, nsecs, 0, word, bits); -+} ++MODULE_ALIAS("platform:leds-rb750"); + -+static u32 ap83_spi_txrx_mode2(struct spi_device *spi, -+ unsigned nsecs, u32 word, u8 bits) ++static int __init rb750_led_init(void) +{ -+ dev_dbg(&spi->dev, "TXRX2 word=%08x, bits=%u\n", word, bits); -+ return bitbang_txrx_be_cpha0(spi, nsecs, 1, word, bits); ++ return platform_driver_register(&rb750_led_driver); +} + -+static u32 ap83_spi_txrx_mode3(struct spi_device *spi, -+ unsigned nsecs, u32 word, u8 bits) ++static void __exit rb750_led_exit(void) +{ -+ dev_dbg(&spi->dev, "TXRX3 word=%08x, bits=%u\n", word, bits); -+ return bitbang_txrx_be_cpha1(spi, nsecs, 1, word, bits); ++ platform_driver_unregister(&rb750_led_driver); +} + -+static int ap83_spi_probe(struct platform_device *pdev) -+{ -+ struct spi_master *master; -+ struct ap83_spi *sp; -+ struct ap83_spi_platform_data *pdata; -+ struct resource *r; -+ int ret; -+ -+ ret = gpio_request(AP83_SPI_GPIO_MISO, "spi-miso"); -+ if (ret) { -+ dev_err(&pdev->dev, "gpio request failed for MISO\n"); -+ return ret; -+ } -+ -+ ret = gpio_request(AP83_SPI_GPIO_CS, "spi-cs"); -+ if (ret) { -+ dev_err(&pdev->dev, "gpio request failed for CS\n"); -+ goto err_free_miso; -+ } -+ -+ ret = gpio_direction_input(AP83_SPI_GPIO_MISO); -+ if (ret) { -+ dev_err(&pdev->dev, "unable to set direction of MISO\n"); -+ goto err_free_cs; -+ } -+ -+ ret = gpio_direction_output(AP83_SPI_GPIO_CS, 0); -+ if (ret) { -+ dev_err(&pdev->dev, "unable to set direction of CS\n"); -+ goto err_free_cs; -+ } -+ -+ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); -+ if (master == NULL) { -+ dev_err(&pdev->dev, "failed to allocate spi master\n"); -+ return -ENOMEM; -+ } -+ -+ sp = spi_master_get_devdata(master); -+ platform_set_drvdata(pdev, sp); -+ -+ pdata = pdev->dev.platform_data; -+ -+ sp->bitbang.master = spi_master_get(master); -+ sp->bitbang.chipselect = ap83_spi_chipselect; -+ sp->bitbang.txrx_word[SPI_MODE_0] = ap83_spi_txrx_mode0; -+ sp->bitbang.txrx_word[SPI_MODE_1] = ap83_spi_txrx_mode1; -+ sp->bitbang.txrx_word[SPI_MODE_2] = ap83_spi_txrx_mode2; -+ sp->bitbang.txrx_word[SPI_MODE_3] = ap83_spi_txrx_mode3; ++module_init(rb750_led_init); ++module_exit(rb750_led_exit); + -+ sp->bitbang.master->bus_num = pdev->id; -+ sp->bitbang.master->num_chipselect = 1; ++MODULE_DESCRIPTION(DRV_NAME); ++MODULE_DESCRIPTION("LED driver for the RouterBOARD 750"); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/leds/leds-wndr3700-usb.c linux-2.6.39/drivers/leds/leds-wndr3700-usb.c +--- linux-2.6.39.orig/drivers/leds/leds-wndr3700-usb.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/leds/leds-wndr3700-usb.c 2011-04-27 12:19:22.267661616 +0200 +@@ -0,0 +1,75 @@ ++/* ++ * USB LED driver for the NETGEAR WNDR3700 ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (r == NULL) { -+ ret = -ENOENT; -+ goto err_spi_put; -+ } ++#include ++#include ++#include + -+ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); -+ if (!sp->base) { -+ ret = -ENXIO; -+ goto err_spi_put; -+ } ++#include + -+ ret = spi_bitbang_start(&sp->bitbang); -+ if (!ret) -+ goto err_unmap; ++#define DRIVER_NAME "wndr3700-led-usb" + -+ dev_info(&pdev->dev, "AP83 SPI adapter at %08x\n", r->start); ++static void wndr3700_usb_led_set(struct led_classdev *cdev, ++ enum led_brightness brightness) ++{ ++ if (brightness) ++ ar71xx_device_start(RESET_MODULE_GE1_PHY); ++ else ++ ar71xx_device_stop(RESET_MODULE_GE1_PHY); ++} + -+ return 0; ++static enum led_brightness wndr3700_usb_led_get(struct led_classdev *cdev) ++{ ++ return ar71xx_device_stopped(RESET_MODULE_GE1_PHY) ? LED_OFF : LED_FULL; ++} + -+ err_unmap: -+ iounmap(sp->base); -+ err_spi_put: -+ platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); ++static struct led_classdev wndr3700_usb_led = { ++ .name = "wndr3700:green:usb", ++ .brightness_set = wndr3700_usb_led_set, ++ .brightness_get = wndr3700_usb_led_get, ++}; + -+ err_free_cs: -+ gpio_free(AP83_SPI_GPIO_CS); -+ err_free_miso: -+ gpio_free(AP83_SPI_GPIO_MISO); -+ return ret; ++static int __devinit wndr3700_usb_led_probe(struct platform_device *pdev) ++{ ++ return led_classdev_register(&pdev->dev, &wndr3700_usb_led); +} + -+static int ap83_spi_remove(struct platform_device *pdev) ++static int __devexit wndr3700_usb_led_remove(struct platform_device *pdev) +{ -+ struct ap83_spi *sp = platform_get_drvdata(pdev); -+ -+ spi_bitbang_stop(&sp->bitbang); -+ iounmap(sp->base); -+ platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); -+ ++ led_classdev_unregister(&wndr3700_usb_led); + return 0; +} + -+static struct platform_driver ap83_spi_drv = { -+ .probe = ap83_spi_probe, -+ .remove = ap83_spi_remove, -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, ++static struct platform_driver wndr3700_usb_led_driver = { ++ .probe = wndr3700_usb_led_probe, ++ .remove = __devexit_p(wndr3700_usb_led_remove), ++ .driver = { ++ .name = DRIVER_NAME, ++ .owner = THIS_MODULE, + }, +}; + -+static int __init ap83_spi_init(void) ++static int __init wndr3700_usb_led_init(void) +{ -+ return platform_driver_register(&ap83_spi_drv); ++ return platform_driver_register(&wndr3700_usb_led_driver); +} -+module_init(ap83_spi_init); + -+static void __exit ap83_spi_exit(void) ++static void __exit wndr3700_usb_led_exit(void) +{ -+ platform_driver_unregister(&ap83_spi_drv); ++ platform_driver_unregister(&wndr3700_usb_led_driver); +} -+module_exit(ap83_spi_exit); + -+MODULE_ALIAS("platform:" DRV_NAME); -+MODULE_DESCRIPTION(DRV_DESC); -+MODULE_VERSION(DRV_VERSION); ++module_init(wndr3700_usb_led_init); ++module_exit(wndr3700_usb_led_exit); ++ ++MODULE_DESCRIPTION("USB LED driver for the NETGEAR WNDR3700"); +MODULE_AUTHOR("Gabor Juhos "); +MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/spi/ar71xx_spi.c linux-2.6.39/drivers/spi/ar71xx_spi.c ---- linux-2.6.39.orig/drivers/spi/ar71xx_spi.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/spi/ar71xx_spi.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,283 @@ ++MODULE_ALIAS("platform:" DRIVER_NAME); +diff -Nur linux-2.6.39.orig/drivers/Makefile linux-2.6.39/drivers/Makefile +--- linux-2.6.39.orig/drivers/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/Makefile 2011-08-23 15:10:42.370478643 +0200 +@@ -46,8 +46,8 @@ + obj-$(CONFIG_SCSI) += scsi/ + obj-$(CONFIG_ATA) += ata/ + obj-$(CONFIG_TARGET_CORE) += target/ +-obj-$(CONFIG_MTD) += mtd/ + obj-$(CONFIG_SPI) += spi/ ++obj-$(CONFIG_MTD) += mtd/ + obj-y += net/ + obj-$(CONFIG_ATM) += atm/ + obj-$(CONFIG_FUSION) += message/ +diff -Nur linux-2.6.39.orig/drivers/mtd/chips/cfi_cmdset_0002.c linux-2.6.39/drivers/mtd/chips/cfi_cmdset_0002.c +--- linux-2.6.39.orig/drivers/mtd/chips/cfi_cmdset_0002.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/mtd/chips/cfi_cmdset_0002.c 2011-08-22 16:22:28.477979654 +0200 +@@ -39,7 +39,7 @@ + #include + + #define AMD_BOOTLOC_BUG +-#define FORCE_WORD_WRITE 0 ++#define FORCE_WORD_WRITE 1 + + #define MAX_WORD_RETRIES 3 + +@@ -50,7 +50,9 @@ + + static int cfi_amdstd_read (struct mtd_info *, loff_t, size_t, size_t *, u_char *); + static int cfi_amdstd_write_words(struct mtd_info *, loff_t, size_t, size_t *, const u_char *); ++#if !FORCE_WORD_WRITE + static int cfi_amdstd_write_buffers(struct mtd_info *, loff_t, size_t, size_t *, const u_char *); ++#endif + static int cfi_amdstd_erase_chip(struct mtd_info *, struct erase_info *); + static int cfi_amdstd_erase_varsize(struct mtd_info *, struct erase_info *); + static void cfi_amdstd_sync (struct mtd_info *); +@@ -186,6 +188,7 @@ + } + #endif + ++#if !FORCE_WORD_WRITE + static void fixup_use_write_buffers(struct mtd_info *mtd) + { + struct map_info *map = mtd->priv; +@@ -195,6 +198,7 @@ + mtd->write = cfi_amdstd_write_buffers; + } + } ++#endif /* !FORCE_WORD_WRITE */ + + /* Atmel chips don't use the same PRI format as AMD chips */ + static void fixup_convert_atmel_pri(struct mtd_info *mtd) +@@ -1377,6 +1381,7 @@ + /* + * FIXME: interleaved mode not tested, and probably not supported! + */ ++#if !FORCE_WORD_WRITE + static int __xipram do_write_buffer(struct map_info *map, struct flchip *chip, + unsigned long adr, const u_char *buf, + int len) +@@ -1487,7 +1492,6 @@ + return ret; + } + +- + static int cfi_amdstd_write_buffers(struct mtd_info *mtd, loff_t to, size_t len, + size_t *retlen, const u_char *buf) + { +@@ -1566,6 +1570,7 @@ + + return 0; + } ++#endif /* !FORCE_WORD_WRITE */ + + + /* +diff -Nur linux-2.6.39.orig/drivers/mtd/maps/ar91xx_flash.c linux-2.6.39/drivers/mtd/maps/ar91xx_flash.c +--- linux-2.6.39.orig/drivers/mtd/maps/ar91xx_flash.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/mtd/maps/ar91xx_flash.c 2011-04-27 12:19:22.177661504 +0200 +@@ -0,0 +1,310 @@ +/* -+ * Atheros AR71xx SPI Controller driver ++ * Parallel flash driver for the Atheros AR91xx SoC + * -+ * Copyright (C) 2008-2009 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * Copyright (C) 2009 Gabor Juhos + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as @@ -15099,2909 +16534,11447 @@ diff -Nur linux-2.6.39.orig/drivers/spi/ar71xx_spi.c linux-2.6.39/drivers/spi/ar + * + */ + ++#include ++#include +#include +#include -+#include -+#include -+#include ++#include ++#include +#include ++#include ++#include ++#include +#include -+#include -+#include -+#include + +#include -+#include -+ -+#define DRV_DESC "Atheros AR71xx SPI Controller driver" -+#define DRV_VERSION "0.2.4" -+#define DRV_NAME "ar71xx-spi" ++#include + -+#undef PER_BIT_READ ++#define DRV_NAME "ar91xx-flash" + -+struct ar71xx_spi { -+ struct spi_bitbang bitbang; -+ u32 ioc_base; -+ u32 reg_ctrl; -+ -+ void __iomem *base; -+ -+ struct platform_device *pdev; -+ u32 (*get_ioc_base)(u8 chip_select, int cs_high, -+ int is_on); ++struct ar91xx_flash_info { ++ struct mtd_info *mtd; ++ struct map_info map; ++#ifdef CONFIG_MTD_PARTITIONS ++ int nr_parts; ++ struct mtd_partition *parts; ++#endif +}; + -+static inline u32 ar71xx_spi_rr(struct ar71xx_spi *sp, unsigned reg) ++static map_word ar91xx_flash_read(struct map_info *map, unsigned long ofs) +{ -+ return __raw_readl(sp->base + reg); -+} ++ map_word val; + -+static inline void ar71xx_spi_wr(struct ar71xx_spi *sp, unsigned reg, u32 val) -+{ -+ __raw_writel(val, sp->base + reg); ++ if (map_bankwidth_is_1(map)) ++ val.x[0] = __raw_readb(map->virt + (ofs ^ 3)); ++ else if (map_bankwidth_is_2(map)) ++ val.x[0] = __raw_readw(map->virt + (ofs ^ 2)); ++ else ++ val = map_word_ff(map); ++ ++ return val; +} + -+static inline struct ar71xx_spi *spidev_to_sp(struct spi_device *spi) ++static void ar91xx_flash_write(struct map_info *map, map_word d, ++ unsigned long ofs) +{ -+ return spi_master_get_devdata(spi->master); ++ if (map_bankwidth_is_1(map)) ++ __raw_writeb(d.x[0], map->virt + (ofs ^ 3)); ++ else if (map_bankwidth_is_2(map)) ++ __raw_writew(d.x[0], map->virt + (ofs ^ 2)); ++ ++ mb(); +} + -+static u32 ar71xx_spi_get_ioc_base(u8 chip_select, int cs_high, int is_on) ++static map_word ar91xx_flash_read_lock(struct map_info *map, unsigned long ofs) +{ -+ u32 ret; ++ map_word ret; + -+ if (is_on == AR71XX_SPI_CS_INACTIVE) -+ ret = SPI_IOC_CS_ALL; -+ else -+ ret = SPI_IOC_CS_ALL & ~SPI_IOC_CS(chip_select); ++ ar71xx_flash_acquire(); ++ ret = ar91xx_flash_read(map, ofs); ++ ar71xx_flash_release(); + + return ret; +} + -+static void ar71xx_spi_chipselect(struct spi_device *spi, int value) ++static void ar91xx_flash_write_lock(struct map_info *map, map_word d, ++ unsigned long ofs) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ void __iomem *base = sp->base; -+ u32 ioc_base; -+ -+ switch (value) { -+ case BITBANG_CS_INACTIVE: -+ ioc_base = sp->get_ioc_base(spi->chip_select, -+ (spi->mode & SPI_CS_HIGH) != 0, -+ AR71XX_SPI_CS_INACTIVE); -+ __raw_writel(ioc_base, base + SPI_REG_IOC); -+ break; -+ -+ case BITBANG_CS_ACTIVE: -+ ioc_base = sp->get_ioc_base(spi->chip_select, -+ (spi->mode & SPI_CS_HIGH) != 0, -+ AR71XX_SPI_CS_ACTIVE); -+ -+ __raw_writel(ioc_base, base + SPI_REG_IOC); -+ sp->ioc_base = ioc_base; -+ break; -+ } ++ ar71xx_flash_acquire(); ++ ar91xx_flash_write(map, d, ofs); ++ ar71xx_flash_release(); +} + -+static void ar71xx_spi_setup_regs(struct spi_device *spi) ++static void ar91xx_flash_copy_from_lock(struct map_info *map, void *to, ++ unsigned long from, ssize_t len) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ -+ /* enable GPIO mode */ -+ ar71xx_spi_wr(sp, SPI_REG_FS, SPI_FS_GPIO); -+ -+ /* save CTRL register */ -+ sp->reg_ctrl = ar71xx_spi_rr(sp, SPI_REG_CTRL); -+ -+ /* TODO: setup speed? */ -+ ar71xx_spi_wr(sp, SPI_REG_CTRL, 0x43); ++ ar71xx_flash_acquire(); ++ inline_map_copy_from(map, to, from, len); ++ ar71xx_flash_release(); +} + -+static void ar71xx_spi_restore_regs(struct spi_device *spi) ++static void ar91xx_flash_copy_to_lock(struct map_info *map, unsigned long to, ++ const void *from, ssize_t len) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ -+ /* restore CTRL register */ -+ ar71xx_spi_wr(sp, SPI_REG_CTRL, sp->reg_ctrl); -+ /* disable GPIO mode */ -+ ar71xx_spi_wr(sp, SPI_REG_FS, 0); ++ ar71xx_flash_acquire(); ++ inline_map_copy_to(map, to, from, len); ++ ar71xx_flash_release(); +} + -+static int ar71xx_spi_setup(struct spi_device *spi) ++static int ar91xx_flash_remove(struct platform_device *pdev) +{ -+ int status; ++ struct ar91xx_flash_platform_data *pdata; ++ struct ar91xx_flash_info *info; + -+ if (spi->bits_per_word > 32) -+ return -EINVAL; ++ info = platform_get_drvdata(pdev); ++ if (info == NULL) ++ return 0; + -+ if (!spi->controller_state) -+ ar71xx_spi_setup_regs(spi); ++ platform_set_drvdata(pdev, NULL); + -+ status = spi_bitbang_setup(spi); -+ if (status && !spi->controller_state) -+ ar71xx_spi_restore_regs(spi); ++ if (info->mtd == NULL) ++ return 0; + -+ return status; -+} ++ pdata = pdev->dev.platform_data; ++#ifdef CONFIG_MTD_PARTITIONS ++ if (info->nr_parts) { ++ del_mtd_partitions(info->mtd); ++ kfree(info->parts); ++ } else if (pdata->nr_parts) { ++ del_mtd_partitions(info->mtd); ++ } else { ++ del_mtd_device(info->mtd); ++ } ++#else ++ del_mtd_device(info->mtd); ++#endif ++ map_destroy(info->mtd); + -+static void ar71xx_spi_cleanup(struct spi_device *spi) -+{ -+ ar71xx_spi_restore_regs(spi); -+ spi_bitbang_cleanup(spi); ++ return 0; +} + -+static u32 ar71xx_spi_txrx_mode0(struct spi_device *spi, unsigned nsecs, -+ u32 word, u8 bits) -+{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ void __iomem *base = sp->base; -+ u32 ioc = sp->ioc_base; -+ u32 ret; ++static const char *rom_probe_types[] = { "cfi_probe", "jedec_probe", NULL }; ++#ifdef CONFIG_MTD_PARTITIONS ++static const char *part_probe_types[] = { "cmdlinepart", "RedBoot", NULL }; ++#endif + -+ /* clock starts at inactive polarity */ -+ for (word <<= (32 - bits); likely(bits); bits--) { -+ u32 out; ++static int ar91xx_flash_probe(struct platform_device *pdev) ++{ ++ struct ar91xx_flash_platform_data *pdata; ++ struct ar91xx_flash_info *info; ++ struct resource *res; ++ struct resource *region; ++ const char **probe_type; ++ int err = 0; + -+ if (word & (1 << 31)) -+ out = ioc | SPI_IOC_DO; -+ else -+ out = ioc & ~SPI_IOC_DO; ++ pdata = pdev->dev.platform_data; ++ if (pdata == NULL) ++ return -EINVAL; + -+ /* setup MSB (to slave) on trailing edge */ -+ __raw_writel(out, base + SPI_REG_IOC); ++ info = devm_kzalloc(&pdev->dev, sizeof(struct ar91xx_flash_info), ++ GFP_KERNEL); ++ if (info == NULL) { ++ err = -ENOMEM; ++ goto err_out; ++ } + -+ __raw_writel(out | SPI_IOC_CLK, base + SPI_REG_IOC); ++ platform_set_drvdata(pdev, info); + -+ word <<= 1; ++ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (res == NULL) { ++ err = -ENOENT; ++ goto err_out; ++ } + -+#ifdef PER_BIT_READ -+ /* sample MSB (from slave) on leading edge */ -+ ret = __raw_readl(base + SPI_REG_RDS); -+ __raw_writel(out, base + SPI_REG_IOC); -+#endif ++ dev_info(&pdev->dev, "%.8llx at %.8llx\n", ++ (unsigned long long)(res->end - res->start + 1), ++ (unsigned long long)res->start); + ++ region = devm_request_mem_region(&pdev->dev, ++ res->start, res->end - res->start + 1, ++ dev_name(&pdev->dev)); ++ if (region == NULL) { ++ dev_err(&pdev->dev, "could not reserve memory region\n"); ++ err = -ENOMEM; ++ goto err_out; + } + -+#ifndef PER_BIT_READ -+ ret = __raw_readl(base + SPI_REG_RDS); -+#endif -+ return ret; -+} ++ info->map.name = dev_name(&pdev->dev); ++ info->map.phys = res->start; ++ info->map.size = res->end - res->start + 1; ++ info->map.bankwidth = pdata->width; + -+static int ar71xx_spi_probe(struct platform_device *pdev) -+{ -+ struct spi_master *master; -+ struct ar71xx_spi *sp; -+ struct ar71xx_spi_platform_data *pdata; -+ struct resource *r; -+ int ret; ++ info->map.virt = devm_ioremap(&pdev->dev, info->map.phys, ++ info->map.size); ++ if (info->map.virt == NULL) { ++ dev_err(&pdev->dev, "failed to ioremap flash region\n"); ++ err = -EIO; ++ goto err_out; ++ } + -+ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); -+ if (master == NULL) { -+ dev_err(&pdev->dev, "failed to allocate spi master\n"); -+ return -ENOMEM; ++ simple_map_init(&info->map); ++ if (pdata->is_shared) { ++ info->map.read = ar91xx_flash_read_lock; ++ info->map.write = ar91xx_flash_write_lock; ++ info->map.copy_from = ar91xx_flash_copy_from_lock; ++ info->map.copy_to = ar91xx_flash_copy_to_lock; ++ } else { ++ info->map.read = ar91xx_flash_read; ++ info->map.write = ar91xx_flash_write; + } + -+ sp = spi_master_get_devdata(master); -+ platform_set_drvdata(pdev, sp); ++ probe_type = rom_probe_types; ++ for (; info->mtd == NULL && *probe_type != NULL; probe_type++) ++ info->mtd = do_map_probe(*probe_type, &info->map); + -+ pdata = pdev->dev.platform_data; ++ if (info->mtd == NULL) { ++ dev_err(&pdev->dev, "map_probe failed\n"); ++ err = -ENXIO; ++ goto err_out; ++ } + -+ master->setup = ar71xx_spi_setup; -+ master->cleanup = ar71xx_spi_cleanup; ++ info->mtd->owner = THIS_MODULE; + -+ sp->bitbang.master = spi_master_get(master); -+ sp->bitbang.chipselect = ar71xx_spi_chipselect; -+ sp->bitbang.txrx_word[SPI_MODE_0] = ar71xx_spi_txrx_mode0; -+ sp->bitbang.setup_transfer = spi_bitbang_setup_transfer; -+ -+ sp->get_ioc_base = ar71xx_spi_get_ioc_base; -+ if (pdata) { -+ sp->bitbang.master->bus_num = pdata->bus_num; -+ sp->bitbang.master->num_chipselect = pdata->num_chipselect; -+ if (pdata->get_ioc_base) -+ sp->get_ioc_base = pdata->get_ioc_base; -+ } else { -+ sp->bitbang.master->bus_num = 0; -+ sp->bitbang.master->num_chipselect = 3; ++#ifdef CONFIG_MTD_PARTITIONS ++ if (pdata->nr_parts) { ++ dev_info(&pdev->dev, "using static partition mapping\n"); ++ add_mtd_partitions(info->mtd, pdata->parts, pdata->nr_parts); ++ return 0; + } + -+ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (r == NULL) { -+ ret = -ENOENT; -+ goto err1; ++ err = parse_mtd_partitions(info->mtd, part_probe_types, ++ &info->parts, 0); ++ if (err > 0) { ++ add_mtd_partitions(info->mtd, info->parts, err); ++ return 0; + } ++#endif + -+ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); -+ if (!sp->base) { -+ ret = -ENXIO; -+ goto err1; -+ } ++ add_mtd_device(info->mtd); ++ return 0; + -+ ret = spi_bitbang_start(&sp->bitbang); -+ if (!ret) -+ return 0; ++err_out: ++ ar91xx_flash_remove(pdev); ++ return err; ++} + -+ iounmap(sp->base); -+ err1: -+ platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); ++#ifdef CONFIG_PM ++static int ar91xx_flash_suspend(struct platform_device *dev, pm_message_t state) ++{ ++ struct ar91xx_flash_info *info = platform_get_drvdata(dev); ++ int ret = 0; ++ ++ if (info->mtd->suspend) ++ ret = info->mtd->suspend(info->mtd); ++ ++ if (ret) ++ goto fail; ++ ++ return 0; ++ ++fail: ++ if (info->mtd->suspend) { ++ BUG_ON(!info->mtd->resume); ++ info->mtd->resume(info->mtd); ++ } + + return ret; +} + -+static int ar71xx_spi_remove(struct platform_device *pdev) ++static int ar91xx_flash_resume(struct platform_device *pdev) +{ -+ struct ar71xx_spi *sp = platform_get_drvdata(pdev); ++ struct ar91xx_flash_info *info = platform_get_drvdata(pdev); + -+ spi_bitbang_stop(&sp->bitbang); -+ iounmap(sp->base); -+ platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); ++ if (info->mtd->resume) ++ info->mtd->resume(info->mtd); + + return 0; +} + -+static struct platform_driver ar71xx_spi_drv = { -+ .probe = ar71xx_spi_probe, -+ .remove = ar71xx_spi_remove, ++static void ar91xx_flash_shutdown(struct platform_device *pdev) ++{ ++ struct ar91xx_flash_info *info = platform_get_drvdata(pdev); ++ ++ if (info->mtd->suspend && info->mtd->resume) ++ if (info->mtd->suspend(info->mtd) == 0) ++ info->mtd->resume(info->mtd); ++} ++#else ++#define ar91xx_flash_suspend NULL ++#define ar91xx_flash_resume NULL ++#define ar91xx_flash_shutdown NULL ++#endif ++ ++static struct platform_driver ar91xx_flash_driver = { ++ .probe = ar91xx_flash_probe, ++ .remove = ar91xx_flash_remove, ++ .suspend = ar91xx_flash_suspend, ++ .resume = ar91xx_flash_resume, ++ .shutdown = ar91xx_flash_shutdown, + .driver = { + .name = DRV_NAME, + .owner = THIS_MODULE, + }, +}; + -+static int __init ar71xx_spi_init(void) ++static int __init ar91xx_flash_init(void) +{ -+ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); -+ return platform_driver_register(&ar71xx_spi_drv); ++ return platform_driver_register(&ar91xx_flash_driver); +} -+module_init(ar71xx_spi_init); + -+static void __exit ar71xx_spi_exit(void) ++static void __exit ar91xx_flash_exit(void) +{ -+ platform_driver_unregister(&ar71xx_spi_drv); ++ platform_driver_unregister(&ar91xx_flash_driver); +} -+module_exit(ar71xx_spi_exit); + -+MODULE_ALIAS("platform:" DRV_NAME); -+MODULE_DESCRIPTION(DRV_DESC); -+MODULE_VERSION(DRV_VERSION); -+MODULE_AUTHOR("Gabor Juhos "); -+MODULE_AUTHOR("Imre Kaloz "); ++module_init(ar91xx_flash_init); ++module_exit(ar91xx_flash_exit); ++ +MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/spi/pb44_spi.c linux-2.6.39/drivers/spi/pb44_spi.c ---- linux-2.6.39.orig/drivers/spi/pb44_spi.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/spi/pb44_spi.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,299 @@ ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_DESCRIPTION("Parallel flash driver for the Atheros AR91xx SoC"); ++MODULE_ALIAS("platform:" DRV_NAME); +diff -Nur linux-2.6.39.orig/drivers/mtd/maps/Kconfig linux-2.6.39/drivers/mtd/maps/Kconfig +--- linux-2.6.39.orig/drivers/mtd/maps/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/mtd/maps/Kconfig 2011-08-22 16:22:06.367979538 +0200 +@@ -260,6 +260,13 @@ + Support for parsing CFE image tag and creating MTD partitions on + Broadcom BCM63xx boards. + ++config MTD_AR91XX_FLASH ++ tristate "Atheros AR91xx parallel flash support" ++ depends on ATHEROS_AR71XX ++ select MTD_COMPLEX_MAPPINGS ++ help ++ Parallel flash driver for the Atheros AR91xx based boards. ++ + config MTD_DILNETPC + tristate "CFI Flash device mapped on DIL/Net PC" + depends on X86 && MTD_PARTITIONS && MTD_CFI_INTELEXT && BROKEN +diff -Nur linux-2.6.39.orig/drivers/mtd/maps/Makefile linux-2.6.39/drivers/mtd/maps/Makefile +--- linux-2.6.39.orig/drivers/mtd/maps/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/mtd/maps/Makefile 2011-08-22 16:22:06.387979567 +0200 +@@ -40,6 +40,7 @@ + obj-$(CONFIG_MTD_DBOX2) += dbox2-flash.o + obj-$(CONFIG_MTD_SOLUTIONENGINE)+= solutionengine.o + obj-$(CONFIG_MTD_PCI) += pci.o ++obj-$(CONFIG_MTD_AR91XX_FLASH) += ar91xx_flash.o + obj-$(CONFIG_MTD_AUTCPU12) += autcpu12-nvram.o + obj-$(CONFIG_MTD_EDB7312) += edb7312.o + obj-$(CONFIG_MTD_IMPA7) += impa7.o +diff -Nur linux-2.6.39.orig/drivers/mtd/nand/Kconfig linux-2.6.39/drivers/mtd/nand/Kconfig +--- linux-2.6.39.orig/drivers/mtd/nand/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/mtd/nand/Kconfig 2011-08-23 14:22:33.407989933 +0200 +@@ -531,4 +531,9 @@ + Enables support for NAND Flash chips on the ST Microelectronics + Flexible Static Memory Controller (FSMC) + ++config MTD_NAND_RB4XX ++ tristate "NAND flash driver for RouterBoard 4xx series" ++ depends on MTD_NAND && AR71XX_MACH_RB4XX ++ select SPI_AR71XX ++ + endif # MTD_NAND +diff -Nur linux-2.6.39.orig/drivers/mtd/nand/Makefile linux-2.6.39/drivers/mtd/nand/Makefile +--- linux-2.6.39.orig/drivers/mtd/nand/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/mtd/nand/Makefile 2011-08-22 16:22:41.217981942 +0200 +@@ -34,6 +34,7 @@ + obj-$(CONFIG_MTD_NAND_PXA3xx) += pxa3xx_nand.o + obj-$(CONFIG_MTD_NAND_TMIO) += tmio_nand.o + obj-$(CONFIG_MTD_NAND_PLATFORM) += plat_nand.o ++obj-$(CONFIG_MTD_NAND_RB4XX) += rb4xx_nand.o + obj-$(CONFIG_MTD_ALAUDA) += alauda.o + obj-$(CONFIG_MTD_NAND_PASEMI) += pasemi_nand.o + obj-$(CONFIG_MTD_NAND_ORION) += orion_nand.o +diff -Nur linux-2.6.39.orig/drivers/mtd/nand/rb4xx_nand.c linux-2.6.39/drivers/mtd/nand/rb4xx_nand.c +--- linux-2.6.39.orig/drivers/mtd/nand/rb4xx_nand.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/mtd/nand/rb4xx_nand.c 2011-08-23 11:36:58.637983055 +0200 +@@ -0,0 +1,311 @@ +/* -+ * Atheros PB44 board SPI controller driver ++ * NAND flash driver for the MikroTik RouterBoard 4xx series + * -+ * Copyright (C) 2009 Gabor Juhos ++ * Copyright (C) 2008-2011 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. ++ * This file was based on the driver for Linux 2.6.22 published by ++ * MikroTik for their RouterBoard 4xx series devices. + * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + -+#include +#include -+#include -+#include -+#include ++#include ++#include ++#include +#include ++#include +#include -+#include -+#include -+#include +#include ++#include + +#include -+#include ++#include + -+#define DRV_DESC "Atheros PB44 SPI Controller driver" -+#define DRV_VERSION "0.1.0" -+#define DRV_NAME "pb44-spi" ++#define DRV_NAME "rb4xx-nand" ++#define DRV_VERSION "0.2.0" ++#define DRV_DESC "NAND flash driver for RouterBoard 4xx series" + -+#undef PER_BIT_READ ++#define RB4XX_NAND_GPIO_READY 5 ++#define RB4XX_NAND_GPIO_ALE 37 ++#define RB4XX_NAND_GPIO_CLE 38 ++#define RB4XX_NAND_GPIO_NCE 39 + -+struct ar71xx_spi { -+ struct spi_bitbang bitbang; -+ u32 ioc_base; -+ u32 reg_ctrl; ++struct rb4xx_nand_info { ++ struct nand_chip chip; ++ struct mtd_info mtd; ++}; + -+ void __iomem *base; ++/* ++ * We need to use the OLD Yaffs-1 OOB layout, otherwise the RB bootloader ++ * will not be able to find the kernel that we load. ++ */ ++static struct nand_ecclayout rb4xx_nand_ecclayout = { ++ .eccbytes = 6, ++ .eccpos = { 8, 9, 10, 13, 14, 15 }, ++ .oobavail = 9, ++ .oobfree = { { 0, 4 }, { 6, 2 }, { 11, 2 }, { 4, 1 } } ++}; + -+ struct platform_device *pdev; ++static struct mtd_partition rb4xx_nand_partitions[] = { ++ { ++ .name = "booter", ++ .offset = 0, ++ .size = (256 * 1024), ++ .mask_flags = MTD_WRITEABLE, ++ }, ++ { ++ .name = "kernel", ++ .offset = (256 * 1024), ++ .size = (6 * 1024 * 1024) - (256 * 1024), ++ }, ++ { ++ .name = "rootfs", ++ .offset = MTDPART_OFS_NXTBLK, ++ .size = MTDPART_SIZ_FULL, ++ }, +}; + -+static inline u32 pb44_spi_rr(struct ar71xx_spi *sp, unsigned reg) ++static int rb4xx_nand_dev_ready(struct mtd_info *mtd) +{ -+ return __raw_readl(sp->base + reg); ++ return gpio_get_value_cansleep(RB4XX_NAND_GPIO_READY); +} + -+static inline void pb44_spi_wr(struct ar71xx_spi *sp, unsigned reg, u32 val) ++static void rb4xx_nand_write_cmd(unsigned char cmd) +{ -+ __raw_writel(val, sp->base + reg); ++ unsigned char data = cmd; ++ int err; ++ ++ err = rb4xx_cpld_write(&data, 1); ++ if (err) ++ pr_err("rb4xx_nand: write cmd failed, err=%d\n", err); +} + -+static inline struct ar71xx_spi *spidev_to_sp(struct spi_device *spi) ++static void rb4xx_nand_cmd_ctrl(struct mtd_info *mtd, int cmd, ++ unsigned int ctrl) +{ -+ return spi_master_get_devdata(spi->master); ++ if (ctrl & NAND_CTRL_CHANGE) { ++ gpio_set_value_cansleep(RB4XX_NAND_GPIO_CLE, ++ (ctrl & NAND_CLE) ? 1 : 0); ++ gpio_set_value_cansleep(RB4XX_NAND_GPIO_ALE, ++ (ctrl & NAND_ALE) ? 1 : 0); ++ gpio_set_value_cansleep(RB4XX_NAND_GPIO_NCE, ++ (ctrl & NAND_NCE) ? 0 : 1); ++ } ++ ++ if (cmd != NAND_CMD_NONE) ++ rb4xx_nand_write_cmd(cmd); +} + -+static void pb44_spi_chipselect(struct spi_device *spi, int is_active) ++static unsigned char rb4xx_nand_read_byte(struct mtd_info *mtd) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ int cs_high = (spi->mode & SPI_CS_HIGH) ? is_active : !is_active; ++ unsigned char data = 0; ++ int err; + -+ if (is_active) { -+ /* set initial clock polarity */ -+ if (spi->mode & SPI_CPOL) -+ sp->ioc_base |= SPI_IOC_CLK; -+ else -+ sp->ioc_base &= ~SPI_IOC_CLK; -+ -+ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); -+ } -+ -+ if (spi->chip_select) { -+ unsigned long gpio = (unsigned long) spi->controller_data; -+ -+ /* SPI is normally active-low */ -+ gpio_set_value(gpio, cs_high); -+ } else { -+ if (cs_high) -+ sp->ioc_base |= SPI_IOC_CS0; -+ else -+ sp->ioc_base &= ~SPI_IOC_CS0; -+ -+ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); -+ } ++ err = rb4xx_cpld_read(&data, NULL, 1); ++ if (err) { ++ pr_err("rb4xx_nand: read data failed, err=%d\n", err); ++ data = 0xff; ++ } + ++ return data; +} + -+static int pb44_spi_setup_cs(struct spi_device *spi) ++static void rb4xx_nand_write_buf(struct mtd_info *mtd, const unsigned char *buf, ++ int len) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ -+ /* enable GPIO mode */ -+ pb44_spi_wr(sp, SPI_REG_FS, SPI_FS_GPIO); -+ -+ /* save CTRL register */ -+ sp->reg_ctrl = pb44_spi_rr(sp, SPI_REG_CTRL); -+ sp->ioc_base = pb44_spi_rr(sp, SPI_REG_IOC); -+ -+ /* TODO: setup speed? */ -+ pb44_spi_wr(sp, SPI_REG_CTRL, 0x43); -+ -+ if (spi->chip_select) { -+ unsigned long gpio = (unsigned long) spi->controller_data; -+ int status = 0; -+ -+ status = gpio_request(gpio, dev_name(&spi->dev)); -+ if (status) -+ return status; -+ -+ status = gpio_direction_output(gpio, spi->mode & SPI_CS_HIGH); -+ if (status) { -+ gpio_free(gpio); -+ return status; -+ } -+ } else { -+ if (spi->mode & SPI_CS_HIGH) -+ sp->ioc_base |= SPI_IOC_CS0; -+ else -+ sp->ioc_base &= ~SPI_IOC_CS0; -+ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); -+ } ++ int err; + -+ return 0; ++ err = rb4xx_cpld_write(buf, len); ++ if (err) ++ pr_err("rb4xx_nand: write buf failed, err=%d\n", err); +} + -+static void pb44_spi_cleanup_cs(struct spi_device *spi) ++static void rb4xx_nand_read_buf(struct mtd_info *mtd, unsigned char *buf, ++ int len) +{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ -+ if (spi->chip_select) { -+ unsigned long gpio = (unsigned long) spi->controller_data; -+ gpio_free(gpio); -+ } ++ int err; + -+ /* restore CTRL register */ -+ pb44_spi_wr(sp, SPI_REG_CTRL, sp->reg_ctrl); -+ /* disable GPIO mode */ -+ pb44_spi_wr(sp, SPI_REG_FS, 0); ++ err = rb4xx_cpld_read(buf, NULL, len); ++ if (err) ++ pr_err("rb4xx_nand: read buf failed, err=%d\n", err); +} + -+static int pb44_spi_setup(struct spi_device *spi) ++static int __init rb4xx_nand_probe(struct platform_device *pdev) +{ -+ int status = 0; ++ struct rb4xx_nand_info *info; ++ int ret; + -+ if (spi->bits_per_word > 32) -+ return -EINVAL; ++ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); + -+ if (!spi->controller_state) { -+ status = pb44_spi_setup_cs(spi); -+ if (status) -+ return status; ++ ret = gpio_request(RB4XX_NAND_GPIO_READY, "NAND RDY"); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to request gpio %d\n", ++ RB4XX_NAND_GPIO_READY); ++ goto err; + } + -+ status = spi_bitbang_setup(spi); -+ if (status && !spi->controller_state) -+ pb44_spi_cleanup_cs(spi); -+ -+ return status; -+} -+ -+static void pb44_spi_cleanup(struct spi_device *spi) -+{ -+ pb44_spi_cleanup_cs(spi); -+ spi_bitbang_cleanup(spi); -+} ++ ret = gpio_direction_input(RB4XX_NAND_GPIO_READY); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set input mode on gpio %d\n", ++ RB4XX_NAND_GPIO_READY); ++ goto err_free_gpio_ready; ++ } + -+static u32 pb44_spi_txrx_mode0(struct spi_device *spi, unsigned nsecs, -+ u32 word, u8 bits) -+{ -+ struct ar71xx_spi *sp = spidev_to_sp(spi); -+ u32 ioc = sp->ioc_base; -+ u32 ret; ++ ret = gpio_request(RB4XX_NAND_GPIO_ALE, "NAND ALE"); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to request gpio %d\n", ++ RB4XX_NAND_GPIO_ALE); ++ goto err_free_gpio_ready; ++ } + -+ /* clock starts at inactive polarity */ -+ for (word <<= (32 - bits); likely(bits); bits--) { -+ u32 out; ++ ret = gpio_direction_output(RB4XX_NAND_GPIO_ALE, 0); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set output mode on gpio %d\n", ++ RB4XX_NAND_GPIO_ALE); ++ goto err_free_gpio_ale; ++ } + -+ if (word & (1 << 31)) -+ out = ioc | SPI_IOC_DO; -+ else -+ out = ioc & ~SPI_IOC_DO; ++ ret = gpio_request(RB4XX_NAND_GPIO_CLE, "NAND CLE"); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to request gpio %d\n", ++ RB4XX_NAND_GPIO_CLE); ++ goto err_free_gpio_ale; ++ } + -+ /* setup MSB (to slave) on trailing edge */ -+ pb44_spi_wr(sp, SPI_REG_IOC, out); -+ pb44_spi_wr(sp, SPI_REG_IOC, out | SPI_IOC_CLK); ++ ret = gpio_direction_output(RB4XX_NAND_GPIO_CLE, 0); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set output mode on gpio %d\n", ++ RB4XX_NAND_GPIO_CLE); ++ goto err_free_gpio_cle; ++ } + -+ word <<= 1; ++ ret = gpio_request(RB4XX_NAND_GPIO_NCE, "NAND NCE"); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to request gpio %d\n", ++ RB4XX_NAND_GPIO_NCE); ++ goto err_free_gpio_cle; ++ } + -+#ifdef PER_BIT_READ -+ /* sample MSB (from slave) on leading edge */ -+ ret = pb44_spi_rr(sp, SPI_REG_RDS); -+ pb44_spi_wr(sp, SPI_REG_IOC, out); -+#endif ++ ret = gpio_direction_output(RB4XX_NAND_GPIO_NCE, 1); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set output mode on gpio %d\n", ++ RB4XX_NAND_GPIO_ALE); ++ goto err_free_gpio_nce; + } + -+#ifndef PER_BIT_READ -+ ret = pb44_spi_rr(sp, SPI_REG_RDS); -+#endif -+ return ret; -+} ++ info = kzalloc(sizeof(*info), GFP_KERNEL); ++ if (!info) { ++ dev_err(&pdev->dev, "rb4xx-nand: no memory for private data\n"); ++ ret = -ENOMEM; ++ goto err_free_gpio_nce; ++ } + -+static int pb44_spi_probe(struct platform_device *pdev) -+{ -+ struct spi_master *master; -+ struct ar71xx_spi *sp; -+ struct ar71xx_spi_platform_data *pdata; -+ struct resource *r; -+ int ret; ++ info->chip.priv = &info; ++ info->mtd.priv = &info->chip; ++ info->mtd.owner = THIS_MODULE; + -+ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); -+ if (master == NULL) { -+ dev_err(&pdev->dev, "failed to allocate spi master\n"); -+ return -ENOMEM; -+ } ++ info->chip.cmd_ctrl = rb4xx_nand_cmd_ctrl; ++ info->chip.dev_ready = rb4xx_nand_dev_ready; ++ info->chip.read_byte = rb4xx_nand_read_byte; ++ info->chip.write_buf = rb4xx_nand_write_buf; ++ info->chip.read_buf = rb4xx_nand_read_buf; ++#if 0 ++ info->chip.verify_buf = rb4xx_nand_verify_buf; ++#endif + -+ sp = spi_master_get_devdata(master); -+ platform_set_drvdata(pdev, sp); ++ info->chip.chip_delay = 25; ++ info->chip.ecc.mode = NAND_ECC_SOFT; ++ info->chip.options |= NAND_NO_AUTOINCR; + -+ pdata = pdev->dev.platform_data; ++ platform_set_drvdata(pdev, info); + -+ master->setup = pb44_spi_setup; -+ master->cleanup = pb44_spi_cleanup; -+ if (pdata) { -+ master->bus_num = pdata->bus_num; -+ master->num_chipselect = pdata->num_chipselect; -+ } else { -+ master->bus_num = 0; -+ master->num_chipselect = 1; ++ ret = nand_scan_ident(&info->mtd, 1, NULL); ++ if (ret) { ++ ret = -ENXIO; ++ goto err_free_info; + } + -+ sp->bitbang.master = spi_master_get(master); -+ sp->bitbang.chipselect = pb44_spi_chipselect; -+ sp->bitbang.txrx_word[SPI_MODE_0] = pb44_spi_txrx_mode0; -+ sp->bitbang.setup_transfer = spi_bitbang_setup_transfer; -+ sp->bitbang.flags = SPI_CS_HIGH; ++ if (info->mtd.writesize == 512) ++ info->chip.ecc.layout = &rb4xx_nand_ecclayout; + -+ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (r == NULL) { -+ ret = -ENOENT; -+ goto err1; ++ ret = nand_scan_tail(&info->mtd); ++ if (ret) { ++ return -ENXIO; ++ goto err_set_drvdata; + } + -+ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); -+ if (!sp->base) { -+ ret = -ENXIO; -+ goto err1; -+ } ++#ifdef CONFIG_MTD_PARTITIONS ++ ret = add_mtd_partitions(&info->mtd, rb4xx_nand_partitions, ++ ARRAY_SIZE(rb4xx_nand_partitions)); ++#else ++ ret = add_mtd_device(&info->mtd); ++#endif ++ if (ret) ++ goto err_release_nand; + -+ ret = spi_bitbang_start(&sp->bitbang); -+ if (!ret) -+ return 0; ++ return 0; + -+ iounmap(sp->base); -+ err1: ++err_release_nand: ++ nand_release(&info->mtd); ++err_set_drvdata: + platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); -+ ++err_free_info: ++ kfree(info); ++err_free_gpio_nce: ++ gpio_free(RB4XX_NAND_GPIO_NCE); ++err_free_gpio_cle: ++ gpio_free(RB4XX_NAND_GPIO_CLE); ++err_free_gpio_ale: ++ gpio_free(RB4XX_NAND_GPIO_ALE); ++err_free_gpio_ready: ++ gpio_free(RB4XX_NAND_GPIO_READY); ++err: + return ret; +} + -+static int pb44_spi_remove(struct platform_device *pdev) ++static int __devexit rb4xx_nand_remove(struct platform_device *pdev) +{ -+ struct ar71xx_spi *sp = platform_get_drvdata(pdev); ++ struct rb4xx_nand_info *info = platform_get_drvdata(pdev); + -+ spi_bitbang_stop(&sp->bitbang); -+ iounmap(sp->base); ++ nand_release(&info->mtd); + platform_set_drvdata(pdev, NULL); -+ spi_master_put(sp->bitbang.master); ++ kfree(info); ++ gpio_free(RB4XX_NAND_GPIO_NCE); ++ gpio_free(RB4XX_NAND_GPIO_CLE); ++ gpio_free(RB4XX_NAND_GPIO_ALE); ++ gpio_free(RB4XX_NAND_GPIO_READY); + + return 0; +} + -+static struct platform_driver pb44_spi_drv = { -+ .probe = pb44_spi_probe, -+ .remove = pb44_spi_remove, -+ .driver = { ++static struct platform_driver rb4xx_nand_driver = { ++ .probe = rb4xx_nand_probe, ++ .remove = __devexit_p(rb4xx_nand_remove), ++ .driver = { + .name = DRV_NAME, + .owner = THIS_MODULE, + }, +}; + -+static int __init pb44_spi_init(void) ++static int __init rb4xx_nand_init(void) +{ -+ return platform_driver_register(&pb44_spi_drv); ++ return platform_driver_register(&rb4xx_nand_driver); +} -+module_init(pb44_spi_init); + -+static void __exit pb44_spi_exit(void) ++static void __exit rb4xx_nand_exit(void) +{ -+ platform_driver_unregister(&pb44_spi_drv); ++ platform_driver_unregister(&rb4xx_nand_driver); +} -+module_exit(pb44_spi_exit); + -+MODULE_ALIAS("platform:" DRV_NAME); ++module_init(rb4xx_nand_init); ++module_exit(rb4xx_nand_exit); ++ +MODULE_DESCRIPTION(DRV_DESC); +MODULE_VERSION(DRV_VERSION); +MODULE_AUTHOR("Gabor Juhos "); ++MODULE_AUTHOR("Imre Kaloz "); +MODULE_LICENSE("GPL v2"); -diff -Nur linux-2.6.39.orig/drivers/spi/spi_vsc7385.c linux-2.6.39/drivers/spi/spi_vsc7385.c ---- linux-2.6.39.orig/drivers/spi/spi_vsc7385.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/spi/spi_vsc7385.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,620 @@ +diff -Nur linux-2.6.39.orig/drivers/mtd/nand/rb750_nand.c linux-2.6.39/drivers/mtd/nand/rb750_nand.c +--- linux-2.6.39.orig/drivers/mtd/nand/rb750_nand.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/mtd/nand/rb750_nand.c 2011-04-27 12:19:22.177661504 +0200 +@@ -0,0 +1,361 @@ +/* -+ * SPI driver for the Vitesse VSC7385 ethernet switch -+ * -+ * Copyright (C) 2009 Gabor Juhos ++ * NAND flash driver for the MikroTik RouterBOARD 750 + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2010 Gabor Juhos + * -+ * This program is free software; you can redistribute 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 free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + */ + -+#include -+#include +#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include ++#include ++#include ++#include ++#include ++#include ++#include + -+#define DRV_NAME "spi-vsc7385" -+#define DRV_DESC "Vitesse VSC7385 Gbit ethernet switch driver" -+#define DRV_VERSION "0.1.0" ++#include ++#include + -+#define VSC73XX_BLOCK_MAC 0x1 -+#define VSC73XX_BLOCK_2 0x2 -+#define VSC73XX_BLOCK_MII 0x3 -+#define VSC73XX_BLOCK_4 0x4 -+#define VSC73XX_BLOCK_5 0x5 -+#define VSC73XX_BLOCK_SYSTEM 0x7 ++#define DRV_NAME "rb750-nand" ++#define DRV_VERSION "0.1.0" ++#define DRV_DESC "NAND flash driver for the RouterBOARD 750" + -+#define VSC73XX_SUBBLOCK_PORT_0 0 -+#define VSC73XX_SUBBLOCK_PORT_1 1 -+#define VSC73XX_SUBBLOCK_PORT_2 2 -+#define VSC73XX_SUBBLOCK_PORT_3 3 -+#define VSC73XX_SUBBLOCK_PORT_4 4 -+#define VSC73XX_SUBBLOCK_PORT_MAC 6 ++#define RB750_NAND_IO0 BIT(RB750_GPIO_NAND_IO0) ++#define RB750_NAND_ALE BIT(RB750_GPIO_NAND_ALE) ++#define RB750_NAND_CLE BIT(RB750_GPIO_NAND_CLE) ++#define RB750_NAND_NRE BIT(RB750_GPIO_NAND_NRE) ++#define RB750_NAND_NWE BIT(RB750_GPIO_NAND_NWE) ++#define RB750_NAND_RDY BIT(RB750_GPIO_NAND_RDY) ++#define RB750_NAND_NCE BIT(RB750_GPIO_NAND_NCE) + -+/* MAC Block registers */ -+#define VSC73XX_MAC_CFG 0x0 -+#define VSC73XX_ADVPORTM 0x19 -+#define VSC73XX_RXOCT 0x50 -+#define VSC73XX_TXOCT 0x51 -+#define VSC73XX_C_RX0 0x52 -+#define VSC73XX_C_RX1 0x53 -+#define VSC73XX_C_RX2 0x54 -+#define VSC73XX_C_TX0 0x55 -+#define VSC73XX_C_TX1 0x56 -+#define VSC73XX_C_TX2 0x57 -+#define VSC73XX_C_CFG 0x58 ++#define RB750_NAND_DATA_SHIFT 1 ++#define RB750_NAND_DATA_BITS (0xff << RB750_NAND_DATA_SHIFT) ++#define RB750_NAND_INPUT_BITS (RB750_NAND_DATA_BITS | RB750_NAND_RDY) ++#define RB750_NAND_OUTPUT_BITS (RB750_NAND_ALE | RB750_NAND_CLE | \ ++ RB750_NAND_NRE | RB750_NAND_NWE | \ ++ RB750_NAND_NCE) + -+/* MAC_CFG register bits */ -+#define VSC73XX_MAC_CFG_WEXC_DIS (1 << 31) -+#define VSC73XX_MAC_CFG_PORT_RST (1 << 29) -+#define VSC73XX_MAC_CFG_TX_EN (1 << 28) -+#define VSC73XX_MAC_CFG_SEED_LOAD (1 << 27) -+#define VSC73XX_MAC_CFG_FDX (1 << 18) -+#define VSC73XX_MAC_CFG_GIGE (1 << 17) -+#define VSC73XX_MAC_CFG_RX_EN (1 << 16) -+#define VSC73XX_MAC_CFG_VLAN_DBLAWR (1 << 15) -+#define VSC73XX_MAC_CFG_VLAN_AWR (1 << 14) -+#define VSC73XX_MAC_CFG_100_BASE_T (1 << 13) -+#define VSC73XX_MAC_CFG_TX_IPG(x) (((x) & 0x1f) << 6) -+#define VSC73XX_MAC_CFG_MAC_RX_RST (1 << 5) -+#define VSC73XX_MAC_CFG_MAC_TX_RST (1 << 4) -+#define VSC73XX_MAC_CFG_BIT2 (1 << 2) -+#define VSC73XX_MAC_CFG_CLK_SEL(x) ((x) & 0x3) ++struct rb750_nand_info { ++ struct nand_chip chip; ++ struct mtd_info mtd; ++}; + -+/* ADVPORTM register bits */ -+#define VSC73XX_ADVPORTM_IFG_PPM (1 << 7) -+#define VSC73XX_ADVPORTM_EXC_COL_CONT (1 << 6) -+#define VSC73XX_ADVPORTM_EXT_PORT (1 << 5) -+#define VSC73XX_ADVPORTM_INV_GTX (1 << 4) -+#define VSC73XX_ADVPORTM_ENA_GTX (1 << 3) -+#define VSC73XX_ADVPORTM_DDR_MODE (1 << 2) -+#define VSC73XX_ADVPORTM_IO_LOOPBACK (1 << 1) -+#define VSC73XX_ADVPORTM_HOST_LOOPBACK (1 << 0) ++/* ++ * We need to use the OLD Yaffs-1 OOB layout, otherwise the RB bootloader ++ * will not be able to find the kernel that we load. ++ */ ++static struct nand_ecclayout rb750_nand_ecclayout = { ++ .eccbytes = 6, ++ .eccpos = { 8, 9, 10, 13, 14, 15 }, ++ .oobavail = 9, ++ .oobfree = { { 0, 4 }, { 6, 2 }, { 11, 2 }, { 4, 1 } } ++}; + -+/* MII Block registers */ -+#define VSC73XX_MII_STAT 0x0 -+#define VSC73XX_MII_CMD 0x1 -+#define VSC73XX_MII_DATA 0x2 ++static struct mtd_partition rb750_nand_partitions[] = { ++ { ++ .name = "booter", ++ .offset = 0, ++ .size = (256 * 1024), ++ .mask_flags = MTD_WRITEABLE, ++ }, { ++ .name = "kernel", ++ .offset = (256 * 1024), ++ .size = (4 * 1024 * 1024) - (256 * 1024), ++ }, { ++ .name = "rootfs", ++ .offset = MTDPART_OFS_NXTBLK, ++ .size = MTDPART_SIZ_FULL, ++ }, ++}; + -+/* System Block registers */ -+#define VSC73XX_ICPU_SIPAD 0x01 -+#define VSC73XX_ICPU_CLOCK_DELAY 0x05 -+#define VSC73XX_ICPU_CTRL 0x10 -+#define VSC73XX_ICPU_ADDR 0x11 -+#define VSC73XX_ICPU_SRAM 0x12 -+#define VSC73XX_ICPU_MBOX_VAL 0x15 -+#define VSC73XX_ICPU_MBOX_SET 0x16 -+#define VSC73XX_ICPU_MBOX_CLR 0x17 -+#define VSC73XX_ICPU_CHIPID 0x18 -+#define VSC73XX_ICPU_GPIO 0x34 ++static void rb750_nand_write(const u8 *buf, unsigned len) ++{ ++ void __iomem *base = ar71xx_gpio_base; ++ u32 out; ++ unsigned i; + -+#define VSC73XX_ICPU_CTRL_CLK_DIV (1 << 8) -+#define VSC73XX_ICPU_CTRL_SRST_HOLD (1 << 7) -+#define VSC73XX_ICPU_CTRL_BOOT_EN (1 << 3) -+#define VSC73XX_ICPU_CTRL_EXT_ACC_EN (1 << 2) -+#define VSC73XX_ICPU_CTRL_CLK_EN (1 << 1) -+#define VSC73XX_ICPU_CTRL_SRST (1 << 0) ++ /* set data lines to output mode */ ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) | RB750_NAND_DATA_BITS, ++ base + GPIO_REG_OE); + -+#define VSC73XX_ICPU_CHIPID_ID_SHIFT 12 -+#define VSC73XX_ICPU_CHIPID_ID_MASK 0xffff -+#define VSC73XX_ICPU_CHIPID_REV_SHIFT 28 -+#define VSC73XX_ICPU_CHIPID_REV_MASK 0xf -+#define VSC73XX_ICPU_CHIPID_ID_7385 0x7385 -+#define VSC73XX_ICPU_CHIPID_ID_7395 0x7395 ++ out = __raw_readl(base + GPIO_REG_OUT); ++ out &= ~(RB750_NAND_DATA_BITS | RB750_NAND_NWE); ++ for (i = 0; i != len; i++) { ++ u32 data; + -+#define VSC73XX_CMD_MODE_READ 0 -+#define VSC73XX_CMD_MODE_WRITE 1 -+#define VSC73XX_CMD_MODE_SHIFT 4 -+#define VSC73XX_CMD_BLOCK_SHIFT 5 -+#define VSC73XX_CMD_BLOCK_MASK 0x7 -+#define VSC73XX_CMD_SUBBLOCK_MASK 0xf ++ data = buf[i]; ++ data <<= RB750_NAND_DATA_SHIFT; ++ data |= out; ++ __raw_writel(data, base + GPIO_REG_OUT); + -+#define VSC7385_CLOCK_DELAY ((3 << 4) | 3) -+#define VSC7385_CLOCK_DELAY_MASK ((3 << 4) | 3) ++ __raw_writel(data | RB750_NAND_NWE, base + GPIO_REG_OUT); ++ /* flush write */ ++ __raw_readl(base + GPIO_REG_OUT); ++ } + -+#define VSC73XX_ICPU_CTRL_STOP (VSC73XX_ICPU_CTRL_SRST_HOLD | \ -+ VSC73XX_ICPU_CTRL_BOOT_EN | \ -+ VSC73XX_ICPU_CTRL_EXT_ACC_EN) ++ /* set data lines to input mode */ ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) & ~RB750_NAND_DATA_BITS, ++ base + GPIO_REG_OE); ++ /* flush write */ ++ __raw_readl(base + GPIO_REG_OE); ++} + -+#define VSC73XX_ICPU_CTRL_START (VSC73XX_ICPU_CTRL_CLK_DIV | \ -+ VSC73XX_ICPU_CTRL_BOOT_EN | \ -+ VSC73XX_ICPU_CTRL_CLK_EN | \ -+ VSC73XX_ICPU_CTRL_SRST) ++static int rb750_nand_read_verify(u8 *read_buf, unsigned len, ++ const u8 *verify_buf) ++{ ++ void __iomem *base = ar71xx_gpio_base; ++ unsigned i; + -+#define VSC7385_ADVPORTM_MASK (VSC73XX_ADVPORTM_IFG_PPM | \ -+ VSC73XX_ADVPORTM_EXC_COL_CONT | \ -+ VSC73XX_ADVPORTM_EXT_PORT | \ -+ VSC73XX_ADVPORTM_INV_GTX | \ -+ VSC73XX_ADVPORTM_ENA_GTX | \ -+ VSC73XX_ADVPORTM_DDR_MODE | \ -+ VSC73XX_ADVPORTM_IO_LOOPBACK | \ -+ VSC73XX_ADVPORTM_HOST_LOOPBACK) ++ for (i = 0; i < len; i++) { ++ u8 data; + -+#define VSC7385_ADVPORTM_INIT (VSC73XX_ADVPORTM_EXT_PORT | \ -+ VSC73XX_ADVPORTM_ENA_GTX | \ -+ VSC73XX_ADVPORTM_DDR_MODE) ++ /* activate RE line */ ++ __raw_writel(RB750_NAND_NRE, base + GPIO_REG_CLEAR); ++ /* flush write */ ++ __raw_readl(base + GPIO_REG_CLEAR); + -+#define VSC7385_MAC_CFG_RESET (VSC73XX_MAC_CFG_PORT_RST | \ -+ VSC73XX_MAC_CFG_MAC_RX_RST | \ -+ VSC73XX_MAC_CFG_MAC_TX_RST) ++ /* read input lines */ ++ data = __raw_readl(base + GPIO_REG_IN) >> RB750_NAND_DATA_SHIFT; + -+#define VSC73XX_MAC_CFG_INIT (VSC73XX_MAC_CFG_TX_EN | \ -+ VSC73XX_MAC_CFG_FDX | \ -+ VSC73XX_MAC_CFG_GIGE | \ -+ VSC73XX_MAC_CFG_RX_EN) ++ /* deactivate RE line */ ++ __raw_writel(RB750_NAND_NRE, base + GPIO_REG_SET); + -+#define VSC73XX_RESET_DELAY 100 ++ if (read_buf) ++ read_buf[i] = data; ++ else if (verify_buf && verify_buf[i] != data) ++ return -EFAULT; ++ } + -+struct vsc7385 { -+ struct spi_device *spi; -+ struct mutex lock; -+ struct vsc7385_platform_data *pdata; -+}; ++ return 0; ++} + -+static int vsc7385_is_addr_valid(u8 block, u8 subblock) ++static void rb750_nand_select_chip(struct mtd_info *mtd, int chip) +{ -+ switch (block) { -+ case VSC73XX_BLOCK_MAC: -+ switch (subblock) { -+ case 0 ... 4: -+ case 6: -+ return 1; -+ } -+ break; ++ void __iomem *base = ar71xx_gpio_base; ++ u32 func; + -+ case VSC73XX_BLOCK_2: -+ case VSC73XX_BLOCK_SYSTEM: -+ switch (subblock) { -+ case 0: -+ return 1; -+ } -+ break; -+ -+ case VSC73XX_BLOCK_MII: -+ case VSC73XX_BLOCK_4: -+ case VSC73XX_BLOCK_5: -+ switch (subblock) { -+ case 0 ... 1: -+ return 1; -+ } -+ break; -+ } -+ -+ return 0; -+} -+ -+static inline u8 vsc7385_make_addr(u8 mode, u8 block, u8 subblock) -+{ -+ u8 ret; -+ -+ ret = (block & VSC73XX_CMD_BLOCK_MASK) << VSC73XX_CMD_BLOCK_SHIFT; -+ ret |= (mode & 1) << VSC73XX_CMD_MODE_SHIFT; -+ ret |= subblock & VSC73XX_CMD_SUBBLOCK_MASK; -+ -+ return ret; -+} -+ -+static int vsc7385_read(struct vsc7385 *vsc, u8 block, u8 subblock, u8 reg, -+ u32 *value) -+{ -+ u8 cmd[4]; -+ u8 buf[4]; -+ struct spi_transfer t[2]; -+ struct spi_message m; -+ int err; -+ -+ if (!vsc7385_is_addr_valid(block, subblock)) -+ return -EINVAL; -+ -+ spi_message_init(&m); -+ -+ memset(&t, 0, sizeof(t)); ++ func = __raw_readl(base + GPIO_REG_FUNC); ++ if (chip >= 0) { ++ /* disable latch */ ++ rb750_latch_change(RB750_LVC573_LE, 0); + -+ t[0].tx_buf = cmd; -+ t[0].len = sizeof(cmd); -+ spi_message_add_tail(&t[0], &m); ++ /* disable alternate functions */ ++ ar71xx_gpio_function_setup(AR724X_GPIO_FUNC_JTAG_DISABLE, ++ AR724X_GPIO_FUNC_SPI_EN); + -+ t[1].rx_buf = buf; -+ t[1].len = sizeof(buf); -+ spi_message_add_tail(&t[1], &m); ++ /* set input mode for data lines */ ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) & ++ ~RB750_NAND_INPUT_BITS, ++ base + GPIO_REG_OE); + -+ cmd[0] = vsc7385_make_addr(VSC73XX_CMD_MODE_READ, block, subblock); -+ cmd[1] = reg; -+ cmd[2] = 0; -+ cmd[3] = 0; ++ /* deactivate RE and WE lines */ ++ __raw_writel(RB750_NAND_NRE | RB750_NAND_NWE, ++ base + GPIO_REG_SET); ++ /* flush write */ ++ (void) __raw_readl(base + GPIO_REG_SET); + -+ mutex_lock(&vsc->lock); -+ err = spi_sync(vsc->spi, &m); -+ mutex_unlock(&vsc->lock); ++ /* activate CE line */ ++ __raw_writel(RB750_NAND_NCE, base + GPIO_REG_CLEAR); ++ } else { ++ /* deactivate CE line */ ++ __raw_writel(RB750_NAND_NCE, base + GPIO_REG_SET); ++ /* flush write */ ++ (void) __raw_readl(base + GPIO_REG_SET); + -+ if (err) -+ return err; ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) | ++ RB750_NAND_IO0 | RB750_NAND_RDY, ++ base + GPIO_REG_OE); + -+ *value = (((u32) buf[0]) << 24) | (((u32) buf[1]) << 16) | -+ (((u32) buf[2]) << 8) | ((u32) buf[3]); ++ /* restore alternate functions */ ++ ar71xx_gpio_function_setup(AR724X_GPIO_FUNC_SPI_EN, ++ AR724X_GPIO_FUNC_JTAG_DISABLE); + -+ return 0; ++ /* enable latch */ ++ rb750_latch_change(0, RB750_LVC573_LE); ++ } +} + -+ -+static int vsc7385_write(struct vsc7385 *vsc, u8 block, u8 subblock, u8 reg, -+ u32 value) ++static int rb750_nand_dev_ready(struct mtd_info *mtd) +{ -+ u8 cmd[2]; -+ u8 buf[4]; -+ struct spi_transfer t[2]; -+ struct spi_message m; -+ int err; -+ -+ if (!vsc7385_is_addr_valid(block, subblock)) -+ return -EINVAL; -+ -+ spi_message_init(&m); -+ -+ memset(&t, 0, sizeof(t)); -+ -+ t[0].tx_buf = cmd; -+ t[0].len = sizeof(cmd); -+ spi_message_add_tail(&t[0], &m); -+ -+ t[1].tx_buf = buf; -+ t[1].len = sizeof(buf); -+ spi_message_add_tail(&t[1], &m); -+ -+ cmd[0] = vsc7385_make_addr(VSC73XX_CMD_MODE_WRITE, block, subblock); -+ cmd[1] = reg; -+ -+ buf[0] = (value >> 24) & 0xff; -+ buf[1] = (value >> 16) & 0xff; -+ buf[2] = (value >> 8) & 0xff; -+ buf[3] = value & 0xff; -+ -+ mutex_lock(&vsc->lock); -+ err = spi_sync(vsc->spi, &m); -+ mutex_unlock(&vsc->lock); ++ void __iomem *base = ar71xx_gpio_base; + -+ return err; ++ return !!(__raw_readl(base + GPIO_REG_IN) & RB750_NAND_RDY); +} + -+static inline int vsc7385_write_verify(struct vsc7385 *vsc, u8 block, -+ u8 subblock, u8 reg, u32 value, -+ u32 read_mask, u32 read_val) ++static void rb750_nand_cmd_ctrl(struct mtd_info *mtd, int cmd, ++ unsigned int ctrl) +{ -+ struct spi_device *spi = vsc->spi; -+ u32 t; -+ int err; ++ if (ctrl & NAND_CTRL_CHANGE) { ++ void __iomem *base = ar71xx_gpio_base; ++ u32 t; + -+ err = vsc7385_write(vsc, block, subblock, reg, value); -+ if (err) -+ return err; ++ t = __raw_readl(base + GPIO_REG_OUT); + -+ err = vsc7385_read(vsc, block, subblock, reg, &t); -+ if (err) -+ return err; ++ t &= ~(RB750_NAND_CLE | RB750_NAND_ALE); ++ t |= (ctrl & NAND_CLE) ? RB750_NAND_CLE : 0; ++ t |= (ctrl & NAND_ALE) ? RB750_NAND_ALE : 0; + -+ if ((t & read_mask) != read_val) { -+ dev_err(&spi->dev, "register write error\n"); -+ return -EIO; ++ __raw_writel(t, base + GPIO_REG_OUT); ++ /* flush write */ ++ __raw_readl(base + GPIO_REG_OUT); + } + -+ return 0; ++ if (cmd != NAND_CMD_NONE) { ++ u8 t = cmd; ++ rb750_nand_write(&t, 1); ++ } +} + -+static inline int vsc7385_set_clock_delay(struct vsc7385 *vsc, u32 val) ++static u8 rb750_nand_read_byte(struct mtd_info *mtd) +{ -+ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_CLOCK_DELAY, val); ++ u8 data = 0; ++ rb750_nand_read_verify(&data, 1, NULL); ++ return data; +} + -+static inline int vsc7385_get_clock_delay(struct vsc7385 *vsc, u32 *val) ++static void rb750_nand_read_buf(struct mtd_info *mtd, u8 *buf, int len) +{ -+ return vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_CLOCK_DELAY, val); ++ rb750_nand_read_verify(buf, len, NULL); +} + -+static inline int vsc7385_icpu_stop(struct vsc7385 *vsc) ++static void rb750_nand_write_buf(struct mtd_info *mtd, const u8 *buf, int len) +{ -+ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_CTRL, -+ VSC73XX_ICPU_CTRL_STOP); ++ rb750_nand_write(buf, len); +} + -+static inline int vsc7385_icpu_start(struct vsc7385 *vsc) ++static int rb750_nand_verify_buf(struct mtd_info *mtd, const u8 *buf, int len) +{ -+ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_CTRL, -+ VSC73XX_ICPU_CTRL_START); ++ return rb750_nand_read_verify(NULL, len, buf); +} + -+static inline int vsc7385_icpu_reset(struct vsc7385 *vsc) ++static void __init rb750_nand_gpio_init(void) +{ -+ int rc; ++ void __iomem *base = ar71xx_gpio_base; ++ u32 out; + -+ rc = vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_ADDR, -+ 0x0000); -+ if (rc) -+ dev_err(&vsc->spi->dev, -+ "could not reset microcode, err=%d\n", rc); ++ out = __raw_readl(base + GPIO_REG_OUT); + -+ return rc; -+} ++ /* setup output levels */ ++ __raw_writel(RB750_NAND_NCE | RB750_NAND_NRE | RB750_NAND_NWE, ++ base + GPIO_REG_SET); + -+static int vsc7385_upload_ucode(struct vsc7385 *vsc) -+{ -+ struct spi_device *spi = vsc->spi; -+ const struct firmware *firmware; -+ char *ucode_name; -+ unsigned char *dp; -+ unsigned int curVal; -+ int i; -+ int diffs; -+ int rc; ++ __raw_writel(RB750_NAND_ALE | RB750_NAND_CLE, ++ base + GPIO_REG_CLEAR); + -+ ucode_name = (vsc->pdata->ucode_name) ? vsc->pdata->ucode_name -+ : "vsc7385_ucode.bin"; -+ rc = request_firmware(&firmware, ucode_name, &spi->dev); -+ if (rc) { -+ dev_err(&spi->dev, "request_firmware failed, err=%d\n", -+ rc); -+ return rc; -+ } ++ /* setup input lines */ ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) & ~(RB750_NAND_INPUT_BITS), ++ base + GPIO_REG_OE); + -+ rc = vsc7385_icpu_stop(vsc); -+ if (rc) -+ goto out; ++ /* setup output lines */ ++ __raw_writel(__raw_readl(base + GPIO_REG_OE) | RB750_NAND_OUTPUT_BITS, ++ base + GPIO_REG_OE); + -+ rc = vsc7385_icpu_reset(vsc); -+ if (rc) -+ goto out; ++ rb750_latch_change(~out & RB750_NAND_IO0, out & RB750_NAND_IO0); ++} + -+ dev_info(&spi->dev, "uploading microcode...\n"); ++static int __init rb750_nand_probe(struct platform_device *pdev) ++{ ++ struct rb750_nand_info *info; ++ int ret; + -+ dp = (unsigned char *) firmware->data; -+ for (i = 0; i < firmware->size; i++) { -+ rc = vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_SRAM, *dp++); -+ if (rc) { -+ dev_err(&spi->dev, "could not load microcode, err=%d\n", -+ rc); -+ goto out; -+ } -+ } ++ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); + -+ rc = vsc7385_icpu_reset(vsc); -+ if (rc) -+ goto out; ++ rb750_nand_gpio_init(); + -+ dev_info(&spi->dev, "verifying microcode...\n"); -+ -+ dp = (unsigned char *) firmware->data; -+ diffs = 0; -+ for (i = 0; i < firmware->size; i++) { -+ rc = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_SRAM, &curVal); -+ if (rc) { -+ dev_err(&spi->dev, "could not read microcode %d\n",rc); -+ goto out; -+ } -+ -+ if (curVal > 0xff) { -+ dev_err(&spi->dev, "bad val read: %04x : %02x %02x\n", -+ i, *dp, curVal); -+ rc = -EIO; -+ goto out; -+ } -+ -+ if ((curVal & 0xff) != *dp) { -+ diffs++; -+ dev_err(&spi->dev, "verify error: %04x : %02x %02x\n", -+ i, *dp, curVal); -+ -+ if (diffs > 4) -+ break; -+ } -+ dp++; -+ } -+ -+ if (diffs) { -+ dev_err(&spi->dev, "microcode verification failed\n"); -+ rc = -EIO; -+ goto out; -+ } -+ -+ dev_info(&spi->dev, "microcode uploaded\n"); -+ -+ rc = vsc7385_icpu_start(vsc); -+ -+ out: -+ release_firmware(firmware); -+ return rc; -+} -+ -+static int vsc7385_setup(struct vsc7385 *vsc) -+{ -+ struct vsc7385_platform_data *pdata = vsc->pdata; -+ u32 t; -+ int err; -+ -+ err = vsc7385_write_verify(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_CLOCK_DELAY, -+ VSC7385_CLOCK_DELAY, -+ VSC7385_CLOCK_DELAY_MASK, -+ VSC7385_CLOCK_DELAY); -+ if (err) -+ goto err; -+ -+ err = vsc7385_write_verify(vsc, VSC73XX_BLOCK_MAC, -+ VSC73XX_SUBBLOCK_PORT_MAC, VSC73XX_ADVPORTM, -+ VSC7385_ADVPORTM_INIT, -+ VSC7385_ADVPORTM_MASK, -+ VSC7385_ADVPORTM_INIT); -+ if (err) -+ goto err; -+ -+ err = vsc7385_write(vsc, VSC73XX_BLOCK_MAC, VSC73XX_SUBBLOCK_PORT_MAC, -+ VSC73XX_MAC_CFG, VSC7385_MAC_CFG_RESET); -+ if (err) -+ goto err; -+ -+ t = VSC73XX_MAC_CFG_INIT; -+ t |= VSC73XX_MAC_CFG_TX_IPG(pdata->mac_cfg.tx_ipg); -+ t |= VSC73XX_MAC_CFG_CLK_SEL(pdata->mac_cfg.clk_sel); -+ if (pdata->mac_cfg.bit2) -+ t |= VSC73XX_MAC_CFG_BIT2; -+ -+ err = vsc7385_write(vsc, VSC73XX_BLOCK_MAC, VSC73XX_SUBBLOCK_PORT_MAC, -+ VSC73XX_MAC_CFG, t); -+ if (err) -+ goto err; -+ -+ return 0; -+ -+ err: -+ return err; -+} -+ -+static int vsc7385_detect(struct vsc7385 *vsc) -+{ -+ struct spi_device *spi = vsc->spi; -+ u32 t; -+ u32 id; -+ u32 rev; -+ int err; -+ -+ err = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_MBOX_VAL, &t); -+ if (err) { -+ dev_err(&spi->dev, "unable to read mailbox, err=%d\n", err); -+ return err; -+ } -+ -+ if (t == 0xffffffff) { -+ dev_dbg(&spi->dev, "assert chip reset\n"); -+ if (vsc->pdata->reset) -+ vsc->pdata->reset(); -+ -+ } -+ -+ err = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, -+ VSC73XX_ICPU_CHIPID, &t); -+ if (err) { -+ dev_err(&spi->dev, "unable to read chip id, err=%d\n", err); -+ return err; -+ } -+ -+ id = (t >> VSC73XX_ICPU_CHIPID_ID_SHIFT) & VSC73XX_ICPU_CHIPID_ID_MASK; -+ switch (id) { -+ case VSC73XX_ICPU_CHIPID_ID_7385: -+ case VSC73XX_ICPU_CHIPID_ID_7395: -+ break; -+ default: -+ dev_err(&spi->dev, "unsupported chip, id=%04x\n", id); -+ return -ENODEV; -+ } -+ -+ rev = (t >> VSC73XX_ICPU_CHIPID_REV_SHIFT) & -+ VSC73XX_ICPU_CHIPID_REV_MASK; -+ dev_info(&spi->dev, "VSC%04X (rev. %d) switch found \n", id, rev); ++ info = kzalloc(sizeof(*info), GFP_KERNEL); ++ if (!info) ++ return -ENOMEM; + -+ return 0; -+} ++ info->chip.priv = &info; ++ info->mtd.priv = &info->chip; ++ info->mtd.owner = THIS_MODULE; + -+static int __devinit vsc7385_probe(struct spi_device *spi) -+{ -+ struct vsc7385 *vsc; -+ struct vsc7385_platform_data *pdata; -+ int err; ++ info->chip.select_chip = rb750_nand_select_chip; ++ info->chip.cmd_ctrl = rb750_nand_cmd_ctrl; ++ info->chip.dev_ready = rb750_nand_dev_ready; ++ info->chip.read_byte = rb750_nand_read_byte; ++ info->chip.write_buf = rb750_nand_write_buf; ++ info->chip.read_buf = rb750_nand_read_buf; ++ info->chip.verify_buf = rb750_nand_verify_buf; + -+ printk(KERN_INFO DRV_DESC " version " DRV_VERSION"\n"); ++ info->chip.chip_delay = 25; ++ info->chip.ecc.mode = NAND_ECC_SOFT; ++ info->chip.options |= NAND_NO_AUTOINCR; + -+ pdata = spi->dev.platform_data; -+ if (!pdata) { -+ dev_err(&spi->dev, "no platform data specified\n"); -+ return-ENODEV; -+ } ++ platform_set_drvdata(pdev, info); + -+ vsc = kzalloc(sizeof(*vsc), GFP_KERNEL); -+ if (!vsc) { -+ dev_err(&spi->dev, "no memory for private data\n"); -+ return-ENOMEM; ++ ret = nand_scan_ident(&info->mtd, 1); ++ if (ret) { ++ ret = -ENXIO; ++ goto err_free_info; + } + -+ mutex_init(&vsc->lock); -+ vsc->pdata = pdata; -+ vsc->spi = spi_dev_get(spi); -+ dev_set_drvdata(&spi->dev, vsc); -+ -+ spi->mode = SPI_MODE_0; -+ spi->bits_per_word = 8; -+ err = spi_setup(spi); -+ if (err) { -+ dev_err(&spi->dev, "spi_setup failed, err=%d \n", err); -+ goto err_drvdata; -+ } ++ if (info->mtd.writesize == 512) ++ info->chip.ecc.layout = &rb750_nand_ecclayout; + -+ err = vsc7385_detect(vsc); -+ if (err) { -+ dev_err(&spi->dev, "no chip found, err=%d \n", err); -+ goto err_drvdata; ++ ret = nand_scan_tail(&info->mtd); ++ if (ret) { ++ return -ENXIO; ++ goto err_set_drvdata; + } + -+ err = vsc7385_upload_ucode(vsc); -+ if (err) -+ goto err_drvdata; -+ -+ err = vsc7385_setup(vsc); -+ if (err) -+ goto err_drvdata; ++#ifdef CONFIG_MTD_PARTITIONS ++ ret = add_mtd_partitions(&info->mtd, rb750_nand_partitions, ++ ARRAY_SIZE(rb750_nand_partitions)); ++#else ++ ret = add_mtd_device(&info->mtd); ++#endif ++ if (ret) ++ goto err_release_nand; + + return 0; + -+ err_drvdata: -+ dev_set_drvdata(&spi->dev, NULL); -+ kfree(vsc); -+ return err; ++err_release_nand: ++ nand_release(&info->mtd); ++err_set_drvdata: ++ platform_set_drvdata(pdev, NULL); ++err_free_info: ++ kfree(info); ++ return ret; +} + -+static int __devexit vsc7385_remove(struct spi_device *spi) ++static int __devexit rb750_nand_remove(struct platform_device *pdev) +{ -+ struct vsc7385_data *vsc; ++ struct rb750_nand_info *info = platform_get_drvdata(pdev); + -+ vsc = dev_get_drvdata(&spi->dev); -+ dev_set_drvdata(&spi->dev, NULL); -+ kfree(vsc); ++ nand_release(&info->mtd); ++ platform_set_drvdata(pdev, NULL); ++ kfree(info); + + return 0; +} + -+static struct spi_driver vsc7385_driver = { -+ .driver = { -+ .name = DRV_NAME, -+ .bus = &spi_bus_type, -+ .owner = THIS_MODULE, ++static struct platform_driver rb750_nand_driver = { ++ .probe = rb750_nand_probe, ++ .remove = __devexit_p(rb750_nand_remove), ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, + }, -+ .probe = vsc7385_probe, -+ .remove = __devexit_p(vsc7385_remove), +}; + -+static int __init vsc7385_init(void) ++static int __init rb750_nand_init(void) +{ -+ return spi_register_driver(&vsc7385_driver); ++ return platform_driver_register(&rb750_nand_driver); +} -+module_init(vsc7385_init); + -+static void __exit vsc7385_exit(void) ++static void __exit rb750_nand_exit(void) +{ -+ spi_unregister_driver(&vsc7385_driver); ++ platform_driver_unregister(&rb750_nand_driver); +} -+module_exit(vsc7385_exit); ++ ++module_init(rb750_nand_init); ++module_exit(rb750_nand_exit); + +MODULE_DESCRIPTION(DRV_DESC); +MODULE_VERSION(DRV_VERSION); +MODULE_AUTHOR("Gabor Juhos "); +MODULE_LICENSE("GPL v2"); -+ -diff -Nur linux-2.6.39.orig/drivers/usb/host/Kconfig linux-2.6.39/drivers/usb/host/Kconfig ---- linux-2.6.39.orig/drivers/usb/host/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/usb/host/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -129,6 +129,13 @@ - config USB_FSL_MPH_DR_OF - tristate - -+config USB_EHCI_AR71XX -+ bool "USB EHCI support for AR71xx" -+ depends on USB_EHCI_HCD && ATHEROS_AR71XX -+ default y -+ help -+ Support for Atheros AR71xx built-in EHCI controller -+ - config USB_EHCI_FSL - bool "Support for Freescale on-chip EHCI USB controller" - depends on USB_EHCI_HCD && FSL_SOC -@@ -287,6 +294,13 @@ - Enables support for the on-chip OHCI controller on - OMAP3 and later chips. - -+config USB_OHCI_AR71XX -+ bool "USB OHCI support for Atheros AR71xx" -+ depends on USB_OHCI_HCD && ATHEROS_AR71XX -+ default y -+ help -+ Support for Atheros AR71xx built-in OHCI controller -+ - config USB_OHCI_HCD_PPC_SOC - bool "OHCI support for on-chip PPC USB controller" - depends on USB_OHCI_HCD && (STB03xxx || PPC_MPC52xx) -diff -Nur linux-2.6.39.orig/drivers/usb/host/ehci-ar71xx.c linux-2.6.39/drivers/usb/host/ehci-ar71xx.c ---- linux-2.6.39.orig/drivers/usb/host/ehci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/usb/host/ehci-ar71xx.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,242 @@ +diff -Nur linux-2.6.39.orig/drivers/mtd/wrt160nl_part.c linux-2.6.39/drivers/mtd/wrt160nl_part.c +--- linux-2.6.39.orig/drivers/mtd/wrt160nl_part.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/mtd/wrt160nl_part.c 2011-08-06 09:32:37.138017083 +0200 +@@ -0,0 +1,190 @@ +/* -+ * Bus Glue for Atheros AR71xx built-in EHCI controller. ++ * Copyright (C) 2009 Christian Daniel ++ * Copyright (C) 2009 Gabor Juhos + * -+ * Copyright (C) 2008-2010 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz ++ * 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. + * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * Copyright (C) 2007 Atheros Communications, Inc. ++ * 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA ++ * ++ * TRX flash partition table. ++ * Based on ar7 map by Felix Fietkau + * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. + */ + -+#include -+#include ++#include ++#include ++#include + -+#include ++#include ++#include + -+extern int usb_disabled(void); ++struct cybertan_header { ++ char magic[4]; ++ u8 res1[4]; ++ char fw_date[3]; ++ char fw_ver[3]; ++ char id[4]; ++ char hw_ver; ++ char unused; ++ u8 flags[2]; ++ u8 res2[10]; ++}; + -+static int ehci_ar71xx_init(struct usb_hcd *hcd) -+{ -+ struct ehci_hcd *ehci = hcd_to_ehci(hcd); -+ int ret; ++#define TRX_PARTS 6 ++#define TRX_MAGIC 0x30524448 ++#define TRX_MAX_OFFSET 3 + -+ ehci->caps = hcd->regs; -+ ehci->regs = hcd->regs + -+ HC_LENGTH(ehci_readl(ehci, &ehci->caps->hc_capbase)); -+ ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params); ++struct trx_header { ++ uint32_t magic; /* "HDR0" */ ++ uint32_t len; /* Length of file including header */ ++ uint32_t crc32; /* 32-bit CRC from flag_version to end of file */ ++ uint32_t flag_version; /* 0:15 flags, 16:31 version */ ++ uint32_t offsets[TRX_MAX_OFFSET]; /* Offsets of partitions from start of header */ ++}; + -+ ehci->sbrn = 0x20; -+ ehci->has_synopsys_hc_bug = 1; ++#define IH_MAGIC 0x27051956 /* Image Magic Number */ ++#define IH_NMLEN 32 /* Image Name Length */ + -+ ehci_reset(ehci); ++struct uimage_header { ++ uint32_t ih_magic; /* Image Header Magic Number */ ++ uint32_t ih_hcrc; /* Image Header CRC Checksum */ ++ uint32_t ih_time; /* Image Creation Timestamp */ ++ uint32_t ih_size; /* Image Data Size */ ++ uint32_t ih_load; /* Data» Load Address */ ++ uint32_t ih_ep; /* Entry Point Address */ ++ uint32_t ih_dcrc; /* Image Data CRC Checksum */ ++ uint8_t ih_os; /* Operating System */ ++ uint8_t ih_arch; /* CPU architecture */ ++ uint8_t ih_type; /* Image Type */ ++ uint8_t ih_comp; /* Compression Type */ ++ uint8_t ih_name[IH_NMLEN]; /* Image Name */ ++}; + -+ ret = ehci_init(hcd); -+ if (ret) -+ return ret; ++struct wrt160nl_header { ++ struct cybertan_header cybertan; ++ struct trx_header trx; ++ struct uimage_header uimage; ++} __attribute__ ((packed)); + -+ ehci_port_power(ehci, 0); ++static struct mtd_partition trx_parts[TRX_PARTS]; + -+ return 0; -+} ++#define WRT160NL_UBOOT_LEN 0x40000 ++#define WRT160NL_ART_LEN 0x10000 ++#define WRT160NL_NVRAM_LEN 0x10000 + -+static int ehci_ar91xx_init(struct usb_hcd *hcd) ++static int wrt160nl_parse_partitions(struct mtd_info *master, ++ struct mtd_partition **pparts, ++ unsigned long origin) +{ -+ struct ehci_hcd *ehci = hcd_to_ehci(hcd); ++ struct wrt160nl_header *header; ++ struct trx_header *theader; ++ struct uimage_header *uheader; ++ size_t retlen; ++ unsigned int kernel_len; ++ unsigned int uboot_len = max(master->erasesize, WRT160NL_UBOOT_LEN); ++ unsigned int nvram_len = max(master->erasesize, WRT160NL_NVRAM_LEN); ++ unsigned int art_len = max(master->erasesize, WRT160NL_ART_LEN); + int ret; + -+ ehci->caps = hcd->regs + 0x100; -+ ehci->regs = hcd->regs + 0x100 + -+ HC_LENGTH(ehci_readl(ehci, &ehci->caps->hc_capbase)); -+ ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params); -+ -+ hcd->has_tt = 1; -+ ehci->sbrn = 0x20; -+ -+ ehci_reset(ehci); ++ header = vmalloc(sizeof(*header)); ++ if (!header) { ++ return -ENOMEM; ++ goto out; ++ } + -+ ret = ehci_init(hcd); ++ ret = master->read(master, uboot_len, sizeof(*header), ++ &retlen, (void *) header); + if (ret) -+ return ret; -+ -+ ehci_port_power(ehci, 0); ++ goto free_hdr; + -+ return 0; -+} ++ if (retlen != sizeof(*header)) { ++ ret = -EIO; ++ goto free_hdr; ++ } + -+static int ehci_ar71xx_probe(const struct hc_driver *driver, -+ struct usb_hcd **hcd_out, -+ struct platform_device *pdev) -+{ -+ struct usb_hcd *hcd; -+ struct resource *res; -+ int irq; -+ int ret; ++ if (strncmp(header->cybertan.magic, "NL16", 4) != 0) { ++ printk(KERN_NOTICE "%s: no WRT160NL signature found\n", ++ master->name); ++ goto free_hdr; ++ } + -+ res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); -+ if (!res) { -+ dev_dbg(&pdev->dev, "no IRQ specified for %s\n", -+ dev_name(&pdev->dev)); -+ return -ENODEV; ++ theader = &header->trx; ++ if (le32_to_cpu(theader->magic) != TRX_MAGIC) { ++ printk(KERN_NOTICE "%s: no TRX header found\n", master->name); ++ goto free_hdr; + } -+ irq = res->start; + -+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (!res) { -+ dev_dbg(&pdev->dev, "no base address specified for %s\n", -+ dev_name(&pdev->dev)); -+ return -ENODEV; ++ uheader = &header->uimage; ++ if (uheader->ih_magic != IH_MAGIC) { ++ printk(KERN_NOTICE "%s: no uImage found\n", master->name); ++ goto free_hdr; + } + -+ hcd = usb_create_hcd(driver, &pdev->dev, dev_name(&pdev->dev)); -+ if (!hcd) -+ return -ENOMEM; ++ kernel_len = le32_to_cpu(theader->offsets[1]) + ++ sizeof(struct cybertan_header); + -+ hcd->rsrc_start = res->start; -+ hcd->rsrc_len = res->end - res->start + 1; ++ trx_parts[0].name = "u-boot"; ++ trx_parts[0].offset = 0; ++ trx_parts[0].size = uboot_len; ++ trx_parts[0].mask_flags = MTD_WRITEABLE; + -+ if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { -+ dev_dbg(&pdev->dev, "controller already in use\n"); -+ ret = -EBUSY; -+ goto err_put_hcd; -+ } ++ trx_parts[1].name = "kernel"; ++ trx_parts[1].offset = trx_parts[0].offset + trx_parts[0].size; ++ trx_parts[1].size = kernel_len; ++ trx_parts[1].mask_flags = 0; + -+ hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len); -+ if (!hcd->regs) { -+ dev_dbg(&pdev->dev, "error mapping memory\n"); -+ ret = -EFAULT; -+ goto err_release_region; -+ } ++ trx_parts[2].name = "rootfs"; ++ trx_parts[2].offset = trx_parts[1].offset + trx_parts[1].size; ++ trx_parts[2].size = master->size - uboot_len - nvram_len - art_len - ++ trx_parts[1].size; ++ trx_parts[2].mask_flags = 0; + -+ ret = usb_add_hcd(hcd, irq, IRQF_DISABLED | IRQF_SHARED); -+ if (ret) -+ goto err_iounmap; ++ trx_parts[3].name = "nvram"; ++ trx_parts[3].offset = master->size - nvram_len - art_len; ++ trx_parts[3].size = nvram_len; ++ trx_parts[3].mask_flags = MTD_WRITEABLE; + -+ return 0; ++ trx_parts[4].name = "art"; ++ trx_parts[4].offset = master->size - art_len; ++ trx_parts[4].size = art_len; ++ trx_parts[4].mask_flags = MTD_WRITEABLE; + -+ err_iounmap: -+ iounmap(hcd->regs); ++ trx_parts[5].name = "firmware"; ++ trx_parts[5].offset = uboot_len; ++ trx_parts[5].size = master->size - uboot_len - nvram_len - art_len; ++ trx_parts[5].mask_flags = 0; + -+ err_release_region: -+ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); -+ err_put_hcd: -+ usb_put_hcd(hcd); ++ *pparts = trx_parts; ++ ret = TRX_PARTS; ++ ++free_hdr: ++ vfree(header); ++out: + return ret; +} + -+static void ehci_ar71xx_remove(struct usb_hcd *hcd, -+ struct platform_device *pdev) ++static struct mtd_part_parser wrt160nl_parser = { ++ .owner = THIS_MODULE, ++ .parse_fn = wrt160nl_parse_partitions, ++ .name = "wrt160nl", ++}; ++ ++static int __init wrt160nl_parser_init(void) +{ -+ usb_remove_hcd(hcd); -+ iounmap(hcd->regs); -+ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); -+ usb_put_hcd(hcd); ++ return register_mtd_parser(&wrt160nl_parser); +} + -+static const struct hc_driver ehci_ar71xx_hc_driver = { -+ .description = hcd_name, -+ .product_desc = "Atheros AR71xx built-in EHCI controller", -+ .hcd_priv_size = sizeof(struct ehci_hcd), -+ -+ .irq = ehci_irq, -+ .flags = HCD_MEMORY | HCD_USB2, -+ -+ .reset = ehci_ar71xx_init, -+ .start = ehci_run, -+ .stop = ehci_stop, -+ .shutdown = ehci_shutdown, ++module_init(wrt160nl_parser_init); + -+ .urb_enqueue = ehci_urb_enqueue, -+ .urb_dequeue = ehci_urb_dequeue, -+ .endpoint_disable = ehci_endpoint_disable, -+ .endpoint_reset = ehci_endpoint_reset, ++MODULE_LICENSE("GPL"); ++MODULE_AUTHOR("Christian Daniel "); +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar7240.c linux-2.6.39/drivers/net/ag71xx/ag71xx_ar7240.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar7240.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_ar7240.c 2011-08-06 09:32:37.298018216 +0200 +@@ -0,0 +1,913 @@ ++/* ++ * Driver for the built-in ethernet switch of the Atheros AR7240 SoC ++ * Copyright (c) 2010 Gabor Juhos ++ * Copyright (c) 2010 Felix Fietkau ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ + -+ .get_frame_number = ehci_get_frame, ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include "ag71xx.h" + -+ .hub_status_data = ehci_hub_status_data, -+ .hub_control = ehci_hub_control, -+#ifdef CONFIG_PM -+ .hub_suspend = ehci_hub_suspend, -+ .hub_resume = ehci_hub_resume, -+#endif -+ .relinquish_port = ehci_relinquish_port, -+ .port_handed_over = ehci_port_handed_over, ++#define BITM(_count) (BIT(_count) - 1) ++#define BITS(_shift, _count) (BITM(_count) << _shift) + -+ .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete, -+}; ++#define AR7240_REG_MASK_CTRL 0x00 ++#define AR7240_MASK_CTRL_REVISION_M BITM(8) ++#define AR7240_MASK_CTRL_VERSION_M BITM(8) ++#define AR7240_MASK_CTRL_VERSION_S 8 ++#define AR7240_MASK_CTRL_SOFT_RESET BIT(31) + -+static const struct hc_driver ehci_ar91xx_hc_driver = { -+ .description = hcd_name, -+ .product_desc = "Atheros AR91xx built-in EHCI controller", -+ .hcd_priv_size = sizeof(struct ehci_hcd), -+ .irq = ehci_irq, -+ .flags = HCD_MEMORY | HCD_USB2, ++#define AR7240_REG_MAC_ADDR0 0x20 ++#define AR7240_REG_MAC_ADDR1 0x24 + -+ .reset = ehci_ar91xx_init, -+ .start = ehci_run, -+ .stop = ehci_stop, -+ .shutdown = ehci_shutdown, ++#define AR7240_REG_FLOOD_MASK 0x2c ++#define AR7240_FLOOD_MASK_BROAD_TO_CPU BIT(26) + -+ .urb_enqueue = ehci_urb_enqueue, -+ .urb_dequeue = ehci_urb_dequeue, -+ .endpoint_disable = ehci_endpoint_disable, -+ .endpoint_reset = ehci_endpoint_reset, ++#define AR7240_REG_GLOBAL_CTRL 0x30 ++#define AR7240_GLOBAL_CTRL_MTU_M BITM(12) + -+ .get_frame_number = ehci_get_frame, ++#define AR7240_REG_VTU 0x0040 ++#define AR7240_VTU_OP BITM(3) ++#define AR7240_VTU_OP_NOOP 0x0 ++#define AR7240_VTU_OP_FLUSH 0x1 ++#define AR7240_VTU_OP_LOAD 0x2 ++#define AR7240_VTU_OP_PURGE 0x3 ++#define AR7240_VTU_OP_REMOVE_PORT 0x4 ++#define AR7240_VTU_ACTIVE BIT(3) ++#define AR7240_VTU_FULL BIT(4) ++#define AR7240_VTU_PORT BITS(8, 4) ++#define AR7240_VTU_PORT_S 8 ++#define AR7240_VTU_VID BITS(16, 12) ++#define AR7240_VTU_VID_S 16 ++#define AR7240_VTU_PRIO BITS(28, 3) ++#define AR7240_VTU_PRIO_S 28 ++#define AR7240_VTU_PRIO_EN BIT(31) ++ ++#define AR7240_REG_VTU_DATA 0x0044 ++#define AR7240_VTUDATA_MEMBER BITS(0, 10) ++#define AR7240_VTUDATA_VALID BIT(11) ++ ++#define AR7240_REG_ATU 0x50 ++#define AR7240_ATU_FLUSH_ALL 0x1 + -+ .hub_status_data = ehci_hub_status_data, -+ .hub_control = ehci_hub_control, -+#ifdef CONFIG_PM -+ .hub_suspend = ehci_hub_suspend, -+ .hub_resume = ehci_hub_resume, -+#endif -+ .relinquish_port = ehci_relinquish_port, -+ .port_handed_over = ehci_port_handed_over, ++#define AR7240_REG_AT_CTRL 0x5c ++#define AR7240_AT_CTRL_AGE_TIME BITS(0, 15) ++#define AR7240_AT_CTRL_AGE_EN BIT(17) ++#define AR7240_AT_CTRL_LEARN_CHANGE BIT(18) ++#define AR7240_AT_CTRL_ARP_EN BIT(20) + -+ .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete, -+}; ++#define AR7240_REG_TAG_PRIORITY 0x70 + -+static int ehci_ar71xx_driver_probe(struct platform_device *pdev) -+{ -+ struct ar71xx_ehci_platform_data *pdata; -+ struct usb_hcd *hcd = NULL; -+ int ret; ++#define AR7240_REG_SERVICE_TAG 0x74 ++#define AR7240_SERVICE_TAG_M BITM(16) + -+ if (usb_disabled()) -+ return -ENODEV; ++#define AR7240_REG_CPU_PORT 0x78 ++#define AR7240_MIRROR_PORT_S 4 ++#define AR7240_CPU_PORT_EN BIT(8) + -+ pdata = pdev->dev.platform_data; -+ if (!pdata) { -+ dev_err(&pdev->dev, "no platform data specified for %s\n", -+ dev_name(&pdev->dev)); -+ return -ENODEV; -+ } ++#define AR7240_REG_MIB_FUNCTION0 0x80 ++#define AR7240_MIB_TIMER_M BITM(16) ++#define AR7240_MIB_AT_HALF_EN BIT(16) ++#define AR7240_MIB_BUSY BIT(17) ++#define AR7240_MIB_FUNC_S 24 ++#define AR7240_MIB_FUNC_NO_OP 0x0 ++#define AR7240_MIB_FUNC_FLUSH 0x1 ++#define AR7240_MIB_FUNC_CAPTURE 0x3 + -+ if (pdata->is_ar91xx) -+ ret = ehci_ar71xx_probe(&ehci_ar91xx_hc_driver, &hcd, pdev); -+ else -+ ret = ehci_ar71xx_probe(&ehci_ar71xx_hc_driver, &hcd, pdev); ++#define AR7240_REG_MDIO_CTRL 0x98 ++#define AR7240_MDIO_CTRL_DATA_M BITM(16) ++#define AR7240_MDIO_CTRL_REG_ADDR_S 16 ++#define AR7240_MDIO_CTRL_PHY_ADDR_S 21 ++#define AR7240_MDIO_CTRL_CMD_WRITE 0 ++#define AR7240_MDIO_CTRL_CMD_READ BIT(27) ++#define AR7240_MDIO_CTRL_MASTER_EN BIT(30) ++#define AR7240_MDIO_CTRL_BUSY BIT(31) + -+ return ret; -+} ++#define AR7240_REG_PORT_BASE(_port) (0x100 + (_port) * 0x100) + -+static int ehci_ar71xx_driver_remove(struct platform_device *pdev) -+{ -+ struct usb_hcd *hcd = platform_get_drvdata(pdev); ++#define AR7240_REG_PORT_STATUS(_port) (AR7240_REG_PORT_BASE((_port)) + 0x00) ++#define AR7240_PORT_STATUS_SPEED_M BITM(2) ++#define AR7240_PORT_STATUS_SPEED_10 0 ++#define AR7240_PORT_STATUS_SPEED_100 1 ++#define AR7240_PORT_STATUS_SPEED_1000 2 ++#define AR7240_PORT_STATUS_TXMAC BIT(2) ++#define AR7240_PORT_STATUS_RXMAC BIT(3) ++#define AR7240_PORT_STATUS_TXFLOW BIT(4) ++#define AR7240_PORT_STATUS_RXFLOW BIT(5) ++#define AR7240_PORT_STATUS_DUPLEX BIT(6) ++#define AR7240_PORT_STATUS_LINK_UP BIT(8) ++#define AR7240_PORT_STATUS_LINK_AUTO BIT(9) ++#define AR7240_PORT_STATUS_LINK_PAUSE BIT(10) + -+ ehci_ar71xx_remove(hcd, pdev); -+ return 0; -+} ++#define AR7240_REG_PORT_CTRL(_port) (AR7240_REG_PORT_BASE((_port)) + 0x04) ++#define AR7240_PORT_CTRL_STATE_M BITM(3) ++#define AR7240_PORT_CTRL_STATE_DISABLED 0 ++#define AR7240_PORT_CTRL_STATE_BLOCK 1 ++#define AR7240_PORT_CTRL_STATE_LISTEN 2 ++#define AR7240_PORT_CTRL_STATE_LEARN 3 ++#define AR7240_PORT_CTRL_STATE_FORWARD 4 ++#define AR7240_PORT_CTRL_LEARN_LOCK BIT(7) ++#define AR7240_PORT_CTRL_VLAN_MODE_S 8 ++#define AR7240_PORT_CTRL_VLAN_MODE_KEEP 0 ++#define AR7240_PORT_CTRL_VLAN_MODE_STRIP 1 ++#define AR7240_PORT_CTRL_VLAN_MODE_ADD 2 ++#define AR7240_PORT_CTRL_VLAN_MODE_DOUBLE_TAG 3 ++#define AR7240_PORT_CTRL_IGMP_SNOOP BIT(10) ++#define AR7240_PORT_CTRL_HEADER BIT(11) ++#define AR7240_PORT_CTRL_MAC_LOOP BIT(12) ++#define AR7240_PORT_CTRL_SINGLE_VLAN BIT(13) ++#define AR7240_PORT_CTRL_LEARN BIT(14) ++#define AR7240_PORT_CTRL_DOUBLE_TAG BIT(15) ++#define AR7240_PORT_CTRL_MIRROR_TX BIT(16) ++#define AR7240_PORT_CTRL_MIRROR_RX BIT(17) + -+MODULE_ALIAS("platform:ar71xx-ehci"); ++#define AR7240_REG_PORT_VLAN(_port) (AR7240_REG_PORT_BASE((_port)) + 0x08) + -+static struct platform_driver ehci_ar71xx_driver = { -+ .probe = ehci_ar71xx_driver_probe, -+ .remove = ehci_ar71xx_driver_remove, -+ .driver = { -+ .name = "ar71xx-ehci", -+ } -+}; -diff -Nur linux-2.6.39.orig/drivers/usb/host/ehci-hcd.c linux-2.6.39/drivers/usb/host/ehci-hcd.c ---- linux-2.6.39.orig/drivers/usb/host/ehci-hcd.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/usb/host/ehci-hcd.c 2011-05-27 14:36:51.000000000 +0200 -@@ -1265,6 +1265,11 @@ - #define PLATFORM_DRIVER tegra_ehci_driver - #endif - -+#ifdef CONFIG_USB_EHCI_AR71XX -+#include "ehci-ar71xx.c" -+#define PLATFORM_DRIVER ehci_ar71xx_driver -+#endif ++#define AR7240_PORT_VLAN_DEFAULT_ID_S 0 ++#define AR7240_PORT_VLAN_DEST_PORTS_S 16 ++#define AR7240_PORT_VLAN_MODE_S 30 ++#define AR7240_PORT_VLAN_MODE_PORT_ONLY 0 ++#define AR7240_PORT_VLAN_MODE_PORT_FALLBACK 1 ++#define AR7240_PORT_VLAN_MODE_VLAN_ONLY 2 ++#define AR7240_PORT_VLAN_MODE_SECURE 3 + - #if !defined(PCI_DRIVER) && !defined(PLATFORM_DRIVER) && \ - !defined(PS3_SYSTEM_BUS_DRIVER) && !defined(OF_PLATFORM_DRIVER) && \ - !defined(XILINX_OF_PLATFORM_DRIVER) -diff -Nur linux-2.6.39.orig/drivers/usb/host/ohci-ar71xx.c linux-2.6.39/drivers/usb/host/ohci-ar71xx.c ---- linux-2.6.39.orig/drivers/usb/host/ohci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/usb/host/ohci-ar71xx.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,165 @@ -+/* -+ * OHCI HCD (Host Controller Driver) for USB. -+ * -+ * Bus Glue for Atheros AR71xx built-in OHCI controller. -+ * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * Parts of this file are based on Atheros' 2.6.15 BSP -+ * Copyright (C) 2007 Atheros Communications, Inc. -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ + -+#include -+#include ++#define AR7240_REG_STATS_BASE(_port) (0x20000 + (_port) * 0x100) + -+extern int usb_disabled(void); ++#define AR7240_STATS_RXBROAD 0x00 ++#define AR7240_STATS_RXPAUSE 0x04 ++#define AR7240_STATS_RXMULTI 0x08 ++#define AR7240_STATS_RXFCSERR 0x0c ++#define AR7240_STATS_RXALIGNERR 0x10 ++#define AR7240_STATS_RXRUNT 0x14 ++#define AR7240_STATS_RXFRAGMENT 0x18 ++#define AR7240_STATS_RX64BYTE 0x1c ++#define AR7240_STATS_RX128BYTE 0x20 ++#define AR7240_STATS_RX256BYTE 0x24 ++#define AR7240_STATS_RX512BYTE 0x28 ++#define AR7240_STATS_RX1024BYTE 0x2c ++#define AR7240_STATS_RX1518BYTE 0x30 ++#define AR7240_STATS_RXMAXBYTE 0x34 ++#define AR7240_STATS_RXTOOLONG 0x38 ++#define AR7240_STATS_RXGOODBYTE 0x3c ++#define AR7240_STATS_RXBADBYTE 0x44 ++#define AR7240_STATS_RXOVERFLOW 0x4c ++#define AR7240_STATS_FILTERED 0x50 ++#define AR7240_STATS_TXBROAD 0x54 ++#define AR7240_STATS_TXPAUSE 0x58 ++#define AR7240_STATS_TXMULTI 0x5c ++#define AR7240_STATS_TXUNDERRUN 0x60 ++#define AR7240_STATS_TX64BYTE 0x64 ++#define AR7240_STATS_TX128BYTE 0x68 ++#define AR7240_STATS_TX256BYTE 0x6c ++#define AR7240_STATS_TX512BYTE 0x70 ++#define AR7240_STATS_TX1024BYTE 0x74 ++#define AR7240_STATS_TX1518BYTE 0x78 ++#define AR7240_STATS_TXMAXBYTE 0x7c ++#define AR7240_STATS_TXOVERSIZE 0x80 ++#define AR7240_STATS_TXBYTE 0x84 ++#define AR7240_STATS_TXCOLLISION 0x8c ++#define AR7240_STATS_TXABORTCOL 0x90 ++#define AR7240_STATS_TXMULTICOL 0x94 ++#define AR7240_STATS_TXSINGLECOL 0x98 ++#define AR7240_STATS_TXEXCDEFER 0x9c ++#define AR7240_STATS_TXDEFER 0xa0 ++#define AR7240_STATS_TXLATECOL 0xa4 + -+static int usb_hcd_ar71xx_probe(const struct hc_driver *driver, -+ struct platform_device *pdev) -+{ -+ struct usb_hcd *hcd; -+ struct resource *res; -+ int irq; -+ int ret; ++#define AR7240_PORT_CPU 0 ++#define AR7240_NUM_PORTS 6 ++#define AR7240_NUM_PHYS 5 + -+ res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); -+ if (!res) { -+ dev_dbg(&pdev->dev, "no IRQ specified for %s\n", -+ dev_name(&pdev->dev)); -+ return -ENODEV; -+ } -+ irq = res->start; ++#define AR7240_PHY_ID1 0x004d ++#define AR7240_PHY_ID2 0xd041 + -+ hcd = usb_create_hcd(driver, &pdev->dev, dev_name(&pdev->dev)); -+ if (!hcd) -+ return -ENOMEM; ++#define AR7240_PORT_MASK(_port) BIT((_port)) ++#define AR7240_PORT_MASK_ALL BITM(AR7240_NUM_PORTS) ++#define AR7240_PORT_MASK_BUT(_port) (AR7240_PORT_MASK_ALL & ~BIT((_port))) + -+ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (!res) { -+ dev_dbg(&pdev->dev, "no base address specified for %s\n", -+ dev_name(&pdev->dev)); -+ ret = -ENODEV; -+ goto err_put_hcd; -+ } -+ hcd->rsrc_start = res->start; -+ hcd->rsrc_len = res->end - res->start + 1; ++#define AR7240_MAX_VLANS 16 + -+ if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { -+ dev_dbg(&pdev->dev, "controller already in use\n"); -+ ret = -EBUSY; -+ goto err_put_hcd; -+ } ++#define sw_to_ar7240(_dev) container_of(_dev, struct ar7240sw, swdev) + -+ hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len); -+ if (!hcd->regs) { -+ dev_dbg(&pdev->dev, "error mapping memory\n"); -+ ret = -EFAULT; -+ goto err_release_region; -+ } ++struct ar7240sw { ++ struct mii_bus *mii_bus; ++ struct switch_dev swdev; ++ bool vlan; ++ u16 vlan_id[AR7240_MAX_VLANS]; ++ u8 vlan_table[AR7240_MAX_VLANS]; ++ u8 vlan_tagged; ++ u16 pvid[AR7240_NUM_PORTS]; ++}; + -+ ohci_hcd_init(hcd_to_ohci(hcd)); ++struct ar7240sw_hw_stat { ++ char string[ETH_GSTRING_LEN]; ++ int sizeof_stat; ++ int reg; ++}; + -+ ret = usb_add_hcd(hcd, irq, IRQF_DISABLED); -+ if (ret) -+ goto err_stop_hcd; ++static DEFINE_MUTEX(reg_mutex); + -+ return 0; ++static inline void ar7240sw_init(struct ar7240sw *as, struct mii_bus *mii) ++{ ++ as->mii_bus = mii; ++} + -+ err_stop_hcd: -+ iounmap(hcd->regs); -+ err_release_region: -+ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); -+ err_put_hcd: -+ usb_put_hcd(hcd); -+ return ret; ++static inline u16 mk_phy_addr(u32 reg) ++{ ++ return 0x17 & ((reg >> 4) | 0x10); +} + -+void usb_hcd_ar71xx_remove(struct usb_hcd *hcd, struct platform_device *pdev) ++static inline u16 mk_phy_reg(u32 reg) +{ -+ usb_remove_hcd(hcd); -+ iounmap(hcd->regs); -+ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); -+ usb_put_hcd(hcd); ++ return (reg << 1) & 0x1e; +} + -+static int __devinit ohci_ar71xx_start(struct usb_hcd *hcd) ++static inline u16 mk_high_addr(u32 reg) +{ -+ struct ohci_hcd *ohci = hcd_to_ohci(hcd); -+ int ret; ++ return (reg >> 7) & 0x1ff; ++} + -+ ret = ohci_init(ohci); -+ if (ret < 0) -+ return ret; ++static u32 __ar7240sw_reg_read(struct mii_bus *mii, u32 reg) ++{ ++ unsigned long flags; ++ u16 phy_addr; ++ u16 phy_reg; ++ u32 hi, lo; + -+ ret = ohci_run(ohci); -+ if (ret < 0) -+ goto err; ++ reg = (reg & 0xfffffffc) >> 2; ++ phy_addr = mk_phy_addr(reg); ++ phy_reg = mk_phy_reg(reg); + -+ return 0; ++ local_irq_save(flags); ++ ag71xx_mdio_mii_write(mii->priv, 0x1f, 0x10, mk_high_addr(reg)); ++ lo = (u32) ag71xx_mdio_mii_read(mii->priv, phy_addr, phy_reg); ++ hi = (u32) ag71xx_mdio_mii_read(mii->priv, phy_addr, phy_reg + 1); ++ local_irq_restore(flags); + -+ err: -+ ohci_stop(hcd); -+ return ret; ++ return (hi << 16) | lo; +} + -+static const struct hc_driver ohci_ar71xx_hc_driver = { -+ .description = hcd_name, -+ .product_desc = "Atheros AR71xx built-in OHCI controller", -+ .hcd_priv_size = sizeof(struct ohci_hcd), ++static void __ar7240sw_reg_write(struct mii_bus *mii, u32 reg, u32 val) ++{ ++ unsigned long flags; ++ u16 phy_addr; ++ u16 phy_reg; + -+ .irq = ohci_irq, -+ .flags = HCD_USB11 | HCD_MEMORY, ++ reg = (reg & 0xfffffffc) >> 2; ++ phy_addr = mk_phy_addr(reg); ++ phy_reg = mk_phy_reg(reg); + -+ .start = ohci_ar71xx_start, -+ .stop = ohci_stop, -+ .shutdown = ohci_shutdown, ++ local_irq_save(flags); ++ ag71xx_mdio_mii_write(mii->priv, 0x1f, 0x10, mk_high_addr(reg)); ++ ag71xx_mdio_mii_write(mii->priv, phy_addr, phy_reg + 1, (val >> 16)); ++ ag71xx_mdio_mii_write(mii->priv, phy_addr, phy_reg, (val & 0xffff)); ++ local_irq_restore(flags); ++} + -+ .urb_enqueue = ohci_urb_enqueue, -+ .urb_dequeue = ohci_urb_dequeue, -+ .endpoint_disable = ohci_endpoint_disable, ++static u32 ar7240sw_reg_read(struct mii_bus *mii, u32 reg_addr) ++{ ++ u32 ret; + -+ /* -+ * scheduling support -+ */ -+ .get_frame_number = ohci_get_frame, ++ mutex_lock(®_mutex); ++ ret = __ar7240sw_reg_read(mii, reg_addr); ++ mutex_unlock(®_mutex); + -+ /* -+ * root hub support -+ */ -+ .hub_status_data = ohci_hub_status_data, -+ .hub_control = ohci_hub_control, -+ .start_port_reset = ohci_start_port_reset, -+}; ++ return ret; ++} + -+static int ohci_hcd_ar71xx_drv_probe(struct platform_device *pdev) ++static void ar7240sw_reg_write(struct mii_bus *mii, u32 reg_addr, u32 reg_val) +{ -+ if (usb_disabled()) -+ return -ENODEV; -+ -+ return usb_hcd_ar71xx_probe(&ohci_ar71xx_hc_driver, pdev); ++ mutex_lock(®_mutex); ++ __ar7240sw_reg_write(mii, reg_addr, reg_val); ++ mutex_unlock(®_mutex); +} + -+static int ohci_hcd_ar71xx_drv_remove(struct platform_device *pdev) ++static u32 ar7240sw_reg_rmw(struct mii_bus *mii, u32 reg, u32 mask, u32 val) +{ -+ struct usb_hcd *hcd = platform_get_drvdata(pdev); ++ u32 t; + -+ usb_hcd_ar71xx_remove(hcd, pdev); -+ return 0; ++ mutex_lock(®_mutex); ++ t = __ar7240sw_reg_read(mii, reg); ++ t &= ~mask; ++ t |= val; ++ __ar7240sw_reg_write(mii, reg, t); ++ mutex_unlock(®_mutex); ++ ++ return t; +} + -+MODULE_ALIAS("platform:ar71xx-ohci"); ++static void ar7240sw_reg_set(struct mii_bus *mii, u32 reg, u32 val) ++{ ++ u32 t; + -+static struct platform_driver ohci_hcd_ar71xx_driver = { -+ .probe = ohci_hcd_ar71xx_drv_probe, -+ .remove = ohci_hcd_ar71xx_drv_remove, -+ .shutdown = usb_hcd_platform_shutdown, -+ .driver = { -+ .name = "ar71xx-ohci", -+ .owner = THIS_MODULE, -+ }, -+}; -diff -Nur linux-2.6.39.orig/drivers/usb/host/ohci-hcd.c linux-2.6.39/drivers/usb/host/ohci-hcd.c ---- linux-2.6.39.orig/drivers/usb/host/ohci-hcd.c 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/usb/host/ohci-hcd.c 2011-05-27 14:36:51.000000000 +0200 -@@ -1105,6 +1105,11 @@ - #define PLATFORM_DRIVER ohci_hcd_cns3xxx_driver - #endif - -+#ifdef CONFIG_USB_OHCI_AR71XX -+#include "ohci-ar71xx.c" -+#define PLATFORM_DRIVER ohci_hcd_ar71xx_driver -+#endif ++ mutex_lock(®_mutex); ++ t = __ar7240sw_reg_read(mii, reg); ++ t |= val; ++ __ar7240sw_reg_write(mii, reg, t); ++ mutex_unlock(®_mutex); ++} + - #if !defined(PCI_DRIVER) && \ - !defined(PLATFORM_DRIVER) && \ - !defined(OMAP1_PLATFORM_DRIVER) && \ -diff -Nur linux-2.6.39.orig/drivers/watchdog/Kconfig linux-2.6.39/drivers/watchdog/Kconfig ---- linux-2.6.39.orig/drivers/watchdog/Kconfig 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/watchdog/Kconfig 2011-05-27 14:36:51.000000000 +0200 -@@ -990,6 +990,13 @@ - To compile this driver as a loadable module, choose M here. - The module will be called bcm63xx_wdt. - -+config AR71XX_WDT -+ tristate "Atheros AR71xx Watchdog Timer" -+ depends on ATHEROS_AR71XX -+ help -+ Hardware driver for the built-in watchdog timer on the Atheros -+ AR71xx SoCs. ++static int __ar7240sw_reg_wait(struct mii_bus *mii, u32 reg, u32 mask, u32 val, ++ unsigned timeout) ++{ ++ int i; + - # PARISC Architecture - - # POWERPC Architecture -diff -Nur linux-2.6.39.orig/drivers/watchdog/Makefile linux-2.6.39/drivers/watchdog/Makefile ---- linux-2.6.39.orig/drivers/watchdog/Makefile 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/drivers/watchdog/Makefile 2011-05-27 14:36:51.000000000 +0200 -@@ -121,6 +121,7 @@ - obj-$(CONFIG_SIBYTE_WDOG) += sb_wdog.o - obj-$(CONFIG_AR7_WDT) += ar7_wdt.o - obj-$(CONFIG_TXX9_WDT) += txx9wdt.o -+obj-$(CONFIG_AR71XX_WDT) += ar71xx_wdt.o - obj-$(CONFIG_OCTEON_WDT) += octeon-wdt.o - octeon-wdt-y := octeon-wdt-main.o octeon-wdt-nmi.o - -diff -Nur linux-2.6.39.orig/drivers/watchdog/ar71xx_wdt.c linux-2.6.39/drivers/watchdog/ar71xx_wdt.c ---- linux-2.6.39.orig/drivers/watchdog/ar71xx_wdt.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/drivers/watchdog/ar71xx_wdt.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,270 @@ -+/* -+ * Driver for the Atheros AR71xx SoC's built-in hardware watchdog timer. -+ * -+ * Copyright (C) 2008 Gabor Juhos -+ * Copyright (C) 2008 Imre Kaloz -+ * -+ * This driver was based on: drivers/watchdog/ixp4xx_wdt.c -+ * Author: Deepak Saxena -+ * Copyright 2004 (c) MontaVista, Software, Inc. -+ * -+ * which again was based on sa1100 driver, -+ * Copyright (C) 2000 Oleg Drokin -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ * -+ */ ++ for (i = 0; i < timeout; i++) { ++ u32 t; + -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+#include ++ t = __ar7240sw_reg_read(mii, reg); ++ if ((t & mask) == val) ++ return 0; + -+#include ++ msleep(1); ++ } + -+#define DRV_NAME "ar71xx-wdt" -+#define DRV_DESC "Atheros AR71xx hardware watchdog driver" -+#define DRV_VERSION "0.1.0" ++ return -ETIMEDOUT; ++} + -+#define WDT_TIMEOUT 15 /* seconds */ ++static int ar7240sw_reg_wait(struct mii_bus *mii, u32 reg, u32 mask, u32 val, ++ unsigned timeout) ++{ ++ int ret; + -+static int nowayout = WATCHDOG_NOWAYOUT; ++ mutex_lock(®_mutex); ++ ret = __ar7240sw_reg_wait(mii, reg, mask, val, timeout); ++ mutex_unlock(®_mutex); ++ return ret; ++} + -+#ifdef CONFIG_WATCHDOG_NOWAYOUT -+module_param(nowayout, int, 0); -+MODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started " -+ "(default=" __MODULE_STRING(WATCHDOG_NOWAYOUT) ")"); -+#endif ++u16 ar7240sw_phy_read(struct mii_bus *mii, unsigned phy_addr, ++ unsigned reg_addr) ++{ ++ u32 t, val = 0xffff; ++ int err; + -+static unsigned long wdt_flags; ++ if (phy_addr >= AR7240_NUM_PHYS) ++ return 0xffff; + -+#define WDT_FLAGS_BUSY 0 -+#define WDT_FLAGS_EXPECT_CLOSE 1 ++ mutex_lock(®_mutex); ++ t = (reg_addr << AR7240_MDIO_CTRL_REG_ADDR_S) | ++ (phy_addr << AR7240_MDIO_CTRL_PHY_ADDR_S) | ++ AR7240_MDIO_CTRL_MASTER_EN | ++ AR7240_MDIO_CTRL_BUSY | ++ AR7240_MDIO_CTRL_CMD_READ; + -+static int wdt_timeout = WDT_TIMEOUT; -+static int boot_status; -+static int max_timeout; ++ __ar7240sw_reg_write(mii, AR7240_REG_MDIO_CTRL, t); ++ err = __ar7240sw_reg_wait(mii, AR7240_REG_MDIO_CTRL, ++ AR7240_MDIO_CTRL_BUSY, 0, 5); ++ if (!err) ++ val = __ar7240sw_reg_read(mii, AR7240_REG_MDIO_CTRL); ++ mutex_unlock(®_mutex); + -+static void inline ar71xx_wdt_keepalive(void) -+{ -+ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG, ar71xx_ahb_freq * wdt_timeout); ++ return val & AR7240_MDIO_CTRL_DATA_M; +} + -+static void inline ar71xx_wdt_enable(void) ++int ar7240sw_phy_write(struct mii_bus *mii, unsigned phy_addr, ++ unsigned reg_addr, u16 reg_val) +{ -+ printk(KERN_DEBUG DRV_NAME ": enabling watchdog timer\n"); -+ ar71xx_wdt_keepalive(); -+ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG_CTRL, WDOG_CTRL_ACTION_FCR); -+} ++ u32 t; ++ int ret; + -+static void inline ar71xx_wdt_disable(void) -+{ -+ printk(KERN_DEBUG DRV_NAME ": disabling watchdog timer\n"); -+ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG_CTRL, WDOG_CTRL_ACTION_NONE); -+} -+ -+static int ar71xx_wdt_set_timeout(int val) -+{ -+ if (val < 1 || val > max_timeout) ++ if (phy_addr >= AR7240_NUM_PHYS) + return -EINVAL; + -+ wdt_timeout = val; -+ ar71xx_wdt_keepalive(); ++ mutex_lock(®_mutex); ++ t = (phy_addr << AR7240_MDIO_CTRL_PHY_ADDR_S) | ++ (reg_addr << AR7240_MDIO_CTRL_REG_ADDR_S) | ++ AR7240_MDIO_CTRL_MASTER_EN | ++ AR7240_MDIO_CTRL_BUSY | ++ AR7240_MDIO_CTRL_CMD_WRITE | ++ reg_val; + -+ printk(KERN_DEBUG DRV_NAME ": timeout=%d secs\n", wdt_timeout); ++ __ar7240sw_reg_write(mii, AR7240_REG_MDIO_CTRL, t); ++ ret = __ar7240sw_reg_wait(mii, AR7240_REG_MDIO_CTRL, ++ AR7240_MDIO_CTRL_BUSY, 0, 5); ++ mutex_unlock(®_mutex); + -+ return 0; ++ return ret; +} + -+static int ar71xx_wdt_open(struct inode *inode, struct file *file) ++static int ar7240sw_capture_stats(struct ar7240sw *as) +{ -+ if (test_and_set_bit(WDT_FLAGS_BUSY, &wdt_flags)) -+ return -EBUSY; -+ -+ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); ++ struct mii_bus *mii = as->mii_bus; ++ int ret; + -+ ar71xx_wdt_enable(); ++ /* Capture the hardware statistics for all ports */ ++ ar7240sw_reg_write(mii, AR7240_REG_MIB_FUNCTION0, ++ (AR7240_MIB_FUNC_CAPTURE << AR7240_MIB_FUNC_S)); + -+ return nonseekable_open(inode, file); ++ /* Wait for the capturing to complete. */ ++ ret = ar7240sw_reg_wait(mii, AR7240_REG_MIB_FUNCTION0, ++ AR7240_MIB_BUSY, 0, 10); ++ return ret; +} + -+static int ar71xx_wdt_release(struct inode *inode, struct file *file) ++static void ar7240sw_disable_port(struct ar7240sw *as, unsigned port) +{ -+ if (test_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags)) { -+ ar71xx_wdt_disable(); -+ } else { -+ printk(KERN_CRIT DRV_NAME ": device closed unexpectedly, " -+ "watchdog timer will not stop!\n"); -+ } -+ -+ clear_bit(WDT_FLAGS_BUSY, &wdt_flags); -+ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); -+ -+ return 0; ++ ar7240sw_reg_write(as->mii_bus, AR7240_REG_PORT_CTRL(port), ++ AR7240_PORT_CTRL_STATE_DISABLED); +} + -+static ssize_t ar71xx_wdt_write(struct file *file, const char *data, -+ size_t len, loff_t *ppos) ++static void ar7240sw_setup(struct ar7240sw *as) +{ -+ if (len) { -+ if (!nowayout) { -+ size_t i; ++ struct mii_bus *mii = as->mii_bus; + -+ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); ++ /* Enable CPU port, and disable mirror port */ ++ ar7240sw_reg_write(mii, AR7240_REG_CPU_PORT, ++ AR7240_CPU_PORT_EN | ++ (15 << AR7240_MIRROR_PORT_S)); + -+ for (i = 0; i != len; i++) { -+ char c; ++ /* Setup TAG priority mapping */ ++ ar7240sw_reg_write(mii, AR7240_REG_TAG_PRIORITY, 0xfa50); + -+ if (get_user(c, data + i)) -+ return -EFAULT; ++ /* Enable ARP frame acknowledge, aging, MAC replacing */ ++ ar7240sw_reg_write(mii, AR7240_REG_AT_CTRL, ++ 0x2b /* 5 min age time */ | ++ AR7240_AT_CTRL_AGE_EN | ++ AR7240_AT_CTRL_ARP_EN | ++ AR7240_AT_CTRL_LEARN_CHANGE); + -+ if (c == 'V') -+ set_bit(WDT_FLAGS_EXPECT_CLOSE, -+ &wdt_flags); -+ } -+ } ++ /* Enable Broadcast frames transmitted to the CPU */ ++ ar7240sw_reg_set(mii, AR7240_REG_FLOOD_MASK, ++ AR7240_FLOOD_MASK_BROAD_TO_CPU); + -+ ar71xx_wdt_keepalive(); -+ } ++ /* setup MTU */ ++ ar7240sw_reg_rmw(mii, AR7240_REG_GLOBAL_CTRL, AR7240_GLOBAL_CTRL_MTU_M, ++ 1536); + -+ return len; ++ /* setup Service TAG */ ++ ar7240sw_reg_rmw(mii, AR7240_REG_SERVICE_TAG, AR7240_SERVICE_TAG_M, 0); +} + -+static struct watchdog_info ar71xx_wdt_info = { -+ .options = WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING | -+ WDIOF_MAGICCLOSE | WDIOF_CARDRESET, -+ .firmware_version = 0, -+ .identity = "AR71XX watchdog", -+}; -+ -+static int ar71xx_wdt_ioctl(struct inode *inode, struct file *file, -+ unsigned int cmd, unsigned long arg) ++static int ar7240sw_reset(struct ar7240sw *as) +{ -+ int t; ++ struct mii_bus *mii = as->mii_bus; + int ret; ++ int i; + -+ switch (cmd) { -+ case WDIOC_GETSUPPORT: -+ ret = copy_to_user((struct watchdog_info *)arg, -+ &ar71xx_wdt_info, -+ sizeof(&ar71xx_wdt_info)) ? -EFAULT : 0; -+ break; ++ /* Set all ports to disabled state. */ ++ for (i = 0; i < AR7240_NUM_PORTS; i++) ++ ar7240sw_disable_port(as, i); + -+ case WDIOC_GETSTATUS: -+ ret = put_user(0, (int *)arg) ? -EFAULT : 0; -+ break; ++ /* Wait for transmit queues to drain. */ ++ msleep(2); + -+ case WDIOC_GETBOOTSTATUS: -+ ret = put_user(boot_status, (int *)arg) ? -EFAULT : 0; -+ break; ++ /* Reset the switch. */ ++ ar7240sw_reg_write(mii, AR7240_REG_MASK_CTRL, ++ AR7240_MASK_CTRL_SOFT_RESET); + -+ case WDIOC_KEEPALIVE: -+ ar71xx_wdt_keepalive(); -+ ret = 0; -+ break; ++ ret = ar7240sw_reg_wait(mii, AR7240_REG_MASK_CTRL, ++ AR7240_MASK_CTRL_SOFT_RESET, 0, 1000); + -+ case WDIOC_SETTIMEOUT: -+ ret = get_user(t, (int *)arg) ? -EFAULT : 0; -+ if (ret) -+ break; ++ ar7240sw_setup(as); ++ return ret; ++} + -+ ret = ar71xx_wdt_set_timeout(t); -+ if (ret) -+ break; ++static void ar7240sw_setup_port(struct ar7240sw *as, unsigned port, u8 portmask) ++{ ++ struct mii_bus *mii = as->mii_bus; ++ u32 ctrl; ++ u32 dest_ports; ++ u32 vlan; + -+ /* fallthrough */ -+ case WDIOC_GETTIMEOUT: -+ ret = put_user(wdt_timeout, (int *)arg) ? -EFAULT : 0; -+ break; ++ ctrl = AR7240_PORT_CTRL_STATE_FORWARD | AR7240_PORT_CTRL_LEARN | ++ AR7240_PORT_CTRL_SINGLE_VLAN; + -+ default: -+ ret = -ENOTTY; -+ break; ++ if (port == AR7240_PORT_CPU) { ++ ar7240sw_reg_write(mii, AR7240_REG_PORT_STATUS(port), ++ AR7240_PORT_STATUS_SPEED_1000 | ++ AR7240_PORT_STATUS_TXFLOW | ++ AR7240_PORT_STATUS_RXFLOW | ++ AR7240_PORT_STATUS_TXMAC | ++ AR7240_PORT_STATUS_RXMAC | ++ AR7240_PORT_STATUS_DUPLEX); ++ } else { ++ ar7240sw_reg_write(mii, AR7240_REG_PORT_STATUS(port), ++ AR7240_PORT_STATUS_LINK_AUTO); + } + -+ return ret; -+} ++ /* Set the default VID for this port */ ++ if (as->vlan) { ++ vlan = as->vlan_id[as->pvid[port]]; ++ vlan |= AR7240_PORT_VLAN_MODE_SECURE << ++ AR7240_PORT_VLAN_MODE_S; ++ } else { ++ vlan = port; ++ vlan |= AR7240_PORT_VLAN_MODE_PORT_ONLY << ++ AR7240_PORT_VLAN_MODE_S; ++ } + -+static const struct file_operations ar71xx_wdt_fops = { -+ .owner = THIS_MODULE, -+ .write = ar71xx_wdt_write, -+ .ioctl = ar71xx_wdt_ioctl, -+ .open = ar71xx_wdt_open, -+ .release = ar71xx_wdt_release, -+}; ++ if (as->vlan && (as->vlan_tagged & BIT(port))) { ++ ctrl |= AR7240_PORT_CTRL_VLAN_MODE_ADD << ++ AR7240_PORT_CTRL_VLAN_MODE_S; ++ } else { ++ ctrl |= AR7240_PORT_CTRL_VLAN_MODE_STRIP << ++ AR7240_PORT_CTRL_VLAN_MODE_S; ++ } + -+static struct miscdevice ar71xx_wdt_miscdev = { -+ .minor = WATCHDOG_MINOR, -+ .name = "watchdog", -+ .fops = &ar71xx_wdt_fops, -+}; ++ if (!portmask) { ++ if (port == AR7240_PORT_CPU) ++ portmask = AR7240_PORT_MASK_BUT(AR7240_PORT_CPU); ++ else ++ portmask = AR7240_PORT_MASK(AR7240_PORT_CPU); ++ } + -+static int __devinit ar71xx_wdt_probe(struct platform_device *pdev) -+{ -+ int ret; ++ /* allow the port to talk to all other ports, but exclude its ++ * own ID to prevent frames from being reflected back to the ++ * port that they came from */ ++ dest_ports = AR7240_PORT_MASK_BUT(port); + -+ max_timeout = (0xfffffffful / ar71xx_ahb_freq); -+ wdt_timeout = (max_timeout < WDT_TIMEOUT) ? max_timeout : WDT_TIMEOUT; ++ /* set default VID and and destination ports for this VLAN */ ++ vlan |= (portmask << AR7240_PORT_VLAN_DEST_PORTS_S); + -+ boot_status = -+ (ar71xx_reset_rr(AR71XX_RESET_REG_WDOG_CTRL) & WDOG_CTRL_LAST_RESET) ? -+ WDIOF_CARDRESET : 0; ++ ar7240sw_reg_write(mii, AR7240_REG_PORT_CTRL(port), ctrl); ++ ar7240sw_reg_write(mii, AR7240_REG_PORT_VLAN(port), vlan); ++} + -+ ret = misc_register(&ar71xx_wdt_miscdev); -+ if (ret) -+ goto err_out; ++static int ar7240_set_addr(struct ar7240sw *as, u8 *addr) ++{ ++ struct mii_bus *mii = as->mii_bus; ++ u32 t; + -+ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); ++ t = (addr[4] << 8) | addr[5]; ++ ar7240sw_reg_write(mii, AR7240_REG_MAC_ADDR0, t); + -+ printk(KERN_DEBUG DRV_NAME ": timeout=%d secs (max=%d)\n", -+ wdt_timeout, max_timeout); ++ t = (addr[0] << 24) | (addr[1] << 16) | (addr[2] << 8) | addr[3]; ++ ar7240sw_reg_write(mii, AR7240_REG_MAC_ADDR1, t); + + return 0; -+ -+err_out: -+ return ret; +} + -+static int __devexit ar71xx_wdt_remove(struct platform_device *pdev) ++static int ++ar7240_set_vid(struct switch_dev *dev, const struct switch_attr *attr, ++ struct switch_val *val) +{ -+ misc_deregister(&ar71xx_wdt_miscdev); ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ as->vlan_id[val->port_vlan] = val->value.i; + return 0; +} + -+static struct platform_driver ar71xx_wdt_driver = { -+ .probe = ar71xx_wdt_probe, -+ .remove = __devexit_p(ar71xx_wdt_remove), -+ .driver = { -+ .name = DRV_NAME, -+ .owner = THIS_MODULE, -+ }, -+}; -+ -+static int __init ar71xx_wdt_init(void) ++static int ++ar7240_get_vid(struct switch_dev *dev, const struct switch_attr *attr, ++ struct switch_val *val) +{ -+ return platform_driver_register(&ar71xx_wdt_driver); ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ val->value.i = as->vlan_id[val->port_vlan]; ++ return 0; +} -+module_init(ar71xx_wdt_init); + -+static void __exit ar71xx_wdt_exit(void) ++static int ++ar7240_set_pvid(struct switch_dev *dev, int port, int vlan) +{ -+ platform_driver_unregister(&ar71xx_wdt_driver); -+} -+module_exit(ar71xx_wdt_exit); ++ struct ar7240sw *as = sw_to_ar7240(dev); + -+MODULE_DESCRIPTION(DRV_DESC); -+MODULE_VERSION(DRV_VERSION); -+MODULE_AUTHOR("Gabor Juhos -- * Copyright (c) 2009 Imre Kaloz -+ * ath9k platform data defines - * -- * Permission to use, copy, modify, and/or distribute this software for any -- * purpose with or without fee is hereby granted, provided that the above -- * copyright notice and this permission notice appear in all copies. -+ * Copyright (C) 2008 Gabor Juhos - * -- * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES -- * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF -- * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR -- * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES -- * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN -- * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF -- * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. - */ - - #ifndef _LINUX_ATH9K_PLATFORM_H -@@ -23,6 +15,9 @@ - - struct ath9k_platform_data { - u16 eeprom_data[ATH9K_PLAT_EEP_MAX_WORDS]; -+ u8 *macaddr; ++ /* make sure no invalid PVIDs get set */ + -+ unsigned long quirk_wndr3700:1; - }; - - #endif /* _LINUX_ATH9K_PLATFORM_H */ -diff -Nur linux-2.6.39.orig/include/linux/gpio_buttons.h linux-2.6.39/include/linux/gpio_buttons.h ---- linux-2.6.39.orig/include/linux/gpio_buttons.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/include/linux/gpio_buttons.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,33 @@ -+/* -+ * Definitions for the GPIO buttons interface driver -+ * -+ * Copyright (C) 2007-2010 Gabor Juhos -+ * -+ * This file was based on: /include/linux/gpio_keys.h -+ * The original gpio_keys.h seems not to have a license. -+ * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. -+ * -+ */ ++ if (vlan >= dev->vlans) ++ return -EINVAL; + -+#ifndef _GPIO_BUTTONS_H_ -+#define _GPIO_BUTTONS_H_ ++ as->pvid[port] = vlan; ++ return 0; ++} + -+struct gpio_button { -+ int gpio; /* GPIO line number */ -+ int active_low; -+ char *desc; /* button description */ -+ int type; /* input event type (EV_KEY, EV_SW) */ -+ int code; /* input event code (KEY_*, SW_*) */ -+ int threshold; /* count threshold */ -+}; ++static int ++ar7240_get_pvid(struct switch_dev *dev, int port, int *vlan) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ *vlan = as->pvid[port]; ++ return 0; ++} + -+struct gpio_buttons_platform_data { -+ struct gpio_button *buttons; -+ int nbuttons; /* number of buttons */ -+ int poll_interval; /* polling interval */ -+}; ++static int ++ar7240_get_ports(struct switch_dev *dev, struct switch_val *val) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ u8 ports = as->vlan_table[val->port_vlan]; ++ int i; + -+#endif /* _GPIO_BUTTONS_H_ */ -diff -Nur linux-2.6.39.orig/include/linux/gpio_dev.h linux-2.6.39/include/linux/gpio_dev.h ---- linux-2.6.39.orig/include/linux/gpio_dev.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/include/linux/gpio_dev.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,11 @@ -+#ifndef _GPIODEV_H__ -+#define _GPIODEV_H__ ++ val->len = 0; ++ for (i = 0; i < AR7240_NUM_PORTS; i++) { ++ struct switch_port *p; + -+#define IOC_GPIODEV_MAGIC 'B' -+#define GPIO_GET _IO(IOC_GPIODEV_MAGIC, 10) -+#define GPIO_SET _IO(IOC_GPIODEV_MAGIC, 11) -+#define GPIO_CLEAR _IO(IOC_GPIODEV_MAGIC, 12) -+#define GPIO_DIR_IN _IO(IOC_GPIODEV_MAGIC, 13) -+#define GPIO_DIR_OUT _IO(IOC_GPIODEV_MAGIC, 14) ++ if (!(ports & (1 << i))) ++ continue; + -+#endif -diff -Nur linux-2.6.39.orig/include/linux/netdevice.h linux-2.6.39/include/linux/netdevice.h ---- linux-2.6.39.orig/include/linux/netdevice.h 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/include/linux/netdevice.h 2011-05-27 14:36:51.000000000 +0200 -@@ -1182,6 +1182,7 @@ - void *ax25_ptr; /* AX.25 specific data */ - struct wireless_dev *ieee80211_ptr; /* IEEE 802.11 specific data, - assign before registering */ -+ void *phy_ptr; /* PHY device specific data */ - - /* - * Cache lines mostly used on receive path (including eth_type_trans()) -diff -Nur linux-2.6.39.orig/include/linux/nxp_74hc153.h linux-2.6.39/include/linux/nxp_74hc153.h ---- linux-2.6.39.orig/include/linux/nxp_74hc153.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/include/linux/nxp_74hc153.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,24 @@ -+/* -+ * NXP 74HC153 - Dual 4-input multiplexer defines -+ * -+ * Copyright (C) 2010 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify -+ * it under the terms of the GNU General Public License version 2 as -+ * published by the Free Software Foundation. -+ */ ++ p = &val->value.ports[val->len++]; ++ p->id = i; ++ if (as->vlan_tagged & (1 << i)) ++ p->flags = (1 << SWITCH_PORT_FLAG_TAGGED); ++ else ++ p->flags = 0; ++ } ++ return 0; ++} + -+#ifndef _NXP_74HC153_H -+#define _NXP_74HC153_H ++static int ++ar7240_set_ports(struct switch_dev *dev, struct switch_val *val) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ u8 *vt = &as->vlan_table[val->port_vlan]; ++ int i, j; ++ ++ *vt = 0; ++ for (i = 0; i < val->len; i++) { ++ struct switch_port *p = &val->value.ports[i]; ++ ++ if (p->flags & (1 << SWITCH_PORT_FLAG_TAGGED)) ++ as->vlan_tagged |= (1 << p->id); ++ else { ++ as->vlan_tagged &= ~(1 << p->id); ++ as->pvid[p->id] = val->port_vlan; ++ ++ /* make sure that an untagged port does not ++ * appear in other vlans */ ++ for (j = 0; j < AR7240_MAX_VLANS; j++) { ++ if (j == val->port_vlan) ++ continue; ++ as->vlan_table[j] &= ~(1 << p->id); ++ } ++ } + -+#define NXP_74HC153_DRIVER_NAME "nxp-74hc153" ++ *vt |= 1 << p->id; ++ } ++ return 0; ++} + -+struct nxp_74hc153_platform_data { -+ unsigned gpio_base; -+ unsigned gpio_pin_s0; -+ unsigned gpio_pin_s1; -+ unsigned gpio_pin_1y; -+ unsigned gpio_pin_2y; -+}; ++static int ++ar7240_set_vlan(struct switch_dev *dev, const struct switch_attr *attr, ++ struct switch_val *val) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ as->vlan = !!val->value.i; ++ return 0; ++} + -+#endif /* _NXP_74HC153_H */ -diff -Nur linux-2.6.39.orig/include/linux/phy.h linux-2.6.39/include/linux/phy.h ---- linux-2.6.39.orig/include/linux/phy.h 2011-05-19 06:06:34.000000000 +0200 -+++ linux-2.6.39/include/linux/phy.h 2011-05-27 14:36:51.000000000 +0200 -@@ -332,6 +332,20 @@ - void (*adjust_link)(struct net_device *dev); - - void (*adjust_state)(struct net_device *dev); ++static int ++ar7240_get_vlan(struct switch_dev *dev, const struct switch_attr *attr, ++ struct switch_val *val) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ val->value.i = as->vlan; ++ return 0; ++} + -+ /* -+ * By default these point to the original functions -+ * with the same name. adding them to the phy_device -+ * allows the phy driver to override them for packet -+ * mangling if the ethernet driver supports it -+ * This is required to support some really horrible -+ * switches such as the Marvell 88E6060 -+ */ -+ int (*netif_receive_skb)(struct sk_buff *skb); -+ int (*netif_rx)(struct sk_buff *skb); + -+ /* alignment offset for packets */ -+ int pkt_align; - }; - #define to_phy_device(d) container_of(d, struct phy_device, dev) - -@@ -508,6 +522,7 @@ - void phy_stop_machine(struct phy_device *phydev); - int phy_ethtool_sset(struct phy_device *phydev, struct ethtool_cmd *cmd); - int phy_ethtool_gset(struct phy_device *phydev, struct ethtool_cmd *cmd); -+int phy_ethtool_ioctl(struct phy_device *phydev, void *useraddr); - int phy_mii_ioctl(struct phy_device *phydev, - struct ifreq *ifr, int cmd); - int phy_start_interrupts(struct phy_device *phydev); -diff -Nur linux-2.6.39.orig/include/linux/spi/vsc7385.h linux-2.6.39/include/linux/spi/vsc7385.h ---- linux-2.6.39.orig/include/linux/spi/vsc7385.h 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/include/linux/spi/vsc7385.h 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,19 @@ -+/* -+ * Platform data definition for the Vitesse VSC7385 ethernet switch driver -+ * -+ * Copyright (C) 2009 Gabor Juhos -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ */ ++static void ++ar7240_vtu_op(struct ar7240sw *as, u32 op, u32 val) ++{ ++ struct mii_bus *mii = as->mii_bus; + -+struct vsc7385_platform_data { -+ void (* reset)(void); -+ char *ucode_name; -+ struct { -+ u32 tx_ipg:5; -+ u32 bit2:1; -+ u32 clk_sel:3; -+ } mac_cfg; ++ if (ar7240sw_reg_wait(mii, AR7240_REG_VTU, AR7240_VTU_ACTIVE, 0, 5)) ++ return; ++ ++ if ((op & AR7240_VTU_OP) == AR7240_VTU_OP_LOAD) { ++ val &= AR7240_VTUDATA_MEMBER; ++ val |= AR7240_VTUDATA_VALID; ++ ar7240sw_reg_write(mii, AR7240_REG_VTU_DATA, val); ++ } ++ op |= AR7240_VTU_ACTIVE; ++ ar7240sw_reg_write(mii, AR7240_REG_VTU, op); ++} ++ ++static int ++ar7240_hw_apply(struct switch_dev *dev) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ u8 portmask[AR7240_NUM_PORTS]; ++ int i, j; ++ ++ /* flush all vlan translation unit entries */ ++ ar7240_vtu_op(as, AR7240_VTU_OP_FLUSH, 0); ++ ++ memset(portmask, 0, sizeof(portmask)); ++ if (as->vlan) { ++ /* calculate the port destination masks and load vlans ++ * into the vlan translation unit */ ++ for (j = 0; j < AR7240_MAX_VLANS; j++) { ++ u8 vp = as->vlan_table[j]; ++ ++ if (!vp) ++ continue; ++ ++ for (i = 0; i < AR7240_NUM_PORTS; i++) { ++ u8 mask = (1 << i); ++ if (vp & mask) ++ portmask[i] |= vp & ~mask; ++ } ++ ++ ar7240_vtu_op(as, ++ AR7240_VTU_OP_LOAD | ++ (as->vlan_id[j] << AR7240_VTU_VID_S), ++ as->vlan_table[j]); ++ } ++ } else { ++ /* vlan disabled: ++ * isolate all ports, but connect them to the cpu port */ ++ for (i = 0; i < AR7240_NUM_PORTS; i++) { ++ if (i == AR7240_PORT_CPU) ++ continue; ++ ++ portmask[i] = 1 << AR7240_PORT_CPU; ++ portmask[AR7240_PORT_CPU] |= (1 << i); ++ } ++ } ++ ++ /* update the port destination mask registers and tag settings */ ++ for (i = 0; i < AR7240_NUM_PORTS; i++) ++ ar7240sw_setup_port(as, i, portmask[i]); ++ ++ return 0; ++} ++ ++static int ++ar7240_reset_switch(struct switch_dev *dev) ++{ ++ struct ar7240sw *as = sw_to_ar7240(dev); ++ ar7240sw_reset(as); ++ return 0; ++} ++ ++static struct switch_attr ar7240_globals[] = { ++ { ++ .type = SWITCH_TYPE_INT, ++ .name = "enable_vlan", ++ .description = "Enable VLAN mode", ++ .set = ar7240_set_vlan, ++ .get = ar7240_get_vlan, ++ .max = 1 ++ }, +}; -diff -Nur linux-2.6.39.orig/net/dsa/ar7240.c linux-2.6.39/net/dsa/ar7240.c ---- linux-2.6.39.orig/net/dsa/ar7240.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/net/dsa/ar7240.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,736 @@ -+/* -+ * DSA driver for the built-in ethernet switch of the Atheros AR7240 SoC -+ * Copyright (c) 2010 Gabor Juhos -+ * -+ * This file was based on: -+ * net/dsa/mv88e6060.c - Driver for Marvell 88e6060 switch chips -+ * Copyright (c) 2008 Marvell Semiconductor -+ * -+ * This program is free software; you can redistribute it and/or modify it -+ * under the terms of the GNU General Public License version 2 as published -+ * by the Free Software Foundation. -+ * -+ */ + -+#include -+#include -+#include -+#include -+#include -+#include ++static struct switch_attr ar7240_port[] = { ++}; + -+#include "dsa_priv.h" ++static struct switch_attr ar7240_vlan[] = { ++ { ++ .type = SWITCH_TYPE_INT, ++ .name = "vid", ++ .description = "VLAN ID", ++ .set = ar7240_set_vid, ++ .get = ar7240_get_vid, ++ .max = 4094, ++ }, ++}; + -+#define BITM(_count) (BIT(_count) - 1) ++static const struct switch_dev_ops ar7240_ops = { ++ .attr_global = { ++ .attr = ar7240_globals, ++ .n_attr = ARRAY_SIZE(ar7240_globals), ++ }, ++ .attr_port = { ++ .attr = ar7240_port, ++ .n_attr = ARRAY_SIZE(ar7240_port), ++ }, ++ .attr_vlan = { ++ .attr = ar7240_vlan, ++ .n_attr = ARRAY_SIZE(ar7240_vlan), ++ }, ++ .get_port_pvid = ar7240_get_pvid, ++ .set_port_pvid = ar7240_set_pvid, ++ .get_vlan_ports = ar7240_get_ports, ++ .set_vlan_ports = ar7240_set_ports, ++ .apply_config = ar7240_hw_apply, ++ .reset_switch = ar7240_reset_switch, ++}; + -+#define AR7240_REG_MASK_CTRL 0x00 -+#define AR7240_MASK_CTRL_REVISION_M BITM(8) -+#define AR7240_MASK_CTRL_VERSION_M BITM(8) -+#define AR7240_MASK_CTRL_VERSION_S 8 -+#define AR7240_MASK_CTRL_SOFT_RESET BIT(31) ++static struct ar7240sw *ar7240_probe(struct ag71xx *ag) ++{ ++ struct mii_bus *mii = ag->mii_bus; ++ struct ar7240sw *as; ++ struct switch_dev *swdev; ++ u32 ctrl; ++ u16 phy_id1; ++ u16 phy_id2; ++ u8 ver; ++ int i; + -+#define AR7240_REG_MAC_ADDR0 0x20 -+#define AR7240_REG_MAC_ADDR1 0x24 ++ as = kzalloc(sizeof(*as), GFP_KERNEL); ++ if (!as) ++ return NULL; + -+#define AR7240_REG_FLOOD_MASK 0x2c -+#define AR7240_FLOOD_MASK_BROAD_TO_CPU BIT(26) ++ ar7240sw_init(as, mii); + -+#define AR7240_REG_GLOBAL_CTRL 0x30 -+#define AR7240_GLOBAL_CTRL_MTU_M BITM(12) ++ ctrl = ar7240sw_reg_read(mii, AR7240_REG_MASK_CTRL); + -+#define AR7240_REG_AT_CTRL 0x5c -+#define AR7240_AT_CTRL_ARP_EN BIT(20) ++ ver = (ctrl >> AR7240_MASK_CTRL_VERSION_S) & AR7240_MASK_CTRL_VERSION_M; ++ if (ver != 1) { ++ pr_err("%s: unsupported chip, ctrl=%08x\n", ++ ag->dev->name, ctrl); ++ return NULL; ++ } + -+#define AR7240_REG_TAG_PRIORITY 0x70 ++ phy_id1 = ar7240sw_phy_read(mii, 0, MII_PHYSID1); ++ phy_id2 = ar7240sw_phy_read(mii, 0, MII_PHYSID2); ++ if (phy_id1 != AR7240_PHY_ID1 || phy_id2 != AR7240_PHY_ID2) { ++ pr_err("%s: unknown phy id '%04x:%04x'\n", ++ ag->dev->name, phy_id1, phy_id2); ++ return NULL; ++ } + -+#define AR7240_REG_SERVICE_TAG 0x74 -+#define AR7240_SERVICE_TAG_M BITM(16) ++ swdev = &as->swdev; ++ swdev->name = "AR7240 built-in switch"; ++ swdev->ports = AR7240_NUM_PORTS; ++ swdev->cpu_port = AR7240_PORT_CPU; ++ swdev->vlans = AR7240_MAX_VLANS; ++ swdev->ops = &ar7240_ops; + -+#define AR7240_REG_CPU_PORT 0x78 -+#define AR7240_MIRROR_PORT_S 4 -+#define AR7240_CPU_PORT_EN BIT(8) ++ if (register_switch(&as->swdev, ag->dev) < 0) { ++ kfree(as); ++ return NULL; ++ } + -+#define AR7240_REG_MIB_FUNCTION0 0x80 -+#define AR7240_MIB_TIMER_M BITM(16) -+#define AR7240_MIB_AT_HALF_EN BIT(16) -+#define AR7240_MIB_BUSY BIT(17) -+#define AR7240_MIB_FUNC_S 24 -+#define AR7240_MIB_FUNC_NO_OP 0x0 -+#define AR7240_MIB_FUNC_FLUSH 0x1 -+#define AR7240_MIB_FUNC_CAPTURE 0x3 ++ pr_info("%s: Found an AR7240 built-in switch\n", ag->dev->name); + -+#define AR7240_REG_MDIO_CTRL 0x98 -+#define AR7240_MDIO_CTRL_DATA_M BITM(16) -+#define AR7240_MDIO_CTRL_REG_ADDR_S 16 -+#define AR7240_MDIO_CTRL_PHY_ADDR_S 21 -+#define AR7240_MDIO_CTRL_CMD_WRITE 0 -+#define AR7240_MDIO_CTRL_CMD_READ BIT(27) -+#define AR7240_MDIO_CTRL_MASTER_EN BIT(30) -+#define AR7240_MDIO_CTRL_BUSY BIT(31) ++ /* initialize defaults */ ++ for (i = 0; i < AR7240_MAX_VLANS; i++) ++ as->vlan_id[i] = i; + -+#define AR7240_REG_PORT_BASE(_port) (0x100 + (_port) * 0x100) ++ as->vlan_table[0] = AR7240_PORT_MASK_ALL; + -+#define AR7240_REG_PORT_STATUS(_port) (AR7240_REG_PORT_BASE((_port)) + 0x00) -+#define AR7240_PORT_STATUS_SPEED_M BITM(2) -+#define AR7240_PORT_STATUS_SPEED_10 0 -+#define AR7240_PORT_STATUS_SPEED_100 1 -+#define AR7240_PORT_STATUS_SPEED_1000 2 -+#define AR7240_PORT_STATUS_TXMAC BIT(2) -+#define AR7240_PORT_STATUS_RXMAC BIT(3) -+#define AR7240_PORT_STATUS_TXFLOW BIT(4) -+#define AR7240_PORT_STATUS_RXFLOW BIT(5) -+#define AR7240_PORT_STATUS_DUPLEX BIT(6) -+#define AR7240_PORT_STATUS_LINK_UP BIT(8) -+#define AR7240_PORT_STATUS_LINK_AUTO BIT(9) -+#define AR7240_PORT_STATUS_LINK_PAUSE BIT(10) ++ return as; ++} + -+#define AR7240_REG_PORT_CTRL(_port) (AR7240_REG_PORT_BASE((_port)) + 0x04) -+#define AR7240_PORT_CTRL_STATE_M BITM(3) -+#define AR7240_PORT_CTRL_STATE_DISABLED 0 -+#define AR7240_PORT_CTRL_STATE_BLOCK 1 -+#define AR7240_PORT_CTRL_STATE_LISTEN 2 -+#define AR7240_PORT_CTRL_STATE_LEARN 3 -+#define AR7240_PORT_CTRL_STATE_FORWARD 4 -+#define AR7240_PORT_CTRL_LEARN_LOCK BIT(7) -+#define AR7240_PORT_CTRL_VLAN_MODE_S 8 -+#define AR7240_PORT_CTRL_VLAN_MODE_KEEP 0 -+#define AR7240_PORT_CTRL_VLAN_MODE_STRIP 1 -+#define AR7240_PORT_CTRL_VLAN_MODE_ADD 2 -+#define AR7240_PORT_CTRL_VLAN_MODE_DOUBLE_TAG 3 -+#define AR7240_PORT_CTRL_IGMP_SNOOP BIT(10) -+#define AR7240_PORT_CTRL_HEADER BIT(11) -+#define AR7240_PORT_CTRL_MAC_LOOP BIT(12) -+#define AR7240_PORT_CTRL_SINGLE_VLAN BIT(13) -+#define AR7240_PORT_CTRL_LEARN BIT(14) -+#define AR7240_PORT_CTRL_DOUBLE_TAG BIT(15) -+#define AR7240_PORT_CTRL_MIRROR_TX BIT(16) -+#define AR7240_PORT_CTRL_MIRROR_RX BIT(17) ++static void link_function(struct work_struct *work) { ++ struct ag71xx *ag = container_of(work, struct ag71xx, link_work.work); ++ unsigned long flags; ++ int i; ++ int status = 0; + -+#define AR7240_REG_PORT_VLAN(_port) (AR7240_REG_PORT_BASE((_port)) + 0x08) ++ for (i = 0; i < 4; i++) { ++ int link = ar7240sw_phy_read(ag->mii_bus, i, MII_BMSR); ++ if(link & BMSR_LSTATUS) { ++ status = 1; ++ break; ++ } ++ } + -+#define AR7240_PORT_VLAN_DEFAULT_ID_S 0 -+#define AR7240_PORT_VLAN_DEST_PORTS_S 16 ++ spin_lock_irqsave(&ag->lock, flags); ++ if(status != ag->link) { ++ ag->link = status; ++ ag71xx_link_adjust(ag); ++ } ++ spin_unlock_irqrestore(&ag->lock, flags); + -+#define AR7240_REG_STATS_BASE(_port) (0x20000 + (_port) * 0x100) ++ schedule_delayed_work(&ag->link_work, HZ / 2); ++} + -+#define AR7240_STATS_RXBROAD 0x00 -+#define AR7240_STATS_RXPAUSE 0x04 -+#define AR7240_STATS_RXMULTI 0x08 -+#define AR7240_STATS_RXFCSERR 0x0c -+#define AR7240_STATS_RXALIGNERR 0x10 -+#define AR7240_STATS_RXRUNT 0x14 -+#define AR7240_STATS_RXFRAGMENT 0x18 -+#define AR7240_STATS_RX64BYTE 0x1c -+#define AR7240_STATS_RX128BYTE 0x20 -+#define AR7240_STATS_RX256BYTE 0x24 -+#define AR7240_STATS_RX512BYTE 0x28 -+#define AR7240_STATS_RX1024BYTE 0x2c -+#define AR7240_STATS_RX1518BYTE 0x30 -+#define AR7240_STATS_RXMAXBYTE 0x34 -+#define AR7240_STATS_RXTOOLONG 0x38 -+#define AR7240_STATS_RXGOODBYTE 0x3c -+#define AR7240_STATS_RXBADBYTE 0x44 -+#define AR7240_STATS_RXOVERFLOW 0x4c -+#define AR7240_STATS_FILTERED 0x50 -+#define AR7240_STATS_TXBROAD 0x54 -+#define AR7240_STATS_TXPAUSE 0x58 -+#define AR7240_STATS_TXMULTI 0x5c -+#define AR7240_STATS_TXUNDERRUN 0x60 -+#define AR7240_STATS_TX64BYTE 0x64 -+#define AR7240_STATS_TX128BYTE 0x68 -+#define AR7240_STATS_TX256BYTE 0x6c -+#define AR7240_STATS_TX512BYTE 0x70 -+#define AR7240_STATS_TX1024BYTE 0x74 -+#define AR7240_STATS_TX1518BYTE 0x78 -+#define AR7240_STATS_TXMAXBYTE 0x7c -+#define AR7240_STATS_TXOVERSIZE 0x80 -+#define AR7240_STATS_TXBYTE 0x84 -+#define AR7240_STATS_TXCOLLISION 0x8c -+#define AR7240_STATS_TXABORTCOL 0x90 -+#define AR7240_STATS_TXMULTICOL 0x94 -+#define AR7240_STATS_TXSINGLECOL 0x98 -+#define AR7240_STATS_TXEXCDEFER 0x9c -+#define AR7240_STATS_TXDEFER 0xa0 -+#define AR7240_STATS_TXLATECOL 0xa4 ++void ag71xx_ar7240_start(struct ag71xx *ag) ++{ ++ struct ar7240sw *as = ag->phy_priv; ++ ++ ar7240sw_reset(as); ++ ++ ag->speed = SPEED_1000; ++ ag->duplex = 1; ++ ++ ar7240_set_addr(as, ag->dev->dev_addr); ++ ar7240_hw_apply(&as->swdev); ++ ++ schedule_delayed_work(&ag->link_work, HZ / 10); ++} ++ ++void ag71xx_ar7240_stop(struct ag71xx *ag) ++{ ++ cancel_delayed_work_sync(&ag->link_work); ++} ++ ++int __devinit ag71xx_ar7240_init(struct ag71xx *ag) ++{ ++ struct ar7240sw *as; ++ ++ as = ar7240_probe(ag); ++ if (!as) ++ return -ENODEV; ++ ++ ag->phy_priv = as; ++ ar7240sw_reset(as); ++ ++ INIT_DELAYED_WORK(&ag->link_work, link_function); ++ ++ return 0; ++} ++ ++void ag71xx_ar7240_cleanup(struct ag71xx *ag) ++{ ++ struct ar7240sw *as = ag->phy_priv; ++ ++ if (!as) ++ return; ++ ++ unregister_switch(&as->swdev); ++ kfree(as); ++ ag->phy_priv = NULL; ++} +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar8216.c linux-2.6.39/drivers/net/ag71xx/ag71xx_ar8216.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ar8216.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_ar8216.c 2011-04-27 12:19:22.257663952 +0200 +@@ -0,0 +1,44 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * Special support for the Atheros ar8216 switch chip ++ * ++ * Copyright (C) 2009-2010 Gabor Juhos ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ag71xx.h" ++ ++#define AR8216_PACKET_TYPE_MASK 0xf ++#define AR8216_PACKET_TYPE_NORMAL 0 ++ ++#define AR8216_HEADER_LEN 2 ++ ++void ag71xx_add_ar8216_header(struct ag71xx *ag, struct sk_buff *skb) ++{ ++ skb_push(skb, AR8216_HEADER_LEN); ++ skb->data[0] = 0x10; ++ skb->data[1] = 0x80; ++} ++ ++int ag71xx_remove_ar8216_header(struct ag71xx *ag, struct sk_buff *skb, ++ int pktlen) ++{ ++ u8 type; ++ ++ type = skb->data[1] & AR8216_PACKET_TYPE_MASK; ++ switch (type) { ++ case AR8216_PACKET_TYPE_NORMAL: ++ break; ++ ++ default: ++ return -EINVAL; ++ } ++ ++ skb_pull(skb, AR8216_HEADER_LEN); ++ return 0; ++} +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_debugfs.c linux-2.6.39/drivers/net/ag71xx/ag71xx_debugfs.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_debugfs.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_debugfs.c 2011-08-06 09:32:37.298018216 +0200 +@@ -0,0 +1,280 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++ ++#include "ag71xx.h" ++ ++static struct dentry *ag71xx_debugfs_root; ++ ++static int ag71xx_debugfs_generic_open(struct inode *inode, struct file *file) ++{ ++ file->private_data = inode->i_private; ++ return 0; ++} ++ ++void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, u32 status) ++{ ++ if (status) ++ ag->debug.int_stats.total++; ++ if (status & AG71XX_INT_TX_PS) ++ ag->debug.int_stats.tx_ps++; ++ if (status & AG71XX_INT_TX_UR) ++ ag->debug.int_stats.tx_ur++; ++ if (status & AG71XX_INT_TX_BE) ++ ag->debug.int_stats.tx_be++; ++ if (status & AG71XX_INT_RX_PR) ++ ag->debug.int_stats.rx_pr++; ++ if (status & AG71XX_INT_RX_OF) ++ ag->debug.int_stats.rx_of++; ++ if (status & AG71XX_INT_RX_BE) ++ ag->debug.int_stats.rx_be++; ++} ++ ++static ssize_t read_file_int_stats(struct file *file, char __user *user_buf, ++ size_t count, loff_t *ppos) ++{ ++#define PR_INT_STAT(_label, _field) \ ++ len += snprintf(buf + len, sizeof(buf) - len, \ ++ "%20s: %10lu\n", _label, ag->debug.int_stats._field); ++ ++ struct ag71xx *ag = file->private_data; ++ char buf[256]; ++ unsigned int len = 0; ++ ++ PR_INT_STAT("TX Packet Sent", tx_ps); ++ PR_INT_STAT("TX Underrun", tx_ur); ++ PR_INT_STAT("TX Bus Error", tx_be); ++ PR_INT_STAT("RX Packet Received", rx_pr); ++ PR_INT_STAT("RX Overflow", rx_of); ++ PR_INT_STAT("RX Bus Error", rx_be); ++ len += snprintf(buf + len, sizeof(buf) - len, "\n"); ++ PR_INT_STAT("Total", total); ++ ++ return simple_read_from_buffer(user_buf, count, ppos, buf, len); ++#undef PR_INT_STAT ++} ++ ++static const struct file_operations ag71xx_fops_int_stats = { ++ .open = ag71xx_debugfs_generic_open, ++ .read = read_file_int_stats, ++ .owner = THIS_MODULE ++}; ++ ++void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, int rx, int tx) ++{ ++ struct ag71xx_napi_stats *stats = &ag->debug.napi_stats; ++ ++ if (rx) { ++ stats->rx_count++; ++ stats->rx_packets += rx; ++ if (rx <= AG71XX_NAPI_WEIGHT) ++ stats->rx[rx]++; ++ if (rx > stats->rx_packets_max) ++ stats->rx_packets_max = rx; ++ } ++ ++ if (tx) { ++ stats->tx_count++; ++ stats->tx_packets += tx; ++ if (tx <= AG71XX_NAPI_WEIGHT) ++ stats->tx[tx]++; ++ if (tx > stats->tx_packets_max) ++ stats->tx_packets_max = tx; ++ } ++} ++ ++static ssize_t read_file_napi_stats(struct file *file, char __user *user_buf, ++ size_t count, loff_t *ppos) ++{ ++ struct ag71xx *ag = file->private_data; ++ struct ag71xx_napi_stats *stats = &ag->debug.napi_stats; ++ char *buf; ++ unsigned int buflen; ++ unsigned int len = 0; ++ unsigned long rx_avg = 0; ++ unsigned long tx_avg = 0; ++ int ret; ++ int i; ++ ++ buflen = 2048; ++ buf = kmalloc(buflen, GFP_KERNEL); ++ if (!buf) ++ return -ENOMEM; ++ ++ if (stats->rx_count) ++ rx_avg = stats->rx_packets / stats->rx_count; ++ ++ if (stats->tx_count) ++ tx_avg = stats->tx_packets / stats->tx_count; ++ ++ len += snprintf(buf + len, buflen - len, "%3s %10s %10s\n", ++ "len", "rx", "tx"); ++ ++ for (i = 1; i <= AG71XX_NAPI_WEIGHT; i++) ++ len += snprintf(buf + len, buflen - len, ++ "%3d: %10lu %10lu\n", ++ i, stats->rx[i], stats->tx[i]); ++ ++ len += snprintf(buf + len, buflen - len, "\n"); ++ ++ len += snprintf(buf + len, buflen - len, "%3s: %10lu %10lu\n", ++ "sum", stats->rx_count, stats->tx_count); ++ len += snprintf(buf + len, buflen - len, "%3s: %10lu %10lu\n", ++ "avg", rx_avg, tx_avg); ++ len += snprintf(buf + len, buflen - len, "%3s: %10lu %10lu\n", ++ "max", stats->rx_packets_max, stats->tx_packets_max); ++ len += snprintf(buf + len, buflen - len, "%3s: %10lu %10lu\n", ++ "pkt", stats->rx_packets, stats->tx_packets); ++ ++ ret = simple_read_from_buffer(user_buf, count, ppos, buf, len); ++ kfree(buf); ++ ++ return ret; ++} ++ ++static const struct file_operations ag71xx_fops_napi_stats = { ++ .open = ag71xx_debugfs_generic_open, ++ .read = read_file_napi_stats, ++ .owner = THIS_MODULE ++}; ++ ++#define DESC_PRINT_LEN 64 ++ ++static ssize_t read_file_ring(struct file *file, char __user *user_buf, ++ size_t count, loff_t *ppos, ++ struct ag71xx *ag, ++ struct ag71xx_ring *ring, ++ unsigned desc_reg) ++{ ++ char *buf; ++ unsigned int buflen; ++ unsigned int len = 0; ++ unsigned long flags; ++ ssize_t ret; ++ int curr; ++ int dirty; ++ u32 desc_hw; ++ int i; ++ ++ buflen = (ring->size * DESC_PRINT_LEN); ++ buf = kmalloc(buflen, GFP_KERNEL); ++ if (!buf) ++ return -ENOMEM; ++ ++ len += snprintf(buf + len, buflen - len, ++ "Idx ... %-8s %-8s %-8s %-8s . %-10s\n", ++ "desc", "next", "data", "ctrl", "timestamp"); ++ ++ spin_lock_irqsave(&ag->lock, flags); ++ ++ curr = (ring->curr % ring->size); ++ dirty = (ring->dirty % ring->size); ++ desc_hw = ag71xx_rr(ag, desc_reg); ++ for (i = 0; i < ring->size; i++) { ++ struct ag71xx_buf *ab = &ring->buf[i]; ++ u32 desc_dma = ((u32) ring->descs_dma) + i * ring->desc_size; ++ ++ len += snprintf(buf + len, buflen - len, ++ "%3d %c%c%c %08x %08x %08x %08x %c %10lu\n", ++ i, ++ (i == curr) ? 'C' : ' ', ++ (i == dirty) ? 'D' : ' ', ++ (desc_hw == desc_dma) ? 'H' : ' ', ++ desc_dma, ++ ab->desc->next, ++ ab->desc->data, ++ ab->desc->ctrl, ++ (ab->desc->ctrl & DESC_EMPTY) ? 'E' : '*', ++ ab->timestamp); ++ } ++ ++ spin_unlock_irqrestore(&ag->lock, flags); ++ ++ ret = simple_read_from_buffer(user_buf, count, ppos, buf, len); ++ kfree(buf); ++ ++ return ret; ++} ++ ++static ssize_t read_file_tx_ring(struct file *file, char __user *user_buf, ++ size_t count, loff_t *ppos) ++{ ++ struct ag71xx *ag = file->private_data; ++ ++ return read_file_ring(file, user_buf, count, ppos, ag, &ag->tx_ring, ++ AG71XX_REG_TX_DESC); ++} ++ ++static const struct file_operations ag71xx_fops_tx_ring = { ++ .open = ag71xx_debugfs_generic_open, ++ .read = read_file_tx_ring, ++ .owner = THIS_MODULE ++}; ++ ++static ssize_t read_file_rx_ring(struct file *file, char __user *user_buf, ++ size_t count, loff_t *ppos) ++{ ++ struct ag71xx *ag = file->private_data; ++ ++ return read_file_ring(file, user_buf, count, ppos, ag, &ag->rx_ring, ++ AG71XX_REG_RX_DESC); ++} ++ ++static const struct file_operations ag71xx_fops_rx_ring = { ++ .open = ag71xx_debugfs_generic_open, ++ .read = read_file_rx_ring, ++ .owner = THIS_MODULE ++}; ++ ++void ag71xx_debugfs_exit(struct ag71xx *ag) ++{ ++ debugfs_remove_recursive(ag->debug.debugfs_dir); ++} ++ ++int ag71xx_debugfs_init(struct ag71xx *ag) ++{ ++ ag->debug.debugfs_dir = debugfs_create_dir(ag->dev->name, ++ ag71xx_debugfs_root); ++ if (!ag->debug.debugfs_dir) ++ return -ENOMEM; ++ ++ debugfs_create_file("int_stats", S_IRUGO, ag->debug.debugfs_dir, ++ ag, &ag71xx_fops_int_stats); ++ debugfs_create_file("napi_stats", S_IRUGO, ag->debug.debugfs_dir, ++ ag, &ag71xx_fops_napi_stats); ++ debugfs_create_file("tx_ring", S_IRUGO, ag->debug.debugfs_dir, ++ ag, &ag71xx_fops_tx_ring); ++ debugfs_create_file("rx_ring", S_IRUGO, ag->debug.debugfs_dir, ++ ag, &ag71xx_fops_rx_ring); ++ ++ return 0; ++} ++ ++int ag71xx_debugfs_root_init(void) ++{ ++ if (ag71xx_debugfs_root) ++ return -EBUSY; ++ ++ ag71xx_debugfs_root = debugfs_create_dir(KBUILD_MODNAME, NULL); ++ if (!ag71xx_debugfs_root) ++ return -ENOENT; ++ ++ return 0; ++} ++ ++void ag71xx_debugfs_root_exit(void) ++{ ++ debugfs_remove(ag71xx_debugfs_root); ++ ag71xx_debugfs_root = NULL; ++} +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ethtool.c linux-2.6.39/drivers/net/ag71xx/ag71xx_ethtool.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_ethtool.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_ethtool.c 2011-08-06 09:32:37.308017908 +0200 +@@ -0,0 +1,124 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ag71xx.h" ++ ++static int ag71xx_ethtool_get_settings(struct net_device *dev, ++ struct ethtool_cmd *cmd) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ struct phy_device *phydev = ag->phy_dev; ++ ++ if (!phydev) ++ return -ENODEV; ++ ++ return phy_ethtool_gset(phydev, cmd); ++} ++ ++static int ag71xx_ethtool_set_settings(struct net_device *dev, ++ struct ethtool_cmd *cmd) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ struct phy_device *phydev = ag->phy_dev; ++ ++ if (!phydev) ++ return -ENODEV; ++ ++ return phy_ethtool_sset(phydev, cmd); ++} ++ ++static void ag71xx_ethtool_get_drvinfo(struct net_device *dev, ++ struct ethtool_drvinfo *info) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ strcpy(info->driver, ag->pdev->dev.driver->name); ++ strcpy(info->version, AG71XX_DRV_VERSION); ++ strcpy(info->bus_info, dev_name(&ag->pdev->dev)); ++} ++ ++static u32 ag71xx_ethtool_get_msglevel(struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ return ag->msg_enable; ++} ++ ++static void ag71xx_ethtool_set_msglevel(struct net_device *dev, u32 msg_level) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ ag->msg_enable = msg_level; ++} ++ ++static void ag71xx_ethtool_get_ringparam(struct net_device *dev, ++ struct ethtool_ringparam *er) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ er->tx_max_pending = AG71XX_TX_RING_SIZE_MAX; ++ er->rx_max_pending = AG71XX_RX_RING_SIZE_MAX; ++ er->rx_mini_max_pending = 0; ++ er->rx_jumbo_max_pending = 0; ++ ++ er->tx_pending = ag->tx_ring.size; ++ er->rx_pending = ag->rx_ring.size; ++ er->rx_mini_pending = 0; ++ er->rx_jumbo_pending = 0; ++} ++ ++static int ag71xx_ethtool_set_ringparam(struct net_device *dev, ++ struct ethtool_ringparam *er) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ unsigned tx_size; ++ unsigned rx_size; ++ int err; ++ ++ if (er->rx_mini_pending != 0|| ++ er->rx_jumbo_pending != 0 || ++ er->rx_pending == 0 || ++ er->tx_pending == 0) ++ return -EINVAL; ++ ++ tx_size = er->tx_pending < AG71XX_TX_RING_SIZE_MAX ? ++ er->tx_pending : AG71XX_TX_RING_SIZE_MAX; ++ ++ rx_size = er->rx_pending < AG71XX_RX_RING_SIZE_MAX ? ++ er->rx_pending : AG71XX_RX_RING_SIZE_MAX; ++ ++ if (netif_running(dev)) { ++ err = dev->netdev_ops->ndo_stop(dev); ++ if (err) ++ return err; ++ } ++ ++ ag->tx_ring.size = tx_size; ++ ag->rx_ring.size = rx_size; ++ ++ if (netif_running(dev)) ++ err = dev->netdev_ops->ndo_open(dev); ++ ++ return err; ++} ++ ++struct ethtool_ops ag71xx_ethtool_ops = { ++ .set_settings = ag71xx_ethtool_set_settings, ++ .get_settings = ag71xx_ethtool_get_settings, ++ .get_drvinfo = ag71xx_ethtool_get_drvinfo, ++ .get_msglevel = ag71xx_ethtool_get_msglevel, ++ .set_msglevel = ag71xx_ethtool_set_msglevel, ++ .get_ringparam = ag71xx_ethtool_get_ringparam, ++ .set_ringparam = ag71xx_ethtool_set_ringparam, ++ .get_link = ethtool_op_get_link, ++}; +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx.h linux-2.6.39/drivers/net/ag71xx/ag71xx.h +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx.h 2011-08-22 07:40:12.160480642 +0200 +@@ -0,0 +1,518 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#ifndef __AG71XX_H ++#define __AG71XX_H ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++ ++#include ++#include ++ ++#define AG71XX_DRV_NAME "ag71xx" ++#define AG71XX_DRV_VERSION "0.5.35" ++ ++#define AG71XX_NAPI_WEIGHT 64 ++#define AG71XX_OOM_REFILL (1 + HZ/10) ++ ++#define AG71XX_INT_ERR (AG71XX_INT_RX_BE | AG71XX_INT_TX_BE) ++#define AG71XX_INT_TX (AG71XX_INT_TX_PS) ++#define AG71XX_INT_RX (AG71XX_INT_RX_PR | AG71XX_INT_RX_OF) ++ ++#define AG71XX_INT_POLL (AG71XX_INT_RX | AG71XX_INT_TX) ++#define AG71XX_INT_INIT (AG71XX_INT_ERR | AG71XX_INT_POLL) ++ ++#define AG71XX_TX_MTU_LEN 1540 ++#define AG71XX_RX_PKT_RESERVE 64 ++#define AG71XX_RX_PKT_SIZE \ ++ (AG71XX_RX_PKT_RESERVE + ETH_FRAME_LEN + ETH_FCS_LEN + VLAN_HLEN) ++ ++#define AG71XX_TX_RING_SIZE_DEFAULT 64 ++#define AG71XX_RX_RING_SIZE_DEFAULT 128 ++ ++#define AG71XX_TX_RING_SIZE_MAX 256 ++#define AG71XX_RX_RING_SIZE_MAX 256 ++ ++#ifdef CONFIG_AG71XX_DEBUG ++#define DBG(fmt, args...) printk(KERN_DEBUG fmt, ## args) ++#else ++#define DBG(fmt, args...) do {} while (0) ++#endif ++ ++#define ag71xx_assert(_cond) \ ++do { \ ++ if (_cond) \ ++ break; \ ++ printk("%s,%d: assertion failed\n", __FILE__, __LINE__); \ ++ BUG(); \ ++} while (0) ++ ++struct ag71xx_desc { ++ u32 data; ++ u32 ctrl; ++#define DESC_EMPTY BIT(31) ++#define DESC_MORE BIT(24) ++#define DESC_PKTLEN_M 0xfff ++ u32 next; ++ u32 pad; ++} __attribute__((aligned(4))); ++ ++struct ag71xx_buf { ++ struct sk_buff *skb; ++ struct ag71xx_desc *desc; ++ dma_addr_t dma_addr; ++ unsigned long timestamp; ++}; ++ ++struct ag71xx_ring { ++ struct ag71xx_buf *buf; ++ u8 *descs_cpu; ++ dma_addr_t descs_dma; ++ unsigned int desc_size; ++ unsigned int curr; ++ unsigned int dirty; ++ unsigned int size; ++}; ++ ++struct ag71xx_mdio { ++ struct mii_bus *mii_bus; ++ int mii_irq[PHY_MAX_ADDR]; ++ void __iomem *mdio_base; ++ struct ag71xx_mdio_platform_data *pdata; ++}; ++ ++struct ag71xx_int_stats { ++ unsigned long rx_pr; ++ unsigned long rx_be; ++ unsigned long rx_of; ++ unsigned long tx_ps; ++ unsigned long tx_be; ++ unsigned long tx_ur; ++ unsigned long total; ++}; ++ ++struct ag71xx_napi_stats { ++ unsigned long napi_calls; ++ unsigned long rx_count; ++ unsigned long rx_packets; ++ unsigned long rx_packets_max; ++ unsigned long tx_count; ++ unsigned long tx_packets; ++ unsigned long tx_packets_max; ++ ++ unsigned long rx[AG71XX_NAPI_WEIGHT + 1]; ++ unsigned long tx[AG71XX_NAPI_WEIGHT + 1]; ++}; ++ ++struct ag71xx_debug { ++ struct dentry *debugfs_dir; ++ ++ struct ag71xx_int_stats int_stats; ++ struct ag71xx_napi_stats napi_stats; ++}; ++ ++struct ag71xx { ++ void __iomem *mac_base; ++ void __iomem *mii_ctrl; ++ ++ spinlock_t lock; ++ struct platform_device *pdev; ++ struct net_device *dev; ++ struct napi_struct napi; ++ u32 msg_enable; ++ ++ struct ag71xx_desc *stop_desc; ++ dma_addr_t stop_desc_dma; ++ ++ struct ag71xx_ring rx_ring; ++ struct ag71xx_ring tx_ring; ++ ++ struct mii_bus *mii_bus; ++ struct phy_device *phy_dev; ++ void *phy_priv; ++ ++ unsigned int link; ++ unsigned int speed; ++ int duplex; ++ ++ struct work_struct restart_work; ++ struct delayed_work link_work; ++ struct timer_list oom_timer; ++ ++#ifdef CONFIG_AG71XX_DEBUG_FS ++ struct ag71xx_debug debug; ++#endif ++}; ++ ++extern struct ethtool_ops ag71xx_ethtool_ops; ++void ag71xx_link_adjust(struct ag71xx *ag); ++ ++int ag71xx_mdio_driver_init(void) __init; ++void ag71xx_mdio_driver_exit(void); ++ ++int ag71xx_phy_connect(struct ag71xx *ag); ++void ag71xx_phy_disconnect(struct ag71xx *ag); ++void ag71xx_phy_start(struct ag71xx *ag); ++void ag71xx_phy_stop(struct ag71xx *ag); ++ ++static inline struct ag71xx_platform_data *ag71xx_get_pdata(struct ag71xx *ag) ++{ ++ return ag->pdev->dev.platform_data; ++} ++ ++static inline int ag71xx_desc_empty(struct ag71xx_desc *desc) ++{ ++ return (desc->ctrl & DESC_EMPTY) != 0; ++} ++ ++static inline int ag71xx_desc_pktlen(struct ag71xx_desc *desc) ++{ ++ return desc->ctrl & DESC_PKTLEN_M; ++} ++ ++/* Register offsets */ ++#define AG71XX_REG_MAC_CFG1 0x0000 ++#define AG71XX_REG_MAC_CFG2 0x0004 ++#define AG71XX_REG_MAC_IPG 0x0008 ++#define AG71XX_REG_MAC_HDX 0x000c ++#define AG71XX_REG_MAC_MFL 0x0010 ++#define AG71XX_REG_MII_CFG 0x0020 ++#define AG71XX_REG_MII_CMD 0x0024 ++#define AG71XX_REG_MII_ADDR 0x0028 ++#define AG71XX_REG_MII_CTRL 0x002c ++#define AG71XX_REG_MII_STATUS 0x0030 ++#define AG71XX_REG_MII_IND 0x0034 ++#define AG71XX_REG_MAC_IFCTL 0x0038 ++#define AG71XX_REG_MAC_ADDR1 0x0040 ++#define AG71XX_REG_MAC_ADDR2 0x0044 ++#define AG71XX_REG_FIFO_CFG0 0x0048 ++#define AG71XX_REG_FIFO_CFG1 0x004c ++#define AG71XX_REG_FIFO_CFG2 0x0050 ++#define AG71XX_REG_FIFO_CFG3 0x0054 ++#define AG71XX_REG_FIFO_CFG4 0x0058 ++#define AG71XX_REG_FIFO_CFG5 0x005c ++#define AG71XX_REG_FIFO_RAM0 0x0060 ++#define AG71XX_REG_FIFO_RAM1 0x0064 ++#define AG71XX_REG_FIFO_RAM2 0x0068 ++#define AG71XX_REG_FIFO_RAM3 0x006c ++#define AG71XX_REG_FIFO_RAM4 0x0070 ++#define AG71XX_REG_FIFO_RAM5 0x0074 ++#define AG71XX_REG_FIFO_RAM6 0x0078 ++#define AG71XX_REG_FIFO_RAM7 0x007c ++ ++#define AG71XX_REG_TX_CTRL 0x0180 ++#define AG71XX_REG_TX_DESC 0x0184 ++#define AG71XX_REG_TX_STATUS 0x0188 ++#define AG71XX_REG_RX_CTRL 0x018c ++#define AG71XX_REG_RX_DESC 0x0190 ++#define AG71XX_REG_RX_STATUS 0x0194 ++#define AG71XX_REG_INT_ENABLE 0x0198 ++#define AG71XX_REG_INT_STATUS 0x019c ++ ++#define AG71XX_REG_FIFO_DEPTH 0x01a8 ++#define AG71XX_REG_RX_SM 0x01b0 ++#define AG71XX_REG_TX_SM 0x01b4 ++ ++#define MAC_CFG1_TXE BIT(0) /* Tx Enable */ ++#define MAC_CFG1_STX BIT(1) /* Synchronize Tx Enable */ ++#define MAC_CFG1_RXE BIT(2) /* Rx Enable */ ++#define MAC_CFG1_SRX BIT(3) /* Synchronize Rx Enable */ ++#define MAC_CFG1_TFC BIT(4) /* Tx Flow Control Enable */ ++#define MAC_CFG1_RFC BIT(5) /* Rx Flow Control Enable */ ++#define MAC_CFG1_LB BIT(8) /* Loopback mode */ ++#define MAC_CFG1_SR BIT(31) /* Soft Reset */ ++ ++#define MAC_CFG2_FDX BIT(0) ++#define MAC_CFG2_CRC_EN BIT(1) ++#define MAC_CFG2_PAD_CRC_EN BIT(2) ++#define MAC_CFG2_LEN_CHECK BIT(4) ++#define MAC_CFG2_HUGE_FRAME_EN BIT(5) ++#define MAC_CFG2_IF_1000 BIT(9) ++#define MAC_CFG2_IF_10_100 BIT(8) ++ ++#define FIFO_CFG0_WTM BIT(0) /* Watermark Module */ ++#define FIFO_CFG0_RXS BIT(1) /* Rx System Module */ ++#define FIFO_CFG0_RXF BIT(2) /* Rx Fabric Module */ ++#define FIFO_CFG0_TXS BIT(3) /* Tx System Module */ ++#define FIFO_CFG0_TXF BIT(4) /* Tx Fabric Module */ ++#define FIFO_CFG0_ALL (FIFO_CFG0_WTM | FIFO_CFG0_RXS | FIFO_CFG0_RXF \ ++ | FIFO_CFG0_TXS | FIFO_CFG0_TXF) ++ ++#define FIFO_CFG0_ENABLE_SHIFT 8 ++ ++#define FIFO_CFG4_DE BIT(0) /* Drop Event */ ++#define FIFO_CFG4_DV BIT(1) /* RX_DV Event */ ++#define FIFO_CFG4_FC BIT(2) /* False Carrier */ ++#define FIFO_CFG4_CE BIT(3) /* Code Error */ ++#define FIFO_CFG4_CR BIT(4) /* CRC error */ ++#define FIFO_CFG4_LM BIT(5) /* Length Mismatch */ ++#define FIFO_CFG4_LO BIT(6) /* Length out of range */ ++#define FIFO_CFG4_OK BIT(7) /* Packet is OK */ ++#define FIFO_CFG4_MC BIT(8) /* Multicast Packet */ ++#define FIFO_CFG4_BC BIT(9) /* Broadcast Packet */ ++#define FIFO_CFG4_DR BIT(10) /* Dribble */ ++#define FIFO_CFG4_LE BIT(11) /* Long Event */ ++#define FIFO_CFG4_CF BIT(12) /* Control Frame */ ++#define FIFO_CFG4_PF BIT(13) /* Pause Frame */ ++#define FIFO_CFG4_UO BIT(14) /* Unsupported Opcode */ ++#define FIFO_CFG4_VT BIT(15) /* VLAN tag detected */ ++#define FIFO_CFG4_FT BIT(16) /* Frame Truncated */ ++#define FIFO_CFG4_UC BIT(17) /* Unicast Packet */ ++ ++#define FIFO_CFG5_DE BIT(0) /* Drop Event */ ++#define FIFO_CFG5_DV BIT(1) /* RX_DV Event */ ++#define FIFO_CFG5_FC BIT(2) /* False Carrier */ ++#define FIFO_CFG5_CE BIT(3) /* Code Error */ ++#define FIFO_CFG5_LM BIT(4) /* Length Mismatch */ ++#define FIFO_CFG5_LO BIT(5) /* Length Out of Range */ ++#define FIFO_CFG5_OK BIT(6) /* Packet is OK */ ++#define FIFO_CFG5_MC BIT(7) /* Multicast Packet */ ++#define FIFO_CFG5_BC BIT(8) /* Broadcast Packet */ ++#define FIFO_CFG5_DR BIT(9) /* Dribble */ ++#define FIFO_CFG5_CF BIT(10) /* Control Frame */ ++#define FIFO_CFG5_PF BIT(11) /* Pause Frame */ ++#define FIFO_CFG5_UO BIT(12) /* Unsupported Opcode */ ++#define FIFO_CFG5_VT BIT(13) /* VLAN tag detected */ ++#define FIFO_CFG5_LE BIT(14) /* Long Event */ ++#define FIFO_CFG5_FT BIT(15) /* Frame Truncated */ ++#define FIFO_CFG5_16 BIT(16) /* unknown */ ++#define FIFO_CFG5_17 BIT(17) /* unknown */ ++#define FIFO_CFG5_SF BIT(18) /* Short Frame */ ++#define FIFO_CFG5_BM BIT(19) /* Byte Mode */ ++ ++#define AG71XX_INT_TX_PS BIT(0) ++#define AG71XX_INT_TX_UR BIT(1) ++#define AG71XX_INT_TX_BE BIT(3) ++#define AG71XX_INT_RX_PR BIT(4) ++#define AG71XX_INT_RX_OF BIT(6) ++#define AG71XX_INT_RX_BE BIT(7) ++ ++#define MAC_IFCTL_SPEED BIT(16) ++ ++#define MII_CFG_CLK_DIV_4 0 ++#define MII_CFG_CLK_DIV_6 2 ++#define MII_CFG_CLK_DIV_8 3 ++#define MII_CFG_CLK_DIV_10 4 ++#define MII_CFG_CLK_DIV_14 5 ++#define MII_CFG_CLK_DIV_20 6 ++#define MII_CFG_CLK_DIV_28 7 ++#define MII_CFG_RESET BIT(31) ++ ++#define MII_CMD_WRITE 0x0 ++#define MII_CMD_READ 0x1 ++#define MII_ADDR_SHIFT 8 ++#define MII_IND_BUSY BIT(0) ++#define MII_IND_INVALID BIT(2) ++ ++#define TX_CTRL_TXE BIT(0) /* Tx Enable */ ++ ++#define TX_STATUS_PS BIT(0) /* Packet Sent */ ++#define TX_STATUS_UR BIT(1) /* Tx Underrun */ ++#define TX_STATUS_BE BIT(3) /* Bus Error */ ++ ++#define RX_CTRL_RXE BIT(0) /* Rx Enable */ ++ ++#define RX_STATUS_PR BIT(0) /* Packet Received */ ++#define RX_STATUS_OF BIT(2) /* Rx Overflow */ ++#define RX_STATUS_BE BIT(3) /* Bus Error */ ++ ++#define MII_CTRL_IF_MASK 3 ++#define MII_CTRL_SPEED_SHIFT 4 ++#define MII_CTRL_SPEED_MASK 3 ++#define MII_CTRL_SPEED_10 0 ++#define MII_CTRL_SPEED_100 1 ++#define MII_CTRL_SPEED_1000 2 ++ ++static inline void ag71xx_check_reg_offset(struct ag71xx *ag, unsigned reg) ++{ ++ switch (reg) { ++ case AG71XX_REG_MAC_CFG1 ... AG71XX_REG_MAC_MFL: ++ case AG71XX_REG_MAC_IFCTL ... AG71XX_REG_INT_STATUS: ++ case AG71XX_REG_MII_CFG: ++ break; ++ ++ default: ++ BUG(); ++ } ++} ++ ++static inline void ag71xx_wr(struct ag71xx *ag, unsigned reg, u32 value) ++{ ++ ag71xx_check_reg_offset(ag, reg); ++ ++ __raw_writel(value, ag->mac_base + reg); ++ /* flush write */ ++ (void) __raw_readl(ag->mac_base + reg); ++} ++ ++static inline u32 ag71xx_rr(struct ag71xx *ag, unsigned reg) ++{ ++ ag71xx_check_reg_offset(ag, reg); ++ ++ return __raw_readl(ag->mac_base + reg); ++} ++ ++static inline void ag71xx_sb(struct ag71xx *ag, unsigned reg, u32 mask) ++{ ++ void __iomem *r; ++ ++ ag71xx_check_reg_offset(ag, reg); ++ ++ r = ag->mac_base + reg; ++ __raw_writel(__raw_readl(r) | mask, r); ++ /* flush write */ ++ (void)__raw_readl(r); ++} ++ ++static inline void ag71xx_cb(struct ag71xx *ag, unsigned reg, u32 mask) ++{ ++ void __iomem *r; ++ ++ ag71xx_check_reg_offset(ag, reg); ++ ++ r = ag->mac_base + reg; ++ __raw_writel(__raw_readl(r) & ~mask, r); ++ /* flush write */ ++ (void) __raw_readl(r); ++} ++ ++static inline void ag71xx_int_enable(struct ag71xx *ag, u32 ints) ++{ ++ ag71xx_sb(ag, AG71XX_REG_INT_ENABLE, ints); ++} ++ ++static inline void ag71xx_int_disable(struct ag71xx *ag, u32 ints) ++{ ++ ag71xx_cb(ag, AG71XX_REG_INT_ENABLE, ints); ++} ++ ++static inline void ag71xx_mii_ctrl_wr(struct ag71xx *ag, u32 value) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ if (pdata->is_ar724x) ++ return; ++ ++ __raw_writel(value, ag->mii_ctrl); ++ ++ /* flush write */ ++ __raw_readl(ag->mii_ctrl); ++} ++ ++static inline u32 ag71xx_mii_ctrl_rr(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ if (pdata->is_ar724x) ++ return 0xffffffff; ++ ++ return __raw_readl(ag->mii_ctrl); ++} ++ ++static inline void ag71xx_mii_ctrl_set_if(struct ag71xx *ag, ++ unsigned int mii_if) ++{ ++ u32 t; ++ ++ t = ag71xx_mii_ctrl_rr(ag); ++ t &= ~(MII_CTRL_IF_MASK); ++ t |= (mii_if & MII_CTRL_IF_MASK); ++ ag71xx_mii_ctrl_wr(ag, t); ++} ++ ++static inline void ag71xx_mii_ctrl_set_speed(struct ag71xx *ag, ++ unsigned int speed) ++{ ++ u32 t; ++ ++ t = ag71xx_mii_ctrl_rr(ag); ++ t &= ~(MII_CTRL_SPEED_MASK << MII_CTRL_SPEED_SHIFT); ++ t |= (speed & MII_CTRL_SPEED_MASK) << MII_CTRL_SPEED_SHIFT; ++ ag71xx_mii_ctrl_wr(ag, t); ++} ++ ++#ifdef CONFIG_AG71XX_AR8216_SUPPORT ++void ag71xx_add_ar8216_header(struct ag71xx *ag, struct sk_buff *skb); ++int ag71xx_remove_ar8216_header(struct ag71xx *ag, struct sk_buff *skb, ++ int pktlen); ++static inline int ag71xx_has_ar8216(struct ag71xx *ag) ++{ ++ return ag71xx_get_pdata(ag)->has_ar8216; ++} ++#else ++static inline void ag71xx_add_ar8216_header(struct ag71xx *ag, ++ struct sk_buff *skb) ++{ ++} ++ ++static inline int ag71xx_remove_ar8216_header(struct ag71xx *ag, ++ struct sk_buff *skb, ++ int pktlen) ++{ ++ return 0; ++} ++static inline int ag71xx_has_ar8216(struct ag71xx *ag) ++{ ++ return 0; ++} ++#endif ++ ++#ifdef CONFIG_AG71XX_DEBUG_FS ++int ag71xx_debugfs_root_init(void); ++void ag71xx_debugfs_root_exit(void); ++int ag71xx_debugfs_init(struct ag71xx *ag); ++void ag71xx_debugfs_exit(struct ag71xx *ag); ++void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, u32 status); ++void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, int rx, int tx); ++#else ++static inline int ag71xx_debugfs_root_init(void) { return 0; } ++static inline void ag71xx_debugfs_root_exit(void) {} ++static inline int ag71xx_debugfs_init(struct ag71xx *ag) { return 0; } ++static inline void ag71xx_debugfs_exit(struct ag71xx *ag) {} ++static inline void ag71xx_debugfs_update_int_stats(struct ag71xx *ag, ++ u32 status) {} ++static inline void ag71xx_debugfs_update_napi_stats(struct ag71xx *ag, ++ int rx, int tx) {} ++#endif /* CONFIG_AG71XX_DEBUG_FS */ ++ ++void ag71xx_ar7240_start(struct ag71xx *ag); ++void ag71xx_ar7240_stop(struct ag71xx *ag); ++int ag71xx_ar7240_init(struct ag71xx *ag); ++void ag71xx_ar7240_cleanup(struct ag71xx *ag); ++ ++int ag71xx_mdio_mii_read(struct ag71xx_mdio *am, int addr, int reg); ++void ag71xx_mdio_mii_write(struct ag71xx_mdio *am, int addr, int reg, u16 val); ++ ++u16 ar7240sw_phy_read(struct mii_bus *mii, unsigned phy_addr, ++ unsigned reg_addr); ++int ar7240sw_phy_write(struct mii_bus *mii, unsigned phy_addr, ++ unsigned reg_addr, u16 reg_val); ++ ++#endif /* _AG71XX_H */ +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_main.c linux-2.6.39/drivers/net/ag71xx/ag71xx_main.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_main.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_main.c 2011-08-22 07:40:12.160480642 +0200 +@@ -0,0 +1,1291 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ag71xx.h" ++ ++#define AG71XX_DEFAULT_MSG_ENABLE \ ++ (NETIF_MSG_DRV \ ++ | NETIF_MSG_PROBE \ ++ | NETIF_MSG_LINK \ ++ | NETIF_MSG_TIMER \ ++ | NETIF_MSG_IFDOWN \ ++ | NETIF_MSG_IFUP \ ++ | NETIF_MSG_RX_ERR \ ++ | NETIF_MSG_TX_ERR) ++ ++static int ag71xx_msg_level = -1; ++ ++module_param_named(msg_level, ag71xx_msg_level, int, 0); ++MODULE_PARM_DESC(msg_level, "Message level (-1=defaults,0=none,...,16=all)"); ++ ++static void ag71xx_dump_dma_regs(struct ag71xx *ag) ++{ ++ DBG("%s: dma_tx_ctrl=%08x, dma_tx_desc=%08x, dma_tx_status=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_TX_CTRL), ++ ag71xx_rr(ag, AG71XX_REG_TX_DESC), ++ ag71xx_rr(ag, AG71XX_REG_TX_STATUS)); ++ ++ DBG("%s: dma_rx_ctrl=%08x, dma_rx_desc=%08x, dma_rx_status=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_RX_CTRL), ++ ag71xx_rr(ag, AG71XX_REG_RX_DESC), ++ ag71xx_rr(ag, AG71XX_REG_RX_STATUS)); ++} ++ ++static void ag71xx_dump_regs(struct ag71xx *ag) ++{ ++ DBG("%s: mac_cfg1=%08x, mac_cfg2=%08x, ipg=%08x, hdx=%08x, mfl=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_MAC_CFG1), ++ ag71xx_rr(ag, AG71XX_REG_MAC_CFG2), ++ ag71xx_rr(ag, AG71XX_REG_MAC_IPG), ++ ag71xx_rr(ag, AG71XX_REG_MAC_HDX), ++ ag71xx_rr(ag, AG71XX_REG_MAC_MFL)); ++ DBG("%s: mac_ifctl=%08x, mac_addr1=%08x, mac_addr2=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL), ++ ag71xx_rr(ag, AG71XX_REG_MAC_ADDR1), ++ ag71xx_rr(ag, AG71XX_REG_MAC_ADDR2)); ++ DBG("%s: fifo_cfg0=%08x, fifo_cfg1=%08x, fifo_cfg2=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG0), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG1), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG2)); ++ DBG("%s: fifo_cfg3=%08x, fifo_cfg4=%08x, fifo_cfg5=%08x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG3), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG4), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5)); ++} ++ ++static inline void ag71xx_dump_intr(struct ag71xx *ag, char *label, u32 intr) ++{ ++ DBG("%s: %s intr=%08x %s%s%s%s%s%s\n", ++ ag->dev->name, label, intr, ++ (intr & AG71XX_INT_TX_PS) ? "TXPS " : "", ++ (intr & AG71XX_INT_TX_UR) ? "TXUR " : "", ++ (intr & AG71XX_INT_TX_BE) ? "TXBE " : "", ++ (intr & AG71XX_INT_RX_PR) ? "RXPR " : "", ++ (intr & AG71XX_INT_RX_OF) ? "RXOF " : "", ++ (intr & AG71XX_INT_RX_BE) ? "RXBE " : ""); ++} ++ ++static void ag71xx_ring_free(struct ag71xx_ring *ring) ++{ ++ kfree(ring->buf); ++ ++ if (ring->descs_cpu) ++ dma_free_coherent(NULL, ring->size * ring->desc_size, ++ ring->descs_cpu, ring->descs_dma); ++} ++ ++static int ag71xx_ring_alloc(struct ag71xx_ring *ring) ++{ ++ int err; ++ int i; ++ ++ ring->desc_size = sizeof(struct ag71xx_desc); ++ if (ring->desc_size % cache_line_size()) { ++ DBG("ag71xx: ring %p, desc size %u rounded to %u\n", ++ ring, ring->desc_size, ++ roundup(ring->desc_size, cache_line_size())); ++ ring->desc_size = roundup(ring->desc_size, cache_line_size()); ++ } ++ ++ ring->descs_cpu = dma_alloc_coherent(NULL, ring->size * ring->desc_size, ++ &ring->descs_dma, GFP_ATOMIC); ++ if (!ring->descs_cpu) { ++ err = -ENOMEM; ++ goto err; ++ } ++ ++ ++ ring->buf = kzalloc(ring->size * sizeof(*ring->buf), GFP_KERNEL); ++ if (!ring->buf) { ++ err = -ENOMEM; ++ goto err; ++ } ++ ++ for (i = 0; i < ring->size; i++) { ++ int idx = i * ring->desc_size; ++ ring->buf[i].desc = (struct ag71xx_desc *)&ring->descs_cpu[idx]; ++ DBG("ag71xx: ring %p, desc %d at %p\n", ++ ring, i, ring->buf[i].desc); ++ } ++ ++ return 0; ++ ++err: ++ return err; ++} ++ ++static void ag71xx_ring_tx_clean(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->tx_ring; ++ struct net_device *dev = ag->dev; ++ ++ while (ring->curr != ring->dirty) { ++ u32 i = ring->dirty % ring->size; ++ ++ if (!ag71xx_desc_empty(ring->buf[i].desc)) { ++ ring->buf[i].desc->ctrl = 0; ++ dev->stats.tx_errors++; ++ } ++ ++ if (ring->buf[i].skb) ++ dev_kfree_skb_any(ring->buf[i].skb); ++ ++ ring->buf[i].skb = NULL; ++ ++ ring->dirty++; ++ } ++ ++ /* flush descriptors */ ++ wmb(); ++ ++} ++ ++static void ag71xx_ring_tx_init(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->tx_ring; ++ int i; ++ ++ for (i = 0; i < ring->size; i++) { ++ ring->buf[i].desc->next = (u32) (ring->descs_dma + ++ ring->desc_size * ((i + 1) % ring->size)); ++ ++ ring->buf[i].desc->ctrl = DESC_EMPTY; ++ ring->buf[i].skb = NULL; ++ } ++ ++ /* flush descriptors */ ++ wmb(); ++ ++ ring->curr = 0; ++ ring->dirty = 0; ++} ++ ++static void ag71xx_ring_rx_clean(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->rx_ring; ++ int i; ++ ++ if (!ring->buf) ++ return; ++ ++ for (i = 0; i < ring->size; i++) ++ if (ring->buf[i].skb) { ++ dma_unmap_single(&ag->dev->dev, ring->buf[i].dma_addr, ++ AG71XX_RX_PKT_SIZE, DMA_FROM_DEVICE); ++ kfree_skb(ring->buf[i].skb); ++ } ++} ++ ++static int ag71xx_rx_reserve(struct ag71xx *ag) ++{ ++ int reserve = 0; ++ ++ if (ag71xx_get_pdata(ag)->is_ar724x) { ++ if (!ag71xx_has_ar8216(ag)) ++ reserve = 2; ++ ++ if (ag->phy_dev) ++ reserve += 4 - (ag->phy_dev->pkt_align % 4); ++ ++ reserve %= 4; ++ } ++ ++ return reserve + AG71XX_RX_PKT_RESERVE; ++} ++ ++ ++static int ag71xx_ring_rx_init(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->rx_ring; ++ unsigned int reserve = ag71xx_rx_reserve(ag); ++ unsigned int i; ++ int ret; ++ ++ ret = 0; ++ for (i = 0; i < ring->size; i++) { ++ ring->buf[i].desc->next = (u32) (ring->descs_dma + ++ ring->desc_size * ((i + 1) % ring->size)); ++ ++ DBG("ag71xx: RX desc at %p, next is %08x\n", ++ ring->buf[i].desc, ++ ring->buf[i].desc->next); ++ } ++ ++ for (i = 0; i < ring->size; i++) { ++ struct sk_buff *skb; ++ dma_addr_t dma_addr; ++ ++ skb = dev_alloc_skb(AG71XX_RX_PKT_SIZE + reserve); ++ if (!skb) { ++ ret = -ENOMEM; ++ break; ++ } ++ ++ skb->dev = ag->dev; ++ skb_reserve(skb, reserve); ++ ++ dma_addr = dma_map_single(&ag->dev->dev, skb->data, ++ AG71XX_RX_PKT_SIZE, ++ DMA_FROM_DEVICE); ++ ring->buf[i].skb = skb; ++ ring->buf[i].dma_addr = dma_addr; ++ ring->buf[i].desc->data = (u32) dma_addr; ++ ring->buf[i].desc->ctrl = DESC_EMPTY; ++ } ++ ++ /* flush descriptors */ ++ wmb(); ++ ++ ring->curr = 0; ++ ring->dirty = 0; ++ ++ return ret; ++} ++ ++static int ag71xx_ring_rx_refill(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->rx_ring; ++ unsigned int reserve = ag71xx_rx_reserve(ag); ++ unsigned int count; ++ ++ count = 0; ++ for (; ring->curr - ring->dirty > 0; ring->dirty++) { ++ unsigned int i; ++ ++ i = ring->dirty % ring->size; ++ ++ if (ring->buf[i].skb == NULL) { ++ dma_addr_t dma_addr; ++ struct sk_buff *skb; ++ ++ skb = dev_alloc_skb(AG71XX_RX_PKT_SIZE + reserve); ++ if (skb == NULL) ++ break; ++ ++ skb_reserve(skb, reserve); ++ skb->dev = ag->dev; ++ ++ dma_addr = dma_map_single(&ag->dev->dev, skb->data, ++ AG71XX_RX_PKT_SIZE, ++ DMA_FROM_DEVICE); ++ ++ ring->buf[i].skb = skb; ++ ring->buf[i].dma_addr = dma_addr; ++ ring->buf[i].desc->data = (u32) dma_addr; ++ } ++ ++ ring->buf[i].desc->ctrl = DESC_EMPTY; ++ count++; ++ } ++ ++ /* flush descriptors */ ++ wmb(); ++ ++ DBG("%s: %u rx descriptors refilled\n", ag->dev->name, count); ++ ++ return count; ++} ++ ++static int ag71xx_rings_init(struct ag71xx *ag) ++{ ++ int ret; ++ ++ ret = ag71xx_ring_alloc(&ag->tx_ring); ++ if (ret) ++ return ret; ++ ++ ag71xx_ring_tx_init(ag); ++ ++ ret = ag71xx_ring_alloc(&ag->rx_ring); ++ if (ret) ++ return ret; ++ ++ ret = ag71xx_ring_rx_init(ag); ++ return ret; ++} ++ ++static void ag71xx_rings_cleanup(struct ag71xx *ag) ++{ ++ ag71xx_ring_rx_clean(ag); ++ ag71xx_ring_free(&ag->rx_ring); ++ ++ ag71xx_ring_tx_clean(ag); ++ ag71xx_ring_free(&ag->tx_ring); ++} ++ ++static unsigned char *ag71xx_speed_str(struct ag71xx *ag) ++{ ++ switch (ag->speed) { ++ case SPEED_1000: ++ return "1000"; ++ case SPEED_100: ++ return "100"; ++ case SPEED_10: ++ return "10"; ++ } ++ ++ return "?"; ++} ++ ++static void ag71xx_hw_set_macaddr(struct ag71xx *ag, unsigned char *mac) ++{ ++ u32 t; ++ ++ t = (((u32) mac[5]) << 24) | (((u32) mac[4]) << 16) ++ | (((u32) mac[3]) << 8) | ((u32) mac[2]); ++ ++ ag71xx_wr(ag, AG71XX_REG_MAC_ADDR1, t); ++ ++ t = (((u32) mac[1]) << 24) | (((u32) mac[0]) << 16); ++ ag71xx_wr(ag, AG71XX_REG_MAC_ADDR2, t); ++} ++ ++static void ag71xx_dma_reset(struct ag71xx *ag) ++{ ++ u32 val; ++ int i; ++ ++ ag71xx_dump_dma_regs(ag); ++ ++ /* stop RX and TX */ ++ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, 0); ++ ag71xx_wr(ag, AG71XX_REG_TX_CTRL, 0); ++ ++ /* ++ * give the hardware some time to really stop all rx/tx activity ++ * clearing the descriptors too early causes random memory corruption ++ */ ++ mdelay(1); ++ ++ /* clear descriptor addresses */ ++ ag71xx_wr(ag, AG71XX_REG_TX_DESC, ag->stop_desc_dma); ++ ag71xx_wr(ag, AG71XX_REG_RX_DESC, ag->stop_desc_dma); ++ ++ /* clear pending RX/TX interrupts */ ++ for (i = 0; i < 256; i++) { ++ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_PR); ++ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_PS); ++ } ++ ++ /* clear pending errors */ ++ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_BE | RX_STATUS_OF); ++ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_BE | TX_STATUS_UR); ++ ++ val = ag71xx_rr(ag, AG71XX_REG_RX_STATUS); ++ if (val) ++ printk(KERN_ALERT "%s: unable to clear DMA Rx status: %08x\n", ++ ag->dev->name, val); ++ ++ val = ag71xx_rr(ag, AG71XX_REG_TX_STATUS); ++ ++ /* mask out reserved bits */ ++ val &= ~0xff000000; ++ ++ if (val) ++ printk(KERN_ALERT "%s: unable to clear DMA Tx status: %08x\n", ++ ag->dev->name, val); ++ ++ ag71xx_dump_dma_regs(ag); ++} ++ ++#define MAC_CFG1_INIT (MAC_CFG1_RXE | MAC_CFG1_TXE | \ ++ MAC_CFG1_SRX | MAC_CFG1_STX) ++ ++#define FIFO_CFG0_INIT (FIFO_CFG0_ALL << FIFO_CFG0_ENABLE_SHIFT) ++ ++#define FIFO_CFG4_INIT (FIFO_CFG4_DE | FIFO_CFG4_DV | FIFO_CFG4_FC | \ ++ FIFO_CFG4_CE | FIFO_CFG4_CR | FIFO_CFG4_LM | \ ++ FIFO_CFG4_LO | FIFO_CFG4_OK | FIFO_CFG4_MC | \ ++ FIFO_CFG4_BC | FIFO_CFG4_DR | FIFO_CFG4_LE | \ ++ FIFO_CFG4_CF | FIFO_CFG4_PF | FIFO_CFG4_UO | \ ++ FIFO_CFG4_VT) ++ ++#define FIFO_CFG5_INIT (FIFO_CFG5_DE | FIFO_CFG5_DV | FIFO_CFG5_FC | \ ++ FIFO_CFG5_CE | FIFO_CFG5_LO | FIFO_CFG5_OK | \ ++ FIFO_CFG5_MC | FIFO_CFG5_BC | FIFO_CFG5_DR | \ ++ FIFO_CFG5_CF | FIFO_CFG5_PF | FIFO_CFG5_VT | \ ++ FIFO_CFG5_LE | FIFO_CFG5_FT | FIFO_CFG5_16 | \ ++ FIFO_CFG5_17 | FIFO_CFG5_SF) ++ ++static void ag71xx_hw_stop(struct ag71xx *ag) ++{ ++ /* disable all interrupts and stop the rx/tx engine */ ++ ag71xx_wr(ag, AG71XX_REG_INT_ENABLE, 0); ++ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, 0); ++ ag71xx_wr(ag, AG71XX_REG_TX_CTRL, 0); ++} ++ ++static void ag71xx_hw_setup(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ /* setup MAC configuration registers */ ++ ag71xx_wr(ag, AG71XX_REG_MAC_CFG1, MAC_CFG1_INIT); ++ ++ ag71xx_sb(ag, AG71XX_REG_MAC_CFG2, ++ MAC_CFG2_PAD_CRC_EN | MAC_CFG2_LEN_CHECK); ++ ++ /* setup max frame length */ ++ ag71xx_wr(ag, AG71XX_REG_MAC_MFL, AG71XX_TX_MTU_LEN); ++ ++ /* setup MII interface type */ ++ ag71xx_mii_ctrl_set_if(ag, pdata->mii_if); ++ ++ /* setup FIFO configuration registers */ ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG0, FIFO_CFG0_INIT); ++ if (pdata->is_ar724x) { ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG1, pdata->fifo_cfg1); ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG2, pdata->fifo_cfg2); ++ } else { ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG1, 0x0fff0000); ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG2, 0x00001fff); ++ } ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG4, FIFO_CFG4_INIT); ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG5, FIFO_CFG5_INIT); ++} ++ ++static void ag71xx_hw_init(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ u32 reset_mask = pdata->reset_bit; ++ ++ ag71xx_hw_stop(ag); ++ ++ if (pdata->is_ar724x) { ++ u32 reset_phy = reset_mask; ++ ++ reset_phy &= RESET_MODULE_GE0_PHY | RESET_MODULE_GE1_PHY; ++ reset_mask &= ~(RESET_MODULE_GE0_PHY | RESET_MODULE_GE1_PHY); ++ ++ ar71xx_device_stop(reset_phy); ++ mdelay(50); ++ ar71xx_device_start(reset_phy); ++ mdelay(200); ++ } ++ ++ ag71xx_sb(ag, AG71XX_REG_MAC_CFG1, MAC_CFG1_SR); ++ udelay(20); ++ ++ ar71xx_device_stop(reset_mask); ++ mdelay(100); ++ ar71xx_device_start(reset_mask); ++ mdelay(200); ++ ++ ag71xx_hw_setup(ag); ++ ++ ag71xx_dma_reset(ag); ++} ++ ++static void ag71xx_fast_reset(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ struct net_device *dev = ag->dev; ++ u32 reset_mask = pdata->reset_bit; ++ u32 rx_ds, tx_ds; ++ u32 mii_reg; ++ ++ reset_mask &= RESET_MODULE_GE0_MAC | RESET_MODULE_GE1_MAC; ++ ++ mii_reg = ag71xx_rr(ag, AG71XX_REG_MII_CFG); ++ rx_ds = ag71xx_rr(ag, AG71XX_REG_RX_DESC); ++ tx_ds = ag71xx_rr(ag, AG71XX_REG_TX_DESC); ++ ++ ar71xx_device_stop(reset_mask); ++ udelay(10); ++ ar71xx_device_start(reset_mask); ++ udelay(10); ++ ++ ag71xx_dma_reset(ag); ++ ag71xx_hw_setup(ag); ++ ++ ag71xx_wr(ag, AG71XX_REG_RX_DESC, rx_ds); ++ ag71xx_wr(ag, AG71XX_REG_TX_DESC, tx_ds); ++ ag71xx_wr(ag, AG71XX_REG_MII_CFG, mii_reg); ++ ++ ag71xx_hw_set_macaddr(ag, dev->dev_addr); ++} ++ ++static void ag71xx_hw_start(struct ag71xx *ag) ++{ ++ /* start RX engine */ ++ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, RX_CTRL_RXE); ++ ++ /* enable interrupts */ ++ ag71xx_wr(ag, AG71XX_REG_INT_ENABLE, AG71XX_INT_INIT); ++} ++ ++void ag71xx_link_adjust(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ u32 cfg2; ++ u32 ifctl; ++ u32 fifo5; ++ u32 mii_speed; ++ ++ if (!ag->link) { ++ ag71xx_hw_stop(ag); ++ netif_carrier_off(ag->dev); ++ if (netif_msg_link(ag)) ++ printk(KERN_INFO "%s: link down\n", ag->dev->name); ++ return; ++ } ++ ++ if (pdata->is_ar724x) ++ ag71xx_fast_reset(ag); ++ ++ cfg2 = ag71xx_rr(ag, AG71XX_REG_MAC_CFG2); ++ cfg2 &= ~(MAC_CFG2_IF_1000 | MAC_CFG2_IF_10_100 | MAC_CFG2_FDX); ++ cfg2 |= (ag->duplex) ? MAC_CFG2_FDX : 0; ++ ++ ifctl = ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL); ++ ifctl &= ~(MAC_IFCTL_SPEED); ++ ++ fifo5 = ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5); ++ fifo5 &= ~FIFO_CFG5_BM; ++ ++ switch (ag->speed) { ++ case SPEED_1000: ++ mii_speed = MII_CTRL_SPEED_1000; ++ cfg2 |= MAC_CFG2_IF_1000; ++ fifo5 |= FIFO_CFG5_BM; ++ break; ++ case SPEED_100: ++ mii_speed = MII_CTRL_SPEED_100; ++ cfg2 |= MAC_CFG2_IF_10_100; ++ ifctl |= MAC_IFCTL_SPEED; ++ break; ++ case SPEED_10: ++ mii_speed = MII_CTRL_SPEED_10; ++ cfg2 |= MAC_CFG2_IF_10_100; ++ break; ++ default: ++ BUG(); ++ return; ++ } ++ ++ if (pdata->is_ar91xx) ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, 0x00780fff); ++ else if (pdata->is_ar724x) ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, pdata->fifo_cfg3); ++ else ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG3, 0x008001ff); ++ ++ if (pdata->set_pll) ++ pdata->set_pll(ag->speed); ++ ++ ag71xx_mii_ctrl_set_speed(ag, mii_speed); ++ ++ ag71xx_wr(ag, AG71XX_REG_MAC_CFG2, cfg2); ++ ag71xx_wr(ag, AG71XX_REG_FIFO_CFG5, fifo5); ++ ag71xx_wr(ag, AG71XX_REG_MAC_IFCTL, ifctl); ++ ag71xx_hw_start(ag); ++ ++ netif_carrier_on(ag->dev); ++ if (netif_msg_link(ag)) ++ printk(KERN_INFO "%s: link up (%sMbps/%s duplex)\n", ++ ag->dev->name, ++ ag71xx_speed_str(ag), ++ (DUPLEX_FULL == ag->duplex) ? "Full" : "Half"); ++ ++ DBG("%s: fifo_cfg0=%#x, fifo_cfg1=%#x, fifo_cfg2=%#x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG0), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG1), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG2)); ++ ++ DBG("%s: fifo_cfg3=%#x, fifo_cfg4=%#x, fifo_cfg5=%#x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG3), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG4), ++ ag71xx_rr(ag, AG71XX_REG_FIFO_CFG5)); ++ ++ DBG("%s: mac_cfg2=%#x, mac_ifctl=%#x, mii_ctrl=%#x\n", ++ ag->dev->name, ++ ag71xx_rr(ag, AG71XX_REG_MAC_CFG2), ++ ag71xx_rr(ag, AG71XX_REG_MAC_IFCTL), ++ ag71xx_mii_ctrl_rr(ag)); ++} ++ ++static int ag71xx_open(struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ int ret; ++ ++ ret = ag71xx_rings_init(ag); ++ if (ret) ++ goto err; ++ ++ napi_enable(&ag->napi); ++ ++ netif_carrier_off(dev); ++ ag71xx_phy_start(ag); ++ ++ ag71xx_wr(ag, AG71XX_REG_TX_DESC, ag->tx_ring.descs_dma); ++ ag71xx_wr(ag, AG71XX_REG_RX_DESC, ag->rx_ring.descs_dma); ++ ++ ag71xx_hw_set_macaddr(ag, dev->dev_addr); ++ ++ netif_start_queue(dev); ++ ++ return 0; ++ ++err: ++ ag71xx_rings_cleanup(ag); ++ return ret; ++} ++ ++static int ag71xx_stop(struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ unsigned long flags; ++ ++ netif_carrier_off(dev); ++ ag71xx_phy_stop(ag); ++ ++ spin_lock_irqsave(&ag->lock, flags); ++ ++ netif_stop_queue(dev); ++ ++ ag71xx_hw_stop(ag); ++ ag71xx_dma_reset(ag); ++ ++ napi_disable(&ag->napi); ++ del_timer_sync(&ag->oom_timer); ++ ++ spin_unlock_irqrestore(&ag->lock, flags); ++ ++ ag71xx_rings_cleanup(ag); ++ ++ return 0; ++} ++ ++static netdev_tx_t ag71xx_hard_start_xmit(struct sk_buff *skb, ++ struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ struct ag71xx_ring *ring = &ag->tx_ring; ++ struct ag71xx_desc *desc; ++ dma_addr_t dma_addr; ++ int i; ++ ++ i = ring->curr % ring->size; ++ desc = ring->buf[i].desc; ++ ++ if (!ag71xx_desc_empty(desc)) ++ goto err_drop; ++ ++ if (ag71xx_has_ar8216(ag)) ++ ag71xx_add_ar8216_header(ag, skb); ++ ++ if (skb->len <= 0) { ++ DBG("%s: packet len is too small\n", ag->dev->name); ++ goto err_drop; ++ } ++ ++ dma_addr = dma_map_single(&dev->dev, skb->data, skb->len, ++ DMA_TO_DEVICE); ++ ++ ring->buf[i].skb = skb; ++ ring->buf[i].timestamp = jiffies; ++ ++ /* setup descriptor fields */ ++ desc->data = (u32) dma_addr; ++ desc->ctrl = (skb->len & DESC_PKTLEN_M); ++ ++ /* flush descriptor */ ++ wmb(); ++ ++ ring->curr++; ++ if (ring->curr == (ring->dirty + ring->size)) { ++ DBG("%s: tx queue full\n", ag->dev->name); ++ netif_stop_queue(dev); ++ } ++ ++ DBG("%s: packet injected into TX queue\n", ag->dev->name); ++ ++ /* enable TX engine */ ++ ag71xx_wr(ag, AG71XX_REG_TX_CTRL, TX_CTRL_TXE); ++ ++ return NETDEV_TX_OK; ++ ++err_drop: ++ dev->stats.tx_dropped++; ++ ++ dev_kfree_skb(skb); ++ return NETDEV_TX_OK; ++} ++ ++static int ag71xx_do_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ int ret; ++ ++ switch (cmd) { ++ case SIOCETHTOOL: ++ if (ag->phy_dev == NULL) ++ break; ++ ++ spin_lock_irq(&ag->lock); ++ ret = phy_ethtool_ioctl(ag->phy_dev, (void *) ifr->ifr_data); ++ spin_unlock_irq(&ag->lock); ++ return ret; ++ ++ case SIOCSIFHWADDR: ++ if (copy_from_user ++ (dev->dev_addr, ifr->ifr_data, sizeof(dev->dev_addr))) ++ return -EFAULT; ++ return 0; ++ ++ case SIOCGIFHWADDR: ++ if (copy_to_user ++ (ifr->ifr_data, dev->dev_addr, sizeof(dev->dev_addr))) ++ return -EFAULT; ++ return 0; ++ ++ case SIOCGMIIPHY: ++ case SIOCGMIIREG: ++ case SIOCSMIIREG: ++ if (ag->phy_dev == NULL) ++ break; ++ ++ return phy_mii_ioctl(ag->phy_dev, ifr, cmd); ++ ++ default: ++ break; ++ } ++ ++ return -EOPNOTSUPP; ++} ++ ++static void ag71xx_oom_timer_handler(unsigned long data) ++{ ++ struct net_device *dev = (struct net_device *) data; ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ napi_schedule(&ag->napi); ++} ++ ++static void ag71xx_tx_timeout(struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ if (netif_msg_tx_err(ag)) ++ printk(KERN_DEBUG "%s: tx timeout\n", ag->dev->name); ++ ++ schedule_work(&ag->restart_work); ++} ++ ++static void ag71xx_restart_work_func(struct work_struct *work) ++{ ++ struct ag71xx *ag = container_of(work, struct ag71xx, restart_work); ++ ++ if (ag71xx_get_pdata(ag)->is_ar724x) { ++ ag->link = 0; ++ ag71xx_link_adjust(ag); ++ return; ++ } ++ ++ ag71xx_stop(ag->dev); ++ ag71xx_open(ag->dev); ++} ++ ++static bool ag71xx_check_dma_stuck(struct ag71xx *ag, unsigned long timestamp) ++{ ++ u32 rx_sm, tx_sm, rx_fd; ++ ++ if (likely(time_before(jiffies, timestamp + HZ/10))) ++ return false; ++ ++ if (!netif_carrier_ok(ag->dev)) ++ return false; ++ ++ rx_sm = ag71xx_rr(ag, AG71XX_REG_RX_SM); ++ if ((rx_sm & 0x7) == 0x3 && ((rx_sm >> 4) & 0x7) == 0x6) ++ return true; ++ ++ tx_sm = ag71xx_rr(ag, AG71XX_REG_TX_SM); ++ rx_fd = ag71xx_rr(ag, AG71XX_REG_FIFO_DEPTH); ++ if (((tx_sm >> 4) & 0x7) == 0 && ((rx_sm & 0x7) == 0) && ++ ((rx_sm >> 4) & 0x7) == 0 && rx_fd == 0) ++ return true; ++ ++ return false; ++} ++ ++static int ag71xx_tx_packets(struct ag71xx *ag) ++{ ++ struct ag71xx_ring *ring = &ag->tx_ring; ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ int sent; ++ ++ DBG("%s: processing TX ring\n", ag->dev->name); ++ ++ sent = 0; ++ while (ring->dirty != ring->curr) { ++ unsigned int i = ring->dirty % ring->size; ++ struct ag71xx_desc *desc = ring->buf[i].desc; ++ struct sk_buff *skb = ring->buf[i].skb; ++ ++ if (!ag71xx_desc_empty(desc)) { ++ if (pdata->is_ar7240 && ++ ag71xx_check_dma_stuck(ag, ring->buf[i].timestamp)) ++ schedule_work(&ag->restart_work); ++ break; ++ } ++ ++ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_PS); ++ ++ ag->dev->stats.tx_bytes += skb->len; ++ ag->dev->stats.tx_packets++; ++ ++ dev_kfree_skb_any(skb); ++ ring->buf[i].skb = NULL; ++ ++ ring->dirty++; ++ sent++; ++ } ++ ++ DBG("%s: %d packets sent out\n", ag->dev->name, sent); ++ ++ if ((ring->curr - ring->dirty) < (ring->size * 3) / 4) ++ netif_wake_queue(ag->dev); ++ ++ return sent; ++} ++ ++static int ag71xx_rx_packets(struct ag71xx *ag, int limit) ++{ ++ struct net_device *dev = ag->dev; ++ struct ag71xx_ring *ring = &ag->rx_ring; ++ int done = 0; ++ ++ DBG("%s: rx packets, limit=%d, curr=%u, dirty=%u\n", ++ dev->name, limit, ring->curr, ring->dirty); ++ ++ while (done < limit) { ++ unsigned int i = ring->curr % ring->size; ++ struct ag71xx_desc *desc = ring->buf[i].desc; ++ struct sk_buff *skb; ++ int pktlen; ++ int err = 0; ++ ++ if (ag71xx_desc_empty(desc)) ++ break; ++ ++ if ((ring->dirty + ring->size) == ring->curr) { ++ ag71xx_assert(0); ++ break; ++ } ++ ++ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_PR); ++ ++ skb = ring->buf[i].skb; ++ pktlen = ag71xx_desc_pktlen(desc); ++ pktlen -= ETH_FCS_LEN; ++ ++ dma_unmap_single(&dev->dev, ring->buf[i].dma_addr, ++ AG71XX_RX_PKT_SIZE, DMA_FROM_DEVICE); ++ ++ dev->last_rx = jiffies; ++ dev->stats.rx_packets++; ++ dev->stats.rx_bytes += pktlen; ++ ++ skb_put(skb, pktlen); ++ if (ag71xx_has_ar8216(ag)) ++ err = ag71xx_remove_ar8216_header(ag, skb, pktlen); ++ ++ if (err) { ++ dev->stats.rx_dropped++; ++ kfree_skb(skb); ++ } else { ++ skb->dev = dev; ++ skb->ip_summed = CHECKSUM_NONE; ++ if (ag->phy_dev) { ++ ag->phy_dev->netif_receive_skb(skb); ++ } else { ++ skb->protocol = eth_type_trans(skb, dev); ++ netif_receive_skb(skb); ++ } ++ } ++ ++ ring->buf[i].skb = NULL; ++ done++; ++ ++ ring->curr++; ++ } ++ ++ ag71xx_ring_rx_refill(ag); ++ ++ DBG("%s: rx finish, curr=%u, dirty=%u, done=%d\n", ++ dev->name, ring->curr, ring->dirty, done); ++ ++ return done; ++} ++ ++static int ag71xx_poll(struct napi_struct *napi, int limit) ++{ ++ struct ag71xx *ag = container_of(napi, struct ag71xx, napi); ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ struct net_device *dev = ag->dev; ++ struct ag71xx_ring *rx_ring; ++ unsigned long flags; ++ u32 status; ++ int tx_done; ++ int rx_done; ++ ++ pdata->ddr_flush(); ++ tx_done = ag71xx_tx_packets(ag); ++ ++ DBG("%s: processing RX ring\n", dev->name); ++ rx_done = ag71xx_rx_packets(ag, limit); ++ ++ ag71xx_debugfs_update_napi_stats(ag, rx_done, tx_done); ++ ++ rx_ring = &ag->rx_ring; ++ if (rx_ring->buf[rx_ring->dirty % rx_ring->size].skb == NULL) ++ goto oom; ++ ++ status = ag71xx_rr(ag, AG71XX_REG_RX_STATUS); ++ if (unlikely(status & RX_STATUS_OF)) { ++ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_OF); ++ dev->stats.rx_fifo_errors++; ++ ++ /* restart RX */ ++ ag71xx_wr(ag, AG71XX_REG_RX_CTRL, RX_CTRL_RXE); ++ } ++ ++ if (rx_done < limit) { ++ if (status & RX_STATUS_PR) ++ goto more; ++ ++ status = ag71xx_rr(ag, AG71XX_REG_TX_STATUS); ++ if (status & TX_STATUS_PS) ++ goto more; ++ ++ DBG("%s: disable polling mode, rx=%d, tx=%d,limit=%d\n", ++ dev->name, rx_done, tx_done, limit); ++ ++ napi_complete(napi); ++ ++ /* enable interrupts */ ++ spin_lock_irqsave(&ag->lock, flags); ++ ag71xx_int_enable(ag, AG71XX_INT_POLL); ++ spin_unlock_irqrestore(&ag->lock, flags); ++ return rx_done; ++ } ++ ++more: ++ DBG("%s: stay in polling mode, rx=%d, tx=%d, limit=%d\n", ++ dev->name, rx_done, tx_done, limit); ++ return rx_done; ++ ++oom: ++ if (netif_msg_rx_err(ag)) ++ printk(KERN_DEBUG "%s: out of memory\n", dev->name); ++ ++ mod_timer(&ag->oom_timer, jiffies + AG71XX_OOM_REFILL); ++ napi_complete(napi); ++ return 0; ++} ++ ++static irqreturn_t ag71xx_interrupt(int irq, void *dev_id) ++{ ++ struct net_device *dev = dev_id; ++ struct ag71xx *ag = netdev_priv(dev); ++ u32 status; ++ ++ status = ag71xx_rr(ag, AG71XX_REG_INT_STATUS); ++ ag71xx_dump_intr(ag, "raw", status); ++ ++ if (unlikely(!status)) ++ return IRQ_NONE; ++ ++ if (unlikely(status & AG71XX_INT_ERR)) { ++ if (status & AG71XX_INT_TX_BE) { ++ ag71xx_wr(ag, AG71XX_REG_TX_STATUS, TX_STATUS_BE); ++ dev_err(&dev->dev, "TX BUS error\n"); ++ } ++ if (status & AG71XX_INT_RX_BE) { ++ ag71xx_wr(ag, AG71XX_REG_RX_STATUS, RX_STATUS_BE); ++ dev_err(&dev->dev, "RX BUS error\n"); ++ } ++ } ++ ++ if (likely(status & AG71XX_INT_POLL)) { ++ ag71xx_int_disable(ag, AG71XX_INT_POLL); ++ DBG("%s: enable polling mode\n", dev->name); ++ napi_schedule(&ag->napi); ++ } ++ ++ ag71xx_debugfs_update_int_stats(ag, status); ++ ++ return IRQ_HANDLED; ++} ++ ++static void ag71xx_set_multicast_list(struct net_device *dev) ++{ ++ /* TODO */ ++} ++ ++#ifdef CONFIG_NET_POLL_CONTROLLER ++/* ++ * Polling 'interrupt' - used by things like netconsole to send skbs ++ * without having to re-enable interrupts. It's not called while ++ * the interrupt routine is executing. ++ */ ++static void ag71xx_netpoll(struct net_device *dev) ++{ ++ disable_irq(dev->irq); ++ ag71xx_interrupt(dev->irq, dev); ++ enable_irq(dev->irq); ++} ++#endif ++ ++static const struct net_device_ops ag71xx_netdev_ops = { ++ .ndo_open = ag71xx_open, ++ .ndo_stop = ag71xx_stop, ++ .ndo_start_xmit = ag71xx_hard_start_xmit, ++ .ndo_set_multicast_list = ag71xx_set_multicast_list, ++ .ndo_do_ioctl = ag71xx_do_ioctl, ++ .ndo_tx_timeout = ag71xx_tx_timeout, ++ .ndo_change_mtu = eth_change_mtu, ++ .ndo_set_mac_address = eth_mac_addr, ++ .ndo_validate_addr = eth_validate_addr, ++#ifdef CONFIG_NET_POLL_CONTROLLER ++ .ndo_poll_controller = ag71xx_netpoll, ++#endif ++}; ++ ++static int __devinit ag71xx_probe(struct platform_device *pdev) ++{ ++ struct net_device *dev; ++ struct resource *res; ++ struct ag71xx *ag; ++ struct ag71xx_platform_data *pdata; ++ int err; ++ ++ pdata = pdev->dev.platform_data; ++ if (!pdata) { ++ dev_err(&pdev->dev, "no platform data specified\n"); ++ err = -ENXIO; ++ goto err_out; ++ } ++ ++ if (pdata->mii_bus_dev == NULL) { ++ dev_err(&pdev->dev, "no MII bus device specified\n"); ++ err = -EINVAL; ++ goto err_out; ++ } ++ ++ dev = alloc_etherdev(sizeof(*ag)); ++ if (!dev) { ++ dev_err(&pdev->dev, "alloc_etherdev failed\n"); ++ err = -ENOMEM; ++ goto err_out; ++ } ++ ++ SET_NETDEV_DEV(dev, &pdev->dev); ++ ++ ag = netdev_priv(dev); ++ ag->pdev = pdev; ++ ag->dev = dev; ++ ag->msg_enable = netif_msg_init(ag71xx_msg_level, ++ AG71XX_DEFAULT_MSG_ENABLE); ++ spin_lock_init(&ag->lock); ++ ++ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "mac_base"); ++ if (!res) { ++ dev_err(&pdev->dev, "no mac_base resource found\n"); ++ err = -ENXIO; ++ goto err_out; ++ } ++ ++ ag->mac_base = ioremap_nocache(res->start, res->end - res->start + 1); ++ if (!ag->mac_base) { ++ dev_err(&pdev->dev, "unable to ioremap mac_base\n"); ++ err = -ENOMEM; ++ goto err_free_dev; ++ } ++ ++ res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "mii_ctrl"); ++ if (!res) { ++ dev_err(&pdev->dev, "no mii_ctrl resource found\n"); ++ err = -ENXIO; ++ goto err_unmap_base; ++ } ++ ++ ag->mii_ctrl = ioremap_nocache(res->start, res->end - res->start + 1); ++ if (!ag->mii_ctrl) { ++ dev_err(&pdev->dev, "unable to ioremap mii_ctrl\n"); ++ err = -ENOMEM; ++ goto err_unmap_base; ++ } ++ ++ dev->irq = platform_get_irq(pdev, 0); ++ err = request_irq(dev->irq, ag71xx_interrupt, ++ IRQF_DISABLED, ++ dev->name, dev); ++ if (err) { ++ dev_err(&pdev->dev, "unable to request IRQ %d\n", dev->irq); ++ goto err_unmap_mii_ctrl; ++ } ++ ++ dev->base_addr = (unsigned long)ag->mac_base; ++ dev->netdev_ops = &ag71xx_netdev_ops; ++ dev->ethtool_ops = &ag71xx_ethtool_ops; ++ ++ INIT_WORK(&ag->restart_work, ag71xx_restart_work_func); ++ ++ init_timer(&ag->oom_timer); ++ ag->oom_timer.data = (unsigned long) dev; ++ ag->oom_timer.function = ag71xx_oom_timer_handler; ++ ++ ag->tx_ring.size = AG71XX_TX_RING_SIZE_DEFAULT; ++ ag->rx_ring.size = AG71XX_RX_RING_SIZE_DEFAULT; ++ ++ ag->stop_desc = dma_alloc_coherent(NULL, ++ sizeof(struct ag71xx_desc), &ag->stop_desc_dma, GFP_KERNEL); ++ ++ if (!ag->stop_desc) ++ goto err_free_irq; ++ ++ ag->stop_desc->data = 0; ++ ag->stop_desc->ctrl = 0; ++ ag->stop_desc->next = (u32) ag->stop_desc_dma; ++ ++ memcpy(dev->dev_addr, pdata->mac_addr, ETH_ALEN); ++ ++ netif_napi_add(dev, &ag->napi, ag71xx_poll, AG71XX_NAPI_WEIGHT); ++ ++ err = register_netdev(dev); ++ if (err) { ++ dev_err(&pdev->dev, "unable to register net device\n"); ++ goto err_free_desc; ++ } ++ ++ printk(KERN_INFO "%s: Atheros AG71xx at 0x%08lx, irq %d\n", ++ dev->name, dev->base_addr, dev->irq); ++ ++ ag71xx_dump_regs(ag); ++ ++ ag71xx_hw_init(ag); ++ ++ ag71xx_dump_regs(ag); ++ ++ err = ag71xx_phy_connect(ag); ++ if (err) ++ goto err_unregister_netdev; ++ ++ err = ag71xx_debugfs_init(ag); ++ if (err) ++ goto err_phy_disconnect; ++ ++ platform_set_drvdata(pdev, dev); ++ ++ return 0; ++ ++err_phy_disconnect: ++ ag71xx_phy_disconnect(ag); ++err_unregister_netdev: ++ unregister_netdev(dev); ++err_free_desc: ++ dma_free_coherent(NULL, sizeof(struct ag71xx_desc), ag->stop_desc, ++ ag->stop_desc_dma); ++err_free_irq: ++ free_irq(dev->irq, dev); ++err_unmap_mii_ctrl: ++ iounmap(ag->mii_ctrl); ++err_unmap_base: ++ iounmap(ag->mac_base); ++err_free_dev: ++ kfree(dev); ++err_out: ++ platform_set_drvdata(pdev, NULL); ++ return err; ++} ++ ++static int __devexit ag71xx_remove(struct platform_device *pdev) ++{ ++ struct net_device *dev = platform_get_drvdata(pdev); ++ ++ if (dev) { ++ struct ag71xx *ag = netdev_priv(dev); ++ ++ ag71xx_debugfs_exit(ag); ++ ag71xx_phy_disconnect(ag); ++ unregister_netdev(dev); ++ free_irq(dev->irq, dev); ++ iounmap(ag->mii_ctrl); ++ iounmap(ag->mac_base); ++ kfree(dev); ++ platform_set_drvdata(pdev, NULL); ++ } ++ ++ return 0; ++} ++ ++static struct platform_driver ag71xx_driver = { ++ .probe = ag71xx_probe, ++ .remove = __exit_p(ag71xx_remove), ++ .driver = { ++ .name = AG71XX_DRV_NAME, ++ } ++}; ++ ++static int __init ag71xx_module_init(void) ++{ ++ int ret; ++ ++ ret = ag71xx_debugfs_root_init(); ++ if (ret) ++ goto err_out; ++ ++ ret = ag71xx_mdio_driver_init(); ++ if (ret) ++ goto err_debugfs_exit; ++ ++ ret = platform_driver_register(&ag71xx_driver); ++ if (ret) ++ goto err_mdio_exit; ++ ++ return 0; ++ ++err_mdio_exit: ++ ag71xx_mdio_driver_exit(); ++err_debugfs_exit: ++ ag71xx_debugfs_root_exit(); ++err_out: ++ return ret; ++} ++ ++static void __exit ag71xx_module_exit(void) ++{ ++ platform_driver_unregister(&ag71xx_driver); ++ ag71xx_mdio_driver_exit(); ++ ag71xx_debugfs_root_exit(); ++} ++ ++module_init(ag71xx_module_init); ++module_exit(ag71xx_module_exit); ++ ++MODULE_VERSION(AG71XX_DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_AUTHOR("Imre Kaloz "); ++MODULE_LICENSE("GPL v2"); ++MODULE_ALIAS("platform:" AG71XX_DRV_NAME); +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_mdio.c linux-2.6.39/drivers/net/ag71xx/ag71xx_mdio.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_mdio.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_mdio.c 2011-04-27 12:19:22.257663952 +0200 +@@ -0,0 +1,248 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ag71xx.h" ++ ++#define AG71XX_MDIO_RETRY 1000 ++#define AG71XX_MDIO_DELAY 5 ++ ++static inline void ag71xx_mdio_wr(struct ag71xx_mdio *am, unsigned reg, ++ u32 value) ++{ ++ void __iomem *r; ++ ++ r = am->mdio_base + reg; ++ __raw_writel(value, r); ++ ++ /* flush write */ ++ (void) __raw_readl(r); ++} ++ ++static inline u32 ag71xx_mdio_rr(struct ag71xx_mdio *am, unsigned reg) ++{ ++ return __raw_readl(am->mdio_base + reg); ++} ++ ++static void ag71xx_mdio_dump_regs(struct ag71xx_mdio *am) ++{ ++ DBG("%s: mii_cfg=%08x, mii_cmd=%08x, mii_addr=%08x\n", ++ am->mii_bus->name, ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_CFG), ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_CMD), ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_ADDR)); ++ DBG("%s: mii_ctrl=%08x, mii_status=%08x, mii_ind=%08x\n", ++ am->mii_bus->name, ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_CTRL), ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_STATUS), ++ ag71xx_mdio_rr(am, AG71XX_REG_MII_IND)); ++} ++ ++int ag71xx_mdio_mii_read(struct ag71xx_mdio *am, int addr, int reg) ++{ ++ int ret; ++ int i; ++ ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_WRITE); ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_ADDR, ++ ((addr & 0xff) << MII_ADDR_SHIFT) | (reg & 0xff)); ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_READ); ++ ++ i = AG71XX_MDIO_RETRY; ++ while (ag71xx_mdio_rr(am, AG71XX_REG_MII_IND) & MII_IND_BUSY) { ++ if (i-- == 0) { ++ printk(KERN_ERR "%s: mii_read timed out\n", ++ am->mii_bus->name); ++ ret = 0xffff; ++ goto out; ++ } ++ udelay(AG71XX_MDIO_DELAY); ++ } ++ ++ ret = ag71xx_mdio_rr(am, AG71XX_REG_MII_STATUS) & 0xffff; ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CMD, MII_CMD_WRITE); ++ ++ DBG("mii_read: addr=%04x, reg=%04x, value=%04x\n", addr, reg, ret); ++ ++out: ++ return ret; ++} ++ ++void ag71xx_mdio_mii_write(struct ag71xx_mdio *am, int addr, int reg, u16 val) ++{ ++ int i; ++ ++ DBG("mii_write: addr=%04x, reg=%04x, value=%04x\n", addr, reg, val); ++ ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_ADDR, ++ ((addr & 0xff) << MII_ADDR_SHIFT) | (reg & 0xff)); ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CTRL, val); ++ ++ i = AG71XX_MDIO_RETRY; ++ while (ag71xx_mdio_rr(am, AG71XX_REG_MII_IND) & MII_IND_BUSY) { ++ if (i-- == 0) { ++ printk(KERN_ERR "%s: mii_write timed out\n", ++ am->mii_bus->name); ++ break; ++ } ++ udelay(AG71XX_MDIO_DELAY); ++ } ++} ++ ++static int ag71xx_mdio_reset(struct mii_bus *bus) ++{ ++ struct ag71xx_mdio *am = bus->priv; ++ u32 t; ++ ++ if (am->pdata->is_ar7240) ++ t = MII_CFG_CLK_DIV_6; ++ else ++ t = MII_CFG_CLK_DIV_28; ++ ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CFG, t | MII_CFG_RESET); ++ udelay(100); ++ ++ ag71xx_mdio_wr(am, AG71XX_REG_MII_CFG, t); ++ udelay(100); ++ ++ return 0; ++} ++ ++static int ag71xx_mdio_read(struct mii_bus *bus, int addr, int reg) ++{ ++ struct ag71xx_mdio *am = bus->priv; ++ ++ if (am->pdata->is_ar7240) ++ return ar7240sw_phy_read(bus, addr, reg); ++ else ++ return ag71xx_mdio_mii_read(am, addr, reg); ++} ++ ++static int ag71xx_mdio_write(struct mii_bus *bus, int addr, int reg, u16 val) ++{ ++ struct ag71xx_mdio *am = bus->priv; ++ ++ if (am->pdata->is_ar7240) ++ ar7240sw_phy_write(bus, addr, reg, val); ++ else ++ ag71xx_mdio_mii_write(am, addr, reg, val); ++ return 0; ++} ++ ++static int __devinit ag71xx_mdio_probe(struct platform_device *pdev) ++{ ++ struct ag71xx_mdio_platform_data *pdata; ++ struct ag71xx_mdio *am; ++ struct resource *res; ++ int i; ++ int err; ++ ++ pdata = pdev->dev.platform_data; ++ if (!pdata) { ++ dev_err(&pdev->dev, "no platform data specified\n"); ++ return -EINVAL; ++ } ++ ++ am = kzalloc(sizeof(*am), GFP_KERNEL); ++ if (!am) { ++ err = -ENOMEM; ++ goto err_out; ++ } ++ ++ am->pdata = pdata; ++ ++ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (!res) { ++ dev_err(&pdev->dev, "no iomem resource found\n"); ++ err = -ENXIO; ++ goto err_out; ++ } ++ ++ am->mdio_base = ioremap_nocache(res->start, res->end - res->start + 1); ++ if (!am->mdio_base) { ++ dev_err(&pdev->dev, "unable to ioremap registers\n"); ++ err = -ENOMEM; ++ goto err_free_mdio; ++ } ++ ++ am->mii_bus = mdiobus_alloc(); ++ if (am->mii_bus == NULL) { ++ err = -ENOMEM; ++ goto err_iounmap; ++ } ++ ++ am->mii_bus->name = "ag71xx_mdio"; ++ am->mii_bus->read = ag71xx_mdio_read; ++ am->mii_bus->write = ag71xx_mdio_write; ++ am->mii_bus->reset = ag71xx_mdio_reset; ++ am->mii_bus->irq = am->mii_irq; ++ am->mii_bus->priv = am; ++ am->mii_bus->parent = &pdev->dev; ++ snprintf(am->mii_bus->id, MII_BUS_ID_SIZE, "%s", dev_name(&pdev->dev)); ++ am->mii_bus->phy_mask = pdata->phy_mask; ++ ++ for (i = 0; i < PHY_MAX_ADDR; i++) ++ am->mii_irq[i] = PHY_POLL; ++ ++ ag71xx_mdio_wr(am, AG71XX_REG_MAC_CFG1, 0); ++ ++ err = mdiobus_register(am->mii_bus); ++ if (err) ++ goto err_free_bus; ++ ++ ag71xx_mdio_dump_regs(am); ++ ++ platform_set_drvdata(pdev, am); ++ return 0; ++ ++err_free_bus: ++ mdiobus_free(am->mii_bus); ++err_iounmap: ++ iounmap(am->mdio_base); ++err_free_mdio: ++ kfree(am); ++err_out: ++ return err; ++} ++ ++static int __devexit ag71xx_mdio_remove(struct platform_device *pdev) ++{ ++ struct ag71xx_mdio *am = platform_get_drvdata(pdev); ++ ++ if (am) { ++ mdiobus_unregister(am->mii_bus); ++ mdiobus_free(am->mii_bus); ++ iounmap(am->mdio_base); ++ kfree(am); ++ platform_set_drvdata(pdev, NULL); ++ } ++ ++ return 0; ++} ++ ++static struct platform_driver ag71xx_mdio_driver = { ++ .probe = ag71xx_mdio_probe, ++ .remove = __exit_p(ag71xx_mdio_remove), ++ .driver = { ++ .name = "ag71xx-mdio", ++ } ++}; ++ ++int __init ag71xx_mdio_driver_init(void) ++{ ++ return platform_driver_register(&ag71xx_mdio_driver); ++} ++ ++void ag71xx_mdio_driver_exit(void) ++{ ++ platform_driver_unregister(&ag71xx_mdio_driver); ++} +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_phy.c linux-2.6.39/drivers/net/ag71xx/ag71xx_phy.c +--- linux-2.6.39.orig/drivers/net/ag71xx/ag71xx_phy.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/ag71xx_phy.c 2011-08-06 09:32:37.298018216 +0200 +@@ -0,0 +1,228 @@ ++/* ++ * Atheros AR71xx built-in ethernet mac driver ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Based on Atheros' AG7100 driver ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include "ag71xx.h" ++ ++static void ag71xx_phy_link_adjust(struct net_device *dev) ++{ ++ struct ag71xx *ag = netdev_priv(dev); ++ struct phy_device *phydev = ag->phy_dev; ++ unsigned long flags; ++ int status_change = 0; ++ ++ spin_lock_irqsave(&ag->lock, flags); ++ ++ if (phydev->link) { ++ if (ag->duplex != phydev->duplex ++ || ag->speed != phydev->speed) { ++ status_change = 1; ++ } ++ } ++ ++ if (phydev->link != ag->link) ++ status_change = 1; ++ ++ ag->link = phydev->link; ++ ag->duplex = phydev->duplex; ++ ag->speed = phydev->speed; ++ ++ if (status_change) ++ ag71xx_link_adjust(ag); ++ ++ spin_unlock_irqrestore(&ag->lock, flags); ++} ++ ++void ag71xx_phy_start(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ if (ag->phy_dev) { ++ phy_start(ag->phy_dev); ++ } else if (pdata->has_ar7240_switch) { ++ ag71xx_ar7240_start(ag); ++ } else { ++ ag->link = 1; ++ ag71xx_link_adjust(ag); ++ } ++} ++ ++void ag71xx_phy_stop(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ if (ag->phy_dev) { ++ phy_stop(ag->phy_dev); ++ } else { ++ if (pdata->has_ar7240_switch) ++ ag71xx_ar7240_stop(ag); ++ ag->link = 0; ++ ag71xx_link_adjust(ag); ++ } ++} ++ ++static int ag71xx_phy_connect_fixed(struct ag71xx *ag) ++{ ++ struct net_device *dev = ag->dev; ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ int ret = 0; ++ ++ /* use fixed settings */ ++ switch (pdata->speed) { ++ case SPEED_10: ++ case SPEED_100: ++ case SPEED_1000: ++ break; ++ default: ++ printk(KERN_ERR "%s: invalid speed specified\n", dev->name); ++ ret = -EINVAL; ++ break; ++ } ++ ++ printk(KERN_DEBUG "%s: using fixed link parameters\n", dev->name); ++ ++ ag->duplex = pdata->duplex; ++ ag->speed = pdata->speed; ++ ++ return ret; ++} ++ ++static int ag71xx_phy_connect_multi(struct ag71xx *ag) ++{ ++ struct net_device *dev = ag->dev; ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ struct phy_device *phydev = NULL; ++ int phy_addr; ++ int ret = 0; ++ ++ for (phy_addr = 0; phy_addr < PHY_MAX_ADDR; phy_addr++) { ++ if (!(pdata->phy_mask & (1 << phy_addr))) ++ continue; ++ ++ if (ag->mii_bus->phy_map[phy_addr] == NULL) ++ continue; ++ ++ DBG("%s: PHY found at %s, uid=%08x\n", ++ dev->name, ++ dev_name(&ag->mii_bus->phy_map[phy_addr]->dev), ++ ag->mii_bus->phy_map[phy_addr]->phy_id); ++ ++ if (phydev == NULL) ++ phydev = ag->mii_bus->phy_map[phy_addr]; ++ } ++ ++ if (!phydev) { ++ printk(KERN_ERR "%s: no PHY found with phy_mask=%08x\n", ++ dev->name, pdata->phy_mask); ++ return -ENODEV; ++ } ++ ++ ag->phy_dev = phy_connect(dev, dev_name(&phydev->dev), ++ &ag71xx_phy_link_adjust, 0, ++ pdata->phy_if_mode); ++ ++ if (IS_ERR(ag->phy_dev)) { ++ printk(KERN_ERR "%s: could not connect to PHY at %s\n", ++ dev->name, dev_name(&phydev->dev)); ++ return PTR_ERR(ag->phy_dev); ++ } ++ ++ /* mask with MAC supported features */ ++ if (pdata->has_gbit) ++ phydev->supported &= PHY_GBIT_FEATURES; ++ else ++ phydev->supported &= PHY_BASIC_FEATURES; ++ ++ phydev->advertising = phydev->supported; ++ ++ printk(KERN_DEBUG "%s: connected to PHY at %s [uid=%08x, driver=%s]\n", ++ dev->name, dev_name(&phydev->dev), ++ phydev->phy_id, phydev->drv->name); ++ ++ ag->link = 0; ++ ag->speed = 0; ++ ag->duplex = -1; ++ ++ return ret; ++} ++ ++static int dev_is_class(struct device *dev, void *class) ++{ ++ if (dev->class != NULL && !strcmp(dev->class->name, class)) ++ return 1; ++ ++ return 0; ++} ++ ++static struct device *dev_find_class(struct device *parent, char *class) ++{ ++ if (dev_is_class(parent, class)) { ++ get_device(parent); ++ return parent; ++ } ++ ++ return device_find_child(parent, class, dev_is_class); ++} ++ ++static struct mii_bus *dev_to_mii_bus(struct device *dev) ++{ ++ struct device *d; ++ ++ d = dev_find_class(dev, "mdio_bus"); ++ if (d != NULL) { ++ struct mii_bus *bus; ++ ++ bus = to_mii_bus(d); ++ put_device(d); ++ ++ return bus; ++ } ++ ++ return NULL; ++} ++ ++int __devinit ag71xx_phy_connect(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ ag->mii_bus = dev_to_mii_bus(pdata->mii_bus_dev); ++ if (ag->mii_bus == NULL) { ++ printk(KERN_ERR "%s: unable to find MII bus on device '%s'\n", ++ ag->dev->name, dev_name(pdata->mii_bus_dev)); ++ return -ENODEV; ++ } ++ ++ /* Reset the mdio bus explicitly */ ++ if (ag->mii_bus->reset) { ++ mutex_lock(&ag->mii_bus->mdio_lock); ++ ag->mii_bus->reset(ag->mii_bus); ++ mutex_unlock(&ag->mii_bus->mdio_lock); ++ } ++ ++ if (pdata->has_ar7240_switch) ++ return ag71xx_ar7240_init(ag); ++ ++ if (pdata->phy_mask) ++ return ag71xx_phy_connect_multi(ag); ++ ++ return ag71xx_phy_connect_fixed(ag); ++} ++ ++void ag71xx_phy_disconnect(struct ag71xx *ag) ++{ ++ struct ag71xx_platform_data *pdata = ag71xx_get_pdata(ag); ++ ++ if (pdata->has_ar7240_switch) ++ ag71xx_ar7240_cleanup(ag); ++ else if (ag->phy_dev) ++ phy_disconnect(ag->phy_dev); ++} +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/Kconfig linux-2.6.39/drivers/net/ag71xx/Kconfig +--- linux-2.6.39.orig/drivers/net/ag71xx/Kconfig 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/Kconfig 2011-04-27 12:19:22.247664026 +0200 +@@ -0,0 +1,33 @@ ++config AG71XX ++ tristate "Atheros AR71xx built-in ethernet mac support" ++ depends on ATHEROS_AR71XX ++ select PHYLIB ++ help ++ If you wish to compile a kernel for AR71xx/91xx and enable ++ ethernet support, then you should always answer Y to this. ++ ++if AG71XX ++ ++config AG71XX_DEBUG ++ bool "Atheros AR71xx built-in ethernet driver debugging" ++ default n ++ help ++ Atheros AR71xx built-in ethernet driver debugging messages. ++ ++config AG71XX_DEBUG_FS ++ bool "Atheros AR71xx built-in ethernet driver debugfs support" ++ depends on DEBUG_FS ++ default n ++ help ++ Say Y, if you need access to various statistics provided by ++ the ag71xx driver. ++ ++config AG71XX_AR8216_SUPPORT ++ bool "special support for the Atheros AR8216 switch" ++ default n ++ default y if AR71XX_MACH_WNR2000 || AR71XX_MACH_MZK_W04NU ++ help ++ Say 'y' here if you want to enable special support for the ++ Atheros AR8216 switch found on some boards. ++ ++endif +diff -Nur linux-2.6.39.orig/drivers/net/ag71xx/Makefile linux-2.6.39/drivers/net/ag71xx/Makefile +--- linux-2.6.39.orig/drivers/net/ag71xx/Makefile 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/ag71xx/Makefile 2011-04-27 12:19:22.257663952 +0200 +@@ -0,0 +1,15 @@ ++# ++# Makefile for the Atheros AR71xx built-in ethernet macs ++# ++ ++ag71xx-y += ag71xx_main.o ++ag71xx-y += ag71xx_ethtool.o ++ag71xx-y += ag71xx_phy.o ++ag71xx-y += ag71xx_mdio.o ++ag71xx-y += ag71xx_ar7240.o ++ ++ag71xx-$(CONFIG_AG71XX_DEBUG_FS) += ag71xx_debugfs.o ++ag71xx-$(CONFIG_AG71XX_AR8216_SUPPORT) += ag71xx_ar8216.o ++ ++obj-$(CONFIG_AG71XX) += ag71xx.o ++ +diff -Nur linux-2.6.39.orig/drivers/net/Kconfig linux-2.6.39/drivers/net/Kconfig +--- linux-2.6.39.orig/drivers/net/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/Kconfig 2011-08-22 16:21:54.787979739 +0200 +@@ -2071,6 +2071,8 @@ + + The safe and default value for this is N. + ++source drivers/net/ag71xx/Kconfig ++ + config DL2K + tristate "DL2000/TC902x-based Gigabit Ethernet support" + depends on PCI +diff -Nur linux-2.6.39.orig/drivers/net/Makefile linux-2.6.39/drivers/net/Makefile +--- linux-2.6.39.orig/drivers/net/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/Makefile 2011-08-22 16:21:54.797980120 +0200 +@@ -112,6 +112,7 @@ + # end link order section + # + ++obj-$(CONFIG_AG71XX) += ag71xx/ + obj-$(CONFIG_SUNDANCE) += sundance.o + obj-$(CONFIG_HAMACHI) += hamachi.o + obj-$(CONFIG_NET) += Space.o loopback.o +diff -Nur linux-2.6.39.orig/drivers/net/phy/Kconfig linux-2.6.39/drivers/net/phy/Kconfig +--- linux-2.6.39.orig/drivers/net/phy/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/phy/Kconfig 2011-08-22 22:19:34.339230055 +0200 +@@ -13,6 +13,12 @@ + + if PHYLIB + ++config SWCONFIG ++ tristate "Switch configuration API" ++ ---help--- ++ Switch configuration API using netlink. This allows ++ you to configure the VLAN features of certain switches. ++ + comment "MII PHY device drivers" + + config MARVELL_PHY +diff -Nur linux-2.6.39.orig/drivers/net/phy/Makefile linux-2.6.39/drivers/net/phy/Makefile +--- linux-2.6.39.orig/drivers/net/phy/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/phy/Makefile 2011-08-22 22:19:34.339230055 +0200 +@@ -3,6 +3,7 @@ + libphy-objs := phy.o phy_device.o mdio_bus.o + + obj-$(CONFIG_PHYLIB) += libphy.o ++obj-$(CONFIG_SWCONFIG) += swconfig.o + obj-$(CONFIG_MARVELL_PHY) += marvell.o + obj-$(CONFIG_DAVICOM_PHY) += davicom.o + obj-$(CONFIG_CICADA_PHY) += cicada.o +diff -Nur linux-2.6.39.orig/drivers/net/phy/micrel.c linux-2.6.39/drivers/net/phy/micrel.c +--- linux-2.6.39.orig/drivers/net/phy/micrel.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/phy/micrel.c 2011-04-27 12:19:22.257663952 +0200 +@@ -1,251 +1,82 @@ + /* +- * drivers/net/phy/micrel.c ++ * Driver for Micrel/Kendin PHYs + * +- * Driver for Micrel PHYs ++ * Copyright (c) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz + * +- * Author: David J. Choi ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. + * +- * Copyright (c) 2010 Micrel, Inc. +- * +- * 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. +- * +- * Support : ksz9021 1000/100/10 phy from Micrel +- * ks8001, ks8737, ks8721, ks8041, ks8051 100/10 phy + */ + +-#include +-#include ++#include ++#include + #include +-#include + +-/* general Interrupt control/status reg in vendor specific block. */ +-#define MII_KSZPHY_INTCS 0x1B +-#define KSZPHY_INTCS_JABBER (1 << 15) +-#define KSZPHY_INTCS_RECEIVE_ERR (1 << 14) +-#define KSZPHY_INTCS_PAGE_RECEIVE (1 << 13) +-#define KSZPHY_INTCS_PARELLEL (1 << 12) +-#define KSZPHY_INTCS_LINK_PARTNER_ACK (1 << 11) +-#define KSZPHY_INTCS_LINK_DOWN (1 << 10) +-#define KSZPHY_INTCS_REMOTE_FAULT (1 << 9) +-#define KSZPHY_INTCS_LINK_UP (1 << 8) +-#define KSZPHY_INTCS_ALL (KSZPHY_INTCS_LINK_UP |\ +- KSZPHY_INTCS_LINK_DOWN) +- +-/* general PHY control reg in vendor specific block. */ +-#define MII_KSZPHY_CTRL 0x1F +-/* bitmap of PHY register to set interrupt mode */ +-#define KSZPHY_CTRL_INT_ACTIVE_HIGH (1 << 9) +-#define KSZ9021_CTRL_INT_ACTIVE_HIGH (1 << 14) +-#define KS8737_CTRL_INT_ACTIVE_HIGH (1 << 14) +-#define KSZ8051_RMII_50MHZ_CLK (1 << 7) ++#define KSZ_REG_INT_CTRL 0x1b + +-static int kszphy_ack_interrupt(struct phy_device *phydev) +-{ +- /* bit[7..0] int status, which is a read and clear register. */ +- int rc; ++#define KSZ_INT_LU_EN (1 << 8) /* enable Link Up interrupt */ ++#define KSZ_INT_RF_EN (1 << 9) /* enable Remote Fault interrupt */ ++#define KSZ_INT_LD_EN (1 << 10) /* enable Link Down interrupt */ + +- rc = phy_read(phydev, MII_KSZPHY_INTCS); +- +- return (rc < 0) ? rc : 0; +-} ++#define KSZ_INT_INIT (KSZ_INT_LU_EN | KSZ_INT_LD_EN) + +-static int kszphy_set_interrupt(struct phy_device *phydev) ++static int ksz8041_ack_interrupt(struct phy_device *phydev) + { +- int temp; +- temp = (PHY_INTERRUPT_ENABLED == phydev->interrupts) ? +- KSZPHY_INTCS_ALL : 0; +- return phy_write(phydev, MII_KSZPHY_INTCS, temp); +-} ++ int err; + +-static int kszphy_config_intr(struct phy_device *phydev) +-{ +- int temp, rc; ++ err = phy_read(phydev, KSZ_REG_INT_CTRL); + +- /* set the interrupt pin active low */ +- temp = phy_read(phydev, MII_KSZPHY_CTRL); +- temp &= ~KSZPHY_CTRL_INT_ACTIVE_HIGH; +- phy_write(phydev, MII_KSZPHY_CTRL, temp); +- rc = kszphy_set_interrupt(phydev); +- return rc < 0 ? rc : 0; ++ return (err < 0) ? err : 0; + } + +-static int ksz9021_config_intr(struct phy_device *phydev) ++static int ksz8041_config_intr(struct phy_device *phydev) + { +- int temp, rc; ++ int err; + +- /* set the interrupt pin active low */ +- temp = phy_read(phydev, MII_KSZPHY_CTRL); +- temp &= ~KSZ9021_CTRL_INT_ACTIVE_HIGH; +- phy_write(phydev, MII_KSZPHY_CTRL, temp); +- rc = kszphy_set_interrupt(phydev); +- return rc < 0 ? rc : 0; +-} +- +-static int ks8737_config_intr(struct phy_device *phydev) +-{ +- int temp, rc; ++ if (phydev->interrupts == PHY_INTERRUPT_ENABLED) ++ err = phy_write(phydev, KSZ_REG_INT_CTRL, ++ KSZ_INT_INIT); ++ else ++ err = phy_write(phydev, KSZ_REG_INT_CTRL, 0); + +- /* set the interrupt pin active low */ +- temp = phy_read(phydev, MII_KSZPHY_CTRL); +- temp &= ~KS8737_CTRL_INT_ACTIVE_HIGH; +- phy_write(phydev, MII_KSZPHY_CTRL, temp); +- rc = kszphy_set_interrupt(phydev); +- return rc < 0 ? rc : 0; ++ return err; + } + +-static int kszphy_config_init(struct phy_device *phydev) +-{ +- return 0; +-} +- +-static int ks8051_config_init(struct phy_device *phydev) +-{ +- int regval; +- +- if (phydev->dev_flags & MICREL_PHY_50MHZ_CLK) { +- regval = phy_read(phydev, MII_KSZPHY_CTRL); +- regval |= KSZ8051_RMII_50MHZ_CLK; +- phy_write(phydev, MII_KSZPHY_CTRL, regval); +- } +- +- return 0; +-} +- +-static struct phy_driver ks8737_driver = { +- .phy_id = PHY_ID_KS8737, +- .phy_id_mask = 0x00fffff0, +- .name = "Micrel KS8737", +- .features = (PHY_BASIC_FEATURES | SUPPORTED_Pause), +- .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, +- .config_init = kszphy_config_init, ++static struct phy_driver ksz8041_phy_driver = { ++ .phy_id = 0x00221512, ++ .name = "Micrel KSZ8041", ++ .phy_id_mask = 0x001fffff, ++ .features = PHY_BASIC_FEATURES, ++ .flags = PHY_HAS_INTERRUPT, + .config_aneg = genphy_config_aneg, + .read_status = genphy_read_status, +- .ack_interrupt = kszphy_ack_interrupt, +- .config_intr = ks8737_config_intr, +- .driver = { .owner = THIS_MODULE,}, ++ .ack_interrupt = ksz8041_ack_interrupt, ++ .config_intr = ksz8041_config_intr, ++ .driver = { ++ .owner = THIS_MODULE, ++ }, + }; + +-static struct phy_driver ks8041_driver = { +- .phy_id = PHY_ID_KS8041, +- .phy_id_mask = 0x00fffff0, +- .name = "Micrel KS8041", +- .features = (PHY_BASIC_FEATURES | SUPPORTED_Pause +- | SUPPORTED_Asym_Pause), +- .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, +- .config_init = kszphy_config_init, +- .config_aneg = genphy_config_aneg, +- .read_status = genphy_read_status, +- .ack_interrupt = kszphy_ack_interrupt, +- .config_intr = kszphy_config_intr, +- .driver = { .owner = THIS_MODULE,}, +-}; +- +-static struct phy_driver ks8051_driver = { +- .phy_id = PHY_ID_KS8051, +- .phy_id_mask = 0x00fffff0, +- .name = "Micrel KS8051", +- .features = (PHY_BASIC_FEATURES | SUPPORTED_Pause +- | SUPPORTED_Asym_Pause), +- .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, +- .config_init = ks8051_config_init, +- .config_aneg = genphy_config_aneg, +- .read_status = genphy_read_status, +- .ack_interrupt = kszphy_ack_interrupt, +- .config_intr = kszphy_config_intr, +- .driver = { .owner = THIS_MODULE,}, +-}; +- +-static struct phy_driver ks8001_driver = { +- .phy_id = PHY_ID_KS8001, +- .name = "Micrel KS8001 or KS8721", +- .phy_id_mask = 0x00fffff0, +- .features = (PHY_BASIC_FEATURES | SUPPORTED_Pause), +- .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, +- .config_init = kszphy_config_init, +- .config_aneg = genphy_config_aneg, +- .read_status = genphy_read_status, +- .ack_interrupt = kszphy_ack_interrupt, +- .config_intr = kszphy_config_intr, +- .driver = { .owner = THIS_MODULE,}, +-}; +- +-static struct phy_driver ksz9021_driver = { +- .phy_id = PHY_ID_KSZ9021, +- .phy_id_mask = 0x000fff10, +- .name = "Micrel KSZ9021 Gigabit PHY", +- .features = (PHY_GBIT_FEATURES | SUPPORTED_Pause +- | SUPPORTED_Asym_Pause), +- .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, +- .config_init = kszphy_config_init, +- .config_aneg = genphy_config_aneg, +- .read_status = genphy_read_status, +- .ack_interrupt = kszphy_ack_interrupt, +- .config_intr = ksz9021_config_intr, +- .driver = { .owner = THIS_MODULE, }, +-}; +- +-static int __init ksphy_init(void) ++static int __init micrel_phy_init(void) + { +- int ret; +- +- ret = phy_driver_register(&ks8001_driver); +- if (ret) +- goto err1; +- +- ret = phy_driver_register(&ksz9021_driver); +- if (ret) +- goto err2; +- +- ret = phy_driver_register(&ks8737_driver); +- if (ret) +- goto err3; +- ret = phy_driver_register(&ks8041_driver); +- if (ret) +- goto err4; +- ret = phy_driver_register(&ks8051_driver); +- if (ret) +- goto err5; +- +- return 0; +- +-err5: +- phy_driver_unregister(&ks8041_driver); +-err4: +- phy_driver_unregister(&ks8737_driver); +-err3: +- phy_driver_unregister(&ksz9021_driver); +-err2: +- phy_driver_unregister(&ks8001_driver); +-err1: +- return ret; ++ return phy_driver_register(&ksz8041_phy_driver); + } + +-static void __exit ksphy_exit(void) ++static void __exit micrel_phy_exit(void) + { +- phy_driver_unregister(&ks8001_driver); +- phy_driver_unregister(&ks8737_driver); +- phy_driver_unregister(&ksz9021_driver); +- phy_driver_unregister(&ks8041_driver); +- phy_driver_unregister(&ks8051_driver); ++ phy_driver_unregister(&ksz8041_phy_driver); + } + +-module_init(ksphy_init); +-module_exit(ksphy_exit); +- +-MODULE_DESCRIPTION("Micrel PHY driver"); +-MODULE_AUTHOR("David J. Choi"); +-MODULE_LICENSE("GPL"); +- +-static struct mdio_device_id __maybe_unused micrel_tbl[] = { +- { PHY_ID_KSZ9021, 0x000fff10 }, +- { PHY_ID_KS8001, 0x00fffff0 }, +- { PHY_ID_KS8737, 0x00fffff0 }, +- { PHY_ID_KS8041, 0x00fffff0 }, +- { PHY_ID_KS8051, 0x00fffff0 }, +- { } +-}; ++#ifdef MODULE ++module_init(micrel_phy_init); ++module_exit(micrel_phy_exit); ++#else ++subsys_initcall(micrel_phy_init); ++#endif + +-MODULE_DEVICE_TABLE(mdio, micrel_tbl); ++MODULE_DESCRIPTION("Micrel/Kendin PHY driver"); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_AUTHOR("Imre Kaloz "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/net/phy/phy.c linux-2.6.39/drivers/net/phy/phy.c +--- linux-2.6.39.orig/drivers/net/phy/phy.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/phy/phy.c 2011-08-22 22:00:02.067980292 +0200 +@@ -297,6 +297,50 @@ + } + EXPORT_SYMBOL(phy_ethtool_gset); + ++int phy_ethtool_ioctl(struct phy_device *phydev, void *useraddr) ++{ ++ u32 cmd; ++ int tmp; ++ struct ethtool_cmd ecmd = { ETHTOOL_GSET }; ++ struct ethtool_value edata = { ETHTOOL_GLINK }; ++ ++ if (get_user(cmd, (u32 *) useraddr)) ++ return -EFAULT; ++ ++ switch (cmd) { ++ case ETHTOOL_GSET: ++ phy_ethtool_gset(phydev, &ecmd); ++ if (copy_to_user(useraddr, &ecmd, sizeof(ecmd))) ++ return -EFAULT; ++ return 0; ++ ++ case ETHTOOL_SSET: ++ if (copy_from_user(&ecmd, useraddr, sizeof(ecmd))) ++ return -EFAULT; ++ return phy_ethtool_sset(phydev, &ecmd); ++ ++ case ETHTOOL_NWAY_RST: ++ /* if autoneg is off, it's an error */ ++ tmp = phy_read(phydev, MII_BMCR); ++ if (tmp & BMCR_ANENABLE) { ++ tmp |= (BMCR_ANRESTART); ++ phy_write(phydev, MII_BMCR, tmp); ++ return 0; ++ } ++ return -EINVAL; ++ ++ case ETHTOOL_GLINK: ++ edata.data = (phy_read(phydev, ++ MII_BMSR) & BMSR_LSTATUS) ? 1 : 0; ++ if (copy_to_user(useraddr, &edata, sizeof(edata))) ++ return -EFAULT; ++ return 0; ++ } ++ ++ return -EOPNOTSUPP; ++} ++EXPORT_SYMBOL(phy_ethtool_ioctl); ++ + /** + * phy_mii_ioctl - generic PHY MII ioctl interface + * @phydev: the phy_device struct +@@ -472,7 +516,7 @@ + int idx; + + idx = phy_find_setting(phydev->speed, phydev->duplex); +- ++ + idx++; + + idx = phy_find_valid(idx, phydev->supported); +diff -Nur linux-2.6.39.orig/drivers/net/phy/phy_device.c linux-2.6.39/drivers/net/phy/phy_device.c +--- linux-2.6.39.orig/drivers/net/phy/phy_device.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/net/phy/phy_device.c 2011-08-22 22:00:06.817981347 +0200 +@@ -149,6 +149,18 @@ + } + EXPORT_SYMBOL(phy_scan_fixups); + ++static int generic_receive_skb(struct sk_buff *skb) ++{ ++ skb->protocol = eth_type_trans(skb, skb->dev); ++ return netif_receive_skb(skb); ++} ++ ++static int generic_rx(struct sk_buff *skb) ++{ ++ skb->protocol = eth_type_trans(skb, skb->dev); ++ return netif_rx(skb); ++} ++ + static struct phy_device* phy_device_create(struct mii_bus *bus, + int addr, int phy_id) + { +@@ -180,6 +192,8 @@ + dev_set_name(&dev->dev, PHY_ID_FMT, bus->id, addr); + + dev->state = PHY_DOWN; ++ dev->netif_receive_skb = &generic_receive_skb; ++ dev->netif_rx = &generic_rx; + + mutex_init(&dev->lock); + INIT_DELAYED_WORK(&dev->state_queue, phy_state_machine); +diff -Nur linux-2.6.39.orig/drivers/net/phy/swconfig.c linux-2.6.39/drivers/net/phy/swconfig.c +--- linux-2.6.39.orig/drivers/net/phy/swconfig.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/net/phy/swconfig.c 2011-08-22 22:18:58.887990974 +0200 +@@ -0,0 +1,954 @@ ++/* ++ * swconfig.c: Switch configuration API ++ * ++ * Copyright (C) 2008 Felix Fietkau ++ * ++ * 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. ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++//#define DEBUG 1 ++#ifdef DEBUG ++#define DPRINTF(format, ...) printk("%s: " format, __func__, ##__VA_ARGS__) ++#else ++#define DPRINTF(...) do {} while(0) ++#endif ++ ++#define SWCONFIG_DEVNAME "switch%d" ++ ++MODULE_AUTHOR("Felix Fietkau "); ++MODULE_LICENSE("GPL"); ++ ++static int swdev_id = 0; ++static struct list_head swdevs; ++static DEFINE_SPINLOCK(swdevs_lock); ++struct swconfig_callback; ++ ++struct swconfig_callback ++{ ++ struct sk_buff *msg; ++ struct genlmsghdr *hdr; ++ struct genl_info *info; ++ int cmd; ++ ++ /* callback for filling in the message data */ ++ int (*fill)(struct swconfig_callback *cb, void *arg); ++ ++ /* callback for closing the message before sending it */ ++ int (*close)(struct swconfig_callback *cb, void *arg); ++ ++ struct nlattr *nest[4]; ++ int args[4]; ++}; ++ ++/* defaults */ ++ ++static int ++swconfig_get_vlan_ports(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ int ret; ++ if (val->port_vlan >= dev->vlans) ++ return -EINVAL; ++ ++ if (!dev->ops->get_vlan_ports) ++ return -EOPNOTSUPP; ++ ++ ret = dev->ops->get_vlan_ports(dev, val); ++ return ret; ++} ++ ++static int ++swconfig_set_vlan_ports(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ struct switch_port *ports = val->value.ports; ++ const struct switch_dev_ops *ops = dev->ops; ++ int i; ++ ++ if (val->port_vlan >= dev->vlans) ++ return -EINVAL; ++ ++ /* validate ports */ ++ if (val->len > dev->ports) ++ return -EINVAL; ++ ++ if (!ops->set_vlan_ports) ++ return -EOPNOTSUPP; ++ ++ for (i = 0; i < val->len; i++) { ++ if (ports[i].id >= dev->ports) ++ return -EINVAL; ++ ++ if (ops->set_port_pvid && ++ !(ports[i].flags & (1 << SWITCH_PORT_FLAG_TAGGED))) ++ ops->set_port_pvid(dev, ports[i].id, val->port_vlan); ++ } ++ ++ return ops->set_vlan_ports(dev, val); ++} ++ ++static int ++swconfig_set_pvid(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ if (val->port_vlan >= dev->ports) ++ return -EINVAL; ++ ++ if (!dev->ops->set_port_pvid) ++ return -EOPNOTSUPP; ++ ++ return dev->ops->set_port_pvid(dev, val->port_vlan, val->value.i); ++} ++ ++static int ++swconfig_get_pvid(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ if (val->port_vlan >= dev->ports) ++ return -EINVAL; ++ ++ if (!dev->ops->get_port_pvid) ++ return -EOPNOTSUPP; ++ ++ return dev->ops->get_port_pvid(dev, val->port_vlan, &val->value.i); ++} ++ ++static int ++swconfig_apply_config(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ /* don't complain if not supported by the switch driver */ ++ if (!dev->ops->apply_config) ++ return 0; ++ ++ return dev->ops->apply_config(dev); ++} ++ ++static int ++swconfig_reset_switch(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val) ++{ ++ /* don't complain if not supported by the switch driver */ ++ if (!dev->ops->reset_switch) ++ return 0; ++ ++ return dev->ops->reset_switch(dev); ++} ++ ++enum global_defaults { ++ GLOBAL_APPLY, ++ GLOBAL_RESET, ++}; ++ ++enum vlan_defaults { ++ VLAN_PORTS, ++}; ++ ++enum port_defaults { ++ PORT_PVID, ++}; ++ ++static struct switch_attr default_global[] = { ++ [GLOBAL_APPLY] = { ++ .type = SWITCH_TYPE_NOVAL, ++ .name = "apply", ++ .description = "Activate changes in the hardware", ++ .set = swconfig_apply_config, ++ }, ++ [GLOBAL_RESET] = { ++ .type = SWITCH_TYPE_NOVAL, ++ .name = "reset", ++ .description = "Reset the switch", ++ .set = swconfig_reset_switch, ++ } ++}; ++ ++static struct switch_attr default_port[] = { ++ [PORT_PVID] = { ++ .type = SWITCH_TYPE_INT, ++ .name = "pvid", ++ .description = "Primary VLAN ID", ++ .set = swconfig_set_pvid, ++ .get = swconfig_get_pvid, ++ } ++}; ++ ++static struct switch_attr default_vlan[] = { ++ [VLAN_PORTS] = { ++ .type = SWITCH_TYPE_PORTS, ++ .name = "ports", ++ .description = "VLAN port mapping", ++ .set = swconfig_set_vlan_ports, ++ .get = swconfig_get_vlan_ports, ++ }, ++}; ++ ++ ++static void swconfig_defaults_init(struct switch_dev *dev) ++{ ++ const struct switch_dev_ops *ops = dev->ops; ++ ++ dev->def_global = 0; ++ dev->def_vlan = 0; ++ dev->def_port = 0; ++ ++ if (ops->get_vlan_ports || ops->set_vlan_ports) ++ set_bit(VLAN_PORTS, &dev->def_vlan); ++ ++ if (ops->get_port_pvid || ops->set_port_pvid) ++ set_bit(PORT_PVID, &dev->def_port); ++ ++ /* always present, can be no-op */ ++ set_bit(GLOBAL_APPLY, &dev->def_global); ++ set_bit(GLOBAL_RESET, &dev->def_global); ++} ++ ++ ++static struct genl_family switch_fam = { ++ .id = GENL_ID_GENERATE, ++ .name = "switch", ++ .hdrsize = 0, ++ .version = 1, ++ .maxattr = SWITCH_ATTR_MAX, ++}; ++ ++static const struct nla_policy switch_policy[SWITCH_ATTR_MAX+1] = { ++ [SWITCH_ATTR_ID] = { .type = NLA_U32 }, ++ [SWITCH_ATTR_OP_ID] = { .type = NLA_U32 }, ++ [SWITCH_ATTR_OP_PORT] = { .type = NLA_U32 }, ++ [SWITCH_ATTR_OP_VLAN] = { .type = NLA_U32 }, ++ [SWITCH_ATTR_OP_VALUE_INT] = { .type = NLA_U32 }, ++ [SWITCH_ATTR_OP_VALUE_STR] = { .type = NLA_NUL_STRING }, ++ [SWITCH_ATTR_OP_VALUE_PORTS] = { .type = NLA_NESTED }, ++ [SWITCH_ATTR_TYPE] = { .type = NLA_U32 }, ++}; ++ ++static const struct nla_policy port_policy[SWITCH_PORT_ATTR_MAX+1] = { ++ [SWITCH_PORT_ID] = { .type = NLA_U32 }, ++ [SWITCH_PORT_FLAG_TAGGED] = { .type = NLA_FLAG }, ++}; ++ ++static inline void ++swconfig_lock(void) ++{ ++ spin_lock(&swdevs_lock); ++} ++ ++static inline void ++swconfig_unlock(void) ++{ ++ spin_unlock(&swdevs_lock); ++} ++ ++static struct switch_dev * ++swconfig_get_dev(struct genl_info *info) ++{ ++ struct switch_dev *dev = NULL; ++ struct switch_dev *p; ++ int id; ++ ++ if (!info->attrs[SWITCH_ATTR_ID]) ++ goto done; ++ ++ id = nla_get_u32(info->attrs[SWITCH_ATTR_ID]); ++ swconfig_lock(); ++ list_for_each_entry(p, &swdevs, dev_list) { ++ if (id != p->id) ++ continue; ++ ++ dev = p; ++ break; ++ } ++ if (dev) ++ spin_lock(&dev->lock); ++ else ++ DPRINTF("device %d not found\n", id); ++ swconfig_unlock(); ++done: ++ return dev; ++} ++ ++static inline void ++swconfig_put_dev(struct switch_dev *dev) ++{ ++ spin_unlock(&dev->lock); ++} ++ ++static int ++swconfig_dump_attr(struct swconfig_callback *cb, void *arg) ++{ ++ struct switch_attr *op = arg; ++ struct genl_info *info = cb->info; ++ struct sk_buff *msg = cb->msg; ++ int id = cb->args[0]; ++ void *hdr; ++ ++ hdr = genlmsg_put(msg, info->snd_pid, info->snd_seq, &switch_fam, ++ NLM_F_MULTI, SWITCH_CMD_NEW_ATTR); ++ if (IS_ERR(hdr)) ++ return -1; ++ ++ NLA_PUT_U32(msg, SWITCH_ATTR_OP_ID, id); ++ NLA_PUT_U32(msg, SWITCH_ATTR_OP_TYPE, op->type); ++ NLA_PUT_STRING(msg, SWITCH_ATTR_OP_NAME, op->name); ++ if (op->description) ++ NLA_PUT_STRING(msg, SWITCH_ATTR_OP_DESCRIPTION, ++ op->description); ++ ++ return genlmsg_end(msg, hdr); ++nla_put_failure: ++ genlmsg_cancel(msg, hdr); ++ return -EMSGSIZE; ++} ++ ++/* spread multipart messages across multiple message buffers */ ++static int ++swconfig_send_multipart(struct swconfig_callback *cb, void *arg) ++{ ++ struct genl_info *info = cb->info; ++ int restart = 0; ++ int err; ++ ++ do { ++ if (!cb->msg) { ++ cb->msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL); ++ if (cb->msg == NULL) ++ goto error; ++ } ++ ++ if (!(cb->fill(cb, arg) < 0)) ++ break; ++ ++ /* fill failed, check if this was already the second attempt */ ++ if (restart) ++ goto error; ++ ++ /* try again in a new message, send the current one */ ++ restart = 1; ++ if (cb->close) { ++ if (cb->close(cb, arg) < 0) ++ goto error; ++ } ++ err = genlmsg_reply(cb->msg, info); ++ cb->msg = NULL; ++ if (err < 0) ++ goto error; ++ ++ } while (restart); ++ ++ return 0; ++ ++error: ++ if (cb->msg) ++ nlmsg_free(cb->msg); ++ return -1; ++} ++ ++static int ++swconfig_list_attrs(struct sk_buff *skb, struct genl_info *info) ++{ ++ struct genlmsghdr *hdr = nlmsg_data(info->nlhdr); ++ const struct switch_attrlist *alist; ++ struct switch_dev *dev; ++ struct swconfig_callback cb; ++ int err = -EINVAL; ++ int i; ++ ++ /* defaults */ ++ struct switch_attr *def_list; ++ unsigned long *def_active; ++ int n_def; ++ ++ dev = swconfig_get_dev(info); ++ if (!dev) ++ return -EINVAL; ++ ++ switch(hdr->cmd) { ++ case SWITCH_CMD_LIST_GLOBAL: ++ alist = &dev->ops->attr_global; ++ def_list = default_global; ++ def_active = &dev->def_global; ++ n_def = ARRAY_SIZE(default_global); ++ break; ++ case SWITCH_CMD_LIST_VLAN: ++ alist = &dev->ops->attr_vlan; ++ def_list = default_vlan; ++ def_active = &dev->def_vlan; ++ n_def = ARRAY_SIZE(default_vlan); ++ break; ++ case SWITCH_CMD_LIST_PORT: ++ alist = &dev->ops->attr_port; ++ def_list = default_port; ++ def_active = &dev->def_port; ++ n_def = ARRAY_SIZE(default_port); ++ break; ++ default: ++ WARN_ON(1); ++ goto out; ++ } ++ ++ memset(&cb, 0, sizeof(cb)); ++ cb.info = info; ++ cb.fill = swconfig_dump_attr; ++ for (i = 0; i < alist->n_attr; i++) { ++ if (alist->attr[i].disabled) ++ continue; ++ cb.args[0] = i; ++ err = swconfig_send_multipart(&cb, (void *) &alist->attr[i]); ++ if (err < 0) ++ goto error; ++ } ++ ++ /* defaults */ ++ for (i = 0; i < n_def; i++) { ++ if (!test_bit(i, def_active)) ++ continue; ++ cb.args[0] = SWITCH_ATTR_DEFAULTS_OFFSET + i; ++ err = swconfig_send_multipart(&cb, (void *) &def_list[i]); ++ if (err < 0) ++ goto error; ++ } ++ swconfig_put_dev(dev); ++ ++ if (!cb.msg) ++ return 0; ++ ++ return genlmsg_reply(cb.msg, info); ++ ++error: ++ if (cb.msg) ++ nlmsg_free(cb.msg); ++out: ++ swconfig_put_dev(dev); ++ return err; ++} ++ ++static const struct switch_attr * ++swconfig_lookup_attr(struct switch_dev *dev, struct genl_info *info, ++ struct switch_val *val) ++{ ++ struct genlmsghdr *hdr = nlmsg_data(info->nlhdr); ++ const struct switch_attrlist *alist; ++ const struct switch_attr *attr = NULL; ++ int attr_id; ++ ++ /* defaults */ ++ struct switch_attr *def_list; ++ unsigned long *def_active; ++ int n_def; ++ ++ if (!info->attrs[SWITCH_ATTR_OP_ID]) ++ goto done; ++ ++ switch(hdr->cmd) { ++ case SWITCH_CMD_SET_GLOBAL: ++ case SWITCH_CMD_GET_GLOBAL: ++ alist = &dev->ops->attr_global; ++ def_list = default_global; ++ def_active = &dev->def_global; ++ n_def = ARRAY_SIZE(default_global); ++ break; ++ case SWITCH_CMD_SET_VLAN: ++ case SWITCH_CMD_GET_VLAN: ++ alist = &dev->ops->attr_vlan; ++ def_list = default_vlan; ++ def_active = &dev->def_vlan; ++ n_def = ARRAY_SIZE(default_vlan); ++ if (!info->attrs[SWITCH_ATTR_OP_VLAN]) ++ goto done; ++ val->port_vlan = nla_get_u32(info->attrs[SWITCH_ATTR_OP_VLAN]); ++ if (val->port_vlan >= dev->vlans) ++ goto done; ++ break; ++ case SWITCH_CMD_SET_PORT: ++ case SWITCH_CMD_GET_PORT: ++ alist = &dev->ops->attr_port; ++ def_list = default_port; ++ def_active = &dev->def_port; ++ n_def = ARRAY_SIZE(default_port); ++ if (!info->attrs[SWITCH_ATTR_OP_PORT]) ++ goto done; ++ val->port_vlan = nla_get_u32(info->attrs[SWITCH_ATTR_OP_PORT]); ++ if (val->port_vlan >= dev->ports) ++ goto done; ++ break; ++ default: ++ WARN_ON(1); ++ goto done; ++ } ++ ++ if (!alist) ++ goto done; ++ ++ attr_id = nla_get_u32(info->attrs[SWITCH_ATTR_OP_ID]); ++ if (attr_id >= SWITCH_ATTR_DEFAULTS_OFFSET) { ++ attr_id -= SWITCH_ATTR_DEFAULTS_OFFSET; ++ if (attr_id >= n_def) ++ goto done; ++ if (!test_bit(attr_id, def_active)) ++ goto done; ++ attr = &def_list[attr_id]; ++ } else { ++ if (attr_id >= alist->n_attr) ++ goto done; ++ attr = &alist->attr[attr_id]; ++ } ++ ++ if (attr->disabled) ++ attr = NULL; ++ ++done: ++ if (!attr) ++ DPRINTF("attribute lookup failed\n"); ++ val->attr = attr; ++ return attr; ++} ++ ++static int ++swconfig_parse_ports(struct sk_buff *msg, struct nlattr *head, ++ struct switch_val *val, int max) ++{ ++ struct nlattr *nla; ++ int rem; ++ ++ val->len = 0; ++ nla_for_each_nested(nla, head, rem) { ++ struct nlattr *tb[SWITCH_PORT_ATTR_MAX+1]; ++ struct switch_port *port = &val->value.ports[val->len]; ++ ++ if (val->len >= max) ++ return -EINVAL; ++ ++ if (nla_parse_nested(tb, SWITCH_PORT_ATTR_MAX, nla, ++ port_policy)) ++ return -EINVAL; ++ ++ if (!tb[SWITCH_PORT_ID]) ++ return -EINVAL; ++ ++ port->id = nla_get_u32(tb[SWITCH_PORT_ID]); ++ if (tb[SWITCH_PORT_FLAG_TAGGED]) ++ port->flags |= (1 << SWITCH_PORT_FLAG_TAGGED); ++ val->len++; ++ } ++ ++ return 0; ++} ++ ++static int ++swconfig_set_attr(struct sk_buff *skb, struct genl_info *info) ++{ ++ const struct switch_attr *attr; ++ struct switch_dev *dev; ++ struct switch_val val; ++ int err = -EINVAL; ++ ++ dev = swconfig_get_dev(info); ++ if (!dev) ++ return -EINVAL; ++ ++ memset(&val, 0, sizeof(val)); ++ attr = swconfig_lookup_attr(dev, info, &val); ++ if (!attr || !attr->set) ++ goto error; ++ ++ val.attr = attr; ++ switch(attr->type) { ++ case SWITCH_TYPE_NOVAL: ++ break; ++ case SWITCH_TYPE_INT: ++ if (!info->attrs[SWITCH_ATTR_OP_VALUE_INT]) ++ goto error; ++ val.value.i = ++ nla_get_u32(info->attrs[SWITCH_ATTR_OP_VALUE_INT]); ++ break; ++ case SWITCH_TYPE_STRING: ++ if (!info->attrs[SWITCH_ATTR_OP_VALUE_STR]) ++ goto error; ++ val.value.s = ++ nla_data(info->attrs[SWITCH_ATTR_OP_VALUE_STR]); ++ break; ++ case SWITCH_TYPE_PORTS: ++ val.value.ports = dev->portbuf; ++ memset(dev->portbuf, 0, ++ sizeof(struct switch_port) * dev->ports); ++ ++ /* TODO: implement multipart? */ ++ if (info->attrs[SWITCH_ATTR_OP_VALUE_PORTS]) { ++ err = swconfig_parse_ports(skb, ++ info->attrs[SWITCH_ATTR_OP_VALUE_PORTS], &val, dev->ports); ++ if (err < 0) ++ goto error; ++ } else { ++ val.len = 0; ++ err = 0; ++ } ++ break; ++ default: ++ goto error; ++ } ++ ++ err = attr->set(dev, attr, &val); ++error: ++ swconfig_put_dev(dev); ++ return err; ++} ++ ++static int ++swconfig_close_portlist(struct swconfig_callback *cb, void *arg) ++{ ++ if (cb->nest[0]) ++ nla_nest_end(cb->msg, cb->nest[0]); ++ return 0; ++} ++ ++static int ++swconfig_send_port(struct swconfig_callback *cb, void *arg) ++{ ++ const struct switch_port *port = arg; ++ struct nlattr *p = NULL; ++ ++ if (!cb->nest[0]) { ++ cb->nest[0] = nla_nest_start(cb->msg, cb->cmd); ++ if (!cb->nest[0]) ++ return -1; ++ } ++ ++ p = nla_nest_start(cb->msg, SWITCH_ATTR_PORT); ++ if (!p) ++ goto error; ++ ++ NLA_PUT_U32(cb->msg, SWITCH_PORT_ID, port->id); ++ if (port->flags & (1 << SWITCH_PORT_FLAG_TAGGED)) ++ NLA_PUT_FLAG(cb->msg, SWITCH_PORT_FLAG_TAGGED); ++ ++ nla_nest_end(cb->msg, p); ++ return 0; ++ ++nla_put_failure: ++ nla_nest_cancel(cb->msg, p); ++error: ++ nla_nest_cancel(cb->msg, cb->nest[0]); ++ return -1; ++} ++ ++static int ++swconfig_send_ports(struct sk_buff **msg, struct genl_info *info, int attr, ++ const struct switch_val *val) ++{ ++ struct swconfig_callback cb; ++ int err = 0; ++ int i; ++ ++ if (!val->value.ports) ++ return -EINVAL; ++ ++ memset(&cb, 0, sizeof(cb)); ++ cb.cmd = attr; ++ cb.msg = *msg; ++ cb.info = info; ++ cb.fill = swconfig_send_port; ++ cb.close = swconfig_close_portlist; ++ ++ cb.nest[0] = nla_nest_start(cb.msg, cb.cmd); ++ for (i = 0; i < val->len; i++) { ++ err = swconfig_send_multipart(&cb, &val->value.ports[i]); ++ if (err) ++ goto done; ++ } ++ err = val->len; ++ swconfig_close_portlist(&cb, NULL); ++ *msg = cb.msg; ++ ++done: ++ return err; ++} ++ ++static int ++swconfig_get_attr(struct sk_buff *skb, struct genl_info *info) ++{ ++ struct genlmsghdr *hdr = nlmsg_data(info->nlhdr); ++ const struct switch_attr *attr; ++ struct switch_dev *dev; ++ struct sk_buff *msg = NULL; ++ struct switch_val val; ++ int err = -EINVAL; ++ int cmd = hdr->cmd; ++ ++ dev = swconfig_get_dev(info); ++ if (!dev) ++ return -EINVAL; ++ ++ memset(&val, 0, sizeof(val)); ++ attr = swconfig_lookup_attr(dev, info, &val); ++ if (!attr || !attr->get) ++ goto error; ++ ++ if (attr->type == SWITCH_TYPE_PORTS) { ++ val.value.ports = dev->portbuf; ++ memset(dev->portbuf, 0, ++ sizeof(struct switch_port) * dev->ports); ++ } ++ ++ err = attr->get(dev, attr, &val); ++ if (err) ++ goto error; ++ ++ msg = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL); ++ if (!msg) ++ goto error; ++ ++ hdr = genlmsg_put(msg, info->snd_pid, info->snd_seq, &switch_fam, ++ 0, cmd); ++ if (IS_ERR(hdr)) ++ goto nla_put_failure; ++ ++ switch(attr->type) { ++ case SWITCH_TYPE_INT: ++ NLA_PUT_U32(msg, SWITCH_ATTR_OP_VALUE_INT, val.value.i); ++ break; ++ case SWITCH_TYPE_STRING: ++ NLA_PUT_STRING(msg, SWITCH_ATTR_OP_VALUE_STR, val.value.s); ++ break; ++ case SWITCH_TYPE_PORTS: ++ err = swconfig_send_ports(&msg, info, ++ SWITCH_ATTR_OP_VALUE_PORTS, &val); ++ if (err < 0) ++ goto nla_put_failure; ++ break; ++ default: ++ DPRINTF("invalid type in attribute\n"); ++ err = -EINVAL; ++ goto error; ++ } ++ err = genlmsg_end(msg, hdr); ++ if (err < 0) ++ goto nla_put_failure; ++ ++ swconfig_put_dev(dev); ++ return genlmsg_reply(msg, info); ++ ++nla_put_failure: ++ if (msg) ++ nlmsg_free(msg); ++error: ++ swconfig_put_dev(dev); ++ if (!err) ++ err = -ENOMEM; ++ return err; ++} ++ ++static int ++swconfig_send_switch(struct sk_buff *msg, u32 pid, u32 seq, int flags, ++ const struct switch_dev *dev) ++{ ++ void *hdr; ++ ++ hdr = genlmsg_put(msg, pid, seq, &switch_fam, flags, ++ SWITCH_CMD_NEW_ATTR); ++ if (IS_ERR(hdr)) ++ return -1; ++ ++ NLA_PUT_U32(msg, SWITCH_ATTR_ID, dev->id); ++ NLA_PUT_STRING(msg, SWITCH_ATTR_DEV_NAME, dev->devname); ++ NLA_PUT_STRING(msg, SWITCH_ATTR_ALIAS, dev->alias); ++ NLA_PUT_STRING(msg, SWITCH_ATTR_NAME, dev->name); ++ NLA_PUT_U32(msg, SWITCH_ATTR_VLANS, dev->vlans); ++ NLA_PUT_U32(msg, SWITCH_ATTR_PORTS, dev->ports); ++ NLA_PUT_U32(msg, SWITCH_ATTR_CPU_PORT, dev->cpu_port); ++ ++ return genlmsg_end(msg, hdr); ++nla_put_failure: ++ genlmsg_cancel(msg, hdr); ++ return -EMSGSIZE; ++} ++ ++static int swconfig_dump_switches(struct sk_buff *skb, ++ struct netlink_callback *cb) ++{ ++ struct switch_dev *dev; ++ int start = cb->args[0]; ++ int idx = 0; ++ ++ swconfig_lock(); ++ list_for_each_entry(dev, &swdevs, dev_list) { ++ if (++idx <= start) ++ continue; ++ if (swconfig_send_switch(skb, NETLINK_CB(cb->skb).pid, ++ cb->nlh->nlmsg_seq, NLM_F_MULTI, ++ dev) < 0) ++ break; ++ } ++ swconfig_unlock(); ++ cb->args[0] = idx; ++ ++ return skb->len; ++} ++ ++static int ++swconfig_done(struct netlink_callback *cb) ++{ ++ return 0; ++} ++ ++static struct genl_ops swconfig_ops[] = { ++ { ++ .cmd = SWITCH_CMD_LIST_GLOBAL, ++ .doit = swconfig_list_attrs, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_LIST_VLAN, ++ .doit = swconfig_list_attrs, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_LIST_PORT, ++ .doit = swconfig_list_attrs, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_GET_GLOBAL, ++ .doit = swconfig_get_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_GET_VLAN, ++ .doit = swconfig_get_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_GET_PORT, ++ .doit = swconfig_get_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_SET_GLOBAL, ++ .doit = swconfig_set_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_SET_VLAN, ++ .doit = swconfig_set_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_SET_PORT, ++ .doit = swconfig_set_attr, ++ .policy = switch_policy, ++ }, ++ { ++ .cmd = SWITCH_CMD_GET_SWITCH, ++ .dumpit = swconfig_dump_switches, ++ .policy = switch_policy, ++ .done = swconfig_done, ++ } ++}; ++ ++int ++register_switch(struct switch_dev *dev, struct net_device *netdev) ++{ ++ struct switch_dev *sdev; ++ const int max_switches = 8 * sizeof(unsigned long); ++ unsigned long in_use = 0; ++ int i; ++ ++ INIT_LIST_HEAD(&dev->dev_list); ++ if (netdev) { ++ dev->netdev = netdev; ++ if (!dev->alias) ++ dev->alias = netdev->name; ++ } ++ BUG_ON(!dev->alias); ++ ++ if (dev->ports > 0) { ++ dev->portbuf = kzalloc(sizeof(struct switch_port) * dev->ports, ++ GFP_KERNEL); ++ if (!dev->portbuf) ++ return -ENOMEM; ++ } ++ swconfig_defaults_init(dev); ++ spin_lock_init(&dev->lock); ++ swconfig_lock(); ++ dev->id = ++swdev_id; ++ ++ list_for_each_entry(sdev, &swdevs, dev_list) { ++ if (!sscanf(sdev->devname, SWCONFIG_DEVNAME, &i)) ++ continue; ++ if (i < 0 || i > max_switches) ++ continue; ++ ++ set_bit(i, &in_use); ++ } ++ i = find_first_zero_bit(&in_use, max_switches); ++ ++ if (i == max_switches) ++ return -ENFILE; ++ ++ /* fill device name */ ++ snprintf(dev->devname, IFNAMSIZ, SWCONFIG_DEVNAME, i); ++ ++ list_add(&dev->dev_list, &swdevs); ++ swconfig_unlock(); ++ ++ return 0; ++} ++EXPORT_SYMBOL_GPL(register_switch); ++ ++void ++unregister_switch(struct switch_dev *dev) ++{ ++ kfree(dev->portbuf); ++ spin_lock(&dev->lock); ++ swconfig_lock(); ++ list_del(&dev->dev_list); ++ swconfig_unlock(); ++ spin_unlock(&dev->lock); ++} ++EXPORT_SYMBOL_GPL(unregister_switch); ++ ++ ++static int __init ++swconfig_init(void) ++{ ++ int i, err; ++ ++ INIT_LIST_HEAD(&swdevs); ++ err = genl_register_family(&switch_fam); ++ if (err) ++ return err; ++ ++ for (i = 0; i < ARRAY_SIZE(swconfig_ops); i++) { ++ err = genl_register_ops(&switch_fam, &swconfig_ops[i]); ++ if (err) ++ goto unregister; ++ } ++ ++ return 0; ++ ++unregister: ++ genl_unregister_family(&switch_fam); ++ return err; ++} ++ ++static void __exit ++swconfig_exit(void) ++{ ++ genl_unregister_family(&switch_fam); ++} ++ ++module_init(swconfig_init); ++module_exit(swconfig_exit); ++ +diff -Nur linux-2.6.39.orig/drivers/spi/ap83_spi.c linux-2.6.39/drivers/spi/ap83_spi.c +--- linux-2.6.39.orig/drivers/spi/ap83_spi.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/ap83_spi.c 2011-04-27 12:19:22.317665385 +0200 +@@ -0,0 +1,283 @@ ++/* ++ * Atheros AP83 board specific SPI Controller driver ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ * ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++#define DRV_DESC "Atheros AP83 board SPI Controller driver" ++#define DRV_VERSION "0.1.0" ++#define DRV_NAME "ap83-spi" ++ ++#define AP83_SPI_CLK_HIGH (1 << 23) ++#define AP83_SPI_CLK_LOW 0 ++#define AP83_SPI_MOSI_HIGH (1 << 22) ++#define AP83_SPI_MOSI_LOW 0 ++ ++#define AP83_SPI_GPIO_CS 1 ++#define AP83_SPI_GPIO_MISO 3 ++ ++struct ap83_spi { ++ struct spi_bitbang bitbang; ++ void __iomem *base; ++ u32 addr; ++ ++ struct platform_device *pdev; ++}; ++ ++static inline u32 ap83_spi_rr(struct ap83_spi *sp, u32 reg) ++{ ++ return __raw_readl(sp->base + reg); ++} ++ ++static inline struct ap83_spi *spidev_to_sp(struct spi_device *spi) ++{ ++ return spi_master_get_devdata(spi->master); ++} ++ ++static inline void setsck(struct spi_device *spi, int val) ++{ ++ struct ap83_spi *sp = spidev_to_sp(spi); ++ ++ if (val) ++ sp->addr |= AP83_SPI_CLK_HIGH; ++ else ++ sp->addr &= ~AP83_SPI_CLK_HIGH; ++ ++ dev_dbg(&spi->dev, "addr=%08x, SCK set to %s\n", ++ sp->addr, (val) ? "HIGH" : "LOW"); ++ ++ ap83_spi_rr(sp, sp->addr); ++} ++ ++static inline void setmosi(struct spi_device *spi, int val) ++{ ++ struct ap83_spi *sp = spidev_to_sp(spi); ++ ++ if (val) ++ sp->addr |= AP83_SPI_MOSI_HIGH; ++ else ++ sp->addr &= ~AP83_SPI_MOSI_HIGH; ++ ++ dev_dbg(&spi->dev, "addr=%08x, MOSI set to %s\n", ++ sp->addr, (val) ? "HIGH" : "LOW"); ++ ++ ap83_spi_rr(sp, sp->addr); ++} ++ ++static inline u32 getmiso(struct spi_device *spi) ++{ ++ u32 ret; ++ ++ ret = gpio_get_value(AP83_SPI_GPIO_MISO) ? 1 : 0; ++ dev_dbg(&spi->dev, "get MISO: %d\n", ret); ++ ++ return ret; ++} ++ ++static inline void do_spidelay(struct spi_device *spi, unsigned nsecs) ++{ ++ ndelay(nsecs); ++} ++ ++static void ap83_spi_chipselect(struct spi_device *spi, int on) ++{ ++ struct ap83_spi *sp = spidev_to_sp(spi); ++ ++ dev_dbg(&spi->dev, "set CS to %d\n", (on) ? 0 : 1); ++ ++ if (on) { ++ ar71xx_flash_acquire(); ++ ++ sp->addr = 0; ++ ap83_spi_rr(sp, sp->addr); ++ ++ gpio_set_value(AP83_SPI_GPIO_CS, 0); ++ } else { ++ gpio_set_value(AP83_SPI_GPIO_CS, 1); ++ ar71xx_flash_release(); ++ } ++} ++ ++#define spidelay(nsecs) \ ++ do { \ ++ /* Steal the spi_device pointer from our caller. \ ++ * The bitbang-API should probably get fixed here... */ \ ++ do_spidelay(spi, nsecs); \ ++ } while (0) ++ ++#define EXPAND_BITBANG_TXRX ++#include ++#include "spi_bitbang_txrx.h" ++ ++static u32 ap83_spi_txrx_mode0(struct spi_device *spi, ++ unsigned nsecs, u32 word, u8 bits) ++{ ++ dev_dbg(&spi->dev, "TXRX0 word=%08x, bits=%u\n", word, bits); ++ return bitbang_txrx_be_cpha0(spi, nsecs, 0, 0, word, bits); ++} ++ ++static u32 ap83_spi_txrx_mode1(struct spi_device *spi, ++ unsigned nsecs, u32 word, u8 bits) ++{ ++ dev_dbg(&spi->dev, "TXRX1 word=%08x, bits=%u\n", word, bits); ++ return bitbang_txrx_be_cpha1(spi, nsecs, 0, 0, word, bits); ++} ++ ++static u32 ap83_spi_txrx_mode2(struct spi_device *spi, ++ unsigned nsecs, u32 word, u8 bits) ++{ ++ dev_dbg(&spi->dev, "TXRX2 word=%08x, bits=%u\n", word, bits); ++ return bitbang_txrx_be_cpha0(spi, nsecs, 1, 0, word, bits); ++} ++ ++static u32 ap83_spi_txrx_mode3(struct spi_device *spi, ++ unsigned nsecs, u32 word, u8 bits) ++{ ++ dev_dbg(&spi->dev, "TXRX3 word=%08x, bits=%u\n", word, bits); ++ return bitbang_txrx_be_cpha1(spi, nsecs, 1, 0, word, bits); ++} ++ ++static int ap83_spi_probe(struct platform_device *pdev) ++{ ++ struct spi_master *master; ++ struct ap83_spi *sp; ++ struct ap83_spi_platform_data *pdata; ++ struct resource *r; ++ int ret; ++ ++ ret = gpio_request(AP83_SPI_GPIO_MISO, "spi-miso"); ++ if (ret) { ++ dev_err(&pdev->dev, "gpio request failed for MISO\n"); ++ return ret; ++ } ++ ++ ret = gpio_request(AP83_SPI_GPIO_CS, "spi-cs"); ++ if (ret) { ++ dev_err(&pdev->dev, "gpio request failed for CS\n"); ++ goto err_free_miso; ++ } ++ ++ ret = gpio_direction_input(AP83_SPI_GPIO_MISO); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set direction of MISO\n"); ++ goto err_free_cs; ++ } ++ ++ ret = gpio_direction_output(AP83_SPI_GPIO_CS, 0); ++ if (ret) { ++ dev_err(&pdev->dev, "unable to set direction of CS\n"); ++ goto err_free_cs; ++ } ++ ++ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); ++ if (master == NULL) { ++ dev_err(&pdev->dev, "failed to allocate spi master\n"); ++ return -ENOMEM; ++ } ++ ++ sp = spi_master_get_devdata(master); ++ platform_set_drvdata(pdev, sp); ++ ++ pdata = pdev->dev.platform_data; ++ ++ sp->bitbang.master = spi_master_get(master); ++ sp->bitbang.chipselect = ap83_spi_chipselect; ++ sp->bitbang.txrx_word[SPI_MODE_0] = ap83_spi_txrx_mode0; ++ sp->bitbang.txrx_word[SPI_MODE_1] = ap83_spi_txrx_mode1; ++ sp->bitbang.txrx_word[SPI_MODE_2] = ap83_spi_txrx_mode2; ++ sp->bitbang.txrx_word[SPI_MODE_3] = ap83_spi_txrx_mode3; ++ ++ sp->bitbang.master->bus_num = pdev->id; ++ sp->bitbang.master->num_chipselect = 1; ++ ++ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (r == NULL) { ++ ret = -ENOENT; ++ goto err_spi_put; ++ } ++ ++ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); ++ if (!sp->base) { ++ ret = -ENXIO; ++ goto err_spi_put; ++ } ++ ++ ret = spi_bitbang_start(&sp->bitbang); ++ if (!ret) ++ goto err_unmap; ++ ++ dev_info(&pdev->dev, "AP83 SPI adapter at %08x\n", r->start); ++ ++ return 0; ++ ++err_unmap: ++ iounmap(sp->base); ++err_spi_put: ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++err_free_cs: ++ gpio_free(AP83_SPI_GPIO_CS); ++err_free_miso: ++ gpio_free(AP83_SPI_GPIO_MISO); ++ return ret; ++} ++ ++static int ap83_spi_remove(struct platform_device *pdev) ++{ ++ struct ap83_spi *sp = platform_get_drvdata(pdev); ++ ++ spi_bitbang_stop(&sp->bitbang); ++ iounmap(sp->base); ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++ return 0; ++} ++ ++static struct platform_driver ap83_spi_drv = { ++ .probe = ap83_spi_probe, ++ .remove = ap83_spi_remove, ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init ap83_spi_init(void) ++{ ++ return platform_driver_register(&ap83_spi_drv); ++} ++module_init(ap83_spi_init); ++ ++static void __exit ap83_spi_exit(void) ++{ ++ platform_driver_unregister(&ap83_spi_drv); ++} ++module_exit(ap83_spi_exit); ++ ++MODULE_ALIAS("platform:" DRV_NAME); ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/spi/ar71xx_spi.c linux-2.6.39/drivers/spi/ar71xx_spi.c +--- linux-2.6.39.orig/drivers/spi/ar71xx_spi.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/ar71xx_spi.c 2011-04-27 12:19:22.317665385 +0200 +@@ -0,0 +1,283 @@ ++/* ++ * Atheros AR71xx SPI Controller driver ++ * ++ * Copyright (C) 2008-2009 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ * ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++#define DRV_DESC "Atheros AR71xx SPI Controller driver" ++#define DRV_VERSION "0.2.4" ++#define DRV_NAME "ar71xx-spi" ++ ++#undef PER_BIT_READ ++ ++struct ar71xx_spi { ++ struct spi_bitbang bitbang; ++ u32 ioc_base; ++ u32 reg_ctrl; ++ ++ void __iomem *base; ++ ++ struct platform_device *pdev; ++ u32 (*get_ioc_base)(u8 chip_select, int cs_high, ++ int is_on); ++}; ++ ++static inline u32 ar71xx_spi_rr(struct ar71xx_spi *sp, unsigned reg) ++{ ++ return __raw_readl(sp->base + reg); ++} ++ ++static inline void ar71xx_spi_wr(struct ar71xx_spi *sp, unsigned reg, u32 val) ++{ ++ __raw_writel(val, sp->base + reg); ++} ++ ++static inline struct ar71xx_spi *spidev_to_sp(struct spi_device *spi) ++{ ++ return spi_master_get_devdata(spi->master); ++} ++ ++static u32 ar71xx_spi_get_ioc_base(u8 chip_select, int cs_high, int is_on) ++{ ++ u32 ret; ++ ++ if (is_on == AR71XX_SPI_CS_INACTIVE) ++ ret = SPI_IOC_CS_ALL; ++ else ++ ret = SPI_IOC_CS_ALL & ~SPI_IOC_CS(chip_select); ++ ++ return ret; ++} ++ ++static void ar71xx_spi_chipselect(struct spi_device *spi, int value) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ void __iomem *base = sp->base; ++ u32 ioc_base; ++ ++ switch (value) { ++ case BITBANG_CS_INACTIVE: ++ ioc_base = sp->get_ioc_base(spi->chip_select, ++ (spi->mode & SPI_CS_HIGH) != 0, ++ AR71XX_SPI_CS_INACTIVE); ++ __raw_writel(ioc_base, base + SPI_REG_IOC); ++ break; ++ ++ case BITBANG_CS_ACTIVE: ++ ioc_base = sp->get_ioc_base(spi->chip_select, ++ (spi->mode & SPI_CS_HIGH) != 0, ++ AR71XX_SPI_CS_ACTIVE); ++ ++ __raw_writel(ioc_base, base + SPI_REG_IOC); ++ sp->ioc_base = ioc_base; ++ break; ++ } ++} ++ ++static void ar71xx_spi_setup_regs(struct spi_device *spi) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ ++ /* enable GPIO mode */ ++ ar71xx_spi_wr(sp, SPI_REG_FS, SPI_FS_GPIO); ++ ++ /* save CTRL register */ ++ sp->reg_ctrl = ar71xx_spi_rr(sp, SPI_REG_CTRL); ++ ++ /* TODO: setup speed? */ ++ ar71xx_spi_wr(sp, SPI_REG_CTRL, 0x43); ++} ++ ++static void ar71xx_spi_restore_regs(struct spi_device *spi) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ ++ /* restore CTRL register */ ++ ar71xx_spi_wr(sp, SPI_REG_CTRL, sp->reg_ctrl); ++ /* disable GPIO mode */ ++ ar71xx_spi_wr(sp, SPI_REG_FS, 0); ++} ++ ++static int ar71xx_spi_setup(struct spi_device *spi) ++{ ++ int status; ++ ++ if (spi->bits_per_word > 32) ++ return -EINVAL; ++ ++ if (!spi->controller_state) ++ ar71xx_spi_setup_regs(spi); ++ ++ status = spi_bitbang_setup(spi); ++ if (status && !spi->controller_state) ++ ar71xx_spi_restore_regs(spi); ++ ++ return status; ++} ++ ++static void ar71xx_spi_cleanup(struct spi_device *spi) ++{ ++ ar71xx_spi_restore_regs(spi); ++ spi_bitbang_cleanup(spi); ++} ++ ++static u32 ar71xx_spi_txrx_mode0(struct spi_device *spi, unsigned nsecs, ++ u32 word, u8 bits) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ void __iomem *base = sp->base; ++ u32 ioc = sp->ioc_base; ++ u32 ret; ++ ++ /* clock starts at inactive polarity */ ++ for (word <<= (32 - bits); likely(bits); bits--) { ++ u32 out; ++ ++ if (word & (1 << 31)) ++ out = ioc | SPI_IOC_DO; ++ else ++ out = ioc & ~SPI_IOC_DO; ++ ++ /* setup MSB (to slave) on trailing edge */ ++ __raw_writel(out, base + SPI_REG_IOC); ++ ++ __raw_writel(out | SPI_IOC_CLK, base + SPI_REG_IOC); ++ ++ word <<= 1; ++ ++#ifdef PER_BIT_READ ++ /* sample MSB (from slave) on leading edge */ ++ ret = __raw_readl(base + SPI_REG_RDS); ++ __raw_writel(out, base + SPI_REG_IOC); ++#endif ++ ++ } ++ ++#ifndef PER_BIT_READ ++ ret = __raw_readl(base + SPI_REG_RDS); ++#endif ++ return ret; ++} ++ ++static int ar71xx_spi_probe(struct platform_device *pdev) ++{ ++ struct spi_master *master; ++ struct ar71xx_spi *sp; ++ struct ar71xx_spi_platform_data *pdata; ++ struct resource *r; ++ int ret; ++ ++ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); ++ if (master == NULL) { ++ dev_err(&pdev->dev, "failed to allocate spi master\n"); ++ return -ENOMEM; ++ } ++ ++ sp = spi_master_get_devdata(master); ++ platform_set_drvdata(pdev, sp); ++ ++ pdata = pdev->dev.platform_data; ++ ++ master->setup = ar71xx_spi_setup; ++ master->cleanup = ar71xx_spi_cleanup; ++ ++ sp->bitbang.master = spi_master_get(master); ++ sp->bitbang.chipselect = ar71xx_spi_chipselect; ++ sp->bitbang.txrx_word[SPI_MODE_0] = ar71xx_spi_txrx_mode0; ++ sp->bitbang.setup_transfer = spi_bitbang_setup_transfer; ++ ++ sp->get_ioc_base = ar71xx_spi_get_ioc_base; ++ if (pdata) { ++ sp->bitbang.master->bus_num = pdata->bus_num; ++ sp->bitbang.master->num_chipselect = pdata->num_chipselect; ++ if (pdata->get_ioc_base) ++ sp->get_ioc_base = pdata->get_ioc_base; ++ } else { ++ sp->bitbang.master->bus_num = 0; ++ sp->bitbang.master->num_chipselect = 3; ++ } ++ ++ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (r == NULL) { ++ ret = -ENOENT; ++ goto err1; ++ } ++ ++ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); ++ if (!sp->base) { ++ ret = -ENXIO; ++ goto err1; ++ } ++ ++ ret = spi_bitbang_start(&sp->bitbang); ++ if (!ret) ++ return 0; ++ ++ iounmap(sp->base); ++err1: ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++ return ret; ++} ++ ++static int ar71xx_spi_remove(struct platform_device *pdev) ++{ ++ struct ar71xx_spi *sp = platform_get_drvdata(pdev); ++ ++ spi_bitbang_stop(&sp->bitbang); ++ iounmap(sp->base); ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++ return 0; ++} ++ ++static struct platform_driver ar71xx_spi_drv = { ++ .probe = ar71xx_spi_probe, ++ .remove = ar71xx_spi_remove, ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init ar71xx_spi_init(void) ++{ ++ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); ++ return platform_driver_register(&ar71xx_spi_drv); ++} ++module_init(ar71xx_spi_init); ++ ++static void __exit ar71xx_spi_exit(void) ++{ ++ platform_driver_unregister(&ar71xx_spi_drv); ++} ++module_exit(ar71xx_spi_exit); ++ ++MODULE_ALIAS("platform:" DRV_NAME); ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_AUTHOR("Imre Kaloz "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/spi/Kconfig linux-2.6.39/drivers/spi/Kconfig +--- linux-2.6.39.orig/drivers/spi/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/spi/Kconfig 2011-08-23 15:10:24.167989908 +0200 +@@ -67,6 +67,13 @@ + This enables support for the SPI controller present on the + Atheros AR71XX/AR724X/AR913X SoCs. + ++config SPI_AR71XX ++ tristate "Atheros AR71xx SPI Controller" ++ depends on SPI_MASTER && ATHEROS_AR71XX ++ select SPI_BITBANG ++ help ++ This is the SPI contoller driver for Atheros AR71xx. ++ + config SPI_ATMEL + tristate "Atmel SPI Controller" + depends on (ARCH_AT91 || AVR32) +@@ -301,6 +308,12 @@ + config SPI_PXA2XX_PCI + def_bool SPI_PXA2XX && X86_32 && PCI + ++config SPI_RB4XX ++ tristate "Mikrotik RB4XX SPI master" ++ depends on SPI_MASTER && AR71XX_MACH_RB4XX ++ help ++ SPI controller driver for the Mikrotik RB4xx series boards. ++ + config SPI_S3C24XX + tristate "Samsung S3C24XX series SPI" + depends on ARCH_S3C2410 && EXPERIMENTAL +@@ -457,6 +470,13 @@ + sysfs interface, with each line presented as a kind of GPIO + exposing both switch control and diagnostic feedback. + ++config SPI_RB4XX_CPLD ++ tristate "MikroTik RB4XX CPLD driver" ++ depends on AR71XX_MACH_RB4XX ++ help ++ SPI driver for the Xilinx CPLD chip present on the ++ MikroTik RB4xx boards. ++ + # + # Add new SPI protocol masters in alphabetical order above this line + # +diff -Nur linux-2.6.39.orig/drivers/spi/Kconfig.orig linux-2.6.39/drivers/spi/Kconfig.orig +--- linux-2.6.39.orig/drivers/spi/Kconfig.orig 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/Kconfig.orig 2011-08-23 15:10:11.277991848 +0200 +@@ -0,0 +1,482 @@ ++# ++# SPI driver configuration ++# ++# NOTE: the reason this doesn't show SPI slave support is mostly that ++# nobody's needed a slave side API yet. The master-role API is not ++# fully appropriate there, so it'd need some thought to do well. ++# ++menuconfig SPI ++ bool "SPI support" ++ depends on HAS_IOMEM ++ help ++ The "Serial Peripheral Interface" is a low level synchronous ++ protocol. Chips that support SPI can have data transfer rates ++ up to several tens of Mbit/sec. Chips are addressed with a ++ controller and a chipselect. Most SPI slaves don't support ++ dynamic device discovery; some are even write-only or read-only. ++ ++ SPI is widely used by microcontrollers to talk with sensors, ++ eeprom and flash memory, codecs and various other controller ++ chips, analog to digital (and d-to-a) converters, and more. ++ MMC and SD cards can be accessed using SPI protocol; and for ++ DataFlash cards used in MMC sockets, SPI must always be used. ++ ++ SPI is one of a family of similar protocols using a four wire ++ interface (select, clock, data in, data out) including Microwire ++ (half duplex), SSP, SSI, and PSP. This driver framework should ++ work with most such devices and controllers. ++ ++if SPI ++ ++config SPI_DEBUG ++ boolean "Debug support for SPI drivers" ++ depends on DEBUG_KERNEL ++ help ++ Say "yes" to enable debug messaging (like dev_dbg and pr_debug), ++ sysfs, and debugfs support in SPI controller and protocol drivers. ++ ++# ++# MASTER side ... talking to discrete SPI slave chips including microcontrollers ++# ++ ++config SPI_MASTER ++# boolean "SPI Master Support" ++ boolean ++ default SPI ++ help ++ If your system has an master-capable SPI controller (which ++ provides the clock and chipselect), you can enable that ++ controller and the protocol drivers for the SPI slave chips ++ that are connected. ++ ++if SPI_MASTER ++ ++comment "SPI Master Controller Drivers" ++ ++config SPI_ALTERA ++ tristate "Altera SPI Controller" ++ select SPI_BITBANG ++ help ++ This is the driver for the Altera SPI Controller. ++ ++config SPI_ATH79 ++ tristate "Atheros AR71XX/AR724X/AR913X SPI controller driver" ++ depends on ATH79 && GENERIC_GPIO ++ select SPI_BITBANG ++ help ++ This enables support for the SPI controller present on the ++ Atheros AR71XX/AR724X/AR913X SoCs. ++ ++config SPI_AR71XX ++ tristate "Atheros AR71xx SPI Controller" ++ depends on SPI_MASTER && ATHEROS_AR71XX ++ select SPI_BITBANG ++ help ++ This is the SPI contoller driver for Atheros AR71xx. ++ ++config SPI_ATMEL ++ tristate "Atmel SPI Controller" ++ depends on (ARCH_AT91 || AVR32) ++ help ++ This selects a driver for the Atmel SPI Controller, present on ++ many AT32 (AVR32) and AT91 (ARM) chips. ++ ++config SPI_BFIN ++ tristate "SPI controller driver for ADI Blackfin5xx" ++ depends on BLACKFIN ++ help ++ This is the SPI controller master driver for Blackfin 5xx processor. ++ ++config SPI_AU1550 ++ tristate "Au1550/Au12x0 SPI Controller" ++ depends on (SOC_AU1550 || SOC_AU1200) && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ If you say yes to this option, support will be included for the ++ Au1550 SPI controller (may also work with Au1200,Au1210,Au1250). ++ ++ This driver can also be built as a module. If so, the module ++ will be called au1550_spi. ++ ++config SPI_BITBANG ++ tristate "Utilities for Bitbanging SPI masters" ++ help ++ With a few GPIO pins, your system can bitbang the SPI protocol. ++ Select this to get SPI support through I/O pins (GPIO, parallel ++ port, etc). Or, some systems' SPI master controller drivers use ++ this code to manage the per-word or per-transfer accesses to the ++ hardware shift registers. ++ ++ This is library code, and is automatically selected by drivers that ++ need it. You only need to select this explicitly to support driver ++ modules that aren't part of this kernel tree. ++ ++config SPI_BUTTERFLY ++ tristate "Parallel port adapter for AVR Butterfly (DEVELOPMENT)" ++ depends on PARPORT ++ select SPI_BITBANG ++ help ++ This uses a custom parallel port cable to connect to an AVR ++ Butterfly , an ++ inexpensive battery powered microcontroller evaluation board. ++ This same cable can be used to flash new firmware. ++ ++config SPI_COLDFIRE_QSPI ++ tristate "Freescale Coldfire QSPI controller" ++ depends on (M520x || M523x || M5249 || M527x || M528x || M532x) ++ help ++ This enables support for the Coldfire QSPI controller in master ++ mode. ++ ++ This driver can also be built as a module. If so, the module ++ will be called coldfire_qspi. ++ ++config SPI_DAVINCI ++ tristate "Texas Instruments DaVinci/DA8x/OMAP-L/AM1x SoC SPI controller" ++ depends on SPI_MASTER && ARCH_DAVINCI ++ select SPI_BITBANG ++ help ++ SPI master controller for DaVinci/DA8x/OMAP-L/AM1x SPI modules. ++ ++ This driver can also be built as a module. The module will be called ++ davinci_spi. ++ ++config SPI_EP93XX ++ tristate "Cirrus Logic EP93xx SPI controller" ++ depends on ARCH_EP93XX ++ help ++ This enables using the Cirrus EP93xx SPI controller in master ++ mode. ++ ++ To compile this driver as a module, choose M here. The module will be ++ called ep93xx_spi. ++ ++config SPI_GPIO ++ tristate "GPIO-based bitbanging SPI Master" ++ depends on GENERIC_GPIO ++ select SPI_BITBANG ++ help ++ This simple GPIO bitbanging SPI master uses the arch-neutral GPIO ++ interface to manage MOSI, MISO, SCK, and chipselect signals. SPI ++ slaves connected to a bus using this driver are configured as usual, ++ except that the spi_board_info.controller_data holds the GPIO number ++ for the chipselect used by this controller driver. ++ ++ Note that this driver often won't achieve even 1 Mbit/sec speeds, ++ making it unusually slow for SPI. If your platform can inline ++ GPIO operations, you should be able to leverage that for better ++ speed with a custom version of this driver; see the source code. ++ ++config SPI_IMX_VER_IMX1 ++ def_bool y if SOC_IMX1 ++ ++config SPI_IMX_VER_0_0 ++ def_bool y if SOC_IMX21 || SOC_IMX27 ++ ++config SPI_IMX_VER_0_4 ++ def_bool y if SOC_IMX31 ++ ++config SPI_IMX_VER_0_7 ++ def_bool y if ARCH_MX25 || SOC_IMX35 || SOC_IMX51 || SOC_IMX53 ++ ++config SPI_IMX_VER_2_3 ++ def_bool y if SOC_IMX51 || SOC_IMX53 ++ ++config SPI_IMX ++ tristate "Freescale i.MX SPI controllers" ++ depends on ARCH_MXC ++ select SPI_BITBANG ++ default m if IMX_HAVE_PLATFORM_SPI_IMX ++ help ++ This enables using the Freescale i.MX SPI controllers in master ++ mode. ++ ++config SPI_LM70_LLP ++ tristate "Parallel port adapter for LM70 eval board (DEVELOPMENT)" ++ depends on PARPORT && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ This driver supports the NS LM70 LLP Evaluation Board, ++ which interfaces to an LM70 temperature sensor using ++ a parallel port. ++ ++config SPI_MPC52xx ++ tristate "Freescale MPC52xx SPI (non-PSC) controller support" ++ depends on PPC_MPC52xx && SPI ++ select SPI_MASTER_OF ++ help ++ This drivers supports the MPC52xx SPI controller in master SPI ++ mode. ++ ++config SPI_MPC52xx_PSC ++ tristate "Freescale MPC52xx PSC SPI controller" ++ depends on PPC_MPC52xx && EXPERIMENTAL ++ help ++ This enables using the Freescale MPC52xx Programmable Serial ++ Controller in master SPI mode. ++ ++config SPI_MPC512x_PSC ++ tristate "Freescale MPC512x PSC SPI controller" ++ depends on SPI_MASTER && PPC_MPC512x ++ help ++ This enables using the Freescale MPC5121 Programmable Serial ++ Controller in SPI master mode. ++ ++config SPI_FSL_LIB ++ tristate ++ depends on FSL_SOC ++ ++config SPI_FSL_SPI ++ tristate "Freescale SPI controller" ++ depends on FSL_SOC ++ select SPI_FSL_LIB ++ help ++ This enables using the Freescale SPI controllers in master mode. ++ MPC83xx platform uses the controller in cpu mode or CPM/QE mode. ++ MPC8569 uses the controller in QE mode, MPC8610 in cpu mode. ++ ++config SPI_FSL_ESPI ++ tristate "Freescale eSPI controller" ++ depends on FSL_SOC ++ select SPI_FSL_LIB ++ help ++ This enables using the Freescale eSPI controllers in master mode. ++ From MPC8536, 85xx platform uses the controller, and all P10xx, ++ P20xx, P30xx,P40xx, P50xx uses this controller. ++ ++config SPI_OC_TINY ++ tristate "OpenCores tiny SPI" ++ depends on GENERIC_GPIO ++ select SPI_BITBANG ++ help ++ This is the driver for OpenCores tiny SPI master controller. ++ ++config SPI_OMAP_UWIRE ++ tristate "OMAP1 MicroWire" ++ depends on ARCH_OMAP1 ++ select SPI_BITBANG ++ help ++ This hooks up to the MicroWire controller on OMAP1 chips. ++ ++config SPI_OMAP24XX ++ tristate "McSPI driver for OMAP" ++ depends on ARCH_OMAP2PLUS ++ help ++ SPI master controller for OMAP24XX and later Multichannel SPI ++ (McSPI) modules. ++ ++config SPI_OMAP_100K ++ tristate "OMAP SPI 100K" ++ depends on SPI_MASTER && (ARCH_OMAP850 || ARCH_OMAP730) ++ help ++ OMAP SPI 100K master controller for omap7xx boards. ++ ++config SPI_ORION ++ tristate "Orion SPI master (EXPERIMENTAL)" ++ depends on PLAT_ORION && EXPERIMENTAL ++ help ++ This enables using the SPI master controller on the Orion chips. ++ ++config SPI_PL022 ++ tristate "ARM AMBA PL022 SSP controller (EXPERIMENTAL)" ++ depends on ARM_AMBA && EXPERIMENTAL ++ default y if MACH_U300 ++ default y if ARCH_REALVIEW ++ default y if INTEGRATOR_IMPD1 ++ default y if ARCH_VERSATILE ++ help ++ This selects the ARM(R) AMBA(R) PrimeCell PL022 SSP ++ controller. If you have an embedded system with an AMBA(R) ++ bus and a PL022 controller, say Y or M here. ++ ++config SPI_PPC4xx ++ tristate "PPC4xx SPI Controller" ++ depends on PPC32 && 4xx && SPI_MASTER ++ select SPI_BITBANG ++ help ++ This selects a driver for the PPC4xx SPI Controller. ++ ++config SPI_PXA2XX ++ tristate "PXA2xx SSP SPI master" ++ depends on (ARCH_PXA || (X86_32 && PCI)) && EXPERIMENTAL ++ select PXA_SSP if ARCH_PXA ++ help ++ This enables using a PXA2xx or Sodaville SSP port as a SPI master ++ controller. The driver can be configured to use any SSP port and ++ additional documentation can be found a Documentation/spi/pxa2xx. ++ ++config SPI_PXA2XX_PCI ++ def_bool SPI_PXA2XX && X86_32 && PCI ++ ++config SPI_S3C24XX ++ tristate "Samsung S3C24XX series SPI" ++ depends on ARCH_S3C2410 && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ SPI driver for Samsung S3C24XX series ARM SoCs ++ ++config SPI_S3C24XX_FIQ ++ bool "S3C24XX driver with FIQ pseudo-DMA" ++ depends on SPI_S3C24XX ++ select FIQ ++ help ++ Enable FIQ support for the S3C24XX SPI driver to provide pseudo ++ DMA by using the fast-interrupt request framework, This allows ++ the driver to get DMA-like performance when there are either ++ no free DMA channels, or when doing transfers that required both ++ TX and RX data paths. ++ ++config SPI_S3C24XX_GPIO ++ tristate "Samsung S3C24XX series SPI by GPIO" ++ depends on ARCH_S3C2410 && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ SPI driver for Samsung S3C24XX series ARM SoCs using ++ GPIO lines to provide the SPI bus. This can be used where ++ the inbuilt hardware cannot provide the transfer mode, or ++ where the board is using non hardware connected pins. ++ ++config SPI_S3C64XX ++ tristate "Samsung S3C64XX series type SPI" ++ depends on (ARCH_S3C64XX || ARCH_S5P64X0) ++ select S3C64XX_DMA if ARCH_S3C64XX ++ help ++ SPI driver for Samsung S3C64XX and newer SoCs. ++ ++config SPI_SH_MSIOF ++ tristate "SuperH MSIOF SPI controller" ++ depends on SUPERH && HAVE_CLK ++ select SPI_BITBANG ++ help ++ SPI driver for SuperH MSIOF blocks. ++ ++config SPI_SH ++ tristate "SuperH SPI controller" ++ depends on SUPERH ++ help ++ SPI driver for SuperH SPI blocks. ++ ++config SPI_SH_SCI ++ tristate "SuperH SCI SPI controller" ++ depends on SUPERH ++ select SPI_BITBANG ++ help ++ SPI driver for SuperH SCI blocks. ++ ++config SPI_STMP3XXX ++ tristate "Freescale STMP37xx/378x SPI/SSP controller" ++ depends on ARCH_STMP3XXX && SPI_MASTER ++ help ++ SPI driver for Freescale STMP37xx/378x SoC SSP interface ++ ++config SPI_TEGRA ++ tristate "Nvidia Tegra SPI controller" ++ depends on ARCH_TEGRA ++ select TEGRA_SYSTEM_DMA ++ help ++ SPI driver for NVidia Tegra SoCs ++ ++config SPI_TI_SSP ++ tristate "TI Sequencer Serial Port - SPI Support" ++ depends on MFD_TI_SSP ++ help ++ This selects an SPI master implementation using a TI sequencer ++ serial port. ++ ++ To compile this driver as a module, choose M here: the ++ module will be called ti-ssp-spi. ++ ++config SPI_TOPCLIFF_PCH ++ tristate "Topcliff PCH SPI Controller" ++ depends on PCI ++ help ++ SPI driver for the Topcliff PCH (Platform Controller Hub) SPI bus ++ used in some x86 embedded processors. ++ ++config SPI_TXX9 ++ tristate "Toshiba TXx9 SPI controller" ++ depends on GENERIC_GPIO && CPU_TX49XX ++ help ++ SPI driver for Toshiba TXx9 MIPS SoCs ++ ++config SPI_XILINX ++ tristate "Xilinx SPI controller common module" ++ depends on HAS_IOMEM && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ This exposes the SPI controller IP from the Xilinx EDK. ++ ++ See the "OPB Serial Peripheral Interface (SPI) (v1.00e)" ++ Product Specification document (DS464) for hardware details. ++ ++ Or for the DS570, see "XPS Serial Peripheral Interface (SPI) (v2.00b)" ++ ++config SPI_NUC900 ++ tristate "Nuvoton NUC900 series SPI" ++ depends on ARCH_W90X900 && EXPERIMENTAL ++ select SPI_BITBANG ++ help ++ SPI driver for Nuvoton NUC900 series ARM SoCs ++ ++# ++# Add new SPI master controllers in alphabetical order above this line ++# ++ ++config SPI_DESIGNWARE ++ tristate "DesignWare SPI controller core support" ++ depends on SPI_MASTER ++ help ++ general driver for SPI controller core from DesignWare ++ ++config SPI_DW_PCI ++ tristate "PCI interface driver for DW SPI core" ++ depends on SPI_DESIGNWARE && PCI ++ ++config SPI_DW_MID_DMA ++ bool "DMA support for DW SPI controller on Intel Moorestown platform" ++ depends on SPI_DW_PCI && INTEL_MID_DMAC ++ ++config SPI_DW_MMIO ++ tristate "Memory-mapped io interface driver for DW SPI core" ++ depends on SPI_DESIGNWARE && HAVE_CLK ++ ++# ++# There are lots of SPI device types, with sensors and memory ++# being probably the most widely used ones. ++# ++comment "SPI Protocol Masters" ++ ++config SPI_SPIDEV ++ tristate "User mode SPI device driver support" ++ depends on EXPERIMENTAL ++ help ++ This supports user mode SPI protocol drivers. ++ ++ Note that this application programming interface is EXPERIMENTAL ++ and hence SUBJECT TO CHANGE WITHOUT NOTICE while it stabilizes. ++ ++config SPI_TLE62X0 ++ tristate "Infineon TLE62X0 (for power switching)" ++ depends on SYSFS ++ help ++ SPI driver for Infineon TLE62X0 series line driver chips, ++ such as the TLE6220, TLE6230 and TLE6240. This provides a ++ sysfs interface, with each line presented as a kind of GPIO ++ exposing both switch control and diagnostic feedback. ++ ++config SPI_RB4XX_CPLD ++ tristate "MikroTik RB4XX CPLD driver" ++ depends on AR71XX_MACH_RB4XX ++ help ++ SPI driver for the Xilinx CPLD chip present on the ++ MikroTik RB4xx boards. ++ ++# ++# Add new SPI protocol masters in alphabetical order above this line ++# ++ ++endif # SPI_MASTER ++ ++# (slave support would go here) ++ ++endif # SPI +diff -Nur linux-2.6.39.orig/drivers/spi/Makefile linux-2.6.39/drivers/spi/Makefile +--- linux-2.6.39.orig/drivers/spi/Makefile 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/spi/Makefile 2011-08-23 15:10:24.199233941 +0200 +@@ -10,6 +10,7 @@ + + # SPI master controller drivers (bus) + obj-$(CONFIG_SPI_ALTERA) += spi_altera.o ++obj-$(CONFIG_SPI_AR71XX) += ar71xx_spi.o + obj-$(CONFIG_SPI_ATMEL) += atmel_spi.o + obj-$(CONFIG_SPI_ATH79) += ath79_spi.o + obj-$(CONFIG_SPI_BFIN) += spi_bfin5xx.o +@@ -54,6 +55,7 @@ + obj-$(CONFIG_SPI_SH_MSIOF) += spi_sh_msiof.o + obj-$(CONFIG_SPI_STMP3XXX) += spi_stmp.o + obj-$(CONFIG_SPI_NUC900) += spi_nuc900.o ++obj-$(CONFIG_SPI_RB4XX) += rb4xx_spi.o + + # special build for s3c24xx spi driver with fiq support + spi_s3c24xx_hw-y := spi_s3c24xx.o +@@ -62,6 +64,7 @@ + # ... add above this line ... + + # SPI protocol drivers (device/link on bus) ++obj-$(CONFIG_SPI_RB4XX_CPLD) += spi_rb4xx_cpld.o + obj-$(CONFIG_SPI_SPIDEV) += spidev.o + obj-$(CONFIG_SPI_TLE62X0) += tle62x0.o + # ... add above this line ... +diff -Nur linux-2.6.39.orig/drivers/spi/Makefile.orig linux-2.6.39/drivers/spi/Makefile.orig +--- linux-2.6.39.orig/drivers/spi/Makefile.orig 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/Makefile.orig 2011-08-23 15:10:11.300479072 +0200 +@@ -0,0 +1,75 @@ ++# ++# Makefile for kernel SPI drivers. ++# ++ ++ccflags-$(CONFIG_SPI_DEBUG) := -DDEBUG ++ ++# small core, mostly translating board-specific ++# config declarations into driver model code ++obj-$(CONFIG_SPI_MASTER) += spi.o ++ ++# SPI master controller drivers (bus) ++obj-$(CONFIG_SPI_ALTERA) += spi_altera.o ++obj-$(CONFIG_SPI_AR71XX) += ar71xx_spi.o ++obj-$(CONFIG_SPI_ATMEL) += atmel_spi.o ++obj-$(CONFIG_SPI_ATH79) += ath79_spi.o ++obj-$(CONFIG_SPI_BFIN) += spi_bfin5xx.o ++obj-$(CONFIG_SPI_BITBANG) += spi_bitbang.o ++obj-$(CONFIG_SPI_AU1550) += au1550_spi.o ++obj-$(CONFIG_SPI_BUTTERFLY) += spi_butterfly.o ++obj-$(CONFIG_SPI_COLDFIRE_QSPI) += coldfire_qspi.o ++obj-$(CONFIG_SPI_DAVINCI) += davinci_spi.o ++obj-$(CONFIG_SPI_DESIGNWARE) += dw_spi.o ++obj-$(CONFIG_SPI_DW_PCI) += dw_spi_midpci.o ++dw_spi_midpci-objs := dw_spi_pci.o dw_spi_mid.o ++obj-$(CONFIG_SPI_DW_MMIO) += dw_spi_mmio.o ++obj-$(CONFIG_SPI_EP93XX) += ep93xx_spi.o ++obj-$(CONFIG_SPI_GPIO) += spi_gpio.o ++obj-$(CONFIG_SPI_IMX) += spi_imx.o ++obj-$(CONFIG_SPI_LM70_LLP) += spi_lm70llp.o ++obj-$(CONFIG_SPI_PXA2XX) += pxa2xx_spi.o ++obj-$(CONFIG_SPI_PXA2XX_PCI) += pxa2xx_spi_pci.o ++obj-$(CONFIG_SPI_OC_TINY) += spi_oc_tiny.o ++obj-$(CONFIG_SPI_OMAP_UWIRE) += omap_uwire.o ++obj-$(CONFIG_SPI_OMAP24XX) += omap2_mcspi.o ++obj-$(CONFIG_SPI_OMAP_100K) += omap_spi_100k.o ++obj-$(CONFIG_SPI_ORION) += orion_spi.o ++obj-$(CONFIG_SPI_PL022) += amba-pl022.o ++obj-$(CONFIG_SPI_MPC512x_PSC) += mpc512x_psc_spi.o ++obj-$(CONFIG_SPI_MPC52xx_PSC) += mpc52xx_psc_spi.o ++obj-$(CONFIG_SPI_MPC52xx) += mpc52xx_spi.o ++obj-$(CONFIG_SPI_FSL_LIB) += spi_fsl_lib.o ++obj-$(CONFIG_SPI_FSL_ESPI) += spi_fsl_espi.o ++obj-$(CONFIG_SPI_FSL_SPI) += spi_fsl_spi.o ++obj-$(CONFIG_SPI_PPC4xx) += spi_ppc4xx.o ++obj-$(CONFIG_SPI_S3C24XX_GPIO) += spi_s3c24xx_gpio.o ++obj-$(CONFIG_SPI_S3C24XX) += spi_s3c24xx_hw.o ++obj-$(CONFIG_SPI_S3C64XX) += spi_s3c64xx.o ++obj-$(CONFIG_SPI_TEGRA) += spi_tegra.o ++obj-$(CONFIG_SPI_TI_SSP) += ti-ssp-spi.o ++obj-$(CONFIG_SPI_TOPCLIFF_PCH) += spi_topcliff_pch.o ++obj-$(CONFIG_SPI_TXX9) += spi_txx9.o ++obj-$(CONFIG_SPI_XILINX) += xilinx_spi.o ++obj-$(CONFIG_SPI_SH) += spi_sh.o ++obj-$(CONFIG_SPI_SH_SCI) += spi_sh_sci.o ++obj-$(CONFIG_SPI_SH_MSIOF) += spi_sh_msiof.o ++obj-$(CONFIG_SPI_STMP3XXX) += spi_stmp.o ++obj-$(CONFIG_SPI_NUC900) += spi_nuc900.o ++ ++# special build for s3c24xx spi driver with fiq support ++spi_s3c24xx_hw-y := spi_s3c24xx.o ++spi_s3c24xx_hw-$(CONFIG_SPI_S3C24XX_FIQ) += spi_s3c24xx_fiq.o ++ ++# ... add above this line ... ++ ++# SPI protocol drivers (device/link on bus) ++obj-$(CONFIG_SPI_RB4XX_CPLD) += spi_rb4xx_cpld.o ++obj-$(CONFIG_SPI_SPIDEV) += spidev.o ++obj-$(CONFIG_SPI_TLE62X0) += tle62x0.o ++# ... add above this line ... ++ ++# SPI slave controller drivers (upstream link) ++# ... add above this line ... ++ ++# SPI slave drivers (protocol for that link) ++# ... add above this line ... +diff -Nur linux-2.6.39.orig/drivers/spi/pb44_spi.c linux-2.6.39/drivers/spi/pb44_spi.c +--- linux-2.6.39.orig/drivers/spi/pb44_spi.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/pb44_spi.c 2011-04-27 12:19:22.317665385 +0200 +@@ -0,0 +1,299 @@ ++/* ++ * Atheros PB44 board SPI controller driver ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ * ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++#define DRV_DESC "Atheros PB44 SPI Controller driver" ++#define DRV_VERSION "0.1.0" ++#define DRV_NAME "pb44-spi" ++ ++#undef PER_BIT_READ ++ ++struct ar71xx_spi { ++ struct spi_bitbang bitbang; ++ u32 ioc_base; ++ u32 reg_ctrl; ++ ++ void __iomem *base; ++ ++ struct platform_device *pdev; ++}; ++ ++static inline u32 pb44_spi_rr(struct ar71xx_spi *sp, unsigned reg) ++{ ++ return __raw_readl(sp->base + reg); ++} ++ ++static inline void pb44_spi_wr(struct ar71xx_spi *sp, unsigned reg, u32 val) ++{ ++ __raw_writel(val, sp->base + reg); ++} ++ ++static inline struct ar71xx_spi *spidev_to_sp(struct spi_device *spi) ++{ ++ return spi_master_get_devdata(spi->master); ++} ++ ++static void pb44_spi_chipselect(struct spi_device *spi, int is_active) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ int cs_high = (spi->mode & SPI_CS_HIGH) ? is_active : !is_active; ++ ++ if (is_active) { ++ /* set initial clock polarity */ ++ if (spi->mode & SPI_CPOL) ++ sp->ioc_base |= SPI_IOC_CLK; ++ else ++ sp->ioc_base &= ~SPI_IOC_CLK; ++ ++ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); ++ } ++ ++ if (spi->chip_select) { ++ unsigned long gpio = (unsigned long) spi->controller_data; ++ ++ /* SPI is normally active-low */ ++ gpio_set_value(gpio, cs_high); ++ } else { ++ if (cs_high) ++ sp->ioc_base |= SPI_IOC_CS0; ++ else ++ sp->ioc_base &= ~SPI_IOC_CS0; ++ ++ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); ++ } ++ ++} ++ ++static int pb44_spi_setup_cs(struct spi_device *spi) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ ++ /* enable GPIO mode */ ++ pb44_spi_wr(sp, SPI_REG_FS, SPI_FS_GPIO); ++ ++ /* save CTRL register */ ++ sp->reg_ctrl = pb44_spi_rr(sp, SPI_REG_CTRL); ++ sp->ioc_base = pb44_spi_rr(sp, SPI_REG_IOC); ++ ++ /* TODO: setup speed? */ ++ pb44_spi_wr(sp, SPI_REG_CTRL, 0x43); ++ ++ if (spi->chip_select) { ++ unsigned long gpio = (unsigned long) spi->controller_data; ++ int status = 0; ++ ++ status = gpio_request(gpio, dev_name(&spi->dev)); ++ if (status) ++ return status; ++ ++ status = gpio_direction_output(gpio, spi->mode & SPI_CS_HIGH); ++ if (status) { ++ gpio_free(gpio); ++ return status; ++ } ++ } else { ++ if (spi->mode & SPI_CS_HIGH) ++ sp->ioc_base |= SPI_IOC_CS0; ++ else ++ sp->ioc_base &= ~SPI_IOC_CS0; ++ pb44_spi_wr(sp, SPI_REG_IOC, sp->ioc_base); ++ } ++ ++ return 0; ++} ++ ++static void pb44_spi_cleanup_cs(struct spi_device *spi) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ ++ if (spi->chip_select) { ++ unsigned long gpio = (unsigned long) spi->controller_data; ++ gpio_free(gpio); ++ } ++ ++ /* restore CTRL register */ ++ pb44_spi_wr(sp, SPI_REG_CTRL, sp->reg_ctrl); ++ /* disable GPIO mode */ ++ pb44_spi_wr(sp, SPI_REG_FS, 0); ++} ++ ++static int pb44_spi_setup(struct spi_device *spi) ++{ ++ int status = 0; ++ ++ if (spi->bits_per_word > 32) ++ return -EINVAL; ++ ++ if (!spi->controller_state) { ++ status = pb44_spi_setup_cs(spi); ++ if (status) ++ return status; ++ } ++ ++ status = spi_bitbang_setup(spi); ++ if (status && !spi->controller_state) ++ pb44_spi_cleanup_cs(spi); ++ ++ return status; ++} ++ ++static void pb44_spi_cleanup(struct spi_device *spi) ++{ ++ pb44_spi_cleanup_cs(spi); ++ spi_bitbang_cleanup(spi); ++} ++ ++static u32 pb44_spi_txrx_mode0(struct spi_device *spi, unsigned nsecs, ++ u32 word, u8 bits) ++{ ++ struct ar71xx_spi *sp = spidev_to_sp(spi); ++ u32 ioc = sp->ioc_base; ++ u32 ret; ++ ++ /* clock starts at inactive polarity */ ++ for (word <<= (32 - bits); likely(bits); bits--) { ++ u32 out; ++ ++ if (word & (1 << 31)) ++ out = ioc | SPI_IOC_DO; ++ else ++ out = ioc & ~SPI_IOC_DO; ++ ++ /* setup MSB (to slave) on trailing edge */ ++ pb44_spi_wr(sp, SPI_REG_IOC, out); ++ pb44_spi_wr(sp, SPI_REG_IOC, out | SPI_IOC_CLK); ++ ++ word <<= 1; ++ ++#ifdef PER_BIT_READ ++ /* sample MSB (from slave) on leading edge */ ++ ret = pb44_spi_rr(sp, SPI_REG_RDS); ++ pb44_spi_wr(sp, SPI_REG_IOC, out); ++#endif ++ } ++ ++#ifndef PER_BIT_READ ++ ret = pb44_spi_rr(sp, SPI_REG_RDS); ++#endif ++ return ret; ++} ++ ++static int pb44_spi_probe(struct platform_device *pdev) ++{ ++ struct spi_master *master; ++ struct ar71xx_spi *sp; ++ struct ar71xx_spi_platform_data *pdata; ++ struct resource *r; ++ int ret; ++ ++ master = spi_alloc_master(&pdev->dev, sizeof(*sp)); ++ if (master == NULL) { ++ dev_err(&pdev->dev, "failed to allocate spi master\n"); ++ return -ENOMEM; ++ } ++ ++ sp = spi_master_get_devdata(master); ++ platform_set_drvdata(pdev, sp); ++ ++ pdata = pdev->dev.platform_data; ++ ++ master->setup = pb44_spi_setup; ++ master->cleanup = pb44_spi_cleanup; ++ if (pdata) { ++ master->bus_num = pdata->bus_num; ++ master->num_chipselect = pdata->num_chipselect; ++ } else { ++ master->bus_num = 0; ++ master->num_chipselect = 1; ++ } ++ ++ sp->bitbang.master = spi_master_get(master); ++ sp->bitbang.chipselect = pb44_spi_chipselect; ++ sp->bitbang.txrx_word[SPI_MODE_0] = pb44_spi_txrx_mode0; ++ sp->bitbang.setup_transfer = spi_bitbang_setup_transfer; ++ sp->bitbang.flags = SPI_CS_HIGH; ++ ++ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (r == NULL) { ++ ret = -ENOENT; ++ goto err1; ++ } ++ ++ sp->base = ioremap_nocache(r->start, r->end - r->start + 1); ++ if (!sp->base) { ++ ret = -ENXIO; ++ goto err1; ++ } ++ ++ ret = spi_bitbang_start(&sp->bitbang); ++ if (!ret) ++ return 0; ++ ++ iounmap(sp->base); ++err1: ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++ return ret; ++} ++ ++static int pb44_spi_remove(struct platform_device *pdev) ++{ ++ struct ar71xx_spi *sp = platform_get_drvdata(pdev); ++ ++ spi_bitbang_stop(&sp->bitbang); ++ iounmap(sp->base); ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(sp->bitbang.master); ++ ++ return 0; ++} ++ ++static struct platform_driver pb44_spi_drv = { ++ .probe = pb44_spi_probe, ++ .remove = pb44_spi_remove, ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init pb44_spi_init(void) ++{ ++ return platform_driver_register(&pb44_spi_drv); ++} ++module_init(pb44_spi_init); ++ ++static void __exit pb44_spi_exit(void) ++{ ++ platform_driver_unregister(&pb44_spi_drv); ++} ++module_exit(pb44_spi_exit); ++ ++MODULE_ALIAS("platform:" DRV_NAME); ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/spi/rb4xx_spi.c linux-2.6.39/drivers/spi/rb4xx_spi.c +--- linux-2.6.39.orig/drivers/spi/rb4xx_spi.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/rb4xx_spi.c 2011-04-27 12:19:22.307664943 +0200 +@@ -0,0 +1,474 @@ ++/* ++ * SPI controller driver for the Mikrotik RB4xx boards ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This file was based on the patches for Linux 2.6.27.39 published by ++ * MikroTik for their RouterBoard 4xx series devices. ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ * ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++ ++#define DRV_NAME "rb4xx-spi" ++#define DRV_DESC "Mikrotik RB4xx SPI controller driver" ++#define DRV_VERSION "0.1.0" ++ ++#define SPI_CTRL_FASTEST 0x40 ++#define SPI_FLASH_HZ 33333334 ++#define SPI_CPLD_HZ 33333334 ++ ++#define CPLD_CMD_READ_FAST 0x0b ++ ++#undef RB4XX_SPI_DEBUG ++ ++struct rb4xx_spi { ++ void __iomem *base; ++ struct spi_master *master; ++ ++ unsigned spi_ctrl_flash; ++ unsigned spi_ctrl_fread; ++ ++ spinlock_t lock; ++ struct list_head queue; ++ int busy:1; ++ int cs_wait; ++}; ++ ++static unsigned spi_clk_low = SPI_IOC_CS1; ++ ++#ifdef RB4XX_SPI_DEBUG ++static inline void do_spi_delay(void) ++{ ++ ndelay(20000); ++} ++#else ++static inline void do_spi_delay(void) { } ++#endif ++ ++static inline void do_spi_init(struct spi_device *spi) ++{ ++ unsigned cs = SPI_IOC_CS0 | SPI_IOC_CS1; ++ ++ if (!(spi->mode & SPI_CS_HIGH)) ++ cs ^= (spi->chip_select == 2) ? SPI_IOC_CS1 : SPI_IOC_CS0; ++ ++ spi_clk_low = cs; ++} ++ ++static inline void do_spi_finish(void __iomem *base) ++{ ++ do_spi_delay(); ++ __raw_writel(SPI_IOC_CS0 | SPI_IOC_CS1, base + SPI_REG_IOC); ++} ++ ++static inline void do_spi_clk(void __iomem *base, int bit) ++{ ++ unsigned bval = spi_clk_low | ((bit & 1) ? SPI_IOC_DO : 0); ++ ++ do_spi_delay(); ++ __raw_writel(bval, base + SPI_REG_IOC); ++ do_spi_delay(); ++ __raw_writel(bval | SPI_IOC_CLK, base + SPI_REG_IOC); ++} ++ ++static void do_spi_byte(void __iomem *base, unsigned char byte) ++{ ++ do_spi_clk(base, byte >> 7); ++ do_spi_clk(base, byte >> 6); ++ do_spi_clk(base, byte >> 5); ++ do_spi_clk(base, byte >> 4); ++ do_spi_clk(base, byte >> 3); ++ do_spi_clk(base, byte >> 2); ++ do_spi_clk(base, byte >> 1); ++ do_spi_clk(base, byte); ++ ++ pr_debug("spi_byte sent 0x%02x got 0x%02x\n", ++ (unsigned)byte, ++ (unsigned char)__raw_readl(base + SPI_REG_RDS)); ++} ++ ++static inline void do_spi_clk_fast(void __iomem *base, unsigned bit1, ++ unsigned bit2) ++{ ++ unsigned bval = (spi_clk_low | ++ ((bit1 & 1) ? SPI_IOC_DO : 0) | ++ ((bit2 & 1) ? SPI_IOC_CS2 : 0)); ++ do_spi_delay(); ++ __raw_writel(bval, base + SPI_REG_IOC); ++ do_spi_delay(); ++ __raw_writel(bval | SPI_IOC_CLK, base + SPI_REG_IOC); ++} ++ ++static void do_spi_byte_fast(void __iomem *base, unsigned char byte) ++{ ++ do_spi_clk_fast(base, byte >> 7, byte >> 6); ++ do_spi_clk_fast(base, byte >> 5, byte >> 4); ++ do_spi_clk_fast(base, byte >> 3, byte >> 2); ++ do_spi_clk_fast(base, byte >> 1, byte >> 0); ++ ++ pr_debug("spi_byte_fast sent 0x%02x got 0x%02x\n", ++ (unsigned)byte, ++ (unsigned char) __raw_readl(base + SPI_REG_RDS)); ++} ++ ++static int rb4xx_spi_txrx(void __iomem *base, struct spi_transfer *t) ++{ ++ const unsigned char *rxv_ptr = NULL; ++ const unsigned char *tx_ptr = t->tx_buf; ++ unsigned char *rx_ptr = t->rx_buf; ++ unsigned i; ++ ++ pr_debug("spi_txrx len %u tx %u rx %u\n", ++ t->len, ++ (t->tx_buf ? 1 : 0), ++ (t->rx_buf ? 1 : 0)); ++ ++ if (t->verify) { ++ rxv_ptr = tx_ptr; ++ tx_ptr = NULL; ++ } ++ ++ for (i = 0; i < t->len; ++i) { ++ unsigned char sdata = tx_ptr ? tx_ptr[i] : 0; ++ ++ if (t->fast_write) ++ do_spi_byte_fast(base, sdata); ++ else ++ do_spi_byte(base, sdata); ++ ++ if (rx_ptr) { ++ rx_ptr[i] = __raw_readl(base + SPI_REG_RDS) & 0xff; ++ } else if (rxv_ptr) { ++ unsigned char c = __raw_readl(base + SPI_REG_RDS); ++ if (rxv_ptr[i] != c) ++ return i; ++ } ++ } ++ ++ return i; ++} ++ ++static int rb4xx_spi_read_fast(struct rb4xx_spi *rbspi, ++ struct spi_message *m) ++{ ++ struct spi_transfer *t; ++ const unsigned char *tx_ptr; ++ unsigned addr; ++ void __iomem *base = rbspi->base; ++ ++ /* check for exactly two transfers */ ++ if (list_empty(&m->transfers) || ++ list_is_last(m->transfers.next, &m->transfers) || ++ !list_is_last(m->transfers.next->next, &m->transfers)) { ++ return -1; ++ } ++ ++ /* first transfer contains command and address */ ++ t = list_entry(m->transfers.next, ++ struct spi_transfer, transfer_list); ++ ++ if (t->len != 5 || t->tx_buf == NULL) ++ return -1; ++ ++ tx_ptr = t->tx_buf; ++ if (tx_ptr[0] != CPLD_CMD_READ_FAST) ++ return -1; ++ ++ addr = tx_ptr[1]; ++ addr = tx_ptr[2] | (addr << 8); ++ addr = tx_ptr[3] | (addr << 8); ++ addr += (unsigned) base; ++ ++ m->actual_length += t->len; ++ ++ /* second transfer contains data itself */ ++ t = list_entry(m->transfers.next->next, ++ struct spi_transfer, transfer_list); ++ ++ if (t->tx_buf && !t->verify) ++ return -1; ++ ++ __raw_writel(SPI_FS_GPIO, base + SPI_REG_FS); ++ __raw_writel(rbspi->spi_ctrl_fread, base + SPI_REG_CTRL); ++ __raw_writel(0, base + SPI_REG_FS); ++ ++ if (t->rx_buf) { ++ memcpy(t->rx_buf, (const void *)addr, t->len); ++ } else if (t->tx_buf) { ++ unsigned char buf[t->len]; ++ memcpy(buf, (const void *)addr, t->len); ++ if (memcmp(t->tx_buf, buf, t->len) != 0) ++ m->status = -EMSGSIZE; ++ } ++ m->actual_length += t->len; ++ ++ if (rbspi->spi_ctrl_flash != rbspi->spi_ctrl_fread) { ++ __raw_writel(SPI_FS_GPIO, base + SPI_REG_FS); ++ __raw_writel(rbspi->spi_ctrl_flash, base + SPI_REG_CTRL); ++ __raw_writel(0, base + SPI_REG_FS); ++ } ++ ++ return 0; ++} ++ ++static int rb4xx_spi_msg(struct rb4xx_spi *rbspi, struct spi_message *m) ++{ ++ struct spi_transfer *t = NULL; ++ void __iomem *base = rbspi->base; ++ ++ m->status = 0; ++ if (list_empty(&m->transfers)) ++ return -1; ++ ++ if (m->fast_read) ++ if (rb4xx_spi_read_fast(rbspi, m) == 0) ++ return -1; ++ ++ __raw_writel(SPI_FS_GPIO, base + SPI_REG_FS); ++ __raw_writel(SPI_CTRL_FASTEST, base + SPI_REG_CTRL); ++ do_spi_init(m->spi); ++ ++ list_for_each_entry(t, &m->transfers, transfer_list) { ++ int len; ++ ++ len = rb4xx_spi_txrx(base, t); ++ if (len != t->len) { ++ m->status = -EMSGSIZE; ++ break; ++ } ++ m->actual_length += len; ++ ++ if (t->cs_change) { ++ if (list_is_last(&t->transfer_list, &m->transfers)) { ++ /* wait for continuation */ ++ return m->spi->chip_select; ++ } ++ do_spi_finish(base); ++ ndelay(100); ++ } ++ } ++ ++ do_spi_finish(base); ++ __raw_writel(rbspi->spi_ctrl_flash, base + SPI_REG_CTRL); ++ __raw_writel(0, base + SPI_REG_FS); ++ return -1; ++} ++ ++static void rb4xx_spi_process_queue_locked(struct rb4xx_spi *rbspi, ++ unsigned long *flags) ++{ ++ int cs = rbspi->cs_wait; ++ ++ rbspi->busy = 1; ++ while (!list_empty(&rbspi->queue)) { ++ struct spi_message *m; ++ ++ list_for_each_entry(m, &rbspi->queue, queue) ++ if (cs < 0 || cs == m->spi->chip_select) ++ break; ++ ++ if (&m->queue == &rbspi->queue) ++ break; ++ ++ list_del_init(&m->queue); ++ spin_unlock_irqrestore(&rbspi->lock, *flags); ++ ++ cs = rb4xx_spi_msg(rbspi, m); ++ m->complete(m->context); ++ ++ spin_lock_irqsave(&rbspi->lock, *flags); ++ } ++ ++ rbspi->cs_wait = cs; ++ rbspi->busy = 0; ++ ++ if (cs >= 0) { ++ /* TODO: add timer to unlock cs after 1s inactivity */ ++ } ++} ++ ++static int rb4xx_spi_transfer(struct spi_device *spi, ++ struct spi_message *m) ++{ ++ struct rb4xx_spi *rbspi = spi_master_get_devdata(spi->master); ++ unsigned long flags; ++ ++ m->actual_length = 0; ++ m->status = -EINPROGRESS; ++ ++ spin_lock_irqsave(&rbspi->lock, flags); ++ list_add_tail(&m->queue, &rbspi->queue); ++ if (rbspi->busy || ++ (rbspi->cs_wait >= 0 && rbspi->cs_wait != m->spi->chip_select)) { ++ /* job will be done later */ ++ spin_unlock_irqrestore(&rbspi->lock, flags); ++ return 0; ++ } ++ ++ /* process job in current context */ ++ rb4xx_spi_process_queue_locked(rbspi, &flags); ++ spin_unlock_irqrestore(&rbspi->lock, flags); ++ ++ return 0; ++} ++ ++static int rb4xx_spi_setup(struct spi_device *spi) ++{ ++ struct rb4xx_spi *rbspi = spi_master_get_devdata(spi->master); ++ unsigned long flags; ++ ++ if (spi->mode & ~(SPI_CS_HIGH)) { ++ dev_err(&spi->dev, "mode %x not supported\n", ++ (unsigned) spi->mode); ++ return -EINVAL; ++ } ++ ++ if (spi->bits_per_word != 8 && spi->bits_per_word != 0) { ++ dev_err(&spi->dev, "bits_per_word %u not supported\n", ++ (unsigned) spi->bits_per_word); ++ return -EINVAL; ++ } ++ ++ spin_lock_irqsave(&rbspi->lock, flags); ++ if (rbspi->cs_wait == spi->chip_select && !rbspi->busy) { ++ rbspi->cs_wait = -1; ++ rb4xx_spi_process_queue_locked(rbspi, &flags); ++ } ++ spin_unlock_irqrestore(&rbspi->lock, flags); ++ ++ return 0; ++} ++ ++static unsigned get_spi_ctrl(unsigned hz_max, const char *name) ++{ ++ unsigned div; ++ ++ div = (ar71xx_ahb_freq - 1) / (2 * hz_max); ++ ++ /* ++ * CPU has a bug at (div == 0) - first bit read is random ++ */ ++ if (div == 0) ++ ++div; ++ ++ if (name) { ++ unsigned ahb_khz = (ar71xx_ahb_freq + 500) / 1000; ++ unsigned div_real = 2 * (div + 1); ++ pr_debug("rb4xx: %s SPI clock %u kHz (AHB %u kHz / %u)\n", ++ name, ++ ahb_khz / div_real, ++ ahb_khz, div_real); ++ } ++ ++ return SPI_CTRL_FASTEST + div; ++} ++ ++static int rb4xx_spi_probe(struct platform_device *pdev) ++{ ++ struct spi_master *master; ++ struct rb4xx_spi *rbspi; ++ struct resource *r; ++ int err = 0; ++ ++ master = spi_alloc_master(&pdev->dev, sizeof(*rbspi)); ++ if (master == NULL) { ++ dev_err(&pdev->dev, "no memory for spi_master\n"); ++ err = -ENOMEM; ++ goto err_out; ++ } ++ ++ master->bus_num = 0; ++ master->num_chipselect = 3; ++ master->setup = rb4xx_spi_setup; ++ master->transfer = rb4xx_spi_transfer; ++ ++ rbspi = spi_master_get_devdata(master); ++ platform_set_drvdata(pdev, rbspi); ++ ++ r = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (r == NULL) { ++ err = -ENOENT; ++ goto err_put_master; ++ } ++ ++ rbspi->base = ioremap(r->start, r->end - r->start + 1); ++ if (!rbspi->base) { ++ err = -ENXIO; ++ goto err_put_master; ++ } ++ ++ rbspi->master = master; ++ rbspi->spi_ctrl_flash = get_spi_ctrl(SPI_FLASH_HZ, "FLASH"); ++ rbspi->spi_ctrl_fread = get_spi_ctrl(SPI_CPLD_HZ, "CPLD"); ++ rbspi->cs_wait = -1; ++ ++ spin_lock_init(&rbspi->lock); ++ INIT_LIST_HEAD(&rbspi->queue); ++ ++ err = spi_register_master(master); ++ if (err) { ++ dev_err(&pdev->dev, "failed to register SPI master\n"); ++ goto err_iounmap; ++ } ++ ++ return 0; ++ ++err_iounmap: ++ iounmap(rbspi->base); ++err_put_master: ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(master); ++err_out: ++ return err; ++} ++ ++static int rb4xx_spi_remove(struct platform_device *pdev) ++{ ++ struct rb4xx_spi *rbspi = platform_get_drvdata(pdev); ++ ++ iounmap(rbspi->base); ++ platform_set_drvdata(pdev, NULL); ++ spi_master_put(rbspi->master); ++ ++ return 0; ++} ++ ++static struct platform_driver rb4xx_spi_drv = { ++ .probe = rb4xx_spi_probe, ++ .remove = rb4xx_spi_remove, ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init rb4xx_spi_init(void) ++{ ++ return platform_driver_register(&rb4xx_spi_drv); ++} ++subsys_initcall(rb4xx_spi_init); ++ ++static void __exit rb4xx_spi_exit(void) ++{ ++ platform_driver_unregister(&rb4xx_spi_drv); ++} ++ ++module_exit(rb4xx_spi_exit); ++ ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/spi/spi_rb4xx_cpld.c linux-2.6.39/drivers/spi/spi_rb4xx_cpld.c +--- linux-2.6.39.orig/drivers/spi/spi_rb4xx_cpld.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/spi_rb4xx_cpld.c 2011-04-27 12:19:22.317665385 +0200 +@@ -0,0 +1,440 @@ ++/* ++ * SPI driver for the CPLD chip on the Mikrotik RB4xx boards ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This file was based on the patches for Linux 2.6.27.39 published by ++ * MikroTik for their RouterBoard 4xx series devices. ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++ ++#define DRV_NAME "spi-rb4xx-cpld" ++#define DRV_DESC "RB4xx CPLD driver" ++#define DRV_VERSION "0.1.0" ++ ++#define CPLD_CMD_WRITE_NAND 0x08 /* send cmd, n x send data, send indle */ ++#define CPLD_CMD_WRITE_CFG 0x09 /* send cmd, n x send cfg */ ++#define CPLD_CMD_READ_NAND 0x0a /* send cmd, send idle, n x read data */ ++#define CPLD_CMD_READ_FAST 0x0b /* send cmd, 4 x idle, n x read data */ ++#define CPLD_CMD_LED5_ON 0x0c /* send cmd */ ++#define CPLD_CMD_LED5_OFF 0x0d /* send cmd */ ++ ++struct rb4xx_cpld { ++ struct spi_device *spi; ++ struct mutex lock; ++ struct gpio_chip chip; ++ unsigned int config; ++}; ++ ++static struct rb4xx_cpld *rb4xx_cpld; ++ ++static inline struct rb4xx_cpld *gpio_to_cpld(struct gpio_chip *chip) ++{ ++ return container_of(chip, struct rb4xx_cpld, chip); ++} ++ ++static int rb4xx_cpld_write_cmd(struct rb4xx_cpld *cpld, unsigned char cmd) ++{ ++ struct spi_transfer t[1]; ++ struct spi_message m; ++ unsigned char tx_buf[1]; ++ int err; ++ ++ spi_message_init(&m); ++ memset(&t, 0, sizeof(t)); ++ ++ t[0].tx_buf = tx_buf; ++ t[0].len = sizeof(tx_buf); ++ spi_message_add_tail(&t[0], &m); ++ ++ tx_buf[0] = cmd; ++ ++ err = spi_sync(cpld->spi, &m); ++ return err; ++} ++ ++static int rb4xx_cpld_write_cfg(struct rb4xx_cpld *cpld, unsigned char config) ++{ ++ struct spi_transfer t[1]; ++ struct spi_message m; ++ unsigned char cmd[2]; ++ int err; ++ ++ spi_message_init(&m); ++ memset(&t, 0, sizeof(t)); ++ ++ t[0].tx_buf = cmd; ++ t[0].len = sizeof(cmd); ++ spi_message_add_tail(&t[0], &m); ++ ++ cmd[0] = CPLD_CMD_WRITE_CFG; ++ cmd[1] = config; ++ ++ err = spi_sync(cpld->spi, &m); ++ return err; ++} ++ ++static int __rb4xx_cpld_change_cfg(struct rb4xx_cpld *cpld, unsigned mask, ++ unsigned value) ++{ ++ unsigned int config; ++ int err; ++ ++ config = cpld->config & ~mask; ++ config |= value; ++ ++ if ((cpld->config ^ config) & 0xff) { ++ err = rb4xx_cpld_write_cfg(cpld, config); ++ if (err) ++ return err; ++ } ++ ++ if ((cpld->config ^ config) & CPLD_CFG_nLED5) { ++ err = rb4xx_cpld_write_cmd(cpld, (value) ? CPLD_CMD_LED5_ON : ++ CPLD_CMD_LED5_OFF); ++ if (err) ++ return err; ++ } ++ ++ cpld->config = config; ++ return 0; ++} ++ ++int rb4xx_cpld_change_cfg(unsigned mask, unsigned value) ++{ ++ int ret; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ mutex_lock(&rb4xx_cpld->lock); ++ ret = __rb4xx_cpld_change_cfg(rb4xx_cpld, mask, value); ++ mutex_unlock(&rb4xx_cpld->lock); ++ ++ return ret; ++} ++EXPORT_SYMBOL_GPL(rb4xx_cpld_change_cfg); ++ ++int rb4xx_cpld_read_from(unsigned addr, unsigned char *rx_buf, ++ const unsigned char *verify_buf, unsigned count) ++{ ++ const unsigned char cmd[5] = { ++ CPLD_CMD_READ_FAST, ++ (addr >> 16) & 0xff, ++ (addr >> 8) & 0xff, ++ addr & 0xff, ++ 0 ++ }; ++ struct spi_transfer t[2] = { ++ { ++ .tx_buf = &cmd, ++ .len = 5, ++ }, ++ { ++ .tx_buf = verify_buf, ++ .rx_buf = rx_buf, ++ .len = count, ++ .verify = (verify_buf != NULL), ++ }, ++ }; ++ struct spi_message m; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ spi_message_init(&m); ++ m.fast_read = 1; ++ spi_message_add_tail(&t[0], &m); ++ spi_message_add_tail(&t[1], &m); ++ return spi_sync(rb4xx_cpld->spi, &m); ++} ++EXPORT_SYMBOL_GPL(rb4xx_cpld_read_from); ++ ++#if 0 ++int rb4xx_cpld_read(unsigned char *buf, unsigned char *verify_buf, ++ unsigned count) ++{ ++ struct spi_transfer t[2]; ++ struct spi_message m; ++ unsigned char cmd[2]; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ spi_message_init(&m); ++ memset(&t, 0, sizeof(t)); ++ ++ /* send command */ ++ t[0].tx_buf = cmd; ++ t[0].len = sizeof(cmd); ++ spi_message_add_tail(&t[0], &m); ++ ++ cmd[0] = CPLD_CMD_READ_NAND; ++ cmd[1] = 0; ++ ++ /* read data */ ++ t[1].rx_buf = buf; ++ t[1].len = count; ++ spi_message_add_tail(&t[1], &m); ++ ++ return spi_sync(rb4xx_cpld->spi, &m); ++} ++#else ++int rb4xx_cpld_read(unsigned char *rx_buf, const unsigned char *verify_buf, ++ unsigned count) ++{ ++ static const unsigned char cmd[2] = { CPLD_CMD_READ_NAND, 0 }; ++ struct spi_transfer t[2] = { ++ { ++ .tx_buf = &cmd, ++ .len = 2, ++ }, { ++ .tx_buf = verify_buf, ++ .rx_buf = rx_buf, ++ .len = count, ++ .verify = (verify_buf != NULL), ++ }, ++ }; ++ struct spi_message m; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ spi_message_init(&m); ++ spi_message_add_tail(&t[0], &m); ++ spi_message_add_tail(&t[1], &m); ++ return spi_sync(rb4xx_cpld->spi, &m); ++} ++#endif ++EXPORT_SYMBOL_GPL(rb4xx_cpld_read); ++ ++int rb4xx_cpld_write(const unsigned char *buf, unsigned count) ++{ ++#if 0 ++ struct spi_transfer t[3]; ++ struct spi_message m; ++ unsigned char cmd[1]; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ memset(&t, 0, sizeof(t)); ++ spi_message_init(&m); ++ ++ /* send command */ ++ t[0].tx_buf = cmd; ++ t[0].len = sizeof(cmd); ++ spi_message_add_tail(&t[0], &m); ++ ++ cmd[0] = CPLD_CMD_WRITE_NAND; ++ ++ /* write data */ ++ t[1].tx_buf = buf; ++ t[1].len = count; ++ spi_message_add_tail(&t[1], &m); ++ ++ /* send idle */ ++ t[2].len = 1; ++ spi_message_add_tail(&t[2], &m); ++ ++ return spi_sync(rb4xx_cpld->spi, &m); ++#else ++ static const unsigned char cmd = CPLD_CMD_WRITE_NAND; ++ struct spi_transfer t[3] = { ++ { ++ .tx_buf = &cmd, ++ .len = 1, ++ }, { ++ .tx_buf = buf, ++ .len = count, ++ .fast_write = 1, ++ }, { ++ .len = 1, ++ .fast_write = 1, ++ }, ++ }; ++ struct spi_message m; ++ ++ if (rb4xx_cpld == NULL) ++ return -ENODEV; ++ ++ spi_message_init(&m); ++ spi_message_add_tail(&t[0], &m); ++ spi_message_add_tail(&t[1], &m); ++ spi_message_add_tail(&t[2], &m); ++ return spi_sync(rb4xx_cpld->spi, &m); ++#endif ++} ++EXPORT_SYMBOL_GPL(rb4xx_cpld_write); ++ ++static int rb4xx_cpld_gpio_get(struct gpio_chip *chip, unsigned offset) ++{ ++ struct rb4xx_cpld *cpld = gpio_to_cpld(chip); ++ int ret; ++ ++ mutex_lock(&cpld->lock); ++ ret = (cpld->config >> offset) & 1; ++ mutex_unlock(&cpld->lock); ++ ++ return ret; ++} ++ ++static void rb4xx_cpld_gpio_set(struct gpio_chip *chip, unsigned offset, ++ int value) ++{ ++ struct rb4xx_cpld *cpld = gpio_to_cpld(chip); ++ ++ mutex_lock(&cpld->lock); ++ __rb4xx_cpld_change_cfg(cpld, (1 << offset), !!value << offset); ++ mutex_unlock(&cpld->lock); ++} ++ ++static int rb4xx_cpld_gpio_direction_input(struct gpio_chip *chip, ++ unsigned offset) ++{ ++ return -EOPNOTSUPP; ++} ++ ++static int rb4xx_cpld_gpio_direction_output(struct gpio_chip *chip, ++ unsigned offset, ++ int value) ++{ ++ struct rb4xx_cpld *cpld = gpio_to_cpld(chip); ++ int ret; ++ ++ mutex_lock(&cpld->lock); ++ ret = __rb4xx_cpld_change_cfg(cpld, (1 << offset), !!value << offset); ++ mutex_unlock(&cpld->lock); ++ ++ return ret; ++} ++ ++static int rb4xx_cpld_gpio_init(struct rb4xx_cpld *cpld, unsigned int base) ++{ ++ int err; ++ ++ /* init config */ ++ cpld->config = CPLD_CFG_nLED1 | CPLD_CFG_nLED2 | CPLD_CFG_nLED3 | ++ CPLD_CFG_nLED4 | CPLD_CFG_nCE; ++ rb4xx_cpld_write_cfg(cpld, cpld->config); ++ ++ /* setup GPIO chip */ ++ cpld->chip.label = DRV_NAME; ++ ++ cpld->chip.get = rb4xx_cpld_gpio_get; ++ cpld->chip.set = rb4xx_cpld_gpio_set; ++ cpld->chip.direction_input = rb4xx_cpld_gpio_direction_input; ++ cpld->chip.direction_output = rb4xx_cpld_gpio_direction_output; ++ ++ cpld->chip.base = base; ++ cpld->chip.ngpio = CPLD_NUM_GPIOS; ++ cpld->chip.can_sleep = 1; ++ cpld->chip.dev = &cpld->spi->dev; ++ cpld->chip.owner = THIS_MODULE; ++ ++ err = gpiochip_add(&cpld->chip); ++ if (err) ++ dev_err(&cpld->spi->dev, "adding GPIO chip failed, err=%d\n", ++ err); ++ ++ return err; ++} ++ ++static int __devinit rb4xx_cpld_probe(struct spi_device *spi) ++{ ++ struct rb4xx_cpld *cpld; ++ struct rb4xx_cpld_platform_data *pdata; ++ int err; ++ ++ pdata = spi->dev.platform_data; ++ if (!pdata) { ++ dev_dbg(&spi->dev, "no platform data\n"); ++ return -EINVAL; ++ } ++ ++ cpld = kzalloc(sizeof(*cpld), GFP_KERNEL); ++ if (!cpld) { ++ dev_err(&spi->dev, "no memory for private data\n"); ++ return -ENOMEM; ++ } ++ ++ mutex_init(&cpld->lock); ++ cpld->spi = spi_dev_get(spi); ++ dev_set_drvdata(&spi->dev, cpld); ++ ++ spi->mode = SPI_MODE_0; ++ spi->bits_per_word = 8; ++ err = spi_setup(spi); ++ if (err) { ++ dev_err(&spi->dev, "spi_setup failed, err=%d\n", err); ++ goto err_drvdata; ++ } ++ ++ err = rb4xx_cpld_gpio_init(cpld, pdata->gpio_base); ++ if (err) ++ goto err_drvdata; ++ ++ rb4xx_cpld = cpld; ++ ++ return 0; ++ ++err_drvdata: ++ dev_set_drvdata(&spi->dev, NULL); ++ kfree(cpld); ++ ++ return err; ++} ++ ++static int __devexit rb4xx_cpld_remove(struct spi_device *spi) ++{ ++ struct rb4xx_cpld *cpld; ++ ++ rb4xx_cpld = NULL; ++ cpld = dev_get_drvdata(&spi->dev); ++ dev_set_drvdata(&spi->dev, NULL); ++ kfree(cpld); ++ ++ return 0; ++} ++ ++static struct spi_driver rb4xx_cpld_driver = { ++ .driver = { ++ .name = DRV_NAME, ++ .bus = &spi_bus_type, ++ .owner = THIS_MODULE, ++ }, ++ .probe = rb4xx_cpld_probe, ++ .remove = __devexit_p(rb4xx_cpld_remove), ++}; ++ ++static int __init rb4xx_cpld_init(void) ++{ ++ return spi_register_driver(&rb4xx_cpld_driver); ++} ++module_init(rb4xx_cpld_init); ++ ++static void __exit rb4xx_cpld_exit(void) ++{ ++ spi_unregister_driver(&rb4xx_cpld_driver); ++} ++module_exit(rb4xx_cpld_exit); ++ ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); +diff -Nur linux-2.6.39.orig/drivers/spi/spi_vsc7385.c linux-2.6.39/drivers/spi/spi_vsc7385.c +--- linux-2.6.39.orig/drivers/spi/spi_vsc7385.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/spi/spi_vsc7385.c 2011-04-27 12:19:22.317665385 +0200 +@@ -0,0 +1,621 @@ ++/* ++ * SPI driver for the Vitesse VSC7385 ethernet switch ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#define DRV_NAME "spi-vsc7385" ++#define DRV_DESC "Vitesse VSC7385 Gbit ethernet switch driver" ++#define DRV_VERSION "0.1.0" ++ ++#define VSC73XX_BLOCK_MAC 0x1 ++#define VSC73XX_BLOCK_2 0x2 ++#define VSC73XX_BLOCK_MII 0x3 ++#define VSC73XX_BLOCK_4 0x4 ++#define VSC73XX_BLOCK_5 0x5 ++#define VSC73XX_BLOCK_SYSTEM 0x7 ++ ++#define VSC73XX_SUBBLOCK_PORT_0 0 ++#define VSC73XX_SUBBLOCK_PORT_1 1 ++#define VSC73XX_SUBBLOCK_PORT_2 2 ++#define VSC73XX_SUBBLOCK_PORT_3 3 ++#define VSC73XX_SUBBLOCK_PORT_4 4 ++#define VSC73XX_SUBBLOCK_PORT_MAC 6 ++ ++/* MAC Block registers */ ++#define VSC73XX_MAC_CFG 0x0 ++#define VSC73XX_ADVPORTM 0x19 ++#define VSC73XX_RXOCT 0x50 ++#define VSC73XX_TXOCT 0x51 ++#define VSC73XX_C_RX0 0x52 ++#define VSC73XX_C_RX1 0x53 ++#define VSC73XX_C_RX2 0x54 ++#define VSC73XX_C_TX0 0x55 ++#define VSC73XX_C_TX1 0x56 ++#define VSC73XX_C_TX2 0x57 ++#define VSC73XX_C_CFG 0x58 ++ ++/* MAC_CFG register bits */ ++#define VSC73XX_MAC_CFG_WEXC_DIS (1 << 31) ++#define VSC73XX_MAC_CFG_PORT_RST (1 << 29) ++#define VSC73XX_MAC_CFG_TX_EN (1 << 28) ++#define VSC73XX_MAC_CFG_SEED_LOAD (1 << 27) ++#define VSC73XX_MAC_CFG_FDX (1 << 18) ++#define VSC73XX_MAC_CFG_GIGE (1 << 17) ++#define VSC73XX_MAC_CFG_RX_EN (1 << 16) ++#define VSC73XX_MAC_CFG_VLAN_DBLAWR (1 << 15) ++#define VSC73XX_MAC_CFG_VLAN_AWR (1 << 14) ++#define VSC73XX_MAC_CFG_100_BASE_T (1 << 13) ++#define VSC73XX_MAC_CFG_TX_IPG(x) (((x) & 0x1f) << 6) ++#define VSC73XX_MAC_CFG_MAC_RX_RST (1 << 5) ++#define VSC73XX_MAC_CFG_MAC_TX_RST (1 << 4) ++#define VSC73XX_MAC_CFG_BIT2 (1 << 2) ++#define VSC73XX_MAC_CFG_CLK_SEL(x) ((x) & 0x3) ++ ++/* ADVPORTM register bits */ ++#define VSC73XX_ADVPORTM_IFG_PPM (1 << 7) ++#define VSC73XX_ADVPORTM_EXC_COL_CONT (1 << 6) ++#define VSC73XX_ADVPORTM_EXT_PORT (1 << 5) ++#define VSC73XX_ADVPORTM_INV_GTX (1 << 4) ++#define VSC73XX_ADVPORTM_ENA_GTX (1 << 3) ++#define VSC73XX_ADVPORTM_DDR_MODE (1 << 2) ++#define VSC73XX_ADVPORTM_IO_LOOPBACK (1 << 1) ++#define VSC73XX_ADVPORTM_HOST_LOOPBACK (1 << 0) ++ ++/* MII Block registers */ ++#define VSC73XX_MII_STAT 0x0 ++#define VSC73XX_MII_CMD 0x1 ++#define VSC73XX_MII_DATA 0x2 ++ ++/* System Block registers */ ++#define VSC73XX_ICPU_SIPAD 0x01 ++#define VSC73XX_ICPU_CLOCK_DELAY 0x05 ++#define VSC73XX_ICPU_CTRL 0x10 ++#define VSC73XX_ICPU_ADDR 0x11 ++#define VSC73XX_ICPU_SRAM 0x12 ++#define VSC73XX_ICPU_MBOX_VAL 0x15 ++#define VSC73XX_ICPU_MBOX_SET 0x16 ++#define VSC73XX_ICPU_MBOX_CLR 0x17 ++#define VSC73XX_ICPU_CHIPID 0x18 ++#define VSC73XX_ICPU_GPIO 0x34 ++ ++#define VSC73XX_ICPU_CTRL_CLK_DIV (1 << 8) ++#define VSC73XX_ICPU_CTRL_SRST_HOLD (1 << 7) ++#define VSC73XX_ICPU_CTRL_BOOT_EN (1 << 3) ++#define VSC73XX_ICPU_CTRL_EXT_ACC_EN (1 << 2) ++#define VSC73XX_ICPU_CTRL_CLK_EN (1 << 1) ++#define VSC73XX_ICPU_CTRL_SRST (1 << 0) ++ ++#define VSC73XX_ICPU_CHIPID_ID_SHIFT 12 ++#define VSC73XX_ICPU_CHIPID_ID_MASK 0xffff ++#define VSC73XX_ICPU_CHIPID_REV_SHIFT 28 ++#define VSC73XX_ICPU_CHIPID_REV_MASK 0xf ++#define VSC73XX_ICPU_CHIPID_ID_7385 0x7385 ++#define VSC73XX_ICPU_CHIPID_ID_7395 0x7395 ++ ++#define VSC73XX_CMD_MODE_READ 0 ++#define VSC73XX_CMD_MODE_WRITE 1 ++#define VSC73XX_CMD_MODE_SHIFT 4 ++#define VSC73XX_CMD_BLOCK_SHIFT 5 ++#define VSC73XX_CMD_BLOCK_MASK 0x7 ++#define VSC73XX_CMD_SUBBLOCK_MASK 0xf ++ ++#define VSC7385_CLOCK_DELAY ((3 << 4) | 3) ++#define VSC7385_CLOCK_DELAY_MASK ((3 << 4) | 3) ++ ++#define VSC73XX_ICPU_CTRL_STOP (VSC73XX_ICPU_CTRL_SRST_HOLD | \ ++ VSC73XX_ICPU_CTRL_BOOT_EN | \ ++ VSC73XX_ICPU_CTRL_EXT_ACC_EN) ++ ++#define VSC73XX_ICPU_CTRL_START (VSC73XX_ICPU_CTRL_CLK_DIV | \ ++ VSC73XX_ICPU_CTRL_BOOT_EN | \ ++ VSC73XX_ICPU_CTRL_CLK_EN | \ ++ VSC73XX_ICPU_CTRL_SRST) ++ ++#define VSC7385_ADVPORTM_MASK (VSC73XX_ADVPORTM_IFG_PPM | \ ++ VSC73XX_ADVPORTM_EXC_COL_CONT | \ ++ VSC73XX_ADVPORTM_EXT_PORT | \ ++ VSC73XX_ADVPORTM_INV_GTX | \ ++ VSC73XX_ADVPORTM_ENA_GTX | \ ++ VSC73XX_ADVPORTM_DDR_MODE | \ ++ VSC73XX_ADVPORTM_IO_LOOPBACK | \ ++ VSC73XX_ADVPORTM_HOST_LOOPBACK) ++ ++#define VSC7385_ADVPORTM_INIT (VSC73XX_ADVPORTM_EXT_PORT | \ ++ VSC73XX_ADVPORTM_ENA_GTX | \ ++ VSC73XX_ADVPORTM_DDR_MODE) ++ ++#define VSC7385_MAC_CFG_RESET (VSC73XX_MAC_CFG_PORT_RST | \ ++ VSC73XX_MAC_CFG_MAC_RX_RST | \ ++ VSC73XX_MAC_CFG_MAC_TX_RST) ++ ++#define VSC73XX_MAC_CFG_INIT (VSC73XX_MAC_CFG_TX_EN | \ ++ VSC73XX_MAC_CFG_FDX | \ ++ VSC73XX_MAC_CFG_GIGE | \ ++ VSC73XX_MAC_CFG_RX_EN) ++ ++#define VSC73XX_RESET_DELAY 100 ++ ++struct vsc7385 { ++ struct spi_device *spi; ++ struct mutex lock; ++ struct vsc7385_platform_data *pdata; ++}; ++ ++static int vsc7385_is_addr_valid(u8 block, u8 subblock) ++{ ++ switch (block) { ++ case VSC73XX_BLOCK_MAC: ++ switch (subblock) { ++ case 0 ... 4: ++ case 6: ++ return 1; ++ } ++ break; ++ ++ case VSC73XX_BLOCK_2: ++ case VSC73XX_BLOCK_SYSTEM: ++ switch (subblock) { ++ case 0: ++ return 1; ++ } ++ break; ++ ++ case VSC73XX_BLOCK_MII: ++ case VSC73XX_BLOCK_4: ++ case VSC73XX_BLOCK_5: ++ switch (subblock) { ++ case 0 ... 1: ++ return 1; ++ } ++ break; ++ } ++ ++ return 0; ++} ++ ++static inline u8 vsc7385_make_addr(u8 mode, u8 block, u8 subblock) ++{ ++ u8 ret; ++ ++ ret = (block & VSC73XX_CMD_BLOCK_MASK) << VSC73XX_CMD_BLOCK_SHIFT; ++ ret |= (mode & 1) << VSC73XX_CMD_MODE_SHIFT; ++ ret |= subblock & VSC73XX_CMD_SUBBLOCK_MASK; ++ ++ return ret; ++} ++ ++static int vsc7385_read(struct vsc7385 *vsc, u8 block, u8 subblock, u8 reg, ++ u32 *value) ++{ ++ u8 cmd[4]; ++ u8 buf[4]; ++ struct spi_transfer t[2]; ++ struct spi_message m; ++ int err; ++ ++ if (!vsc7385_is_addr_valid(block, subblock)) ++ return -EINVAL; ++ ++ spi_message_init(&m); ++ ++ memset(&t, 0, sizeof(t)); ++ ++ t[0].tx_buf = cmd; ++ t[0].len = sizeof(cmd); ++ spi_message_add_tail(&t[0], &m); ++ ++ t[1].rx_buf = buf; ++ t[1].len = sizeof(buf); ++ spi_message_add_tail(&t[1], &m); ++ ++ cmd[0] = vsc7385_make_addr(VSC73XX_CMD_MODE_READ, block, subblock); ++ cmd[1] = reg; ++ cmd[2] = 0; ++ cmd[3] = 0; ++ ++ mutex_lock(&vsc->lock); ++ err = spi_sync(vsc->spi, &m); ++ mutex_unlock(&vsc->lock); ++ ++ if (err) ++ return err; ++ ++ *value = (((u32) buf[0]) << 24) | (((u32) buf[1]) << 16) | ++ (((u32) buf[2]) << 8) | ((u32) buf[3]); ++ ++ return 0; ++} ++ ++ ++static int vsc7385_write(struct vsc7385 *vsc, u8 block, u8 subblock, u8 reg, ++ u32 value) ++{ ++ u8 cmd[2]; ++ u8 buf[4]; ++ struct spi_transfer t[2]; ++ struct spi_message m; ++ int err; ++ ++ if (!vsc7385_is_addr_valid(block, subblock)) ++ return -EINVAL; ++ ++ spi_message_init(&m); ++ ++ memset(&t, 0, sizeof(t)); ++ ++ t[0].tx_buf = cmd; ++ t[0].len = sizeof(cmd); ++ spi_message_add_tail(&t[0], &m); ++ ++ t[1].tx_buf = buf; ++ t[1].len = sizeof(buf); ++ spi_message_add_tail(&t[1], &m); ++ ++ cmd[0] = vsc7385_make_addr(VSC73XX_CMD_MODE_WRITE, block, subblock); ++ cmd[1] = reg; ++ ++ buf[0] = (value >> 24) & 0xff; ++ buf[1] = (value >> 16) & 0xff; ++ buf[2] = (value >> 8) & 0xff; ++ buf[3] = value & 0xff; ++ ++ mutex_lock(&vsc->lock); ++ err = spi_sync(vsc->spi, &m); ++ mutex_unlock(&vsc->lock); ++ ++ return err; ++} ++ ++static inline int vsc7385_write_verify(struct vsc7385 *vsc, u8 block, ++ u8 subblock, u8 reg, u32 value, ++ u32 read_mask, u32 read_val) ++{ ++ struct spi_device *spi = vsc->spi; ++ u32 t; ++ int err; ++ ++ err = vsc7385_write(vsc, block, subblock, reg, value); ++ if (err) ++ return err; ++ ++ err = vsc7385_read(vsc, block, subblock, reg, &t); ++ if (err) ++ return err; ++ ++ if ((t & read_mask) != read_val) { ++ dev_err(&spi->dev, "register write error\n"); ++ return -EIO; ++ } ++ ++ return 0; ++} ++ ++static inline int vsc7385_set_clock_delay(struct vsc7385 *vsc, u32 val) ++{ ++ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_CLOCK_DELAY, val); ++} ++ ++static inline int vsc7385_get_clock_delay(struct vsc7385 *vsc, u32 *val) ++{ ++ return vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_CLOCK_DELAY, val); ++} ++ ++static inline int vsc7385_icpu_stop(struct vsc7385 *vsc) ++{ ++ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_CTRL, ++ VSC73XX_ICPU_CTRL_STOP); ++} ++ ++static inline int vsc7385_icpu_start(struct vsc7385 *vsc) ++{ ++ return vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_CTRL, ++ VSC73XX_ICPU_CTRL_START); ++} ++ ++static inline int vsc7385_icpu_reset(struct vsc7385 *vsc) ++{ ++ int rc; ++ ++ rc = vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, VSC73XX_ICPU_ADDR, ++ 0x0000); ++ if (rc) ++ dev_err(&vsc->spi->dev, ++ "could not reset microcode, err=%d\n", rc); ++ ++ return rc; ++} ++ ++static int vsc7385_upload_ucode(struct vsc7385 *vsc) ++{ ++ struct spi_device *spi = vsc->spi; ++ const struct firmware *firmware; ++ char *ucode_name; ++ unsigned char *dp; ++ unsigned int curVal; ++ int i; ++ int diffs; ++ int rc; ++ ++ ucode_name = (vsc->pdata->ucode_name) ? vsc->pdata->ucode_name ++ : "vsc7385_ucode.bin"; ++ rc = request_firmware(&firmware, ucode_name, &spi->dev); ++ if (rc) { ++ dev_err(&spi->dev, "request_firmware failed, err=%d\n", ++ rc); ++ return rc; ++ } ++ ++ rc = vsc7385_icpu_stop(vsc); ++ if (rc) ++ goto out; ++ ++ rc = vsc7385_icpu_reset(vsc); ++ if (rc) ++ goto out; ++ ++ dev_info(&spi->dev, "uploading microcode...\n"); ++ ++ dp = (unsigned char *) firmware->data; ++ for (i = 0; i < firmware->size; i++) { ++ rc = vsc7385_write(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_SRAM, *dp++); ++ if (rc) { ++ dev_err(&spi->dev, "could not load microcode, err=%d\n", ++ rc); ++ goto out; ++ } ++ } ++ ++ rc = vsc7385_icpu_reset(vsc); ++ if (rc) ++ goto out; ++ ++ dev_info(&spi->dev, "verifying microcode...\n"); ++ ++ dp = (unsigned char *) firmware->data; ++ diffs = 0; ++ for (i = 0; i < firmware->size; i++) { ++ rc = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_SRAM, &curVal); ++ if (rc) { ++ dev_err(&spi->dev, "could not read microcode %d\n", ++ rc); ++ goto out; ++ } ++ ++ if (curVal > 0xff) { ++ dev_err(&spi->dev, "bad val read: %04x : %02x %02x\n", ++ i, *dp, curVal); ++ rc = -EIO; ++ goto out; ++ } ++ ++ if ((curVal & 0xff) != *dp) { ++ diffs++; ++ dev_err(&spi->dev, "verify error: %04x : %02x %02x\n", ++ i, *dp, curVal); ++ ++ if (diffs > 4) ++ break; ++ } ++ dp++; ++ } ++ ++ if (diffs) { ++ dev_err(&spi->dev, "microcode verification failed\n"); ++ rc = -EIO; ++ goto out; ++ } ++ ++ dev_info(&spi->dev, "microcode uploaded\n"); ++ ++ rc = vsc7385_icpu_start(vsc); ++ ++out: ++ release_firmware(firmware); ++ return rc; ++} ++ ++static int vsc7385_setup(struct vsc7385 *vsc) ++{ ++ struct vsc7385_platform_data *pdata = vsc->pdata; ++ u32 t; ++ int err; ++ ++ err = vsc7385_write_verify(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_CLOCK_DELAY, ++ VSC7385_CLOCK_DELAY, ++ VSC7385_CLOCK_DELAY_MASK, ++ VSC7385_CLOCK_DELAY); ++ if (err) ++ goto err; ++ ++ err = vsc7385_write_verify(vsc, VSC73XX_BLOCK_MAC, ++ VSC73XX_SUBBLOCK_PORT_MAC, VSC73XX_ADVPORTM, ++ VSC7385_ADVPORTM_INIT, ++ VSC7385_ADVPORTM_MASK, ++ VSC7385_ADVPORTM_INIT); ++ if (err) ++ goto err; ++ ++ err = vsc7385_write(vsc, VSC73XX_BLOCK_MAC, VSC73XX_SUBBLOCK_PORT_MAC, ++ VSC73XX_MAC_CFG, VSC7385_MAC_CFG_RESET); ++ if (err) ++ goto err; ++ ++ t = VSC73XX_MAC_CFG_INIT; ++ t |= VSC73XX_MAC_CFG_TX_IPG(pdata->mac_cfg.tx_ipg); ++ t |= VSC73XX_MAC_CFG_CLK_SEL(pdata->mac_cfg.clk_sel); ++ if (pdata->mac_cfg.bit2) ++ t |= VSC73XX_MAC_CFG_BIT2; ++ ++ err = vsc7385_write(vsc, VSC73XX_BLOCK_MAC, VSC73XX_SUBBLOCK_PORT_MAC, ++ VSC73XX_MAC_CFG, t); ++ if (err) ++ goto err; ++ ++ return 0; ++ ++err: ++ return err; ++} ++ ++static int vsc7385_detect(struct vsc7385 *vsc) ++{ ++ struct spi_device *spi = vsc->spi; ++ u32 t; ++ u32 id; ++ u32 rev; ++ int err; ++ ++ err = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_MBOX_VAL, &t); ++ if (err) { ++ dev_err(&spi->dev, "unable to read mailbox, err=%d\n", err); ++ return err; ++ } ++ ++ if (t == 0xffffffff) { ++ dev_dbg(&spi->dev, "assert chip reset\n"); ++ if (vsc->pdata->reset) ++ vsc->pdata->reset(); ++ ++ } ++ ++ err = vsc7385_read(vsc, VSC73XX_BLOCK_SYSTEM, 0, ++ VSC73XX_ICPU_CHIPID, &t); ++ if (err) { ++ dev_err(&spi->dev, "unable to read chip id, err=%d\n", err); ++ return err; ++ } ++ ++ id = (t >> VSC73XX_ICPU_CHIPID_ID_SHIFT) & VSC73XX_ICPU_CHIPID_ID_MASK; ++ switch (id) { ++ case VSC73XX_ICPU_CHIPID_ID_7385: ++ case VSC73XX_ICPU_CHIPID_ID_7395: ++ break; ++ default: ++ dev_err(&spi->dev, "unsupported chip, id=%04x\n", id); ++ return -ENODEV; ++ } ++ ++ rev = (t >> VSC73XX_ICPU_CHIPID_REV_SHIFT) & ++ VSC73XX_ICPU_CHIPID_REV_MASK; ++ dev_info(&spi->dev, "VSC%04X (rev. %d) switch found\n", id, rev); ++ ++ return 0; ++} ++ ++static int __devinit vsc7385_probe(struct spi_device *spi) ++{ ++ struct vsc7385 *vsc; ++ struct vsc7385_platform_data *pdata; ++ int err; ++ ++ printk(KERN_INFO DRV_DESC " version " DRV_VERSION"\n"); ++ ++ pdata = spi->dev.platform_data; ++ if (!pdata) { ++ dev_err(&spi->dev, "no platform data specified\n"); ++ return -ENODEV; ++ } ++ ++ vsc = kzalloc(sizeof(*vsc), GFP_KERNEL); ++ if (!vsc) { ++ dev_err(&spi->dev, "no memory for private data\n"); ++ return -ENOMEM; ++ } ++ ++ mutex_init(&vsc->lock); ++ vsc->pdata = pdata; ++ vsc->spi = spi_dev_get(spi); ++ dev_set_drvdata(&spi->dev, vsc); ++ ++ spi->mode = SPI_MODE_0; ++ spi->bits_per_word = 8; ++ err = spi_setup(spi); ++ if (err) { ++ dev_err(&spi->dev, "spi_setup failed, err=%d\n", err); ++ goto err_drvdata; ++ } ++ ++ err = vsc7385_detect(vsc); ++ if (err) { ++ dev_err(&spi->dev, "no chip found, err=%d\n", err); ++ goto err_drvdata; ++ } ++ ++ err = vsc7385_upload_ucode(vsc); ++ if (err) ++ goto err_drvdata; ++ ++ err = vsc7385_setup(vsc); ++ if (err) ++ goto err_drvdata; ++ ++ return 0; ++ ++err_drvdata: ++ dev_set_drvdata(&spi->dev, NULL); ++ kfree(vsc); ++ return err; ++} ++ ++static int __devexit vsc7385_remove(struct spi_device *spi) ++{ ++ struct vsc7385_data *vsc; ++ ++ vsc = dev_get_drvdata(&spi->dev); ++ dev_set_drvdata(&spi->dev, NULL); ++ kfree(vsc); ++ ++ return 0; ++} ++ ++static struct spi_driver vsc7385_driver = { ++ .driver = { ++ .name = DRV_NAME, ++ .bus = &spi_bus_type, ++ .owner = THIS_MODULE, ++ }, ++ .probe = vsc7385_probe, ++ .remove = __devexit_p(vsc7385_remove), ++}; ++ ++static int __init vsc7385_init(void) ++{ ++ return spi_register_driver(&vsc7385_driver); ++} ++module_init(vsc7385_init); ++ ++static void __exit vsc7385_exit(void) ++{ ++ spi_unregister_driver(&vsc7385_driver); ++} ++module_exit(vsc7385_exit); ++ ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); ++ +diff -Nur linux-2.6.39.orig/drivers/tty/serial/ar933x_uart.c linux-2.6.39/drivers/tty/serial/ar933x_uart.c +--- linux-2.6.39.orig/drivers/tty/serial/ar933x_uart.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/tty/serial/ar933x_uart.c 2011-08-06 09:32:37.098016752 +0200 +@@ -0,0 +1,688 @@ ++/* ++ * Atheros AR933X SoC built-in UART driver ++ * ++ * Copyright (C) 2011 Gabor Juhos ++ * ++ * Based on drivers/char/serial.c, by Linus Torvalds, Theodore Ts'o. ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include ++#include ++ ++#define DRIVER_NAME "ar933x-uart" ++ ++#define AR933X_DUMMY_STATUS_RD 0x01 ++ ++static struct uart_driver ar933x_uart_driver; ++ ++struct ar933x_uart_port { ++ struct uart_port port; ++ unsigned int ier; /* shadow Interrupt Enable Register */ ++}; ++ ++static inline unsigned int ar933x_uart_read(struct ar933x_uart_port *up, ++ int offset) ++{ ++ return readl(up->port.membase + offset); ++} ++ ++static inline void ar933x_uart_write(struct ar933x_uart_port *up, ++ int offset, unsigned int value) ++{ ++ writel(value, up->port.membase + offset); ++} ++ ++static inline void ar933x_uart_rmw(struct ar933x_uart_port *up, ++ unsigned int offset, ++ unsigned int mask, ++ unsigned int val) ++{ ++ unsigned int t; ++ ++ t = ar933x_uart_read(up, offset); ++ t &= ~mask; ++ t |= val; ++ ar933x_uart_write(up, offset, t); ++} ++ ++static inline void ar933x_uart_rmw_set(struct ar933x_uart_port *up, ++ unsigned int offset, ++ unsigned int val) ++{ ++ ar933x_uart_rmw(up, offset, 0, val); ++} ++ ++static inline void ar933x_uart_rmw_clear(struct ar933x_uart_port *up, ++ unsigned int offset, ++ unsigned int val) ++{ ++ ar933x_uart_rmw(up, offset, val, 0); ++} ++ ++static inline void ar933x_uart_start_tx_interrupt(struct ar933x_uart_port *up) ++{ ++ up->ier |= AR933X_UART_INT_TX_EMPTY; ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, up->ier); ++} ++ ++static inline void ar933x_uart_stop_tx_interrupt(struct ar933x_uart_port *up) ++{ ++ up->ier &= ~AR933X_UART_INT_TX_EMPTY; ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, up->ier); ++} ++ ++static inline void ar933x_uart_putc(struct ar933x_uart_port *up, int ch) ++{ ++ unsigned int rdata; ++ ++ rdata = ch & AR933X_UART_DATA_TX_RX_MASK; ++ rdata |= AR933X_UART_DATA_TX_CSR; ++ ar933x_uart_write(up, AR933X_UART_DATA_REG, rdata); ++} ++ ++static unsigned int ar933x_uart_tx_empty(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ unsigned long flags; ++ unsigned int rdata; ++ ++ spin_lock_irqsave(&up->port.lock, flags); ++ rdata = ar933x_uart_read(up, AR933X_UART_DATA_REG); ++ spin_unlock_irqrestore(&up->port.lock, flags); ++ ++ return (rdata & AR933X_UART_DATA_TX_CSR) ? 0 : TIOCSER_TEMT; ++} ++ ++static unsigned int ar933x_uart_get_mctrl(struct uart_port *port) ++{ ++ return TIOCM_CAR; ++} ++ ++static void ar933x_uart_set_mctrl(struct uart_port *port, unsigned int mctrl) ++{ ++} ++ ++static void ar933x_uart_start_tx(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ ++ ar933x_uart_start_tx_interrupt(up); ++} ++ ++static void ar933x_uart_stop_tx(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ ++ ar933x_uart_stop_tx_interrupt(up); ++} ++ ++static void ar933x_uart_stop_rx(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ ++ up->ier &= ~AR933X_UART_INT_RX_VALID; ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, up->ier); ++} ++ ++static void ar933x_uart_break_ctl(struct uart_port *port, int break_state) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ unsigned long flags; ++ ++ spin_lock_irqsave(&up->port.lock, flags); ++ if (break_state == -1) ++ ar933x_uart_rmw_set(up, AR933X_UART_CS_REG, ++ AR933X_UART_CS_TX_BREAK); ++ else ++ ar933x_uart_rmw_clear(up, AR933X_UART_CS_REG, ++ AR933X_UART_CS_TX_BREAK); ++ spin_unlock_irqrestore(&up->port.lock, flags); ++} ++ ++static void ar933x_uart_enable_ms(struct uart_port *port) ++{ ++} ++ ++static void ar933x_uart_set_termios(struct uart_port *port, ++ struct ktermios *new, ++ struct ktermios *old) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ unsigned int cs; ++ unsigned long flags; ++ unsigned int baud, scale; ++ ++ /* Only CS8 is supported */ ++ new->c_cflag &= ~CSIZE; ++ new->c_cflag |= CS8; ++ ++ /* Only one stop bit is supported */ ++ new->c_cflag &= ~CSTOPB; ++ ++ cs = 0; ++ if (new->c_cflag & PARENB) { ++ if (!(new->c_cflag & PARODD)) ++ cs |= AR933X_UART_CS_PARITY_EVEN; ++ else ++ cs |= AR933X_UART_CS_PARITY_ODD; ++ } else { ++ cs |= AR933X_UART_CS_PARITY_NONE; ++ } ++ ++ /* Mark/space parity is not supported */ ++ new->c_cflag &= ~CMSPAR; ++ ++ baud = uart_get_baud_rate(port, new, old, 0, port->uartclk / 16); ++ scale = (port->uartclk / (16 * baud)) - 1; ++ ++ /* ++ * Ok, we're now changing the port state. Do it with ++ * interrupts disabled. ++ */ ++ spin_lock_irqsave(&up->port.lock, flags); ++ ++ /* Update the per-port timeout. */ ++ uart_update_timeout(port, new->c_cflag, baud); ++ ++ up->port.ignore_status_mask = 0; ++ ++ /* ignore all characters if CREAD is not set */ ++ if ((new->c_cflag & CREAD) == 0) ++ up->port.ignore_status_mask |= AR933X_DUMMY_STATUS_RD; ++ ++ ar933x_uart_write(up, AR933X_UART_CLOCK_REG, ++ scale << AR933X_UART_CLOCK_SCALE_S | 8192); ++ ++ /* setup configuration register */ ++ ar933x_uart_rmw(up, AR933X_UART_CS_REG, AR933X_UART_CS_PARITY_M, cs); ++ ++ /* enable host interrupt */ ++ ar933x_uart_rmw_set(up, AR933X_UART_CS_REG, ++ AR933X_UART_CS_HOST_INT_EN); ++ ++ spin_unlock_irqrestore(&up->port.lock, flags); ++ ++ if (tty_termios_baud_rate(new)) ++ tty_termios_encode_baud_rate(new, baud, baud); ++} ++ ++static void ar933x_uart_rx_chars(struct ar933x_uart_port *up) ++{ ++ struct tty_struct *tty; ++ int max_count = 256; ++ ++ tty = tty_port_tty_get(&up->port.state->port); ++ do { ++ unsigned int rdata; ++ unsigned char ch; ++ ++ rdata = ar933x_uart_read(up, AR933X_UART_DATA_REG); ++ if ((rdata & AR933X_UART_DATA_RX_CSR) == 0) ++ break; ++ ++ /* remove the character from the FIFO */ ++ ar933x_uart_write(up, AR933X_UART_DATA_REG, ++ AR933X_UART_DATA_RX_CSR); ++ ++ if (!tty) { ++ /* discard the data if no tty available */ ++ continue; ++ } ++ ++ up->port.icount.rx++; ++ ch = rdata & AR933X_UART_DATA_TX_RX_MASK; ++ ++ if (uart_handle_sysrq_char(&up->port, ch)) ++ continue; ++ ++ if ((up->port.ignore_status_mask & AR933X_DUMMY_STATUS_RD) == 0) ++ tty_insert_flip_char(tty, ch, TTY_NORMAL); ++ } while (max_count-- > 0); ++ ++ if (tty) { ++ tty_flip_buffer_push(tty); ++ tty_kref_put(tty); ++ } ++} ++ ++static void ar933x_uart_tx_chars(struct ar933x_uart_port *up) ++{ ++ struct circ_buf *xmit = &up->port.state->xmit; ++ int count; ++ ++ if (uart_tx_stopped(&up->port)) ++ return; ++ ++ count = up->port.fifosize; ++ do { ++ unsigned int rdata; ++ ++ rdata = ar933x_uart_read(up, AR933X_UART_DATA_REG); ++ if ((rdata & AR933X_UART_DATA_TX_CSR) == 0) ++ break; ++ ++ if (up->port.x_char) { ++ ar933x_uart_putc(up, up->port.x_char); ++ up->port.icount.tx++; ++ up->port.x_char = 0; ++ continue; ++ } ++ ++ if (uart_circ_empty(xmit)) ++ break; ++ ++ ar933x_uart_putc(up, xmit->buf[xmit->tail]); ++ ++ xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE - 1); ++ up->port.icount.tx++; ++ } while (--count > 0); ++ ++ if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) ++ uart_write_wakeup(&up->port); ++ ++ if (!uart_circ_empty(xmit)) ++ ar933x_uart_start_tx_interrupt(up); ++} ++ ++static irqreturn_t ar933x_uart_interrupt(int irq, void *dev_id) ++{ ++ struct ar933x_uart_port *up = dev_id; ++ unsigned int status; ++ ++ status = ar933x_uart_read(up, AR933X_UART_CS_REG); ++ if ((status & AR933X_UART_CS_HOST_INT) == 0) ++ return IRQ_NONE; ++ ++ spin_lock(&up->port.lock); ++ ++ status = ar933x_uart_read(up, AR933X_UART_INT_REG); ++ status &= ar933x_uart_read(up, AR933X_UART_INT_EN_REG); ++ ++ if (status & AR933X_UART_INT_RX_VALID) { ++ ar933x_uart_write(up, AR933X_UART_INT_REG, ++ AR933X_UART_INT_RX_VALID); ++ ar933x_uart_rx_chars(up); ++ } ++ ++ if (status & AR933X_UART_INT_TX_EMPTY) { ++ ar933x_uart_write(up, AR933X_UART_INT_REG, ++ AR933X_UART_INT_TX_EMPTY); ++ ar933x_uart_stop_tx_interrupt(up); ++ ar933x_uart_tx_chars(up); ++ } ++ ++ spin_unlock(&up->port.lock); ++ ++ return IRQ_HANDLED; ++} ++ ++static int ar933x_uart_startup(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ unsigned long flags; ++ int ret; ++ ++ ret = request_irq(up->port.irq, ar933x_uart_interrupt, ++ up->port.irqflags, dev_name(up->port.dev), up); ++ if (ret) ++ return ret; ++ ++ spin_lock_irqsave(&up->port.lock, flags); ++ ++ /* Enable HOST interrupts */ ++ ar933x_uart_rmw_set(up, AR933X_UART_CS_REG, ++ AR933X_UART_CS_HOST_INT_EN); ++ ++ /* Enable RX interrupts */ ++ up->ier = AR933X_UART_INT_RX_VALID; ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, up->ier); ++ ++ spin_unlock_irqrestore(&up->port.lock, flags); ++ ++ return 0; ++} ++ ++static void ar933x_uart_shutdown(struct uart_port *port) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ ++ /* Disable all interrupts */ ++ up->ier = 0; ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, up->ier); ++ ++ /* Disable break condition */ ++ ar933x_uart_rmw_clear(up, AR933X_UART_CS_REG, ++ AR933X_UART_CS_TX_BREAK); ++ ++ free_irq(up->port.irq, up); ++} ++ ++static const char *ar933x_uart_type(struct uart_port *port) ++{ ++ return (port->type == PORT_AR933X) ? "AR933X UART" : NULL; ++} ++ ++static void ar933x_uart_release_port(struct uart_port *port) ++{ ++ /* Nothing to release ... */ ++} ++ ++static int ar933x_uart_request_port(struct uart_port *port) ++{ ++ /* UARTs always present */ ++ return 0; ++} ++ ++static void ar933x_uart_config_port(struct uart_port *port, int flags) ++{ ++ if (flags & UART_CONFIG_TYPE) ++ port->type = PORT_AR933X; ++} ++ ++static int ar933x_uart_verify_port(struct uart_port *port, ++ struct serial_struct *ser) ++{ ++ if (ser->type != PORT_UNKNOWN && ++ ser->type != PORT_AR933X) ++ return -EINVAL; ++ ++ if (ser->irq < 0 || ser->irq >= NR_IRQS) ++ return -EINVAL; ++ ++ if (ser->baud_base < 28800) ++ return -EINVAL; ++ ++ return 0; ++} ++ ++static struct uart_ops ar933x_uart_ops = { ++ .tx_empty = ar933x_uart_tx_empty, ++ .set_mctrl = ar933x_uart_set_mctrl, ++ .get_mctrl = ar933x_uart_get_mctrl, ++ .stop_tx = ar933x_uart_stop_tx, ++ .start_tx = ar933x_uart_start_tx, ++ .stop_rx = ar933x_uart_stop_rx, ++ .enable_ms = ar933x_uart_enable_ms, ++ .break_ctl = ar933x_uart_break_ctl, ++ .startup = ar933x_uart_startup, ++ .shutdown = ar933x_uart_shutdown, ++ .set_termios = ar933x_uart_set_termios, ++ .type = ar933x_uart_type, ++ .release_port = ar933x_uart_release_port, ++ .request_port = ar933x_uart_request_port, ++ .config_port = ar933x_uart_config_port, ++ .verify_port = ar933x_uart_verify_port, ++}; ++ ++#ifdef CONFIG_SERIAL_AR933X_CONSOLE ++ ++static struct ar933x_uart_port * ++ar933x_console_ports[CONFIG_SERIAL_AR933X_NR_UARTS]; ++ ++static void ar933x_uart_wait_xmitr(struct ar933x_uart_port *up) ++{ ++ unsigned int status; ++ unsigned int timeout = 60000; ++ ++ /* Wait up to 60ms for the character(s) to be sent. */ ++ do { ++ status = ar933x_uart_read(up, AR933X_UART_DATA_REG); ++ if (--timeout == 0) ++ break; ++ udelay(1); ++ } while ((status & AR933X_UART_DATA_TX_CSR) == 0); ++} ++ ++static void ar933x_uart_console_putchar(struct uart_port *port, int ch) ++{ ++ struct ar933x_uart_port *up = (struct ar933x_uart_port *) port; ++ ++ ar933x_uart_wait_xmitr(up); ++ ar933x_uart_putc(up, ch); ++} ++ ++static void ar933x_uart_console_write(struct console *co, const char *s, ++ unsigned int count) ++{ ++ struct ar933x_uart_port *up = ar933x_console_ports[co->index]; ++ unsigned long flags; ++ unsigned int int_en; ++ int locked = 1; ++ ++ local_irq_save(flags); ++ ++ if (up->port.sysrq) ++ locked = 0; ++ else if (oops_in_progress) ++ locked = spin_trylock(&up->port.lock); ++ else ++ spin_lock(&up->port.lock); ++ ++ /* ++ * First save the IER then disable the interrupts ++ */ ++ int_en = ar933x_uart_read(up, AR933X_UART_INT_EN_REG); ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, 0); ++ ++ uart_console_write(&up->port, s, count, ar933x_uart_console_putchar); ++ ++ /* ++ * Finally, wait for transmitter to become empty ++ * and restore the IER ++ */ ++ ar933x_uart_wait_xmitr(up); ++ ar933x_uart_write(up, AR933X_UART_INT_EN_REG, int_en); ++ ++ ar933x_uart_write(up, AR933X_UART_INT_REG, AR933X_UART_INT_ALLINTS); ++ ++ if (locked) ++ spin_unlock(&up->port.lock); ++ ++ local_irq_restore(flags); ++} ++ ++static int ar933x_uart_console_setup(struct console *co, char *options) ++{ ++ struct ar933x_uart_port *up; ++ int baud = 115200; ++ int bits = 8; ++ int parity = 'n'; ++ int flow = 'n'; ++ ++ if (co->index < 0 || co->index >= CONFIG_SERIAL_AR933X_NR_UARTS) ++ return -EINVAL; ++ ++ up = ar933x_console_ports[co->index]; ++ if (!up) ++ return -ENODEV; ++ ++ if (options) ++ uart_parse_options(options, &baud, &parity, &bits, &flow); ++ ++ return uart_set_options(&up->port, co, baud, parity, bits, flow); ++} ++ ++static struct console ar933x_uart_console = { ++ .name = "ttyATH", ++ .write = ar933x_uart_console_write, ++ .device = uart_console_device, ++ .setup = ar933x_uart_console_setup, ++ .flags = CON_PRINTBUFFER, ++ .index = -1, ++ .data = &ar933x_uart_driver, ++}; ++ ++static void ar933x_uart_add_console_port(struct ar933x_uart_port *up) ++{ ++ ar933x_console_ports[up->port.line] = up; ++} ++ ++#define AR933X_SERIAL_CONSOLE (&ar933x_uart_console) ++ ++#else ++ ++static inline void ar933x_uart_add_console_port(struct ar933x_uart_port *up) {} ++ ++#define AR933X_SERIAL_CONSOLE NULL ++ ++#endif /* CONFIG_SERIAL_AR933X_CONSOLE */ ++ ++static struct uart_driver ar933x_uart_driver = { ++ .owner = THIS_MODULE, ++ .driver_name = DRIVER_NAME, ++ .dev_name = "ttyATH", ++ .nr = CONFIG_SERIAL_AR933X_NR_UARTS, ++ .cons = AR933X_SERIAL_CONSOLE, ++}; ++ ++static int __devinit ar933x_uart_probe(struct platform_device *pdev) ++{ ++ struct ar933x_uart_platform_data *pdata; ++ struct ar933x_uart_port *up; ++ struct uart_port *port; ++ struct resource *mem_res; ++ struct resource *irq_res; ++ int id; ++ int ret; ++ ++ pdata = pdev->dev.platform_data; ++ if (!pdata) ++ return -EINVAL; ++ ++ id = pdev->id; ++ if (id == -1) ++ id = 0; ++ ++ if (id > CONFIG_SERIAL_AR933X_NR_UARTS) ++ return -EINVAL; ++ ++ mem_res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (!mem_res) { ++ dev_err(&pdev->dev, "no MEM resource\n"); ++ return -EINVAL; ++ } ++ ++ irq_res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); ++ if (!irq_res) { ++ dev_err(&pdev->dev, "no IRQ resource\n"); ++ return -EINVAL; ++ } ++ ++ up = kzalloc(sizeof(struct ar933x_uart_port), GFP_KERNEL); ++ if (!up) ++ return -ENOMEM; ++ ++ port = &up->port; ++ port->mapbase = mem_res->start; ++ ++ port->membase = ioremap(mem_res->start, AR933X_UART_REGS_SIZE); ++ if (!port->membase) { ++ ret = -ENOMEM; ++ goto err_free_up; ++ } ++ ++ port->line = id; ++ port->irq = irq_res->start; ++ port->dev = &pdev->dev; ++ port->type = PORT_AR933X; ++ port->iotype = UPIO_MEM32; ++ port->uartclk = pdata->uartclk; ++ ++ port->regshift = 2; ++ port->fifosize = AR933X_UART_FIFO_SIZE; ++ port->ops = &ar933x_uart_ops; ++ ++ ar933x_uart_add_console_port(up); ++ ++ ret = uart_add_one_port(&ar933x_uart_driver, &up->port); ++ if (ret) ++ goto err_unmap; ++ ++ platform_set_drvdata(pdev, up); ++ return 0; ++ ++err_unmap: ++ iounmap(up->port.membase); ++err_free_up: ++ kfree(up); ++ return ret; ++} ++ ++static int __devexit ar933x_uart_remove(struct platform_device *pdev) ++{ ++ struct ar933x_uart_port *up; ++ ++ up = platform_get_drvdata(pdev); ++ platform_set_drvdata(pdev, NULL); ++ ++ if (up) { ++ uart_remove_one_port(&ar933x_uart_driver, &up->port); ++ iounmap(up->port.membase); ++ kfree(up); ++ } ++ ++ return 0; ++} ++ ++static struct platform_driver ar933x_uart_platform_driver = { ++ .probe = ar933x_uart_probe, ++ .remove = __devexit_p(ar933x_uart_remove), ++ .driver = { ++ .name = DRIVER_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; ++ ++static int __init ar933x_uart_init(void) ++{ ++ int ret; ++ ++ ar933x_uart_driver.nr = CONFIG_SERIAL_AR933X_NR_UARTS; ++ ret = uart_register_driver(&ar933x_uart_driver); ++ if (ret) ++ goto err_out; ++ ++ ret = platform_driver_register(&ar933x_uart_platform_driver); ++ if (ret) ++ goto err_unregister_uart_driver; ++ ++ return 0; ++ ++err_unregister_uart_driver: ++ uart_unregister_driver(&ar933x_uart_driver); ++err_out: ++ return ret; ++} ++ ++static void __exit ar933x_uart_exit(void) ++{ ++ platform_driver_unregister(&ar933x_uart_platform_driver); ++ uart_unregister_driver(&ar933x_uart_driver); ++} ++ ++module_init(ar933x_uart_init); ++module_exit(ar933x_uart_exit); ++ ++MODULE_DESCRIPTION("Atheros AR933X UART driver"); ++MODULE_AUTHOR("Gabor Juhos "); ++MODULE_LICENSE("GPL v2"); ++MODULE_ALIAS("platform:" DRIVER_NAME); +diff -Nur linux-2.6.39.orig/drivers/usb/host/ehci-ar71xx.c linux-2.6.39/drivers/usb/host/ehci-ar71xx.c +--- linux-2.6.39.orig/drivers/usb/host/ehci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/usb/host/ehci-ar71xx.c 2011-04-27 12:19:22.267661616 +0200 +@@ -0,0 +1,242 @@ ++/* ++ * Bus Glue for Atheros AR71xx built-in EHCI controller. ++ * ++ * Copyright (C) 2008-2010 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2007 Atheros Communications, Inc. ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++ ++#include ++ ++extern int usb_disabled(void); ++ ++static int ehci_ar71xx_init(struct usb_hcd *hcd) ++{ ++ struct ehci_hcd *ehci = hcd_to_ehci(hcd); ++ int ret; ++ ++ ehci->caps = hcd->regs; ++ ehci->regs = hcd->regs + ++ HC_LENGTH(ehci_readl(ehci, &ehci->caps->hc_capbase)); ++ ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params); ++ ++ ehci->sbrn = 0x20; ++ ehci->has_synopsys_hc_bug = 1; ++ ++ ehci_reset(ehci); ++ ++ ret = ehci_init(hcd); ++ if (ret) ++ return ret; ++ ++ ehci_port_power(ehci, 0); ++ ++ return 0; ++} ++ ++static int ehci_ar91xx_init(struct usb_hcd *hcd) ++{ ++ struct ehci_hcd *ehci = hcd_to_ehci(hcd); ++ int ret; ++ ++ ehci->caps = hcd->regs + 0x100; ++ ehci->regs = hcd->regs + 0x100 + ++ HC_LENGTH(ehci_readl(ehci, &ehci->caps->hc_capbase)); ++ ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params); ++ ++ hcd->has_tt = 1; ++ ehci->sbrn = 0x20; ++ ++ ehci_reset(ehci); ++ ++ ret = ehci_init(hcd); ++ if (ret) ++ return ret; ++ ++ ehci_port_power(ehci, 0); ++ ++ return 0; ++} ++ ++static int ehci_ar71xx_probe(const struct hc_driver *driver, ++ struct usb_hcd **hcd_out, ++ struct platform_device *pdev) ++{ ++ struct usb_hcd *hcd; ++ struct resource *res; ++ int irq; ++ int ret; ++ ++ res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); ++ if (!res) { ++ dev_dbg(&pdev->dev, "no IRQ specified for %s\n", ++ dev_name(&pdev->dev)); ++ return -ENODEV; ++ } ++ irq = res->start; ++ ++ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (!res) { ++ dev_dbg(&pdev->dev, "no base address specified for %s\n", ++ dev_name(&pdev->dev)); ++ return -ENODEV; ++ } ++ ++ hcd = usb_create_hcd(driver, &pdev->dev, dev_name(&pdev->dev)); ++ if (!hcd) ++ return -ENOMEM; ++ ++ hcd->rsrc_start = res->start; ++ hcd->rsrc_len = res->end - res->start + 1; ++ ++ if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { ++ dev_dbg(&pdev->dev, "controller already in use\n"); ++ ret = -EBUSY; ++ goto err_put_hcd; ++ } ++ ++ hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len); ++ if (!hcd->regs) { ++ dev_dbg(&pdev->dev, "error mapping memory\n"); ++ ret = -EFAULT; ++ goto err_release_region; ++ } ++ ++ ret = usb_add_hcd(hcd, irq, IRQF_DISABLED | IRQF_SHARED); ++ if (ret) ++ goto err_iounmap; ++ ++ return 0; ++ ++err_iounmap: ++ iounmap(hcd->regs); ++ ++err_release_region: ++ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); ++err_put_hcd: ++ usb_put_hcd(hcd); ++ return ret; ++} ++ ++static void ehci_ar71xx_remove(struct usb_hcd *hcd, ++ struct platform_device *pdev) ++{ ++ usb_remove_hcd(hcd); ++ iounmap(hcd->regs); ++ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); ++ usb_put_hcd(hcd); ++} ++ ++static const struct hc_driver ehci_ar71xx_hc_driver = { ++ .description = hcd_name, ++ .product_desc = "Atheros AR71xx built-in EHCI controller", ++ .hcd_priv_size = sizeof(struct ehci_hcd), ++ ++ .irq = ehci_irq, ++ .flags = HCD_MEMORY | HCD_USB2, ++ ++ .reset = ehci_ar71xx_init, ++ .start = ehci_run, ++ .stop = ehci_stop, ++ .shutdown = ehci_shutdown, ++ ++ .urb_enqueue = ehci_urb_enqueue, ++ .urb_dequeue = ehci_urb_dequeue, ++ .endpoint_disable = ehci_endpoint_disable, ++ .endpoint_reset = ehci_endpoint_reset, ++ ++ .get_frame_number = ehci_get_frame, ++ ++ .hub_status_data = ehci_hub_status_data, ++ .hub_control = ehci_hub_control, ++#ifdef CONFIG_PM ++ .hub_suspend = ehci_hub_suspend, ++ .hub_resume = ehci_hub_resume, ++#endif ++ .relinquish_port = ehci_relinquish_port, ++ .port_handed_over = ehci_port_handed_over, ++ ++ .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete, ++}; ++ ++static const struct hc_driver ehci_ar91xx_hc_driver = { ++ .description = hcd_name, ++ .product_desc = "Atheros AR91xx built-in EHCI controller", ++ .hcd_priv_size = sizeof(struct ehci_hcd), ++ .irq = ehci_irq, ++ .flags = HCD_MEMORY | HCD_USB2, ++ ++ .reset = ehci_ar91xx_init, ++ .start = ehci_run, ++ .stop = ehci_stop, ++ .shutdown = ehci_shutdown, ++ ++ .urb_enqueue = ehci_urb_enqueue, ++ .urb_dequeue = ehci_urb_dequeue, ++ .endpoint_disable = ehci_endpoint_disable, ++ .endpoint_reset = ehci_endpoint_reset, ++ ++ .get_frame_number = ehci_get_frame, ++ ++ .hub_status_data = ehci_hub_status_data, ++ .hub_control = ehci_hub_control, ++#ifdef CONFIG_PM ++ .hub_suspend = ehci_hub_suspend, ++ .hub_resume = ehci_hub_resume, ++#endif ++ .relinquish_port = ehci_relinquish_port, ++ .port_handed_over = ehci_port_handed_over, ++ ++ .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete, ++}; ++ ++static int ehci_ar71xx_driver_probe(struct platform_device *pdev) ++{ ++ struct ar71xx_ehci_platform_data *pdata; ++ struct usb_hcd *hcd = NULL; ++ int ret; ++ ++ if (usb_disabled()) ++ return -ENODEV; ++ ++ pdata = pdev->dev.platform_data; ++ if (!pdata) { ++ dev_err(&pdev->dev, "no platform data specified for %s\n", ++ dev_name(&pdev->dev)); ++ return -ENODEV; ++ } ++ ++ if (pdata->is_ar91xx) ++ ret = ehci_ar71xx_probe(&ehci_ar91xx_hc_driver, &hcd, pdev); ++ else ++ ret = ehci_ar71xx_probe(&ehci_ar71xx_hc_driver, &hcd, pdev); ++ ++ return ret; ++} ++ ++static int ehci_ar71xx_driver_remove(struct platform_device *pdev) ++{ ++ struct usb_hcd *hcd = platform_get_drvdata(pdev); ++ ++ ehci_ar71xx_remove(hcd, pdev); ++ return 0; ++} ++ ++MODULE_ALIAS("platform:ar71xx-ehci"); ++ ++static struct platform_driver ehci_ar71xx_driver = { ++ .probe = ehci_ar71xx_driver_probe, ++ .remove = ehci_ar71xx_driver_remove, ++ .driver = { ++ .name = "ar71xx-ehci", ++ } ++}; +diff -Nur linux-2.6.39.orig/drivers/usb/host/ehci-hcd.c linux-2.6.39/drivers/usb/host/ehci-hcd.c +--- linux-2.6.39.orig/drivers/usb/host/ehci-hcd.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/usb/host/ehci-hcd.c 2011-08-22 16:21:42.807985568 +0200 +@@ -1265,6 +1265,11 @@ + #define PLATFORM_DRIVER tegra_ehci_driver + #endif + ++#ifdef CONFIG_USB_EHCI_AR71XX ++#include "ehci-ar71xx.c" ++#define PLATFORM_DRIVER ehci_ar71xx_driver ++#endif ++ + #if !defined(PCI_DRIVER) && !defined(PLATFORM_DRIVER) && \ + !defined(PS3_SYSTEM_BUS_DRIVER) && !defined(OF_PLATFORM_DRIVER) && \ + !defined(XILINX_OF_PLATFORM_DRIVER) +diff -Nur linux-2.6.39.orig/drivers/usb/host/Kconfig linux-2.6.39/drivers/usb/host/Kconfig +--- linux-2.6.39.orig/drivers/usb/host/Kconfig 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/usb/host/Kconfig 2011-08-22 16:21:42.767983341 +0200 +@@ -129,6 +129,13 @@ + config USB_FSL_MPH_DR_OF + tristate + ++config USB_EHCI_AR71XX ++ bool "USB EHCI support for AR71xx" ++ depends on USB_EHCI_HCD && ATHEROS_AR71XX ++ default y ++ help ++ Support for Atheros AR71xx built-in EHCI controller ++ + config USB_EHCI_FSL + bool "Support for Freescale on-chip EHCI USB controller" + depends on USB_EHCI_HCD && FSL_SOC +@@ -287,6 +294,13 @@ + Enables support for the on-chip OHCI controller on + OMAP3 and later chips. + ++config USB_OHCI_AR71XX ++ bool "USB OHCI support for Atheros AR71xx" ++ depends on USB_OHCI_HCD && ATHEROS_AR71XX ++ default y ++ help ++ Support for Atheros AR71xx built-in OHCI controller ++ + config USB_OHCI_HCD_PPC_SOC + bool "OHCI support for on-chip PPC USB controller" + depends on USB_OHCI_HCD && (STB03xxx || PPC_MPC52xx) +diff -Nur linux-2.6.39.orig/drivers/usb/host/ohci-ar71xx.c linux-2.6.39/drivers/usb/host/ohci-ar71xx.c +--- linux-2.6.39.orig/drivers/usb/host/ohci-ar71xx.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/usb/host/ohci-ar71xx.c 2011-04-27 12:19:22.267661616 +0200 +@@ -0,0 +1,165 @@ ++/* ++ * OHCI HCD (Host Controller Driver) for USB. ++ * ++ * Bus Glue for Atheros AR71xx built-in OHCI controller. ++ * ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros' 2.6.15 BSP ++ * Copyright (C) 2007 Atheros Communications, Inc. ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ ++ ++#include ++#include ++ ++extern int usb_disabled(void); ++ ++static int usb_hcd_ar71xx_probe(const struct hc_driver *driver, ++ struct platform_device *pdev) ++{ ++ struct usb_hcd *hcd; ++ struct resource *res; ++ int irq; ++ int ret; + -+#define AR7240_PORT_CPU 0 -+#define AR7240_NUM_PORTS 6 -+#define AR7240_NUM_PHYS 5 ++ res = platform_get_resource(pdev, IORESOURCE_IRQ, 0); ++ if (!res) { ++ dev_dbg(&pdev->dev, "no IRQ specified for %s\n", ++ dev_name(&pdev->dev)); ++ return -ENODEV; ++ } ++ irq = res->start; + -+#define AR7240_PHY_ID1 0x004d -+#define AR7240_PHY_ID2 0xd041 ++ hcd = usb_create_hcd(driver, &pdev->dev, dev_name(&pdev->dev)); ++ if (!hcd) ++ return -ENOMEM; + -+#define AR7240_PORT_MASK(_port) BIT((_port)) -+#define AR7240_PORT_MASK_ALL BITM(AR7240_NUM_PORTS) -+#define AR7240_PORT_MASK_BUT(_port) (AR7240_PORT_MASK_ALL & ~BIT((_port))) ++ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); ++ if (!res) { ++ dev_dbg(&pdev->dev, "no base address specified for %s\n", ++ dev_name(&pdev->dev)); ++ ret = -ENODEV; ++ goto err_put_hcd; ++ } ++ hcd->rsrc_start = res->start; ++ hcd->rsrc_len = res->end - res->start + 1; + -+struct ar7240sw { -+ struct mii_bus *mii_bus; -+ struct mutex reg_mutex; -+ struct mutex stats_mutex; -+}; ++ if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) { ++ dev_dbg(&pdev->dev, "controller already in use\n"); ++ ret = -EBUSY; ++ goto err_put_hcd; ++ } + -+struct ar7240sw_hw_stat { -+ char string[ETH_GSTRING_LEN]; -+ int sizeof_stat; -+ int reg; -+}; ++ hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len); ++ if (!hcd->regs) { ++ dev_dbg(&pdev->dev, "error mapping memory\n"); ++ ret = -EFAULT; ++ goto err_release_region; ++ } + -+static inline struct ar7240sw *dsa_to_ar7240sw(struct dsa_switch *ds) -+{ -+ return (struct ar7240sw *)(ds + 1); -+} ++ ohci_hcd_init(hcd_to_ohci(hcd)); + -+static inline void ar7240sw_init(struct ar7240sw *as, struct mii_bus *mii) -+{ -+ as->mii_bus = mii; -+ mutex_init(&as->reg_mutex); -+ mutex_init(&as->stats_mutex); -+} ++ ret = usb_add_hcd(hcd, irq, IRQF_DISABLED); ++ if (ret) ++ goto err_stop_hcd; + -+static inline u16 mk_phy_addr(u32 reg) -+{ -+ return (0x17 & ((reg >> 4) | 0x10)); -+} ++ return 0; + -+static inline u16 mk_phy_reg(u32 reg) -+{ -+ return ((reg << 1) & 0x1e); ++err_stop_hcd: ++ iounmap(hcd->regs); ++err_release_region: ++ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); ++err_put_hcd: ++ usb_put_hcd(hcd); ++ return ret; +} + -+static inline u16 mk_high_addr(u32 reg) ++void usb_hcd_ar71xx_remove(struct usb_hcd *hcd, struct platform_device *pdev) +{ -+ return ((reg >> 7) & 0x1ff); ++ usb_remove_hcd(hcd); ++ iounmap(hcd->regs); ++ release_mem_region(hcd->rsrc_start, hcd->rsrc_len); ++ usb_put_hcd(hcd); +} + -+static u32 __ar7240sw_reg_read(struct ar7240sw *as, u32 reg) ++static int __devinit ohci_ar71xx_start(struct usb_hcd *hcd) +{ -+ struct mii_bus *mii = as->mii_bus; -+ u16 phy_addr; -+ u16 phy_reg; -+ u32 hi, lo; -+ -+ reg = (reg & 0xfffffffc) >> 2; ++ struct ohci_hcd *ohci = hcd_to_ohci(hcd); ++ int ret; + -+ mdiobus_write(mii, 0x1f, 0x10, mk_high_addr(reg)); ++ ret = ohci_init(ohci); ++ if (ret < 0) ++ return ret; + -+ phy_addr = mk_phy_addr(reg); -+ phy_reg = mk_phy_reg(reg); ++ ret = ohci_run(ohci); ++ if (ret < 0) ++ goto err; + -+ lo = (u32) mdiobus_read(mii, phy_addr, phy_reg); -+ hi = (u32) mdiobus_read(mii, phy_addr, phy_reg + 1); ++ return 0; + -+ return ((hi << 16) | lo); ++err: ++ ohci_stop(hcd); ++ return ret; +} + -+static void __ar7240sw_reg_write(struct ar7240sw *as, u32 reg, u32 val) -+{ -+ struct mii_bus *mii = as->mii_bus; -+ u16 phy_addr; -+ u16 phy_reg; -+ -+ reg = (reg & 0xfffffffc) >> 2; -+ -+ mdiobus_write(mii, 0x1f, 0x10, mk_high_addr(reg)); -+ -+ phy_addr = mk_phy_addr(reg); -+ phy_reg = mk_phy_reg(reg); ++static const struct hc_driver ohci_ar71xx_hc_driver = { ++ .description = hcd_name, ++ .product_desc = "Atheros AR71xx built-in OHCI controller", ++ .hcd_priv_size = sizeof(struct ohci_hcd), + -+ mdiobus_write(mii, phy_addr, phy_reg + 1, (val >> 16)); -+ mdiobus_write(mii, phy_addr, phy_reg, (val & 0xffff)); -+} ++ .irq = ohci_irq, ++ .flags = HCD_USB11 | HCD_MEMORY, + -+static u32 ar7240sw_reg_read(struct ar7240sw *as, u32 reg_addr) -+{ -+ u32 ret; ++ .start = ohci_ar71xx_start, ++ .stop = ohci_stop, ++ .shutdown = ohci_shutdown, + -+ mutex_lock(&as->reg_mutex); -+ ret = __ar7240sw_reg_read(as, reg_addr); -+ mutex_unlock(&as->reg_mutex); ++ .urb_enqueue = ohci_urb_enqueue, ++ .urb_dequeue = ohci_urb_dequeue, ++ .endpoint_disable = ohci_endpoint_disable, + -+ return ret; -+} ++ /* ++ * scheduling support ++ */ ++ .get_frame_number = ohci_get_frame, + -+static void ar7240sw_reg_write(struct ar7240sw *as, u32 reg_addr, u32 reg_val) -+{ -+ mutex_lock(&as->reg_mutex); -+ __ar7240sw_reg_write(as, reg_addr, reg_val); -+ mutex_unlock(&as->reg_mutex); -+} ++ /* ++ * root hub support ++ */ ++ .hub_status_data = ohci_hub_status_data, ++ .hub_control = ohci_hub_control, ++ .start_port_reset = ohci_start_port_reset, ++}; + -+static u32 ar7240sw_reg_rmw(struct ar7240sw *as, u32 reg, u32 mask, u32 val) ++static int ohci_hcd_ar71xx_drv_probe(struct platform_device *pdev) +{ -+ u32 t; -+ -+ mutex_lock(&as->reg_mutex); -+ t = __ar7240sw_reg_read(as, reg); -+ t &= ~mask; -+ t |= val; -+ __ar7240sw_reg_write(as, reg, t); -+ mutex_unlock(&as->reg_mutex); ++ if (usb_disabled()) ++ return -ENODEV; + -+ return t; ++ return usb_hcd_ar71xx_probe(&ohci_ar71xx_hc_driver, pdev); +} + -+static void ar7240sw_reg_set(struct ar7240sw *as, u32 reg, u32 val) ++static int ohci_hcd_ar71xx_drv_remove(struct platform_device *pdev) +{ -+ u32 t; ++ struct usb_hcd *hcd = platform_get_drvdata(pdev); + -+ mutex_lock(&as->reg_mutex); -+ t = __ar7240sw_reg_read(as, reg); -+ t |= val; -+ __ar7240sw_reg_write(as, reg, t); -+ mutex_unlock(&as->reg_mutex); ++ usb_hcd_ar71xx_remove(hcd, pdev); ++ return 0; +} + -+static int ar7240sw_reg_wait(struct ar7240sw *as, u32 reg, u32 mask, u32 val, -+ unsigned timeout) -+{ -+ int i; -+ -+ for (i = 0; i < timeout; i++) { -+ u32 t; ++MODULE_ALIAS("platform:ar71xx-ohci"); + -+ t = ar7240sw_reg_read(as, reg); -+ if ((t & mask) == val) -+ return 0; ++static struct platform_driver ohci_hcd_ar71xx_driver = { ++ .probe = ohci_hcd_ar71xx_drv_probe, ++ .remove = ohci_hcd_ar71xx_drv_remove, ++ .shutdown = usb_hcd_platform_shutdown, ++ .driver = { ++ .name = "ar71xx-ohci", ++ .owner = THIS_MODULE, ++ }, ++}; +diff -Nur linux-2.6.39.orig/drivers/usb/host/ohci-hcd.c linux-2.6.39/drivers/usb/host/ohci-hcd.c +--- linux-2.6.39.orig/drivers/usb/host/ohci-hcd.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/drivers/usb/host/ohci-hcd.c 2011-08-22 16:21:42.847983209 +0200 +@@ -1105,6 +1105,11 @@ + #define PLATFORM_DRIVER ohci_hcd_cns3xxx_driver + #endif + ++#ifdef CONFIG_USB_OHCI_AR71XX ++#include "ohci-ar71xx.c" ++#define PLATFORM_DRIVER ohci_hcd_ar71xx_driver ++#endif + -+ msleep(1); -+ } + #if !defined(PCI_DRIVER) && \ + !defined(PLATFORM_DRIVER) && \ + !defined(OMAP1_PLATFORM_DRIVER) && \ +diff -Nur linux-2.6.39.orig/drivers/watchdog/ar71xx_wdt.c linux-2.6.39/drivers/watchdog/ar71xx_wdt.c +--- linux-2.6.39.orig/drivers/watchdog/ar71xx_wdt.c 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/drivers/watchdog/ar71xx_wdt.c 2011-08-06 09:32:37.118022037 +0200 +@@ -0,0 +1,299 @@ ++/* ++ * Driver for the Atheros AR71xx SoC's built-in hardware watchdog timer. ++ * ++ * Copyright (C) 2010-2011 Jaiganesh Narayanan ++ * Copyright (C) 2008 Gabor Juhos ++ * Copyright (C) 2008 Imre Kaloz ++ * ++ * Parts of this file are based on Atheros 2.6.31 BSP ++ * ++ * This driver was based on: drivers/watchdog/ixp4xx_wdt.c ++ * Author: Deepak Saxena ++ * Copyright 2004 (c) MontaVista, Software, Inc. ++ * ++ * which again was based on sa1100 driver, ++ * Copyright (C) 2000 Oleg Drokin ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ + -+ return -ETIMEDOUT; -+} ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include + -+static u16 ar7240sw_phy_read(struct ar7240sw *as, unsigned phy_addr, -+ unsigned reg_addr) -+{ -+ u32 t; -+ int err; ++#include + -+ if (phy_addr >= AR7240_NUM_PHYS) -+ return 0xffff; ++#define DRV_NAME "ar71xx-wdt" ++#define DRV_DESC "Atheros AR71xx hardware watchdog driver" ++#define DRV_VERSION "0.1.0" + -+ t = (reg_addr << AR7240_MDIO_CTRL_REG_ADDR_S) | -+ (phy_addr << AR7240_MDIO_CTRL_PHY_ADDR_S) | -+ AR7240_MDIO_CTRL_MASTER_EN | -+ AR7240_MDIO_CTRL_BUSY | -+ AR7240_MDIO_CTRL_CMD_READ; ++#define WDT_TIMEOUT 15 /* seconds */ + -+ ar7240sw_reg_write(as, AR7240_REG_MDIO_CTRL, t); -+ err = ar7240sw_reg_wait(as, AR7240_REG_MDIO_CTRL, -+ AR7240_MDIO_CTRL_BUSY, 0, 5); -+ if (err) -+ return 0xffff; ++static int nowayout = WATCHDOG_NOWAYOUT; + -+ t = ar7240sw_reg_read(as, AR7240_REG_MDIO_CTRL); -+ return (t & AR7240_MDIO_CTRL_DATA_M); -+} ++#ifdef CONFIG_WATCHDOG_NOWAYOUT ++module_param(nowayout, int, 0); ++MODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started " ++ "(default=" __MODULE_STRING(WATCHDOG_NOWAYOUT) ")"); ++#endif + -+static int ar7240sw_phy_write(struct ar7240sw *as, unsigned phy_addr, -+ unsigned reg_addr, u16 reg_val) -+{ -+ u32 t; -+ int ret; ++static unsigned long wdt_flags; + -+ if (phy_addr >= AR7240_NUM_PHYS) -+ return -EINVAL; ++#define WDT_FLAGS_BUSY 0 ++#define WDT_FLAGS_EXPECT_CLOSE 1 + -+ t = (phy_addr << AR7240_MDIO_CTRL_PHY_ADDR_S) | -+ (reg_addr << AR7240_MDIO_CTRL_REG_ADDR_S) | -+ AR7240_MDIO_CTRL_MASTER_EN | -+ AR7240_MDIO_CTRL_BUSY | -+ AR7240_MDIO_CTRL_CMD_WRITE | -+ reg_val; ++static int wdt_timeout = WDT_TIMEOUT; ++static int boot_status; ++static int max_timeout; ++static u32 wdt_clk_freq; + -+ ar7240sw_reg_write(as, AR7240_REG_MDIO_CTRL, t); -+ ret = ar7240sw_reg_wait(as, AR7240_REG_MDIO_CTRL, -+ AR7240_MDIO_CTRL_BUSY, 0, 5); -+ return ret; ++static inline void ar71xx_wdt_keepalive(void) ++{ ++ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG, wdt_clk_freq * wdt_timeout); +} + -+static int ar7240sw_capture_stats(struct ar7240sw *as) ++static inline void ar71xx_wdt_enable(void) +{ -+ int ret; -+ -+ /* Capture the hardware statistics for all ports */ -+ ar7240sw_reg_write(as, AR7240_REG_MIB_FUNCTION0, -+ (AR7240_MIB_FUNC_CAPTURE << AR7240_MIB_FUNC_S)); -+ -+ /* Wait for the capturing to complete. */ -+ ret = ar7240sw_reg_wait(as, AR7240_REG_MIB_FUNCTION0, -+ AR7240_MIB_BUSY, 0, 10); -+ return ret; ++ printk(KERN_DEBUG DRV_NAME ": enabling watchdog timer\n"); ++ ar71xx_wdt_keepalive(); ++ udelay(2); ++ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG_CTRL, WDOG_CTRL_ACTION_FCR); +} + -+static void ar7240sw_disable_port(struct ar7240sw *as, unsigned port) ++static inline void ar71xx_wdt_disable(void) +{ -+ ar7240sw_reg_write(as, AR7240_REG_PORT_CTRL(port), -+ AR7240_PORT_CTRL_STATE_DISABLED); ++ printk(KERN_DEBUG DRV_NAME ": disabling watchdog timer\n"); ++ ar71xx_reset_wr(AR71XX_RESET_REG_WDOG_CTRL, WDOG_CTRL_ACTION_NONE); +} + -+static int ar7240sw_reset(struct ar7240sw *as) ++static int ar71xx_wdt_set_timeout(int val) +{ -+ int ret; -+ int i; -+ -+ /* Set all ports to disabled state. */ -+ for (i = 0; i < AR7240_NUM_PORTS; i++) -+ ar7240sw_disable_port(as, i); ++ if (val < 1 || val > max_timeout) ++ return -EINVAL; + -+ /* Wait for transmit queues to drain. */ -+ msleep(2); ++ wdt_timeout = val; ++ ar71xx_wdt_keepalive(); + -+ /* Reset the switch. */ -+ ar7240sw_reg_write(as, AR7240_REG_MASK_CTRL, -+ AR7240_MASK_CTRL_SOFT_RESET); ++ printk(KERN_DEBUG DRV_NAME ": timeout=%d secs\n", wdt_timeout); + -+ ret = ar7240sw_reg_wait(as, AR7240_REG_MASK_CTRL, -+ AR7240_MASK_CTRL_SOFT_RESET, 0, 1000); -+ return ret; ++ return 0; +} + -+static void ar7240sw_setup(struct ar7240sw *as) ++static int ar71xx_wdt_open(struct inode *inode, struct file *file) +{ -+ /* Enable CPU port, and disable mirror port */ -+ ar7240sw_reg_write(as, AR7240_REG_CPU_PORT, -+ AR7240_CPU_PORT_EN | -+ (15 << AR7240_MIRROR_PORT_S)); ++ if (test_and_set_bit(WDT_FLAGS_BUSY, &wdt_flags)) ++ return -EBUSY; + -+ /* Setup TAG priority mapping */ -+ ar7240sw_reg_write(as, AR7240_REG_TAG_PRIORITY, 0xfa50); ++ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); + -+ /* Enable ARP frame acknowledge */ -+ ar7240sw_reg_set(as, AR7240_REG_AT_CTRL, AR7240_AT_CTRL_ARP_EN); ++ ar71xx_wdt_enable(); + -+ /* Enable Broadcast frames transmitted to the CPU */ -+ ar7240sw_reg_set(as, AR7240_REG_FLOOD_MASK, -+ AR7240_FLOOD_MASK_BROAD_TO_CPU); ++ return nonseekable_open(inode, file); ++} + -+ /* setup MTU */ -+ ar7240sw_reg_rmw(as, AR7240_REG_GLOBAL_CTRL, AR7240_GLOBAL_CTRL_MTU_M, -+ 1536); ++static int ar71xx_wdt_release(struct inode *inode, struct file *file) ++{ ++ if (test_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags)) { ++ ar71xx_wdt_disable(); ++ } else { ++ printk(KERN_CRIT DRV_NAME ": device closed unexpectedly, " ++ "watchdog timer will not stop!\n"); ++ } + -+ /* setup Service TAG */ -+ ar7240sw_reg_rmw(as, AR7240_REG_SERVICE_TAG, AR7240_SERVICE_TAG_M, -+ ETH_P_QINQ); ++ clear_bit(WDT_FLAGS_BUSY, &wdt_flags); ++ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); ++ ++ return 0; +} + -+static void ar7240sw_setup_port(struct ar7240sw *as, unsigned port) ++static ssize_t ar71xx_wdt_write(struct file *file, const char *data, ++ size_t len, loff_t *ppos) +{ -+ u32 ctrl; -+ u32 dest_ports; -+ u32 vlan; -+ -+ ctrl = AR7240_PORT_CTRL_STATE_FORWARD; ++ if (len) { ++ if (!nowayout) { ++ size_t i; + -+ if (port == AR7240_PORT_CPU) { -+ ar7240sw_reg_write(as, AR7240_REG_PORT_STATUS(port), -+ AR7240_PORT_STATUS_SPEED_1000 | -+ AR7240_PORT_STATUS_TXFLOW | -+ AR7240_PORT_STATUS_RXFLOW | -+ AR7240_PORT_STATUS_TXMAC | -+ AR7240_PORT_STATUS_RXMAC | -+ AR7240_PORT_STATUS_DUPLEX); ++ clear_bit(WDT_FLAGS_EXPECT_CLOSE, &wdt_flags); + -+ /* allow the CPU port to talk to each of the 'real' ports */ -+ dest_ports = AR7240_PORT_MASK_BUT(port); ++ for (i = 0; i != len; i++) { ++ char c; + -+ /* remove service tag from ingress frames */ -+ ctrl |= AR7240_PORT_CTRL_DOUBLE_TAG; -+ } else { -+ ar7240sw_reg_write(as, AR7240_REG_PORT_STATUS(port), -+ AR7240_PORT_STATUS_LINK_AUTO); ++ if (get_user(c, data + i)) ++ return -EFAULT; + -+ /* -+ * allow each of the 'real' ports to only talk to the CPU -+ * port. -+ */ -+ dest_ports = AR7240_PORT_MASK(port) | -+ AR7240_PORT_MASK(AR7240_PORT_CPU); ++ if (c == 'V') ++ set_bit(WDT_FLAGS_EXPECT_CLOSE, ++ &wdt_flags); ++ } ++ } + -+ /* add service tag to egress frames */ -+ ctrl |= (AR7240_PORT_CTRL_VLAN_MODE_DOUBLE_TAG << -+ AR7240_PORT_CTRL_VLAN_MODE_S); ++ ar71xx_wdt_keepalive(); + } + -+ /* set default VID and and destination ports for this VLAN */ -+ vlan = port; -+ vlan |= (dest_ports << AR7240_PORT_VLAN_DEST_PORTS_S); -+ -+ ar7240sw_reg_write(as, AR7240_REG_PORT_CTRL(port), ctrl); -+ ar7240sw_reg_write(as, AR7240_REG_PORT_VLAN(port), vlan); ++ return len; +} + -+static char *ar7240_dsa_probe(struct mii_bus *mii, int sw_addr) ++static struct watchdog_info ar71xx_wdt_info = { ++ .options = WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING | ++ WDIOF_MAGICCLOSE | WDIOF_CARDRESET, ++ .firmware_version = 0, ++ .identity = "AR71XX watchdog", ++}; ++ ++static long ar71xx_wdt_ioctl(struct file *file, ++ unsigned int cmd, unsigned long arg) +{ -+ struct ar7240sw as; -+ u32 ctrl; -+ u16 phy_id1; -+ u16 phy_id2; -+ u8 ver; ++ int t; ++ int ret; + -+ ar7240sw_init(&as, mii); ++ switch (cmd) { ++ case WDIOC_GETSUPPORT: ++ ret = copy_to_user((struct watchdog_info *)arg, ++ &ar71xx_wdt_info, ++ sizeof(ar71xx_wdt_info)) ? -EFAULT : 0; ++ break; + -+ ctrl = ar7240sw_reg_read(&as, AR7240_REG_MASK_CTRL); ++ case WDIOC_GETSTATUS: ++ ret = put_user(0, (int *)arg) ? -EFAULT : 0; ++ break; + -+ ver = (ctrl >> AR7240_MASK_CTRL_VERSION_S) & AR7240_MASK_CTRL_VERSION_M; -+ if (ver != 1) { -+ pr_err("ar7240_dsa: unsupported chip, ctrl=%08x\n", ctrl); -+ return NULL; -+ } ++ case WDIOC_GETBOOTSTATUS: ++ ret = put_user(boot_status, (int *)arg) ? -EFAULT : 0; ++ break; + -+ phy_id1 = ar7240sw_phy_read(&as, 0, MII_PHYSID1); -+ phy_id2 = ar7240sw_phy_read(&as, 0, MII_PHYSID2); -+ if (phy_id1 != AR7240_PHY_ID1 || phy_id2 != AR7240_PHY_ID2) { -+ pr_err("ar7240_dsa: unknown phy id '%04x:%04x'\n", -+ phy_id1, phy_id2); -+ return NULL; ++ case WDIOC_KEEPALIVE: ++ ar71xx_wdt_keepalive(); ++ ret = 0; ++ break; ++ ++ case WDIOC_SETTIMEOUT: ++ ret = get_user(t, (int *)arg) ? -EFAULT : 0; ++ if (ret) ++ break; ++ ++ ret = ar71xx_wdt_set_timeout(t); ++ if (ret) ++ break; ++ ++ /* fallthrough */ ++ case WDIOC_GETTIMEOUT: ++ ret = put_user(wdt_timeout, (int *)arg) ? -EFAULT : 0; ++ break; ++ ++ default: ++ ret = -ENOTTY; ++ break; + } + -+ return "Atheros AR7240 built-in"; ++ return ret; +} + -+static int ar7240_dsa_setup(struct dsa_switch *ds) ++static const struct file_operations ar71xx_wdt_fops = { ++ .owner = THIS_MODULE, ++ .write = ar71xx_wdt_write, ++ .unlocked_ioctl = ar71xx_wdt_ioctl, ++ .open = ar71xx_wdt_open, ++ .release = ar71xx_wdt_release, ++}; ++ ++static struct miscdevice ar71xx_wdt_miscdev = { ++ .minor = WATCHDOG_MINOR, ++ .name = "watchdog", ++ .fops = &ar71xx_wdt_fops, ++}; ++ ++static int __devinit ar71xx_wdt_probe(struct platform_device *pdev) +{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ int i; + int ret; + -+ ar7240sw_init(as, ds->master_mii_bus); ++ switch (ar71xx_soc) { ++ case AR71XX_SOC_AR7130: ++ case AR71XX_SOC_AR7141: ++ case AR71XX_SOC_AR7161: ++ case AR71XX_SOC_AR7240: ++ case AR71XX_SOC_AR7241: ++ case AR71XX_SOC_AR7242: ++ case AR71XX_SOC_AR9130: ++ case AR71XX_SOC_AR9132: ++ wdt_clk_freq = ar71xx_ahb_freq; ++ break; ++ ++ case AR71XX_SOC_AR9330: ++ case AR71XX_SOC_AR9331: ++ case AR71XX_SOC_AR9341: ++ case AR71XX_SOC_AR9342: ++ case AR71XX_SOC_AR9344: ++ wdt_clk_freq = ar71xx_ref_freq; ++ break; ++ ++ default: ++ BUG(); ++ } ++ ++ max_timeout = (0xfffffffful / wdt_clk_freq); ++ wdt_timeout = (max_timeout < WDT_TIMEOUT) ? max_timeout : WDT_TIMEOUT; ++ ++ if (ar71xx_reset_rr(AR71XX_RESET_REG_WDOG_CTRL) & WDOG_CTRL_LAST_RESET) ++ boot_status = WDIOF_CARDRESET; + -+ ret = ar7240sw_reset(as); ++ ret = misc_register(&ar71xx_wdt_miscdev); + if (ret) -+ return ret; ++ goto err_out; + -+ ar7240sw_setup(as); ++ printk(KERN_INFO DRV_DESC " version " DRV_VERSION "\n"); + -+ for (i = 0; i < AR7240_NUM_PORTS; i++) { -+ if (dsa_is_cpu_port(ds, i) || (ds->phys_port_mask & (1 << i))) -+ ar7240sw_setup_port(as, i); -+ else -+ ar7240sw_disable_port(as, i); -+ } ++ printk(KERN_DEBUG DRV_NAME ": timeout=%d secs (max=%d)\n", ++ wdt_timeout, max_timeout); + + return 0; ++ ++err_out: ++ return ret; +} + -+static int ar7240_dsa_set_addr(struct dsa_switch *ds, u8 *addr) ++static int __devexit ar71xx_wdt_remove(struct platform_device *pdev) +{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ u32 t; ++ misc_deregister(&ar71xx_wdt_miscdev); ++ return 0; ++} + -+ t = (addr[4] << 8) | addr[5]; -+ ar7240sw_reg_write(as, AR7240_REG_MAC_ADDR0, t); ++static struct platform_driver ar71xx_wdt_driver = { ++ .probe = ar71xx_wdt_probe, ++ .remove = __devexit_p(ar71xx_wdt_remove), ++ .driver = { ++ .name = DRV_NAME, ++ .owner = THIS_MODULE, ++ }, ++}; + -+ t = (addr[0] << 24) | (addr[1] << 16) | (addr[2] << 8) | addr[3]; -+ ar7240sw_reg_write(as, AR7240_REG_MAC_ADDR1, t); ++static int __init ar71xx_wdt_init(void) ++{ ++ return platform_driver_register(&ar71xx_wdt_driver); ++} ++module_init(ar71xx_wdt_init); + -+ return 0; ++static void __exit ar71xx_wdt_exit(void) ++{ ++ platform_driver_unregister(&ar71xx_wdt_driver); +} ++module_exit(ar71xx_wdt_exit); ++ ++MODULE_DESCRIPTION(DRV_DESC); ++MODULE_VERSION(DRV_VERSION); ++MODULE_AUTHOR("Gabor Juhos 0 && port < AR7240_NUM_PORTS) -+ return port - 1; ++ int led_pin; ++ u32 gpio_mask; ++ u32 gpio_val; + -+ return -EINVAL; -+} ++ bool is_clk_25mhz; ++ int (*get_mac_revision)(void); ++ int (*external_reset)(void); + }; + + #endif /* _LINUX_ATH9K_PLATFORM_H */ +diff -Nur linux-2.6.39.orig/include/linux/ip.h linux-2.6.39/include/linux/ip.h +--- linux-2.6.39.orig/include/linux/ip.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/ip.h 2011-08-24 05:53:21.239229027 +0200 +@@ -102,7 +102,7 @@ + __be32 saddr; + __be32 daddr; + /*The options start here. */ +-}; ++} __packed; + + #ifdef __KERNEL__ + #include +diff -Nur linux-2.6.39.orig/include/linux/ipv6.h linux-2.6.39/include/linux/ipv6.h +--- linux-2.6.39.orig/include/linux/ipv6.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/ipv6.h 2011-08-24 05:53:21.289229059 +0200 +@@ -126,7 +126,7 @@ + + struct in6_addr saddr; + struct in6_addr daddr; +-}; ++} __packed; + + #ifdef __KERNEL__ + /* +diff -Nur linux-2.6.39.orig/include/linux/myloader.h linux-2.6.39/include/linux/myloader.h +--- linux-2.6.39.orig/include/linux/myloader.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/include/linux/myloader.h 2011-08-24 03:12:08.307985040 +0200 +@@ -0,0 +1,120 @@ ++/* ++ * Compex's MyLoader specific definitions ++ * ++ * Copyright (C) 2006-2008 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ * ++ */ + -+static int ar7240_dsa_phy_read(struct dsa_switch *ds, int port, int regnum) -+{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ int phy_addr; ++#ifndef _MYLOADER_H_ ++#define _MYLOADER_H_ ++ ++/* Myloader specific magic numbers */ ++#define MYLO_MAGIC_SYS_PARAMS 0x20021107 ++#define MYLO_MAGIC_PARTITIONS 0x20021103 ++#define MYLO_MAGIC_BOARD_PARAMS 0x20021103 ++ ++/* Vendor ID's (seems to be same as the PCI vendor ID's) */ ++#define VENID_COMPEX 0x11F6 ++ ++/* Devices based on the ADM5120 */ ++#define DEVID_COMPEX_NP27G 0x0078 ++#define DEVID_COMPEX_NP28G 0x044C ++#define DEVID_COMPEX_NP28GHS 0x044E ++#define DEVID_COMPEX_WP54Gv1C 0x0514 ++#define DEVID_COMPEX_WP54G 0x0515 ++#define DEVID_COMPEX_WP54AG 0x0546 ++#define DEVID_COMPEX_WPP54AG 0x0550 ++#define DEVID_COMPEX_WPP54G 0x0555 ++ ++/* Devices based on the Atheros AR2317 */ ++#define DEVID_COMPEX_NP25G 0x05E6 ++#define DEVID_COMPEX_WPE53G 0x05DC ++ ++/* Devices based on the Atheros AR71xx */ ++#define DEVID_COMPEX_WP543 0x0640 ++ ++/* Devices based on the IXP422 */ ++#define DEVID_COMPEX_WP18 0x047E ++#define DEVID_COMPEX_NP18A 0x0489 ++ ++/* Other devices */ ++#define DEVID_COMPEX_NP26G8M 0x03E8 ++#define DEVID_COMPEX_NP26G16M 0x03E9 ++ ++struct mylo_partition { ++ uint16_t flags; /* partition flags */ ++ uint16_t type; /* type of the partition */ ++ uint32_t addr; /* relative address of the partition from the ++ flash start */ ++ uint32_t size; /* size of the partition in bytes */ ++ uint32_t param; /* if this is the active partition, the ++ MyLoader load code to this address */ ++}; ++ ++#define PARTITION_FLAG_ACTIVE 0x8000 /* this is the active partition, ++ * MyLoader loads firmware from here */ ++#define PARTITION_FLAG_ISRAM 0x2000 /* FIXME: this is a RAM partition? */ ++#define PARTIIION_FLAG_RAMLOAD 0x1000 /* FIXME: load this partition into the RAM? */ ++#define PARTITION_FLAG_PRELOAD 0x0800 /* the partition data preloaded to RAM ++ * before decompression */ ++#define PARTITION_FLAG_LZMA 0x0100 /* partition data compressed by LZMA */ ++#define PARTITION_FLAG_HAVEHDR 0x0002 /* the partition data have a header */ ++ ++#define PARTITION_TYPE_FREE 0 ++#define PARTITION_TYPE_USED 1 ++ ++#define MYLO_MAX_PARTITIONS 8 /* maximum number of partitions in the ++ partition table */ ++ ++struct mylo_partition_table { ++ uint32_t magic; /* must be MYLO_MAGIC_PARTITIONS */ ++ uint32_t res0; /* unknown/unused */ ++ uint32_t res1; /* unknown/unused */ ++ uint32_t res2; /* unknown/unused */ ++ struct mylo_partition partitions[MYLO_MAX_PARTITIONS]; ++}; ++ ++struct mylo_partition_header { ++ uint32_t len; /* length of the partition data */ ++ uint32_t crc; /* CRC value of the partition data */ ++}; ++ ++struct mylo_system_params { ++ uint32_t magic; /* must be MYLO_MAGIC_SYS_PARAMS */ ++ uint32_t res0; ++ uint32_t res1; ++ uint32_t mylo_ver; ++ uint16_t vid; /* Vendor ID */ ++ uint16_t did; /* Device ID */ ++ uint16_t svid; /* Sub Vendor ID */ ++ uint16_t sdid; /* Sub Device ID */ ++ uint32_t rev; /* device revision */ ++ uint32_t fwhi; ++ uint32_t fwlo; ++ uint32_t tftp_addr; ++ uint32_t prog_start; ++ uint32_t flash_size; /* size of boot FLASH in bytes */ ++ uint32_t dram_size; /* size of onboard RAM in bytes */ ++}; ++ ++struct mylo_eth_addr { ++ uint8_t mac[6]; ++ uint8_t csum[2]; ++}; ++ ++#define MYLO_ETHADDR_COUNT 8 /* maximum number of ethernet address ++ in the board parameters */ ++ ++struct mylo_board_params { ++ uint32_t magic; /* must be MYLO_MAGIC_BOARD_PARAMS */ ++ uint32_t res0; ++ uint32_t res1; ++ uint32_t res2; ++ struct mylo_eth_addr addr[MYLO_ETHADDR_COUNT]; ++}; ++ ++#endif /* _MYLOADER_H_*/ +diff -Nur linux-2.6.39.orig/include/linux/netdevice.h linux-2.6.39/include/linux/netdevice.h +--- linux-2.6.39.orig/include/linux/netdevice.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/netdevice.h 2011-08-22 22:00:06.937981400 +0200 +@@ -1182,6 +1182,7 @@ + void *ax25_ptr; /* AX.25 specific data */ + struct wireless_dev *ieee80211_ptr; /* IEEE 802.11 specific data, + assign before registering */ ++ void *phy_ptr; /* PHY device specific data */ + + /* + * Cache lines mostly used on receive path (including eth_type_trans()) +diff -Nur linux-2.6.39.orig/include/linux/nxp_74hc153.h linux-2.6.39/include/linux/nxp_74hc153.h +--- linux-2.6.39.orig/include/linux/nxp_74hc153.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/include/linux/nxp_74hc153.h 2011-04-27 12:19:21.817661653 +0200 +@@ -0,0 +1,24 @@ ++/* ++ * NXP 74HC153 - Dual 4-input multiplexer defines ++ * ++ * Copyright (C) 2010 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify ++ * it under the terms of the GNU General Public License version 2 as ++ * published by the Free Software Foundation. ++ */ + -+ phy_addr = ar7240_iort_to_phy_addr(port); -+ if (phy_addr < 0) -+ return 0xffff; ++#ifndef _NXP_74HC153_H ++#define _NXP_74HC153_H + -+ return ar7240sw_phy_read(as, phy_addr, regnum); -+} ++#define NXP_74HC153_DRIVER_NAME "nxp-74hc153" + -+static int ar7240_dsa_phy_write(struct dsa_switch *ds, int port, int regnum, -+ u16 val) -+{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ int phy_addr; ++struct nxp_74hc153_platform_data { ++ unsigned gpio_base; ++ unsigned gpio_pin_s0; ++ unsigned gpio_pin_s1; ++ unsigned gpio_pin_1y; ++ unsigned gpio_pin_2y; ++}; + -+ phy_addr = ar7240_iort_to_phy_addr(port); -+ if (phy_addr < 0) -+ return 0xffff; ++#endif /* _NXP_74HC153_H */ +diff -Nur linux-2.6.39.orig/include/linux/phy.h linux-2.6.39/include/linux/phy.h +--- linux-2.6.39.orig/include/linux/phy.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/phy.h 2011-08-22 22:00:06.867980866 +0200 +@@ -332,6 +332,20 @@ + void (*adjust_link)(struct net_device *dev); + + void (*adjust_state)(struct net_device *dev); + -+ return ar7240sw_phy_write(as, phy_addr, regnum, val); -+} ++ /* ++ * By default these point to the original functions ++ * with the same name. adding them to the phy_device ++ * allows the phy driver to override them for packet ++ * mangling if the ethernet driver supports it ++ * This is required to support some really horrible ++ * switches such as the Marvell 88E6060 ++ */ ++ int (*netif_receive_skb)(struct sk_buff *skb); ++ int (*netif_rx)(struct sk_buff *skb); + -+static const char *ar7240sw_speed_str(unsigned speed) -+{ -+ switch (speed) { -+ case AR7240_PORT_STATUS_SPEED_10: -+ return "10"; -+ case AR7240_PORT_STATUS_SPEED_100: -+ return "100"; -+ case AR7240_PORT_STATUS_SPEED_1000: -+ return "1000"; -+ } ++ /* alignment offset for packets */ ++ int pkt_align; + }; + #define to_phy_device(d) container_of(d, struct phy_device, dev) + +@@ -508,6 +522,7 @@ + void phy_stop_machine(struct phy_device *phydev); + int phy_ethtool_sset(struct phy_device *phydev, struct ethtool_cmd *cmd); + int phy_ethtool_gset(struct phy_device *phydev, struct ethtool_cmd *cmd); ++int phy_ethtool_ioctl(struct phy_device *phydev, void *useraddr); + int phy_mii_ioctl(struct phy_device *phydev, + struct ifreq *ifr, int cmd); + int phy_start_interrupts(struct phy_device *phydev); +diff -Nur linux-2.6.39.orig/include/linux/spi/spi.h linux-2.6.39/include/linux/spi/spi.h +--- linux-2.6.39.orig/include/linux/spi/spi.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/spi/spi.h 2011-08-23 15:10:37.559229523 +0200 +@@ -441,6 +441,8 @@ + dma_addr_t rx_dma; + + unsigned cs_change:1; ++ unsigned verify:1; ++ unsigned fast_write:1; + u8 bits_per_word; + u16 delay_usecs; + u32 speed_hz; +@@ -482,6 +484,7 @@ + struct spi_device *spi; + + unsigned is_dma_mapped:1; ++ unsigned fast_read:1; + + /* REVISIT: we might want a flag affecting the behavior of the + * last transfer ... allowing things like "read 16 bit length L" +diff -Nur linux-2.6.39.orig/include/linux/spi/vsc7385.h linux-2.6.39/include/linux/spi/vsc7385.h +--- linux-2.6.39.orig/include/linux/spi/vsc7385.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/include/linux/spi/vsc7385.h 2011-04-27 12:19:21.817661653 +0200 +@@ -0,0 +1,19 @@ ++/* ++ * Platform data definition for the Vitesse VSC7385 ethernet switch driver ++ * ++ * Copyright (C) 2009 Gabor Juhos ++ * ++ * This program is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 as published ++ * by the Free Software Foundation. ++ */ + -+ return "????"; -+} ++struct vsc7385_platform_data { ++ void (*reset)(void); ++ char *ucode_name; ++ struct { ++ u32 tx_ipg:5; ++ u32 bit2:1; ++ u32 clk_sel:3; ++ } mac_cfg; ++}; +diff -Nur linux-2.6.39.orig/include/linux/switch.h linux-2.6.39/include/linux/switch.h +--- linux-2.6.39.orig/include/linux/switch.h 1970-01-01 01:00:00.000000000 +0100 ++++ linux-2.6.39/include/linux/switch.h 2011-08-22 22:09:59.799231408 +0200 +@@ -0,0 +1,204 @@ ++/* ++ * switch.h: Switch configuration API ++ * ++ * Copyright (C) 2008 Felix Fietkau ++ * ++ * 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. ++ */ + -+static void ar7240_dsa_poll_link(struct dsa_switch *ds) -+{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ int i; ++#ifndef __LINUX_SWITCH_H ++#define __LINUX_SWITCH_H + -+ for (i = 0; i < DSA_MAX_PORTS; i++) { -+ struct net_device *dev; -+ u32 status; -+ int link; -+ unsigned speed; -+ int duplex; ++#include ++#include ++#include ++#include ++#ifndef __KERNEL__ ++#include ++#include ++#include ++#else ++#include ++#endif + -+ dev = ds->ports[i]; -+ if (dev == NULL) -+ continue; ++/* main attributes */ ++enum { ++ SWITCH_ATTR_UNSPEC, ++ /* global */ ++ SWITCH_ATTR_TYPE, ++ /* device */ ++ SWITCH_ATTR_ID, ++ SWITCH_ATTR_DEV_NAME, ++ SWITCH_ATTR_ALIAS, ++ SWITCH_ATTR_NAME, ++ SWITCH_ATTR_VLANS, ++ SWITCH_ATTR_PORTS, ++ SWITCH_ATTR_CPU_PORT, ++ /* attributes */ ++ SWITCH_ATTR_OP_ID, ++ SWITCH_ATTR_OP_TYPE, ++ SWITCH_ATTR_OP_NAME, ++ SWITCH_ATTR_OP_PORT, ++ SWITCH_ATTR_OP_VLAN, ++ SWITCH_ATTR_OP_VALUE_INT, ++ SWITCH_ATTR_OP_VALUE_STR, ++ SWITCH_ATTR_OP_VALUE_PORTS, ++ SWITCH_ATTR_OP_DESCRIPTION, ++ /* port lists */ ++ SWITCH_ATTR_PORT, ++ SWITCH_ATTR_MAX ++}; ++ ++/* commands */ ++enum { ++ SWITCH_CMD_UNSPEC, ++ SWITCH_CMD_GET_SWITCH, ++ SWITCH_CMD_NEW_ATTR, ++ SWITCH_CMD_LIST_GLOBAL, ++ SWITCH_CMD_GET_GLOBAL, ++ SWITCH_CMD_SET_GLOBAL, ++ SWITCH_CMD_LIST_PORT, ++ SWITCH_CMD_GET_PORT, ++ SWITCH_CMD_SET_PORT, ++ SWITCH_CMD_LIST_VLAN, ++ SWITCH_CMD_GET_VLAN, ++ SWITCH_CMD_SET_VLAN ++}; ++ ++/* data types */ ++enum switch_val_type { ++ SWITCH_TYPE_UNSPEC, ++ SWITCH_TYPE_INT, ++ SWITCH_TYPE_STRING, ++ SWITCH_TYPE_PORTS, ++ SWITCH_TYPE_NOVAL, ++}; ++ ++/* port nested attributes */ ++enum { ++ SWITCH_PORT_UNSPEC, ++ SWITCH_PORT_ID, ++ SWITCH_PORT_FLAG_TAGGED, ++ SWITCH_PORT_ATTR_MAX ++}; ++ ++#define SWITCH_ATTR_DEFAULTS_OFFSET 0x1000 ++ ++#ifdef __KERNEL__ ++ ++struct switch_dev; ++struct switch_op; ++struct switch_val; ++struct switch_attr; ++struct switch_attrlist; ++ ++int register_switch(struct switch_dev *dev, struct net_device *netdev); ++void unregister_switch(struct switch_dev *dev); ++ ++/** ++ * struct switch_attrlist - attribute list ++ * ++ * @n_attr: number of attributes ++ * @attr: pointer to the attributes array ++ */ ++struct switch_attrlist { ++ int n_attr; ++ const struct switch_attr *attr; ++}; + -+ link = 0; -+ if (dev->flags & IFF_UP) { -+ status = ar7240sw_reg_read(as, -+ AR7240_REG_PORT_STATUS(i)); -+ link = !!(status & AR7240_PORT_STATUS_LINK_UP); -+ } ++/** ++ * struct switch_dev_ops - switch driver operations ++ * ++ * @attr_global: global switch attribute list ++ * @attr_port: port attribute list ++ * @attr_vlan: vlan attribute list ++ * ++ * Callbacks: ++ * ++ * @get_vlan_ports: read the port list of a VLAN ++ * @set_vlan_ports: set the port list of a VLAN ++ * ++ * @get_port_pvid: get the primary VLAN ID of a port ++ * @set_port_pvid: set the primary VLAN ID of a port ++ * ++ * @apply_config: apply all changed settings to the switch ++ * @reset_switch: resetting the switch ++ */ ++struct switch_dev_ops { ++ struct switch_attrlist attr_global, attr_port, attr_vlan; + -+ if (!link) { -+ if (netif_carrier_ok(dev)) { -+ pr_info("%s: link down\n", dev->name); -+ netif_carrier_off(dev); -+ } -+ continue; -+ } ++ int (*get_vlan_ports)(struct switch_dev *dev, struct switch_val *val); ++ int (*set_vlan_ports)(struct switch_dev *dev, struct switch_val *val); + -+ speed = (status & AR7240_PORT_STATUS_SPEED_M); -+ duplex = (status & AR7240_PORT_STATUS_DUPLEX) ? 1 : 0; -+ if (!netif_carrier_ok(dev)) { -+ pr_info("%s: link up, %sMb/s, %s duplex", -+ dev->name, -+ ar7240sw_speed_str(speed), -+ duplex ? "full" : "half"); -+ netif_carrier_on(dev); -+ } -+ } -+} ++ int (*get_port_pvid)(struct switch_dev *dev, int port, int *val); ++ int (*set_port_pvid)(struct switch_dev *dev, int port, int val); + -+static const struct ar7240sw_hw_stat ar7240_hw_stats[] = { -+ { "rx_broadcast" , 4, AR7240_STATS_RXBROAD, }, -+ { "rx_pause" , 4, AR7240_STATS_RXPAUSE, }, -+ { "rx_multicast" , 4, AR7240_STATS_RXMULTI, }, -+ { "rx_fcs_error" , 4, AR7240_STATS_RXFCSERR, }, -+ { "rx_align_error" , 4, AR7240_STATS_RXALIGNERR, }, -+ { "rx_undersize" , 4, AR7240_STATS_RXRUNT, }, -+ { "rx_fragments" , 4, AR7240_STATS_RXFRAGMENT, }, -+ { "rx_64bytes" , 4, AR7240_STATS_RX64BYTE, }, -+ { "rx_65_127bytes" , 4, AR7240_STATS_RX128BYTE, }, -+ { "rx_128_255bytes" , 4, AR7240_STATS_RX256BYTE, }, -+ { "rx_256_511bytes" , 4, AR7240_STATS_RX512BYTE, }, -+ { "rx_512_1023bytes" , 4, AR7240_STATS_RX1024BYTE, }, -+ { "rx_1024_1518bytes" , 4, AR7240_STATS_RX1518BYTE, }, -+ { "rx_1519_max_bytes" , 4, AR7240_STATS_RXMAXBYTE, }, -+ { "rx_oversize" , 4, AR7240_STATS_RXTOOLONG, }, -+ { "rx_good_bytes" , 8, AR7240_STATS_RXGOODBYTE, }, -+ { "rx_bad_bytes" , 8, AR7240_STATS_RXBADBYTE, }, -+ { "rx_overflow" , 4, AR7240_STATS_RXOVERFLOW, }, -+ { "filtered" , 4, AR7240_STATS_FILTERED, }, -+ { "tx_broadcast" , 4, AR7240_STATS_TXBROAD, }, -+ { "tx_pause" , 4, AR7240_STATS_TXPAUSE, }, -+ { "tx_multicast" , 4, AR7240_STATS_TXMULTI, }, -+ { "tx_underrun" , 4, AR7240_STATS_TXUNDERRUN, }, -+ { "tx_64bytes" , 4, AR7240_STATS_TX64BYTE, }, -+ { "tx_65_127bytes" , 4, AR7240_STATS_TX128BYTE, }, -+ { "tx_128_255bytes" , 4, AR7240_STATS_TX256BYTE, }, -+ { "tx_256_511bytes" , 4, AR7240_STATS_TX512BYTE, }, -+ { "tx_512_1023bytes" , 4, AR7240_STATS_TX1024BYTE, }, -+ { "tx_1024_1518bytes" , 4, AR7240_STATS_TX1518BYTE, }, -+ { "tx_1519_max_bytes" , 4, AR7240_STATS_TXMAXBYTE, }, -+ { "tx_oversize" , 4, AR7240_STATS_TXOVERSIZE, }, -+ { "tx_bytes" , 8, AR7240_STATS_TXBYTE, }, -+ { "tx_collisions" , 4, AR7240_STATS_TXCOLLISION, }, -+ { "tx_abort_collisions" , 4, AR7240_STATS_TXABORTCOL, }, -+ { "tx_multi_collisions" , 4, AR7240_STATS_TXMULTICOL, }, -+ { "tx_single_collisions", 4, AR7240_STATS_TXSINGLECOL, }, -+ { "tx_excessive_deferred", 4, AR7240_STATS_TXEXCDEFER, }, -+ { "tx_deferred" , 4, AR7240_STATS_TXDEFER, }, -+ { "tx_late_collisions" , 4, AR7240_STATS_TXLATECOL, }, -+}; -+ -+static void ar7240_dsa_get_strings(struct dsa_switch *ds, int port, -+ uint8_t *data) -+{ -+ int i; ++ int (*apply_config)(struct switch_dev *dev); ++ int (*reset_switch)(struct switch_dev *dev); ++}; + -+ for (i = 0; i < ARRAY_SIZE(ar7240_hw_stats); i++) { -+ memcpy(data + i * ETH_GSTRING_LEN, -+ ar7240_hw_stats[i].string, ETH_GSTRING_LEN); -+ } -+} ++struct switch_dev { ++ const struct switch_dev_ops *ops; ++ /* will be automatically filled */ ++ char devname[IFNAMSIZ]; + -+static void ar7240_dsa_get_ethtool_stats(struct dsa_switch *ds, int port, -+ uint64_t *data) -+{ -+ struct ar7240sw *as = dsa_to_ar7240sw(ds); -+ int err; -+ int i; ++ const char *name; ++ /* NB: either alias or netdev must be set */ ++ const char *alias; ++ struct net_device *netdev; + -+ mutex_lock(&as->stats_mutex); ++ int ports; ++ int vlans; ++ int cpu_port; + -+ err = ar7240sw_capture_stats(as); -+ if (err) -+ goto unlock; ++ /* the following fields are internal for swconfig */ ++ int id; ++ struct list_head dev_list; ++ unsigned long def_global, def_port, def_vlan; + -+ for (i = 0; i < ARRAY_SIZE(ar7240_hw_stats); i++) { -+ const struct ar7240sw_hw_stat *s = &ar7240_hw_stats[i]; -+ u32 reg = AR7240_REG_STATS_BASE(port); -+ u32 low; -+ u32 high; ++ spinlock_t lock; ++ struct switch_port *portbuf; ++}; + -+ low = ar7240sw_reg_read(as, reg + s->reg); -+ if (s->sizeof_stat == 8) -+ high = ar7240sw_reg_read(as, reg + s->reg); -+ else -+ high = 0; ++struct switch_port { ++ u32 id; ++ u32 flags; ++}; + -+ data[i] = (((u64) high) << 32) | low; -+ } ++struct switch_val { ++ const struct switch_attr *attr; ++ int port_vlan; ++ int len; ++ union { ++ const char *s; ++ u32 i; ++ struct switch_port *ports; ++ } value; ++}; + -+ unlock: -+ mutex_unlock(&as->stats_mutex); -+} ++struct switch_attr { ++ int disabled; ++ int type; ++ const char *name; ++ const char *description; + -+static int ar7240_dsa_get_sset_count(struct dsa_switch *ds) -+{ -+ return ARRAY_SIZE(ar7240_hw_stats); -+} ++ int (*set)(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val); ++ int (*get)(struct switch_dev *dev, const struct switch_attr *attr, struct switch_val *val); + -+static struct dsa_switch_driver ar7240_dsa_driver = { -+ .tag_protocol = htons(ETH_P_QINQ), -+ .priv_size = sizeof(struct ar7240sw), -+ .probe = ar7240_dsa_probe, -+ .setup = ar7240_dsa_setup, -+ .set_addr = ar7240_dsa_set_addr, -+ .phy_read = ar7240_dsa_phy_read, -+ .phy_write = ar7240_dsa_phy_write, -+ .poll_link = ar7240_dsa_poll_link, -+ .get_strings = ar7240_dsa_get_strings, -+ .get_ethtool_stats = ar7240_dsa_get_ethtool_stats, -+ .get_sset_count = ar7240_dsa_get_sset_count, ++ /* for driver internal use */ ++ int id; ++ int ofs; ++ int max; +}; + -+int __init dsa_ar7240_init(void) -+{ -+ register_switch_driver(&ar7240_dsa_driver); -+ return 0; -+} -+module_init(dsa_ar7240_init); ++#endif + -+void __exit dsa_ar7240_cleanup(void) -+{ -+ unregister_switch_driver(&ar7240_dsa_driver); -+} -+module_exit(dsa_ar7240_cleanup); ++#endif +diff -Nur linux-2.6.39.orig/include/linux/tcp.h linux-2.6.39/include/linux/tcp.h +--- linux-2.6.39.orig/include/linux/tcp.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/tcp.h 2011-08-24 05:53:21.379228748 +0200 +@@ -54,7 +54,7 @@ + __be16 window; + __sum16 check; + __be16 urg_ptr; +-}; ++} __packed; + + /* + * The union cast uses a gcc extension to avoid aliasing problems +diff -Nur linux-2.6.39.orig/include/linux/udp.h linux-2.6.39/include/linux/udp.h +--- linux-2.6.39.orig/include/linux/udp.h 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/include/linux/udp.h 2011-08-24 05:53:21.428824967 +0200 +@@ -24,7 +24,7 @@ + __be16 dest; + __be16 len; + __sum16 check; +-}; ++} __packed; + + /* UDP socket options */ + #define UDP_CORK 1 /* Never send partially complete segments */ diff -Nur linux-2.6.39.orig/net/dsa/mv88e6063.c linux-2.6.39/net/dsa/mv88e6063.c --- linux-2.6.39.orig/net/dsa/mv88e6063.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/net/dsa/mv88e6063.c 2011-05-27 14:36:51.000000000 +0200 ++++ linux-2.6.39/net/dsa/mv88e6063.c 2011-04-27 12:19:21.827661792 +0200 @@ -0,0 +1,294 @@ +/* + * net/dsa/mv88e6063.c - Driver for Marvell 88e6063 switch chips @@ -18297,134 +28270,25 @@ diff -Nur linux-2.6.39.orig/net/dsa/mv88e6063.c linux-2.6.39/net/dsa/mv88e6063.c + unregister_switch_driver(&mv88e6063_switch_driver); +} +module_exit(mv88e6063_cleanup); -diff -Nur linux-2.6.39.orig/net/dsa/tag_qinq.c linux-2.6.39/net/dsa/tag_qinq.c ---- linux-2.6.39.orig/net/dsa/tag_qinq.c 1970-01-01 01:00:00.000000000 +0100 -+++ linux-2.6.39/net/dsa/tag_qinq.c 2011-05-27 14:36:51.000000000 +0200 -@@ -0,0 +1,127 @@ -+/* -+ * net/dsa/tag_qinq.c - QinQ tag format handling -+ * Copyright (c) 2010 Gabor Juhos -+ * -+ * This file was based on: -+ * net/dsa/tag_edsa.c - Ethertype DSA tagging -+ * Copyright (c) 2008-2009 Marvell Semiconductor -+ * -+ * 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. -+ */ -+ -+#include -+#include -+#include -+#include -+ -+#include "dsa_priv.h" -+ -+netdev_tx_t qinq_xmit(struct sk_buff *skb, struct net_device *dev) -+{ -+ struct dsa_slave_priv *p = netdev_priv(dev); -+ struct vlan_ethhdr *veth; -+ unsigned int len; -+ int ret; -+ -+ if (skb_cow_head(skb, VLAN_HLEN) < 0) -+ goto out_free_skb; -+ -+ veth = (struct vlan_ethhdr *)skb_push(skb, VLAN_HLEN); -+ -+ /* Move the mac addresses to the beginning of the new header. */ -+ memmove(skb->data, skb->data + VLAN_HLEN, 2 * VLAN_ETH_ALEN); -+ skb->mac_header -= VLAN_HLEN; -+ -+ /* setup VLAN header fields */ -+ veth->h_vlan_proto = htons(ETH_P_QINQ); -+ veth->h_vlan_TCI = htons(p->port); -+ -+ len = skb->len; -+ skb->protocol = htons(ETH_P_QINQ); -+ skb->dev = p->parent->dst->master_netdev; -+ -+ ret = dev_queue_xmit(skb); -+ if (unlikely(ret != NET_XMIT_SUCCESS)) -+ goto out_dropped; -+ -+ dev->stats.tx_packets++; -+ dev->stats.tx_bytes += len; -+ -+ return NETDEV_TX_OK; -+ -+ out_free_skb: -+ kfree_skb(skb); -+ out_dropped: -+ dev->stats.tx_dropped++; -+ return NETDEV_TX_OK; -+} -+ -+static int qinq_rcv(struct sk_buff *skb, struct net_device *dev, -+ struct packet_type *pt, struct net_device *orig_dev) -+{ -+ struct dsa_switch_tree *dst; -+ struct dsa_switch *ds; -+ struct vlan_hdr *vhdr; -+ int source_port; -+ -+ dst = dev->dsa_ptr; -+ if (unlikely(dst == NULL)) -+ goto out_drop; -+ ds = dst->ds[0]; -+ -+ skb = skb_unshare(skb, GFP_ATOMIC); -+ if (skb == NULL) -+ goto out; -+ -+ if (unlikely(!pskb_may_pull(skb, VLAN_HLEN))) -+ goto out_drop; -+ -+ vhdr = (struct vlan_hdr *)skb->data; -+ source_port = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK; -+ if (source_port >= DSA_MAX_PORTS || ds->ports[source_port] == NULL) -+ goto out_drop; -+ -+ /* Remove the outermost VLAN tag and update checksum. */ -+ skb_pull_rcsum(skb, VLAN_HLEN); -+ memmove(skb->data - ETH_HLEN, -+ skb->data - ETH_HLEN - VLAN_HLEN, -+ 2 * ETH_ALEN); -+ -+ skb->dev = ds->ports[source_port]; -+ skb_push(skb, ETH_HLEN); -+ skb->pkt_type = PACKET_HOST; -+ skb->protocol = eth_type_trans(skb, skb->dev); -+ -+ skb->dev->stats.rx_packets++; -+ skb->dev->stats.rx_bytes += skb->len; -+ -+ netif_receive_skb(skb); -+ -+ return 0; -+ -+ out_drop: -+ kfree_skb(skb); -+ out: -+ return 0; -+} -+ -+static struct packet_type qinq_packet_type __read_mostly = { -+ .type = cpu_to_be16(ETH_P_QINQ), -+ .func = qinq_rcv, -+}; -+ -+static int __init qinq_init_module(void) -+{ -+ dev_add_pack(&qinq_packet_type); -+ return 0; -+} -+module_init(qinq_init_module); -+ -+static void __exit qinq_cleanup_module(void) -+{ -+ dev_remove_pack(&qinq_packet_type); -+} -+module_exit(qinq_cleanup_module); +diff -Nur linux-2.6.39.orig/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c linux-2.6.39/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c +--- linux-2.6.39.orig/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c 2011-05-19 06:06:34.000000000 +0200 ++++ linux-2.6.39/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c 2011-08-24 05:53:21.549229118 +0200 +@@ -14,6 +14,7 @@ + #include + #include + #include ++#include + #include + #include + +@@ -44,8 +45,8 @@ + if (ap == NULL) + return false; + +- tuple->src.u3.ip = ap[0]; +- tuple->dst.u3.ip = ap[1]; ++ tuple->src.u3.ip = __get_unaligned_cpu32(ap++); ++ tuple->dst.u3.ip = __get_unaligned_cpu32(ap); + + return true; + } diff --git a/target/mips/Makefile b/target/mips/Makefile index 5d606046f..00a3e8bdc 100644 --- a/target/mips/Makefile +++ b/target/mips/Makefile @@ -51,11 +51,7 @@ ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB532),y) kernel-install: $(TARGET_CROSS)objcopy $(OSTRIP) -S $(KERNEL) $(BUILD_DIR)/$(TARGET_KERNEL) endif -ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB411),y) -kernel-install: - $(TARGET_CROSS)objcopy $(OSTRIP) -S $(KERNEL) $(BUILD_DIR)/$(TARGET_KERNEL) -endif -ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB433),y) +ifeq ($(ADK_TARGET_SYSTEM_MIKROTIK_RB4XX),y) kernel-install: $(TARGET_CROSS)objcopy $(OSTRIP) -S $(KERNEL) $(BUILD_DIR)/$(TARGET_KERNEL) endif diff --git a/target/mips/kernel.config b/target/mips/kernel.config index bdf5beb9f..4bc717861 100644 --- a/target/mips/kernel.config +++ b/target/mips/kernel.config @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux/mips 2.6.37 Kernel Configuration -# Sat Apr 23 20:38:50 2011 +# Linux/mips 2.6.39 Kernel Configuration +# Mon Aug 22 22:28:08 2011 # CONFIG_MIPS=y @@ -10,6 +10,7 @@ CONFIG_MIPS=y # # CONFIG_MIPS_ALCHEMY is not set # CONFIG_AR7 is not set +# CONFIG_ATH79 is not set # CONFIG_ATHEROS_AR71XX is not set # CONFIG_BCM47XX is not set # CONFIG_BCM63XX is not set @@ -52,11 +53,11 @@ CONFIG_MACH_LOONGSON=y # CONFIG_CAVIUM_OCTEON_REFERENCE_BOARD is not set # CONFIG_ALCHEMY_GPIO_INDIRECT is not set CONFIG_ARCH_SPARSEMEM_ENABLE=y -CONFIG_CAVIUM_OCTEON_HELPER=y # CONFIG_LEMOTE_FULOONG2E is not set CONFIG_LEMOTE_MACH2F=y CONFIG_CS5536=y # CONFIG_CS5536_MFGPT is not set +CONFIG_LOONGSON_SUSPEND=y CONFIG_LOONGSON_UART_BASE=y CONFIG_LOONGSON_MC146818=y CONFIG_RWSEM_GENERIC_SPINLOCK=y @@ -64,16 +65,17 @@ CONFIG_RWSEM_GENERIC_SPINLOCK=y # CONFIG_ARCH_HAS_ILOG2_U64 is not set CONFIG_ARCH_SUPPORTS_OPROFILE=y CONFIG_GENERIC_FIND_NEXT_BIT=y +CONFIG_GENERIC_FIND_BIT_LE=y CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_GENERIC_CLOCKEVENTS=y CONFIG_GENERIC_CMOS_UPDATE=y CONFIG_SCHED_OMIT_FRAME_POINTER=y -CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y CONFIG_CEVT_R4K_LIB=y CONFIG_CEVT_R4K=y CONFIG_CSRC_R4K_LIB=y CONFIG_CSRC_R4K=y +CONFIG_ARCH_DMA_ADDR_T_64BIT=y CONFIG_DMA_NONCOHERENT=y CONFIG_NEED_DMA_MAP_STATE=y CONFIG_SYS_HAS_EARLY_PRINTK=y @@ -98,7 +100,6 @@ CONFIG_CPU_NOP_WORKAROUNDS=y CONFIG_CPU_JUMP_WORKAROUNDS=y CONFIG_CPU_LOONGSON2F_WORKAROUNDS=y CONFIG_SYS_SUPPORTS_ZBOOT=y -CONFIG_SYS_SUPPORTS_ZBOOT_UART16550=y CONFIG_CPU_LOONGSON2=y CONFIG_SYS_HAS_CPU_LOONGSON2F=y CONFIG_SYS_SUPPORTS_32BIT_KERNEL=y @@ -132,6 +133,7 @@ CONFIG_HAVE_MEMORY_PRESENT=y CONFIG_SPARSEMEM_STATIC=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 +# CONFIG_COMPACTION is not set CONFIG_PHYS_ADDR_T_64BIT=y CONFIG_ZONE_DMA_FLAG=0 CONFIG_VIRT_TO_BUS=y @@ -141,7 +143,6 @@ CONFIG_NEED_PER_CPU_KM=y # CONFIG_NO_HZ is not set # CONFIG_HIGH_RES_TIMERS is not set CONFIG_GENERIC_CLOCKEVENTS_BUILD=y -CONFIG_CPU_SUPPORTS_HR_SCHED_CLOCK=y # CONFIG_HZ_48 is not set CONFIG_HZ_100=y # CONFIG_HZ_128 is not set @@ -161,6 +162,7 @@ CONFIG_LOCKDEP_SUPPORT=y CONFIG_STACKTRACE_SUPPORT=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y +CONFIG_HAVE_IRQ_WORK=y # # General setup @@ -184,6 +186,7 @@ CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set CONFIG_HAVE_GENERIC_HARDIRQS=y @@ -192,31 +195,28 @@ CONFIG_HAVE_GENERIC_HARDIRQS=y # IRQ subsystem # CONFIG_GENERIC_HARDIRQS=y -# CONFIG_GENERIC_HARDIRQS_NO_DEPRECATED is not set -# CONFIG_HAVE_SPARSE_IRQ is not set CONFIG_GENERIC_IRQ_PROBE=y -# CONFIG_GENERIC_PENDING_IRQ is not set -# CONFIG_AUTO_IRQ_AFFINITY is not set -# CONFIG_IRQ_PER_CPU is not set -# CONFIG_HARDIRQS_SW_RESEND is not set +CONFIG_GENERIC_IRQ_SHOW=y # # RCU Subsystem # CONFIG_TINY_RCU=y # CONFIG_PREEMPT_RCU is not set +# CONFIG_RCU_TRACE is not set # CONFIG_TREE_RCU_TRACE is not set # CONFIG_IKCONFIG is not set CONFIG_LOG_BUF_SHIFT=14 # CONFIG_CGROUPS is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set # CONFIG_SYSFS_DEPRECATED is not set # CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_SYSCTL_SYSCALL=y CONFIG_KALLSYMS=y # CONFIG_KALLSYMS_EXTRA_PASS is not set @@ -233,6 +233,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y CONFIG_HAVE_PERF_EVENTS=y CONFIG_PERF_USE_VMALLOC=y @@ -250,11 +251,13 @@ CONFIG_SLAB=y # CONFIG_PROFILING is not set CONFIG_HAVE_OPROFILE=y # CONFIG_KPROBES is not set +# CONFIG_JUMP_LABEL is not set CONFIG_HAVE_SYSCALL_WRAPPERS=y CONFIG_HAVE_KPROBES=y CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_DMA_API_DEBUG=y +CONFIG_HAVE_ARCH_JUMP_LABEL=y # # GCOV-based kernel profiling @@ -299,7 +302,7 @@ CONFIG_INLINE_WRITE_UNLOCK=y CONFIG_INLINE_WRITE_UNLOCK_IRQ=y # CONFIG_INLINE_WRITE_UNLOCK_IRQRESTORE is not set # CONFIG_MUTEX_SPIN_ON_OWNER is not set -# CONFIG_FREEZER is not set +CONFIG_FREEZER=y # # Bus options (PCI, PCMCIA, EISA, ISA, TC) @@ -314,6 +317,7 @@ CONFIG_ISA=y CONFIG_MMU=y # CONFIG_PCCARD is not set # CONFIG_HOTPLUG_PCI is not set +# CONFIG_RAPIDIO is not set # # Executable file formats @@ -333,7 +337,12 @@ CONFIG_BINFMT_ELF32=y # CONFIG_ARCH_HIBERNATION_POSSIBLE=y CONFIG_ARCH_SUSPEND_POSSIBLE=y -# CONFIG_PM is not set +CONFIG_SUSPEND=y +CONFIG_SUSPEND_FREEZER=y +CONFIG_PM_SLEEP=y +# CONFIG_PM_RUNTIME is not set +CONFIG_PM=y +# CONFIG_PM_DEBUG is not set CONFIG_NET=y # @@ -345,7 +354,6 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set # CONFIG_NET_IPGRE_DEMUX is not set @@ -376,6 +384,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ATM is not set # CONFIG_L2TP is not set # CONFIG_BRIDGE is not set +# CONFIG_NET_DSA is not set # CONFIG_VLAN_8021Q is not set # CONFIG_DECNET is not set # CONFIG_LLC2 is not set @@ -389,6 +398,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -399,7 +409,13 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IRDA is not set # CONFIG_BT is not set # CONFIG_AF_RXRPC is not set -# CONFIG_WIRELESS is not set +CONFIG_WIRELESS=y +# CONFIG_CFG80211 is not set +# CONFIG_LIB80211 is not set + +# +# CFG80211 needs to be enabled for MAC80211 +# # CONFIG_WIMAX is not set # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set @@ -441,7 +457,110 @@ CONFIG_SCSI_MOD=y # CONFIG_FIREWIRE is not set # CONFIG_FIREWIRE_NOSY is not set # CONFIG_I2O is not set -# CONFIG_NETDEVICES is not set +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_MACVLAN is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set +# CONFIG_VETH is not set +# CONFIG_ARCNET is not set +# CONFIG_MII is not set +CONFIG_PHYLIB=y +CONFIG_SWCONFIG=y + +# +# MII PHY device drivers +# +# CONFIG_MARVELL_PHY is not set +# CONFIG_DAVICOM_PHY is not set +# CONFIG_QSEMI_PHY is not set +# CONFIG_LXT_PHY is not set +# CONFIG_CICADA_PHY is not set +# CONFIG_VITESSE_PHY is not set +# CONFIG_SMSC_PHY is not set +# CONFIG_BROADCOM_PHY is not set +# CONFIG_BCM63XX_PHY is not set +# CONFIG_ICPLUS_PHY is not set +# CONFIG_REALTEK_PHY is not set +# CONFIG_NATIONAL_PHY is not set +# CONFIG_STE10XP is not set +# CONFIG_LSI_ET1011C_PHY is not set +# CONFIG_MICREL_PHY is not set +# CONFIG_FIXED_PHY is not set +# CONFIG_MDIO_BITBANG is not set +# CONFIG_NET_ETHERNET is not set +CONFIG_NETDEV_1000=y +# CONFIG_ACENIC is not set +# CONFIG_DL2K is not set +# CONFIG_E1000 is not set +# CONFIG_E1000E is not set +# CONFIG_IP1000 is not set +# CONFIG_IGB is not set +# CONFIG_IGBVF is not set +# CONFIG_NS83820 is not set +# CONFIG_HAMACHI is not set +# CONFIG_YELLOWFIN is not set +# CONFIG_R8169 is not set +# CONFIG_SIS190 is not set +# CONFIG_SKGE is not set +# CONFIG_SKY2 is not set +# CONFIG_VIA_VELOCITY is not set +# CONFIG_TIGON3 is not set +# CONFIG_BNX2 is not set +# CONFIG_CNIC is not set +# CONFIG_QLA3XXX is not set +# CONFIG_ATL1 is not set +# CONFIG_ATL1E is not set +# CONFIG_ATL1C is not set +# CONFIG_JME is not set +# CONFIG_STMMAC_ETH is not set +# CONFIG_PCH_GBE is not set +CONFIG_NETDEV_10000=y +# CONFIG_CHELSIO_T1 is not set +# CONFIG_CHELSIO_T3 is not set +# CONFIG_CHELSIO_T4 is not set +# CONFIG_CHELSIO_T4VF is not set +# CONFIG_ENIC is not set +# CONFIG_IXGBE is not set +# CONFIG_IXGB is not set +# CONFIG_S2IO is not set +# CONFIG_VXGE is not set +# CONFIG_MYRI10GE is not set +# CONFIG_NETXEN_NIC is not set +# CONFIG_NIU is not set +# CONFIG_MLX4_EN is not set +# CONFIG_MLX4_CORE is not set +# CONFIG_TEHUTI is not set +# CONFIG_BNX2X is not set +# CONFIG_QLCNIC is not set +# CONFIG_QLGE is not set +# CONFIG_BNA is not set +# CONFIG_SFC is not set +# CONFIG_BE2NET is not set +# CONFIG_TR is not set +CONFIG_WLAN=y +# CONFIG_AIRO is not set +# CONFIG_ATMEL is not set +# CONFIG_PRISM54 is not set +# CONFIG_HOSTAP is not set + +# +# Enable WiMAX (Networking options) to see the WiMAX drivers +# +# CONFIG_WAN is not set + +# +# CAIF transport drivers +# +# CONFIG_FDDI is not set +# CONFIG_HIPPI is not set +# CONFIG_PPP is not set +# CONFIG_SLIP is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set +# CONFIG_VMXNET3 is not set # CONFIG_ISDN is not set # CONFIG_PHONE is not set @@ -460,10 +579,13 @@ CONFIG_SCSI_MOD=y # Character devices # # CONFIG_VT is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set -# CONFIG_N_GSM is not set # CONFIG_NOZOMI is not set +# CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers @@ -485,9 +607,7 @@ CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_TIMBERDALE is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set +# CONFIG_SERIAL_PCH_UART is not set # CONFIG_TTY_PRINTK is not set # CONFIG_IPMI_HANDLER is not set # CONFIG_HW_RANDOM is not set @@ -495,7 +615,6 @@ CONFIG_UNIX98_PTYS=y # CONFIG_DTLK is not set # CONFIG_R3964 is not set # CONFIG_APPLICOM is not set -# CONFIG_GPIO_DEVICE is not set # CONFIG_TCG_TPM is not set CONFIG_DEVPORT=y # CONFIG_RAMOOPS is not set @@ -506,6 +625,10 @@ CONFIG_DEVPORT=y # PPS support # # CONFIG_PPS is not set + +# +# PPS generators support +# CONFIG_ARCH_REQUIRE_GPIOLIB=y CONFIG_GPIOLIB=y # CONFIG_GPIO_SYSFS is not set @@ -515,8 +638,6 @@ CONFIG_GPIOLIB=y # # CONFIG_GPIO_BASIC_MMIO is not set # CONFIG_GPIO_IT8761E is not set -# CONFIG_GPIO_SCH is not set -# CONFIG_GPIO_VX855 is not set # # I2C GPIO expanders: @@ -525,10 +646,8 @@ CONFIG_GPIOLIB=y # # PCI GPIO expanders: # -# CONFIG_GPIO_CS5535 is not set # CONFIG_GPIO_BT8XX is not set -# CONFIG_GPIO_LANGWELL is not set -# CONFIG_GPIO_PCH is not set +# CONFIG_GPIO_ML_IOH is not set # CONFIG_GPIO_RDC321X is not set # @@ -578,6 +697,7 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set +# CONFIG_NFC_DEVICES is not set # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set # CONFIG_RTC_CLASS is not set @@ -586,33 +706,37 @@ CONFIG_SSB_POSSIBLE=y # CONFIG_UIO is not set CONFIG_STAGING=y # CONFIG_STAGING_EXCLUDE_BUILD is not set +# CONFIG_ET131X is not set # CONFIG_ECHO is not set +# CONFIG_BRCM80211 is not set # CONFIG_COMEDI is not set +# CONFIG_R8187SE is not set +# CONFIG_RTL8192E is not set # CONFIG_POHMELFS is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_VT6655 is not set # CONFIG_VME_BUS is not set +# CONFIG_DX_SEP is not set # CONFIG_IIO is not set -# CONFIG_BATMAN_ADV is not set +# CONFIG_XVMALLOC is not set # CONFIG_CRYSTALHD is not set - -# -# Texas Instruments shared transport line discipline -# -# CONFIG_SMB_FS is not set CONFIG_MACH_NO_WESTBRIDGE=y # CONFIG_FT1000 is not set # # Speakup console speech # -CONFIG_MIPS_PLATFORM_DEVICES=y -# CONFIG_LEMOTE_LYNLOONG2F is not set + +# +# Altera FPGA firmware download module +# # # File systems # +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set # CONFIG_FANOTIFY is not set @@ -641,13 +765,13 @@ CONFIG_TMPFS=y # CONFIG_MISC_FILESYSTEMS is not set # CONFIG_NETWORK_FILESYSTEMS is not set # CONFIG_NLS is not set -# CONFIG_DLM is not set # # Kernel hacking # CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -656,9 +780,9 @@ CONFIG_MAGIC_SYSRQ=y # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set -CONFIG_BKL=y # CONFIG_SPARSE_RCU_POINTER is not set # CONFIG_DEBUG_MEMORY_INIT is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set @@ -674,6 +798,7 @@ CONFIG_TRACING_SUPPORT=y # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_TEST_KSTRTOX is not set CONFIG_EARLY_PRINTK=y CONFIG_CMDLINE_BOOL=y CONFIG_CMDLINE="init=/init" @@ -694,6 +819,7 @@ CONFIG_DEFAULT_SECURITY="" # OCF Configuration # # CONFIG_OCF_OCF is not set +# CONFIG_VIRTUALIZATION is not set # CONFIG_BINARY_PRINTF is not set # @@ -708,8 +834,10 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set -CONFIG_DECOMPRESS_LZMA=y +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y +# CONFIG_AVERAGE is not set diff --git a/target/mips/sys-available/mikrotik-rb411 b/target/mips/sys-available/mikrotik-rb411 deleted file mode 100644 index 6e1f597b1..000000000 --- a/target/mips/sys-available/mikrotik-rb411 +++ /dev/null @@ -1,13 +0,0 @@ -config ADK_TARGET_SYSTEM_MIKROTIK_RB411 - bool "Mikrotik Routerboard 411" - select ADK_mips - select ADK_big - select ADK_mikrotik_rb411 - select ADK_KERNEL_ATHEROS_AR71XX - select ADK_KERNEL_ATHEROS_MACH_RB4XX - select ADK_TARGET_WITH_MINIPCI - select ADK_TARGET_WITH_WATCHDOG - select ADK_TARGET_WITH_NAND - help - Support for Mikrotik RB411. - diff --git a/target/mips/sys-available/mikrotik-rb433 b/target/mips/sys-available/mikrotik-rb433 deleted file mode 100644 index 107f317a6..000000000 --- a/target/mips/sys-available/mikrotik-rb433 +++ /dev/null @@ -1,13 +0,0 @@ -config ADK_TARGET_SYSTEM_MIKROTIK_RB433 - bool "Mikrotik Routerboard 433" - select ADK_mips - select ADK_big - select ADK_mikrotik_rb433 - select ADK_KERNEL_ATHEROS_AR71XX - select ADK_KERNEL_ATHEROS_MACH_RB4XX - select ADK_TARGET_WITH_MINIPCI - select ADK_TARGET_WITH_WATCHDOG - select ADK_TARGET_WITH_NAND - help - Support for Mikrotik RB433. - diff --git a/target/mips/sys-available/mikrotik-rb4xx b/target/mips/sys-available/mikrotik-rb4xx new file mode 100644 index 000000000..421f4abb7 --- /dev/null +++ b/target/mips/sys-available/mikrotik-rb4xx @@ -0,0 +1,15 @@ +config ADK_TARGET_SYSTEM_MIKROTIK_RB4XX + bool "Mikrotik Routerboard 4xx" + select ADK_mips + select ADK_big + select ADK_mikrotik_rb4xx + select ADK_KERNEL_ATHEROS_AR71XX + select ADK_KERNEL_AR71XX_MACH_RB4XX + select ADK_KERNEL_SPI_RB4XX + select ADK_KERNEL_SPI_RB4XX_CPLD + select ADK_TARGET_WITH_MINIPCI + select ADK_TARGET_WITH_WATCHDOG + select ADK_TARGET_WITH_NAND + help + Support for Mikrotik RB411/RB433. + -- cgit v1.2.3 From 52229f5bf2fe45d139c6a692415fe1ffb8ea4041 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 12:19:48 +0200 Subject: add qemu sparc64, but it segfaults --- target/sparc64/Makefile | 2 +- target/sparc64/sys-available/qemu-sparc64 | 13 +++++++++++ toolchain/gcc/patches/no-lib64.patch | 36 +++++++++++++++++++++++++------ 3 files changed, 44 insertions(+), 7 deletions(-) create mode 100644 target/sparc64/sys-available/qemu-sparc64 diff --git a/target/sparc64/Makefile b/target/sparc64/Makefile index 9f2a152f9..39212d52e 100644 --- a/target/sparc64/Makefile +++ b/target/sparc64/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/mk/modules.mk include $(TOPDIR)/mk/kernel-build.mk include $(TOPDIR)/mk/image.mk -KERNEL:=$(LINUX_DIR)/arch/sparc64/boot/zImage +KERNEL:=$(LINUX_DIR)/arch/sparc/boot/zImage ifeq ($(ADK_TARGET_FS),archive) imageinstall: $(BIN_DIR)/$(ROOTFSTARBALL) diff --git a/target/sparc64/sys-available/qemu-sparc64 b/target/sparc64/sys-available/qemu-sparc64 new file mode 100644 index 000000000..06f493ba7 --- /dev/null +++ b/target/sparc64/sys-available/qemu-sparc64 @@ -0,0 +1,13 @@ +config ADK_TARGET_SYSTEM_QEMU_SPARC64 + bool "Qemu Emulator" + select ADK_sparc64 + select ADK_qemu_sparc64 + select ADK_CPU_SPARC_V9 + select ADK_HARDWARE_QEMU + select ADK_TARGET_WITH_VGA + select ADK_TARGET_WITH_INPUT + select ADK_TARGET_WITH_PCI + select ADK_TARGET_WITH_HDD + help + Support for Qemu Emulator (SPARC64). + diff --git a/toolchain/gcc/patches/no-lib64.patch b/toolchain/gcc/patches/no-lib64.patch index 5fc1225e1..5c6e0b045 100644 --- a/toolchain/gcc/patches/no-lib64.patch +++ b/toolchain/gcc/patches/no-lib64.patch @@ -1,6 +1,6 @@ diff -Nur gcc-4.5.3.orig/gcc/config/i386/linux64.h gcc-4.5.3/gcc/config/i386/linux64.h --- gcc-4.5.3.orig/gcc/config/i386/linux64.h 2010-03-24 21:44:48.000000000 +0100 -+++ gcc-4.5.3/gcc/config/i386/linux64.h 2011-08-24 01:58:27.000000000 +0200 ++++ gcc-4.5.3/gcc/config/i386/linux64.h 2011-08-24 06:35:30.000000000 +0200 @@ -59,7 +59,7 @@ done. */ @@ -12,7 +12,7 @@ diff -Nur gcc-4.5.3.orig/gcc/config/i386/linux64.h gcc-4.5.3/gcc/config/i386/lin #define SPEC_32 "m32" diff -Nur gcc-4.5.3.orig/gcc/config/i386/t-linux64 gcc-4.5.3/gcc/config/i386/t-linux64 --- gcc-4.5.3.orig/gcc/config/i386/t-linux64 2009-04-21 21:03:23.000000000 +0200 -+++ gcc-4.5.3/gcc/config/i386/t-linux64 2011-08-24 01:58:27.000000000 +0200 ++++ gcc-4.5.3/gcc/config/i386/t-linux64 2011-08-24 06:35:30.000000000 +0200 @@ -25,7 +25,7 @@ MULTILIB_OPTIONS = m64/m32 @@ -24,7 +24,7 @@ diff -Nur gcc-4.5.3.orig/gcc/config/i386/t-linux64 gcc-4.5.3/gcc/config/i386/t-l INSTALL_LIBGCC = install-multilib diff -Nur gcc-4.5.3.orig/gcc/config/mips/linux64.h gcc-4.5.3/gcc/config/mips/linux64.h --- gcc-4.5.3.orig/gcc/config/mips/linux64.h 2009-02-20 16:20:38.000000000 +0100 -+++ gcc-4.5.3/gcc/config/mips/linux64.h 2011-08-24 01:58:27.000000000 +0200 ++++ gcc-4.5.3/gcc/config/mips/linux64.h 2011-08-24 06:35:30.000000000 +0200 @@ -36,9 +36,9 @@ %{profile:-lc_p} %{!profile:-lc}}" @@ -40,7 +40,7 @@ diff -Nur gcc-4.5.3.orig/gcc/config/mips/linux64.h gcc-4.5.3/gcc/config/mips/lin diff -Nur gcc-4.5.3.orig/gcc/config/mips/t-linux64 gcc-4.5.3/gcc/config/mips/t-linux64 --- gcc-4.5.3.orig/gcc/config/mips/t-linux64 2009-04-21 21:03:23.000000000 +0200 -+++ gcc-4.5.3/gcc/config/mips/t-linux64 2011-08-24 01:58:27.000000000 +0200 ++++ gcc-4.5.3/gcc/config/mips/t-linux64 2011-08-24 06:35:30.000000000 +0200 @@ -18,7 +18,7 @@ MULTILIB_OPTIONS = mabi=n32/mabi=32/mabi=64 @@ -52,7 +52,7 @@ diff -Nur gcc-4.5.3.orig/gcc/config/mips/t-linux64 gcc-4.5.3/gcc/config/mips/t-l diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/linux64.h gcc-4.5.3/gcc/config/rs6000/linux64.h --- gcc-4.5.3.orig/gcc/config/rs6000/linux64.h 2010-11-17 07:09:53.000000000 +0100 -+++ gcc-4.5.3/gcc/config/rs6000/linux64.h 2011-08-24 02:01:35.000000000 +0200 ++++ gcc-4.5.3/gcc/config/rs6000/linux64.h 2011-08-24 06:35:30.000000000 +0200 @@ -341,7 +341,7 @@ #define LINK_OS_DEFAULT_SPEC "%(link_os_linux)" @@ -64,7 +64,7 @@ diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/linux64.h gcc-4.5.3/gcc/config/rs6000 #if UCLIBC_DEFAULT diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/t-linux64 gcc-4.5.3/gcc/config/rs6000/t-linux64 --- gcc-4.5.3.orig/gcc/config/rs6000/t-linux64 2009-04-21 21:03:23.000000000 +0200 -+++ gcc-4.5.3/gcc/config/rs6000/t-linux64 2011-08-24 02:00:50.000000000 +0200 ++++ gcc-4.5.3/gcc/config/rs6000/t-linux64 2011-08-24 06:35:30.000000000 +0200 @@ -36,7 +36,7 @@ MULTILIB_EXTRA_OPTS = fPIC mstrict-align MULTILIB_EXCEPTIONS = m64/msoft-float @@ -74,3 +74,27 @@ diff -Nur gcc-4.5.3.orig/gcc/config/rs6000/t-linux64 gcc-4.5.3/gcc/config/rs6000 MULTILIB_MATCHES = $(MULTILIB_MATCHES_FLOAT) softfp_wrap_start := '\#ifndef __powerpc64__' +diff -Nur gcc-4.5.3.orig/gcc/config/sparc/linux64.h gcc-4.5.3/gcc/config/sparc/linux64.h +--- gcc-4.5.3.orig/gcc/config/sparc/linux64.h 2010-09-22 23:15:37.000000000 +0200 ++++ gcc-4.5.3/gcc/config/sparc/linux64.h 2011-08-24 06:36:52.000000000 +0200 +@@ -110,7 +110,7 @@ + /* If ELF is the default format, we should not use /lib/elf. */ + + #define GLIBC_DYNAMIC_LINKER32 "/lib/ld-linux.so.2" +-#define GLIBC_DYNAMIC_LINKER64 "/lib64/ld-linux.so.2" ++#define GLIBC_DYNAMIC_LINKER64 "/lib/ld-linux.so.2" + + #ifdef SPARC_BI_ARCH + +diff -Nur gcc-4.5.3.orig/gcc/config/sparc/t-linux64 gcc-4.5.3/gcc/config/sparc/t-linux64 +--- gcc-4.5.3.orig/gcc/config/sparc/t-linux64 2010-10-04 18:54:26.000000000 +0200 ++++ gcc-4.5.3/gcc/config/sparc/t-linux64 2011-08-24 06:37:15.000000000 +0200 +@@ -26,7 +26,7 @@ + + MULTILIB_OPTIONS = m64/m32 + MULTILIB_DIRNAMES = 64 32 +-MULTILIB_OSDIRNAMES = ../lib64 $(if $(wildcard $(shell echo $(SYSTEM_HEADER_DIR))/../../usr/lib32),../lib32,../lib) ++MULTILIB_OSDIRNAMES = ../lib $(if $(wildcard $(shell echo $(SYSTEM_HEADER_DIR))/../../usr/lib32),../lib32,../lib) + + LIBGCC = stmp-multilib + INSTALL_LIBGCC = install-multilib -- cgit v1.2.3 From a90eb09d8eb3f03d96c5624af558710d6bbe54b5 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 14:05:31 +0200 Subject: ppc64 works with latest qemu, fix kernel config --- target/ppc64/kernel.config | 10 ++-------- 1 file changed, 2 insertions(+), 8 deletions(-) diff --git a/target/ppc64/kernel.config b/target/ppc64/kernel.config index 0095cb373..64152ccf6 100644 --- a/target/ppc64/kernel.config +++ b/target/ppc64/kernel.config @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit # Linux/powerpc 2.6.39 Kernel Configuration -# Wed Aug 24 03:57:23 2011 +# Wed Aug 24 13:58:26 2011 # CONFIG_PPC64=y @@ -546,12 +546,7 @@ CONFIG_UNIX98_PTYS=y # # Serial drivers # -CONFIG_SERIAL_8250=y -CONFIG_SERIAL_8250_CONSOLE=y -CONFIG_SERIAL_8250_PCI=y -CONFIG_SERIAL_8250_NR_UARTS=4 -CONFIG_SERIAL_8250_RUNTIME_UARTS=4 -# CONFIG_SERIAL_8250_EXTENDED is not set +# CONFIG_SERIAL_8250 is not set # # Non-8250 serial port support @@ -563,7 +558,6 @@ CONFIG_SERIAL_PMACZILOG=y CONFIG_SERIAL_PMACZILOG_TTYS=y CONFIG_SERIAL_PMACZILOG_CONSOLE=y # CONFIG_SERIAL_JSM is not set -# CONFIG_SERIAL_OF_PLATFORM is not set # CONFIG_SERIAL_TIMBERDALE is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -- cgit v1.2.3 From dba3e49a84a07bb1c248d2da9edd0b5d1c502ee8 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 15:37:54 +0200 Subject: now only userland segfaults --- target/sparc64/Makefile | 10 +- target/sparc64/kernel.config | 313 +++++++++++++++++++++++++++++++++---------- 2 files changed, 254 insertions(+), 69 deletions(-) diff --git a/target/sparc64/Makefile b/target/sparc64/Makefile index 39212d52e..3e7240621 100644 --- a/target/sparc64/Makefile +++ b/target/sparc64/Makefile @@ -7,7 +7,7 @@ include $(TOPDIR)/mk/modules.mk include $(TOPDIR)/mk/kernel-build.mk include $(TOPDIR)/mk/image.mk -KERNEL:=$(LINUX_DIR)/arch/sparc/boot/zImage +KERNEL:=$(LINUX_DIR)/vmlinux ifeq ($(ADK_TARGET_FS),archive) imageinstall: $(BIN_DIR)/$(ROOTFSTARBALL) @@ -20,9 +20,17 @@ imageinstall: $(BIN_DIR)/$(INITRAMFS) @cp $(KERNEL) $(BIN_DIR)/$(TARGET_KERNEL) @echo 'The kernel file is: $(BIN_DIR)/${TARGET_KERNEL}' @echo 'The initramfs image is: ${BIN_DIR}/${INITRAMFS}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_SPARC64),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-sparc64 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL) -initrd ${BIN_DIR}/${INITRAMFS}' +endif endif ifeq ($(ADK_TARGET_FS),initramfs-piggyback) imageinstall: ${BUILD_DIR}/${INITRAMFS_PIGGYBACK} createinitramfs @cp $(KERNEL) $(BIN_DIR)/${TARGET_KERNEL} @echo 'The kernel+initramfs file is: $(BIN_DIR)/${TARGET_KERNEL}' +ifeq ($(ADK_TARGET_SYSTEM_QEMU_SPARC64),y) + @echo "Start qemu with following command line:" + @echo 'qemu-system-sparc64 -nographic -kernel $(BIN_DIR)/$(TARGET_KERNEL)' +endif endif diff --git a/target/sparc64/kernel.config b/target/sparc64/kernel.config index 494b9c2ea..5c6b6b7f9 100644 --- a/target/sparc64/kernel.config +++ b/target/sparc64/kernel.config @@ -1,26 +1,33 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.36 -# Fri Nov 19 00:15:14 2010 +# Linux/sparc 2.6.39 Kernel Configuration +# Wed Aug 24 15:35:30 2011 # -# CONFIG_64BIT is not set +CONFIG_64BIT=y CONFIG_SPARC=y -CONFIG_SPARC32=y -# CONFIG_SPARC64 is not set -CONFIG_ARCH_DEFCONFIG="arch/sparc/configs/sparc32_defconfig" -CONFIG_BITS=32 -CONFIG_ARCH_USES_GETTIMEOFFSET=y +# CONFIG_SPARC32 is not set +CONFIG_SPARC64=y +CONFIG_ARCH_DEFCONFIG="arch/sparc/configs/sparc64_defconfig" +CONFIG_BITS=64 CONFIG_GENERIC_CMOS_UPDATE=y +CONFIG_GENERIC_CLOCKEVENTS=y +CONFIG_IOMMU_HELPER=y +CONFIG_QUICKLIST=y +CONFIG_STACKTRACE_SUPPORT=y +CONFIG_LOCKDEP_SUPPORT=y +CONFIG_HAVE_LATENCYTOP_SUPPORT=y CONFIG_AUDIT_ARCH=y +CONFIG_HAVE_SETUP_PER_CPU_AREA=y +CONFIG_NEED_PER_CPU_EMBED_FIRST_CHUNK=y +CONFIG_NEED_PER_CPU_PAGE_FIRST_CHUNK=y CONFIG_MMU=y -CONFIG_HIGHMEM=y -CONFIG_ZONE_DMA=y CONFIG_NEED_DMA_MAP_STATE=y CONFIG_NEED_SG_DMA_LENGTH=y -CONFIG_GENERIC_ISA_DMA=y CONFIG_ARCH_NO_VIRT_TO_BUS=y +CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y +CONFIG_HAVE_IRQ_WORK=y # # General setup @@ -37,30 +44,38 @@ CONFIG_SYSVIPC_SYSCTL=y CONFIG_POSIX_MQUEUE=y CONFIG_POSIX_MQUEUE_SYSCTL=y # CONFIG_BSD_PROCESS_ACCT is not set +# CONFIG_FHANDLE is not set # CONFIG_TASKSTATS is not set # CONFIG_AUDIT is not set +CONFIG_HAVE_GENERIC_HARDIRQS=y + +# +# IRQ subsystem +# +CONFIG_GENERIC_HARDIRQS=y +CONFIG_GENERIC_IRQ_SHOW=y +CONFIG_IRQ_PREFLOW_FASTEOI=y # # RCU Subsystem # -CONFIG_TREE_RCU=y -# CONFIG_TINY_RCU is not set +CONFIG_TINY_RCU=y +# CONFIG_PREEMPT_RCU is not set # CONFIG_RCU_TRACE is not set -CONFIG_RCU_FANOUT=32 -# CONFIG_RCU_FANOUT_EXACT is not set # CONFIG_TREE_RCU_TRACE is not set CONFIG_IKCONFIG=y CONFIG_IKCONFIG_PROC=y CONFIG_LOG_BUF_SHIFT=15 # CONFIG_CGROUPS is not set -# CONFIG_SYSFS_DEPRECATED_V2 is not set -# CONFIG_RELAY is not set # CONFIG_NAMESPACES is not set +# CONFIG_SCHED_AUTOGROUP is not set +# CONFIG_SYSFS_DEPRECATED is not set +# CONFIG_RELAY is not set # CONFIG_BLK_DEV_INITRD is not set CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_SYSCTL=y CONFIG_ANON_INODES=y -CONFIG_EMBEDDED=y +CONFIG_EXPERT=y CONFIG_UID16=y CONFIG_SYSCTL_SYSCALL=y # CONFIG_KALLSYMS is not set @@ -76,6 +91,7 @@ CONFIG_TIMERFD=y CONFIG_EVENTFD=y CONFIG_SHMEM=y CONFIG_AIO=y +CONFIG_EMBEDDED=y CONFIG_HAVE_PERF_EVENTS=y CONFIG_PERF_USE_VMALLOC=y @@ -92,9 +108,15 @@ CONFIG_SLAB=y # CONFIG_SLOB is not set # CONFIG_PROFILING is not set CONFIG_HAVE_OPROFILE=y +# CONFIG_KPROBES is not set +# CONFIG_JUMP_LABEL is not set +CONFIG_HAVE_SYSCALL_WRAPPERS=y +CONFIG_HAVE_KPROBES=y +CONFIG_HAVE_KRETPROBES=y CONFIG_HAVE_ARCH_TRACEHOOK=y CONFIG_HAVE_DMA_ATTRS=y CONFIG_HAVE_DMA_API_DEBUG=y +CONFIG_HAVE_ARCH_JUMP_LABEL=y # # GCOV-based kernel profiling @@ -110,9 +132,9 @@ CONFIG_MODULE_FORCE_UNLOAD=y # CONFIG_MODVERSIONS is not set # CONFIG_MODULE_SRCVERSION_ALL is not set CONFIG_BLOCK=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEV_INTEGRITY is not set +CONFIG_BLOCK_COMPAT=y # # IO Schedulers @@ -164,48 +186,74 @@ CONFIG_HZ_250=y # CONFIG_HZ_1000 is not set CONFIG_HZ=250 # CONFIG_SCHED_HRTICK is not set -CONFIG_RWSEM_GENERIC_SPINLOCK=y +CONFIG_RWSEM_XCHGADD_ALGORITHM=y CONFIG_GENERIC_FIND_NEXT_BIT=y +CONFIG_GENERIC_FIND_BIT_LE=y CONFIG_GENERIC_HWEIGHT=y CONFIG_GENERIC_CALIBRATE_DELAY=y CONFIG_ARCH_MAY_HAVE_PC_FDC=y -CONFIG_EMULATED_CMPXCHG=y +CONFIG_EARLYFB=y +CONFIG_SPARC64_PAGE_SIZE_8KB=y +# CONFIG_SPARC64_PAGE_SIZE_64KB is not set +# CONFIG_SECCOMP is not set +# CONFIG_NO_HZ is not set +# CONFIG_HIGH_RES_TIMERS is not set +CONFIG_GENERIC_CLOCKEVENTS_BUILD=y +# CONFIG_CPU_FREQ is not set +# CONFIG_US3_MC is not set +CONFIG_ARCH_POPULATES_NODE_MAP=y +CONFIG_ARCH_SELECT_MEMORY_MODEL=y +CONFIG_ARCH_SPARSEMEM_ENABLE=y +CONFIG_ARCH_SPARSEMEM_DEFAULT=y CONFIG_SELECT_MEMORY_MODEL=y -CONFIG_FLATMEM_MANUAL=y -CONFIG_FLATMEM=y -CONFIG_FLAT_NODE_MEM_MAP=y +CONFIG_SPARSEMEM_MANUAL=y +CONFIG_SPARSEMEM=y +CONFIG_HAVE_MEMORY_PRESENT=y +CONFIG_SPARSEMEM_EXTREME=y +CONFIG_SPARSEMEM_VMEMMAP_ENABLE=y +# CONFIG_SPARSEMEM_VMEMMAP is not set +CONFIG_HAVE_MEMBLOCK=y CONFIG_PAGEFLAGS_EXTENDED=y CONFIG_SPLIT_PTLOCK_CPUS=4 -# CONFIG_PHYS_ADDR_T_64BIT is not set -CONFIG_ZONE_DMA_FLAG=1 -CONFIG_BOUNCE=y +# CONFIG_COMPACTION is not set +CONFIG_PHYS_ADDR_T_64BIT=y +CONFIG_ZONE_DMA_FLAG=0 +CONFIG_NR_QUICK=1 # CONFIG_KSM is not set CONFIG_DEFAULT_MMAP_MIN_ADDR=4096 -CONFIG_SUN_PM=y -# CONFIG_SPARC_LED is not set -CONFIG_SERIAL_CONSOLE=y -# CONFIG_SPARC_LEON is not set +CONFIG_NEED_PER_CPU_KM=y +CONFIG_PREEMPT_NONE=y +# CONFIG_PREEMPT_VOLUNTARY is not set +# CONFIG_PREEMPT is not set +CONFIG_CMDLINE_BOOL=y +CONFIG_CMDLINE="console=ttyS0,9600" # # Bus options (PCI etc.) # CONFIG_SBUS=y CONFIG_SBUSCHAR=y +# CONFIG_SUN_LDOMS is not set CONFIG_PCI=y +CONFIG_PCI_DOMAINS=y CONFIG_PCI_SYSCALL=y -# CONFIG_ARCH_SUPPORTS_MSI is not set +CONFIG_ARCH_SUPPORTS_MSI=y +# CONFIG_PCI_MSI is not set # CONFIG_PCI_STUB is not set # CONFIG_PCI_IOV is not set # CONFIG_PCCARD is not set -# CONFIG_SUN_OPENPROMFS is not set -CONFIG_SPARC32_PCI=y +CONFIG_SUN_OPENPROMFS=y +CONFIG_SPARC64_PCI=y # # Executable file formats # CONFIG_BINFMT_ELF=y +CONFIG_COMPAT_BINFMT_ELF=y # CONFIG_HAVE_AOUT is not set # CONFIG_BINFMT_MISC is not set +CONFIG_COMPAT=y +CONFIG_SYSVIPC_COMPAT=y CONFIG_NET=y # @@ -217,10 +265,9 @@ CONFIG_UNIX=y CONFIG_INET=y # CONFIG_IP_MULTICAST is not set # CONFIG_IP_ADVANCED_ROUTER is not set -CONFIG_IP_FIB_HASH=y # CONFIG_IP_PNP is not set # CONFIG_NET_IPIP is not set -# CONFIG_NET_IPGRE is not set +# CONFIG_NET_IPGRE_DEMUX is not set # CONFIG_ARPD is not set # CONFIG_SYN_COOKIES is not set # CONFIG_INET_AH is not set @@ -248,6 +295,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_ATM is not set # CONFIG_L2TP is not set # CONFIG_BRIDGE is not set +# CONFIG_NET_DSA is not set # CONFIG_VLAN_8021Q is not set # CONFIG_DECNET is not set # CONFIG_LLC2 is not set @@ -261,6 +309,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_IEEE802154 is not set # CONFIG_NET_SCHED is not set # CONFIG_DCB is not set +# CONFIG_BATMAN_ADV is not set # # Network testing @@ -276,6 +325,7 @@ CONFIG_DEFAULT_TCP_CONG="cubic" # CONFIG_RFKILL is not set # CONFIG_NET_9P is not set # CONFIG_CAIF is not set +# CONFIG_CEPH_LIB is not set # # Device Drivers @@ -296,11 +346,14 @@ CONFIG_DEVTMPFS_MOUNT=y CONFIG_OF=y # -# Flattened Device Tree and Open Firmware support +# Device Tree and Open Firmware support # +CONFIG_OF_PROMTREE=y CONFIG_OF_DEVICE=y +CONFIG_OF_NET=y # CONFIG_PARPORT is not set # CONFIG_BLK_DEV is not set +# CONFIG_SENSORS_LIS3LV02D is not set # CONFIG_MISC_DEVICES is not set CONFIG_HAVE_IDE=y # CONFIG_IDE is not set @@ -320,19 +373,111 @@ CONFIG_SCSI_MOD=y # # IEEE 1394 (FireWire) support # - -# -# You can enable one or both FireWire driver stacks. -# - -# -# The newer stack is recommended. -# # CONFIG_FIREWIRE is not set -# CONFIG_IEEE1394 is not set # CONFIG_FIREWIRE_NOSY is not set # CONFIG_I2O is not set -# CONFIG_NETDEVICES is not set +CONFIG_NETDEVICES=y +# CONFIG_DUMMY is not set +# CONFIG_BONDING is not set +# CONFIG_MACVLAN is not set +# CONFIG_EQUALIZER is not set +# CONFIG_TUN is not set +# CONFIG_VETH is not set +# CONFIG_ARCNET is not set +# CONFIG_MII is not set +# CONFIG_PHYLIB is not set +CONFIG_NET_ETHERNET=y +CONFIG_SUNLANCE=y +# CONFIG_HAPPYMEAL is not set +# CONFIG_SUNBMAC is not set +# CONFIG_SUNQE is not set +# CONFIG_SUNGEM is not set +# CONFIG_CASSINI is not set +# CONFIG_NET_VENDOR_3COM is not set +# CONFIG_ETHOC is not set +# CONFIG_GRETH is not set +# CONFIG_DNET is not set +# CONFIG_NET_TULIP is not set +# CONFIG_HP100 is not set +# CONFIG_IBM_NEW_EMAC_ZMII is not set +# CONFIG_IBM_NEW_EMAC_RGMII is not set +# CONFIG_IBM_NEW_EMAC_TAH is not set +# CONFIG_IBM_NEW_EMAC_EMAC4 is not set +# CONFIG_IBM_NEW_EMAC_NO_FLOW_CTRL is not set +# CONFIG_IBM_NEW_EMAC_MAL_CLR_ICINTSTAT is not set +# CONFIG_IBM_NEW_EMAC_MAL_COMMON_ERR is not set +# CONFIG_NET_PCI is not set +# CONFIG_B44 is not set +# CONFIG_KS8851_MLL is not set +# CONFIG_ATL2 is not set +CONFIG_NETDEV_1000=y +# CONFIG_ACENIC is not set +# CONFIG_DL2K is not set +# CONFIG_E1000 is not set +# CONFIG_E1000E is not set +# CONFIG_IP1000 is not set +# CONFIG_IGB is not set +# CONFIG_IGBVF is not set +# CONFIG_MYRI_SBUS is not set +# CONFIG_NS83820 is not set +# CONFIG_HAMACHI is not set +# CONFIG_YELLOWFIN is not set +# CONFIG_R8169 is not set +# CONFIG_SIS190 is not set +# CONFIG_SKGE is not set +# CONFIG_SKY2 is not set +# CONFIG_VIA_VELOCITY is not set +# CONFIG_TIGON3 is not set +# CONFIG_BNX2 is not set +# CONFIG_CNIC is not set +# CONFIG_QLA3XXX is not set +# CONFIG_ATL1 is not set +# CONFIG_ATL1E is not set +# CONFIG_ATL1C is not set +# CONFIG_JME is not set +# CONFIG_STMMAC_ETH is not set +# CONFIG_PCH_GBE is not set +CONFIG_NETDEV_10000=y +# CONFIG_CHELSIO_T1 is not set +# CONFIG_CHELSIO_T3 is not set +# CONFIG_CHELSIO_T4 is not set +# CONFIG_CHELSIO_T4VF is not set +# CONFIG_ENIC is not set +# CONFIG_IXGBE is not set +# CONFIG_IXGB is not set +# CONFIG_S2IO is not set +# CONFIG_VXGE is not set +# CONFIG_MYRI10GE is not set +# CONFIG_NETXEN_NIC is not set +# CONFIG_NIU is not set +# CONFIG_MLX4_EN is not set +# CONFIG_MLX4_CORE is not set +# CONFIG_TEHUTI is not set +# CONFIG_BNX2X is not set +# CONFIG_QLCNIC is not set +# CONFIG_QLGE is not set +# CONFIG_BNA is not set +# CONFIG_SFC is not set +# CONFIG_BE2NET is not set +# CONFIG_TR is not set +# CONFIG_WLAN is not set + +# +# Enable WiMAX (Networking options) to see the WiMAX drivers +# +# CONFIG_WAN is not set + +# +# CAIF transport drivers +# +# CONFIG_FDDI is not set +# CONFIG_HIPPI is not set +# CONFIG_PPP is not set +# CONFIG_SLIP is not set +# CONFIG_NETCONSOLE is not set +# CONFIG_NETPOLL is not set +# CONFIG_NET_POLL_CONTROLLER is not set +# CONFIG_VMXNET3 is not set # CONFIG_ISDN is not set # CONFIG_PHONE is not set @@ -376,20 +521,18 @@ CONFIG_VT=y CONFIG_VT_CONSOLE=y CONFIG_HW_CONSOLE=y # CONFIG_VT_HW_CONSOLE_BINDING is not set -# CONFIG_DEVKMEM is not set +CONFIG_UNIX98_PTYS=y +# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set +# CONFIG_LEGACY_PTYS is not set # CONFIG_SERIAL_NONSTANDARD is not set -# CONFIG_N_GSM is not set # CONFIG_NOZOMI is not set +# CONFIG_N_GSM is not set +# CONFIG_DEVKMEM is not set # # Serial drivers # -CONFIG_SERIAL_8250=y -CONFIG_SERIAL_8250_CONSOLE=y -# CONFIG_SERIAL_8250_PCI is not set -CONFIG_SERIAL_8250_NR_UARTS=4 -CONFIG_SERIAL_8250_RUNTIME_UARTS=4 -# CONFIG_SERIAL_8250_EXTENDED is not set +# CONFIG_SERIAL_8250 is not set # # Non-8250 serial port support @@ -397,8 +540,10 @@ CONFIG_SERIAL_8250_RUNTIME_UARTS=4 # CONFIG_SERIAL_MFD_HSU is not set CONFIG_SERIAL_SUNCORE=y # CONFIG_SERIAL_SUNZILOG is not set -# CONFIG_SERIAL_SUNSU is not set +CONFIG_SERIAL_SUNSU=y +CONFIG_SERIAL_SUNSU_CONSOLE=y # CONFIG_SERIAL_SUNSAB is not set +# CONFIG_SERIAL_SUNHV is not set CONFIG_SERIAL_CORE=y CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_JSM is not set @@ -406,9 +551,8 @@ CONFIG_SERIAL_CORE_CONSOLE=y # CONFIG_SERIAL_GRLIB_GAISLER_APBUART is not set # CONFIG_SERIAL_ALTERA_JTAGUART is not set # CONFIG_SERIAL_ALTERA_UART is not set -CONFIG_UNIX98_PTYS=y -# CONFIG_DEVPTS_MULTIPLE_INSTANCES is not set -# CONFIG_LEGACY_PTYS is not set +# CONFIG_SERIAL_PCH_UART is not set +# CONFIG_TTY_PRINTK is not set # CONFIG_IPMI_HANDLER is not set # CONFIG_HW_RANDOM is not set # CONFIG_R3964 is not set @@ -424,6 +568,10 @@ CONFIG_DEVPORT=y # PPS support # # CONFIG_PPS is not set + +# +# PPS generators support +# CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y # CONFIG_GPIOLIB is not set # CONFIG_W1 is not set @@ -445,6 +593,8 @@ CONFIG_SSB_POSSIBLE=y # Graphics support # # CONFIG_VGA_ARB is not set +# CONFIG_DRM is not set +# CONFIG_STUB_POULSBO is not set # CONFIG_VGASTATE is not set # CONFIG_VIDEO_OUTPUT_CONTROL is not set # CONFIG_FB is not set @@ -466,6 +616,7 @@ CONFIG_DUMMY_CONSOLE=y # CONFIG_MMC is not set # CONFIG_MEMSTICK is not set # CONFIG_NEW_LEDS is not set +# CONFIG_NFC_DEVICES is not set # CONFIG_ACCESSIBILITY is not set # CONFIG_INFINIBAND is not set CONFIG_RTC_LIB=y @@ -490,6 +641,7 @@ CONFIG_RTC_INTF_DEV=y # # Platform RTC drivers # +CONFIG_RTC_DRV_CMOS=y # CONFIG_RTC_DRV_DS1286 is not set # CONFIG_RTC_DRV_DS1511 is not set # CONFIG_RTC_DRV_DS1553 is not set @@ -499,13 +651,15 @@ CONFIG_RTC_INTF_DEV=y # CONFIG_RTC_DRV_M48T35 is not set CONFIG_RTC_DRV_M48T59=y # CONFIG_RTC_DRV_MSM6242 is not set -# CONFIG_RTC_DRV_BQ4802 is not set +CONFIG_RTC_DRV_BQ4802=y # CONFIG_RTC_DRV_RP5C01 is not set # CONFIG_RTC_DRV_V3020 is not set # # on-CPU RTC drivers # +CONFIG_RTC_DRV_SUN4V=y +CONFIG_RTC_DRV_STARFIRE=y # CONFIG_DMADEVICES is not set # CONFIG_AUXDISPLAY is not set # CONFIG_UIO is not set @@ -514,9 +668,12 @@ CONFIG_RTC_DRV_M48T59=y # # Misc Linux/SPARC drivers # -# CONFIG_SUN_OPENPROMIO is not set +CONFIG_SUN_OPENPROMIO=y +# CONFIG_OBP_FLASH is not set # CONFIG_TADPOLE_TS102_UCTRL is not set -# CONFIG_SUN_JSFLASH is not set +# CONFIG_BBC_I2C is not set +# CONFIG_ENVCTRL is not set +# CONFIG_DISPLAY7SEG is not set # # File systems @@ -526,17 +683,19 @@ CONFIG_RTC_DRV_M48T59=y # CONFIG_EXT4_FS is not set # CONFIG_REISERFS_FS is not set # CONFIG_JFS_FS is not set -# CONFIG_FS_POSIX_ACL is not set # CONFIG_XFS_FS is not set -# CONFIG_OCFS2_FS is not set +# CONFIG_GFS2_FS is not set # CONFIG_BTRFS_FS is not set # CONFIG_NILFS2_FS is not set +CONFIG_FS_POSIX_ACL=y +CONFIG_EXPORTFS=y CONFIG_FILE_LOCKING=y -# CONFIG_FSNOTIFY is not set +CONFIG_FSNOTIFY=y # CONFIG_DNOTIFY is not set # CONFIG_INOTIFY_USER is not set +# CONFIG_FANOTIFY is not set # CONFIG_QUOTA is not set -# CONFIG_AUTOFS_FS is not set +# CONFIG_QUOTACTL is not set # CONFIG_AUTOFS4_FS is not set # CONFIG_FUSE_FS is not set @@ -568,6 +727,7 @@ CONFIG_PROC_SYSCTL=y CONFIG_SYSFS=y CONFIG_TMPFS=y # CONFIG_TMPFS_POSIX_ACL is not set +# CONFIG_HUGETLBFS is not set # CONFIG_HUGETLB_PAGE is not set # CONFIG_CONFIGFS_FS is not set # CONFIG_MISC_FILESYSTEMS is not set @@ -580,13 +740,13 @@ CONFIG_TMPFS=y CONFIG_MSDOS_PARTITION=y CONFIG_SUN_PARTITION=y # CONFIG_NLS is not set -# CONFIG_DLM is not set # # Kernel hacking # CONFIG_TRACE_IRQFLAGS_SUPPORT=y CONFIG_PRINTK_TIME=y +CONFIG_DEFAULT_MESSAGE_LOGLEVEL=4 # CONFIG_ENABLE_WARN_DEPRECATED is not set # CONFIG_ENABLE_MUST_CHECK is not set CONFIG_FRAME_WARN=1024 @@ -595,21 +755,33 @@ CONFIG_FRAME_WARN=1024 # CONFIG_UNUSED_SYMBOLS is not set # CONFIG_DEBUG_FS is not set # CONFIG_HEADERS_CHECK is not set +# CONFIG_DEBUG_SECTION_MISMATCH is not set # CONFIG_DEBUG_KERNEL is not set # CONFIG_HARDLOCKUP_DETECTOR is not set +# CONFIG_SPARSE_RCU_POINTER is not set CONFIG_DEBUG_BUGVERBOSE=y # CONFIG_DEBUG_MEMORY_INIT is not set -# CONFIG_RCU_CPU_STALL_DETECTOR is not set # CONFIG_SYSCTL_SYSCALL_CHECK is not set +CONFIG_HAVE_FUNCTION_TRACER=y +CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y +CONFIG_HAVE_FUNCTION_GRAPH_FP_TEST=y +CONFIG_HAVE_FUNCTION_TRACE_MCOUNT_TEST=y +CONFIG_HAVE_DYNAMIC_FTRACE=y +CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y +CONFIG_HAVE_SYSCALL_TRACEPOINTS=y +CONFIG_TRACING_SUPPORT=y +# CONFIG_FTRACE is not set # CONFIG_DMA_API_DEBUG is not set # CONFIG_ATOMIC64_SELFTEST is not set # CONFIG_SAMPLES is not set CONFIG_HAVE_ARCH_KGDB=y +# CONFIG_TEST_KSTRTOX is not set # # Security options # # CONFIG_KEYS is not set +# CONFIG_SECURITY_DMESG_RESTRICT is not set # CONFIG_SECURITY is not set # CONFIG_SECURITYFS is not set CONFIG_DEFAULT_SECURITY_DAC=y @@ -700,6 +872,8 @@ CONFIG_CRYPTO=y # Random Number Generation # # CONFIG_CRYPTO_ANSI_CPRNG is not set +# CONFIG_CRYPTO_USER_API_HASH is not set +# CONFIG_CRYPTO_USER_API_SKCIPHER is not set # CONFIG_CRYPTO_HW is not set # @@ -720,7 +894,10 @@ CONFIG_GENERIC_FIND_LAST_BIT=y CONFIG_CRC32=y # CONFIG_CRC7 is not set # CONFIG_LIBCRC32C is not set +# CONFIG_XZ_DEC is not set +# CONFIG_XZ_DEC_BCJ is not set CONFIG_HAS_IOMEM=y CONFIG_HAS_IOPORT=y CONFIG_HAS_DMA=y CONFIG_NLATTR=y +# CONFIG_AVERAGE is not set -- cgit v1.2.3 From a32d9bd883df3ed4ee3fabeca3fcc2e3ba768602 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 15:37:37 +0200 Subject: add Tobias to the list of contributors --- THANKS | 1 + 1 file changed, 1 insertion(+) diff --git a/THANKS b/THANKS index 10b3d1767..1c2fc9d53 100644 --- a/THANKS +++ b/THANKS @@ -4,3 +4,4 @@ reports, patches or good suggestions: Thorsten Glaser Joerg Seitter Phil Sutter +Tobias Breckle -- cgit v1.2.3 From 8aebf811b766c899d97620874cf39e37b6e4f7a7 Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Wed, 24 Aug 2011 19:52:33 +0200 Subject: honour target cflags/cxxflags, add explizit search paths for headers and library for non-sysroot toolchains --- package/openjdk/Makefile | 4 ++++ package/openjdk/patches/cxxflags-nozlib.patch | 31 +++++++++++++++++++++++++++ 2 files changed, 35 insertions(+) create mode 100644 package/openjdk/patches/cxxflags-nozlib.patch diff --git a/package/openjdk/Makefile b/package/openjdk/Makefile index 347f3b01d..4bb68bb88 100644 --- a/package/openjdk/Makefile +++ b/package/openjdk/Makefile @@ -98,7 +98,10 @@ CONFIGURE_ENV+= PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET MAKE_ENV+= ALT_COMPILER_PATH=$(STAGING_HOST_DIR)/$(REAL_GNU_TARGET_NAME) \ ADK_ECJ=$(STAGING_JAVA_HOST_DIR)/usr/bin/ecj \ PATH=$(STAGING_JAVA_HOST_DIR)/usr/bin:$${PATH}:${STAGING_TARGET_DIR}/usr/bin \ + OTHER_CFLAGS='$(TARGET_CFLAGS) $(TARGET_CPPFLAGS) $(TARGET_LDFLAGS)' \ + OTHER_CXXFLAGS='$(TARGET_CFLAGS) $(TARGET_CPPFLAGS) $(TARGET_LDFLAGS)' \ GCC_HONOUR_COPTS=s CROSS_COMPILE_ARCH=$(ARCH) + ALL_TARGET:= icedtea # add include path for Xrender.h from staging directory @@ -107,6 +110,7 @@ ifeq ($(QEMU),) $(error Fatal error: $$QEMU not set!) endif $(SED) "s#@ADK_TARGETDIR@#$(STAGING_TARGET_DIR)#" ${WRKDIST}/$(PKG_NAME)-$(PKG_VERSION)/jdk/make/sun/xawt/Makefile + $(SED) "s#OTHER_CXXFLAGS#CXXFLAGS_COMMON#" ${WRKDIST}/$(PKG_NAME)-$(PKG_VERSION)/jdk/make/com/sun/java/pack/Makefile do-extract: cd ${WRKDIST}; mkdir $(PKG_NAME)-$(PKG_VERSION); \ diff --git a/package/openjdk/patches/cxxflags-nozlib.patch b/package/openjdk/patches/cxxflags-nozlib.patch new file mode 100644 index 000000000..67812253a --- /dev/null +++ b/package/openjdk/patches/cxxflags-nozlib.patch @@ -0,0 +1,31 @@ +--- w-openjdk-6.orig/icedtea6-1.10/patches/libraries.patch 2011-02-23 23:32:34.602901049 +0100 ++++ w-openjdk-6/icedtea6-1.10/patches/libraries.patch 2011-08-24 15:07:24.347475241 +0200 +@@ -24648,7 +24648,7 @@ + - $(ZIPOBJDIR)/inffast.$(OBJECT_SUFFIX) + - + - ZINCLUDE=-I$(SHARE_SRC)/native/java/util/zip/zlib-1.1.3 +-- OTHER_CXXFLAGS += $(ZINCLUDE) ++- CXXFLAGS_COMMON += $(ZINCLUDE) + - LDDFLAGS += $(ZIPOBJS) + + $(ZIPOBJDIR)/deflate.$(OBJECT_SUFFIX) \ + + $(ZIPOBJDIR)/trees.$(OBJECT_SUFFIX) \ +@@ -24663,7 +24663,7 @@ + + + + OTHER_LDLIBS += -lz + else +- OTHER_CXXFLAGS += -DNO_ZLIB -DUNPACK_JNI ++ CXXFLAGS_COMMON += -DNO_ZLIB -DUNPACK_JNI + - OTHER_LDLIBS += $(JVMLIB) + + OTHER_LDLIBS += -lz $(JVMLIB) + endif +--- w-openjdk-6.orig/icedtea6-1.10/patches/linker-libs-order.patch 2011-02-23 23:32:34.653236038 +0100 ++++ w-openjdk-6/icedtea6-1.10/patches/linker-libs-order.patch 2011-08-24 15:53:05.047474381 +0200 +@@ -31,7 +31,7 @@ + + - OTHER_LDLIBS += -lz + else +- OTHER_CXXFLAGS += -DNO_ZLIB -DUNPACK_JNI ++ CXXFLAGS_COMMON += -DNO_ZLIB -DUNPACK_JNI + - OTHER_LDLIBS += -lz $(JVMLIB) + + OTHER_LDLIBS += $(JVMLIB) + endif -- cgit v1.2.3 From b2e4d29ea9c3c2f5b99264bd270d4257439dfc3f Mon Sep 17 00:00:00 2001 From: Waldemar Brodkorb Date: Fri, 26 Aug 2011 10:21:17 +0200 Subject: simplify patch, link instead of copy is okay for Linux host --- jtools/openjdk/patches/openjdk.patch | 23 +++-------------------- 1 file changed, 3 insertions(+), 20 deletions(-) diff --git a/jtools/openjdk/patches/openjdk.patch b/jtools/openjdk/patches/openjdk.patch index 1ef7e195f..85fbb87f4 100644 --- a/jtools/openjdk/patches/openjdk.patch +++ b/jtools/openjdk/patches/openjdk.patch @@ -1,4 +1,6 @@ -diff -Nur openjdk-6.orig/Makefile openjdk-6/Makefile + +use precompiled ecj. + --- openjdk-6.orig/Makefile 2011-02-28 17:02:07.000000000 +0100 +++ openjdk-6/Makefile 2011-04-06 19:47:19.261818496 +0200 @@ -25,9 +25,7 @@ @@ -12,27 +14,8 @@ diff -Nur openjdk-6.orig/Makefile openjdk-6/Makefile ifndef JDK_TOPDIR JDK_TOPDIR=$(TOPDIR)/jdk -diff -Nur icedtea6-1.10.orig/Makefile.in icedtea6-1.10/Makefile.in --- icedtea6-1.10.orig/Makefile.in 2011-03-02 20:48:45.161291458 +0100 +++ icedtea6-1.10/Makefile.in 2011-04-06 20:10:40.581819545 +0200 -@@ -1329,7 +1329,7 @@ - @OPENJDK_SRC_DIR_FOUND_TRUE@ cp -pPR $(OPENJDK_SRC_DIR_LINK) $(OPENJDK_SRC_DIR) openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ if ! test -d openjdk ; then \ --@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPRl openjdk.hg openjdk ; \ -+@OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ cp -pPR openjdk.hg openjdk ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_TRUE@ fi - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ set -e ; \ - @OPENJDK_SRC_DIR_FOUND_FALSE@@USE_HG_FALSE@ if ! test -d openjdk ; \ -@@ -1576,7 +1576,7 @@ - # FIXME (missing): Rename to clone-ecj. - stamps/extract-ecj.stamp: $(OPENJDK_TREE) - if ! test -d openjdk-ecj ; then \ -- cp -pPRl openjdk openjdk-ecj ; \ -+ cp -pPR openjdk openjdk-ecj ; \ - fi - mkdir -p stamps - touch stamps/extract-ecj.stamp @@ -1643,10 +1643,14 @@ stamps/native-ecj.stamp: -- cgit v1.2.3