 My name is Jan. I'm here with Mitri and we're going to talk about how Linux containers can help you to manage development environments for IoT and embedded systems. And we are going to do it by showing an open source framework for managing build environments and containers called Rebuild. And before we are going into the how, we need to ask ourselves why. And why if you're dealing with embedded or IoT systems and we develop for one of the devices, you know that in order to compile a code, you need usually to deploy some tool chain, SDKs, and those have different dependencies, different compilers. You might need different tool chains for different devices. You might need to update some packages. And if you have a code base that works on the line of the devices, on several devices, or you have SDK that is changing and you want to update some packaging, always this management of packages, of compilers, of your actual development environments involves some kind of a pain. And there are many tools that are trying to help you in this. So the question, and of course always there is this thing that it works on my machine. So sometimes you can compile it in your environment, but it doesn't compile on the build server. We have some issues in the CI. And then you need to answer yourself, okay, so what exactly happened here? So what we would like to have, and there's several on different levels. So if we're talking about individual contributor to a project or individual developer in the organization, we would like to be able to run environments for multiple platforms on our same development machines. And we want to have a mutable build environment. So when we do, when we run our builds or we do some actions with our build environments, it doesn't change if we don't want it to change. And we want to have the same environment as we use on our development machine, also in different other places in our organization, so build server or CI server. And if we are talking about the team, we would like to share our build environments between the team members. And we want to have the unified experience between the team members that doesn't matter what kind of distros they are using or even what kind of operating systems they are using for their development. And we would like to track the versioning of the environments or how they were created. And if we are talking about the organization itself, then they're different than we need to look to the future. So what will happen in several years when the people that are working now on the product or created the environment today, they are no longer with us or no longer with our project. So what we want to do in this case. And we also have the certification issues. So if we are talking about medical devices or automotive devices, we need to be able to audit our software that we build. And we need to go and show that we used exactly specific packages that were specific libraries that were certified and they were used during our build. So how we would like to solve it. We created an open source framework to manage build environments that we called rebuild. And it leveraged Linux containers and enables seamless integration of the containers with your existing build environments and integrating your existing build environments into containers itself. It will stop this, but it works on my machine situation. And it will enable the easily share build environments between the different team members. So I want here, Dmitry, to help me with the demo. So what we are going to show now is we have some sample source code in our local directory. And what we are going to do is we are going to show you how we can use rebuild. So first of all, let's see that rebuild is installed. The next step will be to find a specific environment that we will want to use to compile our code. So we already have some, we have something that is called environment registry that is also deployed on my PC in this case. And now we will issue rebuild search command to check what kind of environments we already have in our shared repository. So we have here the build environment for Raspberry Pi and we are going to deploy it. So Dmitry will run our build deploy command that will deploy this environment. And this is something that we need to do only once. So once the environment is deployed to local machine, we can use it many times until we change this environment and then we will have another version of the environment. But until we change it, we need to deploy it only once. And once it is deployed, you can instantly use it. So now Dmitry can run our build run with the environment name. Oh, sorry. And before that, you can see that I have different environments locally and this is the one that we just deployed from the repository. And now we can issue rebuild run command with the environment name and just run make to compile our source code. And as you can see that we are using specific tool chain to compile our code. And if you look at our local files, we can see the build artifact here. We can use our environment also in interactive mode. So in this case, we don't tell rebuild what command we want to use. We just run rebuild run with the environment name. And now we can run different commands inside of the environment. So we can see that this environment, for example, is based on Ubuntu. And we can run here also command. So let's run make clean and make again. And you will see that we run exactly the same the same command with the same tool chain again. Okay, so thank you. So now let's see how it works, how actually your build works. So we are leveraging Linux containers. And one of the magics that we are doing is that we are mapping the local local file system into the container in order to preserve all the permissions and ownership when we work with our source code. So the source code is located locally on our file system while we work with different environments. And the good thing is that it can work on almost any modern OS. So it's not only for Linux, but we can run it on Mac OS on Windows as well, because they all support now Linux containers. You can check the project here in GitHub. So let's look at the architecture. So first thing, as you already saw, we use the rebuild CLI to interact with the rebuild. And this is a gateway for the developers or for your scripts on CI or build server to use rebuild. We have also something that we called environment registry. And we can work with several registries now. We can work with Docker Hub. If you want your environment images to be public, we can work with Docker private registry. And we have our own rebuild native registry. And we are leveraging Docker engine to run and manage the container images. And the usage model is that we have this environment registry that is centralized to either our project or our organization. And we have developers that can work with that build servers, CI servers, or support and field engineers. And of course, we have, and later we'll show it as well, we have a local workflow as well. So you don't have to push your environments to registry. But in most cases, of course, you would like to share them and to have the same environments between different members of your project. So let's talk about rebuild CLI. And we have, when we build CLI, we had several concepts. So first of all, it should be seamless for the developer execution. As you saw, it's easy to use it. All you need, you use your existing scripts that you use before that to build your software and just prefix it with rebuild run. And there's no need to know anything about Docker, Docker files or other container technologies because we don't want additional knowledge to be, sometimes your build system is already complicated enough. We don't want to put another complication on that and start dealing with how to manage Docker files. Another thing is that we use a convention for naming. So there's a name and tag. And the tag should be used for showing a different version of your environment. So this is specifically used for, if you want to update your environment, update packages in your environment. So during the life cycle of the build environment and so the development environment, you might update it and this way you can keep track of the history of the updates. And environment registry, as I showed in the architecture slide, stores environment registries and enables you the sharing of the environments between the team members. So what kind of the environments we can support? We can work now with the Docker Hub. So this is a public, in this case, your images will be public. And this is great if you work on some project and you want the development environment for your project to be publicly shared. So this is a good option for you. The other option is Docker private registry. This is the case if you want to deploy it locally in your organization and rebuild native registry. So this is if you don't want to deal too much with the configuration of the registries. As I said, we support Linux, macOS and Windows. Let's talk about installation of rebuild. So rebuild is actually Ruby Jam. And the dependencies is Docker and Ruby 2.0 or higher. And the way you install it, you just run after you install Ruby, you just run Jam install rebuild and it deploys everything that is needed to use rebuild in your environment. And after you install rebuild, so the quick starters, you can already run rebuild help to understand what you should do with rebuild. We already configured rebuild in this case to work with Docker Hub and we put some environments to Docker Hub already for the popular platforms and we are adding more. So the moment you deploy rebuild, you already can deploy environments and you already can compile your code. There's a configuration file for rebuild. It's located in your home directory under dot rebuild rebuild dot com. And in this file, you can configure different options of what type of registry you want to use for your environments. So this is the way you configure the Docker Hub. You can configure rebuild environment or you can configure Docker private registry. And let's talk about workflows, how you work with your build environments. So the basic usage, as we saw in the demo, is you do the search, you find the environment that you want to use, you deploy it and then you run. And of course, this part needs to be done only once for each version of your environment that you want to use. And we already saw this in the demo. So actually, we are searching and we can deploy the environment and then immediately we can use it. And again, we already showed in the demo the interactive usage of build environment. So you don't need to execute one command after each other. You can enter your build environment and you can execute your commands inside of the environment itself. And of course, there are several things that you need to remember that the environment itself is not changing during the rbuild run command. So when you execute this command, you cannot change the environment itself. And the files that are created due to your build execution are preserved with correct permission and ownership. Now, in case if you want to modify your environment, you have a little bit different process. When you run rebuild modify with your environment name, in this case, you can add packages or update packages into your environment. You can change environment variables if you need. And then you can commit your environment locally. And then you can publish it into the repository. If you want to work on the locally, so then you just run rbuild modify and commit. So this is an example of how you can do it. So you run rbuild modify with the environment name and then you can run different commands to update the environment. And of course, do the same in the interactive mode. Get status of the environment so you can see that it was actually modified and you can commit the changes. If you want to revert the changes that you did to environment, you can always use rbuild checkout and revert the changes that you did to your environment. And another thing is the environment creation. So we showed you how you can use ready-made environment, how you can update environment, but now let's say you want to create environments from scratch. So the workflow is that you run rbuild create to create the initial version of the environment. Then you run rbuild modify, commit, and publish. So that's actually already modified workflow that you saw before. And there are two ways that you can create your environment. One is you can use the base image that is located in your environment repository or either on the Docker Hub so you can use the public container image that is published, sorry, official container image that is published there for one of the distros. And another way is to use the file system and to create the environment from scratch. And then after you commit it, you can publish it into the repository. So let's put everything together and see how we can create this environment that you used in the first demo to compile our demo for Raspberry Pi, how we can create it from scratch. So Dmitry will help me here as well. We didn't know what will be the state of the internet connection here so we cheated a little bit. Actually, I have already the Raspberry Pi toolchain, I already got it from GitHub, but actually it's one command, okay, we just need to clone, you need to clone the RPI tools, so they are already here. And now let's see what. And we have already initial repository. Once again, I didn't want to create it from Ubuntu image from scratch to take something like three minutes, but I didn't know what will be the state of the internet connection here. So just in case, anyway, we just run our ability create minus base Ubuntu 16.04 and created this RPI Raspberry initial sorry initial repository, initial environment. And we are going to modify it in order to use it with Raspberry Pi. So actually what we need to do here is we need to copy our toolchain into the environment and we need to set environment variables for the make to call correct compiler. So that's what Dmitry is going to do now. Okay, so now we can exit the environment and we can see that it was modified and committed. And after we save the, after we commit the environment, we can immediately use it again. So you can see it here in the list of our local environments. Okay, so here it is. Here's the compilation result with the environment we just created during this demo. So the thing is that it took us, I don't know, four minutes now, but we know that in some organization to add the additional toolchain to their build system might take between several hours to several days. So in addition, we can of course work with our local environment. So we can, as we saw, we can list them, we can delete our environments and we can save and load, we can save environments into the Docker image that can be uploaded to the repositories that we don't support currently or and can be loaded from Docker file as well. That's right, not the Docker image. Just a demonstration of how to use those commands as well. And another thing that we can do is that we can modify environment variables for each development environment. So for example, we can set different compilers inside of the environment and then save the different version of which environment. So we can create, for example, basic environment that we'll use Clang and then we can use another version of the same environment that we'll use GCC, for example. And in case if rebuild fails for some reason, we have debugging mechanisms that you can use, you can enable tracing and save some logs that will help to understand what went wrong. So once again, it's here in GitHub. And just to summarize, what we wanted to achieve is the seamless usage of the development environments, to have the isolated environments for our usage. And we wanted to be able to easily share those environments between team members. What we want to do in the future is we want to add the role management for rebuild native registry. So you will enable different team members the ability to create the environments and only others can use them. We want to support multiple registries at the same time. We want to add ID plugins, so you would use rebuild straight from your favorite IDs. We want to use, to add usb redirection for non-Linux hosts, so you can also deploy your build artifacts on the devices from rebuild when you use it, not on Linux, but on other OSes as well. And additional tracking of environment usage questions. We just started, so we definitely are going there. So we actually, just now, one of our guys is creating integration reactor. He's working on that. And we are adding additional environments and additional platforms that there will be already ready-made environments. So when you install rebuild and you go to our Docker Hub, you can create, you just instantly can deploy the environment for the specific platform. Of course, you can do it by yourself, but we want to give the ability even not to do that as well, so just use ready-made environments. Yeah, so you just package the toolchain inside of the rebuild environment. So actually, we do have some toolchains inside. So when we saw it, when we did, there are some more here. So we have for an NRF 52 toolchain, and we have Raspberry Pi toolchain, we have Bigelboard toolchain, and we're adding more toolchains inside, but you can add any toolchain. So it's just, it's up to you. No, it's, sometimes you need different distros as we know that our proprietary toolchains that ask you for specific Ubuntu Fedora versions, for example, and quite all that actually. So you can pack, you can pack specific version of the operating system there. So you can see here, by the way, for some other project, I did, I used the rebuild environments for old Fedora here. So they are based on Fedora 20, Fedora 23, with different tools installed there. So I could test some things on the quite old Fedora distributions. Okay, so thank you very much. And calls to actions, you can install rebuild, just run gem install rebuild, send us emails. If you have some questions, go to GitHub, see the wiki, see the, and clone the code. We have here some rebuilt cheat sheet for the commands that you can use. You can go, there's a link from our build.io as well, but you can go directly. Thank you very much.