mirror of
https://github.com/logicog/RTLPlayground.git
synced 2026-10-29 17:54:14 +08:00
stp: give auto-edge back to a port held by its own BPDU
stp_loop_hold_peer() takes operEdge away from the port that sent the BPDU we got back, though that port heard nothing itself. When the hold ran out the port stayed non-edge until its next link change, and every later state change on it counted as a topology change. Restore edge when the hold ends with the port still silent and auto-edge on, before the transition is reported, so the recovery itself is not a change. Hellos go out on edge ports too, so a loop that persists is caught again. The console column that shows seconds since the last BPDU is now called age[s]; it never was a receive count.
This commit is contained in:
1 parent
eb51128ec7
commit
4d009bc8e8
2 files changed
+17
-1
No files matched your search
@@ -268,6 +268,15 @@ is reported with one of the roles Root, Designated, Alternate, Backup or
|
|||||||
Disabled; Disabled covers a port with STP turned off on it, one shut down by
|
Disabled; Disabled covers a port with STP turned off on it, one shut down by
|
||||||
BPDU guard and one without link.
|
BPDU guard and one without link.
|
||||||
|
|
||||||
|
The console's `age[s]` column (previously labelled `bpdu`) is the elapsed
|
||||||
|
time since the last BPDU, capped at 255 seconds; it is not a receive count.
|
||||||
|
Use the web counters or `/stpcnt.json` for full receive counts.
|
||||||
|
|
||||||
|
An own BPDU received back on another port can temporarily hold its sending
|
||||||
|
port in discarding, even if that sending port has received no BPDUs itself.
|
||||||
|
When the hold expires, auto-edge is restored if the sending port has remained
|
||||||
|
silent. A continuing loop keeps the hold active.
|
||||||
|
|
||||||
BPDUs shorter than their type allows, judged by the 802.3 length field, are
|
BPDUs shorter than their type allows, judged by the 802.3 length field, are
|
||||||
dropped: 7 bytes for a TCN, 38 for a Config BPDU and 39 for an RST BPDU,
|
dropped: 7 bytes for a TCN, 38 for a Config BPDU and 39 for an RST BPDU,
|
||||||
LLC header included.
|
LLC header included.
|
||||||
|
|||||||
+8
-1
@@ -297,7 +297,7 @@ void stp_status(void) __banked
|
|||||||
print_string("changes ");
|
print_string("changes ");
|
||||||
print_short(stp_tc_count);
|
print_short(stp_tc_count);
|
||||||
write_char('\n');
|
write_char('\n');
|
||||||
print_string("port state role edge tx bpdu\n");
|
print_string("port state role edge tx age[s]\n");
|
||||||
for (stp_i = 0; stp_i < STP_ENTITIES; stp_i++) {
|
for (stp_i = 0; stp_i < STP_ENTITIES; stp_i++) {
|
||||||
if (!stp_ent_active(stp_i))
|
if (!stp_ent_active(stp_i))
|
||||||
continue;
|
continue;
|
||||||
@@ -1297,6 +1297,13 @@ void stp_timers(void) __banked
|
|||||||
print_string("STP: port learning ");
|
print_string("STP: port learning ");
|
||||||
print_port_nl(stp_i);
|
print_port_nl(stp_i);
|
||||||
} else {
|
} else {
|
||||||
|
/* A returned BPDU can hold its sending port even though
|
||||||
|
* that port never received one. Once the hold expires,
|
||||||
|
* recover auto-edge before the forwarding timer stops. */
|
||||||
|
if (stp_loop_held[stp_i] && (stp_pflags[stp_i] & STP_PF_AUTOEDGE)
|
||||||
|
&& !((stp_heard >> stp_i) & 1)
|
||||||
|
&& stp_bpdu_age[stp_i] > STP_EDGE_DELAY)
|
||||||
|
stp_pflags[stp_i] |= STP_PF_OPEREDGE;
|
||||||
stp_loop_held[stp_i] = 0;
|
stp_loop_held[stp_i] = 0;
|
||||||
stp_backup &= ~((uint16_t)1 << stp_i);
|
stp_backup &= ~((uint16_t)1 << stp_i);
|
||||||
stp_state_set(stp_i, 0b11);
|
stp_state_set(stp_i, 0b11);
|
||||||
|
|||||||
Reference in new issue
Block a user