On 2016 Sep 26 (Mon) at 20:09:13 +0200 (+0200), Peter Hessler wrote:
:We already have a local AS saved per peer.  Let's use it.  This is very
:useful when one needs to change their local AS.
:
:"
:neighbor 192.0.2.1 {
:       remote-as 65530
:       local-as 131000
:}
:"
:
:OK?
:

Updated!

Now it works far better, it supports "local-as 131000 65000", works
better with prepend-self.

You MUST use filters to protect yourself from receiving your own routes
over the local-as peer.  There be dragons and grues.

OK?


Index: bgpd.conf.5
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/bgpd.conf.5,v
retrieving revision 1.152
diff -u -p -u -p -r1.152 bgpd.conf.5
--- bgpd.conf.5 13 Jan 2017 18:59:12 -0000      1.152
+++ bgpd.conf.5 27 May 2017 09:04:28 -0000
@@ -874,6 +874,17 @@ is given,
 .Xr bgpd 8
 binds to this address first.
 .Pp
+.It Ic local-as Ar as-number Op Ar as-number
+Set the AS number sent to the remote system.
+If the first AS number is a 4-byte AS it is possible to specify a secondary
+2-byte AS number which is used for neighbors which do not support 4-byte AS
+numbers.
+The default for the secondary AS is 23456.
+.Pp
+This option is dangerous, and requires you to add filters to prevent
+receiving your global ASN from this peer.
+Intended to be used temporarily, for migrations to another AS.
+.Pp
 .It Ic log no
 Disable neighbor specific logging.
 .Pp
