Index: /trunk/src/VBox/ValidationKit/bootsectors/Config.kmk
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/Config.kmk	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/Config.kmk	(revision 60539)
@@ -85,5 +85,4 @@
                '      extern  _$2_f16' \
        	'BS3_BEGIN_TEXT16_NEARSTUBS' \
-               'GROUP CGROUP16 BS3TEXT16 BS3TEXT16_NEARSTUBS' \
 		'BS3_GLOBAL_NAME_EX _$2_c16, function, 6' \
                '      pop     ax' \
@@ -606,4 +605,12 @@
  	  segment BS3RMCODE16 \
  	  segment BS3RMCODE16_END \
+        clname BS3CLASS16X0CODE \
+ 	  segment BS3X0CODE16_START \
+ 	  segment BS3X0CODE16 \
+ 	  segment BS3X0CODE16_END \
+        clname BS3CLASS16X1CODE \
+ 	  segment BS3X1CODE16_START \
+ 	  segment BS3X1CODE16 \
+ 	  segment BS3X1CODE16_END \
         clname BS3CLASS32CODE \
  	  segment BS3TEXT32_START \
@@ -809,4 +816,12 @@
  	  segment BS3RMCODE16 \
  	  segment BS3RMCODE16_END \
+        clname BS3CLASS16X0CODE \
+ 	  segment BS3X0CODE16_START \
+ 	  segment BS3X0CODE16 \
+ 	  segment BS3X0CODE16_END \
+        clname BS3CLASS16X1CODE \
+ 	  segment BS3X1CODE16_START \
+ 	  segment BS3X1CODE16 \
+ 	  segment BS3X1CODE16_END \
         clname BS3CLASS32CODE \
  	  segment BS3TEXT32 \
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-c.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-c.c	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-c.c	(revision 60539)
@@ -51,5 +51,5 @@
     BS3TESTMODEENTRY_MODE("raise xcpt #1", bs3CpuBasic2_RaiseXcpt1),
     //BS3TESTMODEENTRY_CMN("iret", bs3CpuBasic2_iret),
-//    BS3TESTMODEENTRY_MODE("iret", bs3CpuBasic2_iret),
+    BS3TESTMODEENTRY_MODE("iret", bs3CpuBasic2_iret),
 //    BS3TESTMODEENTRY_MODE("sidt", bs3CpuBasic2_sidt),
 };
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-template.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-template.c	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3-cpu-basic-2-template.c	(revision 60539)
@@ -242,6 +242,6 @@
  */
 #define bs3CpuBasic2_CompareCpuTrapCtx BS3_CMN_NM(bs3CpuBasic2_CompareCpuTrapCtx)
-BS3_DECL(void) bs3CpuBasic2_CompareCpuTrapCtx(PCBS3TRAPFRAME pTrapCtx, PCBS3REGCTX pStartCtx, uint16_t uErrCd, uint8_t bXcpt,
-                                              bool f486ResumeFlagHint)
+void bs3CpuBasic2_CompareCpuTrapCtx(PCBS3TRAPFRAME pTrapCtx, PCBS3REGCTX pStartCtx, uint16_t uErrCd, uint8_t bXcpt,
+                                    bool f486ResumeFlagHint)
 {
     uint16_t const cErrorsBefore = Bs3TestSubErrorCount();
@@ -1498,5 +1498,5 @@
 
 
-BS3_DECL(uint8_t) TMPL_NM(bs3CpuBasic2_TssGateEsp)(uint8_t bMode)
+BS3_DECL_FAR(uint8_t) TMPL_NM(bs3CpuBasic2_TssGateEsp)(uint8_t bMode)
 {
     uint8_t bRet = 0;
@@ -1528,5 +1528,5 @@
 
 
-BS3_DECL(uint8_t) TMPL_NM(bs3CpuBasic2_RaiseXcpt1)(uint8_t bMode)
+BS3_DECL_FAR(uint8_t) TMPL_NM(bs3CpuBasic2_RaiseXcpt1)(uint8_t bMode)
 {
     g_pszTestMode = TMPL_NM(g_szBs3ModeName);
@@ -1565,5 +1565,5 @@
 
 
-BS3_DECL(uint8_t) TMPL_NM(bs3CpuBasic2_iret)(uint8_t bMode)
+BS3_DECL_FAR(uint8_t) TMPL_NM(bs3CpuBasic2_iret)(uint8_t bMode)
 {
     g_pszTestMode = TMPL_NM(g_szBs3ModeName);
@@ -1579,5 +1579,5 @@
 
 
-BS3_DECL(uint8_t) TMPL_NM(bs3CpuBasic2_sidt)(uint8_t bMode)
+BS3_DECL_FAR(uint8_t) TMPL_NM(bs3CpuBasic2_sidt)(uint8_t bMode)
 {
     g_pszTestMode = TMPL_NM(g_szBs3ModeName);
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 60539)
@@ -90,4 +90,7 @@
        bs3-cmn-SelFar32ToFlat32.c \
        bs3-cmn-SelProtFar32ToFlat32.c \
+       bs3-cmn-SelRealModeCodeToProtMode.asm \
+       bs3-cmn-SelFlatCodeToRealMode.asm \
+       bs3-cmn-SelFlatCodeToProtFar16.asm \
        bs3-cmn-SlabInit.c \
        bs3-cmn-SlabAlloc.c \
@@ -176,4 +179,5 @@
 	bs3-rm-InitAll.c \
 	bs3-rm-InitMemory.c \
+	bs3-rm-InitGdt.c \
 	bs3-cmn-hexdigits.c \
 	bs3-cmn-CpuDetectData.c \
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp	(revision 60539)
@@ -3661,6 +3661,6 @@
     /** The segment index. */
     uint16_t        idxSeg;
-    /** The group index for this segment.  This is zero if not yet determined and
-     * UINT16_MAX if no group applicable to this segment. */
+    /** The group index for this segment.  Initially OMF_REPLACE_GRP_XXX values,
+     * later convertOmfWriteDebugGrpDefs replaces them with actual values. */
     uint16_t        idxGrp;
     /** File table. */
@@ -3668,4 +3668,13 @@
 } OMFSEGLINES;
 typedef OMFSEGLINES *POMFSEGLINES;
+
+/** @name OMF_REPLACE_GRP_XXX - Special OMFSEGLINES::idxGrp values.
+ * @{ */
+#define OMF_REPLACE_GRP_CGROUP16    UINT16_C(0xffe0)
+#define OMF_REPLACE_GRP_RMCODE      UINT16_C(0xffe1)
+#define OMF_REPLACE_GRP_X0CODE      UINT16_C(0xffe2)
+#define OMF_REPLACE_GRP_X1CODE      UINT16_C(0xffe3)
+/** @} */
+
 
 /**
@@ -3682,6 +3691,4 @@
     /** Set if this module may need mangling. */
     bool            fMayNeedMangling;
-    /** Set if this module needs CGROUP16 for line number fixupes. */
-    bool            fNeedsCGroup16;
     /** The LNAME index of '$$SYMBOLS' or UINT16_MAX it not found. */
     uint16_t        iSymbolsNm;
@@ -3690,8 +3697,4 @@
     /** The '$$SYMBOLS' segment index. */
     uint16_t        iSymbolsSeg;
-    /** The LNAME index of 'CGROUP16' or UINT16_MAX it not found. */
-    uint16_t        iCGroup16Nm;
-    /** The 'CGROUP16' group definition index or UINT16_MAX it not found. */
-    uint16_t        iCGroup16Grp;
 
     /** Number of SEGDEFs records. */
@@ -3708,4 +3711,29 @@
     /** Name list.  Points to the size repfix. */
     char          **papchLNames;
+
+    /** Code groups we need to keep an eye on for line number fixup purposes. */
+    struct OMFLINEGROUPS
+    {
+        /** The name. */
+        const char *pszName;
+        /** The primary class name. */
+        const char *pszClass1;
+        /** The secondary class name. */
+        const char *pszClass2;
+        /** The name length. */
+        uint8_t     cchName;
+        /** The primary class name length. */
+        uint8_t     cchClass1;
+        /** The secondary class name length. */
+        uint8_t     cchClass2;
+        /** Whether this group is needed. */
+        bool        fNeeded;
+        /** The group index (UINT16_MAX if not found). */
+        uint16_t    idxGroup;
+        /** The group name. */
+        uint16_t    idxName;
+        /** The OMF_REPLACE_GRP_XXX value. */
+        uint16_t    idxReplaceGrp;
+    }               aGroups[4];
 
     /** CV8: Filename string table size. */
@@ -3728,4 +3756,5 @@
 typedef OMFDETAILS *POMFDETAILS;
 typedef OMFDETAILS const *PCOMFDETAILS;
+
 
 /** Grows a table to a given size (a_cNewEntries). */
@@ -3892,10 +3921,15 @@
                 return error("???", "collectOmfAddLine: idxSeg=%#x is out of bounds (%#x)!\n", idxSeg, pOmfStuff->cSegDefs);
             POMFSEGDEF pSegDef = &pOmfStuff->paSegDefs[idxSeg];
-            if (   IS_OMF_STR_EQUAL_EX(pSegDef->cchClass, pSegDef->pchClass, "BS3CLASS16CODE")
-                || IS_OMF_STR_EQUAL_EX(pSegDef->cchClass, pSegDef->pchClass, "CODE"))
-            {
-                pOmfStuff->fNeedsCGroup16 = true;
-                pSegLines->idxGrp = 0;  /* We'll replace zeros by the actual CGROUP16 index later. */
-            }
+            unsigned j = RT_ELEMENTS(pOmfStuff->aGroups);
+            while (j-- > 0)
+                if (   (   pSegDef->cchClass == pOmfStuff->aGroups[j].cchClass1
+                        && memcmp(pSegDef->pchClass, pOmfStuff->aGroups[j].pszClass1, pSegDef->cchClass) == 0)
+                    || (   pSegDef->cchClass == pOmfStuff->aGroups[j].cchClass2
+                        && memcmp(pSegDef->pchClass, pOmfStuff->aGroups[j].pszClass2, pSegDef->cchClass) == 0))
+                {
+                    pOmfStuff->aGroups[j].fNeeded = true;
+                    pSegLines->idxGrp = pOmfStuff->aGroups[j].idxReplaceGrp;
+                    break;
+                }
         }
     }
@@ -3960,6 +3994,4 @@
     pOmfStuff->iSymbolsNm   = UINT16_MAX;
     pOmfStuff->iSymbolsSeg  = UINT16_MAX;
-    pOmfStuff->iCGroup16Nm  = UINT16_MAX;
-    pOmfStuff->iCGroup16Grp = UINT16_MAX;
 
     /* Dummy entries. */
@@ -3973,4 +4005,21 @@
     OMF_GROW_TABLE_RET_ERR(OMFGRPDEF, pOmfStuff->paGrpDefs, pOmfStuff->cGrpDefs, 16);
     pOmfStuff->cGrpDefs = 1;
+
+    /* Groups we seek. */
+#define OMF_INIT_WANTED_GROUP(a_idx, a_szName, a_szClass1, a_szClass2, a_idxReplace) \
+        pOmfStuff->aGroups[a_idx].pszName   = a_szName; \
+        pOmfStuff->aGroups[a_idx].cchName   = sizeof(a_szName) - 1; \
+        pOmfStuff->aGroups[a_idx].pszClass1 = a_szClass1; \
+        pOmfStuff->aGroups[a_idx].cchClass1 = sizeof(a_szClass1) - 1; \
+        pOmfStuff->aGroups[a_idx].pszClass2 = a_szClass2; \
+        pOmfStuff->aGroups[a_idx].cchClass2 = sizeof(a_szClass2) - 1; \
+        pOmfStuff->aGroups[a_idx].fNeeded   = false; \
+        pOmfStuff->aGroups[a_idx].idxGroup  = UINT16_MAX; \
+        pOmfStuff->aGroups[a_idx].idxName   = UINT16_MAX; \
+        pOmfStuff->aGroups[a_idx].idxReplaceGrp = a_idxReplace
+    OMF_INIT_WANTED_GROUP(0, "CGROUP16",         "BS3CLASS16CODE",   "CODE", OMF_REPLACE_GRP_CGROUP16);
+    OMF_INIT_WANTED_GROUP(1, "BS3GROUPRMTEXT16", "BS3CLASS16RMCODE", "",     OMF_REPLACE_GRP_RMCODE);
+    OMF_INIT_WANTED_GROUP(2, "BS3GROUPX0TEXT16", "BS3CLASS16X0CODE", "",     OMF_REPLACE_GRP_X0CODE);
+    OMF_INIT_WANTED_GROUP(3, "BS3GROUPX1TEXT16", "BS3CLASS16X1CODE", "",     OMF_REPLACE_GRP_X1CODE);
 
     /*
@@ -4048,6 +4097,13 @@
                     if (IS_OMF_STR_EQUAL_EX(cch, &pbRec[offRec + 1], "$$SYMBOLS"))
                         pOmfStuff->iSymbolsNm = pOmfStuff->cLNames;
-                    if (IS_OMF_STR_EQUAL_EX(cch, &pbRec[offRec + 1], "CGROUP16"))
-                        pOmfStuff->iCGroup16Nm = pOmfStuff->cLNames;
+
+                    unsigned j = RT_ELEMENTS(pOmfStuff->aGroups);
+                    while (j-- > 0)
+                        if (   cch == pOmfStuff->aGroups[j].cchName
+                            && memcmp(&pbRec[offRec + 1], pOmfStuff->aGroups[j].pszName, pOmfStuff->aGroups[j].cchName) == 0)
+                        {
+                            pOmfStuff->aGroups[j].idxName = pOmfStuff->cLNames;
+                            break;
+                        }
 
                     pOmfStuff->cLNames++;
@@ -4199,6 +4255,12 @@
                 OMF_READ_IDX(pGrpDef->idxName, GRPDEF);
                 OMF_EXPLODE_LNAME(pGrpDef->idxName, pGrpDef->pchName, pGrpDef->cchName, GRPDEF);
-                if (pGrpDef->idxName == pOmfStuff->iCGroup16Grp)
-                    pOmfStuff->iCGroup16Grp = pOmfStuff->cGrpDefs;
+
+                unsigned j = RT_ELEMENTS(pOmfStuff->aGroups);
+                while (j-- > 0)
+                    if (pGrpDef->idxName == pOmfStuff->aGroups[j].idxName)
+                    {
+                        pOmfStuff->aGroups[j].idxGroup = pOmfStuff->cGrpDefs;
+                        break;
+                    }
 
                 pGrpDef->cSegDefs    = 0;
@@ -4366,25 +4428,66 @@
 static bool convertOmfWriteDebugGrpDefs(POMFWRITER pThis, POMFDETAILS pOmfStuff)
 {
-    if (   pOmfStuff->cSegLines == 0
-        || !pOmfStuff->fNeedsCGroup16)
+    if (pOmfStuff->cSegLines == 0)
         return true;
 
-    if (pOmfStuff->iCGroup16Grp == UINT16_MAX)
-    {
-        if (pOmfStuff->iCGroup16Nm == UINT16_MAX)
-            if (   !omfWriter_LNamesBegin(pThis, true)
-                || !omfWriter_LNamesAdd(pThis, "CGROUP16", &pOmfStuff->iCGroup16Nm)
-                || !omfWriter_LNamesEnd(pThis))
-                return false;
-
-        if (   !omfWriter_GrpDefBegin(pThis, pOmfStuff->iCGroup16Nm)
-            || !omfWriter_GrpDefEnd(pThis))
+    /*
+     * See what (if anything) we need.
+     */
+    uint8_t cNames  = 0;
+    uint8_t cGroups = 0;
+    unsigned j = RT_ELEMENTS(pOmfStuff->aGroups);
+    while (j-- > 0)
+        if (pOmfStuff->aGroups[j].fNeeded)
+        {
+            cNames  += pOmfStuff->aGroups[j].idxName  == UINT16_MAX;
+            cGroups += pOmfStuff->aGroups[j].idxGroup == UINT16_MAX;
+        }
+
+    /*
+     * Add any names we need.
+     */
+    if (cNames)
+    {
+        if (!omfWriter_LNamesBegin(pThis, true))
             return false;
-        pOmfStuff->iCGroup16Grp = pOmfStuff->cGrpDefs;
-    }
-
-    for (unsigned i = 0; i < pOmfStuff->cSegLines; i++)
-        if (pOmfStuff->paSegLines[i].idxGrp == 0)
-            pOmfStuff->paSegLines[i].idxGrp = pOmfStuff->iCGroup16Grp;
+        j = RT_ELEMENTS(pOmfStuff->aGroups);
+        while (j-- > 0)
+            if (   pOmfStuff->aGroups[j].fNeeded
+                && pOmfStuff->aGroups[j].idxName == UINT16_MAX)
+                if (!omfWriter_LNamesAdd(pThis, pOmfStuff->aGroups[j].pszName, &pOmfStuff->aGroups[j].idxName))
+                    return false;
+        if (!omfWriter_LNamesEnd(pThis))
+            return false;
+    }
+
+    /*
+     * Add any groups we need.
+     */
+    if (cNames)
+    {
+        uint16_t iGrp = pOmfStuff->cGrpDefs; /* Shouldn't update cGrpDefs as it governs paGrpDefs. */
+        j = RT_ELEMENTS(pOmfStuff->aGroups);
+        while (j-- > 0)
+        {
+            if (   pOmfStuff->aGroups[j].fNeeded
+                && pOmfStuff->aGroups[j].idxGroup == UINT16_MAX)
+            {
+                if (   !omfWriter_GrpDefBegin(pThis, pOmfStuff->aGroups[j].idxName)
+                    || !omfWriter_GrpDefEnd(pThis))
+                    return false;
+                pOmfStuff->aGroups[j].idxGroup = iGrp++;
+            }
+        }
+    }
+
+    /*
+     * Replace group references in the segment lines table.
+     */
+    j = RT_ELEMENTS(pOmfStuff->aGroups);
+    while (j-- > 0)
+        if (pOmfStuff->aGroups[j].fNeeded)
+            for (unsigned i = 0; i < pOmfStuff->cSegLines; i++)
+                if (pOmfStuff->paSegLines[i].idxGrp == pOmfStuff->aGroups[j].idxReplaceGrp)
+                    pOmfStuff->paSegLines[i].idxGrp = pOmfStuff->aGroups[j].idxGroup;
     return true;
 }
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToProtFar16.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToProtFar16.asm	(revision 60539)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToProtFar16.asm	(revision 60539)
@@ -0,0 +1,120 @@
+; $Id$
+;; @file
+; BS3Kit - Bs3SelFlatCodeToProtFar16.
+;
+
+;
+; Copyright (C) 2007-2015 Oracle Corporation
+;
+; This file is part of VirtualBox Open Source Edition (OSE), as
+; available from http://www.virtualbox.org. This file is free software;
+; you can redistribute it and/or modify it under the terms of the GNU
+; General Public License (GPL) as published by the Free Software
+; Foundation, in version 2 as it comes in the "COPYING" file of the
+; VirtualBox OSE distribution. VirtualBox OSE is distributed in the
+; hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
+;
+; The contents of this file may alternatively be used under the terms
+; of the Common Development and Distribution License Version 1.0
+; (CDDL) only, as it comes in the "COPYING.CDDL" file of the
+; VirtualBox OSE distribution, in which case the provisions of the
+; CDDL are applicable instead of those of the GPL.
+;
+; You may elect to license modified versions of this file under the
+; terms and conditions of either the GPL or the CDDL or both.
+;
+
+
+;*********************************************************************************************************************************
+;*      Header Files                                                                                                             *
+;*********************************************************************************************************************************
+%include "bs3kit-template-header.mac"
+
+
+;*********************************************************************************************************************************
+;*  External Symbols                                                                                                             *
+;*********************************************************************************************************************************
+BS3_EXTERN_CMN Bs3SelFlatCodeToRealMode
+BS3_EXTERN_CMN Bs3SelRealModeCodeToProtMode
+TMPL_BEGIN_TEXT
+
+
+;;
+; @cproto   BS3_CMN_PROTO(uint32_t, Bs3SelRealModeCodeToProtMode,(uint32_t uFlatAddr), false);
+;
+; @uses     Only return registers (ax:dx, eax, eax)
+;
+BS3_PROC_BEGIN_CMN Bs3SelFlatCodeToProtFar16, BS3_PBC_NEAR
+        BS3_CALL_CONV_PROLOG 1
+        push    xBP
+        mov     xBP, xSP
+
+        ;
+        ; Call Bs3SelFlatCodeToRealMode and then Bs3SelRealModeCodeToProtMode.
+        ; This avoid some code duplication.
+        ;
+%if TMPL_BITS == 16
+        push    word [xBP + xCB + cbCurRetAddr + 2]
+        push    word [xBP + xCB + cbCurRetAddr]
+        call    Bs3SelFlatCodeToRealMode
+        add     sp, 4h
+
+        push    ax                      ; save the offset as it will be the same.
+
+        push    dx
+        call    Bs3SelRealModeCodeToProtMode
+        add     sp, 2h
+
+        mov     dx, ax                  ; The protected mode selector.
+        pop     ax                      ; The offset.
+
+%elif TMPL_BITS == 32
+        push    dword [xBP + xCB + cbCurRetAddr]
+        call    Bs3SelFlatCodeToRealMode
+        add     esp, 4h
+
+        push    eax                     ; save the result.
+
+        shr     eax, 16
+        push    eax
+        call    Bs3SelRealModeCodeToProtMode
+        add     esp, 4h
+
+        mov     [esp + 2], ax           ; Update the selector before popping the result.
+        pop     eax
+
+%elif TMPL_BITS == 64
+        push    xCX                     ; Preserve RCX to make the behaviour uniform.
+        sub     xSP, 28h                ; 20h bytes of calling convention scratch and 8 byte for saving the result.
+
+        mov     ecx, [xBP + xCB + cbCurRetAddr] ; move straight to parameter 0 register.
+        call    Bs3SelFlatCodeToRealMode
+
+        mov     [xBP - xCB*2], eax      ; Save the result.
+
+        shr     eax, 16
+        mov     ecx, eax                ; Move straight to parameter 0 register.
+        call    Bs3SelRealModeCodeToProtMode
+
+        shl     eax, 16                 ; Shift prot mode selector into result position.
+        mov     ax, [xBP - xCB*2]       ; The segment offset from the previous call.
+
+        add     xSP, 28h
+        pop     xCX
+%else
+ %error "TMPL_BITS=" TMPL_BITS "!"
+%endif
+        pop     xBP
+        BS3_CALL_CONV_EPILOG 1
+        BS3_HYBRID_RET
+BS3_PROC_END_CMN   Bs3SelFlatCodeToProtFar16
+
+
+;
+; We may be using the near code in some critical code paths, so don't
+; penalize it.
+;
+BS3_CMN_FAR_STUB   Bs3SelFlatCodeToProtFar16, 4
+
+
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToRealMode.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToRealMode.asm	(revision 60539)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelFlatCodeToRealMode.asm	(revision 60539)
@@ -0,0 +1,141 @@
+; $Id$
+;; @file
+; BS3Kit - Bs3SelFlatCodeToRealMode.
+;
+
+;
+; Copyright (C) 2007-2015 Oracle Corporation
+;
+; This file is part of VirtualBox Open Source Edition (OSE), as
+; available from http://www.virtualbox.org. This file is free software;
+; you can redistribute it and/or modify it under the terms of the GNU
+; General Public License (GPL) as published by the Free Software
+; Foundation, in version 2 as it comes in the "COPYING" file of the
+; VirtualBox OSE distribution. VirtualBox OSE is distributed in the
+; hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
+;
+; The contents of this file may alternatively be used under the terms
+; of the Common Development and Distribution License Version 1.0
+; (CDDL) only, as it comes in the "COPYING.CDDL" file of the
+; VirtualBox OSE distribution, in which case the provisions of the
+; CDDL are applicable instead of those of the GPL.
+;
+; You may elect to license modified versions of this file under the
+; terms and conditions of either the GPL or the CDDL or both.
+;
+
+
+;*********************************************************************************************************************************
+;*      Header Files                                                                                                             *
+;*********************************************************************************************************************************
+%include "bs3kit-template-header.mac"
+
+
+;*********************************************************************************************************************************
+;*      Global Variables                                                                                                         *
+;*********************************************************************************************************************************
+extern Bs3X0Text16_EndOfSegment
+extern Bs3X1Text16_EndOfSegment
+
+
+;
+; Make sure we can get at all the segments.
+;
+BS3_BEGIN_TEXT16
+BS3_BEGIN_X0TEXT16
+BS3_BEGIN_X1TEXT16
+TMPL_BEGIN_TEXT
+
+
+;;
+; @cproto   BS3_CMN_PROTO(uint32_t, Bs3SelRealModeCodeToProtMode,(uint32_t uFlatAddr), false);
+;
+; @uses     Only return registers (ax:dx, eax, eax)
+;
+BS3_PROC_BEGIN_CMN Bs3SelFlatCodeToRealMode, BS3_PBC_NEAR
+        BS3_CALL_CONV_PROLOG 1
+        push    xBP
+        mov     xBP, xSP
+        push    xCX
+        push    xBX
+%if TMPL_BITS != 16
+        push    xDX
+%endif
+
+        ;
+        ; Load the real mode frame number into DX so we can compare with the
+        ; segment frame numbers fixed up by the linker.
+        ;
+        ; Imagine: FlatAddr = 0x054321
+        ;
+        mov     dx, [xBP + xCB + cbCurRetAddr + 1]      ; dx = 0x0543
+        mov     al, [xBP + xCB + cbCurRetAddr + 0]      ; al =     0x21
+        mov     cl,4
+        shl     dx, 4                                   ; dx =  0x5430
+        shr     al, 4                                   ; al =    0x02
+        or      dl, al                                  ; dx =  0x5432
+
+        mov     ax, dx
+        sub     ax, BS3TEXT16
+        cmp     ax, 1000h
+        jb      .bs3text16
+
+        mov     ax, dx
+        sub     ax, BS3X0TEXT16
+        mov     bx, Bs3X0Text16_EndOfSegment wrt BS3GROUPX0TEXT16
+        add     bx, 15
+        shr     bx, cl
+        cmp     ax, bx
+        jb      .bs3x0text16
+
+        mov     ax, dx
+        sub     ax, BS3X1TEXT16
+        mov     bx, Bs3X1Text16_EndOfSegment wrt BS3GROUPX1TEXT16
+        add     bx, 15
+        shr     bx, cl
+        cmp     ax, bx
+        jb      .bs3x1text16
+
+        extern  BS3_CMN_NM(Bs3Panic)
+        call    BS3_CMN_NM(Bs3Panic)
+
+        ;
+        ; Load the real-mode frame into DX and calc the offset in AX.
+        ;
+.bs3x1text16:
+        mov     dx, BS3X1TEXT16
+        jmp     .calc_return
+.bs3x0text16:
+        mov     dx, BS3X0TEXT16
+        jmp     .calc_return
+.bs3text16:
+        mov     dx, BS3X0TEXT16
+.calc_return:
+        ; Convert the real-mode frame into the low 16-bit base (BX).
+        mov     bx, dx
+        shl     bx, cl
+        ; Subtract the 16-bit base from the flat address. (No need to consider
+        ; the top half on either side.)
+        mov     ax, [xBP + xCB + cbCurRetAddr + 0]
+        sub     ax, bx
+%if TMPL_BITS != 16
+        ; Got a single 32-bit return register here.
+        shl     edx, 16
+        mov     dx, ax
+        mov     eax, edx
+        pop     xDX
+%endif
+        pop     xBX
+        pop     xCX
+        pop     xBP
+        BS3_CALL_CONV_EPILOG 1
+        BS3_HYBRID_RET
+BS3_PROC_END_CMN   Bs3SelFlatCodeToRealMode
+
+;
+; We may be using the near code in some critical code paths, so don't
+; penalize it.
+;
+BS3_CMN_FAR_STUB   Bs3SelFlatCodeToRealMode, 4
+
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelRealModeCodeToProtMode.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelRealModeCodeToProtMode.asm	(revision 60539)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-SelRealModeCodeToProtMode.asm	(revision 60539)
@@ -0,0 +1,76 @@
+; $Id$
+;; @file
+; BS3Kit - Bs3SelRealModeCodeToProtMode.
+;
+
+;
+; Copyright (C) 2007-2016 Oracle Corporation
+;
+; This file is part of VirtualBox Open Source Edition (OSE), as
+; available from http://www.virtualbox.org. This file is free software;
+; you can redistribute it and/or modify it under the terms of the GNU
+; General Public License (GPL) as published by the Free Software
+; Foundation, in version 2 as it comes in the "COPYING" file of the
+; VirtualBox OSE distribution. VirtualBox OSE is distributed in the
+; hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
+;
+; The contents of this file may alternatively be used under the terms
+; of the Common Development and Distribution License Version 1.0
+; (CDDL) only, as it comes in the "COPYING.CDDL" file of the
+; VirtualBox OSE distribution, in which case the provisions of the
+; CDDL are applicable instead of those of the GPL.
+;
+; You may elect to license modified versions of this file under the
+; terms and conditions of either the GPL or the CDDL or both.
+;
+
+%include "bs3kit-template-header.mac"
+
+;
+; Make sure we can get at all the segments.
+;
+BS3_BEGIN_TEXT16
+BS3_BEGIN_X0TEXT16
+BS3_BEGIN_X1TEXT16
+TMPL_BEGIN_TEXT
+
+
+;;
+; @cproto   BS3_CMN_PROTO(uint16_t, Bs3SelRealModeCodeToProtMode,(uint16_t uRealSel), false);
+;
+BS3_PROC_BEGIN_CMN Bs3SelRealModeCodeToProtMode, BS3_PBC_NEAR
+        BS3_CALL_CONV_PROLOG 1
+        push    xBP
+        mov     xBP, xSP
+
+        mov     ax, [xBP + xCB + cbCurRetAddr]
+        cmp     ax, BS3TEXT16
+        je      .bs3text16
+        cmp     ax, BS3X0TEXT16
+        je      .bs3x0text16
+        cmp     ax, BS3X1TEXT16
+        je      .bs3x1text16
+        extern  BS3_CMN_NM(Bs3Panic)
+        call    BS3_CMN_NM(Bs3Panic)
+        jmp     .return
+
+.bs3x1text16:
+        mov     ax, BS3_SEL_X1TEXT16_CS
+        jmp     .return
+.bs3x0text16:
+        mov     ax, BS3_SEL_X0TEXT16_CS
+        jmp     .return
+.bs3text16:
+        mov     ax, BS3_SEL_R0_CS16
+.return:
+        pop     xBP
+        BS3_CALL_CONV_EPILOG 1
+        BS3_HYBRID_RET
+BS3_PROC_END_CMN   Bs3SelRealModeCodeToProtMode
+
+;
+; We may be using the near code in some critical code paths, so don't
+; penalize it.
+;
+BS3_CMN_FAR_STUB   Bs3SelRealModeCodeToProtMode, 2
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-common.mac
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-common.mac	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-common.mac	(revision 60539)
@@ -26,4 +26,10 @@
 
 
+%define BS3_BEGIN_TEXT16_WITHOUT_GROUP
+%define BS3_BEGIN_DATA16_WITHOUT_GROUP
+%define BS3_BEGIN_RMTEXT16_WITHOUT_GROUP
+%define BS3_BEGIN_X0TEXT16_WITHOUT_GROUP
+%define BS3_BEGIN_X1TEXT16_WITHOUT_GROUP
+
 %include "bs3kit.mac"
 
@@ -64,23 +70,15 @@
 .after_eye_catcher:
 
-%ifdef ASM_FORMAT_ELF
-section BS3TEXT16_NEARSTUBS align=1 progbits alloc exec nowrite
-section BS3TEXT16_FARSTUBS  align=1 progbits alloc exec nowrite
-section BS3TEXT16_END       align=1 progbits alloc exec nowrite
-%else
 section _TEXT               align=2 CLASS=BS3CLASS16CODE PUBLIC USE16
 section BS3TEXT16_NEARSTUBS align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
 section BS3TEXT16_FARSTUBS  align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
 section BS3TEXT16_END       align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
-%endif
 
 BS3_GLOBAL_DATA Bs3Text16_EndOfSegment, 0
 
-%ifndef ASM_FORMAT_ELF
- %ifndef BS3_IS_DOS_EXE
+%ifndef BS3_IS_DOS_EXE
 GROUP CGROUP16 BS3TEXT16 _TEXT BS3TEXT16_NEARSTUBS BS3TEXT16_FARSTUBS BS3TEXT16_END
- %else
+%else
 GROUP CGROUP16 BEGTEXT BS3TEXT16 _TEXT BS3TEXT16_NEARSTUBS BS3TEXT16_FARSTUBS BS3TEXT16_END
