segunda-feira, 24 de janeiro de 2011

ASP.NET - Vulnerabilidade - Open Redirection Attacks



O que é?

Qualquer aplicação web que redireciona para uma URL que é especificado através do request, tais como os dados querystring ou de forma potencialmente podem ser alterados para redirecionar os usuários para um URL maliciosa. Esta violação é chamado um ataque de redirecionamento aberto (Open Redirection Attacks).

Como evitar? 

Protegendo Aplicações ASP.NET MVC 1.0 e MVC 2 


Podemos promover três mudanças em nossos aplicativos existentes em ASP.NET MVC 1.0 e 2, incluindo o IsLocalUrl método auxiliar () e alterar o evento LogOn para validar o parâmetro ReturnUrl.

O IsLocalUrl () método da classe 3 ASP.NET MVC UrlHelper

public bool IsLocalUrl(string url) {
    return System.Web.WebPages.RequestExtensions.IsUrlLocalToHost(
        RequestContext.HttpContext.Request, url);
}

IsUrlLocalToHost () método da classe requestExtensions System.Web.WebPages


public static bool IsUrlLocalToHost(this HttpRequestBase request, string url) {
    if (url.IsEmpty()) {
        return false;
    }
 
    Uri absoluteUri;
    if (Uri.TryCreate(url, UriKind.Absolute, out absoluteUri)) {
        return String.Equals(request.Url.Host, absoluteUri.Host, 
                    StringComparison.OrdinalIgnoreCase);
    }
    else {
        bool isLocal = !url.StartsWith("http:", StringComparison.OrdinalIgnoreCase)
            && !url.StartsWith("https:", StringComparison.OrdinalIgnoreCase)
            && Uri.IsWellFormedUriString(url, UriKind.Relative);
        return isLocal;
    }
}

Vamos adicionar o IsLocalUrl () para o AccountController, mas você é encorajado a adicionar em uma classe auxiliar separada, se possível. Nós vamos fazer duas pequenas alterações no ASP.NET MVC versão 3 do IsLocalUrl () para que ele irá trabalhar por dentro da AccountController.


IsLocalUrl () método, que foi modificado para uso com uma classe Controller MVC


//Note: This has been copied from the System.Web.WebPages RequestExtensions class
private bool IsLocalUrl(string url)
{
    if (string.IsNullOrEmpty(url))
    {
        return false;
    }
 
    Uri absoluteUri;
    if (Uri.TryCreate(url, UriKind.Absolute, out absoluteUri))
    {
        return String.Equals(this.Request.Url.Host, absoluteUri.Host, 
                    StringComparison.OrdinalIgnoreCase);
    }
    else
    {
        bool isLocal = !url.StartsWith("http:", StringComparison.OrdinalIgnoreCase)
            && !url.StartsWith("https:", StringComparison.OrdinalIgnoreCase)
            && Uri.IsWellFormedUriString(url, UriKind.Relative);
        return isLocal;
    }
}

Agora podemos chamar nossa ação LogOn para validar o parâmetro ReturnUrl, como mostrado no código a seguir.

Atualizado Método de Logon que valida o parâmetro ReturnUrl


[HttpPost] public ActionResult LogOn(LogOnModel model, string returnUrl) { 
    if (ModelState.IsValid) 
    { 
        if (MembershipService.ValidateUser(model.UserName, model.Password)) 
        { 
            FormsService.SignIn(model.UserName, model.RememberMe); 
            if (IsLocalUrl(returnUrl)) 
            { 
                return Redirect(returnUrl); 
            } 
            else 
            { 
                return RedirectToAction("Index", "Home"); 
            } 
        } 
        else 
        { 
            ModelState.AddModelError("", 
                            "The user name or password provided is incorrect."); 
        } 
    }
}

Resumo

Ataques de redirecionamento aberto pode ocorrer quando o redirecionamento deURLs são passados como parâmetros na URL para um aplicativo. O ASP.NET MVC3  inclui código para proteger contra ataques de redirecionamento aberto.Você pode adicionar esse código com algumas modificações para aplicações ASP.NET MVC 1.0 e 2.0

fontes: