Root Guard vs. Loop Guard vs. BPDU Guard
Three features protect spanning tree topology. Understanding when to use each is critical:
(This article is part of the PingLabz STP series - the full spanning-tree guide maps the whole cluster in reading order.)
This article covers Root Guard and Loop Guard in detail.
Root Guard: Preventing Unauthorized Root Bridges
Root Guard prevents a switch from ever becoming the root bridge on a specific VLAN, no matter what priority or MAC address it claims.
Scenario: Why Root Guard Matters
┌──────────────┐
│ Core (ISP) │
│ Root Bridge │
└──────┬───────┘
│
┌─────────┴─────────┐
│ │
┌──────┐ ┌──────┐
│ SW1 │ │ SW2 │
│Dist. │ │Dist. │
└──┬───┘ └──┬───┘
│ │
┌──┴──────────┬───────┴──┐
│ │ │
┌─────┐ ┌─────┐ ┌─────┐
│ SW3 │ │ SW4 │ │ SW5 │
│Acc. │ │Acc. │ │Acc. │
└─────┘ └─────┘ └─────┘
(User unplugs uplink from SW1 and
plugs a rogue switch claiming priority 0)
Result WITHOUT Root Guard:
Rogue becomes root. Traffic reconverges
through rogue. Chaos.
Result WITH Root Guard:
Root Guard blocks the rogue, STP continues
normally through existing root.
Root Guard Configuration
Enable Root Guard on designated ports that face away from the root, such as distribution downlinks toward access switches. Never put it on a root port or an uplink toward the root:
SW1(config)# interface GigabitEthernet 1/0/1
SW1(config-if)# spanning-tree guard root
SW1(config-if)# exit
This single command tells the switch: "If a BPDU arrives on this port claiming to be root for any VLAN, block this port instead of accepting the new root."
On Multiple Ports
SW1(config)# interface range GigabitEthernet 1/0/1-2
SW1(config-if-range)# spanning-tree guard root
SW1(config-if-range)# exit
Verify Root Guard
SW1# show spanning-tree interface GigabitEthernet 1/0/1 detail
Role: Designated
State: Forwarding
Guard: Root ← Root Guard enabled
When Root Guard is active, a blocking condition is called "root-inconsistent" instead of "discarding". View it with:
SW1# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
Number of inconsistent ports (segments) in the system : 0
A non-zero count with "Root Inconsistent" next to a port means Root Guard is blocking it because a superior BPDU arrived on that port.
Real-World Root Guard Scenario
Test Setup: SW3 (access) with Root Guard on user-facing designated port Gi1/0/10
SW3(config)# interface GigabitEthernet 1/0/10
SW3(config-if)# spanning-tree guard root
SW3(config-if)# end
Normal State
SW3# show spanning-tree vlan 10
VLAN0010
Root ID Priority 4096
MAC-address 0022.55a6.5801
Bridge ID Priority 32768
MAC-address 0055.8844.2203
Interface Role Sts Cost Prio.Nbr Type
Gi1/0/25 Root FWD 4 128.25 P2p
Gi1/0/10 Desg FWD 4 128.10 P2p
Gi1/0/25 is the root port (forwards toward the actual root). Gi1/0/10 is a designated port, which is where Root Guard belongs. Root Guard on the root port would block SW3's own path to the root.
Simulate Rogue Switch Sending Superior BPDU
Someone plugs a rogue switch claiming priority 0 into Gi1/0/10 on SW3:
[Rogue BPDU arrives on Gi1/0/10]
Effect with Root Guard
SW3# show spanning-tree vlan 10
VLAN0010
Root ID Priority 4096
MAC-address 0022.55a6.5801 ! Original root
Bridge ID Priority 32768
MAC-address 0055.8844.2203
Interface Role Sts Cost Prio.Nbr Type
Gi1/0/25 Root FWD 4 128.25 P2p
Gi1/0/10 Desg BKN*4 128.10 P2p *ROOT_Inc
↑
"BKN* ... ROOT_Inc" = root inconsistent
Gi1/0/10 is in the root-inconsistent state (BKN*, ROOT_Inc), blocking traffic. The rogue switch's BPDU is ignored. Gi1/0/25 stays the root port and the network topology is unaffected.
Check inconsistent ports:
SW3# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
VLAN0010 GigabitEthernet1/0/10 Root Inconsistent
Number of inconsistent ports (segments) in the system : 1
IT Response
SW3# show spanning-tree vlan 10 root
Root is a bridge (not this switch)
Root port is Gi1/0/25
! Check what's on the other end
show cdp neighbors interface Gi1/0/25
Capability Codes: R - Router, T - Trans Bridge, B - Source Route Bridge
S - Switch, H - Host, I - IGMP, r - repeater
Device ID Local Intrfce Holdtme Capability Platform
SW1 Gi1/0/25 120 S I Catalyst 9300
The uplink to SW1 is correct and the root hasn't moved. The rogue switch is on Gi1/0/10. Find and isolate it.
Once the rogue is removed:
! Gi1/0/10 recovers automatically:
SW3# show spanning-tree vlan 10
Interface Role Sts Cost Prio.Nbr Type
Gi1/0/25 Root FWD 4 128.25 P2p
Gi1/0/10 Desg FWD 4 128.10 P2p
Loop Guard: Preventing Loops from Unidirectional Links
Loop Guard protects against topology loops caused by unidirectional link failures. If a link carries traffic one direction but fails in the other direction (e.g., due to bad fiber, SFP, or UDLD disabled), blocking ports might transition to forwarding, creating loops.
Scenario: Why Loop Guard Matters
SW1 (Root)
│
Gi0 (sends BPDUs)
│
(GOOD LINK)
│
Gi1 (receives BPDUs)
SW2
Normal state: Both switches send BPDUs correctly.
Now, RX (receive) direction of the link fails:
SW1 (Root)
│
Gi0 (sends BPDUs)
↓
✗ RX FAILS
✗ (BPDUs don't arrive at SW2)
│
Gi1 (no BPDUs received)
SW2
│
(SW2 thinks root is gone)
Without Loop Guard:
SW2 perceives no BPDUs from root port.
↓
"Root must be down!"
↓
Alternate/backup port transitions to Forwarding
↓
Loop created: frames forwarded in both directions
↓
Network congestion
With Loop Guard:
SW2 perceives no BPDUs on its root/alternate port (that should receive them).
↓
"This is suspicious - unidirectional link!"
↓
Port enters loop-inconsistent state (blocked)
↓
No loop. Network continues normally.
Loop Guard Configuration
Enable Loop Guard on ports where unidirectional failures are possible (root and alternate ports):
SW2(config)# interface GigabitEthernet 1/0/25
SW2(config-if)# spanning-tree guard loop
SW2(config-if)# exit
On Multiple Ports
SW2(config)# interface range GigabitEthernet 1/0/25-28
SW2(config-if-range)# spanning-tree guard loop
SW2(config-if-range)# exit
Verify Loop Guard
SW2# show spanning-tree interface GigabitEthernet 1/0/25 detail
Role: Alternate
State: Blocking
Guard: Loop ← Loop Guard enabled
Check Loop Inconsistencies
SW2# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
VLAN0010 GigabitEthernet1/0/26 Loop Inconsistent
Number of inconsistent ports (segments) in the system : 1
A port marked "Loop Inconsistent" means Loop Guard is blocking it due to missing BPDUs.
Loop Guard Recovery
Unlike BPDU Guard, Loop Guard does not have automatic recovery via errdisable recovery. A port in loop-inconsistent state recovers naturally when BPDUs are received again:
! Unidirectional link restored (cable reseated, UDLD recovers)
! BPDUs arrive again
↓
Loop Guard unblocks port automatically
Verify recovery:
SW2# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
Number of inconsistent ports (segments) in the system : 0 ! Port recovered
There's no command that forces a loop-inconsistent port to recover; fix the link so BPDUs flow again. This command is sometimes suggested, but it won't do it:
SW2# clear spanning-tree detected-protocols
It only restarts the STP protocol migration process (renegotiating MST/RSTP vs. legacy 802.1D BPDUs with neighbors). It doesn't clear loop-inconsistent.
Lab Configuration: Root Guard + Loop Guard
Lab topology: Catalyst 9300 (SW1, SW2 Distribution; SW3, SW4 Access).
Distribution Switches (SW1, SW2): Root Guard on Downlinks
Root Guard prevents a lower-layer switch from becoming root:
SW1(config)# interface range GigabitEthernet 1/0/1-2
SW1(config-if-range)# description Downlinks to Access
SW1(config-if-range)# spanning-tree guard root
SW1(config-if-range)# exit
SW1(config)# end
Access Switches (SW3, SW4): Loop Guard on All Uplinks
Loop Guard prevents unidirectional link loops:
SW3(config)# interface range GigabitEthernet 1/0/25-28
SW3(config-if-range)# description Uplinks to Distribution
SW3(config-if-range)# spanning-tree guard loop
SW3(config-if-range)# exit
SW3(config)# end
Repeat for SW4.
Verification Across Network
From SW1:
SW1# show spanning-tree interface brief
Interface Port-Type Status Portfast
------- ------- ------- --------
Gi1/0/1 DesgFWD FWD Disabled (Guard: Root)
Gi1/0/2 DesgFWD FWD Disabled (Guard: Root)
From SW3:
SW3# show spanning-tree interface brief
Interface Port-Type Status Portfast
------- ------- ------- --------
Gi1/0/25 Root FWD Disabled (Guard: Loop)
Gi1/0/26 Altern BLK Disabled (Guard: Loop)
Differences: Root Guard vs. Loop Guard
Root Guard:
- Where: Designated ports (downlinks, facing away from the root)
- Detects: Superior BPDU claiming to be root
- Action: Blocks (root-inconsistent)
- Recovery: Automatic when superior BPDU stops
- Best for: Protecting against rogue root bridges
Loop Guard:
- Where: Root and Alternate ports
- Detects: Loss of BPDUs on blocking port
- Action: Blocks (loop-inconsistent)
- Recovery: Automatic when BPDUs resume
- Best for: Protecting against unidirectional link failures
Both are essential. Root Guard stops unauthorized roots. Loop Guard stops unidirectional link loops.
Loop Guard + UDLD: Comprehensive Protection
UDLD (Unidirectional Link Detection) detects unidirectional links in real-time by sending echo frames. Paired with Loop Guard, it provides comprehensive protection:
SW3(config)# udld enable
SW3(config)# udld aggressive
SW3(config)# interface range GigabitEthernet 1/0/25-28
SW3(config-if-range)# udld port aggressive
SW3(config-if-range)# spanning-tree guard loop
SW3(config-if-range)# exit
SW3(config)# end
Effect:
If a unidirectional link is detected by UDLD:
- UDLD immediately error-disables the port (faster than Loop Guard)
- Loop Guard provides redundant protection if UDLD is disabled
Verify UDLD Status
SW3# show udld neighbors
Port Neighbor Device Neighbor Port Status
Gi1/0/25 SW1 Gi1/0/1 Bidirectional
Gi1/0/26 SW2 Gi1/0/2 Bidirectional
Verification Commands
View Root Guard Status
SW1# show spanning-tree guard root
Interface Role Guard Status
Gi1/0/1 Desg Root OK
Gi1/0/2 Desg Root OK
View Loop Guard Status
SW3# show spanning-tree guard loop
Interface Role Guard Status
Gi1/0/25 Root Loop OK
Gi1/0/26 Alt Loop OK
Combined Detail View
SW3# show spanning-tree interface Gi1/0/25 detail
Role: Root
State: Forwarding
Guard: Loop
Loop Guard: Enabled
Common Mistakes
Mistake 1: Root Guard on Blocking Ports
Problem:
! WRONG: Root Guard on alternate/blocking port
interface GigabitEthernet 1/0/26
spanning-tree guard root ! Misplaced
exit
Root Guard belongs on designated ports that face away from the root. On an alternate port it backfires: an alternate port receives superior BPDUs by design, so Root Guard moves it to root-inconsistent.
Fix:
! Correct placement:
interface GigabitEthernet 1/0/1 ! Designated downlink (SW1)
spanning-tree guard root
exit
interface GigabitEthernet 1/0/26 ! Alternate port (SW3, blocks)
spanning-tree guard loop
exit
Mistake 2: Loop Guard Without UDLD on Fiber Links
Problem:
! Fiber uplink (prone to unidirectional failure)
interface GigabitEthernet 1/0/25
spanning-tree guard loop
! UDLD not enabled
exit
If the fiber has a unidirectional failure, Loop Guard will eventually detect it (after a timeout), but UDLD would catch it immediately.
Fix:
interface GigabitEthernet 1/0/25
udld port aggressive
spanning-tree guard loop
exit
Mistake 3: Both Root Guard and Loop Guard on Same Port
Problem:
! WRONG: Both guards on same port
interface GigabitEthernet 1/0/25
spanning-tree guard root
spanning-tree guard loop
exit
A port can have only one guard. The second command overrides the first.
Fix: Choose the appropriate guard for the port's role:
! Designated port (SW1 downlink)
interface GigabitEthernet 1/0/1
spanning-tree guard root ! Only this
exit
! Alternate port (SW3 backup uplink)
interface GigabitEthernet 1/0/26
spanning-tree guard loop ! Only this
exit
Mistake 4: Not Enabling Root Guard on Access-Layer Designated Ports
Problem: Root Guard enabled on distribution downlinks but not on the access switch's user-facing ports, leaving a vulnerability:
! SW1 (Distribution): Root Guard enabled ✓
interface Gi1/0/1
spanning-tree guard root
exit
! SW3 (Access): Root Guard NOT enabled on user ports ✗
interface range Gi1/0/1-24
! No Root Guard
exit
A rogue switch on one of SW3's user ports can claim root inside SW3. SW1's Root Guard then blocks SW3's uplink as root-inconsistent, cutting SW3 off instead of just the rogue port.
Fix: Enable Root Guard on the access switch's designated user-facing ports too, and keep Loop Guard on its uplinks:
! SW3 (Access): Add Root Guard on user ports
interface range Gi1/0/1-24
spanning-tree guard root
exit
interface Gi1/0/26
spanning-tree guard loop ! Loop Guard on backup
exit
Real-World Deployment
Campus Network with Root Bridge on Distribution Layer
┌─ Core (Root Bridge)
│
┌──┴──┐
│ │
SW1 SW2 (Distribution, Primary Root)
(Guard: Root on downlinks)
│ │
┌──┴──┬──┴──┐
│ │ │
SW3 SW4 SW5 (Access)
(Guard: Loop on uplinks)
Configuration pattern:
! SW1, SW2: Root guard on all downlinks to access
spanning-tree guard root
! SW3, SW4, SW5: Loop guard on all uplinks
spanning-tree guard loop
! All: UDLD aggressive on fiber
udld port aggressive
Data Center with MST
Even with MSTP (Article 14), Root Guard and Loop Guard apply:
Spine switches (Root Bridge per instance)
└─ Guard: Root on downlinks to leaves
Leaf switches (ForwardingPorts per instance)
└─ Guard: Loop on all uplinks to spine
└─ UDLD aggressive on all links
Troubleshooting Root Guard and Loop Guard
Symptom: Port in Root-Inconsistent State
Cause: Root Guard blocking a port because a superior BPDU was received.
Investigation:
SW1# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
VLAN0010 GigabitEthernet1/0/1 Root Inconsistent
Number of inconsistent ports (segments) in the system : 1
Check the neighboring device:
show cdp neighbors interface Gi1/0/1
Device ID Local Intrfce Holdtme Capability
UnknownSwitch Gi1/0/1 120 S
An unknown switch is on the other end of this port, claiming to be root. Find and isolate it.
Symptom: Port in Loop-Inconsistent State
Cause: Loop Guard blocking a port because BPDUs stopped arriving.
Investigation:
SW3# show spanning-tree inconsistentports
Name Interface Inconsistency
-------------------- ------------------------ ------------------
VLAN0010 GigabitEthernet1/0/26 Loop Inconsistent
Number of inconsistent ports (segments) in the system : 1
Check link status:
SW3# show interfaces Gi1/0/26
GigabitEthernet1/0/26 is up, line protocol is up
! Link is up but no BPDUs arriving - likely unidirectional link
show udld neighbors interface Gi1/0/26
Port Neighbor Device Neighbor Port Status
Gi1/0/26 SW2 Gi1/0/2 Unidirectional
UDLD confirms unidirectional failure. Replace fiber or reseat connectors.
Symptom: Legitimate Rerouting Blocked by Root Guard
Scenario: You intentionally change which switch is root bridge, and Root Guard on existing uplinks starts blocking.
Cause: Old root is no longer root, but Root Guard is still configured on the uplink expecting it.
Fix: Verify the new root is correctly elected:
show spanning-tree vlan 10 root
Root ID Priority 4096
MAC-address 0055.8844.2200 ! New root
Root Guard can't tell a planned root move from a rogue one. If the new root legitimately sits behind a Root Guard port, that port stays root-inconsistent until you remove Root Guard from it, so update Root Guard placement whenever you move the root.
What's Next
Root Guard and Loop Guard protect against topology corruption on uplinks and designated ports. However, BPDU filtering is the final STP protection mechanism but is rarely used due to its risks. Article 13 covers "Configuring BPDU Filter on Cisco Switches," explaining when BPDU Filter is appropriate and why it's generally dangerous in production networks.
Related STP Articles
- BPDU Guard Configuration: Protecting Your STP Topology
- Configuring BPDU Filter on Cisco Switches
- Troubleshooting Errdisable and STP Guard Features
- STP Design Best Practices for Enterprise Campus Networks