- %endif
 %endif
 
@@ -89,5 +87,4 @@
 ; 16-bit data
 ;
-%define BS3_BEGIN_DATA16_WITHOUT_GROUP
 BS3_BEGIN_DATA16
 BS3_GLOBAL_DATA Bs3Data16_StartOfSegment, 0
@@ -102,23 +99,25 @@
     dd  BS3_DATA_NM(Bs3Data64_EndOfSegment) wrt CGROUP16
 BS3_GLOBAL_DATA Bs3Text16_Size, 2
-    dd  BS3_DATA_NM(Bs3Text16_EndOfSegment) wrt CGROUP16
-
-%ifdef ASM_FORMAT_ELF
-section BS3DATA16CONST  align=2   progbits alloc noexec write
-section BS3DATA16CONST2 align=2   progbits alloc noexec write
-section BS3DATA16_DATA  align=2   progbits alloc noexec write
-section BS3DATA16_END   align=2   progbits alloc noexec write
-%else
+    dw  BS3_DATA_NM(Bs3Text16_EndOfSegment) wrt CGROUP16
+BS3_GLOBAL_DATA Bs3X0Text16_Size, 2
+    dw  BS3_DATA_NM(Bs3X0Text16_EndOfSegment) wrt BS3GROUPX0TEXT16
+BS3_GLOBAL_DATA Bs3X1Text16_Size, 2
+    dw  BS3_DATA_NM(Bs3X1Text16_EndOfSegment) wrt BS3GROUPX1TEXT16
+BS3_GLOBAL_DATA Bs3X0Text16_FlatAddr, 4
+    dd  BS3_DATA_NM(Bs3X0Text16_StartOfSegment) wrt BS3FLAT
+BS3_GLOBAL_DATA Bs3X1Text16_FlatAddr, 4
+    dd  BS3_DATA_NM(Bs3X1Text16_StartOfSegment) wrt BS3FLAT
+
 section BS3DATA16CONST  align=2   CLASS=BS3KIT_CLASS_DATA16 PUBLIC USE16
 section BS3DATA16CONST2 align=2   CLASS=BS3KIT_CLASS_DATA16 PUBLIC USE16
 section BS3DATA16_DATA  align=2   CLASS=BS3KIT_CLASS_DATA16 PUBLIC USE16
- %ifdef BS3_IS_DOS_EXE
+%ifdef BS3_IS_DOS_EXE
 section _NULL           align=16  CLASS=BEGDATA  PUBLIC USE16
 section _AFTERNULL      align=2   CLASS=BEGDATA  PUBLIC USE16
- %endif
+%endif
 section CONST           align=2   CLASS=DATA     PUBLIC USE16
 section CONST2          align=2   CLASS=DATA     PUBLIC USE16
 section _DATA           align=2   CLASS=DATA     PUBLIC USE16
- %ifdef BS3_IS_DOS_EXE
+%ifdef BS3_IS_DOS_EXE
 section XIB             align=1   CLASS=DATA     PUBLIC USE16
 section XI              align=1   CLASS=DATA     PUBLIC USE16
@@ -127,21 +126,19 @@
 section YI              align=1   CLASS=DATA     PUBLIC USE16
 section YIE             align=1   CLASS=DATA     PUBLIC USE16
- %endif
+%endif
 section STRINGS         align=2   CLASS=DATA     PUBLIC USE16
 section DATA            align=2   CLASS=DATA     PUBLIC USE16
 section _BSS            align=2   CLASS=BS3KIT_CLASS_BSS16 PUBLIC USE16
 section BSS             align=2   CLASS=BS3KIT_CLASS_BSS16 PUBLIC USE16
- %ifdef BS3_IS_DOS_EXE
+%ifdef BS3_IS_DOS_EXE
 section STACK           align=16  CLASS=STACK    STACK  USE16
- %endif
+%endif
 section BS3DATA16_END   align=2   CLASS=BS3KIT_CLASS_BSS16 PUBLIC USE16
-%endif
 
 BS3_GLOBAL_DATA Bs3Data16_EndOfSegment, 0
 
-%ifndef ASM_FORMAT_ELF
- %ifndef BS3_IS_DOS_EXE
+%ifndef BS3_IS_DOS_EXE
 GROUP BS3KIT_GRPNM_DATA16 BS3DATA16 BS3DATA16_DATA _DATA DATA BS3DATA16CONST CONST BS3DATA16CONST2 CONST2 STRINGS _BSS BSS BS3DATA16_END
- %else
+%else
 GROUP BS3KIT_GRPNM_DATA16 \
     _NULL _AFTERNULL \
@@ -149,5 +146,4 @@
     _BSS BSS BS3DATA16_END \
     STACK
- %endif
 %endif
 
@@ -155,21 +151,34 @@
 ; 16-bit real-mode text
 ;
-%ifdef ASM_FORMAT_ELF
-section BS3RMTEXT16_START   align=16 progbits alloc exec nowrite
-%else
 section BS3RMTEXT16_START   align=16 CLASS=BS3CLASS16RMCODE PUBLIC USE16
-%endif
 BS3_GLOBAL_DATA Bs3RmText16_StartOfSegment, 0
     db      10,13,'eye-catcher: BS3RMTEXT16',10,13
-
 BS3_BEGIN_RMTEXT16
-
-%ifdef ASM_FORMAT_ELF
-section BS3RMTEXT16_END   align=1 progbits alloc exec nowrite
-%else
 section BS3RMTEXT16_END   align=1 CLASS=BS3CLASS16RMCODE PUBLIC USE16
-%endif
-
 BS3_GLOBAL_DATA Bs3RmText16_EndOfSegment, 0
