News Analysis

OWASP Guide to Building Secure Web Applications and Web Services, Chapter 10: Authorization

OWASP

This article is provided by special arrangement with the Open Web Application Security Project (OWASP). This article is covered by the Creative Commons Share-Alike Attribution 2.5 license. You can find the latest version of this article and more free and open application security tools and documentation at http://www.owasp.org.


Authorization

Objectives

  • To ensure only authorized users can perform allowed actions within their privilege level
  • To control access to protected resources using decisions based upon role or privilege level
  • To prevent privilege escalation attacks, for example using administration functions whilst only an anonymous user or even an authenticated user.

Environments Affected
All applications.

Relevant COBIT Topics
DS5 – All sections should be reviewed. This section covers nearly all COBIT detailed control objectives.

Principle of least privilege
Far too often, web applications run with excessive privileges, either giving users far too great privilege within protected resources, such as the database (for example, allowing table drops or the ability to select data from any table to running privileged stored procedures like xp_cmdshell()), all the way through to running the web application infrastructure with high privilege system accounts (like LOCALSYSTEM or root), to code in managed environments running with full access outside their sandbox (ie Java's AllPermission, or .NET's FullTrust).

If any other issue is found, the excessive privileges grant the attacker full uncompromised scope to own the machine completely, and often other nearby infrastructure. It cannot be stated strongly enough that web applications require the lowest possible privilege.

How to determine if you are vulnerable

  • System level accounts (those that run the environment) should be as low privilege as possible. Never should "Administrator", "root", "sa", "sysman", "Supervisor", or any other all privileged account be used to run the application or connect to the web server, database, or middleware.

  • User accounts should possess just enough privileges within the application to do their assigned tasks

  • Users should not be administrators

  • Users should not be able to use any unauthorized or administrative functions.

How to protect yourself

  • Development, test and staging environments must be set up to function with the lowest possible privilege so that production will also work with lowest possible privileges

  • Ensure that system level accounts (those that run the environment) should be as low privilege as possible. Never should "Administrator", "root", "sa", "sysman", "Supervisor", or any other all privileged account be used to run the application or connect to the web server, database, or middleware.

  • User accounts should possess just enough privileges within the application to do their assigned tasks

  • Users should not be administrators and vice versa

  • Users should not be able to use any unauthorized or administrative functions. See the authorization section for more details

  • Database access should be through parameterized stored procedures (or similar) to allow all table access to be revoked (ie select, drop, update, insert, etc) using a low privilege database account. This account should not hold any SQL roles above "user" (or similar)

  • Code access security should be evaluated and asserted. If you only need the ability to look up DNS names, you only ask for code access permissions to permit this. That way if the code tries to read /etc/password, it can't and will be terminated

  • Infrastructure accounts should be low privilege users like LOCAL SERVICE or nobody. However, if all code runs as these accounts, the "keys to the kingdom" problem may re-surface. If you know what you're doing, with careful replication of the attributes of low privilege accounts like LOCAL SERVICE or nobody is better to create low privilege users and partition than to share LOCAL SERVICE or "nobody".

Access Control Lists
Many access controls are out of the box insecure. For example, the default Java 2 file system security policy is "All Permission", an access level which is usually not required by applications.

grant codeBase "file:${{java.ext.dirs}}/*" {
 permission java.security.AllPermission;
};

Applications should assert the minimum privileges they need and create access control lists which enforce the tightest possible privileges.

How to determine if you are vulnerable

  • Determine if file, network, user, and other system level access controls are too permissive
  • Determine if users are in a minimal number of groups or roles
  • Determine if roles have minimal sets of privileges
  • Determine if the application asserts reduced privileges, such as by providing a policy file or "safe mode" configuration

How to protect yourself
Access controls to consider:

  • Always start ACL's using "deny all" and then adding only those roles and privileges necessary
  • Network access controls: firewalls and host based filters
  • File system access controls: file and directory permissions
  • User access controls: user and group platform security

Java / .NET / PHP access controls: always write a Java 2 security policy or in .NET ensure that Code Access security is asserted either programmatically or by assembly permissions. In PHP, consider the use of "safe mode" functionality, including open_basedir directives to limit file system access.

Data access controls: try to use stored procedures only, so you can drop most privilege grants to database users – prevents SQL injection.

Exploit your platform: Most Unix variants have "trusted computing base" extensions which include access control lists. Windows has them out of the box. Use them!

Custom authorization controls
Most of the major application frameworks have a well developed authorization mechanism (such as Java's JAAS or .NET's inbuilt authorization capabilities in web.config).

However, many applications contain their own custom authorization code. This adds complexity and bugs. Unless there's a specific reason to override the inbuilt functionality, code should leverage the framework support.

How to determine if you are vulnerable

  • Does the code leverage the inbuilt authorization capabilities of the framework?
  • Could the application be simplified by moving to the inbuilt authentication / authorization model?
  • If custom code is used, consider positive authentication issues and exception handling – can a user be "authorized" if an exception occurs?
  • What coverage is obtained by the use of the custom authentication controls? Is all the code and resources protected by the mechanism?

