7 ms·
Those operating systems already exist. You can run NetBSD on pretty much anything (it currently supports machines with a Motorola 68k CPU for example). Granted
by eric__cartman 1y ago
Those operating systems already exist. You can run NetBSD on pretty much anything (it currently supports machines with a Motorola 68k CPU for example). Granted many of those machines still have an MMU iirc but everything is still simple enough to be comprehend by a single person with some knowledge in systems programming.
- kimixa 1y agoNetBSD doesn't support any devices without an mmu. I think people here are misunderstanding just how "weird" and hacky trying to run an OS like linux on those devices really is.
- kbolino 1y agoYeah, a lot of what defines "operating system" for us nowadays is downstream of having memory isolation. Not having an MMU puts you more into the territory of DOS than UNIX. There is FreeDOS but I'm pretty sure it's x86-only.
- actionfromafar 1y agoMmm... would beg to differ. I have ported stuff to NOMMU Linux and almost everything worked just as on a "real" Linux. Threads, processes (except only vfork, no fork), networking, priorities, you no name it. DOS gives you almost nothing. It has files. The one thing different to a regular Linux was that a crash of a program was not "drop into debugger" but "device reboots or halts". That part I don't miss at all.
- kbolino 1y agoThat's fair. If so, then you still can have things like drivers and HAL and so on too. However, there's no hard security barriers. How do multiple processes actually work, though? Is every executable position-independent? Does the kernel provide the base address(es) in register(s) as part of vfork? Do process heaps have to be constrained so they don't get interleaved?
- jlokier 1y agoThere are many options. Executables can be position-independent, or relocated at run-time, or the device can have an MPU or equivalent registers (for example 8086/80286 segment registers), which is related to an MMU but much simpler. Executables in a no-MMU environment can also share the same code/read-only segments between many processees, the same way shared libraries can, to save memory and, if run-time relocation is used, to reduce that. The original design of UNIX ran on machines without an MMU, and they had fork(). Andrew Tanenbaum's classic book which comes with Minix for teaching OS design explains how to fork() without an MMU, as Minix runs on machines without one. For spawning processes, vfork()+execve() and posix_spawn() are much faster than fork()+execve() from a large process in no-MMU environments though, and almost everything runs fine with vfork() instead of fork(), or threads. So no-MMU Linux provides only vfork(), clone() and pthread_create(), not fork().
- kbolino 1y agoThanks! I was able to find some additional info on no-MMU Linux [1], [2], [3]. It seems position-independent executables are the norm on regular (MMU) Linux now anyway (and probably have been for a long time). I took a look under the covers of uClibc and it seems like malloc just delegates most of its work to mmap, at least for the malloc-simple implementation [4]. That implies to me that different processes' heaps can be interleaved (without overlapping), but the kernel manages the allocations. [1]: https://maskray.me/blog/2024-02-20-mmu-less-systems-and-fdpic https://maskray.me/blog/2024-02-20-mmu-less-systems-and-fdpi... [2]: https://popovicu.com/posts/789-kb-linux-without-mmu-riscv/ https://popovicu.com/posts/789-kb-linux-without-mmu-riscv/ [3]: https://www.kernel.org/doc/Documentation/nommu-mmap.txt https://www.kernel.org/doc/Documentation/nommu-mmap.txt [4]: https://github.com/kraj/uClibc/blob/ca1c74d67dd115d059a875150e10b8560a9c35a8/libc/stdlib/malloc-simple/alloc.c#L23 https://github.com/kraj/uClibc/blob/ca1c74d67dd115d059a87515...
- zgs 1y agoUnder uClinux, executables can be position independent or not. They can run from flash or RAM. They can be compressed (if they run in RAM). Shared libraries are supported on some platforms. All in all it's a really good environment and the vfork() limitation generally isn't too bad. I spent close to ten years working closely with uClinux (a long time ago). I implemented the shared library support for the m68k. Last I looked, gcc still included my additions for this. This allowed execute in place for both executables and shared libraries -- a real space saver. Another guy on the team managed to squeeze the Linux kernel, a reasonable user space and a full IP/SEC implementation into a unit with 1Mb of flash and 4Mb of RAM which was pretty amazing at the time (we didn't think it was even possible). Better still, from power on to login prompt was well under two seconds.
- beeflet 1y agoThis was interesting. It reminded me how fork() is so weird and I found some explanation for its weirdness that loops back to this conversation about nommu: "Originally, fork() didn't do copy on write. Since this made fork() expensive, and fork() was often used to spawn new processes (so often was immediately followed by exec()), an optimized version of fork() appeared: vfork() which shared the memory between parent and child. In those implementations of vfork() the parent would be suspended until the child exec()'ed or _exit()'ed, thus relinquishing the parent's memory. Later, fork() was optimized to do copy on write, making copies of memory pages only when they started differing between parent and child. vfork() later saw renewed interest in ports to !MMU systems (e.g: if you have an ADSL router, it probably runs Linux on a !MMU MIPS CPU), which couldn't do the COW optimization, and moreover could not support fork()'ed processes efficiently. Other source of inefficiencies in fork() is that it initially duplicates the address space (and page tables) of the parent, which may make running short programs from huge programs relatively slow, or may make the OS deny a fork() thinking there may not be enough memory for it (to workaround this one, you could increase your swap space, or change your OS's memory overcommit settings). As an anecdote, Java 7 uses vfork()/posix_spawn() to avoid these problems. On the other hand, fork() makes creating several instances of a same process very efficient: e.g: a web server may have several identical processes serving different clients. Other platforms favour threads, because the cost of spawning a different process is much bigger than the cost of duplicating the current process, which can be just a little bigger than that of spawning a new thread. Which is unfortunate, since shared-everything threads are a magnet for errors." https://stackoverflow.com/questions/8292217/why-fork-works-the-way-it-does https://stackoverflow.com/questions/8292217/why-fork-works-t...
- arp242 1y agoTo clarify: NetBSD has never supported non-MMU systems, or at least hasn't for decades. As opposed to something they removed recently(-ish).
- jmclnx 1y agoFWIW, Linux is not the only OS looking into dropping 32bit. FreeBSD is dumping 32 bit: https://www.osnews.com/story/138578/freebsd-15-16-to-end-support-for-32-bit-platforms/ https://www.osnews.com/story/138578/freebsd-15-16-to-end-sup... OpenBSD has this quote: >...most i386 hardware, only easy and critical security fixes are backported to i386 I tend to think that means 32bit on at least x86 days are numbered. https://www.openbsd.org/i386.html https://www.openbsd.org/i386.html I think DragonflyBSD never supported 32bit For 32bit, I guess NetBSD may eventually be the only game in town.