+
+
+;
+; 16-bit extra text segment #0.
+;
+section BS3X0TEXT16_START   align=16 CLASS=BS3CLASS16X0CODE PUBLIC USE16
+BS3_GLOBAL_DATA Bs3X0Text16_StartOfSegment, 0
+    db      10,13,'eye-catcher: BS3X0TEXT16',10,13
+BS3_BEGIN_X0TEXT16 4
+section BS3X0TEXT16_END   align=16 CLASS=BS3CLASS16X0CODE PUBLIC USE16
+BS3_GLOBAL_DATA Bs3X0Text16_EndOfSegment, 0
+GROUP BS3GROUPX0TEXT16 BS3X0TEXT16_START BS3X0TEXT16 BS3X0TEXT16_END
+
+
+;
+; 16-bit extra text segment #1.
+;
+section BS3X1TEXT16_START   align=16 CLASS=BS3CLASS16X1CODE PUBLIC USE16
+BS3_GLOBAL_DATA Bs3X1Text16_StartOfSegment, 0
+    db      10,13,'eye-catcher: BS3X1TEXT16',10,13
+BS3_BEGIN_X1TEXT16 4
+section BS3X1TEXT16_END   align=16 CLASS=BS3CLASS16X1CODE PUBLIC USE16
+BS3_GLOBAL_DATA Bs3X1Text16_EndOfSegment, 0
+GROUP BS3GROUPX1TEXT16 BS3X1TEXT16_START BS3X1TEXT16 BS3X1TEXT16_END
 
 
@@ -180,10 +189,5 @@
 BS3_GLOBAL_DATA Bs3Text32_StartOfSegment, 0
     db      10,13,'eye-catcher: BS3TEXT32',10,13
-
-%ifdef ASM_FORMAT_ELF
-section BS3TEXT32_END   align=1 progbits alloc exec nowrite
-%else
 section BS3TEXT32_END   align=1 CLASS=BS3CLASS32CODE PUBLIC USE32 FLAT
-%endif
 BS3_GLOBAL_DATA Bs3Text32_EndOfSegment, 0
 
@@ -195,10 +199,5 @@
 BS3_GLOBAL_DATA Bs3Text64_StartOfSegment, 0
     db      10,13,'eye-catcher: BS3TEXT64',10,13
-
-%ifdef ASM_FORMAT_ELF
-section BS3TEXT64_END   align=1 progbits alloc exec nowrite
-%else
 section BS3TEXT64_END   align=1 CLASS=BS3CLASS64CODE PUBLIC USE32 FLAT
-%endif
 BS3_GLOBAL_DATA Bs3Text64_EndOfSegment, 0
 
@@ -217,7 +216,4 @@
 BS3_GLOBAL_DATA Bs3Data32_StartOfSegment, 0
     db      10,13,'eye-catcher: BS3DATA32',10,13
-%ifdef ASM_FORMAT_ELF
-section BS3DATA32_END   align=16   progbits alloc noexec write
-%else
 section BS3DATA32CONST  align=16   CLASS=FAR_DATA PUBLIC USE32
 section BS3DATA32CONST2 align=16   CLASS=FAR_DATA PUBLIC USE32
@@ -225,10 +221,6 @@
 section BS3DATA32_BSS   align=16   CLASS=FAR_DATA PUBLIC USE32
 section BS3DATA32_END   align=16   CLASS=FAR_DATA PUBLIC USE32
-%endif
 BS3_GLOBAL_DATA Bs3Data32_EndOfSegment, 0
-
-%ifndef ASM_FORMAT_ELF
 GROUP BS3DATA32_GROUP BS3DATA32 BS3DATA32_DATA BS3DATA32CONST BS3DATA32CONST2 BS3DATA32_BSS BS3DATA32_END
-%endif
 
 ;
@@ -238,16 +230,9 @@
 BS3_GLOBAL_DATA Bs3Data64_StartOfSegment, 0
     db      10,13,'eye-catcher: BS3DATA64',10,13
-%ifdef ASM_FORMAT_ELF
-section BS3DATA64_END   align=16   progbits alloc noexec write
-%else
 section BS3DATA64CONST  align=16   CLASS=FAR_DATA PUBLIC USE32
 section BS3DATA64_BSS   align=16   CLASS=FAR_DATA PUBLIC USE32
 section BS3DATA64_END   align=16   CLASS=FAR_DATA PUBLIC USE32
-%endif
 BS3_GLOBAL_DATA Bs3Data64_EndOfSegment, 0
-
-%ifndef ASM_FORMAT_ELF
 GROUP BS3DATA64_GROUP BS3DATA64 BS3DATA64CONST BS3DATA64_BSS BS3DATA64_END
-%endif
 
 
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-dosexe.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-dosexe.asm	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-dosexe.asm	(revision 60539)
@@ -26,6 +26,4 @@
 
 
-%include "bs3kit.mac"
-
 ;
 ; Segment defs, grouping and related variables.
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-pe16.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-pe16.asm	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-pe16.asm	(revision 60539)
@@ -29,5 +29,4 @@
 ;*  Header Files                                                                                                                 *
 ;*********************************************************************************************************************************
-%include "bs3kit.mac"
 
 ;
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm	(revision 60539)
@@ -26,7 +26,4 @@
 
 
-
-%include "bs3kit.mac"
-
 ;
 ; Segment defs, grouping and related variables.
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModes.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModes.c	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModes.c	(revision 60539)
@@ -40,14 +40,19 @@
  * in 32-bit and 64-bit modes it is already flat.
  */
-/** @def CONV_TO_BS3TEXT16
- * Get BS3TEXT16 relative address. In 32-bit and 64-bit mode this is a flat
- * address, while in 16-bit it is alreay a BS3TEXT16 relative address.
+/** @def CONV_TO_PROT_FAR16
+ * Get a 32-bit value that makes a protected mode far 16:16 address.
+ */
+/** @def CONV_TO_RM_FAR16
+ * Get a 32-bit value that makes a real mode far 16:16 address.  In 16-bit mode
+ * this is already what we've got, except must be converted to uint32_t.
  */
 #if ARCH_BITS == 16
 # define CONV_TO_FLAT(a_fpfn)           (((uint32_t)BS3_FP_SEG(a_fpfn) << 4) + BS3_FP_OFF(a_fpfn))
-# define CONV_TO_BS3TEXT16(a_pfn)       ((uint16_t)(a_pfn))
+# define CONV_TO_PROT_FAR16(a_fpfn)     RT_MAKE_U32(BS3_FP_OFF(a_fpfn), Bs3SelRealModeCodeToProtMode(BS3_FP_SEG(a_fpfn)))
+# define CONV_TO_RM_FAR16(a_fpfn)       RT_MAKE_U32(BS3_FP_OFF(a_fpfn), BS3_FP_SEG(a_fpfn))
 #else
 # define CONV_TO_FLAT(a_fpfn)           ((uint32_t)(uintptr_t)(a_fpfn))
-# define CONV_TO_BS3TEXT16(a_pfn)       ((uint16_t)(uintptr_t)(a_pfn))
+# define CONV_TO_PROT_FAR16(a_fpfn)     Bs3SelFlatCodeToProtFar16((uint32_t)(uintptr_t)(a_fpfn))
+# define CONV_TO_RM_FAR16(a_fpfn)       Bs3SelFlatCodeToRealMode( (uint32_t)(uintptr_t)(a_fpfn))
 #endif
 
@@ -56,24 +61,24 @@
 *   Assembly Symbols                                                                                                             *
 *********************************************************************************************************************************/
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInRM)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE16)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInRM)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE16)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE16_32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE16_V86)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE16_V86)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE32_16)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPEV86)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP16)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPE32_16)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPEV86)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP16)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP16_32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP16_V86)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP16_V86)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP32_16)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPPV86)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE16)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPP32_16)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPPV86)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE16)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE16_32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE16_V86)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE16_V86)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE32)(uint32_t uFlatAddrCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE32_16)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAEV86)(uint16_t offCallback);
-BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInLM16)(uint16_t offCallback);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAE32_16)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInPAEV86)(uint32_t uCallbackFarPtr);
+BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInLM16)(uint32_t uCallbackFarPtr);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInLM32)(uint32_t uFlatAddrCallback);
 BS3_DECL(uint8_t) TMPL_NM(Bs3TestCallDoerInLM64)(uint32_t uFlatAddrCallback);
@@ -210,5 +215,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_rm);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInRM)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoRM));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInRM)(CONV_TO_RM_FAR16(paEntries[i].pfnDoRM));
             CHECK_RESULT(g_szBs3ModeName_rm);
         }
@@ -227,5 +232,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pe16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPE16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPE16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPE16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPE16));
             CHECK_RESULT(g_szBs3ModeName_pe16);
         }
@@ -247,5 +252,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pe16_v86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPE16_V86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPE16_V86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPE16_V86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPE16_V86));
             CHECK_RESULT(g_szBs3ModeName_pe16_v86);
         }
@@ -261,5 +266,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pe32_16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPE32_16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPE32_16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPE32_16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPE32_16));
             CHECK_RESULT(g_szBs3ModeName_pe32_16);
         }
@@ -268,5 +273,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pev86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPEV86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPEV86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPEV86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPEV86));
             CHECK_RESULT(g_szBs3ModeName_pev86);
         }
@@ -278,5 +283,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pp16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPP16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPP16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPP16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPP16));
             CHECK_RESULT(g_szBs3ModeName_pp16);
         }
@@ -292,5 +297,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pp16_v86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPP16_V86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPP16_V86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPP16_V86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPP16_V86));
             CHECK_RESULT(g_szBs3ModeName_pp16_v86);
         }
@@ -306,5 +311,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pp32_16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPP32_16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPP32_16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPP32_16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPP32_16));
             CHECK_RESULT(g_szBs3ModeName_pp32_16);
         }
@@ -313,5 +318,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_ppv86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPPV86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPPV86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPPV86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPPV86));
             CHECK_RESULT(g_szBs3ModeName_ppv86);
         }
@@ -330,5 +335,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pae16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPAE16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPAE16));
             CHECK_RESULT(g_szBs3ModeName_pae16);
         }
@@ -344,5 +349,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pae16_v86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE16_V86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPAE16_V86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE16_V86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPAE16_V86));
             CHECK_RESULT(g_szBs3ModeName_pae16_v86);
         }
@@ -358,5 +363,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_pae32_16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE32_16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPAE32_16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPAE32_16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoPAE32_16));
             CHECK_RESULT(g_szBs3ModeName_pae32_16);
         }
@@ -365,5 +370,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_paev86);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInPAEV86)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoPAEV86));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInPAEV86)(CONV_TO_RM_FAR16(paEntries[i].pfnDoPAEV86));
             CHECK_RESULT(g_szBs3ModeName_paev86);
         }
@@ -382,5 +387,5 @@
         {
             PRE_DO_CALL(g_szBs3ModeName_lm16);
-            bErrNo = TMPL_NM(Bs3TestCallDoerInLM16)(CONV_TO_BS3TEXT16(paEntries[i].pfnDoLM16));
+            bErrNo = TMPL_NM(Bs3TestCallDoerInLM16)(CONV_TO_PROT_FAR16(paEntries[i].pfnDoLM16));
             CHECK_RESULT(g_szBs3ModeName_lm16);
         }
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModesHlp.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModesHlp.asm	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-mode-TestDoModesHlp.asm	(revision 60539)
@@ -219,5 +219,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -229,5 +230,11 @@
         mov     cx, BS3_MODE_RM
         push    cx
-        call    ax
+        push    cs
+        mov     cx, .return
+        push    cx
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -253,5 +260,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -262,5 +270,10 @@
 
         push    BS3_MODE_PE16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -303,5 +316,6 @@
         jmp     TMPL_NM(bs3TestCallDoerPrologue)
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -312,5 +326,10 @@
 
         push    BS3_MODE_PE16_V86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -355,5 +374,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -364,5 +384,10 @@
 
         push    BS3_MODE_PE32_16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -383,5 +408,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -392,5 +418,10 @@
 
         push    BS3_MODE_PEV86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -417,5 +448,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -426,5 +458,10 @@
 
         push    BS3_MODE_PP16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -468,5 +505,6 @@
         jmp     TMPL_NM(bs3TestCallDoerPrologue)
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -477,5 +515,10 @@
 
         push    BS3_MODE_PP16_V86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -520,5 +563,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -529,5 +573,10 @@
 
         push    BS3_MODE_PP32_16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -548,5 +597,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -557,5 +607,10 @@
 
         push    BS3_MODE_PPV86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -582,5 +637,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -591,5 +647,10 @@
 
         push    BS3_MODE_PAE16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -633,5 +694,6 @@
         jmp     TMPL_NM(bs3TestCallDoerPrologue)
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -642,5 +704,10 @@
 
         push    BS3_MODE_PAE16_V86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -685,5 +752,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -694,5 +762,10 @@
 
         push    BS3_MODE_PAE32_16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -713,5 +786,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -722,5 +796,10 @@
 
         push    BS3_MODE_PAEV86
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
@@ -747,5 +826,6 @@
 BS3_SET_BITS TMPL_BITS
 .doit:
-        mov     ax, [xBP + xCB*2]       ; Load function pointer.
+        mov     ax, [xBP + xCB*2]       ; Load far function pointer.
+        mov     dx, [xBP + xCB*2 + 2]
 
         ; Mode switch, make the call, switch back.
@@ -756,5 +836,10 @@
 
         push    BS3_MODE_LM16
-        call    ax
+        push    cs
+        push    .return
+        push    dx
+        push    ax
+        retf
+.return:
 
         STRICT_SAVE_REGS
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitAll.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitAll.c	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitAll.c	(revision 60539)
@@ -43,4 +43,5 @@
     Bs3CpuDetect_rm();
     Bs3InitMemory_rm();
+    Bs3InitGdt_rm();
 
     ASMIntDisable();
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitGdt.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitGdt.c	(revision 60539)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-rm-InitGdt.c	(revision 60539)
@@ -0,0 +1,54 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3InitGdt
+ */
+
+/*
+ * Copyright (C) 2007-2016 Oracle Corporation
+ *
+ * This file is part of VirtualBox Open Source Edition (OSE), as
+ * available from http://www.virtualbox.org. This file is free software;
+ * you can redistribute it and/or modify it under the terms of the GNU
+ * General Public License (GPL) as published by the Free Software
+ * Foundation, in version 2 as it comes in the "COPYING" file of the
+ * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
+ * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
+ *
+ * The contents of this file may alternatively be used under the terms
+ * of the Common Development and Distribution License Version 1.0
+ * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
+ * VirtualBox OSE distribution, in which case the provisions of the
+ * CDDL are applicable instead of those of the GPL.
+ *
+ * You may elect to license modified versions of this file under the
+ * terms and conditions of either the GPL or the CDDL or both.
+ */
+
+/*********************************************************************************************************************************
+*   Header Files                                                                                                                 *
+*********************************************************************************************************************************/
+#define BS3_USE_RM_TEXT_SEG 1
+#include "bs3kit-template-header.h"
+#include <iprt/asm.h>
+
+#ifdef __WATCOMC__
+# pragma code_seg("BS3RMTEXT16", "BS3CLASS16RMCODE")
+#endif
+
+
+/*********************************************************************************************************************************
+*   Global Variables                                                                                                             *
+*********************************************************************************************************************************/
+
+
+BS3_DECL_FAR(void) Bs3InitGdt_rm(void)
+{
+    Bs3Gdte_X0TEXT16_CS.Gen.u16LimitLow = Bs3X0Text16_Size - 1;
+    Bs3Gdte_X1TEXT16_CS.Gen.u16LimitLow = Bs3X0Text16_Size - 1;
+    Bs3Gdte_X0TEXT16_CS.Gen.u16BaseLow  = (uint16_t)Bs3X0Text16_FlatAddr;
+    Bs3Gdte_X1TEXT16_CS.Gen.u16BaseLow  = (uint16_t)Bs3X1Text16_FlatAddr;
+    Bs3Gdte_X0TEXT16_CS.Gen.u8BaseHigh1 = (uint8_t)(Bs3X0Text16_FlatAddr >> 16);
+    Bs3Gdte_X1TEXT16_CS.Gen.u8BaseHigh1 = (uint8_t)(Bs3X1Text16_FlatAddr >> 16);
+}
+
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-system-data.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-system-data.asm	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-system-data.asm	(revision 60539)
@@ -178,8 +178,12 @@
         dw  00000h, 00000h, 00000h, 00000h      ; Entry 0d8h - currently unused
         dw  00000h, 00000h, 00000h, 00000h      ; Entry 0e0h - currently unused
-        dw  00000h, 00000h, 00000h, 00000h      ; Entry 0e8h - currently unused
-        dw  00000h, 00000h, 00000h, 00000h      ; Entry 0f0h - currently unused
 
         ; Misc selectors.
+BS3_GLOBAL_DATA Bs3Gdte_X0TEXT16_CS, 8          ; Entry 0e8h
+        dw  0fffeh, 00000h                      ; 16-bit conforming code (read+exec) segment, accessed. Will be finalized at startup.
+        dw  09f00h, 00000h
+BS3_GLOBAL_DATA Bs3Gdte_X1TEXT16_CS, 8          ; Entry 0f0h
+        dw  0fffeh, 00000h                      ; 16-bit conforming code (read+exec) segment, accessed. Will be finalized at startup.
+        dw  09f00h, 00000h
 BS3_GLOBAL_DATA Bs3Gdte_R0_MMIO16, 8            ; Entry 0f8h
         dw  0ffffh, 00000h, 09310h, 00000h      ; 16-bit VMMDev MMIO segment with base 0100000h.
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-define.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-define.h	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-define.h	(revision 60539)
@@ -60,6 +60,9 @@
 #define Bs3RegCtxRestore                        BS3_CMN_MANGLER(Bs3RegCtxRestore)
 #define Bs3RegCtxSave                           BS3_CMN_MANGLER(Bs3RegCtxSave)
+#define Bs3SelFlatCodeToRealMode                BS3_CMN_MANGLER(Bs3SelFlatCodeToRealMode)
+#define Bs3SelFlatCodeToProtFar16               BS3_CMN_MANGLER(Bs3SelFlatCodeToProtFar16)
 #define Bs3SelFar32ToFlat32                     BS3_CMN_MANGLER(Bs3SelFar32ToFlat32)
 #define Bs3SelProtFar32ToFlat32                 BS3_CMN_MANGLER(Bs3SelProtFar32ToFlat32)
+#define Bs3SelRealModeCodeToProtMode            BS3_CMN_MANGLER(Bs3SelRealModeCodeToProtMode)
 #define Bs3Shutdown                             BS3_CMN_MANGLER(Bs3Shutdown)
 #define Bs3SlabAlloc                            BS3_CMN_MANGLER(Bs3SlabAlloc)
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-undef.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-undef.h	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit-mangling-code-undef.h	(revision 60539)
@@ -1,5 +1,5 @@
 /* $Id$ */
 /** @file
- * BS3Kit - Undefining function mangling - automatically generated by bs3kit-mangling-functions-undef.h in Makefile.
+ * BS3Kit - Undefining function mangling - automatically generated by the bs3kit-mangling-code-undef.h makefile rule.
  */
 
@@ -60,6 +60,9 @@
 #undef Bs3RegCtxRestore
 #undef Bs3RegCtxSave
+#undef Bs3SelFlatCodeToRealMode
+#undef Bs3SelFlatCodeToProtFar16
 #undef Bs3SelFar32ToFlat32
 #undef Bs3SelProtFar32ToFlat32
+#undef Bs3SelRealModeCodeToProtMode
 #undef Bs3Shutdown
 #undef Bs3SlabAlloc
@@ -105,4 +108,5 @@
 #undef Bs3TrapRmV86SetGate
 #undef Bs3TrapSetHandler
+#undef Bs3TrapSetJmp
 #undef Bs3TrapSetJmpAndRestore
 #undef Bs3TrapUnsetJmp
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 60539)
@@ -228,4 +228,6 @@
 #define BS3_SEL_TSS64_IOBP          0x00a0 /**< The 64-bit TSS selector. */
 
+#define BS3_SEL_X0TEXT16_CS         0x00e8 /**< Conforming code selector for accessing the BS3X0TEXT16 segment. Runtime config. */
+#define BS3_SEL_X1TEXT16_CS         0x00f0 /**< Conforming code selector for accessing the BS3X0TEXT16 segment. Runtime config. */
 #define BS3_SEL_VMMDEV_MMIO16       0x00f8 /**< Selector for accessing the VMMDev MMIO segment at 0100000h from 16-bit code. */
 
@@ -554,5 +556,4 @@
  *
  * @param   a_Name      The name of the function or global variable.
- * @todo fix code vs data issue with _f16
  */
 #define BS3_CMN_NM(a_Name)      RT_CONCAT3(a_Name,_c,ARCH_BITS)
@@ -704,4 +705,6 @@
 extern X86DESC BS3_FAR_DATA Bs3Gdte_Tss64Spare1;            /**< @see BS3_SEL_TSS64_SPARE1 */
 extern X86DESC BS3_FAR_DATA Bs3Gdte_Tss64Iobp;              /**< @see BS3_SEL_TSS64_IOBP */
+extern X86DESC BS3_FAR_DATA Bs3Gdte_X0TEXT16_CS;            /**< @see BS3_SEL_X0TEXT16_CS */
+extern X86DESC BS3_FAR_DATA Bs3Gdte_X1TEXT16_CS;            /**< @see BS3_SEL_X1TEXT16_CS */
 extern X86DESC BS3_FAR_DATA Bs3Gdte_R0_MMIO16;              /**< @see BS3_SEL_VMMDEV_MMIO16 */
 
@@ -923,4 +926,27 @@
 extern uint8_t  BS3_FAR_DATA Bs3Data16_EndOfSegment;
 
+/** Start of the BS3RMTEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3RmText16_StartOfSegment;
+/** End of the BS3RMTEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3RmText16_EndOfSegment;
+
+/** Start of the BS3X0TEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3X0Text16_StartOfSegment;
+/** End of the BS3X0TEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3X0Text16_EndOfSegment;
+/** The size of the BS3X0TEXT16 segment.   */
+extern uint16_t BS3_FAR_DATA Bs3X0Text16_Size;
+/** The flat start address of the BS3X1TEXT16 segment.   */
+extern uint32_t BS3_FAR_DATA Bs3X0Text16_FlatAddr;
+
+/** Start of the BS3X1TEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3X1Text16_StartOfSegment;
+/** End of the BS3X1TEXT16 segment.   */
+extern uint8_t  BS3_FAR_DATA Bs3X1Text16_EndOfSegment;
+/** The size of the BS3X1TEXT16 segment.   */
+extern uint16_t BS3_FAR_DATA Bs3X1Text16_Size;
+/** The flat start address of the BS3X1TEXT16 segment.   */
+extern uint32_t BS3_FAR_DATA Bs3X1Text16_FlatAddr;
+
 /** Start of the BS3TEXT32 segment.   */
 extern uint8_t  BS3_FAR_DATA Bs3Text32_StartOfSegment;
@@ -1487,5 +1513,4 @@
 BS3_CMN_PROTO(uint32_t, Bs3SelProtFar32ToFlat32,(uint32_t off, uint16_t uSel), true);
 
-
 /**
  * Converts a current mode 32-bit far pointer to a 32-bit flat address.
@@ -1496,4 +1521,29 @@
  */
 BS3_CMN_PROTO(uint32_t, Bs3SelFar32ToFlat32,(uint32_t off, uint16_t uSel), true);
+
+/**
+ * Converts a real mode code segment to a protected mode code segment selector.
+ *
+ * @returns protected mode segment selector.
+ * @param   uRealSeg        Real mode code segment.
+ */
+BS3_CMN_PROTO(uint16_t, Bs3SelRealModeCodeToProtMode,(uint16_t uRealSel), false);
+
+/**
+ * Converts a flat code address to a real mode segment and offset.
+ *
+ * @returns Far real mode address (high 16-bit is segment, low is offset)
+ * @param   uFlatAddr       Flat code address.
+ */
+BS3_CMN_PROTO(uint32_t, Bs3SelFlatCodeToRealMode,(uint32_t uFlatAddr), false);
+
+/**
+ * Converts a flat code address to a protected mode 16-bit far pointer (ring-0).
+ *
+ * @returns Far 16-bit protected mode address (high 16-bit is segment selector,
+ *          low is segment offset).
+ * @param   uFlatAddr       Flat code address.
+ */
+BS3_CMN_PROTO(uint32_t, Bs3SelFlatCodeToProtFar16,(uint32_t uFlatAddr), false);
 
 /**
@@ -2319,28 +2369,28 @@
     const char * BS3_FAR    pszSubTest;
 
-    PFNBS3TESTDOMODE        pfnDoRM;
-
-    PFNBS3TESTDOMODE        pfnDoPE16;
+    FPFNBS3TESTDOMODE       pfnDoRM;
+
+    FPFNBS3TESTDOMODE       pfnDoPE16;
     FPFNBS3TESTDOMODE       pfnDoPE16_32;
-    PFNBS3TESTDOMODE        pfnDoPE16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPE16_V86;
     FPFNBS3TESTDOMODE       pfnDoPE32;
-    PFNBS3TESTDOMODE        pfnDoPE32_16;
-    PFNBS3TESTDOMODE        pfnDoPEV86;
-
-    PFNBS3TESTDOMODE        pfnDoPP16;
+    FPFNBS3TESTDOMODE       pfnDoPE32_16;
+    FPFNBS3TESTDOMODE       pfnDoPEV86;
+
+    FPFNBS3TESTDOMODE       pfnDoPP16;
     FPFNBS3TESTDOMODE       pfnDoPP16_32;
-    PFNBS3TESTDOMODE        pfnDoPP16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPP16_V86;
     FPFNBS3TESTDOMODE       pfnDoPP32;
-    PFNBS3TESTDOMODE        pfnDoPP32_16;
-    PFNBS3TESTDOMODE        pfnDoPPV86;
-
-    PFNBS3TESTDOMODE        pfnDoPAE16;
+    FPFNBS3TESTDOMODE       pfnDoPP32_16;
+    FPFNBS3TESTDOMODE       pfnDoPPV86;
+
+    FPFNBS3TESTDOMODE       pfnDoPAE16;
     FPFNBS3TESTDOMODE       pfnDoPAE16_32;
-    PFNBS3TESTDOMODE        pfnDoPAE16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPAE16_V86;
     FPFNBS3TESTDOMODE       pfnDoPAE32;
-    PFNBS3TESTDOMODE        pfnDoPAE32_16;
-    PFNBS3TESTDOMODE        pfnDoPAEV86;
-
-    PFNBS3TESTDOMODE        pfnDoLM16;
+    FPFNBS3TESTDOMODE       pfnDoPAE32_16;
+    FPFNBS3TESTDOMODE       pfnDoPAEV86;
+
+    FPFNBS3TESTDOMODE       pfnDoLM16;
     FPFNBS3TESTDOMODE       pfnDoLM32;
     FPFNBS3TESTDOMODE       pfnDoLM64;
@@ -2380,5 +2430,5 @@
 /** A set of standard protypes to go with #BS3TESTMODEENTRY_CMN. */
 #define BS3TESTMODE_PROTOTYPES_CMN(a_BaseNm) \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _c16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _c16); \
     FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _c32); \
     FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _c64)
@@ -2414,26 +2464,26 @@
 /** A set of standard protypes to go with #BS3TESTMODEENTRY_MODE. */
 #define BS3TESTMODE_PROTOTYPES_MODE(a_BaseNm) \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _rm); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pe16); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pe16_32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pe16_v86); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pe32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pe32_16); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pev86); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pp16); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pp16_32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pp16_v86); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pp32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pp32_16); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _ppv86); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pae16); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pae16_32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pae16_v86); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _pae32); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _pae32_16); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _paev86); \
-    FNBS3TESTDOMODE                 RT_CONCAT(a_BaseNm, _lm16); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _lm32); \
-    FNBS3TESTDOMODE BS3_FAR_CODE    RT_CONCAT(a_BaseNm, _lm64)
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _rm); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pe16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pe16_32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pe16_v86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pe32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pe32_16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pev86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pp16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pp16_32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pp16_v86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pp32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pp32_16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _ppv86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pae16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pae16_32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pae16_v86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pae32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _pae32_16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _paev86); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _lm16); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _lm32); \
+    FNBS3TESTDOMODE BS3_FAR_CODE RT_CONCAT(a_BaseNm, _lm64)
 
 /** @} */
@@ -2451,4 +2501,9 @@
  */
 BS3_DECL_FAR(void) Bs3InitMemory_rm(void);
+
+/**
+ * Initialized the X0TEXT16 and X1TEXT16 GDT entries.
+ */
+BS3_DECL_FAR(void) Bs3InitGdt_rm(void);
 
 
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.mac
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.mac	(revision 60538)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.mac	(revision 60539)
@@ -317,11 +317,19 @@
 
 
-%macro BS3_BEGIN_TEXT16 0
+%macro BS3_BEGIN_TEXT16 0-1 2
  %ifndef  BS3_BEGIN_TEXT16_NOT_FIRST
   %define BS3_BEGIN_TEXT16_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3TEXT16 align=2 progbits alloc exec nowrite
