Update docs and diagram for extended multi-fabric topology
- README: rewritten node inventory, AS map, addressing plan (management, Lo0/Lo1, P2P, hosts), VNI/RD/RT tables, control-plane summary and end-to-end Campus <-> DC test procedures through the Core (VRF gold stitching). - hosts/README: document the two new Campus host configurations. - assets/arista-evpn-fabric.svg: new three-zone layout (Campus, Core, DC) with legend. - evpn-lab.clab.yml.annotations.json: reposition nodes and add zone labels so the ContainerLab graph matches the extended topology.
This commit is contained in:
423
README.md
423
README.md
@@ -1,17 +1,23 @@
|
|||||||
# Arista EVPN-VXLAN ContainerLab
|
# Arista EVPN-VXLAN ContainerLab — DC + Core + Campus
|
||||||
|
|
||||||
A production-ready Arista BGP EVPN-VXLAN data center fabric topology using ContainerLab and cEOS.
|
An extended Arista BGP EVPN-VXLAN multi-fabric lab using ContainerLab and cEOS. The topology interconnects a **Data Center fabric** and a **Campus fabric** through a dedicated **Core L3 transit zone**, with a VRF (`gold`) stretched end-to-end across both fabrics.
|
||||||
|
|
||||||
## 🎯 Overview
|
## 🎯 Overview
|
||||||
|
|
||||||
This lab demonstrates a complete 3-tier EVPN-VXLAN data center fabric with:
|
| Zone | Devices |
|
||||||
|
| ------ | --------------------------------------------------------------------------------------- |
|
||||||
|
| DC | 2 spines, 8 leafs (4 MLAG VTEPs), 2 border leafs (MLAG), 4 access switches, 4 hosts |
|
||||||
|
| Core | 2 core routers (iBGP AS 65500, OSPF underlay with BLs, eBGP to DC & Campus BLs) |
|
||||||
|
| Campus | 2 spines, 4 leafs (2 MLAG VTEPs), 2 border leafs (MLAG), 2 access switches, 2 hosts |
|
||||||
|
|
||||||
- **2 Spine switches** (BGP Route Reflectors)
|
Key design choices:
|
||||||
- **8 Leaf switches** forming 4 VTEPs (MLAG pairs)
|
|
||||||
- **4 Access switches** (L2-only, dual-homed to leaf MLAG pairs)
|
- **eBGP** in both fabrics (underlay + EVPN overlay) between spines and leafs / border leafs.
|
||||||
- **BGP EVPN overlay** with L2/L3 VXLAN
|
- **OSPF area 0 + eBGP multi-hop** between each Border Leaf pair and both Core routers (over dot1q subinterfaces: `.100` = default VRF underlay, `.200` = VRF `gold`).
|
||||||
- **MLAG configuration** for high availability
|
- **MLAG** everywhere there is dual-homing (leaf pairs, border-leaf pairs, access → leafs, host → access).
|
||||||
- **Test hosts** for validation
|
- **VRF `gold`** is stretched end-to-end: DC leafs (VLAN 34 / 78) ↔ DC-BL ↔ Core ↔ Campus-BL ↔ Campus leafs (VLAN 60 / 70), all sharing L3 VNI `100001`.
|
||||||
|
- **VLAN 50** is a campus-local L2 VXLAN stretched between the two Campus VTEPs.
|
||||||
|
- **Convention**: L2 VNI = `110000 + vlan_id`, L3 VNI = `100001` for VRF `gold`, RT `1:100001` in both fabrics.
|
||||||
|
|
||||||
## 📐 Topology
|
## 📐 Topology
|
||||||
|
|
||||||
@@ -21,284 +27,323 @@ This lab demonstrates a complete 3-tier EVPN-VXLAN data center fabric with:
|
|||||||
|
|
||||||
### Prerequisites
|
### Prerequisites
|
||||||
|
|
||||||
- ContainerLab installed
|
- ContainerLab
|
||||||
- Docker installed
|
- Docker
|
||||||
- Arista cEOS image: `ceos:4.35.0`
|
- Arista cEOS image: `ceos:4.35.0`
|
||||||
|
|
||||||
### Deploy the Lab
|
### Deploy the Lab
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# Clone the repository
|
|
||||||
git clone https://gitea.arnodo.fr/Damien/arista-evpn-vxlan-clab.git
|
git clone https://gitea.arnodo.fr/Damien/arista-evpn-vxlan-clab.git
|
||||||
cd arista-evpn-vxlan-clab
|
cd arista-evpn-vxlan-clab
|
||||||
|
|
||||||
# Deploy the topology
|
|
||||||
sudo containerlab deploy -t evpn-lab.clab.yml
|
sudo containerlab deploy -t evpn-lab.clab.yml
|
||||||
|
|
||||||
# Check status
|
|
||||||
sudo containerlab inspect -t evpn-lab.clab.yml
|
sudo containerlab inspect -t evpn-lab.clab.yml
|
||||||
```
|
```
|
||||||
|
|
||||||
### Access Devices
|
### Access Devices
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# SSH to any device (password: admin)
|
# SSH (password: admin) — works for every cEOS node
|
||||||
ssh admin@clab-arista-evpn-fabric-leaf1
|
ssh admin@clab-arista-evpn-fabric-leaf1
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1
|
||||||
|
ssh admin@clab-arista-evpn-fabric-campus-leaf1
|
||||||
|
|
||||||
# Or use docker exec
|
# Or via docker exec
|
||||||
docker exec -it clab-arista-evpn-fabric-leaf1 Cli
|
docker exec -it clab-arista-evpn-fabric-border-leaf-dc1 Cli
|
||||||
```
|
```
|
||||||
|
|
||||||
## 📋 Configuration Details
|
## 📋 Architecture
|
||||||
|
|
||||||
### AS Numbers
|
### Node Inventory
|
||||||
|
|
||||||
- **Spine**: AS 65000
|
| Zone | Role | Nodes | AS |
|
||||||
- **VTEP1 (Leaf1/2)**: AS 65001
|
| ------ | ----------------------- | ------------------------------------------------------ | ------ |
|
||||||
- **VTEP2 (Leaf3/4)**: AS 65002
|
| DC | Spine | `spine1`, `spine2` | 65000 |
|
||||||
- **VTEP3 (Leaf5/6)**: AS 65003
|
| DC | Leaf VTEP1 (MLAG) | `leaf1`, `leaf2` | 65001 |
|
||||||
- **VTEP4 (Leaf7/8)**: AS 65004
|
| DC | Leaf VTEP2 (MLAG) | `leaf3`, `leaf4` | 65002 |
|
||||||
|
| DC | Leaf VTEP3 (MLAG) | `leaf5`, `leaf6` | 65003 |
|
||||||
|
| DC | Leaf VTEP4 (MLAG) | `leaf7`, `leaf8` | 65004 |
|
||||||
|
| DC | Border Leaf (MLAG) | `border-leaf-dc1`, `border-leaf-dc2` | 65005 |
|
||||||
|
| DC | Access (L2-only) | `access1`-`access4` | — |
|
||||||
|
| DC | Host | `host1`-`host4` | — |
|
||||||
|
| Core | Core router | `core1`, `core2` | 65500 |
|
||||||
|
| Campus | Spine | `campus-spine1`, `campus-spine2` | 66000 |
|
||||||
|
| Campus | Leaf VTEP1 (MLAG) | `campus-leaf1`, `campus-leaf2` | 66001 |
|
||||||
|
| Campus | Leaf VTEP2 (MLAG) | `campus-leaf3`, `campus-leaf4` | 66002 |
|
||||||
|
| Campus | Border Leaf (MLAG) | `border-leaf-campus1`, `border-leaf-campus2` | 66005 |
|
||||||
|
| Campus | Access (L2-only) | `campus-access1`, `campus-access2` | — |
|
||||||
|
| Campus | Host | `campus-host1`, `campus-host2` | — |
|
||||||
|
|
||||||
|
### AS Numbering
|
||||||
|
|
||||||
|
| AS | Role |
|
||||||
|
| ----- | ---------------------------------- |
|
||||||
|
| 65000 | DC Spine |
|
||||||
|
| 65001 | DC VTEP1 (leaf1/2) |
|
||||||
|
| 65002 | DC VTEP2 (leaf3/4) |
|
||||||
|
| 65003 | DC VTEP3 (leaf5/6) |
|
||||||
|
| 65004 | DC VTEP4 (leaf7/8) |
|
||||||
|
| 65005 | DC Border Leaf pair |
|
||||||
|
| 65500 | Core (iBGP between core1 & core2) |
|
||||||
|
| 66000 | Campus Spine |
|
||||||
|
| 66001 | Campus VTEP1 (campus-leaf1/2) |
|
||||||
|
| 66002 | Campus VTEP2 (campus-leaf3/4) |
|
||||||
|
| 66005 | Campus Border Leaf pair |
|
||||||
|
|
||||||
### Access Switches
|
### Access Switches
|
||||||
|
|
||||||
| Access Switch | Uplink Leaf Pair | VLAN(s) | Connected Host |
|
| Access Switch | Uplink Pair | VLANs | Host |
|
||||||
| ------------- | ---------------- | ------- | -------------- |
|
| --------------- | ------------------------ | -------- | -------------- |
|
||||||
| access1 | Leaf1/2 (VTEP1) | 40 | host1 |
|
| access1 | leaf1/2 (VTEP1) | 40 | host1 |
|
||||||
| access2 | Leaf3/4 (VTEP2) | 34 | host2 |
|
| access2 | leaf3/4 (VTEP2) | 34 | host2 |
|
||||||
| access3 | Leaf5/6 (VTEP3) | 40 | host3 |
|
| access3 | leaf5/6 (VTEP3) | 40 | host3 |
|
||||||
| access4 | Leaf7/8 (VTEP4) | 78 | host4 |
|
| access4 | leaf7/8 (VTEP4) | 78 | host4 |
|
||||||
|
| campus-access1 | campus-leaf1/2 (VTEP1) | 50, 60 | campus-host1 |
|
||||||
|
| campus-access2 | campus-leaf3/4 (VTEP2) | 50, 70 | campus-host2 |
|
||||||
|
|
||||||
- L2-only switches with LACP uplinks (Port-Channel 10) to leaf MLAG pairs
|
All access switches are L2-only, LACP-bonded to their leaf MLAG pair via `Port-Channel10`, with host downlinks on `Port-Channel1`. MSTP + edge-port BPDU guard.
|
||||||
- Host-facing downlinks via LACP (Port-Channel 1)
|
|
||||||
- STP mode MSTP with edge-port BPDU guard
|
|
||||||
|
|
||||||
### IP Addressing
|
## 🧭 IP Addressing Plan
|
||||||
|
|
||||||
#### Management Network
|
### Management (`172.16.0.0/24`)
|
||||||
|
|
||||||
- Subnet: `172.16.0.0/24`
|
| Node | IP | Node | IP |
|
||||||
- Spine1: `172.16.0.1`
|
| ------------------------- | --------------- | ------------------------- | --------------- |
|
||||||
- Spine2: `172.16.0.2`
|
| spine1 | 172.16.0.1 | campus-spine1 | 172.16.0.20 |
|
||||||
- Leaf1: `172.16.0.25`, Leaf2: `172.16.0.50`, Leaf3-8: `172.16.0.27-32`
|
| spine2 | 172.16.0.2 | campus-spine2 | 172.16.0.21 |
|
||||||
- Access1-4: `172.16.0.41-44`
|
| border-leaf-dc1 | 172.16.0.3 | border-leaf-campus1 | 172.16.0.22 |
|
||||||
|
| border-leaf-dc2 | 172.16.0.4 | border-leaf-campus2 | 172.16.0.23 |
|
||||||
|
| core1 | 172.16.0.10 | campus-leaf1-4 | 172.16.0.51-54 |
|
||||||
|
| core2 | 172.16.0.11 | campus-access1 | 172.16.0.61 |
|
||||||
|
| leaf1 | 172.16.0.25 | campus-access2 | 172.16.0.62 |
|
||||||
|
| leaf2 | 172.16.0.50 | host1-4 | 172.16.0.101-104|
|
||||||
|
| leaf3-8 | 172.16.0.27-32 | campus-host1 | 172.16.0.105 |
|
||||||
|
| access1-4 | 172.16.0.41-44 | campus-host2 | 172.16.0.106 |
|
||||||
|
|
||||||
#### Loopback Interfaces
|
Gateway: `172.16.0.254`.
|
||||||
|
|
||||||
- **Router-ID Loopbacks (Lo0)**: `10.0.250.0/24`
|
### Router-ID Loopback0 (`Lo0`)
|
||||||
- Spine1: `10.0.250.1/32`
|
|
||||||
- Spine2: `10.0.250.2/32`
|
|
||||||
- Leaf1-8: `10.0.250.11-18/32`
|
|
||||||
|
|
||||||
- **VTEP Loopbacks (Lo1)**: `10.0.255.0/24`
|
| Zone | Range | Nodes |
|
||||||
- VTEP1: `10.0.255.11/32`
|
| ------ | ------------------- | --------------------------------------------------------------------- |
|
||||||
- VTEP2: `10.0.255.12/32`
|
| DC | `10.0.250.0/24` | spine1 .1, spine2 .2, leaf1-8 .11-.18, BL-dc1 .21, BL-dc2 .22 |
|
||||||
- VTEP3: `10.0.255.13/32`
|
| Core | `10.0.200.0/24` | core1 `10.0.200.1`, core2 `10.0.200.2` |
|
||||||
- VTEP4: `10.0.255.14/32`
|
| Campus | `10.1.250.0/24` | campus-spine1 .1, campus-spine2 .2, campus-leaf1-4 .11-.14, BL-campus1 .21, BL-campus2 .22 |
|
||||||
|
|
||||||
#### Underlay P2P Links
|
### VTEP Loopback1 (`Lo1`) — shared per MLAG pair
|
||||||
|
|
||||||
- Spine1 to Leafs: `10.0.1.0/31`, `10.0.1.2/31`, ... `10.0.1.14/31`
|
| Fabric | VTEP | Address | Leafs |
|
||||||
- Spine2 to Leafs: `10.0.2.0/31`, `10.0.2.2/31`, ... `10.0.2.14/31`
|
| ------ | ------ | --------------- | ---------------------- |
|
||||||
- MLAG iBGP peering: `10.0.3.0/31`, `10.0.3.2/31`, `10.0.3.4/31`, `10.0.3.6/31`
|
| DC | VTEP1 | `10.0.255.11` | leaf1, leaf2 |
|
||||||
|
| DC | VTEP2 | `10.0.255.12` | leaf3, leaf4 |
|
||||||
|
| DC | VTEP3 | `10.0.255.13` | leaf5, leaf6 |
|
||||||
|
| DC | VTEP4 | `10.0.255.14` | leaf7, leaf8 |
|
||||||
|
| DC | BL | `10.0.255.15` | border-leaf-dc1/2 |
|
||||||
|
| Campus | VTEP1 | `10.1.255.11` | campus-leaf1/2 |
|
||||||
|
| Campus | VTEP2 | `10.1.255.12` | campus-leaf3/4 |
|
||||||
|
| Campus | BL | `10.1.255.21` | border-leaf-campus1/2 |
|
||||||
|
|
||||||
#### Host Network Addressing
|
### Underlay P2P (`/31`)
|
||||||
|
|
||||||
| Host | VLAN | VRF | IP Address | Gateway | Type |
|
| Segment | Subnets |
|
||||||
| ----- | ---- | ------- | --------------- | ---------- | -------- |
|
| -------------------------------- | --------------------------------------- |
|
||||||
| host1 | 40 | default | 10.40.40.101/24 | - | L2 VXLAN |
|
| DC spine1 ↔ leaf/BL | `10.0.1.0/31` … `10.0.1.18/31` |
|
||||||
| host2 | 34 | gold | 10.34.34.102/24 | 10.34.34.1 | L3 VXLAN |
|
| DC spine2 ↔ leaf/BL | `10.0.2.0/31` … `10.0.2.18/31` |
|
||||||
| host3 | 40 | default | 10.40.40.103/24 | - | L2 VXLAN |
|
| DC MLAG iBGP SVIs (per pair) | `10.0.3.0/31`, `.2/31`, `.4/31`, `.6/31`, `.8/31` (BL) |
|
||||||
| host4 | 78 | gold | 10.78.78.104/24 | 10.78.78.1 | L3 VXLAN |
|
| DC MLAG peer-link SVIs | `10.0.199.240/31` … `10.0.199.246/31` |
|
||||||
|
| DC-BL ↔ Core (default, `.100`) | `10.0.4.0/31` .. `10.0.4.6/31` |
|
||||||
|
| DC-BL ↔ Core (VRF gold, `.200`) | `10.0.14.0/31` .. `10.0.14.6/31` |
|
||||||
|
| Campus-BL ↔ Core (default) | `10.0.5.0/31` .. `10.0.5.6/31` |
|
||||||
|
| Campus-BL ↔ Core (VRF gold) | `10.0.15.0/31` .. `10.0.15.6/31` |
|
||||||
|
| Core1 ↔ Core2 (default) | `10.0.200.128/31` |
|
||||||
|
| Core1 ↔ Core2 (VRF gold) | `10.0.200.130/31` |
|
||||||
|
| Campus spine1 ↔ leaf/BL | `10.1.1.0/31` … `10.1.1.10/31` |
|
||||||
|
| Campus spine2 ↔ leaf/BL | `10.1.2.0/31` … `10.1.2.10/31` |
|
||||||
|
| Campus MLAG iBGP SVIs | `10.1.3.0/31`, `.2/31`, `.4/31` |
|
||||||
|
| Campus MLAG peer-link SVIs | `10.1.199.250/31` … `10.1.199.254/31` |
|
||||||
|
|
||||||
**Notes:**
|
### Host Addressing
|
||||||
|
|
||||||
- Host1 and Host3 are in VLAN 40 (L2 VXLAN only) and can communicate at Layer 2
|
| Host | VLAN | VRF | IP / Mask | Gateway | Purpose |
|
||||||
- Host2 and Host4 are in VRF "gold" with different subnets, communicating via EVPN Type-5 routes (L3 VXLAN)
|
| ------------- | ---- | -------- | ----------------- | ------------ | ------------------------------ |
|
||||||
- All hosts use LACP bonding (802.3ad) with dual-homing to access switches
|
| host1 | 40 | default | 10.40.40.101/24 | — | DC L2 stretched (VTEP1↔VTEP3) |
|
||||||
- Each access switch is dual-homed via LACP (Port-Channel) to a leaf MLAG pair
|
| host2 | 34 | gold | 10.34.34.102/24 | 10.34.34.1 | DC L3 VRF gold |
|
||||||
|
| host3 | 40 | default | 10.40.40.103/24 | — | DC L2 stretched |
|
||||||
|
| host4 | 78 | gold | 10.78.78.104/24 | 10.78.78.1 | DC L3 VRF gold |
|
||||||
|
| campus-host1 | 50 | default | 10.50.50.101/24 | — | Campus L2 stretched (VTEP1↔VTEP2) |
|
||||||
|
| campus-host1 | 60 | gold | 10.60.60.101/24 | 10.60.60.1 | Campus L3 VRF gold |
|
||||||
|
| campus-host2 | 50 | default | 10.50.50.102/24 | — | Campus L2 stretched |
|
||||||
|
| campus-host2 | 70 | gold | 10.60.70.102/24 | 10.60.70.1 | Campus L3 VRF gold |
|
||||||
|
|
||||||
### VXLAN Network Identifiers (VNI)
|
## 🏷️ VXLAN Network Identifiers
|
||||||
|
|
||||||
#### L2 VNI (VLAN to VNI Mapping)
|
### L2 VNI Mapping
|
||||||
|
|
||||||
| VLAN | Description | VNI | VTEPs | Route Target | Route Distinguisher |
|
| VLAN | Description | VNI | Scope | RT |
|
||||||
| ---- | ------------- | ------ | ------------------------------- | ------------ | -------------------------- |
|
| ---- | ------------------------------ | ------ | ------------------------------------------------------ | ---------- |
|
||||||
| 40 | test-l2-vxlan | 110040 | VTEP1, VTEP3 (Leaf1/2, Leaf5/6) | 40:110040 | 65001:110040, 65003:110040 |
|
| 40 | DC L2 VXLAN (stretched) | 110040 | DC VTEP1 (leaf1/2) + VTEP3 (leaf5/6) | 40:110040 |
|
||||||
|
| 50 | Campus L2 VXLAN (stretched) | 110050 | Campus VTEP1 (campus-leaf1/2) + VTEP2 (campus-leaf3/4) | 50:110050 |
|
||||||
|
| 34 | DC VRF gold subnet (local) | 110034 | DC VTEP2 only (anycast GW 10.34.34.1) | 34:110034 |
|
||||||
|
| 78 | DC VRF gold subnet (local) | 110078 | DC VTEP4 only (anycast GW 10.78.78.1) | 78:110078 |
|
||||||
|
| 60 | Campus VRF gold subnet (local) | 110060 | Campus VTEP1 only (anycast GW 10.60.60.1) | 60:110060 |
|
||||||
|
| 70 | Campus VRF gold subnet (local) | 110070 | Campus VTEP2 only (anycast GW 10.60.70.1) | 70:110070 |
|
||||||
|
|
||||||
**L2 VNI Details:**
|
### L3 VNI Mapping (end-to-end)
|
||||||
|
|
||||||
- VLAN 40 is stretched across VTEP1 (Leaf1/2) and VTEP3 (Leaf5/6) for pure Layer 2 connectivity
|
| VRF | L3 VNI | RT | Scope |
|
||||||
- Hosts in VLAN 40 (host1 and host3) communicate at Layer 2 across the EVPN fabric
|
| ---- | ------- | ---------- | ----------------------------------------------------- |
|
||||||
- EVPN Type-2 (MAC/IP) routes are used for MAC address learning and distribution
|
| gold | 100001 | 1:100001 | DC VTEP2/VTEP4/DC-BL + Campus VTEP1/VTEP2/Campus-BL |
|
||||||
|
|
||||||
#### L3 VNI (VRF to VNI Mapping)
|
VRF `gold` is announced over EVPN Type-5 (IP prefix) inside each fabric, and **stitched by the Core** via eBGP IPv4 unicast in VRF gold (over the `.200` dot1q subinterfaces). L3 VNI `100001` is re-used end-to-end for symmetry; RT `1:100001` is consistent across both fabrics.
|
||||||
|
|
||||||
| VRF | Description | VNI | VTEPs | Route Target | VLANs |
|
### Route Distinguisher Convention
|
||||||
| ---- | ------------------------------- | ------ | ------------------------------- | ------------ | ------ |
|
|
||||||
| gold | L3 VRF for inter-subnet routing | 100001 | VTEP2, VTEP4 (Leaf3/4, Leaf7/8) | 1:100001 | 34, 78 |
|
|
||||||
|
|
||||||
**L3 VNI Details:**
|
- Leafs / BLs: `rd <Loopback0>:1` for VRF gold; `rd <AS>:<L2_VNI>` per L2 VLAN (e.g. `65001:110040`, `66002:110050`).
|
||||||
|
- Cores: `rd <Loopback0>:100001` for VRF gold (transit only — no EVPN, IPv4 unicast with `redistribute connected`).
|
||||||
|
|
||||||
- VRF "gold" uses VNI 100001 for Layer 3 VXLAN routing between different subnets
|
## 🔀 Control Plane Summary
|
||||||
- VLAN 34 (10.34.34.0/24) on VTEP2 and VLAN 78 (10.78.78.0/24) on VTEP4 are both in VRF gold
|
|
||||||
- EVPN Type-5 (IP Prefix) routes are used for inter-subnet routing
|
|
||||||
- Each VTEP advertises its local subnets via EVPN, enabling routed connectivity between host2 and host4
|
|
||||||
|
|
||||||
#### VNI Summary
|
| Segment | Protocol | Notes |
|
||||||
|
| ----------------------------------- | ------------------------------------ | ------------------------------------- |
|
||||||
| VNI Type | VNI | Purpose | EVPN Route Type |
|
| DC spine ↔ leaf/BL underlay | eBGP IPv4 (AS 65000 ↔ 650xx) | `maximum-paths 4 ecmp 64` |
|
||||||
| -------- | ------ | ----------------------------- | ------------------ |
|
| DC spine ↔ leaf/BL overlay | eBGP EVPN via Loopback0, multi-hop 3 | Spines reflect via `ebgp peer-group` |
|
||||||
| L2 VNI | 110040 | Layer 2 extension for VLAN 40 | Type-2 (MAC/IP) |
|
| DC MLAG pair iBGP | iBGP over VLAN 4091 SVI | `next-hop-self` |
|
||||||
| L3 VNI | 100001 | Layer 3 routing for VRF gold | Type-5 (IP Prefix) |
|
| DC-BL ↔ Core (default) | OSPF area 0 + eBGP AS 65005 ↔ 65500 | on `.100` dot1q subinterface |
|
||||||
|
| DC-BL ↔ Core (VRF gold) | eBGP AS 65005 ↔ 65500 | on `.200` dot1q subinterface |
|
||||||
### Features Implemented
|
| Core1 ↔ Core2 (default) | OSPF area 0 + iBGP AS 65500 | via Loopback0 |
|
||||||
|
| Core1 ↔ Core2 (VRF gold) | iBGP AS 65500 | VRF-aware over `.200` subinterface |
|
||||||
✅ **Underlay**
|
| Campus-BL ↔ Core (default / gold) | OSPF + eBGP AS 66005 ↔ 65500 | same pattern as DC-BL |
|
||||||
|
| Campus spine ↔ leaf/BL underlay | eBGP IPv4 (AS 66000 ↔ 660xx) | |
|
||||||
- BGP IPv4 Unicast
|
| Campus spine ↔ leaf/BL overlay | eBGP EVPN via Loopback0, multi-hop 3 | |
|
||||||
- ECMP with 4 paths
|
| Campus MLAG pair iBGP | iBGP over VLAN 4091 SVI | |
|
||||||
- eBGP between Spine-Leaf
|
|
||||||
- iBGP between MLAG pairs
|
|
||||||
|
|
||||||
✅ **Overlay**
|
|
||||||
|
|
||||||
- BGP EVPN address family
|
|
||||||
- VXLAN data plane
|
|
||||||
- EVPN Type-2 (MAC/IP routes)
|
|
||||||
- EVPN Type-5 (IP Prefix routes)
|
|
||||||
|
|
||||||
✅ **High Availability**
|
|
||||||
|
|
||||||
- MLAG dual-homing
|
|
||||||
- Dual-active detection
|
|
||||||
- Anycast VTEP gateway
|
|
||||||
|
|
||||||
## 🧪 Testing & Validation
|
## 🧪 Testing & Validation
|
||||||
|
|
||||||
### Verify BGP EVPN Neighbors
|
### Fabric health
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# On any spine
|
# DC
|
||||||
show bgp evpn summary
|
ssh admin@clab-arista-evpn-fabric-spine1 "show bgp evpn summary"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-leaf3 "show bgp evpn summary"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-border-leaf-dc1 "show bgp evpn summary"
|
||||||
|
|
||||||
# On any leaf
|
# Campus
|
||||||
show bgp evpn summary
|
ssh admin@clab-arista-evpn-fabric-campus-spine1 "show bgp evpn summary"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-campus-leaf1 "show bgp evpn summary"
|
||||||
|
|
||||||
|
# Core transit (no EVPN — IPv4 only)
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1 "show ip bgp summary"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1 "show ip bgp summary vrf gold"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1 "show ip ospf neighbor"
|
||||||
```
|
```
|
||||||
|
|
||||||
### Verify VXLAN
|
### VXLAN
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# Check VXLAN interface
|
# On any leaf/BL
|
||||||
show interface vxlan1
|
show interface vxlan1
|
||||||
|
|
||||||
# Check remote VTEPs
|
|
||||||
show vxlan vtep
|
show vxlan vtep
|
||||||
|
|
||||||
# Check VXLAN address table
|
|
||||||
show vxlan address-table
|
show vxlan address-table
|
||||||
```
|
```
|
||||||
|
|
||||||
### Verify MLAG
|
### MLAG
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# Check MLAG status
|
|
||||||
show mlag
|
show mlag
|
||||||
|
show mlag interfaces detail
|
||||||
# Check MLAG interfaces
|
|
||||||
show mlag interfaces
|
|
||||||
```
|
```
|
||||||
|
|
||||||
### Test Connectivity
|
### Intra-DC connectivity (existing tests)
|
||||||
|
|
||||||
#### L2 VXLAN Testing (VLAN 40)
|
|
||||||
|
|
||||||
Test Layer 2 connectivity between host1 and host3 across the EVPN fabric:
|
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# From host1 to host3 (same VLAN 40, different VTEPs)
|
# L2 VLAN 40: host1 ↔ host3
|
||||||
docker exec -it clab-arista-evpn-fabric-host1 ping -c 4 10.40.40.103
|
docker exec -it clab-arista-evpn-fabric-host1 ping -c 3 10.40.40.103
|
||||||
|
|
||||||
# Check host1 interface
|
# L3 VRF gold (DC only): host2 ↔ host4
|
||||||
docker exec -it clab-arista-evpn-fabric-host1 ip addr show bond0
|
docker exec -it clab-arista-evpn-fabric-host2 ping -c 3 10.78.78.104
|
||||||
|
|
||||||
# From host3 to host1
|
|
||||||
docker exec -it clab-arista-evpn-fabric-host3 ping -c 4 10.40.40.101
|
|
||||||
```
|
```
|
||||||
|
|
||||||
#### L3 VXLAN Testing (VRF gold)
|
### Intra-Campus connectivity
|
||||||
|
|
||||||
Test Layer 3 connectivity between host2 and host4 in VRF "gold":
|
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# From host2 to host4 (different subnets via EVPN Type-5)
|
# L2 VLAN 50: campus-host1 ↔ campus-host2
|
||||||
docker exec -it clab-arista-evpn-fabric-host2 ping -c 4 10.78.78.104
|
docker exec -it clab-arista-evpn-fabric-campus-host1 ping -c 3 10.50.50.102
|
||||||
|
|
||||||
# From host4 to host2
|
# L3 VRF gold (Campus only): campus-host1 ↔ campus-host2
|
||||||
docker exec -it clab-arista-evpn-fabric-host4 ping -c 4 10.34.34.102
|
docker exec -it clab-arista-evpn-fabric-campus-host1 ping -c 3 10.60.70.102
|
||||||
|
docker exec -it clab-arista-evpn-fabric-campus-host2 ping -c 3 10.60.60.101
|
||||||
# Check routing table on hosts
|
|
||||||
docker exec -it clab-arista-evpn-fabric-host2 ip route
|
|
||||||
docker exec -it clab-arista-evpn-fabric-host4 ip route
|
|
||||||
```
|
```
|
||||||
|
|
||||||
#### Verify EVPN Routes on Switches
|
### End-to-end Campus ↔ DC (VRF gold via Core)
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# Check EVPN Type-2 routes (MAC/IP) - for VLAN 40
|
# campus-host1 (10.60.60.101, VRF gold Campus) → host2 (10.34.34.102, VRF gold DC)
|
||||||
ssh admin@clab-arista-evpn-fabric-leaf1
|
docker exec -it clab-arista-evpn-fabric-campus-host1 ping -c 3 10.34.34.102
|
||||||
show bgp evpn route-type mac-ip
|
|
||||||
|
|
||||||
# Check EVPN Type-5 routes (IP Prefix) - for VRF gold
|
# campus-host2 (10.60.70.102) → host4 (10.78.78.104)
|
||||||
ssh admin@clab-arista-evpn-fabric-leaf3
|
docker exec -it clab-arista-evpn-fabric-campus-host2 ping -c 3 10.78.78.104
|
||||||
show bgp evpn route-type ip-prefix ipv4
|
|
||||||
|
|
||||||
# Verify VXLAN learned MACs
|
# Reverse direction
|
||||||
show vxlan address-table
|
docker exec -it clab-arista-evpn-fabric-host2 ping -c 3 10.60.60.101
|
||||||
|
docker exec -it clab-arista-evpn-fabric-host4 ping -c 3 10.60.70.102
|
||||||
|
|
||||||
# Check MAC addresses learned via EVPN
|
# Traceroute: expected path campus-leaf → campus-BL → core → DC-BL → DC-leaf
|
||||||
show mac address-table
|
docker exec -it clab-arista-evpn-fabric-campus-host1 traceroute 10.34.34.102
|
||||||
|
```
|
||||||
|
|
||||||
|
### Inspect the Core transit path
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Check VRF gold routes on core1 — both DC and Campus prefixes should be present
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1 "show ip route vrf gold"
|
||||||
|
ssh admin@clab-arista-evpn-fabric-core1 "show ip bgp vrf gold"
|
||||||
|
|
||||||
|
# EVPN Type-5 on DC-BL (imported from DC fabric, redistributed from Core into EVPN)
|
||||||
|
ssh admin@clab-arista-evpn-fabric-border-leaf-dc1 "show bgp evpn route-type ip-prefix ipv4"
|
||||||
|
|
||||||
|
# EVPN Type-5 on Campus-BL
|
||||||
|
ssh admin@clab-arista-evpn-fabric-border-leaf-campus1 "show bgp evpn route-type ip-prefix ipv4"
|
||||||
```
|
```
|
||||||
|
|
||||||
## 📁 Repository Structure
|
## 📁 Repository Structure
|
||||||
|
|
||||||
```
|
```
|
||||||
arista-evpn-vxlan-clab/
|
arista-evpn-vxlan-clab/
|
||||||
├── README.md # This file
|
|
||||||
├── TROUBLESHOOTING.md # Troubleshooting guide
|
|
||||||
├── END_TO_END_TESTING.md # Testing procedures
|
|
||||||
├── evpn-lab.clab.yml # ContainerLab topology
|
|
||||||
├── assets/
|
|
||||||
│ └── arista-evpn-fabric.svg # Topology diagram
|
|
||||||
├── configs/ # Device configurations
|
|
||||||
│ ├── spine1.cfg
|
|
||||||
│ ├── spine2.cfg
|
|
||||||
│ ├── leaf1.cfg through leaf8.cfg
|
|
||||||
│ ├── access1.cfg
|
|
||||||
│ ├── access2.cfg
|
|
||||||
│ ├── access3.cfg
|
|
||||||
│ └── access4.cfg
|
|
||||||
└── hosts/ # Host interface configurations
|
|
||||||
├── README.md
|
├── README.md
|
||||||
├── host1_interfaces
|
├── TROUBLESHOOTING.md
|
||||||
├── host2_interfaces
|
├── END_TO_END_TESTING.md
|
||||||
├── host3_interfaces
|
├── evpn-lab.clab.yml
|
||||||
└── host4_interfaces
|
├── evpn-lab.clab.yml.annotations.json
|
||||||
|
├── assets/
|
||||||
|
│ └── arista-evpn-fabric.svg
|
||||||
|
├── configs/
|
||||||
|
│ ├── spine1.cfg, spine2.cfg
|
||||||
|
│ ├── leaf1.cfg … leaf8.cfg
|
||||||
|
│ ├── border-leaf-dc1.cfg, border-leaf-dc2.cfg
|
||||||
|
│ ├── access1.cfg … access4.cfg
|
||||||
|
│ ├── core1.cfg, core2.cfg
|
||||||
|
│ ├── campus-spine1.cfg, campus-spine2.cfg
|
||||||
|
│ ├── campus-leaf1.cfg … campus-leaf4.cfg
|
||||||
|
│ ├── border-leaf-campus1.cfg, border-leaf-campus2.cfg
|
||||||
|
│ └── campus-access1.cfg, campus-access2.cfg
|
||||||
|
└── hosts/
|
||||||
|
├── README.md
|
||||||
|
├── host1_interfaces … host4_interfaces
|
||||||
|
├── campus-host1_interfaces
|
||||||
|
└── campus-host2_interfaces
|
||||||
```
|
```
|
||||||
|
|
||||||
## 🗑️ Cleanup
|
## 🗑️ Cleanup
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
# Destroy the lab
|
|
||||||
sudo containerlab destroy -t evpn-lab.clab.yml
|
|
||||||
|
|
||||||
# Remove all related containers and networks
|
|
||||||
sudo containerlab destroy -t evpn-lab.clab.yml --cleanup
|
sudo containerlab destroy -t evpn-lab.clab.yml --cleanup
|
||||||
```
|
```
|
||||||
|
|
||||||
## 📚 References
|
## 📚 References
|
||||||
|
|
||||||
- [Original Configuration Guide](https://overlaid.net/2019/01/27/arista-bgp-evpn-configuration-example/)
|
|
||||||
- [Arista EOS Documentation](https://www.arista.com/en/support/product-documentation)
|
- [Arista EOS Documentation](https://www.arista.com/en/support/product-documentation)
|
||||||
- [ContainerLab Documentation](https://containerlab.dev/)
|
- [ContainerLab Documentation](https://containerlab.dev/)
|
||||||
- [RFC 7432 - BGP MPLS-Based Ethernet VPN](https://tools.ietf.org/html/rfc7432)
|
- [RFC 7432 — BGP MPLS-Based Ethernet VPN](https://tools.ietf.org/html/rfc7432)
|
||||||
- [RFC 8365 - A Network Virtualization Overlay Solution Using EVPN](https://tools.ietf.org/html/rfc8365)
|
- [RFC 8365 — A Network Virtualization Overlay Solution Using EVPN](https://tools.ietf.org/html/rfc8365)
|
||||||
|
- [RFC 9135 — Integrated Routing and Bridging in EVPN](https://tools.ietf.org/html/rfc9135)
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
|
Before Width: | Height: | Size: 49 KiB After Width: | Height: | Size: 14 KiB |
@@ -1,136 +1,77 @@
|
|||||||
{
|
{
|
||||||
"freeTextAnnotations": [],
|
"freeTextAnnotations": [
|
||||||
|
{
|
||||||
|
"id": "label-campus",
|
||||||
|
"position": { "x": -100, "y": 60 },
|
||||||
|
"text": "CAMPUS FABRIC (AS 66000 / 66001 / 66002 / 66005)",
|
||||||
|
"fontSize": 16,
|
||||||
|
"color": "#2563eb"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "label-core",
|
||||||
|
"position": { "x": 1100, "y": 60 },
|
||||||
|
"text": "CORE (AS 65500)",
|
||||||
|
"fontSize": 16,
|
||||||
|
"color": "#ea580c"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"id": "label-dc",
|
||||||
|
"position": { "x": 1600, "y": 60 },
|
||||||
|
"text": "DATA CENTER FABRIC (AS 65000 / 65001-4 / 65005)",
|
||||||
|
"fontSize": 16,
|
||||||
|
"color": "#16a34a"
|
||||||
|
}
|
||||||
|
],
|
||||||
"freeShapeAnnotations": [],
|
"freeShapeAnnotations": [],
|
||||||
"trafficRateAnnotations": [],
|
"trafficRateAnnotations": [],
|
||||||
"groupStyleAnnotations": [],
|
"groupStyleAnnotations": [],
|
||||||
"networkNodeAnnotations": [],
|
"networkNodeAnnotations": [],
|
||||||
"nodeAnnotations": [
|
"nodeAnnotations": [
|
||||||
{
|
|
||||||
"id": "spine1",
|
{ "id": "campus-spine1", "position": { "x": 120, "y": 160 } },
|
||||||
"position": {
|
{ "id": "campus-spine2", "position": { "x": 420, "y": 160 } },
|
||||||
"x": 260,
|
|
||||||
"y": 160
|
{ "id": "campus-leaf1", "position": { "x": -60, "y": 400 } },
|
||||||
}
|
{ "id": "campus-leaf2", "position": { "x": 80, "y": 400 } },
|
||||||
},
|
{ "id": "campus-leaf3", "position": { "x": 240, "y": 400 } },
|
||||||
{
|
{ "id": "campus-leaf4", "position": { "x": 380, "y": 400 } },
|
||||||
"id": "spine2",
|
|
||||||
"position": {
|
{ "id": "border-leaf-campus1", "position": { "x": 540, "y": 400 } },
|
||||||
"x": 740,
|
{ "id": "border-leaf-campus2", "position": { "x": 680, "y": 400 } },
|
||||||
"y": 160
|
|
||||||
}
|
{ "id": "campus-access1", "position": { "x": 40, "y": 540 } },
|
||||||
},
|
{ "id": "campus-access2", "position": { "x": 320, "y": 540 } },
|
||||||
{
|
|
||||||
"id": "leaf1",
|
{ "id": "campus-host1", "position": { "x": 40, "y": 680 } },
|
||||||
"position": {
|
{ "id": "campus-host2", "position": { "x": 320, "y": 680 } },
|
||||||
"x": -60,
|
|
||||||
"y": 420
|
{ "id": "core1", "position": { "x": 960, "y": 300 } },
|
||||||
}
|
{ "id": "core2", "position": { "x": 1180, "y": 300 } },
|
||||||
},
|
|
||||||
{
|
{ "id": "border-leaf-dc1", "position": { "x": 1380, "y": 400 } },
|
||||||
"id": "leaf2",
|
{ "id": "border-leaf-dc2", "position": { "x": 1520, "y": 400 } },
|
||||||
"position": {
|
|
||||||
"x": 100,
|
{ "id": "spine1", "position": { "x": 1800, "y": 160 } },
|
||||||
"y": 420
|
{ "id": "spine2", "position": { "x": 2280, "y": 160 } },
|
||||||
}
|
|
||||||
},
|
{ "id": "leaf1", "position": { "x": 1660, "y": 400 } },
|
||||||
{
|
{ "id": "leaf2", "position": { "x": 1800, "y": 400 } },
|
||||||
"id": "leaf3",
|
{ "id": "leaf3", "position": { "x": 1940, "y": 400 } },
|
||||||
"position": {
|
{ "id": "leaf4", "position": { "x": 2080, "y": 400 } },
|
||||||
"x": 260,
|
{ "id": "leaf5", "position": { "x": 2220, "y": 400 } },
|
||||||
"y": 420
|
{ "id": "leaf6", "position": { "x": 2360, "y": 400 } },
|
||||||
}
|
{ "id": "leaf7", "position": { "x": 2500, "y": 400 } },
|
||||||
},
|
{ "id": "leaf8", "position": { "x": 2640, "y": 400 } },
|
||||||
{
|
|
||||||
"id": "leaf4",
|
{ "id": "access1", "position": { "x": 1720, "y": 540 } },
|
||||||
"position": {
|
{ "id": "access2", "position": { "x": 2000, "y": 540 } },
|
||||||
"x": 420,
|
{ "id": "access3", "position": { "x": 2280, "y": 540 } },
|
||||||
"y": 420
|
{ "id": "access4", "position": { "x": 2560, "y": 540 } },
|
||||||
}
|
|
||||||
},
|
{ "id": "host1", "position": { "x": 1720, "y": 680 } },
|
||||||
{
|
{ "id": "host2", "position": { "x": 2000, "y": 680 } },
|
||||||
"id": "leaf5",
|
{ "id": "host3", "position": { "x": 2280, "y": 680 } },
|
||||||
"position": {
|
{ "id": "host4", "position": { "x": 2560, "y": 680 } }
|
||||||
"x": 580,
|
|
||||||
"y": 420
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "leaf6",
|
|
||||||
"position": {
|
|
||||||
"x": 740,
|
|
||||||
"y": 420
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "leaf7",
|
|
||||||
"position": {
|
|
||||||
"x": 920,
|
|
||||||
"y": 420
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "leaf8",
|
|
||||||
"position": {
|
|
||||||
"x": 1080,
|
|
||||||
"y": 420
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "host1",
|
|
||||||
"position": {
|
|
||||||
"x": 20,
|
|
||||||
"y": 680
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "host2",
|
|
||||||
"position": {
|
|
||||||
"x": 340,
|
|
||||||
"y": 680
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "host3",
|
|
||||||
"position": {
|
|
||||||
"x": 660,
|
|
||||||
"y": 680
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "host4",
|
|
||||||
"position": {
|
|
||||||
"x": 1000,
|
|
||||||
"y": 680
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "access4",
|
|
||||||
"position": {
|
|
||||||
"x": 1000,
|
|
||||||
"y": 540
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "access3",
|
|
||||||
"position": {
|
|
||||||
"x": 660,
|
|
||||||
"y": 520
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "access2",
|
|
||||||
"position": {
|
|
||||||
"x": 340,
|
|
||||||
"y": 520
|
|
||||||
}
|
|
||||||
},
|
|
||||||
{
|
|
||||||
"id": "access1",
|
|
||||||
"position": {
|
|
||||||
"x": 20,
|
|
||||||
"y": 520
|
|
||||||
}
|
|
||||||
}
|
|
||||||
],
|
],
|
||||||
"edgeAnnotations": [],
|
"edgeAnnotations": [],
|
||||||
"aliasEndpointAnnotations": [],
|
"aliasEndpointAnnotations": [],
|
||||||
|
|||||||
@@ -4,11 +4,18 @@ This directory contains network interface configuration files for Alpine Linux h
|
|||||||
|
|
||||||
## Files
|
## Files
|
||||||
|
|
||||||
|
### DC hosts
|
||||||
|
|
||||||
- `host1_interfaces` - Configuration for host1 (VLAN 40, IP 10.40.40.101)
|
- `host1_interfaces` - Configuration for host1 (VLAN 40, IP 10.40.40.101)
|
||||||
- `host2_interfaces` - Configuration for host2 (VLAN 34, IP 10.34.34.102)
|
- `host2_interfaces` - Configuration for host2 (VLAN 34, IP 10.34.34.102)
|
||||||
- `host3_interfaces` - Configuration for host3 (VLAN 40, IP 10.40.40.103)
|
- `host3_interfaces` - Configuration for host3 (VLAN 40, IP 10.40.40.103)
|
||||||
- `host4_interfaces` - Configuration for host4 (VLAN 78, IP 10.78.78.104)
|
- `host4_interfaces` - Configuration for host4 (VLAN 78, IP 10.78.78.104)
|
||||||
|
|
||||||
|
### Campus hosts
|
||||||
|
|
||||||
|
- `campus-host1_interfaces` - Configuration for campus-host1 (VLAN 50 stretched L2 10.50.50.101, VLAN 60 VRF gold 10.60.60.101)
|
||||||
|
- `campus-host2_interfaces` - Configuration for campus-host2 (VLAN 50 stretched L2 10.50.50.102, VLAN 70 VRF gold 10.60.70.102)
|
||||||
|
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
Each file is mounted to `/etc/network/interfaces` in its respective host container via ContainerLab's `binds` feature:
|
Each file is mounted to `/etc/network/interfaces` in its respective host container via ContainerLab's `binds` feature:
|
||||||
|
|||||||
Reference in New Issue
Block a user