 I am Alan Cecil. With me here is Dan. Dan Petro. And we're going to present on you're doing IoT. Well, you're doing it wrong. You say it. You're doing it wrong. This is great. Thanks again to Defcon for having us. We're really happy to be here. This is a pretty big issue. One of the things that's sort of unique in the IoT landscape is that there's not very much tying IoT devices together. They're very heterogenous as a group. It's hardly a group at all. They share almost nothing together in terms of hardware or software. So it's pretty unlikely. It's pretty rare for a single-like issue, a single vulnerability, per se, to affect nearly all IoT devices. And I've got bad news for you. So before we talk much about random number generators, let's talk first about random numbers. So random numbers are kind of a stand-in for just about anything that a computer might need. Obviously, numbers are kind of how computers work. And so a random number generator doesn't necessarily have to make numbers exactly, right? We're talking about encryption keys, authentication tokens, and lots and lots of other things that could be covered under business logic. Yeah. So there's some interesting things about random numbers. So computers are notoriously bad at making random numbers. For the task stuff I do, I rely on them being bad at this. In general, you want a computer to do deterministic things. So if you need to actually get a random number out of a computer, you need some kind of hardware RNG to make entropy. Which should solve the problem of getting random numbers, right? Yeah. So that's how we started all this obviously was sort of thinking that hardware random number generators surely are the gold standard for generating entropy, for generating random numbers. Oh, also as a quick aside, we'll be using the word entropy around, throwing that word around. That's not actually going to be important that you understand the technical meaning of it. Just sort of assume that it means some quantifiable amount of random numbers. So like you have 121, like 128 bits of entropy, that means a thing. But it's not really important for the purposes of this talk to dig into that much further. So there are two kind of broad categories of random number generators that we're going to care about here. There's the pseudo random number generators, which are software and true random number generators, TRNGs. In particular, I hate the term true random number generators because it sort of implies a certain quality to them, right? You might think of this, you might look at this and say, well, if I want a secure device, surely I want a true random number generator. I don't want any of those stupid pseudo random numbers. I just don't want pseudo random numbers. I want true random numbers, right? The names are leading you astray here. Don't get too caught up in the names. Really the only distinction is one is made in hardware and one is made in software. Really they should be calling these hardware random number generators. That's a much better name. Get your shit together. So within pseudo random number generators, there's two kind of basic kinds. There's like the regular ones, so like the Mersenne twister, Lib Z Rand, all kinds of algorithms basically that start with a seed, an initial number, and then from that produce an endless stream of bits there forward. The regular ones are not meant to be secure. They just like make good random numbers for ordinary, non-secure usages, things like the Mersenne twister. And then there's a cryptographically secure pseudo random number generators, or SISPINGERGA for short, that are like cryptographically secure, meaning that there's no way to take the output from it and derive any of the other inputs from it, any of the previous values or the seed from it. Alright, so hardware design. So how do you actually make a piece of hardware that generates random numbers? It turns out it's actually really hard to do this properly, and lots of times you might think that you're doing it and doing it wrong. One of the other troubles about this though is that trying to get any information on how any particular device works, a particular like IoT sock actually does its random numbers, is really hard. If you try looking up the documentation, the answer is invariably fuck you. So the one exception to this is the STM32 from ST Microelectronics. They actually really great information upon some of which this is based on how to generate random numbers. So we'll go into two really good examples here. The first is using like an analog circuit method. But this isn't an exact logic diagram that you see on the screen here, but basically the way that it works is that you have like a loop in a circuit that has like a knot gate in it. And it's just going to kind of loop back and forth over and over again. It's not clocked by anything. And so the rate at which it's going to spin going 0 and 1, 0 and 1 or depending how you implement it, it could actually be intermediate values in the middle actually. The rate at which it's spinning is not clocked. So it's just going to kind of be an arbitrary, not necessarily random, but arbitrary and sometimes fluctuating frequency. And so if you just kind of pull, if you just ask it, hey, at any given moment in time, hey, what are you, a 0 or 1? It's going to be kind of arbitrary, not necessarily random, right? But certainly arbitrary. And then there's other methods too. Yeah, the other way to do it is with two clocks that are running at different speeds. So yeah, two independent clock sources, say two quartz crystals. And you're measuring the difference between the two because those two clocks are not tied together. There will always be a little bit of a difference in time between the two. So you can measure the delta, the difference between the two and get a normalized distribution effectively. This is oddly something that I struggle with on the tool assisted speedrun side when I'm trying to run stuff on a Super Nintendo because they happen to use two different clocks, one for the main CPU, one for the audio processor. They run at different speeds and it makes it very hard to get deterministic results. So unintentionally in a video game console of all things. But most of the time you'll see these implemented in just a black box. You can't really see what's going on inside of it. You just get the result out of it. Yeah, so there's a number of issues that can run up from some of these designs, right? So you imagine the first method, the analog clock method. So you're just like you have this circuit that's looping, right? Well, what if it's the case that your CPU is much faster than that loop is? You might ask it, hey, what is the value of it? Okay, it's a one right now. And then really quickly afterward you ask it a second time and they didn't get a chance to loop around. It's going to give you a one and then a one again and then a one again. Or what if you're like the clock that you're asking it at just happens to be at a multiple of the frequency of the thing, right? You're always going to get the same answer every single time you ask it. So this isn't actually a really hard problem. So in order to like generate random numbers in the like laptop space, like if you have a desktop computer or laptop server, there's some like beefier methods of doing this that involve like pulling entropy out of the universe through like electromagnetic frequencies and crap like that. And lava lamps and lava lamps, you know, but in the IoT space, things have to be really cheap obviously. So these are two really common designs that you're likely to see. Sure. So in the year 2021, most devices have a most IoT socks that you'll buy us a system on a chip, how you start an IoT device will have a hardware RNG peripheral on them. That is a like a piece of device, a piece of hardware as a device that's made to do this one and only one thing. Surely you must think that like that's fine, right? That's super secure like what's the worst that could happen. The problem starts running in that there's no operating systems in IoT devices typically that really what you're doing is just writing C code that runs on bare metal. When you talk to a peripheral like any other kind of peripheral, you the operating, you the user of this device has to write code to talk to that individual peripheral at the hardware level. C is hardly even, C is usually derided as a portable assembly, but it's not even portable in the IoT world that like trying to run it against a different device is not even a really a thing that works. So this is not any different in the world of hardware RNG peripherals. You basically are given something like this. There's a how function, a hardware abstraction layer function that says here's how you call the RNG. It's a C function that looks something like this. So if you're not familiar with C, there's a function name that's how get random number. This is just pseudo code. Obviously every device is going to call it something slightly different. It'll have an output variable which is a bit weird if you're not familiar with C. This will come up later, so keep in mind this, but you give it a pointer to a region in memory that says here's where you should put the results. So it's an output variable. It's usually a 32 bit number. And then it will return an error code. Whatever that happens to be a boolean, unsigned, 8 bit integer, whatever that happens to be. So I'm going to let him take the rest of this part. Oh, you're sure. So of those two parts, like there's really two things we care about here, right? That output variable and return code. So you can ask the natural question, which is the first question that we thought of upon doing those research was, there's an error code, huh? Like, there's a lot of things that can go wrong when you're calling a piece of hardware. Like, what if the hardware just isn't ready yet? Or what if, like, it was busy? Or what if, like, the relative positions of Jupiter and Saturn aren't aligned for all we know? Like, the hardware could just have an error. And like, what happens if it errors? And what happened? How many people out there are actually checking this code? It turns out almost nobody checks the return code of the hardware RNG function. These are just two examples. Yeah. So what we're finding is that code online repeatedly just doesn't even bother to check the error code. So what happens when you don't check the error code? Well, undefined behavior happens. It's not written down what will happen. So usually undefined behavior is undesirable. So there's a couple of interesting things that can go wrong. Usually you are going to get either partial entropy. Like, some of it is random. Some of it isn't. But one of the interesting results is the number zero. A lot. There's an example down here where the first call got random numbers. The second call, still random numbers. The third and fourth call, they're just zero. And you might not necessarily notice this when you're looking at a file. It might not necessarily pop out at you right away. You can get things that look like they're pretty random, but they're full of zeros. This is the classic XKCD joke of dice roll. Okay, we're just going to return a static value. Just a constant. Here you go. Oh, actually here. Oh, you have one thing. So there's, the XKCD joke is sort of a joke, but it's also kind of an actual real problem. If you see a number like we have to deal with here, right? How do you know that those zeros are, like, not random? The sort of left with this, like, deeply existential problem, which if you try thinking about it too deeply, it will cause you to go into a deep existential panic, and I recommend you not do it. But you're actually left with a real logistical problem of, like, how do you know random data versus not random data? It's not labeled for you, right? Like, how do you know that? And so much of the brunt of our talk at the end here is going to dig into exactly that. So this is also anecdotally how this whole thing sort of got started. We, pentesters, obviously, at Bishop Fox, and we do a number of what we call product security reviews, where if it's like, usually we say, like, if it drops when you break it, then it's a product security review. And so we, on one occasion, we're on an engagement testing, an IoT device. It was like a security device, right? And it involved a lot of cryptography and a lot of random number generation as part of the cryptography. And so on a lark, we just sort of asked, like, hey, like, what are you guys doing for random number generation? Like, on the device, they answered, oh, our SOC has a hardware random number generator embedded on it, so we just sort of used that. And so then on a lark, I just asked, like, hey, could you just, like, give me, like, a gigabyte file, like, just like a big dump of numbers from the RNG, just so I can look at it, right? Just to, like, see how good or bad it is. Kind of expected to just check out, you know, it's a, it's literally a piece of hardware designed to do just this one thing, right? And immediately, it just failed all the statistical randomness tasks we threw at it, which was concerning. And then you just look at the file, you kind of scroll through it, and just large swads of it are zero. This was very concerning. And to the point, I was thinking, like, surely this must be, like, some crazy buggy code or, like, what is going on here? And that sort of leads us down to basically everything that came out of this presentation. So this is where I'd like to segue into what I want to call Petro's Law. That's me. If I could have one law, one eponymous law, help me out here, Defcon. It would be this. It can always be worse. No matter how bad you think it is, it can always be worse. So you might think, wow, entire device making crypto keys of zero, how could it be worse than that? Let me show you. Uninitialized memory. So you might recall that the howRNG function uses an output variable from the call to store the output from, because it has to use the return code for the error code. Well, lots of the howRNG functions will operate in a way that they don't actually set the value to anything in case of an error. Sometimes they'll set it to zero, and that's how you get all those zeros. But not every device works that way. Sometimes if there's an error code, it just won't touch your variable. So if you do something like this where you declare but not instantiate a variable as your random number, it'll just be something in RAM. And then you send it to the howRNG function and then send that on its way out onto the internet or to a potential adversary. You're basically heart bleeding yourself through the random. You think you're sending a random number to your adversary, but you're actually sending tiny chunks of your RAM. Basically like heart bleed style like on your device. And what's so bad is like it'll actually sort of kind of look like random numbers some of the time too. And this is very likely to occur in the real world where you might be doing something like a Diffie-Hellman key exchange where like the very first thing you do is generate a random number and send it to the other guy. So yeah, that's terrifying. So one of the things we want to touch on is that there was a talk, a given, let's see, was this 2019 I believe, that they looked through a large number of certificates and like millions of them. And they found that one in 172 of the certificates were vulnerable to attack. Now I'm not saying that what we're presenting today is what they found, but I'm saying that what we're talking about is what they found. Yeah, in this research in particular, they called out low entropy IoT devices as like one of the like reasons that all these certificates were failing. So one of the things that we immediately realized upon doing this research is that one of the things you should expect to see if this were the case was that lots of IoT devices out in the wild should be like generating bad certificates. And lo and behold, that's like exactly what we see. And so this might actually very well be like the cause of this prior research. So this sounds all nice and tidy, right? Like those stupid users just keep on calling things wrong, ignoring the error code of the HalRNG function like a tale of the oldest time. And all we got to do is get them to use the stupid functions, right? Those stupid users. Like let's actually walk through this a little bit more, right? So the very top here is some code from the MediaTek documentation from the 7697. It has the HalRNG, the tRNG function, I fucking hate the name tRNG, get random number, you give it the output variable, it's checking the error code. And it has this comment in here that says error handle. It turns out that that comment handle error is doing a lot of heavy lifting. The problem is that when you're doing some security critical piece of logic, right? And you need a random number. You really need it. You can't just continue on without it and handle the error, right? It's sort of critical to the core thing you're trying to do at that time. So you kind of just have two options. There's one which is to spin loop. This is actually recommended in some of the documentation and it's terrible. You're just going to keep on calling it using 100% CPU, spin looping, maybe forever in case of like a broken peripheral, like that's a terrible solution. Why would you ever suggest people to do that? Why would you ever expect developers to do that? The second is just to quit out and kill the process entirely. Like can you imagine if like you're in the networking and you're making TLS connections to somebody else and like the RNG function generates an error. Which happens all the time. Like if you're trying to make a 4096 bit RSA key and you call the RNG function really, really quickly, you're literally going to be incapable of creating an RSA key basically using the RNG functions this way. It'll just quit out of the entire network. Like it'll be a stupid and broken and useless device. So what do you give developers? Well, if they can't handle the errors, YOLO. You just go for option number three, which is to ignore the error. And doing that has some consequences. It's not that... How do I say this? Really, it's not the fault of the user. You can't blame them here. They're stuck in a no-win situation. RNG and IoT are fundamentally broken. And now there are some right ways to do RNG. What we're going to probably be talking about for the majority of the talk from here on out is why you need a cryptographically secure pseudo-random member generator. So let's talk about the right way to RNG. As a cryptographically secure pseudo-random generator has some distinct advantages. Namely, it never blocks execution. So we don't have to worry about that here. API calls don't fail. It specifically, and this is the big thing that you should hear, it pulls entropy from multiple sources. So if you have an IoT device, it's probably got one hardware RNG. Now, the problem with seeding anything, even if it's a pseudo-random generator with only a single source, is that if you're an attacker and you control that source, that's what the end number is going to be. This is how tool-assisted speedruns work. As an attacker playing a physical Nintendo, I'm controlling the only source of entropy, which is player input, thereby guaranteeing that I always get exactly results I want and the deterministic behavior out of the pseudo-random generator. So you don't want to rely on a single source that an attacker can take advantage of. Instead, you should be pulling your hand and you would have to have full control of every single source at the same time in order to manipulate that. There's also the big advantage of cryptographic, we secure pseudo-random number generators and I'm not even going to try to get into the same, I'm going to say CSP RNGs always return cryptographic quality results. We're going to come back to that in a second. And this is how every major operating system works, Linux, Mac, Windows, BSD, Solaris, they all have some method of doing CSP RNG and IoT should as well. Anything else you want to say on that topic? Yeah, so the CSP RNG subsystem basically works like the diagram here, right? You're going to stretch out that initial entropy pool indefinitely going forward. In practice, the algorithms for doing this can actually be rather simple. The easiest way to construct one of these is just by using a hashing function. So you just take the entropy pool and you just like it. You can pick whatever hashing function that you prefer. I like md5. You md5 your entropy pool, right? And then in order to produce the next batch, you can md5 the entropy pool and also the last thing you just made. And you can keep on chaining that out indefinitely going forward until that way you can kind of keep on making bits infinitely into the future. What's nice about that is because it's a cryptographically serial hashing function, you can't go backwards. There's no way to take the bits output from it and then derive the seed or any of the other values therein because you also need to know the entropy pool itself. You can switch around those seeds and like I was saying, that's basically how this works everywhere else just not in the world of IoT. So yeah, basically we're going to go into why you really do need a CSP RNG subsystem and know you really can't just make do without it. So nobody codes from scratch, right? If you have a library that does what you want, you're going to use that library and in IoT there's lots of reference and example code for how to call hardware random number generators, even libraries to do it for you. But sometimes the reference code has vulnerabilities that propagate. There are some really unfortunate examples of this. You want to actually talk about these ones? You know this the best. So yeah, the way that some libraries work such as Contiki NG specifically when using the Nordic NRF 840 SOC as well as the link at 7697 Arduino code when you call it for a hardware you call the how function, you might think like I'm going to be getting a number from the hardware RNG, right? That's not actually how it works. All it does is take the hardware RNG, generate a seed and then use libc random there forward. So you're actually not even using the hardware RNG really, you're just using libc random. That is as broken as it sounds and for that we actually have a demo video. Let's see if the audio works on this, there's an audio on this, so if there's anybody that needs to turn that on in the audio section then they should be good. So for this demo we built an IoT security camera device. It takes pictures every few minutes just like a real security camera and post them to a publicly accessible website. So the only thing keeping an attacker from being able to view your photos is that each file is named to this long random file name here, chosen by the camera. Now before you go through. It's not playing. No, the video is not changing. Oh yeah, there it is. So for this demo we built an IoT security camera device. It takes pictures every few minutes just like a real security camera and post them to a publicly accessible website. So the only thing keeping an attacker from being able to view your photos is that each file is named to this long random file name here chosen by the camera. Now before you go thinking that this is unrealistically vulnerable, this is how Discord works and lots of other applications like it. Anytime you take a photo and send it to a friend over Discord, it's publicly accessible. The long random file name is the only thing that's keeping people from seeing your photos. Our device, however, is built using Contiki NG, a popular IoT operating system. When you call the operating system to get a random number it will use the hardware RNG on board, but only to seed the insecure libc random function. So we don't know what the seed is, but we don't have to because we can derive it. So suppose one day you take a photo with your camera and post it on social media. Well what a cool camera you bought. How fun. But what you didn't know is that the attacker can use this file name to derive what the original seed was that generated it. That's because that's how the libc random function works. Our attacker here uses untwister to find the seed. Once they have they can use that seed to determine every past and future value from the RNG. So our attacker can just plug in some of those numbers back into the camera website and view every photo that the camera has ever taken even if they've never been shared before. Cool. Alt tab. Excellent. We're back. That was demo. Cool. So anytime we talk about random number generation and security, the conversation goes to exploitability. How exploitable is this really? Sometimes they turn out to be cryptographic vulnerabilities where crypto is often considered broken if you're able to break it even just a little bit. If you're able to derive RNG, like 128 bit ASP and 127 bits, that's considered broken in cryptographic terms and sometimes RNG vulnerabilities are the same way. Turns out this is very real and very exploitable but just not in a very canned way. So the very often what you're going to find here is that it's going to depend on the particulars of the individual device that you're looking at. Again, like I was saying earlier the IoT devices tend to be really heterogenous and very different. There's a single piece of logic that all IoT devices like use. Not all of them talk over HTTP. Not all of them even use TCPIP. So you're likely to need to look into the individual business logic of the individual device that you're looking at. So it's very unlikely to be like you're doing it wrong .py that kind of like you can just point at devices and like exploit. So keep that in mind. One exception to this, one perhaps notable exception to this is actually asymmetric cryptography. So one of the things that will cause these RNG health functions to fail is calling them very quickly over and over again. And if you're trying to make a 248 or 4096 bit like RSA key, you're going to need a lot of bits and you're going to have to call the RNG function in a loop over and over again and it's a very reliable way of causing the RNG functions to fail. And so if you were a pen tester and you're looking at like trying to use this in your upcoming IoT engagement, I would definitely keep an eye at any asymmetric cryptography that your IoT device is trying to do. Especially if you're able to look at the code, then see if it's checking the error codes coming out of the health function and if not, then there's a very good chance that virtually all of the asymmetric keys that it's creating have just big chunks of zeros in them. There's also a separate talk at this DEF CON called the mechanics of compromising low entropy RSA keys. We did not plan this, that's just kind of a thing that happened. So there's also, I haven't seen that talk yet, there might be some interesting new exploits coming out of that that might be practical for pen testers to use on like actually using some RSA keys that have a bunch of zeros in them. So if you are a pen tester again and you have like an IoT engagement coming up, whether you have source code or not, is going to dictate a lot of like how you're going to try to like attack this going forward. Try to tax the RNG as much as possible. So if there's like a remote request that you can perform to the device that you know will cause it to use the RNG, basically spam those requests and see if they start coming back zero. And that would be like a really good way of trying to see that. Or if you know that there's going to be a lot of photography then keep an eye out for that. Okay. So he had his law. Mine is somewhat different. Alan's law is going to be never write your own RNG code. It's as dangerous as writing your own crypto code. Everyone knows now, or everyone really ought to know by now, that you don't write your own crypto code. It's very difficult to do right. Well, this is at the same level. It's no different than crypto code because there are so many ways to do it wrong. We already talked about the user is already in a bad situation as it is. But even if you manage to do all of the other things right, there are still some interesting gotchas. Sometimes the hardware itself has things you would never expect to encounter. One of the examples we ran into was the LPC 54628. There is a warning on page 1106 that says if you want actually random numbers you have to ask for a random number then ask for 32 more random numbers but throw those away then ask for another random number then throw another 32 away and repeat until you have the length key you want. If you saw this code written down you might think it was a mistake unless someone heavily commented why they were doing this. You would read this code and think what you have to do in order to talk to this particular hardware RNG correctly. And this isn't the only bad example. Even if you are you this is pivoting the talk a little bit but I'm going to get passionate about this one even if you do everything right you read that 1,000 page manual you find the weirdness you're still not out of the weeds you can call the hardware RNG spin loop do everything right you get random numbers that are not random so this is an example of taking a large multi-gig file of randomness and then doing a statistical analysis of how often each byte happens to appear. So 0 through 255 which bytes are happening or which values are happening more often in this byte and what we find on the media text 7697 is this very interesting sawtooth pattern what you would expect to see is that it happens with an even distribution they're all happening at the same frequency and that's not what's happening at all and if you zoom in a little bit you can actually see that the sawtooth pattern of unequal frequency repeats which is even more mysterious and we would really like to understand what exactly was happening there I'm going to let you take this one So you think surely it can't get worse so basically what a lot of this involved was we had to write code for all of these digital dev boards, these socks bought up like every internet of things dev board that we could get, write code for them that would generate random numbers and store them out to a big file, like a couple of gigs worth of files and then analyze them offline. One that's actually really hard to do logistically that very often dev boards are just not set up to do this and had to have some janky setups of uploading it to a web server that we were connecting to and we had to get the I.O. out of the thing it was Wi-Fi and sometimes you can output it over a serial line sometimes they can only read and not write over serial, it was a complete mess so that's kind of the analysis that you're looking at here is us finally like okay no more shenanigans, no more like weird API gotchas no more like silly randomness stuff that can happen through the APIs like what is the actual randomness like coming out of these things is it good is it bad? So this is obviously not great obviously repeating patterns and cryptography don't go along very well together. This is from the Nordic NRF 52-840 it has a curious repeating 12-bit pattern it has three zeros, the 12 bits that repeat every exactly in hex 50 bytes except sometimes it jumps it'll go like 80 or so and so weird that we thought for sure it must have been a mistake in our instrumentation for the longest time and no matter what we did it wouldn't go away so we think it's not that for a few reasons, one of which being that we looked at the code for a really long time and had no idea how there could possibly be a 12-bit repeating pattern if it was one bit you think like maybe it's like a null terminated string you're copying it around stupidly I'm completely capable of writing that code but 12 bits like how does that so that was very concerning it also sort of says something as well that like even if it turns out that so also we're going to be releasing all I think it's up now, releasing all of our code on our github so it's on github.com slash bishop fox there's a repo called you're doing it wrong that has all the source code to the devices that we did and also some of our results things like that so it's entirely possible that maybe this was the result of some buggy code so you have to consider what it means that you know two computer security experts spent months analyzing rngs and spent months trying to find bugs in the rng code that they wrote and still failed at it like what does that say about the state of IOT security having to do with rngs going forward that's very true for the STM32 in this case I took an L432 KC try to say that fast tried to get good random numbers out of this and I failed and I tried again and I got some help and I failed and we tried again and tried blocking in a different way and we still failed the initial numbers we got out of this looked terrible because we weren't actually doing the blocking correctly once we got all of the blocking fully worked out we were spin looping every time we needed to wait for the air condition to clear only getting random numbers from the device and we still had a problem it was mostly clean but then when we ran it through dieharder which is a suite of statistical analysis tests it still managed to fail a particular minimum distance test with a high degree of certainty I'm going to let him try to explain this part of it yeah so there's a well known tool called dieharder excellent name that is a statistical randomness test that's used outside of security people use this for other things like the number of tests one of which being the RGB minimum distance test RGB is just the initials of the dude who made it so the minimum distance test is basically you take a bunch of numbers and you interpret them as integers in n dimensional space and then calculate using a very simple algorithm what the smallest distance between any of the numbers is so really what this is doing is trying to find repeated values or nearly repeated values so you can imagine a world where like you have a generator where some value depends on some other value that's earlier on in the sequence right and maybe it's not always exactly the same maybe it's like it jumps a little bit or something like that those kinds of correlations between data can be really hard to pick out and there's lots of ways of trying to find them this isn't the only way obviously but the way that this works is that like if there's any repeats there's going to be two points in that space that are going to be close to each other and so when you do the subtraction they turn out to be zero or near zero so you can run this test and it'll kind of tell you whether things fall into expected parameters or not so this one was curious only because we never quite figured out exactly what was going wrong with the STM32 like exactly what that repeated value was or like how concerned we should be exactly about it but the whole point of hopefully this presentation is that you should need to care about this sort of thing like the output of the hardware random number generator raw like this is a thing that you should be using as an input to a cryptographically secure pseudo random number generator and not like on its own so we have some conclusions for you and some of them are going to be bigger than any one person because this affects the entire IOT industry it's not a single vendor it's not a single device it's not a single library it's not that the only viable solution is a CSP RNG subsystem that is implemented in software so this can't be fixed by changing documentation and blaming users I'm going to steal a line from him the good news is that this can be fixed through software the bad news is it has to be fixed through software and we're talking about IOT devices here RNG, I said this earlier RNG code should be considered dangerous to write on your own it's just like crypto code you really need to have a viable subsystem that you can call that's already been vetted and last but not least if we haven't shown you this at least enough examples of it there are more out there we didn't include here that you can find in an article we wrote we have more examples of bad stuff but you really don't know how strong or weak your hardware is actually going to be it's really hard to tell what can you actually do about this it depends on where you are first is device owners this is going to have to be a software fix IOT devices not known for their ability to be patched out in the wild but at least it's possible for some devices that have the ability to do over-the-air updates some of the ones that are particularly sensitive to a random number like if it's a security device then hopefully this will be a thing for IOT developers there's this emerging space of IOT operating systems things like Riot OS there's Kintiki NG FreeRT OS we don't have a particular one that we would recommend over the other but the CSPRNG subsystem there since the individual device SDKs are you're unlikely to see the sort of feature here those are mostly about hardware enablement and not so much about trying to implement features that make like a full device so if you're developing a whole new device from scratch I'd really recommend using one of those one because they're actually pretty handy and there's other benefits to them aside from security but that's certainly where the security is there's servers and laptops and desktops because there's an operating system you can just ask Linux like hey please give me a random number just ask devu random for a random number and it will just give it to you and it's perfect but this is not true in the IOT world and it really needs one so IOT device manufacturers and those OS developers you really do need to implement the CSPRNG subsystem like there's not a way around it you can't just change the documentation or try to change the documentation to get people to check the error codes none of that stuff is sufficient it can't just change by blaming users disallowing users certainly deprecating the HAL functions for the RNGs would be a nice way and perhaps even just disabling users from being able to use them entirely would be a good way to go forward and for pentesters this is likely to be a perennial finding for years to come if you have an IOT engagement coming up then keep an eye out for this especially if you have access to source code then trying to find it could be pretty simple and then building out an exploit is going to be highly contextual dependent but entirely possible and that's about it thanks a lot I'm Dan Petro I'm Alan Cecil and I think we're going to do Q&A how much time do we have? if somebody wants to shout we can repeat a question there I see a hand do your very best to shout I didn't hear much of that I'm afraid perhaps you could come a little bit closer yeah so I guess the question is like maybe how hard is it to implement your own CSPRNG subsystem maybe a decent way to do that there's a couple ways you can do that by like the hashing function RNG like code that you can do those are if you're in a real pinch then those are probably better than just like making the call to the howl function yourself there's definitely a lot that can go wrong in the development of a CSPRNG subsystem that's non-trivial and in the abstract I'd love to say to not try to make that yourself but it's not the end of the world it's certainly a lot better than the alternative of just like yoloing the howl function yes there's a lot of implementations of that that are like simpler than others and the simpler you can get probably the better as long as you're sure that it's actually a CSPRNG sub-RNG and not just like linear congruential generator or something like that yeah and again if you can source from multiple entropy pools I don't really care what you use just try to find more than one entropy source so an attacker would have to control all the variables at once time is not a variable that you should use cool do we have yes right in front so there is a FIPS standards like FIPS 140-2 or something like that I want to say around a specifically random number generation and the question is like did we notice any difference between like ones that were like FIPS certified and ones that aren't I think the short answer is no that like the certification so the best that we found was specifically around ST micro electronics had like a proof of randomness they had their own code you could look at so huge shouts to ST for that but otherwise I don't think we really notice the difference between like FIPS certified devices and otherwise yeah and one thing I should note is we were trying to replicate STM32s or the results that ST micro released we were trying to validate and replicate those results and we couldn't do it so it might be that it's from a vendor might work differently than the next one same exact model family just a different device and somehow is less random we don't know so I think that we're going to be doing is there a room for Q&A that we could follow the mob of people that is invariably going to be following us to a Q&A session afterwards we'll keep answering questions for a while but otherwise yeah thanks a lot thank you very much