On 4/19/2016 10:28 AM, Donald Sharp wrote:
> I would prefer that we are rfc compliant as per default

+1 -- and I'll even go further:

IMO non compliance with requirement behavior of an RFC should be viewed
as a bug and fixed.  I'm fine having config support for 'non-standard'
modes of operation, but they shouldn't be default and be clearly be
labeled as likely to break interop (e.g., by introducing routing loops)
with standards complaint implementations.

Lou
> and then have a switch to turn it off if needed.
>
> donald
>
> On Tue, Apr 12, 2016 at 7:58 AM, Paul Jakma <[email protected]
> <mailto:[email protected]>> wrote:
>
>     * The current stub-router support in Quagga ospfd took the
>     "[max-metric
>       links] should not be used for transit traffic" part of RFC3137
>     seriously,
>       as that strict no-transit behavoiur is useful (and what the
>     implementor
>       was after).  However, it seems that wording was not intended to
>     change
>       any standards specified behaviour.
>
>       Quagga as a result has different behaviour to other
>     implementations in its
>       SPF when it encounters 0xffff metric links.  This can lead to
>     routing
>       loops in mixed environments.
>
>       This commit:
>
>       - Makes the SPF behaviour configurable with a
>
>           "compatible max-metric (infinite|follow)"
>
>         command.  The state of this setting is explicitly written out,
>     if the
>         ospfd config is written out.
>
>       - Allows the administrator to specify a "transit" flag to the
>     max-metric
>         command:
>
>           "max-metric router-lsa transit"
>
>         to explicitly specify the RFC2328/RFC3187 "discourage, but
>     transit is
>         still fine" behaviour the administator desires, and for the
>     stub-router
>         to try signal to other routers.
>
>         If this "transit" flag is set, then the router-LSA links are
>     advertised
>         with 0xfffe cost when stub-router is enabled, which should work
>         universally.
>
>         Note, this is separate from the 'max-metric router-lsa ...'
>     command to
>         enable stub-router advertisement.
>
>       - Additionally, sets the "Host" option bit in the Router-LSA if the
>         "transit" flag is not specified to the stub-router command.
>
>       This should allow a Quagga stub-router, at least, to signal its
>     intent
>       clearly:
>
>       - To RFC2328 routers and older Quagga routers, when it /may/
>     still be used
>         for transit.
>
>       - To all routers recognising the H-bit and to older Quagga
>     routers, when
>         it /should not/ be used for transit.
>
>       If and when the H-bit is widely recognised, and has been deployed in
>       Quagga for long enough, we may be able to change the SPF
>     behaviour default
>       to the standards behaviour of "follow".
>
>     * libospf.h: Add OSPF_OUTPUT_COST_DISCOURAGE for the 0xfffe cost.
>     * ospf_dump.c: Add the H bit.
>     * ospf_lsa.c: (ospf_link_cost) The Host-bit configuration controls
>     whether
>       we use infinite/0xffff or discourage/0xfffe cost for links for
>       stub-routers.
>       (ospf_router_lsa_new) Set H-bit when configured and stub-routed.
>     * ospf_spf.c: (ospf_spf_next) Recognise the H-bit.
>       Make the 0xffff link behaviour admin configurable.
>     * ospf_vty.c: (show_ip_ospf) display info on the new flags.
>       (ospf_compatible_max_metric_cmd) Set the SPF compatibility
>     behaviour for
>       maximum metric links.
>       (ospf_max_metric_router_lsa_transit_cmd) Configure whether to
>     advertise
>       transit capability or not, as/when stub-router support is in effect.
>       (config_write_stub_router) write the 2 new flags out.
>       (ospf_vty_init) install commands for new flags.
>     * ospfd.c: H-bit advertisement is configured by default as the
>     existing
>       behaviour.
>     * ospfd.h: Add H-bit option define. Add ospf instance config flags for
>       the SPF max-metric link behaviour, and h-bit/no-transit.
>     * ospfd.texi: Update the docs with the new commands.
>     ---
>      doc/ospfd.texi    | 137
>     ++++++++++++++++++++++++++++++++++++++++++------
>      lib/libospf.h     |   2 +
>      ospfd/ospf_dump.c |   3 +-
>      ospfd/ospf_lsa.c  |  12 ++++-
>      ospfd/ospf_spf.c  |  73 ++++++++++++++++++++++++--
>      ospfd/ospf_vty.c  | 153
>     ++++++++++++++++++++++++++++++++++++++++++++++++------
>      ospfd/ospfd.c     |   2 +
>      ospfd/ospfd.h     |   3 ++
>      8 files changed, 348 insertions(+), 37 deletions(-)
>
>     diff --git a/doc/ospfd.texi b/doc/ospfd.texi
>     index 86cabe4..b87cbce 100644
>     --- a/doc/ospfd.texi
>     +++ b/doc/ospfd.texi
>     @@ -129,6 +129,7 @@ advertise non-OSPF links into stub areas.
>
>      @deffn {OSPF Command} {timers throttle spf @var{delay}
>     @var{initial-holdtime} @var{max-holdtime}} {}
>      @deffnx {OSPF Command} {no timers throttle spf} {}
>     +@anchor{OSPF timers throttle spf}
>      This command sets the initial @var{delay}, the @var{initial-holdtime}
>      and the @var{maximum-holdtime} between when SPF is calculated and the
>      event which triggered the calculation. The times are specified in
>     @@ -172,23 +173,25 @@ releases.
>      @deffn {OSPF Command} {max-metric router-lsa
>     [on-startup|on-shutdown] <5-86400>} {}
>      @deffnx {OSPF Command} {max-metric router-lsa administrative} {}
>      @deffnx {OSPF Command} {no max-metric router-lsa
>     [on-startup|on-shutdown|administrative]} {}
>     -This enables @cite{RFC3137, OSPF Stub Router Advertisement} support,
>     -where the OSPF process describes its transit links in its
>     router-LSA as
>     -having infinite distance so that other routers will avoid calculating
>     -transit paths through the router while still being able to reach
>     -networks through the router.
>     +@anchor{OSPF stub-router}
>     +@anchor{max-metric router-lsa}
>
>     -This support may be enabled administratively (and indefinitely) or
>     -conditionally. Conditional enabling of max-metric router-lsas can be
>     -for a period of seconds after startup and/or for a period of seconds
>     -prior to shutdown.
>     +This enables @cite{RFC6987, OSPF Stub Router Advertisement}
>     support, where
>     +the OSPF process describes its transit links in its router-LSA as
>     having
>     +maximum distance so that other routers are discouraged from
>     calculating
>     +transit paths through the router, while still being able to reach
>     stub
>     +addresses of the router, and any attached stub networks.
>     +
>     +This support may be enabled administratively (and indefinitely)
>     with the
>     +@var{administrative} flag.  It may alternatively be enabled only
>     for a
>     +specified number of seconds after startup and/or before shutdown,
>     with
>     +@var{on-startup} and @var{on-shutdown}.
>
>      Enabling this for a period after startup allows OSPF to converge
>     fully
>     -first without affecting any existing routes used by other routers,
>     -while still allowing any connected stub links and/or redistributed
>     -routes to be reachable. Enabling this for a period of time in advance
>     -of shutdown allows the router to gracefully excuse itself from
>     the OSPF
>     -domain.
>     +first, minimising the impact on existing routes used by other
>     routers,
>     +while still allowing any connected stub links and/or
>     redistributed routes to
>     +be reachable.  Enabling this for a period of time in advance of
>     shutdown
>     +allows the router to gracefully excuse itself from the OSPF domain.
>
>      Enabling this feature administratively allows for administrative
>      intervention for whatever reason, for an indefinite period of time.
>     @@ -199,7 +202,111 @@ until manually deconfigured.
>
>      Configured state of this feature as well as current status, such
>     as the
>      number of second remaining till on-startup or on-shutdown ends,
>     can be
>     -viewed with the @ref{show ip ospf} command.
>     +viewed with the @command{show ip ospf} command, @xref{show ip ospf}.
>     +@end deffn
>     +
>     +@deffn {OSPF Command} {compatible max-metric (infinite|follow)} {}
>     +@deffnx {OSPF Command} {no compatible max-metric} {}
>     +
>     +This flag controls the behaviour of SPF, and how it treats links in
>     +Router-LSAs with the maximum possible metric value.  It toggles
>     between the
>     +@cite{RFC2328} specified behaviour, and a Quagga variation.
>     +
>     +When this flag is set to @var{follow}, then the standard RFC2328
>     behaviour
>     +applies.  The SPF calculation will take links with the maximum
>     value metric
>     +of 0xffff into consideration when calculating transit paths out
>     of remote
>     +routers.
>     +
>     +When this flag is set to @var{infinite}, then Quagga deviates
>     from RFC2328.
>     +The SPF transit tree calculation will treat link the 0xffff
>     maximum metric
>     +as an infinite cost.  Such links will not be considered for the
>     transit
>     +tree.  This only affects whether links @emph{out} of a remote
>     router will be
>     +used for transit - it does not affect the reachability to the
>     router itself,
>     +or to its stub addresses and networks.  The @var{infinite}
>     behaviour allows
>     +routers to advertise links as @emph{strictly} non-transit or
>     merely as
>     +discouraged, but available for transit.
>     +
>     +Newer Quagga implementations use and recognise the "Host" option
>     in the
>     +router-LSA.  @xref{max-metric router-lsa} and the @var{transit}
>     flag for to
>     +have control whether the H-bit is advertised.
>     +
>     +In networks with routers with mixed behaviour, if links are
>     advertised with
>     +the 0xffff maximum metric (e.g., through the @ref{OSPF stub-router}
>     +functionality) then routing loops may potentially occur.
>     +
>     +In networks where all routers recognise the "Host" option, then it is
>     +recommended to configure the RFC @var{follow} behaviour.
>     +
>     +In other networks, the appropriate behaviour to configure depends
>     on whether
>     +the administrator prefers stub-routers to be strictly not
>     available for
>     +transit or not, on whether the network is mixed, and the
>     consequences of
>     +routing loops.
>     +
>     +The default behaviour is @var{infinite}, for compatibility with
>     previous
>     +Quagga releases.  In older Quagga releases this behaviour is not
>     +configurable. The default may change from @var{infinite} to
>     @var{follow} in
>     +a future release, particularly if the "Host" router-LSA option gains
>     +widespread support.
>     +
>     +@end deffn
>     +
>     +@deffn {OSPF Command} {max-metric router-lsa transit} {}
>     +@deffnx {OSPF Command} {no max-metric router-lsa transit} {}
>     +
>     +This flag affects what is advertised when the router is in
>     stub-router mode
>     +(see @ref{OSPF stub-router}).  I.e., during the time when
>     stub-router is
>     +enabled administratively, or during the period after startup
>     and/or before
>     +shutdown where enabled to be active.  This flag affects whether
>     the router
>     +advertises that it is strictly not available for transit traffic
>     going
>     +through it; or whether such through going, transit traffic is
>     discouraged
>     +but still acceptable.
>     +
>     +The local stub addresses of the router (i.e. loopback, PtP and PtMP
>     +addresses) as well as stub broadcast networks (i.e. without any OSPF
>     +adjacencies) attached to the router should remain reachable
>     regardless of
>     +the setting of this flag, whether the router is advertising
>     itself as a
>     +stub-router or not.
>     +
>     +When this flag is set, then when the stub-router mode is active,
>     the router
>     +will try advertise to other routers that transit traffic through
>     this router
>     +is discouraged, but still allowed. With this flag, the
>     stub-router will:
>     +
>     +@itemize @bullet
>     +@item
>     +Advertise its transit links with high-cost (0xfffe) but not
>     maximum cost, to
>     +ensure other routers can include these links in their SPF
>     calculations.
>     +
>     +@item
>     +Leave the "Host" option in the advertised router-LSA @emph{unset} to
>     +indicate the stub-router's links are still available for transit.
>     +@end itemize
>     +
>     +When this flag is not set, the stub-router will try advertise to
>     other
>     +routers that links are strictly not available for transit.  With
>     this flag
>     +unset, the stub-router will:
>     +
>     +@itemize @bullet
>     +
>     +@item
>     +Advertise its transit links with the maximum possible metric, 0xffff,
>     +which some implementations (i.e., older Quagga and Quagga with
>     +@command{compatible max-metric infinite} set) will then not use
>     to calculate
>     +transit paths through.
>     +
>     +@item
>     +Set the "Host" option in its Router-LSA, which will cause all
>     +implementations that support this option to not calculate transit
>     paths
>     +through the local router.
>     +@end itemize
>     +
>     +See @cite{draft-ietf-ospf-ospfv2-hbit} for details on the OSPFv2
>     "Host"
>     +option.
>     +
>     +Note that this command does not make the router go into
>     stub-router mode.
>     +To enable stub-router mode, see the @command{max-metric router-lsa
>     +(administrative|on-shutdown|on-startup)} command, @ref{max-metric
>     +router-lsa}.
>     +
>      @end deffn
>
>      @deffn {OSPF Command} {auto-cost reference-bandwidth <1-4294967>} {}
>     diff --git a/lib/libospf.h b/lib/libospf.h
>     index 9265ca5..5890e03 100644
>     --- a/lib/libospf.h
>     +++ b/lib/libospf.h
>     @@ -63,6 +63,8 @@
>      /* OSPF interface default values. */
>      #define OSPF_OUTPUT_COST_DEFAULT           10
>      #define OSPF_OUTPUT_COST_INFINITE         UINT16_MAX
>     +#define OSPF_OUTPUT_COST_MAX               OSPF_OUTPUT_COST_INFINITE
>     +#define OSPF_OUTPUT_COST_DISCOURAGE        0xfffe
>      #define OSPF_ROUTER_DEAD_INTERVAL_DEFAULT  40
>      #define OSPF_ROUTER_DEAD_INTERVAL_MINIMAL   1
>      #define OSPF_HELLO_INTERVAL_DEFAULT        10
>     diff --git a/ospfd/ospf_dump.c b/ospfd/ospf_dump.c
>     index fb43210..03e208c 100644
>     --- a/ospfd/ospf_dump.c
>     +++ b/ospfd/ospf_dump.c
>     @@ -328,7 +328,8 @@ ospf_options_dump (u_char options)
>      {
>        static char buf[OSPF_OPTION_STR_MAXLEN];
>
>     -  snprintf (buf, OSPF_OPTION_STR_MAXLEN, "*|%s|%s|%s|%s|%s|%s|*",
>     +  snprintf (buf, OSPF_OPTION_STR_MAXLEN, "%s|%s|%s|%s|%s|%s|%s|*",
>     +            (options & OSPF_OPTION_H) ? "H" : "-",
>                 (options & OSPF_OPTION_O) ? "O" : "-",
>                 (options & OSPF_OPTION_DC) ? "DC" : "-",
>                 (options & OSPF_OPTION_EA) ? "EA" : "-",
>     diff --git a/ospfd/ospf_lsa.c b/ospfd/ospf_lsa.c
>     index 634bc43..79ad446 100644
>     --- a/ospfd/ospf_lsa.c
>     +++ b/ospfd/ospf_lsa.c
>     @@ -488,7 +488,8 @@ ospf_link_cost (struct ospf_interface *oi)
>        if (!CHECK_FLAG (oi->area->stub_router_state,
>     OSPF_AREA_IS_STUB_ROUTED))
>          return oi->output_cost;
>        else
>     -    return OSPF_OUTPUT_COST_INFINITE;
>     +    return CHECK_FLAG(oi->area->ospf->config,
>     OSPF_STUB_ROUTER_NO_TRANSIT)
>     +           ? OSPF_OUTPUT_COST_INFINITE : OSPF_OUTPUT_COST_DISCOURAGE;
>      }
>
>      /* Set a link information. */
>     @@ -836,7 +837,14 @@ ospf_router_lsa_new (struct ospf_area *area)
>        /* Create a stream for LSA. */
>        s = stream_new (OSPF_MAX_LSA_SIZE);
>        /* Set LSA common header fields. */
>     -  lsa_header_set (s, LSA_OPTIONS_GET (area) |
>     LSA_OPTIONS_NSSA_GET (area),
>     +  lsa_header_set (s,
>     +                  LSA_OPTIONS_GET (area)
>     +                  | LSA_OPTIONS_NSSA_GET (area)
>     +                  /* H-bit, specific to router-LSA. */
>     +                  | ((CHECK_FLAG (area->stub_router_state,
>     +                                 OSPF_AREA_IS_STUB_ROUTED)
>     +                      && CHECK_FLAG (ospf->config,
>     OSPF_STUB_ROUTER_NO_TRANSIT))
>     +                     ? OSPF_OPTION_H : 0),
>                       OSPF_ROUTER_LSA, ospf->router_id, ospf->router_id);
>
>        /* Set router-LSA body fields. */
>     diff --git a/ospfd/ospf_spf.c b/ospfd/ospf_spf.c
>     index 58a3992..6ae562c 100644
>     --- a/ospfd/ospf_spf.c
>     +++ b/ospfd/ospf_spf.c
>     @@ -812,6 +812,26 @@ ospf_spf_next (struct vertex *v, struct
>     ospf_area *area,
>                      v->type == OSPF_VERTEX_ROUTER ? "Router" : "Network",
>                      inet_ntoa(v->lsa->id));
>
>     +  /* draft-ietf-ospf-ospfv2-hbit-00:
>     +   *
>     +   * "If this is a router-LSA, and the H-bit of the router-LSA is
>     set, and
>     +   *  vertex V is not the root, then the router should not be
>     used for
>     +   *  transit and step (3) should be executed immediately.
>     +   */
>     +  if ((v != area->spf)
>     +      && CHECK_FLAG(v->lsa->options, OSPF_OPTION_H))
>     +    {
>     +      if (v->type != OSPF_VERTEX_ROUTER)
>     +        zlog_warn ("%s: %s has H-bit set, but is not a Router-LSA!",
>     +                   __func__, inet_ntoa(v->lsa->id));
>     +
>     +      if (IS_DEBUG_OSPF_EVENT)
>     +        zlog_debug ("%s: %s has H-bit set,"
>     +                    " not considering for SPF transit tree",
>     +                    __func__, inet_ntoa(v->lsa->id));
>     +      return;
>     +    }
>     +
>        p = ((u_char *) v->lsa) + OSPF_LSA_HEADER_SIZE + 4;
>        lim = ((u_char *) v->lsa) + ntohs (v->lsa->length);
>
>     @@ -837,11 +857,56 @@ ospf_spf_next (struct vertex *v, struct
>     ospf_area *area,
>                if ((type = l->m[0].type) == LSA_LINK_TYPE_STUB)
>                  continue;
>
>     -          /* Infinite distance links shouldn't be followed, except
>     -           * for local links (a stub-routed router still wants to
>     -           * calculate tree, so must follow its own links).
>     +          /* In concept, non-transit links / links out of a
>     stub-routed node
>     +           * shouldn't be followed /out/ of a node - except if
>     the node is
>     +           * the root (in which case, we're calculating initial
>     paths and
>     +           * not transiting the vertex; a stub-routed router
>     still wants to
>     +           * calculate a tree, so SPF with such as the root
>     should follow).
>     +           *
>     +           * Conformant OSPF doesn't have a way to signal transit
>     status of
>     +           * distinct links.  There is only a router-global bit
>     (R-bit in
>     +           * OSPFv3, and the proposed H-bit in v2 - see above). 
>     However,
>     +           * many prior Quagga implementations by default treat
>     0xffff cost
>     +           * links as OSPF_OUTPUT_COST_INFINITE and so will not
>     follow such
>     +           * links out of a non-root vertex, full stop.  (As did
>     original
>     +           * OSPF, prior to 1583).
>     +           *
>     +           * Other implementations treat 0xffff costs as just a
>     very high
>     +           * cost, OSPF_OUTPUT_COST_MAX, but will still include
>     them in the
>     +           * transit tree.
>     +           *
>     +           * Note that a cost of 0xfffe or lower works
>     universally to signal
>     +           * "use of this link is discouraged, but it is still
>     available to
>     +           * transit through".
>     +           *
>     +           * Mixed environments of the two behaviours can lead to
>     routing
>     +           * loops.  The balance of preference between risking
>     routing loops
>     +           * in mixed environments and being able to entirely
>     avoid transit
>     +           * through stub-routers will depend on the administrator.
>     +           *
>     +           * In some use-cases, the administrator may intend "no
>     transit
>     +           * stub-router" to really mean that, even at the risk
>     of loops;
>     +           * while in other cases they may prefer the relaxed
>     interpretation
>     +           * of "no transit".
>     +           *
>     +           * Therefore, this behaviour is configurable, via the OSPF
>     +           * instance OSPF_MAX_METRIC_LINK_FOLLOW config flag,
>     defaulting to
>     +           * the long-standing Quagga behaviour to not follow
>     0xfff links
>     +           * out for now.
>     +           *
>     +           * Note: this has no effect on stub networks attached
>     to the
>     +           * router, such as local loopback and PtP addresses,
>     and broadcast
>     +           * networks without any established OSPF adjacencies.
>     These should
>     +           * always be reachable, regardless.
>     +           *
>     +           * RFC3137/6987 apparently was actually meant to be a
>     no-op with
>     +           * regard to how OSPF is supposed to behave.  Where it
>     said that
>     +           * 0xffff links "should not be used for transit
>     traffic", that
>     +           * apparently should not have been taken to heart.
>                 */
>     -          if ((v != area->spf) && l->m[0].metric >=
>     OSPF_OUTPUT_COST_INFINITE)
>     +          if ((v != area->spf)
>     +              && !CHECK_FLAG(area->ospf->config,
>     OSPF_MAX_METRIC_LINK_FOLLOW)
>     +              && l->m[0].metric >= OSPF_OUTPUT_COST_INFINITE)
>                  continue;
>
>                /* (b) Otherwise, W is a transit vertex (router or transit
>     diff --git a/ospfd/ospf_vty.c b/ospfd/ospf_vty.c
>     index 14ae9a2..4c4f54e 100644
>     --- a/ospfd/ospf_vty.c
>     +++ b/ospfd/ospf_vty.c
>     @@ -2836,6 +2836,17 @@ DEFUN (show_ip_ospf,
>                CHECK_FLAG (ospf->config, OSPF_OPAQUE_CAPABLE) ?
>                 "enabled" : "disabled",
>                 VTY_NEWLINE);
>     +  vty_out (vty, " SPF treats max-metric links as:%s   %s%s",
>     +           VTY_NEWLINE,
>     +           CHECK_FLAG(ospf->config, OSPF_MAX_METRIC_LINK_FOLLOW)
>     +             ? "low preference but transit capable"
>     +             : "infinite cost and not transit capable (RFC
>     deviation)",
>     +           VTY_NEWLINE);
>     +  vty_out (vty,
>     +           " Transit status when stub-router is enabled:"
>     +           " %savailable for transit%s",
>     +           CHECK_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT)
>     ? "not " : "",
>     +           VTY_NEWLINE);
>
>        /* Show stub-router configuration */
>        if (ospf->stub_router_startup_time != OSPF_STUB_ROUTER_UNCONFIGURED
>     @@ -6385,12 +6396,108 @@ ALIAS (no_ip_ospf_mtu_ignore,
>            "OSPF interface commands\n"
>            "Disable mtu mismatch detection\n")
>
>     +#define OSPF_CMD_MAX_METRIC_STR \
>     +  "OSPF maximum / infinite-distance metric links\n"
>     +#define OSPF_CMD_MAX_METRIC_RLSA_STR \
>     +  "Advertise this router as a stub router in its router LSA\n"
>     +
>     +DEFUN (ospf_compatible_max_metric,
>     +       ospf_compatible_max_metric_cmd,
>     +       "compatible max-metric (infinite|follow)",
>     +       "OSPF compatibility list\n"
>     +       "Behaviour for " OSPF_CMD_MAX_METRIC_STR
>     +       "SPF treats max-cost links as infinite and not considered
>     when"
>     +         " examining LSAs for transit out of a router (RFC
>     deviation)\n"
>     +       "SPF treats max-cost links as lowest-preference links, "
>     +         "but still available for transit\n")
>     +{
>     +  struct ospf *ospf = vty->index;
>     +  switch (argv[0][0])
>     +    {
>     +      case 'i':
>     +        UNSET_FLAG (ospf->config, OSPF_MAX_METRIC_LINK_FOLLOW);
>     +        break;
>     +      case 'f':
>     +        SET_FLAG (ospf->config, OSPF_MAX_METRIC_LINK_FOLLOW);
>     +        break;
>     +      default:
>     +        vty_out (vty, "%% Unknown argument %s%s", argv[0],
>     VTY_NEWLINE);
>     +        return CMD_WARNING;
>     +    }
>     +  return CMD_SUCCESS;
>     +}
>     +
>     +DEFUN (no_ospf_compatible_max_metric,
>     +       no_ospf_compatible_max_metric_cmd,
>     +       "no compatible max-metric",
>     +       NO_STR
>     +       "OSPF compatibility list\n"
>     +       "Behaviour for " OSPF_CMD_MAX_METRIC_STR)
>     +{
>     +  struct ospf *ospf = vty->index;
>     +  UNSET_FLAG (ospf->config, OSPF_MAX_METRIC_LINK_FOLLOW);
>     +  return CMD_SUCCESS;
>     +}
>     +
>     +DEFUN (ospf_max_metric_router_lsa_transit,
>     +       ospf_max_metric_router_lsa_transit_cmd,
>     +       "max-metric router-lsa transit",
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>     +       "Advertise this router may still be transited through,"
>     +         " when stub-router advertisement is in effect\n")
>     +{
>     +  struct ospf *ospf = vty->index;
>     +  struct listnode *ln;
>     +  struct ospf_area *area;
>     +
>     +  if (!CHECK_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT))
>     +    return CMD_SUCCESS;
>     +  UNSET_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT);
>     +
>     +  for (ALL_LIST_ELEMENTS_RO (ospf->areas, ln, area))
>     +    {
>     +      if (CHECK_FLAG (area->stub_router_state,
>     OSPF_AREA_IS_STUB_ROUTED))
>     +          ospf_router_lsa_update_area (area);
>     +    }
>     +
>     +  return CMD_SUCCESS;
>     +}
>     +
>     +DEFUN (no_ospf_max_metric_router_lsa_transit,
>     +       no_ospf_max_metric_router_lsa_transit_cmd,
>     +       "no max-metric router-lsa transit",
>     +       NO_STR
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>     +       "Advertise this router may still be transited through,"
>     +         " when stub-router advertisement is in effect\n")
>     +{
>     +  struct ospf *ospf = vty->index;
>     +  struct listnode *ln;
>     +  struct ospf_area *area;
>     +
>     +  if (CHECK_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT))
>     +    return CMD_SUCCESS;
>     +
>     +  SET_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT);
>     +
>     +  for (ALL_LIST_ELEMENTS_RO (ospf->areas, ln, area))
>     +    {
>     +      if (CHECK_FLAG (area->stub_router_state,
>     OSPF_AREA_IS_STUB_ROUTED))
>     +          ospf_router_lsa_update_area (area);
>     +    }
>     +
>     +  return CMD_SUCCESS;
>     +}
>     +
>      DEFUN (ospf_max_metric_router_lsa_admin,
>             ospf_max_metric_router_lsa_admin_cmd,
>             "max-metric router-lsa administrative",
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     -       "Administratively applied, for an indefinite period\n")
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>     +       "Administratively enable stub-router advertisement,"
>     +         " for an indefinite period\n")
>      {
>        struct listnode *ln;
>        struct ospf_area *area;
>     @@ -6403,7 +6510,7 @@ DEFUN (ospf_max_metric_router_lsa_admin,
>            if (!CHECK_FLAG (area->stub_router_state,
>     OSPF_AREA_IS_STUB_ROUTED))
>                ospf_router_lsa_update_area (area);
>          }
>     -
>     +
>        /* Allows for areas configured later to get the property */
>        ospf->stub_router_admin_set = OSPF_STUB_ROUTER_ADMINISTRATIVE_SET;
>
>     @@ -6414,9 +6521,11 @@ DEFUN (no_ospf_max_metric_router_lsa_admin,
>             no_ospf_max_metric_router_lsa_admin_cmd,
>             "no max-metric router-lsa administrative",
>             NO_STR
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     -       "Administratively applied, for an indefinite period\n")
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>     +       "Administratively enable stub-router advertisement,"
>     +         " for an indefinite period\n")
>     +
>      {
>        struct listnode *ln;
>        struct ospf_area *area;
>     @@ -6435,14 +6544,15 @@ DEFUN (no_ospf_max_metric_router_lsa_admin,
>              }
>          }
>        ospf->stub_router_admin_set =
>     OSPF_STUB_ROUTER_ADMINISTRATIVE_UNSET;
>     +
>        return CMD_SUCCESS;
>      }
>
>      DEFUN (ospf_max_metric_router_lsa_startup,
>             ospf_max_metric_router_lsa_startup_cmd,
>             "max-metric router-lsa on-startup <5-86400>",
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>             "Automatically advertise stub Router-LSA on startup of OSPF\n"
>             "Time (seconds) to advertise self as stub-router\n")
>      {
>     @@ -6466,8 +6576,8 @@ DEFUN (no_ospf_max_metric_router_lsa_startup,
>             no_ospf_max_metric_router_lsa_startup_cmd,
>             "no max-metric router-lsa on-startup",
>             NO_STR
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>             "Automatically advertise stub Router-LSA on startup of
>     OSPF\n")
>      {
>        struct listnode *ln;
>     @@ -6494,8 +6604,8 @@ DEFUN (no_ospf_max_metric_router_lsa_startup,
>      DEFUN (ospf_max_metric_router_lsa_shutdown,
>             ospf_max_metric_router_lsa_shutdown_cmd,
>             "max-metric router-lsa on-shutdown <5-86400>",
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>             "Advertise stub-router prior to full shutdown of OSPF\n"
>             "Time (seconds) to wait till full shutdown\n")
>      {
>     @@ -6519,8 +6629,8 @@ DEFUN (no_ospf_max_metric_router_lsa_shutdown,
>             no_ospf_max_metric_router_lsa_shutdown_cmd,
>             "no max-metric router-lsa on-shutdown",
>             NO_STR
>     -       "OSPF maximum / infinite-distance metric\n"
>     -       "Advertise own Router-LSA with infinite distance (stub
>     router)\n"
>     +       OSPF_CMD_MAX_METRIC_STR
>     +       OSPF_CMD_MAX_METRIC_RLSA_STR
>             "Advertise stub-router prior to full shutdown of OSPF\n")
>      {
>        struct ospf *ospf = vty->index;
>     @@ -6536,6 +6646,15 @@ config_write_stub_router (struct vty *vty,
>     struct ospf *ospf)
>        struct listnode *ln;
>        struct ospf_area *area;
>
>     +  vty_out (vty, " compatible max-metric %s%s",
>     +           CHECK_FLAG (ospf->config, OSPF_MAX_METRIC_LINK_FOLLOW)
>     +             ? "follow" : "infinite",
>     +           VTY_NEWLINE);
>     +  if (CHECK_FLAG (ospf->config, OSPF_STUB_ROUTER_NO_TRANSIT))
>     +    vty_out (vty, " no max-metric router-lsa transit%s",
>     VTY_NEWLINE);
>     +  else
>     +    vty_out (vty, " max-metric router-lsa transit%s", VTY_NEWLINE);
>     +
>        if (ospf->stub_router_startup_time !=
>     OSPF_STUB_ROUTER_UNCONFIGURED)
>          vty_out (vty, " max-metric router-lsa on-startup %u%s",
>                   ospf->stub_router_startup_time, VTY_NEWLINE);
>     @@ -7845,6 +7964,10 @@ ospf_vty_init (void)
>        install_element (OSPF_NODE, &no_ospf_refresh_timer_cmd);
>
>        /* max-metric commands */
>     +  install_element (OSPF_NODE, &ospf_compatible_max_metric_cmd);
>     +  install_element (OSPF_NODE, &no_ospf_compatible_max_metric_cmd);
>     +  install_element (OSPF_NODE,
>     &ospf_max_metric_router_lsa_transit_cmd);
>     +  install_element (OSPF_NODE,
>     &no_ospf_max_metric_router_lsa_transit_cmd);
>        install_element (OSPF_NODE, &ospf_max_metric_router_lsa_admin_cmd);
>        install_element (OSPF_NODE,
>     &no_ospf_max_metric_router_lsa_admin_cmd);
>        install_element (OSPF_NODE,
>     &ospf_max_metric_router_lsa_startup_cmd);
>     diff --git a/ospfd/ospfd.c b/ospfd/ospfd.c
>     index c9fcdc3..e8d1117 100644
>     --- a/ospfd/ospfd.c
>     +++ b/ospfd/ospfd.c
>     @@ -191,6 +191,8 @@ ospf_new (void)
>        new->stub_router_startup_time = OSPF_STUB_ROUTER_UNCONFIGURED;
>        new->stub_router_shutdown_time = OSPF_STUB_ROUTER_UNCONFIGURED;
>        new->stub_router_admin_set     =
>     OSPF_STUB_ROUTER_ADMINISTRATIVE_UNSET;
>     +
>     +  SET_FLAG (new->config, OSPF_STUB_ROUTER_NO_TRANSIT);
>
>        /* Distribute parameter init. */
>        for (i = 0; i <= ZEBRA_ROUTE_MAX; i++)
>     diff --git a/ospfd/ospfd.h b/ospfd/ospfd.h
>     index 098fc5f..541539d 100644
>     --- a/ospfd/ospfd.h
>     +++ b/ospfd/ospfd.h
>     @@ -66,6 +66,7 @@
>      #define OSPF_OPTION_EA                   0x10
>      #define OSPF_OPTION_DC                   0x20
>      #define OSPF_OPTION_O                    0x40
>     +#define OSPF_OPTION_H                    0x80
>
>      /* OSPF Database Description flags. */
>      #define OSPF_DD_FLAG_MS                  0x01
>     @@ -130,6 +131,8 @@ struct ospf
>      #define OSPF_OPAQUE_CAPABLE            (1 << 2)
>      #define OSPF_LOG_ADJACENCY_CHANGES     (1 << 3)
>      #define OSPF_LOG_ADJACENCY_DETAIL      (1 << 4)
>     +#define OSPF_MAX_METRIC_LINK_FOLLOW    (1 << 5)
>     +#define OSPF_STUB_ROUTER_NO_TRANSIT     (1 << 6)
>
>        /* Opaque-LSA administrative flags. */
>        u_char opaque;
>     --
>     2.5.5
>
>
>     _______________________________________________
>     Quagga-dev mailing list
>     [email protected] <mailto:[email protected]>
>     https://lists.quagga.net/mailman/listinfo/quagga-dev
>
>
>
>
> _______________________________________________
> Quagga-dev mailing list
> [email protected]
> https://lists.quagga.net/mailman/listinfo/quagga-dev



_______________________________________________
Quagga-dev mailing list
[email protected]
https://lists.quagga.net/mailman/listinfo/quagga-dev

Reply via email to