3 ms·
Konrad Hinsen calls this "software collapse": when the platform has been eroded out from underneath your software and it collapses. https://hal.science/hal-021
by kragen 1y ago
Konrad Hinsen calls this "software collapse": when the platform has been eroded out from underneath your software and it collapses. https://hal.science/hal-02117588/document https://hal.science/hal-02117588/document
There's no reason such a "bedrock platform"♢ needs to be a shitty pain in the ass like the IBM PC or NES (the examples on https://permacomputing.net/bedrock_platform/ https://permacomputing.net/bedrock_platform/). Those platforms were pragmatic tradeoffs for the existing hardware and fabrication technology in the market at the time, based on then-current knowledge. We know how to do much better tradeoffs now. The 8088 in the IBM PC was 29000 transistors, but the ARM 2 was only 27000 transistors†. Both could run at 8 MHz (the 8088 in its later 8088-2 and 80C88 incarnations), but the ARM 2 was a 32-bit processor that delivered about 4 VAX MIPS at that speed (assuming about ½DMIPS/MHz like the ARM3‡) while the 8088 would only deliver about 0.3 VAX MIPS (it was 0.04DMIPS/MHz). And programming for the 8088's segmented memory model was a huge pain in the ass, and it was crippled by only having 20 address lines. 8088 assembly is full of special-purpose registers that certain instructions have to use; ARM assembly is orthogonal and almost as high-level as C.
Same transistor count, same clock speed, dramatically better performance, dramatically better programming experience.
Similarly, Unix and Smalltalk came out about the same time as Nova RDOS and RT-11, and for literally the same machines, but the power Unix and Smalltalk put in the hands of users far outstripped that of those worse-designed systems.
So, let's put together a bedrock platform that we could actually use for our daily computing in practice. Unlike the NES.
______
♢ Stanislav Datskovskiy's term: http://www.loper-os.org/?p=55 http://www.loper-os.org/?p=55
† https://en.wikipedia.org/wiki/Transistor_count https://en.wikipedia.org/wiki/Transistor_count
‡ https://netlib.org/performance/html/dhrystone.data.col0.html https://netlib.org/performance/html/dhrystone.data.col0.html but note that the ARM3 had a cache, so this depends on having RAM that can keep up with 8MHz. Both the ARM2 and ARM3 were mostly-1-instruction-per-clock pipelined RISCs with almost exactly the same instruction set. https://en.wikipedia.org/wiki/Acorn_Archimedes https://en.wikipedia.org/wiki/Acorn_Archimedes, https://www.onirom.fr/wiki/blog/21-04-2022_Acorn-Archimedes/ https://www.onirom.fr/wiki/blog/21-04-2022_Acorn-Archimedes/, and its twin https://wardrome.com/acorn-archimedes-the-worlds-first-risc-based-home-computer/ https://wardrome.com/acorn-archimedes-the-worlds-first-risc-... confirm the 8MHz and 4MIPS.
- WalterBright 1y ago> ARM assembly is orthogonal and almost as high-level as C. The AArch64 is wacky in its own, different, way. For example, loading a constant into a register, dealing with an offset to an index, etc. It also has special purpose registers, like the zero register. The PDP-11 architecture remains the best gem of an orthogonal instruction set ever invented.
- kragen 1y agoYeah, ARM64 is a little weird, and I'm not sure it's a good design, though it does seem to be workable. But I'm talking about the original ARM instruction set implemented on the ARM2, as evidence that architectural design quality matters—the same 29000 transistors can give you 12 times the performance and a much better programming model. The PDP-11 seems pleasant and orthogonal, but I've never written a program for it, just helped to disassemble the original Tetris, written for a Soviet PDP-11 clone. The instruction set doesn't feel nearly as pleasant as the ARM: no conditional execution, no bit-shifted index registers, no bit-shifted addends, only 8 registers instead of 16, and you need multiple instructions for procedure prologues and epilogues if you have to save multiple registers. They share the pleasant attribute of keeping the stack pointer and program counter in general-purpose registers, and having postincrement and predecrement addressing modes, and even the same condition-code flags. (ARM has postdecrement and preincrement, too, including by variable distances determined by a third register.) The PDP-11 also wasn't a speed demon the way the ARM was. I believe that speed trades off against everything, and I think you're on board with that from your language designs. According to the page I linked above, a PDP-11/34 was about the same speed as an IBM PC/XT. Loading a constant into a register is still a problem on the ARM2, but it's a problem that the assembler mostly solves for you with constant pools. And ARM doesn't have indirect addressing (via a pointer in memory), but most of the time you don't need it because of the much larger register set. The ARM2 and ARM3 kept the condition code in the high bits of the program counter, which meant that subroutine calls automatically preserved it. I thought that was a cool feature, but later ARMs removed it in order to support being able to execute code out of more than just the low 16 mebibytes of memory. Here's an operating system I wrote in 32-bit ARM assembler. r10 is reserved for the current task pointer, which doesn't conform to the ARM procedure call standard. (I probably should have used r9.) It's five instructions: .syntax unified .thumb .fpu fpv4-sp-d16 .cpu cortex-m4 .thumb_func yield: push {r4-r9, r11, lr} @ save all callee-saved regs except r10 str sp, [r10], #4 @ save stack pointer in current task ldr r10, [r10] @ load pointer to next task ldr sp, [r10] @ switch to next task's stack pop {r4-r9, r11, pc} @ return into yielded context there http://canonical.org/~kragen/sw/dev3/monokokko.S http://canonical.org/~kragen/sw/dev3/monokokko.S