 All righty, welcome back to operating system. So today we finally get to come full circle and learn about virtual machines. What we started with, we can actually kind of explain them now. So remember what virtualization is? It's just fooling one thing into thinking it has all the resources. So we saw that especially with memory. Everyone's favorite topic, virtual memory. So every process thought it had full control over memory. Well, you can extend that to the entire machine. So that's exactly what a virtual machine is. So each, a virtual machine lets you virtualize the machine so you can install multiple operating systems and each thinks it has control over the entire machine when really it doesn't. So the goal, run multiple operating systems, single machine. Each operating system believes they're the only one running. They would manage their own virtual memory. They would do everything that we have learned in this course but we have to fool them into thinking they actually have control of the machine when they don't. So there's some terminology once you talk about virtual machines. So there is something called the host. The host is the thing that has direct control over the hardware and each virtual machine actually doesn't have physical control over the software. Host is like the operating system that's running first essentially. So sometimes you call these hypervisors or virtual machine managers. We also use those terms interchangeably and they control creating virtual machines, managing them and isolating them. So whatever physical hardware on your machine while it gets to control whether some virtual machines get to see it or not primarily for you, you can see, let it control how many CPUs it gets. If it gets a network card, if it can access your network card directly, how much memory it gets and you can do fun things with video cards. So there are two types of hypervisors. So the thing that runs your virtual machine. So type one is called a bare metal hypervisor and it runs directly on the host hardware and you need special hardware support for that but every one nowadays has that special support. The other type is called type two and they are very slow. So type two hypervisor runs the entire operating system in user mode. So it just runs like any other application except that user mode application is running a kernel which doesn't quite make sense because a kernel would use kernel mode and have access to different instructions. Turns out you basically have to, there's ways to detect that that we'll see later and you essentially just emulate whatever whatever the kernel mode instructions would actually do. And the other term is called a guest. So a guest is the virtual machine running. It only sees a virtual copy of the host. Doesn't have access directly to the host. So your typical machine that we saw is over on the left in A. So there's hardware. The kernel is above that. The kernel can access the hardware through using kernel mode instructions or memory that's mapped specifically by the kernel and then processes are on top of that that are running in user mode that have to go through the what interface, the system call interface, right? That's the only real way to essentially ask your kernel to do things, you have to make a system call. So on this diagram, they're called programming interface. So over on the left is what we currently have and if we introduce virtual machines it actually looks like what's on the right. So the hardware is still sitting there and above that is the virtual machine manager or the hypervisor and that directly controls the hardware and then it makes a virtual machine on top of it that only lets you access some of the host. Yep, yes, yeah. So this essentially, well what we called it as a hypervisor. So hypervisor is actually another CPU mode. So it actually controls something. So there's a new privilege mode that I think we showed in the beginning that we didn't go into that was even below a supervisor mode or kernel mode. So that's hypervisor mode. So it can do things that you can. And it's a bit fuzzy what this actually is. So it can be a separate operating system that doesn't really do much except manage virtual machines. Most operating systems now that can support virtual machines this will be Windows when you boot up and it will become a hypervisor as well as doing Windows things. So the hypervisor gets to create virtual machines which let you access whatever hardware it wants you to or make up new hardware that the virtual machine has access to and then each virtual machine would have a kernel running on it and that kernel while it's speaking directly to the virtual machine and not actually the hardware. It has to go through the middle manager of the hypervisor but apart from that, the kernel and above looks exactly the same. So that kernel would still operate in kernel mode whether or not it's real kernel mode depends on the implementation and then there would be the system call interface and it would run normal processes. So yep, yeah, so Windows would be doing this and then part of Windows would be running its own kernel so you can think of Windows as having this plus kernel. So any of your normal applications that aren't through virtual machine would be talking directly to this and then talking to the hardware and your virtual machine would just be on top of that, another separate part of Windows. Yep, yep, same thing for macOS or Linux. They call it like macOS will, I think it's called hypervisor kit or virtualization kit or something like that but that's basically the hypervisor in macOS. The Linux kernel has something called KBM so that's the kernel virtualization management something like that, basically a hypervisor. So most kernels nowadays will also be kernel and a hypervisor all in one depending on if you're using virtual machines on top of it or if you're just using normal programs. So your normal programs would just pass through the old kernel. Yep, so you can run Windows on a MacBook but that would involve different things because yeah, this has, which is like a separate problem kind of because this is an ARM processor but Windows, there's an ARM version of Windows but it's terrible but sometimes you might be using the x86 version of Windows. So newer Macs can emulate x86 instructions so the virtual machine just looks like a normal x86 machine and it emulates all those instructions but the hardware, CPU hardware is the same and it could emulate hardware that Windows understands if it wanted to, may or may not be slow. All right, any other questions with this? So yeah, here's the slide for that. So virtual machines are not emulation, it's a different problem. So emulation is to translate one instruction set architecture to another or the low level assembly. So x86 to ARM or risk five. So on macOS specifically for the newer M series of processors, there's emulation it's called Rosetta 2 and that will emulate x86 instructions using ARM. So generally the guest operating system will execute this instructions directly on the same CPU using the same ISA but if it's Mac and you're installing an x86 Windows, that won't be the case but on general if you want it to be really, if you want it to be faster, just use the same instruction set architecture so everyone's Windows machine was x86, you probably used x86. It's okay for some uses to just do pure emulation. So like you can write not even a Super Nintendo a Nintendo entertainment system emulator. It's only eight bit CPU, it's super, super simple. And I wrote one when I was bored one summer. So you can actually emulate that really easy because it was like an eight bit processor that ran at like one megahertz or something ridiculous like that. So really easy to emulate. So virtual machine could use emulation if it wants but performance generally suffers greatly because it has to emulate instructions but for the Mac they have some special hardware that makes emulation fast so it's actually not that bad. All right, oh, other fun thing with, oh, yep. So emulation is all I don't have support for some instruction. I like, I have an x86 add instruction. Right, if I tried to execute that on an ARM processor it'd be like, I don't know what that means. So we'd have to look at that instruction and translate it to something that this processor would understand. So it's just, yeah, basically translation if another way to think of emulation. So other things you can do with virtual machines. Well, for you, you let it have network access and all that stuff so it could access your network card but you could isolate a virtual machine so it doesn't have access to the network card and you can experiment with different operating systems and see. For instance, the official operating system of North Korea it's called Red Star OS. You can go download it and install it on a virtual machine. I would not recommend installing it on your actual computer. So you can install it on a virtual machine. Also recommend that you don't give that virtual machine internet access. Otherwise, North Korea will probably do something but you can go ahead, download North Korean's operating system and take it for a spin. I haven't done that yet but you're free to, yep. No, so at least currently, so this is a question about like, hey, most video game consoles if I have to port to PC is that emulation because they run different instructions. Most video game consoles are computers now. PS5 runs an x86 chip, it runs AMD. I think Xbox also runs AMD. They're just computers now. They don't look any different. The only difference between consoles and computer is there is a set hardware target that doesn't change for seven years or whenever a next generation comes out. That's the only difference. Why is it so hard to port games? So the instruction set architecture is not the hard part. Everyone will have, generally it's the graphics API is different, so PlayStation has their own, Nintendo has their own, Xbox has their own and if they use a specific one for that console then that's what they have to port over which is more time consuming. But CPU instructions, they all run the same thing. The core logic wouldn't matter, but core logic doesn't matter if you can't see anything. All right, so other things, virtual machines let you do that you can't do with normal machines is well something like pause and play. So like your kernel can just stop your process from running, context, switch it out and run another process, you can do the same thing with your virtual machine. So you just pause the virtual machine, context, switch it out, maybe I go back to running my windows things, if I'm windows, maybe I've run a different virtual machine, it's up to you. So the hypervisor gets the context switch, now not between processes, it context switches between virtual machines. So it could also save that to disk and restore it later which some of you have encountered for at least using Windows when you have a save state, it just saved this whole state of the virtual machine to disk, pretty much the equivalent of like the process control block but there'd be like a virtual machine control block equivalent. So you could also move it around exactly like a process. So ideally this is how like the servers that you SSH into would work because while a process can move between CPU cores, no problem, you just save it, context switch it to another thing. So with virtual machines, you can actually context switch between actual machines if you really want to. So it could pause your virtual machine, save its current state, send it over the network to a different physical machine and start running it on that machine and you would be none the wiser. So other things it could do is provide some protection through isolation. So the guest, it's essentially the same thing as processes. Processes are isolated from each other by default and virtual machines or guests are also isolated from each other and the host. So the hypervisor can set limits on like CPU time as well, memory, network bandwidth and a compromised guest. So if your operating system gets hacked or I mean if it's pre-hacked from the North Korean one, then it only has access to its own virtualized hardware, can't cause any actual real damage. And if you were running this, it's a bit easier to manage too. So if you find your virtual machine, your virtual machine got hacked, well, if you saved its state every so often, you could just roll it back to when you knew it worked or you just remove it, start a new one, reinstall it from scratch without having to reinstall the whole computer and having physical access to it and putting a USB drive and all that fun stuff. So also help with consolidation. So data centers or clouds will only use virtual machines. So in data centers, there's generally lots of servers running. Often they don't make use of all the resources so they just give you a virtual machine and it's not guaranteed what machine that's actually running on. So you could imagine, well, if they just assigned you a virtual machine or a physical machine, whatever you got a new Amazon instance or something like that, you could imagine like with multi processes with the scheduler, well, one could get overloaded if I had multiple machines and that's not good. We already solved that problem when we had CPU scheduling. So the solution was to move the processes to different cores. In this case, you can do the same thing with virtual machines. You can just move them to a different physical machine. So if Amazon sees that one physical machine is being overloaded and one is not, it'll just start moving some virtual machines over to a different machine and it would do it transparently, so you can't see it. So servers with all different purposes can be sharing that hardware. You could have multiple virtual machines all in the same server as long as there's enough resources or they're not consuming much at the time, it's fine. So this is also very nice. So instead of having just like lightly used physical systems, you can just make them virtual machines and run as many on a single machine as possible. And this is generally how people scale like web applications and stuff. So you could have a database, you could just set up initially, so your database is in a virtual machine, your web server is in a virtual machine and your front end's on a virtual machine and while you don't have that much traffic, well, you put them all on the same physical computer and then while once you have outgrown a single computer, you don't have to re-architect anything. You just buy another machine and throw a virtual machine over on that one, you don't have to redo it from scratch. So it makes it nice and easy to just move things around. So the key abstraction with virtual machines is a whole virtual CPU which kind of sounds like a process, but instead of just keeping track of the user mode registers, a virtual CPU keeps track of literally everything. So all of the kernel state of the CPU and all of that fun stuff. So for processes, it was just a process control block, but yeah, like I said, doesn't emulate or keep track of anything that's specific to kernel mode because why would you bother because while processes only run in user mode anyways. So this vCPU status structure stores the entire state of the CPU. This is what the hypervisor saves when the guest isn't actually running. It's what its context switching in and out. So the virtual machine resumes like the process control block, it just restores it, keeps on running. So the guest, like I said before, it still uses user and kernel modes. There is no changes to the guest whatsoever. The Linux kernel, if it's the Linux kernel in your virtual machine like it is for all of you, well it's still running in kernel mode. So if we think way back when to like the first few lectures on x86, if we remember the silly numbers, user mode is technically in ring zero and kernel mode is in something called ring, or sorry, user mode is in ring three and kernel mode is in ring zero and you could tell that when they first made x86, hypervisor mode did not exist. So hypervisor mode is like new-ish in the last, what, it got standardized within the last like 20 years or something. So the special CPU mode for x86 processors is called ring negative one because they ran out of numbers, zero, they had zero as the lowest they could go and guess what, they came up with a new one that's even lower. So your hypervisor is at ring negative one and it controls the guest. So that's for type one hypervisors that actually have hardware support. For type two hypervisors, well, the host has to create like a virtual user, or sorry, a virtual kernel mode because in actuality, a type two hypervisor is running completely in user mode. It's just running as a normal process. Yep, yep, yeah, hypervisor is more privileged than the kernel. So the hypervisor controls everything and on some of them, like on risk five, there's a user, there's a mode that's even below a hypervisor called machine load, but machine mode, but that's usually for special booting and stuff like that, but that's even more privileged than hypervisor mode. Alrighty, filled it, okay. So if we had a type two hypervisor, so we don't have this special hypervisor mode and we essentially have to emulate what happens in kernel mode, well, that's what one strategy is called. It's called trap and emulate. So the guest again is running completely in user mode. So if you just try, if you somehow knew what the instruction was to, I don't know, change your root page table or anything like that, if you just directly put that into your program and tried to execute that in user mode, well, you would get essentially a trap or a signal that said, hey, a legal instruction, you cannot do that and the default behavior would be just to kill your process. So if you were to implement a hypervisor, you can take advantage of getting a signal. So if you trigger a signal because you tried to set the root page table to something different, well, if you implement a hypervisor, you could catch that illegal instruction, see that you were trying that the kernel that's running was trying to change the root page table and you could emulate what should actually happen. So that's gonna be much, much slower than actually just doing the instruction, but you could do that. So you handle the error in the signal handler, simulate what's supposed to actually happen and then just let it continue running. So it will slow it down significantly, but it will work. And what does that look like? Well, in this case, well, everything's running in user mode. So if my guest was running in what it believes is kernel mode and executed a kernel mode only instruction, it would generate a trap and then it would go to your fake hypervisor, emulate what's supposed to happen, update this virtual CPU that keeps track of what the spec of that CPU architecture says is supposed to happen once you're in kernel mode and then it will return back and just keep executing instructions. So any questions about that one? Yep, so it doesn't have the ability to actually run them. It will let them try and run it and then it will generate a trap like a signal and say illegal instruction and then it just simulates what would happen in user mode. So like, so you can just like, for example, you know that it's supposed to change a register that has to do with the root page table or anything like that. So you would essentially have to emulate that. So you would have to keep track of, okay, I need to keep track of a virtual memory manager and all that stuff. So you just have to know, read the specs of the CPU, read what kernel mode's supposed to do on it and just emulate, keep track of everything. All right, so it doesn't always work. So on some CPUs, especially x86, that would work if there was a clear distinction between privileged instructions or like kernel mode instructions and user mode instructions. So for x86, well, virtual machines then exist in the 70s so they didn't think of this. So there is examples of instructions that are the exact same instructions all the way to the machine code that just change the behavior whether or not you're running in user mode or kernel mode. So for example, there's like a pop F instruction that loads some flags from a register and or sorry, loads of flags from some register to the stack. And well, what flags register it changes just depends on whether or not the CPU is currently in user mode or kernel mode. So if I just do the trap and emulate approach and I think I'm in kernel mode and I execute this instruction, I won't get a trap because it will actually do something in user mode. It will just do something I did not expect and debugging that, well, if you were to write your own virtual machine manager would be terrible because it doesn't generate a trap it just does the user mode thing instead of the kernel mode thing. So these are called special instructions and they need another approach because well, if I try and execute them they'll just work, they just don't behave how I expect. So they need something called binary translation. So if the guest virtual CPU is in user mode you just execute the instruction natively because the two modes agree, the virtual machine and what mode the CPU is physically in actually agree so you don't have to do anything. So if you have switched to kernel mode which you would keep track of in your hypervisor that runs in user mode then it needs to inspect every instruction before it actually executes and it needs to translate them like look at the instruction see if it's one that needs to be translated or handled specially and then intercept it and actually emulate it then. So it would have to read and look ahead at every CPU instruction and then do something if it's one of these special instructions. So the hypervisor could keep track of whether or not you're in user mode well because the instruction to switch between user and kernel mode would generate a trap so you could handle that and know that you are in kernel mode and then you actually need to go ahead and start inspecting every single instruction. So if you have to inspect every instruction before it actually executes while your performance is also going to suffer badly so type two hypervisors will always be slower than type one but for the most part they'll work as long as you're not doing something super intensive and they kind of work and this binary translation by the way is essentially how Valgrind works. So Valgrind will inspect all of your instructions before they execute and see if you're doing a malloc call or something like that and then intercept that and start keeping track of all your mallocs and freeze to see if you have any errors. So that's why if you actually benchmark your program with Valgrind it's like 10 times slower or 100 times slower because it's essentially doing the same thing as this. All right, so this is what it looks like visually so kind of looks like the same as trap and emulate but now if the guest is running some special instructions where I think I'm in kernel mode I have to start translating them I have to start inspecting them translating them if they're a special instruction and then if they are one of these special instructions and I update my virtual CPU that's keeping track of all the special kernel mode stuff that I'm simulating and then I return to user mode and just keep on executing. All right, any questions with that one? All right, so this is where, well, that's slow. So that's where we just added more hardware. So in 2005, which is slightly newer than you are so Intel introduced something called or VTX and AMD also had their own called AMD-V and if you try to enable virtualization on your machines, well, they had a bunch of names throughout their lifetime. So Intel when they were developing it called it codename Vanderpool and then they published the spec as VMX or virtual machine extensions. AMD of course had a different codename Pacifica and they published it as secure virtual machine SVM. So in your BIOS if you try and enable virtualization depending on if you have AMD or Intel and depending on who made your BIOS then it will be called one of those things that you have to enable but they all mean the same thing. Just adds a concept of ring negative one or hypervisor mode. So how Windows works like the host kernel whenever it boots up so like Windows or Mac if that is the first operating system that boots well it claims the hypervisor so it would check, hey, is there a hypervisor mode? Oh, okay, I will become a hypervisor now and then it claims it so it's the only one that has access to it. So it sets the isolation for the guests and what hardware we want to virtualize. So any questions about that? Some of you may or may not had to do that with your virtual machine but it's usually enabled by default. So if we have to schedule a virtual machine well if there's only one core in the physical machine the guest doesn't really know it the host could still present multiple virtual CPUs to the guest even though that there is only one just like you can have multiple threads with only one physical core. So same concept applied to that but now you probably want to do something like mapping virtual CPUs to actual CPU scores schedule them like a process so like a normal corner there'll be hypervisor threads that deal with all the context switching and all that fun stuff but everything we learned applies the same to virtual machines just instead of scheduling processes scheduling a virtual machine. So one approach is just CPU assignment so if there's more physical cores on the host than all the virtual machines just map them one to one because well like we discussed when we had multiple cores with scheduling swapping between them would be bad because well the caches would be invalidated and you could imagine that virtual machines use more information than just a process so context switching them is even more expensive. So with that if we have to share things things get more complicated so if I have more virtual like if I have more CPU cores across all my virtual machines than I physically have something called over committing and it generally gets more complicated and things will slow down because then you have to do context switching and you can imagine context switching again for virtual machines it's going to be much more expensive than for processes. So but same thing overall idea the trade offs are going to be slightly different but uses the same scheduling algorithms we talked about before. If you over commit on resources that has some additional problems so the guest offering system might also start running too unpredictably for soft real-time tasks because well if you had a soft real-time tasks on bare metal so like on your physical hardware well and you know that it always meets the deadline then whenever you move it to a virtual machine that might not be true anymore because while you are doing your soft real-time tasks you don't control the actual hardware anymore so you might get context switched out in the middle of it and when you get context switched back in you have missed your deadline and there's essentially nothing you could do about it. So in this case some things are much harder once you go into virtual machines especially once you care about like really really really tight performance numbers because well they need to be scheduled and they are more unpredictable than just running directly on the hardware. Also you might imagine virtual memory gets a little bit more complex so remember virtual memory each process thinks it has the entire address space which is still true but now the guest kernel also thinks it is managing the entire address space but guess what that's virtual memory too. So the kernel has virtual memory managing virtual memory for each processes each process so each process has like virtual virtual memory like it's doubly not true. So the hypervisor would be controlling would have virtual memory for the guest and then the guest would have virtual memory for each process. So this is even worse if you your virtual machines use more memory than the entire whenever physical memory you have and you have to virtualize it and it's a whole mess and it gets even worse if you over commit on memory and there's just too much. So in order for things to go fast because as you might imagine while virtual memory is slow because of the especially if you have a three level page table lookup then you have to look up three levels and then if you have another set of virtual memory then you have to look at three levels again. So one thing the hypervisor mode will let you do is have nested page tables. So it takes into account whatever the guest kernels page tables are and just does all that translation in one fell swoop and will make sure that the TLB actually knows that hey this is from the virtual machine so don't throw it out of the cache this is where it came from. So what the hypervisor maintains yeah like a nested page table so it would have its own page table and then the kernel running on it would also have a page table that's the nested page table. So if you wanted to if you have run out of memory so like you have to go to swap they can provide something called double paging and in that case if you have swapped while the hypervisor could have its own page replacement and its own swap space and then the kernel that's the guest kernel that's also running could also have swapped space and then it gets even more complicated like which one of you is swapping like is the hypervisor swapping is the guest kernel swapping and yeah generally with that the guest knows the memory access patterns better you should probably let that swap and not the hypervisor but again if you wanted to you can have both of them swap and it gets fairly complicated. So another fun thing you can do is we saw a copy on write before and that was a way to go ahead share the same page across different processes. Well the same thing can actually happen for different virtual machines so they can share pages if they're duplicates right if they're duplicate pages then and if they're only reading them then they can go ahead and share them why would I give two pages of physical memory to them when they can just share one. So this time though there's not like a concept of forking a virtual machine so what it has to do is the hypervisor would essentially calculate the hash of the contents of the page and then if the two hashes are the same it means the pages could or could not have the same content but they definitely are not completely different and if the two hashes are the same then it will go in and check them byte for byte to see if they are the same if they are the same then it can go ahead and share them and then of course if one of the guests tries to write to it the same copy on write thing that we did before would apply I have to make a separate copy of it and then they're independent and it's fine. Other fun things it could do is a hypervisor it can provide virtualized IO devices so if you have like a network card for example while it can multiplex all the virtual machines network card to the same physical network card and each one thinks it has access to the network card. So hypervisor could also emulate devices that don't exist could also map one the physical device to a virtual device in one BEM and that way one virtual machine has exclusive access to the device but the hypervisor is still ultimately in control of it so there's hardware solution for that so the hardware solution is generally something called IOMMU and that will actually just map a device directly to the virtual machine and bypass the hypervisor all together so it just exclusively goes to the guest the guest can only use that and it has control over the device and it looks like it's directly connected to it it's the actual hardware and this is what you do if you really care about performance especially with GPUs and things that are complicated so instead of trying to virtualize a GPU which doesn't work all that well you just give it exclusively to a virtual machine it can go ahead and install its drivers and all that fun stuff and then use the virtual machine or use the GPU as if nothing was there so this is a way that people on Linux can play games so they just have a Windows virtual machine give it a GPU and then it's running at essentially native speeds the only thing it's going through the virtual machine for is like memory and CPU which isn't that bad what you care about as a GPU and it's directly mapped to the virtual machine so runs at native speeds all right so the virtual machine how it boots from a virtualized disk and essentially you made one of those in lab six anyways so in lab six you made a whole file system that one big file that has a file system on it well if that had all the files and had like a kernel in it and had all the other applications you could actually boot off that if you wanted to so that disk image is like the contents of a physical disk and it could contain partitions each partition could have its own file system in your case in lab six well it's just the file system consumes the entire space so with real disk there's a bit more things going on but it's essentially the same thing so usually it's just one big file and some formats let you split it up into different sections but the guest kernel just sees a normal disk that it has full control over and that disk image is all you need for a virtual machine so it makes it easy to move so if you want to share your virtual machine you made for this course with a friend there's a disk image sitting on your hard drive somewhere in the virtual machines folder whatever that default one is called and it's just a big few gigabyte file and if you wanted to share it with your friend just give them that file so then they would have your entire virtual machine they can boot it up on their computer that's essentially a way it's like a very explicit way to context switch between different machines so you could share your virtual machine and they could start executing it on something else and that's all you need to move if you were using virtual box or some things people think they're more complicated like they'll be like an OVA file or something or a different file format but basically all the virtual machine images that you download are basically a disk image and then some settings for the virtual machine for whatever software you're running so if it's like virtual box it will have some defaults that says how much memory this virtual machine should have and CPU cores and all that and then the disk image which makes up like 99% of it so other reasons you might use a virtual machine is to just isolate an application like I said so remember all the way back and oops that's the wrong lecture number when we were talking about libraries and you had an ABI change and you broke something I guess I was also on the midterm too suddenly your application doesn't work if you were at a job and that happened well you have to fix it really quickly and generally you just don't want to be in this situation so if you wanted to you could just create a virtual machine and you just create a virtual machine for that application and you test it and it works and you just deploy that virtual machine and if you want to update it while you update the virtual machine and you test it beforehand you just don't update the software update little pieces of software at a time you keep it all together in one piece so you just freeze everything that virtual machine doesn't change you tell them to run it they run it that's all the virtual machine self-contained so as you might imagine if you did that for applications well then most of that disk image like your application might be like a few megabytes and then you also have to give it a kernel a kernel that's like a gigabyte or something so it seems a bit silly just to send a few gigabytes when your application's only a few megabytes so that's where something like Docker comes in so everyone's probably heard of Docker before yes so Docker same idea tries to get all the advantages of a virtual machine without actually shipping a kernel so it's sharing the current running kernel and Docker is built on Linux so if you are using Docker on Windows or macOS you're actually using it on a Linux virtual machine if you are running it on Linux while you are sharing the Linux kernel and you're not running it on a virtual machine it's using the current running kernel so the hypervisor can set things like limits on CPU time, memory, network bandwidth and things like that so the Linux kernel actually supports that directly if you want to configure it for just normal processes so Linux has something called control groups or C groups and they support all these hypervisor like features to give you nice isolations but for just normal user mode processes so they isolate processes in something called a namespace so if you fork while they're all in the same namespace so they all have the same limits applied to them and with the namespaces you can set what mount points or what files it has access to what IPC it has access to so on and so forth so containers are basically the same idea of having your application on a whole virtual machine except they don't ship a kernel with it so it uses the same kernel it uses a Linux kernel so you just ship your application with all of its dependencies in one file and that's it, minus a kernel and then Docker just glues it to the current running Linux kernel and it uses that to run on all right, any questions about that? Cool, all right virtual machines, virtualize a physical machine so virtual machines give you isolation the hypervisor actually controls all the allocations and controls the actual physical hardware type two hypervisors are slower because it has to do that trap and emulate and then binary translation if you're running on x86 type one hypervisor supported by hardware so there's a special hypervisor mode and you can use things like IOMMU to essentially give a virtual machine direct access to some hardware for performance reasons hypervisors may also over commit on resources so they might need to physically move the virtual machine to a different physical machine but that's possible with virtual machines containers, all they are is they aim to have the exact same benefits as the virtual machine without the overhead of supplying the kernel with your application so yep, what is a full VM better than a container so if you have some very specific kernel things you want so if it's like usually you don't unless you know it needs to run on I don't know, generally people if it's Linux applications you just use containers nowadays if you want to use a virtual machine basically use a virtual machine on top of your operating system because it's easier to manage basically you just do that because it's easier to manage but for most applications you essentially just use containers unless you have like a Windows server application or a Mac one which don't exist in which case they can't use containers because it's Linux only all right, any other questions? All right, cool so just remember, phone for you we're all in this together