HTTP 400 错误请求 (请求标头过长) 对 HTTP 请求的响应

当需要 Kerberos 身份验证的 HTTP 请求发送到托管在 Internet Information Services (IIS) 上并配置为使用 Kerberos 身份验证的网站时,HTTP 请求标头会很长。 本文有助于解决 HTTP 请求标头过长时发生的 HTTP 400 错误。

原始产品版本:Windows Server 2016
原始 KB 编号: 2020943

症状

需要 Kerberos 身份验证的 HTTP 请求将从浏览器发送到托管在 IIS 上的网站。 网站配置为使用 Kerberos 身份验证。 但是,你将收到类似于以下内容的错误消息,而不是接收预期的网页:

HTTP 400 - 错误请求(请求标头过长)

此响应可由包含 Windows 远程管理 (WinRM) 的任何 HTTP 请求生成。

原因

如果用户是许多 Active Directory 用户组的成员,则可能会出现此问题。

对服务器的 HTTP 请求在 WWW-Authenticate 标头中包含 Kerberos 令牌。 标头大小随用户组数的增加而增加。 如果 HTTP 标头或数据包大小的增量超过服务器上配置的限制,服务器可能会拒绝请求并发送错误消息作为响应。

解决方法 1:减少 Active Directory 组的数量

减少用户所属 Active Directory 组的数量。

解决方法 2:设置 MaxFieldLength 和 MaxRequestBytes 注册表项

增加服务器上MaxFieldLengthMaxRequestBytes注册表项的设置,使用户的请求标头不超过这些值。 要确定适当的设置,请使用以下计算方法:

  1. 使用以下文章中所述的公式计算用户的 Kerberos 令牌的大小:
    用户属于多个组时 Kerberos 身份验证的问题

  2. 将服务器上MaxFieldLengthMaxRequestBytes的值设置为 4/3 * T 字节,其中 T 是用户的令牌大小(以字节为单位)。 HTTP 使用 base64 编码对 Kerberos 令牌进行编码。

    注意

    这会将令牌中每三个字节替换为四个 base64 编码字节。 重启 HTTP 服务之前,对注册表所做的更改不会生效。 此外,可能必须重启任何相关服务,例如 IIS 服务。

根据应用程序环境,还可以通过将网站配置为使用 Windows NT LAN Manager (NTLM) 而不是 Kerberos 来解决此问题。 某些应用程序环境需要使用 Kerberos 身份验证来进行委派。 我们认为 Kerberos 身份验证比 NTLM 更安全。 建议在考虑安全性和委派后果之前,不要禁用 Kerberos 身份验证。

更多信息

默认情况下,没有 MaxFieldLength 注册表项。 此项指定每个 HTTP 请求标头的最大大小限制。 MaxRequestBytes 注册表项指定请求行和标头的总大小上限。 通常,此注册表项与 MaxRequestBytes 注册表项一起配置。 如果 MaxRequestBytes 值低于 MaxFieldLength 值,则会调整 MaxFieldLength 值。 在大型 Active Directory 环境中,如果这两个条目的值未设置成足够高的值,用户可能会遇到登录失败。

对于 IIS 6.0 及更高版本,MaxFieldLengthMaxRequestBytes 注册表项位于以下子项中:
HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\HTTP\Parameters

设置下表中所示项值:

Name 值类型 数值数据
MaxFieldLength DWORD (4/3 * T 字节) + 200
MaxRequestBytes DWORD (4/3 * T 字节) + 200

还可以将注册表项设置为其最大值,如下表所示。 对注册表设置进行任何更改之前,请考虑所有潜在的安全影响。

Name 值类型 数值数据
MaxFieldLength DWORD 65536(12 月)或 10000(十六进制)
MaxRequestBytes DWORD 16777216(12 月)或 1000000(十六进制)

重要

更改这些注册表项是极其危险的。 这些项允许将较大的 HTTP 数据包发送到 IIS。 这反过来又可能导致 Http.sys 使用更多内存。 因此,此类更改可能会增加计算机面对恶意攻击的脆弱性。

如果将 MaxFieldLength 设置为其最大值 64 KB,则 MaxTokenSize 注册表值应设置为 3/4 * 64 = 48 KB。 有关 MaxTokenSize 设置的详细信息,请参阅用户属于多个组时 Kerberos 身份验证的问题

References