print-cfm.c

来自「TCPDUMP的C语言源代码,是在数据链路层的应用」· C语言 代码 · 共 642 行 · 第 1/2 页

C
642
字号
           CFM_EXTRACT_VERSION(cfm_common_header->mdlevel_version),           tok2str(cfm_opcode_values, "unknown (%u)", cfm_common_header->opcode),           CFM_EXTRACT_MD_LEVEL(cfm_common_header->mdlevel_version),           length);    /*     * In non-verbose mode just print the opcode and md-level.     */    if (vflag < 1) {        return;    }    printf("\n\tFirst TLV offset %u", cfm_common_header->first_tlv_offset);    tptr += sizeof(const struct cfm_common_header_t);    tlen = length - sizeof(struct cfm_common_header_t);    switch (cfm_common_header->opcode) {    case CFM_OPCODE_CCM:        msg_ptr.cfm_ccm = (const struct cfm_ccm_t *)tptr;        ccm_interval = CFM_EXTRACT_CCM_INTERVAL(cfm_common_header->flags);        printf(", Flags [CCM Interval %u%s]",               ccm_interval,               cfm_common_header->flags & CFM_CCM_RDI_FLAG ?               ", RDI" : "");        /*         * Resolve the CCM interval field.         */        if (ccm_interval) {            printf("\n\t  CCM Interval %.3fs"                   ", min CCM Lifetime %.3fs, max CCM Lifetime %.3fs",                   ccm_interval_base[ccm_interval],                   ccm_interval_base[ccm_interval] * CCM_INTERVAL_MIN_MULTIPLIER,                   ccm_interval_base[ccm_interval] * CCM_INTERVAL_MAX_MULTIPLIER);        }        printf("\n\t  Sequence Number 0x%08x, MA-End-Point-ID 0x%04x",               EXTRACT_32BITS(msg_ptr.cfm_ccm->sequence),               EXTRACT_16BITS(msg_ptr.cfm_ccm->ma_epi));        /*         * Resolve the MD fields.         */        printf("\n\t  MD Name Format %s (%u), MD Name length %u",               tok2str(cfm_md_nameformat_values, "Unknown",                       msg_ptr.cfm_ccm->md_nameformat),               msg_ptr.cfm_ccm->md_nameformat,               msg_ptr.cfm_ccm->md_namelength);        if (msg_ptr.cfm_ccm->md_nameformat != CFM_CCM_MD_FORMAT_NONE) {            printf("\n\t  MD Name: ");            switch (msg_ptr.cfm_ccm->md_nameformat) {            case CFM_CCM_MD_FORMAT_DNS:            case CFM_CCM_MD_FORMAT_CHAR:                safeputs((const char *)msg_ptr.cfm_ccm->md_name, msg_ptr.cfm_ccm->md_namelength);                break;            case CFM_CCM_MD_FORMAT_MAC:                printf("\n\t  MAC %s", etheraddr_string(                           msg_ptr.cfm_ccm->md_name));                break;                /* FIXME add printers for those MD formats - hexdump for now */            case CFM_CCM_MA_FORMAT_8021:            default:                print_unknown_data(msg_ptr.cfm_ccm->md_name, "\n\t    ",                                   msg_ptr.cfm_ccm->md_namelength);            }        }        /*         * Resolve the MA fields.         */        ma_nameformat = msg_ptr.cfm_ccm->md_name + msg_ptr.cfm_ccm->md_namelength;        ma_namelength = msg_ptr.cfm_ccm->md_name + msg_ptr.cfm_ccm->md_namelength + 1;        ma_name = msg_ptr.cfm_ccm->md_name + msg_ptr.cfm_ccm->md_namelength + 2;        printf("\n\t  MA Name-Format %s (%u), MA name length %u",               tok2str(cfm_ma_nameformat_values, "Unknown",                       *ma_nameformat),               *ma_nameformat,               *ma_namelength);                printf("\n\t  MA Name: ");        switch (*ma_nameformat) {        case CFM_CCM_MA_FORMAT_CHAR:            safeputs((const char *)ma_name, *ma_namelength);            break;            /* FIXME add printers for those MA formats - hexdump for now */        case CFM_CCM_MA_FORMAT_8021:        case CFM_CCM_MA_FORMAT_VID:        case CFM_CCM_MA_FORMAT_INT:        case CFM_CCM_MA_FORMAT_VPN:        default:            print_unknown_data(ma_name, "\n\t    ", *ma_namelength);        }        break;    case CFM_OPCODE_LTM:        printf(", Flags [%s]",               bittok2str(cfm_ltm_flag_values, "none",  cfm_common_header->flags));        printf("\n\t  Transaction-ID 0x%08x, Egress-ID %s, ttl %u",               EXTRACT_32BITS(msg_ptr.cfm_ltm->transaction_id),               cfm_egress_id_string(msg_ptr.cfm_ltm->egress_id),               msg_ptr.cfm_ltm->ttl);        printf("\n\t  Original-MAC %s, Target-MAC %s",               etheraddr_string(msg_ptr.cfm_ltm->original_mac),               etheraddr_string(msg_ptr.cfm_ltm->target_mac));        break;    case CFM_OPCODE_LTR:        printf(", Flags [%s]",               bittok2str(cfm_ltr_flag_values, "none",  cfm_common_header->flags));        printf("\n\t  Transaction-ID 0x%08x, Last-Egress-ID %s",               EXTRACT_32BITS(msg_ptr.cfm_ltr->transaction_id),               cfm_egress_id_string(msg_ptr.cfm_ltr->last_egress_id));        printf("\n\t  Next-Egress-ID %s, ttl %u",               cfm_egress_id_string(msg_ptr.cfm_ltr->next_egress_id),               msg_ptr.cfm_ltr->ttl);        printf("\n\t  Replay-Action %s (%u)",               tok2str(cfm_ltr_replay_action_values,                       "Unknown",                       msg_ptr.cfm_ltr->replay_action),               msg_ptr.cfm_ltr->replay_action);        break;        /*         * No message decoder yet.         * Hexdump everything up until the start of the TLVs         */    case CFM_OPCODE_LBR:    case CFM_OPCODE_LBM:    default:        if (tlen > cfm_common_header->first_tlv_offset) {            print_unknown_data(tptr, "\n\t  ",                               tlen -  cfm_common_header->first_tlv_offset);        }        break;    }    /*     * Sanity check for not walking off.     */    if (tlen <= cfm_common_header->first_tlv_offset) {        return;    }    tptr += cfm_common_header->first_tlv_offset;    tlen -= cfm_common_header->first_tlv_offset;        while (tlen > 0) {        cfm_tlv_header = (const struct cfm_tlv_header_t *)tptr;        /* Enough to read the tlv type ? */        TCHECK2(*tptr, 1);        cfm_tlv_type=cfm_tlv_header->type;        if (cfm_tlv_type != CFM_TLV_END) {            /* did we capture enough for fully decoding the object header ? */            TCHECK2(*tptr, sizeof(struct cfm_tlv_header_t));                        cfm_tlv_len=EXTRACT_16BITS(&cfm_tlv_header->length);        } else {            cfm_tlv_len = 0;        }        printf("\n\t%s TLV (0x%02x), length %u",               tok2str(cfm_tlv_values, "Unknown", cfm_tlv_type),               cfm_tlv_type,               cfm_tlv_len);        /* sanity check for not walking off and infinite loop check. */        if ((cfm_tlv_type != CFM_TLV_END) &&            ((cfm_tlv_len + sizeof(struct cfm_tlv_header_t) > tlen) ||             (!cfm_tlv_len))) {            print_unknown_data(tptr,"\n\t  ",tlen);            return;        }        tptr += sizeof(struct cfm_tlv_header_t);        tlen -= sizeof(struct cfm_tlv_header_t);        tlv_ptr = tptr;        /* did we capture enough for fully decoding the object ? */        if (cfm_tlv_type != CFM_TLV_END) {            TCHECK2(*tptr, cfm_tlv_len);        }        hexdump = FALSE;        switch(cfm_tlv_type) {        case CFM_TLV_END:            /* we are done - bail out */            return;        case CFM_TLV_PORT_STATUS:            printf(", Status: %s (%u)",                   tok2str(cfm_tlv_port_status_values, "Unknown", *tptr),                   *tptr);            break;        case CFM_TLV_INTERFACE_STATUS:            printf(", Status: %s (%u)",                   tok2str(cfm_tlv_interface_status_values, "Unknown", *tptr),                   *tptr);            break;        case CFM_TLV_PRIVATE:            printf(", Vendor: %s (%u), Sub-Type %u",                   tok2str(oui_values,"Unknown", EXTRACT_24BITS(tptr)),                   EXTRACT_24BITS(tptr),                   *(tptr+3));            hexdump = TRUE;            break;        case CFM_TLV_SENDER_ID:        {            u_int chassis_id_type, chassis_id_length;            u_int mgmt_addr_length;            /*             * Check if there is a Chassis-ID.             */            chassis_id_length = *tptr;            if (chassis_id_length > tlen) {                hexdump = TRUE;                break;            }            tptr++;            tlen--;            if (chassis_id_length) {                chassis_id_type = *tptr;                printf("\n\t  Chassis-ID Type %s (%u), Chassis-ID length %u",                       tok2str(cfm_tlv_senderid_chassisid_values,                               "Unknown",                               chassis_id_type),                       chassis_id_type,                       chassis_id_length);                switch (chassis_id_type) {                case CFM_CHASSIS_ID_MAC_ADDRESS:                    printf("\n\t  MAC %s", etheraddr_string(tptr+1));                    break;                case CFM_CHASSIS_ID_NETWORK_ADDRESS:                    hexdump |= cfm_mgmt_addr_print(tptr);                    break;                case CFM_CHASSIS_ID_INTERFACE_NAME: /* fall through */                case CFM_CHASSIS_ID_INTERFACE_ALIAS:                case CFM_CHASSIS_ID_LOCAL:                case CFM_CHASSIS_ID_CHASSIS_COMPONENT:                case CFM_CHASSIS_ID_PORT_COMPONENT:                    safeputs((const char *)tptr+1, chassis_id_length);                    break;                default:                    hexdump = TRUE;                    break;                }            }            tptr += chassis_id_length;            tlen -= chassis_id_length;            /*             * Check if there is a Management Address.             */            mgmt_addr_length = *tptr;            if (mgmt_addr_length > tlen) {                hexdump = TRUE;                break;            }            tptr++;            tlen--;            if (mgmt_addr_length) {                hexdump |= cfm_mgmt_addr_print(tptr);            }            tptr += mgmt_addr_length;            tlen -= mgmt_addr_length;        }        break;            /*             * FIXME those are the defined TLVs that lack a decoder             * you are welcome to contribute code ;-)             */        case CFM_TLV_DATA:        case CFM_TLV_REPLY_INGRESS:        case CFM_TLV_REPLY_EGRESS:        default:            hexdump = TRUE;            break;        }        /* do we want to see an additional hexdump ? */        if (hexdump || vflag > 1)            print_unknown_data(tlv_ptr, "\n\t  ", cfm_tlv_len);        tptr+=cfm_tlv_len;        tlen-=cfm_tlv_len;    }    return;trunc:    printf("\n\t\t packet exceeded snapshot");}

⌨️ 快捷键说明

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