Skip to main content

Insecure or unset HTTP headers - Accept

Need

Secure and properly set HTTP headers - Accept

Context

  • Usage of C# for developing robust and efficient applications
  • Usage of Microsoft.AspNetCore.Mvc for building web applications with ASP.NET Core

Description

Non compliant code

public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
}

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseRouting();

app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}

The above code represents a basic setup for an ASP.NET Core application. The Startup class is the entry point to the application, setting up the application's services and configuring the HTTP request pipeline.

The TestController is a basic controller that handles a GET request at the route "/test" and returns a simple "Hello World" message.

The vulnerability lies in the fact that the application does not set the Accept HTTP header or restricts the MIME types that can be accepted in the requests. This means that the application can accept any content-type in the requests, even those that it may not be able to correctly interpret or handle.

An attacker could exploit this vulnerability by sending a request with a content-type that the application does not expect. This could cause the application to interpret the request incorrectly, leading to unexpected behaviors or even errors.

For instance, if the application expects a JSON content-type but receives XML instead, it may fail to parse the request properly, leading to a potential denial of service (DoS) attack. Or, if an attacker sends a content-type that triggers a specific behavior in the application, they could potentially exploit this to perform actions they are not supposed to be able to do.

Steps

  • Implement a middleware to set the Accept header in the incoming requests.
  • Validate and restrict the allowed MIME types in the Accept header.
  • Handle invalid or unexpected content-types appropriately in the application logic.
  • Test the application to ensure that the Accept header is properly set and restricted.

Compliant code

public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddControllers();
}

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseRouting();

// Middleware to set and validate the Accept header
app.Use(async (context, next) =>
{
if (!context.Request.Headers.Keys.Contains("Accept"))
{
context.Request.Headers.Append("Accept", "application/json");
}
else
{
var acceptHeader = context.Request.Headers["Accept"].ToString();
if (acceptHeader != "application/json")
{
context.Response.StatusCode = StatusCodes.Status406NotAcceptable;
await context.Response.WriteAsync("Invalid Accept header. Only 'application/json' is allowed.");
return;
}
}

await next.Invoke();
});

app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
});
}
}

The above code fixes the vulnerability by implementing a middleware that sets and validates the Accept header in the incoming requests.

In the Configure method, a middleware is added using the Use method of the IApplicationBuilder instance. This middleware checks if the Accept header is present in the request. If it's not present, it sets the Accept header to "application/json".

If the Accept header is present, it checks if the value is "application/json". If it's not, it returns a 406 Not Acceptable status code with a message indicating that the Accept header is invalid and only "application/json" is allowed.

This way, the application restricts the allowed MIME types in the Accept header to "application/json" and handles invalid or unexpected content-types appropriately.

After implementing this fix, it's important to test the application to ensure that the Accept header is properly set and restricted.

References