Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why not DriverManager.getConnection(String url, String user, char[] password)?

We know it's a good practice to prefer char[] over java.lang.String to store passwords. That's for the following two reasons (as I have read):

  1. char[] are mutable so we can clear the passwords after the usage.
  2. String literals goes to a pool that will not get garbage collected as other objects, hence might appear in memory dumps.

But java.sql.DriverManager doesn't have a getConnection() that comply with the above best practice because its password parameter is String.

DriverManager.getConnection(String url, String user, String password)

I think the API should have an overloaded method with the following signature:

DriverManager.getConnection(String url, String user, char[] password)

What do you think about this? Do you see any alternative way to overcome this draw back?

Would love to hear your thoughts.

like image 440
Kaushalya Avatar asked Feb 15 '10 14:02

Kaushalya


4 Answers

String literals go in a pool, but I wouldn't expect the password to be a literal (hardcoded in the program). I would expect it to come from a configuration or similar. As such it won't be a literal and will get garbage collected (provided all references are binned).

like image 173
Brian Agnew Avatar answered Sep 28 '22 03:09

Brian Agnew


You make a good point, and most people answering are missing it. The worst case scenario is that the "temporary" password is swapped out by the OS, in clear text mind you. After this, this swap file is easily read, and on the disk can even survive being overwritten by zeroes if the attacker has about $1500 of equipment...

The best you can do is connect, password = null, followed by explicit call to gc(). If you are lucky, this will clear even strings used by driver implementations.

Any way...

  • What you ask is currently not possible, but would be nice.
  • Even char[] can survive certain conditions (e.g. swapping).
  • Your password will get copied many times on the way to the database, so char[] solves only one part of the problem.

The reality is that unless the platform is designed specifically for security, all methods are only delaying tactics. Do, what you can, but if the determined person can gain access to your machine, char[] will gain you 1 hour max.

like image 40
mikijov Avatar answered Sep 28 '22 05:09

mikijov


One can only speculate, unless you can ask the designer of the API.

My speculation is this:

The main API that uses char[] instead of String for passwords that I know of is JPasswordField. It does so in order to allow the program to overwrite the user-entered password with other values once the values have been used (which is not possible with a String, which will linger in memory at least until it is garbage-collected).

The password used to connect to a database is usually not user-entered in most applications I know, but comes from some kind of configuration/directory/...

Not matter where it comes from: the application is able to re-construct it once it is no longer known. This is the big difference between user-entered passwords and programmatically acquired passwords.

Since the password usually can be acquired on easier ways than to search through all the memory a program has used, fixing this attack vector is not a high priority

</speculation>

like image 23
Joachim Sauer Avatar answered Sep 28 '22 05:09

Joachim Sauer


Your reason #2 is the one I've seen given most commonly for use of char[] over String. However, in general I think that if you assume that someone has access to your program state via a debugger or other means, there's no reason they can't also look at the contents of a char[].

like image 22
Alex Miller Avatar answered Sep 28 '22 03:09

Alex Miller