How to protect yourself

  • Always prefer to write less code in applications, particularly when frameworks provide high quality alternatives.
  • If custom code is required, consider positive authentication issues and exception handling – ensure that if an exception is thrown, the user is logged out or at least prevented from accessing the protected resource or function.
  • Ensure that coverage approaches 100% by default.

Centralized authorization routines
A common mistake is to perform an authorization check by cutting and pasting an authorization code snippet, or worse re-writing it every time. Well written applications centralize access control routines, particularly authorization, so if any bugs are found, they can be fixed once and applied everywhere immediately.

How to determine if you are vulnerable
Applications that are vulnerable to this attack have authorization code snippets all over the code.

How to protect yourself

  • Code a library of authorization checks
  • Standardize on calling one or more of the authorization checks

Authorization matrix
Access controlled applications must check that users are allowed to view a page or use an action prior to performing the rendering or action.

How to determine if you are vulnerable
Check:

  • Does each non-anonymous entry point have an access control check?
  • Is the check at or near the top of the activity?

How to protect yourself
Either use the inbuilt authorization checks of the framework, or place the call to a centralized authorization check right at the top of the view or action.

Client-side authorization tokens
Many web application developers are keen to not use session storage – which is misguided when it comes to access control and secrets. So they revert to using the client's state, either in cookies, headers, or in hidden form fields.

How to determine if you are vulnerable
Check your application:

  • Does not set any client-side authentication or authorization tokens in headers, cookies, hidden form fields, or in URL arguments.
  • Does not trust any client-side authentication or authorization tokens (often in old code)

If your application uses an SSO agent, such as IBM's Tivoli Access Manager, Netegrity's SiteMinder, or RSA's ClearTrust, ensure your application validates the agent tokens rather than simply accepting them, and ensure these tokens are not visible to the end user in any form (header, cookie, hidden fields, etc). If the tokens are visible to the end user, ensure that all the properties of a cryptographically secure session handler as per chapter 0 are taken into account.

How to protect yourself
When your application is satisfied that a user is authenticated, associate the session ID with the authentication tokens, flags or state. For example, once the user is logged in, a flag with their authorization levels is set in the session object.

Java
if ( authenticated ) {
}

.NET (C#)
if ( authenticated ) {
 
}

PHP
if ( authenticated ) {
 $_SESSION['authlevel'] = X_USER; // X_USER is defined elsewhere as meaning, the user is authorized
}

Check your application:

  • Does not set any client-side authentication or authorization tokens in headers, cookies, hidden form fields, or in URL arguments.
  • Does not trust any client-side authentication or authorization tokens (often in old code)

If your application uses an SSO agent, such as IBM's Tivoli Access Manager, Netegrity's SiteMinder, or RSA's ClearTrust, ensure your application validates the agent tokens rather than simply accepting them, and ensure these tokens are not visible to the end user in any form (header, cookie, hidden fields, etc). If the tokens are visible to the end user, ensure that all the properties of a cryptographically secure session handler as per chapter 12 are taken into account.

Controlling access to protected resources
Many applications check to see if you are able to use a particular action, but then do not check if the resource you have requested is allowed. For example, forum software may check to see if you are allowed to reply to a previous message, but then doesn't check that the requested message is within a protected or hidden forum or thread. Or an Internet Banking application might check that you are allowed to transfer money, but doesn't validate that the "from account" is one of your accounts.

How to determine if you are vulnerable

  • Does the application verify all resources they've asked for are accessible to the user?
  • Code that uses resources directly, such as dynamic SQL queries, are often more at risk than code that uses the model-view-controller paradigm. The reason for this is that the model is the correct place to gate access to protected resources, whereas a dynamic SQL query often makes false assumptions about the resource.

How to protect yourself

  • Use model code instead of direct access to protected resources
  • Ensure that model code checks the logged in user has access to the resource
  • Ensure that the code asking for the resource has adequate error checking and does not assume that access will always be granted

Protecting access to static resources
Some applications generate static content (say a transaction report in PDF format), and allow the underlying static web server to service access to these files. Often this means that a confidential report may be available to unauthorized access.

How to determine if you are vulnerable

  • Does the application generate or allow access to static content?
  • Is the static content access controlled using the current logged in user?
  • If not, can an anonymous user retrieve that protected content?

How to protect yourself

  • Best -- Generate the static content on the fly and send directly to the browser rather than saving to the web server's file system
  • If protecting static sensitive content, implement authorization checks to prevent anonymous access
  • If you have to save to disk (not recommended), use random filenames (such as a GUID) and clean up temporary files regularly

Further reading
ASP.Net authorization: http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpguide/html/cpconaspnetauthorization.asp


Email Alerts

Register now to receive ComputerWeekly.com IT-related news, guides and more, delivered to your inbox.
By submitting you agree to receive email from TechTarget and its partners. If you reside outside of the United States, you consent to having your personal data transferred to and processed in the United States. Privacy
 

COMMENTS powered by Disqus  //  Commenting policy