-  %else
-        section BS3TEXT16 align=2 CLASS=BS3CLASS16CODE PUBLIC USE16
+        section BS3TEXT16 align=%1 CLASS=BS3CLASS16CODE PUBLIC USE16
+  %ifndef BS3_BEGIN_TEXT16_WITHOUT_GROUP ; bs3-first-common.mac trick.
+   %ifndef BS3_BEGIN_TEXT16_NEARSTUBS_NOT_FIRST
+   %define BS3_BEGIN_TEXT16_NEARSTUBS_NOT_FIRST
+        section BS3TEXT16_NEARSTUBS align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
+   %endif
+   %ifndef BS3_BEGIN_TEXT16_FARSTUBS_NOT_FIRST
+   %define BS3_BEGIN_TEXT16_FARSTUBS_NOT_FIRST
+        section BS3TEXT16_FARSTUBS align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
+   %endif
+        GROUP CGROUP16 BS3TEXT16 BS3TEXT16_NEARSTUBS BS3TEXT16_FARSTUBS
+        section BS3TEXT16
   %endif
  %else
@@ -336,9 +344,5 @@
  %ifndef  BS3_BEGIN_TEXT16_NEARSTUBS_NOT_FIRST
   %define BS3_BEGIN_TEXT16_NEARSTUBS_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3TEXT16_NEARSTUBS align=1 progbits alloc exec nowrite
-  %else
         section BS3TEXT16_NEARSTUBS align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
-  %endif
  %else
         section BS3TEXT16_NEARSTUBS
@@ -352,9 +356,5 @@
  %ifndef  BS3_BEGIN_TEXT16_FARSTUBS_NOT_FIRST
   %define BS3_BEGIN_TEXT16_FARSTUBS_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3TEXT16_FARSTUBS align=1 progbits alloc exec nowrite
-  %else
         section BS3TEXT16_FARSTUBS align=1 CLASS=BS3CLASS16CODE PUBLIC USE16
-  %endif
  %else
         section BS3TEXT16_FARSTUBS
@@ -365,11 +365,10 @@
 %endmacro
 
-%macro BS3_BEGIN_RMTEXT16 0
+%macro BS3_BEGIN_RMTEXT16 0-1 2
  %ifndef  BS3_BEGIN_RMTEXT16_NOT_FIRST
   %define BS3_BEGIN_RMTEXT16_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3RMTEXT16 align=2 progbits alloc exec nowrite
-  %else
-        section BS3RMTEXT16 align=2 CLASS=BS3CLASS16RMCODE PUBLIC USE16
+        section BS3RMTEXT16 align=%1 CLASS=BS3CLASS16RMCODE PUBLIC USE16
+  %ifndef BS3_BEGIN_RMTEXT16_WITHOUT_GROUP ; bs3-first-common.mac trick.
+        GROUP BS3GROUPRMTEXT16 BS3RMTEXT16
   %endif
  %else
@@ -381,14 +380,41 @@
 %endmacro
 
-%macro BS3_BEGIN_DATA16 0
+%macro BS3_BEGIN_X0TEXT16 0-1 2
+ %ifndef  BS3_BEGIN_X0TEXT16_NOT_FIRST
+  %define BS3_BEGIN_X0TEXT16_NOT_FIRST
+        section BS3X0TEXT16 align=%1 CLASS=BS3CLASS16X0CODE PUBLIC USE16
+  %ifndef BS3_BEGIN_X0TEXT16_WITHOUT_GROUP ; bs3-first-common.mac trick.
+        GROUP BS3GROUPX0TEXT16 BS3X0TEXT16
+  %endif
+ %else
+        section BS3X0TEXT16
+ %endif
+ %undef   BS3_CUR_SEG_BEGIN_MACRO
+ %xdefine BS3_CUR_SEG_BEGIN_MACRO   BS3_BEGIN_X0TEXT16
+        BS3_SET_BITS 16
+%endmacro
+
+%macro BS3_BEGIN_X1TEXT16 0-1 2
+ %ifndef  BS3_BEGIN_X1TEXT16_NOT_FIRST
+  %define BS3_BEGIN_X1TEXT16_NOT_FIRST
+        section BS3X1TEXT16 align=%1 CLASS=BS3CLASS16X1CODE PUBLIC USE16
+  %ifndef BS3_BEGIN_X1TEXT16_WITHOUT_GROUP ; bs3-first-common.mac trick.
+        GROUP BS3GROUPX1TEXT16 BS3X1TEXT16
+  %endif
+ %else
+        section BS3X1TEXT16
+ %endif
+ %undef   BS3_CUR_SEG_BEGIN_MACRO
+ %xdefine BS3_CUR_SEG_BEGIN_MACRO   BS3_BEGIN_X1TEXT16
+        BS3_SET_BITS 16
+%endmacro
+
+
+%macro BS3_BEGIN_DATA16 0-1 2
  %ifndef  BS3_BEGIN_DATA16_NOT_FIRST
   %define BS3_BEGIN_DATA16_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3DATA16 align=2 progbits alloc noexec write
-  %else
-        section BS3DATA16 align=2 CLASS=BS3KIT_CLASS_DATA16 PUBLIC USE16
-   %ifndef BS3_BEGIN_DATA16_WITHOUT_GROUP ; bs3-first-common.mac trick.
+        section BS3DATA16 align=%1 CLASS=BS3KIT_CLASS_DATA16 PUBLIC USE16
+  %ifndef BS3_BEGIN_DATA16_WITHOUT_GROUP ; bs3-first-common.mac trick.
     GROUP BS3KIT_GRPNM_DATA16 BS3DATA16
-   %endif
   %endif
  %else
@@ -400,12 +426,8 @@
 %endmacro
 
-%macro BS3_BEGIN_TEXT32 0
+%macro BS3_BEGIN_TEXT32 0-1 2
  %ifndef  BS3_BEGIN_TEXT32_NOT_FIRST
   %define BS3_BEGIN_TEXT32_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3TEXT32 align=1 progbits alloc exec nowrite
-  %else
-        section BS3TEXT32 align=1 CLASS=BS3CLASS32CODE PUBLIC USE32 FLAT
-  %endif
+        section BS3TEXT32 align=%1 CLASS=BS3CLASS32CODE PUBLIC USE32 FLAT
  %else
         section BS3TEXT32
@@ -416,12 +438,8 @@
 %endmacro
 
-%macro BS3_BEGIN_DATA32 0
+%macro BS3_BEGIN_DATA32 0-1 16
  %ifndef  BS3_BEGIN_DATA32_NOT_FIRST
   %define BS3_BEGIN_DATA32_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3DATA32 align=16 progbits alloc noexec write
-  %else
-        section BS3DATA32 align=16 CLASS=FAR_DATA PUBLIC USE32 ;FLAT - compiler doesn't make data flat.
-  %endif
+        section BS3DATA32 align=%1 CLASS=FAR_DATA PUBLIC USE32 ;FLAT - compiler doesn't make data flat.
  %else
         section BS3DATA32
@@ -432,12 +450,8 @@
 %endmacro
 
-%macro BS3_BEGIN_TEXT64 0
+%macro BS3_BEGIN_TEXT64 0-1 2
  %ifndef  BS3_BEGIN_TEXT64_NOT_FIRST
   %define BS3_BEGIN_TEXT64_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3TEXT64 align=1 progbits alloc exec nowrite
-  %else
-        section BS3TEXT64 align=1 CLASS=BS3CLASS64CODE PUBLIC USE32 FLAT
-  %endif
+        section BS3TEXT64 align=%1 CLASS=BS3CLASS64CODE PUBLIC USE32 FLAT
  %else
         section BS3TEXT64
@@ -448,12 +462,8 @@
 %endmacro
 
-%macro BS3_BEGIN_DATA64 0
+%macro BS3_BEGIN_DATA64 0-1 16
  %ifndef  BS3_BEGIN_DATA64_NOT_FIRST
   %define BS3_BEGIN_DATA64_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3DATA64 align=16 progbits alloc noexec write
-  %else
-        section BS3DATA64 align=16 CLASS=FAR_DATA PUBLIC USE32 ;FLAT (see DATA32)
-  %endif
+        section BS3DATA64 align=%1 CLASS=FAR_DATA PUBLIC USE32 ;FLAT (see DATA32)
  %else
         section BS3DATA64
@@ -465,12 +475,8 @@
 
 ;; The system data segment containing the GDT, TSSes and IDTs.
-%macro BS3_BEGIN_SYSTEM16 0
+%macro BS3_BEGIN_SYSTEM16 0-1 16
  %ifndef  BS3_BEGIN_SYSTEM16_NOT_FIRST
   %define BS3_BEGIN_SYSTEM16_NOT_FIRST
-  %ifdef ASM_FORMAT_ELF
-        section BS3SYSTEM16 align=16 progbits alloc noexec write
-  %else
-        section BS3SYSTEM16 align=16 CLASS=BS3SYSTEM16 PUBLIC USE16
-  %endif
+        section BS3SYSTEM16 align=%1 CLASS=BS3SYSTEM16 PUBLIC USE16
  %else
         section BS3SYSTEM16
@@ -804,4 +810,5 @@
 BS3_PROC_BEGIN_CMN %1, BS3_PBC_FAR
         CPU 8086
+        inc     bp                      ; Odd bp is far call indicator.
         push    bp
         mov     bp, sp
@@ -814,4 +821,5 @@
         add     sp, %2
         pop     bp
+        dec     bp
         retf
 BS3_PROC_END_CMN   %1
@@ -1446,4 +1454,6 @@
 %define BS3_SEL_TSS64_IOBP          00a0h ;;< The 64-bit TSS selector.
 
+%define BS3_SEL_X0TEXT16_CS         00e8h ;;< Conforming code selector for accessing the BS3X0TEXT16 segment. Runtime config.
+%define BS3_SEL_X1TEXT16_CS         00f0h ;;< Conforming code selector for accessing the BS3X0TEXT16 segment. Runtime config.
 %define BS3_SEL_VMMDEV_MMIO16       00f8h ;;< Selector for accessing the VMMDev MMIO segment at 0100000h from 16-bit code.
 
