From: John Crispin Date: Tue, 1 Feb 2011 14:30:38 +0000 (+0000) Subject: * rename lqdsl packages to ltq-dsl * small rework of packages * make it work with... X-Git-Tag: reboot~17700 X-Git-Url: http://git.lede-project.org./?a=commitdiff_plain;h=79b3d8f69aa02e2dc80f04a1ac84e971a2a33f8b;p=openwrt%2Fstaging%2Flynxis.git * rename lqdsl packages to ltq-dsl * small rework of packages * make it work with latest kernel SVN-Revision: 25274 --- diff --git a/package/lqdsl-app/Makefile b/package/lqdsl-app/Makefile deleted file mode 100644 index 18ce2a9a54..0000000000 --- a/package/lqdsl-app/Makefile +++ /dev/null @@ -1,81 +0,0 @@ -# -# Copyright (C) 2009-2010 OpenWrt.org -# -# This is free software, licensed under the GNU General Public License v2. -# See /LICENSE for more information. -# -# ralph / blogic - -include $(TOPDIR)/rules.mk -include $(INCLUDE_DIR)/kernel.mk - -PKG_BASE_NAME:=dsl_cpe_control_danube -PKG_VERSION:=3.24.4.4 -PKG_RELEASE:=1 -PKG_SOURCE:=$(PKG_BASE_NAME)-$(PKG_VERSION).tar.gz -PKG_BUILD_DIR:=$(BUILD_DIR)/dsl_cpe_control-$(PKG_VERSION) -PKG_SOURCE_URL:=http://mirror2.openwrt.org/sources/ -PKG_MD5SUM:=ee315306626b68794d3d3636dabfe161 - -include $(INCLUDE_DIR)/package.mk - -define Package/lqdsl-app - SECTION:=net - CATEGORY:=Network - TITLE:=Lantiq DSL userland tool - URL:=http://www.lantiq.com/ - MAINTAINER:=Lantiq - DEPENDS:=@TARGET_lantiq_xway +kmod-lqdsl +libpthread -endef - -define Package/lqdsl-app/description - Infineon DSL CPE API for Amazon SE, Danube and Vinax. -endef - -IFX_DSL_MAX_DEVICE=1 -IFX_DSL_LINES_PER_DEVICE=1 -IFX_DSL_CHANNELS_PER_LINE=1 -#CONFIG_IFX_CLI=y - -CONFIGURE_ARGS += \ - --with-max-device="$(IFX_DSL_MAX_DEVICE)" \ - --with-lines-per-device="$(IFX_DSL_LINES_PER_DEVICE)" \ - --with-channels-per-line="$(IFX_DSL_CHANNELS_PER_LINE)" \ - --enable-danube \ - --enable-driver-include="-I$(STAGING_DIR)/usr/include" \ - --enable-debug-prints \ - --enable-add-appl-cflags="-DMAX_CLI_PIPES=2" \ - --enable-cmv-scripts \ - --enable-debug-tool-interface \ - --enable-adsl-led \ - --enable-dsl-ceoc \ - --enable-script-notification \ - --enable-dsl-pm \ - --enable-dsl-pm-total \ - --enable-dsl-pm-history \ - --enable-dsl-pm-showtime \ - --enable-dsl-pm-channel-counters \ - --enable-dsl-pm-datapath-counters \ - --enable-dsl-pm-line-counters \ - --enable-dsl-pm-channel-thresholds \ - --enable-dsl-pm-datapath-thresholds \ - --enable-dsl-pm-line-thresholds \ - --enable-dsl-pm-optional-parameters - -ifeq ($(CONFIG_IFX_CLI),y) -CONFIGURE_ARGS += \ - --enable-cli-support \ - --enable-soap-support -endif - -TARGET_CFLAGS += -I$(LINUX_DIR)/include - -define Package/lqdsl-app/install - $(INSTALL_DIR) $(1)/etc/init.d - $(INSTALL_BIN) ./files/ifx_cpe_control_init.sh $(1)/etc/init.d/ - - $(INSTALL_DIR) $(1)/sbin - $(INSTALL_BIN) $(PKG_BUILD_DIR)/src/dsl_cpe_control $(1)/sbin -endef - -$(eval $(call BuildPackage,lqdsl-app)) diff --git a/package/lqdsl-app/files/ifx_cpe_control_init.sh b/package/lqdsl-app/files/ifx_cpe_control_init.sh deleted file mode 100644 index 91316938ce..0000000000 --- a/package/lqdsl-app/files/ifx_cpe_control_init.sh +++ /dev/null @@ -1,21 +0,0 @@ -#!/bin/sh /etc/rc.common -# Copyright (C) 2008 OpenWrt.org -START=99 - -start() { - - # start CPE dsl daemon in the background - /sbin/dsl_cpe_control -i -f /lib/firmware/ModemHWE.bin & - -# PS=`ps` -# echo $PS | grep -q dsl_cpe_control && { -# # workaround for nfs: allow write to pipes for non-root -# while [ ! -e /tmp/pipe/dsl_cpe1_ack ] ; do sleep 1; done -# chmod a+w /tmp/pipe/dsl_* -# } - echo $PS | grep -q dsl_cpe_control || { - echo "Start of dsl_cpe_control failed!!!" - false - } - -} diff --git a/package/lqdsl/Config.in b/package/lqdsl/Config.in deleted file mode 100644 index fe503b8538..0000000000 --- a/package/lqdsl/Config.in +++ /dev/null @@ -1,25 +0,0 @@ - -choice - prompt "Firmware" - default LANTIQ_ANNEX_B - depends on PACKAGE_kmod-lqdsl - help - This option controls which firmware is loaded - -config LANTIQ_ANNEX_A - bool "Annex-A" - help - Annex-A - -config LANTIQ_ANNEX_B - bool "Annex-B" - help - Annex-B - -endchoice - -config LANTIQ_DSL_DEBUG - bool "lqdsl debugging" - depends on PACKAGE_kmod-lqdsl - help - Say Y, if you need lantiq-dsl to display debug messages. diff --git a/package/lqdsl/Makefile b/package/lqdsl/Makefile deleted file mode 100644 index bfadd7150d..0000000000 --- a/package/lqdsl/Makefile +++ /dev/null @@ -1,158 +0,0 @@ -# -# Copyright (C) 2009-2010 OpenWrt.org -# -# This is free software, licensed under the GNU General Public License v2. -# See /LICENSE for more information. -# -# ralph / blogic - -include $(TOPDIR)/rules.mk -include $(INCLUDE_DIR)/kernel.mk - -PKG_NAME:=lqdsl -PKG_BASE_NAME:=drv_dsl_cpe_api_danube -PKG_VERSION:=3.24.4.4 -PKG_RELEASE:=2 -PKG_SOURCE:=$(PKG_BASE_NAME)-$(PKG_VERSION).tar.gz -PKG_BUILD_DIR:=$(KERNEL_BUILD_DIR)/drv_dsl_cpe_api-$(PKG_VERSION) -PKG_SOURCE_URL:=http://mirror2.openwrt.org/sources/ -PKG_MD5SUM:=c45bc531c1ed2ac80f68fb986b63bb87 - -ifeq ($(DUMP),) - STAMP_CONFIGURED:=$(strip $(STAMP_CONFIGURED))_$(shell grep '^CONFIG_LANTIQ_DSL_' $(TOPDIR)/.config | md5s) -endif - -FW_BASE_NAME:=dsl_danube_firmware_adsl -FW_A_VER:=02.04.04.00.00.01 -FW_B_VER:=02.04.01.07.00.02 -FW_A_FILE_VER:=244001 -FW_B_FILE_VER:=241702 -FW_A_MD5:=f717db3067a0049a26e233ab11238710 -FW_B_MD5:=349de7cd20368f4ac9b7e8322114a512 - -PATCH_DIR ?= ./patches$(if $(wildcard ./patches-$(KERNEL_PATCHVER)),-$(KERNEL_PATCHVER)) - -include $(INCLUDE_DIR)/package.mk - -define KernelPackage/lqdsl - SECTION:=sys - CATEGORY:=Kernel modules - SUBMENU:=Network Devices - TITLE:=Lantiq dsl driver - URL:=http://www.lantiq.com/ - MAINTAINER:=Lantiq - DEPENDS:=@TARGET_lantiq_xway +kmod-atm - FILES:=$(PKG_BUILD_DIR)/src/mei/lantiq_mei.ko \ - $(PKG_BUILD_DIR)/src/drv_dsl_cpe_api.ko \ - $(PKG_BUILD_DIR)/src/mei/lantiq_atm.ko - AUTOLOAD:=$(call AutoLoad,50,lantiq_mei drv_dsl_cpe_api lantiq_atm) -endef - -define KernelPackage/lqdsl/description - Infineon DSL CPE API for Amazon SE, Danube and Vinax. - - This package contains the DSL CPE API driver for Amazon SE & Danube. - - Supported Devices: - - Amazon SE - - Danube -endef - -define KernelPackage/lqdsl/config - source "$(SOURCE)/Config.in" -endef - -define Download/annex-a - FILE:=$(FW_BASE_NAME)_a-$(FW_A_VER).tar.gz - URL:=http://mirror2.openwrt.org/sources/ - MD5SUM:=$(FW_A_MD5) -endef -$(eval $(call Download,annex-a)) - -define Download/annex-b - FILE:=$(FW_BASE_NAME)_b-$(FW_B_VER).tar.gz - URL:=http://mirror2.openwrt.org/sources/ - MD5SUM:=$(FW_B_MD5) -endef -$(eval $(call Download,annex-b)) - -IFX_DSL_MAX_DEVICE=1 -IFX_DSL_LINES_PER_DEVICE=1 -IFX_DSL_CHANNELS_PER_LINE=1 - -CONFIGURE_ARGS += --enable-kernel-include="$(LINUX_DIR)/include" \ - --with-max-device="$(IFX_DSL_MAX_DEVICE)" \ - --with-lines-per-device="$(IFX_DSL_LINES_PER_DEVICE)" \ - --with-channels-per-line="$(IFX_DSL_CHANNELS_PER_LINE)" \ - --enable-danube \ - --enable-add-drv-cflags="-DMODULE" \ - --disable-dsl-delt-static \ - --disable-adsl-led \ - --enable-dsl-ceoc \ - --enable-dsl-pm \ - --enable-dsl-pm-total \ - --enable-dsl-pm-history \ - --enable-dsl-pm-showtime \ - --enable-dsl-pm-channel-counters \ - --enable-dsl-pm-datapath-counters \ - --enable-dsl-pm-line-counters \ - --enable-dsl-pm-channel-thresholds \ - --enable-dsl-pm-datapath-thresholds \ - --enable-dsl-pm-line-thresholds \ - --enable-dsl-pm-optional-parameters \ - --enable-linux-26 \ - --enable-kernelbuild="$(LINUX_DIR)" \ - ARCH=$(LINUX_KARCH) - -EXTRA_CFLAGS = -fno-pic -mno-abicalls -mlong-calls -G 0 - -ifeq ($(CONFIG_LANTIQ_DSL_DEBUG),y) -CONFIGURE_ARGS += \ - --enable-debug=yes \ - --enable-debug-prints=yes -EXTRA_CFLAGS += -DDEBUG -endif - -define Build/Prepare - $(PKG_UNPACK) - $(INSTALL_DIR) $(PKG_BUILD_DIR)/src/mei/ - $(CP) ./src/* $(PKG_BUILD_DIR)/src/mei/ - $(Build/Patch) -ifeq ($(CONFIG_LANTIQ_DSL_FIRMWARE),) - $(TAR) -C $(PKG_BUILD_DIR) -xzf $(DL_DIR)/$(FW_BASE_NAME)_a-$(FW_A_VER).tar.gz - $(TAR) -C $(PKG_BUILD_DIR) -xzf $(DL_DIR)/$(FW_BASE_NAME)_b-$(FW_B_VER).tar.gz -endif -endef - -define Build/Configure - (cd $(PKG_BUILD_DIR); aclocal && autoconf && automake) - $(call Build/Configure/Default) -endef - -define Build/Compile - cd $(LINUX_DIR); \ - ARCH=mips CROSS_COMPILE="$(KERNEL_CROSS)" \ - $(MAKE) M=$(PKG_BUILD_DIR)/src/mei/ V=1 modules - $(call Build/Compile/Default) -endef - -define Build/InstallDev - $(INSTALL_DIR) $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_ioctl.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_adslmib.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_adslmib_ioctl.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_g997.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_types.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_pm.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_error.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_danube_ctx.h $(1)/usr/include - $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_cmv_danube.h $(1)/usr/include -endef - -define KernelPackage/lqdsl/install - $(INSTALL_DIR) $(1)/lib/firmware/ - $(CP) $(PKG_BUILD_DIR)/$(FW_BASE_NAME)_$(if $(CONFIG_LANTIQ_ANNEX_A),a_$(FW_A_FILE_VER),b_$(FW_B_FILE_VER)).bin $(1)/lib/firmware/ModemHWE.bin -endef - -$(eval $(call KernelPackage,lqdsl)) diff --git a/package/lqdsl/patches/100-dsl_compat.patch b/package/lqdsl/patches/100-dsl_compat.patch deleted file mode 100644 index 334ac6736e..0000000000 --- a/package/lqdsl/patches/100-dsl_compat.patch +++ /dev/null @@ -1,62 +0,0 @@ ---- a/src/include/drv_dsl_cpe_device_danube.h -+++ b/src/include/drv_dsl_cpe_device_danube.h -@@ -24,7 +24,7 @@ - #include "drv_dsl_cpe_simulator_danube.h" - #else - /* Include for the low level driver interface header file */ --#include "asm/ifx/ifx_mei_bsp.h" -+#include "mei/ifxmips_mei_interface.h" - #endif /* defined(DSL_CPE_SIMULATOR_DRIVER) && defined(WIN32)*/ - - #define DSL_MAX_LINE_NUMBER 1 ---- a/src/common/drv_dsl_cpe_os_linux.c -+++ b/src/common/drv_dsl_cpe_os_linux.c -@@ -11,6 +11,7 @@ - #ifdef __LINUX__ - - #define DSL_INTERN -+#include - - #include "drv_dsl_cpe_api.h" - #include "drv_dsl_cpe_api_ioctl.h" -@@ -1058,6 +1059,7 @@ static void DSL_DRV_DebugInit(void) - /* Entry point of driver */ - int __init DSL_ModuleInit(void) - { -+ struct class *dsl_class; - DSL_int_t i; - - printk(DSL_DRV_CRLF DSL_DRV_CRLF "Infineon CPE API Driver version: %s" DSL_DRV_CRLF, -@@ -1104,7 +1106,8 @@ int __init DSL_ModuleInit(void) - } - - DSL_DRV_DevNodeInit(); -- -+ dsl_class = class_create(THIS_MODULE, "dsl_cpe_api"); -+ device_create(dsl_class, NULL, MKDEV(DRV_DSL_CPE_API_DEV_MAJOR, 0), NULL, "dsl_cpe_api"); - return 0; - } - ---- a/src/include/drv_dsl_cpe_os_linux.h -+++ b/src/include/drv_dsl_cpe_os_linux.h -@@ -17,17 +17,17 @@ - #endif - - #include --#include -+#include - #include - #include - #include - #include - #include - #include -- -+#include - - #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,17)) -- #include -+ #include - #endif - - #include diff --git a/package/lqdsl/patches/500-portability.patch b/package/lqdsl/patches/500-portability.patch deleted file mode 100644 index 48e9d173d4..0000000000 --- a/package/lqdsl/patches/500-portability.patch +++ /dev/null @@ -1,218 +0,0 @@ -Index: drv_dsl_cpe_api-3.24.4.4/configure.in -=================================================================== ---- drv_dsl_cpe_api-3.24.4.4.orig/configure.in 2009-08-13 13:39:21.000000000 +0200 -+++ drv_dsl_cpe_api-3.24.4.4/configure.in 2010-10-14 02:14:55.000000000 +0200 -@@ -310,7 +310,7 @@ - AC_ARG_ENABLE(kernelbuild, - AC_HELP_STRING(--enable-kernel-build=x,Set the target kernel build path), - [ -- if test -e $enableval/include/linux/autoconf.h; then -+ if test -e $enableval/include/linux/autoconf.h -o -e $enableval/include/generated/autoconf.h; then - AC_SUBST([KERNEL_BUILD_PATH],[$enableval]) - else - AC_MSG_ERROR([The kernel build directory is not valid or not configured!]) -@@ -333,12 +333,12 @@ - echo Set the lib_ifxos include path $enableval - AC_SUBST([IFXOS_INCLUDE_PATH],[$enableval]) - else -- echo -e Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH -+ echo Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH - AC_SUBST([IFXOS_INCLUDE_PATH],[$DEFAULT_IFXOS_INCLUDE_PATH]) - fi - ], - [ -- echo -e Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH -+ echo Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH - AC_SUBST([IFXOS_INCLUDE_PATH],[$DEFAULT_IFXOS_INCLUDE_PATH]) - ] - ) -@@ -1702,73 +1702,73 @@ - AC_SUBST([DISTCHECK_CONFIGURE_PARAMS],[$CONFIGURE_OPTIONS]) - - AC_CONFIG_COMMANDS_PRE([ --echo -e "------------------------------------------------------------------------" --echo -e " Configuration for drv_dsl_cpe_api:" --echo -e " Configure model type: $DSL_CONFIG_MODEL_TYPE" --echo -e " Source code location: $srcdir" --echo -e " Compiler: $CC" --echo -e " Compiler c-flags: $CFLAGS" --echo -e " Extra compiler c-flags: $EXTRA_DRV_CFLAGS" --echo -e " Host System Type: $host" --echo -e " Install path: $prefix" --echo -e " Linux kernel include path: $KERNEL_INCL_PATH" --echo -e " Linux kernel build path: $KERNEL_BUILD_PATH" --echo -e " Linux kernel architecture: $KERNEL_ARCH" --echo -e " Include IFXOS: $INCLUDE_DSL_CPE_API_IFXOS_SUPPORT" --echo -e " IFXOS include path: $IFXOS_INCLUDE_PATH" --echo -e " Driver Include Path $DSL_DRIVER_INCL_PATH" --echo -e " DSL device: $DSL_DEVICE_NAME" --echo -e " Max device number: $DSL_DRV_MAX_DEVICE_NUMBER" --echo -e " Channels per line: $DSL_CHANNELS_PER_LINE" --echo -e " Build lib (only for kernel 2.6) $DSL_CPE_API_LIBRARY_BUILD_2_6" --echo -e " DSL data led flash frequency: $DSL_DATA_LED_FLASH_FREQUENCY Hz" --echo -e " Disable debug prints: $DSL_DEBUG_DISABLE" --echo -e " Preselection of max. debug level: $DSL_DBG_MAX_LEVEL_SET" --echo -e " Preselected max. debug level: $DSL_DBG_MAX_LEVEL_PRE" --echo -e " Include deprecated functions: $INCLUDE_DEPRECATED" --echo -e " Include Device Exception Codes: $INCLUDE_DEVICE_EXCEPTION_CODES" --echo -e " Include FW request support: $INCLUDE_FW_REQUEST_SUPPORT" --echo -e " Include ADSL trace buffer: $INCLUDE_DSL_CPE_TRACE_BUFFER" --echo -e " Include ADSL MIB: $INCLUDE_DSL_ADSL_MIB" --echo -e " Include ADSL LED: $INCLUDE_ADSL_LED" --echo -e " Include CEOC: $INCLUDE_DSL_CEOC" --echo -e " Include config get support: $INCLUDE_DSL_CONFIG_GET" --echo -e " Include System i/f configuration: $INCLUDE_DSL_SYSTEM_INTERFACE" --echo -e " Include Resource Statistics: $INCLUDE_DSL_RESOURCE_STATISTICS" --echo -e " Include Framing Parameters: $INCLUDE_DSL_FRAMING_PARAMETERS" --echo -e " Include G997 Line Inventory: $INCLUDE_DSL_G997_LINE_INVENTORY" --echo -e " Include G997 Framing Parameters: $INCLUDE_DSL_G997_FRAMING_PARAMETERS" --echo -e " Include G997 per tone data: $INCLUDE_DSL_G997_PER_TONE" --echo -e " Include G997 status: $INCLUDE_DSL_G997_STATUS" --echo -e " Include G997 alarm: $INCLUDE_DSL_G997_ALARM" --echo -e " Include DSL Bonding: $INCLUDE_DSL_BONDING" --echo -e " Include Misc Line Status $INCLUDE_DSL_CPE_MISC_LINE_STATUS" --echo -e " Include DELT: $INCLUDE_DSL_DELT" --echo -e " Include DELT data static storage: $DSL_CPE_STATIC_DELT_DATA" --echo -e " Include PM: $INCLUDE_DSL_PM" --echo -e " Include PM config: $INCLUDE_DSL_CPE_PM_CONFIG" --echo -e " Include PM total: $INCLUDE_DSL_CPE_PM_TOTAL_COUNTERS" --echo -e " Include PM history: $INCLUDE_DSL_CPE_PM_HISTORY" --echo -e " Include PM showtime: $INCLUDE_DSL_CPE_PM_SHOWTIME_COUNTERS" --echo -e " Include PM optional: $INCLUDE_DSL_CPE_PM_OPTIONAL_PARAMETERS" --echo -e " Include PM line: $INCLUDE_DSL_CPE_PM_LINE_COUNTERS" --echo -e " Include PM line event showtime: $INCLUDE_DSL_CPE_PM_LINE_EVENT_SHOWTIME_COUNTERS" --echo -e " Include PM channel: $INCLUDE_DSL_CPE_PM_CHANNEL_COUNTERS" --echo -e " Include PM channel extended: $INCLUDE_DSL_CPE_PM_CHANNEL_EXT_COUNTERS" --echo -e " Include PM data path: $INCLUDE_DSL_CPE_PM_DATA_PATH_COUNTERS" --echo -e " Include PM data path failure: $INCLUDE_DSL_CPE_PM_DATA_PATH_FAILURE_COUNTERS" --echo -e " Include PM ReTx: $INCLUDE_DSL_CPE_PM_RETX_COUNTERS" --echo -e " Include PM line threshold: $INCLUDE_DSL_CPE_PM_LINE_THRESHOLDS" --echo -e " Include PM channel threshold: $INCLUDE_DSL_CPE_PM_CHANNEL_THRESHOLDS" --echo -e " Include PM data path threshold: $INCLUDE_DSL_CPE_PM_DATA_PATH_THRESHOLDS" --echo -e " Include PM ReTx threshold: $INCLUDE_DSL_CPE_PM_RETX_THRESHOLDS" --echo -e " Include FW memory free support: $INCLUDE_DSL_FIRMWARE_MEMORY_FREE" --echo -e "----------------------- deprectated ! ----------------------------------" --echo -e " Include PM line failure: $INCLUDE_DSL_CPE_PM_LINE_FAILURE_COUNTERS" --echo -e "" --echo -e " Settings:" --echo -e " Configure options: $CONFIGURE_OPTIONS" --echo -e "------------------------------------------------------------------------" -+echo "------------------------------------------------------------------------" -+echo " Configuration for drv_dsl_cpe_api:" -+echo " Configure model type: $DSL_CONFIG_MODEL_TYPE" -+echo " Source code location: $srcdir" -+echo " Compiler: $CC" -+echo " Compiler c-flags: $CFLAGS" -+echo " Extra compiler c-flags: $EXTRA_DRV_CFLAGS" -+echo " Host System Type: $host" -+echo " Install path: $prefix" -+echo " Linux kernel include path: $KERNEL_INCL_PATH" -+echo " Linux kernel build path: $KERNEL_BUILD_PATH" -+echo " Linux kernel architecture: $KERNEL_ARCH" -+echo " Include IFXOS: $INCLUDE_DSL_CPE_API_IFXOS_SUPPORT" -+echo " IFXOS include path: $IFXOS_INCLUDE_PATH" -+echo " Driver Include Path $DSL_DRIVER_INCL_PATH" -+echo " DSL device: $DSL_DEVICE_NAME" -+echo " Max device number: $DSL_DRV_MAX_DEVICE_NUMBER" -+echo " Channels per line: $DSL_CHANNELS_PER_LINE" -+echo " Build lib (only for kernel 2.6) $DSL_CPE_API_LIBRARY_BUILD_2_6" -+echo " DSL data led flash frequency: $DSL_DATA_LED_FLASH_FREQUENCY Hz" -+echo " Disable debug prints: $DSL_DEBUG_DISABLE" -+echo " Preselection of max. debug level: $DSL_DBG_MAX_LEVEL_SET" -+echo " Preselected max. debug level: $DSL_DBG_MAX_LEVEL_PRE" -+echo " Include deprecated functions: $INCLUDE_DEPRECATED" -+echo " Include Device Exception Codes: $INCLUDE_DEVICE_EXCEPTION_CODES" -+echo " Include FW request support: $INCLUDE_FW_REQUEST_SUPPORT" -+echo " Include ADSL trace buffer: $INCLUDE_DSL_CPE_TRACE_BUFFER" -+echo " Include ADSL MIB: $INCLUDE_DSL_ADSL_MIB" -+echo " Include ADSL LED: $INCLUDE_ADSL_LED" -+echo " Include CEOC: $INCLUDE_DSL_CEOC" -+echo " Include config get support: $INCLUDE_DSL_CONFIG_GET" -+echo " Include System i/f configuration: $INCLUDE_DSL_SYSTEM_INTERFACE" -+echo " Include Resource Statistics: $INCLUDE_DSL_RESOURCE_STATISTICS" -+echo " Include Framing Parameters: $INCLUDE_DSL_FRAMING_PARAMETERS" -+echo " Include G997 Line Inventory: $INCLUDE_DSL_G997_LINE_INVENTORY" -+echo " Include G997 Framing Parameters: $INCLUDE_DSL_G997_FRAMING_PARAMETERS" -+echo " Include G997 per tone data: $INCLUDE_DSL_G997_PER_TONE" -+echo " Include G997 status: $INCLUDE_DSL_G997_STATUS" -+echo " Include G997 alarm: $INCLUDE_DSL_G997_ALARM" -+echo " Include DSL Bonding: $INCLUDE_DSL_BONDING" -+echo " Include Misc Line Status $INCLUDE_DSL_CPE_MISC_LINE_STATUS" -+echo " Include DELT: $INCLUDE_DSL_DELT" -+echo " Include DELT data static storage: $DSL_CPE_STATIC_DELT_DATA" -+echo " Include PM: $INCLUDE_DSL_PM" -+echo " Include PM config: $INCLUDE_DSL_CPE_PM_CONFIG" -+echo " Include PM total: $INCLUDE_DSL_CPE_PM_TOTAL_COUNTERS" -+echo " Include PM history: $INCLUDE_DSL_CPE_PM_HISTORY" -+echo " Include PM showtime: $INCLUDE_DSL_CPE_PM_SHOWTIME_COUNTERS" -+echo " Include PM optional: $INCLUDE_DSL_CPE_PM_OPTIONAL_PARAMETERS" -+echo " Include PM line: $INCLUDE_DSL_CPE_PM_LINE_COUNTERS" -+echo " Include PM line event showtime: $INCLUDE_DSL_CPE_PM_LINE_EVENT_SHOWTIME_COUNTERS" -+echo " Include PM channel: $INCLUDE_DSL_CPE_PM_CHANNEL_COUNTERS" -+echo " Include PM channel extended: $INCLUDE_DSL_CPE_PM_CHANNEL_EXT_COUNTERS" -+echo " Include PM data path: $INCLUDE_DSL_CPE_PM_DATA_PATH_COUNTERS" -+echo " Include PM data path failure: $INCLUDE_DSL_CPE_PM_DATA_PATH_FAILURE_COUNTERS" -+echo " Include PM ReTx: $INCLUDE_DSL_CPE_PM_RETX_COUNTERS" -+echo " Include PM line threshold: $INCLUDE_DSL_CPE_PM_LINE_THRESHOLDS" -+echo " Include PM channel threshold: $INCLUDE_DSL_CPE_PM_CHANNEL_THRESHOLDS" -+echo " Include PM data path threshold: $INCLUDE_DSL_CPE_PM_DATA_PATH_THRESHOLDS" -+echo " Include PM ReTx threshold: $INCLUDE_DSL_CPE_PM_RETX_THRESHOLDS" -+echo " Include FW memory free support: $INCLUDE_DSL_FIRMWARE_MEMORY_FREE" -+echo "----------------------- deprectated ! ----------------------------------" -+echo " Include PM line failure: $INCLUDE_DSL_CPE_PM_LINE_FAILURE_COUNTERS" -+echo "" -+echo " Settings:" -+echo " Configure options: $CONFIGURE_OPTIONS" -+echo "------------------------------------------------------------------------" - ]) - - AC_CONFIG_FILES([Makefile src/Makefile]) -Index: drv_dsl_cpe_api-3.24.4.4/src/Makefile.am -=================================================================== ---- drv_dsl_cpe_api-3.24.4.4.orig/src/Makefile.am 2009-07-03 14:06:34.000000000 +0200 -+++ drv_dsl_cpe_api-3.24.4.4/src/Makefile.am 2010-10-14 02:14:55.000000000 +0200 -@@ -303,7 +303,7 @@ - drv_dsl_cpe_api_OBJS = "$(subst .c,.o,$(filter %.c,$(drv_dsl_cpe_api_SOURCES)))" - - drv_dsl_cpe_api.ko: $(drv_dsl_cpe_api_SOURCES) -- @echo -e "drv_dsl_cpe_api: Making Linux 2.6.x kernel object" -+ @echo "drv_dsl_cpe_api: Making Linux 2.6.x kernel object" - if test ! -e common/drv_dsl_cpe_api.c ; then \ - echo "copy source files (as links only!)"; \ - for f in $(filter %.c,$(drv_dsl_cpe_api_SOURCES)); do \ -@@ -311,10 +311,10 @@ - cp -s $(addprefix @abs_srcdir@/,$$f) $(PWD)/`dirname $$f`/ ; \ - done \ - fi -- @echo -e "# drv_dsl_cpe_api: Generated to build Linux 2.6.x kernel object" > $(PWD)/Kbuild -- @echo -e "obj-m := $(subst .ko,.o,$@)" >> $(PWD)/Kbuild -- @echo -e "$(subst .ko,,$@)-y := $(drv_dsl_cpe_api_OBJS)" >> $(PWD)/Kbuild -- @echo -e "EXTRA_CFLAGS := $(CFLAGS) -DHAVE_CONFIG_H $(drv_dsl_cpe_api_CFLAGS) $(DSL_DRIVER_INCL_PATH) $(IFXOS_INCLUDE_PATH) -I@abs_srcdir@/include -I$(PWD)/include" >> $(PWD)/Kbuild -+ @echo "# drv_dsl_cpe_api: Generated to build Linux 2.6.x kernel object" > $(PWD)/Kbuild -+ @echo "obj-m := $(subst .ko,.o,$@)" >> $(PWD)/Kbuild -+ @echo "$(subst .ko,,$@)-y := $(drv_dsl_cpe_api_OBJS)" >> $(PWD)/Kbuild -+ @echo "EXTRA_CFLAGS := $(CFLAGS) -DHAVE_CONFIG_H $(drv_dsl_cpe_api_CFLAGS) $(DSL_DRIVER_INCL_PATH) $(IFXOS_INCLUDE_PATH) -I@abs_srcdir@/include -I$(PWD)/include" >> $(PWD)/Kbuild - $(MAKE) ARCH=@KERNEL_ARCH@ -C @KERNEL_BUILD_PATH@ O=@KERNEL_BUILD_PATH@ M=$(PWD) modules - - clean-generic: -Index: drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_os_linux.h -=================================================================== ---- drv_dsl_cpe_api-3.24.4.4.orig/src/include/drv_dsl_cpe_os_linux.h 2010-10-14 02:14:55.000000000 +0200 -+++ drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_os_linux.h 2010-10-14 02:14:55.000000000 +0200 -@@ -16,8 +16,6 @@ - extern "C" { - #endif - --#include --#include - #include - #include - #include -@@ -40,6 +38,7 @@ - #include - #include - #include -+#include - - #ifdef INCLUDE_DSL_CPE_API_IFXOS_SUPPORT - /** IFXOS includes*/ diff --git a/package/lqdsl/src/Makefile b/package/lqdsl/src/Makefile deleted file mode 100644 index 89c4e712d7..0000000000 --- a/package/lqdsl/src/Makefile +++ /dev/null @@ -1,3 +0,0 @@ -obj-m = lantiq_mei.o lantiq_atm.o - -lantiq_atm-objs := ifxmips_atm_core.o ifxmips_atm_danube.o diff --git a/package/lqdsl/src/ifx_atm.h b/package/lqdsl/src/ifx_atm.h deleted file mode 100644 index 32deca54e0..0000000000 --- a/package/lqdsl/src/ifx_atm.h +++ /dev/null @@ -1,108 +0,0 @@ -/****************************************************************************** -** -** FILE NAME : ifx_atm.h -** PROJECT : UEIP -** MODULES : ATM -** -** DATE : 17 Jun 2009 -** AUTHOR : Xu Liang -** DESCRIPTION : Global ATM driver header file -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 07 JUL 2009 Xu Liang Init Version -*******************************************************************************/ - -#ifndef IFX_ATM_H -#define IFX_ATM_H - - - -/* - * ATM MIB - */ - -typedef struct { - __u32 ifHCInOctets_h; /*!< byte counter of ingress cells (upper 32 bits, total 64 bits) */ - __u32 ifHCInOctets_l; /*!< byte counter of ingress cells (lower 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_h; /*!< byte counter of egress cells (upper 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_l; /*!< byte counter of egress cells (lower 32 bits, total 64 bits) */ - __u32 ifInErrors; /*!< counter of error ingress cells */ - __u32 ifInUnknownProtos; /*!< counter of unknown ingress cells */ - __u32 ifOutErrors; /*!< counter of error egress cells */ -} atm_cell_ifEntry_t; - -typedef struct { - __u32 ifHCInOctets_h; /*!< byte counter of ingress packets (upper 32 bits, total 64 bits) */ - __u32 ifHCInOctets_l; /*!< byte counter of ingress packets (lower 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_h; /*!< byte counter of egress packets (upper 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_l; /*!< byte counter of egress packets (lower 32 bits, total 64 bits) */ - __u32 ifInUcastPkts; /*!< counter of ingress packets */ - __u32 ifOutUcastPkts; /*!< counter of egress packets */ - __u32 ifInErrors; /*!< counter of error ingress packets */ - __u32 ifInDiscards; /*!< counter of dropped ingress packets */ - __u32 ifOutErros; /*!< counter of error egress packets */ - __u32 ifOutDiscards; /*!< counter of dropped egress packets */ -} atm_aal5_ifEntry_t; - -typedef struct { - __u32 aal5VccCrcErrors; /*!< counter of ingress packets with CRC error */ - __u32 aal5VccSarTimeOuts; /*!< counter of ingress packets with Re-assemble timeout */ //no timer support yet - __u32 aal5VccOverSizedSDUs; /*!< counter of oversized ingress packets */ -} atm_aal5_vcc_t; - -typedef struct { - int vpi; /*!< VPI of the VCC to get MIB counters */ - int vci; /*!< VCI of the VCC to get MIB counters */ - atm_aal5_vcc_t mib_vcc; /*!< structure to get MIB counters */ -} atm_aal5_vcc_x_t; - -/*! - \brief ATM IOCTL Magic Number - */ -#define PPE_ATM_IOC_MAGIC 'o' -/*! - \brief ATM IOCTL Command - Get Cell Level MIB Counters - - This command is obsolete. User can get cell level MIB from DSL API. - This command uses structure "atm_cell_ifEntry_t" as parameter for output of MIB counters. - */ -#define PPE_ATM_MIB_CELL _IOW(PPE_ATM_IOC_MAGIC, 0, atm_cell_ifEntry_t) -/*! - \brief ATM IOCTL Command - Get AAL5 Level MIB Counters - - Get AAL5 packet counters. - This command uses structure "atm_aal5_ifEntry_t" as parameter for output of MIB counters. - */ -#define PPE_ATM_MIB_AAL5 _IOW(PPE_ATM_IOC_MAGIC, 1, atm_aal5_ifEntry_t) -/*! - \brief ATM IOCTL Command - Get Per PVC MIB Counters - - Get AAL5 packet counters for each PVC. - This command uses structure "atm_aal5_vcc_x_t" as parameter for input of VPI/VCI information and output of MIB counters. - */ -#define PPE_ATM_MIB_VCC _IOWR(PPE_ATM_IOC_MAGIC, 2, atm_aal5_vcc_x_t) -/*! - \brief Total Number of ATM IOCTL Commands - */ -#define PPE_ATM_IOC_MAXNR 3 - -/*@}*/ - - - -#ifdef __KERNEL__ -struct port_cell_info { - unsigned int port_num; - unsigned int tx_link_rate[2]; -}; -#endif -#endif diff --git a/package/lqdsl/src/ifxmips_atm.h b/package/lqdsl/src/ifxmips_atm.h deleted file mode 100644 index ed90b5d4d7..0000000000 --- a/package/lqdsl/src/ifxmips_atm.h +++ /dev/null @@ -1,172 +0,0 @@ -/****************************************************************************** -** -** FILE NAME : ifx_atm.h -** PROJECT : UEIP -** MODULES : ATM -** -** DATE : 17 Jun 2009 -** AUTHOR : Xu Liang -** DESCRIPTION : Global ATM driver header file -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 07 JUL 2009 Xu Liang Init Version -*******************************************************************************/ - -#ifndef IFX_ATM_H -#define IFX_ATM_H - - - -/*! - \defgroup IFX_ATM UEIP Project - ATM driver module - \brief UEIP Project - ATM driver module, support Danube, Amazon-SE, AR9, VR9. - */ - -/*! - \defgroup IFX_ATM_IOCTL IOCTL Commands - \ingroup IFX_ATM - \brief IOCTL Commands used by user application. - */ - -/*! - \defgroup IFX_ATM_STRUCT Structures - \ingroup IFX_ATM - \brief Structures used by user application. - */ - -/*! - \file ifx_atm.h - \ingroup IFX_ATM - \brief ATM driver header file - */ - - - -/* - * #################################### - * Definition - * #################################### - */ - -/*! - \addtogroup IFX_ATM_STRUCT - */ -/*@{*/ - -/* - * ATM MIB - */ - -typedef struct { - __u32 ifHCInOctets_h; /*!< byte counter of ingress cells (upper 32 bits, total 64 bits) */ - __u32 ifHCInOctets_l; /*!< byte counter of ingress cells (lower 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_h; /*!< byte counter of egress cells (upper 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_l; /*!< byte counter of egress cells (lower 32 bits, total 64 bits) */ - __u32 ifInErrors; /*!< counter of error ingress cells */ - __u32 ifInUnknownProtos; /*!< counter of unknown ingress cells */ - __u32 ifOutErrors; /*!< counter of error egress cells */ -} atm_cell_ifEntry_t; - -typedef struct { - __u32 ifHCInOctets_h; /*!< byte counter of ingress packets (upper 32 bits, total 64 bits) */ - __u32 ifHCInOctets_l; /*!< byte counter of ingress packets (lower 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_h; /*!< byte counter of egress packets (upper 32 bits, total 64 bits) */ - __u32 ifHCOutOctets_l; /*!< byte counter of egress packets (lower 32 bits, total 64 bits) */ - __u32 ifInUcastPkts; /*!< counter of ingress packets */ - __u32 ifOutUcastPkts; /*!< counter of egress packets */ - __u32 ifInErrors; /*!< counter of error ingress packets */ - __u32 ifInDiscards; /*!< counter of dropped ingress packets */ - __u32 ifOutErros; /*!< counter of error egress packets */ - __u32 ifOutDiscards; /*!< counter of dropped egress packets */ -} atm_aal5_ifEntry_t; - -typedef struct { - __u32 aal5VccCrcErrors; /*!< counter of ingress packets with CRC error */ - __u32 aal5VccSarTimeOuts; /*!< counter of ingress packets with Re-assemble timeout */ //no timer support yet - __u32 aal5VccOverSizedSDUs; /*!< counter of oversized ingress packets */ -} atm_aal5_vcc_t; - -typedef struct { - int vpi; /*!< VPI of the VCC to get MIB counters */ - int vci; /*!< VCI of the VCC to get MIB counters */ - atm_aal5_vcc_t mib_vcc; /*!< structure to get MIB counters */ -} atm_aal5_vcc_x_t; - -/*@}*/ - - - -/* - * #################################### - * IOCTL - * #################################### - */ - -/*! - \addtogroup IFX_ATM_IOCTL - */ -/*@{*/ - -/* - * ioctl Command - */ -/*! - \brief ATM IOCTL Magic Number - */ -#define PPE_ATM_IOC_MAGIC 'o' -/*! - \brief ATM IOCTL Command - Get Cell Level MIB Counters - - This command is obsolete. User can get cell level MIB from DSL API. - This command uses structure "atm_cell_ifEntry_t" as parameter for output of MIB counters. - */ -#define PPE_ATM_MIB_CELL _IOW(PPE_ATM_IOC_MAGIC, 0, atm_cell_ifEntry_t) -/*! - \brief ATM IOCTL Command - Get AAL5 Level MIB Counters - - Get AAL5 packet counters. - This command uses structure "atm_aal5_ifEntry_t" as parameter for output of MIB counters. - */ -#define PPE_ATM_MIB_AAL5 _IOW(PPE_ATM_IOC_MAGIC, 1, atm_aal5_ifEntry_t) -/*! - \brief ATM IOCTL Command - Get Per PVC MIB Counters - - Get AAL5 packet counters for each PVC. - This command uses structure "atm_aal5_vcc_x_t" as parameter for input of VPI/VCI information and output of MIB counters. - */ -#define PPE_ATM_MIB_VCC _IOWR(PPE_ATM_IOC_MAGIC, 2, atm_aal5_vcc_x_t) -/*! - \brief Total Number of ATM IOCTL Commands - */ -#define PPE_ATM_IOC_MAXNR 3 - -/*@}*/ - - - -/* - * #################################### - * API - * #################################### - */ - -#ifdef __KERNEL__ -struct port_cell_info { - unsigned int port_num; - unsigned int tx_link_rate[2]; -}; -#endif - - - -#endif // IFX_ATM_H - diff --git a/package/lqdsl/src/ifxmips_atm_core.c b/package/lqdsl/src/ifxmips_atm_core.c deleted file mode 100644 index ae85d70650..0000000000 --- a/package/lqdsl/src/ifxmips_atm_core.c +++ /dev/null @@ -1,2510 +0,0 @@ -/****************************************************************************** -** -** FILE NAME : ifxmips_atm_core.c -** PROJECT : UEIP -** MODULES : ATM -** -** DATE : 7 Jul 2009 -** AUTHOR : Xu Liang -** DESCRIPTION : ATM driver common source file (core functions) -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 07 JUL 2009 Xu Liang Init Version -*******************************************************************************/ - - - -/* - * #################################### - * Version No. - * #################################### - */ - -#define IFX_ATM_VER_MAJOR 1 -#define IFX_ATM_VER_MID 0 -#define IFX_ATM_VER_MINOR 8 - - - -/* - * #################################### - * Head File - * #################################### - */ - -/* - * Common Head File - */ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* - * Chip Specific Head File - */ -#include -#include -#include "ifxmips_atm_core.h" - - - -/* - * #################################### - * Kernel Version Adaption - * #################################### - */ -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11) - #define MODULE_PARM_ARRAY(a, b) module_param_array(a, int, NULL, 0) - #define MODULE_PARM(a, b) module_param(a, int, 0) -#else - #define MODULE_PARM_ARRAY(a, b) MODULE_PARM(a, b) -#endif - - - -/*! - \addtogroup IFXMIPS_ATM_MODULE_PARAMS - */ -/*@{*/ -/* - * #################################### - * Parameters to Configure PPE - * #################################### - */ -/*! - \brief QSB cell delay variation due to concurrency - */ -static int qsb_tau = 1; /* QSB cell delay variation due to concurrency */ -/*! - \brief QSB scheduler burst length - */ -static int qsb_srvm = 0x0F; /* QSB scheduler burst length */ -/*! - \brief QSB time step, all legal values are 1, 2, 4 - */ -static int qsb_tstep = 4 ; /* QSB time step, all legal values are 1, 2, 4 */ - -/*! - \brief Write descriptor delay - */ -static int write_descriptor_delay = 0x20; /* Write descriptor delay */ - -/*! - \brief AAL5 padding byte ('~') - */ -static int aal5_fill_pattern = 0x007E; /* AAL5 padding byte ('~') */ -/*! - \brief Max frame size for RX - */ -static int aal5r_max_packet_size = 0x0700; /* Max frame size for RX */ -/*! - \brief Min frame size for RX - */ -static int aal5r_min_packet_size = 0x0000; /* Min frame size for RX */ -/*! - \brief Max frame size for TX - */ -static int aal5s_max_packet_size = 0x0700; /* Max frame size for TX */ -/*! - \brief Min frame size for TX - */ -static int aal5s_min_packet_size = 0x0000; /* Min frame size for TX */ -/*! - \brief Drop error packet in RX path - */ -static int aal5r_drop_error_packet = 1; /* Drop error packet in RX path */ - -/*! - \brief Number of descriptors per DMA RX channel - */ -static int dma_rx_descriptor_length = 128; /* Number of descriptors per DMA RX channel */ -/*! - \brief Number of descriptors per DMA TX channel - */ -static int dma_tx_descriptor_length = 64; /* Number of descriptors per DMA TX channel */ -/*! - \brief PPE core clock cycles between descriptor write and effectiveness in external RAM - */ -static int dma_rx_clp1_descriptor_threshold = 38; -/*@}*/ - -MODULE_PARM(qsb_tau, "i"); -MODULE_PARM_DESC(qsb_tau, "Cell delay variation. Value must be > 0"); -MODULE_PARM(qsb_srvm, "i"); -MODULE_PARM_DESC(qsb_srvm, "Maximum burst size"); -MODULE_PARM(qsb_tstep, "i"); -MODULE_PARM_DESC(qsb_tstep, "n*32 cycles per sbs cycles n=1,2,4"); - -MODULE_PARM(write_descriptor_delay, "i"); -MODULE_PARM_DESC(write_descriptor_delay, "PPE core clock cycles between descriptor write and effectiveness in external RAM"); - -MODULE_PARM(aal5_fill_pattern, "i"); -MODULE_PARM_DESC(aal5_fill_pattern, "Filling pattern (PAD) for AAL5 frames"); -MODULE_PARM(aal5r_max_packet_size, "i"); -MODULE_PARM_DESC(aal5r_max_packet_size, "Max packet size in byte for downstream AAL5 frames"); -MODULE_PARM(aal5r_min_packet_size, "i"); -MODULE_PARM_DESC(aal5r_min_packet_size, "Min packet size in byte for downstream AAL5 frames"); -MODULE_PARM(aal5s_max_packet_size, "i"); -MODULE_PARM_DESC(aal5s_max_packet_size, "Max packet size in byte for upstream AAL5 frames"); -MODULE_PARM(aal5s_min_packet_size, "i"); -MODULE_PARM_DESC(aal5s_min_packet_size, "Min packet size in byte for upstream AAL5 frames"); -MODULE_PARM(aal5r_drop_error_packet, "i"); -MODULE_PARM_DESC(aal5r_drop_error_packet, "Non-zero value to drop error packet for downstream"); - -MODULE_PARM(dma_rx_descriptor_length, "i"); -MODULE_PARM_DESC(dma_rx_descriptor_length, "Number of descriptor assigned to DMA RX channel (>16)"); -MODULE_PARM(dma_tx_descriptor_length, "i"); -MODULE_PARM_DESC(dma_tx_descriptor_length, "Number of descriptor assigned to DMA TX channel (>16)"); -MODULE_PARM(dma_rx_clp1_descriptor_threshold, "i"); -MODULE_PARM_DESC(dma_rx_clp1_descriptor_threshold, "Descriptor threshold for cells with cell loss priority 1"); - - - -/* - * #################################### - * Definition - * #################################### - */ - -#define DUMP_SKB_LEN ~0 - - - -/* - * #################################### - * Declaration - * #################################### - */ - -/* - * Network Operations - */ -static int ppe_ioctl(struct atm_dev *, unsigned int, void *); -static int ppe_open(struct atm_vcc *); -static void ppe_close(struct atm_vcc *); -static int ppe_send(struct atm_vcc *, struct sk_buff *); -static int ppe_send_oam(struct atm_vcc *, void *, int); -static int ppe_change_qos(struct atm_vcc *, struct atm_qos *, int); - -/* - * ADSL LED - */ -static INLINE int adsl_led_flash(void); - -/* - * 64-bit operation used by MIB calculation - */ -static INLINE void u64_add_u32(ppe_u64_t, unsigned int, ppe_u64_t *); - -/* - * buffer manage functions - */ -static INLINE struct sk_buff* alloc_skb_rx(void); -static INLINE struct sk_buff* alloc_skb_tx(unsigned int); -struct sk_buff* atm_alloc_tx(struct atm_vcc *, unsigned int); -static INLINE void atm_free_tx_skb_vcc(struct sk_buff *, struct atm_vcc *); -static INLINE struct sk_buff *get_skb_rx_pointer(unsigned int); -static INLINE int get_tx_desc(unsigned int); - -/* - * mailbox handler and signal function - */ -static INLINE void mailbox_oam_rx_handler(void); -static INLINE void mailbox_aal_rx_handler(void); -#if defined(ENABLE_TASKLET) && ENABLE_TASKLET - static void do_ppe_tasklet(unsigned long); -#endif -static irqreturn_t mailbox_irq_handler(int, void *); -static INLINE void mailbox_signal(unsigned int, int); - -/* - * QSB & HTU setting functions - */ -static void set_qsb(struct atm_vcc *, struct atm_qos *, unsigned int); -static void qsb_global_set(void); -static INLINE void set_htu_entry(unsigned int, unsigned int, unsigned int, int, int); -static INLINE void clear_htu_entry(unsigned int); -static void validate_oam_htu_entry(void); -static void invalidate_oam_htu_entry(void); - -/* - * look up for connection ID - */ -static INLINE int find_vpi(unsigned int); -static INLINE int find_vpivci(unsigned int, unsigned int); -static INLINE int find_vcc(struct atm_vcc *); - -/* - * Debug Functions - */ -#if defined(DEBUG_DUMP_SKB) && DEBUG_DUMP_SKB - static void dump_skb(struct sk_buff *, u32, char *, int, int, int); -#else - #define dump_skb(skb, len, title, port, ch, is_tx) do {} while (0) -#endif - -/* - * Proc File Functions - */ -static INLINE void proc_file_create(void); -static INLINE void proc_file_delete(void); -static int proc_read_version(char *, char **, off_t, int, int *, void *); -static int proc_read_mib(char *, char **, off_t, int, int *, void *); -static int proc_write_mib(struct file *, const char *, unsigned long, void *); -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - static int proc_read_dbg(char *, char **, off_t, int, int *, void *); - static int proc_write_dbg(struct file *, const char *, unsigned long, void *); -#endif -#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC - static int proc_read_htu(char *, char **, off_t, int, int *, void *); - static int proc_read_txq(char *, char **, off_t, int, int *, void *); -#endif - -/* - * Proc Help Functions - */ -static int stricmp(const char *, const char *); -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - static int strincmp(const char *, const char *, int); -#endif -static INLINE int ifx_atm_version(char *); -//static INLINE int print_reset_domain(char *, int); -//static INLINE int print_reset_handler(char *, int, ifx_rcu_handler_t *); - -/* - * Init & clean-up functions - */ -#ifdef MODULE - static INLINE void reset_ppe(void); -#endif -static INLINE void check_parameters(void); -static INLINE int init_priv_data(void); -static INLINE void clear_priv_data(void); -static INLINE void init_rx_tables(void); -static INLINE void init_tx_tables(void); - -/* - * Exteranl Function - */ -#if defined(CONFIG_IFX_OAM) || defined(CONFIG_IFX_OAM_MODULE) - extern void ifx_push_oam(unsigned char *); -#else - static inline void ifx_push_oam(unsigned char *dummy) {} -#endif -#if defined(CONFIG_IFXMIPS_DSL_CPE_MEI) || defined(CONFIG_IFXMIPS_DSL_CPE_MEI_MODULE) - extern int ifx_mei_atm_led_blink(void); - extern int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr); -#else - static inline int ifx_mei_atm_led_blink(void) { return IFX_SUCCESS; } - static inline int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr) - { - if ( is_showtime != NULL ) - *is_showtime = 0; - return IFX_SUCCESS; - } -#endif - -/* - * External variable - */ -extern struct sk_buff* (*ifx_atm_alloc_tx)(struct atm_vcc *, unsigned int); -#if defined(CONFIG_IFXMIPS_DSL_CPE_MEI) || defined(CONFIG_IFXMIPS_DSL_CPE_MEI_MODULE) - extern int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *); - extern int (*ifx_mei_atm_showtime_exit)(void); -#else - int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *) = NULL; - EXPORT_SYMBOL(ifx_mei_atm_showtime_enter); - int (*ifx_mei_atm_showtime_exit)(void) = NULL; - EXPORT_SYMBOL(ifx_mei_atm_showtime_exit); -#endif - - - -/* - * #################################### - * Local Variable - * #################################### - */ - -static struct atm_priv_data g_atm_priv_data; - -static struct atmdev_ops g_ifx_atm_ops = { - .open = ppe_open, - .close = ppe_close, - .ioctl = ppe_ioctl, - .send = ppe_send, - .send_oam = ppe_send_oam, - .change_qos = ppe_change_qos, - .owner = THIS_MODULE, -}; - -#if defined(ENABLE_TASKLET) && ENABLE_TASKLET - DECLARE_TASKLET(g_dma_tasklet, do_ppe_tasklet, 0); -#endif - -static int g_showtime = 0; -static void *g_xdata_addr = NULL; - -unsigned int ifx_atm_dbg_enable = 0; - -static struct proc_dir_entry* g_atm_dir = NULL; - - - -/* - * #################################### - * Local Function - * #################################### - */ - -static int ppe_ioctl(struct atm_dev *dev, unsigned int cmd, void *arg) -{ - int ret = 0; - atm_cell_ifEntry_t mib_cell; - atm_aal5_ifEntry_t mib_aal5; - atm_aal5_vcc_x_t mib_vcc; - unsigned int value; - int conn; - - if ( _IOC_TYPE(cmd) != PPE_ATM_IOC_MAGIC - || _IOC_NR(cmd) >= PPE_ATM_IOC_MAXNR ) - return -ENOTTY; - - if ( _IOC_DIR(cmd) & _IOC_READ ) - ret = !access_ok(VERIFY_WRITE, arg, _IOC_SIZE(cmd)); - else if ( _IOC_DIR(cmd) & _IOC_WRITE ) - ret = !access_ok(VERIFY_READ, arg, _IOC_SIZE(cmd)); - if ( ret ) - return -EFAULT; - - switch ( cmd ) - { - case PPE_ATM_MIB_CELL: /* cell level MIB */ - /* These MIB should be read at ARC side, now put zero only. */ - mib_cell.ifHCInOctets_h = 0; - mib_cell.ifHCInOctets_l = 0; - mib_cell.ifHCOutOctets_h = 0; - mib_cell.ifHCOutOctets_l = 0; - mib_cell.ifInErrors = 0; - mib_cell.ifInUnknownProtos = WAN_MIB_TABLE->wrx_drophtu_cell; - mib_cell.ifOutErrors = 0; - - ret = sizeof(mib_cell) - copy_to_user(arg, &mib_cell, sizeof(mib_cell)); - break; - - case PPE_ATM_MIB_AAL5: /* AAL5 MIB */ - value = WAN_MIB_TABLE->wrx_total_byte; - u64_add_u32(g_atm_priv_data.wrx_total_byte, value - g_atm_priv_data.prev_wrx_total_byte, &g_atm_priv_data.wrx_total_byte); - g_atm_priv_data.prev_wrx_total_byte = value; - mib_aal5.ifHCInOctets_h = g_atm_priv_data.wrx_total_byte.h; - mib_aal5.ifHCInOctets_l = g_atm_priv_data.wrx_total_byte.l; - - value = WAN_MIB_TABLE->wtx_total_byte; - u64_add_u32(g_atm_priv_data.wtx_total_byte, value - g_atm_priv_data.prev_wtx_total_byte, &g_atm_priv_data.wtx_total_byte); - g_atm_priv_data.prev_wtx_total_byte = value; - mib_aal5.ifHCOutOctets_h = g_atm_priv_data.wtx_total_byte.h; - mib_aal5.ifHCOutOctets_l = g_atm_priv_data.wtx_total_byte.l; - - mib_aal5.ifInUcastPkts = g_atm_priv_data.wrx_pdu; - mib_aal5.ifOutUcastPkts = WAN_MIB_TABLE->wtx_total_pdu; - mib_aal5.ifInErrors = WAN_MIB_TABLE->wrx_err_pdu; - mib_aal5.ifInDiscards = WAN_MIB_TABLE->wrx_dropdes_pdu + g_atm_priv_data.wrx_drop_pdu; - mib_aal5.ifOutErros = g_atm_priv_data.wtx_err_pdu; - mib_aal5.ifOutDiscards = g_atm_priv_data.wtx_drop_pdu; - - ret = sizeof(mib_aal5) - copy_to_user(arg, &mib_aal5, sizeof(mib_aal5)); - break; - - case PPE_ATM_MIB_VCC: /* VCC related MIB */ - copy_from_user(&mib_vcc, arg, sizeof(mib_vcc)); - conn = find_vpivci(mib_vcc.vpi, mib_vcc.vci); - if ( conn >= 0 ) - { - mib_vcc.mib_vcc.aal5VccCrcErrors = g_atm_priv_data.conn[conn].aal5_vcc_crc_err; - mib_vcc.mib_vcc.aal5VccOverSizedSDUs = g_atm_priv_data.conn[conn].aal5_vcc_oversize_sdu; - mib_vcc.mib_vcc.aal5VccSarTimeOuts = 0; /* no timer support */ - ret = sizeof(mib_vcc) - copy_to_user(arg, &mib_vcc, sizeof(mib_vcc)); - } - else - ret = -EINVAL; - break; - - default: - ret = -ENOIOCTLCMD; - } - - return ret; -} - -static int ppe_open(struct atm_vcc *vcc) -{ - int ret; - short vpi = vcc->vpi; - int vci = vcc->vci; - struct port *port = &g_atm_priv_data.port[(int)vcc->dev->dev_data]; - int conn; - int f_enable_irq = 0; -#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX - int sys_flag; -#endif - - if ( vcc->qos.aal != ATM_AAL5 && vcc->qos.aal != ATM_AAL0 ) - return -EPROTONOSUPPORT; - - /* check bandwidth */ - if ( (vcc->qos.txtp.traffic_class == ATM_CBR && vcc->qos.txtp.max_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) - || (vcc->qos.txtp.traffic_class == ATM_VBR_RT && vcc->qos.txtp.max_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) - || (vcc->qos.txtp.traffic_class == ATM_VBR_NRT && vcc->qos.txtp.scr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) - || (vcc->qos.txtp.traffic_class == ATM_UBR_PLUS && vcc->qos.txtp.min_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) ) - { - ret = -EINVAL; - goto PPE_OPEN_EXIT; - } - - /* check existing vpi,vci */ - conn = find_vpivci(vpi, vci); - if ( conn >= 0 ) { - ret = -EADDRINUSE; - goto PPE_OPEN_EXIT; - } - - /* check whether it need to enable irq */ - if ( g_atm_priv_data.conn_table == 0 ) - f_enable_irq = 1; - - /* allocate connection */ - for ( conn = 0; conn < MAX_PVC_NUMBER; conn++ ) { - if ( test_and_set_bit(conn, &g_atm_priv_data.conn_table) == 0 ) { - g_atm_priv_data.conn[conn].vcc = vcc; - break; - } - } - if ( conn == MAX_PVC_NUMBER ) - { - ret = -EINVAL; - goto PPE_OPEN_EXIT; - } - - /* reserve bandwidth */ - switch ( vcc->qos.txtp.traffic_class ) { - case ATM_CBR: - case ATM_VBR_RT: - port->tx_current_cell_rate += vcc->qos.txtp.max_pcr; - break; - case ATM_VBR_NRT: - port->tx_current_cell_rate += vcc->qos.txtp.scr; - break; - case ATM_UBR_PLUS: - port->tx_current_cell_rate += vcc->qos.txtp.min_pcr; - break; - } - - /* set qsb */ - set_qsb(vcc, &vcc->qos, conn); - - /* update atm_vcc structure */ - vcc->itf = (int)vcc->dev->dev_data; - vcc->vpi = vpi; - vcc->vci = vci; - set_bit(ATM_VF_READY, &vcc->flags); - - /* enable irq */ - if (f_enable_irq ) { - ifx_atm_alloc_tx = atm_alloc_tx; - - *MBOX_IGU1_ISRC = (1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM); - *MBOX_IGU1_IER = (1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM); - - enable_irq(PPE_MAILBOX_IGU1_INT); - } - - /* set port */ - WTX_QUEUE_CONFIG(conn)->sbid = (int)vcc->dev->dev_data; - - /* set htu entry */ - set_htu_entry(vpi, vci, conn, vcc->qos.aal == ATM_AAL5 ? 1 : 0, 0); - -#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX - // ReTX: occupy second QID - local_irq_save(sys_flag); - if ( g_retx_htu && vcc->qos.aal == ATM_AAL5 ) - { - int retx_conn = (conn + 8) % 16; // ReTX queue - - if ( retx_conn < MAX_PVC_NUMBER && test_and_set_bit(retx_conn, &g_atm_priv_data.conn_table) == 0 ) { - g_atm_priv_data.conn[retx_conn].vcc = vcc; - set_htu_entry(vpi, vci, retx_conn, vcc->qos.aal == ATM_AAL5 ? 1 : 0, 1); - } - } - local_irq_restore(sys_flag); -#endif - - ret = 0; - -PPE_OPEN_EXIT: - return ret; -} - -static void ppe_close(struct atm_vcc *vcc) -{ - int conn; - struct port *port; - struct connection *connection; - - if ( vcc == NULL ) - return; - - /* get connection id */ - conn = find_vcc(vcc); - if ( conn < 0 ) { - err("can't find vcc"); - goto PPE_CLOSE_EXIT; - } - connection = &g_atm_priv_data.conn[conn]; - port = &g_atm_priv_data.port[connection->port]; - - /* clear htu */ - clear_htu_entry(conn); - - /* release connection */ - clear_bit(conn, &g_atm_priv_data.conn_table); - connection->vcc = NULL; - connection->aal5_vcc_crc_err = 0; - connection->aal5_vcc_oversize_sdu = 0; - - /* disable irq */ - if ( g_atm_priv_data.conn_table == 0 ) { - disable_irq(PPE_MAILBOX_IGU1_INT); - ifx_atm_alloc_tx = NULL; - } - - /* release bandwidth */ - switch ( vcc->qos.txtp.traffic_class ) - { - case ATM_CBR: - case ATM_VBR_RT: - port->tx_current_cell_rate -= vcc->qos.txtp.max_pcr; - break; - case ATM_VBR_NRT: - port->tx_current_cell_rate -= vcc->qos.txtp.scr; - break; - case ATM_UBR_PLUS: - port->tx_current_cell_rate -= vcc->qos.txtp.min_pcr; - break; - } - -PPE_CLOSE_EXIT: - return; -} - -static int ppe_send(struct atm_vcc *vcc, struct sk_buff *skb) -{ - int ret; - int conn; - int desc_base; - struct tx_descriptor reg_desc = {0}; - - if ( vcc == NULL || skb == NULL ) - return -EINVAL; - - skb_get(skb); - atm_free_tx_skb_vcc(skb, vcc); - - conn = find_vcc(vcc); - if ( conn < 0 ) { - ret = -EINVAL; - goto FIND_VCC_FAIL; - } - - if ( !g_showtime ) { - err("not in showtime"); - ret = -EIO; - goto PPE_SEND_FAIL; - } - - if ( vcc->qos.aal == ATM_AAL5 ) { - int byteoff; - int datalen; - struct tx_inband_header *header; - - datalen = skb->len; - byteoff = (unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1); - - if ( skb_headroom(skb) < byteoff + TX_INBAND_HEADER_LENGTH ) { - struct sk_buff *new_skb; - - new_skb = alloc_skb_tx(datalen); - if ( new_skb == NULL ) { - err("ALLOC_SKB_TX_FAIL"); - ret = -ENOMEM; - goto PPE_SEND_FAIL; - } - skb_put(new_skb, datalen); - memcpy(new_skb->data, skb->data, datalen); - dev_kfree_skb_any(skb); - skb = new_skb; - byteoff = (unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1); - } - - skb_push(skb, byteoff + TX_INBAND_HEADER_LENGTH); - - header = (struct tx_inband_header *)skb->data; - - /* setup inband trailer */ - header->uu = 0; - header->cpi = 0; - header->pad = aal5_fill_pattern; - header->res1 = 0; - - /* setup cell header */ - header->clp = (vcc->atm_options & ATM_ATMOPT_CLP) ? 1 : 0; - header->pti = ATM_PTI_US0; - header->vci = vcc->vci; - header->vpi = vcc->vpi; - header->gfc = 0; - - /* setup descriptor */ - reg_desc.dataptr = (unsigned int)skb->data >> 2; - reg_desc.datalen = datalen; - reg_desc.byteoff = byteoff; - reg_desc.iscell = 0; - } - else { - /* if data pointer is not aligned, allocate new sk_buff */ - if ( ((unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1)) != 0 ) { - struct sk_buff *new_skb; - - err("skb->data not aligned"); - - new_skb = alloc_skb_tx(skb->len); - if ( new_skb == NULL ) { - err("ALLOC_SKB_TX_FAIL"); - ret = -ENOMEM; - goto PPE_SEND_FAIL; - } - skb_put(new_skb, skb->len); - memcpy(new_skb->data, skb->data, skb->len); - dev_kfree_skb_any(skb); - skb = new_skb; - } - - reg_desc.dataptr = (unsigned int)skb->data >> 2; - reg_desc.datalen = skb->len; - reg_desc.byteoff = 0; - reg_desc.iscell = 1; - } - - reg_desc.own = 1; - reg_desc.c = 1; - reg_desc.sop = reg_desc.eop = 1; - - desc_base = get_tx_desc(conn); - if ( desc_base < 0 ) { - err("ALLOC_TX_CONNECTION_FAIL"); - ret = -EIO; - goto PPE_SEND_FAIL; - } - - if ( vcc->stats ) - atomic_inc(&vcc->stats->tx); - if ( vcc->qos.aal == ATM_AAL5 ) - g_atm_priv_data.wtx_pdu++; - - /* update descriptor send pointer */ - if ( g_atm_priv_data.conn[conn].tx_skb[desc_base] != NULL ) - dev_kfree_skb_any(g_atm_priv_data.conn[conn].tx_skb[desc_base]); - g_atm_priv_data.conn[conn].tx_skb[desc_base] = skb; - - /* write discriptor to memory and write back cache */ - g_atm_priv_data.conn[conn].tx_desc[desc_base] = reg_desc; - dma_cache_wback((unsigned long)skb->data, skb->len); - - dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 1); - - mailbox_signal(conn, 1); - - adsl_led_flash(); - - return 0; - -FIND_VCC_FAIL: - err("FIND_VCC_FAIL"); - g_atm_priv_data.wtx_err_pdu++; - dev_kfree_skb_any(skb); - return ret; - -PPE_SEND_FAIL: - if ( vcc->qos.aal == ATM_AAL5 ) - g_atm_priv_data.wtx_drop_pdu++; - if ( vcc->stats ) - atomic_inc(&vcc->stats->tx_err); - dev_kfree_skb_any(skb); - return ret; -} - -static int ppe_send_oam(struct atm_vcc *vcc, void *cell, int flags) -{ - int conn; - struct uni_cell_header *uni_cell_header = (struct uni_cell_header *)cell; - int desc_base; - struct sk_buff *skb; - struct tx_descriptor reg_desc = {0}; - - if ( ((uni_cell_header->pti == ATM_PTI_SEGF5 || uni_cell_header->pti == ATM_PTI_E2EF5) - && find_vpivci(uni_cell_header->vpi, uni_cell_header->vci) < 0) - || ((uni_cell_header->vci == 0x03 || uni_cell_header->vci == 0x04) - && find_vpi(uni_cell_header->vpi) < 0) ) - return -EINVAL; - - if ( !g_showtime ) { - err("not in showtime"); - return -EIO; - } - - conn = find_vcc(vcc); - if ( conn < 0 ) { - err("FIND_VCC_FAIL"); - return -EINVAL; - } - - skb = alloc_skb_tx(CELL_SIZE); - if ( skb == NULL ) { - err("ALLOC_SKB_TX_FAIL"); - return -ENOMEM; - } - memcpy(skb->data, cell, CELL_SIZE); - - reg_desc.dataptr = (unsigned int)skb->data >> 2; - reg_desc.datalen = CELL_SIZE; - reg_desc.byteoff = 0; - reg_desc.iscell = 1; - - reg_desc.own = 1; - reg_desc.c = 1; - reg_desc.sop = reg_desc.eop = 1; - - desc_base = get_tx_desc(conn); - if ( desc_base < 0 ) { - dev_kfree_skb_any(skb); - err("ALLOC_TX_CONNECTION_FAIL"); - return -EIO; - } - - if ( vcc->stats ) - atomic_inc(&vcc->stats->tx); - - /* update descriptor send pointer */ - if ( g_atm_priv_data.conn[conn].tx_skb[desc_base] != NULL ) - dev_kfree_skb_any(g_atm_priv_data.conn[conn].tx_skb[desc_base]); - g_atm_priv_data.conn[conn].tx_skb[desc_base] = skb; - - /* write discriptor to memory and write back cache */ - g_atm_priv_data.conn[conn].tx_desc[desc_base] = reg_desc; - dma_cache_wback((unsigned long)skb->data, CELL_SIZE); - - dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 1); - - mailbox_signal(conn, 1); - - adsl_led_flash(); - - return 0; -} - -static int ppe_change_qos(struct atm_vcc *vcc, struct atm_qos *qos, int flags) -{ - int conn; - - if ( vcc == NULL || qos == NULL ) - return -EINVAL; - - conn = find_vcc(vcc); - if ( conn < 0 ) - return -EINVAL; - - set_qsb(vcc, qos, conn); - - return 0; -} - -static INLINE int adsl_led_flash(void) -{ - return ifx_mei_atm_led_blink(); -} - -/* - * Description: - * Add a 32-bit value to 64-bit value, and put result in a 64-bit variable. - * Input: - * opt1 --- ppe_u64_t, first operand, a 64-bit unsigned integer value - * opt2 --- unsigned int, second operand, a 32-bit unsigned integer value - * ret --- ppe_u64_t, pointer to a variable to hold result - * Output: - * none - */ -static INLINE void u64_add_u32(ppe_u64_t opt1, unsigned int opt2, ppe_u64_t *ret) -{ - ret->l = opt1.l + opt2; - if ( ret->l < opt1.l || ret->l < opt2 ) - ret->h++; -} - -static INLINE struct sk_buff* alloc_skb_rx(void) -{ - struct sk_buff *skb; - - skb = dev_alloc_skb(RX_DMA_CH_AAL_BUF_SIZE + DATA_BUFFER_ALIGNMENT); - if ( skb != NULL ) { - /* must be burst length alignment */ - if ( ((unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1)) != 0 ) - skb_reserve(skb, ~((unsigned int)skb->data + (DATA_BUFFER_ALIGNMENT - 1)) & (DATA_BUFFER_ALIGNMENT - 1)); - /* pub skb in reserved area "skb->data - 4" */ - *((struct sk_buff **)skb->data - 1) = skb; - /* write back and invalidate cache */ - dma_cache_wback_inv((unsigned long)skb->data - sizeof(skb), sizeof(skb)); - /* invalidate cache */ - dma_cache_inv((unsigned long)skb->data, (unsigned int)skb->end - (unsigned int)skb->data); - } - - return skb; -} - -static INLINE struct sk_buff* alloc_skb_tx(unsigned int size) -{ - struct sk_buff *skb; - - /* allocate memory including header and padding */ - size += TX_INBAND_HEADER_LENGTH + MAX_TX_PACKET_ALIGN_BYTES + MAX_TX_PACKET_PADDING_BYTES; - size &= ~(DATA_BUFFER_ALIGNMENT - 1); - skb = dev_alloc_skb(size + DATA_BUFFER_ALIGNMENT); - /* must be burst length alignment */ - if ( skb != NULL ) - skb_reserve(skb, (~((unsigned int)skb->data + (DATA_BUFFER_ALIGNMENT - 1)) & (DATA_BUFFER_ALIGNMENT - 1)) + TX_INBAND_HEADER_LENGTH); - return skb; -} - -struct sk_buff* atm_alloc_tx(struct atm_vcc *vcc, unsigned int size) -{ - int conn; - struct sk_buff *skb; - - /* oversize packet */ - if ( size > aal5s_max_packet_size ) { - err("atm_alloc_tx: oversize packet"); - return NULL; - } - /* send buffer overflow */ - if ( atomic_read(&sk_atm(vcc)->sk_wmem_alloc) && !atm_may_send(vcc, size) ) { - err("atm_alloc_tx: send buffer overflow"); - return NULL; - } - conn = find_vcc(vcc); - if ( conn < 0 ) { - err("atm_alloc_tx: unknown VCC"); - return NULL; - } - - skb = dev_alloc_skb(size); - if ( skb == NULL ) { - err("atm_alloc_tx: sk buffer is used up"); - return NULL; - } - - atomic_add(skb->truesize, &sk_atm(vcc)->sk_wmem_alloc); - - return skb; -} - -static INLINE void atm_free_tx_skb_vcc(struct sk_buff *skb, struct atm_vcc *vcc) -{ - if ( vcc->pop != NULL ) - vcc->pop(vcc, skb); - else - dev_kfree_skb_any(skb); -} - -static INLINE struct sk_buff *get_skb_rx_pointer(unsigned int dataptr) -{ - unsigned int skb_dataptr; - struct sk_buff *skb; - - skb_dataptr = ((dataptr - 1) << 2) | KSEG1; - skb = *(struct sk_buff **)skb_dataptr; - - ASSERT((unsigned int)skb >= KSEG0, "invalid skb - skb = %#08x, dataptr = %#08x", (unsigned int)skb, dataptr); - ASSERT(((unsigned int)skb->data | KSEG1) == ((dataptr << 2) | KSEG1), "invalid skb - skb = %#08x, skb->data = %#08x, dataptr = %#08x", (unsigned int)skb, (unsigned int)skb->data, dataptr); - - return skb; -} - -static INLINE int get_tx_desc(unsigned int conn) -{ - int desc_base = -1; - struct connection *p_conn = &g_atm_priv_data.conn[conn]; - - if ( p_conn->tx_desc[p_conn->tx_desc_pos].own == 0 ) { - desc_base = p_conn->tx_desc_pos; - if ( ++(p_conn->tx_desc_pos) == dma_tx_descriptor_length ) - p_conn->tx_desc_pos = 0; - } - - return desc_base; -} - -static INLINE void mailbox_oam_rx_handler(void) -{ - unsigned int vlddes = WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_OAM)->vlddes; - struct rx_descriptor reg_desc; - struct uni_cell_header *header; - int conn; - struct atm_vcc *vcc; - unsigned int i; - - for ( i = 0; i < vlddes; i++ ) { - do { - reg_desc = g_atm_priv_data.oam_desc[g_atm_priv_data.oam_desc_pos]; - } while ( reg_desc.own || !reg_desc.c ); // keep test OWN and C bit until data is ready - - header = (struct uni_cell_header *)&g_atm_priv_data.oam_buf[g_atm_priv_data.oam_desc_pos * RX_DMA_CH_OAM_BUF_SIZE]; - - if ( header->pti == ATM_PTI_SEGF5 || header->pti == ATM_PTI_E2EF5 ) - conn = find_vpivci(header->vpi, header->vci); - else if ( header->vci == 0x03 || header->vci == 0x04 ) - conn = find_vpi(header->vpi); - else - conn = -1; - - if ( conn >= 0 && g_atm_priv_data.conn[conn].vcc != NULL ) { - vcc = g_atm_priv_data.conn[conn].vcc; - - if ( vcc->push_oam != NULL ) - vcc->push_oam(vcc, header); - else - ifx_push_oam((unsigned char *)header); - - adsl_led_flash(); - } - - reg_desc.byteoff = 0; - reg_desc.datalen = RX_DMA_CH_OAM_BUF_SIZE; - reg_desc.own = 1; - reg_desc.c = 0; - - g_atm_priv_data.oam_desc[g_atm_priv_data.oam_desc_pos] = reg_desc; - if ( ++g_atm_priv_data.oam_desc_pos == RX_DMA_CH_OAM_DESC_LEN ) - g_atm_priv_data.oam_desc_pos = 0; - - mailbox_signal(RX_DMA_CH_OAM, 0); - } -} - -static INLINE void mailbox_aal_rx_handler(void) -{ - unsigned int vlddes = WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_AAL)->vlddes; - struct rx_descriptor reg_desc; - int conn; - struct atm_vcc *vcc; - struct sk_buff *skb, *new_skb; - struct rx_inband_trailer *trailer; - unsigned int i; - - for ( i = 0; i < vlddes; i++ ) { - do { - reg_desc = g_atm_priv_data.aal_desc[g_atm_priv_data.aal_desc_pos]; - } while ( reg_desc.own || !reg_desc.c ); // keep test OWN and C bit until data is ready - - conn = reg_desc.id; - - if ( g_atm_priv_data.conn[conn].vcc != NULL ) { - vcc = g_atm_priv_data.conn[conn].vcc; - - skb = get_skb_rx_pointer(reg_desc.dataptr); - - if ( reg_desc.err ) { - if ( vcc->qos.aal == ATM_AAL5 ) { - trailer = (struct rx_inband_trailer *)((unsigned int)skb->data + ((reg_desc.byteoff + reg_desc.datalen + MAX_RX_PACKET_PADDING_BYTES) & ~MAX_RX_PACKET_PADDING_BYTES)); - if ( trailer->stw_crc ) - g_atm_priv_data.conn[conn].aal5_vcc_crc_err++; - if ( trailer->stw_ovz ) - g_atm_priv_data.conn[conn].aal5_vcc_oversize_sdu++; - g_atm_priv_data.wrx_drop_pdu++; - } - if ( vcc->stats ) { - atomic_inc(&vcc->stats->rx_drop); - atomic_inc(&vcc->stats->rx_err); - } - } - else if ( atm_charge(vcc, skb->truesize) ) { - new_skb = alloc_skb_rx(); - if ( new_skb != NULL ) { - skb_reserve(skb, reg_desc.byteoff); - skb_put(skb, reg_desc.datalen); - ATM_SKB(skb)->vcc = vcc; - - dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 0); - - vcc->push(vcc, skb); - - if ( vcc->qos.aal == ATM_AAL5 ) - g_atm_priv_data.wrx_pdu++; - if ( vcc->stats ) - atomic_inc(&vcc->stats->rx); - adsl_led_flash(); - - reg_desc.dataptr = (unsigned int)new_skb->data >> 2; - } - else { - atm_return(vcc, skb->truesize); - if ( vcc->qos.aal == ATM_AAL5 ) - g_atm_priv_data.wrx_drop_pdu++; - if ( vcc->stats ) - atomic_inc(&vcc->stats->rx_drop); - } - } - else { - if ( vcc->qos.aal == ATM_AAL5 ) - g_atm_priv_data.wrx_drop_pdu++; - if ( vcc->stats ) - atomic_inc(&vcc->stats->rx_drop); - } - } - else { - g_atm_priv_data.wrx_drop_pdu++; - } - - reg_desc.byteoff = 0; - reg_desc.datalen = RX_DMA_CH_AAL_BUF_SIZE; - reg_desc.own = 1; - reg_desc.c = 0; - - g_atm_priv_data.aal_desc[g_atm_priv_data.aal_desc_pos] = reg_desc; - if ( ++g_atm_priv_data.aal_desc_pos == dma_rx_descriptor_length ) - g_atm_priv_data.aal_desc_pos = 0; - - mailbox_signal(RX_DMA_CH_AAL, 0); - } -} - -#if defined(ENABLE_TASKLET) && ENABLE_TASKLET -static void do_ppe_tasklet(unsigned long arg) -{ - *MBOX_IGU1_ISRC = *MBOX_IGU1_ISR; - mailbox_oam_rx_handler(); - mailbox_aal_rx_handler(); - if ( (*MBOX_IGU1_ISR & ((1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM))) != 0 ) - tasklet_schedule(&g_dma_tasklet); - else - enable_irq(PPE_MAILBOX_IGU1_INT); -} -#endif - -static irqreturn_t mailbox_irq_handler(int irq, void *dev_id) -{ - if ( !*MBOX_IGU1_ISR ) - return IRQ_HANDLED; - -#if defined(ENABLE_TASKLET) && ENABLE_TASKLET - disable_irq(PPE_MAILBOX_IGU1_INT); - tasklet_schedule(&g_dma_tasklet); -#else - *MBOX_IGU1_ISRC = *MBOX_IGU1_ISR; - mailbox_oam_rx_handler(); - mailbox_aal_rx_handler(); -#endif - - return IRQ_HANDLED; -} - -static INLINE void mailbox_signal(unsigned int queue, int is_tx) -{ - if ( is_tx ) { - while ( MBOX_IGU3_ISR_ISR(queue + FIRST_QSB_QID + 16) ); - *MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(queue + FIRST_QSB_QID + 16); - } - else { - while ( MBOX_IGU3_ISR_ISR(queue) ); - *MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(queue); - } -} - -static void set_qsb(struct atm_vcc *vcc, struct atm_qos *qos, unsigned int queue) -{ - struct clk *clk = clk_get(0, "fpi"); - unsigned int qsb_clk = clk_get_rate(clk); - unsigned int qsb_qid = queue + FIRST_QSB_QID; - union qsb_queue_parameter_table qsb_queue_parameter_table = {{0}}; - union qsb_queue_vbr_parameter_table qsb_queue_vbr_parameter_table = {{0}}; - unsigned int tmp; - -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { - static char *str_traffic_class[9] = { - "ATM_NONE", - "ATM_UBR", - "ATM_CBR", - "ATM_VBR", - "ATM_ABR", - "ATM_ANYCLASS", - "ATM_VBR_RT", - "ATM_UBR_PLUS", - "ATM_MAX_PCR" - }; - printk(KERN_INFO "QoS Parameters:\n"); - printk(KERN_INFO "\tAAL : %d\n", qos->aal); - printk(KERN_INFO "\tTX Traffic Class: %s\n", str_traffic_class[qos->txtp.traffic_class]); - printk(KERN_INFO "\tTX Max PCR : %d\n", qos->txtp.max_pcr); - printk(KERN_INFO "\tTX Min PCR : %d\n", qos->txtp.min_pcr); - printk(KERN_INFO "\tTX PCR : %d\n", qos->txtp.pcr); - printk(KERN_INFO "\tTX Max CDV : %d\n", qos->txtp.max_cdv); - printk(KERN_INFO "\tTX Max SDU : %d\n", qos->txtp.max_sdu); - printk(KERN_INFO "\tTX SCR : %d\n", qos->txtp.scr); - printk(KERN_INFO "\tTX MBS : %d\n", qos->txtp.mbs); - printk(KERN_INFO "\tTX CDV : %d\n", qos->txtp.cdv); - printk(KERN_INFO "\tRX Traffic Class: %s\n", str_traffic_class[qos->rxtp.traffic_class]); - printk(KERN_INFO "\tRX Max PCR : %d\n", qos->rxtp.max_pcr); - printk(KERN_INFO "\tRX Min PCR : %d\n", qos->rxtp.min_pcr); - printk(KERN_INFO "\tRX PCR : %d\n", qos->rxtp.pcr); - printk(KERN_INFO "\tRX Max CDV : %d\n", qos->rxtp.max_cdv); - printk(KERN_INFO "\tRX Max SDU : %d\n", qos->rxtp.max_sdu); - printk(KERN_INFO "\tRX SCR : %d\n", qos->rxtp.scr); - printk(KERN_INFO "\tRX MBS : %d\n", qos->rxtp.mbs); - printk(KERN_INFO "\tRX CDV : %d\n", qos->rxtp.cdv); - } -#endif // defined(DEBUG_QOS) && DEBUG_QOS - - /* - * Peak Cell Rate (PCR) Limiter - */ - if ( qos->txtp.max_pcr == 0 ) - qsb_queue_parameter_table.bit.tp = 0; /* disable PCR limiter */ - else { - /* peak cell rate would be slightly lower than requested [maximum_rate / pcr = (qsb_clock / 8) * (time_step / 4) / pcr] */ - tmp = ((qsb_clk * qsb_tstep) >> 5) / qos->txtp.max_pcr + 1; - /* check if overflow takes place */ - qsb_queue_parameter_table.bit.tp = tmp > QSB_TP_TS_MAX ? QSB_TP_TS_MAX : tmp; - } - - // A funny issue. Create two PVCs, one UBR and one UBR with max_pcr. - // Send packets to these two PVCs at same time, it trigger strange behavior. - // In A1, RAM from 0x80000000 to 0x0x8007FFFF was corrupted with fixed pattern 0x00000000 0x40000000. - // In A4, PPE firmware keep emiting unknown cell and do not respond to driver. - // To work around, create UBR always with max_pcr. - // If user want to create UBR without max_pcr, we give a default one larger than line-rate. - if ( qos->txtp.traffic_class == ATM_UBR && qsb_queue_parameter_table.bit.tp == 0 ) { - int port = g_atm_priv_data.conn[queue].port; - unsigned int max_pcr = g_atm_priv_data.port[port].tx_max_cell_rate + 1000; - - tmp = ((qsb_clk * qsb_tstep) >> 5) / max_pcr + 1; - if ( tmp > QSB_TP_TS_MAX ) - tmp = QSB_TP_TS_MAX; - else if ( tmp < 1 ) - tmp = 1; - qsb_queue_parameter_table.bit.tp = tmp; - } - - /* - * Weighted Fair Queueing Factor (WFQF) - */ - switch ( qos->txtp.traffic_class ) { - case ATM_CBR: - case ATM_VBR_RT: - /* real time queue gets weighted fair queueing bypass */ - qsb_queue_parameter_table.bit.wfqf = 0; - break; - case ATM_VBR_NRT: - case ATM_UBR_PLUS: - /* WFQF calculation here is based on virtual cell rates, to reduce granularity for high rates */ - /* WFQF is maximum cell rate / garenteed cell rate */ - /* wfqf = qsb_minimum_cell_rate * QSB_WFQ_NONUBR_MAX / requested_minimum_peak_cell_rate */ - if ( qos->txtp.min_pcr == 0 ) - qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_NONUBR_MAX; - else - { - tmp = QSB_GCR_MIN * QSB_WFQ_NONUBR_MAX / qos->txtp.min_pcr; - if ( tmp == 0 ) - qsb_queue_parameter_table.bit.wfqf = 1; - else if ( tmp > QSB_WFQ_NONUBR_MAX ) - qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_NONUBR_MAX; - else - qsb_queue_parameter_table.bit.wfqf = tmp; - } - break; - default: - case ATM_UBR: - qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_UBR_BYPASS; - } - - /* - * Sustained Cell Rate (SCR) Leaky Bucket Shaper VBR.0/VBR.1 - */ - if ( qos->txtp.traffic_class == ATM_VBR_RT || qos->txtp.traffic_class == ATM_VBR_NRT ) { - if ( qos->txtp.scr == 0 ) { - /* disable shaper */ - qsb_queue_vbr_parameter_table.bit.taus = 0; - qsb_queue_vbr_parameter_table.bit.ts = 0; - } - else { - /* Cell Loss Priority (CLP) */ - if ( (vcc->atm_options & ATM_ATMOPT_CLP) ) - /* CLP1 */ - qsb_queue_parameter_table.bit.vbr = 1; - else - /* CLP0 */ - qsb_queue_parameter_table.bit.vbr = 0; - /* Rate Shaper Parameter (TS) and Burst Tolerance Parameter for SCR (tauS) */ - tmp = ((qsb_clk * qsb_tstep) >> 5) / qos->txtp.scr + 1; - qsb_queue_vbr_parameter_table.bit.ts = tmp > QSB_TP_TS_MAX ? QSB_TP_TS_MAX : tmp; - tmp = (qos->txtp.mbs - 1) * (qsb_queue_vbr_parameter_table.bit.ts - qsb_queue_parameter_table.bit.tp) / 64; - if ( tmp == 0 ) - qsb_queue_vbr_parameter_table.bit.taus = 1; - else if ( tmp > QSB_TAUS_MAX ) - qsb_queue_vbr_parameter_table.bit.taus = QSB_TAUS_MAX; - else - qsb_queue_vbr_parameter_table.bit.taus = tmp; - } - } - else { - qsb_queue_vbr_parameter_table.bit.taus = 0; - qsb_queue_vbr_parameter_table.bit.ts = 0; - } - - /* Queue Parameter Table (QPT) */ - *QSB_RTM = QSB_RTM_DM_SET(QSB_QPT_SET_MASK); - *QSB_RTD = QSB_RTD_TTV_SET(qsb_queue_parameter_table.dword); - *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_QPT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(qsb_qid); -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) - printk("QPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); -#endif - /* Queue VBR Paramter Table (QVPT) */ - *QSB_RTM = QSB_RTM_DM_SET(QSB_QVPT_SET_MASK); - *QSB_RTD = QSB_RTD_TTV_SET(qsb_queue_vbr_parameter_table.dword); - *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_VBR) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(qsb_qid); -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) - printk("QVPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); -#endif - -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { - printk("set_qsb\n"); - printk(" qsb_clk = %lu\n", (unsigned long)qsb_clk); - printk(" qsb_queue_parameter_table.bit.tp = %d\n", (int)qsb_queue_parameter_table.bit.tp); - printk(" qsb_queue_parameter_table.bit.wfqf = %d (0x%08X)\n", (int)qsb_queue_parameter_table.bit.wfqf, (int)qsb_queue_parameter_table.bit.wfqf); - printk(" qsb_queue_parameter_table.bit.vbr = %d\n", (int)qsb_queue_parameter_table.bit.vbr); - printk(" qsb_queue_parameter_table.dword = 0x%08X\n", (int)qsb_queue_parameter_table.dword); - printk(" qsb_queue_vbr_parameter_table.bit.ts = %d\n", (int)qsb_queue_vbr_parameter_table.bit.ts); - printk(" qsb_queue_vbr_parameter_table.bit.taus = %d\n", (int)qsb_queue_vbr_parameter_table.bit.taus); - printk(" qsb_queue_vbr_parameter_table.dword = 0x%08X\n", (int)qsb_queue_vbr_parameter_table.dword); - } -#endif -} - -static void qsb_global_set(void) -{ - struct clk *clk = clk_get(0, "fpi"); - unsigned int qsb_clk = clk_get_rate(clk); - int i; - unsigned int tmp1, tmp2, tmp3; - - *QSB_ICDV = QSB_ICDV_TAU_SET(qsb_tau); - *QSB_SBL = QSB_SBL_SBL_SET(qsb_srvm); - *QSB_CFG = QSB_CFG_TSTEPC_SET(qsb_tstep >> 1); -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { - printk("qsb_clk = %u\n", qsb_clk); - printk("QSB_ICDV (%08X) = %d (%d), QSB_SBL (%08X) = %d (%d), QSB_CFG (%08X) = %d (%d)\n", (unsigned int)QSB_ICDV, *QSB_ICDV, QSB_ICDV_TAU_SET(qsb_tau), (unsigned int)QSB_SBL, *QSB_SBL, QSB_SBL_SBL_SET(qsb_srvm), (unsigned int)QSB_CFG, *QSB_CFG, QSB_CFG_TSTEPC_SET(qsb_tstep >> 1)); - } -#endif - - /* - * set SCT and SPT per port - */ - for ( i = 0; i < ATM_PORT_NUMBER; i++ ) { - if ( g_atm_priv_data.port[i].tx_max_cell_rate != 0 ) { - tmp1 = ((qsb_clk * qsb_tstep) >> 1) / g_atm_priv_data.port[i].tx_max_cell_rate; - tmp2 = tmp1 >> 6; /* integer value of Tsb */ - tmp3 = (tmp1 & ((1 << 6) - 1)) + 1; /* fractional part of Tsb */ - /* carry over to integer part (?) */ - if ( tmp3 == (1 << 6) ) - { - tmp3 = 0; - tmp2++; - } - if ( tmp2 == 0 ) - tmp2 = tmp3 = 1; - /* 1. set mask */ - /* 2. write value to data transfer register */ - /* 3. start the tranfer */ - /* SCT (FracRate) */ - *QSB_RTM = QSB_RTM_DM_SET(QSB_SET_SCT_MASK); - *QSB_RTD = QSB_RTD_TTV_SET(tmp3); - *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_SCT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(i & 0x01); -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) - printk("SCT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); -#endif - /* SPT (SBV + PN + IntRage) */ - *QSB_RTM = QSB_RTM_DM_SET(QSB_SET_SPT_MASK); - *QSB_RTD = QSB_RTD_TTV_SET(QSB_SPT_SBV_VALID | QSB_SPT_PN_SET(i & 0x01) | QSB_SPT_INTRATE_SET(tmp2)); - *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_SPT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(i & 0x01); -#if defined(DEBUG_QOS) && DEBUG_QOS - if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) - printk("SPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); -#endif - } - } -} - -static INLINE void set_htu_entry(unsigned int vpi, unsigned int vci, unsigned int queue, int aal5, int is_retx) -{ - struct htu_entry htu_entry = { res1: 0x00, - clp: is_retx ? 0x01 : 0x00, - pid: g_atm_priv_data.conn[queue].port & 0x01, - vpi: vpi, - vci: vci, - pti: 0x00, - vld: 0x01}; - - struct htu_mask htu_mask = { set: 0x01, -#if !defined(ENABLE_ATM_RETX) || !ENABLE_ATM_RETX - clp: 0x01, - pid_mask: 0x02, -#else - clp: g_retx_htu ? 0x00 : 0x01, - pid_mask: RETX_MODE_CFG->retx_en ? 0x03 : 0x02, -#endif - vpi_mask: 0x00, -#if !defined(ENABLE_ATM_RETX) || !ENABLE_ATM_RETX - vci_mask: 0x0000, -#else - vci_mask: RETX_MODE_CFG->retx_en ? 0xFF00 : 0x0000, -#endif - pti_mask: 0x03, // 0xx, user data - clear: 0x00}; - - struct htu_result htu_result = {res1: 0x00, - cellid: queue, - res2: 0x00, - type: aal5 ? 0x00 : 0x01, - ven: 0x01, - res3: 0x00, - qid: queue}; - - *HTU_RESULT(queue + OAM_HTU_ENTRY_NUMBER) = htu_result; - *HTU_MASK(queue + OAM_HTU_ENTRY_NUMBER) = htu_mask; - *HTU_ENTRY(queue + OAM_HTU_ENTRY_NUMBER) = htu_entry; -} - -static INLINE void clear_htu_entry(unsigned int queue) -{ - HTU_ENTRY(queue + OAM_HTU_ENTRY_NUMBER)->vld = 0; -} - -static void validate_oam_htu_entry(void) -{ - HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY)->vld = 1; - HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY)->vld = 1; - HTU_ENTRY(OAM_F5_HTU_ENTRY)->vld = 1; -#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX - HTU_ENTRY(OAM_ARQ_HTU_ENTRY)->vld = 1; -#endif -} - -static void invalidate_oam_htu_entry(void) -{ - HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY)->vld = 0; - HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY)->vld = 0; - HTU_ENTRY(OAM_F5_HTU_ENTRY)->vld = 0; -#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX - HTU_ENTRY(OAM_ARQ_HTU_ENTRY)->vld = 0; -#endif -} - -static INLINE int find_vpi(unsigned int vpi) -{ - int i; - unsigned int bit; - - for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { - if ( (g_atm_priv_data.conn_table & bit) != 0 - && g_atm_priv_data.conn[i].vcc != NULL - && vpi == g_atm_priv_data.conn[i].vcc->vpi ) - return i; - } - - return -1; -} - -static INLINE int find_vpivci(unsigned int vpi, unsigned int vci) -{ - int i; - unsigned int bit; - - for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { - if ( (g_atm_priv_data.conn_table & bit) != 0 - && g_atm_priv_data.conn[i].vcc != NULL - && vpi == g_atm_priv_data.conn[i].vcc->vpi - && vci == g_atm_priv_data.conn[i].vcc->vci ) - return i; - } - - return -1; -} - -static INLINE int find_vcc(struct atm_vcc *vcc) -{ - int i; - unsigned int bit; - - for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { - if ( (g_atm_priv_data.conn_table & bit) != 0 - && g_atm_priv_data.conn[i].vcc == vcc ) - return i; - } - - return -1; -} - -#if defined(DEBUG_DUMP_SKB) && DEBUG_DUMP_SKB -static void dump_skb(struct sk_buff *skb, u32 len, char *title, int port, int ch, int is_tx) -{ - int i; - - if ( !(ifx_atm_dbg_enable & (is_tx ? DBG_ENABLE_MASK_DUMP_SKB_TX : DBG_ENABLE_MASK_DUMP_SKB_RX)) ) - return; - - if ( skb->len < len ) - len = skb->len; - - if ( len > RX_DMA_CH_AAL_BUF_SIZE ) { - printk("too big data length: skb = %08x, skb->data = %08x, skb->len = %d\n", (u32)skb, (u32)skb->data, skb->len); - return; - } - - if ( ch >= 0 ) - printk("%s (port %d, ch %d)\n", title, port, ch); - else - printk("%s\n", title); - printk(" skb->data = %08X, skb->tail = %08X, skb->len = %d\n", (u32)skb->data, (u32)skb->tail, (int)skb->len); - for ( i = 1; i <= len; i++ ) { - if ( i % 16 == 1 ) - printk(" %4d:", i - 1); - printk(" %02X", (int)(*((char*)skb->data + i - 1) & 0xFF)); - if ( i % 16 == 0 ) - printk("\n"); - } - if ( (i - 1) % 16 != 0 ) - printk("\n"); -} -#endif - -static INLINE void proc_file_create(void) -{ -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - struct proc_dir_entry *res; -#endif - - g_atm_dir = proc_mkdir("driver/ifx_atm", NULL); - - create_proc_read_entry("version", - 0, - g_atm_dir, - proc_read_version, - NULL); - - res = create_proc_entry("mib", - 0, - g_atm_dir); - if ( res != NULL ) { - res->read_proc = proc_read_mib; - res->write_proc = proc_write_mib; - } - -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - res = create_proc_entry("dbg", - 0, - g_atm_dir); - if ( res != NULL ) { - res->read_proc = proc_read_dbg; - res->write_proc = proc_write_dbg; - } -#endif - -#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC - create_proc_read_entry("htu", - 0, - g_atm_dir, - proc_read_htu, - NULL); - - create_proc_read_entry("txq", - 0, - g_atm_dir, - proc_read_txq, - NULL); -#endif -} - -static INLINE void proc_file_delete(void) -{ -#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC - remove_proc_entry("txq", g_atm_dir); - - remove_proc_entry("htu", g_atm_dir); -#endif - -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - remove_proc_entry("dbg", g_atm_dir); -#endif - - remove_proc_entry("version", g_atm_dir); - - remove_proc_entry("driver/ifx_atm", NULL); -} - -static int proc_read_version(char *buf, char **start, off_t offset, int count, int *eof, void *data) -{ - int len = 0; - - len += ifx_atm_version(buf + len); - - if ( offset >= len ) { - *start = buf; - *eof = 1; - return 0; - } - *start = buf + offset; - if ( (len -= offset) > count ) - return count; - *eof = 1; - return len; -} - -static int proc_read_mib(char *page, char **start, off_t off, int count, int *eof, void *data) -{ - int len = 0; - - len += sprintf(page + off + len, "Firmware\n"); - len += sprintf(page + off + len, " wrx_drophtu_cell = %u\n", WAN_MIB_TABLE->wrx_drophtu_cell); - len += sprintf(page + off + len, " wrx_dropdes_pdu = %u\n", WAN_MIB_TABLE->wrx_dropdes_pdu); - len += sprintf(page + off + len, " wrx_correct_pdu = %u\n", WAN_MIB_TABLE->wrx_correct_pdu); - len += sprintf(page + off + len, " wrx_err_pdu = %u\n", WAN_MIB_TABLE->wrx_err_pdu); - len += sprintf(page + off + len, " wrx_dropdes_cell = %u\n", WAN_MIB_TABLE->wrx_dropdes_cell); - len += sprintf(page + off + len, " wrx_correct_cell = %u\n", WAN_MIB_TABLE->wrx_correct_cell); - len += sprintf(page + off + len, " wrx_err_cell = %u\n", WAN_MIB_TABLE->wrx_err_cell); - len += sprintf(page + off + len, " wrx_total_byte = %u\n", WAN_MIB_TABLE->wrx_total_byte); - len += sprintf(page + off + len, " wtx_total_pdu = %u\n", WAN_MIB_TABLE->wtx_total_pdu); - len += sprintf(page + off + len, " wtx_total_cell = %u\n", WAN_MIB_TABLE->wtx_total_cell); - len += sprintf(page + off + len, " wtx_total_byte = %u\n", WAN_MIB_TABLE->wtx_total_byte); - len += sprintf(page + off + len, "Driver\n"); - len += sprintf(page + off + len, " wrx_pdu = %u\n", g_atm_priv_data.wrx_pdu); - len += sprintf(page + off + len, " wrx_drop_pdu = %u\n", g_atm_priv_data.wrx_drop_pdu); - len += sprintf(page + off + len, " wtx_pdu = %u\n", g_atm_priv_data.wtx_pdu); - len += sprintf(page + off + len, " wtx_err_pdu = %u\n", g_atm_priv_data.wtx_err_pdu); - len += sprintf(page + off + len, " wtx_drop_pdu = %u\n", g_atm_priv_data.wtx_drop_pdu); - - *eof = 1; - - return len; -} - -static int proc_write_mib(struct file *file, const char *buf, unsigned long count, void *data) -{ - char str[2048]; - char *p; - int len, rlen; - - len = count < sizeof(str) ? count : sizeof(str) - 1; - rlen = len - copy_from_user(str, buf, len); - while ( rlen && str[rlen - 1] <= ' ' ) - rlen--; - str[rlen] = 0; - for ( p = str; *p && *p <= ' '; p++, rlen-- ); - if ( !*p ) - return 0; - - if ( stricmp(p, "clear") == 0 || stricmp(p, "clear all") == 0 - || stricmp(p, "clean") == 0 || stricmp(p, "clean all") == 0 ) { - memset(WAN_MIB_TABLE, 0, sizeof(*WAN_MIB_TABLE)); - g_atm_priv_data.wrx_pdu = 0; - g_atm_priv_data.wrx_drop_pdu = 0; - g_atm_priv_data.wtx_pdu = 0; - g_atm_priv_data.wtx_err_pdu = 0; - g_atm_priv_data.wtx_drop_pdu = 0; - } - - return count; -} - -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC - -static int proc_read_dbg(char *page, char **start, off_t off, int count, int *eof, void *data) -{ - int len = 0; - - len += sprintf(page + off + len, "error print - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ERR) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "debug print - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DEBUG_PRINT) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "assert - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ASSERT) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "dump rx skb - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_SKB_RX) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "dump tx skb - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_SKB_TX) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "qos - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ? "enabled" : "disabled"); - len += sprintf(page + off + len, "dump init - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_INIT) ? "enabled" : "disabled"); - - *eof = 1; - - return len; -} - -static int proc_write_dbg(struct file *file, const char *buf, unsigned long count, void *data) -{ - static const char *dbg_enable_mask_str[] = { - " error print", - " err", - " debug print", - " dbg", - " assert", - " assert", - " dump rx skb", - " rx", - " dump tx skb", - " tx", - " dump qos", - " qos", - " dump init", - " init", - " all" - }; - static const int dbg_enable_mask_str_len[] = { - 12, 4, - 12, 4, - 7, 7, - 12, 3, - 12, 3, - 9, 4, - 10, 5, - 4 - }; - u32 dbg_enable_mask[] = { - DBG_ENABLE_MASK_ERR, - DBG_ENABLE_MASK_DEBUG_PRINT, - DBG_ENABLE_MASK_ASSERT, - DBG_ENABLE_MASK_DUMP_SKB_RX, - DBG_ENABLE_MASK_DUMP_SKB_TX, - DBG_ENABLE_MASK_DUMP_QOS, - DBG_ENABLE_MASK_DUMP_INIT, - DBG_ENABLE_MASK_ALL - }; - - char str[2048]; - char *p; - - int len, rlen; - - int f_enable = 0; - int i; - - len = count < sizeof(str) ? count : sizeof(str) - 1; - rlen = len - copy_from_user(str, buf, len); - while ( rlen && str[rlen - 1] <= ' ' ) - rlen--; - str[rlen] = 0; - for ( p = str; *p && *p <= ' '; p++, rlen-- ); - if ( !*p ) - return 0; - - if ( strincmp(p, "enable", 6) == 0 ) { - p += 6; - f_enable = 1; - } - else if ( strincmp(p, "disable", 7) == 0 ) { - p += 7; - f_enable = -1; - } - else if ( strincmp(p, "help", 4) == 0 || *p == '?' ) { - printk("echo [err/dbg/assert/rx/tx/init/all] > /proc/eth/dbg\n"); - } - - if ( f_enable ) { - if ( *p == 0 ) { - if ( f_enable > 0 ) - ifx_atm_dbg_enable |= DBG_ENABLE_MASK_ALL; - else - ifx_atm_dbg_enable &= ~DBG_ENABLE_MASK_ALL; - } - else { - do { - for ( i = 0; i < NUM_ENTITY(dbg_enable_mask_str); i++ ) - if ( strincmp(p, dbg_enable_mask_str[i], dbg_enable_mask_str_len[i]) == 0 ) { - if ( f_enable > 0 ) - ifx_atm_dbg_enable |= dbg_enable_mask[i >> 1]; - else - ifx_atm_dbg_enable &= ~dbg_enable_mask[i >> 1]; - p += dbg_enable_mask_str_len[i]; - break; - } - } while ( i < NUM_ENTITY(dbg_enable_mask_str) ); - } - } - - return count; -} - -#endif - -#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC - -static INLINE int print_htu(char *buf, int i) -{ - int len = 0; - - if ( HTU_ENTRY(i)->vld ) { - len += sprintf(buf + len, "%2d. valid\n", i); - len += sprintf(buf + len, " entry 0x%08x - pid %01x vpi %02x vci %04x pti %01x\n", *(u32*)HTU_ENTRY(i), HTU_ENTRY(i)->pid, HTU_ENTRY(i)->vpi, HTU_ENTRY(i)->vci, HTU_ENTRY(i)->pti); - len += sprintf(buf + len, " mask 0x%08x - pid %01x vpi %02x vci %04x pti %01x\n", *(u32*)HTU_MASK(i), HTU_MASK(i)->pid_mask, HTU_MASK(i)->vpi_mask, HTU_MASK(i)->vci_mask, HTU_MASK(i)->pti_mask); - len += sprintf(buf + len, " result 0x%08x - type: %s, qid: %d", *(u32*)HTU_RESULT(i), HTU_RESULT(i)->type ? "cell" : "AAL5", HTU_RESULT(i)->qid); - if ( HTU_RESULT(i)->type ) - len += sprintf(buf + len, ", cell id: %d, verification: %s", HTU_RESULT(i)->cellid, HTU_RESULT(i)->ven ? "on" : "off"); - len += sprintf(buf + len, "\n"); - } - else - len += sprintf(buf + len, "%2d. invalid\n", i); - - return len; -} - -static int proc_read_htu(char *page, char **start, off_t off, int count, int *eof, void *data) -{ - int len = 0; - int len_max = off + count; - char *pstr; - char str[1024]; - int llen; - - int htuts = *CFG_WRX_HTUTS; - int i; - - pstr = *start = page; - - llen = sprintf(pstr, "HTU Table (Max %d):\n", htuts); - pstr += llen; - len += llen; - - for ( i = 0; i < htuts; i++ ) { - llen = print_htu(str, i); - if ( len <= off && len + llen > off ) { - memcpy(pstr, str + off - len, len + llen - off); - pstr += len + llen - off; - } - else if ( len > off ) { - memcpy(pstr, str, llen); - pstr += llen; - } - len += llen; - if ( len >= len_max ) - goto PROC_READ_HTU_OVERRUN_END; - } - - *eof = 1; - - return len - off; - -PROC_READ_HTU_OVERRUN_END: - - return len - llen - off; -} - -static INLINE int print_tx_queue(char *buf, int i) -{ - int len = 0; - - if ( (*WTX_DMACH_ON & (1 << i)) ) { - len += sprintf(buf + len, "%2d. valid\n", i); - len += sprintf(buf + len, " queue 0x%08x - sbid %u, qsb %s\n", *(u32*)WTX_QUEUE_CONFIG(i), (unsigned int)WTX_QUEUE_CONFIG(i)->sbid, WTX_QUEUE_CONFIG(i)->qsben ? "enable" : "disable"); - len += sprintf(buf + len, " dma 0x%08x - base %08x, len %u, vlddes %u\n", *(u32*)WTX_DMA_CHANNEL_CONFIG(i), WTX_DMA_CHANNEL_CONFIG(i)->desba, WTX_DMA_CHANNEL_CONFIG(i)->deslen, WTX_DMA_CHANNEL_CONFIG(i)->vlddes); - } - else - len += sprintf(buf + len, "%2d. invalid\n", i); - - return len; -} - -static int proc_read_txq(char *page, char **start, off_t off, int count, int *eof, void *data) -{ - int len = 0; - int len_max = off + count; - char *pstr; - char str[1024]; - int llen; - - int i; - - pstr = *start = page; - - llen = sprintf(pstr, "TX Queue Config (Max %d):\n", *CFG_WTX_DCHNUM); - pstr += llen; - len += llen; - - for ( i = 0; i < 16; i++ ) { - llen = print_tx_queue(str, i); - if ( len <= off && len + llen > off ) { - memcpy(pstr, str + off - len, len + llen - off); - pstr += len + llen - off; - } - else if ( len > off ) { - memcpy(pstr, str, llen); - pstr += llen; - } - len += llen; - if ( len >= len_max ) - goto PROC_READ_HTU_OVERRUN_END; - } - - *eof = 1; - - return len - off; - -PROC_READ_HTU_OVERRUN_END: - - return len - llen - off; -} - -#endif - -static int stricmp(const char *p1, const char *p2) -{ - int c1, c2; - - while ( *p1 && *p2 ) - { - c1 = *p1 >= 'A' && *p1 <= 'Z' ? *p1 + 'a' - 'A' : *p1; - c2 = *p2 >= 'A' && *p2 <= 'Z' ? *p2 + 'a' - 'A' : *p2; - if ( (c1 -= c2) ) - return c1; - p1++; - p2++; - } - - return *p1 - *p2; -} - -#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC -static int strincmp(const char *p1, const char *p2, int n) -{ - int c1 = 0, c2; - - while ( n && *p1 && *p2 ) - { - c1 = *p1 >= 'A' && *p1 <= 'Z' ? *p1 + 'a' - 'A' : *p1; - c2 = *p2 >= 'A' && *p2 <= 'Z' ? *p2 + 'a' - 'A' : *p2; - if ( (c1 -= c2) ) - return c1; - p1++; - p2++; - n--; - } - - return n ? *p1 - *p2 : c1; -} -#endif - -static INLINE int ifx_atm_version(char *buf) -{ - int len = 0; - unsigned int major, minor; - - ifx_atm_get_fw_ver(&major, &minor); - - len += sprintf(buf + len, "Infineon Technologies ATM driver version %d.%d.%d\n", IFX_ATM_VER_MAJOR, IFX_ATM_VER_MID, IFX_ATM_VER_MINOR); - len += sprintf(buf + len, "Infineon Technologies ATM (A1) firmware version %d.%d\n", major, minor); - - return len; -} - -#ifdef MODULE -static INLINE void reset_ppe(void) -{ - // TODO: -} -#endif - -static INLINE void check_parameters(void) -{ - /* Please refer to Amazon spec 15.4 for setting these values. */ - if ( qsb_tau < 1 ) - qsb_tau = 1; - if ( qsb_tstep < 1 ) - qsb_tstep = 1; - else if ( qsb_tstep > 4 ) - qsb_tstep = 4; - else if ( qsb_tstep == 3 ) - qsb_tstep = 2; - - /* There is a delay between PPE write descriptor and descriptor is */ - /* really stored in memory. Host also has this delay when writing */ - /* descriptor. So PPE will use this value to determine if the write */ - /* operation makes effect. */ - if ( write_descriptor_delay < 0 ) - write_descriptor_delay = 0; - - if ( aal5_fill_pattern < 0 ) - aal5_fill_pattern = 0; - else - aal5_fill_pattern &= 0xFF; - - /* Because of the limitation of length field in descriptors, the packet */ - /* size could not be larger than 64K minus overhead size. */ - if ( aal5r_max_packet_size < 0 ) - aal5r_max_packet_size = 0; - else if ( aal5r_max_packet_size >= 65535 - MAX_RX_FRAME_EXTRA_BYTES ) - aal5r_max_packet_size = 65535 - MAX_RX_FRAME_EXTRA_BYTES; - if ( aal5r_min_packet_size < 0 ) - aal5r_min_packet_size = 0; - else if ( aal5r_min_packet_size > aal5r_max_packet_size ) - aal5r_min_packet_size = aal5r_max_packet_size; - if ( aal5s_max_packet_size < 0 ) - aal5s_max_packet_size = 0; - else if ( aal5s_max_packet_size >= 65535 - MAX_TX_FRAME_EXTRA_BYTES ) - aal5s_max_packet_size = 65535 - MAX_TX_FRAME_EXTRA_BYTES; - if ( aal5s_min_packet_size < 0 ) - aal5s_min_packet_size = 0; - else if ( aal5s_min_packet_size > aal5s_max_packet_size ) - aal5s_min_packet_size = aal5s_max_packet_size; - - if ( dma_rx_descriptor_length < 2 ) - dma_rx_descriptor_length = 2; - if ( dma_tx_descriptor_length < 2 ) - dma_tx_descriptor_length = 2; - if ( dma_rx_clp1_descriptor_threshold < 0 ) - dma_rx_clp1_descriptor_threshold = 0; - else if ( dma_rx_clp1_descriptor_threshold > dma_rx_descriptor_length ) - dma_rx_clp1_descriptor_threshold = dma_rx_descriptor_length; - - if ( dma_tx_descriptor_length < 2 ) - dma_tx_descriptor_length = 2; -} - -static INLINE int init_priv_data(void) -{ - void *p; - int i; - struct rx_descriptor rx_desc = {0}; - struct sk_buff *skb; - volatile struct tx_descriptor *p_tx_desc; - struct sk_buff **ppskb; - - // clear atm private data structure - memset(&g_atm_priv_data, 0, sizeof(g_atm_priv_data)); - - // allocate memory for RX (AAL) descriptors - p = kzalloc(dma_rx_descriptor_length * sizeof(struct rx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); - if ( p == NULL ) - return IFX_ERROR; - dma_cache_wback_inv((unsigned long)p, dma_rx_descriptor_length * sizeof(struct rx_descriptor) + DESC_ALIGNMENT); - g_atm_priv_data.aal_desc_base = p; - p = (void *)((((unsigned int)p + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); - g_atm_priv_data.aal_desc = (volatile struct rx_descriptor *)p; - - // allocate memory for RX (OAM) descriptors - p = kzalloc(RX_DMA_CH_OAM_DESC_LEN * sizeof(struct rx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); - if ( p == NULL ) - return IFX_ERROR; - dma_cache_wback_inv((unsigned long)p, RX_DMA_CH_OAM_DESC_LEN * sizeof(struct rx_descriptor) + DESC_ALIGNMENT); - g_atm_priv_data.oam_desc_base = p; - p = (void *)((((unsigned int)p + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); - g_atm_priv_data.oam_desc = (volatile struct rx_descriptor *)p; - - // allocate memory for RX (OAM) buffer - p = kzalloc(RX_DMA_CH_OAM_DESC_LEN * RX_DMA_CH_OAM_BUF_SIZE + DATA_BUFFER_ALIGNMENT, GFP_KERNEL); - if ( p == NULL ) - return IFX_ERROR; - dma_cache_wback_inv((unsigned long)p, RX_DMA_CH_OAM_DESC_LEN * RX_DMA_CH_OAM_BUF_SIZE + DATA_BUFFER_ALIGNMENT); - g_atm_priv_data.oam_buf_base = p; - p = (void *)(((unsigned int)p + DATA_BUFFER_ALIGNMENT - 1) & ~(DATA_BUFFER_ALIGNMENT - 1)); - g_atm_priv_data.oam_buf = p; - - // allocate memory for TX descriptors - p = kzalloc(MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct tx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); - if ( p == NULL ) - return IFX_ERROR; - dma_cache_wback_inv((unsigned long)p, MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct tx_descriptor) + DESC_ALIGNMENT); - g_atm_priv_data.tx_desc_base = p; - - // allocate memory for TX skb pointers - p = kzalloc(MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct sk_buff *) + 4, GFP_KERNEL); - if ( p == NULL ) - return IFX_ERROR; - dma_cache_wback_inv((unsigned long)p, MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct sk_buff *) + 4); - g_atm_priv_data.tx_skb_base = p; - - // setup RX (AAL) descriptors - rx_desc.own = 1; - rx_desc.c = 0; - rx_desc.sop = 1; - rx_desc.eop = 1; - rx_desc.byteoff = 0; - rx_desc.id = 0; - rx_desc.err = 0; - rx_desc.datalen = RX_DMA_CH_AAL_BUF_SIZE; - for ( i = 0; i < dma_rx_descriptor_length; i++ ) { - skb = alloc_skb_rx(); - if ( skb == NULL ) - return IFX_ERROR; - rx_desc.dataptr = ((unsigned int)skb->data >> 2) & 0x0FFFFFFF; - g_atm_priv_data.aal_desc[i] = rx_desc; - } - - // setup RX (OAM) descriptors - p = (void *)((unsigned int)g_atm_priv_data.oam_buf | KSEG1); - rx_desc.own = 1; - rx_desc.c = 0; - rx_desc.sop = 1; - rx_desc.eop = 1; - rx_desc.byteoff = 0; - rx_desc.id = 0; - rx_desc.err = 0; - rx_desc.datalen = RX_DMA_CH_OAM_BUF_SIZE; - for ( i = 0; i < RX_DMA_CH_OAM_DESC_LEN; i++ ) { - rx_desc.dataptr = ((unsigned int)p >> 2) & 0x0FFFFFFF; - g_atm_priv_data.oam_desc[i] = rx_desc; - p = (void *)((unsigned int)p + RX_DMA_CH_OAM_BUF_SIZE); - } - - // setup TX descriptors and skb pointers - p_tx_desc = (volatile struct tx_descriptor *)((((unsigned int)g_atm_priv_data.tx_desc_base + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); - ppskb = (struct sk_buff **)(((unsigned int)g_atm_priv_data.tx_skb_base + 3) & ~3); - for ( i = 0; i < MAX_PVC_NUMBER; i++ ) { - g_atm_priv_data.conn[i].tx_desc = &p_tx_desc[i * dma_tx_descriptor_length]; - g_atm_priv_data.conn[i].tx_skb = &ppskb[i * dma_tx_descriptor_length]; - } - - for ( i = 0; i < ATM_PORT_NUMBER; i++ ) - g_atm_priv_data.port[i].tx_max_cell_rate = DEFAULT_TX_LINK_RATE; - - return IFX_SUCCESS; -} - -static INLINE void clear_priv_data(void) -{ - int i, j; - struct sk_buff *skb; - - for ( i = 0; i < MAX_PVC_NUMBER; i++ ) { - if ( g_atm_priv_data.conn[i].tx_skb != NULL ) { - for ( j = 0; j < dma_tx_descriptor_length; j++ ) - if ( g_atm_priv_data.conn[i].tx_skb[j] != NULL ) - dev_kfree_skb_any(g_atm_priv_data.conn[i].tx_skb[j]); - } - } - - if ( g_atm_priv_data.tx_skb_base != NULL ) - kfree(g_atm_priv_data.tx_skb_base); - - if ( g_atm_priv_data.tx_desc_base != NULL ) - kfree(g_atm_priv_data.tx_desc_base); - - if ( g_atm_priv_data.oam_buf_base != NULL ) - kfree(g_atm_priv_data.oam_buf_base); - - if ( g_atm_priv_data.oam_desc_base != NULL ) - kfree(g_atm_priv_data.oam_desc_base); - - if ( g_atm_priv_data.aal_desc_base != NULL ) { - for ( i = 0; i < dma_rx_descriptor_length; i++ ) { - if ( g_atm_priv_data.aal_desc[i].sop || g_atm_priv_data.aal_desc[i].eop ) { // descriptor initialized - skb = get_skb_rx_pointer(g_atm_priv_data.aal_desc[i].dataptr); - dev_kfree_skb_any(skb); - } - } - kfree(g_atm_priv_data.aal_desc_base); - } -} - -static INLINE void init_rx_tables(void) -{ - int i; - struct wrx_queue_config wrx_queue_config = {0}; - struct wrx_dma_channel_config wrx_dma_channel_config = {0}; - struct htu_entry htu_entry = {0}; - struct htu_result htu_result = {0}; - struct htu_mask htu_mask = { set: 0x01, - clp: 0x01, - pid_mask: 0x00, - vpi_mask: 0x00, - vci_mask: 0x00, - pti_mask: 0x00, - clear: 0x00}; - - /* - * General Registers - */ - *CFG_WRX_HTUTS = MAX_PVC_NUMBER + OAM_HTU_ENTRY_NUMBER; - *CFG_WRX_QNUM = MAX_QUEUE_NUMBER; - *CFG_WRX_DCHNUM = RX_DMA_CH_TOTAL; - *WRX_DMACH_ON = (1 << RX_DMA_CH_TOTAL) - 1; - *WRX_HUNT_BITTH = DEFAULT_RX_HUNT_BITTH; - - /* - * WRX Queue Configuration Table - */ - wrx_queue_config.uumask = 0; - wrx_queue_config.cpimask = 0; - wrx_queue_config.uuexp = 0; - wrx_queue_config.cpiexp = 0; - wrx_queue_config.mfs = aal5r_max_packet_size; - wrx_queue_config.oversize = aal5r_max_packet_size; - wrx_queue_config.undersize = aal5r_min_packet_size; - wrx_queue_config.errdp = aal5r_drop_error_packet; - wrx_queue_config.dmach = RX_DMA_CH_AAL; - for ( i = 0; i < MAX_QUEUE_NUMBER; i++ ) - *WRX_QUEUE_CONFIG(i) = wrx_queue_config; - WRX_QUEUE_CONFIG(OAM_RX_QUEUE)->dmach = RX_DMA_CH_OAM; - - /* - * WRX DMA Channel Configuration Table - */ - wrx_dma_channel_config.chrl = 0; - wrx_dma_channel_config.clp1th = dma_rx_clp1_descriptor_threshold; - wrx_dma_channel_config.mode = 0; - wrx_dma_channel_config.rlcfg = 0; - - wrx_dma_channel_config.deslen = RX_DMA_CH_OAM_DESC_LEN; - wrx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.oam_desc >> 2) & 0x0FFFFFFF; - *WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_OAM) = wrx_dma_channel_config; - - wrx_dma_channel_config.deslen = dma_rx_descriptor_length; - wrx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.aal_desc >> 2) & 0x0FFFFFFF; - *WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_AAL) = wrx_dma_channel_config; - - /* - * HTU Tables - */ - for ( i = 0; i < MAX_PVC_NUMBER; i++ ) - { - htu_result.qid = (unsigned int)i; - - *HTU_ENTRY(i + OAM_HTU_ENTRY_NUMBER) = htu_entry; - *HTU_MASK(i + OAM_HTU_ENTRY_NUMBER) = htu_mask; - *HTU_RESULT(i + OAM_HTU_ENTRY_NUMBER) = htu_result; - } - /* OAM HTU Entry */ - htu_entry.vci = 0x03; - htu_mask.pid_mask = 0x03; - htu_mask.vpi_mask = 0xFF; - htu_mask.vci_mask = 0x0000; - htu_mask.pti_mask = 0x07; - htu_result.cellid = OAM_RX_QUEUE; - htu_result.type = 1; - htu_result.ven = 1; - htu_result.qid = OAM_RX_QUEUE; - *HTU_RESULT(OAM_F4_SEG_HTU_ENTRY) = htu_result; - *HTU_MASK(OAM_F4_SEG_HTU_ENTRY) = htu_mask; - *HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY) = htu_entry; - htu_entry.vci = 0x04; - htu_result.cellid = OAM_RX_QUEUE; - htu_result.type = 1; - htu_result.ven = 1; - htu_result.qid = OAM_RX_QUEUE; - *HTU_RESULT(OAM_F4_TOT_HTU_ENTRY) = htu_result; - *HTU_MASK(OAM_F4_TOT_HTU_ENTRY) = htu_mask; - *HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY) = htu_entry; - htu_entry.vci = 0x00; - htu_entry.pti = 0x04; - htu_mask.vci_mask = 0xFFFF; - htu_mask.pti_mask = 0x01; - htu_result.cellid = OAM_RX_QUEUE; - htu_result.type = 1; - htu_result.ven = 1; - htu_result.qid = OAM_RX_QUEUE; - *HTU_RESULT(OAM_F5_HTU_ENTRY) = htu_result; - *HTU_MASK(OAM_F5_HTU_ENTRY) = htu_mask; - *HTU_ENTRY(OAM_F5_HTU_ENTRY) = htu_entry; -#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX - htu_entry.pid = 0x0; - htu_entry.vpi = 0x01; - htu_entry.vci = 0x0001; - htu_entry.pti = 0x00; - htu_mask.pid_mask = 0x0; - htu_mask.vpi_mask = 0x00; - htu_mask.vci_mask = 0x0000; - htu_mask.pti_mask = 0x3; - htu_result.cellid = OAM_RX_QUEUE; - htu_result.type = 1; - htu_result.ven = 1; - htu_result.qid = OAM_RX_QUEUE; - *HTU_RESULT(OAM_ARQ_HTU_ENTRY) = htu_result; - *HTU_MASK(OAM_ARQ_HTU_ENTRY) = htu_mask; - *HTU_ENTRY(OAM_ARQ_HTU_ENTRY) = htu_entry; -#endif -} - -static INLINE void init_tx_tables(void) -{ - int i; - struct wtx_queue_config wtx_queue_config = {0}; - struct wtx_dma_channel_config wtx_dma_channel_config = {0}; - struct wtx_port_config wtx_port_config = { res1: 0, - qid: 0, - qsben: 1}; - - /* - * General Registers - */ - *CFG_WTX_DCHNUM = MAX_TX_DMA_CHANNEL_NUMBER; - *WTX_DMACH_ON = ((1 << MAX_TX_DMA_CHANNEL_NUMBER) - 1) ^ ((1 << FIRST_QSB_QID) - 1); - *CFG_WRDES_DELAY = write_descriptor_delay; - - /* - * WTX Port Configuration Table - */ - for ( i = 0; i < ATM_PORT_NUMBER; i++ ) - *WTX_PORT_CONFIG(i) = wtx_port_config; - - /* - * WTX Queue Configuration Table - */ - wtx_queue_config.type = 0x0; - wtx_queue_config.qsben = 1; - wtx_queue_config.sbid = 0; - for ( i = 0; i < MAX_TX_DMA_CHANNEL_NUMBER; i++ ) - *WTX_QUEUE_CONFIG(i) = wtx_queue_config; - - /* - * WTX DMA Channel Configuration Table - */ - wtx_dma_channel_config.mode = 0; - wtx_dma_channel_config.deslen = 0; - wtx_dma_channel_config.desba = 0; - for ( i = 0; i < FIRST_QSB_QID; i++ ) - *WTX_DMA_CHANNEL_CONFIG(i) = wtx_dma_channel_config; - /* normal connection */ - wtx_dma_channel_config.deslen = dma_tx_descriptor_length; - for ( ; i < MAX_TX_DMA_CHANNEL_NUMBER ; i++ ) { - wtx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.conn[i - FIRST_QSB_QID].tx_desc >> 2) & 0x0FFFFFFF; - *WTX_DMA_CHANNEL_CONFIG(i) = wtx_dma_channel_config; - } -} - - - -/* - * #################################### - * Global Function - * #################################### - */ - -static int atm_showtime_enter(struct port_cell_info *port_cell, void *xdata_addr) -{ - int i, j; - - ASSERT(port_cell != NULL, "port_cell is NULL"); - ASSERT(xdata_addr != NULL, "xdata_addr is NULL"); - - for ( j = 0; j < ATM_PORT_NUMBER && j < port_cell->port_num; j++ ) - if ( port_cell->tx_link_rate[j] > 0 ) - break; - for ( i = 0; i < ATM_PORT_NUMBER && i < port_cell->port_num; i++ ) - g_atm_priv_data.port[i].tx_max_cell_rate = port_cell->tx_link_rate[i] > 0 ? port_cell->tx_link_rate[i] : port_cell->tx_link_rate[j]; - - qsb_global_set(); - - for ( i = 0; i < MAX_PVC_NUMBER; i++ ) - if ( g_atm_priv_data.conn[i].vcc != NULL ) - set_qsb(g_atm_priv_data.conn[i].vcc, &g_atm_priv_data.conn[i].vcc->qos, i); - - // TODO: ReTX set xdata_addr - g_xdata_addr = xdata_addr; - - g_showtime = 1; - -#if defined(CONFIG_VR9) - IFX_REG_W32(0x0F, UTP_CFG); -#endif - - pr_debug("enter showtime, cell rate: 0 - %d, 1 - %d, xdata addr: 0x%08x\n", g_atm_priv_data.port[0].tx_max_cell_rate, g_atm_priv_data.port[1].tx_max_cell_rate, (unsigned int)g_xdata_addr); - - return IFX_SUCCESS; -} - -static int atm_showtime_exit(void) -{ -#if defined(CONFIG_VR9) - IFX_REG_W32(0x00, UTP_CFG); -#endif - - g_showtime = 0; - - // TODO: ReTX clean state - g_xdata_addr = NULL; - - pr_debug("leave showtime\n"); - - return IFX_SUCCESS; -} - - - -/* - * #################################### - * Init/Cleanup API - * #################################### - */ - -/* - * Description: - * Initialize global variables, PP32, comunication structures, register IRQ - * and register device. - * Input: - * none - * Output: - * 0 --- successful - * else --- failure, usually it is negative value of error code - */ -static int __devinit ifx_atm_init(void) -{ - int ret; - int port_num; - struct port_cell_info port_cell = {0}; - int i, j; - char ver_str[256]; - -#ifdef MODULE - reset_ppe(); -#endif - - check_parameters(); - - ret = init_priv_data(); - if ( ret != IFX_SUCCESS ) { - err("INIT_PRIV_DATA_FAIL"); - goto INIT_PRIV_DATA_FAIL; - } - - ifx_atm_init_chip(); - init_rx_tables(); - init_tx_tables(); - - /* create devices */ - for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ ) { - g_atm_priv_data.port[port_num].dev = atm_dev_register("ifxmips_atm", &g_ifx_atm_ops, -1, NULL); - if ( !g_atm_priv_data.port[port_num].dev ) { - err("failed to register atm device %d!", port_num); - ret = -EIO; - goto ATM_DEV_REGISTER_FAIL; - } - else { - g_atm_priv_data.port[port_num].dev->ci_range.vpi_bits = 8; - g_atm_priv_data.port[port_num].dev->ci_range.vci_bits = 16; - g_atm_priv_data.port[port_num].dev->link_rate = g_atm_priv_data.port[port_num].tx_max_cell_rate; - g_atm_priv_data.port[port_num].dev->dev_data = (void*)port_num; - } - } - - /* register interrupt handler */ - ret = request_irq(PPE_MAILBOX_IGU1_INT, mailbox_irq_handler, IRQF_DISABLED, "atm_mailbox_isr", &g_atm_priv_data); - if ( ret ) { - if ( ret == -EBUSY ) { - err("IRQ may be occupied by other driver, please reconfig to disable it."); - } - else { - err("request_irq fail"); - } - goto REQUEST_IRQ_PPE_MAILBOX_IGU1_INT_FAIL; - } - disable_irq(PPE_MAILBOX_IGU1_INT); - - ret = ifx_pp32_start(0); - if ( ret ) { - err("ifx_pp32_start fail!"); - goto PP32_START_FAIL; - } - - port_cell.port_num = ATM_PORT_NUMBER; - ifx_mei_atm_showtime_check(&g_showtime, &port_cell, &g_xdata_addr); - if ( g_showtime ) { - for ( i = 0; i < ATM_PORT_NUMBER; i++ ) - if ( port_cell.tx_link_rate[i] != 0 ) - break; - for ( j = 0; j < ATM_PORT_NUMBER; j++ ) - g_atm_priv_data.port[j].tx_max_cell_rate = port_cell.tx_link_rate[j] != 0 ? port_cell.tx_link_rate[j] : port_cell.tx_link_rate[i]; - } - - qsb_global_set(); - validate_oam_htu_entry(); - - /* create proc file */ - proc_file_create(); - - ifx_mei_atm_showtime_enter = atm_showtime_enter; - ifx_mei_atm_showtime_exit = atm_showtime_exit; - - ifx_atm_version(ver_str); - printk(KERN_INFO "%s", ver_str); - - printk("ifxmips_atm: ATM init succeed\n"); - - return IFX_SUCCESS; - -PP32_START_FAIL: - free_irq(PPE_MAILBOX_IGU1_INT, &g_atm_priv_data); -REQUEST_IRQ_PPE_MAILBOX_IGU1_INT_FAIL: -ATM_DEV_REGISTER_FAIL: - while ( port_num-- > 0 ) - atm_dev_deregister(g_atm_priv_data.port[port_num].dev); -INIT_PRIV_DATA_FAIL: - clear_priv_data(); - printk("ifxmips_atm: ATM init failed\n"); - return ret; -} - -/* - * Description: - * Release memory, free IRQ, and deregister device. - * Input: - * none - * Output: - * none - */ -static void __exit ifx_atm_exit(void) -{ - int port_num; - - ifx_mei_atm_showtime_enter = NULL; - ifx_mei_atm_showtime_exit = NULL; - - proc_file_delete(); - - invalidate_oam_htu_entry(); - - ifx_pp32_stop(0); - - free_irq(PPE_MAILBOX_IGU1_INT, &g_atm_priv_data); - - for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ ) - atm_dev_deregister(g_atm_priv_data.port[port_num].dev); - - ifx_atm_uninit_chip(); - - clear_priv_data(); -} - -module_init(ifx_atm_init); -module_exit(ifx_atm_exit); -MODULE_LICENSE("Dual BSD/GPL"); diff --git a/package/lqdsl/src/ifxmips_atm_core.h b/package/lqdsl/src/ifxmips_atm_core.h deleted file mode 100644 index 8f0a3ebfba..0000000000 --- a/package/lqdsl/src/ifxmips_atm_core.h +++ /dev/null @@ -1,249 +0,0 @@ -/****************************************************************************** -** -** FILE NAME : ifxmips_atm_core.h -** PROJECT : UEIP -** MODULES : ATM -** -** DATE : 7 Jul 2009 -** AUTHOR : Xu Liang -** DESCRIPTION : ATM driver header file (core functions) -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 17 JUN 2009 Xu Liang Init Version -*******************************************************************************/ - -#ifndef IFXMIPS_ATM_CORE_H -#define IFXMIPS_ATM_CORE_H - - -#include "ifxmips_compat.h" -#include "ifx_atm.h" -#include "ifxmips_atm_ppe_common.h" -#include "ifxmips_atm_fw_regs_common.h" - - - -/* - * #################################### - * Definition - * #################################### - */ - -/* - * Compile Options - */ - -#define ENABLE_DEBUG 1 - -#define ENABLE_ASSERT 1 - -#define INLINE - -#define DEBUG_DUMP_SKB 1 - -#define DEBUG_QOS 1 - -#define ENABLE_DBG_PROC 1 - -#define ENABLE_FW_PROC 1 - -#ifdef CONFIG_IFX_ATM_TASKLET - #define ENABLE_TASKLET 1 -#endif - - -/* - * Debug/Assert/Error Message - */ - -#define DBG_ENABLE_MASK_ERR (1 << 0) -#define DBG_ENABLE_MASK_DEBUG_PRINT (1 << 1) -#define DBG_ENABLE_MASK_ASSERT (1 << 2) -#define DBG_ENABLE_MASK_DUMP_SKB_RX (1 << 8) -#define DBG_ENABLE_MASK_DUMP_SKB_TX (1 << 9) -#define DBG_ENABLE_MASK_DUMP_QOS (1 << 10) -#define DBG_ENABLE_MASK_DUMP_INIT (1 << 11) -#define DBG_ENABLE_MASK_ALL (DBG_ENABLE_MASK_ERR | DBG_ENABLE_MASK_DEBUG_PRINT | DBG_ENABLE_MASK_ASSERT | DBG_ENABLE_MASK_DUMP_SKB_RX | DBG_ENABLE_MASK_DUMP_SKB_TX | DBG_ENABLE_MASK_DUMP_QOS | DBG_ENABLE_MASK_DUMP_INIT) - -#define err(format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ERR) ) printk(KERN_ERR __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) - -#if defined(ENABLE_DEBUG) && ENABLE_DEBUG - #undef dbg - #define dbg(format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DEBUG_PRINT) ) printk(KERN_WARNING __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) -#else - #if !defined(dbg) - #define dbg(format, arg...) - #endif -#endif - -#if defined(ENABLE_ASSERT) && ENABLE_ASSERT - #define ASSERT(cond, format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ASSERT) && !(cond) ) printk(KERN_ERR __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) -#else - #define ASSERT(cond, format, arg...) -#endif - - -/* - * Constants - */ -#define DEFAULT_TX_LINK_RATE 3200 // in cells - -/* - * ATM Port, QSB Queue, DMA RX/TX Channel Parameters - */ -#define ATM_PORT_NUMBER 2 -#define MAX_QUEUE_NUMBER 16 -#define OAM_RX_QUEUE 15 -#define QSB_RESERVE_TX_QUEUE 0 -#define FIRST_QSB_QID 1 -#define MAX_PVC_NUMBER (MAX_QUEUE_NUMBER - FIRST_QSB_QID) -#define MAX_RX_DMA_CHANNEL_NUMBER 8 -#define MAX_TX_DMA_CHANNEL_NUMBER 16 -#define DATA_BUFFER_ALIGNMENT EMA_ALIGNMENT -#define DESC_ALIGNMENT 8 -#define DEFAULT_RX_HUNT_BITTH 4 - -/* - * RX DMA Channel Allocation - */ -#define RX_DMA_CH_OAM 0 -#define RX_DMA_CH_AAL 1 -#define RX_DMA_CH_TOTAL 2 -#define RX_DMA_CH_OAM_DESC_LEN 32 -#define RX_DMA_CH_OAM_BUF_SIZE (CELL_SIZE & ~15) -#define RX_DMA_CH_AAL_BUF_SIZE (2048 - 48) - -/* - * OAM Constants - */ -#define OAM_HTU_ENTRY_NUMBER 3 -#define OAM_F4_SEG_HTU_ENTRY 0 -#define OAM_F4_TOT_HTU_ENTRY 1 -#define OAM_F5_HTU_ENTRY 2 -#define OAM_F4_CELL_ID 0 -#define OAM_F5_CELL_ID 15 -//#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX -// #undef OAM_HTU_ENTRY_NUMBER -// #define OAM_HTU_ENTRY_NUMBER 4 -// #define OAM_ARQ_HTU_ENTRY 3 -//#endif - -/* - * RX Frame Definitions - */ -#define MAX_RX_PACKET_ALIGN_BYTES 3 -#define MAX_RX_PACKET_PADDING_BYTES 3 -#define RX_INBAND_TRAILER_LENGTH 8 -#define MAX_RX_FRAME_EXTRA_BYTES (RX_INBAND_TRAILER_LENGTH + MAX_RX_PACKET_ALIGN_BYTES + MAX_RX_PACKET_PADDING_BYTES) - -/* - * TX Frame Definitions - */ -#define MAX_TX_HEADER_ALIGN_BYTES 12 -#define MAX_TX_PACKET_ALIGN_BYTES 3 -#define MAX_TX_PACKET_PADDING_BYTES 3 -#define TX_INBAND_HEADER_LENGTH 8 -#define MAX_TX_FRAME_EXTRA_BYTES (TX_INBAND_HEADER_LENGTH + MAX_TX_HEADER_ALIGN_BYTES + MAX_TX_PACKET_ALIGN_BYTES + MAX_TX_PACKET_PADDING_BYTES) - -/* - * Cell Constant - */ -#define CELL_SIZE ATM_AAL0_SDU - - - -/* - * #################################### - * Data Type - * #################################### - */ - -typedef struct { - unsigned int h; - unsigned int l; -} ppe_u64_t; - -struct port { - unsigned int tx_max_cell_rate; - unsigned int tx_current_cell_rate; - - struct atm_dev *dev; -}; - -struct connection { - struct atm_vcc *vcc; - - volatile struct tx_descriptor - *tx_desc; - unsigned int tx_desc_pos; - struct sk_buff **tx_skb; - - unsigned int aal5_vcc_crc_err; /* number of packets with CRC error */ - unsigned int aal5_vcc_oversize_sdu; /* number of packets with oversize error */ - - unsigned int port; -}; - -struct atm_priv_data { - unsigned long conn_table; - struct connection conn[MAX_PVC_NUMBER]; - - volatile struct rx_descriptor - *aal_desc; - unsigned int aal_desc_pos; - - volatile struct rx_descriptor - *oam_desc; - unsigned char *oam_buf; - unsigned int oam_desc_pos; - - struct port port[ATM_PORT_NUMBER]; - - unsigned int wrx_pdu; /* successfully received AAL5 packet */ - unsigned int wrx_drop_pdu; /* AAL5 packet dropped by driver on RX */ - unsigned int wtx_pdu; /* successfully tranmitted AAL5 packet */ - unsigned int wtx_err_pdu; /* error AAL5 packet */ - unsigned int wtx_drop_pdu; /* AAL5 packet dropped by driver on TX */ - - ppe_u64_t wrx_total_byte; - ppe_u64_t wtx_total_byte; - unsigned int prev_wrx_total_byte; - unsigned int prev_wtx_total_byte; - - void *aal_desc_base; - void *oam_desc_base; - void *oam_buf_base; - void *tx_desc_base; - void *tx_skb_base; -}; - - - -/* - * #################################### - * Declaration - * #################################### - */ - -extern unsigned int ifx_atm_dbg_enable; - -extern void ifx_atm_get_fw_ver(unsigned int *major, unsigned int *minor); - -extern void ifx_atm_init_chip(void); -extern void ifx_atm_uninit_chip(void); - -extern int ifx_pp32_start(int pp32); -extern void ifx_pp32_stop(int pp32); - - - -#endif // IFXMIPS_ATM_CORE_H diff --git a/package/lqdsl/src/ifxmips_atm_danube.c b/package/lqdsl/src/ifxmips_atm_danube.c deleted file mode 100644 index 5698e0877c..0000000000 --- a/package/lqdsl/src/ifxmips_atm_danube.c +++ /dev/null @@ -1,271 +0,0 @@ -/****************************************************************************** -** -** FILE NAME : ifxmips_atm_danube.c -** PROJECT : UEIP -** MODULES : ATM -** -** DATE : 7 Jul 2009 -** AUTHOR : Xu Liang -** DESCRIPTION : ATM driver common source file (core functions) -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 07 JUL 2009 Xu Liang Init Version -*******************************************************************************/ - - - -/* - * #################################### - * Head File - * #################################### - */ - -/* - * Common Head File - */ -#include -#include -#include -#include -#include -#include -#include -#include -#include - -/* - * Chip Specific Head File - */ -#include -#include -#include "ifxmips_compat.h" -#include "ifxmips_atm_core.h" -#include "ifxmips_atm_fw_danube.h" - - - -/* - * #################################### - * Definition - * #################################### - */ - -/* - * EMA Settings - */ -#define EMA_CMD_BUF_LEN 0x0040 -#define EMA_CMD_BASE_ADDR (0x00001580 << 2) -#define EMA_DATA_BUF_LEN 0x0100 -#define EMA_DATA_BASE_ADDR (0x00001900 << 2) -#define EMA_WRITE_BURST 0x2 -#define EMA_READ_BURST 0x2 - - - -/* - * #################################### - * Declaration - * #################################### - */ - -/* - * Hardware Init/Uninit Functions - */ -static inline void init_pmu(void); -static inline void uninit_pmu(void); -static inline void init_ema(void); -static inline void init_mailbox(void); -static inline void init_atm_tc(void); -static inline void clear_share_buffer(void); - - - -/* - * #################################### - * Local Variable - * #################################### - */ - - - -/* - * #################################### - * Local Function - * #################################### - */ - -static inline void init_pmu(void) -{ - //*(unsigned long *)0xBF10201C &= ~((1 << 15) | (1 << 13) | (1 << 9)); - PPE_TOP_PMU_SETUP(IFX_PMU_ENABLE); - PPE_SLL01_PMU_SETUP(IFX_PMU_ENABLE); - PPE_TC_PMU_SETUP(IFX_PMU_ENABLE); - PPE_EMA_PMU_SETUP(IFX_PMU_ENABLE); - PPE_QSB_PMU_SETUP(IFX_PMU_ENABLE); - PPE_TPE_PMU_SETUP(IFX_PMU_ENABLE); - DSL_DFE_PMU_SETUP(IFX_PMU_ENABLE); -} - -static inline void uninit_pmu(void) -{ - PPE_SLL01_PMU_SETUP(IFX_PMU_DISABLE); - PPE_TC_PMU_SETUP(IFX_PMU_DISABLE); - PPE_EMA_PMU_SETUP(IFX_PMU_DISABLE); - PPE_QSB_PMU_SETUP(IFX_PMU_DISABLE); - PPE_TPE_PMU_SETUP(IFX_PMU_DISABLE); - DSL_DFE_PMU_SETUP(IFX_PMU_DISABLE); - PPE_TOP_PMU_SETUP(IFX_PMU_DISABLE); -} - -static inline void init_ema(void) -{ - IFX_REG_W32((EMA_CMD_BUF_LEN << 16) | (EMA_CMD_BASE_ADDR >> 2), EMA_CMDCFG); - IFX_REG_W32((EMA_DATA_BUF_LEN << 16) | (EMA_DATA_BASE_ADDR >> 2), EMA_DATACFG); - IFX_REG_W32(0x000000FF, EMA_IER); - IFX_REG_W32(EMA_READ_BURST | (EMA_WRITE_BURST << 2), EMA_CFG); -} - -static inline void init_mailbox(void) -{ - IFX_REG_W32(0xFFFFFFFF, MBOX_IGU1_ISRC); - IFX_REG_W32(0x00000000, MBOX_IGU1_IER); - IFX_REG_W32(0xFFFFFFFF, MBOX_IGU3_ISRC); - IFX_REG_W32(0x00000000, MBOX_IGU3_IER); -} - -static inline void init_atm_tc(void) -{ - // for ReTX expansion in future - //*FFSM_CFG0 = SET_BITS(*FFSM_CFG0, 5, 0, 6); // pnum = 6 - //*FFSM_CFG1 = SET_BITS(*FFSM_CFG1, 5, 0, 6); // pnum = 6 -} - -static inline void clear_share_buffer(void) -{ - volatile u32 *p = SB_RAM0_ADDR(0); - unsigned int i; - - for ( i = 0; i < SB_RAM0_DWLEN + SB_RAM1_DWLEN + SB_RAM2_DWLEN + SB_RAM3_DWLEN; i++ ) - IFX_REG_W32(0, p++); -} - -/* - * Description: - * Download PPE firmware binary code. - * Input: - * src --- u32 *, binary code buffer - * dword_len --- unsigned int, binary code length in DWORD (32-bit) - * Output: - * int --- IFX_SUCCESS: Success - * else: Error Code - */ -static inline int pp32_download_code(u32 *code_src, unsigned int code_dword_len, u32 *data_src, unsigned int data_dword_len) -{ - volatile u32 *dest; - - if ( code_src == 0 || ((unsigned long)code_src & 0x03) != 0 - || data_src == 0 || ((unsigned long)data_src & 0x03) != 0 ) - return IFX_ERROR; - - if ( code_dword_len <= CDM_CODE_MEMORYn_DWLEN(0) ) - IFX_REG_W32(0x00, CDM_CFG); - else - IFX_REG_W32(0x02, CDM_CFG); - - /* copy code */ - dest = CDM_CODE_MEMORY(0, 0); - while ( code_dword_len-- > 0 ) - IFX_REG_W32(*code_src++, dest++); - - /* copy data */ - dest = CDM_DATA_MEMORY(0, 0); - while ( data_dword_len-- > 0 ) - IFX_REG_W32(*data_src++, dest++); - - return IFX_SUCCESS; -} - - - -/* - * #################################### - * Global Function - * #################################### - */ - -extern void ifx_atm_get_fw_ver(unsigned int *major, unsigned int *minor) -{ - ASSERT(major != NULL, "pointer is NULL"); - ASSERT(minor != NULL, "pointer is NULL"); - - *major = ATM_FW_VER_MAJOR; - *minor = ATM_FW_VER_MINOR; -} - -void ifx_atm_init_chip(void) -{ - init_pmu(); - - init_ema(); - - init_mailbox(); - - init_atm_tc(); - - clear_share_buffer(); -} - -void ifx_atm_uninit_chip(void) -{ - uninit_pmu(); -} - -/* - * Description: - * Initialize and start up PP32. - * Input: - * none - * Output: - * int --- IFX_SUCCESS: Success - * else: Error Code - */ -int ifx_pp32_start(int pp32) -{ - int ret; - - /* download firmware */ - ret = pp32_download_code(firmware_binary_code, sizeof(firmware_binary_code) / sizeof(*firmware_binary_code), firmware_binary_data, sizeof(firmware_binary_data) / sizeof(*firmware_binary_data)); - if ( ret != IFX_SUCCESS ) - return ret; - - /* run PP32 */ - IFX_REG_W32(DBG_CTRL_START_SET(1), PP32_DBG_CTRL); - - /* idle for a while to let PP32 init itself */ - udelay(10); - - return IFX_SUCCESS; -} - -/* - * Description: - * Halt PP32. - * Input: - * none - * Output: - * none - */ -void ifx_pp32_stop(int pp32) -{ - /* halt PP32 */ - IFX_REG_W32(DBG_CTRL_STOP_SET(1), PP32_DBG_CTRL); -} diff --git a/package/lqdsl/src/ifxmips_atm_fw_danube.h b/package/lqdsl/src/ifxmips_atm_fw_danube.h deleted file mode 100644 index c36c96845c..0000000000 --- a/package/lqdsl/src/ifxmips_atm_fw_danube.h +++ /dev/null @@ -1,429 +0,0 @@ -#ifndef IFXMIPS_ATM_FW_DANUBE_H -#define IFXMIPS_ATM_FW_DANUBE_H - - -/****************************************************************************** -** -** FILE NAME : ifxmips_atm_fw_danube.h -** PROJECT : Danube -** MODULES : ATM (ADSL) -** -** DATE : 1 AUG 2005 -** AUTHOR : Xu Liang -** DESCRIPTION : ATM Driver (PP32 Firmware) -** COPYRIGHT : Copyright (c) 2006 -** Infineon Technologies AG -** Am Campeon 1-12, 85579 Neubiberg, Germany -** -** 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. -** -** HISTORY -** $Date $Author $Comment -** 4 AUG 2005 Xu Liang Initiate Version -** 23 OCT 2006 Xu Liang Add GPL header. -*******************************************************************************/ - - -#define ATM_FW_VER_MAJOR 0 -#define ATM_FW_VER_MINOR 1 - - -static unsigned int firmware_binary_code[] = { - 0x800004A0, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x8000FFC8, 0x00000000, 0x00000000, 0x00000000, - 0xC1000002, 0xD90C0000, 0xC2000002, 0xDA080001, 0x80004710, 0xC2000000, 0xDA080001, 0x80003D98, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x80003D50, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x80004F18, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x80003C50, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0xC0400000, 0xC0004840, 0xC8840000, 0x800043D0, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0xC0400002, 0xC0004840, 0xC8840000, 0x80004350, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0xC3C00004, 0xDBC80001, 0xC10C0002, 0xD90C0000, 0x8000FEC8, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0xC10E0002, 0xD90C0000, 0xC0004808, 0xC8400000, 0x80004380, 0x00000000, 0x00000000, 0x00000000, - 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, - 0xC3E1FFFE, 0x597DFFFE, 0x593DFE14, 0x900004D9, 0x00000000, 0x00000000, 0x00000000, 0x90CC0481, - 0x00000000, 0x00000000, 0x00000000, 0xC3C00000, 0xDBC80001, 0xC1400008, 0xC1900000, 0x71948000, - 0x15000100, 0xC140000A, 0xC1900002, 0x71948000, 0x15000100, 0xC140000C, 0xC1900004, 0x71948000, - 0x15000100, 0xC1400004, 0xC1900006, 0x71948000, 0x15000100, 0xC1400006, 0xC1900008, 0x71948000, - 0x15000100, 0xC140000E, 0xC190000A, 0x71948000, 0x15000100, 0xC1400000, 0xC190000C, 0x71948000, - 0x15000100, 0xC1400002, 0xC190000E, 0x71948000, 0x15000100, 0xC0400000, 0xC11C0000, 0xC000082C, - 0xCD040E08, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0400002, 0xC11C0000, 0xC000082C, 0xCD040E08, - 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0000824, 0x00000000, 0xCBC00001, 0xCB800001, 0xCB400001, - 0xCB000000, 0xC0004878, 0x5BFC4000, 0xCFC00001, 0x5BB84000, 0xCF800001, 0x5B744000, 0xCF400001, - 0x5B304000, 0xCF000000, 0xC0000A10, 0x00000000, 0xCBC00001, 0xCB800000, 0xC0004874, 0x5BFC4000, - 0xCFC00001, 0x5BB84000, 0xCF800000, 0xC30001FE, 0xC000140A, 0xCF000000, 0xC3000000, 0x7F018000, - 0xC000042E, 0xCF000000, 0xC000040E, 0xCF000000, 0xC3C1FFFE, 0xC000490E, 0xCFC00080, 0xC000492C, - 0xCFC00080, 0xC0004924, 0xCFC00040, 0xC0004912, 0xCFC00040, 0xC0004966, 0xCFC00040, 0xC0004968, - 0xCFC00080, 0xC000496A, 0xCFC00080, 0xC3C00000, 0xC2800020, 0xC3000000, 0x7F018000, 0x6FF88000, - 0x6FD44000, 0x4395C000, 0x5BB84A00, 0x5838000A, 0xCF000000, 0x5BFC0002, 0xB7E8FFA8, 0x00000000, - 0xC3C00000, 0xC2800010, 0x6FF86000, 0x47F9C000, 0x5BB84C80, 0xC3400000, 0x58380004, 0xCB420080, - 0x00000000, 0x58380008, 0xCF400080, 0x5BFC0002, 0xB7E8FF90, 0x00000000, 0xC3C00000, 0xC2800020, - 0xC348001E, 0xC3000000, 0x7F018000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, - 0x58380008, 0xCF400420, 0x5838000A, 0xCF000000, 0x5BFC0002, 0xB7E8FF90, 0x00000000, 0x00000000, - 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x80000518, 0x00000000, 0x80002118, 0x00000000, - 0x8000FFC8, 0xC0004958, 0xC8400000, 0x00000000, 0xC3C00002, 0x7BC42000, 0xCC400000, 0xC0004848, - 0xCB840000, 0xC000495C, 0xCAC40000, 0xC0004844, 0xC8840000, 0x46F90000, 0x8400FF6A, 0xC000487C, - 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCA000000, 0xC0001624, 0xCB040000, 0xA63C005A, - 0x00000000, 0x00000000, 0xA71EFF02, 0x00000000, 0xC0000824, 0xCA840000, 0x6CA08000, 0x6CA42000, - 0x46610000, 0x42290000, 0xC35E0002, 0xC6340068, 0xC0001624, 0xCF440080, 0xC2000000, 0xC161FFFE, - 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004844, 0xC8840000, 0xC000082C, 0xCA040040, 0x00000000, - 0x00000000, 0x58880002, 0xB608FFF8, 0x00000000, 0xC0800000, 0xC0004844, 0xCC840040, 0x5AEC0002, - 0xC000495C, 0xCEC40000, 0x5E6C0006, 0x84000048, 0xC0004848, 0xCB840000, 0xC0000838, 0xC2500002, - 0xCE440808, 0x5FB80002, 0xC0004848, 0xCF840000, 0x5EEC0002, 0xC000495C, 0xCEC40000, 0x00000000, - 0xC121FFFE, 0x5911FE14, 0x15000000, 0x8000FD80, 0xC000495A, 0xC8400000, 0x00000000, 0xC3C00002, - 0x7BC42000, 0xCC400000, 0xC0004960, 0xCAC40000, 0x00000000, 0x00000000, 0x5EEC0000, 0x840000F2, - 0x00000000, 0xB6FC0030, 0xC0001600, 0xCA040000, 0x00000000, 0x00000000, 0xA61E00B2, 0x6FE90000, - 0xC0000A28, 0xCE840808, 0xC2C00000, 0xC2800004, 0xB6E80080, 0xC0001604, 0xCA840000, 0xC0004960, - 0xCEC40000, 0xA69EFCA2, 0x00000000, 0x6FE90000, 0xC0000A28, 0xCE840808, 0xC2C00002, 0xC0001600, - 0xCA040000, 0x00000000, 0x00000000, 0xA61E000A, 0x6FE90000, 0xC0000A28, 0xCE840808, 0xC2C00000, - 0xC0001604, 0xCA840000, 0xC0004960, 0xCEC40000, 0xA69EFC0A, 0xC2400000, 0xC0000A14, 0xCA440030, - 0x00000000, 0x00000000, 0x46E52000, 0xA4400000, 0xC2800000, 0xDFEB0031, 0x8000FFF8, 0xDFEA0031, - 0xB668FB82, 0x00000000, 0xC00048A0, 0xCB040000, 0xC0000A10, 0xCA840000, 0x6F208000, 0x6F242000, - 0x46610000, 0x42A10000, 0xC2400000, 0xC0000A14, 0xCA440030, 0xC35E0002, 0xC6340068, 0xC0001604, - 0xCF440080, 0x5B300002, 0xB670FFF8, 0x5AEC0002, 0xC3000000, 0xC00048A0, 0xCF040000, 0xC0004960, - 0xCEC40000, 0x8000FAC0, 0xC0004918, 0xD2800000, 0xC2000000, 0xDF600040, 0x5E600080, 0x8400025A, - 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000480A, 0xCA000000, 0xC0004912, - 0xCA400000, 0xC0004924, 0xCA800000, 0xC0004966, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0x76610000, 0x76A10000, 0x76E10000, 0x840001B2, 0xC0004918, 0xCA400000, 0xC28001FE, - 0x76A10000, 0x5A640002, 0x6A254010, 0x5EE80000, 0x84000002, 0x6AA54000, 0x8000FFF8, 0xC6280000, - 0x62818008, 0xC0004918, 0xCF000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004966, - 0xCA400000, 0xC2000002, 0x6A310000, 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, - 0x5911FE14, 0x15000000, 0x6F346000, 0x4735A000, 0x5B744C80, 0xC2800000, 0x58340006, 0xCA800080, - 0xC2C00000, 0x58340000, 0xCAC000E0, 0xC2400000, 0x5834000A, 0xCA420080, 0x6EA82000, 0x42E9E000, - 0x6F2CA000, 0x42E56000, 0x5AEC1400, 0xC3990040, 0xC7381C20, 0xC6F80068, 0x99005930, 0xDB980000, - 0xDBD80001, 0x00000000, 0xDEA00000, 0x47210000, 0x8400FD68, 0xC0004958, 0xC8400000, 0x00000000, - 0xC3C00002, 0x7BC42000, 0xCC400000, 0xC0004848, 0xCB840000, 0xC0004844, 0xC8840000, 0x5FB80000, - 0x8400F7DA, 0xC0001A1C, 0xCA000000, 0xC2400002, 0x6A452000, 0x76610000, 0x8400F7AA, 0xC000487C, - 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCA000000, 0xC4240000, 0x00000000, 0xA63C17BA, - 0x00000000, 0xC0004878, 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, 0x40100000, 0xCA000000, - 0xC4240000, 0x00000000, 0xC0004934, 0xCE000000, 0xC2800002, 0xC4681C10, 0xC62821D8, 0xC2600010, - 0x5A650040, 0xC0004800, 0xCB400000, 0xC2200400, 0x5A200000, 0xC7601048, 0xC0001220, 0xCE800000, - 0xC0001200, 0xCE400000, 0xC0001202, 0xCE000000, 0xC0001240, 0xCB400000, 0x00000000, 0x00000000, - 0xA754FFC0, 0xC2000000, 0xC7600048, 0xA7520022, 0x00000000, 0x00000000, 0x990060A8, 0xC0004822, - 0xC9400000, 0xC1800002, 0x80001668, 0x58204080, 0xC2000000, 0xCA000020, 0xC2400000, 0xCA414008, - 0xC2800000, 0xCA812008, 0xC2C00000, 0xCAC20020, 0xC0004938, 0xCE000000, 0xC0004920, 0xCE400000, - 0xC0004916, 0xCE800000, 0xC0004922, 0xCEC00000, 0xA6400520, 0x00000000, 0xC0004938, 0xCBC00000, - 0x00000000, 0xC3800000, 0x6FF48000, 0x6FD44000, 0x4355A000, 0x5B744A00, 0x58340000, 0xCB802018, - 0x00000000, 0xC2000000, 0x6FB46000, 0x47B5A000, 0x5B744C80, 0x5834000C, 0xCA000028, 0xC000491A, - 0xCF800000, 0x5E200000, 0x84000452, 0xC2000000, 0xDF610050, 0x5E6001E8, 0x8800FFD0, 0xC2000002, - 0xC2400466, 0xC2A00000, 0x5AA80000, 0xC0001006, 0xCE000000, 0xC0001008, 0xCE400000, 0xC000100A, - 0xCE800000, 0x99005370, 0xC1A0FFFE, 0xC0000824, 0xC9840068, 0xC0004934, 0xCA400000, 0xC2000000, - 0xC2800002, 0x990053B0, 0xDA980000, 0xC6140000, 0xC6580000, 0xC161FFFE, 0x5955FFFE, 0x15400000, - 0x00000000, 0x99005498, 0xC000491A, 0xC9400000, 0x00000000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0xC0004922, 0xCA001120, 0xC3C00000, 0xC3800000, 0xC0004930, 0xCE001120, 0xC0004932, - 0xCBC000E0, 0xC2800000, 0xC000491E, 0xCFC00000, 0xC0004862, 0xCA800068, 0xC3A0001A, 0x5BB94000, - 0xC6B80068, 0xC000491C, 0xCF800000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0x00000000, - 0x00000000, 0x00000000, 0xA8E2FFC8, 0xC2000000, 0xC1220002, 0xD90C0000, 0xDF600040, 0x5E600080, - 0x8400FFDA, 0xC000491C, 0xCA000000, 0xC000491E, 0xCA400000, 0x00000000, 0x00000000, 0x99005930, - 0xDA180000, 0xDA580001, 0x00000000, 0xC2000000, 0xDF610050, 0x5E6001FE, 0x8800FFD0, 0xC0004916, - 0xCA800000, 0xC2C00000, 0xDFEC0050, 0xC2400000, 0x46E52000, 0x84000032, 0x5EA80000, 0x84000022, - 0xC2600002, 0x990060A8, 0xC000482E, 0xC9400000, 0xC1800002, 0x80000018, 0xC2600000, 0x990060A8, - 0xC000482C, 0xC9400000, 0xC1800002, 0xC2000068, 0xC6240080, 0xC0004930, 0xCE400088, 0xC000491A, - 0xC9800000, 0xC0004862, 0xC9400000, 0x6D9C6000, 0x459CE000, 0x59DC4C80, 0x99005790, 0xD9580000, - 0xD9980001, 0xD9D40000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC2000000, 0xDF600040, - 0x5E600080, 0x8400FFD2, 0x00000000, 0xC000491C, 0xCA000000, 0xC000491E, 0xCA400000, 0x00000000, - 0x00000000, 0x99005930, 0xDA180000, 0xDA580001, 0x00000000, 0x800010D0, 0x00000000, 0x990060A8, - 0xC000482A, 0xC9400000, 0xC1800002, 0x800010A0, 0xC0004938, 0xCBC00000, 0x00000000, 0x00000000, - 0x6FF88000, 0x6FD44000, 0x4395C000, 0x5BB84A00, 0x58380008, 0xCA000000, 0x00000000, 0x00000000, - 0xA6000362, 0x00000000, 0xC0004938, 0xCBC00000, 0xC3000000, 0x00000000, 0x6FF88000, 0x6FD44000, - 0x4395C000, 0x5BB84A00, 0x58380000, 0xCB002018, 0xC2000000, 0x58380008, 0xCA020080, 0x5838000C, - 0xCAC00000, 0x5838000E, 0xCA400000, 0xC000491A, 0xCF000000, 0xC0004930, 0xCEC00000, 0xC000493C, - 0xCE000000, 0xC0004932, 0xCE400000, 0x5E200000, 0x84000108, 0xC2800000, 0xA6FE009A, 0x6F206000, - 0x47210000, 0x5A204C80, 0x5820000C, 0xCA800028, 0x00000000, 0x00000000, 0x5EA80000, 0x840001DA, - 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0x99005498, 0xC000491A, 0xC9400000, - 0x00000000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0xC0004930, 0xCAC00000, 0xC0004932, - 0xCA400000, 0xC7EC1120, 0xC0004930, 0xCEC00000, 0x5838000C, 0xCEC00000, 0x58000002, 0xCE400000, - 0xC0004934, 0xCA000000, 0xC2400002, 0x6E642000, 0x6E642000, 0x76252000, 0x84000012, 0xC2400002, - 0x6E684000, 0x58380008, 0xCE800208, 0xA6000000, 0x6E682000, 0x58380008, 0xCE800108, 0xC2400002, - 0x6E642000, 0x76252000, 0x840000D2, 0x58380008, 0xCA000000, 0xC2800000, 0xC2400000, 0xA60200A0, - 0xDBA80000, 0x6F386000, 0x4739C000, 0x5BB84C80, 0x58380004, 0xCA400080, 0x58380002, 0xCA800080, - 0x00000000, 0xDEB80000, 0x46694000, 0x88000048, 0x00000000, 0xC0004824, 0xCA000000, 0xC2400002, - 0x6E640000, 0x5A200002, 0xCE000000, 0x58380008, 0xCE400008, 0x80000000, 0x00000000, 0x80000030, - 0xC0004934, 0xCA000000, 0x00000000, 0x00000000, 0xA6020C4A, 0x00000000, 0x00000000, 0x80000C80, - 0xC2800000, 0xC2000200, 0xC240001A, 0xDF690050, 0x46A14000, 0x46694000, 0x8800FFBA, 0xC2000006, - 0xC2600982, 0x5A643B6E, 0x5838000A, 0xCA800000, 0xC0001006, 0xCE000000, 0xC0001008, 0xCE400000, - 0xC000100A, 0xCE800000, 0x99005370, 0xC1A0FFFE, 0xC0000824, 0xC9840068, 0xC2000000, 0xC0004930, - 0xCA02E010, 0x58380026, 0xCA400000, 0x00000000, 0xC2800000, 0x990053B0, 0xDA980000, 0xC6140000, - 0xC6580000, 0xC0004934, 0xCA000000, 0x00000000, 0x00000000, 0xA6020002, 0x00000000, 0x00000000, - 0x80000300, 0xC0004938, 0xCBC00000, 0xC0004878, 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, - 0x40100000, 0xCA000000, 0xC4240000, 0x00000000, 0x58240018, 0xCA000000, 0x6FF88000, 0x6FD44000, - 0x4395C000, 0x5BB84A00, 0xC3000000, 0xC3400002, 0xC2C00000, 0xC62C0080, 0xC6270040, 0xC0004940, - 0xCE400040, 0xC6260040, 0xC0004942, 0xCE400040, 0xC000493C, 0xCA000000, 0x5EEC0000, 0x84000172, - 0x5A6C0010, 0x46614000, 0x88000178, 0x5A600052, 0x466D4000, 0x88000160, 0x58380006, 0xCA800000, - 0xC0004940, 0xCA000000, 0xC2400000, 0xC6A70040, 0x7E412000, 0x76252000, 0xC2000000, 0xC6A10040, - 0x46610000, 0x84000120, 0xC0004942, 0xCA000000, 0xC2400000, 0xC6A60040, 0x7E412000, 0x76252000, - 0xC2000000, 0xC6A00040, 0x58380002, 0xCA800000, 0x46610000, 0x840000D0, 0xC2400000, 0xC6A60080, - 0x46E50000, 0x880000C2, 0xC2400000, 0xC6A40080, 0x58380008, 0xCA800000, 0x466D0000, 0x880000A2, - 0x00000000, 0xA682FFF8, 0x00000000, 0xC7700B08, 0xA6840078, 0x00000000, 0xC7700A08, 0x80000068, - 0xC7700208, 0xC000493C, 0xCAC00000, 0x80000048, 0xC7700308, 0xC000493C, 0xCAC00000, 0x80000028, - 0xC7700908, 0x80000018, 0xC7700808, 0x80000008, 0xC7700708, 0x8000FFF8, 0xC7700508, 0xC0004944, - 0xCF000000, 0xC000493E, 0xCEC00000, 0xC0004938, 0xCA400000, 0xC000493C, 0xCB800000, 0xC000493E, - 0xCB400000, 0xC3000000, 0x6E608000, 0x6E544000, 0x42150000, 0x5A204A00, 0x5AA00008, 0x58200004, - 0xCB000080, 0xC0004934, 0xCA000000, 0xC2400000, 0xC0004930, 0xCA42E010, 0xC3C00018, 0xA6020078, - 0x00000000, 0x43656000, 0x46F90000, 0x88000038, 0x47AD6000, 0x6EE04010, 0x5BE00004, 0xC2000000, - 0xC6E00010, 0x5E200000, 0x8400002A, 0x5BFC0002, 0x80000018, 0xC3C00004, 0x5A2C0008, 0x46390000, - 0x8800FFFA, 0x5FB80008, 0x6FE04000, 0x42390000, 0x46312000, 0x88000050, 0xC2400000, 0xC0004930, - 0xCA42E010, 0xC2060002, 0xC6800000, 0xCE000308, 0x6FE04000, 0x4631C000, 0x5F700010, 0x4675A000, - 0xC2000000, 0xC6340010, 0xC25A000A, 0xC000491A, 0xCA401C20, 0xC2800000, 0xC0004932, 0xCA8000E0, - 0xC0004862, 0xCA400068, 0x6FA04010, 0x42290000, 0xC000491E, 0xCE000000, 0xC7E41050, 0xC000491C, - 0xCE400000, 0x6FE04000, 0x43A1C000, 0xC000493C, 0xCF800000, 0xC000493E, 0xCF400000, 0xC000493A, - 0xCFC00000, 0x8000FFF0, 0x00000000, 0x00000000, 0x00000000, 0xC2000000, 0xDCE00000, 0xA622FFB8, - 0xC1220002, 0xD90C0000, 0xC0004938, 0xCBC00000, 0xC0004944, 0xCB400000, 0xC0004862, 0xCB000000, - 0xC0004934, 0xCA000000, 0x6FF88000, 0x6FD44000, 0x4395C000, 0x5BB84A00, 0xA6020248, 0xC2400000, - 0x58380008, 0xCA406008, 0xDFE80000, 0xC2218E08, 0x5A21BAF6, 0x46294000, 0x8400000A, 0xC2080002, - 0x7235A000, 0x80000040, 0x5E640000, 0x8400000A, 0xC20C0002, 0x7235A000, 0x80000018, 0xC2000000, - 0xC760E718, 0xC7604220, 0x5E200000, 0x8400025A, 0xC2200002, 0xC0004930, 0xCE001008, 0x990060A8, - 0xC0004828, 0xC9400000, 0xC1800002, 0x58380000, 0xCA000000, 0x00000000, 0x00000000, 0xA6000112, - 0xC0004940, 0xCA800000, 0xC0004942, 0xCA400000, 0xC7600080, 0xC6A01840, 0xC6601040, 0xC000493A, - 0xCA400000, 0xC0004934, 0xCA800000, 0xC0007200, 0x40300000, 0x40240000, 0x5C000004, 0x5EC07400, - 0x8800FFFA, 0x5C000200, 0xCE000000, 0x58000002, 0x5EC07400, 0x8800FFFA, 0x5C000200, 0xCE800000, - 0xC000493E, 0xCA000000, 0xC2400000, 0x5838000C, 0xCE400000, 0x990060A8, 0xC0004830, 0xC9400000, - 0xC6180000, 0xC0004930, 0xC6100080, 0xCD000080, 0x80000090, 0xC2400002, 0x58380008, 0xCE400008, - 0xC0004944, 0xCF400000, 0x80000260, 0xC000493C, 0xCA400000, 0xDFE80000, 0x5A300018, 0xC0007200, - 0x40200000, 0xCA000000, 0x58380008, 0xC6501080, 0xCD001080, 0x5838000A, 0xCE800000, 0x58380026, - 0xCE000000, 0xC0004944, 0xCF400000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0x80000020, - 0x00000000, 0x990060A8, 0xC0004826, 0xC9400000, 0xC1800002, 0x8000FDC0, 0xC2000000, 0xC2400200, - 0xDF600040, 0xB624FFCA, 0xC000491C, 0xCA400000, 0xC000491E, 0xCA800000, 0x99005930, 0xDA580000, - 0xDA980001, 0x00000000, 0xC0004934, 0xCA000000, 0x00000000, 0xC2800000, 0xA6020140, 0xC2400004, - 0xC2000200, 0xDF690050, 0x46A14000, 0x46694000, 0x8800FFC2, 0x00000000, 0xC000491A, 0xC9800000, - 0xC0004862, 0xC9400000, 0x6D9C6000, 0x459CE000, 0x59DC4C80, 0x99005790, 0xD9580000, 0xD9980001, - 0xD9D40000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC2000000, 0xC2400200, 0xDF600040, - 0xB624FFCA, 0xC000491C, 0xCA400000, 0xC000491E, 0xCA800000, 0x99005930, 0xDA580000, 0xDA980001, - 0x00000000, 0x58380008, 0xCA400000, 0xC2000000, 0xCE000020, 0xC2A1FFFE, 0x5AA9FFFE, 0xCE001080, - 0x5838000A, 0xCE800000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0000838, 0xC2500002, - 0xCE440808, 0xC0004848, 0xCB840000, 0xC2000000, 0xC000082C, 0xCA040030, 0x5FB80002, 0xC0004848, - 0xCF840000, 0x58880002, 0xB608FFF8, 0x00000000, 0xC0800000, 0xC0004844, 0xCC840000, 0x00000000, - 0xC121FFFE, 0x5911FE14, 0x15000000, 0x8000DEC0, 0xC2000000, 0xDF600040, 0x5E200080, 0x84000252, - 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000480C, 0xCA000000, 0xC0004910, - 0xCA400000, 0xC000492C, 0xCA800000, 0xC0004968, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0x76610000, 0x76A10000, 0x762D6000, 0x840001AA, 0xC0004926, 0xCA400000, 0xC201FFFE, - 0x762D6000, 0x5A640002, 0x6AE50010, 0x5F200000, 0x84000002, 0x6A250000, 0x8000FFF8, 0xC6E00000, - 0x62014008, 0xC0004926, 0xCE800000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004968, - 0xCA400000, 0xC2000002, 0x6A290000, 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, - 0x5911FE14, 0x15000000, 0x6EB4A000, 0x6E944000, 0x4575A000, 0x46B5A000, 0x5B744E20, 0x58340002, - 0xC2000000, 0xCA0000E0, 0x5834002E, 0xC2400000, 0xCA400080, 0x6EB0A000, 0x6EBC4000, 0x47F18000, - 0x46B18000, 0x5B300E4E, 0x5B300004, 0x6E642000, 0x4225E000, 0xC39A8024, 0xC7380068, 0xC6B81C20, - 0x99005930, 0xDB980000, 0xDBD80001, 0x00000000, 0xC2000000, 0xDF600040, 0x5E200080, 0x8400028A, - 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA000000, 0xC000492A, - 0xCA400000, 0xC000496A, 0xCB000000, 0xC0004956, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0x76318000, 0x76718000, 0x840001EA, 0xC201FFFE, 0x76318000, 0x5AEC0002, 0x6B2D0010, - 0x5EA00000, 0x84000002, 0x6A2D0000, 0x8000FFF8, 0xC7200000, 0x62016008, 0xC0004956, 0xCEC00000, - 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000496A, 0xCA400000, 0xC2000002, 0x6A2D0000, - 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x6EF4A000, - 0x6ED44000, 0x4575A000, 0x46F5A000, 0x5B744E20, 0x5834000E, 0xC2000000, 0xCA0000E0, 0x58340008, - 0xC2400000, 0xCA420080, 0x5834000C, 0xC2800000, 0xCA832018, 0x6E644010, 0x42250000, 0x4229E000, - 0xC39A8008, 0x58340008, 0xCB809020, 0x58340008, 0xC2800000, 0xCA810018, 0x6EE0A000, 0x6EE44000, - 0x46610000, 0x46E10000, 0x5A200008, 0x5A200E28, 0x42290000, 0xC6380068, 0xC6F81C20, 0x99005930, - 0xDB980000, 0xDBD80001, 0x00000000, 0xC000495A, 0xC8400000, 0x00000000, 0xC3C00002, 0x7BC42000, - 0xCC400000, 0xC0001A1C, 0xCA000000, 0xC2400008, 0x6A452000, 0x76610000, 0x8400D91A, 0xC0000A28, - 0xC3800000, 0xCB840030, 0xC0000A14, 0xC3400000, 0xCB440030, 0xC0004880, 0xCB040000, 0xB7B4D8CA, - 0x58041802, 0xCAC00000, 0xA7000018, 0x00000000, 0x00000000, 0xA6C8D898, 0xC2800000, 0xC6E80020, - 0x80000030, 0xC2800000, 0xC7282020, 0xC000490E, 0xCA400000, 0x6BE9E000, 0x00000000, 0x77E52000, - 0x8400D848, 0x6EA0A000, 0x6E944000, 0x45610000, 0x46A10000, 0x5A204E20, 0x5820000C, 0xCA000000, - 0xC0004946, 0xCE800000, 0xA6220348, 0x00000000, 0xC2200060, 0xC0004948, 0xCE000010, 0xCE001040, - 0xC240000A, 0xC000494A, 0xCE400000, 0xC2B60002, 0xC0004964, 0xCE801B08, 0x99005C00, 0xC00048A0, - 0xC8840000, 0x00000000, 0xC0004946, 0xCBC00000, 0x00000000, 0x00000000, 0x6FF8A000, 0x6FD44000, - 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x990059C0, 0xDBD80000, 0xDB980001, 0x00000000, 0x99005708, - 0xC000491C, 0xC1400000, 0xC9420050, 0xC000491C, 0x99005BB8, 0xC9400001, 0xC9800000, 0x00000000, - 0x99005930, 0xD9580000, 0xD9980001, 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, - 0x990055F8, 0xDBD80000, 0xDB980001, 0xC7D80000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, - 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x58380010, 0xCA000000, 0xC0004874, - 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, 0x40100000, 0xCA400000, 0xC4340000, 0x00000000, - 0xC7400000, 0xCE000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, - 0xC2800002, 0x6ABD4000, 0x72A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, - 0x990060A8, 0xC0004836, 0xC9400000, 0xC1800002, 0x00000000, 0x00000000, 0x00000000, 0xA8E2FFC8, - 0x00000000, 0xC1220002, 0xD90C0000, 0xC2000000, 0xC0000A14, 0xCA040030, 0xC0000A28, 0xC2500002, - 0xCE440808, 0x58880002, 0xB608FFF8, 0xC00048A0, 0xC0800000, 0xCC840000, 0x8000D498, 0xC0004946, - 0xCBC00000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, 0xC2800002, - 0x6ABD4000, 0x72A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x6FF8A000, - 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x58380008, 0xCA000000, 0x5838000C, 0xCA400000, - 0xC3400000, 0xC6340008, 0xC000494E, 0xCF400000, 0xC2800000, 0xC62A0080, 0xC3000000, 0xC6308020, - 0x6F304000, 0x43298000, 0xC000493C, 0xCF000000, 0xC2C00000, 0xC66C0080, 0xC0004950, 0xCEC00000, - 0xC2800000, 0xC66AE028, 0xC0004954, 0xCE800000, 0x5F740000, 0x84000188, 0x5E300028, 0x462D2000, - 0x84000152, 0x462D2000, 0x8800011A, 0x5E300018, 0x462D2000, 0x88000012, 0x462D2000, 0x8400002A, - 0x00000000, 0x800000A8, 0x00000000, 0x99005D40, 0xDBD80000, 0xDB980001, 0xC7800000, 0xC3400002, - 0xC000494E, 0xCF400000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, - 0xC2800002, 0x6ABD4000, 0x7E814000, 0x76A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0xC2200060, 0xC0004948, 0xCE001040, 0xC2000000, 0xC000494C, 0xCE000000, 0x80000068, - 0x00000000, 0x99005D40, 0xDBD80000, 0xDB980001, 0xC7800000, 0x99005F40, 0xDBD80000, 0xDB980001, - 0xC7800000, 0xC2200058, 0xC0004948, 0xCE001040, 0xC2000002, 0xC000494C, 0xCE000000, 0xC2000006, - 0xC0001006, 0xCE000000, 0x5838000A, 0xCA400000, 0xC2200982, 0x5A203B6E, 0xC0001008, 0xCE000000, - 0xC000100A, 0xCE400000, 0xC0004954, 0xCA800000, 0xC200000C, 0xC000494A, 0xCE000000, 0xC0004948, - 0xCE800010, 0xC2B60000, 0xC0004964, 0xCE800000, 0x99005C00, 0xC00048A0, 0xC8840000, 0x00000000, - 0xC0004946, 0xCBC00000, 0xC000494C, 0xCA000000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, - 0x5BB84E20, 0x5E200000, 0x840000E2, 0x00000000, 0x990059C0, 0xDBD80000, 0xDB980001, 0x00000000, - 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC000491C, 0x99005BB8, 0xC9400001, 0xC9800000, - 0x00000000, 0x99005930, 0xD9580000, 0xD9980001, 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, - 0x00000000, 0x990055F8, 0xDBD80000, 0xDB980001, 0xC7D80000, 0x00000000, 0xC121FFFE, 0x5911FE14, - 0x15000000, 0xC000493C, 0xCA800000, 0xC000494E, 0xCAC00000, 0xC3000018, 0xC3400006, 0x5E200000, - 0x84000012, 0xC2800000, 0xC2C00000, 0xC300001E, 0xC3400000, 0xC6AC1080, 0xC72C0420, 0xC76C0818, - 0x58380010, 0xCA800000, 0x58380008, 0xCEC00000, 0xC6280108, 0xC0004874, 0xC8040000, 0x6C908000, - 0x44908000, 0x44908000, 0x40100000, 0xCB000000, 0xC4340000, 0x00000000, 0xC7400000, 0xCE800000, - 0xC0004952, 0xCE800000, 0x00000000, 0x00000000, 0x00000000, 0xA8E2FFC8, 0x00000000, 0xC000494C, - 0xCA000000, 0xC0004950, 0xCAC00000, 0x5E200000, 0x84000052, 0xDFE80000, 0x7E814000, 0x5834001A, - 0xCE800000, 0x990060A8, 0xC0004834, 0xC9400000, 0xC1800002, 0x990060A8, 0xC0004838, 0xC9400000, - 0xC6D80000, 0xC1220002, 0xD90C0000, 0x5E200000, 0x84000028, 0x5838002C, 0xCB000000, 0xDFE80000, - 0x00000000, 0x58380014, 0xCF000000, 0x80000000, 0xC2A1FFFE, 0x5AA9FFFE, 0x5838000A, 0xCE800000, - 0xC3000000, 0xC0000A14, 0xCB040030, 0xC2D00002, 0xC0000A28, 0xCEC40808, 0xC000494E, 0xCA800000, - 0x58880002, 0xB4B0FFF8, 0xC00048A0, 0xC0800000, 0xCC840000, 0x5EA80000, 0x8400013A, 0x5E200000, - 0x84000128, 0xC000493C, 0xCA800000, 0x00000000, 0x00000000, 0x5AA80060, 0xCE800000, 0x99005D40, - 0xDBD80000, 0xDB980001, 0xC7800000, 0x99005F40, 0xDBD80000, 0xDB980001, 0xC7800000, 0xC0004952, - 0xCAC00000, 0x58380000, 0xCA800000, 0xC30C0002, 0xC7F00020, 0xA6800078, 0x00000000, 0x00000000, - 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0001800, 0xCA000000, 0x00000000, 0x00000000, - 0xA60CFFCA, 0xC6F00508, 0xC6B0C408, 0xCF000000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, - 0x8000CB48, 0xDCBC0001, 0x5FFC0000, 0x8400003A, 0xC3800002, 0xDB880001, 0x5FFC0004, 0x8400C4B2, - 0xC3800000, 0xDB880001, 0xC3CE0002, 0xC0000800, 0xCFC00708, 0xC3E1FFFE, 0x597DFFFE, 0x593DFE14, - 0x94000001, 0x00000000, 0x00000000, 0x00000000, 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, - 0x40080000, 0xCBC00000, 0xC4380000, 0x00000000, 0xC000480E, 0xCA000000, 0xC0004858, 0xCB440000, - 0x00000000, 0x00000000, 0x46350000, 0x88000098, 0x00000000, 0xA7C00028, 0xC0004854, 0xC1000002, - 0xCD040000, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x800000C0, 0x00000000, 0xA7D20118, 0x00000000, - 0xC7E14048, 0xC2400000, 0xC6246030, 0xC200006A, 0x46610000, 0xC6240038, 0xC0000810, 0xCE440038, - 0x8000FF58, 0xC2000000, 0xC0000808, 0xCA040018, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x5A200002, - 0x5E600010, 0x8400FFF8, 0xC2000000, 0xC0000808, 0xCE040018, 0xC3400000, 0x80000010, 0xC1200002, - 0xC0000818, 0xCD041008, 0x5B740002, 0xC0004858, 0xCF440000, 0x99005348, 0xC0004848, 0xC9440000, - 0xC1800000, 0xC11C0002, 0xC000082C, 0xCD040E08, 0x800005C8, 0x5B740002, 0xC0004858, 0xCF440000, - 0xC7800000, 0xC13C0002, 0xCD001E08, 0xC0004848, 0xC9440000, 0xC1800000, 0xC000082C, 0xC9840030, - 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB4980540, 0x00000000, 0xC0800000, 0x80000530, - 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCBC00000, 0xC4280000, 0x00000000, - 0xA7C00110, 0xC000484C, 0xCA040000, 0xC2400000, 0xC0001AEC, 0xCA440020, 0x5A200002, 0xC000484C, - 0xCE040000, 0xB624006A, 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC0004848, 0xC9440000, 0xC1800000, - 0xC000082C, 0xC9840030, 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB4980430, 0x00000000, - 0xC0800000, 0x80000420, 0xC0004854, 0xC1000004, 0xCD040000, 0xC0000820, 0xC2000002, 0xCE040000, - 0xC2000000, 0xC000484C, 0xCE040000, 0xC0004858, 0xCE040000, 0x8000FF10, 0xC0004854, 0xC1000000, - 0xCD040000, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x99005348, 0xC0004848, 0xC9440000, 0xC1800000, - 0xC1200000, 0xC0000818, 0xCD041008, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC2000000, 0xC000484C, - 0xCE040000, 0x80000320, 0xC0001AC0, 0xCB840000, 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, - 0x40080000, 0xCBC00000, 0xC4280000, 0x00000000, 0xA780022A, 0x00000000, 0x00000000, 0xA7C001EA, - 0x00000000, 0xC0001B00, 0xC2060006, 0xCE040310, 0xA7E801A2, 0x00000000, 0xC0004850, 0xCA040000, - 0xC2400000, 0xC0001AEC, 0xCA448020, 0x5A200002, 0xC0004850, 0xCE040000, 0xB624008A, 0x00000000, - 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC0001ACC, 0xC2000002, 0xCE040008, 0xC0004848, 0xC9440000, - 0xC1800000, 0xC000082C, 0xC9840030, 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB49801A8, - 0x00000000, 0xC0800000, 0x80000198, 0xC0004854, 0xC1000000, 0xCD040000, 0xC11C0000, 0xC000082C, - 0xCD040E08, 0x99005348, 0xC0004848, 0xC9440000, 0xC1800000, 0xC2000000, 0xC0000820, 0xCE040000, - 0xC1200000, 0xC0000818, 0xCD041008, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0004850, 0xCE040000, - 0xC2000002, 0xC0001ACC, 0xCE040010, 0x800000D0, 0xC2000002, 0xC0004850, 0xCE040000, 0x8000FE70, - 0xC2000000, 0xC0004850, 0xCE040000, 0xA7E60012, 0x00000000, 0xC2000002, 0xC0001B00, 0xCE040008, - 0x8000FE58, 0x00000000, 0xA7860032, 0x00000000, 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC2020002, - 0xC7E2A548, 0xC0001B00, 0xCE040000, 0x8000FE00, 0xC2040002, 0xC0001B00, 0xCE040208, 0x8000FDE0, - 0xC2C80002, 0x6AC56000, 0xDACC0000, 0xC0004854, 0xCB440000, 0xC0004848, 0xCB840000, 0xC0000838, - 0xC3C00000, 0xCBC40030, 0x5EF40004, 0x8400000A, 0xC3000000, 0xC0001ACC, 0xCF040108, 0x47BD8000, - 0x84000012, 0x47BD8000, 0x88000018, 0xC1006E8C, 0x8000B908, 0xC0004840, 0xCC840000, 0x8000F6B8, - 0xC0001AC0, 0xCAC40000, 0xC0004854, 0xCB440000, 0xA6C0FBD2, 0x00000000, 0x5EF40000, 0x8400F712, - 0x5EF40002, 0x8400F9A2, 0x5EF40004, 0x8400FBA2, 0xC1006CE8, 0x8000B880, 0x00000000, 0xC0800000, - 0xDF4B0040, 0xC0004900, 0xCB800000, 0xC2000000, 0xC000490A, 0xA78000B0, 0xCBC00000, 0xC1000000, - 0xD9000001, 0xC1000002, 0xD90C0000, 0x6FF46000, 0x47F5A000, 0x5B744C80, 0xC2400000, 0x58340004, - 0xCA400080, 0xC0004900, 0xCE000008, 0x5A640002, 0x58340004, 0xC6500080, 0xCD000080, 0xC0004914, - 0xCA400000, 0xC2000002, 0x6A3D0000, 0x72252000, 0xCE400000, 0xC0000408, 0xCE000000, 0xA78200B8, - 0xC0004908, 0xCBC00000, 0xC1000000, 0xD9000001, 0xC1000002, 0xD90C0000, 0x6FF4A000, 0x6FD44000, - 0x4575A000, 0x47F5A000, 0x5B744E20, 0xC2800000, 0x58340006, 0xCA800080, 0xC2000000, 0xC0004900, - 0xCE000108, 0x5EA80002, 0x58340006, 0xC6900080, 0xCD000080, 0x5A7C0020, 0xC2000002, 0x6A250000, - 0xC0000408, 0xCE000000, 0xDCA80001, 0x5EA80000, 0x8400B6F0, 0x00000000, 0xA4800210, 0x00000000, - 0xC3C00000, 0xC000140E, 0xCBC00020, 0xC3400000, 0xC2400000, 0x6FF86000, 0x47F9C000, 0x5BB84C80, - 0x58380008, 0xCB400080, 0x58380006, 0xCA400080, 0x5F740002, 0x58380008, 0xC7500080, 0xCD000080, - 0xC2000000, 0x58380004, 0xCA020080, 0xC3000000, 0x5838000C, 0xCB000028, 0x5A640002, 0x46250000, - 0x8400FFF8, 0xC2400000, 0x58380006, 0xC6500080, 0xCD000080, 0xC2000000, 0x5838000A, 0xCA020080, - 0x5B300002, 0x5838000C, 0xC7100028, 0xCD000028, 0xC2420020, 0x5A200004, 0x46612000, 0x8400FFF8, - 0xC2000000, 0x5838000A, 0xC6101080, 0xCD001080, 0xC0004966, 0xCA400000, 0xC2000002, 0x6A3D0000, - 0x72252000, 0xCE400000, 0x5F740000, 0x84000028, 0xC0004912, 0xCA000000, 0xC2C00002, 0x6AFD6000, - 0x7EC16000, 0x76E10000, 0xCE000000, 0x5F300020, 0x84000028, 0xC0004924, 0xCA000000, 0xC2C00002, - 0x6AFD6000, 0x7EC16000, 0x76E10000, 0xCE000000, 0xA4820050, 0xC2400000, 0xC000140E, 0xCA408020, - 0xC2000002, 0xC0004900, 0xCE000008, 0xC000490A, 0xCE400000, 0xC1000000, 0xD9000001, 0xD8400080, - 0xC1000004, 0xD9000001, 0xA4840288, 0x00000000, 0xC3C00000, 0xC000140E, 0xCBC10020, 0xC2800000, - 0xC2000000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x5838002E, 0xCA800080, - 0x58380006, 0xCA020080, 0xC3400000, 0x5838002E, 0xCB420080, 0x5AA80002, 0x46290000, 0x8400FFF8, - 0xC2800000, 0x5838002E, 0xC6900080, 0xCD000080, 0x5F740002, 0x5838002E, 0xC7501080, 0xCD001080, - 0xC0004968, 0xCA400000, 0xC2000002, 0x6A3D0000, 0x72252000, 0xCE400000, 0xC000492A, 0xCA800000, - 0x5E740000, 0x84000028, 0xC0004910, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x7EC16000, 0x76E10000, - 0xCE000000, 0x6ABD4010, 0xA68000D2, 0x00000000, 0xC0004910, 0xCA000000, 0xC2C00002, 0x6AFD6000, - 0x7EC16000, 0x76E10000, 0xCE000000, 0x58380032, 0xCA000000, 0x58000002, 0xCA400000, 0x5838000C, - 0x00000000, 0xCE000001, 0xCE400000, 0xC000492A, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x72E10000, - 0xCE000000, 0xC000492C, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x72E10000, 0xCE000000, 0x80000028, - 0xC000492C, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x7EC16000, 0x76E10000, 0xCE000000, 0xA4880100, - 0xC2C00000, 0xC000140E, 0xCAC20020, 0xC000490E, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x7E010000, - 0x76252000, 0xCE400000, 0xC000496A, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x72252000, 0xCE400000, - 0x6EF0A000, 0x6ED44000, 0x45718000, 0x46F18000, 0x5B304E20, 0x58300000, 0xCA000000, 0x00000000, - 0xC2400002, 0x76252000, 0x84000032, 0xC24C0002, 0xC6E40020, 0xC624C408, 0x58300010, 0xCA400508, - 0x00000000, 0xC0001800, 0xCE400000, 0xA4860050, 0xC2400000, 0xC000140E, 0xCA418020, 0xC2020002, - 0xC0004900, 0xCE000108, 0xC0004908, 0xCE400000, 0xC1000000, 0xD9000001, 0xD8400080, 0xC1000004, - 0xD9000001, 0xC0001408, 0xCC800000, 0xC10E0002, 0xD90C0000, 0x8000EDA8, 0xDFBC0001, 0xC000496E, - 0x99006050, 0xC9400000, 0xC7D80000, 0x00000000, 0xC5700000, 0x5EF00020, 0x88000130, 0x6F346000, - 0x4735A000, 0x5B744C80, 0x58340008, 0xC2400000, 0xCA400080, 0x00000000, 0xC2000000, 0x5A640002, - 0xCE400080, 0x58340004, 0xCA000080, 0x00000000, 0x00000000, 0x5E200002, 0xCE000080, 0xC0004912, - 0xCA800000, 0xC2400002, 0x6A712000, 0x72694000, 0xCE800000, 0x5E200000, 0x8400003A, 0xC000480A, - 0xCA000000, 0xC0000408, 0xCA800000, 0x76610000, 0x00000000, 0x72294000, 0xCE800000, 0x80000020, - 0xC0004914, 0xCA000000, 0x7E412000, 0x00000000, 0x76610000, 0xCE000000, 0x800000B8, 0x6EF4A000, - 0x6ED44000, 0x4575A000, 0x46F5A000, 0x5B744E20, 0x5834002E, 0xC2400000, 0xCA420080, 0x00000000, - 0xC2000000, 0x5A640002, 0xC6501080, 0xCD001080, 0x58340006, 0xCA000080, 0x00000000, 0x00000000, - 0x5A200002, 0xCE000080, 0xC0004910, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x72252000, 0xCE400000, - 0xC2000002, 0x6A310000, 0xC000042A, 0xCE000000, 0xC1040002, 0xD90C0000, 0x00000000, 0x8000EB18, - 0x00000000, 0xC4980930, 0x9D000000, 0xC5580030, 0xC0000838, 0xCD840000, 0xC1440200, 0xC1C03200, - 0xC55C1078, 0xC000100E, 0x9D000000, 0xCD800000, 0xC000100C, 0xCDC00000, 0xC0004862, 0xC9C00000, - 0x00000000, 0x00000000, 0xD9D80001, 0xC0007200, 0x401C0000, 0x5DC07400, 0x8800FFFA, 0x5C000200, - 0xCD800000, 0xC1F0000A, 0x71D4A000, 0xDD980000, 0xDD9C0001, 0x41D8E000, 0xC5D40268, 0xC0001010, - 0xCD400000, 0x6C9C8000, 0x449CE000, 0x449CE000, 0x59DC0004, 0xC1601260, 0xC5D40268, 0x9D000000, - 0xC0001012, 0xCD400000, 0x00000000, 0x00000000, 0xD9580000, 0x6D586000, 0x4558C000, 0x59984C80, - 0xD9980001, 0x5818000A, 0xC1800000, 0xC9800080, 0xC0005400, 0x6D5CA000, 0x401C0000, 0x40180000, - 0xC9400000, 0x58000002, 0x00000000, 0xC9C00000, 0xC0004930, 0xCD400000, 0xC0004932, 0xCDC00000, - 0x59980004, 0xC1C20020, 0xB59CFFF8, 0x00000000, 0xC1800000, 0xDD9C0001, 0x581C000A, 0xCD800080, - 0x581C000C, 0xC1800000, 0xC9800028, 0xC1C00002, 0xDD940000, 0x69D4E000, 0x5D980002, 0xCD800028, - 0xC0004924, 0xC9800000, 0x00000000, 0x9D000000, 0x00000000, 0x71D8C000, 0xCD800000, 0xC000492A, - 0xC9400000, 0xC1C00002, 0x69D8E000, 0x7DC0C000, 0x7594A000, 0xCD400000, 0xC000492C, 0xC9400000, - 0xDD800001, 0x58000032, 0x75D4A000, 0x84000078, 0xC9400001, 0xC9800000, 0xDD800001, 0x5800000C, - 0x00000000, 0xCD400001, 0xCD800000, 0xC000492C, 0xC9400000, 0xC000492A, 0xC9800000, 0x71D4A000, - 0xC000492C, 0xCD400000, 0x71D8C000, 0xC000492A, 0xCD800000, 0x9D000000, 0x00000000, 0x00000000, - 0x00000000, 0xC0004862, 0xC9800000, 0x00000000, 0xC1C00200, 0x4194C000, 0x45D8E000, 0x8800FFFA, - 0xC5D80000, 0xC0004862, 0xCD800000, 0xC0001406, 0xC9800000, 0xC1C00002, 0x9D000000, 0xC5D80A08, - 0xC5581050, 0xCD800000, 0xC0004930, 0xC9800000, 0xC0004932, 0xC9C00000, 0xC140000E, 0xC5581C20, - 0xDD940000, 0xC0007200, 0x40140000, 0x5D407400, 0x8800FFFA, 0x5C000200, 0xCD800000, 0x58000002, - 0x5D407400, 0x8800FFFA, 0x5C000200, 0xCDC00000, 0xDD540000, 0xC1C00000, 0x58140006, 0xC9C20080, - 0xC1800000, 0x58140000, 0xC98000E0, 0x6DDC2000, 0xC000491E, 0x41D8E000, 0xCDC00000, 0xDD980000, - 0xC1C00022, 0xC5D80D78, 0xDD940001, 0xC5581C20, 0xC000491C, 0xCD800000, 0xDD540000, 0xC1C00000, - 0x58140006, 0xC9C20080, 0xC1800000, 0x58140004, 0xC9820080, 0x00000000, 0x59DC0002, 0x459CC000, - 0x8400FFF8, 0xC1C00000, 0x9D000000, 0x58140006, 0xC5D81080, 0xCD801080, 0xC0004860, 0xC9400000, - 0xC1800100, 0xC1D00002, 0x58146B00, 0xD5800000, 0x58000002, 0xD5800001, 0x59540004, 0xB558FFF8, - 0xC0004860, 0xC1400000, 0xCD400000, 0xDD980001, 0x9D000000, 0xDD940000, 0xC0001404, 0xCDC00808, - 0xC1C00000, 0xC1800200, 0x5D980004, 0xDF5D0050, 0x45D8A000, 0x8800FFDA, 0xDD800001, 0x5800000C, - 0x00000000, 0xC9400001, 0xC9800000, 0xC1C00002, 0xC5D43F08, 0xC5D81E08, 0xC0004862, 0xC9C00000, - 0x00000000, 0x00000000, 0x581C7200, 0x5DC07400, 0x8800FFFA, 0x5C000200, 0xCD400000, 0x58000002, - 0x5DC07400, 0x8800FFFA, 0x5C000200, 0xCD800000, 0xC0004862, 0xC9C00000, 0x00000000, 0xC15004C0, - 0xC5D40068, 0xDD9C0000, 0xC5D41C20, 0xC1C00000, 0xDD800001, 0x58000030, 0xC9C00080, 0xDD800001, - 0x58000002, 0xC9800000, 0x6DDC2000, 0xC000491C, 0x41D8E000, 0xCD400001, 0xCDC00000, 0xDD940001, - 0xC1C00000, 0x58140030, 0xC9C00080, 0xC1800000, 0x58140006, 0xC9820080, 0x00000000, 0x59DC0002, - 0x459CC000, 0x8400FFF8, 0xC1C00000, 0x9D000000, 0x58140030, 0xC5D80080, 0xCD800080, 0xC1C00000, - 0xDF5C0040, 0x5DDC0080, 0x8400FFD2, 0x00000000, 0x9D000000, 0x00000000, 0x00000000, 0x00000000, - 0xC160FFFE, 0xC0000A10, 0xC9440068, 0xC1A0FFFE, 0x59980E28, 0xC000100C, 0xCD400000, 0xC000100E, - 0xCD800000, 0xC0004964, 0xC9800000, 0x00000000, 0xC170000A, 0x7194A000, 0x6C988000, 0x4498C000, - 0x4498C000, 0x59980004, 0xC5940278, 0xC0001010, 0xCD400000, 0xC0004946, 0xC9400000, 0x00000000, - 0x00000000, 0x6D58A000, 0x6D5C4000, 0x45D8C000, 0x4558C000, 0xC000494A, 0xC9400000, 0xC0004948, - 0xC9C00000, 0x4194C000, 0xC1400012, 0xC55C1820, 0x9D000000, 0xC59C0270, 0xC0001012, 0xCDC00000, - 0xC1400000, 0x58000012, 0xC9410040, 0xC0004950, 0xC9C00000, 0xC5580000, 0xC5940840, 0xC5581080, - 0xD9940000, 0xC000493C, 0xC9400000, 0xC0004954, 0xC9800000, 0x59DC00A8, 0x455CE000, 0x41D8E000, - 0x5D5C0030, 0x8800FFF8, 0xC1C00030, 0xC1800000, 0xC5D84030, 0xC1400000, 0xC5D40010, 0x5DD40002, - 0x8400005A, 0x5DD40004, 0x84000082, 0x5DD40006, 0x840000AA, 0x5DD80026, 0x840000D2, 0xDD540000, - 0xDD800001, 0x58000008, 0x40180000, 0xCD400000, 0x59980002, 0x8000FFA8, 0xDD540000, 0xDD800001, - 0x58000008, 0x40180000, 0xCD4000C0, 0x59980002, 0x8000FF70, 0xDD540000, 0xDD800001, 0x58000008, - 0x40180000, 0xCD400080, 0x59980002, 0x8000FF38, 0xDD540000, 0xDD800001, 0x58000008, 0x40180000, - 0xCD400040, 0x59980002, 0x8000FF00, 0x00000000, 0x9D000000, 0x00000000, 0x00000000, 0x00000000, - 0x58000012, 0xC9400000, 0xC0004954, 0xC9C00000, 0xC0004950, 0xC9400080, 0xDD800001, 0x58000028, - 0x5D9C0000, 0x8400003A, 0x5D9C0002, 0x8400003A, 0x5D9C0004, 0x84000052, 0xC55B0040, 0xC55C08C0, - 0xCD800041, 0xCDC008C0, 0x80000048, 0xCD400000, 0x80000038, 0xC55900C0, 0xC55C1840, 0xCD8000C1, - 0xCDC01840, 0x80000010, 0xC55A0080, 0xC55C1080, 0xCD800081, 0xCDC01080, 0x9D000000, 0x00000000, - 0x00000000, 0x00000000, 0x59540002, 0x6994E018, 0x61C0C008, 0x4194A000, 0x5D940040, 0x8800FFFA, - 0xC5940000, 0x9D000000, 0xCD400000, 0x00000000, 0x00000000, 0x9D000000, 0x4158A000, 0xCD400000, - 0x00000000, -}; - -static unsigned int firmware_binary_data[] = { -}; - - -#endif // IFXMIPS_ATM_FW_DANUBE_H diff --git a/package/lqdsl/src/ifxmips_atm_fw_regs_common.h b/package/lqdsl/src/ifxmips_atm_fw_regs_common.h deleted file mode 100644 index a5f59b8c40..0000000000 --- a/package/lqdsl/src/ifxmips_atm_fw_regs_common.h +++ /dev/null @@ -1,364 +0,0 @@ -#ifndef IFXMIPS_ATM_FW_REGS_COMMON_H -#define IFXMIPS_ATM_FW_REGS_COMMON_H - - - -#if defined(CONFIG_DANUBE) - #include "ifxmips_atm_fw_regs_danube.h" -#elif defined(CONFIG_AMAZON_SE) - #include "ifxmips_atm_fw_regs_amazon_se.h" -#elif defined(CONFIG_AR9) - #include "ifxmips_atm_fw_regs_ar9.h" -#elif defined(CONFIG_VR9) - #include "ifxmips_atm_fw_regs_vr9.h" -#else - #error Platform is not specified! -#endif - - - -/* - * PPE ATM Cell Header - */ -#if defined(__BIG_ENDIAN) - struct uni_cell_header { - unsigned int gfc :4; - unsigned int vpi :8; - unsigned int vci :16; - unsigned int pti :3; - unsigned int clp :1; - }; -#else - struct uni_cell_header { - unsigned int clp :1; - unsigned int pti :3; - unsigned int vci :16; - unsigned int vpi :8; - unsigned int gfc :4; - }; -#endif // defined(__BIG_ENDIAN) - -/* - * Inband Header and Trailer - */ -#if defined(__BIG_ENDIAN) - struct rx_inband_trailer { - /* 0 - 3h */ - unsigned int uu :8; - unsigned int cpi :8; - unsigned int stw_res1:4; - unsigned int stw_clp :1; - unsigned int stw_ec :1; - unsigned int stw_uu :1; - unsigned int stw_cpi :1; - unsigned int stw_ovz :1; - unsigned int stw_mfl :1; - unsigned int stw_usz :1; - unsigned int stw_crc :1; - unsigned int stw_il :1; - unsigned int stw_ra :1; - unsigned int stw_res2:2; - /* 4 - 7h */ - unsigned int gfc :4; - unsigned int vpi :8; - unsigned int vci :16; - unsigned int pti :3; - unsigned int clp :1; - }; - - struct tx_inband_header { - /* 0 - 3h */ - unsigned int gfc :4; - unsigned int vpi :8; - unsigned int vci :16; - unsigned int pti :3; - unsigned int clp :1; - /* 4 - 7h */ - unsigned int uu :8; - unsigned int cpi :8; - unsigned int pad :8; - unsigned int res1 :8; - }; -#else - struct rx_inband_trailer { - /* 0 - 3h */ - unsigned int stw_res2:2; - unsigned int stw_ra :1; - unsigned int stw_il :1; - unsigned int stw_crc :1; - unsigned int stw_usz :1; - unsigned int stw_mfl :1; - unsigned int stw_ovz :1; - unsigned int stw_cpi :1; - unsigned int stw_uu :1; - unsigned int stw_ec :1; - unsigned int stw_clp :1; - unsigned int stw_res1:4; - unsigned int cpi :8; - unsigned int uu :8; - /* 4 - 7h */ - unsigned int clp :1; - unsigned int pti :3; - unsigned int vci :16; - unsigned int vpi :8; - unsigned int gfc :4; - }; - - struct tx_inband_header { - /* 0 - 3h */ - unsigned int clp :1; - unsigned int pti :3; - unsigned int vci :16; - unsigned int vpi :8; - unsigned int gfc :4; - /* 4 - 7h */ - unsigned int res1 :8; - unsigned int pad :8; - unsigned int cpi :8; - unsigned int uu :8; - }; -#endif // defined(__BIG_ENDIAN) - -/* - * MIB Table Maintained by Firmware - */ -struct wan_mib_table { - u32 res1; - u32 wrx_drophtu_cell; - u32 wrx_dropdes_pdu; - u32 wrx_correct_pdu; - u32 wrx_err_pdu; - u32 wrx_dropdes_cell; - u32 wrx_correct_cell; - u32 wrx_err_cell; - u32 wrx_total_byte; - u32 res2; - u32 wtx_total_pdu; - u32 wtx_total_cell; - u32 wtx_total_byte; -}; - -/* - * Host-PPE Communication Data Structure - */ - -#if defined(__BIG_ENDIAN) - struct wrx_queue_config { - /* 0h */ - unsigned int res2 :27; - unsigned int dmach :4; - unsigned int errdp :1; - /* 1h */ - unsigned int oversize :16; - unsigned int undersize :16; - /* 2h */ - unsigned int res1 :16; - unsigned int mfs :16; - /* 3h */ - unsigned int uumask :8; - unsigned int cpimask :8; - unsigned int uuexp :8; - unsigned int cpiexp :8; - }; - - struct wtx_port_config { - unsigned int res1 :27; - unsigned int qid :4; - unsigned int qsben :1; - }; - - struct wtx_queue_config { - unsigned int res1 :25; - unsigned int sbid :1; - unsigned int res2 :3; - unsigned int type :2; - unsigned int qsben :1; - }; - - struct wrx_dma_channel_config { - /* 0h */ - unsigned int res1 :1; - unsigned int mode :2; - unsigned int rlcfg :1; - unsigned int desba :28; - /* 1h */ - unsigned int chrl :16; - unsigned int clp1th :16; - /* 2h */ - unsigned int deslen :16; - unsigned int vlddes :16; - }; - - struct wtx_dma_channel_config { - /* 0h */ - unsigned int res2 :1; - unsigned int mode :2; - unsigned int res3 :1; - unsigned int desba :28; - /* 1h */ - unsigned int res1 :32; - /* 2h */ - unsigned int deslen :16; - unsigned int vlddes :16; - }; - - struct htu_entry { - unsigned int res1 :1; - unsigned int clp :1; - unsigned int pid :2; - unsigned int vpi :8; - unsigned int vci :16; - unsigned int pti :3; - unsigned int vld :1; - }; - - struct htu_mask { - unsigned int set :1; - unsigned int clp :1; - unsigned int pid_mask :2; - unsigned int vpi_mask :8; - unsigned int vci_mask :16; - unsigned int pti_mask :3; - unsigned int clear :1; - }; - - struct htu_result { - unsigned int res1 :12; - unsigned int cellid :4; - unsigned int res2 :5; - unsigned int type :1; - unsigned int ven :1; - unsigned int res3 :5; - unsigned int qid :4; - }; - - struct rx_descriptor { - /* 0 - 3h */ - unsigned int own :1; - unsigned int c :1; - unsigned int sop :1; - unsigned int eop :1; - unsigned int res1 :3; - unsigned int byteoff :2; - unsigned int res2 :2; - unsigned int id :4; - unsigned int err :1; - unsigned int datalen :16; - /* 4 - 7h */ - unsigned int res3 :4; - unsigned int dataptr :28; - }; - - struct tx_descriptor { - /* 0 - 3h */ - unsigned int own :1; - unsigned int c :1; - unsigned int sop :1; - unsigned int eop :1; - unsigned int byteoff :5; - unsigned int res1 :5; - unsigned int iscell :1; - unsigned int clp :1; - unsigned int datalen :16; - /* 4 - 7h */ - unsigned int res2 :4; - unsigned int dataptr :28; - }; -#else - struct wrx_queue_config { - /* 0h */ - unsigned int errdp :1; - unsigned int dmach :4; - unsigned int res2 :27; - /* 1h */ - unsigned int undersize :16; - unsigned int oversize :16; - /* 2h */ - unsigned int mfs :16; - unsigned int res1 :16; - /* 3h */ - unsigned int cpiexp :8; - unsigned int uuexp :8; - unsigned int cpimask :8; - unsigned int uumask :8; - }; - - struct wtx_port_config { - unsigned int qsben :1; - unsigned int qid :4; - unsigned int res1 :27; - }; - - struct wtx_queue_config { - unsigned int qsben :1; - unsigned int type :2; - unsigned int res2 :3; - unsigned int sbid :1; - unsigned int res1 :25; - }; - - struct wrx_dma_channel_config - { - /* 0h */ - unsigned int desba :28; - unsigned int rlcfg :1; - unsigned int mode :2; - unsigned int res1 :1; - /* 1h */ - unsigned int clp1th :16; - unsigned int chrl :16; - /* 2h */ - unsigned int vlddes :16; - unsigned int deslen :16; - }; - - struct wtx_dma_channel_config { - /* 0h */ - unsigned int desba :28; - unsigned int res3 :1; - unsigned int mode :2; - unsigned int res2 :1; - /* 1h */ - unsigned int res1 :32; - /* 2h */ - unsigned int vlddes :16; - unsigned int deslen :16; - }; - - struct rx_descriptor { - /* 4 - 7h */ - unsigned int dataptr :28; - unsigned int res3 :4; - /* 0 - 3h */ - unsigned int datalen :16; - unsigned int err :1; - unsigned int id :4; - unsigned int res2 :2; - unsigned int byteoff :2; - unsigned int res1 :3; - unsigned int eop :1; - unsigned int sop :1; - unsigned int c :1; - unsigned int own :1; - }; - - struct tx_descriptor { - /* 4 - 7h */ - unsigned int dataptr :28; - unsigned int res2 :4; - /* 0 - 3h */ - unsigned int datalen :16; - unsigned int clp :1; - unsigned int iscell :1; - unsigned int res1 :5; - unsigned int byteoff :5; - unsigned int eop :1; - unsigned int sop :1; - unsigned int c :1; - unsigned int own :1; - }; -#endif // defined(__BIG_ENDIAN) - - - -#endif // IFXMIPS_ATM_FW_REGS_COMMON_H diff --git a/package/lqdsl/src/ifxmips_atm_fw_regs_danube.h b/package/lqdsl/src/ifxmips_atm_fw_regs_danube.h deleted file mode 100644 index c0dfc6a2e0..0000000000 --- a/package/lqdsl/src/ifxmips_atm_fw_regs_danube.h +++ /dev/null @@ -1,30 +0,0 @@ -#ifndef IFXMIPS_ATM_FW_REGS_DANUBE_H -#define IFXMIPS_ATM_FW_REGS_DANUBE_H - - - -/* - * Host-PPE Communication Data Address Mapping - */ -#define FW_VER_ID SB_BUFFER(0x2001) -#define CFG_WRX_HTUTS SB_BUFFER(0x2400) /* WAN RX HTU Table Size, must be configured before enable PPE firmware. */ -#define CFG_WRX_QNUM SB_BUFFER(0x2401) /* WAN RX Queue Number */ -#define CFG_WRX_DCHNUM SB_BUFFER(0x2402) /* WAN RX DMA Channel Number, no more than 8, must be configured before enable PPE firmware. */ -#define CFG_WTX_DCHNUM SB_BUFFER(0x2403) /* WAN TX DMA Channel Number, no more than 16, must be configured before enable PPE firmware. */ -#define CFG_WRDES_DELAY SB_BUFFER(0x2404) /* WAN Descriptor Write Delay, must be configured before enable PPE firmware. */ -#define WRX_DMACH_ON SB_BUFFER(0x2405) /* WAN RX DMA Channel Enable, must be configured before enable PPE firmware. */ -#define WTX_DMACH_ON SB_BUFFER(0x2406) /* WAN TX DMA Channel Enable, must be configured before enable PPE firmware. */ -#define WRX_HUNT_BITTH SB_BUFFER(0x2407) /* WAN RX HUNT Threshold, must be between 2 to 8. */ -#define WRX_QUEUE_CONFIG(i) ((struct wrx_queue_config*) SB_BUFFER(0x2500 + (i) * 20)) -#define WRX_DMA_CHANNEL_CONFIG(i) ((struct wrx_dma_channel_config*) SB_BUFFER(0x2640 + (i) * 7)) -#define WTX_PORT_CONFIG(i) ((struct wtx_port_config*) SB_BUFFER(0x2440 + (i))) -#define WTX_QUEUE_CONFIG(i) ((struct wtx_queue_config*) SB_BUFFER(0x2710 + (i) * 27)) -#define WTX_DMA_CHANNEL_CONFIG(i) ((struct wtx_dma_channel_config*) SB_BUFFER(0x2711 + (i) * 27)) -#define WAN_MIB_TABLE ((struct wan_mib_table*) SB_BUFFER(0x2410)) -#define HTU_ENTRY(i) ((struct htu_entry*) SB_BUFFER(0x2000 + (i))) -#define HTU_MASK(i) ((struct htu_mask*) SB_BUFFER(0x2020 + (i))) -#define HTU_RESULT(i) ((struct htu_result*) SB_BUFFER(0x2040 + (i))) - - - -#endif // IFXMIPS_ATM_FW_REGS_DANUBE_H diff --git a/package/lqdsl/src/ifxmips_atm_ppe_common.h b/package/lqdsl/src/ifxmips_atm_ppe_common.h deleted file mode 100644 index c922276dfb..0000000000 --- a/package/lqdsl/src/ifxmips_atm_ppe_common.h +++ /dev/null @@ -1,231 +0,0 @@ -#ifndef IFXMIPS_ATM_PPE_COMMON_H -#define IFXMIPS_ATM_PPE_COMMON_H - -#if defined(CONFIG_LANTIQ) - #include "ifxmips_atm_ppe_danube.h" - #define CONFIG_DANUBE -#elif defined(CONFIG_DANUBE) - #include "ifxmips_atm_ppe_danube.h" -#elif defined(CONFIG_AMAZON_SE) - #include "ifxmips_atm_ppe_amazon_se.h" -#elif defined(CONFIG_AR9) - #include "ifxmips_atm_ppe_ar9.h" -#elif defined(CONFIG_VR9) - #include "ifxmips_atm_ppe_vr9.h" -#else - #error Platform is not specified! -#endif - - -/* - * Code/Data Memory (CDM) Interface Configuration Register - */ -#define CDM_CFG PPE_REG_ADDR(0x0100) - -#define CDM_CFG_RAM1 GET_BITS(*CDM_CFG, 3, 2) -#define CDM_CFG_RAM0 (*CDM_CFG & (1 << 1)) - -#define CDM_CFG_RAM1_SET(value) SET_BITS(0, 3, 2, value) -#define CDM_CFG_RAM0_SET(value) ((value) ? (1 << 1) : 0) - -/* - * QSB Internal Cell Delay Variation Register - */ -#define QSB_ICDV QSB_CONF_REG_ADDR(0x0007) - -#define QSB_ICDV_TAU GET_BITS(*QSB_ICDV, 5, 0) - -#define QSB_ICDV_TAU_SET(value) SET_BITS(0, 5, 0, value) - -/* - * QSB Scheduler Burst Limit Register - */ -#define QSB_SBL QSB_CONF_REG_ADDR(0x0009) - -#define QSB_SBL_SBL GET_BITS(*QSB_SBL, 3, 0) - -#define QSB_SBL_SBL_SET(value) SET_BITS(0, 3, 0, value) - -/* - * QSB Configuration Register - */ -#define QSB_CFG QSB_CONF_REG_ADDR(0x000A) - -#define QSB_CFG_TSTEPC GET_BITS(*QSB_CFG, 1, 0) - -#define QSB_CFG_TSTEPC_SET(value) SET_BITS(0, 1, 0, value) - -/* - * QSB RAM Transfer Table Register - */ -#define QSB_RTM QSB_CONF_REG_ADDR(0x000B) - -#define QSB_RTM_DM (*QSB_RTM) - -#define QSB_RTM_DM_SET(value) ((value) & 0xFFFFFFFF) - -/* - * QSB RAM Transfer Data Register - */ -#define QSB_RTD QSB_CONF_REG_ADDR(0x000C) - -#define QSB_RTD_TTV (*QSB_RTD) - -#define QSB_RTD_TTV_SET(value) ((value) & 0xFFFFFFFF) - -/* - * QSB RAM Access Register - */ -#define QSB_RAMAC QSB_CONF_REG_ADDR(0x000D) - -#define QSB_RAMAC_RW (*QSB_RAMAC & (1 << 31)) -#define QSB_RAMAC_TSEL GET_BITS(*QSB_RAMAC, 27, 24) -#define QSB_RAMAC_LH (*QSB_RAMAC & (1 << 16)) -#define QSB_RAMAC_TESEL GET_BITS(*QSB_RAMAC, 9, 0) - -#define QSB_RAMAC_RW_SET(value) ((value) ? (1 << 31) : 0) -#define QSB_RAMAC_TSEL_SET(value) SET_BITS(0, 27, 24, value) -#define QSB_RAMAC_LH_SET(value) ((value) ? (1 << 16) : 0) -#define QSB_RAMAC_TESEL_SET(value) SET_BITS(0, 9, 0, value) - -/* - * QSB Queue Scheduling and Shaping Definitions - */ -#define QSB_WFQ_NONUBR_MAX 0x3f00 -#define QSB_WFQ_UBR_BYPASS 0x3fff -#define QSB_TP_TS_MAX 65472 -#define QSB_TAUS_MAX 64512 -#define QSB_GCR_MIN 18 - -/* - * QSB Constant - */ -#define QSB_RAMAC_RW_READ 0 -#define QSB_RAMAC_RW_WRITE 1 - -#define QSB_RAMAC_TSEL_QPT 0x01 -#define QSB_RAMAC_TSEL_SCT 0x02 -#define QSB_RAMAC_TSEL_SPT 0x03 -#define QSB_RAMAC_TSEL_VBR 0x08 - -#define QSB_RAMAC_LH_LOW 0 -#define QSB_RAMAC_LH_HIGH 1 - -#define QSB_QPT_SET_MASK 0x0 -#define QSB_QVPT_SET_MASK 0x0 -#define QSB_SET_SCT_MASK 0x0 -#define QSB_SET_SPT_MASK 0x0 -#define QSB_SET_SPT_SBVALID_MASK 0x7FFFFFFF - -#define QSB_SPT_SBV_VALID (1 << 31) -#define QSB_SPT_PN_SET(value) (((value) & 0x01) ? (1 << 16) : 0) -#define QSB_SPT_INTRATE_SET(value) SET_BITS(0, 13, 0, value) - -/* - * QSB Queue Parameter Table Entry and Queue VBR Parameter Table Entry - */ -#if defined(__BIG_ENDIAN) - union qsb_queue_parameter_table { - struct { - unsigned int res1 :1; - unsigned int vbr :1; - unsigned int wfqf :14; - unsigned int tp :16; - } bit; - u32 dword; - }; - - union qsb_queue_vbr_parameter_table { - struct { - unsigned int taus :16; - unsigned int ts :16; - } bit; - u32 dword; - }; -#else - union qsb_queue_parameter_table { - struct { - unsigned int tp :16; - unsigned int wfqf :14; - unsigned int vbr :1; - unsigned int res1 :1; - } bit; - u32 dword; - }; - - union qsb_queue_vbr_parameter_table { - struct { - unsigned int ts :16; - unsigned int taus :16; - } bit; - u32 dword; - }; -#endif // defined(__BIG_ENDIAN) - -/* - * Mailbox IGU0 Registers - */ -#define MBOX_IGU0_ISRS PPE_REG_ADDR(0x0200) -#define MBOX_IGU0_ISRC PPE_REG_ADDR(0x0201) -#define MBOX_IGU0_ISR PPE_REG_ADDR(0x0202) -#define MBOX_IGU0_IER PPE_REG_ADDR(0x0203) - -#define MBOX_IGU0_ISRS_SET(n) (1 << (n)) -#define MBOX_IGU0_ISRC_CLEAR(n) (1 << (n)) -#define MBOX_IGU0_ISR_ISR(n) (*MBOX_IGU0_ISR & (1 << (n))) -#define MBOX_IGU0_IER_EN(n) (*MBOX_IGU0_IER & (1 << (n))) -#define MBOX_IGU0_IER_EN_SET(n) (1 << (n)) - -/* - * Mailbox IGU1 Registers - */ -#define MBOX_IGU1_ISRS PPE_REG_ADDR(0x0204) -#define MBOX_IGU1_ISRC PPE_REG_ADDR(0x0205) -#define MBOX_IGU1_ISR PPE_REG_ADDR(0x0206) -#define MBOX_IGU1_IER PPE_REG_ADDR(0x0207) - -#define MBOX_IGU1_ISRS_SET(n) (1 << (n)) -#define MBOX_IGU1_ISRC_CLEAR(n) (1 << (n)) -#define MBOX_IGU1_ISR_ISR(n) (*MBOX_IGU1_ISR & (1 << (n))) -#define MBOX_IGU1_IER_EN(n) (*MBOX_IGU1_IER & (1 << (n))) -#define MBOX_IGU1_IER_EN_SET(n) (1 << (n)) - -/* - * Mailbox IGU3 Registers - */ -#define MBOX_IGU3_ISRS PPE_REG_ADDR(0x0214) -#define MBOX_IGU3_ISRC PPE_REG_ADDR(0x0215) -#define MBOX_IGU3_ISR PPE_REG_ADDR(0x0216) -#define MBOX_IGU3_IER PPE_REG_ADDR(0x0217) - -#define MBOX_IGU3_ISRS_SET(n) (1 << (n)) -#define MBOX_IGU3_ISRC_CLEAR(n) (1 << (n)) -#define MBOX_IGU3_ISR_ISR(n) (*MBOX_IGU3_ISR & (1 << (n))) -#define MBOX_IGU3_IER_EN(n) (*MBOX_IGU3_IER & (1 << (n))) -#define MBOX_IGU3_IER_EN_SET(n) (1 << (n)) - -/* - * RTHA/TTHA Registers - */ -#define SFSM_STATE0 PPE_REG_ADDR(0x0410) -#define SFSM_STATE1 PPE_REG_ADDR(0x0411) -#define SFSM_DBA0 PPE_REG_ADDR(0x0412) -#define SFSM_DBA1 PPE_REG_ADDR(0x0413) -#define SFSM_CBA0 PPE_REG_ADDR(0x0414) -#define SFSM_CBA1 PPE_REG_ADDR(0x0415) -#define SFSM_CFG0 PPE_REG_ADDR(0x0416) -#define SFSM_CFG1 PPE_REG_ADDR(0x0417) -#define SFSM_PGCNT0 PPE_REG_ADDR(0x041C) -#define SFSM_PGCNT1 PPE_REG_ADDR(0x041D) -#define FFSM_DBA0 PPE_REG_ADDR(0x0508) -#define FFSM_DBA1 PPE_REG_ADDR(0x0509) -#define FFSM_CFG0 PPE_REG_ADDR(0x050A) -#define FFSM_CFG1 PPE_REG_ADDR(0x050B) -#define FFSM_IDLE_HEAD_BC0 PPE_REG_ADDR(0x050E) -#define FFSM_IDLE_HEAD_BC1 PPE_REG_ADDR(0x050F) -#define FFSM_PGCNT0 PPE_REG_ADDR(0x0514) -#define FFSM_PGCNT1 PPE_REG_ADDR(0x0515) - - - -#endif // IFXMIPS_ATM_PPE_COMMON_H diff --git a/package/lqdsl/src/ifxmips_atm_ppe_danube.h b/package/lqdsl/src/ifxmips_atm_ppe_danube.h deleted file mode 100644 index a60abe1d55..0000000000 --- a/package/lqdsl/src/ifxmips_atm_ppe_danube.h +++ /dev/null @@ -1,100 +0,0 @@ -#ifndef IFXMIPS_ATM_PPE_DANUBE_H -#define IFXMIPS_ATM_PPE_DANUBE_H - -#include - -/* - * FPI Configuration Bus Register and Memory Address Mapping - */ -#define IFX_PPE (KSEG1 | 0x1E180000) -#define PP32_DEBUG_REG_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0000) << 2))) -#define PPM_INT_REG_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0030) << 2))) -#define PP32_INTERNAL_RES_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0040) << 2))) -#define CDM_CODE_MEMORY(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x1000) << 2))) -#define PPE_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x4000) << 2))) -#define CDM_DATA_MEMORY(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x5000) << 2))) -#define PPM_INT_UNIT_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6000) << 2))) -#define PPM_TIMER0_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6100) << 2))) -#define PPM_TASK_IND_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6200) << 2))) -#define PPS_BRK_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6300) << 2))) -#define PPM_TIMER1_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6400) << 2))) -#define SB_RAM0_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8000) << 2))) -#define SB_RAM1_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8400) << 2))) -#define SB_RAM2_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8C00) << 2))) -#define SB_RAM3_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x9600) << 2))) -#define QSB_CONF_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0xC000) << 2))) - -/* - * DWORD-Length of Memory Blocks - */ -#define PP32_DEBUG_REG_DWLEN 0x0030 -#define PPM_INT_REG_DWLEN 0x0010 -#define PP32_INTERNAL_RES_DWLEN 0x00C0 -#define CDM_CODE_MEMORYn_DWLEN(n) ((n) == 0 ? 0x1000 : 0x0800) -#define PPE_REG_DWLEN 0x1000 -#define CDM_DATA_MEMORY_DWLEN CDM_CODE_MEMORYn_DWLEN(1) -#define PPM_INT_UNIT_DWLEN 0x0100 -#define PPM_TIMER0_DWLEN 0x0100 -#define PPM_TASK_IND_REG_DWLEN 0x0100 -#define PPS_BRK_DWLEN 0x0100 -#define PPM_TIMER1_DWLEN 0x0100 -#define SB_RAM0_DWLEN 0x0400 -#define SB_RAM1_DWLEN 0x0800 -#define SB_RAM2_DWLEN 0x0A00 -#define SB_RAM3_DWLEN 0x0400 -#define QSB_CONF_REG_DWLEN 0x0100 - -/* - * PP32 to FPI Address Mapping - */ -#define SB_BUFFER(__sb_addr) ((volatile unsigned int *)((((__sb_addr) >= 0x2000) && ((__sb_addr) <= 0x23FF)) ? SB_RAM0_ADDR((__sb_addr) - 0x2000) : \ - (((__sb_addr) >= 0x2400) && ((__sb_addr) <= 0x2BFF)) ? SB_RAM1_ADDR((__sb_addr) - 0x2400) : \ - (((__sb_addr) >= 0x2C00) && ((__sb_addr) <= 0x35FF)) ? SB_RAM2_ADDR((__sb_addr) - 0x2C00) : \ - (((__sb_addr) >= 0x3600) && ((__sb_addr) <= 0x39FF)) ? SB_RAM3_ADDR((__sb_addr) - 0x3600) : \ - 0)) - -/* - * PP32 Debug Control Register - */ -#define PP32_DBG_CTRL PP32_DEBUG_REG_ADDR(0, 0x0000) - -#define DBG_CTRL_START_SET(value) ((value) ? (1 << 0) : 0) -#define DBG_CTRL_STOP_SET(value) ((value) ? (1 << 1) : 0) -#define DBG_CTRL_STEP_SET(value) ((value) ? (1 << 2) : 0) - -#define PP32_HALT_STAT PP32_DEBUG_REG_ADDR(0, 0x0001) - -#define PP32_BRK_SRC PP32_DEBUG_REG_ADDR(0, 0x0002) - -#define PP32_DBG_PC_MIN(i) PP32_DEBUG_REG_ADDR(0, 0x0010 + (i)) -#define PP32_DBG_PC_MAX(i) PP32_DEBUG_REG_ADDR(0, 0x0014 + (i)) -#define PP32_DBG_DATA_MIN(i) PP32_DEBUG_REG_ADDR(0, 0x0018 + (i)) -#define PP32_DBG_DATA_MAX(i) PP32_DEBUG_REG_ADDR(0, 0x001A + (i)) -#define PP32_DBG_DATA_VAL(i) PP32_DEBUG_REG_ADDR(0, 0x001C + (i)) - -#define PP32_DBG_CUR_PC PP32_DEBUG_REG_ADDR(0, 0x0080) - -#define PP32_DBG_TASK_NO PP32_DEBUG_REG_ADDR(0, 0x0081) - -/* - * EMA Registers - */ -#define EMA_CMDCFG PPE_REG_ADDR(0x0A00) -#define EMA_DATACFG PPE_REG_ADDR(0x0A01) -#define EMA_CMDCNT PPE_REG_ADDR(0x0A02) -#define EMA_DATACNT PPE_REG_ADDR(0x0A03) -#define EMA_ISR PPE_REG_ADDR(0x0A04) -#define EMA_IER PPE_REG_ADDR(0x0A05) -#define EMA_CFG PPE_REG_ADDR(0x0A06) -#define EMA_SUBID PPE_REG_ADDR(0x0A07) - -#define EMA_ALIGNMENT 4 - -/* - * Mailbox IGU1 Interrupt - */ -#define PPE_MAILBOX_IGU1_INT LQ_PPE_MBOX_INT - - - -#endif // IFXMIPS_ATM_PPE_DANUBE_H diff --git a/package/lqdsl/src/ifxmips_compat.h b/package/lqdsl/src/ifxmips_compat.h deleted file mode 100644 index f5b5768466..0000000000 --- a/package/lqdsl/src/ifxmips_compat.h +++ /dev/null @@ -1,43 +0,0 @@ -#ifndef _IFXMIPS_COMPAT_H__ -#define _IFXMIPS_COMPAT_H__ - -#define IFX_SUCCESS 0 -#define IFX_ERROR (-1) - -#define ATM_VBR_NRT ATM_VBR -#define ATM_VBR_RT 6 -#define ATM_UBR_PLUS 7 -#define ATM_GFR 8 - -#define NUM_ENTITY(x) (sizeof(x) / sizeof(*(x))) - -#define SET_BITS(x, msb, lsb, value) \ - (((x) & ~(((1 << ((msb) + 1)) - 1) ^ ((1 << (lsb)) - 1))) | (((value) & ((1 << (1 + (msb) - (lsb))) - 1)) << (lsb))) - - -#define IFX_PMU_ENABLE 1 -#define IFX_PMU_DISABLE 0 - -#define IFX_PMU_MODULE_DSL_DFE (1 << 9) -#define IFX_PMU_MODULE_AHBS (1 << 13) -#define IFX_PMU_MODULE_PPE_QSB (1 << 18) -#define IFX_PMU_MODULE_PPE_SLL01 (1 << 19) -#define IFX_PMU_MODULE_PPE_TC (1 << 21) -#define IFX_PMU_MODULE_PPE_EMA (1 << 22) -#define IFX_PMU_MODULE_PPE_TOP (1 << 29) - -#define ifx_pmu_set(a,b) {if(a == IFX_PMU_ENABLE) lq_pmu_enable(b); else lq_pmu_disable(b);} - -#define PPE_TOP_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_TOP, (__x)) -#define PPE_SLL01_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_SLL01, (__x)) -#define PPE_TC_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_TC, (__x)) -#define PPE_EMA_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_EMA, (__x)) -#define PPE_QSB_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_QSB, (__x)) -#define PPE_TPE_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_AHBS, (__x)) -#define DSL_DFE_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_DSL_DFE, (__x)) - -#define IFX_REG_W32(_v, _r) __raw_writel((_v), (_r)) - -#define CONFIG_IFXMIPS_DSL_CPE_MEI y - -#endif diff --git a/package/lqdsl/src/ifxmips_mei_interface.h b/package/lqdsl/src/ifxmips_mei_interface.h deleted file mode 100644 index ffde6113c8..0000000000 --- a/package/lqdsl/src/ifxmips_mei_interface.h +++ /dev/null @@ -1,700 +0,0 @@ -/****************************************************************************** - - Copyright (c) 2009 - Infineon Technologies AG - Am Campeon 1-12; 81726 Munich, Germany - - For licensing information, see the file 'LICENSE' in the root folder of - this software module. - -******************************************************************************/ - -#ifndef IFXMIPS_MEI_H -#define IFXMIPS_MEI_H - -#define CONFIG_DANUBE 1 - -#if !defined(CONFIG_DANUBE) && !defined(CONFIG_AMAZON_SE) && !defined(CONFIG_AR9) && !defined(CONFIG_VR9) -#error Platform undefined!!! -#endif - -#ifdef IFX_MEI_BSP -/** This is the character datatype. */ -typedef char DSL_char_t; -/** This is the unsigned 8-bit datatype. */ -typedef unsigned char DSL_uint8_t; -/** This is the signed 8-bit datatype. */ -typedef signed char DSL_int8_t; -/** This is the unsigned 16-bit datatype. */ -typedef unsigned short DSL_uint16_t; -/** This is the signed 16-bit datatype. */ -typedef signed short DSL_int16_t; -/** This is the unsigned 32-bit datatype. */ -typedef unsigned long DSL_uint32_t; -/** This is the signed 32-bit datatype. */ -typedef signed long DSL_int32_t; -/** This is the float datatype. */ -typedef float DSL_float_t; -/** This is the void datatype. */ -typedef void DSL_void_t; -/** integer type, width is depending on processor arch */ -typedef int DSL_int_t; -/** unsigned integer type, width is depending on processor arch */ -typedef unsigned int DSL_uint_t; -typedef struct file DSL_DRV_file_t; -typedef struct inode DSL_DRV_inode_t; - -/** - * Defines all possible CMV groups - * */ -typedef enum { - DSL_CMV_GROUP_CNTL = 1, - DSL_CMV_GROUP_STAT = 2, - DSL_CMV_GROUP_INFO = 3, - DSL_CMV_GROUP_TEST = 4, - DSL_CMV_GROUP_OPTN = 5, - DSL_CMV_GROUP_RATE = 6, - DSL_CMV_GROUP_PLAM = 7, - DSL_CMV_GROUP_CNFG = 8 -} DSL_CmvGroup_t; -/** - * Defines all opcode types - * */ -typedef enum { - H2D_CMV_READ = 0x00, - H2D_CMV_WRITE = 0x04, - H2D_CMV_INDICATE_REPLY = 0x10, - H2D_ERROR_OPCODE_UNKNOWN =0x20, - H2D_ERROR_CMV_UNKNOWN =0x30, - - D2H_CMV_READ_REPLY =0x01, - D2H_CMV_WRITE_REPLY = 0x05, - D2H_CMV_INDICATE = 0x11, - D2H_ERROR_OPCODE_UNKNOWN = 0x21, - D2H_ERROR_CMV_UNKNOWN = 0x31, - D2H_ERROR_CMV_READ_NOT_AVAILABLE = 0x41, - D2H_ERROR_CMV_WRITE_ONLY = 0x51, - D2H_ERROR_CMV_READ_ONLY = 0x61, - - H2D_DEBUG_READ_DM = 0x02, - H2D_DEBUG_READ_PM = 0x06, - H2D_DEBUG_WRITE_DM = 0x0a, - H2D_DEBUG_WRITE_PM = 0x0e, - - D2H_DEBUG_READ_DM_REPLY = 0x03, - D2H_DEBUG_READ_FM_REPLY = 0x07, - D2H_DEBUG_WRITE_DM_REPLY = 0x0b, - D2H_DEBUG_WRITE_FM_REPLY = 0x0f, - D2H_ERROR_ADDR_UNKNOWN = 0x33, - - D2H_AUTONOMOUS_MODEM_READY_MSG = 0xf1 -} DSL_CmvOpcode_t; - -/* mutex macros */ -#define MEI_MUTEX_INIT(id,flag) \ - sema_init(&id,flag) -#define MEI_MUTEX_LOCK(id) \ - down_interruptible(&id) -#define MEI_MUTEX_UNLOCK(id) \ - up(&id) -#define MEI_WAIT(ms) \ - {\ - set_current_state(TASK_INTERRUPTIBLE);\ - schedule_timeout(ms);\ - } -#define MEI_INIT_WAKELIST(name,queue) \ - init_waitqueue_head(&queue) - -/* wait for an event, timeout is measured in ms */ -#define MEI_WAIT_EVENT_TIMEOUT(ev,timeout)\ - interruptible_sleep_on_timeout(&ev,timeout * HZ / 1000) -#define MEI_WAKEUP_EVENT(ev)\ - wake_up_interruptible(&ev) -#endif /* IFX_MEI_BSP */ - -/*** Register address offsets, relative to MEI_SPACE_ADDRESS ***/ -#define ME_DX_DATA (0x0000) -#define ME_VERSION (0x0004) -#define ME_ARC_GP_STAT (0x0008) -#define ME_DX_STAT (0x000C) -#define ME_DX_AD (0x0010) -#define ME_DX_MWS (0x0014) -#define ME_ME2ARC_INT (0x0018) -#define ME_ARC2ME_STAT (0x001C) -#define ME_ARC2ME_MASK (0x0020) -#define ME_DBG_WR_AD (0x0024) -#define ME_DBG_RD_AD (0x0028) -#define ME_DBG_DATA (0x002C) -#define ME_DBG_DECODE (0x0030) -#define ME_CONFIG (0x0034) -#define ME_RST_CTRL (0x0038) -#define ME_DBG_MASTER (0x003C) -#define ME_CLK_CTRL (0x0040) -#define ME_BIST_CTRL (0x0044) -#define ME_BIST_STAT (0x0048) -#define ME_XDATA_BASE_SH (0x004c) -#define ME_XDATA_BASE (0x0050) -#define ME_XMEM_BAR_BASE (0x0054) -#define ME_XMEM_BAR0 (0x0054) -#define ME_XMEM_BAR1 (0x0058) -#define ME_XMEM_BAR2 (0x005C) -#define ME_XMEM_BAR3 (0x0060) -#define ME_XMEM_BAR4 (0x0064) -#define ME_XMEM_BAR5 (0x0068) -#define ME_XMEM_BAR6 (0x006C) -#define ME_XMEM_BAR7 (0x0070) -#define ME_XMEM_BAR8 (0x0074) -#define ME_XMEM_BAR9 (0x0078) -#define ME_XMEM_BAR10 (0x007C) -#define ME_XMEM_BAR11 (0x0080) -#define ME_XMEM_BAR12 (0x0084) -#define ME_XMEM_BAR13 (0x0088) -#define ME_XMEM_BAR14 (0x008C) -#define ME_XMEM_BAR15 (0x0090) -#define ME_XMEM_BAR16 (0x0094) - -#define WHILE_DELAY 20000 -/* -** Define where in ME Processor's memory map the Stratify chip lives -*/ - -#define MAXSWAPSIZE (8 * 1024) //8k *(32bits) - -// Mailboxes -#define MSG_LENGTH 16 // x16 bits -#define YES_REPLY 1 -#define NO_REPLY 0 - -#define CMV_TIMEOUT 1000 //jiffies - -// Block size per BAR -#define SDRAM_SEGMENT_SIZE (64*1024) -// Number of Bar registers -#define MAX_BAR_REGISTERS (17) - -#define XDATA_REGISTER (15) - -// ARC register addresss -#define ARC_STATUS 0x0 -#define ARC_LP_START 0x2 -#define ARC_LP_END 0x3 -#define ARC_DEBUG 0x5 -#define ARC_INT_MASK 0x10A - -#define IRAM0_BASE (0x00000) -#define IRAM1_BASE (0x04000) -#if defined(CONFIG_DANUBE) -#define BRAM_BASE (0x0A000) -#elif defined(CONFIG_AMAZON_SE) || defined(CONFIG_AR9) || defined(CONFIG_VR9) -#define BRAM_BASE (0x08000) -#endif -#define XRAM_BASE (0x18000) -#define YRAM_BASE (0x1A000) -#define EXT_MEM_BASE (0x80000) -#define ARC_GPIO_CTRL (0xC030) -#define ARC_GPIO_DATA (0xC034) - -#define IRAM0_SIZE (16*1024) -#define IRAM1_SIZE (16*1024) -#define BRAM_SIZE (12*1024) -#define XRAM_SIZE (8*1024) -#define YRAM_SIZE (8*1024) -#define EXT_MEM_SIZE (1536*1024) - -#define ADSL_BASE (0x20000) -#define CRI_BASE (ADSL_BASE + 0x11F00) -#define CRI_CCR0 (CRI_BASE + 0x00) -#define CRI_RST (CRI_BASE + 0x04*4) -#define ADSL_DILV_BASE (ADSL_BASE+0x20000) - -// -#define IRAM0_ADDR_BIT_MASK 0xFFF -#define IRAM1_ADDR_BIT_MASK 0xFFF -#define BRAM_ADDR_BIT_MASK 0xFFF -#define RX_DILV_ADDR_BIT_MASK 0x1FFF - -/*** Bit definitions ***/ -#define ARC_AUX_HALT (1 << 25) -#define ARC_DEBUG_HALT (1 << 1) -#define FALSE 0 -#define TRUE 1 -#define BIT0 (1<<0) -#define BIT1 (1<<1) -#define BIT2 (1<<2) -#define BIT3 (1<<3) -#define BIT4 (1<<4) -#define BIT5 (1<<5) -#define BIT6 (1<<6) -#define BIT7 (1<<7) -#define BIT8 (1<<8) -#define BIT9 (1<<9) -#define BIT10 (1<<10) -#define BIT11 (1<<11) -#define BIT12 (1<<12) -#define BIT13 (1<<13) -#define BIT14 (1<<14) -#define BIT15 (1<<15) -#define BIT16 (1<<16) -#define BIT17 (1<<17) -#define BIT18 (1<<18) -#define BIT19 (1<<19) -#define BIT20 (1<<20) -#define BIT21 (1<<21) -#define BIT22 (1<<22) -#define BIT23 (1<<23) -#define BIT24 (1<<24) -#define BIT25 (1<<25) -#define BIT26 (1<<26) -#define BIT27 (1<<27) -#define BIT28 (1<<28) -#define BIT29 (1<<29) -#define BIT30 (1<<30) -#define BIT31 (1<<31) - -// CRI_CCR0 Register definitions -#define CLK_2M_MODE_ENABLE BIT6 -#define ACL_CLK_MODE_ENABLE BIT4 -#define FDF_CLK_MODE_ENABLE BIT2 -#define STM_CLK_MODE_ENABLE BIT0 - -// CRI_RST Register definitions -#define FDF_SRST BIT3 -#define MTE_SRST BIT2 -#define FCI_SRST BIT1 -#define AAI_SRST BIT0 - -// MEI_TO_ARC_INTERRUPT Register definitions -#define MEI_TO_ARC_INT1 BIT3 -#define MEI_TO_ARC_INT0 BIT2 -#define MEI_TO_ARC_CS_DONE BIT1 //need to check -#define MEI_TO_ARC_MSGAV BIT0 - -// ARC_TO_MEI_INTERRUPT Register definitions -#define ARC_TO_MEI_INT1 BIT8 -#define ARC_TO_MEI_INT0 BIT7 -#define ARC_TO_MEI_CS_REQ BIT6 -#define ARC_TO_MEI_DBG_DONE BIT5 -#define ARC_TO_MEI_MSGACK BIT4 -#define ARC_TO_MEI_NO_ACCESS BIT3 -#define ARC_TO_MEI_CHECK_AAITX BIT2 -#define ARC_TO_MEI_CHECK_AAIRX BIT1 -#define ARC_TO_MEI_MSGAV BIT0 - -// ARC_TO_MEI_INTERRUPT_MASK Register definitions -#define GP_INT1_EN BIT8 -#define GP_INT0_EN BIT7 -#define CS_REQ_EN BIT6 -#define DBG_DONE_EN BIT5 -#define MSGACK_EN BIT4 -#define NO_ACC_EN BIT3 -#define AAITX_EN BIT2 -#define AAIRX_EN BIT1 -#define MSGAV_EN BIT0 - -#define MEI_SOFT_RESET BIT0 - -#define HOST_MSTR BIT0 - -#define JTAG_MASTER_MODE 0x0 -#define MEI_MASTER_MODE HOST_MSTR - -// MEI_DEBUG_DECODE Register definitions -#define MEI_DEBUG_DEC_MASK (0x3) -#define MEI_DEBUG_DEC_AUX_MASK (0x0) -#define ME_DBG_DECODE_DMP1_MASK (0x1) -#define MEI_DEBUG_DEC_DMP2_MASK (0x2) -#define MEI_DEBUG_DEC_CORE_MASK (0x3) - -#define AUX_STATUS (0x0) -#define AUX_ARC_GPIO_CTRL (0x10C) -#define AUX_ARC_GPIO_DATA (0x10D) -// ARC_TO_MEI_MAILBOX[11] is a special location used to indicate -// page swap requests. -#if defined(CONFIG_DANUBE) -#define OMBOX_BASE 0xDF80 -#define ARC_TO_MEI_MAILBOX 0xDFA0 -#define IMBOX_BASE 0xDFC0 -#define MEI_TO_ARC_MAILBOX 0xDFD0 -#elif defined(CONFIG_AMAZON_SE) || defined(CONFIG_AR9) || defined(CONFIG_VR9) -#define OMBOX_BASE 0xAF80 -#define ARC_TO_MEI_MAILBOX 0xAFA0 -#define IMBOX_BASE 0xAFC0 -#define MEI_TO_ARC_MAILBOX 0xAFD0 -#endif - -#define MEI_TO_ARC_MAILBOXR (MEI_TO_ARC_MAILBOX + 0x2C) -#define ARC_MEI_MAILBOXR (ARC_TO_MEI_MAILBOX + 0x2C) -#define OMBOX1 (OMBOX_BASE+0x4) - -// Codeswap request messages are indicated by setting BIT31 -#define OMB_CODESWAP_MESSAGE_MSG_TYPE_MASK (0x80000000) - -// Clear Eoc messages received are indicated by setting BIT17 -#define OMB_CLEAREOC_INTERRUPT_CODE (0x00020000) -#define OMB_REBOOT_INTERRUPT_CODE (1 << 18) - -/* -** Swap page header -*/ -// Page must be loaded at boot time if size field has BIT31 set -#define BOOT_FLAG (BIT31) -#define BOOT_FLAG_MASK ~BOOT_FLAG - -#define FREE_RELOAD 1 -#define FREE_SHOWTIME 2 -#define FREE_ALL 3 - -// marcos -#define IFX_MEI_WRITE_REGISTER_L(data,addr) *((volatile u32*)(addr)) = (u32)(data) -#define IFX_MEI_READ_REGISTER_L(addr) (*((volatile u32*)(addr))) -#define SET_BIT(reg, mask) reg |= (mask) -#define CLEAR_BIT(reg, mask) reg &= (~mask) -#define CLEAR_BITS(reg, mask) CLEAR_BIT(reg, mask) -//#define SET_BITS(reg, mask) SET_BIT(reg, mask) -#define SET_BITFIELD(reg, mask, off, val) {reg &= (~mask); reg |= (val << off);} - -#define ALIGN_SIZE ( 1L<<10 ) //1K size align -#define MEM_ALIGN(addr) (((addr) + ALIGN_SIZE - 1) & ~ (ALIGN_SIZE -1) ) - -// swap marco -#define MEI_HALF_WORD_SWAP(data) {data = ((data & 0xffff)<<16) + ((data & 0xffff0000)>>16);} -#define MEI_BYTE_SWAP(data) {data = ((data & 0xff)<<24) + ((data & 0xff00)<<8)+ ((data & 0xff0000)>>8)+ ((data & 0xff000000)>>24);} - - -#ifdef CONFIG_PROC_FS -typedef struct reg_entry -{ - int *flag; - char name[30]; /* big enough to hold names */ - char description[100]; /* big enough to hold description */ - unsigned short low_ino; -} reg_entry_t; -#endif -// Swap page header describes size in 32-bit words, load location, and image offset -// for program and/or data segments -typedef struct _arc_swp_page_hdr { - u32 p_offset; //Offset bytes of progseg from beginning of image - u32 p_dest; //Destination addr of progseg on processor - u32 p_size; //Size in 32-bitwords of program segment - u32 d_offset; //Offset bytes of dataseg from beginning of image - u32 d_dest; //Destination addr of dataseg on processor - u32 d_size; //Size in 32-bitwords of data segment -} ARC_SWP_PAGE_HDR; - -/* -** Swap image header -*/ -#define GET_PROG 0 // Flag used for program mem segment -#define GET_DATA 1 // Flag used for data mem segment - -// Image header contains size of image, checksum for image, and count of -// page headers. Following that are 'count' page headers followed by -// the code and/or data segments to be loaded -typedef struct _arc_img_hdr { - u32 size; // Size of binary image in bytes - u32 checksum; // Checksum for image - u32 count; // Count of swp pages in image - ARC_SWP_PAGE_HDR page[1]; // Should be "count" pages - '1' to make compiler happy -} ARC_IMG_HDR; - -typedef struct smmu_mem_info { - int type; - int boot; - unsigned long nCopy; - unsigned long size; - unsigned char *address; - unsigned char *org_address; -} smmu_mem_info_t; - -#ifdef __KERNEL__ -typedef struct ifx_mei_device_private { - int modem_ready; - int arcmsgav; - int cmv_reply; - int cmv_waiting; - // Mei to ARC CMV count, reply count, ARC Indicator count - int modem_ready_cnt; - int cmv_count; - int reply_count; - unsigned long image_size; - int nBar; - u16 Recent_indicator[MSG_LENGTH]; - - u16 CMV_RxMsg[MSG_LENGTH] __attribute__ ((aligned (4))); - - smmu_mem_info_t adsl_mem_info[MAX_BAR_REGISTERS]; - ARC_IMG_HDR *img_hdr; - // to wait for arc cmv reply, sleep on wait_queue_arcmsgav; - wait_queue_head_t wait_queue_arcmsgav; - wait_queue_head_t wait_queue_modemready; - struct semaphore mei_cmv_sema; -} ifx_mei_device_private_t; -#endif -typedef struct winhost_message { - union { - u16 RxMessage[MSG_LENGTH] __attribute__ ((aligned (4))); - u16 TxMessage[MSG_LENGTH] __attribute__ ((aligned (4))); - } msg; -} DSL_DEV_WinHost_Message_t; -/******************************************************************************************************** - * DSL CPE API Driver Stack Interface Definitions - * *****************************************************************************************************/ -/** IOCTL codes for bsp driver */ -#define DSL_IOC_MEI_BSP_MAGIC 's' - -#define DSL_FIO_BSP_DSL_START _IO (DSL_IOC_MEI_BSP_MAGIC, 0) -#define DSL_FIO_BSP_RUN _IO (DSL_IOC_MEI_BSP_MAGIC, 1) -#define DSL_FIO_BSP_FREE_RESOURCE _IO (DSL_IOC_MEI_BSP_MAGIC, 2) -#define DSL_FIO_BSP_RESET _IO (DSL_IOC_MEI_BSP_MAGIC, 3) -#define DSL_FIO_BSP_REBOOT _IO (DSL_IOC_MEI_BSP_MAGIC, 4) -#define DSL_FIO_BSP_HALT _IO (DSL_IOC_MEI_BSP_MAGIC, 5) -#define DSL_FIO_BSP_BOOTDOWNLOAD _IO (DSL_IOC_MEI_BSP_MAGIC, 6) -#define DSL_FIO_BSP_JTAG_ENABLE _IO (DSL_IOC_MEI_BSP_MAGIC, 7) -#define DSL_FIO_FREE_RESOURCE _IO (DSL_IOC_MEI_BSP_MAGIC, 8) -#define DSL_FIO_ARC_MUX_TEST _IO (DSL_IOC_MEI_BSP_MAGIC, 9) -#define DSL_FIO_BSP_REMOTE _IOW (DSL_IOC_MEI_BSP_MAGIC, 10, u32) -#define DSL_FIO_BSP_GET_BASE_ADDRESS _IOR (DSL_IOC_MEI_BSP_MAGIC, 11, u32) -#define DSL_FIO_BSP_IS_MODEM_READY _IOR (DSL_IOC_MEI_BSP_MAGIC, 12, u32) -#define DSL_FIO_BSP_GET_VERSION _IOR (DSL_IOC_MEI_BSP_MAGIC, 13, DSL_DEV_Version_t) -#define DSL_FIO_BSP_CMV_WINHOST _IOWR(DSL_IOC_MEI_BSP_MAGIC, 14, DSL_DEV_WinHost_Message_t) -#define DSL_FIO_BSP_CMV_READ _IOWR(DSL_IOC_MEI_BSP_MAGIC, 15, DSL_DEV_MeiReg_t) -#define DSL_FIO_BSP_CMV_WRITE _IOW (DSL_IOC_MEI_BSP_MAGIC, 16, DSL_DEV_MeiReg_t) -#define DSL_FIO_BSP_DEBUG_READ _IOWR(DSL_IOC_MEI_BSP_MAGIC, 17, DSL_DEV_MeiDebug_t) -#define DSL_FIO_BSP_DEBUG_WRITE _IOWR(DSL_IOC_MEI_BSP_MAGIC, 18, DSL_DEV_MeiDebug_t) -#define DSL_FIO_BSP_GET_CHIP_INFO _IOR (DSL_IOC_MEI_BSP_MAGIC, 19, DSL_DEV_HwVersion_t) - -#define DSL_DEV_MEIDEBUG_BUFFER_SIZES 512 - -typedef struct DSL_DEV_MeiDebug -{ - DSL_uint32_t iAddress; - DSL_uint32_t iCount; - DSL_uint32_t buffer[DSL_DEV_MEIDEBUG_BUFFER_SIZES]; -} DSL_DEV_MeiDebug_t; /* meidebug */ - -/** - * Structure is used for debug access only. - * Refer to configure option INCLUDE_ADSL_WINHOST_DEBUG */ -typedef struct struct_meireg -{ - /* - * Specifies that address for debug access */ - unsigned long iAddress; - /* - * Specifies the pointer to the data that has to be written or returns a - * pointer to the data that has been read out*/ - unsigned long iData; -} DSL_DEV_MeiReg_t; /* meireg */ - -typedef struct DSL_DEV_Device -{ - DSL_int_t nInUse; /* modem state, update by bsp driver, */ - DSL_void_t *pPriv; - DSL_uint32_t base_address; /* mei base address */ - DSL_int_t nIrq[2]; /* irq number */ -#define IFX_DFEIR 0 -#define IFX_DYING_GASP 1 - DSL_DEV_MeiDebug_t lop_debugwr; /* dying gasp */ -#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0)) - struct module *owner; -#endif -} DSL_DEV_Device_t; /* ifx_adsl_device_t */ - -#define DSL_DEV_PRIVATE(dev) ((ifx_mei_device_private_t*)(dev->pPriv)) - -typedef struct DSL_DEV_Version /* ifx_adsl_bsp_version */ -{ - unsigned long major; - unsigned long minor; - unsigned long revision; -} DSL_DEV_Version_t; /* ifx_adsl_bsp_version_t */ - -typedef struct DSL_DEV_ChipInfo -{ - unsigned long major; - unsigned long minor; -} DSL_DEV_HwVersion_t; - -typedef struct -{ - DSL_uint8_t dummy; -} DSL_DEV_DeviceConfig_t; - -/** error code definitions */ -typedef enum DSL_DEV_MeiError -{ - DSL_DEV_MEI_ERR_SUCCESS = 0, - DSL_DEV_MEI_ERR_FAILURE = -1, - DSL_DEV_MEI_ERR_MAILBOX_FULL = -2, - DSL_DEV_MEI_ERR_MAILBOX_EMPTY = -3, - DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT = -4 -} DSL_DEV_MeiError_t; /* MEI_ERROR */ - -typedef enum { - DSL_BSP_MEMORY_READ=0, - DSL_BSP_MEMORY_WRITE, -} DSL_BSP_MemoryAccessType_t; /* ifx_adsl_memory_access_type_t */ - -typedef enum -{ - DSL_LED_LINK_ID=0, - DSL_LED_DATA_ID -} DSL_DEV_LedId_t; /* ifx_adsl_led_id_t */ - -typedef enum -{ - DSL_LED_LINK_TYPE=0, - DSL_LED_DATA_TYPE -} DSL_DEV_LedType_t; /* ifx_adsl_led_type_t */ - -typedef enum -{ - DSL_LED_HD_CPU=0, - DSL_LED_HD_FW -} DSL_DEV_LedHandler_t; /* ifx_adsl_led_handler_t */ - -typedef enum { - DSL_LED_ON=0, - DSL_LED_OFF, - DSL_LED_FLASH, -} DSL_DEV_LedMode_t; /* ifx_adsl_led_mode_t */ - -typedef enum { - DSL_CPU_HALT=0, - DSL_CPU_RUN, - DSL_CPU_RESET, -} DSL_DEV_CpuMode_t; /* ifx_adsl_cpu_mode_t */ - -#if 0 -typedef enum { - DSL_BSP_EVENT_DYING_GASP = 0, - DSL_BSP_EVENT_CEOC_IRQ, -} DSL_BSP_Event_id_t; /* ifx_adsl_event_id_t */ - -typedef union DSL_BSP_CB_Param -{ - DSL_uint32_t nIrqMessage; -} DSL_BSP_CB_Param_t; /* ifx_adsl_cbparam_t */ - -typedef struct DSL_BSP_CB_Event -{ - DSL_BSP_Event_id_t nID; - DSL_DEV_Device_t *pDev; - DSL_BSP_CB_Param_t *pParam; -} DSL_BSP_CB_Event_t; /* ifx_adsl_cb_event_t */ -#endif - -/* external functions (from the BSP Driver) */ -extern DSL_DEV_Device_t* DSL_BSP_DriverHandleGet(int, int); -extern DSL_int_t DSL_BSP_DriverHandleDelete(DSL_DEV_Device_t *); -extern DSL_DEV_MeiError_t DSL_BSP_FWDownload(DSL_DEV_Device_t *, const DSL_char_t *, DSL_uint32_t, DSL_int32_t *, DSL_int32_t *); -extern int DSL_BSP_KernelIoctls(DSL_DEV_Device_t *, unsigned int, unsigned long); -extern DSL_DEV_MeiError_t DSL_BSP_SendCMV(DSL_DEV_Device_t *, DSL_uint16_t *, DSL_int_t, DSL_uint16_t *); -extern DSL_DEV_MeiError_t DSL_BSP_AdslLedInit(DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedType_t, DSL_DEV_LedHandler_t); -extern DSL_DEV_MeiError_t DSL_BSP_Showtime(DSL_DEV_Device_t *, DSL_uint32_t, DSL_uint32_t); -extern int DSL_BSP_ATMLedCBRegister( int (*ifx_adsl_ledcallback)(void)); -extern DSL_DEV_MeiError_t DSL_BSP_MemoryDebugAccess(DSL_DEV_Device_t *, DSL_BSP_MemoryAccessType_t, DSL_uint32_t, DSL_uint32_t *, DSL_uint32_t); -extern volatile DSL_DEV_Device_t *adsl_dev; - -/** - * Dummy structure by now to show mechanism of extended data that will be - * provided within event callback itself. - * */ -typedef struct -{ - /** - * Dummy value */ - DSL_uint32_t nDummy1; -} DSL_BSP_CB_Event1DataDummy_t; - -/** - * Dummy structure by now to show mechanism of extended data that will be - * provided within event callback itself. - * */ -typedef struct -{ - /** - * Dummy value */ - DSL_uint32_t nDummy2; -} DSL_BSP_CB_Event2DataDummy_t; - -/** - * encapsulate all data structures that are necessary for status event - * callbacks. - * */ -typedef union -{ - DSL_BSP_CB_Event1DataDummy_t dataEvent1; - DSL_BSP_CB_Event2DataDummy_t dataEvent2; -} DSL_BSP_CB_DATA_Union_t; - - -typedef enum -{ - /** - * Informs the upper layer driver (DSL CPE API) about a reboot request from the - * firmware. - * \note This event does NOT include any additional data. - * More detailed information upon reboot reason has to be requested from - * upper layer software via CMV (INFO 109) if necessary. */ - DSL_BSP_CB_FIRST = 0, - DSL_BSP_CB_DYING_GASP, - DSL_BSP_CB_CEOC_IRQ, - DSL_BSP_CB_FIRMWARE_REBOOT, - /** - * Delimiter only */ - DSL_BSP_CB_LAST -} DSL_BSP_CB_Type_t; - -/** - * Specifies the common event type that has to be used for registering and - * signalling of interrupts/autonomous status events from MEI BSP Driver. - * - * \param pDev - * Context pointer from MEI BSP Driver. - * - * \param IFX_ADSL_BSP_CallbackType_t - * Specifies the event callback type (reason of callback). Regrading to the - * setting of this value the data which is included in the following union - * might have different meanings. - * Please refer to the description of the union to get information about the - * meaning of the included data. - * - * \param pData - * Data according to \ref DSL_BSP_CB_DATA_Union_t. - * If this pointer is NULL there is no additional data available. - * - * \return depending on event - */ -typedef int (*DSL_BSP_EventCallback_t) -( - DSL_DEV_Device_t *pDev, - DSL_BSP_CB_Type_t nCallbackType, - DSL_BSP_CB_DATA_Union_t *pData -); - -typedef struct { - DSL_BSP_EventCallback_t function; - DSL_BSP_CB_Type_t event; - DSL_BSP_CB_DATA_Union_t *pData; -} DSL_BSP_EventCallBack_t; - -extern int DSL_BSP_EventCBRegister(DSL_BSP_EventCallBack_t *); -extern int DSL_BSP_EventCBUnregister(DSL_BSP_EventCallBack_t *); - -/** Modem states */ -#define DSL_DEV_STAT_InitState 0x0000 -#define DSL_DEV_STAT_ReadyState 0x0001 -#define DSL_DEV_STAT_FailState 0x0002 -#define DSL_DEV_STAT_IdleState 0x0003 -#define DSL_DEV_STAT_QuietState 0x0004 -#define DSL_DEV_STAT_GhsState 0x0005 -#define DSL_DEV_STAT_FullInitState 0x0006 -#define DSL_DEV_STAT_ShowTimeState 0x0007 -#define DSL_DEV_STAT_FastRetrainState 0x0008 -#define DSL_DEV_STAT_LoopDiagMode 0x0009 -#define DSL_DEV_STAT_ShortInit 0x000A /* Bis short initialization */ - -#define DSL_DEV_STAT_CODESWAP_COMPLETE 0x0002 - -#endif //IFXMIPS_MEI_H diff --git a/package/lqdsl/src/lantiq_mei.c b/package/lqdsl/src/lantiq_mei.c deleted file mode 100644 index 7eeab33686..0000000000 --- a/package/lqdsl/src/lantiq_mei.c +++ /dev/null @@ -1,3002 +0,0 @@ -/****************************************************************************** - - Copyright (c) 2009 - Infineon Technologies AG - Am Campeon 1-12; 81726 Munich, Germany - - For licensing information, see the file 'LICENSE' in the root folder of - this software module. - -******************************************************************************/ - -/*! - \defgroup AMAZON_S_MEI Amazon-S MEI Driver Module - \brief Amazon-S MEI driver module - */ - -/*! - \defgroup Internal Compile Parametere - \ingroup AMAZON_S_MEI - \brief exported functions for other driver use - */ - -/*! - \file amazon_s_mei_bsp.c - \ingroup AMAZON_S_MEI - \brief Amazon-S MEI driver file - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include "ifxmips_atm.h" -#define IFX_MEI_BSP -#include "ifxmips_mei_interface.h" - -/*#define LQ_RCU_RST IFX_RCU_RST_REQ -#define LQ_RCU_RST_REQ_ARC_JTAG IFX_RCU_RST_REQ_ARC_JTAG -#define LQ_RCU_RST_REQ_DFE IFX_RCU_RST_REQ_DFE -#define LQ_RCU_RST_REQ_AFE IFX_RCU_RST_REQ_AFE -#define IFXMIPS_FUSE_BASE_ADDR IFX_FUSE_BASE_ADDR -#define IFXMIPS_ICU_IM0_IER IFX_ICU_IM0_IER -#define IFXMIPS_ICU_IM2_IER IFX_ICU_IM2_IER -#define LQ_MEI_INT IFX_MEI_INT -#define LQ_MEI_DYING_GASP_INT IFX_MEI_DYING_GASP_INT -#define LQ_MEI_BASE_ADDR IFX_MEI_SPACE_ACCESS -#define IFXMIPS_PMU_PWDCR IFX_PMU_PWDCR -#define IFXMIPS_MPS_CHIPID IFX_MPS_CHIPID - -#define ifxmips_port_reserve_pin ifx_gpio_pin_reserve -#define ifxmips_port_set_dir_in ifx_gpio_dir_in_set -#define ifxmips_port_clear_altsel0 ifx_gpio_altsel0_set -#define ifxmips_port_clear_altsel1 ifx_gpio_altsel1_clear -#define ifxmips_port_set_open_drain ifx_gpio_open_drain_clear -#define ifxmips_port_free_pin ifx_gpio_pin_free -#define ifxmips_mask_and_ack_irq bsp_mask_and_ack_irq -#define IFXMIPS_MPS_CHIPID_VERSION_GET IFX_MCD_CHIPID_VERSION_GET -#define lq_r32(reg) __raw_readl(reg) -#define lq_w32(val, reg) __raw_writel(val, reg) -#define lq_w32_mask(clear, set, reg) lq_w32((lq_r32(reg) & ~clear) | set, reg) -*/ - -#define LQ_RCU_RST_REQ_DFE (1 << 7) -#define LQ_RCU_RST_REQ_AFE (1 << 11) -#define LQ_PMU_PWDCR ((u32 *)(LQ_PMU_BASE_ADDR + 0x001C)) -#define LQ_PMU_PWDSR ((u32 *)(LQ_PMU_BASE_ADDR + 0x0020)) -#define LQ_RCU_RST ((u32 *)(LQ_RCU_BASE_ADDR + 0x0010)) -#define LQ_RCU_RST_ALL 0x40000000 -#define LQ_ICU_BASE_ADDR (KSEG1 | 0x1F880200) - -#define LQ_ICU_IM0_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0000)) -#define LQ_ICU_IM0_IER ((u32 *)(LQ_ICU_BASE_ADDR + 0x0008)) -#define LQ_ICU_IM0_IOSR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0010)) -#define LQ_ICU_IM0_IRSR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0018)) -#define LQ_ICU_IM0_IMR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0020)) - - -#define LQ_ICU_IM1_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0028)) -#define LQ_ICU_IM2_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0050)) -#define LQ_ICU_IM3_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0078)) -#define LQ_ICU_IM4_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x00A0)) - -#define LQ_ICU_OFFSET (LQ_ICU_IM1_ISR - LQ_ICU_IM0_ISR) -#define LQ_ICU_IM2_IER (LQ_ICU_IM0_IER + LQ_ICU_OFFSET) - -#define IFX_MEI_EMSG(fmt, args...) pr_err("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args) -#define IFX_MEI_DMSG(fmt, args...) pr_debug("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args) - -#define LQ_FUSE_BASE (KSEG1 + 0x1F107354) - -#ifdef CONFIG_LQ_MEI_FW_LOOPBACK -//#define DFE_MEM_TEST -//#define DFE_PING_TEST -#define DFE_ATM_LOOPBACK - - -#ifdef DFE_ATM_LOOPBACK -#include -#endif - -void dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev); - -#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK - -DSL_DEV_Version_t bsp_mei_version = { - major: 5, - minor: 0, - revision:0 -}; -DSL_DEV_HwVersion_t bsp_chip_info; - -#define IFX_MEI_DEVNAME "ifx_mei" -#define BSP_MAX_DEVICES 1 - -DSL_DEV_MeiError_t DSL_BSP_FWDownload (DSL_DEV_Device_t *, const char *, unsigned long, long *, long *); -DSL_DEV_MeiError_t DSL_BSP_Showtime (DSL_DEV_Device_t *, DSL_uint32_t, DSL_uint32_t); -DSL_DEV_MeiError_t DSL_BSP_AdslLedInit (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedType_t, DSL_DEV_LedHandler_t); -//DSL_DEV_MeiError_t DSL_BSP_AdslLedSet (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedMode_t); -DSL_DEV_MeiError_t DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t *, DSL_BSP_MemoryAccessType_t, DSL_uint32_t, DSL_uint32_t*, DSL_uint32_t); -DSL_DEV_MeiError_t DSL_BSP_SendCMV (DSL_DEV_Device_t *, u16 *, int, u16 *); - -int DSL_BSP_KernelIoctls (DSL_DEV_Device_t *, unsigned int, unsigned long); - -static DSL_DEV_MeiError_t IFX_MEI_RunAdslModem (DSL_DEV_Device_t *); -static DSL_DEV_MeiError_t IFX_MEI_CpuModeSet (DSL_DEV_Device_t *, DSL_DEV_CpuMode_t); -static DSL_DEV_MeiError_t IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *); -static DSL_DEV_MeiError_t IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *, int); -static DSL_DEV_MeiError_t IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *, int); - -static int IFX_MEI_GetPage (DSL_DEV_Device_t *, u32, u32, u32, u32 *, u32 *); -static int IFX_MEI_BarUpdate (DSL_DEV_Device_t *, int); - -static ssize_t IFX_MEI_Write (DSL_DRV_file_t *, const char *, size_t, loff_t *); -static int IFX_MEI_UserIoctls (DSL_DRV_inode_t *, DSL_DRV_file_t *, unsigned int, unsigned long); -static int IFX_MEI_Open (DSL_DRV_inode_t *, DSL_DRV_file_t *); -static int IFX_MEI_Release (DSL_DRV_inode_t *, DSL_DRV_file_t *); - -void AMAZON_SE_MEI_ARC_MUX_Test(void); - -#ifdef CONFIG_PROC_FS -static int IFX_MEI_ProcRead (struct file *, char *, size_t, loff_t *); -static ssize_t IFX_MEI_ProcWrite (struct file *, const char *, size_t, loff_t *); - -#define PROC_ITEMS 11 -#define MEI_DIRNAME "ifxmips_mei" - -static struct proc_dir_entry *meidir; -static struct file_operations IFX_MEI_ProcOperations = { - read:IFX_MEI_ProcRead, - write:IFX_MEI_ProcWrite, -}; -static reg_entry_t regs[BSP_MAX_DEVICES][PROC_ITEMS]; //total items to be monitored by /proc/mei -#define NUM_OF_REG_ENTRY (sizeof(regs[0])/sizeof(reg_entry_t)) -#endif //CONFIG_PROC_FS - -void IFX_MEI_ARC_MUX_Test(void); - -static int adsl_dummy_ledcallback(void); - -int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *) = NULL; -EXPORT_SYMBOL(ifx_mei_atm_showtime_enter); - -int (*ifx_mei_atm_showtime_exit)(void) = NULL; -EXPORT_SYMBOL(ifx_mei_atm_showtime_exit); - -static int (*g_adsl_ledcallback)(void) = adsl_dummy_ledcallback; - -static unsigned int g_tx_link_rate[2] = {0}; - -static void *g_xdata_addr = NULL; - -static u32 *mei_arc_swap_buff = NULL; // holding swap pages - -extern void lq_mask_and_ack_irq(unsigned int irq_nr); -#define MEI_MASK_AND_ACK_IRQ lq_mask_and_ack_irq - -#define MEI_MAJOR 105 -static int dev_major = MEI_MAJOR; - -static struct file_operations bsp_mei_operations = { - owner:THIS_MODULE, - open:IFX_MEI_Open, - release:IFX_MEI_Release, - write:IFX_MEI_Write, - ioctl:IFX_MEI_UserIoctls, -}; - -static DSL_DEV_Device_t dsl_devices[BSP_MAX_DEVICES]; - -static ifx_mei_device_private_t - sDanube_Mei_Private[BSP_MAX_DEVICES]; - -static DSL_BSP_EventCallBack_t dsl_bsp_event_callback[DSL_BSP_CB_LAST + 1]; - -/** - * Write a value to register - * This function writes a value to danube register - * - * \param ul_address The address to write - * \param ul_data The value to write - * \ingroup Internal - */ -static void -IFX_MEI_LongWordWrite (u32 ul_address, u32 ul_data) -{ - IFX_MEI_WRITE_REGISTER_L (ul_data, ul_address); - wmb(); - return; -} - -/** - * Write a value to register - * This function writes a value to danube register - * - * \param pDev the device pointer - * \param ul_address The address to write - * \param ul_data The value to write - * \ingroup Internal - */ -static void -IFX_MEI_LongWordWriteOffset (DSL_DEV_Device_t * pDev, u32 ul_address, - u32 ul_data) -{ - IFX_MEI_WRITE_REGISTER_L (ul_data, pDev->base_address + ul_address); - wmb(); - return; -} - -/** - * Read the danube register - * This function read the value from danube register - * - * \param ul_address The address to write - * \param pul_data Pointer to the data - * \ingroup Internal - */ -static void -IFX_MEI_LongWordRead (u32 ul_address, u32 * pul_data) -{ - *pul_data = IFX_MEI_READ_REGISTER_L (ul_address); - rmb(); - return; -} - -/** - * Read the danube register - * This function read the value from danube register - * - * \param pDev the device pointer - * \param ul_address The address to write - * \param pul_data Pointer to the data - * \ingroup Internal - */ -static void -IFX_MEI_LongWordReadOffset (DSL_DEV_Device_t * pDev, u32 ul_address, - u32 * pul_data) -{ - *pul_data = IFX_MEI_READ_REGISTER_L (pDev->base_address + ul_address); - rmb(); - return; -} - -/** - * Write several DWORD datas to ARC memory via ARC DMA interface - * This function writes several DWORD datas to ARC memory via DMA interface. - * - * \param pDev the device pointer - * \param destaddr The address to write - * \param databuff Pointer to the data buffer - * \param databuffsize Number of DWORDs to write - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_DMAWrite (DSL_DEV_Device_t * pDev, u32 destaddr, - u32 * databuff, u32 databuffsize) -{ - u32 *p = databuff; - u32 temp; - - if (destaddr & 3) - return DSL_DEV_MEI_ERR_FAILURE; - - // Set the write transfer address - IFX_MEI_LongWordWriteOffset (pDev, ME_DX_AD, destaddr); - - // Write the data pushed across DMA - while (databuffsize--) { - temp = *p; - if (destaddr == MEI_TO_ARC_MAILBOX) - MEI_HALF_WORD_SWAP (temp); - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_DATA, temp); - p++; - } - - return DSL_DEV_MEI_ERR_SUCCESS; - -} - -/** - * Read several DWORD datas from ARC memory via ARC DMA interface - * This function reads several DWORD datas from ARC memory via DMA interface. - * - * \param pDev the device pointer - * \param srcaddr The address to read - * \param databuff Pointer to the data buffer - * \param databuffsize Number of DWORDs to read - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_DMARead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff, - u32 databuffsize) -{ - u32 *p = databuff; - u32 temp; - - if (srcaddr & 3) - return DSL_DEV_MEI_ERR_FAILURE; - - // Set the read transfer address - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_AD, srcaddr); - - // Read the data popped across DMA - while (databuffsize--) { - IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DX_DATA, &temp); - if (databuff == (u32 *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg) // swap half word - MEI_HALF_WORD_SWAP (temp); - *p = temp; - p++; - } - - return DSL_DEV_MEI_ERR_SUCCESS; - -} - -/** - * Switch the ARC control mode - * This function switchs the ARC control mode to JTAG mode or MEI mode - * - * \param pDev the device pointer - * \param mode The mode want to switch: JTAG_MASTER_MODE or MEI_MASTER_MODE. - * \ingroup Internal - */ -static void -IFX_MEI_ControlModeSet (DSL_DEV_Device_t * pDev, int mode) -{ - u32 temp = 0x0; - - IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_MASTER, &temp); - switch (mode) { - case JTAG_MASTER_MODE: - temp &= ~(HOST_MSTR); - break; - case MEI_MASTER_MODE: - temp |= (HOST_MSTR); - break; - default: - IFX_MEI_EMSG ("IFX_MEI_ControlModeSet: unkonwn mode [%d]\n", mode); - return; - } - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_MASTER, temp); -} - -/** - * Disable ARC to MEI interrupt - * - * \param pDev the device pointer - * \ingroup Internal - */ -static void -IFX_MEI_IRQDisable (DSL_DEV_Device_t * pDev) -{ - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK, 0x0); -} - -/** - * Eable ARC to MEI interrupt - * - * \param pDev the device pointer - * \ingroup Internal - */ -static void -IFX_MEI_IRQEnable (DSL_DEV_Device_t * pDev) -{ - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK, MSGAV_EN); -} - -/** - * Poll for transaction complete signal - * This function polls and waits for transaction complete signal. - * - * \param pDev the device pointer - * \ingroup Internal - */ -static void -meiPollForDbgDone (DSL_DEV_Device_t * pDev) -{ - u32 query = 0; - int i = 0; - - while (i < WHILE_DELAY) { - IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ARC2ME_STAT, &query); - query &= (ARC_TO_MEI_DBG_DONE); - if (query) - break; - i++; - if (i == WHILE_DELAY) { - IFX_MEI_EMSG ("PollforDbg fail!\n"); - } - } - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_DBG_DONE); // to clear this interrupt -} - -/** - * ARC Debug Memory Access for a single DWORD reading. - * This function used for direct, address-based access to ARC memory. - * - * \param pDev the device pointer - * \param DEC_mode ARC memory space to used - * \param address Address to read - * \param data Pointer to data - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -_IFX_MEI_DBGLongWordRead (DSL_DEV_Device_t * pDev, u32 DEC_mode, - u32 address, u32 * data) -{ - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode); - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_RD_AD, address); - meiPollForDbgDone (pDev); - IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_DATA, data); - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * ARC Debug Memory Access for a single DWORD writing. - * This function used for direct, address-based access to ARC memory. - * - * \param pDev the device pointer - * \param DEC_mode ARC memory space to used - * \param address The address to write - * \param data The data to write - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -_IFX_MEI_DBGLongWordWrite (DSL_DEV_Device_t * pDev, u32 DEC_mode, - u32 address, u32 data) -{ - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode); - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_WR_AD, address); - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DATA, data); - meiPollForDbgDone (pDev); - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * ARC Debug Memory Access for writing. - * This function used for direct, address-based access to ARC memory. - * - * \param pDev the device pointer - * \param destaddr The address to read - * \param databuffer Pointer to data - * \param databuffsize The number of DWORDs to read - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ - -static DSL_DEV_MeiError_t -IFX_MEI_DebugWrite (DSL_DEV_Device_t * pDev, u32 destaddr, - u32 * databuff, u32 databuffsize) -{ - u32 i; - u32 temp = 0x0; - u32 address = 0x0; - u32 *buffer = 0x0; - - // Open the debug port before DMP memory write - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - - // For the requested length, write the address and write the data - address = destaddr; - buffer = databuff; - for (i = 0; i < databuffsize; i++) { - temp = *buffer; - _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK, address, temp); - address += 4; - buffer++; - } - - // Close the debug port after DMP memory write - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * ARC Debug Memory Access for reading. - * This function used for direct, address-based access to ARC memory. - * - * \param pDev the device pointer - * \param srcaddr The address to read - * \param databuffer Pointer to data - * \param databuffsize The number of DWORDs to read - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_DebugRead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff, u32 databuffsize) -{ - u32 i; - u32 temp = 0x0; - u32 address = 0x0; - u32 *buffer = 0x0; - - // Open the debug port before DMP memory read - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - - // For the requested length, write the address and read the data - address = srcaddr; - buffer = databuff; - for (i = 0; i < databuffsize; i++) { - _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK, address, &temp); - *buffer = temp; - address += 4; - buffer++; - } - - // Close the debug port after DMP memory read - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * Send a message to ARC MailBox. - * This function sends a message to ARC Mailbox via ARC DMA interface. - * - * \param pDev the device pointer - * \param msgsrcbuffer Pointer to message. - * \param msgsize The number of words to write. - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_MailboxWrite (DSL_DEV_Device_t * pDev, u16 * msgsrcbuffer, - u16 msgsize) -{ - int i; - u32 arc_mailbox_status = 0x0; - u32 temp = 0; - DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS; - - // Write to mailbox - meiMailboxError = - IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOX, (u32 *) msgsrcbuffer, msgsize / 2); - meiMailboxError = - IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOXR, (u32 *) (&temp), 1); - - // Notify arc that mailbox write completed - DSL_DEV_PRIVATE(pDev)->cmv_waiting = 1; - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV); - - i = 0; - while (i < WHILE_DELAY) { // wait for ARC to clear the bit - IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ME2ARC_INT, &arc_mailbox_status); - if ((arc_mailbox_status & MEI_TO_ARC_MSGAV) != MEI_TO_ARC_MSGAV) - break; - i++; - if (i == WHILE_DELAY) { - IFX_MEI_EMSG (">>> Timeout waiting for ARC to clear MEI_TO_ARC_MSGAV!!!" - " MEI_TO_ARC message size = %d DWORDs <<<\n", msgsize/2); - meiMailboxError = DSL_DEV_MEI_ERR_FAILURE; - } - } - - return meiMailboxError; -} - -/** - * Read a message from ARC MailBox. - * This function reads a message from ARC Mailbox via ARC DMA interface. - * - * \param pDev the device pointer - * \param msgsrcbuffer Pointer to message. - * \param msgsize The number of words to read - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_MailboxRead (DSL_DEV_Device_t * pDev, u16 * msgdestbuffer, - u16 msgsize) -{ - DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS; - // Read from mailbox - meiMailboxError = - IFX_MEI_DMARead (pDev, ARC_TO_MEI_MAILBOX, (u32 *) msgdestbuffer, msgsize / 2); - - // Notify arc that mailbox read completed - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); - - return meiMailboxError; -} - -/** - * Download boot pages to ARC. - * This function downloads boot pages to ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_DownloadBootPages (DSL_DEV_Device_t * pDev) -{ - int boot_loop; - int page_size; - u32 dest_addr; - - /* - ** DMA the boot code page(s) - */ - - for (boot_loop = 1; - boot_loop < - (DSL_DEV_PRIVATE(pDev)->img_hdr-> count); boot_loop++) { - if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].p_size) & BOOT_FLAG) { - page_size = IFX_MEI_GetPage (pDev, boot_loop, - GET_PROG, MAXSWAPSIZE, - mei_arc_swap_buff, - &dest_addr); - if (page_size > 0) { - IFX_MEI_DMAWrite (pDev, dest_addr, - mei_arc_swap_buff, - page_size); - } - } - if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].d_size) & BOOT_FLAG) { - page_size = IFX_MEI_GetPage (pDev, boot_loop, - GET_DATA, MAXSWAPSIZE, - mei_arc_swap_buff, - &dest_addr); - if (page_size > 0) { - IFX_MEI_DMAWrite (pDev, dest_addr, - mei_arc_swap_buff, - page_size); - } - } - } - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * Initial efuse rar. - **/ -static void -IFX_MEI_FuseInit (DSL_DEV_Device_t * pDev) -{ - u32 data = 0; - IFX_MEI_DMAWrite (pDev, IRAM0_BASE, &data, 1); - IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, &data, 1); - IFX_MEI_DMAWrite (pDev, IRAM1_BASE, &data, 1); - IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, &data, 1); - IFX_MEI_DMAWrite (pDev, BRAM_BASE, &data, 1); - IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, &data, 1); - IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, &data, 1); - IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, &data, 1); -} - -/** - * efuse rar program - **/ -static void -IFX_MEI_FuseProg (DSL_DEV_Device_t * pDev) -{ - u32 reg_data, fuse_value; - int i = 0; - - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); - while ((reg_data & 0x10000000) == 0) { - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); - i++; - /* 0x4000 translate to about 16 ms@111M, so should be enough */ - if (i == 0x4000) - return; - } - // STEP a: Prepare memory for external accesses - // Write fuse_en bit24 - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); - IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data | (1 << 24)); - - IFX_MEI_FuseInit (pDev); - for (i = 0; i < 4; i++) { - IFX_MEI_LongWordRead ((u32) (LQ_FUSE_BASE) + i * 4, &fuse_value); - switch (fuse_value & 0xF0000) { - case 0x80000: - reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) | - (RX_DILV_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, ®_data, 1); - break; - case 0x90000: - reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) | - (RX_DILV_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, ®_data, 1); - break; - case 0xA0000: - reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) | - (IRAM0_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, IRAM0_BASE, ®_data, 1); - break; - case 0xB0000: - reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) | - (IRAM0_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, ®_data, 1); - break; - case 0xC0000: - reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) | - (IRAM1_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, IRAM1_BASE, ®_data, 1); - break; - case 0xD0000: - reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) | - (IRAM1_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, ®_data, 1); - break; - case 0xE0000: - reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) | - (BRAM_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, BRAM_BASE, ®_data, 1); - break; - case 0xF0000: - reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) | - (BRAM_ADDR_BIT_MASK + 0x1)); - IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, ®_data, 1); - break; - default: // PPE efuse - break; - } - } - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); - IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data & ~(1 << 24)); - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); -} - -/** - * Enable DFE Clock - * This function enables DFE Clock - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_EnableCLK (DSL_DEV_Device_t * pDev) -{ - u32 arc_debug_data = 0; - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - //enable ac_clk signal - _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK, - CRI_CCR0, &arc_debug_data); - arc_debug_data |= ACL_CLK_MODE_ENABLE; - _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK, - CRI_CCR0, arc_debug_data); - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * Halt the ARC. - * This function halts the ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_HaltArc (DSL_DEV_Device_t * pDev) -{ - u32 arc_debug_data = 0x0; - - // Switch arc control from JTAG mode to MEI mode - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK, - ARC_DEBUG, &arc_debug_data); - arc_debug_data |= ARC_DEBUG_HALT; - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, - ARC_DEBUG, arc_debug_data); - // Switch arc control from MEI mode to JTAG mode - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - MEI_WAIT (10); - - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * Run the ARC. - * This function runs the ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_RunArc (DSL_DEV_Device_t * pDev) -{ - u32 arc_debug_data = 0x0; - - // Switch arc control from JTAG mode to MEI mode- write '1' to bit0 - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK, - AUX_STATUS, &arc_debug_data); - - // Write debug data reg with content ANDd with 0xFDFFFFFF (halt bit cleared) - arc_debug_data &= ~ARC_AUX_HALT; - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, - AUX_STATUS, arc_debug_data); - - // Switch arc control from MEI mode to JTAG mode- write '0' to bit0 - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - // Enable mask for arc codeswap interrupts - IFX_MEI_IRQEnable (pDev); - - return DSL_DEV_MEI_ERR_SUCCESS; - -} - -/** - * Reset the ARC. - * This function resets the ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_ResetARC (DSL_DEV_Device_t * pDev) -{ - u32 arc_debug_data = 0; - - IFX_MEI_HaltArc (pDev); - - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, &arc_debug_data); - IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, - arc_debug_data | LQ_RCU_RST_REQ_DFE | LQ_RCU_RST_REQ_AFE); - - // reset ARC - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, MEI_SOFT_RESET); - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, 0); - - IFX_MEI_IRQDisable (pDev); - - IFX_MEI_EnableCLK (pDev); - -#if 0 - // reset part of PPE - *(unsigned long *) (BSP_PPE32_SRST) = 0xC30; - *(unsigned long *) (BSP_PPE32_SRST) = 0xFFF; -#endif - - DSL_DEV_PRIVATE(pDev)->modem_ready = 0; - - return DSL_DEV_MEI_ERR_SUCCESS; -} - -DSL_DEV_MeiError_t -DSL_BSP_Showtime (DSL_DEV_Device_t * dev, DSL_uint32_t rate_fast, DSL_uint32_t rate_intl) -{ - struct port_cell_info port_cell = {0}; - - IFX_MEI_EMSG ("Datarate US intl = %d, fast = %d\n", (int)rate_intl, - (int)rate_fast); - - if ( rate_fast ) - g_tx_link_rate[0] = rate_fast / (53 * 8); - if ( rate_intl ) - g_tx_link_rate[1] = rate_intl / (53 * 8); - - if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ) { - IFX_MEI_EMSG ("Got rate fail.\n"); - } - - if ( ifx_mei_atm_showtime_enter ) - { - port_cell.port_num = 2; - port_cell.tx_link_rate[0] = g_tx_link_rate[0]; - port_cell.tx_link_rate[1] = g_tx_link_rate[1]; - ifx_mei_atm_showtime_enter(&port_cell, g_xdata_addr); - } - else - { - IFX_MEI_EMSG("no hookup from ATM driver to set cell rate\n"); - } - - return DSL_DEV_MEI_ERR_SUCCESS; -}; - -/** - * Reset/halt/run the DFE. - * This function provide operations to reset/halt/run the DFE. - * - * \param pDev the device pointer - * \param mode which operation want to do - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_CpuModeSet (DSL_DEV_Device_t *pDev, - DSL_DEV_CpuMode_t mode) -{ - DSL_DEV_MeiError_t err_ret = DSL_DEV_MEI_ERR_FAILURE; - switch (mode) { - case DSL_CPU_HALT: - err_ret = IFX_MEI_HaltArc (pDev); - break; - case DSL_CPU_RUN: - err_ret = IFX_MEI_RunArc (pDev); - break; - case DSL_CPU_RESET: - err_ret = IFX_MEI_ResetARC (pDev); - break; - default: - break; - } - return err_ret; -} - -/** - * Accress DFE memory. - * This function provide a way to access DFE memory; - * - * \param pDev the device pointer - * \param type read or write - * \param destaddr destination address - * \param databuff pointer to hold data - * \param databuffsize size want to read/write - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -DSL_DEV_MeiError_t -DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t * pDev, - DSL_BSP_MemoryAccessType_t type, - DSL_uint32_t destaddr, DSL_uint32_t *databuff, - DSL_uint32_t databuffsize) -{ - DSL_DEV_MeiError_t meierr = DSL_DEV_MEI_ERR_SUCCESS; - switch (type) { - case DSL_BSP_MEMORY_READ: - meierr = IFX_MEI_DebugRead (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize); - break; - case DSL_BSP_MEMORY_WRITE: - meierr = IFX_MEI_DebugWrite (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize); - break; - } - return DSL_DEV_MEI_ERR_SUCCESS; -}; - -/** - * Download boot code to ARC. - * This function downloads boot code to ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *pDev) -{ - IFX_MEI_IRQDisable (pDev); - - IFX_MEI_EnableCLK (pDev); - - IFX_MEI_FuseProg (pDev); //program fuse rar - - IFX_MEI_DownloadBootPages (pDev); - - return DSL_DEV_MEI_ERR_SUCCESS; -}; - -/** - * Enable Jtag debugger interface - * This function setups mips gpio to enable jtag debugger - * - * \param pDev the device pointer - * \param enable enable or disable - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *dev, int enable) -{ - /* - int meierr=0; - u32 reg_data; - switch (enable) { - case 1: - //reserve gpio 9, 10, 11, 14, 19 for ARC JTAG - ifxmips_port_reserve_pin (0, 9); - ifxmips_port_reserve_pin (0, 10); - ifxmips_port_reserve_pin (0, 11); - ifxmips_port_reserve_pin (0, 14); - ifxmips_port_reserve_pin (1, 3); - - ifxmips_port_set_dir_in(0, 11); - ifxmips_port_clear_altsel0(0, 11); - ifxmips_port_clear_altsel1(0, 11); - ifxmips_port_set_open_drain(0, 11); - //enable ARC JTAG - IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); - IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data | LQ_RCU_RST_REQ_ARC_JTAG); - break; - case 0: - default: - break; - } -jtag_end: - if (meierr) - return DSL_DEV_MEI_ERR_FAILURE; -*/ - printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__); - printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__); - - return DSL_DEV_MEI_ERR_SUCCESS; -}; - -/** - * Enable DFE to MIPS interrupt - * This function enable DFE to MIPS interrupt - * - * \param pDev the device pointer - * \param enable enable or disable - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *pDev, int enable) -{ - DSL_DEV_MeiError_t meierr; - switch (enable) { - case 0: - meierr = DSL_DEV_MEI_ERR_SUCCESS; - IFX_MEI_IRQDisable (pDev); - break; - case 1: - IFX_MEI_IRQEnable (pDev); - meierr = DSL_DEV_MEI_ERR_SUCCESS; - break; - default: - meierr = DSL_DEV_MEI_ERR_FAILURE; - break; - - } - return meierr; -} - -/** - * Get the modem status - * This function return the modem status - * - * \param pDev the device pointer - * \return 1: modem ready 0: not ready - * \ingroup Internal - */ -static int -IFX_MEI_IsModemReady (DSL_DEV_Device_t * pDev) -{ - return DSL_DEV_PRIVATE(pDev)->modem_ready; -} - -DSL_DEV_MeiError_t -DSL_BSP_AdslLedInit (DSL_DEV_Device_t * dev, - DSL_DEV_LedId_t led_number, - DSL_DEV_LedType_t type, - DSL_DEV_LedHandler_t handler) -{ -#if 0 - struct led_config_param param; - if (led_number == DSL_LED_LINK_ID && type == DSL_LED_LINK_TYPE && handler == /*DSL_LED_HD_CPU*/DSL_LED_HD_FW) { - param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE; - param.led = 0x01; - param.source = 0x01; -// bsp_led_config (¶m); - - } else if (led_number == DSL_LED_DATA_ID && type == DSL_LED_DATA_TYPE && (handler == DSL_LED_HD_FW)) { - param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE; - param.led = 0x02; - param.source = 0x02; -// bsp_led_config (¶m); - } -#endif - return DSL_DEV_MEI_ERR_SUCCESS; -}; -#if 0 -DSL_DEV_MeiError_t -DSL_BSP_AdslLedSet (DSL_DEV_Device_t * dev, DSL_DEV_LedId_t led_number, DSL_DEV_LedMode_t mode) -{ - printk(KERN_INFO "[%s %d]: mode = %#x, led_number = %d\n", __func__, __LINE__, mode, led_number); - switch (mode) { - case DSL_LED_OFF: - switch (led_number) { - case DSL_LED_LINK_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (1, 0); - bsp_led_set_data (1, 0); -#endif - break; - case DSL_LED_DATA_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (0, 0); - bsp_led_set_data (0, 0); -#endif - break; - } - break; - case DSL_LED_FLASH: - switch (led_number) { - case DSL_LED_LINK_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (1, 1); // data -#endif - break; - case DSL_LED_DATA_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (0, 1); // data -#endif - break; - } - break; - case DSL_LED_ON: - switch (led_number) { - case DSL_LED_LINK_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (1, 0); - bsp_led_set_data (1, 1); -#endif - break; - case DSL_LED_DATA_ID: -#ifdef CONFIG_BSP_LED - bsp_led_set_blink (0, 0); - bsp_led_set_data (0, 1); -#endif - break; - } - break; - } - return DSL_DEV_MEI_ERR_SUCCESS; -}; - -#endif - -/** -* Compose a message. -* This function compose a message from opcode, group, address, index, size, and data -* -* \param opcode The message opcode -* \param group The message group number -* \param address The message address. -* \param index The message index. -* \param size The number of words to read/write. -* \param data The pointer to data. -* \param CMVMSG The pointer to message buffer. -* \ingroup Internal -*/ -void -makeCMV (u8 opcode, u8 group, u16 address, u16 index, int size, u16 * data, u16 *CMVMSG) -{ - memset (CMVMSG, 0, MSG_LENGTH * 2); - CMVMSG[0] = (opcode << 4) + (size & 0xf); - CMVMSG[1] = (((index == 0) ? 0 : 1) << 7) + (group & 0x7f); - CMVMSG[2] = address; - CMVMSG[3] = index; - if (opcode == H2D_CMV_WRITE) - memcpy (CMVMSG + 4, data, size * 2); - return; -} - -/** - * Send a message to ARC and read the response - * This function sends a message to arc, waits the response, and reads the responses. - * - * \param pDev the device pointer - * \param request Pointer to the request - * \param reply Wait reply or not. - * \param response Pointer to the response - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -DSL_DEV_MeiError_t -DSL_BSP_SendCMV (DSL_DEV_Device_t * pDev, u16 * request, int reply, u16 * response) // write cmv to arc, if reply needed, wait for reply -{ - DSL_DEV_MeiError_t meierror; -#if defined(BSP_PORT_RTEMS) - int delay_counter = 0; -#endif - - if (MEI_MUTEX_LOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema)) - return -ERESTARTSYS; - - DSL_DEV_PRIVATE(pDev)->cmv_reply = reply; - memset (DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, 0, - sizeof (DSL_DEV_PRIVATE(pDev)-> - CMV_RxMsg)); - DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; - - meierror = IFX_MEI_MailboxWrite (pDev, request, MSG_LENGTH); - - if (meierror != DSL_DEV_MEI_ERR_SUCCESS) { - DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0; - DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; - IFX_MEI_EMSG ("MailboxWrite Fail!\n"); - IFX_MEI_EMSG ("Resetting ARC...\n"); - IFX_MEI_ResetARC(pDev); - MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); - return meierror; - } - else { - DSL_DEV_PRIVATE(pDev)->cmv_count++; - } - - if (DSL_DEV_PRIVATE(pDev)->cmv_reply == - NO_REPLY) { - MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); - return DSL_DEV_MEI_ERR_SUCCESS; - } - -#if !defined(BSP_PORT_RTEMS) - if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0) - MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav, CMV_TIMEOUT); -#else - while (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0 && delay_counter < CMV_TIMEOUT / 5) { - MEI_WAIT (5); - delay_counter++; - } -#endif - - DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0; - if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0) { //CMV_timeout - DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; - IFX_MEI_EMSG ("\%s: DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT\n", - __FUNCTION__); - MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); - return DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT; - } - else { - DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; - DSL_DEV_PRIVATE(pDev)-> - reply_count++; - memcpy (response, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2); - MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); - return DSL_DEV_MEI_ERR_SUCCESS; - } - MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/** - * Reset the ARC, download boot codes, and run the ARC. - * This function resets the ARC, downloads boot codes to ARC, and runs the ARC. - * - * \param pDev the device pointer - * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE - * \ingroup Internal - */ -static DSL_DEV_MeiError_t -IFX_MEI_RunAdslModem (DSL_DEV_Device_t *pDev) -{ - int nSize = 0, idx = 0; - uint32_t im0_register, im2_register; -// DSL_DEV_WinHost_Message_t m; - - if (mei_arc_swap_buff == NULL) { - mei_arc_swap_buff = - (u32 *) kmalloc (MAXSWAPSIZE * 4, GFP_KERNEL); - if (mei_arc_swap_buff == NULL) { - IFX_MEI_EMSG (">>> malloc fail for codeswap buff!!! <<<\n"); - return DSL_DEV_MEI_ERR_FAILURE; - } - IFX_MEI_DMSG("allocate %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff); - } - - DSL_DEV_PRIVATE(pDev)->img_hdr = - (ARC_IMG_HDR *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[0].address; - if ((DSL_DEV_PRIVATE(pDev)->img_hdr-> - count) * sizeof (ARC_SWP_PAGE_HDR) > SDRAM_SEGMENT_SIZE) { - IFX_MEI_EMSG ("firmware header size is bigger than 64K segment size\n"); - return DSL_DEV_MEI_ERR_FAILURE; - } - // check image size - for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) { - nSize += DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].nCopy; - } - if (nSize != - DSL_DEV_PRIVATE(pDev)->image_size) { - IFX_MEI_EMSG ("Firmware download is not completed. Please download firmware again!\n"); - return DSL_DEV_MEI_ERR_FAILURE; - } - // TODO: check crc - /// - - IFX_MEI_ResetARC (pDev); - IFX_MEI_HaltArc (pDev); - IFX_MEI_BarUpdate (pDev, DSL_DEV_PRIVATE(pDev)->nBar); - - //IFX_MEI_DMSG("Starting to meiDownloadBootCode\n"); - - IFX_MEI_DownloadBootCode (pDev); - - im0_register = (*LQ_ICU_IM0_IER) & (1 << 20); - im2_register = (*LQ_ICU_IM2_IER) & (1 << 20); - /* Turn off irq */ - #ifdef CONFIG_LANTIQ_AMAZON_SE - disable_irq (IFXMIPS_USB_OC_INT0); - disable_irq (IFXMIPS_USB_OC_INT2); - #elif defined(CONFIG_LANTIQ_AR9) - disable_irq (IFXMIPS_USB_OC_INT0); - disable_irq (IFXMIPS_USB_OC_INT2); - #elif defined(CONFIG_SOC_LANTIQ_XWAY) - disable_irq (LQ_USB_OC_INT); - #else - #error unkonwn arch - #endif - disable_irq (pDev->nIrq[IFX_DYING_GASP]); - - IFX_MEI_RunArc (pDev); - - MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready, 1000); - - #ifdef CONFIG_LANTIQ_AMAZON_SE - MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0); - MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2); - #elif defined(CONFIG_LANTIQ_AMAZON_S) - MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0); - MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2); - #elif defined(CONFIG_SOC_LANTIQ_XWAY) - MEI_MASK_AND_ACK_IRQ (LQ_USB_OC_INT); - #else - #error unkonwn arch - #endif - MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]); - - /* Re-enable irq */ - enable_irq(pDev->nIrq[IFX_DYING_GASP]); - *LQ_ICU_IM0_IER |= im0_register; - *LQ_ICU_IM2_IER |= im2_register; - - if (DSL_DEV_PRIVATE(pDev)->modem_ready != 1) { - IFX_MEI_EMSG ("Modem failed to be ready!\n"); - return DSL_DEV_MEI_ERR_FAILURE; - } else { - IFX_MEI_DMSG("Modem is ready.\n"); - return DSL_DEV_MEI_ERR_SUCCESS; - } -} - -/** - * Get the page's data pointer - * This function caculats the data address from the firmware header. - * - * \param pDev the device pointer - * \param Page The page number. - * \param data Data page or program page. - * \param MaxSize The maximum size to read. - * \param Buffer Pointer to data. - * \param Dest Pointer to the destination address. - * \return The number of bytes to read. - * \ingroup Internal - */ -static int -IFX_MEI_GetPage (DSL_DEV_Device_t * pDev, u32 Page, u32 data, - u32 MaxSize, u32 * Buffer, u32 * Dest) -{ - u32 size; - u32 i; - u32 *p; - u32 idx, offset, nBar = 0; - - if (Page > DSL_DEV_PRIVATE(pDev)->img_hdr->count) - return -2; - /* - ** Get program or data size, depending on "data" flag - */ - size = (data == GET_DATA) ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_size) : - (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_size); - size &= BOOT_FLAG_MASK; // Clear boot bit! - if (size > MaxSize) - return -1; - - if (size == 0) - return 0; - /* - ** Get program or data offset, depending on "data" flag - */ - i = data ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_offset) : - (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_offset); - - /* - ** Copy data/program to buffer - */ - - idx = i / SDRAM_SEGMENT_SIZE; - offset = i % SDRAM_SEGMENT_SIZE; - p = (u32 *) ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address + offset); - - for (i = 0; i < size; i++) { - if (offset + i * 4 - (nBar * SDRAM_SEGMENT_SIZE) >= SDRAM_SEGMENT_SIZE) { - idx++; - nBar++; - p = (u32 *) ((u8 *) KSEG1ADDR ((u32)DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address)); - } - Buffer[i] = *p++; - } - - /* - ** Pass back data/program destination address - */ - *Dest = data ? (DSL_DEV_PRIVATE(pDev)-> img_hdr->page[Page].d_dest) : - (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_dest); - - return size; -} - -/** - * Free the memory for ARC firmware - * - * \param pDev the device pointer - * \param type Free all memory or free the unused memory after showtime - * \ingroup Internal - */ -const char *free_str[4] = {"Invalid", "Free_Reload", "Free_Showtime", "Free_All"}; -static int -IFX_MEI_DFEMemoryFree (DSL_DEV_Device_t * pDev, int type) -{ - int idx = 0; - smmu_mem_info_t *adsl_mem_info = - DSL_DEV_PRIVATE(pDev)->adsl_mem_info; - - for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) { - if (type == FREE_ALL ||adsl_mem_info[idx].type == type) { - if (adsl_mem_info[idx].size > 0) { - IFX_MEI_DMSG ("Freeing memory %p (%s)\n", adsl_mem_info[idx].org_address, free_str[adsl_mem_info[idx].type]); - if ( idx == XDATA_REGISTER ) { - g_xdata_addr = NULL; - if ( ifx_mei_atm_showtime_exit ) - ifx_mei_atm_showtime_exit(); - } - kfree (adsl_mem_info[idx].org_address); - adsl_mem_info[idx].org_address = 0; - adsl_mem_info[idx].address = 0; - adsl_mem_info[idx].size = 0; - adsl_mem_info[idx].type = 0; - adsl_mem_info[idx].nCopy = 0; - } - } - } - - if(mei_arc_swap_buff != NULL){ - IFX_MEI_DMSG("free %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff); - kfree(mei_arc_swap_buff); - mei_arc_swap_buff=NULL; - } - - return 0; -} -static int -IFX_MEI_DFEMemoryAlloc (DSL_DEV_Device_t * pDev, long size) -{ - unsigned long mem_ptr; - char *org_mem_ptr = NULL; - int idx = 0; - long total_size = 0; - int err = 0; - smmu_mem_info_t *adsl_mem_info = - ((ifx_mei_device_private_t *) pDev->pPriv)->adsl_mem_info; -// DSL_DEV_PRIVATE(pDev)->adsl_mem_info; - int allocate_size = SDRAM_SEGMENT_SIZE; - - IFX_MEI_DMSG("image_size = %ld\n", size); - // Alloc Swap Pages - for (idx = 0; size > 0 && idx < MAX_BAR_REGISTERS; idx++) { - // skip bar15 for XDATA usage. - if (idx == XDATA_REGISTER) - continue; -#if 0 - if (size < SDRAM_SEGMENT_SIZE) { - allocate_size = size; - if (allocate_size < 1024) - allocate_size = 1024; - } -#endif - if (idx == (MAX_BAR_REGISTERS - 1)) - allocate_size = size; - else - allocate_size = SDRAM_SEGMENT_SIZE; - org_mem_ptr = kmalloc (allocate_size + 1024, GFP_KERNEL); - if (org_mem_ptr == NULL) { - IFX_MEI_EMSG ("%d: kmalloc %d bytes memory fail!\n", idx, allocate_size); - err = -ENOMEM; - goto allocate_error; - } - mem_ptr = (unsigned long) (org_mem_ptr + 1023) & ~(1024 -1); - adsl_mem_info[idx].address = (char *) mem_ptr; - adsl_mem_info[idx].org_address = org_mem_ptr; - adsl_mem_info[idx].size = allocate_size; - size -= allocate_size; - total_size += allocate_size; - } - if (size > 0) { - IFX_MEI_EMSG ("Image size is too large!\n"); - err = -EFBIG; - goto allocate_error; - } - err = idx; - return err; - - allocate_error: - IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); - return err; -} - -/** - * Program the BAR registers - * - * \param pDev the device pointer - * \param nTotalBar The number of bar to program. - * \ingroup Internal - */ -static int -IFX_MEI_BarUpdate (DSL_DEV_Device_t * pDev, int nTotalBar) -{ - int idx = 0; - smmu_mem_info_t *adsl_mem_info = - DSL_DEV_PRIVATE(pDev)->adsl_mem_info; - - for (idx = 0; idx < nTotalBar; idx++) { - //skip XDATA register - if (idx == XDATA_REGISTER) - continue; - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + idx * 4, - (((uint32_t) adsl_mem_info[idx].address) & 0x0FFFFFFF)); - } - for (idx = nTotalBar; idx < MAX_BAR_REGISTERS; idx++) { - if (idx == XDATA_REGISTER) - continue; - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + idx * 4, - (((uint32_t)adsl_mem_info[nTotalBar - 1].address) & 0x0FFFFFFF)); - /* These are for /proc/danube_mei/meminfo purpose */ - adsl_mem_info[idx].address = adsl_mem_info[nTotalBar - 1].address; - adsl_mem_info[idx].org_address = adsl_mem_info[nTotalBar - 1].org_address; - adsl_mem_info[idx].size = 0; /* Prevent it from being freed */ - } - - g_xdata_addr = adsl_mem_info[XDATA_REGISTER].address; - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + XDATA_REGISTER * 4, - (((uint32_t) adsl_mem_info [XDATA_REGISTER].address) & 0x0FFFFFFF)); - // update MEI_XDATA_BASE_SH - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH, - ((unsigned long)adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF); - - return DSL_DEV_MEI_ERR_SUCCESS; -} - -/* This copies the firmware from secondary storage to 64k memory segment in SDRAM */ -DSL_DEV_MeiError_t -DSL_BSP_FWDownload (DSL_DEV_Device_t * pDev, const char *buf, - unsigned long size, long *loff, long *current_offset) -{ - ARC_IMG_HDR img_hdr_tmp; - smmu_mem_info_t *adsl_mem_info = DSL_DEV_PRIVATE(pDev)->adsl_mem_info; - - size_t nRead = 0, nCopy = 0; - char *mem_ptr; - ssize_t retval = -ENOMEM; - int idx = 0; - - IFX_MEI_DMSG("\n"); - - if (*loff == 0) { - if (size < sizeof (img_hdr_tmp)) { - IFX_MEI_EMSG ("Firmware size is too small!\n"); - return retval; - } - copy_from_user ((char *) &img_hdr_tmp, buf, sizeof (img_hdr_tmp)); - // header of image_size and crc are not included. - DSL_DEV_PRIVATE(pDev)->image_size = le32_to_cpu (img_hdr_tmp.size) + 8; - - if (DSL_DEV_PRIVATE(pDev)->image_size > 1024 * 1024) { - IFX_MEI_EMSG ("Firmware size is too large!\n"); - return retval; - } - // check if arc is halt - IFX_MEI_ResetARC (pDev); - IFX_MEI_HaltArc (pDev); - - IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); //free all - - retval = IFX_MEI_DFEMemoryAlloc (pDev, DSL_DEV_PRIVATE(pDev)->image_size); - if (retval < 0) { - IFX_MEI_EMSG ("Error: No memory space left.\n"); - goto error; - } - for (idx = 0; idx < retval; idx++) { - //skip XDATA register - if (idx == XDATA_REGISTER) - continue; - if (idx * SDRAM_SEGMENT_SIZE < le32_to_cpu (img_hdr_tmp.page[0].p_offset)) - adsl_mem_info[idx].type = FREE_RELOAD; - else - adsl_mem_info[idx].type = FREE_SHOWTIME; - } - DSL_DEV_PRIVATE(pDev)->nBar = retval; - - DSL_DEV_PRIVATE(pDev)->img_hdr = - (ARC_IMG_HDR *) adsl_mem_info[0].address; - - adsl_mem_info[XDATA_REGISTER].org_address = kmalloc (SDRAM_SEGMENT_SIZE + 1024, GFP_KERNEL); - adsl_mem_info[XDATA_REGISTER].address = - (char *) ((unsigned long) (adsl_mem_info[XDATA_REGISTER].org_address + 1023) & 0xFFFFFC00); - - adsl_mem_info[XDATA_REGISTER].size = SDRAM_SEGMENT_SIZE; - - if (adsl_mem_info[XDATA_REGISTER].address == NULL) { - IFX_MEI_EMSG ("kmalloc memory fail!\n"); - retval = -ENOMEM; - goto error; - } - adsl_mem_info[XDATA_REGISTER].type = FREE_RELOAD; - IFX_MEI_DMSG("-> IFX_MEI_BarUpdate()\n"); - IFX_MEI_BarUpdate (pDev, (DSL_DEV_PRIVATE(pDev)->nBar)); - } - else if (DSL_DEV_PRIVATE(pDev)-> image_size == 0) { - IFX_MEI_EMSG ("Error: Firmware size=0! \n"); - goto error; - } - - nRead = 0; - while (nRead < size) { - long offset = ((long) (*loff) + nRead) % SDRAM_SEGMENT_SIZE; - idx = (((long) (*loff)) + nRead) / SDRAM_SEGMENT_SIZE; - mem_ptr = (char *) KSEG1ADDR ((unsigned long) (adsl_mem_info[idx].address) + offset); - if ((size - nRead + offset) > SDRAM_SEGMENT_SIZE) - nCopy = SDRAM_SEGMENT_SIZE - offset; - else - nCopy = size - nRead; - copy_from_user (mem_ptr, buf + nRead, nCopy); - for (offset = 0; offset < (nCopy / 4); offset++) { - ((unsigned long *) mem_ptr)[offset] = le32_to_cpu (((unsigned long *) mem_ptr)[offset]); - } - nRead += nCopy; - adsl_mem_info[idx].nCopy += nCopy; - } - - *loff += size; - *current_offset = size; - return DSL_DEV_MEI_ERR_SUCCESS; -error: - IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); - return DSL_DEV_MEI_ERR_FAILURE; -} -/* - * Register a callback event. - * Return: - * -1 if the event already has a callback function registered. - * 0 success - */ -int DSL_BSP_EventCBRegister(DSL_BSP_EventCallBack_t *p) -{ - if (!p) { - IFX_MEI_EMSG("Invalid parameter!\n"); - return -EINVAL; - } - if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) { - IFX_MEI_EMSG("Invalid Event %d\n", p->event); - return -EINVAL; - } - if (dsl_bsp_event_callback[p->event].function) { - IFX_MEI_EMSG("Event %d already has a callback function registered!\n", p->event); - return -1; - } else { - dsl_bsp_event_callback[p->event].function = p->function; - dsl_bsp_event_callback[p->event].event = p->event; - dsl_bsp_event_callback[p->event].pData = p->pData; - } - return 0; -} -int DSL_BSP_EventCBUnregister(DSL_BSP_EventCallBack_t *p) -{ - if (!p) { - IFX_MEI_EMSG("Invalid parameter!\n"); - return -EINVAL; - } - if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) { - IFX_MEI_EMSG("Invalid Event %d\n", p->event); - return -EINVAL; - } - if (dsl_bsp_event_callback[p->event].function) { - IFX_MEI_EMSG("Unregistering Event %d...\n", p->event); - dsl_bsp_event_callback[p->event].function = NULL; - dsl_bsp_event_callback[p->event].pData = NULL; - } else { - IFX_MEI_EMSG("Event %d is not registered!\n", p->event); - return -1; - } - return 0; -} - -/** - * MEI Dying Gasp interrupt handler - * - * \param int1 - * \param void0 - * \param regs Pointer to the structure of danube mips registers - * \ingroup Internal - */ -static irqreturn_t IFX_MEI_Dying_Gasp_IrqHandle (int int1, void *void0) -{ - DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0; - DSL_BSP_CB_Type_t event; - - if (pDev == NULL) - IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n"); - -#ifndef CONFIG_SMP - disable_irq (pDev->nIrq[IFX_DYING_GASP]); -#else - disable_irq_nosync(pDev->nIrq[IFX_DYING_GASP]); -#endif - event = DSL_BSP_CB_DYING_GASP; - - if (dsl_bsp_event_callback[event].function) - (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); - -#ifdef CONFIG_USE_EMULATOR - IFX_MEI_EMSG("Dying Gasp! Shutting Down... (Work around for Amazon-S Venus emulator)\n"); -#else - IFX_MEI_EMSG("Dying Gasp! Shutting Down...\n"); -// kill_proc (1, SIGINT, 1); /* Ask init to reboot us */ -#endif - return IRQ_HANDLED; -} - -extern void ifx_usb_enable_afe_oc(void); - -/** - * MEI interrupt handler - * - * \param int1 - * \param void0 - * \param regs Pointer to the structure of danube mips registers - * \ingroup Internal - */ -static irqreturn_t IFX_MEI_IrqHandle (int int1, void *void0) -{ - u32 scratch; - DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0; -#if defined(CONFIG_LQ_MEI_FW_LOOPBACK) && defined(DFE_PING_TEST) - dfe_loopback_irq_handler (pDev); - return IRQ_HANDLED; -#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK - DSL_BSP_CB_Type_t event; - - if (pDev == NULL) - IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n"); - - IFX_MEI_DebugRead (pDev, ARC_MEI_MAILBOXR, &scratch, 1); - if (scratch & OMB_CODESWAP_MESSAGE_MSG_TYPE_MASK) { - IFX_MEI_EMSG("Receive Code Swap Request interrupt!!!\n"); - return IRQ_HANDLED; - } - else if (scratch & OMB_CLEAREOC_INTERRUPT_CODE) { - // clear eoc message interrupt - IFX_MEI_DMSG("OMB_CLEAREOC_INTERRUPT_CODE\n"); - event = DSL_BSP_CB_CEOC_IRQ; - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); - if (dsl_bsp_event_callback[event].function) - (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); - } else if (scratch & OMB_REBOOT_INTERRUPT_CODE) { - // Reboot - IFX_MEI_DMSG("OMB_REBOOT_INTERRUPT_CODE\n"); - event = DSL_BSP_CB_FIRMWARE_REBOOT; - - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); - - if (dsl_bsp_event_callback[event].function) - (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); - } else { // normal message - IFX_MEI_MailboxRead (pDev, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH); - if (DSL_DEV_PRIVATE(pDev)-> cmv_waiting == 1) { - DSL_DEV_PRIVATE(pDev)-> arcmsgav = 1; - DSL_DEV_PRIVATE(pDev)-> cmv_waiting = 0; -#if !defined(BSP_PORT_RTEMS) - MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav); -#endif - } - else { - DSL_DEV_PRIVATE(pDev)-> modem_ready_cnt++; - memcpy ((char *) DSL_DEV_PRIVATE(pDev)->Recent_indicator, - (char *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2); - if (((DSL_DEV_PRIVATE(pDev)->CMV_RxMsg[0] & 0xff0) >> 4) == D2H_AUTONOMOUS_MODEM_READY_MSG) { - //check ARC ready message - IFX_MEI_DMSG ("Got MODEM_READY_MSG\n"); - DSL_DEV_PRIVATE(pDev)->modem_ready = 1; - MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready); - } - } - } - - return IRQ_HANDLED; -} - -int -DSL_BSP_ATMLedCBRegister (int (*ifx_adsl_ledcallback) (void)) -{ - g_adsl_ledcallback = ifx_adsl_ledcallback; - return 0; -} - -int -DSL_BSP_ATMLedCBUnregister (int (*ifx_adsl_ledcallback) (void)) -{ - g_adsl_ledcallback = adsl_dummy_ledcallback; - return 0; -} - -#if 0 -int -DSL_BSP_EventCBRegister (int (*ifx_adsl_callback) - (DSL_BSP_CB_Event_t * param)) -{ - int error = 0; - - if (DSL_EventCB == NULL) { - DSL_EventCB = ifx_adsl_callback; - } - else { - error = -EIO; - } - return error; -} - -int -DSL_BSP_EventCBUnregister (int (*ifx_adsl_callback) - (DSL_BSP_CB_Event_t * param)) -{ - int error = 0; - - if (DSL_EventCB == ifx_adsl_callback) { - DSL_EventCB = NULL; - } - else { - error = -EIO; - } - return error; -} - -static int -DSL_BSP_GetEventCB (int (**ifx_adsl_callback) - (DSL_BSP_CB_Event_t * param)) -{ - *ifx_adsl_callback = DSL_EventCB; - return 0; -} -#endif - -#ifdef CONFIG_LQ_MEI_FW_LOOPBACK -#define mte_reg_base (0x4800*4+0x20000) - -/* Iridia Registers Address Constants */ -#define MTE_Reg(r) (int)(mte_reg_base + (r*4)) - -#define IT_AMODE MTE_Reg(0x0004) - -#define TIMER_DELAY (1024) -#define BC0_BYTES (32) -#define BC1_BYTES (30) -#define NUM_MB (12) -#define TIMEOUT_VALUE 2000 - -static void -BFMWait (u32 cycle) -{ - u32 i; - for (i = 0; i < cycle; i++); -} - -static void -WriteRegLong (u32 addr, u32 data) -{ - //*((volatile u32 *)(addr)) = data; - IFX_MEI_WRITE_REGISTER_L (data, addr); -} - -static u32 -ReadRegLong (u32 addr) -{ - // u32 rd_val; - //rd_val = *((volatile u32 *)(addr)); - // return rd_val; - return IFX_MEI_READ_REGISTER_L (addr); -} - -/* This routine writes the mailbox with the data in an input array */ -static void -WriteMbox (u32 * mboxarray, u32 size) -{ - IFX_MEI_DebugWrite (&dsl_devices[0], IMBOX_BASE, mboxarray, size); - IFX_MEI_DMSG("write to %X\n", IMBOX_BASE); - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV); -} - -/* This routine reads the output mailbox and places the results into an array */ -static void -ReadMbox (u32 * mboxarray, u32 size) -{ - IFX_MEI_DebugRead (&dsl_devices[0], OMBOX_BASE, mboxarray, size); - IFX_MEI_DMSG("read from %X\n", OMBOX_BASE); -} - -static void -MEIWriteARCValue (u32 address, u32 value) -{ - u32 i, check = 0; - - /* Write address register */ - IFX_MEI_WRITE_REGISTER_L (address, ME_DBG_WR_AD + LQ_MEI_BASE_ADDR); - - /* Write data register */ - IFX_MEI_WRITE_REGISTER_L (value, ME_DBG_DATA + LQ_MEI_BASE_ADDR); - - /* wait until complete - timeout at 40 */ - for (i = 0; i < 40; i++) { - check = IFX_MEI_READ_REGISTER_L (ME_ARC2ME_STAT + LQ_MEI_BASE_ADDR); - - if ((check & ARC_TO_MEI_DBG_DONE)) - break; - } - /* clear the flag */ - IFX_MEI_WRITE_REGISTER_L (ARC_TO_MEI_DBG_DONE, ME_ARC2ME_STAT + LQ_MEI_BASE_ADDR); -} - -void -arc_code_page_download (uint32_t arc_code_length, uint32_t * start_address) -{ - int count; - - IFX_MEI_DMSG("try to download pages,size=%d\n", arc_code_length); - IFX_MEI_ControlModeSet (&dsl_devices[0], MEI_MASTER_MODE); - IFX_MEI_HaltArc (&dsl_devices[0]); - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_AD, 0); - for (count = 0; count < arc_code_length; count++) { - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_DATA, - *(start_address + count)); - } - IFX_MEI_ControlModeSet (&dsl_devices[0], JTAG_MASTER_MODE); -} -static int -load_jump_table (unsigned long addr) -{ - int i; - uint32_t addr_le, addr_be; - uint32_t jump_table[32]; - - for (i = 0; i < 16; i++) { - addr_le = i * 8 + addr; - addr_be = ((addr_le >> 16) & 0xffff); - addr_be |= ((addr_le & 0xffff) << 16); - jump_table[i * 2 + 0] = 0x0f802020; - jump_table[i * 2 + 1] = addr_be; - //printk("jt %X %08X %08X\n",i,jump_table[i*2+0],jump_table[i*2+1]); - } - arc_code_page_download (32, &jump_table[0]); -return 0; -} - -int got_int = 0; - -void -dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev) -{ - uint32_t rd_mbox[10]; - - memset (&rd_mbox[0], 0, 10 * 4); - ReadMbox (&rd_mbox[0], 6); - if (rd_mbox[0] == 0x0) { - FX_MEI_DMSG("Get ARC_ACK\n"); - got_int = 1; - } - else if (rd_mbox[0] == 0x5) { - IFX_MEI_DMSG("Get ARC_BUSY\n"); - got_int = 2; - } - else if (rd_mbox[0] == 0x3) { - IFX_MEI_DMSG("Get ARC_EDONE\n"); - if (rd_mbox[1] == 0x0) { - got_int = 3; - IFX_MEI_DMSG("Get E_MEMTEST\n"); - if (rd_mbox[2] != 0x1) { - got_int = 4; - IFX_MEI_DMSG("Get Result %X\n", rd_mbox[2]); - } - } - } - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_STAT, - ARC_TO_MEI_DBG_DONE); - MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]); - disable_irq (pDev->nIrq[IFX_DFEIR]); - //got_int = 1; - return; -} - -static void -wait_mem_test_result (void) -{ - uint32_t mbox[5]; - mbox[0] = 0; - - IFX_MEI_DMSG("Waiting Starting\n"); - while (mbox[0] == 0) { - ReadMbox (&mbox[0], 5); - } - IFX_MEI_DMSG("Try to get mem test result.\n"); - ReadMbox (&mbox[0], 5); - if (mbox[0] == 0xA) { - IFX_MEI_DMSG("Success.\n"); - } - else if (mbox[0] == 0xA) { - IFX_MEI_EMSG("Fail,address %X,except data %X,receive data %X\n", - mbox[1], mbox[2], mbox[3]); - } - else { - IFX_MEI_EMSG("Fail\n"); - } -} - -static int -arc_ping_testing (DSL_DEV_Device_t *pDev) -{ -#define MEI_PING 0x00000001 - uint32_t wr_mbox[10], rd_mbox[10]; - int i; - - for (i = 0; i < 10; i++) { - wr_mbox[i] = 0; - rd_mbox[i] = 0; - } - - FX_MEI_DMSG("send ping msg\n"); - wr_mbox[0] = MEI_PING; - WriteMbox (&wr_mbox[0], 10); - - while (got_int == 0) { - MEI_WAIT (100); - } - - IFX_MEI_DMSG("send start event\n"); - got_int = 0; - - wr_mbox[0] = 0x4; - wr_mbox[1] = 0; - wr_mbox[2] = 0; - wr_mbox[3] = (uint32_t) 0xf5acc307e; - wr_mbox[4] = 5; - wr_mbox[5] = 2; - wr_mbox[6] = 0x1c000; - wr_mbox[7] = 64; - wr_mbox[8] = 0; - wr_mbox[9] = 0; - WriteMbox (&wr_mbox[0], 10); - DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]); - //printk("IFX_MEI_MailboxWrite ret=%d\n",i); - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], - (u32) ME_ME2ARC_INT, - MEI_TO_ARC_MSGAV); - IFX_MEI_DMSG("sleeping\n"); - while (1) { - if (got_int > 0) { - - if (got_int > 3) - IFX_MEI_DMSG("got_int >>>> 3\n"); - else - IFX_MEI_DMSG("got int = %d\n", got_int); - got_int = 0; - //schedule(); - DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]); - } - //mbox_read(&rd_mbox[0],6); - MEI_WAIT (100); - } - return 0; -} - -static DSL_DEV_MeiError_t -DFE_Loopback_Test (void) -{ - int i = 0; - u32 arc_debug_data = 0, temp; - DSL_DEV_Device_t *pDev = &dsl_devices[0]; - uint32_t wr_mbox[10]; - - IFX_MEI_ResetARC (pDev); - // start the clock - arc_debug_data = ACL_CLK_MODE_ENABLE; - IFX_MEI_DebugWrite (pDev, CRI_CCR0, &arc_debug_data, 1); - -#if defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK) - // WriteARCreg(AUX_XMEM_LTEST,0); - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); -#define AUX_XMEM_LTEST 0x128 - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, AUX_XMEM_LTEST, 0); - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - // WriteARCreg(AUX_XDMA_GAP,0); - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); -#define AUX_XDMA_GAP 0x114 - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, AUX_XDMA_GAP, 0); - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); - temp = 0; - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, - (u32) ME_XDATA_BASE_SH + LQ_MEI_BASE_ADDR, temp); - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - i = IFX_MEI_DFEMemoryAlloc (pDev, SDRAM_SEGMENT_SIZE * 16); - if (i >= 0) { - int idx; - - for (idx = 0; idx < i; idx++) { - DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].type = FREE_RELOAD; - IFX_MEI_WRITE_REGISTER_L ((((uint32_t) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address) & 0x0fffffff), - LQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE + idx * 4); - IFX_MEI_DMSG("bar%d(%X)=%X\n", idx, - LQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE + - idx * 4, (((uint32_t) - ((ifx_mei_device_private_t *) - pDev->pPriv)->adsl_mem_info[idx]. - address) & 0x0fffffff)); - memset ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address, 0, SDRAM_SEGMENT_SIZE); - } - - IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH, - ((unsigned long) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF); - } - else { - IFX_MEI_EMSG ("cannot load image: no memory\n"); - return DSL_DEV_MEI_ERR_FAILURE; - } - //WriteARCreg(AUX_IC_CTRL,2); - IFX_MEI_DMSG("Setting MEI_MASTER_MODE..\n"); - IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); -#define AUX_IC_CTRL 0x11 - _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, - AUX_IC_CTRL, 2); - IFX_MEI_DMSG("Setting JTAG_MASTER_MODE..\n"); - IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); - - IFX_MEI_DMSG("Halting ARC...\n"); - IFX_MEI_HaltArc (&dsl_devices[0]); - -#ifdef DFE_PING_TEST - - IFX_MEI_DMSG("ping test image size=%d\n", sizeof (arc_ahb_access_code)); - memcpy ((u8 *) (DSL_DEV_PRIVATE(pDev)-> - adsl_mem_info[0].address + 0x1004), - &arc_ahb_access_code[0], sizeof (arc_ahb_access_code)); - load_jump_table (0x80000 + 0x1004); - -#endif //DFE_PING_TEST - - IFX_MEI_DMSG("ARC ping test code download complete\n"); -#endif //defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK) -#ifdef DFE_MEM_TEST - IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_MASK, MSGAV_EN); - - arc_code_page_download (1537, &code_array[0]); - IFX_MEI_DMSG("ARC mem test code download complete\n"); -#endif //DFE_MEM_TEST -#ifdef DFE_ATM_LOOPBACK - arc_debug_data = 0xf; - arc_code_page_download (sizeof(code_array) / sizeof(*code_array), &code_array[0]); - wr_mbox[0] = 0; //TIMER_DELAY - org: 1024 - wr_mbox[1] = 0; //TXFB_START0 - wr_mbox[2] = 0x7f; //TXFB_END0 - org: 49 - wr_mbox[3] = 0x80; //TXFB_START1 - org: 80 - wr_mbox[4] = 0xff; //TXFB_END1 - org: 109 - wr_mbox[5] = 0x100; //RXFB_START0 - org: 0 - wr_mbox[6] = 0x17f; //RXFB_END0 - org: 49 - wr_mbox[7] = 0x180; //RXFB_START1 - org: 256 - wr_mbox[8] = 0x1ff; //RXFB_END1 - org: 315 - WriteMbox (&wr_mbox[0], 9); - // Start Iridia IT_AMODE (in dmp access) why is it required? - IFX_MEI_DebugWrite (&dsl_devices[0], 0x32010, &arc_debug_data, 1); -#endif //DFE_ATM_LOOPBACK - IFX_MEI_IRQEnable (pDev); - IFX_MEI_DMSG("run ARC...\n"); - IFX_MEI_RunArc (&dsl_devices[0]); - -#ifdef DFE_PING_TEST - arc_ping_testing (pDev); -#endif //DFE_PING_TEST -#ifdef DFE_MEM_TEST - wait_mem_test_result (); -#endif //DFE_MEM_TEST - - IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); - return DSL_DEV_MEI_ERR_SUCCESS; -} - -#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK - -static int -IFX_MEI_InitDevNode (int num) -{ - if (num == 0) { - if ((dev_major = register_chrdev (dev_major, IFX_MEI_DEVNAME, &bsp_mei_operations)) < 0) { - IFX_MEI_EMSG ("register_chrdev(%d %s) failed!\n", dev_major, IFX_MEI_DEVNAME); - return -ENODEV; - } - } - return 0; -} - -static int -IFX_MEI_CleanUpDevNode (int num) -{ - if (num == 0) - unregister_chrdev (dev_major, MEI_DIRNAME); - return 0; -} - -static int -IFX_MEI_InitDevice (int num) -{ - DSL_DEV_Device_t *pDev; - u32 temp; - pDev = &dsl_devices[num]; - if (pDev == NULL) - return -ENOMEM; - pDev->pPriv = &sDanube_Mei_Private[num]; - memset (pDev->pPriv, 0, sizeof (ifx_mei_device_private_t)); - - memset (&DSL_DEV_PRIVATE(pDev)-> - adsl_mem_info[0], 0, - sizeof (smmu_mem_info_t) * MAX_BAR_REGISTERS); - - if (num == 0) { - pDev->nIrq[IFX_DFEIR] = LQ_MEI_INT; - pDev->nIrq[IFX_DYING_GASP] = LQ_MEI_DYING_GASP_INT; - pDev->base_address = LQ_MEI_BASE_ADDR; - - /* Power up MEI */ -#ifdef CONFIG_LANTIQ_AMAZON_SE - *LQ_PMU_PWDCR &= ~(1 << 9); // enable dsl - *LQ_PMU_PWDCR &= ~(1 << 15); // enable AHB base -#else - temp = lq_r32(LQ_PMU_PWDCR); - temp &= 0xffff7dbe; - lq_w32(temp, LQ_PMU_PWDCR); -#endif - } - pDev->nInUse = 0; - DSL_DEV_PRIVATE(pDev)->modem_ready = 0; - DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; - - MEI_INIT_WAKELIST ("arcq", DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav); // for ARCMSGAV - MEI_INIT_WAKELIST ("arcr", DSL_DEV_PRIVATE(pDev)->wait_queue_modemready); // for arc modem ready - - MEI_MUTEX_INIT (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema, 1); // semaphore initialization, mutex -#if 0 - MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]); - MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]); -#endif - if (request_irq (pDev->nIrq[IFX_DFEIR], IFX_MEI_IrqHandle, 0, "DFEIR", pDev) != 0) { - IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DFEIR]); - return -1; - } - /*if (request_irq (pDev->nIrq[IFX_DYING_GASP], IFX_MEI_Dying_Gasp_IrqHandle, 0, "DYING_GASP", pDev) != 0) { - IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DYING_GASP]); - return -1; - }*/ -// IFX_MEI_DMSG("Device %d initialized. IER %#x\n", num, bsp_get_irq_ier(pDev->nIrq[IFX_DYING_GASP])); - return 0; -} - -static int -IFX_MEI_ExitDevice (int num) -{ - DSL_DEV_Device_t *pDev; - pDev = &dsl_devices[num]; - - if (pDev == NULL) - return -EIO; - - disable_irq (pDev->nIrq[IFX_DFEIR]); - disable_irq (pDev->nIrq[IFX_DYING_GASP]); - - free_irq(pDev->nIrq[IFX_DFEIR], pDev); - free_irq(pDev->nIrq[IFX_DYING_GASP], pDev); - - return 0; -} - -static DSL_DEV_Device_t * -IFX_BSP_HandleGet (int maj, int num) -{ - if (num > BSP_MAX_DEVICES) - return NULL; - return &dsl_devices[num]; -} - -DSL_DEV_Device_t * -DSL_BSP_DriverHandleGet (int maj, int num) -{ - DSL_DEV_Device_t *pDev; - - if (num > BSP_MAX_DEVICES) - return NULL; - - pDev = &dsl_devices[num]; - if (!try_module_get(pDev->owner)) - return NULL; - - pDev->nInUse++; - return pDev; -} - -int -DSL_BSP_DriverHandleDelete (DSL_DEV_Device_t * nHandle) -{ - DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) nHandle; - if (pDev->nInUse) - pDev->nInUse--; - module_put(pDev->owner); - return 0; -} - -static int -IFX_MEI_Open (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil) -{ - int maj = MAJOR (ino->i_rdev); - int num = MINOR (ino->i_rdev); - - DSL_DEV_Device_t *pDev = NULL; - if ((pDev = DSL_BSP_DriverHandleGet (maj, num)) == NULL) { - IFX_MEI_EMSG("open(%d:%d) fail!\n", maj, num); - return -EIO; - } - fil->private_data = pDev; - return 0; -} - -static int -IFX_MEI_Release (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil) -{ - //int maj = MAJOR(ino->i_rdev); - int num = MINOR (ino->i_rdev); - DSL_DEV_Device_t *pDev; - - pDev = &dsl_devices[num]; - if (pDev == NULL) - return -EIO; - DSL_BSP_DriverHandleDelete (pDev); - return 0; -} - -/** - * Callback function for linux userspace program writing - */ -static ssize_t -IFX_MEI_Write (DSL_DRV_file_t * filp, const char *buf, size_t size, loff_t * loff) -{ - DSL_DEV_MeiError_t mei_error = DSL_DEV_MEI_ERR_FAILURE; - long offset = 0; - DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) filp->private_data; - - if (pDev == NULL) - return -EIO; - - mei_error = - DSL_BSP_FWDownload (pDev, buf, size, (long *) loff, &offset); - - if (mei_error == DSL_DEV_MEI_ERR_FAILURE) - return -EIO; - return (ssize_t) offset; -} - -/** - * Callback function for linux userspace program ioctling - */ -static int -IFX_MEI_IoctlCopyFrom (int from_kernel, char *dest, char *from, int size) -{ - int ret = 0; - - if (!from_kernel) - ret = copy_from_user ((char *) dest, (char *) from, size); - else - ret = (int)memcpy ((char *) dest, (char *) from, size); - return ret; -} - -static int -IFX_MEI_IoctlCopyTo (int from_kernel, char *dest, char *from, int size) -{ - int ret = 0; - - if (!from_kernel) - ret = copy_to_user ((char *) dest, (char *) from, size); - else - ret = (int)memcpy ((char *) dest, (char *) from, size); - return ret; -} - -static int -IFX_MEI_Ioctls (DSL_DEV_Device_t * pDev, int from_kernel, unsigned int command, unsigned long lon) -{ - int i = 0; - int meierr = DSL_DEV_MEI_ERR_SUCCESS; - u32 base_address = LQ_MEI_BASE_ADDR; - DSL_DEV_WinHost_Message_t winhost_msg, m; - DSL_DEV_MeiDebug_t debugrdwr; - DSL_DEV_MeiReg_t regrdwr; - - switch (command) { - - case DSL_FIO_BSP_CMV_WINHOST: - IFX_MEI_IoctlCopyFrom (from_kernel, (char *) winhost_msg.msg.TxMessage, - (char *) lon, MSG_LENGTH * 2); - - if ((meierr = DSL_BSP_SendCMV (pDev, winhost_msg.msg.TxMessage, YES_REPLY, - winhost_msg.msg.RxMessage)) != DSL_DEV_MEI_ERR_SUCCESS) { - IFX_MEI_EMSG ("WINHOST CMV fail :TxMessage:%X %X %X %X, RxMessage:%X %X %X %X %X\n", - winhost_msg.msg.TxMessage[0], winhost_msg.msg.TxMessage[1], winhost_msg.msg.TxMessage[2], winhost_msg.msg.TxMessage[3], - winhost_msg.msg.RxMessage[0], winhost_msg.msg.RxMessage[1], winhost_msg.msg.RxMessage[2], winhost_msg.msg.RxMessage[3], - winhost_msg.msg.RxMessage[4]); - meierr = DSL_DEV_MEI_ERR_FAILURE; - } - else { - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, - (char *) winhost_msg.msg.RxMessage, - MSG_LENGTH * 2); - } - break; - - case DSL_FIO_BSP_CMV_READ: - IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (®rdwr), - (char *) lon, sizeof (DSL_DEV_MeiReg_t)); - - IFX_MEI_LongWordRead ((u32) regrdwr.iAddress, - (u32 *) & (regrdwr.iData)); - - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, - (char *) (®rdwr), - sizeof (DSL_DEV_MeiReg_t)); - - break; - - case DSL_FIO_BSP_CMV_WRITE: - IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (®rdwr), - (char *) lon, sizeof (DSL_DEV_MeiReg_t)); - - IFX_MEI_LongWordWrite ((u32) regrdwr.iAddress, - regrdwr.iData); - break; - - case DSL_FIO_BSP_GET_BASE_ADDRESS: - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, - (char *) (&base_address), - sizeof (base_address)); - break; - - case DSL_FIO_BSP_IS_MODEM_READY: - i = IFX_MEI_IsModemReady (pDev); - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, - (char *) (&i), sizeof (int)); - meierr = DSL_DEV_MEI_ERR_SUCCESS; - break; - case DSL_FIO_BSP_RESET: - case DSL_FIO_BSP_REBOOT: - meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RESET); - meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT); - break; - - case DSL_FIO_BSP_HALT: - meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT); - break; - - case DSL_FIO_BSP_RUN: - meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RUN); - break; - case DSL_FIO_BSP_BOOTDOWNLOAD: - meierr = IFX_MEI_DownloadBootCode (pDev); - break; - case DSL_FIO_BSP_JTAG_ENABLE: - meierr = IFX_MEI_ArcJtagEnable (pDev, 1); - break; - - case DSL_FIO_BSP_REMOTE: - IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (&i), - (char *) lon, sizeof (int)); - - meierr = IFX_MEI_AdslMailboxIRQEnable (pDev, i); - break; - - case DSL_FIO_BSP_DSL_START: - IFX_MEI_DMSG("DSL_FIO_BSP_DSL_START\n"); - if ((meierr = IFX_MEI_RunAdslModem (pDev)) != DSL_DEV_MEI_ERR_SUCCESS) { - IFX_MEI_EMSG ("IFX_MEI_RunAdslModem() error..."); - meierr = DSL_DEV_MEI_ERR_FAILURE; - } - break; - - case DSL_FIO_BSP_DEBUG_READ: - case DSL_FIO_BSP_DEBUG_WRITE: - IFX_MEI_IoctlCopyFrom (from_kernel, - (char *) (&debugrdwr), - (char *) lon, - sizeof (debugrdwr)); - - if (command == DSL_FIO_BSP_DEBUG_READ) - meierr = DSL_BSP_MemoryDebugAccess (pDev, - DSL_BSP_MEMORY_READ, - debugrdwr. - iAddress, - debugrdwr. - buffer, - debugrdwr. - iCount); - else - meierr = DSL_BSP_MemoryDebugAccess (pDev, - DSL_BSP_MEMORY_WRITE, - debugrdwr. - iAddress, - debugrdwr. - buffer, - debugrdwr. - iCount); - - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&debugrdwr), sizeof (debugrdwr)); - break; - case DSL_FIO_BSP_GET_VERSION: - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_mei_version), sizeof (DSL_DEV_Version_t)); - break; - -#define LQ_MPS_CHIPID_VERSION_GET(value) (((value) >> 28) & ((1 << 4) - 1)) - case DSL_FIO_BSP_GET_CHIP_INFO: - bsp_chip_info.major = 1; - bsp_chip_info.minor = LQ_MPS_CHIPID_VERSION_GET(*LQ_MPS_CHIPID); - IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_chip_info), sizeof (DSL_DEV_HwVersion_t)); - meierr = DSL_DEV_MEI_ERR_SUCCESS; - break; - - case DSL_FIO_BSP_FREE_RESOURCE: - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_STAT, 4, 0, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) { - meierr = DSL_DEV_MEI_ERR_FAILURE; - return -EIO; - } - IFX_MEI_DMSG("RxMessage[4] = %#x\n", m.msg.RxMessage[4]); - if (!(m.msg.RxMessage[4] & DSL_DEV_STAT_CODESWAP_COMPLETE)) { - meierr = DSL_DEV_MEI_ERR_FAILURE; - return -EAGAIN; - } - IFX_MEI_DMSG("Freeing all memories marked FREE_SHOWTIME\n"); - IFX_MEI_DFEMemoryFree (pDev, FREE_SHOWTIME); - meierr = DSL_DEV_MEI_ERR_SUCCESS; - break; -#ifdef CONFIG_IFXMIPS_AMAZON_SE - case DSL_FIO_ARC_MUX_TEST: - AMAZON_SE_MEI_ARC_MUX_Test(); - break; -#endif - default: -// IFX_MEI_EMSG("Invalid IOCTL command: %d\n"); - break; - } - return meierr; -} - -#ifdef CONFIG_IFXMIPS_AMAZON_SE -void AMAZON_SE_MEI_ARC_MUX_Test(void) -{ - u32 *p, i; - *LQ_RCU_RST |= LQ_RCU_RST_REQ_MUX_ARC; - - p = (u32*)(DFE_LDST_BASE_ADDR + IRAM0_BASE); - IFX_MEI_EMSG("Writing to IRAM0(%p)...\n", p); - for (i = 0; i < IRAM0_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - - p = (u32*)(DFE_LDST_BASE_ADDR + IRAM1_BASE); - IFX_MEI_EMSG("Writing to IRAM1(%p)...\n", p); - for (i = 0; i < IRAM1_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - - p = (u32*)(DFE_LDST_BASE_ADDR + BRAM_BASE); - IFX_MEI_EMSG("Writing to BRAM(%p)...\n", p); - for (i = 0; i < BRAM_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - - p = (u32*)(DFE_LDST_BASE_ADDR + XRAM_BASE); - IFX_MEI_EMSG("Writing to XRAM(%p)...\n", p); - for (i = 0; i < XRAM_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - - p = (u32*)(DFE_LDST_BASE_ADDR + YRAM_BASE); - IFX_MEI_EMSG("Writing to YRAM(%p)...\n", p); - for (i = 0; i < YRAM_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - - p = (u32*)(DFE_LDST_BASE_ADDR + EXT_MEM_BASE); - IFX_MEI_EMSG("Writing to EXT_MEM(%p)...\n", p); - for (i = 0; i < EXT_MEM_SIZE/sizeof(u32); i++, p++) { - *p = 0xdeadbeef; - if (*p != 0xdeadbeef) - IFX_MEI_EMSG("%p: %#x\n", p, *p); - } - *LQ_RCU_RST &= ~LQ_RCU_RST_REQ_MUX_ARC; -} -#endif -int -DSL_BSP_KernelIoctls (DSL_DEV_Device_t * pDev, unsigned int command, - unsigned long lon) -{ - int error = 0; - - error = IFX_MEI_Ioctls (pDev, 1, command, lon); - return error; -} - -static int -IFX_MEI_UserIoctls (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil, - unsigned int command, unsigned long lon) -{ - int error = 0; - int maj = MAJOR (ino->i_rdev); - int num = MINOR (ino->i_rdev); - DSL_DEV_Device_t *pDev; - - pDev = IFX_BSP_HandleGet (maj, num); - if (pDev == NULL) - return -EIO; - - error = IFX_MEI_Ioctls (pDev, 0, command, lon); - return error; -} - -#ifdef CONFIG_PROC_FS -/* - * Register a callback function for linux proc filesystem - */ -static int -IFX_MEI_InitProcFS (int num) -{ - struct proc_dir_entry *entry; - int i ; - DSL_DEV_Device_t *pDev; - reg_entry_t regs_temp[PROC_ITEMS] = { - /* flag, name, description } */ - {NULL, "arcmsgav", "arc to mei message ", 0}, - {NULL, "cmv_reply", "cmv needs reply", 0}, - {NULL, "cmv_waiting", "waiting for cmv reply from arc", 0}, - {NULL, "modem_ready_cnt", "ARC to MEI indicator count", 0}, - {NULL, "cmv_count", "MEI to ARC CMVs", 0}, - {NULL, "reply_count", "ARC to MEI Reply", 0}, - {NULL, "Recent_indicator", "most recent indicator", 0}, - {NULL, "fw_version", "Firmware Version", 0}, - {NULL, "fw_date", "Firmware Date", 0}, - {NULL, "meminfo", "Memory Allocation Information", 0}, - {NULL, "version", "MEI version information", 0}, - }; - - pDev = &dsl_devices[num]; - if (pDev == NULL) - return -ENOMEM; - - regs_temp[0].flag = &(DSL_DEV_PRIVATE(pDev)->arcmsgav); - regs_temp[1].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_reply); - regs_temp[2].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_waiting); - regs_temp[3].flag = &(DSL_DEV_PRIVATE(pDev)->modem_ready_cnt); - regs_temp[4].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_count); - regs_temp[5].flag = &(DSL_DEV_PRIVATE(pDev)->reply_count); - regs_temp[6].flag = (int *) &(DSL_DEV_PRIVATE(pDev)->Recent_indicator); - - memcpy ((char *) regs[num], (char *) regs_temp, sizeof (regs_temp)); - // procfs - meidir = proc_mkdir (MEI_DIRNAME, NULL); - if (meidir == NULL) { - IFX_MEI_EMSG ("Failed to create /proc/%s\n", MEI_DIRNAME); - return (-ENOMEM); - } - - for (i = 0; i < NUM_OF_REG_ENTRY; i++) { - entry = create_proc_entry (regs[num][i].name, - S_IWUSR | S_IRUSR | S_IRGRP | - S_IROTH, meidir); - if (entry) { - regs[num][i].low_ino = entry->low_ino; - entry->proc_fops = &IFX_MEI_ProcOperations; - } - else { - IFX_MEI_EMSG ("Failed to create /proc/%s/%s\n", MEI_DIRNAME, regs[num][i].name); - return (-ENOMEM); - } - } - return 0; -} - -/* - * Reading function for linux proc filesystem - */ -static int -IFX_MEI_ProcRead (struct file *file, char *buf, size_t nbytes, loff_t * ppos) -{ - int i_ino = (file->f_dentry->d_inode)->i_ino; - char *p = buf; - int i; - int num; - reg_entry_t *entry = NULL; - DSL_DEV_Device_t *pDev = NULL; - DSL_DEV_WinHost_Message_t m; - - for (num = 0; num < BSP_MAX_DEVICES; num++) { - for (i = 0; i < NUM_OF_REG_ENTRY; i++) { - if (regs[num][i].low_ino == (unsigned short)i_ino) { - entry = ®s[num][i]; - pDev = &dsl_devices[num]; - break; - } - } - } - if (entry == NULL) - return -EINVAL; - else if (strcmp(entry->name, "meminfo") == 0) { - if (*ppos > 0) /* Assume reading completed in previous read */ - return 0; - p += sprintf (p, "No Address Size\n"); - for (i = 0; i < MAX_BAR_REGISTERS; i++) { - p += sprintf (p, "BAR[%02d] Addr:0x%08X Size:%lu\n", - i, (u32) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[i].address, - DSL_DEV_PRIVATE(pDev)-> adsl_mem_info[i].size); - //printk( "BAR[%02d] Addr:0x%08X Size:%d\n",i,adsl_mem_info[i].address,adsl_mem_info[i].size); - } - *ppos += (p - buf); - } else if (strcmp(entry->name, "fw_version") == 0) { - if (*ppos > 0) /* Assume reading completed in previous read */ - return 0; - if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1) - return -EAGAIN; - //major:bits 0-7 - //minor:bits 8-15 - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 0, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) - return -EIO; - p += sprintf(p, "FW Version: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF); - //sub_version:bits 4-7 - //int_version:bits 0-3 - //spl_appl:bits 8-13 - //rel_state:bits 14-15 - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 1, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) - return -EIO; - p += sprintf(p, "%d.%d.%d.%d\n", - (m.msg.RxMessage[4] >> 4) & 0xF, m.msg.RxMessage[4] & 0xF, - (m.msg.RxMessage[4] >> 14) & 3, (m.msg.RxMessage[4] >> 8) & 0x3F); - *ppos += (p - buf); - } else if (strcmp(entry->name, "fw_date") == 0) { - if (*ppos > 0) /* Assume reading completed in previous read */ - return 0; - if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1) - return -EAGAIN; - - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 0, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) - return -EIO; - /* Day/Month */ - p += sprintf(p, "FW Date: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF); - - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 2, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) - return -EIO; - /* Year */ - p += sprintf(p, "%d ", m.msg.RxMessage[4]); - - makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 1, 1, NULL, m.msg.TxMessage); - if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) - return -EIO; - /* Hour:Minute */ - p += sprintf(p, "%d:%d\n", (m.msg.RxMessage[4] >> 8) & 0xFF, m.msg.RxMessage[4] & 0xFF); - - *ppos += (p - buf); - } else if (strcmp(entry->name, "version") == 0) { - if (*ppos > 0) /* Assume reading completed in previous read */ - return 0; - p += sprintf (p, "IFX MEI V%ld.%ld.%ld\n", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision); - - *ppos += (p - buf); - } else if (entry->flag != (int *) DSL_DEV_PRIVATE(pDev)->Recent_indicator) { - if (*ppos > 0) /* Assume reading completed in previous read */ - return 0; // indicates end of file - p += sprintf (p, "0x%08X\n\n", *(entry->flag)); - *ppos += (p - buf); - if ((p - buf) > nbytes) /* Assume output can be read at one time */ - return -EINVAL; - } else { - if ((int) (*ppos) / ((int) 7) == 16) - return 0; // indicate end of the message - p += sprintf (p, "0x%04X\n\n", *(((u16 *) (entry->flag)) + (int) (*ppos) / ((int) 7))); - *ppos += (p - buf); - } - return p - buf; -} - -/* - * Writing function for linux proc filesystem - */ -static ssize_t -IFX_MEI_ProcWrite (struct file *file, const char *buffer, size_t count, loff_t * ppos) -{ - int i_ino = (file->f_dentry->d_inode)->i_ino; - reg_entry_t *current_reg = NULL; - int i = 0; - int num = 0; - unsigned long newRegValue = 0; - char *endp = NULL; - DSL_DEV_Device_t *pDev = NULL; - - for (num = 0; num < BSP_MAX_DEVICES; num++) { - for (i = 0; i < NUM_OF_REG_ENTRY; i++) { - if (regs[num][i].low_ino == i_ino) { - current_reg = ®s[num][i]; - pDev = &dsl_devices[num]; - break; - } - } - } - if ((current_reg == NULL) - || (current_reg->flag == - (int *) DSL_DEV_PRIVATE(pDev)-> - Recent_indicator)) - return -EINVAL; - - newRegValue = simple_strtoul (buffer, &endp, 0); - *(current_reg->flag) = (int) newRegValue; - return (count + endp - buffer); -} -#endif //CONFIG_PROC_FS - -static int adsl_dummy_ledcallback(void) -{ - return 0; -} - -int ifx_mei_atm_led_blink(void) -{ - return g_adsl_ledcallback(); -} -EXPORT_SYMBOL(ifx_mei_atm_led_blink); - -int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr) -{ - int i; - - if ( is_showtime ) { - *is_showtime = g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ? 0 : 1; - } - - if ( port_cell ) { - for ( i = 0; i < port_cell->port_num && i < 2; i++ ) - port_cell->tx_link_rate[i] = g_tx_link_rate[i]; - } - - if ( xdata_addr ) { - if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ) - *xdata_addr = NULL; - else - *xdata_addr = g_xdata_addr; - } - - return 0; -} -EXPORT_SYMBOL(ifx_mei_atm_showtime_check); - -/* - * Writing function for linux proc filesystem - */ -int __init -IFX_MEI_ModuleInit (void) -{ - int i = 0; - static struct class *dsl_class; - - pr_info("IFX MEI Version %ld.%02ld.%02ld", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision); - - for (i = 0; i < BSP_MAX_DEVICES; i++) { - if (IFX_MEI_InitDevice (i) != 0) { - IFX_MEI_EMSG("Init device fail!\n"); - return -EIO; - } - IFX_MEI_InitDevNode (i); -#ifdef CONFIG_PROC_FS - IFX_MEI_InitProcFS (i); -#endif - } - for (i = 0; i <= DSL_BSP_CB_LAST ; i++) - dsl_bsp_event_callback[i].function = NULL; - -#ifdef CONFIG_LQ_MEI_FW_LOOPBACK - IFX_MEI_DMSG("Start loopback test...\n"); - DFE_Loopback_Test (); -#endif - dsl_class = class_create(THIS_MODULE, "ifx_mei"); - device_create(dsl_class, NULL, MKDEV(MEI_MAJOR, 0), NULL, "ifx_mei"); - return 0; -} - -void __exit -IFX_MEI_ModuleExit (void) -{ - int i = 0; - int num; - - for (num = 0; num < BSP_MAX_DEVICES; num++) { - IFX_MEI_CleanUpDevNode (num); -#ifdef CONFIG_PROC_FS - for (i = 0; i < NUM_OF_REG_ENTRY; i++) { - remove_proc_entry (regs[num][i].name, meidir); - } -#endif - } - - remove_proc_entry (MEI_DIRNAME, NULL); - for (i = 0; i < BSP_MAX_DEVICES; i++) { - for (i = 0; i < BSP_MAX_DEVICES; i++) { - IFX_MEI_ExitDevice (i); - } - } -} - -/* export function for DSL Driver */ - -/* The functions of MEI_DriverHandleGet and MEI_DriverHandleDelete are -something like open/close in kernel space , where the open could be used -to register a callback for autonomous messages and returns a mei driver context pointer (comparable to the file descriptor in user space) - The context will be required for the multi line chips future! */ - -EXPORT_SYMBOL (DSL_BSP_DriverHandleGet); -EXPORT_SYMBOL (DSL_BSP_DriverHandleDelete); - -EXPORT_SYMBOL (DSL_BSP_ATMLedCBRegister); -EXPORT_SYMBOL (DSL_BSP_ATMLedCBUnregister); -EXPORT_SYMBOL (DSL_BSP_KernelIoctls); -EXPORT_SYMBOL (DSL_BSP_AdslLedInit); -//EXPORT_SYMBOL (DSL_BSP_AdslLedSet); -EXPORT_SYMBOL (DSL_BSP_FWDownload); -EXPORT_SYMBOL (DSL_BSP_Showtime); - -EXPORT_SYMBOL (DSL_BSP_MemoryDebugAccess); -EXPORT_SYMBOL (DSL_BSP_SendCMV); - -// provide a register/unregister function for DSL driver to register a event callback function -EXPORT_SYMBOL (DSL_BSP_EventCBRegister); -EXPORT_SYMBOL (DSL_BSP_EventCBUnregister); - -module_init (IFX_MEI_ModuleInit); -module_exit (IFX_MEI_ModuleExit); - -MODULE_LICENSE("Dual BSD/GPL"); diff --git a/package/ltq-dsl-app/Makefile b/package/ltq-dsl-app/Makefile new file mode 100644 index 0000000000..5be052f6e2 --- /dev/null +++ b/package/ltq-dsl-app/Makefile @@ -0,0 +1,80 @@ +# +# Copyright (C) 2011 OpenWrt.org +# +# This is free software, licensed under the GNU General Public License v2. +# See /LICENSE for more information. +# + +include $(TOPDIR)/rules.mk +include $(INCLUDE_DIR)/kernel.mk + +PKG_BASE_NAME:=dsl_cpe_control_danube +PKG_VERSION:=3.24.4.4 +PKG_RELEASE:=1 +PKG_SOURCE:=$(PKG_BASE_NAME)-$(PKG_VERSION).tar.gz +PKG_BUILD_DIR:=$(BUILD_DIR)/dsl_cpe_control-$(PKG_VERSION) +PKG_SOURCE_URL:=http://mirror2.openwrt.org/sources/ +PKG_MD5SUM:=ee315306626b68794d3d3636dabfe161 + +include $(INCLUDE_DIR)/package.mk + +define Package/ltq-dsl-app + SECTION:=net + CATEGORY:=Network + TITLE:=Lantiq DSL userland tool + URL:=http://www.lantiq.com/ + DEPENDS:=@TARGET_lantiq_xway +kmod-ltq-dsl +libpthread + MAINTAINER:=John Crispin +endef + +define Package/ltq-dsl-app/description + Infineon DSL CPE API for Amazon SE, Danube and Vinax. +endef + +IFX_DSL_MAX_DEVICE=1 +IFX_DSL_LINES_PER_DEVICE=1 +IFX_DSL_CHANNELS_PER_LINE=1 +#CONFIG_IFX_CLI=y + +CONFIGURE_ARGS += \ + --with-max-device="$(IFX_DSL_MAX_DEVICE)" \ + --with-lines-per-device="$(IFX_DSL_LINES_PER_DEVICE)" \ + --with-channels-per-line="$(IFX_DSL_CHANNELS_PER_LINE)" \ + --enable-danube \ + --enable-driver-include="-I$(STAGING_DIR)/usr/include" \ + --enable-debug-prints \ + --enable-add-appl-cflags="-DMAX_CLI_PIPES=2" \ + --enable-cmv-scripts \ + --enable-debug-tool-interface \ + --enable-adsl-led \ + --enable-dsl-ceoc \ + --enable-script-notification \ + --enable-dsl-pm \ + --enable-dsl-pm-total \ + --enable-dsl-pm-history \ + --enable-dsl-pm-showtime \ + --enable-dsl-pm-channel-counters \ + --enable-dsl-pm-datapath-counters \ + --enable-dsl-pm-line-counters \ + --enable-dsl-pm-channel-thresholds \ + --enable-dsl-pm-datapath-thresholds \ + --enable-dsl-pm-line-thresholds \ + --enable-dsl-pm-optional-parameters + +ifeq ($(CONFIG_IFX_CLI),y) +CONFIGURE_ARGS += \ + --enable-cli-support \ + --enable-soap-support +endif + +TARGET_CFLAGS += -I$(LINUX_DIR)/include + +define Package/ltq-dsl-app/install + $(INSTALL_DIR) $(1)/etc/init.d + $(INSTALL_BIN) ./files/ifx_cpe_control_init.sh $(1)/etc/init.d/ + + $(INSTALL_DIR) $(1)/sbin + $(INSTALL_BIN) $(PKG_BUILD_DIR)/src/dsl_cpe_control $(1)/sbin +endef + +$(eval $(call BuildPackage,ltq-dsl-app)) diff --git a/package/ltq-dsl-app/files/ifx_cpe_control_init.sh b/package/ltq-dsl-app/files/ifx_cpe_control_init.sh new file mode 100644 index 0000000000..91316938ce --- /dev/null +++ b/package/ltq-dsl-app/files/ifx_cpe_control_init.sh @@ -0,0 +1,21 @@ +#!/bin/sh /etc/rc.common +# Copyright (C) 2008 OpenWrt.org +START=99 + +start() { + + # start CPE dsl daemon in the background + /sbin/dsl_cpe_control -i -f /lib/firmware/ModemHWE.bin & + +# PS=`ps` +# echo $PS | grep -q dsl_cpe_control && { +# # workaround for nfs: allow write to pipes for non-root +# while [ ! -e /tmp/pipe/dsl_cpe1_ack ] ; do sleep 1; done +# chmod a+w /tmp/pipe/dsl_* +# } + echo $PS | grep -q dsl_cpe_control || { + echo "Start of dsl_cpe_control failed!!!" + false + } + +} diff --git a/package/ltq-dsl/Config.in b/package/ltq-dsl/Config.in new file mode 100644 index 0000000000..6d9caf4419 --- /dev/null +++ b/package/ltq-dsl/Config.in @@ -0,0 +1,5 @@ +config LANTIQ_DSL_DEBUG + bool "verbose debugging" + depends on PACKAGE_kmod-ltq-dsl + help + Say Y, if you need ltq-dsl to display debug messages. diff --git a/package/ltq-dsl/Makefile b/package/ltq-dsl/Makefile new file mode 100644 index 0000000000..6f8f6ba0c6 --- /dev/null +++ b/package/ltq-dsl/Makefile @@ -0,0 +1,170 @@ +# +# Copyright (C) 2011 OpenWrt.org +# +# This is free software, licensed under the GNU General Public License v2. +# See /LICENSE for more information. +# + +include $(TOPDIR)/rules.mk +include $(INCLUDE_DIR)/kernel.mk + +PKG_NAME:=ltq-dsl +PKG_BASE_NAME:=drv_dsl_cpe_api_danube +PKG_VERSION:=3.24.4.4 +PKG_RELEASE:=2 +PKG_SOURCE:=$(PKG_BASE_NAME)-$(PKG_VERSION).tar.gz +PKG_BUILD_DIR:=$(KERNEL_BUILD_DIR)/drv_dsl_cpe_api-$(PKG_VERSION) +PKG_SOURCE_URL:=http://mirror2.openwrt.org/sources/ +PKG_MD5SUM:=c45bc531c1ed2ac80f68fb986b63bb87 + +FW_BASE_NAME:=dsl_danube_firmware_adsl +FW_A_VER:=02.04.04.00.00.01 +FW_B_VER:=02.04.01.07.00.02 +FW_A_FILE_VER:=244001 +FW_B_FILE_VER:=241702 +FW_A_MD5:=f717db3067a0049a26e233ab11238710 +FW_B_MD5:=349de7cd20368f4ac9b7e8322114a512 + +include $(INCLUDE_DIR)/package.mk + +define KernelPackage/ltq-dsl + SECTION:=sys + CATEGORY:=Kernel modules + SUBMENU:=Network Devices + TITLE:=Lantiq dsl driver + URL:=http://www.lantiq.com/ + DEPENDS:=@TARGET_lantiq_xway +kmod-atm + FILES:=$(PKG_BUILD_DIR)/src/mei/lantiq_mei.ko \ + $(PKG_BUILD_DIR)/src/drv_dsl_cpe_api.ko \ + $(PKG_BUILD_DIR)/src/mei/lantiq_atm.ko + AUTOLOAD:=$(call AutoLoad,50,lantiq_mei drv_dsl_cpe_api lantiq_atm) + MAINTAINER:=John Crispin +endef + +define Package/kmod-ltq-dsl-firmware/default + SECTION:=sys + CATEGORY:=Kernel modules + SUBMENU:=Network Devices + TITLE:=Firmware + URL:=http://www.lantiq.com/ + DEPENDS:=@TARGET_lantiq_xway kmod-ltq-dsl + MAINTAINER:=John Crispin +endef + +define Package/kmod-ltq-dsl-firmware-a + $(call Package/kmod-ltq-dsl-firmware/default) + TITLE+=Annex-A Danube +endef + +define Package/kmod-ltq-dsl-firmware-b + $(call Package/kmod-ltq-dsl-firmware/default) + TITLE+=Annex-B Danube +endef + +define KernelPackage/ltq-dsl/description + Lantiq DSL CPE API for Amazon SE, Danube and Vinax. +endef + +define KernelPackage/ltq-dsl/config + source "$(SOURCE)/Config.in" +endef + +define Download/annex-a + FILE:=$(FW_BASE_NAME)_a-$(FW_A_VER).tar.gz + URL:=http://mirror2.openwrt.org/sources/ + MD5SUM:=$(FW_A_MD5) +endef +$(eval $(call Download,annex-a)) + +define Download/annex-b + FILE:=$(FW_BASE_NAME)_b-$(FW_B_VER).tar.gz + URL:=http://mirror2.openwrt.org/sources/ + MD5SUM:=$(FW_B_MD5) +endef +$(eval $(call Download,annex-b)) + +IFX_DSL_MAX_DEVICE=1 +IFX_DSL_LINES_PER_DEVICE=1 +IFX_DSL_CHANNELS_PER_LINE=1 + +CONFIGURE_ARGS += --enable-kernel-include="$(LINUX_DIR)/include" \ + --with-max-device="$(IFX_DSL_MAX_DEVICE)" \ + --with-lines-per-device="$(IFX_DSL_LINES_PER_DEVICE)" \ + --with-channels-per-line="$(IFX_DSL_CHANNELS_PER_LINE)" \ + --enable-danube \ + --enable-add-drv-cflags="-DMODULE" \ + --disable-dsl-delt-static \ + --disable-adsl-led \ + --enable-dsl-ceoc \ + --enable-dsl-pm \ + --enable-dsl-pm-total \ + --enable-dsl-pm-history \ + --enable-dsl-pm-showtime \ + --enable-dsl-pm-channel-counters \ + --enable-dsl-pm-datapath-counters \ + --enable-dsl-pm-line-counters \ + --enable-dsl-pm-channel-thresholds \ + --enable-dsl-pm-datapath-thresholds \ + --enable-dsl-pm-line-thresholds \ + --enable-dsl-pm-optional-parameters \ + --enable-linux-26 \ + --enable-kernelbuild="$(LINUX_DIR)" \ + ARCH=$(LINUX_KARCH) + +EXTRA_CFLAGS = -fno-pic -mno-abicalls -mlong-calls -G 0 + +ifeq ($(CONFIG_LANTIQ_DSL_DEBUG),y) +CONFIGURE_ARGS += \ + --enable-debug=yes \ + --enable-debug-prints=yes +EXTRA_CFLAGS += -DDEBUG +endif + +define Build/Prepare + $(PKG_UNPACK) + $(INSTALL_DIR) $(PKG_BUILD_DIR)/src/mei/ + $(CP) ./src/* $(PKG_BUILD_DIR)/src/mei/ + $(Build/Patch) + $(TAR) -C $(PKG_BUILD_DIR) -xzf $(DL_DIR)/$(FW_BASE_NAME)_a-$(FW_A_VER).tar.gz + $(TAR) -C $(PKG_BUILD_DIR) -xzf $(DL_DIR)/$(FW_BASE_NAME)_b-$(FW_B_VER).tar.gz +endef + +define Build/Configure + (cd $(PKG_BUILD_DIR); aclocal && autoconf && automake) + $(call Build/Configure/Default) +endef + +define Build/Compile + cd $(LINUX_DIR); \ + ARCH=mips CROSS_COMPILE="$(KERNEL_CROSS)" \ + $(MAKE) M=$(PKG_BUILD_DIR)/src/mei/ V=1 modules + $(call Build/Compile/Default) +endef + +define Build/InstallDev + $(INSTALL_DIR) $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_ioctl.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_adslmib.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_adslmib_ioctl.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_g997.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_types.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_pm.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_api_error.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_danube_ctx.h $(1)/usr/include + $(CP) $(PKG_BUILD_DIR)/src/include/drv_dsl_cpe_cmv_danube.h $(1)/usr/include +endef + +define Package/ltq-dsl-firmware-a/install + $(INSTALL_DIR) $(1)/lib/firmware/ + $(CP) $(PKG_BUILD_DIR)/$(FW_BASE_NAME)_a_$(FW_A_FILE_VER).bin $(1)/lib/firmware/ModemHWE.bin +endef + +define Package/ltq-dsl-firmware-b/install + $(INSTALL_DIR) $(1)/lib/firmware/ + $(CP) $(PKG_BUILD_DIR)/$(FW_BASE_NAME)_b_$(FW_B_FILE_VER).bin $(1)/lib/firmware/ModemHWE.bin +endef + +$(eval $(call KernelPackage,ltq-dsl)) +$(eval $(call BuildPackage,kmod-ltq-dsl-firmware-a)) +$(eval $(call BuildPackage,kmod-ltq-dsl-firmware-b)) diff --git a/package/ltq-dsl/patches/100-dsl_compat.patch b/package/ltq-dsl/patches/100-dsl_compat.patch new file mode 100644 index 0000000000..334ac6736e --- /dev/null +++ b/package/ltq-dsl/patches/100-dsl_compat.patch @@ -0,0 +1,62 @@ +--- a/src/include/drv_dsl_cpe_device_danube.h ++++ b/src/include/drv_dsl_cpe_device_danube.h +@@ -24,7 +24,7 @@ + #include "drv_dsl_cpe_simulator_danube.h" + #else + /* Include for the low level driver interface header file */ +-#include "asm/ifx/ifx_mei_bsp.h" ++#include "mei/ifxmips_mei_interface.h" + #endif /* defined(DSL_CPE_SIMULATOR_DRIVER) && defined(WIN32)*/ + + #define DSL_MAX_LINE_NUMBER 1 +--- a/src/common/drv_dsl_cpe_os_linux.c ++++ b/src/common/drv_dsl_cpe_os_linux.c +@@ -11,6 +11,7 @@ + #ifdef __LINUX__ + + #define DSL_INTERN ++#include + + #include "drv_dsl_cpe_api.h" + #include "drv_dsl_cpe_api_ioctl.h" +@@ -1058,6 +1059,7 @@ static void DSL_DRV_DebugInit(void) + /* Entry point of driver */ + int __init DSL_ModuleInit(void) + { ++ struct class *dsl_class; + DSL_int_t i; + + printk(DSL_DRV_CRLF DSL_DRV_CRLF "Infineon CPE API Driver version: %s" DSL_DRV_CRLF, +@@ -1104,7 +1106,8 @@ int __init DSL_ModuleInit(void) + } + + DSL_DRV_DevNodeInit(); +- ++ dsl_class = class_create(THIS_MODULE, "dsl_cpe_api"); ++ device_create(dsl_class, NULL, MKDEV(DRV_DSL_CPE_API_DEV_MAJOR, 0), NULL, "dsl_cpe_api"); + return 0; + } + +--- a/src/include/drv_dsl_cpe_os_linux.h ++++ b/src/include/drv_dsl_cpe_os_linux.h +@@ -17,17 +17,17 @@ + #endif + + #include +-#include ++#include + #include + #include + #include + #include + #include + #include +- ++#include + + #if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,17)) +- #include ++ #include + #endif + + #include diff --git a/package/ltq-dsl/patches/500-portability.patch b/package/ltq-dsl/patches/500-portability.patch new file mode 100644 index 0000000000..48e9d173d4 --- /dev/null +++ b/package/ltq-dsl/patches/500-portability.patch @@ -0,0 +1,218 @@ +Index: drv_dsl_cpe_api-3.24.4.4/configure.in +=================================================================== +--- drv_dsl_cpe_api-3.24.4.4.orig/configure.in 2009-08-13 13:39:21.000000000 +0200 ++++ drv_dsl_cpe_api-3.24.4.4/configure.in 2010-10-14 02:14:55.000000000 +0200 +@@ -310,7 +310,7 @@ + AC_ARG_ENABLE(kernelbuild, + AC_HELP_STRING(--enable-kernel-build=x,Set the target kernel build path), + [ +- if test -e $enableval/include/linux/autoconf.h; then ++ if test -e $enableval/include/linux/autoconf.h -o -e $enableval/include/generated/autoconf.h; then + AC_SUBST([KERNEL_BUILD_PATH],[$enableval]) + else + AC_MSG_ERROR([The kernel build directory is not valid or not configured!]) +@@ -333,12 +333,12 @@ + echo Set the lib_ifxos include path $enableval + AC_SUBST([IFXOS_INCLUDE_PATH],[$enableval]) + else +- echo -e Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH ++ echo Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH + AC_SUBST([IFXOS_INCLUDE_PATH],[$DEFAULT_IFXOS_INCLUDE_PATH]) + fi + ], + [ +- echo -e Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH ++ echo Set the default lib_ifxos include path $DEFAULT_IFXOS_INCLUDE_PATH + AC_SUBST([IFXOS_INCLUDE_PATH],[$DEFAULT_IFXOS_INCLUDE_PATH]) + ] + ) +@@ -1702,73 +1702,73 @@ + AC_SUBST([DISTCHECK_CONFIGURE_PARAMS],[$CONFIGURE_OPTIONS]) + + AC_CONFIG_COMMANDS_PRE([ +-echo -e "------------------------------------------------------------------------" +-echo -e " Configuration for drv_dsl_cpe_api:" +-echo -e " Configure model type: $DSL_CONFIG_MODEL_TYPE" +-echo -e " Source code location: $srcdir" +-echo -e " Compiler: $CC" +-echo -e " Compiler c-flags: $CFLAGS" +-echo -e " Extra compiler c-flags: $EXTRA_DRV_CFLAGS" +-echo -e " Host System Type: $host" +-echo -e " Install path: $prefix" +-echo -e " Linux kernel include path: $KERNEL_INCL_PATH" +-echo -e " Linux kernel build path: $KERNEL_BUILD_PATH" +-echo -e " Linux kernel architecture: $KERNEL_ARCH" +-echo -e " Include IFXOS: $INCLUDE_DSL_CPE_API_IFXOS_SUPPORT" +-echo -e " IFXOS include path: $IFXOS_INCLUDE_PATH" +-echo -e " Driver Include Path $DSL_DRIVER_INCL_PATH" +-echo -e " DSL device: $DSL_DEVICE_NAME" +-echo -e " Max device number: $DSL_DRV_MAX_DEVICE_NUMBER" +-echo -e " Channels per line: $DSL_CHANNELS_PER_LINE" +-echo -e " Build lib (only for kernel 2.6) $DSL_CPE_API_LIBRARY_BUILD_2_6" +-echo -e " DSL data led flash frequency: $DSL_DATA_LED_FLASH_FREQUENCY Hz" +-echo -e " Disable debug prints: $DSL_DEBUG_DISABLE" +-echo -e " Preselection of max. debug level: $DSL_DBG_MAX_LEVEL_SET" +-echo -e " Preselected max. debug level: $DSL_DBG_MAX_LEVEL_PRE" +-echo -e " Include deprecated functions: $INCLUDE_DEPRECATED" +-echo -e " Include Device Exception Codes: $INCLUDE_DEVICE_EXCEPTION_CODES" +-echo -e " Include FW request support: $INCLUDE_FW_REQUEST_SUPPORT" +-echo -e " Include ADSL trace buffer: $INCLUDE_DSL_CPE_TRACE_BUFFER" +-echo -e " Include ADSL MIB: $INCLUDE_DSL_ADSL_MIB" +-echo -e " Include ADSL LED: $INCLUDE_ADSL_LED" +-echo -e " Include CEOC: $INCLUDE_DSL_CEOC" +-echo -e " Include config get support: $INCLUDE_DSL_CONFIG_GET" +-echo -e " Include System i/f configuration: $INCLUDE_DSL_SYSTEM_INTERFACE" +-echo -e " Include Resource Statistics: $INCLUDE_DSL_RESOURCE_STATISTICS" +-echo -e " Include Framing Parameters: $INCLUDE_DSL_FRAMING_PARAMETERS" +-echo -e " Include G997 Line Inventory: $INCLUDE_DSL_G997_LINE_INVENTORY" +-echo -e " Include G997 Framing Parameters: $INCLUDE_DSL_G997_FRAMING_PARAMETERS" +-echo -e " Include G997 per tone data: $INCLUDE_DSL_G997_PER_TONE" +-echo -e " Include G997 status: $INCLUDE_DSL_G997_STATUS" +-echo -e " Include G997 alarm: $INCLUDE_DSL_G997_ALARM" +-echo -e " Include DSL Bonding: $INCLUDE_DSL_BONDING" +-echo -e " Include Misc Line Status $INCLUDE_DSL_CPE_MISC_LINE_STATUS" +-echo -e " Include DELT: $INCLUDE_DSL_DELT" +-echo -e " Include DELT data static storage: $DSL_CPE_STATIC_DELT_DATA" +-echo -e " Include PM: $INCLUDE_DSL_PM" +-echo -e " Include PM config: $INCLUDE_DSL_CPE_PM_CONFIG" +-echo -e " Include PM total: $INCLUDE_DSL_CPE_PM_TOTAL_COUNTERS" +-echo -e " Include PM history: $INCLUDE_DSL_CPE_PM_HISTORY" +-echo -e " Include PM showtime: $INCLUDE_DSL_CPE_PM_SHOWTIME_COUNTERS" +-echo -e " Include PM optional: $INCLUDE_DSL_CPE_PM_OPTIONAL_PARAMETERS" +-echo -e " Include PM line: $INCLUDE_DSL_CPE_PM_LINE_COUNTERS" +-echo -e " Include PM line event showtime: $INCLUDE_DSL_CPE_PM_LINE_EVENT_SHOWTIME_COUNTERS" +-echo -e " Include PM channel: $INCLUDE_DSL_CPE_PM_CHANNEL_COUNTERS" +-echo -e " Include PM channel extended: $INCLUDE_DSL_CPE_PM_CHANNEL_EXT_COUNTERS" +-echo -e " Include PM data path: $INCLUDE_DSL_CPE_PM_DATA_PATH_COUNTERS" +-echo -e " Include PM data path failure: $INCLUDE_DSL_CPE_PM_DATA_PATH_FAILURE_COUNTERS" +-echo -e " Include PM ReTx: $INCLUDE_DSL_CPE_PM_RETX_COUNTERS" +-echo -e " Include PM line threshold: $INCLUDE_DSL_CPE_PM_LINE_THRESHOLDS" +-echo -e " Include PM channel threshold: $INCLUDE_DSL_CPE_PM_CHANNEL_THRESHOLDS" +-echo -e " Include PM data path threshold: $INCLUDE_DSL_CPE_PM_DATA_PATH_THRESHOLDS" +-echo -e " Include PM ReTx threshold: $INCLUDE_DSL_CPE_PM_RETX_THRESHOLDS" +-echo -e " Include FW memory free support: $INCLUDE_DSL_FIRMWARE_MEMORY_FREE" +-echo -e "----------------------- deprectated ! ----------------------------------" +-echo -e " Include PM line failure: $INCLUDE_DSL_CPE_PM_LINE_FAILURE_COUNTERS" +-echo -e "" +-echo -e " Settings:" +-echo -e " Configure options: $CONFIGURE_OPTIONS" +-echo -e "------------------------------------------------------------------------" ++echo "------------------------------------------------------------------------" ++echo " Configuration for drv_dsl_cpe_api:" ++echo " Configure model type: $DSL_CONFIG_MODEL_TYPE" ++echo " Source code location: $srcdir" ++echo " Compiler: $CC" ++echo " Compiler c-flags: $CFLAGS" ++echo " Extra compiler c-flags: $EXTRA_DRV_CFLAGS" ++echo " Host System Type: $host" ++echo " Install path: $prefix" ++echo " Linux kernel include path: $KERNEL_INCL_PATH" ++echo " Linux kernel build path: $KERNEL_BUILD_PATH" ++echo " Linux kernel architecture: $KERNEL_ARCH" ++echo " Include IFXOS: $INCLUDE_DSL_CPE_API_IFXOS_SUPPORT" ++echo " IFXOS include path: $IFXOS_INCLUDE_PATH" ++echo " Driver Include Path $DSL_DRIVER_INCL_PATH" ++echo " DSL device: $DSL_DEVICE_NAME" ++echo " Max device number: $DSL_DRV_MAX_DEVICE_NUMBER" ++echo " Channels per line: $DSL_CHANNELS_PER_LINE" ++echo " Build lib (only for kernel 2.6) $DSL_CPE_API_LIBRARY_BUILD_2_6" ++echo " DSL data led flash frequency: $DSL_DATA_LED_FLASH_FREQUENCY Hz" ++echo " Disable debug prints: $DSL_DEBUG_DISABLE" ++echo " Preselection of max. debug level: $DSL_DBG_MAX_LEVEL_SET" ++echo " Preselected max. debug level: $DSL_DBG_MAX_LEVEL_PRE" ++echo " Include deprecated functions: $INCLUDE_DEPRECATED" ++echo " Include Device Exception Codes: $INCLUDE_DEVICE_EXCEPTION_CODES" ++echo " Include FW request support: $INCLUDE_FW_REQUEST_SUPPORT" ++echo " Include ADSL trace buffer: $INCLUDE_DSL_CPE_TRACE_BUFFER" ++echo " Include ADSL MIB: $INCLUDE_DSL_ADSL_MIB" ++echo " Include ADSL LED: $INCLUDE_ADSL_LED" ++echo " Include CEOC: $INCLUDE_DSL_CEOC" ++echo " Include config get support: $INCLUDE_DSL_CONFIG_GET" ++echo " Include System i/f configuration: $INCLUDE_DSL_SYSTEM_INTERFACE" ++echo " Include Resource Statistics: $INCLUDE_DSL_RESOURCE_STATISTICS" ++echo " Include Framing Parameters: $INCLUDE_DSL_FRAMING_PARAMETERS" ++echo " Include G997 Line Inventory: $INCLUDE_DSL_G997_LINE_INVENTORY" ++echo " Include G997 Framing Parameters: $INCLUDE_DSL_G997_FRAMING_PARAMETERS" ++echo " Include G997 per tone data: $INCLUDE_DSL_G997_PER_TONE" ++echo " Include G997 status: $INCLUDE_DSL_G997_STATUS" ++echo " Include G997 alarm: $INCLUDE_DSL_G997_ALARM" ++echo " Include DSL Bonding: $INCLUDE_DSL_BONDING" ++echo " Include Misc Line Status $INCLUDE_DSL_CPE_MISC_LINE_STATUS" ++echo " Include DELT: $INCLUDE_DSL_DELT" ++echo " Include DELT data static storage: $DSL_CPE_STATIC_DELT_DATA" ++echo " Include PM: $INCLUDE_DSL_PM" ++echo " Include PM config: $INCLUDE_DSL_CPE_PM_CONFIG" ++echo " Include PM total: $INCLUDE_DSL_CPE_PM_TOTAL_COUNTERS" ++echo " Include PM history: $INCLUDE_DSL_CPE_PM_HISTORY" ++echo " Include PM showtime: $INCLUDE_DSL_CPE_PM_SHOWTIME_COUNTERS" ++echo " Include PM optional: $INCLUDE_DSL_CPE_PM_OPTIONAL_PARAMETERS" ++echo " Include PM line: $INCLUDE_DSL_CPE_PM_LINE_COUNTERS" ++echo " Include PM line event showtime: $INCLUDE_DSL_CPE_PM_LINE_EVENT_SHOWTIME_COUNTERS" ++echo " Include PM channel: $INCLUDE_DSL_CPE_PM_CHANNEL_COUNTERS" ++echo " Include PM channel extended: $INCLUDE_DSL_CPE_PM_CHANNEL_EXT_COUNTERS" ++echo " Include PM data path: $INCLUDE_DSL_CPE_PM_DATA_PATH_COUNTERS" ++echo " Include PM data path failure: $INCLUDE_DSL_CPE_PM_DATA_PATH_FAILURE_COUNTERS" ++echo " Include PM ReTx: $INCLUDE_DSL_CPE_PM_RETX_COUNTERS" ++echo " Include PM line threshold: $INCLUDE_DSL_CPE_PM_LINE_THRESHOLDS" ++echo " Include PM channel threshold: $INCLUDE_DSL_CPE_PM_CHANNEL_THRESHOLDS" ++echo " Include PM data path threshold: $INCLUDE_DSL_CPE_PM_DATA_PATH_THRESHOLDS" ++echo " Include PM ReTx threshold: $INCLUDE_DSL_CPE_PM_RETX_THRESHOLDS" ++echo " Include FW memory free support: $INCLUDE_DSL_FIRMWARE_MEMORY_FREE" ++echo "----------------------- deprectated ! ----------------------------------" ++echo " Include PM line failure: $INCLUDE_DSL_CPE_PM_LINE_FAILURE_COUNTERS" ++echo "" ++echo " Settings:" ++echo " Configure options: $CONFIGURE_OPTIONS" ++echo "------------------------------------------------------------------------" + ]) + + AC_CONFIG_FILES([Makefile src/Makefile]) +Index: drv_dsl_cpe_api-3.24.4.4/src/Makefile.am +=================================================================== +--- drv_dsl_cpe_api-3.24.4.4.orig/src/Makefile.am 2009-07-03 14:06:34.000000000 +0200 ++++ drv_dsl_cpe_api-3.24.4.4/src/Makefile.am 2010-10-14 02:14:55.000000000 +0200 +@@ -303,7 +303,7 @@ + drv_dsl_cpe_api_OBJS = "$(subst .c,.o,$(filter %.c,$(drv_dsl_cpe_api_SOURCES)))" + + drv_dsl_cpe_api.ko: $(drv_dsl_cpe_api_SOURCES) +- @echo -e "drv_dsl_cpe_api: Making Linux 2.6.x kernel object" ++ @echo "drv_dsl_cpe_api: Making Linux 2.6.x kernel object" + if test ! -e common/drv_dsl_cpe_api.c ; then \ + echo "copy source files (as links only!)"; \ + for f in $(filter %.c,$(drv_dsl_cpe_api_SOURCES)); do \ +@@ -311,10 +311,10 @@ + cp -s $(addprefix @abs_srcdir@/,$$f) $(PWD)/`dirname $$f`/ ; \ + done \ + fi +- @echo -e "# drv_dsl_cpe_api: Generated to build Linux 2.6.x kernel object" > $(PWD)/Kbuild +- @echo -e "obj-m := $(subst .ko,.o,$@)" >> $(PWD)/Kbuild +- @echo -e "$(subst .ko,,$@)-y := $(drv_dsl_cpe_api_OBJS)" >> $(PWD)/Kbuild +- @echo -e "EXTRA_CFLAGS := $(CFLAGS) -DHAVE_CONFIG_H $(drv_dsl_cpe_api_CFLAGS) $(DSL_DRIVER_INCL_PATH) $(IFXOS_INCLUDE_PATH) -I@abs_srcdir@/include -I$(PWD)/include" >> $(PWD)/Kbuild ++ @echo "# drv_dsl_cpe_api: Generated to build Linux 2.6.x kernel object" > $(PWD)/Kbuild ++ @echo "obj-m := $(subst .ko,.o,$@)" >> $(PWD)/Kbuild ++ @echo "$(subst .ko,,$@)-y := $(drv_dsl_cpe_api_OBJS)" >> $(PWD)/Kbuild ++ @echo "EXTRA_CFLAGS := $(CFLAGS) -DHAVE_CONFIG_H $(drv_dsl_cpe_api_CFLAGS) $(DSL_DRIVER_INCL_PATH) $(IFXOS_INCLUDE_PATH) -I@abs_srcdir@/include -I$(PWD)/include" >> $(PWD)/Kbuild + $(MAKE) ARCH=@KERNEL_ARCH@ -C @KERNEL_BUILD_PATH@ O=@KERNEL_BUILD_PATH@ M=$(PWD) modules + + clean-generic: +Index: drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_os_linux.h +=================================================================== +--- drv_dsl_cpe_api-3.24.4.4.orig/src/include/drv_dsl_cpe_os_linux.h 2010-10-14 02:14:55.000000000 +0200 ++++ drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_os_linux.h 2010-10-14 02:14:55.000000000 +0200 +@@ -16,8 +16,6 @@ + extern "C" { + #endif + +-#include +-#include + #include + #include + #include +@@ -40,6 +38,7 @@ + #include + #include + #include ++#include + + #ifdef INCLUDE_DSL_CPE_API_IFXOS_SUPPORT + /** IFXOS includes*/ diff --git a/package/ltq-dsl/src/Makefile b/package/ltq-dsl/src/Makefile new file mode 100644 index 0000000000..89c4e712d7 --- /dev/null +++ b/package/ltq-dsl/src/Makefile @@ -0,0 +1,3 @@ +obj-m = lantiq_mei.o lantiq_atm.o + +lantiq_atm-objs := ifxmips_atm_core.o ifxmips_atm_danube.o diff --git a/package/ltq-dsl/src/ifx_atm.h b/package/ltq-dsl/src/ifx_atm.h new file mode 100644 index 0000000000..32deca54e0 --- /dev/null +++ b/package/ltq-dsl/src/ifx_atm.h @@ -0,0 +1,108 @@ +/****************************************************************************** +** +** FILE NAME : ifx_atm.h +** PROJECT : UEIP +** MODULES : ATM +** +** DATE : 17 Jun 2009 +** AUTHOR : Xu Liang +** DESCRIPTION : Global ATM driver header file +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 07 JUL 2009 Xu Liang Init Version +*******************************************************************************/ + +#ifndef IFX_ATM_H +#define IFX_ATM_H + + + +/* + * ATM MIB + */ + +typedef struct { + __u32 ifHCInOctets_h; /*!< byte counter of ingress cells (upper 32 bits, total 64 bits) */ + __u32 ifHCInOctets_l; /*!< byte counter of ingress cells (lower 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_h; /*!< byte counter of egress cells (upper 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_l; /*!< byte counter of egress cells (lower 32 bits, total 64 bits) */ + __u32 ifInErrors; /*!< counter of error ingress cells */ + __u32 ifInUnknownProtos; /*!< counter of unknown ingress cells */ + __u32 ifOutErrors; /*!< counter of error egress cells */ +} atm_cell_ifEntry_t; + +typedef struct { + __u32 ifHCInOctets_h; /*!< byte counter of ingress packets (upper 32 bits, total 64 bits) */ + __u32 ifHCInOctets_l; /*!< byte counter of ingress packets (lower 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_h; /*!< byte counter of egress packets (upper 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_l; /*!< byte counter of egress packets (lower 32 bits, total 64 bits) */ + __u32 ifInUcastPkts; /*!< counter of ingress packets */ + __u32 ifOutUcastPkts; /*!< counter of egress packets */ + __u32 ifInErrors; /*!< counter of error ingress packets */ + __u32 ifInDiscards; /*!< counter of dropped ingress packets */ + __u32 ifOutErros; /*!< counter of error egress packets */ + __u32 ifOutDiscards; /*!< counter of dropped egress packets */ +} atm_aal5_ifEntry_t; + +typedef struct { + __u32 aal5VccCrcErrors; /*!< counter of ingress packets with CRC error */ + __u32 aal5VccSarTimeOuts; /*!< counter of ingress packets with Re-assemble timeout */ //no timer support yet + __u32 aal5VccOverSizedSDUs; /*!< counter of oversized ingress packets */ +} atm_aal5_vcc_t; + +typedef struct { + int vpi; /*!< VPI of the VCC to get MIB counters */ + int vci; /*!< VCI of the VCC to get MIB counters */ + atm_aal5_vcc_t mib_vcc; /*!< structure to get MIB counters */ +} atm_aal5_vcc_x_t; + +/*! + \brief ATM IOCTL Magic Number + */ +#define PPE_ATM_IOC_MAGIC 'o' +/*! + \brief ATM IOCTL Command - Get Cell Level MIB Counters + + This command is obsolete. User can get cell level MIB from DSL API. + This command uses structure "atm_cell_ifEntry_t" as parameter for output of MIB counters. + */ +#define PPE_ATM_MIB_CELL _IOW(PPE_ATM_IOC_MAGIC, 0, atm_cell_ifEntry_t) +/*! + \brief ATM IOCTL Command - Get AAL5 Level MIB Counters + + Get AAL5 packet counters. + This command uses structure "atm_aal5_ifEntry_t" as parameter for output of MIB counters. + */ +#define PPE_ATM_MIB_AAL5 _IOW(PPE_ATM_IOC_MAGIC, 1, atm_aal5_ifEntry_t) +/*! + \brief ATM IOCTL Command - Get Per PVC MIB Counters + + Get AAL5 packet counters for each PVC. + This command uses structure "atm_aal5_vcc_x_t" as parameter for input of VPI/VCI information and output of MIB counters. + */ +#define PPE_ATM_MIB_VCC _IOWR(PPE_ATM_IOC_MAGIC, 2, atm_aal5_vcc_x_t) +/*! + \brief Total Number of ATM IOCTL Commands + */ +#define PPE_ATM_IOC_MAXNR 3 + +/*@}*/ + + + +#ifdef __KERNEL__ +struct port_cell_info { + unsigned int port_num; + unsigned int tx_link_rate[2]; +}; +#endif +#endif diff --git a/package/ltq-dsl/src/ifxmips_atm.h b/package/ltq-dsl/src/ifxmips_atm.h new file mode 100644 index 0000000000..ed90b5d4d7 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm.h @@ -0,0 +1,172 @@ +/****************************************************************************** +** +** FILE NAME : ifx_atm.h +** PROJECT : UEIP +** MODULES : ATM +** +** DATE : 17 Jun 2009 +** AUTHOR : Xu Liang +** DESCRIPTION : Global ATM driver header file +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 07 JUL 2009 Xu Liang Init Version +*******************************************************************************/ + +#ifndef IFX_ATM_H +#define IFX_ATM_H + + + +/*! + \defgroup IFX_ATM UEIP Project - ATM driver module + \brief UEIP Project - ATM driver module, support Danube, Amazon-SE, AR9, VR9. + */ + +/*! + \defgroup IFX_ATM_IOCTL IOCTL Commands + \ingroup IFX_ATM + \brief IOCTL Commands used by user application. + */ + +/*! + \defgroup IFX_ATM_STRUCT Structures + \ingroup IFX_ATM + \brief Structures used by user application. + */ + +/*! + \file ifx_atm.h + \ingroup IFX_ATM + \brief ATM driver header file + */ + + + +/* + * #################################### + * Definition + * #################################### + */ + +/*! + \addtogroup IFX_ATM_STRUCT + */ +/*@{*/ + +/* + * ATM MIB + */ + +typedef struct { + __u32 ifHCInOctets_h; /*!< byte counter of ingress cells (upper 32 bits, total 64 bits) */ + __u32 ifHCInOctets_l; /*!< byte counter of ingress cells (lower 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_h; /*!< byte counter of egress cells (upper 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_l; /*!< byte counter of egress cells (lower 32 bits, total 64 bits) */ + __u32 ifInErrors; /*!< counter of error ingress cells */ + __u32 ifInUnknownProtos; /*!< counter of unknown ingress cells */ + __u32 ifOutErrors; /*!< counter of error egress cells */ +} atm_cell_ifEntry_t; + +typedef struct { + __u32 ifHCInOctets_h; /*!< byte counter of ingress packets (upper 32 bits, total 64 bits) */ + __u32 ifHCInOctets_l; /*!< byte counter of ingress packets (lower 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_h; /*!< byte counter of egress packets (upper 32 bits, total 64 bits) */ + __u32 ifHCOutOctets_l; /*!< byte counter of egress packets (lower 32 bits, total 64 bits) */ + __u32 ifInUcastPkts; /*!< counter of ingress packets */ + __u32 ifOutUcastPkts; /*!< counter of egress packets */ + __u32 ifInErrors; /*!< counter of error ingress packets */ + __u32 ifInDiscards; /*!< counter of dropped ingress packets */ + __u32 ifOutErros; /*!< counter of error egress packets */ + __u32 ifOutDiscards; /*!< counter of dropped egress packets */ +} atm_aal5_ifEntry_t; + +typedef struct { + __u32 aal5VccCrcErrors; /*!< counter of ingress packets with CRC error */ + __u32 aal5VccSarTimeOuts; /*!< counter of ingress packets with Re-assemble timeout */ //no timer support yet + __u32 aal5VccOverSizedSDUs; /*!< counter of oversized ingress packets */ +} atm_aal5_vcc_t; + +typedef struct { + int vpi; /*!< VPI of the VCC to get MIB counters */ + int vci; /*!< VCI of the VCC to get MIB counters */ + atm_aal5_vcc_t mib_vcc; /*!< structure to get MIB counters */ +} atm_aal5_vcc_x_t; + +/*@}*/ + + + +/* + * #################################### + * IOCTL + * #################################### + */ + +/*! + \addtogroup IFX_ATM_IOCTL + */ +/*@{*/ + +/* + * ioctl Command + */ +/*! + \brief ATM IOCTL Magic Number + */ +#define PPE_ATM_IOC_MAGIC 'o' +/*! + \brief ATM IOCTL Command - Get Cell Level MIB Counters + + This command is obsolete. User can get cell level MIB from DSL API. + This command uses structure "atm_cell_ifEntry_t" as parameter for output of MIB counters. + */ +#define PPE_ATM_MIB_CELL _IOW(PPE_ATM_IOC_MAGIC, 0, atm_cell_ifEntry_t) +/*! + \brief ATM IOCTL Command - Get AAL5 Level MIB Counters + + Get AAL5 packet counters. + This command uses structure "atm_aal5_ifEntry_t" as parameter for output of MIB counters. + */ +#define PPE_ATM_MIB_AAL5 _IOW(PPE_ATM_IOC_MAGIC, 1, atm_aal5_ifEntry_t) +/*! + \brief ATM IOCTL Command - Get Per PVC MIB Counters + + Get AAL5 packet counters for each PVC. + This command uses structure "atm_aal5_vcc_x_t" as parameter for input of VPI/VCI information and output of MIB counters. + */ +#define PPE_ATM_MIB_VCC _IOWR(PPE_ATM_IOC_MAGIC, 2, atm_aal5_vcc_x_t) +/*! + \brief Total Number of ATM IOCTL Commands + */ +#define PPE_ATM_IOC_MAXNR 3 + +/*@}*/ + + + +/* + * #################################### + * API + * #################################### + */ + +#ifdef __KERNEL__ +struct port_cell_info { + unsigned int port_num; + unsigned int tx_link_rate[2]; +}; +#endif + + + +#endif // IFX_ATM_H + diff --git a/package/ltq-dsl/src/ifxmips_atm_core.c b/package/ltq-dsl/src/ifxmips_atm_core.c new file mode 100644 index 0000000000..ae85d70650 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_core.c @@ -0,0 +1,2510 @@ +/****************************************************************************** +** +** FILE NAME : ifxmips_atm_core.c +** PROJECT : UEIP +** MODULES : ATM +** +** DATE : 7 Jul 2009 +** AUTHOR : Xu Liang +** DESCRIPTION : ATM driver common source file (core functions) +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 07 JUL 2009 Xu Liang Init Version +*******************************************************************************/ + + + +/* + * #################################### + * Version No. + * #################################### + */ + +#define IFX_ATM_VER_MAJOR 1 +#define IFX_ATM_VER_MID 0 +#define IFX_ATM_VER_MINOR 8 + + + +/* + * #################################### + * Head File + * #################################### + */ + +/* + * Common Head File + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* + * Chip Specific Head File + */ +#include +#include +#include "ifxmips_atm_core.h" + + + +/* + * #################################### + * Kernel Version Adaption + * #################################### + */ +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11) + #define MODULE_PARM_ARRAY(a, b) module_param_array(a, int, NULL, 0) + #define MODULE_PARM(a, b) module_param(a, int, 0) +#else + #define MODULE_PARM_ARRAY(a, b) MODULE_PARM(a, b) +#endif + + + +/*! + \addtogroup IFXMIPS_ATM_MODULE_PARAMS + */ +/*@{*/ +/* + * #################################### + * Parameters to Configure PPE + * #################################### + */ +/*! + \brief QSB cell delay variation due to concurrency + */ +static int qsb_tau = 1; /* QSB cell delay variation due to concurrency */ +/*! + \brief QSB scheduler burst length + */ +static int qsb_srvm = 0x0F; /* QSB scheduler burst length */ +/*! + \brief QSB time step, all legal values are 1, 2, 4 + */ +static int qsb_tstep = 4 ; /* QSB time step, all legal values are 1, 2, 4 */ + +/*! + \brief Write descriptor delay + */ +static int write_descriptor_delay = 0x20; /* Write descriptor delay */ + +/*! + \brief AAL5 padding byte ('~') + */ +static int aal5_fill_pattern = 0x007E; /* AAL5 padding byte ('~') */ +/*! + \brief Max frame size for RX + */ +static int aal5r_max_packet_size = 0x0700; /* Max frame size for RX */ +/*! + \brief Min frame size for RX + */ +static int aal5r_min_packet_size = 0x0000; /* Min frame size for RX */ +/*! + \brief Max frame size for TX + */ +static int aal5s_max_packet_size = 0x0700; /* Max frame size for TX */ +/*! + \brief Min frame size for TX + */ +static int aal5s_min_packet_size = 0x0000; /* Min frame size for TX */ +/*! + \brief Drop error packet in RX path + */ +static int aal5r_drop_error_packet = 1; /* Drop error packet in RX path */ + +/*! + \brief Number of descriptors per DMA RX channel + */ +static int dma_rx_descriptor_length = 128; /* Number of descriptors per DMA RX channel */ +/*! + \brief Number of descriptors per DMA TX channel + */ +static int dma_tx_descriptor_length = 64; /* Number of descriptors per DMA TX channel */ +/*! + \brief PPE core clock cycles between descriptor write and effectiveness in external RAM + */ +static int dma_rx_clp1_descriptor_threshold = 38; +/*@}*/ + +MODULE_PARM(qsb_tau, "i"); +MODULE_PARM_DESC(qsb_tau, "Cell delay variation. Value must be > 0"); +MODULE_PARM(qsb_srvm, "i"); +MODULE_PARM_DESC(qsb_srvm, "Maximum burst size"); +MODULE_PARM(qsb_tstep, "i"); +MODULE_PARM_DESC(qsb_tstep, "n*32 cycles per sbs cycles n=1,2,4"); + +MODULE_PARM(write_descriptor_delay, "i"); +MODULE_PARM_DESC(write_descriptor_delay, "PPE core clock cycles between descriptor write and effectiveness in external RAM"); + +MODULE_PARM(aal5_fill_pattern, "i"); +MODULE_PARM_DESC(aal5_fill_pattern, "Filling pattern (PAD) for AAL5 frames"); +MODULE_PARM(aal5r_max_packet_size, "i"); +MODULE_PARM_DESC(aal5r_max_packet_size, "Max packet size in byte for downstream AAL5 frames"); +MODULE_PARM(aal5r_min_packet_size, "i"); +MODULE_PARM_DESC(aal5r_min_packet_size, "Min packet size in byte for downstream AAL5 frames"); +MODULE_PARM(aal5s_max_packet_size, "i"); +MODULE_PARM_DESC(aal5s_max_packet_size, "Max packet size in byte for upstream AAL5 frames"); +MODULE_PARM(aal5s_min_packet_size, "i"); +MODULE_PARM_DESC(aal5s_min_packet_size, "Min packet size in byte for upstream AAL5 frames"); +MODULE_PARM(aal5r_drop_error_packet, "i"); +MODULE_PARM_DESC(aal5r_drop_error_packet, "Non-zero value to drop error packet for downstream"); + +MODULE_PARM(dma_rx_descriptor_length, "i"); +MODULE_PARM_DESC(dma_rx_descriptor_length, "Number of descriptor assigned to DMA RX channel (>16)"); +MODULE_PARM(dma_tx_descriptor_length, "i"); +MODULE_PARM_DESC(dma_tx_descriptor_length, "Number of descriptor assigned to DMA TX channel (>16)"); +MODULE_PARM(dma_rx_clp1_descriptor_threshold, "i"); +MODULE_PARM_DESC(dma_rx_clp1_descriptor_threshold, "Descriptor threshold for cells with cell loss priority 1"); + + + +/* + * #################################### + * Definition + * #################################### + */ + +#define DUMP_SKB_LEN ~0 + + + +/* + * #################################### + * Declaration + * #################################### + */ + +/* + * Network Operations + */ +static int ppe_ioctl(struct atm_dev *, unsigned int, void *); +static int ppe_open(struct atm_vcc *); +static void ppe_close(struct atm_vcc *); +static int ppe_send(struct atm_vcc *, struct sk_buff *); +static int ppe_send_oam(struct atm_vcc *, void *, int); +static int ppe_change_qos(struct atm_vcc *, struct atm_qos *, int); + +/* + * ADSL LED + */ +static INLINE int adsl_led_flash(void); + +/* + * 64-bit operation used by MIB calculation + */ +static INLINE void u64_add_u32(ppe_u64_t, unsigned int, ppe_u64_t *); + +/* + * buffer manage functions + */ +static INLINE struct sk_buff* alloc_skb_rx(void); +static INLINE struct sk_buff* alloc_skb_tx(unsigned int); +struct sk_buff* atm_alloc_tx(struct atm_vcc *, unsigned int); +static INLINE void atm_free_tx_skb_vcc(struct sk_buff *, struct atm_vcc *); +static INLINE struct sk_buff *get_skb_rx_pointer(unsigned int); +static INLINE int get_tx_desc(unsigned int); + +/* + * mailbox handler and signal function + */ +static INLINE void mailbox_oam_rx_handler(void); +static INLINE void mailbox_aal_rx_handler(void); +#if defined(ENABLE_TASKLET) && ENABLE_TASKLET + static void do_ppe_tasklet(unsigned long); +#endif +static irqreturn_t mailbox_irq_handler(int, void *); +static INLINE void mailbox_signal(unsigned int, int); + +/* + * QSB & HTU setting functions + */ +static void set_qsb(struct atm_vcc *, struct atm_qos *, unsigned int); +static void qsb_global_set(void); +static INLINE void set_htu_entry(unsigned int, unsigned int, unsigned int, int, int); +static INLINE void clear_htu_entry(unsigned int); +static void validate_oam_htu_entry(void); +static void invalidate_oam_htu_entry(void); + +/* + * look up for connection ID + */ +static INLINE int find_vpi(unsigned int); +static INLINE int find_vpivci(unsigned int, unsigned int); +static INLINE int find_vcc(struct atm_vcc *); + +/* + * Debug Functions + */ +#if defined(DEBUG_DUMP_SKB) && DEBUG_DUMP_SKB + static void dump_skb(struct sk_buff *, u32, char *, int, int, int); +#else + #define dump_skb(skb, len, title, port, ch, is_tx) do {} while (0) +#endif + +/* + * Proc File Functions + */ +static INLINE void proc_file_create(void); +static INLINE void proc_file_delete(void); +static int proc_read_version(char *, char **, off_t, int, int *, void *); +static int proc_read_mib(char *, char **, off_t, int, int *, void *); +static int proc_write_mib(struct file *, const char *, unsigned long, void *); +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + static int proc_read_dbg(char *, char **, off_t, int, int *, void *); + static int proc_write_dbg(struct file *, const char *, unsigned long, void *); +#endif +#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC + static int proc_read_htu(char *, char **, off_t, int, int *, void *); + static int proc_read_txq(char *, char **, off_t, int, int *, void *); +#endif + +/* + * Proc Help Functions + */ +static int stricmp(const char *, const char *); +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + static int strincmp(const char *, const char *, int); +#endif +static INLINE int ifx_atm_version(char *); +//static INLINE int print_reset_domain(char *, int); +//static INLINE int print_reset_handler(char *, int, ifx_rcu_handler_t *); + +/* + * Init & clean-up functions + */ +#ifdef MODULE + static INLINE void reset_ppe(void); +#endif +static INLINE void check_parameters(void); +static INLINE int init_priv_data(void); +static INLINE void clear_priv_data(void); +static INLINE void init_rx_tables(void); +static INLINE void init_tx_tables(void); + +/* + * Exteranl Function + */ +#if defined(CONFIG_IFX_OAM) || defined(CONFIG_IFX_OAM_MODULE) + extern void ifx_push_oam(unsigned char *); +#else + static inline void ifx_push_oam(unsigned char *dummy) {} +#endif +#if defined(CONFIG_IFXMIPS_DSL_CPE_MEI) || defined(CONFIG_IFXMIPS_DSL_CPE_MEI_MODULE) + extern int ifx_mei_atm_led_blink(void); + extern int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr); +#else + static inline int ifx_mei_atm_led_blink(void) { return IFX_SUCCESS; } + static inline int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr) + { + if ( is_showtime != NULL ) + *is_showtime = 0; + return IFX_SUCCESS; + } +#endif + +/* + * External variable + */ +extern struct sk_buff* (*ifx_atm_alloc_tx)(struct atm_vcc *, unsigned int); +#if defined(CONFIG_IFXMIPS_DSL_CPE_MEI) || defined(CONFIG_IFXMIPS_DSL_CPE_MEI_MODULE) + extern int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *); + extern int (*ifx_mei_atm_showtime_exit)(void); +#else + int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *) = NULL; + EXPORT_SYMBOL(ifx_mei_atm_showtime_enter); + int (*ifx_mei_atm_showtime_exit)(void) = NULL; + EXPORT_SYMBOL(ifx_mei_atm_showtime_exit); +#endif + + + +/* + * #################################### + * Local Variable + * #################################### + */ + +static struct atm_priv_data g_atm_priv_data; + +static struct atmdev_ops g_ifx_atm_ops = { + .open = ppe_open, + .close = ppe_close, + .ioctl = ppe_ioctl, + .send = ppe_send, + .send_oam = ppe_send_oam, + .change_qos = ppe_change_qos, + .owner = THIS_MODULE, +}; + +#if defined(ENABLE_TASKLET) && ENABLE_TASKLET + DECLARE_TASKLET(g_dma_tasklet, do_ppe_tasklet, 0); +#endif + +static int g_showtime = 0; +static void *g_xdata_addr = NULL; + +unsigned int ifx_atm_dbg_enable = 0; + +static struct proc_dir_entry* g_atm_dir = NULL; + + + +/* + * #################################### + * Local Function + * #################################### + */ + +static int ppe_ioctl(struct atm_dev *dev, unsigned int cmd, void *arg) +{ + int ret = 0; + atm_cell_ifEntry_t mib_cell; + atm_aal5_ifEntry_t mib_aal5; + atm_aal5_vcc_x_t mib_vcc; + unsigned int value; + int conn; + + if ( _IOC_TYPE(cmd) != PPE_ATM_IOC_MAGIC + || _IOC_NR(cmd) >= PPE_ATM_IOC_MAXNR ) + return -ENOTTY; + + if ( _IOC_DIR(cmd) & _IOC_READ ) + ret = !access_ok(VERIFY_WRITE, arg, _IOC_SIZE(cmd)); + else if ( _IOC_DIR(cmd) & _IOC_WRITE ) + ret = !access_ok(VERIFY_READ, arg, _IOC_SIZE(cmd)); + if ( ret ) + return -EFAULT; + + switch ( cmd ) + { + case PPE_ATM_MIB_CELL: /* cell level MIB */ + /* These MIB should be read at ARC side, now put zero only. */ + mib_cell.ifHCInOctets_h = 0; + mib_cell.ifHCInOctets_l = 0; + mib_cell.ifHCOutOctets_h = 0; + mib_cell.ifHCOutOctets_l = 0; + mib_cell.ifInErrors = 0; + mib_cell.ifInUnknownProtos = WAN_MIB_TABLE->wrx_drophtu_cell; + mib_cell.ifOutErrors = 0; + + ret = sizeof(mib_cell) - copy_to_user(arg, &mib_cell, sizeof(mib_cell)); + break; + + case PPE_ATM_MIB_AAL5: /* AAL5 MIB */ + value = WAN_MIB_TABLE->wrx_total_byte; + u64_add_u32(g_atm_priv_data.wrx_total_byte, value - g_atm_priv_data.prev_wrx_total_byte, &g_atm_priv_data.wrx_total_byte); + g_atm_priv_data.prev_wrx_total_byte = value; + mib_aal5.ifHCInOctets_h = g_atm_priv_data.wrx_total_byte.h; + mib_aal5.ifHCInOctets_l = g_atm_priv_data.wrx_total_byte.l; + + value = WAN_MIB_TABLE->wtx_total_byte; + u64_add_u32(g_atm_priv_data.wtx_total_byte, value - g_atm_priv_data.prev_wtx_total_byte, &g_atm_priv_data.wtx_total_byte); + g_atm_priv_data.prev_wtx_total_byte = value; + mib_aal5.ifHCOutOctets_h = g_atm_priv_data.wtx_total_byte.h; + mib_aal5.ifHCOutOctets_l = g_atm_priv_data.wtx_total_byte.l; + + mib_aal5.ifInUcastPkts = g_atm_priv_data.wrx_pdu; + mib_aal5.ifOutUcastPkts = WAN_MIB_TABLE->wtx_total_pdu; + mib_aal5.ifInErrors = WAN_MIB_TABLE->wrx_err_pdu; + mib_aal5.ifInDiscards = WAN_MIB_TABLE->wrx_dropdes_pdu + g_atm_priv_data.wrx_drop_pdu; + mib_aal5.ifOutErros = g_atm_priv_data.wtx_err_pdu; + mib_aal5.ifOutDiscards = g_atm_priv_data.wtx_drop_pdu; + + ret = sizeof(mib_aal5) - copy_to_user(arg, &mib_aal5, sizeof(mib_aal5)); + break; + + case PPE_ATM_MIB_VCC: /* VCC related MIB */ + copy_from_user(&mib_vcc, arg, sizeof(mib_vcc)); + conn = find_vpivci(mib_vcc.vpi, mib_vcc.vci); + if ( conn >= 0 ) + { + mib_vcc.mib_vcc.aal5VccCrcErrors = g_atm_priv_data.conn[conn].aal5_vcc_crc_err; + mib_vcc.mib_vcc.aal5VccOverSizedSDUs = g_atm_priv_data.conn[conn].aal5_vcc_oversize_sdu; + mib_vcc.mib_vcc.aal5VccSarTimeOuts = 0; /* no timer support */ + ret = sizeof(mib_vcc) - copy_to_user(arg, &mib_vcc, sizeof(mib_vcc)); + } + else + ret = -EINVAL; + break; + + default: + ret = -ENOIOCTLCMD; + } + + return ret; +} + +static int ppe_open(struct atm_vcc *vcc) +{ + int ret; + short vpi = vcc->vpi; + int vci = vcc->vci; + struct port *port = &g_atm_priv_data.port[(int)vcc->dev->dev_data]; + int conn; + int f_enable_irq = 0; +#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX + int sys_flag; +#endif + + if ( vcc->qos.aal != ATM_AAL5 && vcc->qos.aal != ATM_AAL0 ) + return -EPROTONOSUPPORT; + + /* check bandwidth */ + if ( (vcc->qos.txtp.traffic_class == ATM_CBR && vcc->qos.txtp.max_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) + || (vcc->qos.txtp.traffic_class == ATM_VBR_RT && vcc->qos.txtp.max_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) + || (vcc->qos.txtp.traffic_class == ATM_VBR_NRT && vcc->qos.txtp.scr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) + || (vcc->qos.txtp.traffic_class == ATM_UBR_PLUS && vcc->qos.txtp.min_pcr > (port->tx_max_cell_rate - port->tx_current_cell_rate)) ) + { + ret = -EINVAL; + goto PPE_OPEN_EXIT; + } + + /* check existing vpi,vci */ + conn = find_vpivci(vpi, vci); + if ( conn >= 0 ) { + ret = -EADDRINUSE; + goto PPE_OPEN_EXIT; + } + + /* check whether it need to enable irq */ + if ( g_atm_priv_data.conn_table == 0 ) + f_enable_irq = 1; + + /* allocate connection */ + for ( conn = 0; conn < MAX_PVC_NUMBER; conn++ ) { + if ( test_and_set_bit(conn, &g_atm_priv_data.conn_table) == 0 ) { + g_atm_priv_data.conn[conn].vcc = vcc; + break; + } + } + if ( conn == MAX_PVC_NUMBER ) + { + ret = -EINVAL; + goto PPE_OPEN_EXIT; + } + + /* reserve bandwidth */ + switch ( vcc->qos.txtp.traffic_class ) { + case ATM_CBR: + case ATM_VBR_RT: + port->tx_current_cell_rate += vcc->qos.txtp.max_pcr; + break; + case ATM_VBR_NRT: + port->tx_current_cell_rate += vcc->qos.txtp.scr; + break; + case ATM_UBR_PLUS: + port->tx_current_cell_rate += vcc->qos.txtp.min_pcr; + break; + } + + /* set qsb */ + set_qsb(vcc, &vcc->qos, conn); + + /* update atm_vcc structure */ + vcc->itf = (int)vcc->dev->dev_data; + vcc->vpi = vpi; + vcc->vci = vci; + set_bit(ATM_VF_READY, &vcc->flags); + + /* enable irq */ + if (f_enable_irq ) { + ifx_atm_alloc_tx = atm_alloc_tx; + + *MBOX_IGU1_ISRC = (1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM); + *MBOX_IGU1_IER = (1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM); + + enable_irq(PPE_MAILBOX_IGU1_INT); + } + + /* set port */ + WTX_QUEUE_CONFIG(conn)->sbid = (int)vcc->dev->dev_data; + + /* set htu entry */ + set_htu_entry(vpi, vci, conn, vcc->qos.aal == ATM_AAL5 ? 1 : 0, 0); + +#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX + // ReTX: occupy second QID + local_irq_save(sys_flag); + if ( g_retx_htu && vcc->qos.aal == ATM_AAL5 ) + { + int retx_conn = (conn + 8) % 16; // ReTX queue + + if ( retx_conn < MAX_PVC_NUMBER && test_and_set_bit(retx_conn, &g_atm_priv_data.conn_table) == 0 ) { + g_atm_priv_data.conn[retx_conn].vcc = vcc; + set_htu_entry(vpi, vci, retx_conn, vcc->qos.aal == ATM_AAL5 ? 1 : 0, 1); + } + } + local_irq_restore(sys_flag); +#endif + + ret = 0; + +PPE_OPEN_EXIT: + return ret; +} + +static void ppe_close(struct atm_vcc *vcc) +{ + int conn; + struct port *port; + struct connection *connection; + + if ( vcc == NULL ) + return; + + /* get connection id */ + conn = find_vcc(vcc); + if ( conn < 0 ) { + err("can't find vcc"); + goto PPE_CLOSE_EXIT; + } + connection = &g_atm_priv_data.conn[conn]; + port = &g_atm_priv_data.port[connection->port]; + + /* clear htu */ + clear_htu_entry(conn); + + /* release connection */ + clear_bit(conn, &g_atm_priv_data.conn_table); + connection->vcc = NULL; + connection->aal5_vcc_crc_err = 0; + connection->aal5_vcc_oversize_sdu = 0; + + /* disable irq */ + if ( g_atm_priv_data.conn_table == 0 ) { + disable_irq(PPE_MAILBOX_IGU1_INT); + ifx_atm_alloc_tx = NULL; + } + + /* release bandwidth */ + switch ( vcc->qos.txtp.traffic_class ) + { + case ATM_CBR: + case ATM_VBR_RT: + port->tx_current_cell_rate -= vcc->qos.txtp.max_pcr; + break; + case ATM_VBR_NRT: + port->tx_current_cell_rate -= vcc->qos.txtp.scr; + break; + case ATM_UBR_PLUS: + port->tx_current_cell_rate -= vcc->qos.txtp.min_pcr; + break; + } + +PPE_CLOSE_EXIT: + return; +} + +static int ppe_send(struct atm_vcc *vcc, struct sk_buff *skb) +{ + int ret; + int conn; + int desc_base; + struct tx_descriptor reg_desc = {0}; + + if ( vcc == NULL || skb == NULL ) + return -EINVAL; + + skb_get(skb); + atm_free_tx_skb_vcc(skb, vcc); + + conn = find_vcc(vcc); + if ( conn < 0 ) { + ret = -EINVAL; + goto FIND_VCC_FAIL; + } + + if ( !g_showtime ) { + err("not in showtime"); + ret = -EIO; + goto PPE_SEND_FAIL; + } + + if ( vcc->qos.aal == ATM_AAL5 ) { + int byteoff; + int datalen; + struct tx_inband_header *header; + + datalen = skb->len; + byteoff = (unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1); + + if ( skb_headroom(skb) < byteoff + TX_INBAND_HEADER_LENGTH ) { + struct sk_buff *new_skb; + + new_skb = alloc_skb_tx(datalen); + if ( new_skb == NULL ) { + err("ALLOC_SKB_TX_FAIL"); + ret = -ENOMEM; + goto PPE_SEND_FAIL; + } + skb_put(new_skb, datalen); + memcpy(new_skb->data, skb->data, datalen); + dev_kfree_skb_any(skb); + skb = new_skb; + byteoff = (unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1); + } + + skb_push(skb, byteoff + TX_INBAND_HEADER_LENGTH); + + header = (struct tx_inband_header *)skb->data; + + /* setup inband trailer */ + header->uu = 0; + header->cpi = 0; + header->pad = aal5_fill_pattern; + header->res1 = 0; + + /* setup cell header */ + header->clp = (vcc->atm_options & ATM_ATMOPT_CLP) ? 1 : 0; + header->pti = ATM_PTI_US0; + header->vci = vcc->vci; + header->vpi = vcc->vpi; + header->gfc = 0; + + /* setup descriptor */ + reg_desc.dataptr = (unsigned int)skb->data >> 2; + reg_desc.datalen = datalen; + reg_desc.byteoff = byteoff; + reg_desc.iscell = 0; + } + else { + /* if data pointer is not aligned, allocate new sk_buff */ + if ( ((unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1)) != 0 ) { + struct sk_buff *new_skb; + + err("skb->data not aligned"); + + new_skb = alloc_skb_tx(skb->len); + if ( new_skb == NULL ) { + err("ALLOC_SKB_TX_FAIL"); + ret = -ENOMEM; + goto PPE_SEND_FAIL; + } + skb_put(new_skb, skb->len); + memcpy(new_skb->data, skb->data, skb->len); + dev_kfree_skb_any(skb); + skb = new_skb; + } + + reg_desc.dataptr = (unsigned int)skb->data >> 2; + reg_desc.datalen = skb->len; + reg_desc.byteoff = 0; + reg_desc.iscell = 1; + } + + reg_desc.own = 1; + reg_desc.c = 1; + reg_desc.sop = reg_desc.eop = 1; + + desc_base = get_tx_desc(conn); + if ( desc_base < 0 ) { + err("ALLOC_TX_CONNECTION_FAIL"); + ret = -EIO; + goto PPE_SEND_FAIL; + } + + if ( vcc->stats ) + atomic_inc(&vcc->stats->tx); + if ( vcc->qos.aal == ATM_AAL5 ) + g_atm_priv_data.wtx_pdu++; + + /* update descriptor send pointer */ + if ( g_atm_priv_data.conn[conn].tx_skb[desc_base] != NULL ) + dev_kfree_skb_any(g_atm_priv_data.conn[conn].tx_skb[desc_base]); + g_atm_priv_data.conn[conn].tx_skb[desc_base] = skb; + + /* write discriptor to memory and write back cache */ + g_atm_priv_data.conn[conn].tx_desc[desc_base] = reg_desc; + dma_cache_wback((unsigned long)skb->data, skb->len); + + dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 1); + + mailbox_signal(conn, 1); + + adsl_led_flash(); + + return 0; + +FIND_VCC_FAIL: + err("FIND_VCC_FAIL"); + g_atm_priv_data.wtx_err_pdu++; + dev_kfree_skb_any(skb); + return ret; + +PPE_SEND_FAIL: + if ( vcc->qos.aal == ATM_AAL5 ) + g_atm_priv_data.wtx_drop_pdu++; + if ( vcc->stats ) + atomic_inc(&vcc->stats->tx_err); + dev_kfree_skb_any(skb); + return ret; +} + +static int ppe_send_oam(struct atm_vcc *vcc, void *cell, int flags) +{ + int conn; + struct uni_cell_header *uni_cell_header = (struct uni_cell_header *)cell; + int desc_base; + struct sk_buff *skb; + struct tx_descriptor reg_desc = {0}; + + if ( ((uni_cell_header->pti == ATM_PTI_SEGF5 || uni_cell_header->pti == ATM_PTI_E2EF5) + && find_vpivci(uni_cell_header->vpi, uni_cell_header->vci) < 0) + || ((uni_cell_header->vci == 0x03 || uni_cell_header->vci == 0x04) + && find_vpi(uni_cell_header->vpi) < 0) ) + return -EINVAL; + + if ( !g_showtime ) { + err("not in showtime"); + return -EIO; + } + + conn = find_vcc(vcc); + if ( conn < 0 ) { + err("FIND_VCC_FAIL"); + return -EINVAL; + } + + skb = alloc_skb_tx(CELL_SIZE); + if ( skb == NULL ) { + err("ALLOC_SKB_TX_FAIL"); + return -ENOMEM; + } + memcpy(skb->data, cell, CELL_SIZE); + + reg_desc.dataptr = (unsigned int)skb->data >> 2; + reg_desc.datalen = CELL_SIZE; + reg_desc.byteoff = 0; + reg_desc.iscell = 1; + + reg_desc.own = 1; + reg_desc.c = 1; + reg_desc.sop = reg_desc.eop = 1; + + desc_base = get_tx_desc(conn); + if ( desc_base < 0 ) { + dev_kfree_skb_any(skb); + err("ALLOC_TX_CONNECTION_FAIL"); + return -EIO; + } + + if ( vcc->stats ) + atomic_inc(&vcc->stats->tx); + + /* update descriptor send pointer */ + if ( g_atm_priv_data.conn[conn].tx_skb[desc_base] != NULL ) + dev_kfree_skb_any(g_atm_priv_data.conn[conn].tx_skb[desc_base]); + g_atm_priv_data.conn[conn].tx_skb[desc_base] = skb; + + /* write discriptor to memory and write back cache */ + g_atm_priv_data.conn[conn].tx_desc[desc_base] = reg_desc; + dma_cache_wback((unsigned long)skb->data, CELL_SIZE); + + dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 1); + + mailbox_signal(conn, 1); + + adsl_led_flash(); + + return 0; +} + +static int ppe_change_qos(struct atm_vcc *vcc, struct atm_qos *qos, int flags) +{ + int conn; + + if ( vcc == NULL || qos == NULL ) + return -EINVAL; + + conn = find_vcc(vcc); + if ( conn < 0 ) + return -EINVAL; + + set_qsb(vcc, qos, conn); + + return 0; +} + +static INLINE int adsl_led_flash(void) +{ + return ifx_mei_atm_led_blink(); +} + +/* + * Description: + * Add a 32-bit value to 64-bit value, and put result in a 64-bit variable. + * Input: + * opt1 --- ppe_u64_t, first operand, a 64-bit unsigned integer value + * opt2 --- unsigned int, second operand, a 32-bit unsigned integer value + * ret --- ppe_u64_t, pointer to a variable to hold result + * Output: + * none + */ +static INLINE void u64_add_u32(ppe_u64_t opt1, unsigned int opt2, ppe_u64_t *ret) +{ + ret->l = opt1.l + opt2; + if ( ret->l < opt1.l || ret->l < opt2 ) + ret->h++; +} + +static INLINE struct sk_buff* alloc_skb_rx(void) +{ + struct sk_buff *skb; + + skb = dev_alloc_skb(RX_DMA_CH_AAL_BUF_SIZE + DATA_BUFFER_ALIGNMENT); + if ( skb != NULL ) { + /* must be burst length alignment */ + if ( ((unsigned int)skb->data & (DATA_BUFFER_ALIGNMENT - 1)) != 0 ) + skb_reserve(skb, ~((unsigned int)skb->data + (DATA_BUFFER_ALIGNMENT - 1)) & (DATA_BUFFER_ALIGNMENT - 1)); + /* pub skb in reserved area "skb->data - 4" */ + *((struct sk_buff **)skb->data - 1) = skb; + /* write back and invalidate cache */ + dma_cache_wback_inv((unsigned long)skb->data - sizeof(skb), sizeof(skb)); + /* invalidate cache */ + dma_cache_inv((unsigned long)skb->data, (unsigned int)skb->end - (unsigned int)skb->data); + } + + return skb; +} + +static INLINE struct sk_buff* alloc_skb_tx(unsigned int size) +{ + struct sk_buff *skb; + + /* allocate memory including header and padding */ + size += TX_INBAND_HEADER_LENGTH + MAX_TX_PACKET_ALIGN_BYTES + MAX_TX_PACKET_PADDING_BYTES; + size &= ~(DATA_BUFFER_ALIGNMENT - 1); + skb = dev_alloc_skb(size + DATA_BUFFER_ALIGNMENT); + /* must be burst length alignment */ + if ( skb != NULL ) + skb_reserve(skb, (~((unsigned int)skb->data + (DATA_BUFFER_ALIGNMENT - 1)) & (DATA_BUFFER_ALIGNMENT - 1)) + TX_INBAND_HEADER_LENGTH); + return skb; +} + +struct sk_buff* atm_alloc_tx(struct atm_vcc *vcc, unsigned int size) +{ + int conn; + struct sk_buff *skb; + + /* oversize packet */ + if ( size > aal5s_max_packet_size ) { + err("atm_alloc_tx: oversize packet"); + return NULL; + } + /* send buffer overflow */ + if ( atomic_read(&sk_atm(vcc)->sk_wmem_alloc) && !atm_may_send(vcc, size) ) { + err("atm_alloc_tx: send buffer overflow"); + return NULL; + } + conn = find_vcc(vcc); + if ( conn < 0 ) { + err("atm_alloc_tx: unknown VCC"); + return NULL; + } + + skb = dev_alloc_skb(size); + if ( skb == NULL ) { + err("atm_alloc_tx: sk buffer is used up"); + return NULL; + } + + atomic_add(skb->truesize, &sk_atm(vcc)->sk_wmem_alloc); + + return skb; +} + +static INLINE void atm_free_tx_skb_vcc(struct sk_buff *skb, struct atm_vcc *vcc) +{ + if ( vcc->pop != NULL ) + vcc->pop(vcc, skb); + else + dev_kfree_skb_any(skb); +} + +static INLINE struct sk_buff *get_skb_rx_pointer(unsigned int dataptr) +{ + unsigned int skb_dataptr; + struct sk_buff *skb; + + skb_dataptr = ((dataptr - 1) << 2) | KSEG1; + skb = *(struct sk_buff **)skb_dataptr; + + ASSERT((unsigned int)skb >= KSEG0, "invalid skb - skb = %#08x, dataptr = %#08x", (unsigned int)skb, dataptr); + ASSERT(((unsigned int)skb->data | KSEG1) == ((dataptr << 2) | KSEG1), "invalid skb - skb = %#08x, skb->data = %#08x, dataptr = %#08x", (unsigned int)skb, (unsigned int)skb->data, dataptr); + + return skb; +} + +static INLINE int get_tx_desc(unsigned int conn) +{ + int desc_base = -1; + struct connection *p_conn = &g_atm_priv_data.conn[conn]; + + if ( p_conn->tx_desc[p_conn->tx_desc_pos].own == 0 ) { + desc_base = p_conn->tx_desc_pos; + if ( ++(p_conn->tx_desc_pos) == dma_tx_descriptor_length ) + p_conn->tx_desc_pos = 0; + } + + return desc_base; +} + +static INLINE void mailbox_oam_rx_handler(void) +{ + unsigned int vlddes = WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_OAM)->vlddes; + struct rx_descriptor reg_desc; + struct uni_cell_header *header; + int conn; + struct atm_vcc *vcc; + unsigned int i; + + for ( i = 0; i < vlddes; i++ ) { + do { + reg_desc = g_atm_priv_data.oam_desc[g_atm_priv_data.oam_desc_pos]; + } while ( reg_desc.own || !reg_desc.c ); // keep test OWN and C bit until data is ready + + header = (struct uni_cell_header *)&g_atm_priv_data.oam_buf[g_atm_priv_data.oam_desc_pos * RX_DMA_CH_OAM_BUF_SIZE]; + + if ( header->pti == ATM_PTI_SEGF5 || header->pti == ATM_PTI_E2EF5 ) + conn = find_vpivci(header->vpi, header->vci); + else if ( header->vci == 0x03 || header->vci == 0x04 ) + conn = find_vpi(header->vpi); + else + conn = -1; + + if ( conn >= 0 && g_atm_priv_data.conn[conn].vcc != NULL ) { + vcc = g_atm_priv_data.conn[conn].vcc; + + if ( vcc->push_oam != NULL ) + vcc->push_oam(vcc, header); + else + ifx_push_oam((unsigned char *)header); + + adsl_led_flash(); + } + + reg_desc.byteoff = 0; + reg_desc.datalen = RX_DMA_CH_OAM_BUF_SIZE; + reg_desc.own = 1; + reg_desc.c = 0; + + g_atm_priv_data.oam_desc[g_atm_priv_data.oam_desc_pos] = reg_desc; + if ( ++g_atm_priv_data.oam_desc_pos == RX_DMA_CH_OAM_DESC_LEN ) + g_atm_priv_data.oam_desc_pos = 0; + + mailbox_signal(RX_DMA_CH_OAM, 0); + } +} + +static INLINE void mailbox_aal_rx_handler(void) +{ + unsigned int vlddes = WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_AAL)->vlddes; + struct rx_descriptor reg_desc; + int conn; + struct atm_vcc *vcc; + struct sk_buff *skb, *new_skb; + struct rx_inband_trailer *trailer; + unsigned int i; + + for ( i = 0; i < vlddes; i++ ) { + do { + reg_desc = g_atm_priv_data.aal_desc[g_atm_priv_data.aal_desc_pos]; + } while ( reg_desc.own || !reg_desc.c ); // keep test OWN and C bit until data is ready + + conn = reg_desc.id; + + if ( g_atm_priv_data.conn[conn].vcc != NULL ) { + vcc = g_atm_priv_data.conn[conn].vcc; + + skb = get_skb_rx_pointer(reg_desc.dataptr); + + if ( reg_desc.err ) { + if ( vcc->qos.aal == ATM_AAL5 ) { + trailer = (struct rx_inband_trailer *)((unsigned int)skb->data + ((reg_desc.byteoff + reg_desc.datalen + MAX_RX_PACKET_PADDING_BYTES) & ~MAX_RX_PACKET_PADDING_BYTES)); + if ( trailer->stw_crc ) + g_atm_priv_data.conn[conn].aal5_vcc_crc_err++; + if ( trailer->stw_ovz ) + g_atm_priv_data.conn[conn].aal5_vcc_oversize_sdu++; + g_atm_priv_data.wrx_drop_pdu++; + } + if ( vcc->stats ) { + atomic_inc(&vcc->stats->rx_drop); + atomic_inc(&vcc->stats->rx_err); + } + } + else if ( atm_charge(vcc, skb->truesize) ) { + new_skb = alloc_skb_rx(); + if ( new_skb != NULL ) { + skb_reserve(skb, reg_desc.byteoff); + skb_put(skb, reg_desc.datalen); + ATM_SKB(skb)->vcc = vcc; + + dump_skb(skb, DUMP_SKB_LEN, (char *)__func__, 0, conn, 0); + + vcc->push(vcc, skb); + + if ( vcc->qos.aal == ATM_AAL5 ) + g_atm_priv_data.wrx_pdu++; + if ( vcc->stats ) + atomic_inc(&vcc->stats->rx); + adsl_led_flash(); + + reg_desc.dataptr = (unsigned int)new_skb->data >> 2; + } + else { + atm_return(vcc, skb->truesize); + if ( vcc->qos.aal == ATM_AAL5 ) + g_atm_priv_data.wrx_drop_pdu++; + if ( vcc->stats ) + atomic_inc(&vcc->stats->rx_drop); + } + } + else { + if ( vcc->qos.aal == ATM_AAL5 ) + g_atm_priv_data.wrx_drop_pdu++; + if ( vcc->stats ) + atomic_inc(&vcc->stats->rx_drop); + } + } + else { + g_atm_priv_data.wrx_drop_pdu++; + } + + reg_desc.byteoff = 0; + reg_desc.datalen = RX_DMA_CH_AAL_BUF_SIZE; + reg_desc.own = 1; + reg_desc.c = 0; + + g_atm_priv_data.aal_desc[g_atm_priv_data.aal_desc_pos] = reg_desc; + if ( ++g_atm_priv_data.aal_desc_pos == dma_rx_descriptor_length ) + g_atm_priv_data.aal_desc_pos = 0; + + mailbox_signal(RX_DMA_CH_AAL, 0); + } +} + +#if defined(ENABLE_TASKLET) && ENABLE_TASKLET +static void do_ppe_tasklet(unsigned long arg) +{ + *MBOX_IGU1_ISRC = *MBOX_IGU1_ISR; + mailbox_oam_rx_handler(); + mailbox_aal_rx_handler(); + if ( (*MBOX_IGU1_ISR & ((1 << RX_DMA_CH_AAL) | (1 << RX_DMA_CH_OAM))) != 0 ) + tasklet_schedule(&g_dma_tasklet); + else + enable_irq(PPE_MAILBOX_IGU1_INT); +} +#endif + +static irqreturn_t mailbox_irq_handler(int irq, void *dev_id) +{ + if ( !*MBOX_IGU1_ISR ) + return IRQ_HANDLED; + +#if defined(ENABLE_TASKLET) && ENABLE_TASKLET + disable_irq(PPE_MAILBOX_IGU1_INT); + tasklet_schedule(&g_dma_tasklet); +#else + *MBOX_IGU1_ISRC = *MBOX_IGU1_ISR; + mailbox_oam_rx_handler(); + mailbox_aal_rx_handler(); +#endif + + return IRQ_HANDLED; +} + +static INLINE void mailbox_signal(unsigned int queue, int is_tx) +{ + if ( is_tx ) { + while ( MBOX_IGU3_ISR_ISR(queue + FIRST_QSB_QID + 16) ); + *MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(queue + FIRST_QSB_QID + 16); + } + else { + while ( MBOX_IGU3_ISR_ISR(queue) ); + *MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(queue); + } +} + +static void set_qsb(struct atm_vcc *vcc, struct atm_qos *qos, unsigned int queue) +{ + struct clk *clk = clk_get(0, "fpi"); + unsigned int qsb_clk = clk_get_rate(clk); + unsigned int qsb_qid = queue + FIRST_QSB_QID; + union qsb_queue_parameter_table qsb_queue_parameter_table = {{0}}; + union qsb_queue_vbr_parameter_table qsb_queue_vbr_parameter_table = {{0}}; + unsigned int tmp; + +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { + static char *str_traffic_class[9] = { + "ATM_NONE", + "ATM_UBR", + "ATM_CBR", + "ATM_VBR", + "ATM_ABR", + "ATM_ANYCLASS", + "ATM_VBR_RT", + "ATM_UBR_PLUS", + "ATM_MAX_PCR" + }; + printk(KERN_INFO "QoS Parameters:\n"); + printk(KERN_INFO "\tAAL : %d\n", qos->aal); + printk(KERN_INFO "\tTX Traffic Class: %s\n", str_traffic_class[qos->txtp.traffic_class]); + printk(KERN_INFO "\tTX Max PCR : %d\n", qos->txtp.max_pcr); + printk(KERN_INFO "\tTX Min PCR : %d\n", qos->txtp.min_pcr); + printk(KERN_INFO "\tTX PCR : %d\n", qos->txtp.pcr); + printk(KERN_INFO "\tTX Max CDV : %d\n", qos->txtp.max_cdv); + printk(KERN_INFO "\tTX Max SDU : %d\n", qos->txtp.max_sdu); + printk(KERN_INFO "\tTX SCR : %d\n", qos->txtp.scr); + printk(KERN_INFO "\tTX MBS : %d\n", qos->txtp.mbs); + printk(KERN_INFO "\tTX CDV : %d\n", qos->txtp.cdv); + printk(KERN_INFO "\tRX Traffic Class: %s\n", str_traffic_class[qos->rxtp.traffic_class]); + printk(KERN_INFO "\tRX Max PCR : %d\n", qos->rxtp.max_pcr); + printk(KERN_INFO "\tRX Min PCR : %d\n", qos->rxtp.min_pcr); + printk(KERN_INFO "\tRX PCR : %d\n", qos->rxtp.pcr); + printk(KERN_INFO "\tRX Max CDV : %d\n", qos->rxtp.max_cdv); + printk(KERN_INFO "\tRX Max SDU : %d\n", qos->rxtp.max_sdu); + printk(KERN_INFO "\tRX SCR : %d\n", qos->rxtp.scr); + printk(KERN_INFO "\tRX MBS : %d\n", qos->rxtp.mbs); + printk(KERN_INFO "\tRX CDV : %d\n", qos->rxtp.cdv); + } +#endif // defined(DEBUG_QOS) && DEBUG_QOS + + /* + * Peak Cell Rate (PCR) Limiter + */ + if ( qos->txtp.max_pcr == 0 ) + qsb_queue_parameter_table.bit.tp = 0; /* disable PCR limiter */ + else { + /* peak cell rate would be slightly lower than requested [maximum_rate / pcr = (qsb_clock / 8) * (time_step / 4) / pcr] */ + tmp = ((qsb_clk * qsb_tstep) >> 5) / qos->txtp.max_pcr + 1; + /* check if overflow takes place */ + qsb_queue_parameter_table.bit.tp = tmp > QSB_TP_TS_MAX ? QSB_TP_TS_MAX : tmp; + } + + // A funny issue. Create two PVCs, one UBR and one UBR with max_pcr. + // Send packets to these two PVCs at same time, it trigger strange behavior. + // In A1, RAM from 0x80000000 to 0x0x8007FFFF was corrupted with fixed pattern 0x00000000 0x40000000. + // In A4, PPE firmware keep emiting unknown cell and do not respond to driver. + // To work around, create UBR always with max_pcr. + // If user want to create UBR without max_pcr, we give a default one larger than line-rate. + if ( qos->txtp.traffic_class == ATM_UBR && qsb_queue_parameter_table.bit.tp == 0 ) { + int port = g_atm_priv_data.conn[queue].port; + unsigned int max_pcr = g_atm_priv_data.port[port].tx_max_cell_rate + 1000; + + tmp = ((qsb_clk * qsb_tstep) >> 5) / max_pcr + 1; + if ( tmp > QSB_TP_TS_MAX ) + tmp = QSB_TP_TS_MAX; + else if ( tmp < 1 ) + tmp = 1; + qsb_queue_parameter_table.bit.tp = tmp; + } + + /* + * Weighted Fair Queueing Factor (WFQF) + */ + switch ( qos->txtp.traffic_class ) { + case ATM_CBR: + case ATM_VBR_RT: + /* real time queue gets weighted fair queueing bypass */ + qsb_queue_parameter_table.bit.wfqf = 0; + break; + case ATM_VBR_NRT: + case ATM_UBR_PLUS: + /* WFQF calculation here is based on virtual cell rates, to reduce granularity for high rates */ + /* WFQF is maximum cell rate / garenteed cell rate */ + /* wfqf = qsb_minimum_cell_rate * QSB_WFQ_NONUBR_MAX / requested_minimum_peak_cell_rate */ + if ( qos->txtp.min_pcr == 0 ) + qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_NONUBR_MAX; + else + { + tmp = QSB_GCR_MIN * QSB_WFQ_NONUBR_MAX / qos->txtp.min_pcr; + if ( tmp == 0 ) + qsb_queue_parameter_table.bit.wfqf = 1; + else if ( tmp > QSB_WFQ_NONUBR_MAX ) + qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_NONUBR_MAX; + else + qsb_queue_parameter_table.bit.wfqf = tmp; + } + break; + default: + case ATM_UBR: + qsb_queue_parameter_table.bit.wfqf = QSB_WFQ_UBR_BYPASS; + } + + /* + * Sustained Cell Rate (SCR) Leaky Bucket Shaper VBR.0/VBR.1 + */ + if ( qos->txtp.traffic_class == ATM_VBR_RT || qos->txtp.traffic_class == ATM_VBR_NRT ) { + if ( qos->txtp.scr == 0 ) { + /* disable shaper */ + qsb_queue_vbr_parameter_table.bit.taus = 0; + qsb_queue_vbr_parameter_table.bit.ts = 0; + } + else { + /* Cell Loss Priority (CLP) */ + if ( (vcc->atm_options & ATM_ATMOPT_CLP) ) + /* CLP1 */ + qsb_queue_parameter_table.bit.vbr = 1; + else + /* CLP0 */ + qsb_queue_parameter_table.bit.vbr = 0; + /* Rate Shaper Parameter (TS) and Burst Tolerance Parameter for SCR (tauS) */ + tmp = ((qsb_clk * qsb_tstep) >> 5) / qos->txtp.scr + 1; + qsb_queue_vbr_parameter_table.bit.ts = tmp > QSB_TP_TS_MAX ? QSB_TP_TS_MAX : tmp; + tmp = (qos->txtp.mbs - 1) * (qsb_queue_vbr_parameter_table.bit.ts - qsb_queue_parameter_table.bit.tp) / 64; + if ( tmp == 0 ) + qsb_queue_vbr_parameter_table.bit.taus = 1; + else if ( tmp > QSB_TAUS_MAX ) + qsb_queue_vbr_parameter_table.bit.taus = QSB_TAUS_MAX; + else + qsb_queue_vbr_parameter_table.bit.taus = tmp; + } + } + else { + qsb_queue_vbr_parameter_table.bit.taus = 0; + qsb_queue_vbr_parameter_table.bit.ts = 0; + } + + /* Queue Parameter Table (QPT) */ + *QSB_RTM = QSB_RTM_DM_SET(QSB_QPT_SET_MASK); + *QSB_RTD = QSB_RTD_TTV_SET(qsb_queue_parameter_table.dword); + *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_QPT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(qsb_qid); +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) + printk("QPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); +#endif + /* Queue VBR Paramter Table (QVPT) */ + *QSB_RTM = QSB_RTM_DM_SET(QSB_QVPT_SET_MASK); + *QSB_RTD = QSB_RTD_TTV_SET(qsb_queue_vbr_parameter_table.dword); + *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_VBR) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(qsb_qid); +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) + printk("QVPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); +#endif + +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { + printk("set_qsb\n"); + printk(" qsb_clk = %lu\n", (unsigned long)qsb_clk); + printk(" qsb_queue_parameter_table.bit.tp = %d\n", (int)qsb_queue_parameter_table.bit.tp); + printk(" qsb_queue_parameter_table.bit.wfqf = %d (0x%08X)\n", (int)qsb_queue_parameter_table.bit.wfqf, (int)qsb_queue_parameter_table.bit.wfqf); + printk(" qsb_queue_parameter_table.bit.vbr = %d\n", (int)qsb_queue_parameter_table.bit.vbr); + printk(" qsb_queue_parameter_table.dword = 0x%08X\n", (int)qsb_queue_parameter_table.dword); + printk(" qsb_queue_vbr_parameter_table.bit.ts = %d\n", (int)qsb_queue_vbr_parameter_table.bit.ts); + printk(" qsb_queue_vbr_parameter_table.bit.taus = %d\n", (int)qsb_queue_vbr_parameter_table.bit.taus); + printk(" qsb_queue_vbr_parameter_table.dword = 0x%08X\n", (int)qsb_queue_vbr_parameter_table.dword); + } +#endif +} + +static void qsb_global_set(void) +{ + struct clk *clk = clk_get(0, "fpi"); + unsigned int qsb_clk = clk_get_rate(clk); + int i; + unsigned int tmp1, tmp2, tmp3; + + *QSB_ICDV = QSB_ICDV_TAU_SET(qsb_tau); + *QSB_SBL = QSB_SBL_SBL_SET(qsb_srvm); + *QSB_CFG = QSB_CFG_TSTEPC_SET(qsb_tstep >> 1); +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) { + printk("qsb_clk = %u\n", qsb_clk); + printk("QSB_ICDV (%08X) = %d (%d), QSB_SBL (%08X) = %d (%d), QSB_CFG (%08X) = %d (%d)\n", (unsigned int)QSB_ICDV, *QSB_ICDV, QSB_ICDV_TAU_SET(qsb_tau), (unsigned int)QSB_SBL, *QSB_SBL, QSB_SBL_SBL_SET(qsb_srvm), (unsigned int)QSB_CFG, *QSB_CFG, QSB_CFG_TSTEPC_SET(qsb_tstep >> 1)); + } +#endif + + /* + * set SCT and SPT per port + */ + for ( i = 0; i < ATM_PORT_NUMBER; i++ ) { + if ( g_atm_priv_data.port[i].tx_max_cell_rate != 0 ) { + tmp1 = ((qsb_clk * qsb_tstep) >> 1) / g_atm_priv_data.port[i].tx_max_cell_rate; + tmp2 = tmp1 >> 6; /* integer value of Tsb */ + tmp3 = (tmp1 & ((1 << 6) - 1)) + 1; /* fractional part of Tsb */ + /* carry over to integer part (?) */ + if ( tmp3 == (1 << 6) ) + { + tmp3 = 0; + tmp2++; + } + if ( tmp2 == 0 ) + tmp2 = tmp3 = 1; + /* 1. set mask */ + /* 2. write value to data transfer register */ + /* 3. start the tranfer */ + /* SCT (FracRate) */ + *QSB_RTM = QSB_RTM_DM_SET(QSB_SET_SCT_MASK); + *QSB_RTD = QSB_RTD_TTV_SET(tmp3); + *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_SCT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(i & 0x01); +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) + printk("SCT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); +#endif + /* SPT (SBV + PN + IntRage) */ + *QSB_RTM = QSB_RTM_DM_SET(QSB_SET_SPT_MASK); + *QSB_RTD = QSB_RTD_TTV_SET(QSB_SPT_SBV_VALID | QSB_SPT_PN_SET(i & 0x01) | QSB_SPT_INTRATE_SET(tmp2)); + *QSB_RAMAC = QSB_RAMAC_RW_SET(QSB_RAMAC_RW_WRITE) | QSB_RAMAC_TSEL_SET(QSB_RAMAC_TSEL_SPT) | QSB_RAMAC_LH_SET(QSB_RAMAC_LH_LOW) | QSB_RAMAC_TESEL_SET(i & 0x01); +#if defined(DEBUG_QOS) && DEBUG_QOS + if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ) + printk("SPT: QSB_RTM (%08X) = 0x%08X, QSB_RTD (%08X) = 0x%08X, QSB_RAMAC (%08X) = 0x%08X\n", (unsigned int)QSB_RTM, *QSB_RTM, (unsigned int)QSB_RTD, *QSB_RTD, (unsigned int)QSB_RAMAC, *QSB_RAMAC); +#endif + } + } +} + +static INLINE void set_htu_entry(unsigned int vpi, unsigned int vci, unsigned int queue, int aal5, int is_retx) +{ + struct htu_entry htu_entry = { res1: 0x00, + clp: is_retx ? 0x01 : 0x00, + pid: g_atm_priv_data.conn[queue].port & 0x01, + vpi: vpi, + vci: vci, + pti: 0x00, + vld: 0x01}; + + struct htu_mask htu_mask = { set: 0x01, +#if !defined(ENABLE_ATM_RETX) || !ENABLE_ATM_RETX + clp: 0x01, + pid_mask: 0x02, +#else + clp: g_retx_htu ? 0x00 : 0x01, + pid_mask: RETX_MODE_CFG->retx_en ? 0x03 : 0x02, +#endif + vpi_mask: 0x00, +#if !defined(ENABLE_ATM_RETX) || !ENABLE_ATM_RETX + vci_mask: 0x0000, +#else + vci_mask: RETX_MODE_CFG->retx_en ? 0xFF00 : 0x0000, +#endif + pti_mask: 0x03, // 0xx, user data + clear: 0x00}; + + struct htu_result htu_result = {res1: 0x00, + cellid: queue, + res2: 0x00, + type: aal5 ? 0x00 : 0x01, + ven: 0x01, + res3: 0x00, + qid: queue}; + + *HTU_RESULT(queue + OAM_HTU_ENTRY_NUMBER) = htu_result; + *HTU_MASK(queue + OAM_HTU_ENTRY_NUMBER) = htu_mask; + *HTU_ENTRY(queue + OAM_HTU_ENTRY_NUMBER) = htu_entry; +} + +static INLINE void clear_htu_entry(unsigned int queue) +{ + HTU_ENTRY(queue + OAM_HTU_ENTRY_NUMBER)->vld = 0; +} + +static void validate_oam_htu_entry(void) +{ + HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY)->vld = 1; + HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY)->vld = 1; + HTU_ENTRY(OAM_F5_HTU_ENTRY)->vld = 1; +#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX + HTU_ENTRY(OAM_ARQ_HTU_ENTRY)->vld = 1; +#endif +} + +static void invalidate_oam_htu_entry(void) +{ + HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY)->vld = 0; + HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY)->vld = 0; + HTU_ENTRY(OAM_F5_HTU_ENTRY)->vld = 0; +#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX + HTU_ENTRY(OAM_ARQ_HTU_ENTRY)->vld = 0; +#endif +} + +static INLINE int find_vpi(unsigned int vpi) +{ + int i; + unsigned int bit; + + for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { + if ( (g_atm_priv_data.conn_table & bit) != 0 + && g_atm_priv_data.conn[i].vcc != NULL + && vpi == g_atm_priv_data.conn[i].vcc->vpi ) + return i; + } + + return -1; +} + +static INLINE int find_vpivci(unsigned int vpi, unsigned int vci) +{ + int i; + unsigned int bit; + + for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { + if ( (g_atm_priv_data.conn_table & bit) != 0 + && g_atm_priv_data.conn[i].vcc != NULL + && vpi == g_atm_priv_data.conn[i].vcc->vpi + && vci == g_atm_priv_data.conn[i].vcc->vci ) + return i; + } + + return -1; +} + +static INLINE int find_vcc(struct atm_vcc *vcc) +{ + int i; + unsigned int bit; + + for ( i = 0, bit = 1; i < MAX_PVC_NUMBER; i++, bit <<= 1 ) { + if ( (g_atm_priv_data.conn_table & bit) != 0 + && g_atm_priv_data.conn[i].vcc == vcc ) + return i; + } + + return -1; +} + +#if defined(DEBUG_DUMP_SKB) && DEBUG_DUMP_SKB +static void dump_skb(struct sk_buff *skb, u32 len, char *title, int port, int ch, int is_tx) +{ + int i; + + if ( !(ifx_atm_dbg_enable & (is_tx ? DBG_ENABLE_MASK_DUMP_SKB_TX : DBG_ENABLE_MASK_DUMP_SKB_RX)) ) + return; + + if ( skb->len < len ) + len = skb->len; + + if ( len > RX_DMA_CH_AAL_BUF_SIZE ) { + printk("too big data length: skb = %08x, skb->data = %08x, skb->len = %d\n", (u32)skb, (u32)skb->data, skb->len); + return; + } + + if ( ch >= 0 ) + printk("%s (port %d, ch %d)\n", title, port, ch); + else + printk("%s\n", title); + printk(" skb->data = %08X, skb->tail = %08X, skb->len = %d\n", (u32)skb->data, (u32)skb->tail, (int)skb->len); + for ( i = 1; i <= len; i++ ) { + if ( i % 16 == 1 ) + printk(" %4d:", i - 1); + printk(" %02X", (int)(*((char*)skb->data + i - 1) & 0xFF)); + if ( i % 16 == 0 ) + printk("\n"); + } + if ( (i - 1) % 16 != 0 ) + printk("\n"); +} +#endif + +static INLINE void proc_file_create(void) +{ +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + struct proc_dir_entry *res; +#endif + + g_atm_dir = proc_mkdir("driver/ifx_atm", NULL); + + create_proc_read_entry("version", + 0, + g_atm_dir, + proc_read_version, + NULL); + + res = create_proc_entry("mib", + 0, + g_atm_dir); + if ( res != NULL ) { + res->read_proc = proc_read_mib; + res->write_proc = proc_write_mib; + } + +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + res = create_proc_entry("dbg", + 0, + g_atm_dir); + if ( res != NULL ) { + res->read_proc = proc_read_dbg; + res->write_proc = proc_write_dbg; + } +#endif + +#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC + create_proc_read_entry("htu", + 0, + g_atm_dir, + proc_read_htu, + NULL); + + create_proc_read_entry("txq", + 0, + g_atm_dir, + proc_read_txq, + NULL); +#endif +} + +static INLINE void proc_file_delete(void) +{ +#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC + remove_proc_entry("txq", g_atm_dir); + + remove_proc_entry("htu", g_atm_dir); +#endif + +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + remove_proc_entry("dbg", g_atm_dir); +#endif + + remove_proc_entry("version", g_atm_dir); + + remove_proc_entry("driver/ifx_atm", NULL); +} + +static int proc_read_version(char *buf, char **start, off_t offset, int count, int *eof, void *data) +{ + int len = 0; + + len += ifx_atm_version(buf + len); + + if ( offset >= len ) { + *start = buf; + *eof = 1; + return 0; + } + *start = buf + offset; + if ( (len -= offset) > count ) + return count; + *eof = 1; + return len; +} + +static int proc_read_mib(char *page, char **start, off_t off, int count, int *eof, void *data) +{ + int len = 0; + + len += sprintf(page + off + len, "Firmware\n"); + len += sprintf(page + off + len, " wrx_drophtu_cell = %u\n", WAN_MIB_TABLE->wrx_drophtu_cell); + len += sprintf(page + off + len, " wrx_dropdes_pdu = %u\n", WAN_MIB_TABLE->wrx_dropdes_pdu); + len += sprintf(page + off + len, " wrx_correct_pdu = %u\n", WAN_MIB_TABLE->wrx_correct_pdu); + len += sprintf(page + off + len, " wrx_err_pdu = %u\n", WAN_MIB_TABLE->wrx_err_pdu); + len += sprintf(page + off + len, " wrx_dropdes_cell = %u\n", WAN_MIB_TABLE->wrx_dropdes_cell); + len += sprintf(page + off + len, " wrx_correct_cell = %u\n", WAN_MIB_TABLE->wrx_correct_cell); + len += sprintf(page + off + len, " wrx_err_cell = %u\n", WAN_MIB_TABLE->wrx_err_cell); + len += sprintf(page + off + len, " wrx_total_byte = %u\n", WAN_MIB_TABLE->wrx_total_byte); + len += sprintf(page + off + len, " wtx_total_pdu = %u\n", WAN_MIB_TABLE->wtx_total_pdu); + len += sprintf(page + off + len, " wtx_total_cell = %u\n", WAN_MIB_TABLE->wtx_total_cell); + len += sprintf(page + off + len, " wtx_total_byte = %u\n", WAN_MIB_TABLE->wtx_total_byte); + len += sprintf(page + off + len, "Driver\n"); + len += sprintf(page + off + len, " wrx_pdu = %u\n", g_atm_priv_data.wrx_pdu); + len += sprintf(page + off + len, " wrx_drop_pdu = %u\n", g_atm_priv_data.wrx_drop_pdu); + len += sprintf(page + off + len, " wtx_pdu = %u\n", g_atm_priv_data.wtx_pdu); + len += sprintf(page + off + len, " wtx_err_pdu = %u\n", g_atm_priv_data.wtx_err_pdu); + len += sprintf(page + off + len, " wtx_drop_pdu = %u\n", g_atm_priv_data.wtx_drop_pdu); + + *eof = 1; + + return len; +} + +static int proc_write_mib(struct file *file, const char *buf, unsigned long count, void *data) +{ + char str[2048]; + char *p; + int len, rlen; + + len = count < sizeof(str) ? count : sizeof(str) - 1; + rlen = len - copy_from_user(str, buf, len); + while ( rlen && str[rlen - 1] <= ' ' ) + rlen--; + str[rlen] = 0; + for ( p = str; *p && *p <= ' '; p++, rlen-- ); + if ( !*p ) + return 0; + + if ( stricmp(p, "clear") == 0 || stricmp(p, "clear all") == 0 + || stricmp(p, "clean") == 0 || stricmp(p, "clean all") == 0 ) { + memset(WAN_MIB_TABLE, 0, sizeof(*WAN_MIB_TABLE)); + g_atm_priv_data.wrx_pdu = 0; + g_atm_priv_data.wrx_drop_pdu = 0; + g_atm_priv_data.wtx_pdu = 0; + g_atm_priv_data.wtx_err_pdu = 0; + g_atm_priv_data.wtx_drop_pdu = 0; + } + + return count; +} + +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC + +static int proc_read_dbg(char *page, char **start, off_t off, int count, int *eof, void *data) +{ + int len = 0; + + len += sprintf(page + off + len, "error print - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ERR) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "debug print - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DEBUG_PRINT) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "assert - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ASSERT) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "dump rx skb - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_SKB_RX) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "dump tx skb - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_SKB_TX) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "qos - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_QOS) ? "enabled" : "disabled"); + len += sprintf(page + off + len, "dump init - %s\n", (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DUMP_INIT) ? "enabled" : "disabled"); + + *eof = 1; + + return len; +} + +static int proc_write_dbg(struct file *file, const char *buf, unsigned long count, void *data) +{ + static const char *dbg_enable_mask_str[] = { + " error print", + " err", + " debug print", + " dbg", + " assert", + " assert", + " dump rx skb", + " rx", + " dump tx skb", + " tx", + " dump qos", + " qos", + " dump init", + " init", + " all" + }; + static const int dbg_enable_mask_str_len[] = { + 12, 4, + 12, 4, + 7, 7, + 12, 3, + 12, 3, + 9, 4, + 10, 5, + 4 + }; + u32 dbg_enable_mask[] = { + DBG_ENABLE_MASK_ERR, + DBG_ENABLE_MASK_DEBUG_PRINT, + DBG_ENABLE_MASK_ASSERT, + DBG_ENABLE_MASK_DUMP_SKB_RX, + DBG_ENABLE_MASK_DUMP_SKB_TX, + DBG_ENABLE_MASK_DUMP_QOS, + DBG_ENABLE_MASK_DUMP_INIT, + DBG_ENABLE_MASK_ALL + }; + + char str[2048]; + char *p; + + int len, rlen; + + int f_enable = 0; + int i; + + len = count < sizeof(str) ? count : sizeof(str) - 1; + rlen = len - copy_from_user(str, buf, len); + while ( rlen && str[rlen - 1] <= ' ' ) + rlen--; + str[rlen] = 0; + for ( p = str; *p && *p <= ' '; p++, rlen-- ); + if ( !*p ) + return 0; + + if ( strincmp(p, "enable", 6) == 0 ) { + p += 6; + f_enable = 1; + } + else if ( strincmp(p, "disable", 7) == 0 ) { + p += 7; + f_enable = -1; + } + else if ( strincmp(p, "help", 4) == 0 || *p == '?' ) { + printk("echo [err/dbg/assert/rx/tx/init/all] > /proc/eth/dbg\n"); + } + + if ( f_enable ) { + if ( *p == 0 ) { + if ( f_enable > 0 ) + ifx_atm_dbg_enable |= DBG_ENABLE_MASK_ALL; + else + ifx_atm_dbg_enable &= ~DBG_ENABLE_MASK_ALL; + } + else { + do { + for ( i = 0; i < NUM_ENTITY(dbg_enable_mask_str); i++ ) + if ( strincmp(p, dbg_enable_mask_str[i], dbg_enable_mask_str_len[i]) == 0 ) { + if ( f_enable > 0 ) + ifx_atm_dbg_enable |= dbg_enable_mask[i >> 1]; + else + ifx_atm_dbg_enable &= ~dbg_enable_mask[i >> 1]; + p += dbg_enable_mask_str_len[i]; + break; + } + } while ( i < NUM_ENTITY(dbg_enable_mask_str) ); + } + } + + return count; +} + +#endif + +#if defined(ENABLE_FW_PROC) && ENABLE_FW_PROC + +static INLINE int print_htu(char *buf, int i) +{ + int len = 0; + + if ( HTU_ENTRY(i)->vld ) { + len += sprintf(buf + len, "%2d. valid\n", i); + len += sprintf(buf + len, " entry 0x%08x - pid %01x vpi %02x vci %04x pti %01x\n", *(u32*)HTU_ENTRY(i), HTU_ENTRY(i)->pid, HTU_ENTRY(i)->vpi, HTU_ENTRY(i)->vci, HTU_ENTRY(i)->pti); + len += sprintf(buf + len, " mask 0x%08x - pid %01x vpi %02x vci %04x pti %01x\n", *(u32*)HTU_MASK(i), HTU_MASK(i)->pid_mask, HTU_MASK(i)->vpi_mask, HTU_MASK(i)->vci_mask, HTU_MASK(i)->pti_mask); + len += sprintf(buf + len, " result 0x%08x - type: %s, qid: %d", *(u32*)HTU_RESULT(i), HTU_RESULT(i)->type ? "cell" : "AAL5", HTU_RESULT(i)->qid); + if ( HTU_RESULT(i)->type ) + len += sprintf(buf + len, ", cell id: %d, verification: %s", HTU_RESULT(i)->cellid, HTU_RESULT(i)->ven ? "on" : "off"); + len += sprintf(buf + len, "\n"); + } + else + len += sprintf(buf + len, "%2d. invalid\n", i); + + return len; +} + +static int proc_read_htu(char *page, char **start, off_t off, int count, int *eof, void *data) +{ + int len = 0; + int len_max = off + count; + char *pstr; + char str[1024]; + int llen; + + int htuts = *CFG_WRX_HTUTS; + int i; + + pstr = *start = page; + + llen = sprintf(pstr, "HTU Table (Max %d):\n", htuts); + pstr += llen; + len += llen; + + for ( i = 0; i < htuts; i++ ) { + llen = print_htu(str, i); + if ( len <= off && len + llen > off ) { + memcpy(pstr, str + off - len, len + llen - off); + pstr += len + llen - off; + } + else if ( len > off ) { + memcpy(pstr, str, llen); + pstr += llen; + } + len += llen; + if ( len >= len_max ) + goto PROC_READ_HTU_OVERRUN_END; + } + + *eof = 1; + + return len - off; + +PROC_READ_HTU_OVERRUN_END: + + return len - llen - off; +} + +static INLINE int print_tx_queue(char *buf, int i) +{ + int len = 0; + + if ( (*WTX_DMACH_ON & (1 << i)) ) { + len += sprintf(buf + len, "%2d. valid\n", i); + len += sprintf(buf + len, " queue 0x%08x - sbid %u, qsb %s\n", *(u32*)WTX_QUEUE_CONFIG(i), (unsigned int)WTX_QUEUE_CONFIG(i)->sbid, WTX_QUEUE_CONFIG(i)->qsben ? "enable" : "disable"); + len += sprintf(buf + len, " dma 0x%08x - base %08x, len %u, vlddes %u\n", *(u32*)WTX_DMA_CHANNEL_CONFIG(i), WTX_DMA_CHANNEL_CONFIG(i)->desba, WTX_DMA_CHANNEL_CONFIG(i)->deslen, WTX_DMA_CHANNEL_CONFIG(i)->vlddes); + } + else + len += sprintf(buf + len, "%2d. invalid\n", i); + + return len; +} + +static int proc_read_txq(char *page, char **start, off_t off, int count, int *eof, void *data) +{ + int len = 0; + int len_max = off + count; + char *pstr; + char str[1024]; + int llen; + + int i; + + pstr = *start = page; + + llen = sprintf(pstr, "TX Queue Config (Max %d):\n", *CFG_WTX_DCHNUM); + pstr += llen; + len += llen; + + for ( i = 0; i < 16; i++ ) { + llen = print_tx_queue(str, i); + if ( len <= off && len + llen > off ) { + memcpy(pstr, str + off - len, len + llen - off); + pstr += len + llen - off; + } + else if ( len > off ) { + memcpy(pstr, str, llen); + pstr += llen; + } + len += llen; + if ( len >= len_max ) + goto PROC_READ_HTU_OVERRUN_END; + } + + *eof = 1; + + return len - off; + +PROC_READ_HTU_OVERRUN_END: + + return len - llen - off; +} + +#endif + +static int stricmp(const char *p1, const char *p2) +{ + int c1, c2; + + while ( *p1 && *p2 ) + { + c1 = *p1 >= 'A' && *p1 <= 'Z' ? *p1 + 'a' - 'A' : *p1; + c2 = *p2 >= 'A' && *p2 <= 'Z' ? *p2 + 'a' - 'A' : *p2; + if ( (c1 -= c2) ) + return c1; + p1++; + p2++; + } + + return *p1 - *p2; +} + +#if defined(ENABLE_DBG_PROC) && ENABLE_DBG_PROC +static int strincmp(const char *p1, const char *p2, int n) +{ + int c1 = 0, c2; + + while ( n && *p1 && *p2 ) + { + c1 = *p1 >= 'A' && *p1 <= 'Z' ? *p1 + 'a' - 'A' : *p1; + c2 = *p2 >= 'A' && *p2 <= 'Z' ? *p2 + 'a' - 'A' : *p2; + if ( (c1 -= c2) ) + return c1; + p1++; + p2++; + n--; + } + + return n ? *p1 - *p2 : c1; +} +#endif + +static INLINE int ifx_atm_version(char *buf) +{ + int len = 0; + unsigned int major, minor; + + ifx_atm_get_fw_ver(&major, &minor); + + len += sprintf(buf + len, "Infineon Technologies ATM driver version %d.%d.%d\n", IFX_ATM_VER_MAJOR, IFX_ATM_VER_MID, IFX_ATM_VER_MINOR); + len += sprintf(buf + len, "Infineon Technologies ATM (A1) firmware version %d.%d\n", major, minor); + + return len; +} + +#ifdef MODULE +static INLINE void reset_ppe(void) +{ + // TODO: +} +#endif + +static INLINE void check_parameters(void) +{ + /* Please refer to Amazon spec 15.4 for setting these values. */ + if ( qsb_tau < 1 ) + qsb_tau = 1; + if ( qsb_tstep < 1 ) + qsb_tstep = 1; + else if ( qsb_tstep > 4 ) + qsb_tstep = 4; + else if ( qsb_tstep == 3 ) + qsb_tstep = 2; + + /* There is a delay between PPE write descriptor and descriptor is */ + /* really stored in memory. Host also has this delay when writing */ + /* descriptor. So PPE will use this value to determine if the write */ + /* operation makes effect. */ + if ( write_descriptor_delay < 0 ) + write_descriptor_delay = 0; + + if ( aal5_fill_pattern < 0 ) + aal5_fill_pattern = 0; + else + aal5_fill_pattern &= 0xFF; + + /* Because of the limitation of length field in descriptors, the packet */ + /* size could not be larger than 64K minus overhead size. */ + if ( aal5r_max_packet_size < 0 ) + aal5r_max_packet_size = 0; + else if ( aal5r_max_packet_size >= 65535 - MAX_RX_FRAME_EXTRA_BYTES ) + aal5r_max_packet_size = 65535 - MAX_RX_FRAME_EXTRA_BYTES; + if ( aal5r_min_packet_size < 0 ) + aal5r_min_packet_size = 0; + else if ( aal5r_min_packet_size > aal5r_max_packet_size ) + aal5r_min_packet_size = aal5r_max_packet_size; + if ( aal5s_max_packet_size < 0 ) + aal5s_max_packet_size = 0; + else if ( aal5s_max_packet_size >= 65535 - MAX_TX_FRAME_EXTRA_BYTES ) + aal5s_max_packet_size = 65535 - MAX_TX_FRAME_EXTRA_BYTES; + if ( aal5s_min_packet_size < 0 ) + aal5s_min_packet_size = 0; + else if ( aal5s_min_packet_size > aal5s_max_packet_size ) + aal5s_min_packet_size = aal5s_max_packet_size; + + if ( dma_rx_descriptor_length < 2 ) + dma_rx_descriptor_length = 2; + if ( dma_tx_descriptor_length < 2 ) + dma_tx_descriptor_length = 2; + if ( dma_rx_clp1_descriptor_threshold < 0 ) + dma_rx_clp1_descriptor_threshold = 0; + else if ( dma_rx_clp1_descriptor_threshold > dma_rx_descriptor_length ) + dma_rx_clp1_descriptor_threshold = dma_rx_descriptor_length; + + if ( dma_tx_descriptor_length < 2 ) + dma_tx_descriptor_length = 2; +} + +static INLINE int init_priv_data(void) +{ + void *p; + int i; + struct rx_descriptor rx_desc = {0}; + struct sk_buff *skb; + volatile struct tx_descriptor *p_tx_desc; + struct sk_buff **ppskb; + + // clear atm private data structure + memset(&g_atm_priv_data, 0, sizeof(g_atm_priv_data)); + + // allocate memory for RX (AAL) descriptors + p = kzalloc(dma_rx_descriptor_length * sizeof(struct rx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); + if ( p == NULL ) + return IFX_ERROR; + dma_cache_wback_inv((unsigned long)p, dma_rx_descriptor_length * sizeof(struct rx_descriptor) + DESC_ALIGNMENT); + g_atm_priv_data.aal_desc_base = p; + p = (void *)((((unsigned int)p + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); + g_atm_priv_data.aal_desc = (volatile struct rx_descriptor *)p; + + // allocate memory for RX (OAM) descriptors + p = kzalloc(RX_DMA_CH_OAM_DESC_LEN * sizeof(struct rx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); + if ( p == NULL ) + return IFX_ERROR; + dma_cache_wback_inv((unsigned long)p, RX_DMA_CH_OAM_DESC_LEN * sizeof(struct rx_descriptor) + DESC_ALIGNMENT); + g_atm_priv_data.oam_desc_base = p; + p = (void *)((((unsigned int)p + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); + g_atm_priv_data.oam_desc = (volatile struct rx_descriptor *)p; + + // allocate memory for RX (OAM) buffer + p = kzalloc(RX_DMA_CH_OAM_DESC_LEN * RX_DMA_CH_OAM_BUF_SIZE + DATA_BUFFER_ALIGNMENT, GFP_KERNEL); + if ( p == NULL ) + return IFX_ERROR; + dma_cache_wback_inv((unsigned long)p, RX_DMA_CH_OAM_DESC_LEN * RX_DMA_CH_OAM_BUF_SIZE + DATA_BUFFER_ALIGNMENT); + g_atm_priv_data.oam_buf_base = p; + p = (void *)(((unsigned int)p + DATA_BUFFER_ALIGNMENT - 1) & ~(DATA_BUFFER_ALIGNMENT - 1)); + g_atm_priv_data.oam_buf = p; + + // allocate memory for TX descriptors + p = kzalloc(MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct tx_descriptor) + DESC_ALIGNMENT, GFP_KERNEL); + if ( p == NULL ) + return IFX_ERROR; + dma_cache_wback_inv((unsigned long)p, MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct tx_descriptor) + DESC_ALIGNMENT); + g_atm_priv_data.tx_desc_base = p; + + // allocate memory for TX skb pointers + p = kzalloc(MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct sk_buff *) + 4, GFP_KERNEL); + if ( p == NULL ) + return IFX_ERROR; + dma_cache_wback_inv((unsigned long)p, MAX_PVC_NUMBER * dma_tx_descriptor_length * sizeof(struct sk_buff *) + 4); + g_atm_priv_data.tx_skb_base = p; + + // setup RX (AAL) descriptors + rx_desc.own = 1; + rx_desc.c = 0; + rx_desc.sop = 1; + rx_desc.eop = 1; + rx_desc.byteoff = 0; + rx_desc.id = 0; + rx_desc.err = 0; + rx_desc.datalen = RX_DMA_CH_AAL_BUF_SIZE; + for ( i = 0; i < dma_rx_descriptor_length; i++ ) { + skb = alloc_skb_rx(); + if ( skb == NULL ) + return IFX_ERROR; + rx_desc.dataptr = ((unsigned int)skb->data >> 2) & 0x0FFFFFFF; + g_atm_priv_data.aal_desc[i] = rx_desc; + } + + // setup RX (OAM) descriptors + p = (void *)((unsigned int)g_atm_priv_data.oam_buf | KSEG1); + rx_desc.own = 1; + rx_desc.c = 0; + rx_desc.sop = 1; + rx_desc.eop = 1; + rx_desc.byteoff = 0; + rx_desc.id = 0; + rx_desc.err = 0; + rx_desc.datalen = RX_DMA_CH_OAM_BUF_SIZE; + for ( i = 0; i < RX_DMA_CH_OAM_DESC_LEN; i++ ) { + rx_desc.dataptr = ((unsigned int)p >> 2) & 0x0FFFFFFF; + g_atm_priv_data.oam_desc[i] = rx_desc; + p = (void *)((unsigned int)p + RX_DMA_CH_OAM_BUF_SIZE); + } + + // setup TX descriptors and skb pointers + p_tx_desc = (volatile struct tx_descriptor *)((((unsigned int)g_atm_priv_data.tx_desc_base + DESC_ALIGNMENT - 1) & ~(DESC_ALIGNMENT - 1)) | KSEG1); + ppskb = (struct sk_buff **)(((unsigned int)g_atm_priv_data.tx_skb_base + 3) & ~3); + for ( i = 0; i < MAX_PVC_NUMBER; i++ ) { + g_atm_priv_data.conn[i].tx_desc = &p_tx_desc[i * dma_tx_descriptor_length]; + g_atm_priv_data.conn[i].tx_skb = &ppskb[i * dma_tx_descriptor_length]; + } + + for ( i = 0; i < ATM_PORT_NUMBER; i++ ) + g_atm_priv_data.port[i].tx_max_cell_rate = DEFAULT_TX_LINK_RATE; + + return IFX_SUCCESS; +} + +static INLINE void clear_priv_data(void) +{ + int i, j; + struct sk_buff *skb; + + for ( i = 0; i < MAX_PVC_NUMBER; i++ ) { + if ( g_atm_priv_data.conn[i].tx_skb != NULL ) { + for ( j = 0; j < dma_tx_descriptor_length; j++ ) + if ( g_atm_priv_data.conn[i].tx_skb[j] != NULL ) + dev_kfree_skb_any(g_atm_priv_data.conn[i].tx_skb[j]); + } + } + + if ( g_atm_priv_data.tx_skb_base != NULL ) + kfree(g_atm_priv_data.tx_skb_base); + + if ( g_atm_priv_data.tx_desc_base != NULL ) + kfree(g_atm_priv_data.tx_desc_base); + + if ( g_atm_priv_data.oam_buf_base != NULL ) + kfree(g_atm_priv_data.oam_buf_base); + + if ( g_atm_priv_data.oam_desc_base != NULL ) + kfree(g_atm_priv_data.oam_desc_base); + + if ( g_atm_priv_data.aal_desc_base != NULL ) { + for ( i = 0; i < dma_rx_descriptor_length; i++ ) { + if ( g_atm_priv_data.aal_desc[i].sop || g_atm_priv_data.aal_desc[i].eop ) { // descriptor initialized + skb = get_skb_rx_pointer(g_atm_priv_data.aal_desc[i].dataptr); + dev_kfree_skb_any(skb); + } + } + kfree(g_atm_priv_data.aal_desc_base); + } +} + +static INLINE void init_rx_tables(void) +{ + int i; + struct wrx_queue_config wrx_queue_config = {0}; + struct wrx_dma_channel_config wrx_dma_channel_config = {0}; + struct htu_entry htu_entry = {0}; + struct htu_result htu_result = {0}; + struct htu_mask htu_mask = { set: 0x01, + clp: 0x01, + pid_mask: 0x00, + vpi_mask: 0x00, + vci_mask: 0x00, + pti_mask: 0x00, + clear: 0x00}; + + /* + * General Registers + */ + *CFG_WRX_HTUTS = MAX_PVC_NUMBER + OAM_HTU_ENTRY_NUMBER; + *CFG_WRX_QNUM = MAX_QUEUE_NUMBER; + *CFG_WRX_DCHNUM = RX_DMA_CH_TOTAL; + *WRX_DMACH_ON = (1 << RX_DMA_CH_TOTAL) - 1; + *WRX_HUNT_BITTH = DEFAULT_RX_HUNT_BITTH; + + /* + * WRX Queue Configuration Table + */ + wrx_queue_config.uumask = 0; + wrx_queue_config.cpimask = 0; + wrx_queue_config.uuexp = 0; + wrx_queue_config.cpiexp = 0; + wrx_queue_config.mfs = aal5r_max_packet_size; + wrx_queue_config.oversize = aal5r_max_packet_size; + wrx_queue_config.undersize = aal5r_min_packet_size; + wrx_queue_config.errdp = aal5r_drop_error_packet; + wrx_queue_config.dmach = RX_DMA_CH_AAL; + for ( i = 0; i < MAX_QUEUE_NUMBER; i++ ) + *WRX_QUEUE_CONFIG(i) = wrx_queue_config; + WRX_QUEUE_CONFIG(OAM_RX_QUEUE)->dmach = RX_DMA_CH_OAM; + + /* + * WRX DMA Channel Configuration Table + */ + wrx_dma_channel_config.chrl = 0; + wrx_dma_channel_config.clp1th = dma_rx_clp1_descriptor_threshold; + wrx_dma_channel_config.mode = 0; + wrx_dma_channel_config.rlcfg = 0; + + wrx_dma_channel_config.deslen = RX_DMA_CH_OAM_DESC_LEN; + wrx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.oam_desc >> 2) & 0x0FFFFFFF; + *WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_OAM) = wrx_dma_channel_config; + + wrx_dma_channel_config.deslen = dma_rx_descriptor_length; + wrx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.aal_desc >> 2) & 0x0FFFFFFF; + *WRX_DMA_CHANNEL_CONFIG(RX_DMA_CH_AAL) = wrx_dma_channel_config; + + /* + * HTU Tables + */ + for ( i = 0; i < MAX_PVC_NUMBER; i++ ) + { + htu_result.qid = (unsigned int)i; + + *HTU_ENTRY(i + OAM_HTU_ENTRY_NUMBER) = htu_entry; + *HTU_MASK(i + OAM_HTU_ENTRY_NUMBER) = htu_mask; + *HTU_RESULT(i + OAM_HTU_ENTRY_NUMBER) = htu_result; + } + /* OAM HTU Entry */ + htu_entry.vci = 0x03; + htu_mask.pid_mask = 0x03; + htu_mask.vpi_mask = 0xFF; + htu_mask.vci_mask = 0x0000; + htu_mask.pti_mask = 0x07; + htu_result.cellid = OAM_RX_QUEUE; + htu_result.type = 1; + htu_result.ven = 1; + htu_result.qid = OAM_RX_QUEUE; + *HTU_RESULT(OAM_F4_SEG_HTU_ENTRY) = htu_result; + *HTU_MASK(OAM_F4_SEG_HTU_ENTRY) = htu_mask; + *HTU_ENTRY(OAM_F4_SEG_HTU_ENTRY) = htu_entry; + htu_entry.vci = 0x04; + htu_result.cellid = OAM_RX_QUEUE; + htu_result.type = 1; + htu_result.ven = 1; + htu_result.qid = OAM_RX_QUEUE; + *HTU_RESULT(OAM_F4_TOT_HTU_ENTRY) = htu_result; + *HTU_MASK(OAM_F4_TOT_HTU_ENTRY) = htu_mask; + *HTU_ENTRY(OAM_F4_TOT_HTU_ENTRY) = htu_entry; + htu_entry.vci = 0x00; + htu_entry.pti = 0x04; + htu_mask.vci_mask = 0xFFFF; + htu_mask.pti_mask = 0x01; + htu_result.cellid = OAM_RX_QUEUE; + htu_result.type = 1; + htu_result.ven = 1; + htu_result.qid = OAM_RX_QUEUE; + *HTU_RESULT(OAM_F5_HTU_ENTRY) = htu_result; + *HTU_MASK(OAM_F5_HTU_ENTRY) = htu_mask; + *HTU_ENTRY(OAM_F5_HTU_ENTRY) = htu_entry; +#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX + htu_entry.pid = 0x0; + htu_entry.vpi = 0x01; + htu_entry.vci = 0x0001; + htu_entry.pti = 0x00; + htu_mask.pid_mask = 0x0; + htu_mask.vpi_mask = 0x00; + htu_mask.vci_mask = 0x0000; + htu_mask.pti_mask = 0x3; + htu_result.cellid = OAM_RX_QUEUE; + htu_result.type = 1; + htu_result.ven = 1; + htu_result.qid = OAM_RX_QUEUE; + *HTU_RESULT(OAM_ARQ_HTU_ENTRY) = htu_result; + *HTU_MASK(OAM_ARQ_HTU_ENTRY) = htu_mask; + *HTU_ENTRY(OAM_ARQ_HTU_ENTRY) = htu_entry; +#endif +} + +static INLINE void init_tx_tables(void) +{ + int i; + struct wtx_queue_config wtx_queue_config = {0}; + struct wtx_dma_channel_config wtx_dma_channel_config = {0}; + struct wtx_port_config wtx_port_config = { res1: 0, + qid: 0, + qsben: 1}; + + /* + * General Registers + */ + *CFG_WTX_DCHNUM = MAX_TX_DMA_CHANNEL_NUMBER; + *WTX_DMACH_ON = ((1 << MAX_TX_DMA_CHANNEL_NUMBER) - 1) ^ ((1 << FIRST_QSB_QID) - 1); + *CFG_WRDES_DELAY = write_descriptor_delay; + + /* + * WTX Port Configuration Table + */ + for ( i = 0; i < ATM_PORT_NUMBER; i++ ) + *WTX_PORT_CONFIG(i) = wtx_port_config; + + /* + * WTX Queue Configuration Table + */ + wtx_queue_config.type = 0x0; + wtx_queue_config.qsben = 1; + wtx_queue_config.sbid = 0; + for ( i = 0; i < MAX_TX_DMA_CHANNEL_NUMBER; i++ ) + *WTX_QUEUE_CONFIG(i) = wtx_queue_config; + + /* + * WTX DMA Channel Configuration Table + */ + wtx_dma_channel_config.mode = 0; + wtx_dma_channel_config.deslen = 0; + wtx_dma_channel_config.desba = 0; + for ( i = 0; i < FIRST_QSB_QID; i++ ) + *WTX_DMA_CHANNEL_CONFIG(i) = wtx_dma_channel_config; + /* normal connection */ + wtx_dma_channel_config.deslen = dma_tx_descriptor_length; + for ( ; i < MAX_TX_DMA_CHANNEL_NUMBER ; i++ ) { + wtx_dma_channel_config.desba = ((unsigned int)g_atm_priv_data.conn[i - FIRST_QSB_QID].tx_desc >> 2) & 0x0FFFFFFF; + *WTX_DMA_CHANNEL_CONFIG(i) = wtx_dma_channel_config; + } +} + + + +/* + * #################################### + * Global Function + * #################################### + */ + +static int atm_showtime_enter(struct port_cell_info *port_cell, void *xdata_addr) +{ + int i, j; + + ASSERT(port_cell != NULL, "port_cell is NULL"); + ASSERT(xdata_addr != NULL, "xdata_addr is NULL"); + + for ( j = 0; j < ATM_PORT_NUMBER && j < port_cell->port_num; j++ ) + if ( port_cell->tx_link_rate[j] > 0 ) + break; + for ( i = 0; i < ATM_PORT_NUMBER && i < port_cell->port_num; i++ ) + g_atm_priv_data.port[i].tx_max_cell_rate = port_cell->tx_link_rate[i] > 0 ? port_cell->tx_link_rate[i] : port_cell->tx_link_rate[j]; + + qsb_global_set(); + + for ( i = 0; i < MAX_PVC_NUMBER; i++ ) + if ( g_atm_priv_data.conn[i].vcc != NULL ) + set_qsb(g_atm_priv_data.conn[i].vcc, &g_atm_priv_data.conn[i].vcc->qos, i); + + // TODO: ReTX set xdata_addr + g_xdata_addr = xdata_addr; + + g_showtime = 1; + +#if defined(CONFIG_VR9) + IFX_REG_W32(0x0F, UTP_CFG); +#endif + + pr_debug("enter showtime, cell rate: 0 - %d, 1 - %d, xdata addr: 0x%08x\n", g_atm_priv_data.port[0].tx_max_cell_rate, g_atm_priv_data.port[1].tx_max_cell_rate, (unsigned int)g_xdata_addr); + + return IFX_SUCCESS; +} + +static int atm_showtime_exit(void) +{ +#if defined(CONFIG_VR9) + IFX_REG_W32(0x00, UTP_CFG); +#endif + + g_showtime = 0; + + // TODO: ReTX clean state + g_xdata_addr = NULL; + + pr_debug("leave showtime\n"); + + return IFX_SUCCESS; +} + + + +/* + * #################################### + * Init/Cleanup API + * #################################### + */ + +/* + * Description: + * Initialize global variables, PP32, comunication structures, register IRQ + * and register device. + * Input: + * none + * Output: + * 0 --- successful + * else --- failure, usually it is negative value of error code + */ +static int __devinit ifx_atm_init(void) +{ + int ret; + int port_num; + struct port_cell_info port_cell = {0}; + int i, j; + char ver_str[256]; + +#ifdef MODULE + reset_ppe(); +#endif + + check_parameters(); + + ret = init_priv_data(); + if ( ret != IFX_SUCCESS ) { + err("INIT_PRIV_DATA_FAIL"); + goto INIT_PRIV_DATA_FAIL; + } + + ifx_atm_init_chip(); + init_rx_tables(); + init_tx_tables(); + + /* create devices */ + for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ ) { + g_atm_priv_data.port[port_num].dev = atm_dev_register("ifxmips_atm", &g_ifx_atm_ops, -1, NULL); + if ( !g_atm_priv_data.port[port_num].dev ) { + err("failed to register atm device %d!", port_num); + ret = -EIO; + goto ATM_DEV_REGISTER_FAIL; + } + else { + g_atm_priv_data.port[port_num].dev->ci_range.vpi_bits = 8; + g_atm_priv_data.port[port_num].dev->ci_range.vci_bits = 16; + g_atm_priv_data.port[port_num].dev->link_rate = g_atm_priv_data.port[port_num].tx_max_cell_rate; + g_atm_priv_data.port[port_num].dev->dev_data = (void*)port_num; + } + } + + /* register interrupt handler */ + ret = request_irq(PPE_MAILBOX_IGU1_INT, mailbox_irq_handler, IRQF_DISABLED, "atm_mailbox_isr", &g_atm_priv_data); + if ( ret ) { + if ( ret == -EBUSY ) { + err("IRQ may be occupied by other driver, please reconfig to disable it."); + } + else { + err("request_irq fail"); + } + goto REQUEST_IRQ_PPE_MAILBOX_IGU1_INT_FAIL; + } + disable_irq(PPE_MAILBOX_IGU1_INT); + + ret = ifx_pp32_start(0); + if ( ret ) { + err("ifx_pp32_start fail!"); + goto PP32_START_FAIL; + } + + port_cell.port_num = ATM_PORT_NUMBER; + ifx_mei_atm_showtime_check(&g_showtime, &port_cell, &g_xdata_addr); + if ( g_showtime ) { + for ( i = 0; i < ATM_PORT_NUMBER; i++ ) + if ( port_cell.tx_link_rate[i] != 0 ) + break; + for ( j = 0; j < ATM_PORT_NUMBER; j++ ) + g_atm_priv_data.port[j].tx_max_cell_rate = port_cell.tx_link_rate[j] != 0 ? port_cell.tx_link_rate[j] : port_cell.tx_link_rate[i]; + } + + qsb_global_set(); + validate_oam_htu_entry(); + + /* create proc file */ + proc_file_create(); + + ifx_mei_atm_showtime_enter = atm_showtime_enter; + ifx_mei_atm_showtime_exit = atm_showtime_exit; + + ifx_atm_version(ver_str); + printk(KERN_INFO "%s", ver_str); + + printk("ifxmips_atm: ATM init succeed\n"); + + return IFX_SUCCESS; + +PP32_START_FAIL: + free_irq(PPE_MAILBOX_IGU1_INT, &g_atm_priv_data); +REQUEST_IRQ_PPE_MAILBOX_IGU1_INT_FAIL: +ATM_DEV_REGISTER_FAIL: + while ( port_num-- > 0 ) + atm_dev_deregister(g_atm_priv_data.port[port_num].dev); +INIT_PRIV_DATA_FAIL: + clear_priv_data(); + printk("ifxmips_atm: ATM init failed\n"); + return ret; +} + +/* + * Description: + * Release memory, free IRQ, and deregister device. + * Input: + * none + * Output: + * none + */ +static void __exit ifx_atm_exit(void) +{ + int port_num; + + ifx_mei_atm_showtime_enter = NULL; + ifx_mei_atm_showtime_exit = NULL; + + proc_file_delete(); + + invalidate_oam_htu_entry(); + + ifx_pp32_stop(0); + + free_irq(PPE_MAILBOX_IGU1_INT, &g_atm_priv_data); + + for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ ) + atm_dev_deregister(g_atm_priv_data.port[port_num].dev); + + ifx_atm_uninit_chip(); + + clear_priv_data(); +} + +module_init(ifx_atm_init); +module_exit(ifx_atm_exit); +MODULE_LICENSE("Dual BSD/GPL"); diff --git a/package/ltq-dsl/src/ifxmips_atm_core.h b/package/ltq-dsl/src/ifxmips_atm_core.h new file mode 100644 index 0000000000..8f0a3ebfba --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_core.h @@ -0,0 +1,249 @@ +/****************************************************************************** +** +** FILE NAME : ifxmips_atm_core.h +** PROJECT : UEIP +** MODULES : ATM +** +** DATE : 7 Jul 2009 +** AUTHOR : Xu Liang +** DESCRIPTION : ATM driver header file (core functions) +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 17 JUN 2009 Xu Liang Init Version +*******************************************************************************/ + +#ifndef IFXMIPS_ATM_CORE_H +#define IFXMIPS_ATM_CORE_H + + +#include "ifxmips_compat.h" +#include "ifx_atm.h" +#include "ifxmips_atm_ppe_common.h" +#include "ifxmips_atm_fw_regs_common.h" + + + +/* + * #################################### + * Definition + * #################################### + */ + +/* + * Compile Options + */ + +#define ENABLE_DEBUG 1 + +#define ENABLE_ASSERT 1 + +#define INLINE + +#define DEBUG_DUMP_SKB 1 + +#define DEBUG_QOS 1 + +#define ENABLE_DBG_PROC 1 + +#define ENABLE_FW_PROC 1 + +#ifdef CONFIG_IFX_ATM_TASKLET + #define ENABLE_TASKLET 1 +#endif + + +/* + * Debug/Assert/Error Message + */ + +#define DBG_ENABLE_MASK_ERR (1 << 0) +#define DBG_ENABLE_MASK_DEBUG_PRINT (1 << 1) +#define DBG_ENABLE_MASK_ASSERT (1 << 2) +#define DBG_ENABLE_MASK_DUMP_SKB_RX (1 << 8) +#define DBG_ENABLE_MASK_DUMP_SKB_TX (1 << 9) +#define DBG_ENABLE_MASK_DUMP_QOS (1 << 10) +#define DBG_ENABLE_MASK_DUMP_INIT (1 << 11) +#define DBG_ENABLE_MASK_ALL (DBG_ENABLE_MASK_ERR | DBG_ENABLE_MASK_DEBUG_PRINT | DBG_ENABLE_MASK_ASSERT | DBG_ENABLE_MASK_DUMP_SKB_RX | DBG_ENABLE_MASK_DUMP_SKB_TX | DBG_ENABLE_MASK_DUMP_QOS | DBG_ENABLE_MASK_DUMP_INIT) + +#define err(format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ERR) ) printk(KERN_ERR __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) + +#if defined(ENABLE_DEBUG) && ENABLE_DEBUG + #undef dbg + #define dbg(format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_DEBUG_PRINT) ) printk(KERN_WARNING __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) +#else + #if !defined(dbg) + #define dbg(format, arg...) + #endif +#endif + +#if defined(ENABLE_ASSERT) && ENABLE_ASSERT + #define ASSERT(cond, format, arg...) do { if ( (ifx_atm_dbg_enable & DBG_ENABLE_MASK_ASSERT) && !(cond) ) printk(KERN_ERR __FILE__ ":%d:%s: " format "\n", __LINE__, __FUNCTION__, ##arg); } while ( 0 ) +#else + #define ASSERT(cond, format, arg...) +#endif + + +/* + * Constants + */ +#define DEFAULT_TX_LINK_RATE 3200 // in cells + +/* + * ATM Port, QSB Queue, DMA RX/TX Channel Parameters + */ +#define ATM_PORT_NUMBER 2 +#define MAX_QUEUE_NUMBER 16 +#define OAM_RX_QUEUE 15 +#define QSB_RESERVE_TX_QUEUE 0 +#define FIRST_QSB_QID 1 +#define MAX_PVC_NUMBER (MAX_QUEUE_NUMBER - FIRST_QSB_QID) +#define MAX_RX_DMA_CHANNEL_NUMBER 8 +#define MAX_TX_DMA_CHANNEL_NUMBER 16 +#define DATA_BUFFER_ALIGNMENT EMA_ALIGNMENT +#define DESC_ALIGNMENT 8 +#define DEFAULT_RX_HUNT_BITTH 4 + +/* + * RX DMA Channel Allocation + */ +#define RX_DMA_CH_OAM 0 +#define RX_DMA_CH_AAL 1 +#define RX_DMA_CH_TOTAL 2 +#define RX_DMA_CH_OAM_DESC_LEN 32 +#define RX_DMA_CH_OAM_BUF_SIZE (CELL_SIZE & ~15) +#define RX_DMA_CH_AAL_BUF_SIZE (2048 - 48) + +/* + * OAM Constants + */ +#define OAM_HTU_ENTRY_NUMBER 3 +#define OAM_F4_SEG_HTU_ENTRY 0 +#define OAM_F4_TOT_HTU_ENTRY 1 +#define OAM_F5_HTU_ENTRY 2 +#define OAM_F4_CELL_ID 0 +#define OAM_F5_CELL_ID 15 +//#if defined(ENABLE_ATM_RETX) && ENABLE_ATM_RETX +// #undef OAM_HTU_ENTRY_NUMBER +// #define OAM_HTU_ENTRY_NUMBER 4 +// #define OAM_ARQ_HTU_ENTRY 3 +//#endif + +/* + * RX Frame Definitions + */ +#define MAX_RX_PACKET_ALIGN_BYTES 3 +#define MAX_RX_PACKET_PADDING_BYTES 3 +#define RX_INBAND_TRAILER_LENGTH 8 +#define MAX_RX_FRAME_EXTRA_BYTES (RX_INBAND_TRAILER_LENGTH + MAX_RX_PACKET_ALIGN_BYTES + MAX_RX_PACKET_PADDING_BYTES) + +/* + * TX Frame Definitions + */ +#define MAX_TX_HEADER_ALIGN_BYTES 12 +#define MAX_TX_PACKET_ALIGN_BYTES 3 +#define MAX_TX_PACKET_PADDING_BYTES 3 +#define TX_INBAND_HEADER_LENGTH 8 +#define MAX_TX_FRAME_EXTRA_BYTES (TX_INBAND_HEADER_LENGTH + MAX_TX_HEADER_ALIGN_BYTES + MAX_TX_PACKET_ALIGN_BYTES + MAX_TX_PACKET_PADDING_BYTES) + +/* + * Cell Constant + */ +#define CELL_SIZE ATM_AAL0_SDU + + + +/* + * #################################### + * Data Type + * #################################### + */ + +typedef struct { + unsigned int h; + unsigned int l; +} ppe_u64_t; + +struct port { + unsigned int tx_max_cell_rate; + unsigned int tx_current_cell_rate; + + struct atm_dev *dev; +}; + +struct connection { + struct atm_vcc *vcc; + + volatile struct tx_descriptor + *tx_desc; + unsigned int tx_desc_pos; + struct sk_buff **tx_skb; + + unsigned int aal5_vcc_crc_err; /* number of packets with CRC error */ + unsigned int aal5_vcc_oversize_sdu; /* number of packets with oversize error */ + + unsigned int port; +}; + +struct atm_priv_data { + unsigned long conn_table; + struct connection conn[MAX_PVC_NUMBER]; + + volatile struct rx_descriptor + *aal_desc; + unsigned int aal_desc_pos; + + volatile struct rx_descriptor + *oam_desc; + unsigned char *oam_buf; + unsigned int oam_desc_pos; + + struct port port[ATM_PORT_NUMBER]; + + unsigned int wrx_pdu; /* successfully received AAL5 packet */ + unsigned int wrx_drop_pdu; /* AAL5 packet dropped by driver on RX */ + unsigned int wtx_pdu; /* successfully tranmitted AAL5 packet */ + unsigned int wtx_err_pdu; /* error AAL5 packet */ + unsigned int wtx_drop_pdu; /* AAL5 packet dropped by driver on TX */ + + ppe_u64_t wrx_total_byte; + ppe_u64_t wtx_total_byte; + unsigned int prev_wrx_total_byte; + unsigned int prev_wtx_total_byte; + + void *aal_desc_base; + void *oam_desc_base; + void *oam_buf_base; + void *tx_desc_base; + void *tx_skb_base; +}; + + + +/* + * #################################### + * Declaration + * #################################### + */ + +extern unsigned int ifx_atm_dbg_enable; + +extern void ifx_atm_get_fw_ver(unsigned int *major, unsigned int *minor); + +extern void ifx_atm_init_chip(void); +extern void ifx_atm_uninit_chip(void); + +extern int ifx_pp32_start(int pp32); +extern void ifx_pp32_stop(int pp32); + + + +#endif // IFXMIPS_ATM_CORE_H diff --git a/package/ltq-dsl/src/ifxmips_atm_danube.c b/package/ltq-dsl/src/ifxmips_atm_danube.c new file mode 100644 index 0000000000..5698e0877c --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_danube.c @@ -0,0 +1,271 @@ +/****************************************************************************** +** +** FILE NAME : ifxmips_atm_danube.c +** PROJECT : UEIP +** MODULES : ATM +** +** DATE : 7 Jul 2009 +** AUTHOR : Xu Liang +** DESCRIPTION : ATM driver common source file (core functions) +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 07 JUL 2009 Xu Liang Init Version +*******************************************************************************/ + + + +/* + * #################################### + * Head File + * #################################### + */ + +/* + * Common Head File + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* + * Chip Specific Head File + */ +#include +#include +#include "ifxmips_compat.h" +#include "ifxmips_atm_core.h" +#include "ifxmips_atm_fw_danube.h" + + + +/* + * #################################### + * Definition + * #################################### + */ + +/* + * EMA Settings + */ +#define EMA_CMD_BUF_LEN 0x0040 +#define EMA_CMD_BASE_ADDR (0x00001580 << 2) +#define EMA_DATA_BUF_LEN 0x0100 +#define EMA_DATA_BASE_ADDR (0x00001900 << 2) +#define EMA_WRITE_BURST 0x2 +#define EMA_READ_BURST 0x2 + + + +/* + * #################################### + * Declaration + * #################################### + */ + +/* + * Hardware Init/Uninit Functions + */ +static inline void init_pmu(void); +static inline void uninit_pmu(void); +static inline void init_ema(void); +static inline void init_mailbox(void); +static inline void init_atm_tc(void); +static inline void clear_share_buffer(void); + + + +/* + * #################################### + * Local Variable + * #################################### + */ + + + +/* + * #################################### + * Local Function + * #################################### + */ + +static inline void init_pmu(void) +{ + //*(unsigned long *)0xBF10201C &= ~((1 << 15) | (1 << 13) | (1 << 9)); + PPE_TOP_PMU_SETUP(IFX_PMU_ENABLE); + PPE_SLL01_PMU_SETUP(IFX_PMU_ENABLE); + PPE_TC_PMU_SETUP(IFX_PMU_ENABLE); + PPE_EMA_PMU_SETUP(IFX_PMU_ENABLE); + PPE_QSB_PMU_SETUP(IFX_PMU_ENABLE); + PPE_TPE_PMU_SETUP(IFX_PMU_ENABLE); + DSL_DFE_PMU_SETUP(IFX_PMU_ENABLE); +} + +static inline void uninit_pmu(void) +{ + PPE_SLL01_PMU_SETUP(IFX_PMU_DISABLE); + PPE_TC_PMU_SETUP(IFX_PMU_DISABLE); + PPE_EMA_PMU_SETUP(IFX_PMU_DISABLE); + PPE_QSB_PMU_SETUP(IFX_PMU_DISABLE); + PPE_TPE_PMU_SETUP(IFX_PMU_DISABLE); + DSL_DFE_PMU_SETUP(IFX_PMU_DISABLE); + PPE_TOP_PMU_SETUP(IFX_PMU_DISABLE); +} + +static inline void init_ema(void) +{ + IFX_REG_W32((EMA_CMD_BUF_LEN << 16) | (EMA_CMD_BASE_ADDR >> 2), EMA_CMDCFG); + IFX_REG_W32((EMA_DATA_BUF_LEN << 16) | (EMA_DATA_BASE_ADDR >> 2), EMA_DATACFG); + IFX_REG_W32(0x000000FF, EMA_IER); + IFX_REG_W32(EMA_READ_BURST | (EMA_WRITE_BURST << 2), EMA_CFG); +} + +static inline void init_mailbox(void) +{ + IFX_REG_W32(0xFFFFFFFF, MBOX_IGU1_ISRC); + IFX_REG_W32(0x00000000, MBOX_IGU1_IER); + IFX_REG_W32(0xFFFFFFFF, MBOX_IGU3_ISRC); + IFX_REG_W32(0x00000000, MBOX_IGU3_IER); +} + +static inline void init_atm_tc(void) +{ + // for ReTX expansion in future + //*FFSM_CFG0 = SET_BITS(*FFSM_CFG0, 5, 0, 6); // pnum = 6 + //*FFSM_CFG1 = SET_BITS(*FFSM_CFG1, 5, 0, 6); // pnum = 6 +} + +static inline void clear_share_buffer(void) +{ + volatile u32 *p = SB_RAM0_ADDR(0); + unsigned int i; + + for ( i = 0; i < SB_RAM0_DWLEN + SB_RAM1_DWLEN + SB_RAM2_DWLEN + SB_RAM3_DWLEN; i++ ) + IFX_REG_W32(0, p++); +} + +/* + * Description: + * Download PPE firmware binary code. + * Input: + * src --- u32 *, binary code buffer + * dword_len --- unsigned int, binary code length in DWORD (32-bit) + * Output: + * int --- IFX_SUCCESS: Success + * else: Error Code + */ +static inline int pp32_download_code(u32 *code_src, unsigned int code_dword_len, u32 *data_src, unsigned int data_dword_len) +{ + volatile u32 *dest; + + if ( code_src == 0 || ((unsigned long)code_src & 0x03) != 0 + || data_src == 0 || ((unsigned long)data_src & 0x03) != 0 ) + return IFX_ERROR; + + if ( code_dword_len <= CDM_CODE_MEMORYn_DWLEN(0) ) + IFX_REG_W32(0x00, CDM_CFG); + else + IFX_REG_W32(0x02, CDM_CFG); + + /* copy code */ + dest = CDM_CODE_MEMORY(0, 0); + while ( code_dword_len-- > 0 ) + IFX_REG_W32(*code_src++, dest++); + + /* copy data */ + dest = CDM_DATA_MEMORY(0, 0); + while ( data_dword_len-- > 0 ) + IFX_REG_W32(*data_src++, dest++); + + return IFX_SUCCESS; +} + + + +/* + * #################################### + * Global Function + * #################################### + */ + +extern void ifx_atm_get_fw_ver(unsigned int *major, unsigned int *minor) +{ + ASSERT(major != NULL, "pointer is NULL"); + ASSERT(minor != NULL, "pointer is NULL"); + + *major = ATM_FW_VER_MAJOR; + *minor = ATM_FW_VER_MINOR; +} + +void ifx_atm_init_chip(void) +{ + init_pmu(); + + init_ema(); + + init_mailbox(); + + init_atm_tc(); + + clear_share_buffer(); +} + +void ifx_atm_uninit_chip(void) +{ + uninit_pmu(); +} + +/* + * Description: + * Initialize and start up PP32. + * Input: + * none + * Output: + * int --- IFX_SUCCESS: Success + * else: Error Code + */ +int ifx_pp32_start(int pp32) +{ + int ret; + + /* download firmware */ + ret = pp32_download_code(firmware_binary_code, sizeof(firmware_binary_code) / sizeof(*firmware_binary_code), firmware_binary_data, sizeof(firmware_binary_data) / sizeof(*firmware_binary_data)); + if ( ret != IFX_SUCCESS ) + return ret; + + /* run PP32 */ + IFX_REG_W32(DBG_CTRL_START_SET(1), PP32_DBG_CTRL); + + /* idle for a while to let PP32 init itself */ + udelay(10); + + return IFX_SUCCESS; +} + +/* + * Description: + * Halt PP32. + * Input: + * none + * Output: + * none + */ +void ifx_pp32_stop(int pp32) +{ + /* halt PP32 */ + IFX_REG_W32(DBG_CTRL_STOP_SET(1), PP32_DBG_CTRL); +} diff --git a/package/ltq-dsl/src/ifxmips_atm_fw_danube.h b/package/ltq-dsl/src/ifxmips_atm_fw_danube.h new file mode 100644 index 0000000000..c36c96845c --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_fw_danube.h @@ -0,0 +1,429 @@ +#ifndef IFXMIPS_ATM_FW_DANUBE_H +#define IFXMIPS_ATM_FW_DANUBE_H + + +/****************************************************************************** +** +** FILE NAME : ifxmips_atm_fw_danube.h +** PROJECT : Danube +** MODULES : ATM (ADSL) +** +** DATE : 1 AUG 2005 +** AUTHOR : Xu Liang +** DESCRIPTION : ATM Driver (PP32 Firmware) +** COPYRIGHT : Copyright (c) 2006 +** Infineon Technologies AG +** Am Campeon 1-12, 85579 Neubiberg, Germany +** +** 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. +** +** HISTORY +** $Date $Author $Comment +** 4 AUG 2005 Xu Liang Initiate Version +** 23 OCT 2006 Xu Liang Add GPL header. +*******************************************************************************/ + + +#define ATM_FW_VER_MAJOR 0 +#define ATM_FW_VER_MINOR 1 + + +static unsigned int firmware_binary_code[] = { + 0x800004A0, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x8000FFC8, 0x00000000, 0x00000000, 0x00000000, + 0xC1000002, 0xD90C0000, 0xC2000002, 0xDA080001, 0x80004710, 0xC2000000, 0xDA080001, 0x80003D98, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x80003D50, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x80004F18, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x80003C50, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0xC0400000, 0xC0004840, 0xC8840000, 0x800043D0, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0xC0400002, 0xC0004840, 0xC8840000, 0x80004350, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0xC3C00004, 0xDBC80001, 0xC10C0002, 0xD90C0000, 0x8000FEC8, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0xC10E0002, 0xD90C0000, 0xC0004808, 0xC8400000, 0x80004380, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0xC3E1FFFE, 0x597DFFFE, 0x593DFE14, 0x900004D9, 0x00000000, 0x00000000, 0x00000000, 0x90CC0481, + 0x00000000, 0x00000000, 0x00000000, 0xC3C00000, 0xDBC80001, 0xC1400008, 0xC1900000, 0x71948000, + 0x15000100, 0xC140000A, 0xC1900002, 0x71948000, 0x15000100, 0xC140000C, 0xC1900004, 0x71948000, + 0x15000100, 0xC1400004, 0xC1900006, 0x71948000, 0x15000100, 0xC1400006, 0xC1900008, 0x71948000, + 0x15000100, 0xC140000E, 0xC190000A, 0x71948000, 0x15000100, 0xC1400000, 0xC190000C, 0x71948000, + 0x15000100, 0xC1400002, 0xC190000E, 0x71948000, 0x15000100, 0xC0400000, 0xC11C0000, 0xC000082C, + 0xCD040E08, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0400002, 0xC11C0000, 0xC000082C, 0xCD040E08, + 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0000824, 0x00000000, 0xCBC00001, 0xCB800001, 0xCB400001, + 0xCB000000, 0xC0004878, 0x5BFC4000, 0xCFC00001, 0x5BB84000, 0xCF800001, 0x5B744000, 0xCF400001, + 0x5B304000, 0xCF000000, 0xC0000A10, 0x00000000, 0xCBC00001, 0xCB800000, 0xC0004874, 0x5BFC4000, + 0xCFC00001, 0x5BB84000, 0xCF800000, 0xC30001FE, 0xC000140A, 0xCF000000, 0xC3000000, 0x7F018000, + 0xC000042E, 0xCF000000, 0xC000040E, 0xCF000000, 0xC3C1FFFE, 0xC000490E, 0xCFC00080, 0xC000492C, + 0xCFC00080, 0xC0004924, 0xCFC00040, 0xC0004912, 0xCFC00040, 0xC0004966, 0xCFC00040, 0xC0004968, + 0xCFC00080, 0xC000496A, 0xCFC00080, 0xC3C00000, 0xC2800020, 0xC3000000, 0x7F018000, 0x6FF88000, + 0x6FD44000, 0x4395C000, 0x5BB84A00, 0x5838000A, 0xCF000000, 0x5BFC0002, 0xB7E8FFA8, 0x00000000, + 0xC3C00000, 0xC2800010, 0x6FF86000, 0x47F9C000, 0x5BB84C80, 0xC3400000, 0x58380004, 0xCB420080, + 0x00000000, 0x58380008, 0xCF400080, 0x5BFC0002, 0xB7E8FF90, 0x00000000, 0xC3C00000, 0xC2800020, + 0xC348001E, 0xC3000000, 0x7F018000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, + 0x58380008, 0xCF400420, 0x5838000A, 0xCF000000, 0x5BFC0002, 0xB7E8FF90, 0x00000000, 0x00000000, + 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x80000518, 0x00000000, 0x80002118, 0x00000000, + 0x8000FFC8, 0xC0004958, 0xC8400000, 0x00000000, 0xC3C00002, 0x7BC42000, 0xCC400000, 0xC0004848, + 0xCB840000, 0xC000495C, 0xCAC40000, 0xC0004844, 0xC8840000, 0x46F90000, 0x8400FF6A, 0xC000487C, + 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCA000000, 0xC0001624, 0xCB040000, 0xA63C005A, + 0x00000000, 0x00000000, 0xA71EFF02, 0x00000000, 0xC0000824, 0xCA840000, 0x6CA08000, 0x6CA42000, + 0x46610000, 0x42290000, 0xC35E0002, 0xC6340068, 0xC0001624, 0xCF440080, 0xC2000000, 0xC161FFFE, + 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004844, 0xC8840000, 0xC000082C, 0xCA040040, 0x00000000, + 0x00000000, 0x58880002, 0xB608FFF8, 0x00000000, 0xC0800000, 0xC0004844, 0xCC840040, 0x5AEC0002, + 0xC000495C, 0xCEC40000, 0x5E6C0006, 0x84000048, 0xC0004848, 0xCB840000, 0xC0000838, 0xC2500002, + 0xCE440808, 0x5FB80002, 0xC0004848, 0xCF840000, 0x5EEC0002, 0xC000495C, 0xCEC40000, 0x00000000, + 0xC121FFFE, 0x5911FE14, 0x15000000, 0x8000FD80, 0xC000495A, 0xC8400000, 0x00000000, 0xC3C00002, + 0x7BC42000, 0xCC400000, 0xC0004960, 0xCAC40000, 0x00000000, 0x00000000, 0x5EEC0000, 0x840000F2, + 0x00000000, 0xB6FC0030, 0xC0001600, 0xCA040000, 0x00000000, 0x00000000, 0xA61E00B2, 0x6FE90000, + 0xC0000A28, 0xCE840808, 0xC2C00000, 0xC2800004, 0xB6E80080, 0xC0001604, 0xCA840000, 0xC0004960, + 0xCEC40000, 0xA69EFCA2, 0x00000000, 0x6FE90000, 0xC0000A28, 0xCE840808, 0xC2C00002, 0xC0001600, + 0xCA040000, 0x00000000, 0x00000000, 0xA61E000A, 0x6FE90000, 0xC0000A28, 0xCE840808, 0xC2C00000, + 0xC0001604, 0xCA840000, 0xC0004960, 0xCEC40000, 0xA69EFC0A, 0xC2400000, 0xC0000A14, 0xCA440030, + 0x00000000, 0x00000000, 0x46E52000, 0xA4400000, 0xC2800000, 0xDFEB0031, 0x8000FFF8, 0xDFEA0031, + 0xB668FB82, 0x00000000, 0xC00048A0, 0xCB040000, 0xC0000A10, 0xCA840000, 0x6F208000, 0x6F242000, + 0x46610000, 0x42A10000, 0xC2400000, 0xC0000A14, 0xCA440030, 0xC35E0002, 0xC6340068, 0xC0001604, + 0xCF440080, 0x5B300002, 0xB670FFF8, 0x5AEC0002, 0xC3000000, 0xC00048A0, 0xCF040000, 0xC0004960, + 0xCEC40000, 0x8000FAC0, 0xC0004918, 0xD2800000, 0xC2000000, 0xDF600040, 0x5E600080, 0x8400025A, + 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000480A, 0xCA000000, 0xC0004912, + 0xCA400000, 0xC0004924, 0xCA800000, 0xC0004966, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0x76610000, 0x76A10000, 0x76E10000, 0x840001B2, 0xC0004918, 0xCA400000, 0xC28001FE, + 0x76A10000, 0x5A640002, 0x6A254010, 0x5EE80000, 0x84000002, 0x6AA54000, 0x8000FFF8, 0xC6280000, + 0x62818008, 0xC0004918, 0xCF000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004966, + 0xCA400000, 0xC2000002, 0x6A310000, 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, + 0x5911FE14, 0x15000000, 0x6F346000, 0x4735A000, 0x5B744C80, 0xC2800000, 0x58340006, 0xCA800080, + 0xC2C00000, 0x58340000, 0xCAC000E0, 0xC2400000, 0x5834000A, 0xCA420080, 0x6EA82000, 0x42E9E000, + 0x6F2CA000, 0x42E56000, 0x5AEC1400, 0xC3990040, 0xC7381C20, 0xC6F80068, 0x99005930, 0xDB980000, + 0xDBD80001, 0x00000000, 0xDEA00000, 0x47210000, 0x8400FD68, 0xC0004958, 0xC8400000, 0x00000000, + 0xC3C00002, 0x7BC42000, 0xCC400000, 0xC0004848, 0xCB840000, 0xC0004844, 0xC8840000, 0x5FB80000, + 0x8400F7DA, 0xC0001A1C, 0xCA000000, 0xC2400002, 0x6A452000, 0x76610000, 0x8400F7AA, 0xC000487C, + 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCA000000, 0xC4240000, 0x00000000, 0xA63C17BA, + 0x00000000, 0xC0004878, 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, 0x40100000, 0xCA000000, + 0xC4240000, 0x00000000, 0xC0004934, 0xCE000000, 0xC2800002, 0xC4681C10, 0xC62821D8, 0xC2600010, + 0x5A650040, 0xC0004800, 0xCB400000, 0xC2200400, 0x5A200000, 0xC7601048, 0xC0001220, 0xCE800000, + 0xC0001200, 0xCE400000, 0xC0001202, 0xCE000000, 0xC0001240, 0xCB400000, 0x00000000, 0x00000000, + 0xA754FFC0, 0xC2000000, 0xC7600048, 0xA7520022, 0x00000000, 0x00000000, 0x990060A8, 0xC0004822, + 0xC9400000, 0xC1800002, 0x80001668, 0x58204080, 0xC2000000, 0xCA000020, 0xC2400000, 0xCA414008, + 0xC2800000, 0xCA812008, 0xC2C00000, 0xCAC20020, 0xC0004938, 0xCE000000, 0xC0004920, 0xCE400000, + 0xC0004916, 0xCE800000, 0xC0004922, 0xCEC00000, 0xA6400520, 0x00000000, 0xC0004938, 0xCBC00000, + 0x00000000, 0xC3800000, 0x6FF48000, 0x6FD44000, 0x4355A000, 0x5B744A00, 0x58340000, 0xCB802018, + 0x00000000, 0xC2000000, 0x6FB46000, 0x47B5A000, 0x5B744C80, 0x5834000C, 0xCA000028, 0xC000491A, + 0xCF800000, 0x5E200000, 0x84000452, 0xC2000000, 0xDF610050, 0x5E6001E8, 0x8800FFD0, 0xC2000002, + 0xC2400466, 0xC2A00000, 0x5AA80000, 0xC0001006, 0xCE000000, 0xC0001008, 0xCE400000, 0xC000100A, + 0xCE800000, 0x99005370, 0xC1A0FFFE, 0xC0000824, 0xC9840068, 0xC0004934, 0xCA400000, 0xC2000000, + 0xC2800002, 0x990053B0, 0xDA980000, 0xC6140000, 0xC6580000, 0xC161FFFE, 0x5955FFFE, 0x15400000, + 0x00000000, 0x99005498, 0xC000491A, 0xC9400000, 0x00000000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0xC0004922, 0xCA001120, 0xC3C00000, 0xC3800000, 0xC0004930, 0xCE001120, 0xC0004932, + 0xCBC000E0, 0xC2800000, 0xC000491E, 0xCFC00000, 0xC0004862, 0xCA800068, 0xC3A0001A, 0x5BB94000, + 0xC6B80068, 0xC000491C, 0xCF800000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0x00000000, + 0x00000000, 0x00000000, 0xA8E2FFC8, 0xC2000000, 0xC1220002, 0xD90C0000, 0xDF600040, 0x5E600080, + 0x8400FFDA, 0xC000491C, 0xCA000000, 0xC000491E, 0xCA400000, 0x00000000, 0x00000000, 0x99005930, + 0xDA180000, 0xDA580001, 0x00000000, 0xC2000000, 0xDF610050, 0x5E6001FE, 0x8800FFD0, 0xC0004916, + 0xCA800000, 0xC2C00000, 0xDFEC0050, 0xC2400000, 0x46E52000, 0x84000032, 0x5EA80000, 0x84000022, + 0xC2600002, 0x990060A8, 0xC000482E, 0xC9400000, 0xC1800002, 0x80000018, 0xC2600000, 0x990060A8, + 0xC000482C, 0xC9400000, 0xC1800002, 0xC2000068, 0xC6240080, 0xC0004930, 0xCE400088, 0xC000491A, + 0xC9800000, 0xC0004862, 0xC9400000, 0x6D9C6000, 0x459CE000, 0x59DC4C80, 0x99005790, 0xD9580000, + 0xD9980001, 0xD9D40000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC2000000, 0xDF600040, + 0x5E600080, 0x8400FFD2, 0x00000000, 0xC000491C, 0xCA000000, 0xC000491E, 0xCA400000, 0x00000000, + 0x00000000, 0x99005930, 0xDA180000, 0xDA580001, 0x00000000, 0x800010D0, 0x00000000, 0x990060A8, + 0xC000482A, 0xC9400000, 0xC1800002, 0x800010A0, 0xC0004938, 0xCBC00000, 0x00000000, 0x00000000, + 0x6FF88000, 0x6FD44000, 0x4395C000, 0x5BB84A00, 0x58380008, 0xCA000000, 0x00000000, 0x00000000, + 0xA6000362, 0x00000000, 0xC0004938, 0xCBC00000, 0xC3000000, 0x00000000, 0x6FF88000, 0x6FD44000, + 0x4395C000, 0x5BB84A00, 0x58380000, 0xCB002018, 0xC2000000, 0x58380008, 0xCA020080, 0x5838000C, + 0xCAC00000, 0x5838000E, 0xCA400000, 0xC000491A, 0xCF000000, 0xC0004930, 0xCEC00000, 0xC000493C, + 0xCE000000, 0xC0004932, 0xCE400000, 0x5E200000, 0x84000108, 0xC2800000, 0xA6FE009A, 0x6F206000, + 0x47210000, 0x5A204C80, 0x5820000C, 0xCA800028, 0x00000000, 0x00000000, 0x5EA80000, 0x840001DA, + 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0x99005498, 0xC000491A, 0xC9400000, + 0x00000000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0xC0004930, 0xCAC00000, 0xC0004932, + 0xCA400000, 0xC7EC1120, 0xC0004930, 0xCEC00000, 0x5838000C, 0xCEC00000, 0x58000002, 0xCE400000, + 0xC0004934, 0xCA000000, 0xC2400002, 0x6E642000, 0x6E642000, 0x76252000, 0x84000012, 0xC2400002, + 0x6E684000, 0x58380008, 0xCE800208, 0xA6000000, 0x6E682000, 0x58380008, 0xCE800108, 0xC2400002, + 0x6E642000, 0x76252000, 0x840000D2, 0x58380008, 0xCA000000, 0xC2800000, 0xC2400000, 0xA60200A0, + 0xDBA80000, 0x6F386000, 0x4739C000, 0x5BB84C80, 0x58380004, 0xCA400080, 0x58380002, 0xCA800080, + 0x00000000, 0xDEB80000, 0x46694000, 0x88000048, 0x00000000, 0xC0004824, 0xCA000000, 0xC2400002, + 0x6E640000, 0x5A200002, 0xCE000000, 0x58380008, 0xCE400008, 0x80000000, 0x00000000, 0x80000030, + 0xC0004934, 0xCA000000, 0x00000000, 0x00000000, 0xA6020C4A, 0x00000000, 0x00000000, 0x80000C80, + 0xC2800000, 0xC2000200, 0xC240001A, 0xDF690050, 0x46A14000, 0x46694000, 0x8800FFBA, 0xC2000006, + 0xC2600982, 0x5A643B6E, 0x5838000A, 0xCA800000, 0xC0001006, 0xCE000000, 0xC0001008, 0xCE400000, + 0xC000100A, 0xCE800000, 0x99005370, 0xC1A0FFFE, 0xC0000824, 0xC9840068, 0xC2000000, 0xC0004930, + 0xCA02E010, 0x58380026, 0xCA400000, 0x00000000, 0xC2800000, 0x990053B0, 0xDA980000, 0xC6140000, + 0xC6580000, 0xC0004934, 0xCA000000, 0x00000000, 0x00000000, 0xA6020002, 0x00000000, 0x00000000, + 0x80000300, 0xC0004938, 0xCBC00000, 0xC0004878, 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, + 0x40100000, 0xCA000000, 0xC4240000, 0x00000000, 0x58240018, 0xCA000000, 0x6FF88000, 0x6FD44000, + 0x4395C000, 0x5BB84A00, 0xC3000000, 0xC3400002, 0xC2C00000, 0xC62C0080, 0xC6270040, 0xC0004940, + 0xCE400040, 0xC6260040, 0xC0004942, 0xCE400040, 0xC000493C, 0xCA000000, 0x5EEC0000, 0x84000172, + 0x5A6C0010, 0x46614000, 0x88000178, 0x5A600052, 0x466D4000, 0x88000160, 0x58380006, 0xCA800000, + 0xC0004940, 0xCA000000, 0xC2400000, 0xC6A70040, 0x7E412000, 0x76252000, 0xC2000000, 0xC6A10040, + 0x46610000, 0x84000120, 0xC0004942, 0xCA000000, 0xC2400000, 0xC6A60040, 0x7E412000, 0x76252000, + 0xC2000000, 0xC6A00040, 0x58380002, 0xCA800000, 0x46610000, 0x840000D0, 0xC2400000, 0xC6A60080, + 0x46E50000, 0x880000C2, 0xC2400000, 0xC6A40080, 0x58380008, 0xCA800000, 0x466D0000, 0x880000A2, + 0x00000000, 0xA682FFF8, 0x00000000, 0xC7700B08, 0xA6840078, 0x00000000, 0xC7700A08, 0x80000068, + 0xC7700208, 0xC000493C, 0xCAC00000, 0x80000048, 0xC7700308, 0xC000493C, 0xCAC00000, 0x80000028, + 0xC7700908, 0x80000018, 0xC7700808, 0x80000008, 0xC7700708, 0x8000FFF8, 0xC7700508, 0xC0004944, + 0xCF000000, 0xC000493E, 0xCEC00000, 0xC0004938, 0xCA400000, 0xC000493C, 0xCB800000, 0xC000493E, + 0xCB400000, 0xC3000000, 0x6E608000, 0x6E544000, 0x42150000, 0x5A204A00, 0x5AA00008, 0x58200004, + 0xCB000080, 0xC0004934, 0xCA000000, 0xC2400000, 0xC0004930, 0xCA42E010, 0xC3C00018, 0xA6020078, + 0x00000000, 0x43656000, 0x46F90000, 0x88000038, 0x47AD6000, 0x6EE04010, 0x5BE00004, 0xC2000000, + 0xC6E00010, 0x5E200000, 0x8400002A, 0x5BFC0002, 0x80000018, 0xC3C00004, 0x5A2C0008, 0x46390000, + 0x8800FFFA, 0x5FB80008, 0x6FE04000, 0x42390000, 0x46312000, 0x88000050, 0xC2400000, 0xC0004930, + 0xCA42E010, 0xC2060002, 0xC6800000, 0xCE000308, 0x6FE04000, 0x4631C000, 0x5F700010, 0x4675A000, + 0xC2000000, 0xC6340010, 0xC25A000A, 0xC000491A, 0xCA401C20, 0xC2800000, 0xC0004932, 0xCA8000E0, + 0xC0004862, 0xCA400068, 0x6FA04010, 0x42290000, 0xC000491E, 0xCE000000, 0xC7E41050, 0xC000491C, + 0xCE400000, 0x6FE04000, 0x43A1C000, 0xC000493C, 0xCF800000, 0xC000493E, 0xCF400000, 0xC000493A, + 0xCFC00000, 0x8000FFF0, 0x00000000, 0x00000000, 0x00000000, 0xC2000000, 0xDCE00000, 0xA622FFB8, + 0xC1220002, 0xD90C0000, 0xC0004938, 0xCBC00000, 0xC0004944, 0xCB400000, 0xC0004862, 0xCB000000, + 0xC0004934, 0xCA000000, 0x6FF88000, 0x6FD44000, 0x4395C000, 0x5BB84A00, 0xA6020248, 0xC2400000, + 0x58380008, 0xCA406008, 0xDFE80000, 0xC2218E08, 0x5A21BAF6, 0x46294000, 0x8400000A, 0xC2080002, + 0x7235A000, 0x80000040, 0x5E640000, 0x8400000A, 0xC20C0002, 0x7235A000, 0x80000018, 0xC2000000, + 0xC760E718, 0xC7604220, 0x5E200000, 0x8400025A, 0xC2200002, 0xC0004930, 0xCE001008, 0x990060A8, + 0xC0004828, 0xC9400000, 0xC1800002, 0x58380000, 0xCA000000, 0x00000000, 0x00000000, 0xA6000112, + 0xC0004940, 0xCA800000, 0xC0004942, 0xCA400000, 0xC7600080, 0xC6A01840, 0xC6601040, 0xC000493A, + 0xCA400000, 0xC0004934, 0xCA800000, 0xC0007200, 0x40300000, 0x40240000, 0x5C000004, 0x5EC07400, + 0x8800FFFA, 0x5C000200, 0xCE000000, 0x58000002, 0x5EC07400, 0x8800FFFA, 0x5C000200, 0xCE800000, + 0xC000493E, 0xCA000000, 0xC2400000, 0x5838000C, 0xCE400000, 0x990060A8, 0xC0004830, 0xC9400000, + 0xC6180000, 0xC0004930, 0xC6100080, 0xCD000080, 0x80000090, 0xC2400002, 0x58380008, 0xCE400008, + 0xC0004944, 0xCF400000, 0x80000260, 0xC000493C, 0xCA400000, 0xDFE80000, 0x5A300018, 0xC0007200, + 0x40200000, 0xCA000000, 0x58380008, 0xC6501080, 0xCD001080, 0x5838000A, 0xCE800000, 0x58380026, + 0xCE000000, 0xC0004944, 0xCF400000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0x80000020, + 0x00000000, 0x990060A8, 0xC0004826, 0xC9400000, 0xC1800002, 0x8000FDC0, 0xC2000000, 0xC2400200, + 0xDF600040, 0xB624FFCA, 0xC000491C, 0xCA400000, 0xC000491E, 0xCA800000, 0x99005930, 0xDA580000, + 0xDA980001, 0x00000000, 0xC0004934, 0xCA000000, 0x00000000, 0xC2800000, 0xA6020140, 0xC2400004, + 0xC2000200, 0xDF690050, 0x46A14000, 0x46694000, 0x8800FFC2, 0x00000000, 0xC000491A, 0xC9800000, + 0xC0004862, 0xC9400000, 0x6D9C6000, 0x459CE000, 0x59DC4C80, 0x99005790, 0xD9580000, 0xD9980001, + 0xD9D40000, 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC2000000, 0xC2400200, 0xDF600040, + 0xB624FFCA, 0xC000491C, 0xCA400000, 0xC000491E, 0xCA800000, 0x99005930, 0xDA580000, 0xDA980001, + 0x00000000, 0x58380008, 0xCA400000, 0xC2000000, 0xCE000020, 0xC2A1FFFE, 0x5AA9FFFE, 0xCE001080, + 0x5838000A, 0xCE800000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0000838, 0xC2500002, + 0xCE440808, 0xC0004848, 0xCB840000, 0xC2000000, 0xC000082C, 0xCA040030, 0x5FB80002, 0xC0004848, + 0xCF840000, 0x58880002, 0xB608FFF8, 0x00000000, 0xC0800000, 0xC0004844, 0xCC840000, 0x00000000, + 0xC121FFFE, 0x5911FE14, 0x15000000, 0x8000DEC0, 0xC2000000, 0xDF600040, 0x5E200080, 0x84000252, + 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000480C, 0xCA000000, 0xC0004910, + 0xCA400000, 0xC000492C, 0xCA800000, 0xC0004968, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0x76610000, 0x76A10000, 0x762D6000, 0x840001AA, 0xC0004926, 0xCA400000, 0xC201FFFE, + 0x762D6000, 0x5A640002, 0x6AE50010, 0x5F200000, 0x84000002, 0x6A250000, 0x8000FFF8, 0xC6E00000, + 0x62014008, 0xC0004926, 0xCE800000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0004968, + 0xCA400000, 0xC2000002, 0x6A290000, 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, + 0x5911FE14, 0x15000000, 0x6EB4A000, 0x6E944000, 0x4575A000, 0x46B5A000, 0x5B744E20, 0x58340002, + 0xC2000000, 0xCA0000E0, 0x5834002E, 0xC2400000, 0xCA400080, 0x6EB0A000, 0x6EBC4000, 0x47F18000, + 0x46B18000, 0x5B300E4E, 0x5B300004, 0x6E642000, 0x4225E000, 0xC39A8024, 0xC7380068, 0xC6B81C20, + 0x99005930, 0xDB980000, 0xDBD80001, 0x00000000, 0xC2000000, 0xDF600040, 0x5E200080, 0x8400028A, + 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA000000, 0xC000492A, + 0xCA400000, 0xC000496A, 0xCB000000, 0xC0004956, 0xCAC00000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0x76318000, 0x76718000, 0x840001EA, 0xC201FFFE, 0x76318000, 0x5AEC0002, 0x6B2D0010, + 0x5EA00000, 0x84000002, 0x6A2D0000, 0x8000FFF8, 0xC7200000, 0x62016008, 0xC0004956, 0xCEC00000, + 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000496A, 0xCA400000, 0xC2000002, 0x6A2D0000, + 0x7E010000, 0x76252000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x6EF4A000, + 0x6ED44000, 0x4575A000, 0x46F5A000, 0x5B744E20, 0x5834000E, 0xC2000000, 0xCA0000E0, 0x58340008, + 0xC2400000, 0xCA420080, 0x5834000C, 0xC2800000, 0xCA832018, 0x6E644010, 0x42250000, 0x4229E000, + 0xC39A8008, 0x58340008, 0xCB809020, 0x58340008, 0xC2800000, 0xCA810018, 0x6EE0A000, 0x6EE44000, + 0x46610000, 0x46E10000, 0x5A200008, 0x5A200E28, 0x42290000, 0xC6380068, 0xC6F81C20, 0x99005930, + 0xDB980000, 0xDBD80001, 0x00000000, 0xC000495A, 0xC8400000, 0x00000000, 0xC3C00002, 0x7BC42000, + 0xCC400000, 0xC0001A1C, 0xCA000000, 0xC2400008, 0x6A452000, 0x76610000, 0x8400D91A, 0xC0000A28, + 0xC3800000, 0xCB840030, 0xC0000A14, 0xC3400000, 0xCB440030, 0xC0004880, 0xCB040000, 0xB7B4D8CA, + 0x58041802, 0xCAC00000, 0xA7000018, 0x00000000, 0x00000000, 0xA6C8D898, 0xC2800000, 0xC6E80020, + 0x80000030, 0xC2800000, 0xC7282020, 0xC000490E, 0xCA400000, 0x6BE9E000, 0x00000000, 0x77E52000, + 0x8400D848, 0x6EA0A000, 0x6E944000, 0x45610000, 0x46A10000, 0x5A204E20, 0x5820000C, 0xCA000000, + 0xC0004946, 0xCE800000, 0xA6220348, 0x00000000, 0xC2200060, 0xC0004948, 0xCE000010, 0xCE001040, + 0xC240000A, 0xC000494A, 0xCE400000, 0xC2B60002, 0xC0004964, 0xCE801B08, 0x99005C00, 0xC00048A0, + 0xC8840000, 0x00000000, 0xC0004946, 0xCBC00000, 0x00000000, 0x00000000, 0x6FF8A000, 0x6FD44000, + 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x990059C0, 0xDBD80000, 0xDB980001, 0x00000000, 0x99005708, + 0xC000491C, 0xC1400000, 0xC9420050, 0xC000491C, 0x99005BB8, 0xC9400001, 0xC9800000, 0x00000000, + 0x99005930, 0xD9580000, 0xD9980001, 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, + 0x990055F8, 0xDBD80000, 0xDB980001, 0xC7D80000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, + 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x58380010, 0xCA000000, 0xC0004874, + 0xC8040000, 0x6C908000, 0x44908000, 0x44908000, 0x40100000, 0xCA400000, 0xC4340000, 0x00000000, + 0xC7400000, 0xCE000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, + 0xC2800002, 0x6ABD4000, 0x72A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, + 0x990060A8, 0xC0004836, 0xC9400000, 0xC1800002, 0x00000000, 0x00000000, 0x00000000, 0xA8E2FFC8, + 0x00000000, 0xC1220002, 0xD90C0000, 0xC2000000, 0xC0000A14, 0xCA040030, 0xC0000A28, 0xC2500002, + 0xCE440808, 0x58880002, 0xB608FFF8, 0xC00048A0, 0xC0800000, 0xCC840000, 0x8000D498, 0xC0004946, + 0xCBC00000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, 0xC2800002, + 0x6ABD4000, 0x72A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, 0x6FF8A000, + 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x58380008, 0xCA000000, 0x5838000C, 0xCA400000, + 0xC3400000, 0xC6340008, 0xC000494E, 0xCF400000, 0xC2800000, 0xC62A0080, 0xC3000000, 0xC6308020, + 0x6F304000, 0x43298000, 0xC000493C, 0xCF000000, 0xC2C00000, 0xC66C0080, 0xC0004950, 0xCEC00000, + 0xC2800000, 0xC66AE028, 0xC0004954, 0xCE800000, 0x5F740000, 0x84000188, 0x5E300028, 0x462D2000, + 0x84000152, 0x462D2000, 0x8800011A, 0x5E300018, 0x462D2000, 0x88000012, 0x462D2000, 0x8400002A, + 0x00000000, 0x800000A8, 0x00000000, 0x99005D40, 0xDBD80000, 0xDB980001, 0xC7800000, 0xC3400002, + 0xC000494E, 0xCF400000, 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC000490E, 0xCA400000, + 0xC2800002, 0x6ABD4000, 0x7E814000, 0x76A52000, 0xCE400000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0xC2200060, 0xC0004948, 0xCE001040, 0xC2000000, 0xC000494C, 0xCE000000, 0x80000068, + 0x00000000, 0x99005D40, 0xDBD80000, 0xDB980001, 0xC7800000, 0x99005F40, 0xDBD80000, 0xDB980001, + 0xC7800000, 0xC2200058, 0xC0004948, 0xCE001040, 0xC2000002, 0xC000494C, 0xCE000000, 0xC2000006, + 0xC0001006, 0xCE000000, 0x5838000A, 0xCA400000, 0xC2200982, 0x5A203B6E, 0xC0001008, 0xCE000000, + 0xC000100A, 0xCE400000, 0xC0004954, 0xCA800000, 0xC200000C, 0xC000494A, 0xCE000000, 0xC0004948, + 0xCE800010, 0xC2B60000, 0xC0004964, 0xCE800000, 0x99005C00, 0xC00048A0, 0xC8840000, 0x00000000, + 0xC0004946, 0xCBC00000, 0xC000494C, 0xCA000000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, + 0x5BB84E20, 0x5E200000, 0x840000E2, 0x00000000, 0x990059C0, 0xDBD80000, 0xDB980001, 0x00000000, + 0x99005708, 0xC000491C, 0xC1400000, 0xC9420050, 0xC000491C, 0x99005BB8, 0xC9400001, 0xC9800000, + 0x00000000, 0x99005930, 0xD9580000, 0xD9980001, 0x00000000, 0xC161FFFE, 0x5955FFFE, 0x15400000, + 0x00000000, 0x990055F8, 0xDBD80000, 0xDB980001, 0xC7D80000, 0x00000000, 0xC121FFFE, 0x5911FE14, + 0x15000000, 0xC000493C, 0xCA800000, 0xC000494E, 0xCAC00000, 0xC3000018, 0xC3400006, 0x5E200000, + 0x84000012, 0xC2800000, 0xC2C00000, 0xC300001E, 0xC3400000, 0xC6AC1080, 0xC72C0420, 0xC76C0818, + 0x58380010, 0xCA800000, 0x58380008, 0xCEC00000, 0xC6280108, 0xC0004874, 0xC8040000, 0x6C908000, + 0x44908000, 0x44908000, 0x40100000, 0xCB000000, 0xC4340000, 0x00000000, 0xC7400000, 0xCE800000, + 0xC0004952, 0xCE800000, 0x00000000, 0x00000000, 0x00000000, 0xA8E2FFC8, 0x00000000, 0xC000494C, + 0xCA000000, 0xC0004950, 0xCAC00000, 0x5E200000, 0x84000052, 0xDFE80000, 0x7E814000, 0x5834001A, + 0xCE800000, 0x990060A8, 0xC0004834, 0xC9400000, 0xC1800002, 0x990060A8, 0xC0004838, 0xC9400000, + 0xC6D80000, 0xC1220002, 0xD90C0000, 0x5E200000, 0x84000028, 0x5838002C, 0xCB000000, 0xDFE80000, + 0x00000000, 0x58380014, 0xCF000000, 0x80000000, 0xC2A1FFFE, 0x5AA9FFFE, 0x5838000A, 0xCE800000, + 0xC3000000, 0xC0000A14, 0xCB040030, 0xC2D00002, 0xC0000A28, 0xCEC40808, 0xC000494E, 0xCA800000, + 0x58880002, 0xB4B0FFF8, 0xC00048A0, 0xC0800000, 0xCC840000, 0x5EA80000, 0x8400013A, 0x5E200000, + 0x84000128, 0xC000493C, 0xCA800000, 0x00000000, 0x00000000, 0x5AA80060, 0xCE800000, 0x99005D40, + 0xDBD80000, 0xDB980001, 0xC7800000, 0x99005F40, 0xDBD80000, 0xDB980001, 0xC7800000, 0xC0004952, + 0xCAC00000, 0x58380000, 0xCA800000, 0xC30C0002, 0xC7F00020, 0xA6800078, 0x00000000, 0x00000000, + 0xC161FFFE, 0x5955FFFE, 0x15400000, 0x00000000, 0xC0001800, 0xCA000000, 0x00000000, 0x00000000, + 0xA60CFFCA, 0xC6F00508, 0xC6B0C408, 0xCF000000, 0x00000000, 0xC121FFFE, 0x5911FE14, 0x15000000, + 0x8000CB48, 0xDCBC0001, 0x5FFC0000, 0x8400003A, 0xC3800002, 0xDB880001, 0x5FFC0004, 0x8400C4B2, + 0xC3800000, 0xDB880001, 0xC3CE0002, 0xC0000800, 0xCFC00708, 0xC3E1FFFE, 0x597DFFFE, 0x593DFE14, + 0x94000001, 0x00000000, 0x00000000, 0x00000000, 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, + 0x40080000, 0xCBC00000, 0xC4380000, 0x00000000, 0xC000480E, 0xCA000000, 0xC0004858, 0xCB440000, + 0x00000000, 0x00000000, 0x46350000, 0x88000098, 0x00000000, 0xA7C00028, 0xC0004854, 0xC1000002, + 0xCD040000, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x800000C0, 0x00000000, 0xA7D20118, 0x00000000, + 0xC7E14048, 0xC2400000, 0xC6246030, 0xC200006A, 0x46610000, 0xC6240038, 0xC0000810, 0xCE440038, + 0x8000FF58, 0xC2000000, 0xC0000808, 0xCA040018, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x5A200002, + 0x5E600010, 0x8400FFF8, 0xC2000000, 0xC0000808, 0xCE040018, 0xC3400000, 0x80000010, 0xC1200002, + 0xC0000818, 0xCD041008, 0x5B740002, 0xC0004858, 0xCF440000, 0x99005348, 0xC0004848, 0xC9440000, + 0xC1800000, 0xC11C0002, 0xC000082C, 0xCD040E08, 0x800005C8, 0x5B740002, 0xC0004858, 0xCF440000, + 0xC7800000, 0xC13C0002, 0xCD001E08, 0xC0004848, 0xC9440000, 0xC1800000, 0xC000082C, 0xC9840030, + 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB4980540, 0x00000000, 0xC0800000, 0x80000530, + 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, 0x40080000, 0xCBC00000, 0xC4280000, 0x00000000, + 0xA7C00110, 0xC000484C, 0xCA040000, 0xC2400000, 0xC0001AEC, 0xCA440020, 0x5A200002, 0xC000484C, + 0xCE040000, 0xB624006A, 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC0004848, 0xC9440000, 0xC1800000, + 0xC000082C, 0xC9840030, 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB4980430, 0x00000000, + 0xC0800000, 0x80000420, 0xC0004854, 0xC1000004, 0xCD040000, 0xC0000820, 0xC2000002, 0xCE040000, + 0xC2000000, 0xC000484C, 0xCE040000, 0xC0004858, 0xCE040000, 0x8000FF10, 0xC0004854, 0xC1000000, + 0xCD040000, 0xC11C0000, 0xC000082C, 0xCD040E08, 0x99005348, 0xC0004848, 0xC9440000, 0xC1800000, + 0xC1200000, 0xC0000818, 0xCD041008, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC2000000, 0xC000484C, + 0xCE040000, 0x80000320, 0xC0001AC0, 0xCB840000, 0xC000487C, 0xC8040000, 0x00000000, 0x00000000, + 0x40080000, 0xCBC00000, 0xC4280000, 0x00000000, 0xA780022A, 0x00000000, 0x00000000, 0xA7C001EA, + 0x00000000, 0xC0001B00, 0xC2060006, 0xCE040310, 0xA7E801A2, 0x00000000, 0xC0004850, 0xCA040000, + 0xC2400000, 0xC0001AEC, 0xCA448020, 0x5A200002, 0xC0004850, 0xCE040000, 0xB624008A, 0x00000000, + 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC0001ACC, 0xC2000002, 0xCE040008, 0xC0004848, 0xC9440000, + 0xC1800000, 0xC000082C, 0xC9840030, 0x59540002, 0xC0004848, 0xCD440000, 0x58880002, 0xB49801A8, + 0x00000000, 0xC0800000, 0x80000198, 0xC0004854, 0xC1000000, 0xCD040000, 0xC11C0000, 0xC000082C, + 0xCD040E08, 0x99005348, 0xC0004848, 0xC9440000, 0xC1800000, 0xC2000000, 0xC0000820, 0xCE040000, + 0xC1200000, 0xC0000818, 0xCD041008, 0xC11C0002, 0xC000082C, 0xCD040E08, 0xC0004850, 0xCE040000, + 0xC2000002, 0xC0001ACC, 0xCE040010, 0x800000D0, 0xC2000002, 0xC0004850, 0xCE040000, 0x8000FE70, + 0xC2000000, 0xC0004850, 0xCE040000, 0xA7E60012, 0x00000000, 0xC2000002, 0xC0001B00, 0xCE040008, + 0x8000FE58, 0x00000000, 0xA7860032, 0x00000000, 0xC6800000, 0xC13C0002, 0xCD001E08, 0xC2020002, + 0xC7E2A548, 0xC0001B00, 0xCE040000, 0x8000FE00, 0xC2040002, 0xC0001B00, 0xCE040208, 0x8000FDE0, + 0xC2C80002, 0x6AC56000, 0xDACC0000, 0xC0004854, 0xCB440000, 0xC0004848, 0xCB840000, 0xC0000838, + 0xC3C00000, 0xCBC40030, 0x5EF40004, 0x8400000A, 0xC3000000, 0xC0001ACC, 0xCF040108, 0x47BD8000, + 0x84000012, 0x47BD8000, 0x88000018, 0xC1006E8C, 0x8000B908, 0xC0004840, 0xCC840000, 0x8000F6B8, + 0xC0001AC0, 0xCAC40000, 0xC0004854, 0xCB440000, 0xA6C0FBD2, 0x00000000, 0x5EF40000, 0x8400F712, + 0x5EF40002, 0x8400F9A2, 0x5EF40004, 0x8400FBA2, 0xC1006CE8, 0x8000B880, 0x00000000, 0xC0800000, + 0xDF4B0040, 0xC0004900, 0xCB800000, 0xC2000000, 0xC000490A, 0xA78000B0, 0xCBC00000, 0xC1000000, + 0xD9000001, 0xC1000002, 0xD90C0000, 0x6FF46000, 0x47F5A000, 0x5B744C80, 0xC2400000, 0x58340004, + 0xCA400080, 0xC0004900, 0xCE000008, 0x5A640002, 0x58340004, 0xC6500080, 0xCD000080, 0xC0004914, + 0xCA400000, 0xC2000002, 0x6A3D0000, 0x72252000, 0xCE400000, 0xC0000408, 0xCE000000, 0xA78200B8, + 0xC0004908, 0xCBC00000, 0xC1000000, 0xD9000001, 0xC1000002, 0xD90C0000, 0x6FF4A000, 0x6FD44000, + 0x4575A000, 0x47F5A000, 0x5B744E20, 0xC2800000, 0x58340006, 0xCA800080, 0xC2000000, 0xC0004900, + 0xCE000108, 0x5EA80002, 0x58340006, 0xC6900080, 0xCD000080, 0x5A7C0020, 0xC2000002, 0x6A250000, + 0xC0000408, 0xCE000000, 0xDCA80001, 0x5EA80000, 0x8400B6F0, 0x00000000, 0xA4800210, 0x00000000, + 0xC3C00000, 0xC000140E, 0xCBC00020, 0xC3400000, 0xC2400000, 0x6FF86000, 0x47F9C000, 0x5BB84C80, + 0x58380008, 0xCB400080, 0x58380006, 0xCA400080, 0x5F740002, 0x58380008, 0xC7500080, 0xCD000080, + 0xC2000000, 0x58380004, 0xCA020080, 0xC3000000, 0x5838000C, 0xCB000028, 0x5A640002, 0x46250000, + 0x8400FFF8, 0xC2400000, 0x58380006, 0xC6500080, 0xCD000080, 0xC2000000, 0x5838000A, 0xCA020080, + 0x5B300002, 0x5838000C, 0xC7100028, 0xCD000028, 0xC2420020, 0x5A200004, 0x46612000, 0x8400FFF8, + 0xC2000000, 0x5838000A, 0xC6101080, 0xCD001080, 0xC0004966, 0xCA400000, 0xC2000002, 0x6A3D0000, + 0x72252000, 0xCE400000, 0x5F740000, 0x84000028, 0xC0004912, 0xCA000000, 0xC2C00002, 0x6AFD6000, + 0x7EC16000, 0x76E10000, 0xCE000000, 0x5F300020, 0x84000028, 0xC0004924, 0xCA000000, 0xC2C00002, + 0x6AFD6000, 0x7EC16000, 0x76E10000, 0xCE000000, 0xA4820050, 0xC2400000, 0xC000140E, 0xCA408020, + 0xC2000002, 0xC0004900, 0xCE000008, 0xC000490A, 0xCE400000, 0xC1000000, 0xD9000001, 0xD8400080, + 0xC1000004, 0xD9000001, 0xA4840288, 0x00000000, 0xC3C00000, 0xC000140E, 0xCBC10020, 0xC2800000, + 0xC2000000, 0x6FF8A000, 0x6FD44000, 0x4579C000, 0x47F9C000, 0x5BB84E20, 0x5838002E, 0xCA800080, + 0x58380006, 0xCA020080, 0xC3400000, 0x5838002E, 0xCB420080, 0x5AA80002, 0x46290000, 0x8400FFF8, + 0xC2800000, 0x5838002E, 0xC6900080, 0xCD000080, 0x5F740002, 0x5838002E, 0xC7501080, 0xCD001080, + 0xC0004968, 0xCA400000, 0xC2000002, 0x6A3D0000, 0x72252000, 0xCE400000, 0xC000492A, 0xCA800000, + 0x5E740000, 0x84000028, 0xC0004910, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x7EC16000, 0x76E10000, + 0xCE000000, 0x6ABD4010, 0xA68000D2, 0x00000000, 0xC0004910, 0xCA000000, 0xC2C00002, 0x6AFD6000, + 0x7EC16000, 0x76E10000, 0xCE000000, 0x58380032, 0xCA000000, 0x58000002, 0xCA400000, 0x5838000C, + 0x00000000, 0xCE000001, 0xCE400000, 0xC000492A, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x72E10000, + 0xCE000000, 0xC000492C, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x72E10000, 0xCE000000, 0x80000028, + 0xC000492C, 0xCA000000, 0xC2C00002, 0x6AFD6000, 0x7EC16000, 0x76E10000, 0xCE000000, 0xA4880100, + 0xC2C00000, 0xC000140E, 0xCAC20020, 0xC000490E, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x7E010000, + 0x76252000, 0xCE400000, 0xC000496A, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x72252000, 0xCE400000, + 0x6EF0A000, 0x6ED44000, 0x45718000, 0x46F18000, 0x5B304E20, 0x58300000, 0xCA000000, 0x00000000, + 0xC2400002, 0x76252000, 0x84000032, 0xC24C0002, 0xC6E40020, 0xC624C408, 0x58300010, 0xCA400508, + 0x00000000, 0xC0001800, 0xCE400000, 0xA4860050, 0xC2400000, 0xC000140E, 0xCA418020, 0xC2020002, + 0xC0004900, 0xCE000108, 0xC0004908, 0xCE400000, 0xC1000000, 0xD9000001, 0xD8400080, 0xC1000004, + 0xD9000001, 0xC0001408, 0xCC800000, 0xC10E0002, 0xD90C0000, 0x8000EDA8, 0xDFBC0001, 0xC000496E, + 0x99006050, 0xC9400000, 0xC7D80000, 0x00000000, 0xC5700000, 0x5EF00020, 0x88000130, 0x6F346000, + 0x4735A000, 0x5B744C80, 0x58340008, 0xC2400000, 0xCA400080, 0x00000000, 0xC2000000, 0x5A640002, + 0xCE400080, 0x58340004, 0xCA000080, 0x00000000, 0x00000000, 0x5E200002, 0xCE000080, 0xC0004912, + 0xCA800000, 0xC2400002, 0x6A712000, 0x72694000, 0xCE800000, 0x5E200000, 0x8400003A, 0xC000480A, + 0xCA000000, 0xC0000408, 0xCA800000, 0x76610000, 0x00000000, 0x72294000, 0xCE800000, 0x80000020, + 0xC0004914, 0xCA000000, 0x7E412000, 0x00000000, 0x76610000, 0xCE000000, 0x800000B8, 0x6EF4A000, + 0x6ED44000, 0x4575A000, 0x46F5A000, 0x5B744E20, 0x5834002E, 0xC2400000, 0xCA420080, 0x00000000, + 0xC2000000, 0x5A640002, 0xC6501080, 0xCD001080, 0x58340006, 0xCA000080, 0x00000000, 0x00000000, + 0x5A200002, 0xCE000080, 0xC0004910, 0xCA400000, 0xC2000002, 0x6A2D0000, 0x72252000, 0xCE400000, + 0xC2000002, 0x6A310000, 0xC000042A, 0xCE000000, 0xC1040002, 0xD90C0000, 0x00000000, 0x8000EB18, + 0x00000000, 0xC4980930, 0x9D000000, 0xC5580030, 0xC0000838, 0xCD840000, 0xC1440200, 0xC1C03200, + 0xC55C1078, 0xC000100E, 0x9D000000, 0xCD800000, 0xC000100C, 0xCDC00000, 0xC0004862, 0xC9C00000, + 0x00000000, 0x00000000, 0xD9D80001, 0xC0007200, 0x401C0000, 0x5DC07400, 0x8800FFFA, 0x5C000200, + 0xCD800000, 0xC1F0000A, 0x71D4A000, 0xDD980000, 0xDD9C0001, 0x41D8E000, 0xC5D40268, 0xC0001010, + 0xCD400000, 0x6C9C8000, 0x449CE000, 0x449CE000, 0x59DC0004, 0xC1601260, 0xC5D40268, 0x9D000000, + 0xC0001012, 0xCD400000, 0x00000000, 0x00000000, 0xD9580000, 0x6D586000, 0x4558C000, 0x59984C80, + 0xD9980001, 0x5818000A, 0xC1800000, 0xC9800080, 0xC0005400, 0x6D5CA000, 0x401C0000, 0x40180000, + 0xC9400000, 0x58000002, 0x00000000, 0xC9C00000, 0xC0004930, 0xCD400000, 0xC0004932, 0xCDC00000, + 0x59980004, 0xC1C20020, 0xB59CFFF8, 0x00000000, 0xC1800000, 0xDD9C0001, 0x581C000A, 0xCD800080, + 0x581C000C, 0xC1800000, 0xC9800028, 0xC1C00002, 0xDD940000, 0x69D4E000, 0x5D980002, 0xCD800028, + 0xC0004924, 0xC9800000, 0x00000000, 0x9D000000, 0x00000000, 0x71D8C000, 0xCD800000, 0xC000492A, + 0xC9400000, 0xC1C00002, 0x69D8E000, 0x7DC0C000, 0x7594A000, 0xCD400000, 0xC000492C, 0xC9400000, + 0xDD800001, 0x58000032, 0x75D4A000, 0x84000078, 0xC9400001, 0xC9800000, 0xDD800001, 0x5800000C, + 0x00000000, 0xCD400001, 0xCD800000, 0xC000492C, 0xC9400000, 0xC000492A, 0xC9800000, 0x71D4A000, + 0xC000492C, 0xCD400000, 0x71D8C000, 0xC000492A, 0xCD800000, 0x9D000000, 0x00000000, 0x00000000, + 0x00000000, 0xC0004862, 0xC9800000, 0x00000000, 0xC1C00200, 0x4194C000, 0x45D8E000, 0x8800FFFA, + 0xC5D80000, 0xC0004862, 0xCD800000, 0xC0001406, 0xC9800000, 0xC1C00002, 0x9D000000, 0xC5D80A08, + 0xC5581050, 0xCD800000, 0xC0004930, 0xC9800000, 0xC0004932, 0xC9C00000, 0xC140000E, 0xC5581C20, + 0xDD940000, 0xC0007200, 0x40140000, 0x5D407400, 0x8800FFFA, 0x5C000200, 0xCD800000, 0x58000002, + 0x5D407400, 0x8800FFFA, 0x5C000200, 0xCDC00000, 0xDD540000, 0xC1C00000, 0x58140006, 0xC9C20080, + 0xC1800000, 0x58140000, 0xC98000E0, 0x6DDC2000, 0xC000491E, 0x41D8E000, 0xCDC00000, 0xDD980000, + 0xC1C00022, 0xC5D80D78, 0xDD940001, 0xC5581C20, 0xC000491C, 0xCD800000, 0xDD540000, 0xC1C00000, + 0x58140006, 0xC9C20080, 0xC1800000, 0x58140004, 0xC9820080, 0x00000000, 0x59DC0002, 0x459CC000, + 0x8400FFF8, 0xC1C00000, 0x9D000000, 0x58140006, 0xC5D81080, 0xCD801080, 0xC0004860, 0xC9400000, + 0xC1800100, 0xC1D00002, 0x58146B00, 0xD5800000, 0x58000002, 0xD5800001, 0x59540004, 0xB558FFF8, + 0xC0004860, 0xC1400000, 0xCD400000, 0xDD980001, 0x9D000000, 0xDD940000, 0xC0001404, 0xCDC00808, + 0xC1C00000, 0xC1800200, 0x5D980004, 0xDF5D0050, 0x45D8A000, 0x8800FFDA, 0xDD800001, 0x5800000C, + 0x00000000, 0xC9400001, 0xC9800000, 0xC1C00002, 0xC5D43F08, 0xC5D81E08, 0xC0004862, 0xC9C00000, + 0x00000000, 0x00000000, 0x581C7200, 0x5DC07400, 0x8800FFFA, 0x5C000200, 0xCD400000, 0x58000002, + 0x5DC07400, 0x8800FFFA, 0x5C000200, 0xCD800000, 0xC0004862, 0xC9C00000, 0x00000000, 0xC15004C0, + 0xC5D40068, 0xDD9C0000, 0xC5D41C20, 0xC1C00000, 0xDD800001, 0x58000030, 0xC9C00080, 0xDD800001, + 0x58000002, 0xC9800000, 0x6DDC2000, 0xC000491C, 0x41D8E000, 0xCD400001, 0xCDC00000, 0xDD940001, + 0xC1C00000, 0x58140030, 0xC9C00080, 0xC1800000, 0x58140006, 0xC9820080, 0x00000000, 0x59DC0002, + 0x459CC000, 0x8400FFF8, 0xC1C00000, 0x9D000000, 0x58140030, 0xC5D80080, 0xCD800080, 0xC1C00000, + 0xDF5C0040, 0x5DDC0080, 0x8400FFD2, 0x00000000, 0x9D000000, 0x00000000, 0x00000000, 0x00000000, + 0xC160FFFE, 0xC0000A10, 0xC9440068, 0xC1A0FFFE, 0x59980E28, 0xC000100C, 0xCD400000, 0xC000100E, + 0xCD800000, 0xC0004964, 0xC9800000, 0x00000000, 0xC170000A, 0x7194A000, 0x6C988000, 0x4498C000, + 0x4498C000, 0x59980004, 0xC5940278, 0xC0001010, 0xCD400000, 0xC0004946, 0xC9400000, 0x00000000, + 0x00000000, 0x6D58A000, 0x6D5C4000, 0x45D8C000, 0x4558C000, 0xC000494A, 0xC9400000, 0xC0004948, + 0xC9C00000, 0x4194C000, 0xC1400012, 0xC55C1820, 0x9D000000, 0xC59C0270, 0xC0001012, 0xCDC00000, + 0xC1400000, 0x58000012, 0xC9410040, 0xC0004950, 0xC9C00000, 0xC5580000, 0xC5940840, 0xC5581080, + 0xD9940000, 0xC000493C, 0xC9400000, 0xC0004954, 0xC9800000, 0x59DC00A8, 0x455CE000, 0x41D8E000, + 0x5D5C0030, 0x8800FFF8, 0xC1C00030, 0xC1800000, 0xC5D84030, 0xC1400000, 0xC5D40010, 0x5DD40002, + 0x8400005A, 0x5DD40004, 0x84000082, 0x5DD40006, 0x840000AA, 0x5DD80026, 0x840000D2, 0xDD540000, + 0xDD800001, 0x58000008, 0x40180000, 0xCD400000, 0x59980002, 0x8000FFA8, 0xDD540000, 0xDD800001, + 0x58000008, 0x40180000, 0xCD4000C0, 0x59980002, 0x8000FF70, 0xDD540000, 0xDD800001, 0x58000008, + 0x40180000, 0xCD400080, 0x59980002, 0x8000FF38, 0xDD540000, 0xDD800001, 0x58000008, 0x40180000, + 0xCD400040, 0x59980002, 0x8000FF00, 0x00000000, 0x9D000000, 0x00000000, 0x00000000, 0x00000000, + 0x58000012, 0xC9400000, 0xC0004954, 0xC9C00000, 0xC0004950, 0xC9400080, 0xDD800001, 0x58000028, + 0x5D9C0000, 0x8400003A, 0x5D9C0002, 0x8400003A, 0x5D9C0004, 0x84000052, 0xC55B0040, 0xC55C08C0, + 0xCD800041, 0xCDC008C0, 0x80000048, 0xCD400000, 0x80000038, 0xC55900C0, 0xC55C1840, 0xCD8000C1, + 0xCDC01840, 0x80000010, 0xC55A0080, 0xC55C1080, 0xCD800081, 0xCDC01080, 0x9D000000, 0x00000000, + 0x00000000, 0x00000000, 0x59540002, 0x6994E018, 0x61C0C008, 0x4194A000, 0x5D940040, 0x8800FFFA, + 0xC5940000, 0x9D000000, 0xCD400000, 0x00000000, 0x00000000, 0x9D000000, 0x4158A000, 0xCD400000, + 0x00000000, +}; + +static unsigned int firmware_binary_data[] = { +}; + + +#endif // IFXMIPS_ATM_FW_DANUBE_H diff --git a/package/ltq-dsl/src/ifxmips_atm_fw_regs_common.h b/package/ltq-dsl/src/ifxmips_atm_fw_regs_common.h new file mode 100644 index 0000000000..a5f59b8c40 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_fw_regs_common.h @@ -0,0 +1,364 @@ +#ifndef IFXMIPS_ATM_FW_REGS_COMMON_H +#define IFXMIPS_ATM_FW_REGS_COMMON_H + + + +#if defined(CONFIG_DANUBE) + #include "ifxmips_atm_fw_regs_danube.h" +#elif defined(CONFIG_AMAZON_SE) + #include "ifxmips_atm_fw_regs_amazon_se.h" +#elif defined(CONFIG_AR9) + #include "ifxmips_atm_fw_regs_ar9.h" +#elif defined(CONFIG_VR9) + #include "ifxmips_atm_fw_regs_vr9.h" +#else + #error Platform is not specified! +#endif + + + +/* + * PPE ATM Cell Header + */ +#if defined(__BIG_ENDIAN) + struct uni_cell_header { + unsigned int gfc :4; + unsigned int vpi :8; + unsigned int vci :16; + unsigned int pti :3; + unsigned int clp :1; + }; +#else + struct uni_cell_header { + unsigned int clp :1; + unsigned int pti :3; + unsigned int vci :16; + unsigned int vpi :8; + unsigned int gfc :4; + }; +#endif // defined(__BIG_ENDIAN) + +/* + * Inband Header and Trailer + */ +#if defined(__BIG_ENDIAN) + struct rx_inband_trailer { + /* 0 - 3h */ + unsigned int uu :8; + unsigned int cpi :8; + unsigned int stw_res1:4; + unsigned int stw_clp :1; + unsigned int stw_ec :1; + unsigned int stw_uu :1; + unsigned int stw_cpi :1; + unsigned int stw_ovz :1; + unsigned int stw_mfl :1; + unsigned int stw_usz :1; + unsigned int stw_crc :1; + unsigned int stw_il :1; + unsigned int stw_ra :1; + unsigned int stw_res2:2; + /* 4 - 7h */ + unsigned int gfc :4; + unsigned int vpi :8; + unsigned int vci :16; + unsigned int pti :3; + unsigned int clp :1; + }; + + struct tx_inband_header { + /* 0 - 3h */ + unsigned int gfc :4; + unsigned int vpi :8; + unsigned int vci :16; + unsigned int pti :3; + unsigned int clp :1; + /* 4 - 7h */ + unsigned int uu :8; + unsigned int cpi :8; + unsigned int pad :8; + unsigned int res1 :8; + }; +#else + struct rx_inband_trailer { + /* 0 - 3h */ + unsigned int stw_res2:2; + unsigned int stw_ra :1; + unsigned int stw_il :1; + unsigned int stw_crc :1; + unsigned int stw_usz :1; + unsigned int stw_mfl :1; + unsigned int stw_ovz :1; + unsigned int stw_cpi :1; + unsigned int stw_uu :1; + unsigned int stw_ec :1; + unsigned int stw_clp :1; + unsigned int stw_res1:4; + unsigned int cpi :8; + unsigned int uu :8; + /* 4 - 7h */ + unsigned int clp :1; + unsigned int pti :3; + unsigned int vci :16; + unsigned int vpi :8; + unsigned int gfc :4; + }; + + struct tx_inband_header { + /* 0 - 3h */ + unsigned int clp :1; + unsigned int pti :3; + unsigned int vci :16; + unsigned int vpi :8; + unsigned int gfc :4; + /* 4 - 7h */ + unsigned int res1 :8; + unsigned int pad :8; + unsigned int cpi :8; + unsigned int uu :8; + }; +#endif // defined(__BIG_ENDIAN) + +/* + * MIB Table Maintained by Firmware + */ +struct wan_mib_table { + u32 res1; + u32 wrx_drophtu_cell; + u32 wrx_dropdes_pdu; + u32 wrx_correct_pdu; + u32 wrx_err_pdu; + u32 wrx_dropdes_cell; + u32 wrx_correct_cell; + u32 wrx_err_cell; + u32 wrx_total_byte; + u32 res2; + u32 wtx_total_pdu; + u32 wtx_total_cell; + u32 wtx_total_byte; +}; + +/* + * Host-PPE Communication Data Structure + */ + +#if defined(__BIG_ENDIAN) + struct wrx_queue_config { + /* 0h */ + unsigned int res2 :27; + unsigned int dmach :4; + unsigned int errdp :1; + /* 1h */ + unsigned int oversize :16; + unsigned int undersize :16; + /* 2h */ + unsigned int res1 :16; + unsigned int mfs :16; + /* 3h */ + unsigned int uumask :8; + unsigned int cpimask :8; + unsigned int uuexp :8; + unsigned int cpiexp :8; + }; + + struct wtx_port_config { + unsigned int res1 :27; + unsigned int qid :4; + unsigned int qsben :1; + }; + + struct wtx_queue_config { + unsigned int res1 :25; + unsigned int sbid :1; + unsigned int res2 :3; + unsigned int type :2; + unsigned int qsben :1; + }; + + struct wrx_dma_channel_config { + /* 0h */ + unsigned int res1 :1; + unsigned int mode :2; + unsigned int rlcfg :1; + unsigned int desba :28; + /* 1h */ + unsigned int chrl :16; + unsigned int clp1th :16; + /* 2h */ + unsigned int deslen :16; + unsigned int vlddes :16; + }; + + struct wtx_dma_channel_config { + /* 0h */ + unsigned int res2 :1; + unsigned int mode :2; + unsigned int res3 :1; + unsigned int desba :28; + /* 1h */ + unsigned int res1 :32; + /* 2h */ + unsigned int deslen :16; + unsigned int vlddes :16; + }; + + struct htu_entry { + unsigned int res1 :1; + unsigned int clp :1; + unsigned int pid :2; + unsigned int vpi :8; + unsigned int vci :16; + unsigned int pti :3; + unsigned int vld :1; + }; + + struct htu_mask { + unsigned int set :1; + unsigned int clp :1; + unsigned int pid_mask :2; + unsigned int vpi_mask :8; + unsigned int vci_mask :16; + unsigned int pti_mask :3; + unsigned int clear :1; + }; + + struct htu_result { + unsigned int res1 :12; + unsigned int cellid :4; + unsigned int res2 :5; + unsigned int type :1; + unsigned int ven :1; + unsigned int res3 :5; + unsigned int qid :4; + }; + + struct rx_descriptor { + /* 0 - 3h */ + unsigned int own :1; + unsigned int c :1; + unsigned int sop :1; + unsigned int eop :1; + unsigned int res1 :3; + unsigned int byteoff :2; + unsigned int res2 :2; + unsigned int id :4; + unsigned int err :1; + unsigned int datalen :16; + /* 4 - 7h */ + unsigned int res3 :4; + unsigned int dataptr :28; + }; + + struct tx_descriptor { + /* 0 - 3h */ + unsigned int own :1; + unsigned int c :1; + unsigned int sop :1; + unsigned int eop :1; + unsigned int byteoff :5; + unsigned int res1 :5; + unsigned int iscell :1; + unsigned int clp :1; + unsigned int datalen :16; + /* 4 - 7h */ + unsigned int res2 :4; + unsigned int dataptr :28; + }; +#else + struct wrx_queue_config { + /* 0h */ + unsigned int errdp :1; + unsigned int dmach :4; + unsigned int res2 :27; + /* 1h */ + unsigned int undersize :16; + unsigned int oversize :16; + /* 2h */ + unsigned int mfs :16; + unsigned int res1 :16; + /* 3h */ + unsigned int cpiexp :8; + unsigned int uuexp :8; + unsigned int cpimask :8; + unsigned int uumask :8; + }; + + struct wtx_port_config { + unsigned int qsben :1; + unsigned int qid :4; + unsigned int res1 :27; + }; + + struct wtx_queue_config { + unsigned int qsben :1; + unsigned int type :2; + unsigned int res2 :3; + unsigned int sbid :1; + unsigned int res1 :25; + }; + + struct wrx_dma_channel_config + { + /* 0h */ + unsigned int desba :28; + unsigned int rlcfg :1; + unsigned int mode :2; + unsigned int res1 :1; + /* 1h */ + unsigned int clp1th :16; + unsigned int chrl :16; + /* 2h */ + unsigned int vlddes :16; + unsigned int deslen :16; + }; + + struct wtx_dma_channel_config { + /* 0h */ + unsigned int desba :28; + unsigned int res3 :1; + unsigned int mode :2; + unsigned int res2 :1; + /* 1h */ + unsigned int res1 :32; + /* 2h */ + unsigned int vlddes :16; + unsigned int deslen :16; + }; + + struct rx_descriptor { + /* 4 - 7h */ + unsigned int dataptr :28; + unsigned int res3 :4; + /* 0 - 3h */ + unsigned int datalen :16; + unsigned int err :1; + unsigned int id :4; + unsigned int res2 :2; + unsigned int byteoff :2; + unsigned int res1 :3; + unsigned int eop :1; + unsigned int sop :1; + unsigned int c :1; + unsigned int own :1; + }; + + struct tx_descriptor { + /* 4 - 7h */ + unsigned int dataptr :28; + unsigned int res2 :4; + /* 0 - 3h */ + unsigned int datalen :16; + unsigned int clp :1; + unsigned int iscell :1; + unsigned int res1 :5; + unsigned int byteoff :5; + unsigned int eop :1; + unsigned int sop :1; + unsigned int c :1; + unsigned int own :1; + }; +#endif // defined(__BIG_ENDIAN) + + + +#endif // IFXMIPS_ATM_FW_REGS_COMMON_H diff --git a/package/ltq-dsl/src/ifxmips_atm_fw_regs_danube.h b/package/ltq-dsl/src/ifxmips_atm_fw_regs_danube.h new file mode 100644 index 0000000000..c0dfc6a2e0 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_fw_regs_danube.h @@ -0,0 +1,30 @@ +#ifndef IFXMIPS_ATM_FW_REGS_DANUBE_H +#define IFXMIPS_ATM_FW_REGS_DANUBE_H + + + +/* + * Host-PPE Communication Data Address Mapping + */ +#define FW_VER_ID SB_BUFFER(0x2001) +#define CFG_WRX_HTUTS SB_BUFFER(0x2400) /* WAN RX HTU Table Size, must be configured before enable PPE firmware. */ +#define CFG_WRX_QNUM SB_BUFFER(0x2401) /* WAN RX Queue Number */ +#define CFG_WRX_DCHNUM SB_BUFFER(0x2402) /* WAN RX DMA Channel Number, no more than 8, must be configured before enable PPE firmware. */ +#define CFG_WTX_DCHNUM SB_BUFFER(0x2403) /* WAN TX DMA Channel Number, no more than 16, must be configured before enable PPE firmware. */ +#define CFG_WRDES_DELAY SB_BUFFER(0x2404) /* WAN Descriptor Write Delay, must be configured before enable PPE firmware. */ +#define WRX_DMACH_ON SB_BUFFER(0x2405) /* WAN RX DMA Channel Enable, must be configured before enable PPE firmware. */ +#define WTX_DMACH_ON SB_BUFFER(0x2406) /* WAN TX DMA Channel Enable, must be configured before enable PPE firmware. */ +#define WRX_HUNT_BITTH SB_BUFFER(0x2407) /* WAN RX HUNT Threshold, must be between 2 to 8. */ +#define WRX_QUEUE_CONFIG(i) ((struct wrx_queue_config*) SB_BUFFER(0x2500 + (i) * 20)) +#define WRX_DMA_CHANNEL_CONFIG(i) ((struct wrx_dma_channel_config*) SB_BUFFER(0x2640 + (i) * 7)) +#define WTX_PORT_CONFIG(i) ((struct wtx_port_config*) SB_BUFFER(0x2440 + (i))) +#define WTX_QUEUE_CONFIG(i) ((struct wtx_queue_config*) SB_BUFFER(0x2710 + (i) * 27)) +#define WTX_DMA_CHANNEL_CONFIG(i) ((struct wtx_dma_channel_config*) SB_BUFFER(0x2711 + (i) * 27)) +#define WAN_MIB_TABLE ((struct wan_mib_table*) SB_BUFFER(0x2410)) +#define HTU_ENTRY(i) ((struct htu_entry*) SB_BUFFER(0x2000 + (i))) +#define HTU_MASK(i) ((struct htu_mask*) SB_BUFFER(0x2020 + (i))) +#define HTU_RESULT(i) ((struct htu_result*) SB_BUFFER(0x2040 + (i))) + + + +#endif // IFXMIPS_ATM_FW_REGS_DANUBE_H diff --git a/package/ltq-dsl/src/ifxmips_atm_ppe_common.h b/package/ltq-dsl/src/ifxmips_atm_ppe_common.h new file mode 100644 index 0000000000..c922276dfb --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_ppe_common.h @@ -0,0 +1,231 @@ +#ifndef IFXMIPS_ATM_PPE_COMMON_H +#define IFXMIPS_ATM_PPE_COMMON_H + +#if defined(CONFIG_LANTIQ) + #include "ifxmips_atm_ppe_danube.h" + #define CONFIG_DANUBE +#elif defined(CONFIG_DANUBE) + #include "ifxmips_atm_ppe_danube.h" +#elif defined(CONFIG_AMAZON_SE) + #include "ifxmips_atm_ppe_amazon_se.h" +#elif defined(CONFIG_AR9) + #include "ifxmips_atm_ppe_ar9.h" +#elif defined(CONFIG_VR9) + #include "ifxmips_atm_ppe_vr9.h" +#else + #error Platform is not specified! +#endif + + +/* + * Code/Data Memory (CDM) Interface Configuration Register + */ +#define CDM_CFG PPE_REG_ADDR(0x0100) + +#define CDM_CFG_RAM1 GET_BITS(*CDM_CFG, 3, 2) +#define CDM_CFG_RAM0 (*CDM_CFG & (1 << 1)) + +#define CDM_CFG_RAM1_SET(value) SET_BITS(0, 3, 2, value) +#define CDM_CFG_RAM0_SET(value) ((value) ? (1 << 1) : 0) + +/* + * QSB Internal Cell Delay Variation Register + */ +#define QSB_ICDV QSB_CONF_REG_ADDR(0x0007) + +#define QSB_ICDV_TAU GET_BITS(*QSB_ICDV, 5, 0) + +#define QSB_ICDV_TAU_SET(value) SET_BITS(0, 5, 0, value) + +/* + * QSB Scheduler Burst Limit Register + */ +#define QSB_SBL QSB_CONF_REG_ADDR(0x0009) + +#define QSB_SBL_SBL GET_BITS(*QSB_SBL, 3, 0) + +#define QSB_SBL_SBL_SET(value) SET_BITS(0, 3, 0, value) + +/* + * QSB Configuration Register + */ +#define QSB_CFG QSB_CONF_REG_ADDR(0x000A) + +#define QSB_CFG_TSTEPC GET_BITS(*QSB_CFG, 1, 0) + +#define QSB_CFG_TSTEPC_SET(value) SET_BITS(0, 1, 0, value) + +/* + * QSB RAM Transfer Table Register + */ +#define QSB_RTM QSB_CONF_REG_ADDR(0x000B) + +#define QSB_RTM_DM (*QSB_RTM) + +#define QSB_RTM_DM_SET(value) ((value) & 0xFFFFFFFF) + +/* + * QSB RAM Transfer Data Register + */ +#define QSB_RTD QSB_CONF_REG_ADDR(0x000C) + +#define QSB_RTD_TTV (*QSB_RTD) + +#define QSB_RTD_TTV_SET(value) ((value) & 0xFFFFFFFF) + +/* + * QSB RAM Access Register + */ +#define QSB_RAMAC QSB_CONF_REG_ADDR(0x000D) + +#define QSB_RAMAC_RW (*QSB_RAMAC & (1 << 31)) +#define QSB_RAMAC_TSEL GET_BITS(*QSB_RAMAC, 27, 24) +#define QSB_RAMAC_LH (*QSB_RAMAC & (1 << 16)) +#define QSB_RAMAC_TESEL GET_BITS(*QSB_RAMAC, 9, 0) + +#define QSB_RAMAC_RW_SET(value) ((value) ? (1 << 31) : 0) +#define QSB_RAMAC_TSEL_SET(value) SET_BITS(0, 27, 24, value) +#define QSB_RAMAC_LH_SET(value) ((value) ? (1 << 16) : 0) +#define QSB_RAMAC_TESEL_SET(value) SET_BITS(0, 9, 0, value) + +/* + * QSB Queue Scheduling and Shaping Definitions + */ +#define QSB_WFQ_NONUBR_MAX 0x3f00 +#define QSB_WFQ_UBR_BYPASS 0x3fff +#define QSB_TP_TS_MAX 65472 +#define QSB_TAUS_MAX 64512 +#define QSB_GCR_MIN 18 + +/* + * QSB Constant + */ +#define QSB_RAMAC_RW_READ 0 +#define QSB_RAMAC_RW_WRITE 1 + +#define QSB_RAMAC_TSEL_QPT 0x01 +#define QSB_RAMAC_TSEL_SCT 0x02 +#define QSB_RAMAC_TSEL_SPT 0x03 +#define QSB_RAMAC_TSEL_VBR 0x08 + +#define QSB_RAMAC_LH_LOW 0 +#define QSB_RAMAC_LH_HIGH 1 + +#define QSB_QPT_SET_MASK 0x0 +#define QSB_QVPT_SET_MASK 0x0 +#define QSB_SET_SCT_MASK 0x0 +#define QSB_SET_SPT_MASK 0x0 +#define QSB_SET_SPT_SBVALID_MASK 0x7FFFFFFF + +#define QSB_SPT_SBV_VALID (1 << 31) +#define QSB_SPT_PN_SET(value) (((value) & 0x01) ? (1 << 16) : 0) +#define QSB_SPT_INTRATE_SET(value) SET_BITS(0, 13, 0, value) + +/* + * QSB Queue Parameter Table Entry and Queue VBR Parameter Table Entry + */ +#if defined(__BIG_ENDIAN) + union qsb_queue_parameter_table { + struct { + unsigned int res1 :1; + unsigned int vbr :1; + unsigned int wfqf :14; + unsigned int tp :16; + } bit; + u32 dword; + }; + + union qsb_queue_vbr_parameter_table { + struct { + unsigned int taus :16; + unsigned int ts :16; + } bit; + u32 dword; + }; +#else + union qsb_queue_parameter_table { + struct { + unsigned int tp :16; + unsigned int wfqf :14; + unsigned int vbr :1; + unsigned int res1 :1; + } bit; + u32 dword; + }; + + union qsb_queue_vbr_parameter_table { + struct { + unsigned int ts :16; + unsigned int taus :16; + } bit; + u32 dword; + }; +#endif // defined(__BIG_ENDIAN) + +/* + * Mailbox IGU0 Registers + */ +#define MBOX_IGU0_ISRS PPE_REG_ADDR(0x0200) +#define MBOX_IGU0_ISRC PPE_REG_ADDR(0x0201) +#define MBOX_IGU0_ISR PPE_REG_ADDR(0x0202) +#define MBOX_IGU0_IER PPE_REG_ADDR(0x0203) + +#define MBOX_IGU0_ISRS_SET(n) (1 << (n)) +#define MBOX_IGU0_ISRC_CLEAR(n) (1 << (n)) +#define MBOX_IGU0_ISR_ISR(n) (*MBOX_IGU0_ISR & (1 << (n))) +#define MBOX_IGU0_IER_EN(n) (*MBOX_IGU0_IER & (1 << (n))) +#define MBOX_IGU0_IER_EN_SET(n) (1 << (n)) + +/* + * Mailbox IGU1 Registers + */ +#define MBOX_IGU1_ISRS PPE_REG_ADDR(0x0204) +#define MBOX_IGU1_ISRC PPE_REG_ADDR(0x0205) +#define MBOX_IGU1_ISR PPE_REG_ADDR(0x0206) +#define MBOX_IGU1_IER PPE_REG_ADDR(0x0207) + +#define MBOX_IGU1_ISRS_SET(n) (1 << (n)) +#define MBOX_IGU1_ISRC_CLEAR(n) (1 << (n)) +#define MBOX_IGU1_ISR_ISR(n) (*MBOX_IGU1_ISR & (1 << (n))) +#define MBOX_IGU1_IER_EN(n) (*MBOX_IGU1_IER & (1 << (n))) +#define MBOX_IGU1_IER_EN_SET(n) (1 << (n)) + +/* + * Mailbox IGU3 Registers + */ +#define MBOX_IGU3_ISRS PPE_REG_ADDR(0x0214) +#define MBOX_IGU3_ISRC PPE_REG_ADDR(0x0215) +#define MBOX_IGU3_ISR PPE_REG_ADDR(0x0216) +#define MBOX_IGU3_IER PPE_REG_ADDR(0x0217) + +#define MBOX_IGU3_ISRS_SET(n) (1 << (n)) +#define MBOX_IGU3_ISRC_CLEAR(n) (1 << (n)) +#define MBOX_IGU3_ISR_ISR(n) (*MBOX_IGU3_ISR & (1 << (n))) +#define MBOX_IGU3_IER_EN(n) (*MBOX_IGU3_IER & (1 << (n))) +#define MBOX_IGU3_IER_EN_SET(n) (1 << (n)) + +/* + * RTHA/TTHA Registers + */ +#define SFSM_STATE0 PPE_REG_ADDR(0x0410) +#define SFSM_STATE1 PPE_REG_ADDR(0x0411) +#define SFSM_DBA0 PPE_REG_ADDR(0x0412) +#define SFSM_DBA1 PPE_REG_ADDR(0x0413) +#define SFSM_CBA0 PPE_REG_ADDR(0x0414) +#define SFSM_CBA1 PPE_REG_ADDR(0x0415) +#define SFSM_CFG0 PPE_REG_ADDR(0x0416) +#define SFSM_CFG1 PPE_REG_ADDR(0x0417) +#define SFSM_PGCNT0 PPE_REG_ADDR(0x041C) +#define SFSM_PGCNT1 PPE_REG_ADDR(0x041D) +#define FFSM_DBA0 PPE_REG_ADDR(0x0508) +#define FFSM_DBA1 PPE_REG_ADDR(0x0509) +#define FFSM_CFG0 PPE_REG_ADDR(0x050A) +#define FFSM_CFG1 PPE_REG_ADDR(0x050B) +#define FFSM_IDLE_HEAD_BC0 PPE_REG_ADDR(0x050E) +#define FFSM_IDLE_HEAD_BC1 PPE_REG_ADDR(0x050F) +#define FFSM_PGCNT0 PPE_REG_ADDR(0x0514) +#define FFSM_PGCNT1 PPE_REG_ADDR(0x0515) + + + +#endif // IFXMIPS_ATM_PPE_COMMON_H diff --git a/package/ltq-dsl/src/ifxmips_atm_ppe_danube.h b/package/ltq-dsl/src/ifxmips_atm_ppe_danube.h new file mode 100644 index 0000000000..a60abe1d55 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_atm_ppe_danube.h @@ -0,0 +1,100 @@ +#ifndef IFXMIPS_ATM_PPE_DANUBE_H +#define IFXMIPS_ATM_PPE_DANUBE_H + +#include + +/* + * FPI Configuration Bus Register and Memory Address Mapping + */ +#define IFX_PPE (KSEG1 | 0x1E180000) +#define PP32_DEBUG_REG_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0000) << 2))) +#define PPM_INT_REG_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0030) << 2))) +#define PP32_INTERNAL_RES_ADDR(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x0040) << 2))) +#define CDM_CODE_MEMORY(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x1000) << 2))) +#define PPE_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x4000) << 2))) +#define CDM_DATA_MEMORY(i, x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x5000) << 2))) +#define PPM_INT_UNIT_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6000) << 2))) +#define PPM_TIMER0_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6100) << 2))) +#define PPM_TASK_IND_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6200) << 2))) +#define PPS_BRK_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6300) << 2))) +#define PPM_TIMER1_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x6400) << 2))) +#define SB_RAM0_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8000) << 2))) +#define SB_RAM1_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8400) << 2))) +#define SB_RAM2_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x8C00) << 2))) +#define SB_RAM3_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0x9600) << 2))) +#define QSB_CONF_REG_ADDR(x) ((volatile unsigned int*)(IFX_PPE + (((x) + 0xC000) << 2))) + +/* + * DWORD-Length of Memory Blocks + */ +#define PP32_DEBUG_REG_DWLEN 0x0030 +#define PPM_INT_REG_DWLEN 0x0010 +#define PP32_INTERNAL_RES_DWLEN 0x00C0 +#define CDM_CODE_MEMORYn_DWLEN(n) ((n) == 0 ? 0x1000 : 0x0800) +#define PPE_REG_DWLEN 0x1000 +#define CDM_DATA_MEMORY_DWLEN CDM_CODE_MEMORYn_DWLEN(1) +#define PPM_INT_UNIT_DWLEN 0x0100 +#define PPM_TIMER0_DWLEN 0x0100 +#define PPM_TASK_IND_REG_DWLEN 0x0100 +#define PPS_BRK_DWLEN 0x0100 +#define PPM_TIMER1_DWLEN 0x0100 +#define SB_RAM0_DWLEN 0x0400 +#define SB_RAM1_DWLEN 0x0800 +#define SB_RAM2_DWLEN 0x0A00 +#define SB_RAM3_DWLEN 0x0400 +#define QSB_CONF_REG_DWLEN 0x0100 + +/* + * PP32 to FPI Address Mapping + */ +#define SB_BUFFER(__sb_addr) ((volatile unsigned int *)((((__sb_addr) >= 0x2000) && ((__sb_addr) <= 0x23FF)) ? SB_RAM0_ADDR((__sb_addr) - 0x2000) : \ + (((__sb_addr) >= 0x2400) && ((__sb_addr) <= 0x2BFF)) ? SB_RAM1_ADDR((__sb_addr) - 0x2400) : \ + (((__sb_addr) >= 0x2C00) && ((__sb_addr) <= 0x35FF)) ? SB_RAM2_ADDR((__sb_addr) - 0x2C00) : \ + (((__sb_addr) >= 0x3600) && ((__sb_addr) <= 0x39FF)) ? SB_RAM3_ADDR((__sb_addr) - 0x3600) : \ + 0)) + +/* + * PP32 Debug Control Register + */ +#define PP32_DBG_CTRL PP32_DEBUG_REG_ADDR(0, 0x0000) + +#define DBG_CTRL_START_SET(value) ((value) ? (1 << 0) : 0) +#define DBG_CTRL_STOP_SET(value) ((value) ? (1 << 1) : 0) +#define DBG_CTRL_STEP_SET(value) ((value) ? (1 << 2) : 0) + +#define PP32_HALT_STAT PP32_DEBUG_REG_ADDR(0, 0x0001) + +#define PP32_BRK_SRC PP32_DEBUG_REG_ADDR(0, 0x0002) + +#define PP32_DBG_PC_MIN(i) PP32_DEBUG_REG_ADDR(0, 0x0010 + (i)) +#define PP32_DBG_PC_MAX(i) PP32_DEBUG_REG_ADDR(0, 0x0014 + (i)) +#define PP32_DBG_DATA_MIN(i) PP32_DEBUG_REG_ADDR(0, 0x0018 + (i)) +#define PP32_DBG_DATA_MAX(i) PP32_DEBUG_REG_ADDR(0, 0x001A + (i)) +#define PP32_DBG_DATA_VAL(i) PP32_DEBUG_REG_ADDR(0, 0x001C + (i)) + +#define PP32_DBG_CUR_PC PP32_DEBUG_REG_ADDR(0, 0x0080) + +#define PP32_DBG_TASK_NO PP32_DEBUG_REG_ADDR(0, 0x0081) + +/* + * EMA Registers + */ +#define EMA_CMDCFG PPE_REG_ADDR(0x0A00) +#define EMA_DATACFG PPE_REG_ADDR(0x0A01) +#define EMA_CMDCNT PPE_REG_ADDR(0x0A02) +#define EMA_DATACNT PPE_REG_ADDR(0x0A03) +#define EMA_ISR PPE_REG_ADDR(0x0A04) +#define EMA_IER PPE_REG_ADDR(0x0A05) +#define EMA_CFG PPE_REG_ADDR(0x0A06) +#define EMA_SUBID PPE_REG_ADDR(0x0A07) + +#define EMA_ALIGNMENT 4 + +/* + * Mailbox IGU1 Interrupt + */ +#define PPE_MAILBOX_IGU1_INT LQ_PPE_MBOX_INT + + + +#endif // IFXMIPS_ATM_PPE_DANUBE_H diff --git a/package/ltq-dsl/src/ifxmips_compat.h b/package/ltq-dsl/src/ifxmips_compat.h new file mode 100644 index 0000000000..f5b5768466 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_compat.h @@ -0,0 +1,43 @@ +#ifndef _IFXMIPS_COMPAT_H__ +#define _IFXMIPS_COMPAT_H__ + +#define IFX_SUCCESS 0 +#define IFX_ERROR (-1) + +#define ATM_VBR_NRT ATM_VBR +#define ATM_VBR_RT 6 +#define ATM_UBR_PLUS 7 +#define ATM_GFR 8 + +#define NUM_ENTITY(x) (sizeof(x) / sizeof(*(x))) + +#define SET_BITS(x, msb, lsb, value) \ + (((x) & ~(((1 << ((msb) + 1)) - 1) ^ ((1 << (lsb)) - 1))) | (((value) & ((1 << (1 + (msb) - (lsb))) - 1)) << (lsb))) + + +#define IFX_PMU_ENABLE 1 +#define IFX_PMU_DISABLE 0 + +#define IFX_PMU_MODULE_DSL_DFE (1 << 9) +#define IFX_PMU_MODULE_AHBS (1 << 13) +#define IFX_PMU_MODULE_PPE_QSB (1 << 18) +#define IFX_PMU_MODULE_PPE_SLL01 (1 << 19) +#define IFX_PMU_MODULE_PPE_TC (1 << 21) +#define IFX_PMU_MODULE_PPE_EMA (1 << 22) +#define IFX_PMU_MODULE_PPE_TOP (1 << 29) + +#define ifx_pmu_set(a,b) {if(a == IFX_PMU_ENABLE) lq_pmu_enable(b); else lq_pmu_disable(b);} + +#define PPE_TOP_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_TOP, (__x)) +#define PPE_SLL01_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_SLL01, (__x)) +#define PPE_TC_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_TC, (__x)) +#define PPE_EMA_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_EMA, (__x)) +#define PPE_QSB_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_PPE_QSB, (__x)) +#define PPE_TPE_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_AHBS, (__x)) +#define DSL_DFE_PMU_SETUP(__x) ifx_pmu_set(IFX_PMU_MODULE_DSL_DFE, (__x)) + +#define IFX_REG_W32(_v, _r) __raw_writel((_v), (_r)) + +#define CONFIG_IFXMIPS_DSL_CPE_MEI y + +#endif diff --git a/package/ltq-dsl/src/ifxmips_mei_interface.h b/package/ltq-dsl/src/ifxmips_mei_interface.h new file mode 100644 index 0000000000..ffde6113c8 --- /dev/null +++ b/package/ltq-dsl/src/ifxmips_mei_interface.h @@ -0,0 +1,700 @@ +/****************************************************************************** + + Copyright (c) 2009 + Infineon Technologies AG + Am Campeon 1-12; 81726 Munich, Germany + + For licensing information, see the file 'LICENSE' in the root folder of + this software module. + +******************************************************************************/ + +#ifndef IFXMIPS_MEI_H +#define IFXMIPS_MEI_H + +#define CONFIG_DANUBE 1 + +#if !defined(CONFIG_DANUBE) && !defined(CONFIG_AMAZON_SE) && !defined(CONFIG_AR9) && !defined(CONFIG_VR9) +#error Platform undefined!!! +#endif + +#ifdef IFX_MEI_BSP +/** This is the character datatype. */ +typedef char DSL_char_t; +/** This is the unsigned 8-bit datatype. */ +typedef unsigned char DSL_uint8_t; +/** This is the signed 8-bit datatype. */ +typedef signed char DSL_int8_t; +/** This is the unsigned 16-bit datatype. */ +typedef unsigned short DSL_uint16_t; +/** This is the signed 16-bit datatype. */ +typedef signed short DSL_int16_t; +/** This is the unsigned 32-bit datatype. */ +typedef unsigned long DSL_uint32_t; +/** This is the signed 32-bit datatype. */ +typedef signed long DSL_int32_t; +/** This is the float datatype. */ +typedef float DSL_float_t; +/** This is the void datatype. */ +typedef void DSL_void_t; +/** integer type, width is depending on processor arch */ +typedef int DSL_int_t; +/** unsigned integer type, width is depending on processor arch */ +typedef unsigned int DSL_uint_t; +typedef struct file DSL_DRV_file_t; +typedef struct inode DSL_DRV_inode_t; + +/** + * Defines all possible CMV groups + * */ +typedef enum { + DSL_CMV_GROUP_CNTL = 1, + DSL_CMV_GROUP_STAT = 2, + DSL_CMV_GROUP_INFO = 3, + DSL_CMV_GROUP_TEST = 4, + DSL_CMV_GROUP_OPTN = 5, + DSL_CMV_GROUP_RATE = 6, + DSL_CMV_GROUP_PLAM = 7, + DSL_CMV_GROUP_CNFG = 8 +} DSL_CmvGroup_t; +/** + * Defines all opcode types + * */ +typedef enum { + H2D_CMV_READ = 0x00, + H2D_CMV_WRITE = 0x04, + H2D_CMV_INDICATE_REPLY = 0x10, + H2D_ERROR_OPCODE_UNKNOWN =0x20, + H2D_ERROR_CMV_UNKNOWN =0x30, + + D2H_CMV_READ_REPLY =0x01, + D2H_CMV_WRITE_REPLY = 0x05, + D2H_CMV_INDICATE = 0x11, + D2H_ERROR_OPCODE_UNKNOWN = 0x21, + D2H_ERROR_CMV_UNKNOWN = 0x31, + D2H_ERROR_CMV_READ_NOT_AVAILABLE = 0x41, + D2H_ERROR_CMV_WRITE_ONLY = 0x51, + D2H_ERROR_CMV_READ_ONLY = 0x61, + + H2D_DEBUG_READ_DM = 0x02, + H2D_DEBUG_READ_PM = 0x06, + H2D_DEBUG_WRITE_DM = 0x0a, + H2D_DEBUG_WRITE_PM = 0x0e, + + D2H_DEBUG_READ_DM_REPLY = 0x03, + D2H_DEBUG_READ_FM_REPLY = 0x07, + D2H_DEBUG_WRITE_DM_REPLY = 0x0b, + D2H_DEBUG_WRITE_FM_REPLY = 0x0f, + D2H_ERROR_ADDR_UNKNOWN = 0x33, + + D2H_AUTONOMOUS_MODEM_READY_MSG = 0xf1 +} DSL_CmvOpcode_t; + +/* mutex macros */ +#define MEI_MUTEX_INIT(id,flag) \ + sema_init(&id,flag) +#define MEI_MUTEX_LOCK(id) \ + down_interruptible(&id) +#define MEI_MUTEX_UNLOCK(id) \ + up(&id) +#define MEI_WAIT(ms) \ + {\ + set_current_state(TASK_INTERRUPTIBLE);\ + schedule_timeout(ms);\ + } +#define MEI_INIT_WAKELIST(name,queue) \ + init_waitqueue_head(&queue) + +/* wait for an event, timeout is measured in ms */ +#define MEI_WAIT_EVENT_TIMEOUT(ev,timeout)\ + interruptible_sleep_on_timeout(&ev,timeout * HZ / 1000) +#define MEI_WAKEUP_EVENT(ev)\ + wake_up_interruptible(&ev) +#endif /* IFX_MEI_BSP */ + +/*** Register address offsets, relative to MEI_SPACE_ADDRESS ***/ +#define ME_DX_DATA (0x0000) +#define ME_VERSION (0x0004) +#define ME_ARC_GP_STAT (0x0008) +#define ME_DX_STAT (0x000C) +#define ME_DX_AD (0x0010) +#define ME_DX_MWS (0x0014) +#define ME_ME2ARC_INT (0x0018) +#define ME_ARC2ME_STAT (0x001C) +#define ME_ARC2ME_MASK (0x0020) +#define ME_DBG_WR_AD (0x0024) +#define ME_DBG_RD_AD (0x0028) +#define ME_DBG_DATA (0x002C) +#define ME_DBG_DECODE (0x0030) +#define ME_CONFIG (0x0034) +#define ME_RST_CTRL (0x0038) +#define ME_DBG_MASTER (0x003C) +#define ME_CLK_CTRL (0x0040) +#define ME_BIST_CTRL (0x0044) +#define ME_BIST_STAT (0x0048) +#define ME_XDATA_BASE_SH (0x004c) +#define ME_XDATA_BASE (0x0050) +#define ME_XMEM_BAR_BASE (0x0054) +#define ME_XMEM_BAR0 (0x0054) +#define ME_XMEM_BAR1 (0x0058) +#define ME_XMEM_BAR2 (0x005C) +#define ME_XMEM_BAR3 (0x0060) +#define ME_XMEM_BAR4 (0x0064) +#define ME_XMEM_BAR5 (0x0068) +#define ME_XMEM_BAR6 (0x006C) +#define ME_XMEM_BAR7 (0x0070) +#define ME_XMEM_BAR8 (0x0074) +#define ME_XMEM_BAR9 (0x0078) +#define ME_XMEM_BAR10 (0x007C) +#define ME_XMEM_BAR11 (0x0080) +#define ME_XMEM_BAR12 (0x0084) +#define ME_XMEM_BAR13 (0x0088) +#define ME_XMEM_BAR14 (0x008C) +#define ME_XMEM_BAR15 (0x0090) +#define ME_XMEM_BAR16 (0x0094) + +#define WHILE_DELAY 20000 +/* +** Define where in ME Processor's memory map the Stratify chip lives +*/ + +#define MAXSWAPSIZE (8 * 1024) //8k *(32bits) + +// Mailboxes +#define MSG_LENGTH 16 // x16 bits +#define YES_REPLY 1 +#define NO_REPLY 0 + +#define CMV_TIMEOUT 1000 //jiffies + +// Block size per BAR +#define SDRAM_SEGMENT_SIZE (64*1024) +// Number of Bar registers +#define MAX_BAR_REGISTERS (17) + +#define XDATA_REGISTER (15) + +// ARC register addresss +#define ARC_STATUS 0x0 +#define ARC_LP_START 0x2 +#define ARC_LP_END 0x3 +#define ARC_DEBUG 0x5 +#define ARC_INT_MASK 0x10A + +#define IRAM0_BASE (0x00000) +#define IRAM1_BASE (0x04000) +#if defined(CONFIG_DANUBE) +#define BRAM_BASE (0x0A000) +#elif defined(CONFIG_AMAZON_SE) || defined(CONFIG_AR9) || defined(CONFIG_VR9) +#define BRAM_BASE (0x08000) +#endif +#define XRAM_BASE (0x18000) +#define YRAM_BASE (0x1A000) +#define EXT_MEM_BASE (0x80000) +#define ARC_GPIO_CTRL (0xC030) +#define ARC_GPIO_DATA (0xC034) + +#define IRAM0_SIZE (16*1024) +#define IRAM1_SIZE (16*1024) +#define BRAM_SIZE (12*1024) +#define XRAM_SIZE (8*1024) +#define YRAM_SIZE (8*1024) +#define EXT_MEM_SIZE (1536*1024) + +#define ADSL_BASE (0x20000) +#define CRI_BASE (ADSL_BASE + 0x11F00) +#define CRI_CCR0 (CRI_BASE + 0x00) +#define CRI_RST (CRI_BASE + 0x04*4) +#define ADSL_DILV_BASE (ADSL_BASE+0x20000) + +// +#define IRAM0_ADDR_BIT_MASK 0xFFF +#define IRAM1_ADDR_BIT_MASK 0xFFF +#define BRAM_ADDR_BIT_MASK 0xFFF +#define RX_DILV_ADDR_BIT_MASK 0x1FFF + +/*** Bit definitions ***/ +#define ARC_AUX_HALT (1 << 25) +#define ARC_DEBUG_HALT (1 << 1) +#define FALSE 0 +#define TRUE 1 +#define BIT0 (1<<0) +#define BIT1 (1<<1) +#define BIT2 (1<<2) +#define BIT3 (1<<3) +#define BIT4 (1<<4) +#define BIT5 (1<<5) +#define BIT6 (1<<6) +#define BIT7 (1<<7) +#define BIT8 (1<<8) +#define BIT9 (1<<9) +#define BIT10 (1<<10) +#define BIT11 (1<<11) +#define BIT12 (1<<12) +#define BIT13 (1<<13) +#define BIT14 (1<<14) +#define BIT15 (1<<15) +#define BIT16 (1<<16) +#define BIT17 (1<<17) +#define BIT18 (1<<18) +#define BIT19 (1<<19) +#define BIT20 (1<<20) +#define BIT21 (1<<21) +#define BIT22 (1<<22) +#define BIT23 (1<<23) +#define BIT24 (1<<24) +#define BIT25 (1<<25) +#define BIT26 (1<<26) +#define BIT27 (1<<27) +#define BIT28 (1<<28) +#define BIT29 (1<<29) +#define BIT30 (1<<30) +#define BIT31 (1<<31) + +// CRI_CCR0 Register definitions +#define CLK_2M_MODE_ENABLE BIT6 +#define ACL_CLK_MODE_ENABLE BIT4 +#define FDF_CLK_MODE_ENABLE BIT2 +#define STM_CLK_MODE_ENABLE BIT0 + +// CRI_RST Register definitions +#define FDF_SRST BIT3 +#define MTE_SRST BIT2 +#define FCI_SRST BIT1 +#define AAI_SRST BIT0 + +// MEI_TO_ARC_INTERRUPT Register definitions +#define MEI_TO_ARC_INT1 BIT3 +#define MEI_TO_ARC_INT0 BIT2 +#define MEI_TO_ARC_CS_DONE BIT1 //need to check +#define MEI_TO_ARC_MSGAV BIT0 + +// ARC_TO_MEI_INTERRUPT Register definitions +#define ARC_TO_MEI_INT1 BIT8 +#define ARC_TO_MEI_INT0 BIT7 +#define ARC_TO_MEI_CS_REQ BIT6 +#define ARC_TO_MEI_DBG_DONE BIT5 +#define ARC_TO_MEI_MSGACK BIT4 +#define ARC_TO_MEI_NO_ACCESS BIT3 +#define ARC_TO_MEI_CHECK_AAITX BIT2 +#define ARC_TO_MEI_CHECK_AAIRX BIT1 +#define ARC_TO_MEI_MSGAV BIT0 + +// ARC_TO_MEI_INTERRUPT_MASK Register definitions +#define GP_INT1_EN BIT8 +#define GP_INT0_EN BIT7 +#define CS_REQ_EN BIT6 +#define DBG_DONE_EN BIT5 +#define MSGACK_EN BIT4 +#define NO_ACC_EN BIT3 +#define AAITX_EN BIT2 +#define AAIRX_EN BIT1 +#define MSGAV_EN BIT0 + +#define MEI_SOFT_RESET BIT0 + +#define HOST_MSTR BIT0 + +#define JTAG_MASTER_MODE 0x0 +#define MEI_MASTER_MODE HOST_MSTR + +// MEI_DEBUG_DECODE Register definitions +#define MEI_DEBUG_DEC_MASK (0x3) +#define MEI_DEBUG_DEC_AUX_MASK (0x0) +#define ME_DBG_DECODE_DMP1_MASK (0x1) +#define MEI_DEBUG_DEC_DMP2_MASK (0x2) +#define MEI_DEBUG_DEC_CORE_MASK (0x3) + +#define AUX_STATUS (0x0) +#define AUX_ARC_GPIO_CTRL (0x10C) +#define AUX_ARC_GPIO_DATA (0x10D) +// ARC_TO_MEI_MAILBOX[11] is a special location used to indicate +// page swap requests. +#if defined(CONFIG_DANUBE) +#define OMBOX_BASE 0xDF80 +#define ARC_TO_MEI_MAILBOX 0xDFA0 +#define IMBOX_BASE 0xDFC0 +#define MEI_TO_ARC_MAILBOX 0xDFD0 +#elif defined(CONFIG_AMAZON_SE) || defined(CONFIG_AR9) || defined(CONFIG_VR9) +#define OMBOX_BASE 0xAF80 +#define ARC_TO_MEI_MAILBOX 0xAFA0 +#define IMBOX_BASE 0xAFC0 +#define MEI_TO_ARC_MAILBOX 0xAFD0 +#endif + +#define MEI_TO_ARC_MAILBOXR (MEI_TO_ARC_MAILBOX + 0x2C) +#define ARC_MEI_MAILBOXR (ARC_TO_MEI_MAILBOX + 0x2C) +#define OMBOX1 (OMBOX_BASE+0x4) + +// Codeswap request messages are indicated by setting BIT31 +#define OMB_CODESWAP_MESSAGE_MSG_TYPE_MASK (0x80000000) + +// Clear Eoc messages received are indicated by setting BIT17 +#define OMB_CLEAREOC_INTERRUPT_CODE (0x00020000) +#define OMB_REBOOT_INTERRUPT_CODE (1 << 18) + +/* +** Swap page header +*/ +// Page must be loaded at boot time if size field has BIT31 set +#define BOOT_FLAG (BIT31) +#define BOOT_FLAG_MASK ~BOOT_FLAG + +#define FREE_RELOAD 1 +#define FREE_SHOWTIME 2 +#define FREE_ALL 3 + +// marcos +#define IFX_MEI_WRITE_REGISTER_L(data,addr) *((volatile u32*)(addr)) = (u32)(data) +#define IFX_MEI_READ_REGISTER_L(addr) (*((volatile u32*)(addr))) +#define SET_BIT(reg, mask) reg |= (mask) +#define CLEAR_BIT(reg, mask) reg &= (~mask) +#define CLEAR_BITS(reg, mask) CLEAR_BIT(reg, mask) +//#define SET_BITS(reg, mask) SET_BIT(reg, mask) +#define SET_BITFIELD(reg, mask, off, val) {reg &= (~mask); reg |= (val << off);} + +#define ALIGN_SIZE ( 1L<<10 ) //1K size align +#define MEM_ALIGN(addr) (((addr) + ALIGN_SIZE - 1) & ~ (ALIGN_SIZE -1) ) + +// swap marco +#define MEI_HALF_WORD_SWAP(data) {data = ((data & 0xffff)<<16) + ((data & 0xffff0000)>>16);} +#define MEI_BYTE_SWAP(data) {data = ((data & 0xff)<<24) + ((data & 0xff00)<<8)+ ((data & 0xff0000)>>8)+ ((data & 0xff000000)>>24);} + + +#ifdef CONFIG_PROC_FS +typedef struct reg_entry +{ + int *flag; + char name[30]; /* big enough to hold names */ + char description[100]; /* big enough to hold description */ + unsigned short low_ino; +} reg_entry_t; +#endif +// Swap page header describes size in 32-bit words, load location, and image offset +// for program and/or data segments +typedef struct _arc_swp_page_hdr { + u32 p_offset; //Offset bytes of progseg from beginning of image + u32 p_dest; //Destination addr of progseg on processor + u32 p_size; //Size in 32-bitwords of program segment + u32 d_offset; //Offset bytes of dataseg from beginning of image + u32 d_dest; //Destination addr of dataseg on processor + u32 d_size; //Size in 32-bitwords of data segment +} ARC_SWP_PAGE_HDR; + +/* +** Swap image header +*/ +#define GET_PROG 0 // Flag used for program mem segment +#define GET_DATA 1 // Flag used for data mem segment + +// Image header contains size of image, checksum for image, and count of +// page headers. Following that are 'count' page headers followed by +// the code and/or data segments to be loaded +typedef struct _arc_img_hdr { + u32 size; // Size of binary image in bytes + u32 checksum; // Checksum for image + u32 count; // Count of swp pages in image + ARC_SWP_PAGE_HDR page[1]; // Should be "count" pages - '1' to make compiler happy +} ARC_IMG_HDR; + +typedef struct smmu_mem_info { + int type; + int boot; + unsigned long nCopy; + unsigned long size; + unsigned char *address; + unsigned char *org_address; +} smmu_mem_info_t; + +#ifdef __KERNEL__ +typedef struct ifx_mei_device_private { + int modem_ready; + int arcmsgav; + int cmv_reply; + int cmv_waiting; + // Mei to ARC CMV count, reply count, ARC Indicator count + int modem_ready_cnt; + int cmv_count; + int reply_count; + unsigned long image_size; + int nBar; + u16 Recent_indicator[MSG_LENGTH]; + + u16 CMV_RxMsg[MSG_LENGTH] __attribute__ ((aligned (4))); + + smmu_mem_info_t adsl_mem_info[MAX_BAR_REGISTERS]; + ARC_IMG_HDR *img_hdr; + // to wait for arc cmv reply, sleep on wait_queue_arcmsgav; + wait_queue_head_t wait_queue_arcmsgav; + wait_queue_head_t wait_queue_modemready; + struct semaphore mei_cmv_sema; +} ifx_mei_device_private_t; +#endif +typedef struct winhost_message { + union { + u16 RxMessage[MSG_LENGTH] __attribute__ ((aligned (4))); + u16 TxMessage[MSG_LENGTH] __attribute__ ((aligned (4))); + } msg; +} DSL_DEV_WinHost_Message_t; +/******************************************************************************************************** + * DSL CPE API Driver Stack Interface Definitions + * *****************************************************************************************************/ +/** IOCTL codes for bsp driver */ +#define DSL_IOC_MEI_BSP_MAGIC 's' + +#define DSL_FIO_BSP_DSL_START _IO (DSL_IOC_MEI_BSP_MAGIC, 0) +#define DSL_FIO_BSP_RUN _IO (DSL_IOC_MEI_BSP_MAGIC, 1) +#define DSL_FIO_BSP_FREE_RESOURCE _IO (DSL_IOC_MEI_BSP_MAGIC, 2) +#define DSL_FIO_BSP_RESET _IO (DSL_IOC_MEI_BSP_MAGIC, 3) +#define DSL_FIO_BSP_REBOOT _IO (DSL_IOC_MEI_BSP_MAGIC, 4) +#define DSL_FIO_BSP_HALT _IO (DSL_IOC_MEI_BSP_MAGIC, 5) +#define DSL_FIO_BSP_BOOTDOWNLOAD _IO (DSL_IOC_MEI_BSP_MAGIC, 6) +#define DSL_FIO_BSP_JTAG_ENABLE _IO (DSL_IOC_MEI_BSP_MAGIC, 7) +#define DSL_FIO_FREE_RESOURCE _IO (DSL_IOC_MEI_BSP_MAGIC, 8) +#define DSL_FIO_ARC_MUX_TEST _IO (DSL_IOC_MEI_BSP_MAGIC, 9) +#define DSL_FIO_BSP_REMOTE _IOW (DSL_IOC_MEI_BSP_MAGIC, 10, u32) +#define DSL_FIO_BSP_GET_BASE_ADDRESS _IOR (DSL_IOC_MEI_BSP_MAGIC, 11, u32) +#define DSL_FIO_BSP_IS_MODEM_READY _IOR (DSL_IOC_MEI_BSP_MAGIC, 12, u32) +#define DSL_FIO_BSP_GET_VERSION _IOR (DSL_IOC_MEI_BSP_MAGIC, 13, DSL_DEV_Version_t) +#define DSL_FIO_BSP_CMV_WINHOST _IOWR(DSL_IOC_MEI_BSP_MAGIC, 14, DSL_DEV_WinHost_Message_t) +#define DSL_FIO_BSP_CMV_READ _IOWR(DSL_IOC_MEI_BSP_MAGIC, 15, DSL_DEV_MeiReg_t) +#define DSL_FIO_BSP_CMV_WRITE _IOW (DSL_IOC_MEI_BSP_MAGIC, 16, DSL_DEV_MeiReg_t) +#define DSL_FIO_BSP_DEBUG_READ _IOWR(DSL_IOC_MEI_BSP_MAGIC, 17, DSL_DEV_MeiDebug_t) +#define DSL_FIO_BSP_DEBUG_WRITE _IOWR(DSL_IOC_MEI_BSP_MAGIC, 18, DSL_DEV_MeiDebug_t) +#define DSL_FIO_BSP_GET_CHIP_INFO _IOR (DSL_IOC_MEI_BSP_MAGIC, 19, DSL_DEV_HwVersion_t) + +#define DSL_DEV_MEIDEBUG_BUFFER_SIZES 512 + +typedef struct DSL_DEV_MeiDebug +{ + DSL_uint32_t iAddress; + DSL_uint32_t iCount; + DSL_uint32_t buffer[DSL_DEV_MEIDEBUG_BUFFER_SIZES]; +} DSL_DEV_MeiDebug_t; /* meidebug */ + +/** + * Structure is used for debug access only. + * Refer to configure option INCLUDE_ADSL_WINHOST_DEBUG */ +typedef struct struct_meireg +{ + /* + * Specifies that address for debug access */ + unsigned long iAddress; + /* + * Specifies the pointer to the data that has to be written or returns a + * pointer to the data that has been read out*/ + unsigned long iData; +} DSL_DEV_MeiReg_t; /* meireg */ + +typedef struct DSL_DEV_Device +{ + DSL_int_t nInUse; /* modem state, update by bsp driver, */ + DSL_void_t *pPriv; + DSL_uint32_t base_address; /* mei base address */ + DSL_int_t nIrq[2]; /* irq number */ +#define IFX_DFEIR 0 +#define IFX_DYING_GASP 1 + DSL_DEV_MeiDebug_t lop_debugwr; /* dying gasp */ +#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,0)) + struct module *owner; +#endif +} DSL_DEV_Device_t; /* ifx_adsl_device_t */ + +#define DSL_DEV_PRIVATE(dev) ((ifx_mei_device_private_t*)(dev->pPriv)) + +typedef struct DSL_DEV_Version /* ifx_adsl_bsp_version */ +{ + unsigned long major; + unsigned long minor; + unsigned long revision; +} DSL_DEV_Version_t; /* ifx_adsl_bsp_version_t */ + +typedef struct DSL_DEV_ChipInfo +{ + unsigned long major; + unsigned long minor; +} DSL_DEV_HwVersion_t; + +typedef struct +{ + DSL_uint8_t dummy; +} DSL_DEV_DeviceConfig_t; + +/** error code definitions */ +typedef enum DSL_DEV_MeiError +{ + DSL_DEV_MEI_ERR_SUCCESS = 0, + DSL_DEV_MEI_ERR_FAILURE = -1, + DSL_DEV_MEI_ERR_MAILBOX_FULL = -2, + DSL_DEV_MEI_ERR_MAILBOX_EMPTY = -3, + DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT = -4 +} DSL_DEV_MeiError_t; /* MEI_ERROR */ + +typedef enum { + DSL_BSP_MEMORY_READ=0, + DSL_BSP_MEMORY_WRITE, +} DSL_BSP_MemoryAccessType_t; /* ifx_adsl_memory_access_type_t */ + +typedef enum +{ + DSL_LED_LINK_ID=0, + DSL_LED_DATA_ID +} DSL_DEV_LedId_t; /* ifx_adsl_led_id_t */ + +typedef enum +{ + DSL_LED_LINK_TYPE=0, + DSL_LED_DATA_TYPE +} DSL_DEV_LedType_t; /* ifx_adsl_led_type_t */ + +typedef enum +{ + DSL_LED_HD_CPU=0, + DSL_LED_HD_FW +} DSL_DEV_LedHandler_t; /* ifx_adsl_led_handler_t */ + +typedef enum { + DSL_LED_ON=0, + DSL_LED_OFF, + DSL_LED_FLASH, +} DSL_DEV_LedMode_t; /* ifx_adsl_led_mode_t */ + +typedef enum { + DSL_CPU_HALT=0, + DSL_CPU_RUN, + DSL_CPU_RESET, +} DSL_DEV_CpuMode_t; /* ifx_adsl_cpu_mode_t */ + +#if 0 +typedef enum { + DSL_BSP_EVENT_DYING_GASP = 0, + DSL_BSP_EVENT_CEOC_IRQ, +} DSL_BSP_Event_id_t; /* ifx_adsl_event_id_t */ + +typedef union DSL_BSP_CB_Param +{ + DSL_uint32_t nIrqMessage; +} DSL_BSP_CB_Param_t; /* ifx_adsl_cbparam_t */ + +typedef struct DSL_BSP_CB_Event +{ + DSL_BSP_Event_id_t nID; + DSL_DEV_Device_t *pDev; + DSL_BSP_CB_Param_t *pParam; +} DSL_BSP_CB_Event_t; /* ifx_adsl_cb_event_t */ +#endif + +/* external functions (from the BSP Driver) */ +extern DSL_DEV_Device_t* DSL_BSP_DriverHandleGet(int, int); +extern DSL_int_t DSL_BSP_DriverHandleDelete(DSL_DEV_Device_t *); +extern DSL_DEV_MeiError_t DSL_BSP_FWDownload(DSL_DEV_Device_t *, const DSL_char_t *, DSL_uint32_t, DSL_int32_t *, DSL_int32_t *); +extern int DSL_BSP_KernelIoctls(DSL_DEV_Device_t *, unsigned int, unsigned long); +extern DSL_DEV_MeiError_t DSL_BSP_SendCMV(DSL_DEV_Device_t *, DSL_uint16_t *, DSL_int_t, DSL_uint16_t *); +extern DSL_DEV_MeiError_t DSL_BSP_AdslLedInit(DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedType_t, DSL_DEV_LedHandler_t); +extern DSL_DEV_MeiError_t DSL_BSP_Showtime(DSL_DEV_Device_t *, DSL_uint32_t, DSL_uint32_t); +extern int DSL_BSP_ATMLedCBRegister( int (*ifx_adsl_ledcallback)(void)); +extern DSL_DEV_MeiError_t DSL_BSP_MemoryDebugAccess(DSL_DEV_Device_t *, DSL_BSP_MemoryAccessType_t, DSL_uint32_t, DSL_uint32_t *, DSL_uint32_t); +extern volatile DSL_DEV_Device_t *adsl_dev; + +/** + * Dummy structure by now to show mechanism of extended data that will be + * provided within event callback itself. + * */ +typedef struct +{ + /** + * Dummy value */ + DSL_uint32_t nDummy1; +} DSL_BSP_CB_Event1DataDummy_t; + +/** + * Dummy structure by now to show mechanism of extended data that will be + * provided within event callback itself. + * */ +typedef struct +{ + /** + * Dummy value */ + DSL_uint32_t nDummy2; +} DSL_BSP_CB_Event2DataDummy_t; + +/** + * encapsulate all data structures that are necessary for status event + * callbacks. + * */ +typedef union +{ + DSL_BSP_CB_Event1DataDummy_t dataEvent1; + DSL_BSP_CB_Event2DataDummy_t dataEvent2; +} DSL_BSP_CB_DATA_Union_t; + + +typedef enum +{ + /** + * Informs the upper layer driver (DSL CPE API) about a reboot request from the + * firmware. + * \note This event does NOT include any additional data. + * More detailed information upon reboot reason has to be requested from + * upper layer software via CMV (INFO 109) if necessary. */ + DSL_BSP_CB_FIRST = 0, + DSL_BSP_CB_DYING_GASP, + DSL_BSP_CB_CEOC_IRQ, + DSL_BSP_CB_FIRMWARE_REBOOT, + /** + * Delimiter only */ + DSL_BSP_CB_LAST +} DSL_BSP_CB_Type_t; + +/** + * Specifies the common event type that has to be used for registering and + * signalling of interrupts/autonomous status events from MEI BSP Driver. + * + * \param pDev + * Context pointer from MEI BSP Driver. + * + * \param IFX_ADSL_BSP_CallbackType_t + * Specifies the event callback type (reason of callback). Regrading to the + * setting of this value the data which is included in the following union + * might have different meanings. + * Please refer to the description of the union to get information about the + * meaning of the included data. + * + * \param pData + * Data according to \ref DSL_BSP_CB_DATA_Union_t. + * If this pointer is NULL there is no additional data available. + * + * \return depending on event + */ +typedef int (*DSL_BSP_EventCallback_t) +( + DSL_DEV_Device_t *pDev, + DSL_BSP_CB_Type_t nCallbackType, + DSL_BSP_CB_DATA_Union_t *pData +); + +typedef struct { + DSL_BSP_EventCallback_t function; + DSL_BSP_CB_Type_t event; + DSL_BSP_CB_DATA_Union_t *pData; +} DSL_BSP_EventCallBack_t; + +extern int DSL_BSP_EventCBRegister(DSL_BSP_EventCallBack_t *); +extern int DSL_BSP_EventCBUnregister(DSL_BSP_EventCallBack_t *); + +/** Modem states */ +#define DSL_DEV_STAT_InitState 0x0000 +#define DSL_DEV_STAT_ReadyState 0x0001 +#define DSL_DEV_STAT_FailState 0x0002 +#define DSL_DEV_STAT_IdleState 0x0003 +#define DSL_DEV_STAT_QuietState 0x0004 +#define DSL_DEV_STAT_GhsState 0x0005 +#define DSL_DEV_STAT_FullInitState 0x0006 +#define DSL_DEV_STAT_ShowTimeState 0x0007 +#define DSL_DEV_STAT_FastRetrainState 0x0008 +#define DSL_DEV_STAT_LoopDiagMode 0x0009 +#define DSL_DEV_STAT_ShortInit 0x000A /* Bis short initialization */ + +#define DSL_DEV_STAT_CODESWAP_COMPLETE 0x0002 + +#endif //IFXMIPS_MEI_H diff --git a/package/ltq-dsl/src/lantiq_mei.c b/package/ltq-dsl/src/lantiq_mei.c new file mode 100644 index 0000000000..7eeab33686 --- /dev/null +++ b/package/ltq-dsl/src/lantiq_mei.c @@ -0,0 +1,3002 @@ +/****************************************************************************** + + Copyright (c) 2009 + Infineon Technologies AG + Am Campeon 1-12; 81726 Munich, Germany + + For licensing information, see the file 'LICENSE' in the root folder of + this software module. + +******************************************************************************/ + +/*! + \defgroup AMAZON_S_MEI Amazon-S MEI Driver Module + \brief Amazon-S MEI driver module + */ + +/*! + \defgroup Internal Compile Parametere + \ingroup AMAZON_S_MEI + \brief exported functions for other driver use + */ + +/*! + \file amazon_s_mei_bsp.c + \ingroup AMAZON_S_MEI + \brief Amazon-S MEI driver file + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include "ifxmips_atm.h" +#define IFX_MEI_BSP +#include "ifxmips_mei_interface.h" + +/*#define LQ_RCU_RST IFX_RCU_RST_REQ +#define LQ_RCU_RST_REQ_ARC_JTAG IFX_RCU_RST_REQ_ARC_JTAG +#define LQ_RCU_RST_REQ_DFE IFX_RCU_RST_REQ_DFE +#define LQ_RCU_RST_REQ_AFE IFX_RCU_RST_REQ_AFE +#define IFXMIPS_FUSE_BASE_ADDR IFX_FUSE_BASE_ADDR +#define IFXMIPS_ICU_IM0_IER IFX_ICU_IM0_IER +#define IFXMIPS_ICU_IM2_IER IFX_ICU_IM2_IER +#define LQ_MEI_INT IFX_MEI_INT +#define LQ_MEI_DYING_GASP_INT IFX_MEI_DYING_GASP_INT +#define LQ_MEI_BASE_ADDR IFX_MEI_SPACE_ACCESS +#define IFXMIPS_PMU_PWDCR IFX_PMU_PWDCR +#define IFXMIPS_MPS_CHIPID IFX_MPS_CHIPID + +#define ifxmips_port_reserve_pin ifx_gpio_pin_reserve +#define ifxmips_port_set_dir_in ifx_gpio_dir_in_set +#define ifxmips_port_clear_altsel0 ifx_gpio_altsel0_set +#define ifxmips_port_clear_altsel1 ifx_gpio_altsel1_clear +#define ifxmips_port_set_open_drain ifx_gpio_open_drain_clear +#define ifxmips_port_free_pin ifx_gpio_pin_free +#define ifxmips_mask_and_ack_irq bsp_mask_and_ack_irq +#define IFXMIPS_MPS_CHIPID_VERSION_GET IFX_MCD_CHIPID_VERSION_GET +#define lq_r32(reg) __raw_readl(reg) +#define lq_w32(val, reg) __raw_writel(val, reg) +#define lq_w32_mask(clear, set, reg) lq_w32((lq_r32(reg) & ~clear) | set, reg) +*/ + +#define LQ_RCU_RST_REQ_DFE (1 << 7) +#define LQ_RCU_RST_REQ_AFE (1 << 11) +#define LQ_PMU_PWDCR ((u32 *)(LQ_PMU_BASE_ADDR + 0x001C)) +#define LQ_PMU_PWDSR ((u32 *)(LQ_PMU_BASE_ADDR + 0x0020)) +#define LQ_RCU_RST ((u32 *)(LQ_RCU_BASE_ADDR + 0x0010)) +#define LQ_RCU_RST_ALL 0x40000000 +#define LQ_ICU_BASE_ADDR (KSEG1 | 0x1F880200) + +#define LQ_ICU_IM0_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0000)) +#define LQ_ICU_IM0_IER ((u32 *)(LQ_ICU_BASE_ADDR + 0x0008)) +#define LQ_ICU_IM0_IOSR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0010)) +#define LQ_ICU_IM0_IRSR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0018)) +#define LQ_ICU_IM0_IMR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0020)) + + +#define LQ_ICU_IM1_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0028)) +#define LQ_ICU_IM2_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0050)) +#define LQ_ICU_IM3_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x0078)) +#define LQ_ICU_IM4_ISR ((u32 *)(LQ_ICU_BASE_ADDR + 0x00A0)) + +#define LQ_ICU_OFFSET (LQ_ICU_IM1_ISR - LQ_ICU_IM0_ISR) +#define LQ_ICU_IM2_IER (LQ_ICU_IM0_IER + LQ_ICU_OFFSET) + +#define IFX_MEI_EMSG(fmt, args...) pr_err("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args) +#define IFX_MEI_DMSG(fmt, args...) pr_debug("[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args) + +#define LQ_FUSE_BASE (KSEG1 + 0x1F107354) + +#ifdef CONFIG_LQ_MEI_FW_LOOPBACK +//#define DFE_MEM_TEST +//#define DFE_PING_TEST +#define DFE_ATM_LOOPBACK + + +#ifdef DFE_ATM_LOOPBACK +#include +#endif + +void dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev); + +#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK + +DSL_DEV_Version_t bsp_mei_version = { + major: 5, + minor: 0, + revision:0 +}; +DSL_DEV_HwVersion_t bsp_chip_info; + +#define IFX_MEI_DEVNAME "ifx_mei" +#define BSP_MAX_DEVICES 1 + +DSL_DEV_MeiError_t DSL_BSP_FWDownload (DSL_DEV_Device_t *, const char *, unsigned long, long *, long *); +DSL_DEV_MeiError_t DSL_BSP_Showtime (DSL_DEV_Device_t *, DSL_uint32_t, DSL_uint32_t); +DSL_DEV_MeiError_t DSL_BSP_AdslLedInit (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedType_t, DSL_DEV_LedHandler_t); +//DSL_DEV_MeiError_t DSL_BSP_AdslLedSet (DSL_DEV_Device_t *, DSL_DEV_LedId_t, DSL_DEV_LedMode_t); +DSL_DEV_MeiError_t DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t *, DSL_BSP_MemoryAccessType_t, DSL_uint32_t, DSL_uint32_t*, DSL_uint32_t); +DSL_DEV_MeiError_t DSL_BSP_SendCMV (DSL_DEV_Device_t *, u16 *, int, u16 *); + +int DSL_BSP_KernelIoctls (DSL_DEV_Device_t *, unsigned int, unsigned long); + +static DSL_DEV_MeiError_t IFX_MEI_RunAdslModem (DSL_DEV_Device_t *); +static DSL_DEV_MeiError_t IFX_MEI_CpuModeSet (DSL_DEV_Device_t *, DSL_DEV_CpuMode_t); +static DSL_DEV_MeiError_t IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *); +static DSL_DEV_MeiError_t IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *, int); +static DSL_DEV_MeiError_t IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *, int); + +static int IFX_MEI_GetPage (DSL_DEV_Device_t *, u32, u32, u32, u32 *, u32 *); +static int IFX_MEI_BarUpdate (DSL_DEV_Device_t *, int); + +static ssize_t IFX_MEI_Write (DSL_DRV_file_t *, const char *, size_t, loff_t *); +static int IFX_MEI_UserIoctls (DSL_DRV_inode_t *, DSL_DRV_file_t *, unsigned int, unsigned long); +static int IFX_MEI_Open (DSL_DRV_inode_t *, DSL_DRV_file_t *); +static int IFX_MEI_Release (DSL_DRV_inode_t *, DSL_DRV_file_t *); + +void AMAZON_SE_MEI_ARC_MUX_Test(void); + +#ifdef CONFIG_PROC_FS +static int IFX_MEI_ProcRead (struct file *, char *, size_t, loff_t *); +static ssize_t IFX_MEI_ProcWrite (struct file *, const char *, size_t, loff_t *); + +#define PROC_ITEMS 11 +#define MEI_DIRNAME "ifxmips_mei" + +static struct proc_dir_entry *meidir; +static struct file_operations IFX_MEI_ProcOperations = { + read:IFX_MEI_ProcRead, + write:IFX_MEI_ProcWrite, +}; +static reg_entry_t regs[BSP_MAX_DEVICES][PROC_ITEMS]; //total items to be monitored by /proc/mei +#define NUM_OF_REG_ENTRY (sizeof(regs[0])/sizeof(reg_entry_t)) +#endif //CONFIG_PROC_FS + +void IFX_MEI_ARC_MUX_Test(void); + +static int adsl_dummy_ledcallback(void); + +int (*ifx_mei_atm_showtime_enter)(struct port_cell_info *, void *) = NULL; +EXPORT_SYMBOL(ifx_mei_atm_showtime_enter); + +int (*ifx_mei_atm_showtime_exit)(void) = NULL; +EXPORT_SYMBOL(ifx_mei_atm_showtime_exit); + +static int (*g_adsl_ledcallback)(void) = adsl_dummy_ledcallback; + +static unsigned int g_tx_link_rate[2] = {0}; + +static void *g_xdata_addr = NULL; + +static u32 *mei_arc_swap_buff = NULL; // holding swap pages + +extern void lq_mask_and_ack_irq(unsigned int irq_nr); +#define MEI_MASK_AND_ACK_IRQ lq_mask_and_ack_irq + +#define MEI_MAJOR 105 +static int dev_major = MEI_MAJOR; + +static struct file_operations bsp_mei_operations = { + owner:THIS_MODULE, + open:IFX_MEI_Open, + release:IFX_MEI_Release, + write:IFX_MEI_Write, + ioctl:IFX_MEI_UserIoctls, +}; + +static DSL_DEV_Device_t dsl_devices[BSP_MAX_DEVICES]; + +static ifx_mei_device_private_t + sDanube_Mei_Private[BSP_MAX_DEVICES]; + +static DSL_BSP_EventCallBack_t dsl_bsp_event_callback[DSL_BSP_CB_LAST + 1]; + +/** + * Write a value to register + * This function writes a value to danube register + * + * \param ul_address The address to write + * \param ul_data The value to write + * \ingroup Internal + */ +static void +IFX_MEI_LongWordWrite (u32 ul_address, u32 ul_data) +{ + IFX_MEI_WRITE_REGISTER_L (ul_data, ul_address); + wmb(); + return; +} + +/** + * Write a value to register + * This function writes a value to danube register + * + * \param pDev the device pointer + * \param ul_address The address to write + * \param ul_data The value to write + * \ingroup Internal + */ +static void +IFX_MEI_LongWordWriteOffset (DSL_DEV_Device_t * pDev, u32 ul_address, + u32 ul_data) +{ + IFX_MEI_WRITE_REGISTER_L (ul_data, pDev->base_address + ul_address); + wmb(); + return; +} + +/** + * Read the danube register + * This function read the value from danube register + * + * \param ul_address The address to write + * \param pul_data Pointer to the data + * \ingroup Internal + */ +static void +IFX_MEI_LongWordRead (u32 ul_address, u32 * pul_data) +{ + *pul_data = IFX_MEI_READ_REGISTER_L (ul_address); + rmb(); + return; +} + +/** + * Read the danube register + * This function read the value from danube register + * + * \param pDev the device pointer + * \param ul_address The address to write + * \param pul_data Pointer to the data + * \ingroup Internal + */ +static void +IFX_MEI_LongWordReadOffset (DSL_DEV_Device_t * pDev, u32 ul_address, + u32 * pul_data) +{ + *pul_data = IFX_MEI_READ_REGISTER_L (pDev->base_address + ul_address); + rmb(); + return; +} + +/** + * Write several DWORD datas to ARC memory via ARC DMA interface + * This function writes several DWORD datas to ARC memory via DMA interface. + * + * \param pDev the device pointer + * \param destaddr The address to write + * \param databuff Pointer to the data buffer + * \param databuffsize Number of DWORDs to write + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_DMAWrite (DSL_DEV_Device_t * pDev, u32 destaddr, + u32 * databuff, u32 databuffsize) +{ + u32 *p = databuff; + u32 temp; + + if (destaddr & 3) + return DSL_DEV_MEI_ERR_FAILURE; + + // Set the write transfer address + IFX_MEI_LongWordWriteOffset (pDev, ME_DX_AD, destaddr); + + // Write the data pushed across DMA + while (databuffsize--) { + temp = *p; + if (destaddr == MEI_TO_ARC_MAILBOX) + MEI_HALF_WORD_SWAP (temp); + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_DATA, temp); + p++; + } + + return DSL_DEV_MEI_ERR_SUCCESS; + +} + +/** + * Read several DWORD datas from ARC memory via ARC DMA interface + * This function reads several DWORD datas from ARC memory via DMA interface. + * + * \param pDev the device pointer + * \param srcaddr The address to read + * \param databuff Pointer to the data buffer + * \param databuffsize Number of DWORDs to read + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_DMARead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff, + u32 databuffsize) +{ + u32 *p = databuff; + u32 temp; + + if (srcaddr & 3) + return DSL_DEV_MEI_ERR_FAILURE; + + // Set the read transfer address + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DX_AD, srcaddr); + + // Read the data popped across DMA + while (databuffsize--) { + IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DX_DATA, &temp); + if (databuff == (u32 *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg) // swap half word + MEI_HALF_WORD_SWAP (temp); + *p = temp; + p++; + } + + return DSL_DEV_MEI_ERR_SUCCESS; + +} + +/** + * Switch the ARC control mode + * This function switchs the ARC control mode to JTAG mode or MEI mode + * + * \param pDev the device pointer + * \param mode The mode want to switch: JTAG_MASTER_MODE or MEI_MASTER_MODE. + * \ingroup Internal + */ +static void +IFX_MEI_ControlModeSet (DSL_DEV_Device_t * pDev, int mode) +{ + u32 temp = 0x0; + + IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_MASTER, &temp); + switch (mode) { + case JTAG_MASTER_MODE: + temp &= ~(HOST_MSTR); + break; + case MEI_MASTER_MODE: + temp |= (HOST_MSTR); + break; + default: + IFX_MEI_EMSG ("IFX_MEI_ControlModeSet: unkonwn mode [%d]\n", mode); + return; + } + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_MASTER, temp); +} + +/** + * Disable ARC to MEI interrupt + * + * \param pDev the device pointer + * \ingroup Internal + */ +static void +IFX_MEI_IRQDisable (DSL_DEV_Device_t * pDev) +{ + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK, 0x0); +} + +/** + * Eable ARC to MEI interrupt + * + * \param pDev the device pointer + * \ingroup Internal + */ +static void +IFX_MEI_IRQEnable (DSL_DEV_Device_t * pDev) +{ + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_MASK, MSGAV_EN); +} + +/** + * Poll for transaction complete signal + * This function polls and waits for transaction complete signal. + * + * \param pDev the device pointer + * \ingroup Internal + */ +static void +meiPollForDbgDone (DSL_DEV_Device_t * pDev) +{ + u32 query = 0; + int i = 0; + + while (i < WHILE_DELAY) { + IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ARC2ME_STAT, &query); + query &= (ARC_TO_MEI_DBG_DONE); + if (query) + break; + i++; + if (i == WHILE_DELAY) { + IFX_MEI_EMSG ("PollforDbg fail!\n"); + } + } + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_DBG_DONE); // to clear this interrupt +} + +/** + * ARC Debug Memory Access for a single DWORD reading. + * This function used for direct, address-based access to ARC memory. + * + * \param pDev the device pointer + * \param DEC_mode ARC memory space to used + * \param address Address to read + * \param data Pointer to data + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +_IFX_MEI_DBGLongWordRead (DSL_DEV_Device_t * pDev, u32 DEC_mode, + u32 address, u32 * data) +{ + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode); + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_RD_AD, address); + meiPollForDbgDone (pDev); + IFX_MEI_LongWordReadOffset (pDev, (u32) ME_DBG_DATA, data); + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * ARC Debug Memory Access for a single DWORD writing. + * This function used for direct, address-based access to ARC memory. + * + * \param pDev the device pointer + * \param DEC_mode ARC memory space to used + * \param address The address to write + * \param data The data to write + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +_IFX_MEI_DBGLongWordWrite (DSL_DEV_Device_t * pDev, u32 DEC_mode, + u32 address, u32 data) +{ + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DECODE, DEC_mode); + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_WR_AD, address); + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_DBG_DATA, data); + meiPollForDbgDone (pDev); + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * ARC Debug Memory Access for writing. + * This function used for direct, address-based access to ARC memory. + * + * \param pDev the device pointer + * \param destaddr The address to read + * \param databuffer Pointer to data + * \param databuffsize The number of DWORDs to read + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ + +static DSL_DEV_MeiError_t +IFX_MEI_DebugWrite (DSL_DEV_Device_t * pDev, u32 destaddr, + u32 * databuff, u32 databuffsize) +{ + u32 i; + u32 temp = 0x0; + u32 address = 0x0; + u32 *buffer = 0x0; + + // Open the debug port before DMP memory write + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + + // For the requested length, write the address and write the data + address = destaddr; + buffer = databuff; + for (i = 0; i < databuffsize; i++) { + temp = *buffer; + _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK, address, temp); + address += 4; + buffer++; + } + + // Close the debug port after DMP memory write + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * ARC Debug Memory Access for reading. + * This function used for direct, address-based access to ARC memory. + * + * \param pDev the device pointer + * \param srcaddr The address to read + * \param databuffer Pointer to data + * \param databuffsize The number of DWORDs to read + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_DebugRead (DSL_DEV_Device_t * pDev, u32 srcaddr, u32 * databuff, u32 databuffsize) +{ + u32 i; + u32 temp = 0x0; + u32 address = 0x0; + u32 *buffer = 0x0; + + // Open the debug port before DMP memory read + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + + // For the requested length, write the address and read the data + address = srcaddr; + buffer = databuff; + for (i = 0; i < databuffsize; i++) { + _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK, address, &temp); + *buffer = temp; + address += 4; + buffer++; + } + + // Close the debug port after DMP memory read + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * Send a message to ARC MailBox. + * This function sends a message to ARC Mailbox via ARC DMA interface. + * + * \param pDev the device pointer + * \param msgsrcbuffer Pointer to message. + * \param msgsize The number of words to write. + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_MailboxWrite (DSL_DEV_Device_t * pDev, u16 * msgsrcbuffer, + u16 msgsize) +{ + int i; + u32 arc_mailbox_status = 0x0; + u32 temp = 0; + DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS; + + // Write to mailbox + meiMailboxError = + IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOX, (u32 *) msgsrcbuffer, msgsize / 2); + meiMailboxError = + IFX_MEI_DMAWrite (pDev, MEI_TO_ARC_MAILBOXR, (u32 *) (&temp), 1); + + // Notify arc that mailbox write completed + DSL_DEV_PRIVATE(pDev)->cmv_waiting = 1; + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV); + + i = 0; + while (i < WHILE_DELAY) { // wait for ARC to clear the bit + IFX_MEI_LongWordReadOffset (pDev, (u32) ME_ME2ARC_INT, &arc_mailbox_status); + if ((arc_mailbox_status & MEI_TO_ARC_MSGAV) != MEI_TO_ARC_MSGAV) + break; + i++; + if (i == WHILE_DELAY) { + IFX_MEI_EMSG (">>> Timeout waiting for ARC to clear MEI_TO_ARC_MSGAV!!!" + " MEI_TO_ARC message size = %d DWORDs <<<\n", msgsize/2); + meiMailboxError = DSL_DEV_MEI_ERR_FAILURE; + } + } + + return meiMailboxError; +} + +/** + * Read a message from ARC MailBox. + * This function reads a message from ARC Mailbox via ARC DMA interface. + * + * \param pDev the device pointer + * \param msgsrcbuffer Pointer to message. + * \param msgsize The number of words to read + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_MailboxRead (DSL_DEV_Device_t * pDev, u16 * msgdestbuffer, + u16 msgsize) +{ + DSL_DEV_MeiError_t meiMailboxError = DSL_DEV_MEI_ERR_SUCCESS; + // Read from mailbox + meiMailboxError = + IFX_MEI_DMARead (pDev, ARC_TO_MEI_MAILBOX, (u32 *) msgdestbuffer, msgsize / 2); + + // Notify arc that mailbox read completed + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); + + return meiMailboxError; +} + +/** + * Download boot pages to ARC. + * This function downloads boot pages to ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_DownloadBootPages (DSL_DEV_Device_t * pDev) +{ + int boot_loop; + int page_size; + u32 dest_addr; + + /* + ** DMA the boot code page(s) + */ + + for (boot_loop = 1; + boot_loop < + (DSL_DEV_PRIVATE(pDev)->img_hdr-> count); boot_loop++) { + if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].p_size) & BOOT_FLAG) { + page_size = IFX_MEI_GetPage (pDev, boot_loop, + GET_PROG, MAXSWAPSIZE, + mei_arc_swap_buff, + &dest_addr); + if (page_size > 0) { + IFX_MEI_DMAWrite (pDev, dest_addr, + mei_arc_swap_buff, + page_size); + } + } + if ((DSL_DEV_PRIVATE(pDev)-> img_hdr->page[boot_loop].d_size) & BOOT_FLAG) { + page_size = IFX_MEI_GetPage (pDev, boot_loop, + GET_DATA, MAXSWAPSIZE, + mei_arc_swap_buff, + &dest_addr); + if (page_size > 0) { + IFX_MEI_DMAWrite (pDev, dest_addr, + mei_arc_swap_buff, + page_size); + } + } + } + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * Initial efuse rar. + **/ +static void +IFX_MEI_FuseInit (DSL_DEV_Device_t * pDev) +{ + u32 data = 0; + IFX_MEI_DMAWrite (pDev, IRAM0_BASE, &data, 1); + IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, &data, 1); + IFX_MEI_DMAWrite (pDev, IRAM1_BASE, &data, 1); + IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, &data, 1); + IFX_MEI_DMAWrite (pDev, BRAM_BASE, &data, 1); + IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, &data, 1); + IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, &data, 1); + IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, &data, 1); +} + +/** + * efuse rar program + **/ +static void +IFX_MEI_FuseProg (DSL_DEV_Device_t * pDev) +{ + u32 reg_data, fuse_value; + int i = 0; + + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); + while ((reg_data & 0x10000000) == 0) { + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); + i++; + /* 0x4000 translate to about 16 ms@111M, so should be enough */ + if (i == 0x4000) + return; + } + // STEP a: Prepare memory for external accesses + // Write fuse_en bit24 + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); + IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data | (1 << 24)); + + IFX_MEI_FuseInit (pDev); + for (i = 0; i < 4; i++) { + IFX_MEI_LongWordRead ((u32) (LQ_FUSE_BASE) + i * 4, &fuse_value); + switch (fuse_value & 0xF0000) { + case 0x80000: + reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) | + (RX_DILV_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE, ®_data, 1); + break; + case 0x90000: + reg_data = ((fuse_value & RX_DILV_ADDR_BIT_MASK) | + (RX_DILV_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, ADSL_DILV_BASE + 4, ®_data, 1); + break; + case 0xA0000: + reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) | + (IRAM0_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, IRAM0_BASE, ®_data, 1); + break; + case 0xB0000: + reg_data = ((fuse_value & IRAM0_ADDR_BIT_MASK) | + (IRAM0_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, IRAM0_BASE + 4, ®_data, 1); + break; + case 0xC0000: + reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) | + (IRAM1_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, IRAM1_BASE, ®_data, 1); + break; + case 0xD0000: + reg_data = ((fuse_value & IRAM1_ADDR_BIT_MASK) | + (IRAM1_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, IRAM1_BASE + 4, ®_data, 1); + break; + case 0xE0000: + reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) | + (BRAM_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, BRAM_BASE, ®_data, 1); + break; + case 0xF0000: + reg_data = ((fuse_value & BRAM_ADDR_BIT_MASK) | + (BRAM_ADDR_BIT_MASK + 0x1)); + IFX_MEI_DMAWrite (pDev, BRAM_BASE + 4, ®_data, 1); + break; + default: // PPE efuse + break; + } + } + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); + IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data & ~(1 << 24)); + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); +} + +/** + * Enable DFE Clock + * This function enables DFE Clock + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_EnableCLK (DSL_DEV_Device_t * pDev) +{ + u32 arc_debug_data = 0; + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + //enable ac_clk signal + _IFX_MEI_DBGLongWordRead (pDev, ME_DBG_DECODE_DMP1_MASK, + CRI_CCR0, &arc_debug_data); + arc_debug_data |= ACL_CLK_MODE_ENABLE; + _IFX_MEI_DBGLongWordWrite (pDev, ME_DBG_DECODE_DMP1_MASK, + CRI_CCR0, arc_debug_data); + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * Halt the ARC. + * This function halts the ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_HaltArc (DSL_DEV_Device_t * pDev) +{ + u32 arc_debug_data = 0x0; + + // Switch arc control from JTAG mode to MEI mode + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK, + ARC_DEBUG, &arc_debug_data); + arc_debug_data |= ARC_DEBUG_HALT; + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, + ARC_DEBUG, arc_debug_data); + // Switch arc control from MEI mode to JTAG mode + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + MEI_WAIT (10); + + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * Run the ARC. + * This function runs the ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_RunArc (DSL_DEV_Device_t * pDev) +{ + u32 arc_debug_data = 0x0; + + // Switch arc control from JTAG mode to MEI mode- write '1' to bit0 + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + _IFX_MEI_DBGLongWordRead (pDev, MEI_DEBUG_DEC_AUX_MASK, + AUX_STATUS, &arc_debug_data); + + // Write debug data reg with content ANDd with 0xFDFFFFFF (halt bit cleared) + arc_debug_data &= ~ARC_AUX_HALT; + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, + AUX_STATUS, arc_debug_data); + + // Switch arc control from MEI mode to JTAG mode- write '0' to bit0 + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + // Enable mask for arc codeswap interrupts + IFX_MEI_IRQEnable (pDev); + + return DSL_DEV_MEI_ERR_SUCCESS; + +} + +/** + * Reset the ARC. + * This function resets the ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_ResetARC (DSL_DEV_Device_t * pDev) +{ + u32 arc_debug_data = 0; + + IFX_MEI_HaltArc (pDev); + + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, &arc_debug_data); + IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, + arc_debug_data | LQ_RCU_RST_REQ_DFE | LQ_RCU_RST_REQ_AFE); + + // reset ARC + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, MEI_SOFT_RESET); + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_RST_CTRL, 0); + + IFX_MEI_IRQDisable (pDev); + + IFX_MEI_EnableCLK (pDev); + +#if 0 + // reset part of PPE + *(unsigned long *) (BSP_PPE32_SRST) = 0xC30; + *(unsigned long *) (BSP_PPE32_SRST) = 0xFFF; +#endif + + DSL_DEV_PRIVATE(pDev)->modem_ready = 0; + + return DSL_DEV_MEI_ERR_SUCCESS; +} + +DSL_DEV_MeiError_t +DSL_BSP_Showtime (DSL_DEV_Device_t * dev, DSL_uint32_t rate_fast, DSL_uint32_t rate_intl) +{ + struct port_cell_info port_cell = {0}; + + IFX_MEI_EMSG ("Datarate US intl = %d, fast = %d\n", (int)rate_intl, + (int)rate_fast); + + if ( rate_fast ) + g_tx_link_rate[0] = rate_fast / (53 * 8); + if ( rate_intl ) + g_tx_link_rate[1] = rate_intl / (53 * 8); + + if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ) { + IFX_MEI_EMSG ("Got rate fail.\n"); + } + + if ( ifx_mei_atm_showtime_enter ) + { + port_cell.port_num = 2; + port_cell.tx_link_rate[0] = g_tx_link_rate[0]; + port_cell.tx_link_rate[1] = g_tx_link_rate[1]; + ifx_mei_atm_showtime_enter(&port_cell, g_xdata_addr); + } + else + { + IFX_MEI_EMSG("no hookup from ATM driver to set cell rate\n"); + } + + return DSL_DEV_MEI_ERR_SUCCESS; +}; + +/** + * Reset/halt/run the DFE. + * This function provide operations to reset/halt/run the DFE. + * + * \param pDev the device pointer + * \param mode which operation want to do + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_CpuModeSet (DSL_DEV_Device_t *pDev, + DSL_DEV_CpuMode_t mode) +{ + DSL_DEV_MeiError_t err_ret = DSL_DEV_MEI_ERR_FAILURE; + switch (mode) { + case DSL_CPU_HALT: + err_ret = IFX_MEI_HaltArc (pDev); + break; + case DSL_CPU_RUN: + err_ret = IFX_MEI_RunArc (pDev); + break; + case DSL_CPU_RESET: + err_ret = IFX_MEI_ResetARC (pDev); + break; + default: + break; + } + return err_ret; +} + +/** + * Accress DFE memory. + * This function provide a way to access DFE memory; + * + * \param pDev the device pointer + * \param type read or write + * \param destaddr destination address + * \param databuff pointer to hold data + * \param databuffsize size want to read/write + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +DSL_DEV_MeiError_t +DSL_BSP_MemoryDebugAccess (DSL_DEV_Device_t * pDev, + DSL_BSP_MemoryAccessType_t type, + DSL_uint32_t destaddr, DSL_uint32_t *databuff, + DSL_uint32_t databuffsize) +{ + DSL_DEV_MeiError_t meierr = DSL_DEV_MEI_ERR_SUCCESS; + switch (type) { + case DSL_BSP_MEMORY_READ: + meierr = IFX_MEI_DebugRead (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize); + break; + case DSL_BSP_MEMORY_WRITE: + meierr = IFX_MEI_DebugWrite (pDev, (u32)destaddr, (u32*)databuff, (u32)databuffsize); + break; + } + return DSL_DEV_MEI_ERR_SUCCESS; +}; + +/** + * Download boot code to ARC. + * This function downloads boot code to ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_DownloadBootCode (DSL_DEV_Device_t *pDev) +{ + IFX_MEI_IRQDisable (pDev); + + IFX_MEI_EnableCLK (pDev); + + IFX_MEI_FuseProg (pDev); //program fuse rar + + IFX_MEI_DownloadBootPages (pDev); + + return DSL_DEV_MEI_ERR_SUCCESS; +}; + +/** + * Enable Jtag debugger interface + * This function setups mips gpio to enable jtag debugger + * + * \param pDev the device pointer + * \param enable enable or disable + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_ArcJtagEnable (DSL_DEV_Device_t *dev, int enable) +{ + /* + int meierr=0; + u32 reg_data; + switch (enable) { + case 1: + //reserve gpio 9, 10, 11, 14, 19 for ARC JTAG + ifxmips_port_reserve_pin (0, 9); + ifxmips_port_reserve_pin (0, 10); + ifxmips_port_reserve_pin (0, 11); + ifxmips_port_reserve_pin (0, 14); + ifxmips_port_reserve_pin (1, 3); + + ifxmips_port_set_dir_in(0, 11); + ifxmips_port_clear_altsel0(0, 11); + ifxmips_port_clear_altsel1(0, 11); + ifxmips_port_set_open_drain(0, 11); + //enable ARC JTAG + IFX_MEI_LongWordRead ((u32) LQ_RCU_RST, ®_data); + IFX_MEI_LongWordWrite ((u32) LQ_RCU_RST, reg_data | LQ_RCU_RST_REQ_ARC_JTAG); + break; + case 0: + default: + break; + } +jtag_end: + if (meierr) + return DSL_DEV_MEI_ERR_FAILURE; +*/ + printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__); + printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__); + + return DSL_DEV_MEI_ERR_SUCCESS; +}; + +/** + * Enable DFE to MIPS interrupt + * This function enable DFE to MIPS interrupt + * + * \param pDev the device pointer + * \param enable enable or disable + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_AdslMailboxIRQEnable (DSL_DEV_Device_t *pDev, int enable) +{ + DSL_DEV_MeiError_t meierr; + switch (enable) { + case 0: + meierr = DSL_DEV_MEI_ERR_SUCCESS; + IFX_MEI_IRQDisable (pDev); + break; + case 1: + IFX_MEI_IRQEnable (pDev); + meierr = DSL_DEV_MEI_ERR_SUCCESS; + break; + default: + meierr = DSL_DEV_MEI_ERR_FAILURE; + break; + + } + return meierr; +} + +/** + * Get the modem status + * This function return the modem status + * + * \param pDev the device pointer + * \return 1: modem ready 0: not ready + * \ingroup Internal + */ +static int +IFX_MEI_IsModemReady (DSL_DEV_Device_t * pDev) +{ + return DSL_DEV_PRIVATE(pDev)->modem_ready; +} + +DSL_DEV_MeiError_t +DSL_BSP_AdslLedInit (DSL_DEV_Device_t * dev, + DSL_DEV_LedId_t led_number, + DSL_DEV_LedType_t type, + DSL_DEV_LedHandler_t handler) +{ +#if 0 + struct led_config_param param; + if (led_number == DSL_LED_LINK_ID && type == DSL_LED_LINK_TYPE && handler == /*DSL_LED_HD_CPU*/DSL_LED_HD_FW) { + param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE; + param.led = 0x01; + param.source = 0x01; +// bsp_led_config (¶m); + + } else if (led_number == DSL_LED_DATA_ID && type == DSL_LED_DATA_TYPE && (handler == DSL_LED_HD_FW)) { + param.operation_mask = CONFIG_OPERATION_UPDATE_SOURCE; + param.led = 0x02; + param.source = 0x02; +// bsp_led_config (¶m); + } +#endif + return DSL_DEV_MEI_ERR_SUCCESS; +}; +#if 0 +DSL_DEV_MeiError_t +DSL_BSP_AdslLedSet (DSL_DEV_Device_t * dev, DSL_DEV_LedId_t led_number, DSL_DEV_LedMode_t mode) +{ + printk(KERN_INFO "[%s %d]: mode = %#x, led_number = %d\n", __func__, __LINE__, mode, led_number); + switch (mode) { + case DSL_LED_OFF: + switch (led_number) { + case DSL_LED_LINK_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (1, 0); + bsp_led_set_data (1, 0); +#endif + break; + case DSL_LED_DATA_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (0, 0); + bsp_led_set_data (0, 0); +#endif + break; + } + break; + case DSL_LED_FLASH: + switch (led_number) { + case DSL_LED_LINK_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (1, 1); // data +#endif + break; + case DSL_LED_DATA_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (0, 1); // data +#endif + break; + } + break; + case DSL_LED_ON: + switch (led_number) { + case DSL_LED_LINK_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (1, 0); + bsp_led_set_data (1, 1); +#endif + break; + case DSL_LED_DATA_ID: +#ifdef CONFIG_BSP_LED + bsp_led_set_blink (0, 0); + bsp_led_set_data (0, 1); +#endif + break; + } + break; + } + return DSL_DEV_MEI_ERR_SUCCESS; +}; + +#endif + +/** +* Compose a message. +* This function compose a message from opcode, group, address, index, size, and data +* +* \param opcode The message opcode +* \param group The message group number +* \param address The message address. +* \param index The message index. +* \param size The number of words to read/write. +* \param data The pointer to data. +* \param CMVMSG The pointer to message buffer. +* \ingroup Internal +*/ +void +makeCMV (u8 opcode, u8 group, u16 address, u16 index, int size, u16 * data, u16 *CMVMSG) +{ + memset (CMVMSG, 0, MSG_LENGTH * 2); + CMVMSG[0] = (opcode << 4) + (size & 0xf); + CMVMSG[1] = (((index == 0) ? 0 : 1) << 7) + (group & 0x7f); + CMVMSG[2] = address; + CMVMSG[3] = index; + if (opcode == H2D_CMV_WRITE) + memcpy (CMVMSG + 4, data, size * 2); + return; +} + +/** + * Send a message to ARC and read the response + * This function sends a message to arc, waits the response, and reads the responses. + * + * \param pDev the device pointer + * \param request Pointer to the request + * \param reply Wait reply or not. + * \param response Pointer to the response + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +DSL_DEV_MeiError_t +DSL_BSP_SendCMV (DSL_DEV_Device_t * pDev, u16 * request, int reply, u16 * response) // write cmv to arc, if reply needed, wait for reply +{ + DSL_DEV_MeiError_t meierror; +#if defined(BSP_PORT_RTEMS) + int delay_counter = 0; +#endif + + if (MEI_MUTEX_LOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema)) + return -ERESTARTSYS; + + DSL_DEV_PRIVATE(pDev)->cmv_reply = reply; + memset (DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, 0, + sizeof (DSL_DEV_PRIVATE(pDev)-> + CMV_RxMsg)); + DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; + + meierror = IFX_MEI_MailboxWrite (pDev, request, MSG_LENGTH); + + if (meierror != DSL_DEV_MEI_ERR_SUCCESS) { + DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0; + DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; + IFX_MEI_EMSG ("MailboxWrite Fail!\n"); + IFX_MEI_EMSG ("Resetting ARC...\n"); + IFX_MEI_ResetARC(pDev); + MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); + return meierror; + } + else { + DSL_DEV_PRIVATE(pDev)->cmv_count++; + } + + if (DSL_DEV_PRIVATE(pDev)->cmv_reply == + NO_REPLY) { + MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); + return DSL_DEV_MEI_ERR_SUCCESS; + } + +#if !defined(BSP_PORT_RTEMS) + if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0) + MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav, CMV_TIMEOUT); +#else + while (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0 && delay_counter < CMV_TIMEOUT / 5) { + MEI_WAIT (5); + delay_counter++; + } +#endif + + DSL_DEV_PRIVATE(pDev)->cmv_waiting = 0; + if (DSL_DEV_PRIVATE(pDev)->arcmsgav == 0) { //CMV_timeout + DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; + IFX_MEI_EMSG ("\%s: DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT\n", + __FUNCTION__); + MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); + return DSL_DEV_MEI_ERR_MAILBOX_TIMEOUT; + } + else { + DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; + DSL_DEV_PRIVATE(pDev)-> + reply_count++; + memcpy (response, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2); + MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); + return DSL_DEV_MEI_ERR_SUCCESS; + } + MEI_MUTEX_UNLOCK (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema); + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/** + * Reset the ARC, download boot codes, and run the ARC. + * This function resets the ARC, downloads boot codes to ARC, and runs the ARC. + * + * \param pDev the device pointer + * \return DSL_DEV_MEI_ERR_SUCCESS or DSL_DEV_MEI_ERR_FAILURE + * \ingroup Internal + */ +static DSL_DEV_MeiError_t +IFX_MEI_RunAdslModem (DSL_DEV_Device_t *pDev) +{ + int nSize = 0, idx = 0; + uint32_t im0_register, im2_register; +// DSL_DEV_WinHost_Message_t m; + + if (mei_arc_swap_buff == NULL) { + mei_arc_swap_buff = + (u32 *) kmalloc (MAXSWAPSIZE * 4, GFP_KERNEL); + if (mei_arc_swap_buff == NULL) { + IFX_MEI_EMSG (">>> malloc fail for codeswap buff!!! <<<\n"); + return DSL_DEV_MEI_ERR_FAILURE; + } + IFX_MEI_DMSG("allocate %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff); + } + + DSL_DEV_PRIVATE(pDev)->img_hdr = + (ARC_IMG_HDR *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[0].address; + if ((DSL_DEV_PRIVATE(pDev)->img_hdr-> + count) * sizeof (ARC_SWP_PAGE_HDR) > SDRAM_SEGMENT_SIZE) { + IFX_MEI_EMSG ("firmware header size is bigger than 64K segment size\n"); + return DSL_DEV_MEI_ERR_FAILURE; + } + // check image size + for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) { + nSize += DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].nCopy; + } + if (nSize != + DSL_DEV_PRIVATE(pDev)->image_size) { + IFX_MEI_EMSG ("Firmware download is not completed. Please download firmware again!\n"); + return DSL_DEV_MEI_ERR_FAILURE; + } + // TODO: check crc + /// + + IFX_MEI_ResetARC (pDev); + IFX_MEI_HaltArc (pDev); + IFX_MEI_BarUpdate (pDev, DSL_DEV_PRIVATE(pDev)->nBar); + + //IFX_MEI_DMSG("Starting to meiDownloadBootCode\n"); + + IFX_MEI_DownloadBootCode (pDev); + + im0_register = (*LQ_ICU_IM0_IER) & (1 << 20); + im2_register = (*LQ_ICU_IM2_IER) & (1 << 20); + /* Turn off irq */ + #ifdef CONFIG_LANTIQ_AMAZON_SE + disable_irq (IFXMIPS_USB_OC_INT0); + disable_irq (IFXMIPS_USB_OC_INT2); + #elif defined(CONFIG_LANTIQ_AR9) + disable_irq (IFXMIPS_USB_OC_INT0); + disable_irq (IFXMIPS_USB_OC_INT2); + #elif defined(CONFIG_SOC_LANTIQ_XWAY) + disable_irq (LQ_USB_OC_INT); + #else + #error unkonwn arch + #endif + disable_irq (pDev->nIrq[IFX_DYING_GASP]); + + IFX_MEI_RunArc (pDev); + + MEI_WAIT_EVENT_TIMEOUT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready, 1000); + + #ifdef CONFIG_LANTIQ_AMAZON_SE + MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0); + MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2); + #elif defined(CONFIG_LANTIQ_AMAZON_S) + MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT0); + MEI_MASK_AND_ACK_IRQ (IFXMIPS_USB_OC_INT2); + #elif defined(CONFIG_SOC_LANTIQ_XWAY) + MEI_MASK_AND_ACK_IRQ (LQ_USB_OC_INT); + #else + #error unkonwn arch + #endif + MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]); + + /* Re-enable irq */ + enable_irq(pDev->nIrq[IFX_DYING_GASP]); + *LQ_ICU_IM0_IER |= im0_register; + *LQ_ICU_IM2_IER |= im2_register; + + if (DSL_DEV_PRIVATE(pDev)->modem_ready != 1) { + IFX_MEI_EMSG ("Modem failed to be ready!\n"); + return DSL_DEV_MEI_ERR_FAILURE; + } else { + IFX_MEI_DMSG("Modem is ready.\n"); + return DSL_DEV_MEI_ERR_SUCCESS; + } +} + +/** + * Get the page's data pointer + * This function caculats the data address from the firmware header. + * + * \param pDev the device pointer + * \param Page The page number. + * \param data Data page or program page. + * \param MaxSize The maximum size to read. + * \param Buffer Pointer to data. + * \param Dest Pointer to the destination address. + * \return The number of bytes to read. + * \ingroup Internal + */ +static int +IFX_MEI_GetPage (DSL_DEV_Device_t * pDev, u32 Page, u32 data, + u32 MaxSize, u32 * Buffer, u32 * Dest) +{ + u32 size; + u32 i; + u32 *p; + u32 idx, offset, nBar = 0; + + if (Page > DSL_DEV_PRIVATE(pDev)->img_hdr->count) + return -2; + /* + ** Get program or data size, depending on "data" flag + */ + size = (data == GET_DATA) ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_size) : + (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_size); + size &= BOOT_FLAG_MASK; // Clear boot bit! + if (size > MaxSize) + return -1; + + if (size == 0) + return 0; + /* + ** Get program or data offset, depending on "data" flag + */ + i = data ? (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].d_offset) : + (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_offset); + + /* + ** Copy data/program to buffer + */ + + idx = i / SDRAM_SEGMENT_SIZE; + offset = i % SDRAM_SEGMENT_SIZE; + p = (u32 *) ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address + offset); + + for (i = 0; i < size; i++) { + if (offset + i * 4 - (nBar * SDRAM_SEGMENT_SIZE) >= SDRAM_SEGMENT_SIZE) { + idx++; + nBar++; + p = (u32 *) ((u8 *) KSEG1ADDR ((u32)DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address)); + } + Buffer[i] = *p++; + } + + /* + ** Pass back data/program destination address + */ + *Dest = data ? (DSL_DEV_PRIVATE(pDev)-> img_hdr->page[Page].d_dest) : + (DSL_DEV_PRIVATE(pDev)->img_hdr->page[Page].p_dest); + + return size; +} + +/** + * Free the memory for ARC firmware + * + * \param pDev the device pointer + * \param type Free all memory or free the unused memory after showtime + * \ingroup Internal + */ +const char *free_str[4] = {"Invalid", "Free_Reload", "Free_Showtime", "Free_All"}; +static int +IFX_MEI_DFEMemoryFree (DSL_DEV_Device_t * pDev, int type) +{ + int idx = 0; + smmu_mem_info_t *adsl_mem_info = + DSL_DEV_PRIVATE(pDev)->adsl_mem_info; + + for (idx = 0; idx < MAX_BAR_REGISTERS; idx++) { + if (type == FREE_ALL ||adsl_mem_info[idx].type == type) { + if (adsl_mem_info[idx].size > 0) { + IFX_MEI_DMSG ("Freeing memory %p (%s)\n", adsl_mem_info[idx].org_address, free_str[adsl_mem_info[idx].type]); + if ( idx == XDATA_REGISTER ) { + g_xdata_addr = NULL; + if ( ifx_mei_atm_showtime_exit ) + ifx_mei_atm_showtime_exit(); + } + kfree (adsl_mem_info[idx].org_address); + adsl_mem_info[idx].org_address = 0; + adsl_mem_info[idx].address = 0; + adsl_mem_info[idx].size = 0; + adsl_mem_info[idx].type = 0; + adsl_mem_info[idx].nCopy = 0; + } + } + } + + if(mei_arc_swap_buff != NULL){ + IFX_MEI_DMSG("free %dKB swap buff memory at: 0x%p\n", ksize(mei_arc_swap_buff)/1024, mei_arc_swap_buff); + kfree(mei_arc_swap_buff); + mei_arc_swap_buff=NULL; + } + + return 0; +} +static int +IFX_MEI_DFEMemoryAlloc (DSL_DEV_Device_t * pDev, long size) +{ + unsigned long mem_ptr; + char *org_mem_ptr = NULL; + int idx = 0; + long total_size = 0; + int err = 0; + smmu_mem_info_t *adsl_mem_info = + ((ifx_mei_device_private_t *) pDev->pPriv)->adsl_mem_info; +// DSL_DEV_PRIVATE(pDev)->adsl_mem_info; + int allocate_size = SDRAM_SEGMENT_SIZE; + + IFX_MEI_DMSG("image_size = %ld\n", size); + // Alloc Swap Pages + for (idx = 0; size > 0 && idx < MAX_BAR_REGISTERS; idx++) { + // skip bar15 for XDATA usage. + if (idx == XDATA_REGISTER) + continue; +#if 0 + if (size < SDRAM_SEGMENT_SIZE) { + allocate_size = size; + if (allocate_size < 1024) + allocate_size = 1024; + } +#endif + if (idx == (MAX_BAR_REGISTERS - 1)) + allocate_size = size; + else + allocate_size = SDRAM_SEGMENT_SIZE; + org_mem_ptr = kmalloc (allocate_size + 1024, GFP_KERNEL); + if (org_mem_ptr == NULL) { + IFX_MEI_EMSG ("%d: kmalloc %d bytes memory fail!\n", idx, allocate_size); + err = -ENOMEM; + goto allocate_error; + } + mem_ptr = (unsigned long) (org_mem_ptr + 1023) & ~(1024 -1); + adsl_mem_info[idx].address = (char *) mem_ptr; + adsl_mem_info[idx].org_address = org_mem_ptr; + adsl_mem_info[idx].size = allocate_size; + size -= allocate_size; + total_size += allocate_size; + } + if (size > 0) { + IFX_MEI_EMSG ("Image size is too large!\n"); + err = -EFBIG; + goto allocate_error; + } + err = idx; + return err; + + allocate_error: + IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); + return err; +} + +/** + * Program the BAR registers + * + * \param pDev the device pointer + * \param nTotalBar The number of bar to program. + * \ingroup Internal + */ +static int +IFX_MEI_BarUpdate (DSL_DEV_Device_t * pDev, int nTotalBar) +{ + int idx = 0; + smmu_mem_info_t *adsl_mem_info = + DSL_DEV_PRIVATE(pDev)->adsl_mem_info; + + for (idx = 0; idx < nTotalBar; idx++) { + //skip XDATA register + if (idx == XDATA_REGISTER) + continue; + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + idx * 4, + (((uint32_t) adsl_mem_info[idx].address) & 0x0FFFFFFF)); + } + for (idx = nTotalBar; idx < MAX_BAR_REGISTERS; idx++) { + if (idx == XDATA_REGISTER) + continue; + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + idx * 4, + (((uint32_t)adsl_mem_info[nTotalBar - 1].address) & 0x0FFFFFFF)); + /* These are for /proc/danube_mei/meminfo purpose */ + adsl_mem_info[idx].address = adsl_mem_info[nTotalBar - 1].address; + adsl_mem_info[idx].org_address = adsl_mem_info[nTotalBar - 1].org_address; + adsl_mem_info[idx].size = 0; /* Prevent it from being freed */ + } + + g_xdata_addr = adsl_mem_info[XDATA_REGISTER].address; + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XMEM_BAR_BASE + XDATA_REGISTER * 4, + (((uint32_t) adsl_mem_info [XDATA_REGISTER].address) & 0x0FFFFFFF)); + // update MEI_XDATA_BASE_SH + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH, + ((unsigned long)adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF); + + return DSL_DEV_MEI_ERR_SUCCESS; +} + +/* This copies the firmware from secondary storage to 64k memory segment in SDRAM */ +DSL_DEV_MeiError_t +DSL_BSP_FWDownload (DSL_DEV_Device_t * pDev, const char *buf, + unsigned long size, long *loff, long *current_offset) +{ + ARC_IMG_HDR img_hdr_tmp; + smmu_mem_info_t *adsl_mem_info = DSL_DEV_PRIVATE(pDev)->adsl_mem_info; + + size_t nRead = 0, nCopy = 0; + char *mem_ptr; + ssize_t retval = -ENOMEM; + int idx = 0; + + IFX_MEI_DMSG("\n"); + + if (*loff == 0) { + if (size < sizeof (img_hdr_tmp)) { + IFX_MEI_EMSG ("Firmware size is too small!\n"); + return retval; + } + copy_from_user ((char *) &img_hdr_tmp, buf, sizeof (img_hdr_tmp)); + // header of image_size and crc are not included. + DSL_DEV_PRIVATE(pDev)->image_size = le32_to_cpu (img_hdr_tmp.size) + 8; + + if (DSL_DEV_PRIVATE(pDev)->image_size > 1024 * 1024) { + IFX_MEI_EMSG ("Firmware size is too large!\n"); + return retval; + } + // check if arc is halt + IFX_MEI_ResetARC (pDev); + IFX_MEI_HaltArc (pDev); + + IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); //free all + + retval = IFX_MEI_DFEMemoryAlloc (pDev, DSL_DEV_PRIVATE(pDev)->image_size); + if (retval < 0) { + IFX_MEI_EMSG ("Error: No memory space left.\n"); + goto error; + } + for (idx = 0; idx < retval; idx++) { + //skip XDATA register + if (idx == XDATA_REGISTER) + continue; + if (idx * SDRAM_SEGMENT_SIZE < le32_to_cpu (img_hdr_tmp.page[0].p_offset)) + adsl_mem_info[idx].type = FREE_RELOAD; + else + adsl_mem_info[idx].type = FREE_SHOWTIME; + } + DSL_DEV_PRIVATE(pDev)->nBar = retval; + + DSL_DEV_PRIVATE(pDev)->img_hdr = + (ARC_IMG_HDR *) adsl_mem_info[0].address; + + adsl_mem_info[XDATA_REGISTER].org_address = kmalloc (SDRAM_SEGMENT_SIZE + 1024, GFP_KERNEL); + adsl_mem_info[XDATA_REGISTER].address = + (char *) ((unsigned long) (adsl_mem_info[XDATA_REGISTER].org_address + 1023) & 0xFFFFFC00); + + adsl_mem_info[XDATA_REGISTER].size = SDRAM_SEGMENT_SIZE; + + if (adsl_mem_info[XDATA_REGISTER].address == NULL) { + IFX_MEI_EMSG ("kmalloc memory fail!\n"); + retval = -ENOMEM; + goto error; + } + adsl_mem_info[XDATA_REGISTER].type = FREE_RELOAD; + IFX_MEI_DMSG("-> IFX_MEI_BarUpdate()\n"); + IFX_MEI_BarUpdate (pDev, (DSL_DEV_PRIVATE(pDev)->nBar)); + } + else if (DSL_DEV_PRIVATE(pDev)-> image_size == 0) { + IFX_MEI_EMSG ("Error: Firmware size=0! \n"); + goto error; + } + + nRead = 0; + while (nRead < size) { + long offset = ((long) (*loff) + nRead) % SDRAM_SEGMENT_SIZE; + idx = (((long) (*loff)) + nRead) / SDRAM_SEGMENT_SIZE; + mem_ptr = (char *) KSEG1ADDR ((unsigned long) (adsl_mem_info[idx].address) + offset); + if ((size - nRead + offset) > SDRAM_SEGMENT_SIZE) + nCopy = SDRAM_SEGMENT_SIZE - offset; + else + nCopy = size - nRead; + copy_from_user (mem_ptr, buf + nRead, nCopy); + for (offset = 0; offset < (nCopy / 4); offset++) { + ((unsigned long *) mem_ptr)[offset] = le32_to_cpu (((unsigned long *) mem_ptr)[offset]); + } + nRead += nCopy; + adsl_mem_info[idx].nCopy += nCopy; + } + + *loff += size; + *current_offset = size; + return DSL_DEV_MEI_ERR_SUCCESS; +error: + IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); + return DSL_DEV_MEI_ERR_FAILURE; +} +/* + * Register a callback event. + * Return: + * -1 if the event already has a callback function registered. + * 0 success + */ +int DSL_BSP_EventCBRegister(DSL_BSP_EventCallBack_t *p) +{ + if (!p) { + IFX_MEI_EMSG("Invalid parameter!\n"); + return -EINVAL; + } + if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) { + IFX_MEI_EMSG("Invalid Event %d\n", p->event); + return -EINVAL; + } + if (dsl_bsp_event_callback[p->event].function) { + IFX_MEI_EMSG("Event %d already has a callback function registered!\n", p->event); + return -1; + } else { + dsl_bsp_event_callback[p->event].function = p->function; + dsl_bsp_event_callback[p->event].event = p->event; + dsl_bsp_event_callback[p->event].pData = p->pData; + } + return 0; +} +int DSL_BSP_EventCBUnregister(DSL_BSP_EventCallBack_t *p) +{ + if (!p) { + IFX_MEI_EMSG("Invalid parameter!\n"); + return -EINVAL; + } + if (p->event > DSL_BSP_CB_LAST || p->event < DSL_BSP_CB_FIRST) { + IFX_MEI_EMSG("Invalid Event %d\n", p->event); + return -EINVAL; + } + if (dsl_bsp_event_callback[p->event].function) { + IFX_MEI_EMSG("Unregistering Event %d...\n", p->event); + dsl_bsp_event_callback[p->event].function = NULL; + dsl_bsp_event_callback[p->event].pData = NULL; + } else { + IFX_MEI_EMSG("Event %d is not registered!\n", p->event); + return -1; + } + return 0; +} + +/** + * MEI Dying Gasp interrupt handler + * + * \param int1 + * \param void0 + * \param regs Pointer to the structure of danube mips registers + * \ingroup Internal + */ +static irqreturn_t IFX_MEI_Dying_Gasp_IrqHandle (int int1, void *void0) +{ + DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0; + DSL_BSP_CB_Type_t event; + + if (pDev == NULL) + IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n"); + +#ifndef CONFIG_SMP + disable_irq (pDev->nIrq[IFX_DYING_GASP]); +#else + disable_irq_nosync(pDev->nIrq[IFX_DYING_GASP]); +#endif + event = DSL_BSP_CB_DYING_GASP; + + if (dsl_bsp_event_callback[event].function) + (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); + +#ifdef CONFIG_USE_EMULATOR + IFX_MEI_EMSG("Dying Gasp! Shutting Down... (Work around for Amazon-S Venus emulator)\n"); +#else + IFX_MEI_EMSG("Dying Gasp! Shutting Down...\n"); +// kill_proc (1, SIGINT, 1); /* Ask init to reboot us */ +#endif + return IRQ_HANDLED; +} + +extern void ifx_usb_enable_afe_oc(void); + +/** + * MEI interrupt handler + * + * \param int1 + * \param void0 + * \param regs Pointer to the structure of danube mips registers + * \ingroup Internal + */ +static irqreturn_t IFX_MEI_IrqHandle (int int1, void *void0) +{ + u32 scratch; + DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) void0; +#if defined(CONFIG_LQ_MEI_FW_LOOPBACK) && defined(DFE_PING_TEST) + dfe_loopback_irq_handler (pDev); + return IRQ_HANDLED; +#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK + DSL_BSP_CB_Type_t event; + + if (pDev == NULL) + IFX_MEI_EMSG("Error: Got Interrupt but pDev is NULL!!!!\n"); + + IFX_MEI_DebugRead (pDev, ARC_MEI_MAILBOXR, &scratch, 1); + if (scratch & OMB_CODESWAP_MESSAGE_MSG_TYPE_MASK) { + IFX_MEI_EMSG("Receive Code Swap Request interrupt!!!\n"); + return IRQ_HANDLED; + } + else if (scratch & OMB_CLEAREOC_INTERRUPT_CODE) { + // clear eoc message interrupt + IFX_MEI_DMSG("OMB_CLEAREOC_INTERRUPT_CODE\n"); + event = DSL_BSP_CB_CEOC_IRQ; + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); + if (dsl_bsp_event_callback[event].function) + (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); + } else if (scratch & OMB_REBOOT_INTERRUPT_CODE) { + // Reboot + IFX_MEI_DMSG("OMB_REBOOT_INTERRUPT_CODE\n"); + event = DSL_BSP_CB_FIRMWARE_REBOOT; + + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_ARC2ME_STAT, ARC_TO_MEI_MSGAV); + + if (dsl_bsp_event_callback[event].function) + (*dsl_bsp_event_callback[event].function)(pDev, event, dsl_bsp_event_callback[event].pData); + } else { // normal message + IFX_MEI_MailboxRead (pDev, DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH); + if (DSL_DEV_PRIVATE(pDev)-> cmv_waiting == 1) { + DSL_DEV_PRIVATE(pDev)-> arcmsgav = 1; + DSL_DEV_PRIVATE(pDev)-> cmv_waiting = 0; +#if !defined(BSP_PORT_RTEMS) + MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav); +#endif + } + else { + DSL_DEV_PRIVATE(pDev)-> modem_ready_cnt++; + memcpy ((char *) DSL_DEV_PRIVATE(pDev)->Recent_indicator, + (char *) DSL_DEV_PRIVATE(pDev)->CMV_RxMsg, MSG_LENGTH * 2); + if (((DSL_DEV_PRIVATE(pDev)->CMV_RxMsg[0] & 0xff0) >> 4) == D2H_AUTONOMOUS_MODEM_READY_MSG) { + //check ARC ready message + IFX_MEI_DMSG ("Got MODEM_READY_MSG\n"); + DSL_DEV_PRIVATE(pDev)->modem_ready = 1; + MEI_WAKEUP_EVENT (DSL_DEV_PRIVATE(pDev)->wait_queue_modemready); + } + } + } + + return IRQ_HANDLED; +} + +int +DSL_BSP_ATMLedCBRegister (int (*ifx_adsl_ledcallback) (void)) +{ + g_adsl_ledcallback = ifx_adsl_ledcallback; + return 0; +} + +int +DSL_BSP_ATMLedCBUnregister (int (*ifx_adsl_ledcallback) (void)) +{ + g_adsl_ledcallback = adsl_dummy_ledcallback; + return 0; +} + +#if 0 +int +DSL_BSP_EventCBRegister (int (*ifx_adsl_callback) + (DSL_BSP_CB_Event_t * param)) +{ + int error = 0; + + if (DSL_EventCB == NULL) { + DSL_EventCB = ifx_adsl_callback; + } + else { + error = -EIO; + } + return error; +} + +int +DSL_BSP_EventCBUnregister (int (*ifx_adsl_callback) + (DSL_BSP_CB_Event_t * param)) +{ + int error = 0; + + if (DSL_EventCB == ifx_adsl_callback) { + DSL_EventCB = NULL; + } + else { + error = -EIO; + } + return error; +} + +static int +DSL_BSP_GetEventCB (int (**ifx_adsl_callback) + (DSL_BSP_CB_Event_t * param)) +{ + *ifx_adsl_callback = DSL_EventCB; + return 0; +} +#endif + +#ifdef CONFIG_LQ_MEI_FW_LOOPBACK +#define mte_reg_base (0x4800*4+0x20000) + +/* Iridia Registers Address Constants */ +#define MTE_Reg(r) (int)(mte_reg_base + (r*4)) + +#define IT_AMODE MTE_Reg(0x0004) + +#define TIMER_DELAY (1024) +#define BC0_BYTES (32) +#define BC1_BYTES (30) +#define NUM_MB (12) +#define TIMEOUT_VALUE 2000 + +static void +BFMWait (u32 cycle) +{ + u32 i; + for (i = 0; i < cycle; i++); +} + +static void +WriteRegLong (u32 addr, u32 data) +{ + //*((volatile u32 *)(addr)) = data; + IFX_MEI_WRITE_REGISTER_L (data, addr); +} + +static u32 +ReadRegLong (u32 addr) +{ + // u32 rd_val; + //rd_val = *((volatile u32 *)(addr)); + // return rd_val; + return IFX_MEI_READ_REGISTER_L (addr); +} + +/* This routine writes the mailbox with the data in an input array */ +static void +WriteMbox (u32 * mboxarray, u32 size) +{ + IFX_MEI_DebugWrite (&dsl_devices[0], IMBOX_BASE, mboxarray, size); + IFX_MEI_DMSG("write to %X\n", IMBOX_BASE); + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ME2ARC_INT, MEI_TO_ARC_MSGAV); +} + +/* This routine reads the output mailbox and places the results into an array */ +static void +ReadMbox (u32 * mboxarray, u32 size) +{ + IFX_MEI_DebugRead (&dsl_devices[0], OMBOX_BASE, mboxarray, size); + IFX_MEI_DMSG("read from %X\n", OMBOX_BASE); +} + +static void +MEIWriteARCValue (u32 address, u32 value) +{ + u32 i, check = 0; + + /* Write address register */ + IFX_MEI_WRITE_REGISTER_L (address, ME_DBG_WR_AD + LQ_MEI_BASE_ADDR); + + /* Write data register */ + IFX_MEI_WRITE_REGISTER_L (value, ME_DBG_DATA + LQ_MEI_BASE_ADDR); + + /* wait until complete - timeout at 40 */ + for (i = 0; i < 40; i++) { + check = IFX_MEI_READ_REGISTER_L (ME_ARC2ME_STAT + LQ_MEI_BASE_ADDR); + + if ((check & ARC_TO_MEI_DBG_DONE)) + break; + } + /* clear the flag */ + IFX_MEI_WRITE_REGISTER_L (ARC_TO_MEI_DBG_DONE, ME_ARC2ME_STAT + LQ_MEI_BASE_ADDR); +} + +void +arc_code_page_download (uint32_t arc_code_length, uint32_t * start_address) +{ + int count; + + IFX_MEI_DMSG("try to download pages,size=%d\n", arc_code_length); + IFX_MEI_ControlModeSet (&dsl_devices[0], MEI_MASTER_MODE); + IFX_MEI_HaltArc (&dsl_devices[0]); + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_AD, 0); + for (count = 0; count < arc_code_length; count++) { + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_DX_DATA, + *(start_address + count)); + } + IFX_MEI_ControlModeSet (&dsl_devices[0], JTAG_MASTER_MODE); +} +static int +load_jump_table (unsigned long addr) +{ + int i; + uint32_t addr_le, addr_be; + uint32_t jump_table[32]; + + for (i = 0; i < 16; i++) { + addr_le = i * 8 + addr; + addr_be = ((addr_le >> 16) & 0xffff); + addr_be |= ((addr_le & 0xffff) << 16); + jump_table[i * 2 + 0] = 0x0f802020; + jump_table[i * 2 + 1] = addr_be; + //printk("jt %X %08X %08X\n",i,jump_table[i*2+0],jump_table[i*2+1]); + } + arc_code_page_download (32, &jump_table[0]); +return 0; +} + +int got_int = 0; + +void +dfe_loopback_irq_handler (DSL_DEV_Device_t *pDev) +{ + uint32_t rd_mbox[10]; + + memset (&rd_mbox[0], 0, 10 * 4); + ReadMbox (&rd_mbox[0], 6); + if (rd_mbox[0] == 0x0) { + FX_MEI_DMSG("Get ARC_ACK\n"); + got_int = 1; + } + else if (rd_mbox[0] == 0x5) { + IFX_MEI_DMSG("Get ARC_BUSY\n"); + got_int = 2; + } + else if (rd_mbox[0] == 0x3) { + IFX_MEI_DMSG("Get ARC_EDONE\n"); + if (rd_mbox[1] == 0x0) { + got_int = 3; + IFX_MEI_DMSG("Get E_MEMTEST\n"); + if (rd_mbox[2] != 0x1) { + got_int = 4; + IFX_MEI_DMSG("Get Result %X\n", rd_mbox[2]); + } + } + } + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_STAT, + ARC_TO_MEI_DBG_DONE); + MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]); + disable_irq (pDev->nIrq[IFX_DFEIR]); + //got_int = 1; + return; +} + +static void +wait_mem_test_result (void) +{ + uint32_t mbox[5]; + mbox[0] = 0; + + IFX_MEI_DMSG("Waiting Starting\n"); + while (mbox[0] == 0) { + ReadMbox (&mbox[0], 5); + } + IFX_MEI_DMSG("Try to get mem test result.\n"); + ReadMbox (&mbox[0], 5); + if (mbox[0] == 0xA) { + IFX_MEI_DMSG("Success.\n"); + } + else if (mbox[0] == 0xA) { + IFX_MEI_EMSG("Fail,address %X,except data %X,receive data %X\n", + mbox[1], mbox[2], mbox[3]); + } + else { + IFX_MEI_EMSG("Fail\n"); + } +} + +static int +arc_ping_testing (DSL_DEV_Device_t *pDev) +{ +#define MEI_PING 0x00000001 + uint32_t wr_mbox[10], rd_mbox[10]; + int i; + + for (i = 0; i < 10; i++) { + wr_mbox[i] = 0; + rd_mbox[i] = 0; + } + + FX_MEI_DMSG("send ping msg\n"); + wr_mbox[0] = MEI_PING; + WriteMbox (&wr_mbox[0], 10); + + while (got_int == 0) { + MEI_WAIT (100); + } + + IFX_MEI_DMSG("send start event\n"); + got_int = 0; + + wr_mbox[0] = 0x4; + wr_mbox[1] = 0; + wr_mbox[2] = 0; + wr_mbox[3] = (uint32_t) 0xf5acc307e; + wr_mbox[4] = 5; + wr_mbox[5] = 2; + wr_mbox[6] = 0x1c000; + wr_mbox[7] = 64; + wr_mbox[8] = 0; + wr_mbox[9] = 0; + WriteMbox (&wr_mbox[0], 10); + DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]); + //printk("IFX_MEI_MailboxWrite ret=%d\n",i); + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], + (u32) ME_ME2ARC_INT, + MEI_TO_ARC_MSGAV); + IFX_MEI_DMSG("sleeping\n"); + while (1) { + if (got_int > 0) { + + if (got_int > 3) + IFX_MEI_DMSG("got_int >>>> 3\n"); + else + IFX_MEI_DMSG("got int = %d\n", got_int); + got_int = 0; + //schedule(); + DSL_ENABLE_IRQ (pDev->nIrq[IFX_DFEIR]); + } + //mbox_read(&rd_mbox[0],6); + MEI_WAIT (100); + } + return 0; +} + +static DSL_DEV_MeiError_t +DFE_Loopback_Test (void) +{ + int i = 0; + u32 arc_debug_data = 0, temp; + DSL_DEV_Device_t *pDev = &dsl_devices[0]; + uint32_t wr_mbox[10]; + + IFX_MEI_ResetARC (pDev); + // start the clock + arc_debug_data = ACL_CLK_MODE_ENABLE; + IFX_MEI_DebugWrite (pDev, CRI_CCR0, &arc_debug_data, 1); + +#if defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK) + // WriteARCreg(AUX_XMEM_LTEST,0); + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); +#define AUX_XMEM_LTEST 0x128 + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, AUX_XMEM_LTEST, 0); + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + // WriteARCreg(AUX_XDMA_GAP,0); + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); +#define AUX_XDMA_GAP 0x114 + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, AUX_XDMA_GAP, 0); + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); + temp = 0; + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, + (u32) ME_XDATA_BASE_SH + LQ_MEI_BASE_ADDR, temp); + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + i = IFX_MEI_DFEMemoryAlloc (pDev, SDRAM_SEGMENT_SIZE * 16); + if (i >= 0) { + int idx; + + for (idx = 0; idx < i; idx++) { + DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].type = FREE_RELOAD; + IFX_MEI_WRITE_REGISTER_L ((((uint32_t) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address) & 0x0fffffff), + LQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE + idx * 4); + IFX_MEI_DMSG("bar%d(%X)=%X\n", idx, + LQ_MEI_BASE_ADDR + ME_XMEM_BAR_BASE + + idx * 4, (((uint32_t) + ((ifx_mei_device_private_t *) + pDev->pPriv)->adsl_mem_info[idx]. + address) & 0x0fffffff)); + memset ((u8 *) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[idx].address, 0, SDRAM_SEGMENT_SIZE); + } + + IFX_MEI_LongWordWriteOffset (pDev, (u32) ME_XDATA_BASE_SH, + ((unsigned long) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[XDATA_REGISTER].address) & 0x0FFFFFFF); + } + else { + IFX_MEI_EMSG ("cannot load image: no memory\n"); + return DSL_DEV_MEI_ERR_FAILURE; + } + //WriteARCreg(AUX_IC_CTRL,2); + IFX_MEI_DMSG("Setting MEI_MASTER_MODE..\n"); + IFX_MEI_ControlModeSet (pDev, MEI_MASTER_MODE); +#define AUX_IC_CTRL 0x11 + _IFX_MEI_DBGLongWordWrite (pDev, MEI_DEBUG_DEC_AUX_MASK, + AUX_IC_CTRL, 2); + IFX_MEI_DMSG("Setting JTAG_MASTER_MODE..\n"); + IFX_MEI_ControlModeSet (pDev, JTAG_MASTER_MODE); + + IFX_MEI_DMSG("Halting ARC...\n"); + IFX_MEI_HaltArc (&dsl_devices[0]); + +#ifdef DFE_PING_TEST + + IFX_MEI_DMSG("ping test image size=%d\n", sizeof (arc_ahb_access_code)); + memcpy ((u8 *) (DSL_DEV_PRIVATE(pDev)-> + adsl_mem_info[0].address + 0x1004), + &arc_ahb_access_code[0], sizeof (arc_ahb_access_code)); + load_jump_table (0x80000 + 0x1004); + +#endif //DFE_PING_TEST + + IFX_MEI_DMSG("ARC ping test code download complete\n"); +#endif //defined( DFE_PING_TEST )|| defined( DFE_ATM_LOOPBACK) +#ifdef DFE_MEM_TEST + IFX_MEI_LongWordWriteOffset (&dsl_devices[0], (u32) ME_ARC2ME_MASK, MSGAV_EN); + + arc_code_page_download (1537, &code_array[0]); + IFX_MEI_DMSG("ARC mem test code download complete\n"); +#endif //DFE_MEM_TEST +#ifdef DFE_ATM_LOOPBACK + arc_debug_data = 0xf; + arc_code_page_download (sizeof(code_array) / sizeof(*code_array), &code_array[0]); + wr_mbox[0] = 0; //TIMER_DELAY - org: 1024 + wr_mbox[1] = 0; //TXFB_START0 + wr_mbox[2] = 0x7f; //TXFB_END0 - org: 49 + wr_mbox[3] = 0x80; //TXFB_START1 - org: 80 + wr_mbox[4] = 0xff; //TXFB_END1 - org: 109 + wr_mbox[5] = 0x100; //RXFB_START0 - org: 0 + wr_mbox[6] = 0x17f; //RXFB_END0 - org: 49 + wr_mbox[7] = 0x180; //RXFB_START1 - org: 256 + wr_mbox[8] = 0x1ff; //RXFB_END1 - org: 315 + WriteMbox (&wr_mbox[0], 9); + // Start Iridia IT_AMODE (in dmp access) why is it required? + IFX_MEI_DebugWrite (&dsl_devices[0], 0x32010, &arc_debug_data, 1); +#endif //DFE_ATM_LOOPBACK + IFX_MEI_IRQEnable (pDev); + IFX_MEI_DMSG("run ARC...\n"); + IFX_MEI_RunArc (&dsl_devices[0]); + +#ifdef DFE_PING_TEST + arc_ping_testing (pDev); +#endif //DFE_PING_TEST +#ifdef DFE_MEM_TEST + wait_mem_test_result (); +#endif //DFE_MEM_TEST + + IFX_MEI_DFEMemoryFree (pDev, FREE_ALL); + return DSL_DEV_MEI_ERR_SUCCESS; +} + +#endif //CONFIG_AMAZON_S_MEI_FW_LOOPBACK + +static int +IFX_MEI_InitDevNode (int num) +{ + if (num == 0) { + if ((dev_major = register_chrdev (dev_major, IFX_MEI_DEVNAME, &bsp_mei_operations)) < 0) { + IFX_MEI_EMSG ("register_chrdev(%d %s) failed!\n", dev_major, IFX_MEI_DEVNAME); + return -ENODEV; + } + } + return 0; +} + +static int +IFX_MEI_CleanUpDevNode (int num) +{ + if (num == 0) + unregister_chrdev (dev_major, MEI_DIRNAME); + return 0; +} + +static int +IFX_MEI_InitDevice (int num) +{ + DSL_DEV_Device_t *pDev; + u32 temp; + pDev = &dsl_devices[num]; + if (pDev == NULL) + return -ENOMEM; + pDev->pPriv = &sDanube_Mei_Private[num]; + memset (pDev->pPriv, 0, sizeof (ifx_mei_device_private_t)); + + memset (&DSL_DEV_PRIVATE(pDev)-> + adsl_mem_info[0], 0, + sizeof (smmu_mem_info_t) * MAX_BAR_REGISTERS); + + if (num == 0) { + pDev->nIrq[IFX_DFEIR] = LQ_MEI_INT; + pDev->nIrq[IFX_DYING_GASP] = LQ_MEI_DYING_GASP_INT; + pDev->base_address = LQ_MEI_BASE_ADDR; + + /* Power up MEI */ +#ifdef CONFIG_LANTIQ_AMAZON_SE + *LQ_PMU_PWDCR &= ~(1 << 9); // enable dsl + *LQ_PMU_PWDCR &= ~(1 << 15); // enable AHB base +#else + temp = lq_r32(LQ_PMU_PWDCR); + temp &= 0xffff7dbe; + lq_w32(temp, LQ_PMU_PWDCR); +#endif + } + pDev->nInUse = 0; + DSL_DEV_PRIVATE(pDev)->modem_ready = 0; + DSL_DEV_PRIVATE(pDev)->arcmsgav = 0; + + MEI_INIT_WAKELIST ("arcq", DSL_DEV_PRIVATE(pDev)->wait_queue_arcmsgav); // for ARCMSGAV + MEI_INIT_WAKELIST ("arcr", DSL_DEV_PRIVATE(pDev)->wait_queue_modemready); // for arc modem ready + + MEI_MUTEX_INIT (DSL_DEV_PRIVATE(pDev)->mei_cmv_sema, 1); // semaphore initialization, mutex +#if 0 + MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DFEIR]); + MEI_MASK_AND_ACK_IRQ (pDev->nIrq[IFX_DYING_GASP]); +#endif + if (request_irq (pDev->nIrq[IFX_DFEIR], IFX_MEI_IrqHandle, 0, "DFEIR", pDev) != 0) { + IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DFEIR]); + return -1; + } + /*if (request_irq (pDev->nIrq[IFX_DYING_GASP], IFX_MEI_Dying_Gasp_IrqHandle, 0, "DYING_GASP", pDev) != 0) { + IFX_MEI_EMSG ("request_irq %d failed!\n", pDev->nIrq[IFX_DYING_GASP]); + return -1; + }*/ +// IFX_MEI_DMSG("Device %d initialized. IER %#x\n", num, bsp_get_irq_ier(pDev->nIrq[IFX_DYING_GASP])); + return 0; +} + +static int +IFX_MEI_ExitDevice (int num) +{ + DSL_DEV_Device_t *pDev; + pDev = &dsl_devices[num]; + + if (pDev == NULL) + return -EIO; + + disable_irq (pDev->nIrq[IFX_DFEIR]); + disable_irq (pDev->nIrq[IFX_DYING_GASP]); + + free_irq(pDev->nIrq[IFX_DFEIR], pDev); + free_irq(pDev->nIrq[IFX_DYING_GASP], pDev); + + return 0; +} + +static DSL_DEV_Device_t * +IFX_BSP_HandleGet (int maj, int num) +{ + if (num > BSP_MAX_DEVICES) + return NULL; + return &dsl_devices[num]; +} + +DSL_DEV_Device_t * +DSL_BSP_DriverHandleGet (int maj, int num) +{ + DSL_DEV_Device_t *pDev; + + if (num > BSP_MAX_DEVICES) + return NULL; + + pDev = &dsl_devices[num]; + if (!try_module_get(pDev->owner)) + return NULL; + + pDev->nInUse++; + return pDev; +} + +int +DSL_BSP_DriverHandleDelete (DSL_DEV_Device_t * nHandle) +{ + DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) nHandle; + if (pDev->nInUse) + pDev->nInUse--; + module_put(pDev->owner); + return 0; +} + +static int +IFX_MEI_Open (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil) +{ + int maj = MAJOR (ino->i_rdev); + int num = MINOR (ino->i_rdev); + + DSL_DEV_Device_t *pDev = NULL; + if ((pDev = DSL_BSP_DriverHandleGet (maj, num)) == NULL) { + IFX_MEI_EMSG("open(%d:%d) fail!\n", maj, num); + return -EIO; + } + fil->private_data = pDev; + return 0; +} + +static int +IFX_MEI_Release (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil) +{ + //int maj = MAJOR(ino->i_rdev); + int num = MINOR (ino->i_rdev); + DSL_DEV_Device_t *pDev; + + pDev = &dsl_devices[num]; + if (pDev == NULL) + return -EIO; + DSL_BSP_DriverHandleDelete (pDev); + return 0; +} + +/** + * Callback function for linux userspace program writing + */ +static ssize_t +IFX_MEI_Write (DSL_DRV_file_t * filp, const char *buf, size_t size, loff_t * loff) +{ + DSL_DEV_MeiError_t mei_error = DSL_DEV_MEI_ERR_FAILURE; + long offset = 0; + DSL_DEV_Device_t *pDev = (DSL_DEV_Device_t *) filp->private_data; + + if (pDev == NULL) + return -EIO; + + mei_error = + DSL_BSP_FWDownload (pDev, buf, size, (long *) loff, &offset); + + if (mei_error == DSL_DEV_MEI_ERR_FAILURE) + return -EIO; + return (ssize_t) offset; +} + +/** + * Callback function for linux userspace program ioctling + */ +static int +IFX_MEI_IoctlCopyFrom (int from_kernel, char *dest, char *from, int size) +{ + int ret = 0; + + if (!from_kernel) + ret = copy_from_user ((char *) dest, (char *) from, size); + else + ret = (int)memcpy ((char *) dest, (char *) from, size); + return ret; +} + +static int +IFX_MEI_IoctlCopyTo (int from_kernel, char *dest, char *from, int size) +{ + int ret = 0; + + if (!from_kernel) + ret = copy_to_user ((char *) dest, (char *) from, size); + else + ret = (int)memcpy ((char *) dest, (char *) from, size); + return ret; +} + +static int +IFX_MEI_Ioctls (DSL_DEV_Device_t * pDev, int from_kernel, unsigned int command, unsigned long lon) +{ + int i = 0; + int meierr = DSL_DEV_MEI_ERR_SUCCESS; + u32 base_address = LQ_MEI_BASE_ADDR; + DSL_DEV_WinHost_Message_t winhost_msg, m; + DSL_DEV_MeiDebug_t debugrdwr; + DSL_DEV_MeiReg_t regrdwr; + + switch (command) { + + case DSL_FIO_BSP_CMV_WINHOST: + IFX_MEI_IoctlCopyFrom (from_kernel, (char *) winhost_msg.msg.TxMessage, + (char *) lon, MSG_LENGTH * 2); + + if ((meierr = DSL_BSP_SendCMV (pDev, winhost_msg.msg.TxMessage, YES_REPLY, + winhost_msg.msg.RxMessage)) != DSL_DEV_MEI_ERR_SUCCESS) { + IFX_MEI_EMSG ("WINHOST CMV fail :TxMessage:%X %X %X %X, RxMessage:%X %X %X %X %X\n", + winhost_msg.msg.TxMessage[0], winhost_msg.msg.TxMessage[1], winhost_msg.msg.TxMessage[2], winhost_msg.msg.TxMessage[3], + winhost_msg.msg.RxMessage[0], winhost_msg.msg.RxMessage[1], winhost_msg.msg.RxMessage[2], winhost_msg.msg.RxMessage[3], + winhost_msg.msg.RxMessage[4]); + meierr = DSL_DEV_MEI_ERR_FAILURE; + } + else { + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, + (char *) winhost_msg.msg.RxMessage, + MSG_LENGTH * 2); + } + break; + + case DSL_FIO_BSP_CMV_READ: + IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (®rdwr), + (char *) lon, sizeof (DSL_DEV_MeiReg_t)); + + IFX_MEI_LongWordRead ((u32) regrdwr.iAddress, + (u32 *) & (regrdwr.iData)); + + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, + (char *) (®rdwr), + sizeof (DSL_DEV_MeiReg_t)); + + break; + + case DSL_FIO_BSP_CMV_WRITE: + IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (®rdwr), + (char *) lon, sizeof (DSL_DEV_MeiReg_t)); + + IFX_MEI_LongWordWrite ((u32) regrdwr.iAddress, + regrdwr.iData); + break; + + case DSL_FIO_BSP_GET_BASE_ADDRESS: + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, + (char *) (&base_address), + sizeof (base_address)); + break; + + case DSL_FIO_BSP_IS_MODEM_READY: + i = IFX_MEI_IsModemReady (pDev); + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, + (char *) (&i), sizeof (int)); + meierr = DSL_DEV_MEI_ERR_SUCCESS; + break; + case DSL_FIO_BSP_RESET: + case DSL_FIO_BSP_REBOOT: + meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RESET); + meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT); + break; + + case DSL_FIO_BSP_HALT: + meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_HALT); + break; + + case DSL_FIO_BSP_RUN: + meierr = IFX_MEI_CpuModeSet (pDev, DSL_CPU_RUN); + break; + case DSL_FIO_BSP_BOOTDOWNLOAD: + meierr = IFX_MEI_DownloadBootCode (pDev); + break; + case DSL_FIO_BSP_JTAG_ENABLE: + meierr = IFX_MEI_ArcJtagEnable (pDev, 1); + break; + + case DSL_FIO_BSP_REMOTE: + IFX_MEI_IoctlCopyFrom (from_kernel, (char *) (&i), + (char *) lon, sizeof (int)); + + meierr = IFX_MEI_AdslMailboxIRQEnable (pDev, i); + break; + + case DSL_FIO_BSP_DSL_START: + IFX_MEI_DMSG("DSL_FIO_BSP_DSL_START\n"); + if ((meierr = IFX_MEI_RunAdslModem (pDev)) != DSL_DEV_MEI_ERR_SUCCESS) { + IFX_MEI_EMSG ("IFX_MEI_RunAdslModem() error..."); + meierr = DSL_DEV_MEI_ERR_FAILURE; + } + break; + + case DSL_FIO_BSP_DEBUG_READ: + case DSL_FIO_BSP_DEBUG_WRITE: + IFX_MEI_IoctlCopyFrom (from_kernel, + (char *) (&debugrdwr), + (char *) lon, + sizeof (debugrdwr)); + + if (command == DSL_FIO_BSP_DEBUG_READ) + meierr = DSL_BSP_MemoryDebugAccess (pDev, + DSL_BSP_MEMORY_READ, + debugrdwr. + iAddress, + debugrdwr. + buffer, + debugrdwr. + iCount); + else + meierr = DSL_BSP_MemoryDebugAccess (pDev, + DSL_BSP_MEMORY_WRITE, + debugrdwr. + iAddress, + debugrdwr. + buffer, + debugrdwr. + iCount); + + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&debugrdwr), sizeof (debugrdwr)); + break; + case DSL_FIO_BSP_GET_VERSION: + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_mei_version), sizeof (DSL_DEV_Version_t)); + break; + +#define LQ_MPS_CHIPID_VERSION_GET(value) (((value) >> 28) & ((1 << 4) - 1)) + case DSL_FIO_BSP_GET_CHIP_INFO: + bsp_chip_info.major = 1; + bsp_chip_info.minor = LQ_MPS_CHIPID_VERSION_GET(*LQ_MPS_CHIPID); + IFX_MEI_IoctlCopyTo (from_kernel, (char *) lon, (char *) (&bsp_chip_info), sizeof (DSL_DEV_HwVersion_t)); + meierr = DSL_DEV_MEI_ERR_SUCCESS; + break; + + case DSL_FIO_BSP_FREE_RESOURCE: + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_STAT, 4, 0, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) { + meierr = DSL_DEV_MEI_ERR_FAILURE; + return -EIO; + } + IFX_MEI_DMSG("RxMessage[4] = %#x\n", m.msg.RxMessage[4]); + if (!(m.msg.RxMessage[4] & DSL_DEV_STAT_CODESWAP_COMPLETE)) { + meierr = DSL_DEV_MEI_ERR_FAILURE; + return -EAGAIN; + } + IFX_MEI_DMSG("Freeing all memories marked FREE_SHOWTIME\n"); + IFX_MEI_DFEMemoryFree (pDev, FREE_SHOWTIME); + meierr = DSL_DEV_MEI_ERR_SUCCESS; + break; +#ifdef CONFIG_IFXMIPS_AMAZON_SE + case DSL_FIO_ARC_MUX_TEST: + AMAZON_SE_MEI_ARC_MUX_Test(); + break; +#endif + default: +// IFX_MEI_EMSG("Invalid IOCTL command: %d\n"); + break; + } + return meierr; +} + +#ifdef CONFIG_IFXMIPS_AMAZON_SE +void AMAZON_SE_MEI_ARC_MUX_Test(void) +{ + u32 *p, i; + *LQ_RCU_RST |= LQ_RCU_RST_REQ_MUX_ARC; + + p = (u32*)(DFE_LDST_BASE_ADDR + IRAM0_BASE); + IFX_MEI_EMSG("Writing to IRAM0(%p)...\n", p); + for (i = 0; i < IRAM0_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + + p = (u32*)(DFE_LDST_BASE_ADDR + IRAM1_BASE); + IFX_MEI_EMSG("Writing to IRAM1(%p)...\n", p); + for (i = 0; i < IRAM1_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + + p = (u32*)(DFE_LDST_BASE_ADDR + BRAM_BASE); + IFX_MEI_EMSG("Writing to BRAM(%p)...\n", p); + for (i = 0; i < BRAM_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + + p = (u32*)(DFE_LDST_BASE_ADDR + XRAM_BASE); + IFX_MEI_EMSG("Writing to XRAM(%p)...\n", p); + for (i = 0; i < XRAM_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + + p = (u32*)(DFE_LDST_BASE_ADDR + YRAM_BASE); + IFX_MEI_EMSG("Writing to YRAM(%p)...\n", p); + for (i = 0; i < YRAM_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + + p = (u32*)(DFE_LDST_BASE_ADDR + EXT_MEM_BASE); + IFX_MEI_EMSG("Writing to EXT_MEM(%p)...\n", p); + for (i = 0; i < EXT_MEM_SIZE/sizeof(u32); i++, p++) { + *p = 0xdeadbeef; + if (*p != 0xdeadbeef) + IFX_MEI_EMSG("%p: %#x\n", p, *p); + } + *LQ_RCU_RST &= ~LQ_RCU_RST_REQ_MUX_ARC; +} +#endif +int +DSL_BSP_KernelIoctls (DSL_DEV_Device_t * pDev, unsigned int command, + unsigned long lon) +{ + int error = 0; + + error = IFX_MEI_Ioctls (pDev, 1, command, lon); + return error; +} + +static int +IFX_MEI_UserIoctls (DSL_DRV_inode_t * ino, DSL_DRV_file_t * fil, + unsigned int command, unsigned long lon) +{ + int error = 0; + int maj = MAJOR (ino->i_rdev); + int num = MINOR (ino->i_rdev); + DSL_DEV_Device_t *pDev; + + pDev = IFX_BSP_HandleGet (maj, num); + if (pDev == NULL) + return -EIO; + + error = IFX_MEI_Ioctls (pDev, 0, command, lon); + return error; +} + +#ifdef CONFIG_PROC_FS +/* + * Register a callback function for linux proc filesystem + */ +static int +IFX_MEI_InitProcFS (int num) +{ + struct proc_dir_entry *entry; + int i ; + DSL_DEV_Device_t *pDev; + reg_entry_t regs_temp[PROC_ITEMS] = { + /* flag, name, description } */ + {NULL, "arcmsgav", "arc to mei message ", 0}, + {NULL, "cmv_reply", "cmv needs reply", 0}, + {NULL, "cmv_waiting", "waiting for cmv reply from arc", 0}, + {NULL, "modem_ready_cnt", "ARC to MEI indicator count", 0}, + {NULL, "cmv_count", "MEI to ARC CMVs", 0}, + {NULL, "reply_count", "ARC to MEI Reply", 0}, + {NULL, "Recent_indicator", "most recent indicator", 0}, + {NULL, "fw_version", "Firmware Version", 0}, + {NULL, "fw_date", "Firmware Date", 0}, + {NULL, "meminfo", "Memory Allocation Information", 0}, + {NULL, "version", "MEI version information", 0}, + }; + + pDev = &dsl_devices[num]; + if (pDev == NULL) + return -ENOMEM; + + regs_temp[0].flag = &(DSL_DEV_PRIVATE(pDev)->arcmsgav); + regs_temp[1].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_reply); + regs_temp[2].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_waiting); + regs_temp[3].flag = &(DSL_DEV_PRIVATE(pDev)->modem_ready_cnt); + regs_temp[4].flag = &(DSL_DEV_PRIVATE(pDev)->cmv_count); + regs_temp[5].flag = &(DSL_DEV_PRIVATE(pDev)->reply_count); + regs_temp[6].flag = (int *) &(DSL_DEV_PRIVATE(pDev)->Recent_indicator); + + memcpy ((char *) regs[num], (char *) regs_temp, sizeof (regs_temp)); + // procfs + meidir = proc_mkdir (MEI_DIRNAME, NULL); + if (meidir == NULL) { + IFX_MEI_EMSG ("Failed to create /proc/%s\n", MEI_DIRNAME); + return (-ENOMEM); + } + + for (i = 0; i < NUM_OF_REG_ENTRY; i++) { + entry = create_proc_entry (regs[num][i].name, + S_IWUSR | S_IRUSR | S_IRGRP | + S_IROTH, meidir); + if (entry) { + regs[num][i].low_ino = entry->low_ino; + entry->proc_fops = &IFX_MEI_ProcOperations; + } + else { + IFX_MEI_EMSG ("Failed to create /proc/%s/%s\n", MEI_DIRNAME, regs[num][i].name); + return (-ENOMEM); + } + } + return 0; +} + +/* + * Reading function for linux proc filesystem + */ +static int +IFX_MEI_ProcRead (struct file *file, char *buf, size_t nbytes, loff_t * ppos) +{ + int i_ino = (file->f_dentry->d_inode)->i_ino; + char *p = buf; + int i; + int num; + reg_entry_t *entry = NULL; + DSL_DEV_Device_t *pDev = NULL; + DSL_DEV_WinHost_Message_t m; + + for (num = 0; num < BSP_MAX_DEVICES; num++) { + for (i = 0; i < NUM_OF_REG_ENTRY; i++) { + if (regs[num][i].low_ino == (unsigned short)i_ino) { + entry = ®s[num][i]; + pDev = &dsl_devices[num]; + break; + } + } + } + if (entry == NULL) + return -EINVAL; + else if (strcmp(entry->name, "meminfo") == 0) { + if (*ppos > 0) /* Assume reading completed in previous read */ + return 0; + p += sprintf (p, "No Address Size\n"); + for (i = 0; i < MAX_BAR_REGISTERS; i++) { + p += sprintf (p, "BAR[%02d] Addr:0x%08X Size:%lu\n", + i, (u32) DSL_DEV_PRIVATE(pDev)->adsl_mem_info[i].address, + DSL_DEV_PRIVATE(pDev)-> adsl_mem_info[i].size); + //printk( "BAR[%02d] Addr:0x%08X Size:%d\n",i,adsl_mem_info[i].address,adsl_mem_info[i].size); + } + *ppos += (p - buf); + } else if (strcmp(entry->name, "fw_version") == 0) { + if (*ppos > 0) /* Assume reading completed in previous read */ + return 0; + if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1) + return -EAGAIN; + //major:bits 0-7 + //minor:bits 8-15 + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 0, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) + return -EIO; + p += sprintf(p, "FW Version: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF); + //sub_version:bits 4-7 + //int_version:bits 0-3 + //spl_appl:bits 8-13 + //rel_state:bits 14-15 + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 54, 1, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) + return -EIO; + p += sprintf(p, "%d.%d.%d.%d\n", + (m.msg.RxMessage[4] >> 4) & 0xF, m.msg.RxMessage[4] & 0xF, + (m.msg.RxMessage[4] >> 14) & 3, (m.msg.RxMessage[4] >> 8) & 0x3F); + *ppos += (p - buf); + } else if (strcmp(entry->name, "fw_date") == 0) { + if (*ppos > 0) /* Assume reading completed in previous read */ + return 0; + if (DSL_DEV_PRIVATE(pDev)->modem_ready_cnt < 1) + return -EAGAIN; + + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 0, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) + return -EIO; + /* Day/Month */ + p += sprintf(p, "FW Date: %d.%d.", m.msg.RxMessage[4] & 0xFF, (m.msg.RxMessage[4] >> 8) & 0xFF); + + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 2, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) + return -EIO; + /* Year */ + p += sprintf(p, "%d ", m.msg.RxMessage[4]); + + makeCMV (H2D_CMV_READ, DSL_CMV_GROUP_INFO, 55, 1, 1, NULL, m.msg.TxMessage); + if (DSL_BSP_SendCMV (pDev, m.msg.TxMessage, YES_REPLY, m.msg.RxMessage) != DSL_DEV_MEI_ERR_SUCCESS) + return -EIO; + /* Hour:Minute */ + p += sprintf(p, "%d:%d\n", (m.msg.RxMessage[4] >> 8) & 0xFF, m.msg.RxMessage[4] & 0xFF); + + *ppos += (p - buf); + } else if (strcmp(entry->name, "version") == 0) { + if (*ppos > 0) /* Assume reading completed in previous read */ + return 0; + p += sprintf (p, "IFX MEI V%ld.%ld.%ld\n", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision); + + *ppos += (p - buf); + } else if (entry->flag != (int *) DSL_DEV_PRIVATE(pDev)->Recent_indicator) { + if (*ppos > 0) /* Assume reading completed in previous read */ + return 0; // indicates end of file + p += sprintf (p, "0x%08X\n\n", *(entry->flag)); + *ppos += (p - buf); + if ((p - buf) > nbytes) /* Assume output can be read at one time */ + return -EINVAL; + } else { + if ((int) (*ppos) / ((int) 7) == 16) + return 0; // indicate end of the message + p += sprintf (p, "0x%04X\n\n", *(((u16 *) (entry->flag)) + (int) (*ppos) / ((int) 7))); + *ppos += (p - buf); + } + return p - buf; +} + +/* + * Writing function for linux proc filesystem + */ +static ssize_t +IFX_MEI_ProcWrite (struct file *file, const char *buffer, size_t count, loff_t * ppos) +{ + int i_ino = (file->f_dentry->d_inode)->i_ino; + reg_entry_t *current_reg = NULL; + int i = 0; + int num = 0; + unsigned long newRegValue = 0; + char *endp = NULL; + DSL_DEV_Device_t *pDev = NULL; + + for (num = 0; num < BSP_MAX_DEVICES; num++) { + for (i = 0; i < NUM_OF_REG_ENTRY; i++) { + if (regs[num][i].low_ino == i_ino) { + current_reg = ®s[num][i]; + pDev = &dsl_devices[num]; + break; + } + } + } + if ((current_reg == NULL) + || (current_reg->flag == + (int *) DSL_DEV_PRIVATE(pDev)-> + Recent_indicator)) + return -EINVAL; + + newRegValue = simple_strtoul (buffer, &endp, 0); + *(current_reg->flag) = (int) newRegValue; + return (count + endp - buffer); +} +#endif //CONFIG_PROC_FS + +static int adsl_dummy_ledcallback(void) +{ + return 0; +} + +int ifx_mei_atm_led_blink(void) +{ + return g_adsl_ledcallback(); +} +EXPORT_SYMBOL(ifx_mei_atm_led_blink); + +int ifx_mei_atm_showtime_check(int *is_showtime, struct port_cell_info *port_cell, void **xdata_addr) +{ + int i; + + if ( is_showtime ) { + *is_showtime = g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ? 0 : 1; + } + + if ( port_cell ) { + for ( i = 0; i < port_cell->port_num && i < 2; i++ ) + port_cell->tx_link_rate[i] = g_tx_link_rate[i]; + } + + if ( xdata_addr ) { + if ( g_tx_link_rate[0] == 0 && g_tx_link_rate[1] == 0 ) + *xdata_addr = NULL; + else + *xdata_addr = g_xdata_addr; + } + + return 0; +} +EXPORT_SYMBOL(ifx_mei_atm_showtime_check); + +/* + * Writing function for linux proc filesystem + */ +int __init +IFX_MEI_ModuleInit (void) +{ + int i = 0; + static struct class *dsl_class; + + pr_info("IFX MEI Version %ld.%02ld.%02ld", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision); + + for (i = 0; i < BSP_MAX_DEVICES; i++) { + if (IFX_MEI_InitDevice (i) != 0) { + IFX_MEI_EMSG("Init device fail!\n"); + return -EIO; + } + IFX_MEI_InitDevNode (i); +#ifdef CONFIG_PROC_FS + IFX_MEI_InitProcFS (i); +#endif + } + for (i = 0; i <= DSL_BSP_CB_LAST ; i++) + dsl_bsp_event_callback[i].function = NULL; + +#ifdef CONFIG_LQ_MEI_FW_LOOPBACK + IFX_MEI_DMSG("Start loopback test...\n"); + DFE_Loopback_Test (); +#endif + dsl_class = class_create(THIS_MODULE, "ifx_mei"); + device_create(dsl_class, NULL, MKDEV(MEI_MAJOR, 0), NULL, "ifx_mei"); + return 0; +} + +void __exit +IFX_MEI_ModuleExit (void) +{ + int i = 0; + int num; + + for (num = 0; num < BSP_MAX_DEVICES; num++) { + IFX_MEI_CleanUpDevNode (num); +#ifdef CONFIG_PROC_FS + for (i = 0; i < NUM_OF_REG_ENTRY; i++) { + remove_proc_entry (regs[num][i].name, meidir); + } +#endif + } + + remove_proc_entry (MEI_DIRNAME, NULL); + for (i = 0; i < BSP_MAX_DEVICES; i++) { + for (i = 0; i < BSP_MAX_DEVICES; i++) { + IFX_MEI_ExitDevice (i); + } + } +} + +/* export function for DSL Driver */ + +/* The functions of MEI_DriverHandleGet and MEI_DriverHandleDelete are +something like open/close in kernel space , where the open could be used +to register a callback for autonomous messages and returns a mei driver context pointer (comparable to the file descriptor in user space) + The context will be required for the multi line chips future! */ + +EXPORT_SYMBOL (DSL_BSP_DriverHandleGet); +EXPORT_SYMBOL (DSL_BSP_DriverHandleDelete); + +EXPORT_SYMBOL (DSL_BSP_ATMLedCBRegister); +EXPORT_SYMBOL (DSL_BSP_ATMLedCBUnregister); +EXPORT_SYMBOL (DSL_BSP_KernelIoctls); +EXPORT_SYMBOL (DSL_BSP_AdslLedInit); +//EXPORT_SYMBOL (DSL_BSP_AdslLedSet); +EXPORT_SYMBOL (DSL_BSP_FWDownload); +EXPORT_SYMBOL (DSL_BSP_Showtime); + +EXPORT_SYMBOL (DSL_BSP_MemoryDebugAccess); +EXPORT_SYMBOL (DSL_BSP_SendCMV); + +// provide a register/unregister function for DSL driver to register a event callback function +EXPORT_SYMBOL (DSL_BSP_EventCBRegister); +EXPORT_SYMBOL (DSL_BSP_EventCBUnregister); + +module_init (IFX_MEI_ModuleInit); +module_exit (IFX_MEI_ModuleExit); + +MODULE_LICENSE("Dual BSD/GPL");