5 ms·
> I'm less thrilled about it being written in a garbage collected language What are the security problems with garbage-collected languages? (not being sarcast
by jrochkind1 4y ago
> I'm less thrilled about it being written in a garbage collected language
What are the security problems with garbage-collected languages?
(not being sarcastic, don't have an agenda, I have no previous knowledge on this, and am not a security expert. Just had never heard this suggested before, and am curious what he meant. Legit question!)
- grecy 4y ago> What are the security problems with garbage-collected languages? None that I'm aware of. I think this is a petty swipe at programmers who use garbage-collected languages, implying they're "less" than programmers who use "real" languages that don't have garbage collection.
- deleted 4y ago[deleted]
- kstrauser 4y agoAt the risk of conjuring a strawman, I've heard people worry about the loss of control, like maybe the process has some sensitive data in RAM that it will release and then the OS will alloc() it to another process. And that's true on one level, but nothing prevents a garbage collected language from overwriting all the data in a block of RAM as it free()s it. I think the risk of memory related bugs in a non-managed language is far, far greater than any GC-related hypothetical risks. And then you have languages like Rust which "feels" like it's a GC language because it manages all the alloc()s and free()s for you, but isn't GC at all because the language's semantics make those calls deterministic. I'd vastly rather see sensitive security software developed in a modern garbage collected language (or in Rust and similar languages) than in C or C++.
- IcePic 4y ago> At the risk of conjuring a strawman, I've heard people worry about the loss of control, like maybe the process has some sensitive data in RAM that it will release and then the OS will alloc() it to another process. I'm sure some people worry about this, but I think you will be hard pressed to find a modern OS that actually would give away your contents to another PID. Just because a program can malloc(8), fill eight bytes with known content, free() the pointer, malloc(8) again and see their old content doesn't mean the OS hands your data to anyone, just that the libc (or whatever runtime you use) is not actually getting a whole page for that single 8 byte malloc, and it didn't give it back to the OS at free() either, so you "owned" the page where those 8 bytes lives all the time during execution of this simple test. The limit for which your allocator starts _actually_ handing back data is probably never less than 4k and upwards to 256k depending on page size, malloc settings and OS/libc defaults. So while there are a lot of traps code can fall into as mentioned in other comments in this thread, I think everyone can stop worrying about "the next program to malloc() will get my old data" because that just doesn't happen.
- ffssffss 4y agoIf anything I would intuit such an implementation is sacrificing performance for security, since it rules out some classic vulnerabilities.
- acatton 4y agoUsually security nuts like to override the clear-text string with zeros or random characters before calling free() on it. This way, if this chunk of data stays in memory (which is most likely the case with libc's free()) it cannot be read by exploiting a buffer overflow. With garbage collected language, programmers don't know when their variable is "free()ed", since it could be held in multiple thread, and the last thread dying will release the memory for this variable. Since programmers often don't know when the password variable will be "free()ed", it is very unlikely that they scrambled the password before releasing the memory. Thus, leading to the password being kept in some region of the program memory, in clear text, exploitable by a buffer overflow & co. for an indefinite amount of time.
- aflag 4y agoYou should be able to know all the references to a variable, if you are careful when writing your program. Also, you could write a destructor that scrambles the memory location before the object is collected. However, you would still not have control over copies that the GC may decide to make and it is a bit trickier to force a free, since the GC is in no obligation of freeing an object as soon as it has no more references (though you can probably force that to happen in most GCed languages).
- acatton 4y ago> You should be able to know all the references to a variable, if you are careful when writing your program. The issue is: what if thread A and thread B hold a reference to the password variable? And you don't know in which order they will execute. In which thread do you scramble the password before releasing the variable reference? From what I understand, OP's point is: because of the nature of C, you have to know where your variable is "free()ed", because you have to do it yourself. Therefore you can scramble there. Even if you have two thread doing: n = decr_reference(password) if (n == 0) { scramble(password) free(password) }
- nebulous1 4y agoThat issue seems the same in a GC language as it is in a non-GC one. Either way you need to know when you're done with the data and it's time to scramble.
- tredre3 4y agoI suppose it's a lot more difficult to wipe memory clean in a garbage collected language. For example: password = "my-secret-password"; // do stuff then remove the pass from memory password = "" or null or delete or unset We have no guarantee that the first string "my-secret-password" will be collected and removed any time soon whereas in C or C++ we could just memset it before freeing it. But that feels like a very generous interpretation, I'm sure the author really meant it as a "real programmers don't use GC language"...
- sixothree 4y agoC# has SecureString. I assume BitWarden uses this. edit: https://learn.microsoft.com/en-us/dotnet/api/system.security.securestring?view=net-7.0 https://learn.microsoft.com/en-us/dotnet/api/system.security...
- aflag 4y agoInterestingly, in those docs they recommend against using that class and point to this github repo explaining the reason: https://github.com/dotnet/platform-compat/blob/master/docs/DE0001.md https://github.com/dotnet/platform-compat/blob/master/docs/D...
- piaste 4y agoTo be pedantic, they're not saying the class is making things worse - it just doesn't do anything on .NET Core because it lacks cross-platform encryption APIs comparable to the ones used on .NET Framework. So it's basically just a String. It's a little frustrating that their only recommended alternative is "just give us your secrets bro" though: > The general approach of dealing with credentials is to avoid them and instead rely on other means to authenticate, such as certificates or Windows authentication.
- kcartlidge 4y agoNice. Less of a SecureString and more of a SlightlySmallerWindowOfInsecurityString. TIL.
- 4y ago
- aflag 4y agoI'm not an specialist, but I suspect the rationale is that you have less control of how the memory is cleaned up after use. In special, the GC can actually copy objects around without the programmer's knowledge, potentially making multiple copies of secrets which the programmer cannot clean up (by setting the bits randomly) later on. Without a GC, the programmer is able of knowing how many copies there are of any given secret and can dispose of them, if needed. On that note, probably writing their own "malloc" is probably a good choice. That said, I'm sure there are workarounds even in GCed languages. For instance, you can usually create C extensions which could allocate and manage memory outside of the GC's control. So, such extesion could potentially give back memory control of certain special memory regions where secrets can be stored, while everything else just goes through normal GC.
- danShumway 4y agoThe arguments people are giving about being able to explicitly call `free` make a lot of sense to me for getting rid of some attack vectors, but it still seems like the security risks of using a memory-unsafe language would heavily outweigh the risks of the garbage collector not clearing strings fast enough? I know that's not an either-or proposition, there are memory safe languages that aren't garbage collected. But if people aren't talking about those languages, if they're just bringing up C or something... I am not an expert, I might not know what I'm talking about here at all -- but my instinct is that I would rather see security-critical code written in a garbage collected language than in C. Frankly, I don't trust developers not to make memory errors in C. Maybe I'm underestimating the risk of the garbage collector not zeroing out variables? Or maybe I'm over-complicating it and the answer is just the obligatory "write it in Rust" refrain so you can avoid both problems? But I'm also a little surprised to see this line, my impression was that security advice was starting to trend towards recommending GC languages, not away from them.
- hcks 4y agoThese kind of concerns are so funnily out of touch. The real dangers always turns out to be crazily bad security practices (the kind obvious to everyone after the fact), not theoretical attacks that probably weren’t ever demonstrated in the wild.
- mjg59 4y agoPeople have described the concern about memory not being zeroed in a predictable way, but not why that's a security concern. And, honestly, for most people I don't think it is. If an attacker is in a position to read arbitrary memory out of your browser then the chance that they won't obtain something else about as powerful as a password (eg, a valid session cookie) seems minimal. Or a crash dump file may include passwords, but then how does someone have access to that and not be able to read your cookie store? For a niche set of people I think there's greater concern around cold boot attacks - someone with physical possession of a suspended machine powers it off and quickly boots another OS, then dumps RAM (think laptop being taken away from you in an airport situation). That can be mitigated through firmware just wiping RAM on unclean boots (TCG has a spec for this, Linux and Windows implement it), and getting around that involves much more invasive attacks. I don't want to say the concerns are entirely unwarranted, but I really don't think it's a big deal for the vast majority of people.
- letmeinhere 4y agoI buy the explanations that they mostly want to be able to explicitly overwrite sensitive memory at a time of their choosing. My question: does the nondeterministic execution pauses that garbage collection injects into a program's runtime aid or prevent timing attacks? It seems like it would prevent them, since it makes it that much harder to predict execution duration, but I have this vague impression that high-security operations are more likely to demand real-time computing. Maybe that's just incidental, and applications that must highly perform also tend to need to be secured from attack?