Quebra de autenticação e gerenciamento de sessões (Broken Authentication and Session Management)
A Quebra de autenticação e gerenciamento de sessões (Broken Authentication and Session Management) é uma vulnerabilidade que ocorre quando um atacante consegue acessar o sistema ou aplicação utilizando credenciais inválidas ou explorando falhas na gestão das sessões – permitindo acesso a dados sensíveis ou operações críticas.
Neste artigo, discutiremos as possíveis consequências de uma falha de autenticação ou gerenciamento de sessões e apresentaremos exemplos de código em Java, Javascript e Python que demonstram esses problemas, bem como soluções para corrigi-los.
Prejuízos causados
Uma violação de autenticação e gerenciamento de sessões pode resultar em vazamento de informações confidenciais, perda de integridade de dados, acesso não autorizado a operações críticas, entre outros.
Por exemplo, um atacante pode obter acesso a uma conta bancária de um usuário, modificar ou excluir informações do sistema ou alterar as configurações de segurança. Isso pode resultar em perdas financeiras significativas e até mesmo na perda de confiança dos clientes.
Exemplo de código – Java
// Cenário vulnerável de Broken Authentication e Session Management em Javapublic
class LoginController {
private static Map<String, String> users = new HashMap<>();
public String login(String username, String password) {
if (users.containsKey(username) && users.get(username).equals(password)) {
// Criação de sessão para o usuário
autenticadoHttpSession session = request.getSession();
session.setAttribute("username", username);
return "dashboard";
} else {
return "login";
}
}
public String logout() {
// Finalização da sessão atual
HttpSession session = request.getSession(false);
if (session != null) {
session.invalidate();
}
return "login";
}
}
Para corrigir essa vulnerabilidade, é importante implementar uma gestão de sessão adequada, definindo um tempo limite para expiração de sessões inativas, além de utilizar um gerador de token aleatório para identificação das sessões ativas.
// Validação de autenticação e sessão
public boolean validarSessao(HttpServletRequest request) {
HttpSession sessao = request.getSession(false);
// não cria sessão nova caso não exista
if (sessao != null && sessao.getAttribute("usuario") != null) {
// Sessão e usuário autenticados, retorna true
return true;
}
// Caso contrário, redireciona para página de login
response.sendRedirect("login.jsp");
return false;
}
// Método de login do usuário
public void fazerLogin(HttpServletRequest request, HttpServletResponse response) {
String usuario = request.getParameter("usuario");
String senha = request.getParameter("senha");
if (validarUsuario(usuario, senha)) {
// Autenticação do usuário
HttpSession sessao = request.getSession();
sessao.setAttribute("usuario", usuario);
// Redirecionamento para página principal
response.sendRedirect("index.jsp");
} else {
// Caso contrário, redireciona para página de login com mensagem de erro
request.setAttribute("erro", "Usuário ou senha incorretos!");
request.getRequestDispatcher("login.jsp").forward(request, response);
}
}
Um outro exemplo de vulnerabilidade de autenticação em Java pode ocorrer quando a aplicação não implementa o bloqueio de contas após um número limite de tentativas de login mal-sucedidas. Isso pode permitir que um atacante use força bruta para tentar adivinhar a senha de um usuário.
Para corrigir esse problema, a aplicação pode adotar medidas como implementar bloqueios de contas temporários após um número máximo de tentativas, além de permitir a configuração de senhas mais fortes.
Exemplo de código – JavaScript
Um exemplo comum de vulnerabilidade em Javascript é a não invalidação de sessões antigas após o logout do usuário. Isso pode permitir que um atacante acesse o sistema com uma sessão válida, mesmo depois de o usuário ter feito logout. Para corrigir esse problema, a aplicação pode implementar a invalidação adequada da sessão após o logout do usuário.
// Cenário vulnerável de Broken Authentication e Session Management em JavaScript
function login() {
var username = document.getElementById('username').value;
var password = document.getElementById('password').value;
if (checkCredentials(username, password)) {
// Criação de sessão para o usuário autenticado
localStorage.setItem('username', username);
window.location.href = '/dashboard';
} else {
alert('Invalid username or password');
}
}
function logout() {
// Finalização da sessão atual
localStorage.removeItem('username');
window.location.href = '/login';
}
Para corrigir essa vulnerabilidade, é importante implementar um gerenciamento de sessões seguro e adequado, utilizando tokens aleatórios para identificação das sessões, bem como definir um tempo limite para expiração de sessões inativas.
// Validação de autenticação e sessão
function validarSessao() {
var usuario = sessionStorage.getItem("usuario");
if (usuario != null) {
// Sessão e usuário autenticados, retorna true
return true;
}
// Caso contrário, redireciona para página de login
window.location.href = "login.html";
return false;
}
// Método de login do usuáriofunction fazerLogin() {
var usuario = document.getElementById("usuario").value;
var senha = document.getElementById("senha").value;
if (validarUsuario(usuario, senha)) {
// Autenticação do usuário
sessionStorage.setItem("usuario", usuario);
// Redirecionamento para página principal
window.location.href = "index.html";
} else {
// Caso contrário, exibe mensagem de erro
document.getElementById("erro").innerHTML = "Usuário ou senha incorretos!";
}
}
Exemplo de código – Python
# Cenário vulnerável de Broken Authentication e Session Management em Python
@app.route('/login', methods=['POST'])
def login():
username = request.form['username']
password = request.form['password']
if check_credentials(username, password):
# Criação de sessão para o usuário autenticado
session['username'] = username
return redirect(url_for('dashboard'))
else:
return render_template('login.html', error='Invalid username or password')
@app.route('/logout')def logout():
# Finalização da sessão atual
session.pop('username', None)
return redirect(url_for('login'))
Para corrigir essa vulnerabilidade, é importante armazenar as credenciais do usuário de forma segura, utilizando funções de hash para proteger senhas e outras informações sensíveis, além de utilizar um gerenciador de sessões com tempo limite definido.
Um outro exemplo de vulnerabilidade em Python pode ocorrer quando a aplicação não gerencia corretamente as sessões, permitindo que um atacante obtenha acesso não autorizado a informações confidenciais. Para corrigir esse problema, a aplicação pode utilizar técnicas de armazenamento seguro de dados, como criptografia de dados de sessão.
Conclusão
Para evitar as vulnerabilidades de autenticação e gerenciamento de sessões, é importante que as empresas adotem medidas de segurança durante o ciclo de vida do desenvolvimento de software.
A abordagem DevSecOps é uma boa prática que integra a segurança em todas as etapas do processo de desenvolvimento de software.
Combinando as melhores práticas de segurança de desenvolvimento, testes de segurança e monitoramento contínuo, é possível garantir que a aplicação esteja protegida contra ataques de quebra de autenticação e gerenciamento de sessões, bem como outras vulnerabilidades listadas no OWASP Top 10.