4 ms·
So you'd think that if anything, these kinds of 'trivial' bugs, memory leaks and buffer overflows, would not be present in LibreSSL. Especially not in the same
by Confusion 11y ago
So you'd think that if anything, these kinds of 'trivial' bugs, memory leaks and buffer overflows, would not be present in LibreSSL. Especially not in the same function. I wonder what went wrong and how it can be prevented.
- byuu 11y agoI know this opinion won't be popular, and I know encryption is a very complex topic, but ... TLS is simply vastly too complicated. How many of us here could write a TLS library even if we wanted to? So you end up with code so complex that even the smartest people can barely understand it, let alone debug it, and you get terrifyingly long CVE lists like for OpenSSL as a result. Compare that to a basic unencrypted HTTP server, which you can write in ~10KiB of code. Complexity breeds these kinds of problems as a natural consequence. I do know that verifiability is significantly easier than all of this (signatures; hashing), but it's quite possible there is no simpler solution for the secrecy aspect of TLS. I certainly wish there was more support for HTTP+integrity, for those who didn't need the secrecy component. These constant CVEs in every TLS library put our servers at risk in cases where secrecy simply isn't necessary.
- quonn 11y ago> Complexity breeds these kinds of problems as a natural consequence. But the bugs described are not complex - they are local problems that can be understood by just reading one function. The problem here is not complexity, but size (not enough people spend enough time to review all of the code) and the fact that the library is written in a language with manual memory management and unsafe memory access. > I do know that verifiability is significantly easier than all of this (signatures; hashing), but it's quite possible there is no simpler solution for the secrecy aspect of TLS. In this case, the affected component was related to the identity part (certificates), which are needed for verifiability. It was not directly related to secrecy.
- byuu 11y ago> the library is written in a language with manual memory management and unsafe memory access. C's simplicity is certainly a blessing and a curse. Right now, I'm of the opinion that C++ is the best we've got, even if not perfectly ideal. RAII, shared pointers and smart containers with bounds checking allows you to keep nearly all of the performance without the drastic downsides of tracing garbage collectors (obscene amounts of memory usage, nasty stalls, etc.) And when you get into the really high-level languages (Python, Ruby), they simply don't scale. Everyone's darling right now is Rust. I still think it's too early in its life to know how it'll play out (hot new languages follow a predictable path of gaining negative baggage and shortcomings as they increase in real-world usage), but I guess we'll see. Maybe it will indeed be a great panacea to these issues. > In this case, the affected component was related to the identity part (certificates), which are needed for verifiability. It was not directly related to secrecy. Sure, but I'm generalizing here. I can (and did) write a SHA256 hashing algorithm in 3KiB of code. Combined with a package gist updater (these use signing with local keys for updates), that's enough to secure binary package downloads on the BSDs over plain-text HTTP. Surely we can come up with a less complex system for verification alone. Something akin to signify, perhaps. I know that doesn't solve how to universally handle anonymously verifying public key authenticity, but surely we can make something less complex than the clusterfuck that is TLS and the CAs. Yet it doesn't seem there's much, if any, interest in even trying. Everyone has hitched their wagons to HTTP/2 and mandatory TLS; which to me feels like a huge step backward by means of making tech vastly more complex.
- Tepix 11y agoBuilding a system for verification alone seems like a bad idea. You end up with something like DNSSEC and then there's no easy way to add privacy later on.
- riffraff 11y ago> And when you get into the really high-level languages (Python, Ruby), they simply don't scale. I think you need to qualify what "scale" means in this context. Otherwise java is, for all its warts, more or less as high level as ruby and python, and it's probably been proven to scale up (to big machines, or many developers) reasonably well.
- masklinn 11y agoIs it TLS specifically or X509 (both by itself and because it uses ASN.1)? I dimly remember X509 and ASN.1 being commonly criticised for their complexity, does TLS pile on additional complexity or just inherit it?
- viraptor 11y agoIt's everything. ASN.1 is complex - people still make mistakes in the DER parsers as seen in this CVE. X509 is even more complex - it's not just ASN.1. It can be DER in DER in DER (parameters of certificate extensions). Have fun with that and memory ownership! (you have to recalculate and replace an object 2 levels above what you're actually changing) TLS is even worse, because it includes X509 as a format and then a ton more of actual processing logic, state machines, cryptography code, ... I don't trust any implementation of it that uses unmanaged code. (yes, pretty much assuming everything based on openssl will be broken time and time again)
- alricb 11y agoIn this case it's definitely ASN.1; the problem is that "objects" are defined with OIDs, which are sequences of integers (called arcs numbers) like { 1 2 840 113549 1 }. The first integer is always 0, 1 or 2, and with 0 or 1, the second is between 0 and 39. But the other integers can be arbitrarily large, and it's important not to overflow: https://www.viathinksoft.de/~daniel-marschall/asn.1/oid_facts.html#chap7 https://www.viathinksoft.de/~daniel-marschall/asn.1/oid_fact... You need to use some sort of bignum function if you want to display large arc numbers in decimal. Which is what OpenSSL and LibreSSL do, and that involves creating and destroying BIGNUM objects. The problem is that someone in LibreSSL moved the free() to outside the loop body handling the arc numbers while they were cleaning up. So only the last BIGNUM used gets freed. Oh, did I tell you that arc numbers are encoded in base 128, with the first bit of every octet used to signal whether it's the last octet of that arc number? Because they are.
- masklinn 11y agoWell these are ASN.1 facts I did not need to know and I would like to not subscribe to that mailing list, but regardless thank you for the explanation.
- MichaelGG 11y agoThis doesn't seem to be a case of a complicated spec causing a logic error. Just another case of a memory unsafe language in action. So it's more an issue of people wanting fast, runtime-free, portable code, and being OK with the security implications C brings in exchange. (A TLS lib written in Rust might eventually be an answer, maybe.)
- NKCSS 11y agoStop writing unmanaged code? This is just the same ol' story...
- Asmod4n 11y agoIf you want interoperability you are kinda stuck with C. Nearly every Language can use C Libraries either directly or via FFI. While Rust can export functions the same way C does it you are in unmanaged land again then. With http://www.ponylang.org/ http://www.ponylang.org/ its much better, it can export functions like C does it, but its fully managed. The only limitation are the Data Types, you are restricted to those C knows.
- dbaupp 11y agoDo you have more info about Pony's ability to expose C-compatible functions? I can't see anything in the docs (e.g. http://tutorial.ponylang.org/c-ffi/c-abi/ http://tutorial.ponylang.org/c-ffi/c-abi/ talks about going the other direction). Also, FWIW, I don't think Rust should be considered unmanaged for these purposes: it bridges the divide between "managed" and "unmanaged" by bringing the memory safety of the former to a language that doesn't require a complicated runtime. So strictly speaking, yes, it's unmanaged, but it doesn't suffer the worst of the problems of existing unmanaged languages like C or C++.
- Asmod4n 11y agoI belive all you have to do is to prefix a Actor or function with a "@" and then call ponyc with --library, which generates a header and library you can use in your c program.
- masklinn 11y ago> With http://www.ponylang.org/ http://www.ponylang.org/ its much better, it can export functions like C does it, but its fully managed. You can do that with most "managed" languages. You can call Python, Haskell, Go or OCaml from C, pony isn't exactly special here. One issue in all these cases is you're carrying a whole runtime with you, possibly one per library you're using, praying they don't conflict with one another[0] and limiting the portability of the whole[1]. You're also significantly increasing the cost of using the library in question as it now brings in megabytes of runtime along for the ride. [0] with conflicting signal handling for instance [1] if only because all those runtimes you're bringing in might be doing stuff like spawning their own threads and the like, so that needs to be available on the target platform
- keeperofdakeys 11y agoUnfortunately code will always have bugs, especially when you are adding or changing it. However the numbers speak for themselves, LibreSSL has been removing large amounts of code http://www.openbsd.org/papers/libtls-fsec-2015/mgp00004.html http://www.openbsd.org/papers/libtls-fsec-2015/mgp00004.html and has so far had fewer CVEs http://www.openbsd.org/papers/libtls-fsec-2015/mgp00005.html http://www.openbsd.org/papers/libtls-fsec-2015/mgp00005.html.