The Wikipedia page on X86 Memory Segmentation says

In real mode, the registers CS, DS, SS, and ES point to the currently used program code segment (CS), the current data segment (DS), the current stack segment (SS), and one extra segment determined by the programmer (ES). The Intel 80386, introduced in 1985, adds two additional segment registers, FS and GS, with no specific uses defined by the hardware.

Was there any technical or social reason to chose FS/GS/ES? Was there a convention with regard to any of these?

  • 3
    ES has some specific uses defined by hardware, with the MOVS instruction for example. FS/GS were almost never used in 16-bit code, even by code that required other '386 features. They were (and are) used in 32-bit code for certain fixed purposes by DOS extenders and operating systems. (eg. FS as a thread local pointer in Windows and Linux).
    – user722
    Jun 2, 2018 at 17:29
  • 4
    You could, maybe, see these registers as a bit exotic, which was basically caused by the operating systems of the time: "Standard" DOS applications couldn't use them, as they would have lost compatibility with earlier CPUs, and new, 386-only systems tended to use linear 32bit addressing, thus not having a lot of use for segment registers, so they were pretty much ignored by standard applications and compilers for a long time.
    – tofro
    Jun 2, 2018 at 21:42

1 Answer 1


TL;DR: No.

By default all memory addresses are within DS. Exceptions are the destination addresses of STOSx/MOVSx and CMPSx where ES is used (*1). DS can be replaced by any other segment register in all instructions by adding a segment override prefix.

So with the exception of ES when it comes to string destination segment any segment can be used (overwritten) at cost of an additional instruction byte. Which segment register to be used when leaving the default is rather arbitrary.

The introduction of FS/GS eased the need to reload segment registers.

Adding one segment (FS) eased A=B+C type operations where each of the components resides in a separate segment, like when doing large amounts of data (tables), without constant reloading of segment registers. After all, each load needs not only to load all segment information, but also runs necessary privilege checks. It still requires reloading of DS after such sections.

Adding a two (FS&GS) even removed that restriction, allowing a program to hold three arbitrary data segments in addition to Code, Programm Data and Stack.

Fire at Will

*1 - And then there are all addressing modes with BP and SP,as they are calculated with SS as base value - after all, BP is the stack frame pointer.

  • 4
    IMHO, the original 8086 segmentation design was brilliant, save for the lack of a few instructions like mov segreg,immed and second "scratchpad" segment register. The 80286 is my least favorite design, because it massively increased the cost of repeated segment-register loads without doing anything to alleviate the need for them. The wimpy 16-bit selectors make 80386 segmentation just about useless, but fortunately the large offsets minimize the need for it.
    – supercat
    Jun 4, 2018 at 14:57
  • The 286 competes the 16 bit design as it now offers large and virtual memory while being fully compatible. Any clean 8086 code (that is none using atrocities like huge memory model / calculated segment values) culd run right away in a virtual memory environment. Sure, the implementation how segment descriptors are haldled was less than great. Still, increased speeds did more than compensate for this. Ofc, code written against the segmentation philosopy did not realy do well. Not Intels fault.
    – Raffzahn
    Jun 4, 2018 at 16:33
  • 2
    The only way to avoid frequent segment register loads is to arrange related objects into common segments. That can improve things a lot if one is using machine code, but high-level languages don't support that except for one main data segment, the stack segment, and for Turbo Pascal versions before 4.0, the code segment. I know Intel CPUs are what they are, but it's ironic that Intel added FS: and GS: to an architecture where they were no longer really needed.
    – supercat
    Jun 4, 2018 at 17:58
  • 1
    In 16-bit real mode SP can't be used as part of an effective address, only BP. On a 386 it is possible (in real mode) to use ESP as part of an effective address. Jun 19, 2018 at 6:00
  • 1
    @Raffzahn : It says addressing modes with BP and SP, . There are no addressing modes where SP is allowed as a base address. Push and Pop are always implicit but they are not considered addressing modes Jun 19, 2018 at 13:32

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .