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.

Últimas publicações