Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 59865)
@@ -100,4 +100,9 @@
        bs3-cmn-TestData.c \
        bs3-cmn-TestInit.c \
+       bs3-cmn-TestFailed.c \
+       bs3-cmn-TestSkipped.c \
+       bs3-cmn-TestSub.c \
+       bs3-cmn-TestSubDone.c \
+       bs3-cmn-TestSubErrorCount.c \
        bs3-cmn-TestTerm.c \
 	bs3-cmn-TestSendCmdWithStr.asm \
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestData.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestData.c	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestData.c	(revision 59865)
@@ -49,4 +49,6 @@
 /** Whether we've reported the sub-test result or not. */
 bool        g_fbBs3SubTestReported = true;
+/** Whether the sub-test has been skipped or not. */
+bool        g_fbBs3SubTestSkipped = false;
 
 /** The number of sub tests. */
@@ -93,9 +95,11 @@
 };
 
+
+/** The subtest name. */
+char        g_szBs3SubTest[64];
+
 #endif /* ARCH_BITS == 16 */
 
 /** The test name. */
 const char BS3_FAR *BS3_CMN_NM(g_pszBs3Test) = NULL;
-/** The subtest name. */
-const char BS3_FAR *BS3_CMN_NM(g_pszBs3SubTest) = NULL;
 
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestFailed.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestFailed.c	(revision 59865)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestFailed.c	(revision 59865)
@@ -0,0 +1,112 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3TestFailed, Bs3TestFailedF, Bs3TestFailedV.
+ */
+
+/*
+ * 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                                                                                                                 *
+*********************************************************************************************************************************/
+#include "bs3kit-template-header.h"
+#include "bs3-cmn-test.h"
+#include <iprt/asm-amd64-x86.h>
+
+
+/**
+ * @impl_callback_method{FNBS3STRFORMATOUTPUT,
+ *      Used by Bs3TestFailedV and Bs3TestSkippedV.}
+ */
+BS3_DECL_CALLBACK(size_t) bs3TestFailedStrOutput(char ch, void BS3_FAR *pvUser)
+{
+    bool *pfNewLine = (bool *)pvUser;
+
+    /*
+     * VMMDev first.
+     */
+    if (BS3_DATA_NM(g_fbBs3VMMDevTesting))
+        ASMOutU8(VMMDEV_TESTING_IOPORT_DATA, ch);
+
+    /*
+     * Console next.
+     */
+    if (ch != 0)
+    {
+        if (ch != '\n')
+        {
+            Bs3PrintChr(ch);
+            *pfNewLine = false;
+        }
+        else
+        {
+            Bs3PrintStr("\r\n");
+            *pfNewLine = true;
+        }
+    }
+    /* We're called with '\0' to indicate end-of-string. Supply trailing
+       newline if necessary. */
+    else if (!*pfNewLine)
+        Bs3PrintStr("\r\n");
+
+    return 1;
+}
+
+
+/**
+ * Equivalent to RTTestIFailedV.
+ */
+BS3_DECL(void) Bs3TestFailedV(const char *pszFormat, va_list va)
+{
+    bool fNewLine;
+
+    if (!++BS3_DATA_NM(g_cusBs3TestErrors))
+        BS3_DATA_NM(g_cusBs3TestErrors)++;
+
+    if (BS3_DATA_NM(g_fbBs3VMMDevTesting))
+        ASMOutU32(VMMDEV_TESTING_IOPORT_CMD, VMMDEV_TESTING_CMD_FAILED);
+
+    fNewLine = false;
+    Bs3StrFormatV(pszFormat, va, bs3TestFailedStrOutput, &fNewLine);
+}
+
+
+/**
+ * Equivalent to RTTestIFailedF.
+ */
+BS3_DECL(void) Bs3TestFailedF(const char *pszFormat, ...)
+{
+    va_list va;
+    va_start(va, pszFormat);
+    Bs3TestFailedV(pszFormat, va);
+    va_end(va);
+}
+
+
+/**
+ * Equivalent to RTTestIFailed.
+ */
+BS3_DECL(void) Bs3TestFailed(const char *pszMessage)
+{
+    Bs3TestFailedF("%s", pszMessage);
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestInit.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestInit.c	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestInit.c	(revision 59865)
@@ -26,4 +26,7 @@
 
 
+/*********************************************************************************************************************************
+*   Header Files                                                                                                                 *
+*********************************************************************************************************************************/
 #include "bs3kit-template-header.h"
 #include "bs3-cmn-test.h"
@@ -35,18 +38,18 @@
  * @param   pszTest         The test name.
  */
-#undef Bs3TestInit
-BS3_DECL(void) BS3_CMN_NM(Bs3TestInit)(const char BS3_FAR *pszTest)
+BS3_DECL(void) Bs3TestInit(const char BS3_FAR *pszTest)
 {
     /*
      * Initialize the globals.
      */
-    BS3_CMN_NM(g_pszBs3Test)    = pszTest;
-    BS3_CMN_NM(g_pszBs3SubTest) = NULL;
-    g_cusBs3TestErrors          = 0;
-    g_cusBs3SubTestAtErrors     = 0;
-    g_fbBs3SubTestReported      = true;
-    g_cusBs3SubTests            = 0;
-    g_cusBs3SubTestsFailed      = 0;
-    g_fbBs3VMMDevTesting        = bs3TestIsVmmDevTestingPresent();
+    BS3_CMN_NM(g_pszBs3Test)                 = pszTest;
+    BS3_DATA_NM(g_szBs3SubTest)[0]           = '\0';
+    BS3_DATA_NM(g_cusBs3TestErrors)          = 0;
+    BS3_DATA_NM(g_cusBs3SubTestAtErrors)     = 0;
+    BS3_DATA_NM(g_fbBs3SubTestReported)      = true;
+    BS3_DATA_NM(g_fbBs3SubTestSkipped)       = true;
+    BS3_DATA_NM(g_cusBs3SubTests)            = 0;
+    BS3_DATA_NM(g_cusBs3SubTestsFailed)      = 0;
+    BS3_DATA_NM(g_fbBs3VMMDevTesting)        = bs3TestIsVmmDevTestingPresent();
 
     /*
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSkipped.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSkipped.c	(revision 59865)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSkipped.c	(revision 59865)
@@ -0,0 +1,71 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3TestSkipped
+ */
+
+/*
+ * 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                                                                                                                 *
+*********************************************************************************************************************************/
+#include "bs3kit-template-header.h"
+#include "bs3-cmn-test.h"
+
+
+/**
+ * Equivalent to RTTestSkippedV.
+ */
+BS3_DECL(void) Bs3TestSkippedV(const char *pszFormat, va_list va)
+{
+    /* Just mark it as skipped and deal with it when the sub-test is done. */
+    BS3_DATA_NM(g_fbBs3SubTestSkipped) = true;
+
+    /* The reason why it was skipp is optional. */
+    if (pszFormat)
+    {
+        bool fNewLine = false;
+        Bs3StrFormatV(pszFormat, va, bs3TestFailedStrOutput, &fNewLine);
+    }
+}
+
+
+/**
+ * Equivalent to RTTestSkipped.
+ */
+BS3_DECL(void) Bs3TestSkippedF(const char *pszFormat, ...)
+{
+    va_list va;
+    va_start(va, pszFormat);
+    Bs3TestSkippedV(pszFormat, va);
+    va_end(va);
+}
+
+
+/**
+ * Equivalent to RTTestSkipped.
+ */
+BS3_DECL(void) Bs3TestSkipped(const char *pszWhy)
+{
+    Bs3TestSkippedF(pszWhy ? "%s" : NULL, pszWhy);
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSub.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSub.c	(revision 59865)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSub.c	(revision 59865)
@@ -0,0 +1,88 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3TestSub, Bs3TestSubF, Bs3TestSubV.
+ */
+
+/*
+ * 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                                                                                                                 *
+*********************************************************************************************************************************/
+#include "bs3kit-template-header.h"
+#include "bs3-cmn-test.h"
+
+
+
+/**
+ * Equivalent to RTTestISubV.
+ */
+BS3_DECL(void) Bs3TestSubV(const char *pszFormat, va_list va)
+{
+    size_t cch;
+
+    /*
+     * Cleanup any previous sub-test.
+     */
+    bs3TestSubCleanup();
+
+    /*
+     * Format the sub-test name and update globals.
+     */
+    cch = Bs3StrPrintfV(BS3_DATA_NM(g_szBs3SubTest), sizeof(BS3_DATA_NM(g_szBs3SubTest)), pszFormat, va);
+    BS3_DATA_NM(g_cusBs3SubTestAtErrors) = BS3_DATA_NM(g_cusBs3TestErrors);
+    BS3_ASSERT(!BS3_DATA_NM(g_fbBs3SubTestSkipped));
+
+    /*
+     * Tell VMMDev and output to the console.
+     */
+    bs3TestSendCmdWithStr(VMMDEV_TESTING_CMD_SUB_NEW, pszFormat);
+
+    Bs3PrintStr(BS3_DATA_NM(g_szBs3SubTest));
+    Bs3PrintChr(':');
+    do
+       Bs3PrintChr(' ');
+    while (cch++ < 49);
+    Bs3PrintStr(" TESTING\n");
+}
+
+
+/**
+ * Equivalent to RTTestIFailedF.
+ */
+BS3_DECL(void) Bs3TestSubF(const char *pszFormat, ...)
+{
+    va_list va;
+    va_start(va, pszFormat);
+    Bs3TestSubV(pszFormat, va);
+    va_end(va);
+}
+
+
+/**
+ * Equivalent to RTTestISub.
+ */
+BS3_DECL(void) Bs3TestSub(const char *pszMessage)
+{
+    Bs3TestSubF("%s", pszMessage);
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubDone.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubDone.c	(revision 59865)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubDone.c	(revision 59865)
@@ -0,0 +1,43 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3TestSubDone.
+ */
+
+/*
+ * 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                                                                                                                 *
+*********************************************************************************************************************************/
+#include "bs3kit-template-header.h"
+#include "bs3-cmn-test.h"
+
+
+
+/**
+ * Equivalent to RTTestISubDone.
+ */
+BS3_DECL(void) Bs3TestSubDone(void)
+{
+    bs3TestSubCleanup();
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubErrorCount.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubErrorCount.c	(revision 59865)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestSubErrorCount.c	(revision 59865)
@@ -0,0 +1,43 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3TestSubErrorCount.
+ */
+
+/*
+ * 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                                                                                                                 *
+*********************************************************************************************************************************/
+#include "bs3kit-template-header.h"
+#include "bs3-cmn-test.h"
+
+
+
+/**
+ * Equivalent to RTTestSubErrorCount.
+ */
+BS3_DECL(uint16_t) Bs3TestSubErrorCount(void)
+{
+    return BS3_DATA_NM(g_cusBs3TestErrors) - BS3_DATA_NM(g_cusBs3SubTestAtErrors);
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestTerm.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestTerm.c	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-TestTerm.c	(revision 59865)
@@ -26,6 +26,50 @@
 
 
+/*********************************************************************************************************************************
+*   Header Files                                                                                                                 *
+*********************************************************************************************************************************/
 #include "bs3kit-template-header.h"
 #include "bs3-cmn-test.h"
+
+
+
+/**
+ * Equivalent to rtTestSubCleanup + rtTestSubTestReport.
+ */
+BS3_DECL(void) bs3TestSubCleanup(void)
+{
+    if (BS3_DATA_NM(g_szBs3SubTest)[0] != '\0')
+    {
+        if (!BS3_DATA_NM(g_fbBs3SubTestReported))
+        {
+            size_t   cch;
+            uint16_t cErrors = BS3_DATA_NM(g_cusBs3TestErrors) - BS3_DATA_NM(g_cusBs3SubTestAtErrors);
+
+            /* Tell VMMDev. */
+            bs3TestSendCmdWithU32(VMMDEV_TESTING_CMD_SUB_DONE, cErrors);
+
+            /* Print result to the console. */
+            Bs3PrintStr(BS3_DATA_NM(g_szBs3SubTest));
+            Bs3PrintChr(':');
+            cch = Bs3StrLen(BS3_DATA_NM(g_szBs3SubTest));
+            do
+                Bs3PrintChr(' ');
+            while (cch++ < 49);
+
+            if (!cErrors)
+                Bs3PrintStr(!BS3_DATA_NM(g_fbBs3SubTestSkipped) ? "PASSED\n" : "SKIPPED\n");
+            else
+            {
+                BS3_DATA_NM(g_cusBs3SubTestsFailed)++;
+                Bs3Printf("FAILED (%u errors)\n", BS3_DATA_NM(g_szBs3SubTest), cErrors);
+            }
+        }
+
+        /* Reset the sub-test. */
+        BS3_DATA_NM(g_fbBs3SubTestReported) = true;
+        BS3_DATA_NM(g_fbBs3SubTestSkipped)  = false;
+        BS3_DATA_NM(g_szBs3SubTest)[0]      = '\0';
+    }
+}
 
 
@@ -36,11 +80,7 @@
 {
     /*
-     * Close current sub-test.
+     * Close any current sub-test.
      */
-    if (BS3_CMN_NM(g_pszBs3SubTest))
-    {
-
-    }
-
+    bs3TestSubCleanup();
 
     /*
@@ -50,8 +90,9 @@
     {
         Bs3PrintStr(BS3_CMN_NM(g_pszBs3Test));
-        if (g_cusBs3TestErrors == 0)
-            Bs3Printf(": SUCCESS (%u tests)\n", g_cusBs3SubTests);
+        if (BS3_DATA_NM(g_cusBs3TestErrors) == 0)
+            Bs3Printf(": SUCCESS (%u tests)\n", BS3_DATA_NM(g_cusBs3SubTests));
         else
-            Bs3Printf(": FAILURE - %u (%u of %u tests)\n", g_cusBs3TestErrors, g_cusBs3SubTestsFailed, g_cusBs3SubTests);
+            Bs3Printf(": FAILURE - %u (%u of %u tests)\n",
+                      BS3_DATA_NM(g_cusBs3TestErrors), BS3_DATA_NM(g_cusBs3SubTestsFailed), BS3_DATA_NM(g_cusBs3SubTests));
     }
 
@@ -59,6 +100,5 @@
      * Tell VMMDev.
      */
-    bs3TestSendCmdWithU32(VMMDEV_TESTING_CMD_TERM, g_cusBs3TestErrors);
-    for (;;) { }
+    bs3TestSendCmdWithU32(VMMDEV_TESTING_CMD_TERM, BS3_DATA_NM(g_cusBs3TestErrors));
 
     BS3_CMN_NM(g_pszBs3Test) = NULL;
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-test.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-test.h	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-test.h	(revision 59865)
@@ -33,23 +33,25 @@
 
 /** Indicates whether the VMMDev is operational. */
-extern bool                 g_fbBs3VMMDevTesting;
+extern bool                 BS3_DATA_NM(g_fbBs3VMMDevTesting);
 
 /** The number of tests that have failed. */
-extern uint16_t             g_cusBs3TestErrors;
+extern uint16_t             BS3_DATA_NM(g_cusBs3TestErrors);
 
 /** The start error count of the current subtest. */
-extern uint16_t             g_cusBs3SubTestAtErrors;
+extern uint16_t             BS3_DATA_NM(g_cusBs3SubTestAtErrors);
 
 /**  Whether we've reported the sub-test result or not. */
-extern bool                 g_fbBs3SubTestReported;
+extern bool                 BS3_DATA_NM(g_fbBs3SubTestReported);
+/** Whether the sub-test has been skipped or not. */
+extern bool                 BS3_DATA_NM(g_fbBs3SubTestSkipped);
 
 /** The number of sub tests. */
-extern uint16_t             g_cusBs3SubTests;
+extern uint16_t             BS3_DATA_NM(g_cusBs3SubTests);
 
 /** The number of sub tests that failed. */
-extern uint16_t             g_cusBs3SubTestsFailed;
+extern uint16_t             BS3_DATA_NM(g_cusBs3SubTestsFailed);
 
 /** VMMDEV_TESTING_UNIT_XXX -> string */
-extern char const           g_aszBs3TestUnitNames[][16];
+extern char const           BS3_DATA_NM(g_aszBs3TestUnitNames)[][16];
 
 /** The test name. */
@@ -57,8 +59,7 @@
 extern const char          *g_pszBs3Test_c32;
 extern const char          *g_pszBs3Test_c64;
+
 /** The subtest name. */
-extern const char BS3_FAR  *g_pszBs3SubTest_c16;
-extern const char          *g_pszBs3SubTest_c32;
-extern const char          *g_pszBs3SubTest_c64;
+extern char                 BS3_DATA_NM(g_szBs3SubTest)[64];
 
 
@@ -91,5 +92,4 @@
 #define bs3TestSendCmdWithU32 BS3_CMN_NM(bs3TestSendCmdWithU32) /**< Selects #bs3TestSendCmdWithU32_c16, #bs3TestSendCmdWithU32_c32 or #bs3TestSendCmdWithU32_c64. */
 
-
 /**
  * Checks if the VMMDev is configured for testing.
@@ -102,4 +102,22 @@
 #define bs3TestIsVmmDevTestingPresent BS3_CMN_NM(bs3TestIsVmmDevTestingPresent) /**< Selects #bs3TestIsVmmDevTestingPresent_c16, #bs3TestIsVmmDevTestingPresent_c32 or #bs3TestIsVmmDevTestingPresent_c64. */
 
+/**
+ * Similar to rtTestSubCleanup.
+ */
+BS3_DECL(void) bs3TestSubCleanup_c16(void);
+BS3_DECL(void) bs3TestSubCleanup_c32(void); /**< @copydoc bs3TestSubCleanup_c16 */
+BS3_DECL(void) bs3TestSubCleanup_c64(void); /**< @copydoc bs3TestSubCleanup_c16 */
+#define bs3TestSubCleanup BS3_CMN_NM(bs3TestSubCleanup) /**< Selects #bs3TestSubCleanup_c16, #bs3TestSubCleanup_c32 or #bs3TestSubCleanup_c64. */
+
+/**
+ * @impl_callback_method{FNBS3STRFORMATOUTPUT,
+ *      Used by Bs3TestFailedV and Bs3TestSkippedV.
+ *
+ *      The @a pvUser parameter must point to a boolean that was initialized to false. }
+ */
+BS3_DECL_CALLBACK(size_t) bs3TestFailedStrOutput_c16(char ch, void BS3_FAR *pvUser);
+BS3_DECL_CALLBACK(size_t) bs3TestFailedStrOutput_c32(char ch, void BS3_FAR *pvUser);
+BS3_DECL_CALLBACK(size_t) bs3TestFailedStrOutput_c64(char ch, void BS3_FAR *pvUser);
+#define bs3TestFailedStrOutput BS3_CMN_NM(bs3TestFailedStrOutput) /**< Selects #bs3TestFailedStrOutput_c16, #bs3TestFailedStrOutput_c32 or #bs3TestFailedStrOutput_c64. */
 
 #endif
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 59864)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 59865)
@@ -1148,7 +1148,7 @@
  * @param   pvUser  User argument supplied to #Bs3StrFormatV.
  */
-typedef size_t BS3_CALL FNBS3STRFORMATOUTPUT(char ch, void BS3_FAR *pvUser);
+typedef BS3_DECL_CALLBACK(size_t) FNBS3STRFORMATOUTPUT(char ch, void BS3_FAR *pvUser);
 /** Pointer to an output function for #Bs3StrFormatV. */
-typedef FNBS3STRFORMATOUTPUT BS3_NEAR_CODE *PFNBS3STRFORMATOUTPUT;
+typedef FNBS3STRFORMATOUTPUT *PFNBS3STRFORMATOUTPUT;
 
 /**
@@ -1328,4 +1328,161 @@
 BS3_DECL(void) Bs3TestTerm_c64(void); /**< @copydoc Bs3TestTerm_c16 */
 #define Bs3TestTerm BS3_CMN_NM(Bs3TestTerm) /**< Selects #Bs3TestTerm_c16, #Bs3TestTerm_c32 or #Bs3TestTerm_c64. */
+
+/**
+ * Equivalent to RTTestISub.
+ */
+BS3_DECL(void) Bs3TestSub_c16(const char BS3_FAR *pszSubTest);
+BS3_DECL(void) Bs3TestSub_c32(const char BS3_FAR *pszSubTest); /**< @copydoc Bs3TestSub_c16 */
+BS3_DECL(void) Bs3TestSub_c64(const char BS3_FAR *pszSubTest); /**< @copydoc Bs3TestSub_c16 */
+#define Bs3TestSub BS3_CMN_NM(Bs3TestSub) /**< Selects #Bs3TestSub_c16, #Bs3TestSub_c32 or #Bs3TestSub_c64. */
+
+/**
+ * Equivalent to RTTestIFailedF.
+ */
+BS3_DECL(void) Bs3TestSubF_c16(const char BS3_FAR *pszFormat, ...);
+BS3_DECL(void) Bs3TestSubF_c32(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestSubF_c16 */
+BS3_DECL(void) Bs3TestSubF_c64(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestSubF_c16 */
+#define Bs3TestSubF BS3_CMN_NM(Bs3TestSubF) /**< Selects #Bs3TestSubF_c16, #Bs3TestSubF_c32 or #Bs3TestSubF_c64. */
+
+/**
+ * Equivalent to RTTestISubV.
+ */
+BS3_DECL(void) Bs3TestSubV_c16(const char BS3_FAR *pszFormat, va_list va);
+BS3_DECL(void) Bs3TestSubV_c32(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestSubV_c16 */
+BS3_DECL(void) Bs3TestSubV_c64(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestSubV_c16 */
+#define Bs3TestSubV BS3_CMN_NM(Bs3TestSubV) /**< Selects #Bs3TestSubV_c16, #Bs3TestSubV_c32 or #Bs3TestSubV_c64. */
+
+/**
+ * Equivalent to RTTestISubDone.
+ */
+BS3_DECL(void) Bs3TestSubDone_c16(void);
+BS3_DECL(void) Bs3TestSubDone_c32(void); /**< @copydoc Bs3TestSubDone_c16 */
+BS3_DECL(void) Bs3TestSubDone_c64(void); /**< @copydoc Bs3TestSubDone_c16 */
+#define Bs3TestSubDone BS3_CMN_NM(Bs3TestSubDone) /**< Selects #Bs3TestSubDone_c16, #Bs3TestSubDone_c32 or #Bs3TestSubDone_c64. */
+
+/**
+ * Equivalent to RTTestSubErrorCount.
+ */
+BS3_DECL(uint16_t) Bs3TestSubErrorCount_c16(void);
+BS3_DECL(uint16_t) Bs3TestSubErrorCount_c32(void); /**< @copydoc Bs3TestSubErrorCount_c16 */
+BS3_DECL(uint16_t) Bs3TestSubErrorCount_c64(void); /**< @copydoc Bs3TestSubErrorCount_c16 */
+#define Bs3TestSubErrorCount BS3_CMN_NM(Bs3TestSubErrorCount) /**< Selects #Bs3TestSubErrorCount_c16, #Bs3TestSubErrorCount_c32 or #Bs3TestSubErrorCount_c64. */
+
+/**
+ * Equivalent to RTTestIFailed.
+ */
+BS3_DECL(void) Bs3TestFailed_c16(const char BS3_FAR *pszMessage);
+BS3_DECL(void) Bs3TestFailed_c32(const char BS3_FAR *pszMessage); /**< @copydoc Bs3TestFailed_c16 */
+BS3_DECL(void) Bs3TestFailed_c64(const char BS3_FAR *pszMessage); /**< @copydoc Bs3TestFailed_c16 */
+#define Bs3TestFailed BS3_CMN_NM(Bs3TestFailed) /**< Selects #Bs3TestFailed_c16, #Bs3TestFailed_c32 or #Bs3TestFailed_c64. */
+
+/**
+ * Equivalent to RTTestIFailedF.
+ */
+BS3_DECL(void) Bs3TestFailedF_c16(const char BS3_FAR *pszFormat, ...);
+BS3_DECL(void) Bs3TestFailedF_c32(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestFailedF_c16 */
+BS3_DECL(void) Bs3TestFailedF_c64(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestFailedF_c16 */
+#define Bs3TestFailedF BS3_CMN_NM(Bs3TestFailedF) /**< Selects #Bs3TestFailedF_c16, #Bs3TestFailedF_c32 or #Bs3TestFailedF_c64. */
+
+/**
+ * Equivalent to RTTestIFailedV.
+ */
+BS3_DECL(void) Bs3TestFailedV_c16(const char BS3_FAR *pszFormat, va_list va);
+BS3_DECL(void) Bs3TestFailedV_c32(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestFailedV_c16 */
+BS3_DECL(void) Bs3TestFailedV_c64(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestFailedV_c16 */
+#define Bs3TestFailedV BS3_CMN_NM(Bs3TestFailedV) /**< Selects #Bs3TestFailedV_c16, #Bs3TestFailedV_c32 or #Bs3TestFailedV_c64. */
+
+/**
+ * Equivalent to RTTestISkipped.
+ *
+ * @param   pszWhy          Optional reason why it's being skipped.
+ */
+BS3_DECL(void) Bs3TestSkipped_c16(const char BS3_FAR *pszWhy);
+BS3_DECL(void) Bs3TestSkipped_c32(const char BS3_FAR *pszWhy); /**< @copydoc Bs3TestSkipped_c16 */
+BS3_DECL(void) Bs3TestSkipped_c64(const char BS3_FAR *pszWhy); /**< @copydoc Bs3TestSkipped_c16 */
+#define Bs3TestSkipped BS3_CMN_NM(Bs3TestSkipped) /**< Selects #Bs3TestSkipped_c16, #Bs3TestSkipped_c32 or #Bs3TestSkipped_c64. */
+
+/**
+ * Equivalent to RTTestISkippedF.
+ *
+ * @param   pszFormat       Optional reason why it's being skipped.
+ * @param   ...             Format arguments.
+ */
+BS3_DECL(void) Bs3TestSkippedF_c16(const char BS3_FAR *pszFormat, ...);
+BS3_DECL(void) Bs3TestSkippedF_c32(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestSkippedF_c16 */
+BS3_DECL(void) Bs3TestSkippedF_c64(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3TestSkippedF_c16 */
+#define Bs3TestSkippedF BS3_CMN_NM(Bs3TestSkippedF) /**< Selects #Bs3TestSkippedF_c16, #Bs3TestSkippedF_c32 or #Bs3TestSkippedF_c64. */
+
+/**
+ * Equivalent to RTTestISkippedV.
+ *
+ * @param   pszFormat       Optional reason why it's being skipped.
+ * @param   va              Format arguments.
+ */
+BS3_DECL(void) Bs3TestSkippedV_c16(const char BS3_FAR *pszFormat, va_list va);
+BS3_DECL(void) Bs3TestSkippedV_c32(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestSkippedV_c16 */
+BS3_DECL(void) Bs3TestSkippedV_c64(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3TestSkippedV_c16 */
+#define Bs3TestSkippedV BS3_CMN_NM(Bs3TestSkippedV) /**< Selects #Bs3TestSkippedV_c16, #Bs3TestSkippedV_c32 or #Bs3TestSkippedV_c64. */
+
+
+/**
+ * Performs the testing for the given mode.
+ *
+ * This is called with the CPU already switch to that mode.
+ *
+ * @returns 0 on success or directly Bs3TestFailed calls, non-zero to indicate
+ *          where the test when wrong.
+ * @param   bMode       The current CPU mode.
+ */
+typedef BS3_DECL_CALLBACK(uint8_t) FNBS3TESTDOMODE(uint8_t bMode);
+/** Near pointer to a test (for 16-bit code). */
+typedef FNBS3TESTDOMODE               *PFNBS3TESTDOMODE;
+/** Far pointer to a test (for 32-bit and 64-bit code, will be flatten). */
+typedef FNBS3TESTDOMODE BS3_FAR_CODE  *FPFNBS3TESTDOMODE;
+
+/**
+ * Mode sub-test entry.
+ *
+ * This can only be passed around to functions with the same bit count, as it
+ * contains function pointers.  In 16-bit mode, the 16-bit pointers are near and
+ * implies BS3TEXT16, whereas the 32-bit and 64-bit pointers are far real mode
+ * addresses that will be converted to flat address prior to calling them.
+ * Similarly, in 32-bit and 64-bit the addresses are all flat and the 16-bit
+ * ones will be converted to BS3TEXT16 based addresses prior to calling.
+ */
+typedef struct BS3TESTMODEENTRY
+{
+    const char * BS3_FAR    pszSubTest;
+
+    PFNBS3TESTDOMODE        pfnDoRM;
+
+    PFNBS3TESTDOMODE        pfnDoPE16;
+    FPFNBS3TESTDOMODE       pfnDoPE16_32;
+    PFNBS3TESTDOMODE        pfnDoPE16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPE32;
+    PFNBS3TESTDOMODE        pfnDoPE32_16;
+    PFNBS3TESTDOMODE        pfnDoPEV86;
+
+    PFNBS3TESTDOMODE        pfnDoPP16;
+    FPFNBS3TESTDOMODE       pfnDoPP16_32;
+    PFNBS3TESTDOMODE        pfnDoPP16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPP32;
+    PFNBS3TESTDOMODE        pfnDoPP32_16;
+    PFNBS3TESTDOMODE        pfnDoPPV86;
+
+    PFNBS3TESTDOMODE        pfnDoPAE16;
+    FPFNBS3TESTDOMODE       pfnDoPAE16_32;
+    PFNBS3TESTDOMODE        pfnDoPAE16_V86;
+    FPFNBS3TESTDOMODE       pfnDoPAE32;
+    PFNBS3TESTDOMODE        pfnDoPAE32_16;
+    PFNBS3TESTDOMODE        pfnDoPAEV86;
+
+    PFNBS3TESTDOMODE        pfnDoLM16;
+    FPFNBS3TESTDOMODE       pfnDoLM32;
+    FPFNBS3TESTDOMODE       pfnDoLM64;
+
+} BS3TESTMODEENTRY;
+/** Pointer to a mode sub-test entry. */
+typedef BS3TESTMODEENTRY const *PCBS3TESTMODEENTRY;
 
 
@@ -2030,4 +2187,12 @@
 
 
+/**
+ * Executes the array of tests in every possibly mode.
+ *
+ * @param   paEntries       The mode sub-test entries.
+ * @param   cEntries        The number of sub-test entries.
+ */
+BS3_MODE_EXPAND_PROTOTYPES(void, Bs3TestDoModes, (BS3TESTMODEENTRY paEntries, unsigned cEntries));
+
 /** @} */
 
