511 lines
16 KiB
C
511 lines
16 KiB
C
/*
|
||
* Copyright : (C) 2022 Phytium Information Technology, Inc.
|
||
* All Rights Reserved.
|
||
*
|
||
* This program is OPEN SOURCE software: you can redistribute it and/or modify it
|
||
* under the terms of the Phytium Public License as published by the Phytium Technology Co.,Ltd,
|
||
* either version 1.0 of the License, or (at your option) any later version.
|
||
*
|
||
* This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY;
|
||
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||
* See the Phytium Public License for more details.
|
||
*
|
||
*
|
||
* FilePath: fgmac.c
|
||
* Date: 2022-04-06 14:46:52
|
||
* LastEditTime: 2022-04-06 14:46:58
|
||
* Description: This file is for gmac driver .Functions in this file are the minimum required functions
|
||
* for this driver.
|
||
*
|
||
* Modify History:
|
||
* Ver Who Date Changes
|
||
* ----- ------ -------- --------------------------------------
|
||
* 1.0 huanghe 2021/07/13 first release
|
||
*/
|
||
|
||
|
||
/***************************** Include Files *********************************/
|
||
#include <string.h>
|
||
#include "fio.h"
|
||
#include "ferror_code.h"
|
||
#include "ftypes.h"
|
||
#include "fdebug.h"
|
||
#include "fassert.h"
|
||
#include "fgmac_hw.h"
|
||
#include "fgmac_phy.h"
|
||
#include "fgmac.h"
|
||
|
||
/************************** Constant Definitions *****************************/
|
||
|
||
/**************************** Type Definitions *******************************/
|
||
|
||
/***************** Macros (Inline Functions) Definitions *********************/
|
||
#define FGMAC_DEBUG_TAG "FGMAC"
|
||
#define FGMAC_ERROR(format, ...) FT_DEBUG_PRINT_E(FGMAC_DEBUG_TAG, format, ##__VA_ARGS__)
|
||
#define FGMAC_WARN(format, ...) FT_DEBUG_PRINT_W(FGMAC_DEBUG_TAG, format, ##__VA_ARGS__)
|
||
#define FGMAC_INFO(format, ...) FT_DEBUG_PRINT_I(FGMAC_DEBUG_TAG, format, ##__VA_ARGS__)
|
||
#define FGMAC_DEBUG(format, ...) FT_DEBUG_PRINT_D(FGMAC_DEBUG_TAG, format, ##__VA_ARGS__)
|
||
|
||
|
||
/************************** Function Prototypes ******************************/
|
||
static FError FGmacReset(FGmac *instance_p);
|
||
static FError FGmacDmaConfigure(FGmac *instance_p);
|
||
static FError FGmacControllerConfigure(FGmac *instance_p);
|
||
/************************** Variable Definitions *****************************/
|
||
|
||
/*****************************************************************************/
|
||
|
||
/* 此文件主要为了完成用户对外接口,用户可以使用这些接口直接开始工作 */
|
||
|
||
/* - 包括用户API的定义和实现
|
||
- 同时包含必要的OPTION方法,方便用户进行配置
|
||
- 如果驱动可以直接进行I/O操作,在此源文件下可以将API 进行实现 */
|
||
|
||
/* - 包括用户API的定义和实现
|
||
- 同时包含必要的OPTION方法,方便用户进行配置
|
||
- 如果驱动可以直接进行I/O操作,在此源文件下可以将API 进行实现 */
|
||
|
||
/*
|
||
* @name: FGmacStop
|
||
* @msg: 停止FGMAC控制器寄存器
|
||
* @return {*}
|
||
* @param {FGmac} *instance_p 驱动控制数据
|
||
*/
|
||
void FGmacStop(FGmac *instance_p)
|
||
{
|
||
FASSERT(instance_p);
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
u32 reg_val;
|
||
|
||
/* disable dma tx and rx */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_DMA_OP_OFFSET);
|
||
reg_val &= (~FGMAC_DMA_OP_ST);
|
||
reg_val &= (~FGMAC_DMA_OP_SR);
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_DMA_OP_OFFSET, reg_val);
|
||
|
||
/* disable gmac tx and rx */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_CONF_OFFSET);
|
||
reg_val &= (~FGMAC_CONF_TX_EN);
|
||
reg_val &= (~FGMAC_CONF_RX_EN);
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_CONF_OFFSET, reg_val);
|
||
|
||
}
|
||
|
||
|
||
/**
|
||
* @name: FGmacCfgInitialize
|
||
* @msg: init FGMAC controller
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @param {FGmacConfig} *cofig_p, input configuration parameters
|
||
* @return err code information, FGMAC_SUCCESS indicates success,others indicates failed
|
||
*/
|
||
FError FGmacCfgInitialize(FGmac *instance_p, const FGmacConfig *input_config_p)
|
||
{
|
||
FASSERT(instance_p && input_config_p);
|
||
FError ret = FGMAC_SUCCESS;
|
||
|
||
/* indicating device is started */
|
||
if (FT_COMPONENT_IS_READY == instance_p->is_ready)
|
||
{
|
||
FGMAC_WARN("Device is already initialized!!!");
|
||
}
|
||
|
||
/* de-initialize device instance */
|
||
FGmacDeInitialize(instance_p);
|
||
instance_p->config = *input_config_p;
|
||
|
||
/* Phy Awaken */
|
||
ret = FGmacPhyAwaken(instance_p);
|
||
if (FGMAC_SUCCESS != ret)
|
||
{
|
||
FGMAC_ERROR("Phy awaken failed!");
|
||
return ret;
|
||
}
|
||
|
||
|
||
/* initialize the gmac controller */
|
||
ret = FGmacReset(instance_p);
|
||
if (FGMAC_SUCCESS != ret)
|
||
{
|
||
/*permit failed*/
|
||
FGMAC_ERROR("Gmac reset failed.");
|
||
}
|
||
|
||
ret = FGmacControllerConfigure(instance_p);
|
||
if (FGMAC_SUCCESS != ret)
|
||
{
|
||
return ret;
|
||
}
|
||
|
||
/* initialize the gmac dma controller */
|
||
ret = FGmacDmaConfigure(instance_p);
|
||
if (FGMAC_SUCCESS == ret)
|
||
{
|
||
instance_p->is_ready = FT_COMPONENT_IS_READY;
|
||
}
|
||
|
||
return ret;
|
||
}
|
||
|
||
/**
|
||
* @name: FGmacDeInitialize
|
||
* @msg: deinit FGMAC controller
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @return err code information, FGMAC_SUCCESS indicates success,others indicates failed
|
||
*/
|
||
FError FGmacDeInitialize(FGmac *instance_p)
|
||
{
|
||
FASSERT(instance_p);
|
||
FError ret = FGMAC_SUCCESS;
|
||
|
||
instance_p->is_ready = 0;
|
||
memset(instance_p, 0, sizeof(*instance_p));
|
||
|
||
return ret;
|
||
}
|
||
|
||
/**
|
||
* @name: FGmacReset
|
||
* @msg: reset FGMAC controller
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @return err code information, FGMAC_SUCCESS indicates success,others indicates failed
|
||
*/
|
||
static FError FGmacReset(FGmac *instance_p)
|
||
{
|
||
FASSERT(instance_p);
|
||
FGmacMacAddr mac_addr;
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
FError ret = FGMAC_SUCCESS;
|
||
u32 reg_val;
|
||
|
||
|
||
/* backup mac address before software reset */
|
||
memset(mac_addr, 0, sizeof(mac_addr));
|
||
FGmacGetMacAddr(base_addr, mac_addr);
|
||
|
||
/* disable all gmac & dma intr */
|
||
FGmacSetInterruptMask(instance_p, FGMAC_CTRL_INTR, FGMAC_ISR_MASK_ALL_BITS);
|
||
FGmacSetInterruptMask(instance_p, FGMAC_DMA_INTR, FGMAC_DMA_INTR_ENA_ALL_MASK);
|
||
|
||
/* stop gmac/dma tx and rx */
|
||
FGmacStop(instance_p);
|
||
|
||
/* do software reset per init */
|
||
ret = FGmacSoftwareReset(base_addr, FGMAC_RETRY_TIMES);
|
||
|
||
|
||
/* disable gmac & dma interrupts */
|
||
FGmacSetInterruptMask(instance_p, FGMAC_CTRL_INTR, FGMAC_ISR_MASK_ALL_BITS);
|
||
FGmacSetInterruptMask(instance_p, FGMAC_DMA_INTR, FGMAC_DMA_INTR_ENA_ALL_MASK);
|
||
|
||
/* recover mac address after softwate reset */
|
||
FGmacSetMacAddr(base_addr, mac_addr);
|
||
|
||
return ret;
|
||
}
|
||
|
||
/**
|
||
* @name: FGmacControllerSpeedConfig
|
||
* @msg: fgmac speed configuration
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @param {u32} speed, speed value
|
||
* @return {*}
|
||
*/
|
||
void FGmacControllerSpeedConfig(FGmac *instance_p, u32 speed)
|
||
{
|
||
FASSERT(instance_p);
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
u32 reg_val = 0;
|
||
|
||
/* MAC配置寄存器 */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_CONF_OFFSET);
|
||
|
||
/* 设置通信速度FES=1000Mbps */
|
||
if (speed == FGMAC_PHY_SPEED_1000)
|
||
{
|
||
reg_val &= (~FGMAC_CONF_PORTSELECT);
|
||
reg_val &= (~FGMAC_CONF_FES);
|
||
}
|
||
|
||
/* 设置通信速度FES=100Mbps */
|
||
if (speed == FGMAC_PHY_SPEED_100)
|
||
{
|
||
reg_val |= FGMAC_CONF_PORTSELECT;
|
||
reg_val |= FGMAC_CONF_FES;
|
||
}
|
||
|
||
/* 设置通信速度FES=10Mbps */
|
||
if (speed == FGMAC_PHY_SPEED_10)
|
||
{
|
||
reg_val |= FGMAC_CONF_PORTSELECT;
|
||
reg_val &= (~FGMAC_CONF_FES);
|
||
}
|
||
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_CONF_OFFSET, reg_val);
|
||
}
|
||
|
||
/**
|
||
* @name: FGmacControllerDuplexConfig
|
||
* @msg: fgmac deplex mode configuration
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @param {u32} duplex, duplex mode
|
||
* @return {*}
|
||
*/
|
||
void FGmacControllerDuplexConfig(FGmac *instance_p, u32 duplex)
|
||
{
|
||
FASSERT(instance_p);
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
u32 reg_val = 0;
|
||
|
||
/* MAC配置寄存器 */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_CONF_OFFSET);
|
||
|
||
/* 设置双工模式 */
|
||
if (duplex == FGMAC_PHY_MODE_FULLDUPLEX)
|
||
{
|
||
reg_val |= FGMAC_CONF_DUPLEX_MODE;
|
||
}
|
||
else
|
||
{
|
||
reg_val &= ~FGMAC_CONF_DUPLEX_MODE;
|
||
}
|
||
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_CONF_OFFSET, reg_val);
|
||
|
||
}
|
||
|
||
/**
|
||
* @name: FGmacControllerConfigure
|
||
* @msg: config FGMAC controller
|
||
* @param {FGmac} *instance_p, instance of FGmac controller
|
||
* @return err code information, FGMAC_SUCCESS indicates success,others indicates failed
|
||
*/
|
||
static FError FGmacControllerConfigure(FGmac *instance_p)
|
||
{
|
||
FASSERT(instance_p);
|
||
FGmacMacAddr mac_addr;
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
FError ret = FGMAC_SUCCESS;
|
||
u32 reg_val = 0;
|
||
|
||
/********gmac ctrl reg init*********/
|
||
/* Set the WD bit according to ETH Watchdog value */
|
||
/* Set the JD: bit according to ETH Jabber value */
|
||
/* Set the IFG bit according to ETH InterFrameGap value */
|
||
/* Set the DCRS bit according to ETH CarrierSense value */
|
||
/* Set the FES bit according to ETH Speed value */
|
||
/* Set the DO bit according to ETH ReceiveOwn value */
|
||
/* Set the LM bit according to ETH LoopbackMode value */
|
||
/* Set the DM bit according to ETH Mode value */
|
||
/* Set the IPCO bit according to ETH ChecksumOffload value */
|
||
/* Set the DR bit according to ETH RetryTransmission value */
|
||
/* Set the ACS bit according to ETH AutomaticPadCRCStrip value */
|
||
/* Set the BL bit according to ETH BackOffLimit value */
|
||
/* Set the DC bit according to ETH DeferralCheck value */
|
||
|
||
/* MAC配置寄存器 */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_CONF_OFFSET);
|
||
|
||
/* 使能载波侦听DCRS、失能环回模式LM */
|
||
reg_val &= ~(FGMAC_CONF_DCRS | FGMAC_CONF_LOOPBACK_MODE);
|
||
|
||
/* 设置帧内间隔IFG */
|
||
reg_val |= FGMAC_CONF_IFG(0);
|
||
|
||
/* 1000Mbps default */
|
||
reg_val &= (~FGMAC_CONF_PORTSELECT);
|
||
reg_val &= (~FGMAC_CONF_FES);
|
||
|
||
/* 双工模式 */
|
||
if (instance_p->config.duplex_mode)
|
||
{
|
||
reg_val |= FGMAC_CONF_DUPLEX_MODE;
|
||
}
|
||
else
|
||
{
|
||
reg_val &= ~FGMAC_CONF_DUPLEX_MODE;
|
||
}
|
||
|
||
/* 使能校验和卸载IPS */
|
||
if (FGMAC_CHECKSUM_BY_HARDWARE == instance_p->config.cheksum_mode)
|
||
{
|
||
reg_val |= FGMAC_CONF_IPC;
|
||
}
|
||
else
|
||
{
|
||
reg_val &= ~FGMAC_CONF_IPC;
|
||
}
|
||
|
||
/* 重发DR=1, 重发一次 */
|
||
reg_val |= FGMAC_CONF_DISABLE_RETRY;
|
||
|
||
/* 自动 PAD/ CRC 剥线, 全双工模式保留 */
|
||
reg_val |= FGMAC_CONF_ACS;
|
||
|
||
/* 后退限制, 全双工模式保留 */
|
||
reg_val |= FGMAC_CONF_BL(0);
|
||
|
||
/* 延期检查禁用 */
|
||
reg_val &= ~FGMAC_CONF_DC;
|
||
|
||
/* 使能类型帧的CRC剥离、禁用看门狗WD、禁用Jabber JD、帧突发启用BE、不能自接收DO(全双工保留)*/
|
||
reg_val |= (FGMAC_CONF_CST | FGMAC_CONF_WD | FGMAC_CONF_JD | FGMAC_CONF_BE | FGMAC_CONF_DO);
|
||
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_CONF_OFFSET, reg_val);
|
||
|
||
/********gmac filter reg init*********/
|
||
/* Set the RA bit according to ETH ReceiveAll value */
|
||
/* Set the SAF and SAIF bits according to ETH SourceAddrFilter value */
|
||
/* Set the PCF bit according to ETH PassControlFrames value */
|
||
/* Set the DBF bit according to ETH BroadcastFramesReception value */
|
||
/* Set the DAIF bit according to ETH DestinationAddrFilter value */
|
||
/* Set the PR bit according to ETH PromiscuousMode value */
|
||
/* Set the PM, HMC and HPF bits according to ETH MulticastFramesFilter value */
|
||
/* Set the HUC and HPF bits according to ETH UnicastFramesFilter value */
|
||
|
||
/* MAC帧过滤寄存器 */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_FRAME_FILTER_OFFSET);
|
||
|
||
/* 全部接收RA */
|
||
reg_val |= FGMAC_FRAME_FILTER_RA;
|
||
|
||
/* 通过控制帧PCF 10b */
|
||
reg_val |= FGMAC_FRAME_FILTER_PCF(2);
|
||
|
||
/* 失能禁用广播帧DBF */
|
||
reg_val &= ~FGMAC_FRAME_FILTER_DBF;
|
||
|
||
/* 失能通过所有多播PM */
|
||
reg_val &= ~FGMAC_FRAME_FILTER_PM;
|
||
|
||
/* 失能目的地址反向过滤DAIF */
|
||
reg_val &= ~FGMAC_FRAME_FILTER_DAIF;
|
||
|
||
/* 失能哈希单播PR */
|
||
reg_val &= ~FGMAC_FRAME_FILTER_PR;
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_FRAME_FILTER_OFFSET, reg_val);
|
||
|
||
/********hash reg*********/
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_HASH_HIGH_OFFSET, 0x0);
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_HASH_LOW_OFFSET, 0x0);
|
||
|
||
/********gmac flow ctrl reg init*********/
|
||
|
||
/* Set the PT bit according to ETH PauseTime value */
|
||
/* Set the DZPQ bit according to ETH ZeroQuantaPause value */
|
||
/* Set the PLT bit according to ETH PauseLowThreshold value */
|
||
/* Set the UP bit according to ETH UnicastPauseFrameDetect value */
|
||
/* Set the RFE bit according to ETH ReceiveFlowControl value */
|
||
/* Set the TFE bit according to ETH TransmitFlowControl value */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_FLOW_CTRL_OFFSET);
|
||
/* 禁用自动零暂停帧生成DZPQ */
|
||
reg_val |= FGMAC_FLOW_DZPQ;
|
||
|
||
/* 暂停低阈值PLT */
|
||
reg_val |= FGMAC_FLOW_PLT(0);
|
||
|
||
/* 禁用接收流控制RFE */
|
||
reg_val &= ~FGMAC_FLOW_RFE;
|
||
|
||
/* 禁用传输流控制TFE */
|
||
reg_val &= ~FGMAC_FLOW_TFE;
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_FLOW_CTRL_OFFSET, reg_val);
|
||
|
||
/********vlan tag reg*********/
|
||
/* Set the ETV bit according to ETH VLANTagComparison value */
|
||
/* Set the VL bit according to ETH VLANTagIdentifier value */
|
||
/* 接收帧的 VLAN 标记标识符 VL */
|
||
reg_val = FGMAC_VLAN_TAG_VL(0);
|
||
/* 设置VLAN 标记比较的位数ETV 1-12bit 0-16bit */
|
||
reg_val &= ~FGMAC_VLAN_TAG_ETV;
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_VLAN_TAG_OFFSET, reg_val);
|
||
|
||
return ret;
|
||
}
|
||
|
||
static FError FGmacDmaConfigure(FGmac *instance_p)
|
||
{
|
||
FASSERT(instance_p);
|
||
u32 reg_val;
|
||
FError ret = FGMAC_SUCCESS;
|
||
uintptr base_addr = instance_p->config.base_addr;
|
||
|
||
/********DMA总线模式寄存器*********/
|
||
/* Set the AAL bit according to ETH AddressAlignedBeats value */
|
||
/* Set the FB bit according to ETH FixedBurst value */
|
||
/* Set the RPBL and 4*PBL bits according to ETH RxDMABurstLength value */
|
||
/* Set the PBL and 4*PBL bits according to ETH TxDMABurstLength value */
|
||
/* Set the Enhanced DMA descriptors bit according to ETH EnhancedDescriptorFormat value*/
|
||
/* Set the DSL bit according to ETH DesciptorSkipLength value */
|
||
/* Set the PR and DA bits according to ETH DMAArbitration value */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_DMA_BUS_MODE_OFFSET);
|
||
reg_val |= FGMAC_DMA_BUS_AAL;
|
||
/* 使用单独的 PBL USP */
|
||
reg_val |= FGMAC_DMA_BUS_USP;
|
||
/* RxDMA PBL RPBL */
|
||
reg_val |= FGMAC_DMA_BUS_RPBL(32);
|
||
|
||
/* 固定突发 FB */
|
||
reg_val |= FGMAC_DMA_BUS_FB;
|
||
|
||
/* 控制 RxDMA 和 TxDMA 之间的加权循环仲裁中的优先级比率 PR */
|
||
reg_val |= FGMAC_DMA_BUS_PR(0);
|
||
|
||
/* 可编程突发长度 PBL */
|
||
reg_val |= FGMAC_DMA_BUS_PBL(32);
|
||
|
||
/* 交替描述表大小 ATDS */
|
||
reg_val |= FGMAC_DMA_BUS_ATDS;
|
||
|
||
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_DMA_BUS_MODE_OFFSET, reg_val);
|
||
|
||
/* dma set bus mode */
|
||
// FGMAC_WRITE_REG32(base_addr, FGMAC_DMA_BUS_MODE_OFFSET, FGMAC_DMA_BUS_INIT);
|
||
|
||
/********DMA操作模式寄存器*********/
|
||
/* Set the DT bit according to ETH DropTCPIPChecksumErrorFrame value */
|
||
/* Set the RSF bit according to ETH ReceiveStoreForward value */
|
||
/* Set the DFF bit according to ETH FlushReceivedFrame value */
|
||
/* Set the TSF bit according to ETH TransmitStoreForward value */
|
||
/* Set the TTC bit according to ETH TransmitThresholdControl value */
|
||
/* Set the FEF bit according to ETH ForwardErrorFrames value */
|
||
/* Set the FUF bit according to ETH ForwardUndersizedGoodFrames value */
|
||
/* Set the RTC bit according to ETH ReceiveThresholdControl value */
|
||
/* Set the OSF bit according to ETH SecondFrameOperate value */
|
||
reg_val = FGMAC_READ_REG32(base_addr, FGMAC_DMA_OP_OFFSET);
|
||
reg_val &= FGMAC_DMA_OP_CLEAR_MASK;
|
||
/* 丢弃 TCP / IP 校验和错误帧 DT */
|
||
reg_val &= ~FGMAC_DMA_OP_DT;
|
||
|
||
/* 接收存储转发 RSF */
|
||
reg_val |= FGMAC_DMA_OP_RSF;
|
||
|
||
/* 刷新正在接收的帧 DFF */
|
||
reg_val &= ~FGMAC_DMA_OP_DFF;
|
||
|
||
/* 发送存储和转发 TSF */
|
||
reg_val |= FGMAC_DMA_OP_TSF;
|
||
|
||
/* 传输阈值控制 TTC */
|
||
reg_val |= FGMAC_DMA_OP_TTC(7);
|
||
|
||
/* 在第二帧上操作 OSF */
|
||
reg_val |= FGMAC_DMA_OP_OSF;
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_DMA_OP_OFFSET, reg_val);
|
||
|
||
/* 刷新DMA发送FIFO FTF */
|
||
ret = FGmacFlushTxFifo(base_addr, FGMAC_RETRY_TIMES);
|
||
|
||
if (FGMAC_SUCCESS != ret)
|
||
{
|
||
FGMAC_ERROR("Gmac flush failed.");
|
||
}
|
||
|
||
/* AXI 突发长度 BLEN 16,8,4 */
|
||
reg_val = (FGMAC_DMA_AXI_BUS_MOD_BLEN16 | FGMAC_DMA_AXI_BUS_MOD_BLEN8 | FGMAC_DMA_AXI_BUS_MOD_BLEN4);
|
||
FGMAC_WRITE_REG32(base_addr, FGMAC_DMA_AXI_BUS_MOD_OFFSET, reg_val);
|
||
|
||
return ret;
|
||
}
|