 I work for a little company called Rose Point out of Redmond, Washington, and we've been using NERVs to build devices for the marine navigation world. And I also have been experimenting with NERVs independently. So I'm going to talk about NERVs a bit. I'm going to talk about where it's been and where it's going. And I'm curious before I start to get an idea of how many people here have heard of NERVs before. Wow. I'd say more than half the audience. That's a huge difference. At ElixirConf I asked the same question. I got just a few hands. How many of you have actually tried to use NERVs? Far less. Okay. Well, good. How many of you have seen the previous talk that I did at ElixirConf or one of the previous talks that Justin did? A few. Okay. Good. I'd say about 10. I think that was. All right. So I guess I'm going to go through a little bit then on what NERVs is. NERVs is really a way to build firmware using Elixir for small devices. And I really kind of wish I had seen the previous talk before I wrote these slides because I have so much, I have such a kinship with the concepts that Jean François presented including the Society of Agents concept, which is one of the main reasons that I started getting into using Elixir to control devices. And so I really resonate with what he did there. And my motivation for getting involved with NERVs in particular was to be able to apply those concepts to embedded control systems. So what NERVs is is really three separate pieces. We have a platform, which is actually kind of a, you can think of as a custom build of Linux that's designed for small devices, a framework, which are basically libraries and to do common kinds of things that devices need to do. And then we have some tooling that makes it easier to actually get the firmware built. And I'm going to talk about all three of those. And especially the third one I'm going to talk about today. There's some major advances in tooling over the last few months that have made it much more accessible, it made NERVs much more accessible to most of you than it used to be. So I just want to emphasize NERVs is actually being used in real shipping products today, has been for over a year now. We have, this is my company's products, we have two products on the market now using NERVs and we're working on some others. And it's so far been rock solid for us. NERVs itself has not been any issue. We have a number of devices in the field that just go out and they work. We don't have issues with memory leaks. We don't have issues with stability at all. And honestly, the biggest issues we have are things like cabling with these devices and other user installation issues. So why Elixir? I'm going to start with that before I get into why NERVs. And to me, Elixir is such a natural fit for embedded control systems. It's unbelievable and that should be expected but I think most people forget that Erlang was actually originally invented in an embedded context. It was designed to run telephone switches, which are one of the more complex embedded control systems out there. And so it shouldn't be a surprise to anyone that it works really well there, especially because it was working on hardware 20 years ago and the hardware now is so much more capable that it's a natural fit that it should be easy to do all this stuff in Elixir. I get people still don't seem to think of embedded as the natural fit for Elixir. Some of these points are pretty obvious. The last point I have to admit, I did doctor my slide to put in society of agents in the parentheses there. But this is exactly what I meant by the actor model. The actor model meaning a bunch of independent things that are sitting and listening to events and hardware and deciding what to do with them. It turns out that I've built control systems in Python, C, a shame to say visual basic back in the 90s, right? So once you've gone through a bunch of different iterations of building these kinds of systems, one thing really emerges about control systems is it's a highly concurrent problem. There's lots of asynchronous stuff happening. And Elixir lets you solve those problems in ways that you just can't with other languages. And of course, binaries and pattern matching are a godsend when you're dealing with low-level protocols from devices. So why nerves in particular? Let's see. I'm going to go, these are a couple slides that some of you may have seen before. So I had this slide up from the previous talk I gave. Many of you have seen a variant of this slide showing just how dramatically CPU power has increased over the last 20 years or 30 years or 30 years. And really today you can get something that you couldn't have possibly imagined getting back then. It's created this incredible explosion of devices. There's lots of them out there from lots of manufacturers and seem to be more every day. There are two in particular that caught my attention and got me into this. The first one was this thing called the Beaglebone Black. I'm curious how many of you have seen this or used it? Okay, quite a few. So Beaglebone Black is interesting for a couple reasons, but to me the most interesting thing is it's open source hardware. So unlike the Raspberry Pi, you can literally engineer something on the Beaglebone Black and put it into production. And you can take the schematics from the Beaglebone Black and the board layout that they give you and basically build your own board around it, eliminate the components you don't want. You can source all the components in small quantities. So if you're a manufacturer and actually wanting to build a real device that ships to consumers, this is a great prototyping platform. It also uses industrial temp range components for the most part, so you can actually build products that meet fairly rigorous specs. Most of that is not so true of the Raspberry Pi, but of course there's the Raspberry Pi and I didn't have a picture of the Raspberry Pi 3 to put up here, but as many of you know it was released a week ago I think and something like that. Still 35 bucks and it adds Wi-Fi, Bluetooth and a 64 bit cores that run I think 1.2 GHz. So the trend continues for more and more horsepower in these tiny devices. So NERS fits in kind of in this space. It's neither a real-time operating system for little tiny devices like calculators nor is it a...or it's not a microcontroller, it's not a real-time operating system for tiny devices nor is it like a general purpose thing like iOS or Debian. It really fits in the middle of those spaces and that's kind of a sweet spot for a lot of consumer or industrial control solutions because you want something that is really isn't...it's smart enough to do something like a Society of Agents model but still manageable in terms of updates and ability to produce small reliable signed releases. So I'll get to all some of that. So I want to talk a bit about how NERS works. Some of this is our old slides and I'm not going to go into...spent a lot of time on them but they're still better than the ones I have now in terms of giving an overview. So basically your app gets cross-compiled so it's not actually running entirely in the...I mean it runs on the Beam interpreter but you may have C code for instance with your app that needs to be cross-compiled for the target platform. So if you're running on something like a Raspberry Pi, your C code that you have has to be of course in ARM form and so NERS gives you a process to cross-compile all the stuff, wrap it with your Erlang code or your Elixir code and bundle it together with a minimal Linux and all the features that are needed to support Linux or to support that platform and burn it into a small tight firmware image. To give you an idea of what we mean by small and tight, it's about 18 megabytes which if you're an embedded developer you'll say that's huge but if you're a Linux guy you'll realize 18 megabytes is nothing compared to most Linux distributions and that includes Erlang, Elixir, and your app. Let's see. So it fits generally, we generally put things on an SD card, there are options for how you do this but generally what we do is we put two different partitions on an SD card each of which is a complete system and can be booted and the nice thing about putting two complete systems is that you can update one while the other is running and then reboot to the second one. So this gives you a way of doing firmware updates and fall back. The entire system and app is a monolithic chunk that's created so you don't have to, you really, and it also, excuse me, it also runs read-only and read-only file systems may be kind of a new thing to those that are in the web world but if you're in the embedded space read-only file systems are almost a requirement because they give you stability and reliability for things like power being pulled and security features, we'll get some of those. So the other thing about NURBS is it boots really, really quickly, generally about four to five seconds before your code is running, sometimes even less. And that does not include the time it takes for the bootloader to decide to actually start booting but this is from the time the bootloader starts loading things off the disk until your app is running generally four to five seconds. It's also reasonably small in that we, this is actually from a slide that Frank Hunliffe did for a camera project that he had about a year and a half ago but the exact same slide with almost exactly the same numbers applies to the devices, to at least one of the devices that our company is shipping and that is we're seeing the memory goes up, we end up using about 28 megabytes of RAM and it just stays there and it'll stay there not just for days but for weeks so it's incredibly stable and immune to memory leaks so we're really, really impressed with the platform. Let's see, we talked a bit about firmware updates already so I'm not going to go too far into that. So basically to recap what NURBS is, it's both a platform which is the operating system piece and the tool chain needed to build your software, it's a framework of libraries and it's this tooling that puts it all together and wraps it together. So one of the questions I hear occasionally is well okay I have a Raspberry Pi, it comes with a Raspbian, why don't I just use that and the best answer is you should if what you're doing is playing around and building a, you know, something that's for your own use and you just want to kind of make it once and you don't mind having to install Raspbian and compile your code on the Raspberry Pi and you don't mind updating things by using apt-get update on the host or excuse me on the Raspberry Pi. I think Jean François said that he installed Erlang by doing compile on the Pi, it takes a while, right, the first time. It's great but let's say you're actually trying to build something that you want to give to 50 people or 500 people or 50,000 people and actually turn it into a product. It's not a viable solution for using Elixir in that regard and NERVs is really designed more for producing a production ready, robust environment that can be deployed in large numbers and maintain in large numbers. So let's see, some of these slides might repeat things I just said. Yeah, oh read-only file system, so I alluded to this before. Dibbian is not a read-only file system, you're not going to be able to have a stable device forever, it may last a long time but there will be issues that will come up because everything that happens eventually changes that root file system and so if you're looking at putting something into the field that's going to be used for years or decades without being touched, it's very hard to build a system like that on the stock Linux that comes with these distributions or distributions that come with these devices. Let's see, other challenges in the embedded environment that make the common distributions difficult is quite often things will lose power, regain power, lose power, regain power right in the middle of something important like writing a log or whatever or worse, writing configuration and so it turns out in the real world in embedded devices you have to be very, very careful about when writes happen and how they're committed and manage especially the application partitions so that they don't get corrupted and NERVs has a philosophy of read-only partitions that we've talked about but also the other philosophy that's throughout NERVs is you don't write to storage unless you really want to and you know when you do it and that ends up being a really important concept. Some of these other things are pieces that NERVs doesn't entirely do yet like remote management certificates but part of the NERVs philosophy is to build tools to allow you to do these kinds of things and build production devices and certainly remote management is part of that. So a quick comparison between NERVs and Raspbian just to give you an idea of the scale of thing we're talking about. Okay, so the second part of my talk which is going to include a little bit of a demo is what's new, at least I hope the demo is going to work, we'll find out, what's new with NERVs and what's really new I'll get to in a second but I'm going to talk about some things that are, so I'm going to talk a little bit about what's new in the platform first. So the number one thing that's new is we do support a couple new boards. We now support, we don't actually have official support for the Beaglebone Green yet although I don't know that there's any reason it won't work. I'm not sure you'll be able to have the drivers for the, I remember what those ports are called that are on the green, but we plan to support the green. The Intel Galileo has official support now and the Raspberry Pi model zero has support and then of course we support the original Pi and the Pi B plus and the Pi 2. We don't yet have support for Pi 3, that's something that is going to be coming. So the other thing, I say here, community board support coming soon, I'll talk about that a little bit later, but our goal is to break apart NERVs so that we can let you create support packages for hardware you're interested in. So if you have a particular hardware platform you love and you want to get NERVs working on it, you can create a GitHub repo that has the details to support that particular board. Let's see, we're doing some things with the framework. This is actually an area that I personally have lagged on getting some of my stuff done. Part of it has been waiting for the tool chain to settle down a bit. So firmware updates are still real soon now and part of that is that we've revised the way that we actually write firmware to create a tool called Bake, which I'm going to talk about now. So Bake is a thing that I talked about a bit back at ElixirConf in October. Bake is a tool that lets you assemble firmware for one of these devices. And back when I talked about it in October, the big problem with NERVs is it has to be cross-compiled. The even bigger problem is because NERVs is based on BuildRoot and BuildRootLinux, BuildRootLinux likes to be built on Linux, not anywhere else. And it doesn't have support for compiling BuildRoot on OS X. And so the way that we were going to solve this for Mac users, and if you look around, we'll see why this is a big issue, including me. We had to take our source code, shove it up to a server, have the server build everything under Linux, and then ship the firmware back down. And that was the strategy we had for doing builds in the bake that we talked about. So increasingly it's clear that's not a great answer. So Justin Schneck and Frank Hunlitz got together and came up with a better answer. And I'm just amazed that this works at all. But basically we now can do builds of firmware entirely on the desktop on the Mac. And the way it's done is to break apart some things called tool chains and systems. And so there are pre-built tool chains and systems for common platforms that get downloaded onto your machine. And then you can actually build firmware entirely on your machine. And I'm going to do my best to demo this. We'll see if it actually works. Now the real challenge is how can I get to the screen that I demo it? Let's see if I can figure that out. Hey, sort of. I'm missing a character on the left, but we'll live with it. Okay, so I'm here in a little demo app called Blinky. Any of you that have looked at the NERVs repo know that this is like the most commonly built app. All it does is blink lights, right? It's pretty basic and stupid. But the way we're going to build it is not basic and stupid. So just to give you an idea, this is basic. I'm sorry? Let's see, a little more. Is that good? There we go. Okay, so this is basically nothing more than a stock mix new app with a couple configuration changes. I'm going to see if I can get an editor to show up on that screen so you can see what those are. Okay, yeah, this is going to be difficult because my tree's off the left-hand side. Maybe I can, there we go. Okay, so this is the one and only Elixir file in the entire app, which is it's a little more complicated than it needs to be. And I'll explain why in a second. It actually supports blinking lights on a number of different platforms. I want to point out two different files here. There's one called bakefile and one called bakefile.lock. And then let's look at our mixfile first. So you'll notice in our mixfile, this is pretty much a stock mixfile with exceptions that we've included a couple modules. We included new NERVS IO LED, which is the way we actually blink LEDs. We've included logger. And then we've included a dependency on NERVS itself, the NERVS package. And just by doing this, we now have all the support we need to build this app. The bakefile is an app that basically says which recipe to use to build a firmware for the given platforms you want to target. So this particular sample right now is set up to either target Beaglebone Black, the Raspberry Pi 2, or the Raspberry Pi. And I'm going to build it for the Raspberry Pi 2 here. So let's see if I can make that work. Okay, so the first thing you want to do is install bakeware. And bakeware is actually, you can find it, bakeware.io. I'm not going to actually take you to the webpage. But there's instructions for installing it there. It works on either Linux or Mac today. If you're extremely excited about Windows and want to help do that, there's some people I could hook you up with. So let's do bake. So what this is doing is saying, let's get the system needed to build this firmware for its standard default target platform, which I have set as Raspberry Pi 2. And it turns out that's already in my cache. All the systems are cached in a subdirectory of your home directory. So it's already pulled the system. But if I look there, you can see there are a number of different systems for all the different versions we've been through, some for the Raspberry Pi 2 and some for the Beaglebone Black here of different varieties, including some that probably I shouldn't use today. So it'll download this automatically for you and put it in your cache directory if it's not there. Otherwise, it just leaks to it. And then I'm also going to get something called a tool chain. And what this does is it looks at your current project and grabs a tool chain that's useful to build this project. And the tool chain it chose is Nerve's arm, unknown Linux, whatever all that is. Anyway, you get the idea. But it's basically a tool chain designed for this version of OS X to build and cross compile code for the ARM platform. And it turns out the same tool chain is used for either the Raspberry Pi or the Raspberry Pi 2 or the Beaglebone. So at the moment, you don't need to be download very many tool chains to support all those. And given all that, I can just type bake firmware. And it goes through and does a bunch of magic. Make sure that it has everything up to date. It uses those tool chains. It actually configures the compiler in using the environment that the tool chain sets up. So the compiler that's running now is actually a cross compiler that is building code for the ARM platform. And not just Erlang, but any C code or any C modules you have will get cross compiled. Then there's a release manager that happens, and I'll go through a little slide on this in a second, and you end up with a piece of firmware. And so, let's do this. So if I look at my images, you'll see I have this little file called blinkyrpi2.fw. And now I can just burn that. And I have a little USB memory stick writer here. I don't know if you guys can see this. And I have a little microSD card. I'm just going to put the microSD card in it. And again, thanks to Frank, it actually figures out that the SD card is there, and which one to use. This eliminates the biggest source of trouble, which is mistakenly burning over your root partition of your hard drive. So it's going to prompt me for some password to make sure I really do want to do this. And then indeed it's done. So if you saw the demo back in October, that was like a five minute process, the burning, and now it's about a three to five second process. And the reason for the dramatic difference is we no longer produce an entire image, we produce a zip file, and the burn tool takes the zip file and actually formats the SD card in the appropriate form as it's burning. So it's an incredibly efficient way to do it. And so I'll go ahead and pop this in here. And see if I can do the obligatory. Linky demo, unfortunately my power cord is not working. There we go, I don't have to figure out where to plug it in. There we go, so let's see. Okay, so that started booting, and now it's running. There you go. I'm always amazed people clap for blinking lights. It's really cool. All right, let me go back to my presentation. So how do I get that over here? I guess I have to close that window. How do I get that back here? Let's try this. There we go. Okay, so next, how bake works? So this is a diagram I actually got last night. Justin Schneck explained this to somebody on a whiteboard, and then the guy that he explained it to took a snapshot of it and posted it. And I thought it was a great explanation, so I thought I'd show it all to you. But I have a simplified version. Okay, so basically your app and a target specific tool chain gets used to compile your app into something called a release. And to do that, it uses the standard mix tool and something called EXRM. And the release then is combined with a pre-built Linux. And in a process we call assembly. Apologies to those of you who used to write assembly language like me. But we call that process assembly as an assembling the firmware. And the result is a firmware file that we then can burn. And bake's job is to manage all of those dependencies. Now, I'm going to skip this part because I'm a little low on time, but it would be trivial for me to say bakefirmware-target equals BBB for Beaglebone Black. And it would grab the other recipe and I'd end up with a second firmware file that I could burn and launch on this device, which is a Beaglebone Black. It happens to be orange, that's just the case. So anyway, that's a status of nerves at the moment. And the things that we've been working on. I'm actually really excited to be at this point. We've been trying to get here for a long time to have nerves ready to actually be usable by somebody that doesn't want to run Linux virtual machines. And it finally is at that point. I haven't run a Linux virtual machine for months. And I'm very happy not to have to do that on my laptop. Nothing against Linux. Okay, so last I want to talk a little bit about where nerves is going in the future. And what we're working on. And some of this is near-term. Some of it is longer-term. I'll try to differentiate. Now that we've got bake done, the next thing we want to do is sort of get rid of it. And what we're really talking about doing, and this is partly through conversations that Jose has had with Justin, is really integrating the whole notion of baking firmware into MIX so that you don't have to have a separate tool chain for making firmware. And we wanted to do this from the beginning, but it turns out it's really hard. And one of the reasons it's really hard is you have to run MIX from within the environment that you eventually are cross-compiling for, but it doesn't know what environment you're cross-compiling for yet. And so there's this kind of recursive problem that took a little bit of work to work around. And when we're done, we expect bake may still be there as a command line, but most people use MIX. And we think about that as MIX will manage all the dependencies of systems and tool chains really, really well, and allow you to, for instance, build all your projects or one project and manage the dependencies between the projects, which currently our system doesn't quite do. The other thing we get out of this is something we call build aggregation. And build aggregation is where, let's say you've got a Raspberry Pi. This is a great example. I have Raspberry Pi 2 here, but I also have something called a Pi Face 2. I don't know how many know about this. It's a little interface board that plugs into the Raspberry Pi 2. But I need some extra configuration to the system in order to use my Pi Face 2. It goes well above and beyond what the standard Raspberry Pi has. I need some extra drivers, let's say, to use that. All I have to do is create an extra set of files specifically to support this device. And I can take my standard Raspberry Pi 2 recipe and aggregate on some deltas to it and build a whole new system that then I can reuse to build firmware for this, for the combined thing. And we expect that to kind of arrive with the MIX-based baking. Related to that is community target support. So this I alluded to earlier. We'd like to have the ability for you guys to help us support more platforms. And right at the moment we just don't have enough resources to support more than the Raspberry Pi and the Beaglebone and the Galileo. So this will allow us to do that by making these separate platforms their own projects and using build aggregation and the MIX tools we can make all that happen. Let's see. So platform itself as opposed to the tool chain, we're adding support for Pi 3 sometime soon. Part of doing that really comes down to supporting Bluetooth and Wi-Fi. It's a much requested feature. We're working on it. And I think some of you here might be helping us. I'm not sure. This bullet universal IO device tree probably means nothing to anyone who hasn't used a Beaglebone Black, but it's a big deal to those that have. And then modular configuration support I just talked about. One other thing that we're experimenting with a bit. I'm just going to quickly whiz through this. We're looking at UI and how to build UI for these kind of devices. And like Jean François, we're looking at using Elm and trying to find a way to get Elm actually running on a device using Chromium and Ozone and GLES. And if anybody here is at all experienced with getting GLES running on embedded platforms, I really want to talk to you after the talk because it's not been easy for us, especially for me. So I say as a way to build HMIs, I don't know if any of you guys know what the term HMI stands for, but in the embedded control space it commonly means human-machine interface. And so this is kind of what we're aiming to do, is find a way to use some kind of JavaScript-based UI library, preferably Elm, as a way to, I realize Elm isn't a library, so don't flame me on that, to provide a client toward some kind of server that runs on the device. And that client we'd like to be able to run either on the embedded device itself to build the embedded devices that have UIs, or as a desktop platform or something that's built into an iOS app through Cordova, for instance. That's the general philosophy we're investigating for how to build UI onto actual devices. Let's see, other things we're working on. When service discovery, or device and service discovery are complicated words, and every time I use them they're misunderstood by me or the people that are listening to me. So by device discovery I mean you plug this thing into a network, like plug it into a wall socket here, you're screwed, you have no idea how to talk to it. Device discovery are the protocols that let you discover where it is, what IP address it's on, how to communicate with it. And we already are doing land device discovery, sort of. We're doing some land device discovery, so we allow you to, through multicast SSDP packets, if you're familiar with that, find the device. And we're going to support MD&S in the near future. But there's another kind of device discovery, which is WAN device discovery. I plug this in here, how do I get to it from my house? Because it's no longer on a local network. Well there has to be some infrastructure and servers to make that all happen, and we're looking at different ways to solve that. Related to that is firewall traversal. You have to be able to get through firewalls and find ways to tunnel through firewalls. Because I guarantee, I already know, our wireless network, or our network here is not publicly routed. And there's some interesting NATs going on there. And, you know, so that problem is tricky. And we're working on that. Service discovery is different than media device discovery. Service discovery is once you find a device, how do you figure out what it does, and how do you represent the things it's capable of doing? So we're working on that. I have become a better partner with Phoenix on here. I'm not going to elaborate on that other than, right now we don't actually, we use Cowboy for historical reasons, and we really need to figure out how to like, take our own protocols for communicating with devices and Phoenix's way of communicating and figure out how to make sense of it all and turn it into something that's more collaborative. And then some of these remaining bullets on here are really about... This is kind of a really, really, really big point. When you start building devices with this stuff, especially devices that are commercial devices and in the field, security becomes huge. It becomes monumental. How do you know when you make a request of advice to do something, who that request came from? How do you authenticate that that person had the credentials to do what they're asking the device to do? And so there are layers of security, both at the application layer and at the transport layer, that need to be included. And there aren't, even though you could say, oh well you just use HTTPS or TLS, turns out those aren't really great answers for a lot of devices. For instance, some devices operate where there is no access to public key infrastructure. And the devices our company builds, for instance, on vessels, they can't make internet connections to find out whether the certificate coming with the request is valid. So there are all kinds of tricky issues around managing internet of things security and layers of security protocols that need to be implemented to make that stuff work, and we're looking at that a little bit, or at least I'm looking at that piece. And I already talked about human-machine interfaces, so I won't go there. So I actually think that's it. That's all I was going to talk. I have some other things I could go into, but I can demo those later for people that are interested. Main resources, nerfsproject.org and bakeware.io. And then we are very active on the Slack channel, the Nerve Slack channel on Elixir Slack. And I think that's probably the best way to get in touch with us. And that's it.