📄 ospf_te.c
字号:
ospf_lsa_header_dump (new->data); } rc = 0;out: return rc;}static intospf_mpls_te_lsa_originate (void *arg){ struct ospf_area *area = (struct ospf_area *) arg; listnode node; struct mpls_te_link *lp; int rc = -1; if (OspfMplsTE.status == disabled) { zlog_info ("ospf_mpls_te_lsa_originate: MPLS-TE is disabled now."); rc = 0; /* This is not an error case. */ goto out; } for (node = listhead (OspfMplsTE.iflist); node; nextnode (node)) { if ((lp = getdata (node)) == NULL) continue; if (lp->area == NULL) continue; if (! IPV4_ADDR_SAME (&lp->area->area_id, &area->area_id)) continue; if (lp->flags & LPFLG_LSA_ENGAGED) { if (lp->flags & LPFLG_LSA_FORCED_REFRESH) { lp->flags &= ~LPFLG_LSA_FORCED_REFRESH; ospf_mpls_te_lsa_schedule (lp, REFRESH_THIS_LSA); } continue; } if (! is_mandated_params_set (lp)) { zlog_warn ("ospf_mpls_te_lsa_originate: Link(%s) lacks some mandated MPLS-TE parameters.", lp->ifp ? lp->ifp->name : "?"); continue; } /* Ok, let's try to originate an LSA for this area and Link. */ if (ospf_mpls_te_lsa_originate1 (area, lp) != 0) goto out; } rc = 0;out: return rc;}static voidospf_mpls_te_lsa_refresh (struct ospf_lsa *lsa){ struct mpls_te_link *lp; struct ospf_area *area = lsa->area; struct ospf_lsa *new = NULL; if (OspfMplsTE.status == disabled) { /* * This LSA must have flushed before due to MPLS-TE status change. * It seems a slip among routers in the routing domain. */ zlog_info ("ospf_mpls_te_lsa_refresh: MPLS-TE is disabled now."); lsa->data->ls_age = htons (OSPF_LSA_MAXAGE); /* Flush it anyway. */ } /* At first, resolve lsa/lp relationship. */ if ((lp = lookup_linkparams_by_instance (lsa)) == NULL) { zlog_warn ("ospf_mpls_te_lsa_refresh: Invalid parameter?"); lsa->data->ls_age = htons (OSPF_LSA_MAXAGE); /* Flush it anyway. */ } /* If the lsa's age reached to MaxAge, start flushing procedure. */ if (IS_LSA_MAXAGE (lsa)) { lp->flags &= ~LPFLG_LSA_ENGAGED; ospf_opaque_lsa_flush_schedule (lsa); goto out; } /* Create new Opaque-LSA/MPLS-TE instance. */ if ((new = ospf_mpls_te_lsa_new (area, lp)) == NULL) { zlog_warn ("ospf_mpls_te_lsa_refresh: ospf_mpls_te_lsa_new() ?"); goto out; } new->data->ls_seqnum = lsa_seqnum_increment (lsa); /* Install this LSA into LSDB. */ /* Given "lsa" will be freed in the next function. */ if (ospf_lsa_install (area->ospf, NULL/*oi*/, new) == NULL) { zlog_warn ("ospf_mpls_te_lsa_refresh: ospf_lsa_install() ?"); ospf_lsa_free (new); goto out; } /* Flood updated LSA through area. */ ospf_flood_through_area (area, NULL/*nbr*/, new); /* Debug logging. */ if (IS_DEBUG_OSPF (lsa, LSA_GENERATE)) { zlog_info ("LSA[Type%d:%s]: Refresh Opaque-LSA/MPLS-TE", new->data->type, inet_ntoa (new->data->id)); ospf_lsa_header_dump (new->data); }out: return;}static voidospf_mpls_te_lsa_schedule (struct mpls_te_link *lp, enum sched_opcode opcode){ struct ospf_lsa lsa; struct lsa_header lsah; u_int32_t tmp; memset (&lsa, 0, sizeof (lsa)); memset (&lsah, 0, sizeof (lsah)); lsa.area = lp->area; lsa.data = &lsah; lsah.type = OSPF_OPAQUE_AREA_LSA; tmp = SET_OPAQUE_LSID (OPAQUE_TYPE_TRAFFIC_ENGINEERING_LSA, lp->instance); lsah.id.s_addr = htonl (tmp); switch (opcode) { case REORIGINATE_PER_AREA: ospf_opaque_lsa_reoriginate_schedule ((void *) lp->area, OSPF_OPAQUE_AREA_LSA, OPAQUE_TYPE_TRAFFIC_ENGINEERING_LSA); break; case REFRESH_THIS_LSA: ospf_opaque_lsa_refresh_schedule (&lsa); break; case FLUSH_THIS_LSA: lp->flags &= ~LPFLG_LSA_ENGAGED; ospf_opaque_lsa_flush_schedule (&lsa); break; default: zlog_warn ("ospf_mpls_te_lsa_schedule: Unknown opcode (%u)", opcode); break; } return;}/*------------------------------------------------------------------------* * Followings are vty session control functions. *------------------------------------------------------------------------*/static u_int16_tshow_vty_router_addr (struct vty *vty, struct te_tlv_header *tlvh){ struct te_tlv_router_addr *top = (struct te_tlv_router_addr *) tlvh; if (vty != NULL) vty_out (vty, " Router-Address: %s%s", inet_ntoa (top->value), VTY_NEWLINE); else zlog_info (" Router-Address: %s", inet_ntoa (top->value)); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_header (struct vty *vty, struct te_tlv_header *tlvh){ struct te_tlv_link *top = (struct te_tlv_link *) tlvh; if (vty != NULL) vty_out (vty, " Link: %u octets of data%s", ntohs (top->header.length), VTY_NEWLINE); else zlog_info (" Link: %u octets of data", ntohs (top->header.length)); return TLV_HDR_SIZE; /* Here is special, not "TLV_SIZE". */}static u_int16_tshow_vty_link_subtlv_link_type (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_link_type *top; const char *cp = "Unknown"; top = (struct te_link_subtlv_link_type *) tlvh; switch (top->link_type.value) { case LINK_TYPE_SUBTLV_VALUE_PTP: cp = "Point-to-point"; break; case LINK_TYPE_SUBTLV_VALUE_MA: cp = "Multiaccess"; break; default: break; } if (vty != NULL) vty_out (vty, " Link-Type: %s (%u)%s", cp, top->link_type.value, VTY_NEWLINE); else zlog_info (" Link-Type: %s (%u)", cp, top->link_type.value); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_link_id (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_link_id *top; top = (struct te_link_subtlv_link_id *) tlvh; if (vty != NULL) vty_out (vty, " Link-ID: %s%s", inet_ntoa (top->value), VTY_NEWLINE); else zlog_info (" Link-ID: %s", inet_ntoa (top->value)); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_lclif_ipaddr (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_lclif_ipaddr *top; int i, n; top = (struct te_link_subtlv_lclif_ipaddr *) tlvh; n = ntohs (tlvh->length) / sizeof (top->value[0]); if (vty != NULL) vty_out (vty, " Local Interface IP Address(es): %d%s", n, VTY_NEWLINE); else zlog_info (" Local Interface IP Address(es): %d", n); for (i = 0; i < n; i++) { if (vty != NULL) vty_out (vty, " #%d: %s%s", i, inet_ntoa (top->value[i]), VTY_NEWLINE); else zlog_info (" #%d: %s", i, inet_ntoa (top->value[i])); } return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_rmtif_ipaddr (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_rmtif_ipaddr *top; int i, n; top = (struct te_link_subtlv_rmtif_ipaddr *) tlvh; n = ntohs (tlvh->length) / sizeof (top->value[0]); if (vty != NULL) vty_out (vty, " Remote Interface IP Address(es): %d%s", n, VTY_NEWLINE); else zlog_info (" Remote Interface IP Address(es): %d", n); for (i = 0; i < n; i++) { if (vty != NULL) vty_out (vty, " #%d: %s%s", i, inet_ntoa (top->value[i]), VTY_NEWLINE); else zlog_info (" #%d: %s", i, inet_ntoa (top->value[i])); } return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_te_metric (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_te_metric *top; top = (struct te_link_subtlv_te_metric *) tlvh; if (vty != NULL) vty_out (vty, " Traffic Engineering Metric: %u%s", (u_int32_t) ntohl (top->value), VTY_NEWLINE); else zlog_info (" Traffic Engineering Metric: %u", (u_int32_t) ntohl (top->value)); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_max_bw (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_max_bw *top; float fval; top = (struct te_link_subtlv_max_bw *) tlvh; ntohf (&top->value, &fval); if (vty != NULL) vty_out (vty, " Maximum Bandwidth: %g (Bytes/sec)%s", fval, VTY_NEWLINE); else zlog_info (" Maximum Bandwidth: %g (Bytes/sec)", fval); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_max_rsv_bw (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_max_rsv_bw *top; float fval; top = (struct te_link_subtlv_max_rsv_bw *) tlvh; ntohf (&top->value, &fval); if (vty != NULL) vty_out (vty, " Maximum Reservable Bandwidth: %g (Bytes/sec)%s", fval, VTY_NEWLINE); else zlog_info (" Maximum Reservable Bandwidth: %g (Bytes/sec)", fval); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_unrsv_bw (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_unrsv_bw *top; float fval; int i; top = (struct te_link_subtlv_unrsv_bw *) tlvh; for (i = 0; i < 8; i++) { ntohf (&top->value[i], &fval); if (vty != NULL) vty_out (vty, " Unreserved Bandwidth (pri %d): %g (Bytes/sec)%s", i, fval, VTY_NEWLINE); else zlog_info (" Unreserved Bandwidth (pri %d): %g (Bytes/sec)", i, fval); } return TLV_SIZE (tlvh);}static u_int16_tshow_vty_link_subtlv_rsc_clsclr (struct vty *vty, struct te_tlv_header *tlvh){ struct te_link_subtlv_rsc_clsclr *top; top = (struct te_link_subtlv_rsc_clsclr *) tlvh; if (vty != NULL) vty_out (vty, " Resource class/color: 0x%x%s", (u_int32_t) ntohl (top->value), VTY_NEWLINE); else zlog_info (" Resource Class/Color: 0x%x", (u_int32_t) ntohl (top->value)); return TLV_SIZE (tlvh);}static u_int16_tshow_vty_unknown_tlv (struct vty *vty, struct te_tlv_header *tlvh){ if (vty != NULL) vty_out (vty, " Unknown TLV: [type(0x%x), length(0x%x)]%s", ntohs (tlvh->type), ntohs (tlvh->length), VTY_NEWLINE); else zlog_info (" Unknown TLV: [type(0x%x), length(0x%x)]", ntohs (tlvh->type), ntohs (tlvh->length)); return TLV_SIZE (tlvh);}static u_int16_tospf_mpls_te_show_link_subtlv (struct vty *vty, struct te_tlv_header *tlvh0, u_int16_t subtotal, u_int16_t total){ struct te_tlv_header *tlvh, *next; u_int16_t sum = subtotal; for (tlvh = tlvh0; sum < total; tlvh = (next ? next : TLV_HDR_NEXT (tlvh))) { next = NULL; switch (ntohs (tlvh->type)) { case TE_LINK_SUBTLV_LINK_TYPE: sum += show_vty_link_subtlv_link_type (vty, tlvh); break; case TE_LINK_SUBTLV_LINK_ID: sum += show_vty_link_subtlv_link_id (vty, tlvh); break; case TE_LINK_SUBTLV_LCLIF_IPADDR: sum += show_vty_link_subtlv_lclif_ipaddr (vty, tlvh); break; case TE_LINK_SUBTLV_RMTIF_IPADDR: sum += show_vty_link_subtlv_rmtif_ipaddr (vty, tlvh); break; case TE_LINK_SUBTLV_TE_METRIC: sum += show_vty_link_subtlv_te_metric (vty, tlvh); break; case TE_LINK_SUBTLV_MAX_BW: sum += show_vty_link_subtlv_max_bw (vty, tlvh); break; case TE_LINK_SUBTLV_MAX_RSV_BW: sum += show_vty_link_subtlv_max_rsv_bw (vty, tlvh); break; case TE_LINK_SUBTLV_UNRSV_BW: sum += show_vty_link_subtlv_unrsv_bw (vty, tlvh); break; case TE_LINK_SUBTLV_RSC_CLSCLR: sum += show_vty_link_subtlv_rsc_clsclr (vty, tlvh); break; default: sum += show_vty_unknown_tlv (vty, tlvh); break; } } return sum;}static voidospf_mpls_te_show_info (struct vty *vty, struct ospf_lsa *lsa){ struct lsa_header *lsah = (struct lsa_header *) lsa->data; struct te_tlv_header *tlvh, *next; u_int16_t sum, total; u_int16_t (* subfunc)(struct vty *vty, struct te_tlv_header *tlvh, u_int16_t subtotal, u_int16_t total) = NULL; sum = 0; total = ntohs (lsah->length) - OSPF_LSA_HEADER_SIZE; for (tlvh = TLV_HDR_TOP (lsah); sum < total; tlvh = (next ? next : TLV_HDR_NEXT (tlvh))) { if (subfunc != NULL) { sum = (* subfunc)(vty, tlvh, sum, total); next = (struct te_tlv_header *)((char *) tlvh + sum); subfunc = NULL; continue; } next = NULL; switch (ntohs (tlvh->type)) { case TE_TLV_ROUTER_ADDR: sum += show_vty_router_addr (vty, tlvh); break; case TE_TLV_LINK: sum += show_vty_link_header (vty, tlvh); subfunc = ospf_mpls_te_show_link_subtlv; next = tlvh + 1; break; default: sum += show_vty_unknown_tlv (vty, tlvh); break; } } return;}static voidospf_mpls_te_config_write_router (struct vty *vty){ if (OspfMplsTE.status == enabled) { vty_out (vty, " mpls-te%s", VTY_NEWLINE); vty_out (vty, " mpls-te router-address %s%s", inet_ntoa (OspfMplsTE.router_addr.value), VTY_NEWLINE); } return;}static voidospf_mpls_te_config_write_if (struct vty *vty, struct interface *ifp){ struct mpls_te_link *lp; if ((OspfMplsTE.status == enabled) && (! if_is_loopback (ifp) && if_is_up (ifp) && ospf_oi_count (ifp) > 0) && ((lp = lookup_linkparams_by_ifp (ifp)) != NULL)) { float fval;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -