In the vast majority of cases, running a Linux-based operating system involves a pretty powerful processor with a lot of memory on hand, and perhaps most importantly, a memory management unit, or MMU. This is a piece of hardware which manages virtual memory, seamlessly giving each process its own memory sandbox in which it shouldn’t be able to rain on its neighbours’ parade. If there’s no MMU all is not lost though, and [Uros Popovic] gives us a complete guide to building the MMU-less μClinux on a RISC-V microcontroller.
The result is something of a Linux-from-scratch for this platform and kernel flavour, but it’s so much more than that aside from its step-by-step explanation. It’s probable that most of us have heard something of μClinux but have little direct knowledge of it, and he leads us through its workings as well as its limitations. As examples, standard ELF binaries aren’t suitable for these systems, and programmers need to use memory-safe techniques.
Whether or not any of you will run with this guide and build a tiny MMU-less Linux system, anything which expands our knowledge on the subject has to be a good thing. it’s not the first time we’ve seen a RISC-V microcontroller turned to this task, with a nifty trick to get round the limitations of a particular architecture.
“789 KB Linux Without MMU on RISC-V”
If you remove the TCP/IP stack and craft your packets in userspace, you can cut that amount in 2.
Good work. Definitely more complicated than programming in DOS :)
Sounds potentially valuable for safety/high security apps for reason that
NSA in ~1983 mandated that only their app software was to be in memory.
At Sandia labs some of us kept app module sizes no greater than one page of code
to be in compliance with Boeing hardware engineers’ software standards.
All modules included a smudge.
If the app-called system module, then smudge bit was removed.
Then all modules which had a smudge bit were removed from memory.
Our orders were to first write random numbers into deleted modules.
Several years later a member of Sandia’s chip manufacturing division told me
that if zeros were only written then is was possible to read the previous values.
Running without an MMU is never a good idea for safety or for security. Get a real SoC instead.
Running multiple programs simultaneously is never a good idea for safety or security. Get rid of the MMU.
It doesn’t protect against bad pointers.
What be a “smudge”?
How much value is there in projects like this?
One of my dreams is to design and build (user) programmable test equipment. somewhere between little (for example temperature, voltage, current) logging devices to desktop DMM’s. Those devices will have build in functionality, but with the addition of user loadable scripts. For very small / cheap devices something like micropython could be used, but full blown Linux computers are so cheap that it’s hard to justify putting anything in between. I’m guessing that most people will glady pay EUR20 extra for the hardware if they can hardware for that price that “just works” in a standard way, instead of fiddling with each and every library to make it work on uCLinux. As far as I know uCLinux has been mostly dead for some 8 or so years for this same reason. Hardware is either to limited to make good use of it, or if you need more capable hardware, then the jump to a more standard Linux capable SBC is likely a more logical choice.
I may be wrong, but I guess this project belongs in the shits and giggles category and “just because I can”.
If you want to run user scripts, look at lua or micropython – you don’t necessarily need a full linux environment, although it’s certainly convenient.
I’d consider something like this for single-purpose applications. For example, a Pi-hole, a temperature-control system for sous-vide, etc.
SBCs usually run a general purpose OS. For anything needing precise timing you want a real time operating system or no form of operating system which is even better.
You could combine an MCU or FPGA and SBC, use the MCU or FPGA for data acquisition since the timing will be much better and use the SBC for data processing and visualisation if you can’t do that on the MCU or FPGA too.
Excellent. This combined with an rp2040, and were ready for some fun.
Can you run linux a chip with no MMU? Sure.
Should you? Absolutely not.
I built a uclinux distro with ucdist for isl3893, with softmmu. I can confirm chips without an MMU are not worth it if you have the choice.
Since it doesn’t protect against bad pointers it’s neither safe nor secure. The only way to protect against bad pointers without an MMU I can think of are either using a language that has pointer checks(doesn’t work for maliciously edited binaries) or to build a virtual machine with pointer checks that runs byte code.
If you’re running software you wrote there’s no issue.
Writing the complete software yourself only rules out maliciously written software. You can still have security vulnerabilities, unsafe failures and hard to debug failures that would have otherwise been caught by an MMU.
Yes, that’s a good point. Fortunately in microcontroller systems, there is usually read-mostly memory, which can be locked out in a way that requires a multi-step process to enable writing to it. This can even be hardware-based, so that you have to place a jumper on the board or a button that has to be held down while booting to enable “development mode”. The main thing here is to be able to reboot when your code or anybody else’s snow-crashes. In the 80’s 8-bit computers, there was always some amount of ROM, and that made those pretty bulletproof.
Good point. Though that only protects against certain writes to the flash. It doesn’t protect against writes to RAM or peripherals. And it doesn’t protect against reads (which can even have side effects).
why not run fuzix?
Or even UZI. Seriously, I think that even Linux is bloatware, and when we’re running things on microcontrollers, just how important is multi-user operation? For the sake of security, if you’re connecting to a network, you do need an OS that has some level of resource protection, but that can be based on restricting program loading to local devices only, and/or some other sort of firewall. Without an MMU, code that comes from outside must be interpreted, with the security provided by the interpreter, a la Javascript. Or, maybe privileged functions can only be called from addresses in read-only memory. I haven’t thought about this in any great depth.