You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

Veracode开放重定向漏洞(CWE-601)求助:URL校验方法无效

修复开放重定向(CWE-601)漏洞:改进你的URL校验方法

首先,咱们先拆解下你当前的GetValidLocalUrl方法为什么挡不住开放重定向攻击:

你的校验逻辑是判断URLhttp:/https:开头,且是合法的相对URI就认为是安全的,但这里有个致命漏洞:协议相对URL(比如//evil.com/path)不会被你的开头检查拦截,而浏览器会自动用当前页面的协议(http/https)去请求这个外部站点,直接触发开放重定向。

先贴出你现有的代码方便对比:

public static string GetValidLocalUrl(string url) { 
    bool isLocal = false; 
    if (string.IsNullOrEmpty(url)) { } 
    else { 
        isLocal = !url.StartsWith("http:", StringComparison.OrdinalIgnoreCase) && !url.StartsWith("https:", StringComparison.OrdinalIgnoreCase) && Uri.IsWellFormedUriString(url, UriKind.Relative); 
    } 
    if (isLocal) return url; 
    else return string.Empty; 
}

改进后的校验方案

我调整了校验逻辑,重点解决协议相对URL的绕过问题,同时增加了绝对URL的可信主机验证(允许合法的本地绝对URL):

public static string GetValidLocalUrl(string url, string trustedHost) 
{
    // 空URL直接返回空
    if (string.IsNullOrWhiteSpace(url))
        return string.Empty;

    // 拦截协议相对URL(//example.com),这是最常见的绕过手段
    if (url.StartsWith("//", StringComparison.OrdinalIgnoreCase))
        return string.Empty;

    // 尝试解析URL,确保格式合法
    if (!Uri.TryCreate(url, UriKind.RelativeOrAbsolute, out Uri parsedUri))
        return string.Empty;

    // 如果是绝对URL,必须匹配可信主机(比如你的应用域名)
    if (parsedUri.IsAbsoluteUri)
    {
        if (string.Equals(parsedUri.Host, trustedHost, StringComparison.OrdinalIgnoreCase))
            return url;
        else
            return string.Empty;
    }

    // 相对URL,确保格式合法(避免无效路径)
    if (Uri.IsWellFormedUriString(url, UriKind.Relative))
        return url;

    // 所有不满足的情况返回空
    return string.Empty;
}

安全使用方式

在调用Response.Redirect时,必须严格使用校验后的URL,并且兜底到安全页面:

// 替换成你的应用域名,比如"myapp.com"
string trustedHost = "your-app-domain.com";
string requestedUrl = Request.QueryString["redirectUrl"]; // 假设从请求中获取跳转地址

string safeUrl = GetValidLocalUrl(requestedUrl, trustedHost);
if (!string.IsNullOrEmpty(safeUrl))
{
    Response.Redirect(safeUrl);
}
else
{
    // 校验失败时,重定向到安全的默认页面(比如首页)
    Response.Redirect("/");
}

关键修复点说明

  • 新增了对//开头的协议相对URL的拦截,彻底堵住这类绕过
  • 使用Uri.TryCreate替代单纯的字符串检查,更可靠地判断URL格式
  • 允许合法的本地绝对URL(比如用户输入https://your-app-domain.com/profile),同时拦截外部绝对URL
  • 保留了相对URL的合法性校验,避免无效路径跳转

内容的提问来源于stack exchange,提问作者Vangelis Pablo

火山引擎 最新活动