⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ns8390x.c

📁 基于psos操作系统的ns8390驱动源码
💻 C
📖 第 1 页 / 共 5 页
字号:
/* Mask interrupts                                                     */
/*---------------------------------------------------------------------*/
iLevel = splhigh();

dev_num = hdrPtr->dev_num;
/*---------------------------------------------------------------------*/
/* Link returned envelope to the envelope previously at the top of the */
/* free queue and point "free_head" to the newly returned envelope.    */
/*---------------------------------------------------------------------*/
hdrPtr->next  = RxLstFreeHead[dev_num];
RxLstFreeHead[dev_num] = hdrPtr;
RxLstFreeCount[dev_num]++;

/*---------------------------------------------------------------------*/
/* Unmask interrupts                                                   */
/*---------------------------------------------------------------------*/
splx(iLevel);

if (RxLstFreeCount[dev_num] == (RxLowWaterMark[dev_num] + 1))
    return (NI_RX_ABOVE_LOW_WATERMARK | (lan_intfs[dev_num].if_num << 16));
else
    return (0);
}

/***********************************************************************/
/* RxPktRcv: Accept good packets and set up copying of data.           */
/*                                                                     */
/* INPUTS:  long dev_num   = Device number                             */
/* OUTPUTS: None                                                       */
/*                                                                     */
/***********************************************************************/
STATIC void RxPktRcv(long dev_num)
{
LAN_RXPKT_LIST *rcvHdrPtr;
ULONG           iLevel;
ULONG           rxing_page, next_page, this_page;
ULONG           tmp = 0;


for (;;)
    {
    /*-----------------------------------------------------------------*/
    /* Disable Interrupts                                              */
    /*-----------------------------------------------------------------*/
    iLevel = splhigh();

    if (!((tmp = rdStNicReg(dev_num, LAN_PG0_RSR, LAN_PAGE0)) & LAN_PG0_RSR_PRXS))
       {
       if (tmp & LAN_PG0_RSR_FO)
          {
          G_stat[dev_num].r_orun++;
          RxOflow(dev_num);
          }
       else
          G_stat[dev_num].r_other++;
          
       splx(iLevel);
       return;
       }

    /*-----------------------------------------------------------------*/
    /* Get the boundary page and current page                          */
    /*-----------------------------------------------------------------*/
    rxing_page = rdStNicReg(dev_num, LAN_PG1_CURR, LAN_PAGE1);
    this_page = rdStNicReg(dev_num, LAN_PG0_BNRY, LAN_PAGE0) + 1;

    if (this_page >= LAN_RXSTOP)
       this_page = LAN_RXSTART;

    /*-----------------------------------------------------------------*/
    /* If the boundary ptr equals the current ptr break.               */
    /*-----------------------------------------------------------------*/
    if (this_page == rxing_page)
       {
       splx (iLevel);
       return;
       }
    RxPktPagePtr[dev_num] = this_page; /* current page */

    /*-----------------------------------------------------------------*/
    /* Allocate a header from the RxFreeHdr list. If there a no        */
    /* headers available get out of the loop.                          */
    /*-----------------------------------------------------------------*/
    if (RxLstFreeHead[dev_num] != NULL)
       {
       rcvHdrPtr     = RxLstFreeHead[dev_num];
       RxLstFreeHead[dev_num] = RxLstFreeHead[dev_num]->next;
       RxLstFreeCount[dev_num]--;

       /*--------------------------------------------------------------*/
       /* Read four bytes from the boundary pointer                    */
       /*--------------------------------------------------------------*/
       remDmaSetup(dev_num, (RxPktPagePtr[dev_num] << 8) + 0, 4, REMOTE_READ);
       remDmaDo(dev_num, (UCHAR *) &(rcvHdrPtr->bufStat), 4, REMOTE_READ);

       /*--------------------------------------------------------------*/
       /* Per packet initialization.                                   */
       /*--------------------------------------------------------------*/
       rcvHdrPtr->dataLen = (rcvHdrPtr->bufStat.sizeLsb
                          + ((USHORT)(rcvHdrPtr->bufStat.sizeMsb) << 8));
       rcvHdrPtr->pageNum = RxPktPagePtr[dev_num];

       /*--------------------------------------------------------------*/
       /* Check if this nextPage value is not bogus                    */
       /*--------------------------------------------------------------*/
       next_page = rcvHdrPtr->pageNum + 1 + (rcvHdrPtr->dataLen >> 8);

       /*--------------------------------------------------------------*/
       /* Advance Page Pointer                                         */
       /*--------------------------------------------------------------*/
       RxPktPagePtr[dev_num] = rcvHdrPtr->bufStat.nextPage;

       /*--------------------------------------------------------------*/
       /* Determine if this packet is okay.                            */
       /* Packets with CRC & Frame alignment errors  & runt errors are */
       /* rejected. See RCR setup in StNicInit()                       */
       /*--------------------------------------------------------------*/
       if ((rcvHdrPtr->bufStat.nextPage != next_page) &&
           (rcvHdrPtr->bufStat.nextPage != next_page + 1) &&
           (rcvHdrPtr->bufStat.nextPage != next_page - LAN_NUM_RXBUFFS) &&
           (rcvHdrPtr->bufStat.nextPage != next_page + 1 - LAN_NUM_RXBUFFS))
          {
          /*----------------------------------------------------------*/
          /* Update MIB stats                                         */
          /*----------------------------------------------------------*/
          G_stat[dev_num].r_oflo++;

          /*----------------------------------------------------------*/
          /* Free the header                                          */
          /*----------------------------------------------------------*/
          RxPktDetach(rcvHdrPtr);

          /*----------------------------------------------------------*/
          /* Reset current/boundary page                              */
          /*----------------------------------------------------------*/
          RxPktPagePtr[dev_num] = rxing_page;
          }
       else if (((rcvHdrPtr->bufStat.frameStat & (LAN_PG0_RSR_CRCE |
                                                  LAN_PG0_RSR_FAE  |
                                                  LAN_PG0_RSR_FO   |
                                                  LAN_PG0_RSR_MPA)) != 0)
                            || (rcvHdrPtr->dataLen > (BSP_LAN1_MTU + 18)))
          {
          UCHAR    frameStat = rcvHdrPtr->bufStat.frameStat;

          /*----------------------------------------------------------*/
          /* Update MIB stats                                         */
          /*----------------------------------------------------------*/
          if (frameStat & LAN_PG0_RSR_CRCE)
             G_stat[dev_num].r_crc++;
          else if (frameStat & LAN_PG0_RSR_FAE)
             G_stat[dev_num].r_fram++;
          else if (frameStat & LAN_PG0_RSR_FO)
             G_stat[dev_num].r_orun++;
          else if (frameStat & LAN_PG0_RSR_MPA)
             G_stat[dev_num].r_miss++;
          else
             G_stat[dev_num].r_too_long++;

          /*----------------------------------------------------------*/
          /* Free the header                                          */
          /*----------------------------------------------------------*/
          RxPktDetach(rcvHdrPtr);
          }
       else
          {
          /*-----------------------------------------------------------*/
          /* Copy buffer data to a header.                             */
          /*-----------------------------------------------------------*/
          RxCpyData(rcvHdrPtr);

          /*-----------------------------------------------------------*/
          /* Process the Packet                                        */
          /*-----------------------------------------------------------*/
          RxPktProc(rcvHdrPtr);
          }
       }
    else
       {
       /*--------------------------------------------------------------*/
       /* Increment missed frame count                                 */
       /*--------------------------------------------------------------*/
       G_stat[dev_num].r_nobufs++;
       splx(iLevel);
       break;
       }

    /*-----------------------------------------------------------------*/
    /* Update boundary page register in ST-NIC                         */
    /*-----------------------------------------------------------------*/
    if (RxPktPagePtr[dev_num] >= LAN_RXSTOP)
       RxPktPagePtr[dev_num] = LAN_RXSTART;
    wrStNicReg(dev_num, LAN_PG0_BNRY, (UCHAR)(RxPktPagePtr[dev_num] - 1),
                                      LAN_PAGE0);

    /*-----------------------------------------------------------------*/
    /* Enable Interrupts                                               */
    /*-----------------------------------------------------------------*/
    splx(iLevel);
    }
    return;
}