Index: parse.y
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/parse.y,v
retrieving revision 1.300
diff -u -p -u -p -r1.300 parse.y
--- parse.y     26 May 2017 14:08:51 -0000      1.300
+++ parse.y     27 May 2017 08:55:02 -0000
@@ -188,7 +188,7 @@ typedef struct {
 %token RDOMAIN RD EXPORTTRGT IMPORTTRGT
 %token RDE RIB EVALUATE IGNORE COMPARE
 %token GROUP NEIGHBOR NETWORK
-%token REMOTEAS DESCR LOCALADDR MULTIHOP PASSIVE MAXPREFIX RESTART
+%token LOCALAS REMOTEAS DESCR LOCALADDR MULTIHOP PASSIVE MAXPREFIX RESTART
 %token ANNOUNCE CAPABILITIES REFRESH AS4BYTE CONNECTRETRY
 %token DEMOTE ENFORCE NEIGHBORAS REFLECTOR DEPEND DOWN SOFTRECONFIG
 %token DUMP IN OUT SOCKET RESTRICTED
@@ -1038,6 +1038,17 @@ peeroptsl        : peeropts nl
 peeropts       : REMOTEAS as4number    {
                        curpeer->conf.remote_as = $2;
                }
+               | LOCALAS as4number     {
+                       curpeer->conf.local_as = $2;
+                       if ($2 > USHRT_MAX)
+                               curpeer->conf.local_short_as = AS_TRANS;
+                       else
+                               curpeer->conf.local_short_as = $2;
+               }
+               | LOCALAS as4number asnumber {
+                       curpeer->conf.local_as = $2;
+                       curpeer->conf.local_short_as = $3;
+               }
                | DESCR string          {
                        if (strlcpy(curpeer->conf.descr, $2,
                            sizeof(curpeer->conf.descr)) >=
@@ -2369,6 +2380,7 @@ lookup(char *s)
                { "large-community",    LARGECOMMUNITY},
                { "listen",             LISTEN},
                { "local-address",      LOCALADDR},
+               { "local-as",           LOCALAS},
                { "localpref",          LOCALPREF},
                { "log",                LOG},
                { "match",              MATCH},
Index: printconf.c
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/printconf.c,v
retrieving revision 1.100
diff -u -p -u -p -r1.100 printconf.c
--- printconf.c 24 Jan 2017 04:22:42 -0000      1.100
+++ printconf.c 26 May 2017 18:01:32 -0000
@@ -414,6 +414,8 @@ print_peer(struct peer_config *p, struct
                printf("%s\trib \"%s\"\n", c, p->rib);
        if (p->remote_as)
                printf("%s\tremote-as %s\n", c, log_as(p->remote_as));
+       if (p->local_as != conf->as)
+               printf("%s\tlocal-as %s\n", c, log_as(p->local_as));
        if (p->down)
                printf("%s\tdown\n", c);
        if (p->distance > 1)
Index: rde.c
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/rde.c,v
retrieving revision 1.361
diff -u -p -u -p -r1.361 rde.c
--- rde.c       25 Jan 2017 03:21:55 -0000      1.361
+++ rde.c       27 May 2017 08:26:56 -0000
@@ -1103,7 +1103,8 @@ rde_update_dispatch(struct imsg *imsg)
        p += 2 + attrpath_len;
 
        /* aspath needs to be loop free nota bene this is not a hard error */
-       if (peer->conf.ebgp && !aspath_loopfree(asp->aspath, conf->as))
+       if (peer->conf.ebgp &&
+           !aspath_loopfree(asp->aspath, peer->conf.local_as))
                asp->flags |= F_ATTR_LOOP;
 
        /* parse nlri prefix */
Index: rde_filter.c
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/rde_filter.c,v
retrieving revision 1.80
diff -u -p -u -p -r1.80 rde_filter.c
--- rde_filter.c        24 Jan 2017 04:22:42 -0000      1.80
+++ rde_filter.c        27 May 2017 08:44:37 -0000
@@ -106,7 +106,7 @@ rde_apply_set(struct rde_aspath *asp, st
                        }
                        break;
                case ACTION_SET_PREPEND_SELF:
-                       prep_as = rde_local_as();
+                       prep_as = peer->conf.local_as;
                        prepend = set->action.prepend;
                        np = aspath_prepend(asp->aspath, prep_as, prepend, &nl);
                        aspath_put(asp->aspath);
Index: rde_update.c
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/rde_update.c,v
retrieving revision 1.84
diff -u -p -u -p -r1.84 rde_update.c
--- rde_update.c        24 Jan 2017 04:22:42 -0000      1.84
+++ rde_update.c        27 May 2017 08:43:51 -0000
@@ -746,9 +746,9 @@ up_generate_attr(struct rde_peer *peer, 
        /* aspath */
        if (!peer->conf.ebgp ||
            peer->conf.flags & PEERFLAG_TRANS_AS)
-               pdata = aspath_prepend(a->aspath, rde_local_as(), 0, &plen);
+               pdata = aspath_prepend(a->aspath, peer->conf.local_as, 0, 
&plen);
        else
-               pdata = aspath_prepend(a->aspath, rde_local_as(), 1, &plen);
+               pdata = aspath_prepend(a->aspath, peer->conf.local_as, 1, 
&plen);
 
        if (!rde_as4byte(peer))
                pdata = aspath_deflate(pdata, &plen, &neednewpath);
@@ -881,10 +881,10 @@ up_generate_attr(struct rde_peer *peer, 
        if (neednewpath) {
                if (!peer->conf.ebgp ||
                    peer->conf.flags & PEERFLAG_TRANS_AS)
-                       pdata = aspath_prepend(a->aspath, rde_local_as(), 0,
+                       pdata = aspath_prepend(a->aspath, peer->conf.local_as, 
0,
                            &plen);
                else
-                       pdata = aspath_prepend(a->aspath, rde_local_as(), 1,
+                       pdata = aspath_prepend(a->aspath, peer->conf.local_as, 
1,
                            &plen);
                flags = ATTR_OPTIONAL|ATTR_TRANSITIVE;
                if (!(a->flags & F_PREFIX_ANNOUNCED))
Index: session.c
===================================================================
RCS file: /cvs/openbsd/src/usr.sbin/bgpd/session.c,v
retrieving revision 1.359
diff -u -p -u -p -r1.359 session.c
--- session.c   13 Feb 2017 14:48:44 -0000      1.359
+++ session.c   27 May 2017 07:51:34 -0000
@@ -1467,7 +1467,7 @@ session_open(struct peer *p)
        if (p->capa.ann.as4byte) {      /* 4 bytes data */
                u_int32_t       nas;
 
-               nas = htonl(conf->as);
+               nas = htonl(p->conf.local_as);
                errs += session_capa_add(opb, CAPA_AS4BYTE, sizeof(nas));
                errs += ibuf_add(opb, &nas, sizeof(nas));
        }
@@ -1484,7 +1484,7 @@ session_open(struct peer *p)
        }
 
        msg.version = 4;
-       msg.myas = htons(conf->short_as);
+       msg.myas = htons(p->conf.local_short_as);
        if (p->conf.holdtime)
                msg.holdtime = htons(p->conf.holdtime);
        else
@@ -2128,7 +2128,7 @@ parse_open(struct peer *peer)
        /* if remote-as is zero and it's a cloned neighbor, accept any */
        if (peer->template && !peer->conf.remote_as && as != AS_TRANS) {
                peer->conf.remote_as = as;
-               peer->conf.ebgp = (peer->conf.remote_as != conf->as);
+               peer->conf.ebgp = (peer->conf.remote_as != peer->conf.local_as);
                if (!peer->conf.ebgp)
                        /* force enforce_as off for iBGP sessions */
                        peer->conf.enforce_as = ENFORCE_AS_OFF;
@@ -3110,7 +3110,7 @@ session_template_clone(struct peer *p, s
 
        if (as) {
                p->conf.remote_as = as;
-               p->conf.ebgp = (p->conf.remote_as != conf->as);
+               p->conf.ebgp = (p->conf.remote_as != p->conf.local_as);
                if (!p->conf.ebgp)
                        /* force enforce_as off for iBGP sessions */
                        p->conf.enforce_as = ENFORCE_AS_OFF;



-- 
Politicians are the same all over.  They promise to build a bridge even
where there is no river.
        -- Nikita Khrushchev

Reply via email to