6

When studying Java I learned that Strings were not safe for storing passwords, since you can't manually clear the memory associated with them (you can't be sure they will eventually be gc'ed, interned strings may never be, and even after gc you can't be sure the physical memory contents were really wiped). Instead, I were to use char arrays, so I can zero-out them after use. I've tried to search for similar practices in other languages and platforms, but so far I couldn't find the relevant info (usually all I see are code examples of passwords stored in strings with no mention of any security issue).

I'm particularly interested in the situation with browsers. I use jQuery a lot, and my usual approach is just the set the value of a password field to an empty string and forget about it:

$(myPasswordField).val("");

But I'm not 100% convinced it is enough. I also have no idea whether or not the strings used for intermediate access are safe (for instance, when I use $.ajax to send the password to the server). As for other languages, usually I see no mention of this issue (another language I'm interested in particular is Python).

I know questions attempting to build lists are controversial, but since this deals with a common security issue that is largely overlooked, IMHO it's worth it. If I'm mistaken, I'd be happy to know just from JavaScript (in browsers) and Python then. I was also unsure whether to ask here, at security.SE or at programmers.SE, but since it involves the actual code to safely perform the task (not a conceptual question) I believe this site is the best option.

Note: in low-level languages, or languages that unambiguously support characters as primitive types, the answer should be obvious (Edit: not really obvious, as @Gabe showed in his answer below). I'm asking for those high level languages in which "everything is an object" or something like that, and also for those that perform automatic string interning behind the scenes (so you may create a security hole without realizing it, even if you're reasonably careful).

Update: according to an answer in a related question, even using char[] in Java is not guaranteed to be bulletproof (or .NET SecureString, for that matter), since the gc might move the array around so its contents might stick in the memory even after clearing (SecureString at least sticks in the same RAM address, guaranteeing clearing, but its consumers/producers might still leave traces).

I guess @NiklasB. is right, even though the vulnerability exists, the likelyhood of an exploit is low and the difficulty to prevent it is high, that might be the reason this issue is mostly ignored. I wish I could find at least some reference of this problem concerning browsers, but googling for it has been fruitless so far (does this scenario at least have a name?).

Cœur
  • 37,241
  • 25
  • 195
  • 267
mgibsonbr
  • 21,755
  • 7
  • 70
  • 112
  • 1
    I think you're overestimating the security implications. If someone can arbitrarily read the memory of your programs, you're screwed anyways. – Niklas B. Apr 15 '12 at 23:16
  • 2
    @NiklasB.: It's actually quite a valid concern. If I type in my password now, that memory could persist in my browser process's memory for months (assuming the process lasts that long). In the event of a crash, that password would then end up in the dump file. After a successful shutdown, the password could even be left stored on disk in the system's virtual memory backing file. – Gabe Apr 15 '12 at 23:38
  • @Gabe: What kind of crash dump would contain heap memory contents? The second argument (memory residing in swap files) seems more valid, but this, too, will require administrative or even local access to exploit, in which case a key logger or network sniffer could be planted just as well (probably resulting in much better results). – Niklas B. Apr 15 '12 at 23:55
  • 1
    I'm not saying that the issue is non-existant, but the specificity of the attacking scenario here might well be the reason why there's not a lot of information about this to be found. – Niklas B. Apr 16 '12 at 00:03
  • 2
    @Niklas: Most crash dumps contain heap contents. The thing about this sort of attack is that it can be performed off-line. A key logger can only capture passwords that I type in after you install it and is detectable. Securing secret strings prevents somebody with one-time physical access (a computer repair tech, police, or just the person who used the computer after me at the Internet cafe) from being able to find out the secrets. – Gabe Apr 16 '12 at 01:02
  • @Gabe: Good point. Thanks for the explanation. – Niklas B. Apr 16 '12 at 01:07

2 Answers2

4

The .NET solution to this is SecureString.

A SecureString object is similar to a String object in that it has a text value. However, the value of a SecureString object is automatically encrypted, can be modified until your application marks it as read-only, and can be deleted from computer memory by either your application or the .NET Framework garbage collector.

Note that even for low-level languages like C, the answer isn't as obvious as it seems. Modern compilers can determine that you are writing to the string (zeroing it out) but never reading the values you read out, and just optimize away the zeroing. In order to prevent optimizing away the security, Windows provides SecureZeroMemory.

Gabe
  • 84,912
  • 12
  • 139
  • 238
1

For Python, there's no way to do that that, according to this answer. A possibility would be using lists of characters (as length-1 strings or maybe code units as integers) instead of strings, so you can overwrite that list after use, but that would require every code that touches it to support this format (if even a single one of them creates a string with its contents, it's over).

There is also a mention to a method using ctypes, but the link is broken, so I'm unaware of its contents. This other answer also refers to it, but there's not a lot of detail.

Community
  • 1
  • 1
mgibsonbr
  • 21,755
  • 7
  • 70
  • 112