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

📄 net_icmp.c

📁 ucos的tcpip协议占
💻 C
📖 第 1 页 / 共 5 页
字号:
*                                                               --- RETURNED BY NetICMP_TxPktDiscard() : ---
*                               NET_ERR_TX                      Transmit error; packet discarded.
*
* Return(s)   : none.
*
* Caller(s)   : various.
*
*               This function is an INTERNAL network protocol suite function & MUST NOT be called by 
*               application function(s).
*
* Note(s)     : (2) NetICMP_TxMsgErr() blocked until network initialization completes; perform NO action.
*
*               (3) (a) The following IP header fields MUST be decoded &/or converted from network-order to host-
*                       order BEFORE any ICMP Error Messages are transmitted (see 'net_ip.c  NetIP_RxPktValidate()
*                       Note #3') :
*
*                       (1) Header Length                           
*                       (2) Total  Length
*                       (3) Source      Address
*                       (4) Destination Address
*
*                   (b) The following IP header fields were NOT previously decoded &/or converted from network-
*                       order to host-order & are NOT available :
*
*                       (1) IP Data Length
*
*               (4) Default case already invalidated in NetICMP_TxMsgErrValidate().  However, the default 
*                   case is included as an extra precaution in case 'type' is incorrectly modified.
*
*               (5) Assumes network buffer's protocol header size is large enough to accomodate ICMP header
*                   size (see 'net_buf.h  NETWORK BUFFER INDEX & SIZE DEFINES  Note #1').
*$PAGE*
*               (6) Some buffer controls were previously initialized in NetBuf_Get() when the buffer
*                   was allocated earlier in this function.  These buffer controls do NOT need to be
*                   re-initialized but are shown for completeness.
*
*               (7) (a) ICMP message Check-Sum MUST be calculated AFTER the entire ICMP message has been
*                       prepared.  In addition, ALL multi-octet words are converted from host-order to 
*                       network-order since "the sum of 16-bit integers can be computed in either byte 
*                       order" [RFC #1071, Section 2.(B)].
*
*                   (b) ICMP message Check-Sum field MUST be cleared to '0' BEFORE the ICMP message Check-Sum
*                       is calculated (see RFC #792, Sections 'Destination Unreachable Message : Checksum',
*                       'Time Exceeded Message : Checksum', 'Source Quench Message : Checksum', & 'Parameter
*                       Problem Message : Checksum').
*
*                   (c) The ICMP message Check-Sum field is returned in network-order & MUST NOT be re-converted 
*                       back to host-order (see 'net_util.c  NetUtil_16BitOnesCplChkSumHdrCalc()  Note #3b').
*
*               (8) Network buffer already freed by lower layer; only increment error counter.
*
*               (9) #### 'perr' may NOT be necessary (remove if unnecessary).
*********************************************************************************************************
*/

void  NetICMP_TxMsgErr (NET_BUF     *pbuf,
                        CPU_INT08U   type,
                        CPU_INT08U   code,
                        CPU_INT08U   ptr,
                        NET_ERR     *perr)
{
#if (((NET_CTR_CFG_STAT_EN     == DEF_ENABLED)                    || \
      (NET_CTR_CFG_ERR_EN      == DEF_ENABLED))                   && \
      (CPU_CFG_CRITICAL_METHOD == CPU_CRITICAL_METHOD_STATUS_LOCAL))
    CPU_SR                    cpu_sr;
#endif
    NET_BUF_HDR              *pbuf_hdr;
    NET_IP_HDR               *pip_hdr;
    NET_BUF                  *pmsg_err;
    NET_BUF_HDR              *pmsg_err_hdr;
    NET_ICMP_HDR_ERR         *picmp_hdr_err;
    NET_ICMP_HDR_PARAM_PROB  *picmp_hdr_param_prob;
    CPU_INT16U                msg_size_hdr;
    CPU_INT16U                msg_size_data_ip;
    CPU_INT16U                msg_size_data;
    CPU_INT16U                msg_size_tot;
    CPU_INT16U                msg_ix;
    CPU_INT16U                msg_ix_data;
    CPU_INT16U                msg_chk_sum;
    NET_ERR                   err;


#if (NET_ERR_CFG_ARG_CHK_EXT_EN == DEF_ENABLED)
    if (Net_InitDone != DEF_YES) {                              /* If init NOT complete, exit tx (see Note #2).         */
       *perr = NET_ERR_INIT_INCOMPLETE;
        return;
    }
#endif


#if (NET_ERR_CFG_ARG_CHK_DBG_EN == DEF_ENABLED)
                                                                /* ------------------- VALIDATE PTR ------------------- */
    if (pbuf == (NET_BUF *)0) {
        NetICMP_TxPktDiscard((NET_BUF *)0, perr);
        NET_CTR_ERR_INC(NetICMP_ErrNullPtrCtr);
        return;
    }
#endif



                                                                /* ------------- VALIDATE ICMP TX ERR MSG ------------- */
    pbuf_hdr = &pbuf->Hdr;
#if (NET_ERR_CFG_ARG_CHK_DBG_EN == DEF_ENABLED)
    if (pbuf_hdr->IP_HdrIx == NET_BUF_IX_NONE) {
        NetICMP_TxPktDiscard((NET_BUF *)0, perr);
        NET_CTR_ERR_INC(NetICMP_ErrRxInvalidBufIxCtr);
        return;
    }
#endif
    pip_hdr = (NET_IP_HDR *)&pbuf->Data[pbuf_hdr->IP_HdrIx];


    NetICMP_TxMsgErrValidate(pbuf, pbuf_hdr, pip_hdr, type, code, ptr, &err);

    if (err != NET_ICMP_ERR_NONE) {
        NetICMP_TxPktDiscard((NET_BUF *)0, perr);
        return;
    }


/*$PAGE*/
                                                                /* --------------- GET ICMP ERR MSG BUF --------------- */
                                                                /* Calc err msg buf size.                               */
    switch (type) {
        case NET_ICMP_MSG_TYPE_DEST_UNREACH:
             msg_size_hdr = NET_ICMP_HDR_SIZE_DEST_UNREACH;
             break;


        case NET_ICMP_MSG_TYPE_SRC_QUENCH:
             msg_size_hdr = NET_ICMP_HDR_SIZE_SRC_QUENCH;
             break;


        case NET_ICMP_MSG_TYPE_TIME_EXCEED:
             msg_size_hdr = NET_ICMP_HDR_SIZE_TIME_EXCEED;
             break;


        case NET_ICMP_MSG_TYPE_PARAM_PROB:
             msg_size_hdr = NET_ICMP_HDR_SIZE_PARAM_PROB;
             break;


        default:                                                /* See Note #4.                                         */
             NetICMP_TxPktDiscard((NET_BUF *)0, perr);
             return;                                            /* Prevent 'break NOT reachable' compiler warning.      */
    }


    if (pbuf_hdr->IP_TotLen >= pbuf_hdr->IP_HdrLen) {                       /* If IP tot len > IP hdr len &      ...    */
        msg_size_data_ip = pbuf_hdr->IP_TotLen - pbuf_hdr->IP_HdrLen;       /* Calc IP data len (see Note #3b1).        */
        if (msg_size_data_ip >= NET_ICMP_MSG_ERR_DATA_SIZE_MIN_OCTETS) {    /* ... ip data >= min ICMP data len, ...    */
                                                                            /* ... get max ICMP err msg len.            */
            msg_size_data = pbuf_hdr->IP_HdrLen + NET_ICMP_MSG_ERR_DATA_SIZE_MIN_OCTETS; 
        } else {                                                            /* Else get max IP tot len.                 */
            msg_size_data = pbuf_hdr->IP_TotLen;
        }
    } else {                                                                /* Else get max IP tot len.                 */
        msg_size_data = pbuf_hdr->IP_TotLen;
    }

    msg_size_tot = msg_size_hdr + msg_size_data;


#if (NET_ERR_CFG_ARG_CHK_DBG_EN == DEF_ENABLED)
    if (NET_BUF_DATA_TX_IX < msg_size_hdr) {                    /* See Note #5.                                         */
        NetICMP_TxPktDiscard((NET_BUF *)0, perr);
        NET_CTR_ERR_INC(NetICMP_ErrTxInvalidBufIxCtr);
        return;
    }
#endif
    msg_ix   = NET_BUF_DATA_TX_IX - msg_size_hdr;


    pmsg_err = NetBuf_Get((NET_BUF_SIZE) msg_size_tot,          /* Get err msg buf.                                     */
                          (NET_BUF_SIZE) msg_ix,
                          (CPU_INT16U  ) NET_BUF_FLAG_NONE,
                          (NET_ERR    *)&err);
    if (err != NET_BUF_ERR_NONE) {
        NetICMP_TxPktDiscard(pmsg_err, perr);
        return;
    }


    msg_ix_data = msg_ix + msg_size_hdr;
    NetBuf_DataWr((NET_BUF    *) pmsg_err,                      /* Copy rx'd IP hdr & data into ICMP err tx buf.        */
                  (NET_BUF_SIZE) msg_ix_data,
                  (NET_BUF_SIZE) msg_size_data,
                  (CPU_INT08U *) pip_hdr,
                  (NET_ERR    *)&err);
    if (err != NET_BUF_ERR_NONE) {
        NetICMP_TxPktDiscard(pmsg_err, perr);
        return;
    }

                                                                /* Init err msg buf ctrls.                              */
    pmsg_err_hdr                  = &pmsg_err->Hdr;
    pmsg_err_hdr->ICMP_MsgIx      = (CPU_INT16U  )msg_ix;
    pmsg_err_hdr->ICMP_MsgLen     = (CPU_INT16U  )msg_size_tot;
    pmsg_err_hdr->ICMP_HdrLen     = (CPU_INT16U  )msg_size_hdr;
    pmsg_err_hdr->TotLen          = (NET_BUF_SIZE)pmsg_err_hdr->ICMP_MsgLen;
    pmsg_err_hdr->ProtocolHdrType =  NET_PROTOCOL_TYPE_ICMP;
#if 0                                                           /* Init'd in NetBuf_Get() [see Note #6].                */
    pmsg_err_hdr->DataIx          =  NET_BUF_IX_NONE;
    pmsg_err_hdr->DataLen         =  0;
#endif



/*$PAGE*/
                                                                /* --------------- PREPARE ICMP ERR MSG --------------- */
    switch (type) {
        case NET_ICMP_MSG_TYPE_DEST_UNREACH:
        case NET_ICMP_MSG_TYPE_SRC_QUENCH:
        case NET_ICMP_MSG_TYPE_TIME_EXCEED:
             picmp_hdr_err       = (NET_ICMP_HDR_ERR *)&pmsg_err->Data[pmsg_err_hdr->ICMP_MsgIx];
             picmp_hdr_err->Type =  type;
             picmp_hdr_err->Code =  code;
                                                                            /* Clr unused octets.                       */
             Mem_Clr((void     *)picmp_hdr_err->Unused,
                     (CPU_SIZE_T)NET_ICMP_HDR_NBR_OCTETS_UNUSED);
                                                                            /* Calc ICMP msg chk sum (see Note #7).     */
             NET_UTIL_VAL_SET_NET_16(&picmp_hdr_err->ChkSum, 0x0000);       /* Clr           chk sum (see Note #7b).    */
             msg_chk_sum = NetUtil_16BitOnesCplChkSumHdrCalc((void     *) picmp_hdr_err,
                                                             (CPU_INT16U) pmsg_err_hdr->ICMP_MsgLen,
                                                             (NET_ERR  *)&err);
             NET_UTIL_VAL_COPY_16(&picmp_hdr_err->ChkSum, &msg_chk_sum);    /* Copy chk sum in net order (see Note #7c).*/
             break;


        case NET_ICMP_MSG_TYPE_PARAM_PROB:
             picmp_hdr_param_prob       = (NET_ICMP_HDR_PARAM_PROB *)&pmsg_err->Data[pmsg_err_hdr->ICMP_MsgIx];
             picmp_hdr_param_prob->Type =  type;
             picmp_hdr_param_prob->Code =  code;
             picmp_hdr_param_prob->Ptr  =  ptr;
                                                                            /* Clr unused octets.                       */
             Mem_Clr((void     *)picmp_hdr_param_prob->Unused,
                     (CPU_SIZE_T)NET_ICMP_HDR_NBR_OCTETS_UNUSED_PARAM_PROB);
                                                                            /* Calc ICMP msg chk sum (see Note #7).     */
             NET_UTIL_VAL_SET_NET_16(&picmp_hdr_param_prob->ChkSum, 0x0000);/* Clr           chk sum (see Note #7b).    */
             msg_chk_sum = NetUtil_16BitOnesCplChkSumHdrCalc((void     *) picmp_hdr_param_prob,
                                                             (CPU_INT16U) pmsg_err_hdr->ICMP_MsgLen,
                                                             (NET_ERR  *)&err);
                                                                            /* Copy chk sum in net order (see Note #7c).*/
             NET_UTIL_VAL_COPY_16(&picmp_hdr_param_prob->ChkSum, &msg_chk_sum);
             break;


        default:                                                /* See Note #4.                                         */
             NetICMP_TxPktDiscard(pmsg_err, perr);
             return;                                            /* Prevent 'break NOT reachable' compiler warning.      */
    }

    if (err != NET_UTIL_ERR_NONE) {                             /* Chk err from NetUtil_16BitOnesCplChkSumHdrCalc().    */
        NetICMP_TxPktDiscard(pmsg_err, perr);
        return;
    }



                                                                /* ----------------- TX ICMP ERR MSG ------------------ */
    NetIP_Tx((NET_BUF   *)pmsg_err,
             (NET_IP_ADDR)pbuf_hdr->IP_AddrDest,
             (NET_IP_ADDR)pbuf_hdr->IP_AddrSrc,
             (NET_IP_TOS )NET_IP_TOS_DFLT,                      /* See Note #1da.                                       */
             (NET_IP_TTL )NET_IP_TTL_DFLT,
             (CPU_INT16U )NET_IP_FLAG_NONE,
             (void      *)0,
             (NET_ERR   *)perr);



                                                                /* ------- FREE ICMP ERR MSG / UPDATE TX STATS -------- */
    switch (*perr) {
        case NET_IP_ERR_NONE:
             NetICMP_TxPktFree(pmsg_err);
             NET_CTR_STAT_INC(NetICMP_StatTxMsgCtr);
             NET_CTR_STAT_INC(NetICMP_StatTxMsgErrCtr);
             break;


        case NET_ERR_INIT_INCOMPLETE:
        case NET_ERR_TX:
             NET_CTR_ERR_INC(NetICMP_ErrTxPktDiscardedCtr);     /* See Note #8.                                         */
             return;                                            /* Prevent 'break NOT reachable' compiler warning.      */
        
                       

⌨️ 快捷键说明

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