bgpd: harden attribute parsing and packet handling in a few places - #21095
Conversation
Greptile SummaryThis PR applies five security fixes across BGP attribute parsing and packet handling to prevent buffer over-reads and incorrect continued processing after error conditions. Key changes:
Confidence Score: 4/5
Important Files Changed
Flowchart%%{init: {'theme': 'neutral'}}%%
flowchart TD
A[Receive BGP UPDATE / CAPABILITY / ROUTE-REFRESH] --> B{Message type?}
B -->|ROUTE-REFRESH| C{subtype != 0?}
C -->|Yes| D{msg_length == 4?}
D -->|No| E[bgp_notify_send INVALID_MSG_LEN\n+ return BGP_Stop β
FIXED]
D -->|Yes| F{subtype > 2?}
F -->|Yes| G[flog_err + return BGP_PACKET_NOOP β
FIXED]
F -->|No| H[Process ORF data]
B -->|CAPABILITY: GRACEFUL_RESTART| I[data = pnt + 3\nend = data + hdr->length β
FIXED\nlen = end - data]
I --> J{len < 2?}
J -->|Yes| K[Error: invalid length, return]
J -->|No| L[Parse gr_restart_flag_time\nIterate AFI/SAFI entries]
B -->|UPDATE: AIGP attr| M[bgp_attr_aigp_get_tlv_metric]
M --> N{length >= tlv_length? β
FIXED}
N -->|No| O[flog_err + return false]
N -->|Yes| P[Read metric value]
B -->|UPDATE: Tunnel Encap attr| Q{subtype < 128?}
Q -->|Yes| R{length >= 2? β
FIXED}
R -->|No| S[bgp_attr_malformed]
R -->|Yes| T[Read 1-byte sublength]
Q -->|No| U{length >= 3? β
FIXED}
U -->|No| S
U -->|Yes| V[Read 2-byte sublength]
|
f70941e to
e0c7d40
Compare
The NOTIFY tears down the session asynchronously, but the function continues parsing attacker-controlled bytes as ORF data before the session actually closes. Signed-off-by: Donatas Abraitis <donatas@opensourcerouting.org>
β¦ability
The GR function computes end 3 bytes too early (pnt vs data), causing
it to stop parsing 3 bytes before the real end. For a carefully
crafted GR capability, the last AFI/SAFI entry (4 bytes) is silently
dropped.
Dynamic capability header is:
+------------------------------+
| Action (1 octet) |
+------------------------------+
| Capability Code (1 octet) |
+------------------------------+
| Capability Length (1 octet) |
+------------------------------+
| Capability Value (variable) |
+------------------------------+
So we set wrongly the end of the packet (too early).
Signed-off-by: Donatas Abraitis <donatas@opensourcerouting.org>
If "length" is 1 before the subtraction, "length -= 2" wraps to 65535 (unsigned). The subsequent "sublength > length" check then passes when it should fail, because length is now enormous. The parser consumes bytes from adjacent attributes, corrupting the overall attribute parse state. The STREAM_READABLE check at line 3184 prevents actual buffer overflows, but attribute boundary violations can cause incorrect route processing. Signed-off-by: Donatas Abraitis <donatas@opensourcerouting.org>
e0c7d40 to
5e55e12
Compare
When data + 1 == end (exactly 1 byte remaining, sufficient to read the length byte), the function incorrectly rejects the capability. Same issue at line 3498 for domain name length. Also, hostname len can't be 0 (while domainname - can), so let's fix this too. Signed-off-by: Donatas Abraitis <donatas@opensourcerouting.org>
|
@Mergifyio backport stable/10.6 stable/10.5 stable/10.4 |
β Backports have been createdDetails
Cherry-pick of f31897c has failed: Cherry-pick of 5e55e12 has failed: Cherry-pick of 3e34a1a has failed: To fix up this pull request, you can check it out locally. See documentation: https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/reviewing-changes-in-pull-requests/checking-out-pull-requests-locally
Cherry-pick of f31897c has failed: Cherry-pick of 5e55e12 has failed: Cherry-pick of 3e34a1a has failed: To fix up this pull request, you can check it out locally. See documentation: https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/reviewing-changes-in-pull-requests/checking-out-pull-requests-locally |
bgpd: harden attribute parsing and packet handling in a few places (backport #21095)
No description provided.