资讯动态

Envoy 修复 CVE-2026-48521:基于 ALPN 自动协商上游协议时 HTTP/3 空指针崩溃深度解析

发布时间:2026/9/10 22:13:13 来源:尧图企业网站定制
Envoy 修复 CVE-2026-48521基于 ALPN 自动协商上游协议时 HTTP/3 空指针崩溃深度解析【免费下载链接】envoyCloud-native high-performance edge/middle/service proxy项目地址: https://gitcode.com/GitHub_Trending/en/envoy本指南围绕 Envoy 上游链路中一项重要的安全修复展开当集群配置为基于 ALPNApplication-Layer Protocol Negotiation自动选择与上游服务器之间的通信协议且上游通过 HTTP/3 响应时Envoy 可能因空指针解引用null dereference发生异常进程终止即 CVE-2026-48521对应 GitHub 安全公告 GHSA-5vff-j9p4-38j3。读完本文你将理解该崩溃的触发场景、上游 HTTP/3 与自动协议协商的底层架构原理掌握如何正确配置 auto_config HTTP/3 上游、识别潜在空指针风险点并通过源码与测试用例验证修复行为。一、漏洞概要一次异常进程终止该修复记录于仓库的 changelog/current/bug_fixes 目录属于current未发布变更集中 bug_fixes 类别的安全修复条目。其描述的核心事实如下受影响场景Envoy 被配置为基于 ALPN 与上游服务器自动选择协议触发条件上游服务器使用 HTTP/3影响进程异常终止abnormal process termination即服务崩溃而非优雅退出根因空指针解引用null deref。对于边缘/中间/服务型代理而言进程级崩溃意味着所有经过该实例的在途连接被瞬间切断属于需要优先处理的高危缺陷。该条目标记为 CVE-2026-48521说明这是一次具有安全影响的公开漏洞修复。二、问题场景还原auto_config ALPN HTTP/3 上游要理解崩溃为何发生必须先弄清基于 ALPN 自动选择协议这一配置模式的语义。它对应 envoy.extensions.upstreams.http.v3.HttpProtocolOptions 中的auto_configAutoHttpConfig分支而不是固定协议explicit_http_config或跟随下游use_downstream_protocol_config。2.1 AutoHttpConfig 的协商语义从 AutoHttpConfig 的 proto 定义 可以看到关键约束使用该配置时集群可以在 HTTP/1 与 HTTP/2 之间选择具体使用哪个协议由与上游的 ALPN 协商结果决定如果上游不支持 ALPN则回退fail over到 HTTP/1该模式只能用于支持 ALPN 的传输套接字使用不支持 ALPN 的传输套接字会导致配置加载失败传输层可以配置自定义 ALPN但集群默认或自定义 ALPN 失败时的 ALPN 列表为h2,http/1.1。与 HTTP/1、HTTP/2 不同HTTP/3 不会被无条件启用只有在配置中存在http3_protocol_options且有服务器端支持 HTTP/3 的明确通告advertisement时才会使用。这正是本文漏洞场景的核心——自动协商链路中混入了 HTTP/3 这一条件性协议。2.2 HTTP/3 上游的特殊性上游 HTTP/3 架构说明 指出HTTP/3 上游支持比 HTTP/1/2 复杂得多原因在于当auto_config中配置了 HTTP/3 时Envoy只对通告了 HTTP/3 支持的服务器发起 HTTP/3 连接尝试通告来源是 HTTP Alt-SvcRFC 7838或 HTTPS DNS 资源记录没有这类通告时回退使用 HTTP/2 或 HTTP/1HTTP/3 运行在 QUIC基于 UDP之上而 HTTP/1、HTTP/2 基于 TCP。网络设备经常拦截 UDP 流量导致上游 HTTP/3 连接尝试被网络阻断而失败此时必须回退到 HTTP/2因此上游连接代码需要跟踪 HTTP/3 连接尝试是否持续失败避免发起注定失败的连接而在 HTTP/3 工作正常的网络上又要避免无谓地尝试 HTTP/2。这套既要探测、又要回退、还要记忆失败状态的机制引入了比固定协议模式更多的状态对象与异步回调路径一旦某个状态对象在特定时序下尚未初始化就被访问空指针解引用便可能发生——这正是本 CVE 的典型土壤。三、上游 HTTP/3 的核心组件源码级拆解围绕上述机制仓库中对应实现了三个核心组件可参见 ConnPoolGrid 实现 与 HTTP/3 上游文档。3.1 ConnectivityGridQUIC 与 TCP 双池路由ConnectivityGrid是一个ConnectionPool内部同时包装Http3ConnPoolImplQUIC 连接池即createHttp3Pool()创建的池见 conn_pool_grid.ccHttpConnPoolImplMixedTCP 混合连接池即createHttp2Pool()见 conn_pool_grid.cc。请求分派逻辑见 newStream 实现若 HTTP/3 当前可用shouldAttemptHttp3()且请求允许can_use_http3_优先使用 HTTP/3 池若 HTTP/3 已标记为 broken 或最近失败则不再延迟 TCP 尝试delay_tcp_attempt false立即并行发起 TCP 连接若 HTTP/3 未被通告alternate protocols cache 中没有记录请求直接进入混合TCP池若 HTTP/3 已通告且工作正常请求走 HTTP/3 池若 300ms 内未成功则同时向混合池发起请求谁先成功谁胜出对应 conn_pool_grid.cc 中的kDefaultTimeoutMs 300。这套双池竞速race逻辑中http3_pool_、http3_alternate_pool_等成员均为惰性创建getOrCreateHttp3Pool()若在创建/回调时序上出现空指针访问就会直接触发崩溃。3.2 HttpServerPropertiesCacheHTTP/3 通告的来源HttpServerPropertiesCache实现在 http_server_properties_cache_impl.cc负责追踪哪些服务器通告了 HTTP/3。通告来源是 Alt-Svc 响应头未来还将支持 HTTPS DNS RR目前只存储与请求相同主机名和端口的通告。与之对应的配置结构是 AlternateProtocolsCacheOptions关键字段包括字段说明默认值name缓存名称同名缓存在不同配置组件中被引用时各字段必须完全一致否则配置加载失败必填max_entries缓存最大条目数实现为近似值在每个 worker 线程上独立执行实际条目数可能因时序略超配置值1024key_value_store_config可选持久化 KV 存储将条目刷盘目前仅在并发度为 1 时支持无prepopulated_entries预置条目以 7 天生命周期预填充 HTTP/3 条目使 Envoy 对未通告的上游也尝试 HTTP/3会被 Alt-Svc 响应头覆盖无canonical_suffixes可选主机名后缀列表用于在可共享后缀的多个主机间共享 Alt-Svc 条目条目必须以.开头无3.3 HTTP/3 状态追踪失败记忆与退避Broken HTTP/3 追踪器负责记住哪些上游的 HTTP/3 连接不可用。其现代实现是 Http3StatusTrackerImpl状态机包含PendingHTTP/3 待定Broken已标记损坏进入退避FailedRecently最近失败Confirmed已确认可用。值得注意的细节架构文档描述的是首次损坏 5 分钟、再次损坏翻倍、上限 1 天但当前源码实现实际为初始损坏期为 1 秒DefaultExpirationTime{1}每次被标记损坏后按1 consecutive_broken_count_指数翻倍最大连续损坏计数为 17MaxConsecutiveBrokenCount 17即最长约 2^17 秒 ≈ 36 小时一旦被标记为Confirmed则计数归零、恢复初始 1 秒。以源码为准这在单元测试中有完整验证例如MarkBrokenWithBackoff用例依次断言损坏期为 1s → 2s → 4s → 8s见 测试文件第 67-99 行MarkBrokenWithBackoffMax用例则验证 2^17 秒封顶第 101-124 行。四、空指针风险的来源与修复要点由于 changelog 条目仅声明修复了空指针解引用导致的异常进程终止未披露具体修复代码我们只能结合源码结构推断该场景下可能的空指针来源以下为基于代码结构的推断非官方修复细节惰性池成员访问ConnectivityGrid的http3_pool_、http2_pool_均为惰性创建若在回调路径如onPoolFailure、onPoolReady、WrapperCallbacks的回调中某成员尚未通过getOrCreateXxxPool()创建即被解引用即为典型的空指针风险点。测试用例DoubleFailureThenSuccessSerial见 conn_pool_grid_test.cc 第 323-357 行专门覆盖了HTTP/3 池失败 → 交替池失败 → HTTP/2 池成功的完整回退链正说明这些回调路径节点密集、易出问题状态追踪器未就绪Http3StatusTracker与HttpServerPropertiesCache::Origin关联若alternate_protocols_缓存尚未创建或 origin 解析失败追踪器访问同样可能解引用空指针配置校验兜底仓库已在配置解析层强制约束——当auto_config启用 HTTP/3 时必须同时配置alternate_protocols_cache_options否则配置加载直接报错alternate protocols cache must be configured when HTTP/3 is enabled with auto_config见 upstreams/http/config.cc 第 92-98 行。这一校验从配置入口堵住了HTTP/3 已启用但缓存缺失的空状态。从工程角度此类修复通常包含两部分在崩溃路径上增加空指针判空/提前返回以及补充覆盖该时序的回归测试。建议运维侧以升级到包含该修复的版本为第一优先级。五、如何正确配置 auto_config HTTP/3 上游结合 AutoHttpConfig proto 与 上游 HTTP/3 文档 的Required configuration章节完整配置需要三处配合。5.1 集群侧auto_config 必须完整声明三种协议static_resources: clusters: - name: upstream_with_h3 connect_timeout: 5s type: STRICT_DNS load_assignment: cluster_name: upstream_with_h3 endpoints: - lb_endpoints: - endpoint: address: socket_address: address: upstream.example.com port_value: 443 transport_socket: name: envoy.transport_sockets.tls typed_config: type: type.googleapis.com/envoy.extensions.transport_sockets.tls.v3.UpstreamTlsContext sni: upstream.example.com typed_extension_protocol_options: envoy.extensions.upstreams.http.v3.HttpProtocolOptions: type: type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions auto_config: http_protocol_options: {} http2_protocol_options: {} http3_protocol_options: {} alternate_protocols_cache_options: name: default_alternate_protocols_cache max_entries: 1024要点说明auto_config下三种协议选项都必须出现HTTP/1、HTTP/2、HTTP/3缺一不可http3_protocol_options只负责允许 HTTP/3实际是否启用仍取决于上游是否通告Alt-Svc/HTTPS DNS RRalternate_protocols_cache_options在启用 HTTP/3 时为必填由 config.cc 校验逻辑 强制保证其name用于标识缓存实例由于AutoHttpConfig依赖 ALPNtransport_socket必须是支持 ALPN 的 TLS 套接字例如envoy.transport_sockets.tls的UpstreamTlsContext默认 ALPN 为h2,http/1.1。5.2 过滤器侧启用 Alternate Protocols Cache Filter为了让 Alt-Svc 响应头被解析并写入缓存还需要在 HTTP 连接管理器HttpConnectionManager的过滤器链中启用 alternate protocols cache 过滤器http_filters: - name: envoy.filters.http.alternate_protocols_cache typed_config: type: type.googleapis.com/envoy.extensions.filters.http.alternate_protocols_cache.v3.FilterConfig注意该过滤器的配置类型 FilterConfig 中原本的alternate_protocols_cache_options字段已标记废弃deprecated计划在 3.0 移除注释明确指出该字段会被忽略——过滤器将直接使用请求路由所对应集群的缓存。因此新的配置方式应为在集群auto_config.alternate_protocols_cache_options中声明缓存如 5.1 所示并确保该缓存名称与过滤器引用一致。5.3 验证与测试佐证仓库提供两层测试可验证行为状态追踪器单元测试test/common/http/http3_status_tracker_impl_test.cc覆盖初始化状态、标记 Broken、指数退避、封顶、Confirmed 重置、Broken→Confirmed→Broken 等全部状态迁移可用于确认失败记忆逻辑符合预期连接池网格集成测试test/common/http/conn_pool_grid_test.cc其中Success用例验证了HTTP/3 通告存在 → 走 QUIC 池 → 握手完成后标记 Confirmed第 286-304 行DoubleFailureThenSuccessSerial用例则验证了HTTP/3 池失败 → 不向上抛错 → 交替池失败 → 回退 HTTP/2 池成功 → 最终标记 HTTP/3 为 broken第 323-357 行这正是该场景下保证不崩溃、可优雅降级的核心路径。运行相关测试需要 Bazel 构建环境可参考bazel test //test/common/http:conn_pool_grid_test与//test/common/http:http3_status_tracker_impl_test对应的目标。六、升级与防护建议优先升级包含 CVE-2026-48521 修复的 Envoy 版本是首要动作尤其对使用auto_config且上游可能通告 HTTP/3 的集群审视配置确认集群的auto_config是否完整声明三种协议、是否已配置alternate_protocols_cache_options避免因缺少缓存配置导致的配置加载失败关注 UDP 可达性若上游实际部署在网络会拦截 UDP 的环境中HTTP/3 连接将持续失败此时依赖状态追踪器的退避机制回退 TCP——这正是本文所讲修复所保护的核心路径跟踪回归以 HTTP/3 状态追踪测试 和 连接池网格测试 为基线确认升级后上述失败回退与空指针防护行为仍被测试覆盖。参考依据仓库内证据索引修复条目changelogs/current/bug_fixes/http3__fixed-crash-due-to-null-deref.rst架构说明source/docs/http3_upstream.md协议定义api/envoy/extensions/upstreams/http/v3/http_protocol_options.proto、api/envoy/config/core/v3/protocol.proto过滤器定义api/envoy/extensions/filters/http/alternate_protocols_cache/v3/alternate_protocols_cache.proto核心实现source/common/http/conn_pool_grid.cc、source/common/http/http3_status_tracker_impl.cc、source/common/http/http_server_properties_cache_impl.cc、source/extensions/upstreams/http/config.cc测试用例test/common/http/conn_pool_grid_test.cc、test/common/http/http3_status_tracker_impl_test.cc、test/common/http/http_server_properties_cache_impl_test.cc【免费下载链接】envoyCloud-native high-performance edge/middle/service proxy项目地址: https://gitcode.com/GitHub_Trending/en/envoy创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价