📄 net_nic.c
字号:
* Arguments : none
*********************************************************************************************************
*/
void NetNIC_IntClr (void)
{
AT91C_BASE_AIC->AIC_ICCR = 1 << AT91C_ID_EMAC; /* Clear the EMAC interrupts */
AT91C_BASE_AIC->AIC_EOICR = 0; /* Signal end of interrupt */
}
/*
*********************************************************************************************************
* EMAC_TxEn()
*
* Description : Enable AT91SAM7X256 EMAC Transmitter.
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : EMAC_Init().
*********************************************************************************************************
*/
static void EMAC_TxEn (void)
{
#if (CPU_CFG_CRITICAL_METHOD == CPU_CRITICAL_METHOD_STATUS_LOCAL)
CPU_SR cpu_sr;
#endif
CPU_CRITICAL_ENTER();
AT91C_BASE_EMAC->EMAC_NCR |= AT91C_EMAC_TE; /* Enable the transmitter */
CPU_CRITICAL_EXIT();
}
/*
*********************************************************************************************************
* EMAC_TxDis()
*
* Description : Disable AT91SAM7X256 EMAC Transmitter.
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : AT91SAM7X256_EMAC_Init().
*********************************************************************************************************
*/
static void EMAC_TxDis (void)
{
#if (CPU_CFG_CRITICAL_METHOD == CPU_CRITICAL_METHOD_STATUS_LOCAL)
CPU_SR cpu_sr;
#endif
CPU_CRITICAL_ENTER(); /* See 'AT91SAM7X256 REGISTERS Note #5b'. */
AT91C_BASE_EMAC->EMAC_NCR &= ~AT91C_EMAC_TE; /* Disable the transmitter */
CPU_CRITICAL_EXIT();
}
/*
*********************************************************************************************************
* EMAC_RxEn()
*
* Description : Enable AT91SAM7X256 EMAC Receiver.
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : AT91SAM7X256_EMAC_Init().
*********************************************************************************************************
*/
static void EMAC_RxEn (void)
{
#if (CPU_CFG_CRITICAL_METHOD == CPU_CRITICAL_METHOD_STATUS_LOCAL)
CPU_SR cpu_sr;
#endif
CPU_CRITICAL_ENTER(); /* See 'AT91SAM7X256 REGISTERS Note #5b'. */
AT91C_BASE_EMAC->EMAC_NCR |= AT91C_EMAC_RE;
CPU_CRITICAL_EXIT();
}
/*
*********************************************************************************************************
* EMAC_RxDis()
*
* Description : Disable AT91SAM7X256 EMAC Receiver.
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : AT91SAM7X256_EMAC_Init().
*********************************************************************************************************
*/
static void EMAC_RxDis (void)
{
#if (CPU_CFG_CRITICAL_METHOD == CPU_CRITICAL_METHOD_STATUS_LOCAL)
CPU_SR cpu_sr;
#endif
CPU_CRITICAL_ENTER(); /* See 'AT91SAM7X256 REGISTERS Note #5b'. */
AT91C_BASE_EMAC->EMAC_NCR &= ~AT91C_EMAC_RE;
CPU_CRITICAL_EXIT();
}
/*
*********************************************************************************************************
* NetNIC_ISR_Handler()
*
* Description : (1) Decode ISR & call appropriate ISR handler :
*
* (a) AT91SAM7X256 Receive Buffer Not Available ISR NetNIC_RxPktDiscard().
* (b) AT91SAM7X256 Receive ISR NetNIC_RxISR_Handler().
* (c) AT91SAM7X256 Transmit ISR NetNIC_TxISR_Handler().
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : This is an ISR
*
* Note(s) : (2) AT91SAM7X256 ISR MUST call NetNIC_ISR_Handler() & MUST be developer-implemented in
*
* \<Your Product Application>\net_isr*.*
*
* where
* <Your Product Application> directory path for Your Product's Application.
*
* (3) This function clears the interrupt source(s) on an external interrupt controller &, if
* ENABLED, MUST be developer-implemented in
*
* \<Your Product Application>\net_isr.c
*
* where
* <Your Product Application> directory path for Your Product's Application.
*
* (4) Interrupt flags are cleared automatically upon reading the EMAC_ISR register, however,
* the AIC 'end of interrupt' must be writen to before exiting the ISR handler.
*********************************************************************************************************
*/
void NetNIC_ISR_Handler (void)
{
CPU_INT32U ISR_Status;
CPU_INT32U RSR_Status;
CPU_INT32U TSR_Status;
AT91C_BASE_AIC->AIC_IVR = 0; /* Write the IVR, as required in Protection Mode */
/* Read the interrupt status register */
ISR_Status = AT91C_BASE_EMAC->EMAC_ISR; /* This read clears the bits in the ISR register */
ISR_Status = ISR_Status; /* Prevent compiler optimized removal of EMAC ISR read */
(void)ISR_Status;
/* Check for 'frame received' interrupt */
RSR_Status = AT91C_BASE_EMAC->EMAC_RSR; /* Read the Receive Status Register */
if ((RSR_Status & AT91C_EMAC_REC) == AT91C_EMAC_REC) { /* Check if we have recieved a frame */
NetNIC_RxISR_Handler(); /* Call the Rx Handler */
AT91C_BASE_EMAC->EMAC_RSR = AT91C_EMAC_REC; /* Clear the Receive Status Register REC bit */
}
/* Check for 'transmit complete' interrupt */
TSR_Status = AT91C_BASE_EMAC->EMAC_TSR; /* Read the Transmit Status Register */
if ((TSR_Status & AT91C_EMAC_COMP) == AT91C_EMAC_COMP) { /* Check if we have completed transmitting a frame */
AT91C_BASE_EMAC->EMAC_TSR = AT91C_EMAC_COMP; /* Clear the Transmit Status Register COMP bit */
NetNIC_TxISR_Handler(); /* Call the Tx Handler */
}
/* If a transmit buffer was read, clear the Used bit */
if ((TSR_Status & AT91C_EMAC_UBR) == AT91C_EMAC_UBR) { /* Check if 'Used Bit Read' is set */
AT91C_BASE_EMAC->EMAC_TSR = AT91C_EMAC_UBR; /* Clear 'Used Bit Read' */
}
if ((RSR_Status & (AT91C_EMAC_BNA | AT91C_EMAC_OVR)) > 0) { /* Clear all receiver errors if they have occured */
AT91C_BASE_EMAC->EMAC_RSR = (AT91C_EMAC_BNA | AT91C_EMAC_OVR);
NetNIC_RxISR_Handler(); /* If any error occured, we call NetNIC_RxISR_Handler() */
} /* to ensure that we havent missed any events */
NetNIC_IntClr(); /* Clr int ctrl'r AT91SAM7X256 int (see Note #3). */
}
/*
*********************************************************************************************************
* NetNIC_RxISR_Handler()
*
* Description : Signal Network Interface Receive Task that a receive packet is available.
*
* Argument(s) : none.
*
* Return(s) : none.
*
* Caller(s) : NetNIC_ISR_Handler().
*
* Note(s) : (1) NetNIC_ISR_Handler() decodes AT91SAM7X256 Receive ISR & calls NetNIC_RxISR_Handler().
*********************************************************************************************************
*/
static void NetNIC_RxISR_Handler (void)
{
CPU_INT16U n_new;
NET_ERR err;
n_new = NIC_GetNRdy() - NIC_RxNRdyCtr; /* Determine how many NEW packets have been received */
while (n_new > 0) {
NetOS_IF_RxTaskSignal(&err); /* Signal Net IF Rx Task of NIC rx pkt. */
switch (err) {
case NET_IF_ERR_NONE:
if (NIC_RxNRdyCtr < NIC_RX_N_BUFS) {
NIC_RxNRdyCtr++;
}
break;
case NET_IF_ERR_RX_Q_FULL:
case NET_IF_ERR_RX_Q_POST_FAIL:
default:
NetNIC_RxPktDiscard(0, &err); /* If any net drv signal err, discard rx pkt. */
break;
}
n_new--;
}
}
/*
*********************************************************************************************************
* NIC_GetNRdy()
*
* Description : Determines how many packets we are ready to be processed.
* This is determined by looping through the entire list of Rx Descriptors
* and counting the number of present EOF descriptors that are currently owned
* by software.
*
* Parameters : None.
*
* Returns : Number of NIC buffers that are ready to be processed by the stack.
*
* Notes : 1) In some situations, it is possible to have extra SOF descriptors. This
* can happen whenever an EMAC error occurs and cannot complete the write
* of additional descriptors into RAM. The EMAC will ONLY recover the last
* descriptor that it has attempted to utilize, however, it will not
* recover previous descriptors filled with frame data.
*********************************************************************************************************
*/
static CPU_INT16U NIC_GetNRdy (void)
{
CPU_INT16U n_rdy;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -