The segment model seems clever if you assume that you never have an object that is larger than 64kb. And once you have that you need to care about segment overflow, pointer comparisons no longer work, everything now has to carry around segment+offset instead of just offset, and so on. And if you want an example of a >=64kb object - the html alone for that page is one.
> 8086 Segmented Memory Was a Good Idea.<p>Yet the article goes about the most ass backward way of explaining 8086 segments and constructs a convoluted mental picture of dividing memory into overlapping chunks.<p>It's really, <i>really</i> simple: segments on the 8086/88 are 64k <i>sliding windows</i> into an 1M address space. You can move them around at 16 byte granularity.<p>You need more than 64k for code + data? No problem, the CPU knows when it's fetching an instruction vs when it's fetching data, you can have two sliding windows: code (CS) and data (DS). Split them apart, and it's not much different than a Harvard-style machine and gives you access to more than 64k at a time.<p>Still need more? No problem, the CPU has a hardware stack with dedicated push/pop/call/ret instructions and a base pointer for stack indexing. It knows when it's accessing the stack, so we can split the data window into regular data (DS) and stack data (SS). Oh, you occasionally want to copy stuff between segments or somewhere else in memory? Well, to encode 3 segments we need 2 bits anyway, let's throw in an extra data window (ES) and some DS-to-ES copy instructions.
What is the difference between the segmentation model used by Intel and the banking model used by a lot of consoles? I've worked with the code of a couple of NES and GBC games, and while banking could be annoying, I never saw it as a particularly difficult model to follow and use. It did require more planning for the various functionality, but it wasn't even the most complex or difficult thing about developing for consoles.
It might have worked better if x86 had general-purpose registers where every register could work as a segment. Or maybe just many more segment registers. But with only two data segment registers to play with and quite cubersome (and slow!) loads, most software just chose not to bother.
Google's native client (NaCl) even used it on 32-bit x86...<p>Segmented memory (on hardware that supported segment permissions) was used to good effect in Multics as well.
No<p>No, it wasn't<p>It's the "great idea" that sounds great 5 min in and horrible 10min afterwards<p>You know, kinda like using null as a string end character<p>But more importantly it kept the x86 world for too long in that dead end that was 8086 mode programming<p>"Oh if developers would just..." They won't. They haven't. And they will not ever.<p>In hindsight maybe a binary level translator from 8080 to 8086 would have worked better (and be simple enough)
The 8086 was a stopgap measure to accommodate the fact the iAPX432 was in the middle of turning into the disaster it did. Given the engineering resources and timelines involved in the 8086, it wasn't a bad compromise approach.<p>> But more importantly it kept the x86 world for too long in that dead end that was 8086 mode programming
>
> "Oh if developers would just..." They won't. They haven't. And they will not ever.<p>8086 real mode programming in the mainstream lasted from 1981 until 1991 or so. The last 35 years have 32-bit (and later 64-bit) flat model addressing with pages for the most part. Seems like a reasonable transition period, really.<p>> In hindsight maybe a binary level translator from 8080 to 8086 would have worked better (and be simple enough)<p>Part of the reason they liked the segmented model is that it was possible to set the segments to the same value and then ignore them entirely. That gave a programming model for the 8086 that was sufficiently close to the 8080 that it was possible to use a sort of cross assembler to do something like what you suggest. You could then opt into 8086 specific instructions and segmentation as you needed. (Which took a few years... the first IBM PC's shipped with as little as 16K of RAM.)
Indeed, I say as much at the end.<p>But what should Intel have done? They needed a CPU that can run 8080 code but with more memory. Also it's the year ~1980 and we're limited to the technology of the age.<p>A system with 64k sized windows seems unavoidable.<p>If you extend the size of the address registers, 8080 code will only run in the first 64k, or require some kind of current window register.<p>An 8080 mode might have worked but that would have been expensive.
It's not all that different from the memory pages we have today, except that the 'segment' addressing has become a lot more complex under the hood (multi-level page tables) and a lot simpler at the surface (by merging the 'segment-' and page-address bits into a single virtual address).<p>PS: and segmented memory wasn't all that different from the memory banking used before in 8-bit home computers to address more than 64 KBytes, except that the memory mapping hardware was implemented outside the CPU.
> In hindsight maybe a binary level translator from 8080 to 8086 would have worked better (and be simple enough)<p>Many programs written in assembly language used self modifying code back then. It saved RAM and improved performance. All programs that used such trickery would have broken by a binary translator.