adds dsl support, thank you infineon/lantiq
SVN-Revision: 18259
This commit is contained in:
parent
eff68fb14b
commit
976d1a1024
34 changed files with 8430 additions and 3351 deletions
|
@ -1,49 +0,0 @@
|
|||
# Copyright (C) 2009 OpenWrt.org
|
||||
# All rights reserved.
|
||||
#
|
||||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
#
|
||||
# blogic@openwrt.org
|
||||
#
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=ifxmips-atm
|
||||
PKG_RELEASE:=1
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
define KernelPackage/ifxmips-atm
|
||||
SUBMENU:=Network Devices
|
||||
DEPENDS:=@BROKEN @TARGET_ifxmips +kmod-atm
|
||||
TITLE:=ifxmips atm driver
|
||||
FILES:=$(PKG_BUILD_DIR)/ifx-atm.$(LINUX_KMOD_SUFFIX)
|
||||
AUTOLOAD:=$(call AutoLoad,50,ifx-atm)
|
||||
endef
|
||||
|
||||
define Kernel/Package/ifxmips-atm/description
|
||||
This package provides the atm driver needed to make dsl work on ifxmips based boards
|
||||
endef
|
||||
|
||||
define Build/Prepare
|
||||
mkdir -p $(PKG_BUILD_DIR)
|
||||
$(CP) ./src/* $(PKG_BUILD_DIR)/
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
$(MAKE) -C "$(LINUX_DIR)" \
|
||||
CROSS_COMPILE="$(TARGET_CROSS)" \
|
||||
ARCH="$(LINUX_KARCH)" \
|
||||
SUBDIRS="$(PKG_BUILD_DIR)" \
|
||||
modules
|
||||
endef
|
||||
|
||||
define KernelPackage/ifxmips-atm/install
|
||||
$(INSTALL_DIR) $(1)/lib/modules/$(LINUX_VERSION)
|
||||
$(CP) $(PKG_BUILD_DIR)/ifx-atm.ko $(1)/lib/modules/$(LINUX_VERSION)
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,ifxmips-atm))
|
||||
|
|
@ -1,4 +0,0 @@
|
|||
obj-m += ifx-atm.o
|
||||
ifx-atm-objs := skb.o irq.o proc.o core.o ppe.o
|
||||
|
||||
EXTRA_CFLAGS += -DENABLE_RX_QOS=1
|
|
@ -1,896 +0,0 @@
|
|||
#include <linux/atmdev.h>
|
||||
#include <asm/ifxmips/ifxmips_irq.h>
|
||||
#include <linux/irq.h>
|
||||
#include <linux/sem.h>
|
||||
#include <linux/coda.h>
|
||||
|
||||
#define RX_DMA_CH_CBR 0
|
||||
#define RX_DMA_CH_VBR_RT 1
|
||||
#define RX_DMA_CH_VBR_NRT 2
|
||||
#define RX_DMA_CH_AVR 3
|
||||
#define RX_DMA_CH_UBR 4
|
||||
#define RX_DMA_CH_OAM 5
|
||||
#define RX_DMA_CH_TOTAL 6
|
||||
|
||||
#define WRX_DMA_CHANNEL_INTERRUPT_MODE 0x00
|
||||
#define WRX_DMA_CHANNEL_POLLING_MODE 0x01
|
||||
//#define WRX_DMA_CHANNEL_COUNTER_MODE 0x02
|
||||
#define WRX_DMA_CHANNEL_COUNTER_MODE WRX_DMA_CHANNEL_INTERRUPT_MODE
|
||||
#define WRX_DMA_BUF_LEN_PER_DESCRIPTOR 0x00
|
||||
#define WRX_DMA_BUF_LEN_PER_CHANNEL 0x01
|
||||
|
||||
#define ATM_VBR_RT 6
|
||||
#define ATM_VBR_NRT ATM_VBR
|
||||
#define ATM_UBR_PLUS 7
|
||||
|
||||
#define SET_BITS(x, msb, lsb, value) (((x) & ~(((1 << ((msb) + 1)) - 1) ^ ((1 << (lsb)) - 1))) | (((value) & ((1 << (1 + (msb) - (lsb))) - 1)) << (lsb)))
|
||||
|
||||
#define GET_ATM_PRIV(dev) ((Atm_Priv *)dev->priv)
|
||||
|
||||
#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)
|
||||
|
||||
/*
|
||||
* 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)
|
||||
|
||||
|
||||
/*
|
||||
* QSB RAM Access Register
|
||||
*/
|
||||
#define QSB_RAMAC QSB_CONF_REG(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 */
|
||||
#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 Internal Cell Delay Variation Register
|
||||
*/
|
||||
#define QSB_ICDV QSB_CONF_REG(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(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(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(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(0x000C)
|
||||
|
||||
#define QSB_RTD_TTV (*QSB_RTD)
|
||||
|
||||
#define QSB_RTD_TTV_SET(value) ((value) & 0xFFFFFFFF)
|
||||
|
||||
/*
|
||||
* PP32 Debug Control Register
|
||||
*/
|
||||
#define PP32_DBG_CTRL PP32_DEBUG_REG_ADDR(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 SB_RAM0_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x8000) << 2)))
|
||||
#define UPDATE_VCC_STAT(conn, item, num) do { ppe_dev.connection[conn].item += num; } while (0)
|
||||
/*
|
||||
* 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
|
||||
|
||||
|
||||
#define CELL_SIZE ATM_AAL0_SDU
|
||||
#define IDLE_CYCLE_NUMBER 30000
|
||||
|
||||
#define MBOX_IGU1_ISR PPE_REG_ADDR(0x0206)
|
||||
#define MBOX_IGU3_ISRS PPE_REG_ADDR(0x0214)
|
||||
#define MBOX_IGU1_ISRC PPE_REG_ADDR(0x0205)
|
||||
#define MBOX_IGU3_ISR PPE_REG_ADDR(0x0216)
|
||||
#define MBOX_IGU3_ISRS_SET(n) (1 << (n))
|
||||
#define MBOX_IGU3_ISR_ISR(n) (*MBOX_IGU3_ISR & (1 << (n)))
|
||||
/*
|
||||
* * Mailbox IGU1 Registers
|
||||
* */
|
||||
#define MBOX_IGU1_ISRS PPE_REG_ADDR(0x0204)
|
||||
#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_ISRC PPE_REG_ADDR(0x0215)
|
||||
#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))
|
||||
|
||||
|
||||
// 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)
|
||||
|
||||
|
||||
// DWORD-Length of Memory Blocks
|
||||
#define PP32_DEBUG_REG_DWLEN 0x0030
|
||||
#define PPM_INT_REG_DWLEN 0x0010
|
||||
#define PP32_INTERNAL_RES_DWLEN 0x00C0
|
||||
#define PPE_CLOCK_CONTROL_DWLEN 0x0F00
|
||||
#define CDM_CODE_MEMORY_RAM0_DWLEN 0x1000
|
||||
#define CDM_CODE_MEMORY_RAM1_DWLEN 0x0800
|
||||
#define PPE_REG_DWLEN 0x1000
|
||||
#define PP32_DATA_MEMORY_RAM1_DWLEN 0x0800
|
||||
#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
|
||||
/*
|
||||
* 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
|
||||
|
||||
|
||||
|
||||
// OAM Definitions
|
||||
#define OAM_RX_QUEUE_NUMBER 1
|
||||
#define OAM_TX_QUEUE_NUMBER_PER_PORT 0
|
||||
#define OAM_RX_DMA_CHANNEL_NUMBER OAM_RX_QUEUE_NUMBER
|
||||
#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
|
||||
|
||||
// ATM Port, QSB Queue, DMA RX/TX Channel Parameters
|
||||
#define ATM_PORT_NUMBER 2
|
||||
#define MAX_QUEUE_NUMBER 16
|
||||
#define QSB_QUEUE_NUMBER_BASE 1
|
||||
#define MAX_QUEUE_NUMBER_PER_PORT (MAX_QUEUE_NUMBER - QSB_QUEUE_NUMBER_BASE)
|
||||
#define MAX_CONNECTION_NUMBER MAX_QUEUE_NUMBER
|
||||
#define MAX_RX_DMA_CHANNEL_NUMBER 8
|
||||
#define MAX_TX_DMA_CHANNEL_NUMBER 16
|
||||
#define DMA_ALIGNMENT 4
|
||||
|
||||
#define DEFAULT_RX_HUNT_BITTH 4
|
||||
|
||||
/*
|
||||
* FPI Configuration Bus Register and Memory Address Mapping
|
||||
*/
|
||||
#define DANUBE_PPE (KSEG1 + 0x1E180000)
|
||||
#define PP32_DEBUG_REG_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x0000) << 2)))
|
||||
#define PPM_INT_REG_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x0030) << 2)))
|
||||
#define PP32_INTERNAL_RES_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x0040) << 2)))
|
||||
#define PPE_CLOCK_CONTROL_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x0100) << 2)))
|
||||
#define CDM_CODE_MEMORY_RAM0_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x1000) << 2)))
|
||||
#define CDM_CODE_MEMORY_RAM1_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x2000) << 2)))
|
||||
#define PPE_REG_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x4000) << 2)))
|
||||
#define PP32_DATA_MEMORY_RAM1_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x5000) << 2)))
|
||||
#define PPM_INT_UNIT_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x6000) << 2)))
|
||||
#define PPM_TIMER0_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x6100) << 2)))
|
||||
#define PPM_TASK_IND_REG_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x6200) << 2)))
|
||||
#define PPS_BRK_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x6300) << 2)))
|
||||
#define PPM_TIMER1_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x6400) << 2)))
|
||||
#define SB_RAM0_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x8000) << 2)))
|
||||
#define SB_RAM1_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x8400) << 2)))
|
||||
#define SB_RAM2_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x8C00) << 2)))
|
||||
#define SB_RAM3_ADDR(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0x9600) << 2)))
|
||||
#define QSB_CONF_REG(x) ((volatile u32*)(DANUBE_PPE + (((x) + 0xC000) << 2)))
|
||||
|
||||
/*
|
||||
* Host-PPE Communication Data Address Mapping
|
||||
*/
|
||||
#define CFG_WRX_HTUTS PPM_INT_UNIT_ADDR(0x2400) /* WAN RX HTU Table Size, must be configured before enable PPE firmware. */
|
||||
#define CFG_WRX_QNUM PPM_INT_UNIT_ADDR(0x2401) /* WAN RX Queue Number */
|
||||
#define CFG_WRX_DCHNUM PPM_INT_UNIT_ADDR(0x2402) /* WAN RX DMA Channel Number, no more than 8, must be configured before enable PPE firmware. */
|
||||
#define CFG_WTX_DCHNUM PPM_INT_UNIT_ADDR(0x2403) /* WAN TX DMA Channel Number, no more than 16, must be configured before enable PPE firmware. */
|
||||
#define CFG_WRDES_DELAY PPM_INT_UNIT_ADDR(0x2404) /* WAN Descriptor Write Delay, must be configured before enable PPE firmware. */
|
||||
#define WRX_DMACH_ON PPM_INT_UNIT_ADDR(0x2405) /* WAN RX DMA Channel Enable, must be configured before enable PPE firmware. */
|
||||
#define WTX_DMACH_ON PPM_INT_UNIT_ADDR(0x2406) /* WAN TX DMA Channel Enable, must be configured before enable PPE firmware. */
|
||||
#define WRX_HUNT_BITTH PPM_INT_UNIT_ADDR(0x2407) /* WAN RX HUNT Threshold, must be between 2 to 8. */
|
||||
#define WRX_QUEUE_CONFIG(i) ((struct wrx_queue_config*)PPM_INT_UNIT_ADDR(0x2500 + (i) * 20))
|
||||
#define WRX_DMA_CHANNEL_CONFIG(i) ((struct wrx_dma_channel_config*)PPM_INT_UNIT_ADDR(0x2640 + (i) * 7))
|
||||
#define WTX_PORT_CONFIG(i) ((struct wtx_port_config*)PPM_INT_UNIT_ADDR(0x2440 + (i)))
|
||||
#define WTX_QUEUE_CONFIG(i) ((struct wtx_queue_config*)PPM_INT_UNIT_ADDR(0x2710 + (i) * 27))
|
||||
#define WTX_DMA_CHANNEL_CONFIG(i) ((struct wtx_dma_channel_config*)PPM_INT_UNIT_ADDR(0x2711 + (i) * 27))
|
||||
#define WAN_MIB_TABLE ((struct wan_mib_table*)PPM_INT_UNIT_ADDR(0x2410))
|
||||
#define HTU_ENTRY(i) ((struct htu_entry*)PPM_INT_UNIT_ADDR(0x2000 + (i)))
|
||||
#define HTU_MASK(i) ((struct htu_mask*)PPM_INT_UNIT_ADDR(0x2020 + (i)))
|
||||
#define HTU_RESULT(i) ((struct htu_result*)PPM_INT_UNIT_ADDR(0x2040 + (i)))
|
||||
|
||||
// DREG Idle Counters
|
||||
#define DREG_AT_CELL0 PPE_REG_ADDR(0x0D24)
|
||||
#define DREG_AT_CELL1 PPE_REG_ADDR(0x0D25)
|
||||
#define DREG_AT_IDLE_CNT0 PPE_REG_ADDR(0x0D26)
|
||||
#define DREG_AT_IDLE_CNT1 PPE_REG_ADDR(0x0D27)
|
||||
#define DREG_AR_CELL0 PPE_REG_ADDR(0x0D68)
|
||||
#define DREG_AR_CELL1 PPE_REG_ADDR(0x0D69)
|
||||
#define DREG_AR_IDLE_CNT0 PPE_REG_ADDR(0x0D6A)
|
||||
#define DREG_AR_IDLE_CNT1 PPE_REG_ADDR(0x0D6B)
|
||||
#define DREG_AR_AIIDLE_CNT0 PPE_REG_ADDR(0x0D6C)
|
||||
#define DREG_AR_AIIDLE_CNT1 PPE_REG_ADDR(0x0D6D)
|
||||
#define DREG_AR_BE_CNT0 PPE_REG_ADDR(0x0D6E)
|
||||
#define DREG_AR_BE_CNT1 PPE_REG_ADDR(0x0D6F)
|
||||
|
||||
|
||||
/*
|
||||
* 64-bit Data Type
|
||||
*/
|
||||
typedef struct {
|
||||
unsigned int h: 32;
|
||||
unsigned int l: 32;
|
||||
} ppe_u64_t;
|
||||
|
||||
/*
|
||||
* 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)
|
||||
|
||||
struct wan_mib_table {
|
||||
unsigned int res1;
|
||||
unsigned int wrx_drophtu_cell;
|
||||
unsigned int wrx_dropdes_pdu;
|
||||
unsigned int wrx_correct_pdu;
|
||||
unsigned int wrx_err_pdu;
|
||||
unsigned int wrx_dropdes_cell;
|
||||
unsigned int wrx_correct_cell;
|
||||
unsigned int wrx_err_cell;
|
||||
unsigned int wrx_total_byte;
|
||||
unsigned int wtx_total_pdu;
|
||||
unsigned int wtx_total_cell;
|
||||
unsigned int wtx_total_byte;
|
||||
};
|
||||
|
||||
/*
|
||||
* Internal Structure of Device
|
||||
*/
|
||||
struct port {
|
||||
int connection_base; /* first connection ID (RX/TX queue ID) */
|
||||
unsigned int max_connections; /* maximum connection number */
|
||||
unsigned int connection_table; /* connection opened status, every bit */
|
||||
unsigned int tx_max_cell_rate; /* maximum cell rate */
|
||||
unsigned int tx_current_cell_rate; /* currently used cell rate */
|
||||
#if !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
int rx_dma_channel_base; /* first RX DMA channel ID */
|
||||
unsigned int rx_dma_channel_assigned;/* totally RX DMA channels used */
|
||||
#endif // !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
int oam_tx_queue; /* first TX queue ID of OAM cell */
|
||||
struct atm_dev *dev;
|
||||
|
||||
};
|
||||
|
||||
struct connection {
|
||||
struct atm_vcc *vcc; /* opened VCC */
|
||||
struct timespec access_time; /* time when last F4/F5 user cell arrives */
|
||||
unsigned int aal5_vcc_crc_err; /* number of packets with CRC error */
|
||||
unsigned int aal5_vcc_oversize_sdu; /* number of packets with oversize error */
|
||||
int rx_dma_channel; /* RX DMA channel ID assigned */
|
||||
int port; /* to which port the connection belongs */
|
||||
unsigned int rx_pdu;
|
||||
unsigned int rx_err_pdu;
|
||||
unsigned int rx_sw_drop_pdu;
|
||||
unsigned int tx_pdu;
|
||||
unsigned int tx_err_pdu;
|
||||
unsigned int tx_hw_drop_pdu;
|
||||
unsigned int tx_sw_drop_pdu;
|
||||
};
|
||||
|
||||
struct ppe_dev {
|
||||
struct connection connection[MAX_CONNECTION_NUMBER];
|
||||
struct port port[ATM_PORT_NUMBER];
|
||||
|
||||
struct aal5 {
|
||||
unsigned char padding_byte; /* padding byte pattern of AAL5 packet */
|
||||
unsigned int rx_max_packet_size; /* max AAL5 packet length */
|
||||
unsigned int rx_min_packet_size; /* min AAL5 packet length */
|
||||
unsigned int rx_buffer_size; /* max memory allocated for a AAL5 packet */
|
||||
unsigned int tx_max_packet_size; /* max AAL5 packet length */
|
||||
unsigned int tx_min_packet_size; /* min AAL5 packet length */
|
||||
unsigned int tx_buffer_size; /* max memory allocated for a AAL5 packet */
|
||||
unsigned int rx_drop_error_packet; /* 1: drop error packet, 0: ignore errors */
|
||||
} aal5;
|
||||
|
||||
struct qsb {
|
||||
unsigned int tau; /* cell delay variation due to concurrency */
|
||||
unsigned int tstepc; /* shceduler burst length */
|
||||
unsigned int sbl; /* time step */
|
||||
} qsb;
|
||||
|
||||
struct dma {
|
||||
unsigned int rx_descriptor_number; /* number of RX descriptors */
|
||||
unsigned int tx_descriptor_number; /* number of TX descriptors */
|
||||
unsigned int rx_clp1_desc_threshold; /* threshold to drop cells with CLP1 */
|
||||
unsigned int write_descriptor_delay; /* delay on descriptor write path */
|
||||
unsigned int rx_total_channel_used; /* total RX channel used */
|
||||
void *rx_descriptor_addr; /* base address of memory allocated for */
|
||||
struct rx_descriptor
|
||||
*rx_descriptor_base; /* base address of RX descriptors */
|
||||
int rx_desc_read_pos[MAX_RX_DMA_CHANNEL_NUMBER]; /* first RX descriptor */
|
||||
/* to be read */
|
||||
// struct sk_buff **rx_skb_pointers; /* base address of RX sk_buff pointers */
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
long rx_weight[MAX_RX_DMA_CHANNEL_NUMBER]; /* RX schedule weight */
|
||||
long rx_default_weight[MAX_RX_DMA_CHANNEL_NUMBER]; /* default weight */
|
||||
#endif
|
||||
|
||||
unsigned int tx_total_channel_used; /* total TX channel used */
|
||||
void *tx_descriptor_addr; /* base address of memory allocated for */
|
||||
/* TX descriptors */
|
||||
struct tx_descriptor
|
||||
*tx_descriptor_base; /* base address of TX descriptors */
|
||||
int tx_desc_alloc_pos[MAX_TX_DMA_CHANNEL_NUMBER]; /* first TX descriptor */
|
||||
/* could be allocated */
|
||||
// int tx_desc_alloc_num[MAX_TX_DMA_CHANNEL_NUMBER]; /* number of allocated */
|
||||
// /* TX descriptors */
|
||||
int tx_desc_alloc_flag[MAX_TX_DMA_CHANNEL_NUMBER]; /* at least one TX */
|
||||
/* descriptor is alloc */
|
||||
// int tx_desc_send_pos[MAX_TX_DMA_CHANNEL_NUMBER]; /* first TX descriptor */
|
||||
// /* to be send */
|
||||
int tx_desc_release_pos[MAX_TX_DMA_CHANNEL_NUMBER]; /* first TX descriptor */
|
||||
/* to be released */
|
||||
struct sk_buff **tx_skb_pointers; /* base address of TX sk_buff pointers */
|
||||
} dma;
|
||||
|
||||
struct mib {
|
||||
ppe_u64_t wrx_total_byte; /* bit-64 extention of MIB table member */
|
||||
ppe_u64_t wtx_total_byte; /* bit-64 extention of MIB talbe member */
|
||||
|
||||
unsigned int wrx_pdu; /* successfully received AAL5 packet */
|
||||
unsigned int wrx_drop_pdu; /* AAL5 packet dropped by driver on RX */
|
||||
unsigned int wtx_err_pdu; /* error AAL5 packet */
|
||||
unsigned int wtx_drop_pdu; /* AAL5 packet dropped by driver on TX */
|
||||
} mib;
|
||||
struct wan_mib_table prev_mib;
|
||||
|
||||
int oam_rx_queue; /* RX queue ID of OAM cell */
|
||||
int oam_rx_dma_channel; /* RX DMA channel ID of OAM cell */
|
||||
int max_connections; /* total connections available */
|
||||
|
||||
struct semaphore sem; /* lock used by open/close function */
|
||||
};
|
||||
|
||||
/*
|
||||
* 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 :2;
|
||||
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 :2;
|
||||
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)
|
||||
|
||||
/*
|
||||
* 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;
|
||||
unsigned int dword;
|
||||
};
|
||||
|
||||
union qsb_queue_vbr_parameter_table {
|
||||
struct {
|
||||
unsigned int taus :16;
|
||||
unsigned int ts :16;
|
||||
} bit;
|
||||
unsigned int 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;
|
||||
unsigned int dword;
|
||||
};
|
||||
|
||||
union qsb_queue_vbr_parameter_table {
|
||||
struct {
|
||||
unsigned int ts :16;
|
||||
unsigned int taus :16;
|
||||
} bit;
|
||||
unsigned int dword;
|
||||
};
|
||||
#endif // defined(__BIG_ENDIAN)
|
||||
|
||||
|
||||
typedef enum
|
||||
{
|
||||
IAD_ATM_CBR = 6, /* IAD_ATM_PRI_HIGH, */
|
||||
IAD_ATM_VBR_RT = 4, /* IAD_ATM_PRI_MED_HIGH, VBR, Real-Time */
|
||||
IAD_ATM_VBR_NRT = 2, /* IAD_ATM_PRI_MED_LOW, VBR, Non-Real-Time */
|
||||
IAD_ATM_UBR = 0, /* IAD_ATM_PRI_LOW */
|
||||
} iad_atmServiceCategory;
|
||||
|
||||
typedef unsigned int iad_atmDiffServCategory;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int cellRate;
|
||||
int round; /* IAD_ATM_RATE_CEILING, IAD_ATM_RATE_FLOOR */
|
||||
} iad_atmCellRateDesc;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int phyID; /* IAD_ATM_PHY0, IAD_ATM_PHY1 */
|
||||
unsigned int txQHnd; /* Tx HW Q */
|
||||
union _pri
|
||||
{
|
||||
int priority; /* TS Q: 4 priorities: IAD_ATM_PRI_HIGH, IAD_ATM_PRI_MED_HIGH, IAD_ATM_PRI_MED_LOW, IAD_ATM_PRI_LOW
|
||||
non-TS Q: 8 priorities: IAD_ATM_PRI_LEVEL_7, IAD_ATM_PRI_LEVEL_6,..., IAD_ATM_PRI_LEVEL_0 */
|
||||
iad_atmServiceCategory qosClass; /* IAD_ATM_CBR, IAD_ATM_VBR_RT, IAD_ATM_VBR_NRT, IAD_ATM_UBR */
|
||||
iad_atmDiffServCategory diffServClass; /* IP_QOS */
|
||||
} srvCat; /* service category */
|
||||
iad_atmCellRateDesc pcr; /* Peak Cell Rate */
|
||||
iad_atmCellRateDesc scr; /* Sustained Cell Rate. */
|
||||
iad_atmCellRateDesc mcr; /* Minimum Cell Rate, not used */
|
||||
int mbs; /* maximum bursting size in cells */
|
||||
int isPrioritize; /* TRUE: This flow is of the higher priority than the flows of the same QOS category.(Use MCR to boost priority) */
|
||||
} iad_atmTrfPar; /* Tx Traffic Parameters */
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int txGrpId;
|
||||
unsigned int flowId;
|
||||
iad_atmTrfPar trfPar;
|
||||
} Atm_Ictl_Flow_Set;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
unsigned int txGrpId;
|
||||
unsigned int vpi;
|
||||
unsigned int vci;
|
||||
|
||||
unsigned int encaps;
|
||||
unsigned int proto;
|
||||
|
||||
} Atm_Ictl_Open_Vcc;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
struct atm_vcc vcc;
|
||||
unsigned int valid;
|
||||
unsigned int on;
|
||||
unsigned int vccIndex; /* 0~7 */
|
||||
unsigned int itf;
|
||||
struct net_device_stats stats;
|
||||
} Atm_Priv;
|
||||
|
||||
|
||||
extern struct ppe_dev ppe_dev;
|
||||
|
||||
|
||||
int pp32_start(void);
|
||||
void pp32_stop(void);
|
||||
void init_rx_tables(void);
|
||||
void init_tx_tables(void);
|
||||
struct sk_buff* alloc_skb_rx(void);
|
||||
struct sk_buff* alloc_skb_tx(unsigned int);
|
||||
void resize_skb_rx(struct sk_buff *, unsigned int, int);
|
||||
struct sk_buff* atm_alloc_tx(struct atm_vcc *, unsigned int);
|
||||
void atm_free_tx_skb_vcc(struct sk_buff *);
|
||||
int alloc_tx_connection(int);
|
||||
int ppe_open(struct atm_vcc *vcc);
|
||||
void ppe_close(struct atm_vcc *vcc);
|
||||
int ppe_ioctl(struct atm_dev *dev, unsigned int cmd, void *arg);
|
||||
int ppe_send(struct atm_vcc *vcc, struct sk_buff *skb);
|
||||
int ppe_send_oam(struct atm_vcc *vcc, void *cell, int flags);
|
||||
int ppe_change_qos(struct atm_vcc *vcc, struct atm_qos *qos, int flags);
|
||||
irqreturn_t mailbox_irq_handler(int, void *);
|
||||
int find_vcc(struct atm_vcc *vcc);
|
||||
int find_vpi(unsigned int vpi);
|
||||
int find_vpivci(unsigned int vpi, unsigned int vci);
|
||||
void mailbox_signal(unsigned int channel, int is_tx);
|
||||
|
|
@ -1,800 +0,0 @@
|
|||
#include <asm/mach-ifxmips/cgu.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/atmdev.h>
|
||||
#include <linux/irq.h>
|
||||
|
||||
#include "common.h"
|
||||
#include "proc.h"
|
||||
|
||||
// our main struct
|
||||
struct ppe_dev ppe_dev;
|
||||
|
||||
static int port_max_connection[2] = {7, 7}; /* Maximum number of connections for ports (0-14) */
|
||||
static int port_cell_rate_up[2] = {3200, 3200}; /* Maximum TX cell rate for ports */
|
||||
static int qsb_tau = 1;
|
||||
static int qsb_srvm = 0x0f;
|
||||
static int qsb_tstep = 4;
|
||||
static int write_descriptor_delay = 0x20;
|
||||
static int aal5_fill_pattern = 0x007E;
|
||||
static int aal5r_max_packet_size = 0x0700;
|
||||
static int aal5r_min_packet_size = 0x0000;
|
||||
static int aal5s_max_packet_size = 0x0700;
|
||||
static int aal5s_min_packet_size = 0x0000;
|
||||
static int aal5r_drop_error_packet = 1;
|
||||
static int dma_rx_descriptor_length = 48;
|
||||
static int dma_tx_descriptor_length = 64;
|
||||
static int dma_rx_clp1_descriptor_threshold = 38;
|
||||
|
||||
//module_param(port_max_connection, "2-2i");
|
||||
//module_param(port_cell_rate_up, "2-2i");
|
||||
module_param(qsb_tau, int, 0);
|
||||
module_param(qsb_srvm, int, 0);
|
||||
module_param(qsb_tstep, int, 0);
|
||||
module_param(write_descriptor_delay, int, 0);
|
||||
module_param(aal5_fill_pattern, int, 0);
|
||||
module_param(aal5r_max_packet_size, int, 0);
|
||||
module_param(aal5r_min_packet_size, int, 0);
|
||||
module_param(aal5s_max_packet_size, int, 0);
|
||||
module_param(aal5s_min_packet_size, int, 0);
|
||||
module_param(aal5r_drop_error_packet, int, 0);
|
||||
module_param(dma_rx_descriptor_length, int, 0);
|
||||
module_param(dma_tx_descriptor_length, int, 0);
|
||||
module_param(dma_rx_clp1_descriptor_threshold, int, 0);
|
||||
|
||||
MODULE_PARM_DESC(port_cell_rate_up, "ATM port upstream rate in cells/s");
|
||||
MODULE_PARM_DESC(port_max_connection, "Maximum atm connection for port (0-1)");
|
||||
MODULE_PARM_DESC(qsb_tau, "Cell delay variation. Value must be > 0");
|
||||
MODULE_PARM_DESC(qsb_srvm, "Maximum burst size");
|
||||
MODULE_PARM_DESC(qsb_tstep, "n*32 cycles per sbs cycles n=1,2,4");
|
||||
MODULE_PARM_DESC(write_descriptor_delay, "PPE core clock cycles between descriptor write and effectiveness in external RAM");
|
||||
MODULE_PARM_DESC(a5_fill_pattern, "Filling pattern (PAD) for AAL5 frames");
|
||||
MODULE_PARM_DESC(aal5r_max_packet_size, "Max packet size in byte for downstream AAL5 frames");
|
||||
MODULE_PARM_DESC(aal5r_min_packet_size, "Min packet size in byte for downstream AAL5 frames");
|
||||
MODULE_PARM_DESC(aal5s_max_packet_size, "Max packet size in byte for upstream AAL5 frames");
|
||||
MODULE_PARM_DESC(aal5s_min_packet_size, "Min packet size in byte for upstream AAL5 frames");
|
||||
MODULE_PARM_DESC(aal5r_drop_error_packet, "Non-zero value to drop error packet for downstream");
|
||||
MODULE_PARM_DESC(dma_rx_descriptor_length, "Number of descriptor assigned to DMA RX channel (>16)");
|
||||
MODULE_PARM_DESC(dma_tx_descriptor_length, "Number of descriptor assigned to DMA TX channel (>16)");
|
||||
MODULE_PARM_DESC(dma_rx_clp1_descriptor_threshold, "Descriptor threshold for cells with cell loss priority 1");
|
||||
|
||||
void init_rx_tables(void)
|
||||
{
|
||||
int i, j;
|
||||
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: 0x03,
|
||||
pid_mask: 0x00,
|
||||
vpi_mask: 0x00,
|
||||
vci_mask: 0x00,
|
||||
pti_mask: 0x00,
|
||||
clear: 0x00};
|
||||
|
||||
/*
|
||||
* General Registers
|
||||
*/
|
||||
*CFG_WRX_HTUTS = ppe_dev.max_connections + OAM_HTU_ENTRY_NUMBER;
|
||||
*CFG_WRX_QNUM = ppe_dev.max_connections + OAM_RX_QUEUE_NUMBER + QSB_QUEUE_NUMBER_BASE;
|
||||
*CFG_WRX_DCHNUM = ppe_dev.dma.rx_total_channel_used;
|
||||
*WRX_DMACH_ON = (1 << ppe_dev.dma.rx_total_channel_used) - 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 = ppe_dev.aal5.rx_max_packet_size; // rx_buffer_size
|
||||
wrx_queue_config.oversize = ppe_dev.aal5.rx_max_packet_size;
|
||||
wrx_queue_config.undersize = ppe_dev.aal5.rx_min_packet_size;
|
||||
wrx_queue_config.errdp = ppe_dev.aal5.rx_drop_error_packet;
|
||||
for ( i = 0; i < QSB_QUEUE_NUMBER_BASE; i++ )
|
||||
*WRX_QUEUE_CONFIG(i) = wrx_queue_config;
|
||||
for ( j = 0; j < ppe_dev.max_connections; j++ )
|
||||
{
|
||||
#if !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
/* If RX QoS is disabled, the DMA channel must be fixed. */
|
||||
wrx_queue_config.dmach = ppe_dev.connection[i].rx_dma_channel;
|
||||
#endif // !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
*WRX_QUEUE_CONFIG(i++) = wrx_queue_config;
|
||||
}
|
||||
/* OAM RX Queue */
|
||||
for ( j = 0; j < OAM_RX_DMA_CHANNEL_NUMBER; j++ )
|
||||
{
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
wrx_queue_config.dmach = RX_DMA_CH_OAM;
|
||||
#else
|
||||
wrx_queue_config.dmach = ppe_dev.oam_rx_dma_channel + j;
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
*WRX_QUEUE_CONFIG(i++) = wrx_queue_config;
|
||||
}
|
||||
|
||||
wrx_dma_channel_config.deslen = ppe_dev.dma.rx_descriptor_number;
|
||||
wrx_dma_channel_config.chrl = 0;
|
||||
wrx_dma_channel_config.clp1th = ppe_dev.dma.rx_clp1_desc_threshold;
|
||||
wrx_dma_channel_config.mode = WRX_DMA_CHANNEL_COUNTER_MODE;
|
||||
wrx_dma_channel_config.rlcfg = WRX_DMA_BUF_LEN_PER_DESCRIPTOR;
|
||||
for ( i = 0; i < ppe_dev.dma.rx_total_channel_used; i++ )
|
||||
{
|
||||
wrx_dma_channel_config.desba = (((u32)ppe_dev.dma.rx_descriptor_base >> 2) & 0x0FFFFFFF) + ppe_dev.dma.rx_descriptor_number * i * (sizeof(struct rx_descriptor) >> 2);
|
||||
*WRX_DMA_CHANNEL_CONFIG(i) = wrx_dma_channel_config;
|
||||
}
|
||||
|
||||
/*
|
||||
* HTU Tables
|
||||
*/
|
||||
for ( i = 0; i < ppe_dev.max_connections; 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 = ppe_dev.oam_rx_queue;
|
||||
htu_result.type = 1;
|
||||
htu_result.ven = 1;
|
||||
htu_result.qid = ppe_dev.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 = ppe_dev.oam_rx_queue;
|
||||
htu_result.type = 1;
|
||||
htu_result.ven = 1;
|
||||
htu_result.qid = ppe_dev.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 = ppe_dev.oam_rx_queue;
|
||||
htu_result.type = 1;
|
||||
htu_result.ven = 1;
|
||||
htu_result.qid = ppe_dev.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;
|
||||
}
|
||||
|
||||
void init_tx_tables(void)
|
||||
{
|
||||
int i, j;
|
||||
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 = ppe_dev.dma.tx_total_channel_used + QSB_QUEUE_NUMBER_BASE;
|
||||
*WTX_DMACH_ON = ((1 << (ppe_dev.dma.tx_total_channel_used + QSB_QUEUE_NUMBER_BASE)) - 1) ^ ((1 << QSB_QUEUE_NUMBER_BASE) - 1);
|
||||
*CFG_WRDES_DELAY = ppe_dev.dma.write_descriptor_delay;
|
||||
|
||||
/*
|
||||
* WTX Port Configuration Table
|
||||
*/
|
||||
#if !defined(DISABLE_QSB) || !DISABLE_QSB
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
*WTX_PORT_CONFIG(i) = wtx_port_config;
|
||||
#else
|
||||
wtx_port_config.qsben = 0;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
{
|
||||
wtx_port_config.qid = ppe_dev.port[i].connection_base;
|
||||
*WTX_PORT_CONFIG(i) = wtx_port_config;
|
||||
|
||||
printk("port %d: qid = %d, qsb disabled\n", i, wtx_port_config.qid);
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* WTX Queue Configuration Table
|
||||
*/
|
||||
wtx_queue_config.res1 = 0;
|
||||
wtx_queue_config.res2 = 0;
|
||||
// wtx_queue_config.type = 0x03;
|
||||
wtx_queue_config.type = 0x0;
|
||||
#if !defined(DISABLE_QSB) || !DISABLE_QSB
|
||||
wtx_queue_config.qsben = 1;
|
||||
#else
|
||||
wtx_queue_config.qsben = 0;
|
||||
#endif
|
||||
wtx_queue_config.sbid = 0;
|
||||
for ( i = 0; i < QSB_QUEUE_NUMBER_BASE; i++ )
|
||||
*WTX_QUEUE_CONFIG(i) = wtx_queue_config;
|
||||
for ( j = 0; j < ppe_dev.max_connections; j++ )
|
||||
{
|
||||
wtx_queue_config.sbid = ppe_dev.connection[i].port & 0x01; /* assign QSB to TX queue */
|
||||
*WTX_QUEUE_CONFIG(i) = wtx_queue_config;
|
||||
i++;
|
||||
}
|
||||
/* OAM TX Queue */
|
||||
// wtx_queue_config.type = 0x01;
|
||||
wtx_queue_config.type = 0x00;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
{
|
||||
wtx_queue_config.sbid = i & 0x01;
|
||||
for ( j = 0; j < OAM_TX_QUEUE_NUMBER_PER_PORT; j++ )
|
||||
*WTX_QUEUE_CONFIG(ppe_dev.port[i].oam_tx_queue + j) = wtx_queue_config;
|
||||
}
|
||||
|
||||
wtx_dma_channel_config.mode = WRX_DMA_CHANNEL_COUNTER_MODE;
|
||||
wtx_dma_channel_config.deslen = 0;
|
||||
wtx_dma_channel_config.desba = 0;
|
||||
for ( i = 0; i < QSB_QUEUE_NUMBER_BASE; i++ )
|
||||
*WTX_DMA_CHANNEL_CONFIG(i) = wtx_dma_channel_config;
|
||||
/* normal connection and OAM channel */
|
||||
wtx_dma_channel_config.deslen = ppe_dev.dma.tx_descriptor_number;
|
||||
for ( j = 0; j < ppe_dev.dma.tx_total_channel_used; j++ )
|
||||
{
|
||||
wtx_dma_channel_config.desba = (((u32)ppe_dev.dma.tx_descriptor_base >> 2) & 0x0FFFFFFF) + ppe_dev.dma.tx_descriptor_number * j * (sizeof(struct tx_descriptor) >> 2);
|
||||
*WTX_DMA_CHANNEL_CONFIG(i++) = wtx_dma_channel_config;
|
||||
}
|
||||
}
|
||||
|
||||
static inline void qsb_global_set(void)
|
||||
{
|
||||
int i, j;
|
||||
u32 qsb_clk = cgu_get_fpi_bus_clock(2);
|
||||
u32 tmp1, tmp2, tmp3;
|
||||
union qsb_queue_parameter_table qsb_queue_parameter_table = {{0}};
|
||||
union qsb_queue_vbr_parameter_table qsb_queue_vbr_parameter_table = {{0}};
|
||||
int qsb_qid;
|
||||
|
||||
*QSB_ICDV = QSB_ICDV_TAU_SET(ppe_dev.qsb.tau);
|
||||
*QSB_SBL = QSB_SBL_SBL_SET(ppe_dev.qsb.sbl);
|
||||
*QSB_CFG = QSB_CFG_TSTEPC_SET(ppe_dev.qsb.tstepc >> 1);
|
||||
|
||||
/*
|
||||
* set SCT and SPT per port
|
||||
*/
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( ppe_dev.port[i].max_connections != 0 && ppe_dev.port[i].tx_max_cell_rate != 0 )
|
||||
{
|
||||
tmp1 = ((qsb_clk * ppe_dev.qsb.tstepc) >> 1) / ppe_dev.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);
|
||||
/* 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);
|
||||
}
|
||||
|
||||
/*
|
||||
* set OAM TX queue
|
||||
*/
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( ppe_dev.port[i].max_connections != 0 )
|
||||
{
|
||||
tmp1 = ((qsb_clk * ppe_dev.qsb.tstepc) >> 1) / ppe_dev.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);
|
||||
|
||||
/* 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);
|
||||
}
|
||||
|
||||
/*
|
||||
* * set OAM TX queue
|
||||
* */
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( ppe_dev.port[i].max_connections != 0 )
|
||||
for ( j = 0; j < OAM_TX_QUEUE_NUMBER_PER_PORT; j++ )
|
||||
{
|
||||
qsb_qid = ppe_dev.port[i].oam_tx_queue + j;
|
||||
|
||||
/* disable PCR limiter */
|
||||
qsb_queue_parameter_table.bit.tp = 0;
|
||||
/* set WFQ as real time queue */
|
||||
qsb_queue_parameter_table.bit.wfqf = 0;
|
||||
/* disable leaky bucket shaper */
|
||||
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);
|
||||
/* 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);
|
||||
}
|
||||
}
|
||||
|
||||
static inline void clear_ppe_dev(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < ppe_dev.dma.tx_total_channel_used; i++ )
|
||||
{
|
||||
int conn = i + QSB_QUEUE_NUMBER_BASE;
|
||||
int desc_base;
|
||||
struct sk_buff *skb;
|
||||
|
||||
while(ppe_dev.dma.tx_desc_release_pos[conn] != ppe_dev.dma.tx_desc_alloc_pos[conn])
|
||||
{
|
||||
desc_base = ppe_dev.dma.tx_descriptor_number * (conn - QSB_QUEUE_NUMBER_BASE) + ppe_dev.dma.tx_desc_release_pos[conn];
|
||||
if(!ppe_dev.dma.tx_descriptor_base[desc_base].own)
|
||||
{
|
||||
skb = ppe_dev.dma.tx_skb_pointers[desc_base];
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
|
||||
// pretend PP32 hold owner bit, so that won't be released more than once, so allocation process don't check this bit
|
||||
ppe_dev.dma.tx_descriptor_base[desc_base].own = 1;
|
||||
}
|
||||
if (++ppe_dev.dma.tx_desc_release_pos[conn] == ppe_dev.dma.tx_descriptor_number)
|
||||
ppe_dev.dma.tx_desc_release_pos[conn] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = ppe_dev.dma.rx_total_channel_used * ppe_dev.dma.rx_descriptor_number - 1; i >= 0; i--)
|
||||
dev_kfree_skb_any(*(struct sk_buff **)(((ppe_dev.dma.rx_descriptor_base[i].dataptr << 2) | KSEG0) - 4));
|
||||
|
||||
kfree(ppe_dev.dma.tx_skb_pointers);
|
||||
kfree(ppe_dev.dma.tx_descriptor_addr);
|
||||
kfree(ppe_dev.dma.rx_descriptor_addr);
|
||||
}
|
||||
|
||||
static inline int init_ppe_dev(void)
|
||||
{
|
||||
int i, j;
|
||||
int rx_desc, tx_desc;
|
||||
int conn;
|
||||
int oam_tx_queue;
|
||||
#if !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
int rx_dma_channel_base;
|
||||
int rx_dma_channel_assigned;
|
||||
#endif // !defined(ENABLE_RX_QOS) || !ENABLE_RX_QOS
|
||||
|
||||
struct rx_descriptor rx_descriptor = { own: 1,
|
||||
c: 0,
|
||||
sop: 1,
|
||||
eop: 1,
|
||||
res1: 0,
|
||||
byteoff:0,
|
||||
res2: 0,
|
||||
id: 0,
|
||||
err: 0,
|
||||
datalen:0,
|
||||
res3: 0,
|
||||
dataptr:0};
|
||||
|
||||
struct tx_descriptor tx_descriptor = { own: 1, // pretend it's hold by PP32
|
||||
c: 0,
|
||||
sop: 1,
|
||||
eop: 1,
|
||||
byteoff:0,
|
||||
res1: 0,
|
||||
iscell: 0,
|
||||
clp: 0,
|
||||
datalen:0,
|
||||
res2: 0,
|
||||
dataptr:0};
|
||||
|
||||
memset(&ppe_dev, 0, sizeof(ppe_dev));
|
||||
|
||||
/*
|
||||
* Setup AAL5 members, buffer size must be larger than max packet size plus overhead.
|
||||
*/
|
||||
ppe_dev.aal5.padding_byte = (u8)aal5_fill_pattern;
|
||||
ppe_dev.aal5.rx_max_packet_size = (u32)aal5r_max_packet_size;
|
||||
ppe_dev.aal5.rx_min_packet_size = (u32)aal5r_min_packet_size;
|
||||
ppe_dev.aal5.rx_buffer_size = ((u32)(aal5r_max_packet_size > CELL_SIZE ? aal5r_max_packet_size + MAX_RX_FRAME_EXTRA_BYTES : CELL_SIZE + MAX_RX_FRAME_EXTRA_BYTES) + DMA_ALIGNMENT - 1) & ~(DMA_ALIGNMENT - 1);
|
||||
ppe_dev.aal5.tx_max_packet_size = (u32)aal5s_max_packet_size;
|
||||
ppe_dev.aal5.tx_min_packet_size = (u32)aal5s_min_packet_size;
|
||||
ppe_dev.aal5.tx_buffer_size = ((u32)(aal5s_max_packet_size > CELL_SIZE ? aal5s_max_packet_size + MAX_TX_FRAME_EXTRA_BYTES : CELL_SIZE + MAX_TX_FRAME_EXTRA_BYTES) + DMA_ALIGNMENT - 1) & ~(DMA_ALIGNMENT - 1);
|
||||
ppe_dev.aal5.rx_drop_error_packet = aal5r_drop_error_packet ? 1 : 0;
|
||||
|
||||
/*
|
||||
* Setup QSB members, please refer to Amazon spec 15.4 to get the value calculation formula.
|
||||
*/
|
||||
ppe_dev.qsb.tau = (u32)qsb_tau;
|
||||
ppe_dev.qsb.tstepc = (u32)qsb_tstep;
|
||||
ppe_dev.qsb.sbl = (u32)qsb_srvm;
|
||||
|
||||
/*
|
||||
* Setup port, connection, other members.
|
||||
*/
|
||||
conn = 0;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
{
|
||||
/* first connection ID of port */
|
||||
ppe_dev.port[i].connection_base = conn + QSB_QUEUE_NUMBER_BASE;
|
||||
/* max number of connections of port */
|
||||
ppe_dev.port[i].max_connections = (u32)port_max_connection[i];
|
||||
/* max cell rate the port has */
|
||||
ppe_dev.port[i].tx_max_cell_rate = (u32)port_cell_rate_up[i];
|
||||
|
||||
/* link connection ID to port ID */
|
||||
for ( j = port_max_connection[i] - 1; j >= 0; j-- )
|
||||
ppe_dev.connection[conn++ + QSB_QUEUE_NUMBER_BASE].port = i;
|
||||
}
|
||||
/* total connection numbers of all ports */
|
||||
ppe_dev.max_connections = conn;
|
||||
/* OAM RX queue ID, which is the first available connection ID after */
|
||||
/* connections assigned to ports. */
|
||||
ppe_dev.oam_rx_queue = conn + QSB_QUEUE_NUMBER_BASE;
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
oam_tx_queue = conn;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( port_max_connection[i] != 0 )
|
||||
{
|
||||
ppe_dev.port[i].oam_tx_queue = oam_tx_queue + QSB_QUEUE_NUMBER_BASE;
|
||||
|
||||
for ( j = 0; j < OAM_TX_QUEUE_NUMBER_PER_PORT; j++ )
|
||||
/* Since connection ID is one to one mapped to RX/TX queue ID, the connection */
|
||||
/* structure must be reserved for OAM RX/TX queues, and member "port" is set */
|
||||
/* according to port to which OAM TX queue is connected. */
|
||||
ppe_dev.connection[oam_tx_queue++ + QSB_QUEUE_NUMBER_BASE].port = i;
|
||||
}
|
||||
/* DMA RX channel assigned to OAM RX queue */
|
||||
ppe_dev.oam_rx_dma_channel = RX_DMA_CH_OAM;
|
||||
/* DMA RX channel will be assigned dynamically when VCC is open. */
|
||||
#else // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
rx_dma_channel_base = 0;
|
||||
oam_tx_queue = conn;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( port_max_connection[i] != 0 )
|
||||
{
|
||||
/* Calculate the number of DMA RX channels could be assigned to port. */
|
||||
rx_dma_channel_assigned = i == ATM_PORT_NUMBER - 1
|
||||
? (MAX_RX_DMA_CHANNEL_NUMBER - OAM_RX_DMA_CHANNEL_NUMBER) - rx_dma_channel_base
|
||||
: (ppe_dev.port[i].max_connections * (MAX_RX_DMA_CHANNEL_NUMBER - OAM_RX_DMA_CHANNEL_NUMBER) + ppe_dev.max_connections / 2) / ppe_dev.max_connections;
|
||||
/* Amend the number, which could be zero. */
|
||||
if ( rx_dma_channel_assigned == 0 )
|
||||
rx_dma_channel_assigned = 1;
|
||||
/* Calculate the first DMA RX channel ID could be assigned to port. */
|
||||
if ( rx_dma_channel_base + rx_dma_channel_assigned > MAX_RX_DMA_CHANNEL_NUMBER - OAM_RX_DMA_CHANNEL_NUMBER )
|
||||
rx_dma_channel_base = MAX_RX_DMA_CHANNEL_NUMBER - OAM_RX_DMA_CHANNEL_NUMBER - rx_dma_channel_assigned;
|
||||
|
||||
/* first DMA RX channel ID */
|
||||
ppe_dev.port[i].rx_dma_channel_base = rx_dma_channel_base;
|
||||
/* number of DMA RX channels assigned to this port */
|
||||
ppe_dev.port[i].rx_dma_channel_assigned = rx_dma_channel_assigned;
|
||||
/* OAM TX queue ID, which must be assigned after connections assigned to ports */
|
||||
ppe_dev.port[i].oam_tx_queue = oam_tx_queue + QSB_QUEUE_NUMBER_BASE;
|
||||
|
||||
rx_dma_channel_base += rx_dma_channel_assigned;
|
||||
|
||||
for ( j = 0; j < OAM_TX_QUEUE_NUMBER_PER_PORT; j++ )
|
||||
/* Since connection ID is one to one mapped to RX/TX queue ID, the connection */
|
||||
/* structure must be reserved for OAM RX/TX queues, and member "port" is set */
|
||||
/* according to port to which OAM TX queue is connected. */
|
||||
ppe_dev.connection[oam_tx_queue++ + QSB_QUEUE_NUMBER_BASE].port = i;
|
||||
}
|
||||
/* DMA RX channel assigned to OAM RX queue */
|
||||
ppe_dev.oam_rx_dma_channel = rx_dma_channel_base;
|
||||
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
for ( j = 0; j < port_max_connection[i]; j++ )
|
||||
/* Assign DMA RX channel to RX queues. One channel could be assigned to more than one queue. */
|
||||
ppe_dev.connection[ppe_dev.port[i].connection_base + j].rx_dma_channel = ppe_dev.port[i].rx_dma_channel_base + j % ppe_dev.port[i].rx_dma_channel_assigned;
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
|
||||
/* initialize semaphore used by open and close */
|
||||
sema_init(&ppe_dev.sem, 1);
|
||||
/* descriptor number of RX DMA channel */
|
||||
ppe_dev.dma.rx_descriptor_number = dma_rx_descriptor_length;
|
||||
/* descriptor number of TX DMA channel */
|
||||
ppe_dev.dma.tx_descriptor_number = dma_tx_descriptor_length;
|
||||
/* If used descriptors are more than this value, cell with CLP1 is dropped. */
|
||||
ppe_dev.dma.rx_clp1_desc_threshold = dma_rx_clp1_descriptor_threshold;
|
||||
|
||||
/* delay on descriptor write path */
|
||||
ppe_dev.dma.write_descriptor_delay = write_descriptor_delay;
|
||||
|
||||
/* total DMA RX channel used */
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
ppe_dev.dma.rx_total_channel_used = RX_DMA_CH_TOTAL;
|
||||
#else
|
||||
ppe_dev.dma.rx_total_channel_used = rx_dma_channel_base + OAM_RX_DMA_CHANNEL_NUMBER;
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
/* total DMA TX channel used (exclude channel reserved by QSB) */
|
||||
ppe_dev.dma.tx_total_channel_used = oam_tx_queue;
|
||||
|
||||
/* allocate memory for RX descriptors */
|
||||
ppe_dev.dma.rx_descriptor_addr = kmalloc(ppe_dev.dma.rx_total_channel_used * ppe_dev.dma.rx_descriptor_number * sizeof(struct rx_descriptor) + 4, GFP_KERNEL | GFP_DMA);
|
||||
if ( !ppe_dev.dma.rx_descriptor_addr )
|
||||
goto RX_DESCRIPTOR_BASE_ALLOCATE_FAIL;
|
||||
/* do alignment (DWORD) */
|
||||
ppe_dev.dma.rx_descriptor_base = (struct rx_descriptor *)(((u32)ppe_dev.dma.rx_descriptor_addr + 0x03) & ~0x03);
|
||||
ppe_dev.dma.rx_descriptor_base = (struct rx_descriptor *)((u32)ppe_dev.dma.rx_descriptor_base | KSEG1); // no cache
|
||||
|
||||
/* allocate memory for TX descriptors */
|
||||
ppe_dev.dma.tx_descriptor_addr = kmalloc(ppe_dev.dma.tx_total_channel_used * ppe_dev.dma.tx_descriptor_number * sizeof(struct tx_descriptor) + 4, GFP_KERNEL | GFP_DMA);
|
||||
if ( !ppe_dev.dma.tx_descriptor_addr )
|
||||
goto TX_DESCRIPTOR_BASE_ALLOCATE_FAIL;
|
||||
/* do alignment (DWORD) */
|
||||
ppe_dev.dma.tx_descriptor_base = (struct tx_descriptor *)(((u32)ppe_dev.dma.tx_descriptor_addr + 0x03) & ~0x03);
|
||||
ppe_dev.dma.tx_descriptor_base = (struct tx_descriptor *)((u32)ppe_dev.dma.tx_descriptor_base | KSEG1); // no cache
|
||||
/* allocate pointers to TX sk_buff */
|
||||
ppe_dev.dma.tx_skb_pointers = kmalloc(ppe_dev.dma.tx_total_channel_used * ppe_dev.dma.tx_descriptor_number * sizeof(struct sk_buff *), GFP_KERNEL);
|
||||
if ( !ppe_dev.dma.tx_skb_pointers )
|
||||
goto TX_SKB_POINTER_ALLOCATE_FAIL;
|
||||
memset(ppe_dev.dma.tx_skb_pointers, 0, ppe_dev.dma.tx_total_channel_used * ppe_dev.dma.tx_descriptor_number * sizeof(struct sk_buff *));
|
||||
|
||||
/* Allocate RX sk_buff and fill up RX descriptors. */
|
||||
rx_descriptor.datalen = ppe_dev.aal5.rx_buffer_size;
|
||||
for ( rx_desc = ppe_dev.dma.rx_total_channel_used * ppe_dev.dma.rx_descriptor_number - 1; rx_desc >= 0; rx_desc-- )
|
||||
{
|
||||
struct sk_buff *skb;
|
||||
skb = alloc_skb_rx();
|
||||
if ( skb == NULL )
|
||||
panic("sk buffer is used up\n");
|
||||
rx_descriptor.dataptr = (u32)skb->data >> 2;
|
||||
ppe_dev.dma.rx_descriptor_base[rx_desc] = rx_descriptor;
|
||||
|
||||
}
|
||||
|
||||
/* Fill up TX descriptors. */
|
||||
tx_descriptor.datalen = ppe_dev.aal5.tx_buffer_size;
|
||||
for ( tx_desc = ppe_dev.dma.tx_total_channel_used * ppe_dev.dma.tx_descriptor_number - 1; tx_desc >= 0; tx_desc-- )
|
||||
ppe_dev.dma.tx_descriptor_base[tx_desc] = tx_descriptor;
|
||||
|
||||
return 0;
|
||||
|
||||
TX_SKB_POINTER_ALLOCATE_FAIL:
|
||||
kfree(ppe_dev.dma.tx_descriptor_addr);
|
||||
TX_DESCRIPTOR_BASE_ALLOCATE_FAIL:
|
||||
kfree(ppe_dev.dma.rx_descriptor_addr);
|
||||
RX_DESCRIPTOR_BASE_ALLOCATE_FAIL:
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
|
||||
static inline void clear_share_buffer(void)
|
||||
{
|
||||
volatile u32 *p = SB_RAM0_ADDR(0);
|
||||
unsigned int i;
|
||||
|
||||
/* write all zeros only */
|
||||
for ( i = 0; i < SB_RAM0_DWLEN + SB_RAM1_DWLEN + SB_RAM2_DWLEN + SB_RAM3_DWLEN; i++ )
|
||||
*p++ = 0;
|
||||
}
|
||||
|
||||
|
||||
static inline void check_parameters(void)
|
||||
{
|
||||
int i;
|
||||
int enabled_port_number;
|
||||
int unassigned_queue_number;
|
||||
int assigned_queue_number;
|
||||
|
||||
enabled_port_number = 0;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( port_max_connection[i] < 1 )
|
||||
port_max_connection[i] = 0;
|
||||
else
|
||||
enabled_port_number++;
|
||||
/* If the max connection number of a port is not 0, the port is enabled */
|
||||
/* and at lease two connection ID must be reserved for this port. One of */
|
||||
/* them is used as OAM TX path. */
|
||||
unassigned_queue_number = MAX_QUEUE_NUMBER - QSB_QUEUE_NUMBER_BASE;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( port_max_connection[i] > 0 )
|
||||
{
|
||||
enabled_port_number--;
|
||||
assigned_queue_number = unassigned_queue_number - enabled_port_number * (1 + OAM_TX_QUEUE_NUMBER_PER_PORT) - OAM_TX_QUEUE_NUMBER_PER_PORT;
|
||||
if ( assigned_queue_number > MAX_QUEUE_NUMBER_PER_PORT - OAM_TX_QUEUE_NUMBER_PER_PORT )
|
||||
assigned_queue_number = MAX_QUEUE_NUMBER_PER_PORT - OAM_TX_QUEUE_NUMBER_PER_PORT;
|
||||
if ( port_max_connection[i] > assigned_queue_number )
|
||||
{
|
||||
port_max_connection[i] = assigned_queue_number;
|
||||
unassigned_queue_number -= assigned_queue_number;
|
||||
}
|
||||
else
|
||||
unassigned_queue_number -= port_max_connection[i];
|
||||
}
|
||||
|
||||
/* 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 >= 65536 - MAX_RX_FRAME_EXTRA_BYTES )
|
||||
aal5r_max_packet_size = 65536 - 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 >= 65536 - MAX_TX_FRAME_EXTRA_BYTES )
|
||||
aal5s_max_packet_size = 65536 - 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;
|
||||
}
|
||||
|
||||
static struct atmdev_ops ppe_atm_ops = {
|
||||
owner: THIS_MODULE,
|
||||
open: ppe_open,
|
||||
close: ppe_close,
|
||||
ioctl: ppe_ioctl,
|
||||
send: ppe_send,
|
||||
send_oam: ppe_send_oam,
|
||||
change_qos: ppe_change_qos,
|
||||
};
|
||||
|
||||
int __init danube_ppe_init(void)
|
||||
{
|
||||
int ret;
|
||||
int port_num;
|
||||
|
||||
check_parameters();
|
||||
|
||||
ret = init_ppe_dev();
|
||||
if ( ret )
|
||||
goto INIT_PPE_DEV_FAIL;
|
||||
|
||||
clear_share_buffer();
|
||||
init_rx_tables();
|
||||
init_tx_tables();
|
||||
printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__);
|
||||
|
||||
for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ )
|
||||
if ( ppe_dev.port[port_num].max_connections != 0 )
|
||||
{
|
||||
printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__);
|
||||
ppe_dev.port[port_num].dev = atm_dev_register("danube_atm", &ppe_atm_ops, -1, 0UL);
|
||||
if ( !ppe_dev.port[port_num].dev )
|
||||
{
|
||||
printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__);
|
||||
ret = -EIO;
|
||||
goto ATM_DEV_REGISTER_FAIL;
|
||||
}
|
||||
else
|
||||
{
|
||||
printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__);
|
||||
ppe_dev.port[port_num].dev->ci_range.vpi_bits = 8;
|
||||
ppe_dev.port[port_num].dev->ci_range.vci_bits = 16;
|
||||
ppe_dev.port[port_num].dev->link_rate = ppe_dev.port[port_num].tx_max_cell_rate;
|
||||
ppe_dev.port[port_num].dev->dev_data = (void*)port_num;
|
||||
}
|
||||
}
|
||||
/* register interrupt handler */
|
||||
ret = request_irq(IFXMIPS_PPE_MBOX_INT, mailbox_irq_handler, IRQF_DISABLED, "ppe_mailbox_isr", NULL);
|
||||
if ( ret )
|
||||
{
|
||||
if ( ret == -EBUSY )
|
||||
printk("ppe: IRQ may be occupied by ETH2 driver, please reconfig to disable it.\n");
|
||||
goto REQUEST_IRQ_IFXMIPS_PPE_MBOX_INT_FAIL;
|
||||
}
|
||||
disable_irq(IFXMIPS_PPE_MBOX_INT);
|
||||
|
||||
#if defined(CONFIG_PCI) && defined(USE_FIX_FOR_PCI_PPE) && USE_FIX_FOR_PCI_PPE
|
||||
ret = request_irq(PPE_MAILBOX_IGU0_INT, pci_fix_irq_handler, SA_INTERRUPT, "ppe_pci_fix_isr", NULL);
|
||||
if ( ret )
|
||||
printk("failed in registering mailbox 0 interrupt (pci fix)\n");
|
||||
#endif // defined(CONFIG_PCI) && defined(USE_FIX_FOR_PCI_PPE) && USE_FIX_FOR_PCI_PPE
|
||||
|
||||
ret = pp32_start();
|
||||
if ( ret )
|
||||
goto PP32_START_FAIL;
|
||||
|
||||
qsb_global_set();
|
||||
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;
|
||||
|
||||
/* create proc file */
|
||||
proc_file_create();
|
||||
|
||||
printk("ppe: ATM init succeeded (firmware version 1.1.0.2.1.13\n");
|
||||
return 0;
|
||||
|
||||
PP32_START_FAIL:
|
||||
|
||||
free_irq(IFXMIPS_PPE_MBOX_INT, NULL);
|
||||
REQUEST_IRQ_IFXMIPS_PPE_MBOX_INT_FAIL:
|
||||
ATM_DEV_REGISTER_FAIL:
|
||||
clear_ppe_dev();
|
||||
INIT_PPE_DEV_FAIL:
|
||||
printk("ppe: ATM init failed\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
void __exit danube_ppe_exit(void)
|
||||
{
|
||||
int port_num;
|
||||
register int l;
|
||||
proc_file_delete();
|
||||
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;
|
||||
/* idle for a while to finish running HTU search */
|
||||
for (l = 0; l < IDLE_CYCLE_NUMBER; l++ );
|
||||
pp32_stop();
|
||||
free_irq(IFXMIPS_PPE_MBOX_INT, NULL);
|
||||
for ( port_num = 0; port_num < ATM_PORT_NUMBER; port_num++ )
|
||||
if ( ppe_dev.port[port_num].max_connections != 0 )
|
||||
atm_dev_deregister(ppe_dev.port[port_num].dev);
|
||||
clear_ppe_dev();
|
||||
}
|
||||
|
||||
module_init(danube_ppe_init);
|
||||
module_exit(danube_ppe_exit);
|
||||
|
||||
MODULE_LICENSE("GPL");
|
||||
|
|
@ -1,506 +0,0 @@
|
|||
#include <linux/atmdev.h>
|
||||
#include <linux/irq.h>
|
||||
|
||||
#include "common.h"
|
||||
|
||||
void mailbox_signal(unsigned int channel, int is_tx)
|
||||
{
|
||||
if(is_tx)
|
||||
{
|
||||
while(MBOX_IGU3_ISR_ISR(channel + 16));
|
||||
*MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(channel + 16);
|
||||
} else {
|
||||
while(MBOX_IGU3_ISR_ISR(channel));
|
||||
*MBOX_IGU3_ISRS = MBOX_IGU3_ISRS_SET(channel);
|
||||
}
|
||||
}
|
||||
|
||||
static int mailbox_rx_irq_handler(unsigned int channel, unsigned int *len)
|
||||
{
|
||||
int conn;
|
||||
int skb_base;
|
||||
register struct rx_descriptor reg_desc;
|
||||
struct rx_descriptor *desc;
|
||||
struct sk_buff *skb;
|
||||
struct atm_vcc *vcc;
|
||||
struct rx_inband_trailer *trailer;
|
||||
|
||||
/* get sk_buff pointer and descriptor */
|
||||
skb_base = ppe_dev.dma.rx_descriptor_number * channel + ppe_dev.dma.rx_desc_read_pos[channel];
|
||||
desc = &ppe_dev.dma.rx_descriptor_base[skb_base];
|
||||
reg_desc = *desc;
|
||||
if ( reg_desc.own || !reg_desc.c )
|
||||
return -EAGAIN;
|
||||
|
||||
if ( ++ppe_dev.dma.rx_desc_read_pos[channel] == ppe_dev.dma.rx_descriptor_number )
|
||||
ppe_dev.dma.rx_desc_read_pos[channel] = 0;
|
||||
|
||||
skb = *(struct sk_buff **)((((u32)reg_desc.dataptr << 2) | KSEG0) - 4);
|
||||
if ( (u32)skb <= 0x80000000 )
|
||||
{
|
||||
int key = 0;
|
||||
printk("skb problem: skb = %08X, system is panic!\n", (u32)skb);
|
||||
for ( ; !key; );
|
||||
}
|
||||
|
||||
conn = reg_desc.id;
|
||||
|
||||
if ( conn == ppe_dev.oam_rx_queue )
|
||||
{
|
||||
/* OAM */
|
||||
struct uni_cell_header *header = (struct uni_cell_header *)skb->data;
|
||||
|
||||
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 && ppe_dev.connection[conn].vcc != NULL )
|
||||
{
|
||||
vcc = ppe_dev.connection[conn].vcc;
|
||||
ppe_dev.connection[conn].access_time = xtime;
|
||||
if ( vcc->push_oam != NULL )
|
||||
vcc->push_oam(vcc, skb->data);
|
||||
}
|
||||
|
||||
/* don't need resize */
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( len )
|
||||
*len = 0;
|
||||
|
||||
if ( ppe_dev.connection[conn].vcc != NULL )
|
||||
{
|
||||
vcc = ppe_dev.connection[conn].vcc;
|
||||
|
||||
if ( !reg_desc.err )
|
||||
if ( vcc->qos.aal == ATM_AAL5 )
|
||||
{
|
||||
/* AAL5 packet */
|
||||
resize_skb_rx(skb, reg_desc.datalen + reg_desc.byteoff, 0);
|
||||
skb_reserve(skb, reg_desc.byteoff);
|
||||
skb_put(skb, reg_desc.datalen);
|
||||
|
||||
if ( (u32)ATM_SKB(skb) <= 0x80000000 )
|
||||
{
|
||||
int key = 0;
|
||||
printk("ATM_SKB(skb) problem: ATM_SKB(skb) = %08X, system is panic!\n", (u32)ATM_SKB(skb));
|
||||
for ( ; !key; );
|
||||
}
|
||||
ATM_SKB(skb)->vcc = vcc;
|
||||
ppe_dev.connection[conn].access_time = xtime;
|
||||
if ( atm_charge(vcc, skb->truesize) )
|
||||
{
|
||||
struct sk_buff *new_skb;
|
||||
|
||||
new_skb = alloc_skb_rx();
|
||||
if ( new_skb )
|
||||
{
|
||||
|
||||
UPDATE_VCC_STAT(conn, rx_pdu, 1);
|
||||
|
||||
ppe_dev.mib.wrx_pdu++;
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx);
|
||||
vcc->push(vcc, skb);
|
||||
{
|
||||
struct k_atm_aal_stats stats = *vcc->stats;
|
||||
int flag = 0;
|
||||
|
||||
vcc->push(vcc, skb);
|
||||
if ( vcc->stats->rx.counter != stats.rx.counter )
|
||||
{
|
||||
printk("vcc->stats->rx (diff) = %d", vcc->stats->rx.counter - stats.rx.counter);
|
||||
flag++;
|
||||
}
|
||||
if ( vcc->stats->rx_err.counter != stats.rx_err.counter )
|
||||
{
|
||||
printk("vcc->stats->rx_err (diff) = %d", vcc->stats->rx_err.counter - stats.rx_err.counter);
|
||||
flag++;
|
||||
}
|
||||
if ( vcc->stats->rx_drop.counter != stats.rx_drop.counter )
|
||||
{
|
||||
printk("vcc->stats->rx_drop (diff) = %d", vcc->stats->rx_drop.counter - stats.rx_drop.counter);
|
||||
flag++;
|
||||
}
|
||||
if ( vcc->stats->tx.counter != stats.tx.counter )
|
||||
{
|
||||
printk("vcc->stats->tx (diff) = %d", vcc->stats->tx.counter - stats.tx.counter);
|
||||
flag++;
|
||||
}
|
||||
if ( vcc->stats->tx_err.counter != stats.tx_err.counter )
|
||||
{
|
||||
printk("vcc->stats->tx_err (diff) = %d", vcc->stats->tx_err.counter - stats.tx_err.counter);
|
||||
flag++;
|
||||
}
|
||||
if ( !flag )
|
||||
printk("vcc->stats not changed");
|
||||
}
|
||||
reg_desc.dataptr = (u32)new_skb->data >> 2;
|
||||
|
||||
if ( len )
|
||||
*len = reg_desc.datalen;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* no sk buffer */
|
||||
UPDATE_VCC_STAT(conn, rx_sw_drop_pdu, 1);
|
||||
|
||||
ppe_dev.mib.wrx_drop_pdu++;
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx_drop);
|
||||
|
||||
resize_skb_rx(skb, ppe_dev.aal5.rx_buffer_size, 0);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* no enough space */
|
||||
UPDATE_VCC_STAT(conn, rx_sw_drop_pdu, 1);
|
||||
|
||||
ppe_dev.mib.wrx_drop_pdu++;
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx_drop);
|
||||
|
||||
resize_skb_rx(skb, ppe_dev.aal5.rx_buffer_size, 0);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* AAL0 cell */
|
||||
resize_skb_rx(skb, CELL_SIZE, 1);
|
||||
skb_put(skb, CELL_SIZE);
|
||||
|
||||
ATM_SKB(skb)->vcc = vcc;
|
||||
ppe_dev.connection[conn].access_time = xtime;
|
||||
if ( atm_charge(vcc, skb->truesize) )
|
||||
{
|
||||
struct sk_buff *new_skb;
|
||||
|
||||
new_skb = alloc_skb_rx();
|
||||
if ( new_skb )
|
||||
{
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx);
|
||||
vcc->push(vcc, skb);
|
||||
reg_desc.dataptr = (u32)new_skb->data >> 2;
|
||||
|
||||
if ( len )
|
||||
*len = CELL_SIZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx_drop);
|
||||
resize_skb_rx(skb, ppe_dev.aal5.rx_buffer_size, 0);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx_drop);
|
||||
resize_skb_rx(skb, ppe_dev.aal5.rx_buffer_size, 0);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printk("reg_desc.err\n");
|
||||
|
||||
/* drop packet/cell */
|
||||
if ( vcc->qos.aal == ATM_AAL5 )
|
||||
{
|
||||
UPDATE_VCC_STAT(conn, rx_err_pdu, 1);
|
||||
|
||||
trailer = (struct rx_inband_trailer *)((u32)skb->data + ((reg_desc.byteoff + reg_desc.datalen + DMA_ALIGNMENT - 1) & ~ (DMA_ALIGNMENT - 1)));
|
||||
if ( trailer->stw_crc )
|
||||
ppe_dev.connection[conn].aal5_vcc_crc_err++;
|
||||
if ( trailer->stw_ovz )
|
||||
ppe_dev.connection[conn].aal5_vcc_oversize_sdu++;
|
||||
}
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->rx_err);
|
||||
/* don't need resize */
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
printk("ppe_dev.connection[%d].vcc == NULL\n", conn);
|
||||
|
||||
ppe_dev.mib.wrx_drop_pdu++;
|
||||
|
||||
/* don't need resize */
|
||||
}
|
||||
}
|
||||
|
||||
reg_desc.byteoff = 0;
|
||||
reg_desc.datalen = ppe_dev.aal5.rx_buffer_size;
|
||||
reg_desc.own = 1;
|
||||
reg_desc.c = 0;
|
||||
|
||||
/* write discriptor to memory */
|
||||
*desc = reg_desc;
|
||||
|
||||
printk("leave mailbox_rx_irq_handler");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline void mailbox_tx_irq_handler(unsigned int conn)
|
||||
{
|
||||
if ( ppe_dev.dma.tx_desc_alloc_flag[conn] )
|
||||
{
|
||||
int desc_base;
|
||||
int *release_pos;
|
||||
struct sk_buff *skb;
|
||||
|
||||
release_pos = &ppe_dev.dma.tx_desc_release_pos[conn];
|
||||
desc_base = ppe_dev.dma.tx_descriptor_number * (conn - QSB_QUEUE_NUMBER_BASE) + *release_pos;
|
||||
while ( !ppe_dev.dma.tx_descriptor_base[desc_base].own )
|
||||
{
|
||||
skb = ppe_dev.dma.tx_skb_pointers[desc_base];
|
||||
|
||||
ppe_dev.dma.tx_descriptor_base[desc_base].own = 1; // pretend PP32 hold owner bit, so that won't be released more than once, so allocation process don't check this bit
|
||||
|
||||
if ( ++*release_pos == ppe_dev.dma.tx_descriptor_number )
|
||||
*release_pos = 0;
|
||||
|
||||
if ( *release_pos == ppe_dev.dma.tx_desc_alloc_pos[conn] )
|
||||
{
|
||||
ppe_dev.dma.tx_desc_alloc_flag[conn] = 0;
|
||||
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
break;
|
||||
}
|
||||
|
||||
if ( *release_pos == 0 )
|
||||
desc_base = ppe_dev.dma.tx_descriptor_number * (conn - QSB_QUEUE_NUMBER_BASE);
|
||||
else
|
||||
desc_base++;
|
||||
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
static inline int check_desc_valid(unsigned int channel)
|
||||
{
|
||||
int skb_base;
|
||||
struct rx_descriptor *desc;
|
||||
|
||||
skb_base = ppe_dev.dma.rx_descriptor_number * channel + ppe_dev.dma.rx_desc_read_pos[channel];
|
||||
desc = &ppe_dev.dma.rx_descriptor_base[skb_base];
|
||||
return !desc->own && desc->c ? 1 : 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
irqreturn_t mailbox_irq_handler(int irq, void *dev_id)
|
||||
{
|
||||
int channel_mask; /* DMA channel accordant IRQ bit mask */
|
||||
int channel;
|
||||
unsigned int rx_irq_number[MAX_RX_DMA_CHANNEL_NUMBER] = {0};
|
||||
unsigned int total_rx_irq_number = 0;
|
||||
|
||||
printk("mailbox_irq_handler");
|
||||
|
||||
if ( !*MBOX_IGU1_ISR )
|
||||
return IRQ_RETVAL(1);
|
||||
|
||||
channel_mask = 1;
|
||||
channel = 0;
|
||||
while ( channel < ppe_dev.dma.rx_total_channel_used )
|
||||
{
|
||||
if ( (*MBOX_IGU1_ISR & channel_mask) )
|
||||
{
|
||||
/* RX */
|
||||
/* clear IRQ */
|
||||
*MBOX_IGU1_ISRC = channel_mask;
|
||||
printk(" RX: *MBOX_IGU1_ISR = 0x%08X\n", *MBOX_IGU1_ISR);
|
||||
/* wait for mailbox cleared */
|
||||
while ( (*MBOX_IGU3_ISR & channel_mask) );
|
||||
|
||||
/* shadow the number of valid descriptor */
|
||||
rx_irq_number[channel] = WRX_DMA_CHANNEL_CONFIG(channel)->vlddes;
|
||||
|
||||
total_rx_irq_number += rx_irq_number[channel];
|
||||
|
||||
printk("total_rx_irq_number = %d", total_rx_irq_number);
|
||||
printk("vlddes = %d, rx_irq_number[%d] = %d, total_rx_irq_number = %d\n", WRX_DMA_CHANNEL_CONFIG(channel)->vlddes, channel, rx_irq_number[channel], total_rx_irq_number);
|
||||
}
|
||||
|
||||
channel_mask <<= 1;
|
||||
channel++;
|
||||
}
|
||||
|
||||
channel_mask = 1 << (16 + QSB_QUEUE_NUMBER_BASE);
|
||||
channel = QSB_QUEUE_NUMBER_BASE;
|
||||
while ( channel - QSB_QUEUE_NUMBER_BASE < ppe_dev.dma.tx_total_channel_used )
|
||||
{
|
||||
if ( (*MBOX_IGU1_ISR & channel_mask) )
|
||||
{
|
||||
// if ( channel != 1 )
|
||||
// {
|
||||
printk("TX irq error\n");
|
||||
// while ( 1 )
|
||||
// {
|
||||
// }
|
||||
// }
|
||||
/* TX */
|
||||
/* clear IRQ */
|
||||
*MBOX_IGU1_ISRC = channel_mask;
|
||||
printk(" TX: *MBOX_IGU1_ISR = 0x%08X\n", *MBOX_IGU1_ISR);
|
||||
mailbox_tx_irq_handler(channel);
|
||||
}
|
||||
|
||||
channel_mask <<= 1;
|
||||
channel++;
|
||||
}
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
channel = 0;
|
||||
while ( total_rx_irq_number )
|
||||
{
|
||||
switch ( channel )
|
||||
{
|
||||
case RX_DMA_CH_CBR:
|
||||
case RX_DMA_CH_OAM:
|
||||
/* handle it as soon as possible */
|
||||
while ( rx_irq_number[channel] != 0 && mailbox_rx_irq_handler(channel, NULL) == 0 )
|
||||
{
|
||||
rx_irq_number[channel]--;
|
||||
total_rx_irq_number--;
|
||||
printk("RX_DMA_CH_CBR, total_rx_irq_number = %d", total_rx_irq_number);
|
||||
printk("RX_DMA_CH_CBR, total_rx_irq_number = %d, rx_irq_number[%d] = %d\n", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
}
|
||||
// if ( rx_irq_number[channel] != 0 )
|
||||
printk("RX_DMA_CH_CBR, rx_irq_number[channel] = %d", rx_irq_number[channel]);
|
||||
break;
|
||||
case RX_DMA_CH_VBR_RT:
|
||||
/* WFQ */
|
||||
if ( rx_irq_number[RX_DMA_CH_VBR_RT] != 0
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_NRT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_NRT) || ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] < ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT])
|
||||
&& (rx_irq_number[RX_DMA_CH_AVR] == 0 || !check_desc_valid(RX_DMA_CH_AVR) || ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] < ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT])
|
||||
)
|
||||
{
|
||||
unsigned int len;
|
||||
|
||||
if ( mailbox_rx_irq_handler(RX_DMA_CH_VBR_RT, &len) == 0 )
|
||||
{
|
||||
rx_irq_number[RX_DMA_CH_VBR_RT]--;
|
||||
total_rx_irq_number--;
|
||||
printk("RX_DMA_CH_VBR_RT, total_rx_irq_number = %d", total_rx_irq_number);
|
||||
printk("RX_DMA_CH_VBR_RT, total_rx_irq_number = %d, rx_irq_number[%d] = %d\n", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
|
||||
len = (len + CELL_SIZE - 1) / CELL_SIZE;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] <= len )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_RT] + ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] - len;
|
||||
}
|
||||
}
|
||||
// if ( rx_irq_number[channel] != 0 )
|
||||
// {
|
||||
printk("RX_DMA_CH_VBR_RT, rx_irq_number[channel] = %d, total_rx_irq_number = %d", rx_irq_number[channel], total_rx_irq_number);
|
||||
// rx_irq_number[channel] = 0;
|
||||
// total_rx_irq_number = 0;
|
||||
// }
|
||||
break;
|
||||
case RX_DMA_CH_VBR_NRT:
|
||||
/* WFQ */
|
||||
if ( rx_irq_number[RX_DMA_CH_VBR_NRT] != 0
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_RT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_RT) || ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] < ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT])
|
||||
&& (rx_irq_number[RX_DMA_CH_AVR] == 0 || !check_desc_valid(RX_DMA_CH_AVR) || ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] < ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT])
|
||||
)
|
||||
{
|
||||
unsigned int len;
|
||||
|
||||
if ( mailbox_rx_irq_handler(RX_DMA_CH_VBR_NRT, &len) == 0 )
|
||||
{
|
||||
rx_irq_number[RX_DMA_CH_VBR_NRT]--;
|
||||
total_rx_irq_number--;
|
||||
printk("RX_DMA_CH_VBR_NRT, total_rx_irq_number = %d", total_rx_irq_number);
|
||||
printk("RX_DMA_CH_VBR_NRT, total_rx_irq_number = %d, rx_irq_number[%d] = %d\n", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
|
||||
len = (len + CELL_SIZE - 1) / CELL_SIZE;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] <= len )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_NRT] + ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] - len;
|
||||
}
|
||||
}
|
||||
// if ( rx_irq_number[channel] != 0 )
|
||||
printk("RX_DMA_CH_VBR_NRT, rx_irq_number[channel] = %d", rx_irq_number[channel]);
|
||||
break;
|
||||
case RX_DMA_CH_AVR:
|
||||
/* WFQ */
|
||||
if ( rx_irq_number[RX_DMA_CH_AVR] != 0
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_RT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_RT) || ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] < ppe_dev.dma.rx_weight[RX_DMA_CH_AVR])
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_NRT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_NRT) || ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] < ppe_dev.dma.rx_weight[RX_DMA_CH_AVR])
|
||||
)
|
||||
{
|
||||
unsigned int len;
|
||||
|
||||
if ( mailbox_rx_irq_handler(RX_DMA_CH_AVR, &len) == 0 )
|
||||
{
|
||||
rx_irq_number[RX_DMA_CH_AVR]--;
|
||||
total_rx_irq_number--;
|
||||
printk("RX_DMA_CH_AVR, total_rx_irq_number = %d", total_rx_irq_number);
|
||||
printk("RX_DMA_CH_AVR, total_rx_irq_number = %d, rx_irq_number[%d] = %d\n", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
|
||||
len = (len + CELL_SIZE - 1) / CELL_SIZE;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] <= len )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_AVR] + ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] - len;
|
||||
}
|
||||
}
|
||||
// if ( rx_irq_number[channel] != 0 )
|
||||
printk("RX_DMA_CH_AVR, rx_irq_number[channel] = %d", rx_irq_number[channel]);
|
||||
break;
|
||||
case RX_DMA_CH_UBR:
|
||||
default:
|
||||
/* Handle it when all others are handled or others are not available to handle. */
|
||||
if ( rx_irq_number[channel] != 0
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_RT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_RT))
|
||||
&& (rx_irq_number[RX_DMA_CH_VBR_NRT] == 0 || !check_desc_valid(RX_DMA_CH_VBR_NRT))
|
||||
&& (rx_irq_number[RX_DMA_CH_AVR] == 0 || !check_desc_valid(RX_DMA_CH_AVR)) )
|
||||
if ( mailbox_rx_irq_handler(channel, NULL) == 0 )
|
||||
{
|
||||
rx_irq_number[channel]--;
|
||||
total_rx_irq_number--;
|
||||
printk("RX_DMA_CH_UBR, total_rx_irq_number = %d, rx_irq_number[%d] = %d", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
printk("RX_DMA_CH_UBR, total_rx_irq_number = %d, rx_irq_number[%d] = %d\n", total_rx_irq_number, channel, rx_irq_number[channel]);
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
}
|
||||
printk("RX_DMA_CH_UBR, rx_irq_number[channel] = %d", rx_irq_number[channel]);
|
||||
}
|
||||
|
||||
if ( ++channel == ppe_dev.dma.rx_total_channel_used )
|
||||
channel = 0;
|
||||
}
|
||||
#else
|
||||
channel = 0;
|
||||
while ( total_rx_irq_number )
|
||||
{
|
||||
while ( rx_irq_number[channel] != 0 && mailbox_rx_irq_handler(channel, NULL) == 0 )
|
||||
{
|
||||
rx_irq_number[channel]--;
|
||||
total_rx_irq_number--;
|
||||
/* signal firmware that descriptor is updated */
|
||||
mailbox_signal(channel, 0);
|
||||
}
|
||||
|
||||
if ( ++channel == ppe_dev.dma.rx_total_channel_used )
|
||||
channel = 0;
|
||||
}
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
return IRQ_RETVAL(1);
|
||||
}
|
||||
|
||||
|
|
@ -1,838 +0,0 @@
|
|||
#include <asm/mach-ifxmips/cgu.h>
|
||||
#include "common.h"
|
||||
|
||||
#include "ifx_ppe_fw.h"
|
||||
static void set_qsb(struct atm_vcc *vcc, struct atm_qos *qos, unsigned int connection)
|
||||
{
|
||||
|
||||
u32 qsb_clk = cgu_get_fpi_bus_clock(2); /* FPI configuration 2 (slow FPI bus) */
|
||||
union qsb_queue_parameter_table qsb_queue_parameter_table = {{0}};
|
||||
union qsb_queue_vbr_parameter_table qsb_queue_vbr_parameter_table = {{0}};
|
||||
u32 tmp;
|
||||
|
||||
/*
|
||||
* 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 * ppe_dev.qsb.tstepc) >> 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;
|
||||
}
|
||||
/*
|
||||
* 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 * ppe_dev.qsb.tstepc) >> 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(connection);
|
||||
/* 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(connection);
|
||||
|
||||
}
|
||||
|
||||
|
||||
static inline void u64_add_u32(ppe_u64_t opt1, u32 opt2,ppe_u64_t *ret)
|
||||
{
|
||||
ret->l = opt1.l + opt2;
|
||||
if ( ret->l < opt1.l || ret->l < opt2 )
|
||||
ret->h++;
|
||||
}
|
||||
|
||||
int find_vcc(struct atm_vcc *vcc)
|
||||
{
|
||||
int i;
|
||||
struct connection *connection = ppe_dev.connection;
|
||||
int max_connections = ppe_dev.port[(int)vcc->dev->dev_data].max_connections;
|
||||
u32 occupation_table = ppe_dev.port[(int)vcc->dev->dev_data].connection_table;
|
||||
int base = ppe_dev.port[(int)vcc->dev->dev_data].connection_base;
|
||||
for ( i = 0; i < max_connections; i++, base++ )
|
||||
if ( (occupation_table & (1 << i))
|
||||
&& connection[base].vcc == vcc )
|
||||
return base;
|
||||
return -1;
|
||||
}
|
||||
|
||||
int find_vpi(unsigned int vpi)
|
||||
{
|
||||
int i, j;
|
||||
struct connection *connection = ppe_dev.connection;
|
||||
struct port *port;
|
||||
int base;
|
||||
|
||||
port = ppe_dev.port;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++, port++ )
|
||||
{
|
||||
base = port->connection_base;
|
||||
for ( j = 0; j < port->max_connections; j++, base++ )
|
||||
if ( (port->connection_table & (1 << j))
|
||||
&& connection[base].vcc != NULL
|
||||
&& vpi == connection[base].vcc->vpi )
|
||||
return base;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
int find_vpivci(unsigned int vpi, unsigned int vci)
|
||||
{
|
||||
int i, j;
|
||||
struct connection *connection = ppe_dev.connection;
|
||||
struct port *port;
|
||||
int base;
|
||||
|
||||
port = ppe_dev.port;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++, port++ )
|
||||
{
|
||||
base = port->connection_base;
|
||||
for ( j = 0; j < port->max_connections; j++, base++ )
|
||||
if ( (port->connection_table & (1 << j))
|
||||
&& connection[base].vcc != NULL
|
||||
&& vpi == connection[base].vcc->vpi
|
||||
&& vci == connection[base].vcc->vci )
|
||||
return base;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
static inline void clear_htu_entry(unsigned int connection)
|
||||
{
|
||||
HTU_ENTRY(connection - QSB_QUEUE_NUMBER_BASE + OAM_HTU_ENTRY_NUMBER)->vld = 0;
|
||||
}
|
||||
|
||||
static inline void set_htu_entry(unsigned int vpi, unsigned int vci, unsigned int connection, int aal5)
|
||||
{
|
||||
struct htu_entry htu_entry = { res1: 0x00,
|
||||
pid: ppe_dev.connection[connection].port & 0x01,
|
||||
vpi: vpi,
|
||||
vci: vci,
|
||||
pti: 0x00,
|
||||
vld: 0x01};
|
||||
|
||||
struct htu_mask htu_mask = { set: 0x03,
|
||||
pid_mask: 0x02,
|
||||
vpi_mask: 0x00,
|
||||
vci_mask: 0x0000,
|
||||
pti_mask: 0x03, // 0xx, user data
|
||||
clear: 0x00};
|
||||
|
||||
struct htu_result htu_result = {res1: 0x00,
|
||||
cellid: connection,
|
||||
res2: 0x00,
|
||||
type: aal5 ? 0x00 : 0x01,
|
||||
ven: 0x01,
|
||||
res3: 0x00,
|
||||
qid: connection};
|
||||
|
||||
*HTU_RESULT(connection - QSB_QUEUE_NUMBER_BASE + OAM_HTU_ENTRY_NUMBER) = htu_result;
|
||||
*HTU_MASK(connection - QSB_QUEUE_NUMBER_BASE + OAM_HTU_ENTRY_NUMBER) = htu_mask;
|
||||
*HTU_ENTRY(connection - QSB_QUEUE_NUMBER_BASE + OAM_HTU_ENTRY_NUMBER) = htu_entry;
|
||||
}
|
||||
|
||||
int alloc_tx_connection(int connection)
|
||||
{
|
||||
unsigned long sys_flag;
|
||||
int desc_base;
|
||||
|
||||
if ( ppe_dev.dma.tx_desc_alloc_pos[connection] == ppe_dev.dma.tx_desc_release_pos[connection] && ppe_dev.dma.tx_desc_alloc_flag[connection] )
|
||||
return -1;
|
||||
|
||||
/* amend descriptor pointer and allocation number */
|
||||
local_irq_save(sys_flag);
|
||||
desc_base = ppe_dev.dma.tx_descriptor_number * (connection - QSB_QUEUE_NUMBER_BASE) + ppe_dev.dma.tx_desc_alloc_pos[connection];
|
||||
if ( ++ppe_dev.dma.tx_desc_alloc_pos[connection] == ppe_dev.dma.tx_descriptor_number )
|
||||
ppe_dev.dma.tx_desc_alloc_pos[connection] = 0;
|
||||
ppe_dev.dma.tx_desc_alloc_flag[connection] = 1;
|
||||
local_irq_restore(sys_flag);
|
||||
|
||||
return desc_base;
|
||||
}
|
||||
|
||||
|
||||
int ppe_open(struct atm_vcc *vcc)
|
||||
{
|
||||
int ret;
|
||||
struct port *port = &ppe_dev.port[(int)vcc->dev->dev_data];
|
||||
int conn;
|
||||
int f_enable_irq = 0;
|
||||
int i;
|
||||
printk("%s:%s[%d] removed 2 args from signature\n", __FILE__, __func__, __LINE__);
|
||||
|
||||
printk("ppe_open");
|
||||
|
||||
if ( vcc->qos.aal != ATM_AAL5 && vcc->qos.aal != ATM_AAL0 )
|
||||
return -EPROTONOSUPPORT;
|
||||
|
||||
down(&ppe_dev.sem);
|
||||
|
||||
/* 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.pcr > (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;
|
||||
}
|
||||
|
||||
printk("alloc vpi = %d, vci = %d\n", vcc->vpi, vcc->vci);
|
||||
|
||||
/* check existing vpi,vci */
|
||||
conn = find_vpivci(vcc->vpi, vcc->vci);
|
||||
if ( conn >= 0 )
|
||||
{
|
||||
ret = -EADDRINUSE;
|
||||
goto PPE_OPEN_EXIT;
|
||||
}
|
||||
|
||||
/* check whether it need to enable irq */
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( ppe_dev.port[i].max_connections != 0 && ppe_dev.port[i].connection_table != 0 )
|
||||
break;
|
||||
if ( i == ATM_PORT_NUMBER )
|
||||
f_enable_irq = 1;
|
||||
|
||||
/* allocate connection */
|
||||
for ( i = 0, conn = port->connection_base; i < port->max_connections; i++, conn++ )
|
||||
if ( !(port->connection_table & (1 << i)) )
|
||||
{
|
||||
port->connection_table |= 1 << i;
|
||||
ppe_dev.connection[conn].vcc = vcc;
|
||||
break;
|
||||
}
|
||||
if ( i == port->max_connections )
|
||||
{
|
||||
ret = -EINVAL;
|
||||
goto PPE_OPEN_EXIT;
|
||||
}
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
/* assign DMA channel and setup weight value for RX QoS */
|
||||
switch ( vcc->qos.rxtp.traffic_class )
|
||||
{
|
||||
case ATM_CBR:
|
||||
ppe_dev.connection[conn].rx_dma_channel = RX_DMA_CH_CBR;
|
||||
break;
|
||||
case ATM_VBR_RT:
|
||||
ppe_dev.connection[conn].rx_dma_channel = RX_DMA_CH_VBR_RT;
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_RT] += vcc->qos.rxtp.max_pcr;
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] += vcc->qos.rxtp.max_pcr;
|
||||
break;
|
||||
case ATM_VBR_NRT:
|
||||
ppe_dev.connection[conn].rx_dma_channel = RX_DMA_CH_VBR_NRT;
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_NRT] += vcc->qos.rxtp.pcr;
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] += vcc->qos.rxtp.pcr;
|
||||
break;
|
||||
case ATM_ABR:
|
||||
ppe_dev.connection[conn].rx_dma_channel = RX_DMA_CH_AVR;
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_AVR] += vcc->qos.rxtp.min_pcr;
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] += vcc->qos.rxtp.min_pcr;
|
||||
break;
|
||||
case ATM_UBR_PLUS:
|
||||
default:
|
||||
ppe_dev.connection[conn].rx_dma_channel = RX_DMA_CH_UBR;
|
||||
break;
|
||||
}
|
||||
|
||||
/* update RX queue configuration table */
|
||||
WRX_QUEUE_CONFIG(conn)->dmach = ppe_dev.connection[conn].rx_dma_channel;
|
||||
|
||||
printk("ppe_open: QID %d, DMA %d\n", conn, WRX_QUEUE_CONFIG(conn)->dmach);
|
||||
|
||||
printk("conn = %d, dmach = %d", conn, WRX_QUEUE_CONFIG(conn)->dmach);
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
|
||||
/* 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.pcr;
|
||||
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;
|
||||
|
||||
set_bit(ATM_VF_READY, &vcc->flags);
|
||||
|
||||
/* enable irq */
|
||||
printk("ppe_open: enable_irq\n");
|
||||
if ( f_enable_irq )
|
||||
enable_irq(IFXMIPS_PPE_MBOX_INT);
|
||||
|
||||
/* enable mailbox */
|
||||
*MBOX_IGU1_ISRC = (1 << conn) | (1 << (conn + 16));
|
||||
*MBOX_IGU1_IER |= (1 << conn) | (1 << (conn + 16));
|
||||
*MBOX_IGU3_ISRC = (1 << conn) | (1 << (conn + 16));
|
||||
*MBOX_IGU3_IER |= (1 << conn) | (1 << (conn + 16));
|
||||
|
||||
/* set htu entry */
|
||||
set_htu_entry(vcc->vpi, vcc->vci, conn, vcc->qos.aal == ATM_AAL5 ? 1 : 0);
|
||||
|
||||
ret = 0;
|
||||
|
||||
printk("ppe_open(%d.%d): conn = %d, ppe_dev.dma = %08X\n", vcc->vpi, vcc->vci, conn, (u32)&ppe_dev.dma.rx_descriptor_number);
|
||||
|
||||
|
||||
PPE_OPEN_EXIT:
|
||||
up(&ppe_dev.sem);
|
||||
|
||||
printk("open ATM itf = %d, vpi = %d, vci = %d, ret = %d", (int)vcc->dev->dev_data, (int)vcc->vpi, vcc->vci, ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
void ppe_close(struct atm_vcc *vcc)
|
||||
{
|
||||
int conn;
|
||||
struct port *port;
|
||||
struct connection *connection;
|
||||
int i;
|
||||
|
||||
if ( vcc == NULL )
|
||||
return;
|
||||
|
||||
down(&ppe_dev.sem);
|
||||
|
||||
/* get connection id */
|
||||
conn = find_vcc(vcc);
|
||||
if ( conn < 0 )
|
||||
{
|
||||
printk("can't find vcc\n");
|
||||
goto PPE_CLOSE_EXIT;
|
||||
}
|
||||
if(!((Atm_Priv *)vcc)->on)
|
||||
goto PPE_CLOSE_EXIT;
|
||||
connection = &ppe_dev.connection[conn];
|
||||
port = &ppe_dev.port[connection->port];
|
||||
|
||||
/* clear htu */
|
||||
clear_htu_entry(conn);
|
||||
|
||||
/* release connection */
|
||||
port->connection_table &= ~(1 << (conn - port->connection_base));
|
||||
connection->vcc = NULL;
|
||||
connection->access_time.tv_sec = 0;
|
||||
connection->access_time.tv_nsec = 0;
|
||||
connection->aal5_vcc_crc_err = 0;
|
||||
connection->aal5_vcc_oversize_sdu = 0;
|
||||
|
||||
/* disable irq */
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++ )
|
||||
if ( ppe_dev.port[i].max_connections != 0 && ppe_dev.port[i].connection_table != 0 )
|
||||
break;
|
||||
if ( i == ATM_PORT_NUMBER )
|
||||
disable_irq(IFXMIPS_PPE_MBOX_INT);
|
||||
|
||||
*MBOX_IGU1_ISRC = (1 << conn) | (1 << (conn + 16));
|
||||
|
||||
#if defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
/* remove weight value from RX DMA channel */
|
||||
switch ( vcc->qos.rxtp.traffic_class )
|
||||
{
|
||||
case ATM_VBR_RT:
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_RT] -= vcc->qos.rxtp.max_pcr;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] > ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_RT] )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_RT] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_RT];
|
||||
break;
|
||||
case ATM_VBR_NRT:
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_NRT] -= vcc->qos.rxtp.pcr;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] > ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_NRT] )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_VBR_NRT] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_VBR_NRT];
|
||||
break;
|
||||
case ATM_ABR:
|
||||
ppe_dev.dma.rx_default_weight[RX_DMA_CH_AVR] -= vcc->qos.rxtp.min_pcr;
|
||||
if ( ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] > ppe_dev.dma.rx_default_weight[RX_DMA_CH_AVR] )
|
||||
ppe_dev.dma.rx_weight[RX_DMA_CH_AVR] = ppe_dev.dma.rx_default_weight[RX_DMA_CH_AVR];
|
||||
break;
|
||||
case ATM_CBR:
|
||||
case ATM_UBR_PLUS:
|
||||
default:
|
||||
break;
|
||||
}
|
||||
#endif // defined(ENABLE_RX_QOS) && ENABLE_RX_QOS
|
||||
|
||||
/* 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.pcr;
|
||||
break;
|
||||
case ATM_UBR_PLUS:
|
||||
port->tx_current_cell_rate -= vcc->qos.txtp.min_pcr;
|
||||
break;
|
||||
}
|
||||
|
||||
/* idle for a while to let parallel operation finish */
|
||||
for ( i = 0; i < IDLE_CYCLE_NUMBER; i++ );
|
||||
((Atm_Priv *)vcc)->on = 0;
|
||||
|
||||
PPE_CLOSE_EXIT:
|
||||
up(&ppe_dev.sem);
|
||||
}
|
||||
|
||||
int ppe_ioctl(struct atm_dev *dev, unsigned int cmd, void *arg)
|
||||
{
|
||||
return -ENOTTY;
|
||||
}
|
||||
|
||||
int ppe_send(struct atm_vcc *vcc, struct sk_buff *skb)
|
||||
{
|
||||
int ret;
|
||||
int conn;
|
||||
int desc_base;
|
||||
register struct tx_descriptor reg_desc;
|
||||
struct tx_descriptor *desc;
|
||||
|
||||
|
||||
printk("ppe_send");
|
||||
printk("ppe_send\n");
|
||||
printk("skb->users = %d\n", skb->users.counter);
|
||||
|
||||
if ( vcc == NULL || skb == NULL )
|
||||
return -EINVAL;
|
||||
|
||||
// down(&ppe_dev.sem);
|
||||
|
||||
ATM_SKB(skb)->vcc = vcc;
|
||||
conn = find_vcc(vcc);
|
||||
// if ( conn != 1 )
|
||||
printk("ppe_send: conn = %d\n", conn);
|
||||
if ( conn < 0 )
|
||||
{
|
||||
ret = -EINVAL;
|
||||
goto FIND_VCC_FAIL;
|
||||
}
|
||||
|
||||
printk("find_vcc");
|
||||
|
||||
if ( vcc->qos.aal == ATM_AAL5 )
|
||||
{
|
||||
int byteoff;
|
||||
int datalen;
|
||||
struct tx_inband_header *header;
|
||||
|
||||
/* allocate descriptor */
|
||||
desc_base = alloc_tx_connection(conn);
|
||||
if ( desc_base < 0 )
|
||||
{
|
||||
ret = -EIO;
|
||||
//goto ALLOC_TX_CONNECTION_FAIL;
|
||||
}
|
||||
desc = &ppe_dev.dma.tx_descriptor_base[desc_base];
|
||||
|
||||
/* load descriptor from memory */
|
||||
reg_desc = *desc;
|
||||
|
||||
datalen = skb->len;
|
||||
byteoff = (u32)skb->data & (DMA_ALIGNMENT - 1);
|
||||
if ( skb_headroom(skb) < byteoff + TX_INBAND_HEADER_LENGTH )
|
||||
{
|
||||
struct sk_buff *new_skb;
|
||||
|
||||
printk("skb_headroom(skb) < byteoff + TX_INBAND_HEADER_LENGTH");
|
||||
printk("skb_headroom(skb 0x%08X, skb->data 0x%08X) (%d) < byteoff (%d) + TX_INBAND_HEADER_LENGTH (%d)\n", (u32)skb, (u32)skb->data, skb_headroom(skb), byteoff, TX_INBAND_HEADER_LENGTH);
|
||||
|
||||
new_skb = alloc_skb_tx(datalen);
|
||||
if ( new_skb == NULL )
|
||||
{
|
||||
printk("alloc_skb_tx: fail\n");
|
||||
ret = -ENOMEM;
|
||||
goto ALLOC_SKB_TX_FAIL;
|
||||
}
|
||||
ATM_SKB(new_skb)->vcc = NULL;
|
||||
skb_put(new_skb, datalen);
|
||||
memcpy(new_skb->data, skb->data, datalen);
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
skb = new_skb;
|
||||
byteoff = (u32)skb->data & (DMA_ALIGNMENT - 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
printk("skb_headroom(skb) >= byteoff + TX_INBAND_HEADER_LENGTH");
|
||||
}
|
||||
printk("before skb_push, skb->data = 0x%08X", (u32)skb->data);
|
||||
skb_push(skb, byteoff + TX_INBAND_HEADER_LENGTH);
|
||||
printk("after skb_push, skb->data = 0x%08X", (u32)skb->data);
|
||||
|
||||
header = (struct tx_inband_header *)(u32)skb->data;
|
||||
printk("header = 0x%08X", (u32)header);
|
||||
|
||||
/* setup inband trailer */
|
||||
header->uu = 0;
|
||||
header->cpi = 0;
|
||||
header->pad = ppe_dev.aal5.padding_byte;
|
||||
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 = (u32)skb->data >> 2;
|
||||
reg_desc.datalen = datalen;
|
||||
reg_desc.byteoff = byteoff;
|
||||
reg_desc.iscell = 0;
|
||||
|
||||
printk("setup header, datalen = %d, byteoff = %d", reg_desc.datalen, reg_desc.byteoff);
|
||||
|
||||
UPDATE_VCC_STAT(conn, tx_pdu, 1);
|
||||
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->tx);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* allocate descriptor */
|
||||
desc_base = alloc_tx_connection(conn);
|
||||
if ( desc_base < 0 )
|
||||
{
|
||||
ret = -EIO;
|
||||
goto ALLOC_TX_CONNECTION_FAIL;
|
||||
}
|
||||
desc = &ppe_dev.dma.tx_descriptor_base[desc_base];
|
||||
|
||||
/* load descriptor from memory */
|
||||
reg_desc = *desc;
|
||||
|
||||
/* if data pointer is not aligned, allocate new sk_buff */
|
||||
if ( ((u32)skb->data & (DMA_ALIGNMENT - 1)) )
|
||||
{
|
||||
struct sk_buff *new_skb;
|
||||
|
||||
printk("skb->data not aligned\n");
|
||||
|
||||
new_skb = alloc_skb_tx(skb->len);
|
||||
if ( new_skb == NULL )
|
||||
{
|
||||
ret = -ENOMEM;
|
||||
goto ALLOC_SKB_TX_FAIL;
|
||||
}
|
||||
ATM_SKB(new_skb)->vcc = NULL;
|
||||
skb_put(new_skb, skb->len);
|
||||
memcpy(new_skb->data, skb->data, skb->len);
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
skb = new_skb;
|
||||
}
|
||||
|
||||
reg_desc.dataptr = (u32)skb->data >> 2;
|
||||
reg_desc.datalen = skb->len;
|
||||
reg_desc.byteoff = 0;
|
||||
reg_desc.iscell = 1;
|
||||
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->tx);
|
||||
}
|
||||
|
||||
reg_desc.own = 1;
|
||||
reg_desc.c = 1;
|
||||
|
||||
printk("update descriptor send pointer, desc = 0x%08X", (u32)desc);
|
||||
|
||||
ppe_dev.dma.tx_skb_pointers[desc_base] = skb;
|
||||
*desc = reg_desc;
|
||||
dma_cache_wback((unsigned long)skb->data, skb->len);
|
||||
|
||||
mailbox_signal(conn, 1);
|
||||
|
||||
printk("ppe_send: success");
|
||||
// up(&ppe_dev.sem);
|
||||
|
||||
return 0;
|
||||
|
||||
FIND_VCC_FAIL:
|
||||
printk("FIND_VCC_FAIL\n");
|
||||
|
||||
// up(&ppe_dev.sem);
|
||||
ppe_dev.mib.wtx_err_pdu++;
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
|
||||
return ret;
|
||||
|
||||
ALLOC_SKB_TX_FAIL:
|
||||
printk("ALLOC_SKB_TX_FAIL\n");
|
||||
|
||||
// up(&ppe_dev.sem);
|
||||
if ( vcc->qos.aal == ATM_AAL5 )
|
||||
{
|
||||
UPDATE_VCC_STAT(conn, tx_err_pdu, 1);
|
||||
ppe_dev.mib.wtx_err_pdu++;
|
||||
}
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->tx_err);
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
|
||||
return ret;
|
||||
|
||||
ALLOC_TX_CONNECTION_FAIL:
|
||||
printk("ALLOC_TX_CONNECTION_FAIL\n");
|
||||
|
||||
// up(&ppe_dev.sem);
|
||||
if ( vcc->qos.aal == ATM_AAL5 )
|
||||
{
|
||||
UPDATE_VCC_STAT(conn, tx_sw_drop_pdu, 1);
|
||||
ppe_dev.mib.wtx_drop_pdu++;
|
||||
}
|
||||
if ( vcc->stats )
|
||||
atomic_inc(&vcc->stats->tx_err);
|
||||
atm_free_tx_skb_vcc(skb);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
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;
|
||||
register struct tx_descriptor reg_desc;
|
||||
struct tx_descriptor *desc;
|
||||
|
||||
printk("ppe_send_oam");
|
||||
|
||||
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 OAM_TX_QUEUE_NUMBER_PER_PORT != 0
|
||||
/* get queue ID of OAM TX queue, and the TX DMA channel ID is the same as queue ID */
|
||||
conn = ppe_dev.port[(int)vcc->dev->dev_data].oam_tx_queue;
|
||||
#else
|
||||
/* find queue ID */
|
||||
conn = find_vcc(vcc);
|
||||
if ( conn < 0 )
|
||||
{
|
||||
printk("OAM not find queue\n");
|
||||
// up(&ppe_dev.sem);
|
||||
return -EINVAL;
|
||||
}
|
||||
#endif // OAM_TX_QUEUE_NUMBER_PER_PORT != 0
|
||||
|
||||
/* allocate descriptor */
|
||||
desc_base = alloc_tx_connection(conn);
|
||||
if ( desc_base < 0 )
|
||||
{
|
||||
printk("OAM not alloc tx connection\n");
|
||||
// up(&ppe_dev.sem);
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
desc = &ppe_dev.dma.tx_descriptor_base[desc_base];
|
||||
|
||||
/* load descriptor from memory */
|
||||
reg_desc = *(struct tx_descriptor *)desc;
|
||||
|
||||
/* allocate sk_buff */
|
||||
skb = alloc_skb_tx(CELL_SIZE);
|
||||
if ( skb == NULL )
|
||||
{
|
||||
// up(&ppe_dev.sem);
|
||||
return -ENOMEM;
|
||||
}
|
||||
#if OAM_TX_QUEUE_NUMBER_PER_PORT != 0
|
||||
ATM_SKB(skb)->vcc = NULL;
|
||||
#else
|
||||
ATM_SKB(skb)->vcc = vcc;
|
||||
#endif // OAM_TX_QUEUE_NUMBER_PER_PORT != 0
|
||||
|
||||
/* copy data */
|
||||
skb_put(skb, CELL_SIZE);
|
||||
memcpy(skb->data, cell, CELL_SIZE);
|
||||
|
||||
/* setup descriptor */
|
||||
reg_desc.dataptr = (u32)skb->data >> 2;
|
||||
reg_desc.datalen = CELL_SIZE;
|
||||
reg_desc.byteoff = 0;
|
||||
reg_desc.iscell = 1;
|
||||
reg_desc.own = 1;
|
||||
reg_desc.c = 1;
|
||||
|
||||
/* update descriptor send pointer */
|
||||
ppe_dev.dma.tx_skb_pointers[desc_base] = skb;
|
||||
|
||||
/* write discriptor to memory and write back cache */
|
||||
*(struct tx_descriptor *)desc = reg_desc;
|
||||
dma_cache_wback((unsigned long)skb->data, skb->len);
|
||||
|
||||
/* signal PPE */
|
||||
mailbox_signal(conn, 1);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ppe_change_qos(struct atm_vcc *vcc, struct atm_qos *qos, int flags)
|
||||
{
|
||||
int conn;
|
||||
printk("%s:%s[%d]\n", __FILE__, __func__, __LINE__);
|
||||
|
||||
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 void init_chip(void)
|
||||
{
|
||||
/* enable PPE module in PMU */
|
||||
*(unsigned long *)0xBF10201C &= ~((1 << 15) | (1 << 13) | (1 << 9));
|
||||
|
||||
*EMA_CMDCFG = (EMA_CMD_BUF_LEN << 16) | (EMA_CMD_BASE_ADDR >> 2);
|
||||
*EMA_DATACFG = (EMA_DATA_BUF_LEN << 16) | (EMA_DATA_BASE_ADDR >> 2);
|
||||
*EMA_IER = 0x000000FF;
|
||||
*EMA_CFG = EMA_READ_BURST | (EMA_WRITE_BURST << 2);
|
||||
|
||||
/* enable mailbox */
|
||||
*MBOX_IGU1_ISRC = 0xFFFFFFFF;
|
||||
*MBOX_IGU1_IER = 0x00000000;
|
||||
*MBOX_IGU3_ISRC = 0xFFFFFFFF;
|
||||
*MBOX_IGU3_IER = 0x00000000;
|
||||
}
|
||||
|
||||
int pp32_download_code(u32 *code_src, unsigned int code_dword_len, u32 *data_src, unsigned int data_dword_len)
|
||||
{
|
||||
u32 reg_old_value;
|
||||
volatile u32 *dest;
|
||||
|
||||
if ( code_src == 0 || ((unsigned long)code_src & 0x03) != 0
|
||||
|| data_src == 0 || ((unsigned long)data_src & 0x03) )
|
||||
return -EINVAL;
|
||||
|
||||
/* save the old value of CDM_CFG and set PPE code memory to FPI bus access mode */
|
||||
reg_old_value = *CDM_CFG;
|
||||
if ( code_dword_len <= 4096 )
|
||||
*CDM_CFG = CDM_CFG_RAM1_SET(0x00) | CDM_CFG_RAM0_SET(0x00);
|
||||
else
|
||||
*CDM_CFG = CDM_CFG_RAM1_SET(0x01) | CDM_CFG_RAM0_SET(0x00);
|
||||
|
||||
/* copy code */
|
||||
dest = CDM_CODE_MEMORY_RAM0_ADDR(0);
|
||||
while ( code_dword_len-- > 0 )
|
||||
*dest++ = *code_src++;
|
||||
|
||||
/* copy data */
|
||||
dest = PP32_DATA_MEMORY_RAM1_ADDR(0);
|
||||
while ( data_dword_len-- > 0 )
|
||||
*dest++ = *data_src++;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pp32_start(void)
|
||||
{
|
||||
int ret;
|
||||
register int i;
|
||||
init_chip();
|
||||
/* 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 )
|
||||
return ret;
|
||||
|
||||
/* run PP32 */
|
||||
*PP32_DBG_CTRL = DBG_CTRL_START_SET(1);
|
||||
|
||||
/* idle for a while to let PP32 init itself */
|
||||
for ( i = 0; i < IDLE_CYCLE_NUMBER; i++ );
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void pp32_stop(void)
|
||||
{
|
||||
/* halt PP32 */
|
||||
*PP32_DBG_CTRL = DBG_CTRL_STOP_SET(1);
|
||||
}
|
|
@ -1,98 +0,0 @@
|
|||
#include <linux/atm.h>
|
||||
#include <linux/proc_fs.h>
|
||||
|
||||
#include "proc.h"
|
||||
#include "common.h"
|
||||
|
||||
struct proc_dir_entry *ppe_proc_dir;
|
||||
|
||||
int proc_read_idle_counter(char *page, char **start, off_t off, int count, int *eof, void *data)
|
||||
{
|
||||
int len = 0;
|
||||
|
||||
len += sprintf(page + off, "Channel 0\n");
|
||||
len += sprintf(page + off + len, " TX\n");
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AT_CELL0 = %d\n", *DREG_AT_CELL0 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AT_IDLE_CNT0 = %d\n", *DREG_AT_IDLE_CNT0 & 0xFFFF);
|
||||
len += sprintf(page + off + len, " RX\n");
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_CELL0 = %d\n", *DREG_AR_CELL0 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_IDLE_CNT0 = %d\n", *DREG_AR_IDLE_CNT0 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_AIIDLE_CNT0 = %d\n", *DREG_AR_AIIDLE_CNT0 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_BE_CNT0 = %d\n", *DREG_AR_BE_CNT0 & 0xFFFF);
|
||||
len += sprintf(page + off + len, "Channel 1\n");
|
||||
len += sprintf(page + off + len, " TX\n");
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AT_CELL1 = %d\n", *DREG_AT_CELL1 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AT_IDLE_CNT1 = %d\n", *DREG_AT_IDLE_CNT1 & 0xFFFF);
|
||||
len += sprintf(page + off + len, " RX\n");
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_CELL1 = %d\n", *DREG_AR_CELL1 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_IDLE_CNT1 = %d\n", *DREG_AR_IDLE_CNT1 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_AIIDLE_CNT1 = %d\n", *DREG_AR_AIIDLE_CNT1 & 0xFFFF);
|
||||
len += sprintf(page + off + len,
|
||||
" DREG_AR_BE_CNT1 = %d\n", *DREG_AR_BE_CNT1 & 0xFFFF);
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
int proc_read_stats(char *page, char **start, off_t off, int count, int *eof, void *data)
|
||||
{
|
||||
int len = 0;
|
||||
|
||||
int i, j;
|
||||
struct connection *connection;
|
||||
struct port *port;
|
||||
int base;
|
||||
|
||||
len += sprintf(page + off, "ATM Stats:\n");
|
||||
|
||||
connection = ppe_dev.connection;
|
||||
port = ppe_dev.port;
|
||||
for ( i = 0; i < ATM_PORT_NUMBER; i++, port++ )
|
||||
{
|
||||
base = port->connection_base;
|
||||
for ( j = 0; j < port->max_connections; j++, base++ )
|
||||
if ( (port->connection_table & (1 << j))
|
||||
&& connection[base].vcc != NULL )
|
||||
{
|
||||
if ( connection[base].vcc->stats )
|
||||
{
|
||||
struct k_atm_aal_stats *stats = connection[base].vcc->stats;
|
||||
|
||||
len += sprintf(page + off + len, " VCC %d.%d.%d (stats)\n", i, connection[base].vcc->vpi, connection[base].vcc->vci);
|
||||
len += sprintf(page + off + len, " rx = %d\n", stats->rx.counter);
|
||||
len += sprintf(page + off + len, " rx_err = %d\n", stats->rx_err.counter);
|
||||
len += sprintf(page + off + len, " rx_drop = %d\n", stats->rx_drop.counter);
|
||||
len += sprintf(page + off + len, " tx = %d\n", stats->tx.counter);
|
||||
len += sprintf(page + off + len, " tx_err = %d\n", stats->tx_err.counter);
|
||||
}
|
||||
else
|
||||
len += sprintf(page + off + len, " VCC %d.%d.%d\n", i, connection[base].vcc->vpi, connection[base].vcc->vci);
|
||||
}
|
||||
}
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
void proc_file_create(void)
|
||||
{
|
||||
ppe_proc_dir = proc_mkdir("ppe", NULL);
|
||||
create_proc_read_entry("idle_counter", 0, ppe_proc_dir, proc_read_idle_counter, NULL);
|
||||
create_proc_read_entry("stats", 0, ppe_proc_dir, proc_read_stats, NULL);
|
||||
}
|
||||
|
||||
void proc_file_delete(void)
|
||||
{
|
||||
remove_proc_entry("idle_counter", ppe_proc_dir);
|
||||
remove_proc_entry("stats", ppe_proc_dir);
|
||||
remove_proc_entry("ppe", NULL);
|
||||
}
|
|
@ -1,9 +0,0 @@
|
|||
#ifndef _IFXMIPS_PPE_PROC_H__
|
||||
#define _IFXMIPS_PPE_PROC_H__
|
||||
|
||||
void proc_file_create(void);
|
||||
void proc_file_delete(void);
|
||||
int proc_read_idle_counter(char *page, char **start, off_t off, int count, int *eof, void *data);
|
||||
int proc_read_stats(char *page, char **start, off_t off, int count, int *eof, void *data);
|
||||
|
||||
#endif
|
|
@ -1,128 +0,0 @@
|
|||
#include <linux/skbuff.h>
|
||||
|
||||
#include "common.h"
|
||||
|
||||
void resize_skb_rx(struct sk_buff *skb, unsigned int size, int is_cell)
|
||||
{
|
||||
if((u32)skb < 0x80000000)
|
||||
{
|
||||
int key = 0;
|
||||
printk("resize_skb_rx problem: skb = %08X, size = %d, is_cell = %d\n", (u32)skb, size, is_cell);
|
||||
while(!key){}
|
||||
}
|
||||
skb->data = (unsigned char*)(((u32)skb->head + 16 + (DMA_ALIGNMENT - 1)) & ~(DMA_ALIGNMENT - 1));
|
||||
skb->tail = skb->data;
|
||||
|
||||
/* Set up other state */
|
||||
skb->len = 0;
|
||||
skb->cloned = 0;
|
||||
#if defined(CONFIG_IMQ) || defined (CONFIG_IMQ_MODULE)
|
||||
skb->imq_flags = 0;
|
||||
skb->nf_info = NULL;
|
||||
#endif
|
||||
skb->data_len = 0;
|
||||
}
|
||||
|
||||
struct sk_buff* alloc_skb_rx(void)
|
||||
{
|
||||
struct sk_buff *skb;
|
||||
|
||||
/* allocate memroy including trailer and padding */
|
||||
skb = dev_alloc_skb(ppe_dev.aal5.rx_buffer_size + DMA_ALIGNMENT);
|
||||
if (skb)
|
||||
{
|
||||
/* must be burst length alignment */
|
||||
if ( ((u32)skb->data & (DMA_ALIGNMENT - 1)) != 0 )
|
||||
skb_reserve(skb, ~((u32)skb->data + (DMA_ALIGNMENT - 1)) & (DMA_ALIGNMENT - 1));
|
||||
/* put skb in reserved area "skb->data - 4" */
|
||||
*((u32*)skb->data - 1) = (u32)skb;
|
||||
/* invalidate cache */
|
||||
dma_cache_inv((unsigned long)skb->head, (u32)skb->end - (u32)skb->head);
|
||||
}
|
||||
return skb;
|
||||
}
|
||||
|
||||
void atm_free_tx_skb_vcc(struct sk_buff *skb)
|
||||
{
|
||||
struct atm_vcc* vcc;
|
||||
|
||||
if ( (u32)skb <= 0x80000000 )
|
||||
{
|
||||
volatile int key = 0;
|
||||
printk("atm_free_tx_skb_vcc: skb = %08X\n", (u32)skb);
|
||||
for ( ; !key; );
|
||||
}
|
||||
|
||||
vcc = ATM_SKB(skb)->vcc;
|
||||
if ( vcc != NULL && vcc->pop != NULL )
|
||||
{
|
||||
if ( atomic_read(&skb->users) == 0 )
|
||||
{
|
||||
volatile int key = 0;
|
||||
printk("atm_free_tx_skb_vcc(vcc->pop): skb->users == 0, skb = %08X\n", (u32)skb);
|
||||
for ( ; !key; );
|
||||
}
|
||||
vcc->pop(vcc, skb);
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( atomic_read(&skb->users) == 0 )
|
||||
{
|
||||
volatile int key = 0;
|
||||
printk("atm_free_tx_skb_vcc(dev_kfree_skb_any): skb->users == 0, skb = %08X\n", (u32)skb);
|
||||
for ( ; !key; );
|
||||
}
|
||||
dev_kfree_skb_any(skb);
|
||||
}
|
||||
}
|
||||
|
||||
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 &= ~(DMA_ALIGNMENT - 1);
|
||||
skb = dev_alloc_skb(size + DMA_ALIGNMENT);
|
||||
/* must be burst length alignment */
|
||||
if ( skb )
|
||||
skb_reserve(skb, (~((u32)skb->data + (DMA_ALIGNMENT - 1)) & (DMA_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 + TX_INBAND_HEADER_LENGTH + MAX_TX_PACKET_ALIGN_BYTES + MAX_TX_PACKET_PADDING_BYTES) & ~(DMA_ALIGNMENT - 1)) > ppe_dev.aal5.tx_max_packet_size )
|
||||
{
|
||||
printk("atm_alloc_tx: oversize packet\n");
|
||||
return NULL;
|
||||
}
|
||||
/* send buffer overflow */
|
||||
if ( atomic_read(&vcc->sk.sk_wmem_alloc) && !atm_may_send(vcc, size) )
|
||||
{
|
||||
printk("atm_alloc_tx: send buffer overflow\n");
|
||||
return NULL;
|
||||
}
|
||||
conn = find_vcc(vcc);
|
||||
if ( conn < 0 )
|
||||
{
|
||||
printk("atm_alloc_tx: unknown VCC\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
skb = dev_alloc_skb(size);
|
||||
if ( skb == NULL )
|
||||
{
|
||||
printk("atm_alloc_tx: sk buffer is used up\n");
|
||||
return NULL;
|
||||
}
|
||||
#define ATM_PDU_OVHD 0
|
||||
atomic_add(skb->truesize + ATM_PDU_OVHD, &vcc->sk.sk_wmem_alloc);
|
||||
|
||||
return skb;
|
||||
}
|
||||
|
18
package/ifxmips-dsl-api/Config.in
Normal file
18
package/ifxmips-dsl-api/Config.in
Normal file
|
@ -0,0 +1,18 @@
|
|||
choice
|
||||
prompt "Firmware"
|
||||
depends on PACKAGE_kmod-ifxmips-dsl-api
|
||||
default IFXMIPS_ANNEX_B
|
||||
help
|
||||
This option controls which firmware is loaded
|
||||
|
||||
config IFXMIPS_ANNEX_A
|
||||
bool "Annex-A"
|
||||
help
|
||||
Annex-A
|
||||
|
||||
config IFXMIPS_ANNEX_B
|
||||
bool "Annex-B"
|
||||
help
|
||||
Annex-B
|
||||
|
||||
endchoice
|
140
package/ifxmips-dsl-api/Makefile
Normal file
140
package/ifxmips-dsl-api/Makefile
Normal file
|
@ -0,0 +1,140 @@
|
|||
#
|
||||
# Copyright (C) 2009 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:=ifxmips-dsl-api
|
||||
PKG_BASE_NAME:=drv_dsl_cpe_api_danube
|
||||
PKG_VERSION:=3.24.4.4
|
||||
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/ifxmips-dsl-api
|
||||
SECTION:=driver
|
||||
CATEGORY:=Infineon
|
||||
TITLE:=DSL CPE API driver
|
||||
URL:=http://www.infineon.com/
|
||||
MAINTAINER:=Infineon Technologies AG / Lantiq / blogic@openwrt.org
|
||||
DEPENDS:=@TARGET_ifxmips
|
||||
FILES:=$(PKG_BUILD_DIR)/src/mei/ifxmips_mei.$(LINUX_KMOD_SUFFIX) \
|
||||
$(PKG_BUILD_DIR)/src/drv_dsl_cpe_api.$(LINUX_KMOD_SUFFIX) \
|
||||
$(PKG_BUILD_DIR)/src/mei/ifxmips_atm.$(LINUX_KMOD_SUFFIX)
|
||||
AUTOLOAD:=$(call AutoLoad,50,ifxmips_mei drv_dsl_cpe_api ifxmips_atm)
|
||||
endef
|
||||
|
||||
define KernelPackage/ifxmips-dsl-api/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
|
||||
|
||||
This package was kindly contributed to openwrt by Infineon/Lantiq
|
||||
endef
|
||||
|
||||
define KernelPackage/ifxmips-dsl-api/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" \
|
||||
--enable-debug=yes \
|
||||
--enable-debug-prints=yes \
|
||||
--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
|
||||
|
||||
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/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/ifxmips-dsl-api/install
|
||||
$(INSTALL_DIR) $(1)/lib/firmware/
|
||||
$(CP) $(PKG_BUILD_DIR)/$(FW_BASE_NAME)_$(if $(CONFIG_IFXMIPS_ANNEX_A),a_$(FW_A_FILE_VER),b_$(FW_B_FILE_VER)).bin $(1)/lib/firmware/ModemHWE.bin
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,ifxmips-dsl-api))
|
43
package/ifxmips-dsl-api/patches/100-dsl_compat.patch
Normal file
43
package/ifxmips-dsl-api/patches/100-dsl_compat.patch
Normal file
|
@ -0,0 +1,43 @@
|
|||
Index: drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_device_danube.h
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/include/drv_dsl_cpe_device_danube.h 2009-05-12 20:02:16.000000000 +0200
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/include/drv_dsl_cpe_device_danube.h 2009-11-01 00:57:23.000000000 +0100
|
||||
@@ -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
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/common/drv_dsl_cpe_os_linux.c
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/common/drv_dsl_cpe_os_linux.c 2009-11-01 01:00:08.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/common/drv_dsl_cpe_os_linux.c 2009-11-01 01:03:51.000000000 +0100
|
||||
@@ -11,6 +11,7 @@
|
||||
#ifdef __LINUX__
|
||||
|
||||
#define DSL_INTERN
|
||||
+#include <linux/device.h>
|
||||
|
||||
#include "drv_dsl_cpe_api.h"
|
||||
#include "drv_dsl_cpe_api_ioctl.h"
|
||||
@@ -1058,6 +1059,7 @@
|
||||
/* 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 @@
|
||||
}
|
||||
|
||||
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;
|
||||
}
|
||||
|
95
package/ifxmips-dsl-api/patches/200-mei_compat.patch
Normal file
95
package/ifxmips-dsl-api/patches/200-mei_compat.patch
Normal file
|
@ -0,0 +1,95 @@
|
|||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_mei.c
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_mei.c 2009-10-31 23:30:20.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_mei.c 2009-11-01 04:41:58.000000000 +0100
|
||||
@@ -41,18 +41,19 @@
|
||||
#include <linux/init.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/delay.h>
|
||||
+#include <linux/device.h>
|
||||
#include <asm/uaccess.h>
|
||||
#include <asm/hardirq.h>
|
||||
-#include <asm/ifx/ifx_regs.h>
|
||||
-#include <asm/ifx/irq.h>
|
||||
-#include <asm/ifx/ifx_gpio.h>
|
||||
-//#include <asm/ifx/ifx_led.h>
|
||||
-#include <asm/ifx/ifx_pmu.h>
|
||||
-#include <asm/ifx/ifx_atm.h>
|
||||
+
|
||||
+#include <ifxmips.h>
|
||||
+#include <ifxmips_irq.h>
|
||||
+#include <ifxmips_gpio.h>
|
||||
+#include <ifxmips_pmu.h>
|
||||
+#include "ifxmips_atm.h"
|
||||
#define IFX_MEI_BSP
|
||||
#include "ifxmips_mei_interface.h"
|
||||
|
||||
-#define IFXMIPS_RCU_RST IFX_RCU_RST_REQ
|
||||
+/*#define IFXMIPS_RCU_RST IFX_RCU_RST_REQ
|
||||
#define IFXMIPS_RCU_RST_REQ_ARC_JTAG IFX_RCU_RST_REQ_ARC_JTAG
|
||||
#define IFXMIPS_RCU_RST_REQ_DFE IFX_RCU_RST_REQ_DFE
|
||||
#define IFXMIPS_RCU_RST_REQ_AFE IFX_RCU_RST_REQ_AFE
|
||||
@@ -76,7 +77,7 @@
|
||||
#define ifxmips_r32(reg) __raw_readl(reg)
|
||||
#define ifxmips_w32(val, reg) __raw_writel(val, reg)
|
||||
#define ifxmips_w32_mask(clear, set, reg) ifxmips_w32((ifxmips_r32(reg) & ~clear) | set, reg)
|
||||
-
|
||||
+*/
|
||||
#define IFX_MEI_EMSG(fmt, args...) printk(KERN_ERR "[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args)
|
||||
#define IFX_MEI_DMSG(fmt, args...) printk(KERN_INFO "[%s %d]: " fmt,__FUNCTION__, __LINE__, ## args)
|
||||
|
||||
@@ -173,7 +174,8 @@
|
||||
extern void ifxmips_mask_and_ack_irq(unsigned int irq_nr);
|
||||
#define MEI_MASK_AND_ACK_IRQ ifxmips_mask_and_ack_irq
|
||||
|
||||
-static int dev_major = 105;
|
||||
+#define MEI_MAJOR 105
|
||||
+static int dev_major = MEI_MAJOR;
|
||||
|
||||
static struct file_operations bsp_mei_operations = {
|
||||
owner:THIS_MODULE,
|
||||
@@ -2294,10 +2296,10 @@
|
||||
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) {
|
||||
+ /*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;
|
||||
}
|
||||
@@ -2922,6 +2924,7 @@
|
||||
IFX_MEI_ModuleInit (void)
|
||||
{
|
||||
int i = 0;
|
||||
+ static struct class *dsl_class;
|
||||
|
||||
printk ("IFX MEI Version %ld.%02ld.%02ld", bsp_mei_version.major, bsp_mei_version.minor, bsp_mei_version.revision);
|
||||
|
||||
@@ -2935,14 +2938,15 @@
|
||||
IFX_MEI_InitProcFS (i);
|
||||
#endif
|
||||
}
|
||||
- for (i = 0; i <= DSL_BSP_CB_LAST ; i++)
|
||||
+ for (i = 0; i <= DSL_BSP_CB_LAST ; i++)
|
||||
dsl_bsp_event_callback[i].function = NULL;
|
||||
|
||||
#ifdef CONFIG_IFXMIPS_MEI_FW_LOOPBACK
|
||||
printk(KERN_INFO "[%s %s %d]: Start loopback test...\n", __FILE__, __func__, __LINE__);
|
||||
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;
|
||||
}
|
||||
|
||||
@@ -2996,3 +3000,5 @@
|
||||
|
||||
module_init (IFX_MEI_ModuleInit);
|
||||
module_exit (IFX_MEI_ModuleExit);
|
||||
+
|
||||
+MODULE_LICENSE("Dual BSD/GPL");
|
168
package/ifxmips-dsl-api/patches/300-atm_compat.patch
Normal file
168
package/ifxmips-dsl-api/patches/300-atm_compat.patch
Normal file
|
@ -0,0 +1,168 @@
|
|||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_core.c
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_atm_core.c 2009-11-01 14:29:05.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_core.c 2009-11-01 16:07:46.000000000 +0100
|
||||
@@ -58,9 +58,8 @@
|
||||
/*
|
||||
* Chip Specific Head File
|
||||
*/
|
||||
-#include <asm/ifx/ifx_types.h>
|
||||
-#include <asm/ifx/ifx_regs.h>
|
||||
-#include <asm/ifx/common_routines.h>
|
||||
+#include <ifxmips.h>
|
||||
+#include <ifxmips_cgu.h>
|
||||
#include "ifxmips_atm_core.h"
|
||||
|
||||
|
||||
@@ -1146,7 +1145,7 @@
|
||||
|
||||
static void set_qsb(struct atm_vcc *vcc, struct atm_qos *qos, unsigned int queue)
|
||||
{
|
||||
- unsigned int qsb_clk = ifx_get_fpi_hz();
|
||||
+ unsigned int qsb_clk = ifxmips_get_fpi_hz();
|
||||
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}};
|
||||
@@ -1318,7 +1317,7 @@
|
||||
|
||||
static void qsb_global_set(void)
|
||||
{
|
||||
- unsigned int qsb_clk = ifx_get_fpi_hz();
|
||||
+ unsigned int qsb_clk = ifxmips_get_fpi_hz();
|
||||
int i;
|
||||
unsigned int tmp1, tmp2, tmp3;
|
||||
|
||||
@@ -2505,3 +2504,4 @@
|
||||
|
||||
module_init(ifx_atm_init);
|
||||
module_exit(ifx_atm_exit);
|
||||
+MODULE_LICENSE("Dual BSD/GPL");
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_ppe_common.h
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_atm_ppe_common.h 2009-11-01 14:30:55.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_ppe_common.h 2009-11-01 15:58:50.000000000 +0100
|
||||
@@ -1,9 +1,10 @@
|
||||
#ifndef IFXMIPS_ATM_PPE_COMMON_H
|
||||
#define IFXMIPS_ATM_PPE_COMMON_H
|
||||
|
||||
-
|
||||
-
|
||||
-#if defined(CONFIG_DANUBE)
|
||||
+#if defined(CONFIG_IFXMIPS)
|
||||
+ #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"
|
||||
@@ -16,7 +17,6 @@
|
||||
#endif
|
||||
|
||||
|
||||
-
|
||||
/*
|
||||
* Code/Data Memory (CDM) Interface Configuration Register
|
||||
*/
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_core.h
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_atm_core.h 2009-11-01 14:30:55.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_core.h 2009-11-01 15:58:50.000000000 +0100
|
||||
@@ -25,8 +25,8 @@
|
||||
#define IFXMIPS_ATM_CORE_H
|
||||
|
||||
|
||||
-
|
||||
-#include <asm/ifx/ifx_atm.h>
|
||||
+#include "ifxmips_compat.h"
|
||||
+#include "ifx_atm.h"
|
||||
#include "ifxmips_atm_ppe_common.h"
|
||||
#include "ifxmips_atm_fw_regs_common.h"
|
||||
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_compat.h
|
||||
===================================================================
|
||||
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_compat.h 2009-11-01 15:58:50.000000000 +0100
|
||||
@@ -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) ifxmips_pmu_enable(b); else ifxmips_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
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_ppe_danube.h
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_atm_ppe_danube.h 2009-11-01 14:30:55.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_ppe_danube.h 2009-11-01 15:58:50.000000000 +0100
|
||||
@@ -1,7 +1,7 @@
|
||||
#ifndef IFXMIPS_ATM_PPE_DANUBE_H
|
||||
#define IFXMIPS_ATM_PPE_DANUBE_H
|
||||
|
||||
-
|
||||
+#include <ifxmips_irq.h>
|
||||
|
||||
/*
|
||||
* FPI Configuration Bus Register and Memory Address Mapping
|
||||
@@ -93,7 +93,7 @@
|
||||
/*
|
||||
* Mailbox IGU1 Interrupt
|
||||
*/
|
||||
-#define PPE_MAILBOX_IGU1_INT INT_NUM_IM2_IRL24
|
||||
+#define PPE_MAILBOX_IGU1_INT IFXMIPS_PPE_MBOX_INT
|
||||
|
||||
|
||||
|
||||
Index: drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_danube.c
|
||||
===================================================================
|
||||
--- drv_dsl_cpe_api-3.24.4.4.orig/src/mei/ifxmips_atm_danube.c 2009-11-01 14:29:18.000000000 +0100
|
||||
+++ drv_dsl_cpe_api-3.24.4.4/src/mei/ifxmips_atm_danube.c 2009-11-01 15:58:50.000000000 +0100
|
||||
@@ -45,10 +45,9 @@
|
||||
/*
|
||||
* Chip Specific Head File
|
||||
*/
|
||||
-#include <asm/ifx/ifx_types.h>
|
||||
-#include <asm/ifx/ifx_regs.h>
|
||||
-#include <asm/ifx/common_routines.h>
|
||||
-#include <asm/ifx/ifx_pmu.h>
|
||||
+#include <ifxmips.h>
|
||||
+#include <ifxmips_pmu.h>
|
||||
+#include "ifxmips_compat.h"
|
||||
#include "ifxmips_atm_core.h"
|
||||
#include "ifxmips_atm_fw_danube.h"
|
||||
|
3
package/ifxmips-dsl-api/src/Makefile
Normal file
3
package/ifxmips-dsl-api/src/Makefile
Normal file
|
@ -0,0 +1,3 @@
|
|||
obj-m = ifxmips_mei.o ifxmips_atm.o
|
||||
|
||||
ifxmips_atm-objs := ifxmips_atm_core.o ifxmips_atm_danube.o
|
172
package/ifxmips-dsl-api/src/ifx_atm.h
Normal file
172
package/ifxmips-dsl-api/src/ifx_atm.h
Normal file
|
@ -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
|
||||
|
172
package/ifxmips-dsl-api/src/ifxmips_atm.h
Normal file
172
package/ifxmips-dsl-api/src/ifxmips_atm.h
Normal file
|
@ -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
|
||||
|
2507
package/ifxmips-dsl-api/src/ifxmips_atm_core.c
Normal file
2507
package/ifxmips-dsl-api/src/ifxmips_atm_core.c
Normal file
File diff suppressed because it is too large
Load diff
249
package/ifxmips-dsl-api/src/ifxmips_atm_core.h
Normal file
249
package/ifxmips-dsl-api/src/ifxmips_atm_core.h
Normal file
|
@ -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 <asm/ifx/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
|
272
package/ifxmips-dsl-api/src/ifxmips_atm_danube.c
Normal file
272
package/ifxmips-dsl-api/src/ifxmips_atm_danube.c
Normal file
|
@ -0,0 +1,272 @@
|
|||
/******************************************************************************
|
||||
**
|
||||
** 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 <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/version.h>
|
||||
#include <linux/types.h>
|
||||
#include <linux/errno.h>
|
||||
#include <linux/proc_fs.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/ioctl.h>
|
||||
#include <asm/delay.h>
|
||||
|
||||
/*
|
||||
* Chip Specific Head File
|
||||
*/
|
||||
#include <asm/ifx/ifx_types.h>
|
||||
#include <asm/ifx/ifx_regs.h>
|
||||
#include <asm/ifx/common_routines.h>
|
||||
#include <asm/ifx/ifx_pmu.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);
|
||||
}
|
|
@ -1,10 +1,10 @@
|
|||
#ifndef __DANUBE_PPE_FW_H__2005_08_04__12_00__
|
||||
#define __DANUBE_PPE_FW_H__2005_08_04__12_00__
|
||||
#ifndef IFXMIPS_ATM_FW_DANUBE_H
|
||||
#define IFXMIPS_ATM_FW_DANUBE_H
|
||||
|
||||
|
||||
/******************************************************************************
|
||||
**
|
||||
** FILE NAME : danube_ppe_fw.h
|
||||
** FILE NAME : ifxmips_atm_fw_danube.h
|
||||
** PROJECT : Danube
|
||||
** MODULES : ATM (ADSL)
|
||||
**
|
||||
|
@ -27,7 +27,11 @@
|
|||
*******************************************************************************/
|
||||
|
||||
|
||||
static u32 firmware_binary_code[] = {
|
||||
#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,
|
||||
|
@ -418,9 +422,8 @@ static u32 firmware_binary_code[] = {
|
|||
0x00000000,
|
||||
};
|
||||
|
||||
static u32 firmware_binary_data[] = {
|
||||
static unsigned int firmware_binary_data[] = {
|
||||
};
|
||||
|
||||
|
||||
#endif // __DANUBE_PPE_FW_H__2005_08_04__12_00__
|
||||
|
||||
#endif // IFXMIPS_ATM_FW_DANUBE_H
|
364
package/ifxmips-dsl-api/src/ifxmips_atm_fw_regs_common.h
Normal file
364
package/ifxmips-dsl-api/src/ifxmips_atm_fw_regs_common.h
Normal file
|
@ -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
|
30
package/ifxmips-dsl-api/src/ifxmips_atm_fw_regs_danube.h
Normal file
30
package/ifxmips-dsl-api/src/ifxmips_atm_fw_regs_danube.h
Normal file
|
@ -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
|
231
package/ifxmips-dsl-api/src/ifxmips_atm_ppe_common.h
Normal file
231
package/ifxmips-dsl-api/src/ifxmips_atm_ppe_common.h
Normal file
|
@ -0,0 +1,231 @@
|
|||
#ifndef IFXMIPS_ATM_PPE_COMMON_H
|
||||
#define IFXMIPS_ATM_PPE_COMMON_H
|
||||
|
||||
|
||||
|
||||
#if 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
|
100
package/ifxmips-dsl-api/src/ifxmips_atm_ppe_danube.h
Normal file
100
package/ifxmips-dsl-api/src/ifxmips_atm_ppe_danube.h
Normal file
|
@ -0,0 +1,100 @@
|
|||
#ifndef IFXMIPS_ATM_PPE_DANUBE_H
|
||||
#define IFXMIPS_ATM_PPE_DANUBE_H
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* 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 INT_NUM_IM2_IRL24
|
||||
|
||||
|
||||
|
||||
#endif // IFXMIPS_ATM_PPE_DANUBE_H
|
2998
package/ifxmips-dsl-api/src/ifxmips_mei.c
Normal file
2998
package/ifxmips-dsl-api/src/ifxmips_mei.c
Normal file
File diff suppressed because it is too large
Load diff
700
package/ifxmips-dsl-api/src/ifxmips_mei_interface.h
Normal file
700
package/ifxmips-dsl-api/src/ifxmips_mei_interface.h
Normal file
|
@ -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
|
84
package/ifxmips-dsl-control/Makefile
Normal file
84
package/ifxmips-dsl-control/Makefile
Normal file
|
@ -0,0 +1,84 @@
|
|||
#
|
||||
# Copyright (C) 2009 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
|
||||
|
||||
PKG_BASE_NAME:=dsl_cpe_control_danube
|
||||
PKG_VERSION:=3.24.4.4
|
||||
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/ifxmips-dsl-control
|
||||
SECTION:=application
|
||||
CATEGORY:=Infineon
|
||||
TITLE:=DSL CPE control application
|
||||
URL:=http://www.infineon.com/
|
||||
MAINTAINER:=Infineon Technologies AG / Lantiq / blogic@openwrt.org
|
||||
DEPENDS:=+kmod-ifxmips-dsl-api +libpthread
|
||||
endef
|
||||
|
||||
define Package/ifxmips-dsl-control/description
|
||||
Infineon DSL CPE API for Amazon SE, Danube and Vinax.
|
||||
This package contains the DSL CPE control application for Amazon SE & Danube.
|
||||
|
||||
Supported Devices:
|
||||
- Amazon SE
|
||||
- Danube
|
||||
|
||||
This package was kindly contributed to openwrt by Infineon/Lantiq
|
||||
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
|
||||
|
||||
define Package/ifxmips-dsl-control/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,ifxmips-dsl-control))
|
21
package/ifxmips-dsl-control/files/ifx_cpe_control_init.sh
Normal file
21
package/ifxmips-dsl-control/files/ifx_cpe_control_init.sh
Normal file
|
@ -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
|
||||
}
|
||||
|
||||
}
|
|
@ -12,15 +12,3 @@ Index: linux-2.6.28.10/include/linux/atm.h
|
|||
/* extra params for ABR */
|
||||
unsigned int icr; /* Initial Cell Rate (24-bit) */
|
||||
unsigned int tbe; /* Transient Buffer Exposure (24-bit) */
|
||||
Index: linux-2.6.28.10/kernel/time/timekeeping.c
|
||||
===================================================================
|
||||
--- linux-2.6.28.10.orig/kernel/time/timekeeping.c 2009-09-02 15:41:06.000000000 +0200
|
||||
+++ linux-2.6.28.10/kernel/time/timekeeping.c 2009-09-02 15:41:23.000000000 +0200
|
||||
@@ -43,6 +43,7 @@
|
||||
* used instead.
|
||||
*/
|
||||
struct timespec xtime __attribute__ ((aligned (16)));
|
||||
+EXPORT_SYMBOL(xtime);
|
||||
struct timespec wall_to_monotonic __attribute__ ((aligned (16)));
|
||||
static unsigned long total_sleep_time; /* seconds */
|
||||
|
|
@ -13,9 +13,10 @@ FEATURES:=squashfs jffs2 atm
|
|||
|
||||
LINUX_VERSION:=2.6.30.9
|
||||
|
||||
CFLAGS=-Os -pipe -mips32r2 -mtune=mips32r2 -funit-at-a-time
|
||||
|
||||
include $(INCLUDE_DIR)/target.mk
|
||||
DEFAULT_PACKAGES+=uboot-ifxmips
|
||||
#kmod-pppoa ppp-mod-pppoa linux-atm atm-tools br2684ctl kmod-ifxmips-atm
|
||||
DEFAULT_PACKAGES+=kmod-pppoa ppp-mod-pppoa linux-atm atm-tools br2684ctl ifxmips-dsl-api ifxmips-dsl-control
|
||||
|
||||
define Target/Description
|
||||
Build firmware images for Infineon Mips Controllers
|
||||
|
|
|
@ -23,5 +23,4 @@ config interface wan
|
|||
option proto pppoe
|
||||
option username ""
|
||||
option password ""
|
||||
option defaultroute 0
|
||||
option unit 1
|
||||
option unit 0
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
#define IFXMIPS_SSC_RIR (INT_NUM_IM0_IRL0 + 14)
|
||||
#define IFXMIPS_SSC_EIR (INT_NUM_IM0_IRL0 + 16)
|
||||
|
||||
#define IFXMIPS_MEI_DYING_GASP_INT (INT_NUM_IM1_IRL0 + 21)
|
||||
#define IFXMIPS_MEI_INT (INT_NUM_IM1_IRL0 + 23)
|
||||
|
||||
#define IFXMIPS_TIMER6_INT (INT_NUM_IM1_IRL0 + 23)
|
||||
|
|
48
target/linux/ifxmips/patches-2.6.30/400-atm_hack.patch
Normal file
48
target/linux/ifxmips/patches-2.6.30/400-atm_hack.patch
Normal file
|
@ -0,0 +1,48 @@
|
|||
Index: linux-2.6.30.9/arch/mips/mm/cache.c
|
||||
===================================================================
|
||||
--- linux-2.6.30.9.orig/arch/mips/mm/cache.c 2009-11-01 16:10:29.000000000 +0100
|
||||
+++ linux-2.6.30.9/arch/mips/mm/cache.c 2009-11-01 16:11:56.000000000 +0100
|
||||
@@ -52,6 +52,8 @@
|
||||
void (*_dma_cache_inv)(unsigned long start, unsigned long size);
|
||||
|
||||
EXPORT_SYMBOL(_dma_cache_wback_inv);
|
||||
+EXPORT_SYMBOL(_dma_cache_wback);
|
||||
+EXPORT_SYMBOL(_dma_cache_inv);
|
||||
|
||||
#endif /* CONFIG_DMA_NONCOHERENT */
|
||||
|
||||
Index: linux-2.6.30.9/net/atm/proc.c
|
||||
===================================================================
|
||||
--- linux-2.6.30.9.orig/net/atm/proc.c 2009-11-01 16:34:42.000000000 +0100
|
||||
+++ linux-2.6.30.9/net/atm/proc.c 2009-11-01 16:35:59.000000000 +0100
|
||||
@@ -151,7 +151,7 @@
|
||||
|
||||
static void pvc_info(struct seq_file *seq, struct atm_vcc *vcc)
|
||||
{
|
||||
- static const char *class_name[] = { "off","UBR","CBR","VBR","ABR" };
|
||||
+ static const char *class_name[] = { "off","UBR","CBR","NTR-VBR","ABR","ANY","RT-VBR","UBR+","GFR" };
|
||||
static const char *aal_name[] = {
|
||||
"---", "1", "2", "3/4", /* 0- 3 */
|
||||
"???", "5", "???", "???", /* 4- 7 */
|
||||
Index: linux-2.6.30.9/net/atm/common.c
|
||||
===================================================================
|
||||
--- linux-2.6.30.9.orig/net/atm/common.c 2009-11-01 16:38:12.000000000 +0100
|
||||
+++ linux-2.6.30.9/net/atm/common.c 2009-11-01 16:47:06.000000000 +0100
|
||||
@@ -56,12 +56,17 @@
|
||||
write_unlock_irq(&vcc_sklist_lock);
|
||||
}
|
||||
|
||||
+struct sk_buff* (*ifx_atm_alloc_tx)(struct atm_vcc *, unsigned int) = NULL;
|
||||
+EXPORT_SYMBOL(ifx_atm_alloc_tx);
|
||||
|
||||
static struct sk_buff *alloc_tx(struct atm_vcc *vcc,unsigned int size)
|
||||
{
|
||||
struct sk_buff *skb;
|
||||
struct sock *sk = sk_atm(vcc);
|
||||
|
||||
+ if (ifx_atm_alloc_tx != NULL)
|
||||
+ return ifx_atm_alloc_tx(vcc, size);
|
||||
+
|
||||
if (atomic_read(&sk->sk_wmem_alloc) && !atm_may_send(vcc, size)) {
|
||||
pr_debug("Sorry: wmem_alloc = %d, size = %d, sndbuf = %d\n",
|
||||
atomic_read(&sk->sk_wmem_alloc), size,
|
Loading…
Reference in a new issue