Skip to main content

Automatic information enumeration - Personal Information

Need

Prevention of unauthorized access to personal information

Context

  • Usage of Java for building robust and scalable applications
  • Usage of javax.servlet for Java web application development
  • Usage of java.io for input and output operations in Java

Description

Non compliant code

import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;

public class UserInfoServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String userId = request.getParameter("userId");
// Fetch user information based on userId
User user = Database.getUserById(userId);

response.setContentType("text/html");
PrintWriter out = response.getWriter();
out.println("<h1>" + user.getName() + "</h1>");
out.println("<p>Email: " + user.getEmail() + "</p>");
out.println("<p>Login Method: " + user.getLoginMethod() + "</p>");
}
}

The above code is a servlet that responds to a GET request by fetching and displaying user information based on a user ID provided as a parameter in the request.

The vulnerability lies in the fact that the servlet does not check whether the user making the request is authorized to view the information of the user with the provided ID. This means that an attacker could potentially input any user ID and retrieve their personal information, including their name, email, and login method.

The servlet also does not use a token associated with the account to consult the information, which means there is no mechanism to prevent unauthorized access to other users' information. This can lead to automatic information enumeration, where an attacker could potentially iterate over a range of user IDs to retrieve personal information of multiple users.

In a nutshell, the lack of authorization checks and token-based authentication in this servlet makes it vulnerable to information disclosure attacks.

Steps

  • Implement authentication and authorization mechanisms to ensure that only authenticated and authorized users can access the user information.
  • Use a token-based authentication system to securely authenticate users and associate the token with their account.
  • Ensure that the token is required to access the user information and validate the token before retrieving the user information.
  • Implement access control checks to ensure that a user can only access their own information and not information of other users.
  • Consider implementing additional security measures such as rate limiting, session management, and encryption to protect the user information.

Compliant code

import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;

public class UserInfoServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
HttpSession session = request.getSession();
String sessionUserId = (String) session.getAttribute("userId");
String token = (String) session.getAttribute("token");

if (sessionUserId == null || token == null) {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "Unauthorized access");
return;
}

String userId = request.getParameter("userId");
if (!sessionUserId.equals(userId)) {
response.sendError(HttpServletResponse.SC_FORBIDDEN, "Access denied");
return;
}

// Validate the token
if (!TokenManager.isValid(token, userId)) {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "Invalid token");
return;
}

// Fetch user information based on userId
User user = Database.getUserById(userId);

response.setContentType("text/html");
PrintWriter out = response.getWriter();
out.println("<h1>" + user.getName() + "</h1>");
out.println("<p>Email: " + user.getEmail() + "</p>");
out.println("<p>Login Method: " + user.getLoginMethod() + "</p>");
}
}

The updated code now includes an authentication and authorization mechanism to ensure that only authenticated and authorized users can access the user information.

Firstly, the code retrieves the user ID and token from the session. If either of these are not present, it sends an unauthorized error and returns.

Next, it checks if the user ID from the session matches the user ID from the request. If they do not match, it sends a forbidden error and returns. This ensures that a user can only access their own information and not information of other users.

Then, it validates the token using a hypothetical TokenManager.isValid() method. If the token is not valid, it sends an unauthorized error and returns.

Finally, if all checks pass, it fetches the user information from the database and sends it in the response. This ensures that only authenticated and authorized users can access the user information, and they can only access their own information.

Additional security measures such as rate limiting, session management, and encryption should also be considered to further protect the user information.

References