Friday, November 4, 2011

Oracle Security Controversies

There are several areas of security that I delve into in the book where I take a contrarian position: Client Wallets, Virtual Private Database and Password-Protected Roles. It is not so much that I oppose using those things; it's just that there are security weaknesses that I believe are unacceptable. There are also some areas that I discuss in the book that need to be considered carefully when used in your Oracle Security scheme, for example Password storage for Data On Disk Encryption.

Why are Client Wallets bad?
Client Wallets are a secure storage file for Oracle account passwords. The wallet file is encrypted with a password, so it cannot be easily deciphered. The algorithm parameters are embedded in Java and DLLs, so they are not beyond attack, but that is not the real problem. The truly scary reality of client wallet files is that if someone gets hold of the file, they can use it to log into Oracle as the target account without any further authentication. Normally these files are stored in user's home directories, and so the assumption is that they are protected by the Operating System file system security; but the wallet is simply a file that can be copied or even e-mailed (by a hacker, administrator or hapless user), or even stolen from backups or archives.

One more security lapse that is created by client wallet files is the dependency on SQLnet configuration files for application. An encrypted password in the wallet is tied to an entry in the TNSNames.ora file or equivalent. For example the user mUser on the Oracle instance mOra might have a TNSNames entry mOra_mUser for which a password exists in the client wallet. The obvious security loophole here is that the TNSNames entry can point to ANY oracle instance -- if the Oracle user exists on that instance, the client wallet can be used to log in as that user. In some Oracle instances, mUser may have more privileges or more sensitive data access, and if the user account has the same password on that instance, the wallet can be used to get access, even if that's not the instance for which the wallet entry was created.

What's wrong with Virtual Private Database?
Let me say that there is nothing really wrong with VPD, and it can be configured so that it does enhance security. But the way it is usually defined, it bases security on data. For example: only show the current user rows in the employee table for employees with the same company code as the current user. This is data filtering data -- it is not a basis for security.

In the book, I show VPD based on two parameters that are security-related, not data-related: proxy grants and role grants. I also show that without VPD, by limiting grants to the data and limiting grants to stored procedures, you can embed dynamic where clauses (the heart of VPD) into your views and procedures and accomplish the same thing. My argument for doing that is to make the security enforcement obvious and not hidden in policy settings. There is nothing inherently more secure about a policy setting, which can be unset with a single command, than in the application of common security measures.

My take on Password-Protected Roles.
In Oracle 11g, Oracle Corporation has removed the ability to acquire a password-protected role without entering the password, even if the role is a default password. This is a good correction, and my argument is that a role should not be granted if the user should not have access. Then if the user should have access, why is a password required?

I realize that some applications acquire the password and then set the role, and the idea is that within the application a user can get the role, but from outside the application, she can not. Well, we have to ask, can she really NOT get the password and get the role? Perhaps not if you are limiting all other clients by Product User Profile. But an impostor application that presents the same Product User Profile (or none) can do whatever the original application does to acquire the role: query a view or execute a procedure or function.

In other words, the addition of passwords to roles buys you nothing, but requires more user maintenance and code support. My final analysis is that you should not grant a role to anyone who does not need it all the time, and if you really want to password-protect a role, then make the user enter it -- do not encode the password acquisition.

Password Storage for Data Encryption on Disk
As in the discussion of Client Wallet encryption, here again the algorithms and parameters used for encrypting data using the DBMS_CRYPTO package are codified in Java and DLLs and perhaps wrapped procedures. They can be attacked. But once again, that is not the real problem. The problem is where to store the password.

The solution I came up with is to calculate an application-specific password based on identity artifacts from the application and designated starter codes. I use a complex wrapped procedure to do the password calculation. So where is the password stored? It really isn't. Someone accessing the data or the Oracle server will not find password records in the database tables, nor in files on the server. It would require much more effort.

PUBLIC and the SYS Data Dictionary Views
For the most part, those views in the data dictionary that are granted to PUBLIC are helpful and probably even necessary for use of the database. However, it would be nice to be able to create an Oracle user/schema and not have them acquire ANYTHING. Perhaps I handle authentication through a database (as I do in the book), so I have to let users connect, but I don't want to expose some of the PUBLIC data dictionary views to the user until they have proven themselves. I solve this by turning off PUBLIC access to views like SYS.ALL_USERS.

What I would prefer is for PUBLIC to be a regular role, with one addition. PUBLIC never disappears, even when you set role -- that is a nice feature. I would like to be able to revoke PUBLIC from users, or to have the requirement to specifically grant PUBLIC before it became active. Perhaps there could be a PUBLIC_REQUIRED like the current PUBLIC, and a PUBLIC_OPTIONAL that is more like an ordinary role, that can be granted and revoked, with the additional feature of never disappearing.

That is all the controversies I'd like to address at this moment. I hope this discussion has led to more insight, not just more argument.

Synonyms Are Not Good
This is something I spend time discussing in the book, and I wanted to mention it as a controversy... Perhaps you and your application programmers depend on synonyms to find things scattered around many different schemas. This is a bad dependency - just say "No".

Basically, there are security, code-sharing and maintenance issues, as well as potential production issues with code promoted from a lower environment. All this for a shortcut syntax!?! Just say "No", and make everyone refer to your Oracle structures with the schema prefix. This goes for public synonyms as well as private.

I admit that one instance of a synonym may be beneficial - a synonym for a structure reference across a database link. The benefits in this case are (1) removing the complex reference from the application code and (2) giving the Oracle DBAs an extra layer of flexibility to use in moving databases and structures around. Yes, these may be the same arguments (flexibility) that you use for regular synonyms; but if you are using views, you already have sufficient flexibility for local structures. In truth, you can point a database link at the new location and get flexibility with just the link, but you may want to maintain link names that correlate to the database instance names, so you need another layer of flexibility.

No comments:

Post a Comment