/***********************************************************************/
/* RxPktProc: Process received packets.                                */
/*                                                                     */
/* INPUTS:  rcvHdrPtr: Process this receive packet pointer             */
/* OUTPUTS: None                                                       */
/*                                                                     */
/***********************************************************************/
STATIC void RxPktProc(LAN_RXPKT_LIST *rcvHdrPtr)
{
mblk_t *msgBlk;
frtn_t  frtn;
ULONG   type;
long    dev_num;
long   (*Announce)();

/*---------------------------------------------------------------------*/
/* Set up the device number from the packet structure                  */
/*---------------------------------------------------------------------*/
dev_num = rcvHdrPtr->dev_num;

/*---------------------------------------------------------------------*/
/* Set up the packet address parameters                                */
/*---------------------------------------------------------------------*/
type = (ULONG)(ntohs(rcvHdrPtr->type));

/*---------------------------------------------------------------------*/
/* Collect stats for MIB on broadcast and unicast packets.             */
/*---------------------------------------------------------------------*/
if (rcvHdrPtr->daddr.ea_bytes[0] & 0x1)
   MG_stat[dev_num].innucastpkts++;
else
   MG_stat[dev_num].inucastpkts++;

/*---------------------------------------------------------------------*/
/* Check if type is IP, ARP, or RARP and update count of packets       */
/* received with unknown protocol.                                     */
/*---------------------------------------------------------------------*/
if ((type != LAN_IP) && (type != LAN_ARP) && (type != LAN_RARP))
   MG_stat[dev_num].inunknownprotos++;

/*---------------------------------------------------------------------*/
/* If the packet is acceptable, pass it to pNA+.  Otherwise, count the */
/* receive error and return envelope to the free queue.                */
/*---------------------------------------------------------------------*/
G_stat[dev_num].l_rcv++;
MG_stat[dev_num].inoctets           += rcvHdrPtr->dataLen;
rcvHdrPtr->dataLen -= 14;

frtn.free_arg  = (void *)     rcvHdrPtr;
frtn.free_func = (void (*)()) RxPktDetach;

Announce = lan_intfs[dev_num].if_announce;
if ((Announce != NULL) && ((msgBlk = 
           lan_intfs[dev_num].if_ni_funcs.esballoc((char *) rcvHdrPtr->pktbuf,
                                (int)rcvHdrPtr->dataLen, 0, &frtn)) != 0))
   {

   if (RxLstFreeCount[dev_num] <= RxLowWaterMark[dev_num]) {
      type |= NI_RX_LOW_WATERMARK_REACHED;
   }
 
   msgBlk->b_wptr += rcvHdrPtr->dataLen;
   (*Announce)(type, (char *) msgBlk, rcvHdrPtr->dataLen, 
                               lan_intfs[dev_num].if_num,
                               (char *) &(rcvHdrPtr->saddr),
                               (char *) &(rcvHdrPtr->daddr));
   }
else
   RxPktDetach(rcvHdrPtr);
}

/***********************************************************************/
/* RxCpyData: Copy data from receive buffers to a receive header       */
/*                                                                     */
/* INPUTS:  LAN_RXPKT_LIST *rcvHdrPtr = Address of Receive header      */
/* OUTPUTS: None                                                       */
/*                                                                     */
/***********************************************************************/
STATIC void RxCpyData(LAN_RXPKT_LIST *rcvHdrPtr)
{
register ULONG numBytes;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -