Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 58808)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/Makefile.kmk	(revision 58809)
@@ -446,5 +446,5 @@
 	bs3-cmn-Panic.asm \
 	bs3-cmn-PrintChr.asm \
-	bs3-cmn-PrintF.c \
+	bs3-cmn-Printf.c \
 	bs3-cmn-PrintU32.asm \
 	bs3-cmn-PrintX32.asm \
@@ -452,4 +452,6 @@
        bs3-cmn-PrintStrColonSpaces.asm \
        bs3-cmn-PrintStrSpacesColonSpace.c \
+       bs3-cmn-StrFormatV.c \
+       bs3-cmn-StrPrintf.c \
        bs3-cmn-StrLen.c \
        bs3-cmn-StrNLen.c \
@@ -488,5 +490,14 @@
 	bs3-system-data.asm \
 	bs3-rm-InitMemory.c \
-	bs3-cmn-hexdigits.c
+	bs3-cmn-hexdigits.c \
+	bs3-wc16-U8DR.asm \
+	bs3-wc16-U8DQ.asm \
+	bs3-wc16-I8DR.asm \
+	bs3-wc16-I8DQ.asm \
+	bs3-wc16-I8RS.asm \
+	bs3-wc16-U8RS.asm \
+	bs3-wc16-U8LS.asm \
+	bs3-wc16-U4D.asm \
+	bs3-wc16-I4D.asm \
 
 # The 32-bit BS3Kit library.
@@ -495,5 +506,10 @@
 bs3kit-common-32_DEFS     = TMPL_PE32 BS3_CMN_ONLY
 bs3kit-common-32_ASDEFS   = RT_ASMDEFS_INC_FIRST_FILE
-bs3kit-common-32_SOURCES  = $(VBOX_BS3KIT_COMMON_SOURCES)
+bs3kit-common-32_SOURCES  = $(VBOX_BS3KIT_COMMON_SOURCES) \
+	bs3-wc32-U8D.asm \
+	bs3-wc32-I8D.asm \
+	bs3-wc32-I8RS.asm \
+	bs3-wc32-U8RS.asm \
+	bs3-wc32-U8LS.asm \
 
 # The 64-bit BS3Kit library.
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp	(revision 58808)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/VBoxBs3ObjConverter.cpp	(revision 58809)
@@ -516,4 +516,5 @@
     "\x05" "__I4D",
     "\x05" "__I4M",
+    "\x05" "__I8D",
     "\x06" "__I8DQ",
     "\x07" "__I8DQE",
@@ -530,4 +531,5 @@
     "\x05" "__U4D",
     "\x05" "__U4M",
+    "\x05" "__U8D",
     "\x06" "__U8DQ",
     "\x07" "__U8DQE",
@@ -617,6 +619,6 @@
                                 && memcmp(&g_apszExtDefRenames[i][1], pchName, cch) == 0)
                             {
-                                pchName[0] = fProbably32bit ? '3' : '1';
-                                pchName[1] = fProbably32bit ? '2' : '6';
+                                pchName[0] = fProbably32bit ? '?' : '_';
+                                pchName[1] = fProbably32bit ? '?' : '?';
                                 break;
                             }
Index: unk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-PrintF.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-PrintF.c	(revision 58808)
+++ 	(revision )
@@ -1,541 +1,0 @@
-/* $Id$ */
-/** @file
- * BS3Kit - Bs3PrintF
- */
-
-/*
- * 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.
- */
-
-#include "bs3kit-template-header.h"
-#include <iprt/ctype.h>
-
-
-#define STR_F_CAPITAL         0x0001
-#define STR_F_LEFT            0x0002
-#define STR_F_ZEROPAD         0x0004
-#define STR_F_SPECIAL         0x0008
-#define STR_F_VALSIGNED       0x0010
-#define STR_F_PLUS            0x0020
-#define STR_F_BLANK           0x0040
-#define STR_F_WIDTH           0x0080
-#define STR_F_PRECISION       0x0100
-#define STR_F_THOUSAND_SEP    0x0200
-
-
-static size_t bs3PrintFormatString(const char *psz, size_t cchMax, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    size_t cchRet;
-    if (cchMax == ~(size_t)0)
-        cchMax = Bs3StrNLen(psz, cchMax);
-    cchRet = cchMax;
-
-    /** @todo this is kind of crude, full fleged formatting can wait.  */
-    while (cchMax-- > 0)
-        Bs3PrintChr(*psz++);
-
-    return cchRet;
-}
-
-
-static size_t bs3PrintFormatU64(char szTmp[64], uint64_t uValue, unsigned uBase, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-#if 0
-    const char *pachDigits = !(fFlags & STR_F_CAPITAL) ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
-    char       *psz = &szTmp[64];
-
-    *--psz = '\0';
-    if (uBase == 10)
-    {
-        do
-        {
-            *--psz = pachDigits[uValue % 10];
-            uValue /= 10;
-        } while (uValue > 0);
-    }
-    else
-    {
-        unsigned const cShift = uBase == 8 ? 2 : 3;
-        unsigned const fMask  = uBase == 8 ? 7 : 15;
-        do
-        {
-            *--psz = pachDigits[uValue & fMask];
-            uValue >>= cShift;
-        } while (uValue > 0);
-    }
-    return bs3PrintFormatString(psz, &szTmp[63] - psz, 0, 0, 0);
-#else
-    return 0;
-#endif
-}
-
-#if ARCH_BITS == 64
-# define bs3PrintFormatU32 bs3PrintFormatU64
-# define bs3PrintFormatU16 bs3PrintFormatU64
-
-#else
-static size_t bs3PrintFormatU32(char szTmp[64], uint32_t uValue, unsigned uBase, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    const char *pachDigits = !(fFlags & STR_F_CAPITAL) ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
-    char       *psz = &szTmp[64];
-
-    *--psz = '\0';
-    if (uBase == 10)
-    {
-        do
-        {
-            *--psz = pachDigits[uValue % 10];
-            uValue /= 10;
-        } while (uValue > 0);
-    }
-    else
-    {
-        unsigned const cShift = uBase == 8 ? 2 : 3;
-        unsigned const fMask  = uBase == 8 ? 7 : 15;
-        do
-        {
-            *--psz = pachDigits[uValue & fMask];
-            uValue >>= cShift;
-        } while (uValue > 0);
-    }
-    return bs3PrintFormatString(psz, &szTmp[63] - psz, 0, 0, 0);
-}
-
-# if ARCH_BITS == 16
-static size_t bs3PrintFormatU16(char szTmp[64], uint16_t uValue, unsigned uBase, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    if (uBase == 10)
-    {
-        const char *pachDigits = !(fFlags & STR_F_CAPITAL) ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
-        char       *psz = &szTmp[64];
-
-        *--psz = '\0';
-        do
-        {
-            *--psz = pachDigits[uValue % 10];
-            uValue /= 10;
-        } while (uValue > 0);
-        return bs3PrintFormatString(psz, &szTmp[63] - psz, 0, 0, 0);
-    }
-    /* 32-bit shifting is reasonably cheap, so combine with 32-bit. */
-    return bs3PrintFormatU32(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-}
-# endif /* 16-bit */
-#endif /* !64-bit */
-
-
-static size_t bs3PrintFormatS64(char szTmp[64], int16_t iValue, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    /** @todo this is kind of crude, full fleged formatting can wait.  */
-    size_t cchRet = 0;
-    if (iValue < 0)
-    {
-        Bs3PrintChr('-');
-        cchRet++;
-    }
-    cchRet += bs3PrintFormatU64(szTmp, iValue, 10, fFlags & ~STR_F_VALSIGNED, cchWidth, cchPrecision);
-    return cchRet;
-}
-
-
-static size_t bs3PrintFormatS32(char szTmp[64], int16_t iValue, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    /** @todo this is kind of crude, full fleged formatting can wait.  */
-    size_t cchRet = 0;
-    if (iValue < 0)
-    {
-        Bs3PrintChr('-');
-        cchRet++;
-    }
-    cchRet += bs3PrintFormatU32(szTmp, iValue, 10, fFlags & ~STR_F_VALSIGNED, cchWidth, cchPrecision);
-    return cchRet;
-}
-
-
-#if ARCH_BITS == 16
-static size_t bs3PrintFormatS16(char szTmp[64], int16_t iValue, uint16_t fFlags, int cchWidth, int cchPrecision)
-{
-    /** @todo this is kind of crude, full fleged formatting can wait.  */
-    size_t cchRet = 0;
-    if (iValue < 0)
-    {
-        Bs3PrintChr('-');
-        cchRet++;
-    }
-    cchRet += bs3PrintFormatU16(szTmp, iValue, 10, fFlags & ~STR_F_VALSIGNED, cchWidth, cchPrecision);
-    return cchRet;
-}
-#endif
-
-
-
-
-
-BS3_DECL(size_t) Bs3PrintFV(const char BS3_FAR *pszFormat, va_list va)
-{
-    size_t cchRet = 0;
-    char ch;
-    while ((ch = *pszFormat++) != '\0')
-    {
-        unsigned int    fFlags;
-        int             cchWidth;
-        int             cchPrecision;
-        char            chArgSize;
-        char            szTmp[64];
-
-        /*
-         * Deal with plain chars.
-         */
-        if (ch != '%')
-        {
-            if (ch == '\n')
-                Bs3PrintChr('\r');
-            Bs3PrintChr(ch);
-            cchRet++;
-            continue;
-        }
-
-        ch = *pszFormat++;
-        if (ch == '%')
-        {
-            Bs3PrintChr(ch);
-            cchRet++;
-            continue;
-        }
-
-        /*
-         * Flags.
-         */
-        fFlags = 0;
-        for (;;)
-        {
-            unsigned int fThis;
-            switch (ch)
-            {
-                default:    fThis = 0;                  break;
-                case '#':   fThis = STR_F_SPECIAL;      break;
-                case '-':   fThis = STR_F_LEFT;         break;
-                case '+':   fThis = STR_F_PLUS;         break;
-                case ' ':   fThis = STR_F_BLANK;        break;
-                case '0':   fThis = STR_F_ZEROPAD;      break;
-                case '\'':  fThis = STR_F_THOUSAND_SEP; break;
-            }
-            if (!fThis)
-                break;
-            fFlags |= fThis;
-            ch = *pszFormat++;
-        }
-
-        /*
-         * Width.
-         */
-        cchWidth = 0;
-        if (RT_C_IS_DIGIT(ch))
-        {
-            do
-            {
-                cchWidth *= 10;
-                cchWidth  = ch - '0';
-                ch = *pszFormat++;
-            } while (RT_C_IS_DIGIT(ch));
-            fFlags |= STR_F_WIDTH;
-        }
-        else if (ch == '*')
-        {
-            cchWidth = va_arg(va, int);
-            if (cchWidth < 0)
-            {
-                cchWidth = -cchWidth;
-                fFlags |= STR_F_LEFT;
-            }
-            fFlags |= STR_F_WIDTH;
-        }
-
-        /*
-         * Precision
-         */
-        cchPrecision = 0;
-        if (RT_C_IS_DIGIT(ch))
-        {
-            do
-            {
-                cchPrecision *= 10;
-                cchPrecision  = ch - '0';
-                ch = *pszFormat++;
-            } while (RT_C_IS_DIGIT(ch));
-            fFlags |= STR_F_PRECISION;
-        }
-        else if (ch == '*')
-        {
-            cchPrecision = va_arg(va, int);
-            if (cchPrecision < 0)
-                cchPrecision = 0;
-            fFlags |= STR_F_PRECISION;
-        }
-
-        /*
-         * Argument size.
-         */
-        chArgSize = ch;
-        switch (ch)
-        {
-            default:
-                chArgSize = 0;
-                break;
-
-            case 'z':
-            case 'L':
-            case 'j':
-            case 't':
-                ch = *pszFormat++;
-                break;
-
-            case 'l':
-                ch = *pszFormat++;
-                if (ch == 'l')
-                {
-                    chArgSize = 'L';
-                    ch = *pszFormat++;
-                }
-                break;
-
-            case 'h':
-                ch = *pszFormat++;
-                if (ch == 'h')
-                {
-                    chArgSize = 'H';
-                    ch = *pszFormat++;
-                }
-                break;
-        }
-
-        /*
-         * The type.
-         */
-        switch (ch)
-        {
-            /*
-             * Char
-             */
-            case 'c':
-                szTmp[0] = va_arg(va, int /*char*/);
-                szTmp[1] = '\0';
-                cchRet += bs3PrintFormatString(szTmp, 1, fFlags, cchWidth, cchPrecision);
-                break;
-
-            /*
-             * String.
-             */
-            case 's':
-            {
-                const char BS3_FAR *psz = va_arg(va, const char BS3_FAR *);
-                if (psz == NULL)
-                    psz = "<NULL>";
-                cchRet += bs3PrintFormatString(psz, ~(size_t)0, fFlags, cchWidth, cchPrecision);
-                break;
-            }
-
-            /*
-             * Signed integers.
-             */
-            case 'i':
-            case 'd':
-                fFlags |= STR_F_VALSIGNED;
-                switch (chArgSize)
-                {
-                    case 0:
-                    case 'h': /* signed short should be promoted to int or be the same as int */
-                    case 'H': /* signed char should be promoted to int. */
-                    {
-                        signed int iValue = va_arg(va, signed int);
-#if ARCH_BITS == 16
-                        cchRet += bs3PrintFormatS16(szTmp, iValue, fFlags, cchWidth, cchPrecision);
-#else
-                        cchRet += bs3PrintFormatS32(szTmp, iValue, fFlags, cchWidth, cchPrecision);
-#endif
-                        break;
-                    }
-                    case 'l':
-                    {
-                        signed long lValue = va_arg(va, signed long);
-                        if (sizeof(lValue) == 4)
-                            cchRet += bs3PrintFormatS32(szTmp, lValue, fFlags, cchWidth, cchPrecision);
-                        else
-                            cchRet += bs3PrintFormatS64(szTmp, lValue, fFlags, cchWidth, cchPrecision);
-                        break;
-                    }
-                    case 'L':
-                    {
-                        unsigned long long ullValue = va_arg(va, unsigned long long);
-                        cchRet += bs3PrintFormatS64(szTmp, ullValue, fFlags, cchWidth, cchPrecision);
-                        break;
-                    }
-                }
-                break;
-
-            /*
-             * Unsigned integers.
-             */
-            case 'X':
-                fFlags |= STR_F_CAPITAL;
-            case 'x':
-            case 'u':
-            {
-                unsigned uBase = ch = 'u' ? 10 : 16;
-                switch (chArgSize)
-                {
-                    case 0:
-                    case 'h': /* unsigned short should be promoted to int or be the same as int */
-                    case 'H': /* unsigned char should be promoted to int. */
-                    {
-                        unsigned int uValue = va_arg(va, unsigned int);
-#if ARCH_BITS == 16
-                        cchRet += bs3PrintFormatU16(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-#else
-                        cchRet += bs3PrintFormatU32(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-#endif
-                        break;
-                    }
-                    case 'l':
-                    {
-                        unsigned long ulValue = va_arg(va, unsigned long);
-                        if (sizeof(ulValue) == 4)
-                            cchRet += bs3PrintFormatU32(szTmp, ulValue, uBase, fFlags, cchWidth, cchPrecision);
-                        else
-                            cchRet += bs3PrintFormatU64(szTmp, ulValue, uBase, fFlags, cchWidth, cchPrecision);
-                        break;
-                    }
-                    case 'L':
-                    {
-                        unsigned long long ullValue = va_arg(va, unsigned long long);
-                        cchRet += bs3PrintFormatU64(szTmp, ullValue, uBase, fFlags, cchWidth, cchPrecision);
-                        break;
-                    }
-                }
-                break;
-            }
-
-            /*
-             * Our stuff.
-             */
-            case 'R':
-            {
-                unsigned uBase;
-                ch = *pszFormat++;
-                switch (ch)
-                {
-                    case 'I':
-                        fFlags |= STR_F_VALSIGNED;
-                        /* fall thru */
-                    case 'U':
-                        uBase = 10;
-                        break;
-                    case 'X':
-                        uBase = 16;
-                        break;
-                    default:
-                        uBase = 0;
-                        break;
-                }
-                if (uBase)
-                {
-                    ch = *pszFormat++;
-                    switch (ch)
-                    {
-#if ARCH_BITS != 16
-                        case '3':
-                        case '1': /* Will an unsigned 16-bit value always be promoted
-                                     to a 16-bit unsigned int. It certainly will be promoted to a 32-bit int. */
-                            pszFormat++; /* Assumes (1)'6' or (3)'2' */
-#else
-                        case '1':
-                            pszFormat++; /* Assumes (1)'6' */
-#endif
-                        case '8': /* An unsigned 8-bit value should be promoted to int, which is at least 16-bit. */
-                        {
-                            unsigned int uValue = va_arg(va, unsigned int);
-#if ARCH_BITS == 16
-                            cchRet += bs3PrintFormatU16(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-#else
-                            cchRet += bs3PrintFormatU32(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-#endif
-                            break;
-                        }
-#if ARCH_BITS == 16
-                        case '3':
-                        {
-                            uint32_t uValue = va_arg(va, uint32_t);
-                            pszFormat++;
-                            cchRet += bs3PrintFormatU32(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-                            break;
-                        }
-#endif
-                        case '6':
-                        {
-                            uint64_t uValue = va_arg(va, uint64_t);
-                            pszFormat++;
-                            cchRet += bs3PrintFormatU64(szTmp, uValue, uBase, fFlags, cchWidth, cchPrecision);
-                            break;
-                        }
-                    }
-                }
-                break;
-            }
-
-            /*
-             * Pointers.
-             */
-            case 'P':
-                fFlags |= STR_F_CAPITAL;
-                /* fall thru */
-            case 'p':
-            {
-                void BS3_FAR *pv = va_arg(va, void BS3_FAR *);
-#if ARCH_BITS == 16
-                cchRet += bs3PrintFormatU16(szTmp, BS3_FP_SEG(pv), 16, fFlags, fFlags & STR_F_SPECIAL ? 6 : 4, 0);
-                Bs3PrintChr(':');
-                cchRet += 1;
-                cchRet += bs3PrintFormatU16(szTmp, BS3_FP_OFF(pv), 16, fFlags & ~STR_F_SPECIAL, 4, 0);
-#elif ARCH_BITS == 32
-                cchRet += bs3PrintFormatU32(szTmp, (uintptr_t)pv, 16, fFlags | STR_F_SPECIAL, 10, 0);
-#elif ARCH_BITS == 64
-                cchRet += bs3PrintFormatU64(szTmp, (uintptr_t)pv, 16, fFlags | STR_F_SPECIAL | STR_F_THOUSAND_SEP, 19, 0);
-#else
-# error "Undefined or invalid ARCH_BITS."
-#endif
-                break;
-            }
-
-        }
-    }
-    return cchRet;
-}
-
-
-BS3_DECL(size_t) Bs3PrintF(const char BS3_FAR *pszFormat, ...)
-{
-    size_t cchRet;
-    va_list va;
-    va_start(va, pszFormat);
-    cchRet = Bs3PrintFV(pszFormat, va);
-    va_end(va);
-    return cchRet;
-}
-
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-Printf.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-Printf.c	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-Printf.c	(revision 58809)
@@ -0,0 +1,60 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3Printf, Bs3PrintfV
+ */
+
+/*
+ * 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.
+ */
+
+#include "bs3kit-template-header.h"
+#include <iprt/ctype.h>
+
+
+BS3_DECL(size_t) bs3PrintFmtOutput(char ch, void *pvUser)
+{
+    if (ch)
+    {
+        if (ch != '\n')
+            Bs3PrintChr('\r');
+        Bs3PrintChr(ch);
+        return 1;
+    }
+    NOREF(pvUser);
+    return 0;
+}
+
+
+BS3_DECL(size_t) Bs3PrintfV(const char BS3_FAR *pszFormat, va_list va)
+{
+    return Bs3StrFormatV(pszFormat, va, bs3PrintFmtOutput, NULL);
+}
+
+
+BS3_DECL(size_t) Bs3Printf(const char BS3_FAR *pszFormat, ...)
+{
+    size_t cchRet;
+    va_list va;
+    va_start(va, pszFormat);
+    cchRet = Bs3StrFormatV(pszFormat, va, bs3PrintFmtOutput, NULL);
+    va_end(va);
+    return cchRet;
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-StrFormatV.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-StrFormatV.c	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-cmn-StrFormatV.c	(revision 58809)
@@ -0,0 +1,744 @@
+/* $Id$ */
+/** @file
+ * BS3Kit - Bs3StrFormatV
+ */
+
+/*
+ * 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.h"
+#include <iprt/ctype.h>
+
+
+/*********************************************************************************************************************************
+*   Defined Constants And Macros                                                                                                 *
+*********************************************************************************************************************************/
+#define STR_F_CAPITAL           0x0001
+#define STR_F_LEFT              0x0002
+#define STR_F_ZEROPAD           0x0004
+#define STR_F_SPECIAL           0x0008
+#define STR_F_VALSIGNED         0x0010
+#define STR_F_PLUS              0x0020
+#define STR_F_BLANK             0x0040
+#define STR_F_WIDTH             0x0080
+#define STR_F_PRECISION         0x0100
+#define STR_F_THOUSAND_SEP      0x0200
+#define STR_F_NEGATIVE          0x0400 /**< Used to indicated '-' must be printed. */
+
+
+/*********************************************************************************************************************************
+*   Structures and Typedefs                                                                                                      *
+*********************************************************************************************************************************/
+/** Size of the temporary buffer. */
+#define BS3FMT_TMP_SIZE    64
+
+/**
+ * BS3kit string format state.
+ */
+typedef struct BS3FMTSTATE
+{
+    /** The output function. */
+    PFNBS3STRFORMATOUTPUT pfnOutput;
+    /** User argument for pfnOutput. */
+    void BS3_FAR  *pvUser;
+
+    /** STR_F_XXX flags.   */
+    unsigned        fFlags;
+    /** The width when STR_F_WIDTH is specific. */
+    int             cchWidth;
+    /** The width when STR_F_PRECISION is specific. */
+    int             cchPrecision;
+    /** The number format base. */
+    unsigned        uBase;
+    /** Temporary buffer. */
+    char            szTmp[BS3FMT_TMP_SIZE];
+} BS3FMTSTATE;
+/** Pointer to a BS3Kit string formatter state. */
+typedef BS3FMTSTATE *PBS3FMTSTATE;
+
+
+
+/*********************************************************************************************************************************
+*   Internal Functions                                                                                                           *
+*********************************************************************************************************************************/
+#if ARCH_BITS != 64
+static size_t bs3StrFormatU32(PBS3FMTSTATE pState, uint32_t uValue);
+#endif
+
+
+
+/**
+ * Formats a number string.
+ *
+ * @returns Number of chars printed.
+ * @param   pState              The string formatter state.
+ * @param   pszNumber           The formatted number string.
+ * @param   cchNumber           The length of the number.
+ */
+static size_t bs3StrFormatNumberString(PBS3FMTSTATE pState, char const *pszNumber, size_t cchNumber)
+{
+    /*
+     * Calc the length of the core number with prefixes.
+     */
+    size_t cchActual = 0;
+    size_t cchRet = cchNumber;
+
+    /* Accunt for sign char. */
+    cchRet += !!(pState->fFlags & (STR_F_NEGATIVE | STR_F_PLUS | STR_F_BLANK));
+
+    /* Account for the hex prefix: '0x' or '0X' */
+    if (pState->fFlags & STR_F_SPECIAL)
+    {
+        cchRet += 2;
+        BS3_ASSERT(pState->uBase == 16);
+    }
+
+    /* Account for thousand separators (applied while printing). */
+    if (pState->fFlags & STR_F_THOUSAND_SEP)
+        cchRet += (cchNumber - 1) / (pState->uBase == 10 ? 3 : 8);
+
+    /*
+     * Do left blank padding.
+     */
+    if ((pState->fFlags & (STR_F_ZEROPAD | STR_F_LEFT | STR_F_WIDTH)) == STR_F_WIDTH)
+        while (cchRet < pState->cchWidth)
+        {
+            cchActual += pState->pfnOutput(' ', pState->pvUser);
+            cchRet++;
+        }
+
+    /*
+     * Sign indicator / space.
+     */
+    if (pState->fFlags & (STR_F_NEGATIVE | STR_F_PLUS | STR_F_BLANK))
+    {
+        char ch;
+        if (pState->fFlags & STR_F_NEGATIVE)
+            ch = '-';
+        else if (pState->fFlags & STR_F_PLUS)
+            ch = '+';
+        else
+            ch = ' ';
+        cchActual += pState->pfnOutput(ch, pState->pvUser);
+    }
+
+    /*
+     * Hex prefix.
+     */
+    if (pState->fFlags & STR_F_SPECIAL)
+    {
+        cchActual += pState->pfnOutput(0, pState->pvUser);
+        cchActual += pState->pfnOutput(!(pState->fFlags & STR_F_CAPITAL) ? 'x' : 'X', pState->pvUser);
+    }
+
+    /*
+     * Zero padding.
+     */
+    if (pState->fFlags & STR_F_ZEROPAD)
+        while (cchRet < pState->cchWidth)
+        {
+            cchActual += pState->pfnOutput('0', pState->pvUser);
+            cchRet++;
+        }
+
+    /*
+     * Output the number.
+     */
+    if (   !(pState->fFlags & STR_F_THOUSAND_SEP)
+        || cchNumber < 4)
+        while (cchNumber-- > 0)
+            cchActual += pState->pfnOutput(*pszNumber++, pState->pvUser);
+    else
+    {
+        char const      chSep    = pState->uBase == 10 ? ' ' : '\'';
+        unsigned const  cchEvery = pState->uBase == 10 ? 3   : 8;
+        unsigned        cchLeft  = --cchNumber % cchEvery;
+
+        cchActual += pState->pfnOutput(*pszNumber++, pState->pvUser);
+        while (cchNumber-- > 0)
+        {
+            if (cchLeft == 0)
+            {
+                cchActual += pState->pfnOutput(chSep, pState->pvUser);
+                cchLeft = cchEvery;
+            }
+            cchLeft--;
+            cchActual += pState->pfnOutput(*pszNumber++, pState->pvUser);
+        }
+    }
+
+    /*
+     * Do right blank padding.
+     */
+    if ((pState->fFlags & (STR_F_ZEROPAD | STR_F_LEFT | STR_F_WIDTH)) == (STR_F_WIDTH | STR_F_LEFT))
+        while (cchRet < pState->cchWidth)
+        {
+            cchActual += pState->pfnOutput(' ', pState->pvUser);
+            cchRet++;
+        }
+
+    return cchActual;
+}
+
+
+/**
+ * Format a 64-bit number.
+ *
+ * @returns Number of characters.
+ * @param   pState          The string formatter state.
+ * @param   uValue          The value.
+ */
+static size_t bs3StrFormatU64(PBS3FMTSTATE pState, uint64_t uValue)
+{
+#if ARCH_BITS != 64
+    /* Avoid 64-bit division by formatting 64-bit numbers as hex if they're higher than _4G. */
+    if (   pState->uBase == 10
+        && !(uValue >> 32)) /* uValue <= UINT32_MAX does not work, trouble with 64-bit compile time math! */
+        return bs3StrFormatU32(pState, uValue);
+    pState->fFlags |= STR_F_SPECIAL;
+    pState->uBase = 16;
+#endif
+
+    {
+        const char *pachDigits = !(pState->fFlags & STR_F_CAPITAL)
+                               ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
+        char       *psz = &pState->szTmp[BS3FMT_TMP_SIZE];
+
+        *--psz = '\0';
+#if ARCH_BITS == 64
+        if (pState->uBase == 10)
+        {
+            do
+            {
+                *--psz = pachDigits[uValue % 10];
+                uValue /= 10;
+            } while (uValue > 0);
+        }
+        else
+#endif
+        {
+            BS3_ASSERT(pState->uBase == 16);
+            do
+            {
+                *--psz = pachDigits[uValue & 0xf];
+                uValue >>= 4;
+            } while (uValue > 0);
+        }
+        return bs3StrFormatNumberString(pState, psz, &pState->szTmp[BS3FMT_TMP_SIZE - 1] - psz);
+    }
+}
+
+
+/**
+ * Format a 32-bit number.
+ *
+ * @returns Number of characters.
+ * @param   pState          The string formatter state.
+ * @param   uValue          The value.
+ */
+static size_t bs3StrFormatU32(PBS3FMTSTATE pState, uint32_t uValue)
+{
+#if ARCH_BITS < 64
+    const char *pachDigits = !(pState->fFlags & STR_F_CAPITAL)
+                           ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
+    char       *psz = &pState->szTmp[BS3FMT_TMP_SIZE];
+
+    *--psz = '\0';
+    if (pState->uBase == 10)
+    {
+        do
+        {
+            *--psz = pachDigits[uValue % 10];
+            uValue /= 10;
+        } while (uValue > 0);
+    }
+    else
+    {
+        BS3_ASSERT(pState->uBase == 16);
+        do
+        {
+            *--psz = pachDigits[uValue & 0xf];
+            uValue >>= 4;
+        } while (uValue > 0);
+    }
+    return bs3StrFormatNumberString(pState, psz, &pState->szTmp[BS3FMT_TMP_SIZE - 1] - psz);
+
+#else
+    /* We've got native 64-bit division, save space. */
+    return bs3StrFormatU64(pState, uValue);
+#endif
+}
+
+
+#if ARCH_BITS == 16
+/**
+ * Format a 16-bit number.
+ *
+ * @returns Number of characters.
+ * @param   pState          The string formatter state.
+ * @param   uValue          The value.
+ */
+static size_t bs3StrFormatU16(PBS3FMTSTATE pState, uint16_t uValue)
+{
+    if (pState->uBase == 10)
+    {
+        const char *pachDigits = !(pState->fFlags & STR_F_CAPITAL)
+                               ? BS3_DATA_NM(g_achBs3HexDigits) : BS3_DATA_NM(g_achBs3HexDigitsUpper);
+        char       *psz = &pState->szTmp[BS3FMT_TMP_SIZE];
+
+        *--psz = '\0';
+        do
+        {
+            *--psz = pachDigits[uValue % 10];
+            uValue /= 10;
+        } while (uValue > 0);
+        return bs3StrFormatNumberString(pState, psz, &pState->szTmp[BS3FMT_TMP_SIZE - 1] - psz);
+    }
+
+    /*
+     * 32-bit shifting is reasonably cheap and inlined, so combine with 32-bit.
+     */
+    return bs3StrFormatU32(pState, uValue);
+}
+#endif
+
+
+static size_t bs3StrFormatS64(PBS3FMTSTATE pState, int32_t iValue)
+{
+    if (iValue < 0)
+    {
+        iValue = -iValue;
+        pState->fFlags |= STR_F_NEGATIVE;
+    }
+    return bs3StrFormatU64(pState, iValue);
+}
+
+
+static size_t bs3StrFormatS32(PBS3FMTSTATE pState, int32_t iValue)
+{
+    if (iValue < 0)
+    {
+        iValue = -iValue;
+        pState->fFlags |= STR_F_NEGATIVE;
+    }
+    return bs3StrFormatU32(pState, iValue);
+}
+
+
+#if ARCH_BITS == 16
+static size_t bs3StrFormatS16(PBS3FMTSTATE pState, int16_t iValue)
+{
+    if (iValue < 0)
+    {
+        iValue = -iValue;
+        pState->fFlags |= STR_F_NEGATIVE;
+    }
+    return bs3StrFormatU16(pState, iValue);
+}
+#endif
+
+
+BS3_DECL(size_t) Bs3StrFormatV(const char BS3_FAR *pszFormat, va_list va, PFNBS3STRFORMATOUTPUT pfnOutput, void *pvUser)
+{
+    BS3FMTSTATE State;
+    size_t      cchRet = 0;
+    char        ch;
+
+    State.pfnOutput = pfnOutput;
+    State.pvUser    = pvUser;
+
+    while ((ch = *pszFormat++) != '\0')
+    {
+        char        chArgSize;
+
+        /*
+         * Deal with plain chars.
+         */
+        if (ch != '%')
+        {
+            cchRet += State.pfnOutput(ch, State.pvUser);
+            continue;
+        }
+
+        ch = *pszFormat++;
+        if (ch == '%')
+        {
+            cchRet += State.pfnOutput(ch, State.pvUser);
+            continue;
+        }
+
+        /*
+         * Flags.
+         */
+        State.fFlags = 0;
+        for (;;)
+        {
+            unsigned int fThis;
+            switch (ch)
+            {
+                default:    fThis = 0;                  break;
+                case '#':   fThis = STR_F_SPECIAL;      break;
+                case '-':   fThis = STR_F_LEFT;         break;
+                case '+':   fThis = STR_F_PLUS;         break;
+                case ' ':   fThis = STR_F_BLANK;        break;
+                case '0':   fThis = STR_F_ZEROPAD;      break;
+                case '\'':  fThis = STR_F_THOUSAND_SEP; break;
+            }
+            if (!fThis)
+                break;
+            State.fFlags |= fThis;
+            ch = *pszFormat++;
+        }
+
+        /*
+         * Width.
+         */
+        State.cchWidth = 0;
+        if (RT_C_IS_DIGIT(ch))
+        {
+            do
+            {
+                State.cchWidth *= 10;
+                State.cchWidth  = ch - '0';
+                ch = *pszFormat++;
+            } while (RT_C_IS_DIGIT(ch));
+            State.fFlags |= STR_F_WIDTH;
+        }
+        else if (ch == '*')
+        {
+            State.cchWidth = va_arg(va, int);
+            if (State.cchWidth < 0)
+            {
+                State.cchWidth = -State.cchWidth;
+                State.fFlags |= STR_F_LEFT;
+            }
+            State.fFlags |= STR_F_WIDTH;
+        }
+
+        /*
+         * Precision
+         */
+        State.cchPrecision = 0;
+        if (RT_C_IS_DIGIT(ch))
+        {
+            do
+            {
+                State.cchPrecision *= 10;
+                State.cchPrecision  = ch - '0';
+                ch = *pszFormat++;
+            } while (RT_C_IS_DIGIT(ch));
+            State.fFlags |= STR_F_PRECISION;
+        }
+        else if (ch == '*')
+        {
+            State.cchPrecision = va_arg(va, int);
+            if (State.cchPrecision < 0)
+                State.cchPrecision = 0;
+            State.fFlags |= STR_F_PRECISION;
+        }
+
+        /*
+         * Argument size.
+         */
+        chArgSize = ch;
+        switch (ch)
+        {
+            default:
+                chArgSize = 0;
+                break;
+
+            case 'z':
+            case 'L':
+            case 'j':
+            case 't':
+                ch = *pszFormat++;
+                break;
+
+            case 'l':
+                ch = *pszFormat++;
+                if (ch == 'l')
+                {
+                    chArgSize = 'L';
+                    ch = *pszFormat++;
+                }
+                break;
+
+            case 'h':
+                ch = *pszFormat++;
+                if (ch == 'h')
+                {
+                    chArgSize = 'H';
+                    ch = *pszFormat++;
+                }
+                break;
+        }
+
+        /*
+         * The type.
+         */
+        switch (ch)
+        {
+            /*
+             * Char
+             */
+            case 'c':
+            {
+                char ch = va_arg(va, int /*char*/);
+                cchRet += State.pfnOutput(ch, State.pvUser);
+                break;
+            }
+
+            /*
+             * String.
+             */
+            case 's':
+            {
+                const char BS3_FAR *psz = va_arg(va, const char BS3_FAR *);
+                size_t              cch;
+                if (psz != NULL)
+                    cch = Bs3StrNLen(psz, State.fFlags & STR_F_PRECISION ? RT_ABS(State.cchPrecision) : ~(size_t)0);
+                else
+                {
+                    psz = "<NULL>";
+                    cch = 6;
+                }
+
+                if ((State.fFlags & (STR_F_LEFT | STR_F_WIDTH)) == STR_F_WIDTH)
+                    while (--State.cchWidth >= cch)
+                        cchRet += State.pfnOutput(' ', State.pvUser);
+
+                cchRet += cch;
+                while (cch-- > 0)
+                    cchRet += State.pfnOutput(*psz++, State.pvUser);
+
+                if ((State.fFlags & (STR_F_LEFT | STR_F_WIDTH)) == (STR_F_LEFT | STR_F_WIDTH))
+                    while (--State.cchWidth >= cch)
+                        cchRet += State.pfnOutput(' ', State.pvUser);
+                break;
+            }
+
+            /*
+             * Signed integers.
+             */
+            case 'i':
+            case 'd':
+                State.fFlags &= ~STR_F_SPECIAL;
+                State.fFlags |= STR_F_VALSIGNED;
+                State.uBase   = 10;
+                switch (chArgSize)
+                {
+                    case 0:
+                    case 'h': /* signed short should be promoted to int or be the same as int */
+                    case 'H': /* signed char should be promoted to int. */
+                    {
+                        signed int iValue = va_arg(va, signed int);
+#if ARCH_BITS == 16
+                        cchRet += bs3StrFormatS16(&State, iValue);
+#else
+                        cchRet += bs3StrFormatS32(&State, iValue);
+#endif
+                        break;
+                    }
+                    case 'l':
+                    {
+                        signed long lValue = va_arg(va, signed long);
+                        if (sizeof(lValue) == 4)
+                            cchRet += bs3StrFormatS32(&State, lValue);
+                        else
+                            cchRet += bs3StrFormatS64(&State, lValue);
+                        break;
+                    }
+                    case 'L':
+                    {
+                        unsigned long long ullValue = va_arg(va, unsigned long long);
+                        cchRet += bs3StrFormatS64(&State, ullValue);
+                        break;
+                    }
+                }
+                break;
+
+            /*
+             * Unsigned integers.
+             */
+            case 'X':
+                State.fFlags |= STR_F_CAPITAL;
+            case 'x':
+            case 'u':
+            {
+                if (ch == 'u')
+                {
+                    State.uBase   = 10;
+                    State.fFlags &= ~(STR_F_PLUS | STR_F_BLANK | STR_F_SPECIAL);
+                }
+                else
+                {
+                    State.uBase   = 16;
+                    State.fFlags &= ~(STR_F_PLUS | STR_F_BLANK);
+                }
+                switch (chArgSize)
+                {
+                    case 0:
+                    case 'h': /* unsigned short should be promoted to int or be the same as int */
+                    case 'H': /* unsigned char should be promoted to int. */
+                    {
+                        unsigned int uValue = va_arg(va, unsigned int);
+#if ARCH_BITS == 16
+                        cchRet += bs3StrFormatU16(&State, uValue);
+#else
+                        cchRet += bs3StrFormatU32(&State, uValue);
+#endif
+                        break;
+                    }
+                    case 'l':
+                    {
+                        unsigned long ulValue = va_arg(va, unsigned long);
+                        if (sizeof(ulValue) == 4)
+                            cchRet += bs3StrFormatU32(&State, ulValue);
+                        else
+                            cchRet += bs3StrFormatU64(&State, ulValue);
+                        break;
+                    }
+                    case 'L':
+                    {
+                        unsigned long long ullValue = va_arg(va, unsigned long long);
+                        cchRet += bs3StrFormatU64(&State, ullValue);
+                        break;
+                    }
+                }
+                break;
+            }
+
+            /*
+             * Our stuff.
+             */
+            case 'R':
+            {
+                ch = *pszFormat++;
+                switch (ch)
+                {
+                    case 'I':
+                        State.fFlags |= STR_F_VALSIGNED;
+                        State.uBase  &= ~STR_F_SPECIAL;
+                        State.uBase   = 10;
+                        break;
+                    case 'U':
+                        State.fFlags &= ~(STR_F_PLUS | STR_F_BLANK | STR_F_SPECIAL);
+                        State.uBase   = 10;
+                        break;
+                    case 'X':
+                        State.fFlags &= ~(STR_F_PLUS | STR_F_BLANK);
+                        State.uBase   = 16;
+                        break;
+                    default:
+                        State.uBase   = 0;
+                        break;
+                }
+                if (State.uBase)
+                {
+                    ch = *pszFormat++;
+                    switch (ch)
+                    {
+#if ARCH_BITS != 16
+                        case '3':
+                        case '1': /* Will an unsigned 16-bit value always be promoted
+                                     to a 16-bit unsigned int. It certainly will be promoted to a 32-bit int. */
+                            pszFormat++; /* Assumes (1)'6' or (3)'2' */
+#else
+                        case '1':
+                            pszFormat++; /* Assumes (1)'6' */
+#endif
+                        case '8': /* An unsigned 8-bit value should be promoted to int, which is at least 16-bit. */
+                        {
+                            unsigned int uValue = va_arg(va, unsigned int);
+#if ARCH_BITS == 16
+                            cchRet += bs3StrFormatU16(&State, uValue);
+#else
+                            cchRet += bs3StrFormatU32(&State, uValue);
+#endif
+                            break;
+                        }
+#if ARCH_BITS == 16
+                        case '3':
+                        {
+                            uint32_t uValue = va_arg(va, uint32_t);
+                            pszFormat++;
+                            cchRet += bs3StrFormatU32(&State, uValue);
+                            break;
+                        }
+#endif
+                        case '6':
+                        {
+                            uint64_t uValue = va_arg(va, uint64_t);
+                            pszFormat++;
+                            cchRet += bs3StrFormatU64(&State, uValue);
+                            break;
+                        }
+                    }
+                }
+                break;
+            }
+
+            /*
+             * Pointers.
+             */
+            case 'P':
+                State.fFlags |= STR_F_CAPITAL;
+                /* fall thru */
+            case 'p':
+            {
+                void BS3_FAR *pv = va_arg(va, void BS3_FAR *);
+                State.uBase   = 16;
+                State.fFlags &= ~(STR_F_PLUS | STR_F_BLANK);
+#if ARCH_BITS == 16
+                State.fFlags |= STR_F_ZEROPAD;
+                State.cchWidth = State.fFlags & STR_F_SPECIAL ? 6: 4;
+                cchRet += bs3StrFormatU16(&State, BS3_FP_SEG(pv));
+                cchRet += State.pfnOutput(':', State.pvUser);
+                cchRet += bs3StrFormatU16(&State, BS3_FP_OFF(pv));
+#elif ARCH_BITS == 32
+                State.fFlags |= STR_F_SPECIAL | STR_F_ZEROPAD;
+                State.cchWidth = 10;
+                cchRet += bs3StrFormatU32(&State, (uintptr_t)pv);
+#elif ARCH_BITS == 64
+                State.fFlags |= STR_F_SPECIAL | STR_F_ZEROPAD | STR_F_THOUSAND_SEP;
+                State.cchWidth = 19;
+                cchRet += bs3StrFormatU64(&State, (uintptr_t)pv);
+#else
+# error "Undefined or invalid ARCH_BITS."
+#endif
+                break;
+            }
+
+        }
+    }
+
+    /*
+     * Termination call.
+     */
+    cchRet += State.pfnOutput(0, State.pvUser);
+
+    return cchRet;
+}
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm	(revision 58808)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-first-rm.asm	(revision 58809)
@@ -141,5 +141,4 @@
 extern BS3_CMN_NM(Bs3Shutdown)
 extern NAME(Main_rm)
-extern _Bs3PrintF_c32
 
 BS3_BEGIN_SYSTEM16
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-shutdown.c
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-shutdown.c	(revision 58808)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-shutdown.c	(revision 58809)
@@ -23,5 +23,5 @@
 Bs3PrintStr("\r\n");
 
-Bs3PrintF("Bs3PrintF: RX32=%RX32\n", UINT32_C(0xfdb97531));
+Bs3Printf("Bs3Printf: RX32=%#'RX32 string='%s' d=%d p=%p\n", UINT32_C(0xfdb97531), "my string", 42, Main_rm);
 
 pvTmp2 = Bs3MemAlloc(BS3MEMKIND_REAL, _4K);
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I4D.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I4D.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I4D.asm	(revision 58809)
@@ -0,0 +1,66 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 32-bit signed integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 32-bit signed integer division.
+;
+; @returns  DX:AX quotient, CX:BX remainder.
+; @param    DX:AX           Dividend.
+; @param    CX:BX           Divisor
+;
+; @uses     Nothing.
+;
+global $_?I4D
+$_?I4D:
+;; @todo no idea if we're getting the negative division stuff right here according to what watcom expectes...
+extern TODO_NEGATIVE_SIGNED_DIVISION
+        ; Move dividend into EDX:EAX
+        shl     eax, 10h
+        mov     ax, dx
+        sar     dx, 0fh
+        movsx   edx, dx
+
+        ; Move divisor into ebx.
+        shl     ebx, 10h
+        mov     bx, cx
+
+        ; Do it!
+        idiv    ebx
+
+        ; Reminder in to CX:BX
+        mov     bx, dx
+        shr     edx, 10h
+        mov     cx, dx
+
+        ; Quotient into DX:AX
+        mov     edx, eax
+        shr     edx, 10h
+
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DQ.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DQ.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DQ.asm	(revision 58809)
@@ -0,0 +1,100 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit unsigned integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3Int64Div
+
+
+;;
+; 64-bit unsigned integer division, SS variant.
+;
+; @returns  ax:bx:cx:dx quotient.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [ss:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?I8DQ
+$_?I8DQ:
+        push    es
+        push    ss
+        pop     es
+        call    $_?I8DQE
+        pop     es
+        ret
+
+;;
+; 64-bit unsigned integer division, ES variant.
+;
+; @returns  ax:bx:cx:dx quotient.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [es:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?I8DQE
+$_?I8DQE:
+        push    ds
+        push    es
+
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame of sorts, allocating 16 bytes for the result buffer.
+        push    bp
+        sub     sp, 10h
+        mov     bp, sp
+
+        ; Pointer to the return buffer.
+        push    ss
+        push    bp
+        add     bp, 10h                 ; Correct bp.
+
+        ; The divisor.
+        push    dword [es:si + 4]
+        push    dword [es:si]
+
+        ; The dividend.
+        push    dx
+        push    cx
+        push    bx
+        push    ax
+
+        call    Bs3Int64Div
+
+        ; Load the quotient.
+        mov     ax, [bp - 10h + 8 + 6]
+        mov     bx, [bp - 10h + 8 + 4]
+        mov     cx, [bp - 10h + 8 + 2]
+        mov     dx, [bp - 10h + 8]
+
+        leave
+        pop     es
+        pop     ds
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DR.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DR.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8DR.asm	(revision 58809)
@@ -0,0 +1,100 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit unsigned integer modulo.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3Int64Div
+
+
+;;
+; 64-bit unsigned integer modulo, SS variant.
+;
+; @returns  ax:bx:cx:dx reminder.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [ss:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?I8DR
+$_?I8DR:
+        push    es
+        push    ss
+        pop     es
+        call    $_?I8DRE
+        pop     es
+        ret
+
+;;
+; 64-bit unsigned integer modulo, ES variant.
+;
+; @returns  ax:bx:cx:dx reminder.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [es:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?I8DRE
+$_?I8DRE:
+        push    ds
+        push    es
+
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame of sorts, allocating 16 bytes for the result buffer.
+        push    bp
+        sub     sp, 10h
+        mov     bp, sp
+
+        ; Pointer to the return buffer.
+        push    ss
+        push    bp
+        add     bp, 10h                 ; Correct bp.
+
+        ; The divisor.
+        push    dword [es:si + 4]
+        push    dword [es:si]
+
+        ; The dividend.
+        push    dx
+        push    cx
+        push    bx
+        push    ax
+
+        call    Bs3Int64Div
+
+        ; Load the reminder.
+        mov     ax, [bp - 10h + 8 + 6]
+        mov     bx, [bp - 10h + 8 + 4]
+        mov     cx, [bp - 10h + 8 + 2]
+        mov     dx, [bp - 10h + 8]
+
+        leave
+        pop     es
+        pop     ds
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8RS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8RS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-I8RS.asm	(revision 58809)
@@ -0,0 +1,64 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit signed integer right shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit signed integer left shift.
+;
+; @returns  AX:BX:CX:DX
+; @param    AX:BX:CX:DX Value to shift.
+; @param    SI          Shift count.
+;
+global $_?I8RS
+$_?I8RS:
+        push    si
+
+        ;
+        ; The 16-bit watcom code differs from the 32-bit one in the way it
+        ; handles the shift count. All 16-bit bits are used in the 16-bit
+        ; code, we do the same as the 32-bit one as we don't want to wast
+        ; time in the below loop.
+        ;
+        ; Using 8086 comatible approach here as it's less hazzle to write
+        ; and smaller.
+        ;
+        and     si, 3fh
+        jz      .return
+
+.next_shift:
+        sar     ax, 1
+        rcr     bx, 1
+        rcr     cx, 1
+        rcr     dx, 1
+        dec     si
+        jnz     .next_shift
+
+.return:
+        pop     si
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U4D.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U4D.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U4D.asm	(revision 58809)
@@ -0,0 +1,63 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 32-bit unsigned integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 32-bit unsigned integer division.
+;
+; @returns  DX:AX quotient, CX:BX remainder.
+; @param    DX:AX           Dividend.
+; @param    CX:BX           Divisor
+;
+; @uses     Nothing.
+;
+global $_?U4D
+$_?U4D:
+        ; Move dividend into EDX:EAX
+        shl     eax, 10h
+        mov     ax, dx
+        xor     edx, edx
+
+        ; Move divisor into ebx.
+        shl     ebx, 10h
+        mov     bx, cx
+
+        ; Do it!
+        div     ebx
+
+        ; Reminder in to CX:BX
+        mov     bx, dx
+        shr     edx, 10h
+        mov     cx, dx
+
+        ; Quotient into DX:AX
+        mov     edx, eax
+        shr     edx, 10h
+
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DQ.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DQ.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DQ.asm	(revision 58809)
@@ -0,0 +1,100 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit unsigned integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3UInt64Div
+
+
+;;
+; 64-bit unsigned integer division, SS variant.
+;
+; @returns  ax:bx:cx:dx quotient.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [ss:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?U8DQ
+$_?U8DQ:
+        push    es
+        push    ss
+        pop     es
+        call    $_?U8DQE
+        pop     es
+        ret
+
+;;
+; 64-bit unsigned integer division, ES variant.
+;
+; @returns  ax:bx:cx:dx quotient.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [es:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?U8DQE
+$_?U8DQE:
+        push    ds
+        push    es
+
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame of sorts, allocating 16 bytes for the result buffer.
+        push    bp
+        sub     sp, 10h
+        mov     bp, sp
+
+        ; Pointer to the return buffer.
+        push    ss
+        push    bp
+        add     bp, 10h                 ; Correct bp.
+
+        ; The divisor.
+        push    dword [es:si + 4]
+        push    dword [es:si]
+
+        ; The dividend.
+        push    dx
+        push    cx
+        push    bx
+        push    ax
+
+        call    Bs3UInt64Div
+
+        ; Load the quotient.
+        mov     ax, [bp - 10h + 8 + 6]
+        mov     bx, [bp - 10h + 8 + 4]
+        mov     cx, [bp - 10h + 8 + 2]
+        mov     dx, [bp - 10h + 8]
+
+        leave
+        pop     es
+        pop     ds
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DR.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DR.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8DR.asm	(revision 58809)
@@ -0,0 +1,100 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit unsigned integer modulo.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3UInt64Div
+
+
+;;
+; 64-bit unsigned integer modulo, SS variant.
+;
+; @returns  ax:bx:cx:dx reminder.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [ss:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?U8DR
+$_?U8DR:
+        push    es
+        push    ss
+        pop     es
+        call    $_?U8DRE
+        pop     es
+        ret
+
+;;
+; 64-bit unsigned integer modulo, ES variant.
+;
+; @returns  ax:bx:cx:dx reminder.
+; @param    ax:bx:cx:dx     Dividend.
+; @param    [es:si]         Divisor
+;
+; @uses     Nothing.
+;
+global $_?U8DRE
+$_?U8DRE:
+        push    ds
+        push    es
+
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame of sorts, allocating 16 bytes for the result buffer.
+        push    bp
+        sub     sp, 10h
+        mov     bp, sp
+
+        ; Pointer to the return buffer.
+        push    ss
+        push    bp
+        add     bp, 10h                 ; Correct bp.
+
+        ; The divisor.
+        push    dword [es:si + 4]
+        push    dword [es:si]
+
+        ; The dividend.
+        push    dx
+        push    cx
+        push    bx
+        push    ax
+
+        call    Bs3UInt64Div
+
+        ; Load the reminder.
+        mov     ax, [bp - 10h + 8 + 6]
+        mov     bx, [bp - 10h + 8 + 4]
+        mov     cx, [bp - 10h + 8 + 2]
+        mov     dx, [bp - 10h + 8]
+
+        leave
+        pop     es
+        pop     ds
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8LS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8LS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8LS.asm	(revision 58809)
@@ -0,0 +1,66 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit integer left shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit integer left shift.
+;
+; @returns  AX:BX:CX:DX
+; @param    AX:BX:CX:DX Value to shift.
+; @param    SI          Shift count.
+;
+global $_?U8LS
+$_?U8LS:
+global $_?I8LS
+$_?I8LS:
+        push    si
+
+        ;
+        ; The 16-bit watcom code differs from the 32-bit one in the way it
+        ; handles the shift count. All 16-bit bits are used in the 16-bit
+        ; code, we do the same as the 32-bit one as we don't want to wast
+        ; time in the below loop.
+        ;
+        ; Using 8086 comatible approach here as it's less hazzle to write
+        ; and smaller.
+        ;
+        and     si, 3fh
+        jz      .return
+
+.next_shift:
+        shl     ax, 1
+        rcl     bx, 1
+        rcl     cx, 1
+        rcl     dx, 1
+        dec     si
+        jnz     .next_shift
+
+.return:
+        pop     si
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8RS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8RS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc16-U8RS.asm	(revision 58809)
@@ -0,0 +1,64 @@
+; $Id$
+;; @file
+; BS3Kit - 16-bit Watcom C/C++, 64-bit unsigned integer right shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit unsigned integer left shift.
+;
+; @returns  AX:BX:CX:DX
+; @param    AX:BX:CX:DX Value to shift.
+; @param    SI          Shift count.
+;
+global $_?U8RS
+$_?U8RS:
+        push    si
+
+        ;
+        ; The 16-bit watcom code differs from the 32-bit one in the way it
+        ; handles the shift count. All 16-bit bits are used in the 16-bit
+        ; code, we do the same as the 32-bit one as we don't want to wast
+        ; time in the below loop.
+        ;
+        ; Using 8086 comatible approach here as it's less hazzle to write
+        ; and smaller.
+        ;
+        and     si, 3fh
+        jz      .return
+
+.next_shift:
+        shr     ax, 1
+        rcr     bx, 1
+        rcr     cx, 1
+        rcr     dx, 1
+        dec     si
+        jnz     .next_shift
+
+.return:
+        pop     si
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8D.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8D.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8D.asm	(revision 58809)
@@ -0,0 +1,71 @@
+; $Id$
+;; @file
+; BS3Kit - 32-bit Watcom C/C++, 64-bit signed integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3Int64Div
+
+
+;;
+; 64-bit signed integer division.
+;
+; @returns  EDX:EAX Quotient, ECX:EBX Remainder.
+; @param    EDX:EAX     Dividend.
+; @param    ECX:EBX     Divisor
+;
+global $??I8D
+$??I8D:
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame, allocating 16 bytes for the result buffer.
+        push    ebp
+        mov     ebp, esp
+        sub     esp, 10h
+
+        ; Pointer to the return buffer.
+        push    esp
+
+        ; The dividend.
+        push    ecx
+        push    ebx
+
+        ; The dividend.
+        push    edx
+        push    eax
+
+        call    Bs3Int64Div
+
+        ; Load the result.
+        mov     ecx, [ebp - 10h + 12]
+        mov     ebx, [ebp - 10h + 8]
+        mov     edx, [ebp - 10h + 4]
+        mov     eax, [ebp - 10h]
+
+        leave
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8RS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8RS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-I8RS.asm	(revision 58809)
@@ -0,0 +1,60 @@
+; $Id$
+;; @file
+; BS3Kit - 32-bit Watcom C/C++, 64-bit signed integer right shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit signed integer left shift.
+;
+; @returns  EDX:EAX
+; @param    EDX:EAX     Value to shift.
+; @param    BL          Shift count (it's specified as ECX:EBX, but we only use BL).
+;
+global $??I8RS
+$??I8RS:
+        push    ecx                     ; We're allowed to trash ECX, but why bother.
+
+        mov     cl, bl
+        and     cl, 3fh
+        test    cl, 20h
+        jnz     .big_shift
+
+        ; Shifting less than 32.
+        shrd    eax, edx, cl
+        sar     edx, cl
+
+.return:
+        pop     ecx
+        ret
+
+.big_shift:
+        ; Shifting 32 or more.
+        mov     eax, edx
+        sar     eax, cl                 ; Only uses lower 5 bits.
+        sar     edx, 1fh                ; Sign extend it.
+        jmp     .return
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8D.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8D.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8D.asm	(revision 58809)
@@ -0,0 +1,71 @@
+; $Id$
+;; @file
+; BS3Kit - 32-bit Watcom C/C++, 64-bit unsigned integer division.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+BS3_EXTERN_CMN Bs3UInt64Div
+
+
+;;
+; 64-bit unsigned integer division.
+;
+; @returns  EDX:EAX Quotient, ECX:EBX Remainder.
+; @param    EDX:EAX     Dividend.
+; @param    ECX:EBX     Divisor
+;
+global $??U8D
+$??U8D:
+        ;
+        ; Convert to a C __cdecl call - not doing this in assembly.
+        ;
+
+        ; Set up a frame, allocating 16 bytes for the result buffer.
+        push    ebp
+        mov     ebp, esp
+        sub     esp, 10h
+
+        ; Pointer to the return buffer.
+        push    esp
+
+        ; The dividend.
+        push    ecx
+        push    ebx
+
+        ; The dividend.
+        push    edx
+        push    eax
+
+        call    Bs3UInt64Div
+
+        ; Load the result.
+        mov     ecx, [ebp - 10h + 12]
+        mov     ebx, [ebp - 10h + 8]
+        mov     edx, [ebp - 10h + 4]
+        mov     eax, [ebp - 10h]
+
+        leave
+        ret
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8LS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8LS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8LS.asm	(revision 58809)
@@ -0,0 +1,62 @@
+; $Id$
+;; @file
+; BS3Kit - 32-bit Watcom C/C++, 64-bit integer left shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit integer left shift.
+;
+; @returns  EDX:EAX
+; @param    EDX:EAX     Value to shift.
+; @param    BL          Shift count (it's specified as ECX:EBX, but we only use BL).
+;
+global $??U8LS
+$??U8LS:
+global $??I8LS
+$??I8LS:
+        push    ecx                     ; We're allowed to trash ECX, but why bother.
+
+        mov     cl, bl
+        and     cl, 3fh
+        test    cl, 20h
+        jnz     .big_shift
+
+        ; Shifting less than 32.
+        shld    edx, eax, cl
+        shl     eax, cl
+
+.return:
+        pop     ecx
+        ret
+
+.big_shift:
+        ; Shifting 32 or more.
+        mov     edx, eax
+        shl     edx, cl                 ; Only uses lower 5 bits.
+        xor     eax, eax
+        jmp     .return
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8RS.asm
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8RS.asm	(revision 58809)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3-wc32-U8RS.asm	(revision 58809)
@@ -0,0 +1,60 @@
+; $Id$
+;; @file
+; BS3Kit - 32-bit Watcom C/C++, 64-bit unsigned integer right shift.
+;
+
+;
+; 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.
+;
+
+%include "bs3kit-template-header.mac"
+
+
+;;
+; 64-bit unsigned integer right shift.
+;
+; @returns  EDX:EAX
+; @param    EDX:EAX     Value to shift.
+; @param    BL          Shift count (it's specified as ECX:EBX, but we only use BL).
+;
+global $??U8RS
+$??U8RS:
+        push    ecx                     ; We're allowed to trash ECX, but why bother.
+
+        mov     cl, bl
+        and     cl, 3fh
+        test    cl, 20h
+        jnz     .big_shift
+
+        ; Shifting less than 32.
+        shrd    eax, edx, cl
+        shr     edx, cl
+
+.return:
+        pop     ecx
+        ret
+
+.big_shift:
+        ; Shifting 32 or more.
+        mov     eax, edx
+        shr     eax, cl                 ; Only uses lower 5 bits.
+        xor     edx, edx
+        jmp     .return
+
Index: /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h
===================================================================
--- /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 58808)
+++ /trunk/src/VBox/ValidationKit/bootsectors/bs3kit/bs3kit.h	(revision 58809)
@@ -937,31 +937,61 @@
 
 /**
- * Converts a 64-bit unsigned integer to a string.
- *
- * @returns The length for the formatted string.
- * @param   pszDst      The destination buffer.  Caller is responsible for
- *                      ensuring sufficient space.
- * @param   uValue      The 64-bit value.
- * @param   uBase       The base to format the number in: 2, 8,10 or 16.
- */
-BS3_DECL(size_t) Bs3FormatU64_c16(char BS3_FAR *pszDst, uint64_t uValue, unsigned uBase);
-BS3_DECL(size_t) Bs3FormatU64_c32(char BS3_FAR *pszDst, uint64_t uValue, unsigned uBase); /**< @copydoc Bs3FormatU64_c16 */
-BS3_DECL(size_t) Bs3FormatU64_c64(char BS3_FAR *pszDst, uint64_t uValue, unsigned uBase); /**< @copydoc Bs3FormatU64_c16 */
-#define Bs3FormatU64 BS3_CMN_NM(Bs3FormatU64) /**< Selects #Bs3FormatU64_c16, #Bs3FormatU64_c32 or #Bs3FormatU64_c64. */
-
-/**
  * Formats and prints a string to the screen.
  *
- * @param   pszFormat       The format string.  See #Bs3PrintFV for supported
- *                          format types and flags.
+ * See #Bs3StrFormatV_c16 for supported format types.
+ *
+ * @param   pszFormat       The format string.
  * @param   ...             Format arguments.
  */
-BS3_DECL(size_t) Bs3PrintF_c16(const char BS3_FAR *pszFormat, ...);
-BS3_DECL(size_t) Bs3PrintF_c32(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3PrintF_c16 */
-BS3_DECL(size_t) Bs3PrintF_c64(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3PrintF_c16 */
-#define Bs3PrintF BS3_CMN_NM(Bs3PrintF) /**< Selects #Bs3PrintF_c16, #Bs3PrintF_c32 or #Bs3PrintF_c64. */
+BS3_DECL(size_t) Bs3Printf_c16(const char BS3_FAR *pszFormat, ...);
+BS3_DECL(size_t) Bs3Printf_c32(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3Printf_c16 */
+BS3_DECL(size_t) Bs3Printf_c64(const char BS3_FAR *pszFormat, ...); /**< @copydoc Bs3Printf_c16 */
+#define Bs3Printf BS3_CMN_NM(Bs3Printf) /**< Selects #Bs3Printf_c16, #Bs3Printf_c32 or #Bs3Printf_c64. */
 
 /**
  * Formats and prints a string to the screen, va_list version.
+ *
+ * See #Bs3Format_c16 for supported format types.
+ *
+ * @param   pszFormat       The format string.
+ * @param   va              Format arguments.
+ */
+BS3_DECL(size_t) Bs3PrintfV_c16(const char BS3_FAR *pszFormat, va_list va);
+BS3_DECL(size_t) Bs3PrintfV_c32(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3PrintfV_c16 */
+BS3_DECL(size_t) Bs3PrintfV_c64(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3PrintfV_c16 */
+#define Bs3PrintfV BS3_CMN_NM(Bs3PrintfV) /**< Selects #Bs3PrintfV_c16, #Bs3PrintfV_c32 or #Bs3PrintfV_c64. */
+
+/**
+ * Prints a string to the screen.
+ *
+ * @param   pszString       The string to print.
+ */
+BS3_DECL(void) Bs3PrintStr_c16(const char BS3_FAR *pszString);
+BS3_DECL(void) Bs3PrintStr_c32(const char BS3_FAR *pszString); /**< @copydoc Bs3PrintStr_c16 */
+BS3_DECL(void) Bs3PrintStr_c64(const char BS3_FAR *pszString); /**< @copydoc Bs3PrintStr_c16 */
+#define Bs3PrintStr BS3_CMN_NM(Bs3PrintStr) /**< Selects #Bs3PrintStr_c16, #Bs3PrintStr_c32 or #Bs3PrintStr_c64. */
+
+/**
+ * Prints a char to the screen.
+ *
+ * @param   ch              The character to print.
+ */
+BS3_DECL(void) Bs3PrintChr_c16(char ch);
+BS3_DECL(void) Bs3PrintChr_c32(char ch); /**< @copydoc Bs3PrintChr_c16 */
+BS3_DECL(void) Bs3PrintChr_c64(char ch); /**< @copydoc Bs3PrintChr_c16 */
+#define Bs3PrintChr BS3_CMN_NM(Bs3PrintChr) /**< Selects #Bs3PrintChr_c16, #Bs3PrintChr_c32 or #Bs3PrintChr_c64. */
+
+
+/**
+ * Pointer to a #Bs3StrFormatV output function.
+ *
+ * @returns Number of characters written.
+ * @param   ch      The character to write. Zero in the final call.
+ * @param   pvUser  User argument supplied to #Bs3StrFormatV.
+ */
+typedef size_t (BS3_CALL *PFNBS3STRFORMATOUTPUT)(char ch, void *pvUser);
+
+/**
+ * Formats a string, sending the output to @a pfnOutput.
  *
  * Supported types:
@@ -976,32 +1006,54 @@
  *      - %s (far pointer)
  *
- * @param   pszFormat       The format string.  See #Bs3PrintFV for supported
- *                          format types and flags.
- * @param   va              Format arguments.
- */
-BS3_DECL(size_t) Bs3PrintFV_c16(const char BS3_FAR *pszFormat, va_list va);
-BS3_DECL(size_t) Bs3PrintFV_c32(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3PrintFV_c16 */
-BS3_DECL(size_t) Bs3PrintFV_c64(const char BS3_FAR *pszFormat, va_list va); /**< @copydoc Bs3PrintFV_c16 */
-#define Bs3PrintFV BS3_CMN_NM(Bs3PrintFV) /**< Selects #Bs3PrintFV_c16, #Bs3PrintFV_c32 or #Bs3PrintFV_c64. */
-
-/**
- * Prints a string to the screen.
- *
- * @param   pszString       The string to print.
- */
-BS3_DECL(void) Bs3PrintStr_c16(const char BS3_FAR *pszString);
-BS3_DECL(void) Bs3PrintStr_c32(const char BS3_FAR *pszString); /**< @copydoc Bs3PrintStr_c16 */
-BS3_DECL(void) Bs3PrintStr_c64(const char BS3_FAR *pszString); /**< @copydoc Bs3PrintStr_c16 */
-#define Bs3PrintStr BS3_CMN_NM(Bs3PrintStr) /**< Selects #Bs3PrintStr_c16, #Bs3PrintStr_c32 or #Bs3PrintStr_c64. */
-
-/**
- * Prints a char to the screen.
- *
- * @param   ch              The character to print.
- */
-BS3_DECL(void) Bs3PrintChr_c16(char ch);
-BS3_DECL(void) Bs3PrintChr_c32(char ch); /**< @copydoc Bs3PrintChr_c16 */
-BS3_DECL(void) Bs3PrintChr_c64(char ch); /**< @copydoc Bs3PrintChr_c16 */
-#define Bs3PrintChr BS3_CMN_NM(Bs3PrintChr) /**< Selects #Bs3PrintChr_c16, #Bs3PrintChr_c32 or #Bs3PrintChr_c64. */
+ * @returns Sum of @a pfnOutput return values.
+ * @param   pszFormat   The format string.
+ * @param   va          Format arguments.
+ * @param   pfnOutput   The output function.
+ * @param   pvUser      The user argument for the output function.
+ */
+BS3_DECL(size_t) Bs3StrFormatV_c16(const char BS3_FAR *pszFormat, va_list va, PFNBS3STRFORMATOUTPUT pfnOutput, void *pvUser);
+/** @copydoc Bs3StrFormatV_c16  */
+BS3_DECL(size_t) Bs3StrFormatV_c32(const char BS3_FAR *pszFormat, va_list va, PFNBS3STRFORMATOUTPUT pfnOutput, void *pvUser);
+/** @copydoc Bs3StrFormatV_c16  */
+BS3_DECL(size_t) Bs3StrFormatV_c64(const char BS3_FAR *pszFormat, va_list va, PFNBS3STRFORMATOUTPUT pfnOutput, void *pvUser);
+#define Bs3StrFormatV BS3_CMN_NM(Bs3StrFormatV) /**< Selects #Bs3StrFormatV_c16, #Bs3StrFormatV_c32 or #Bs3StrFormatV_c64. */
+
+/**
+ * Formats a string into a buffer.
+ *
+ * See #Bs3Format_c16 for supported format types.
+ *
+ * @returns The length of the formatted string (excluding terminator).
+ *          This will be higher or equal to @c cbBuf in case of an overflow.
+ * @param   pszBuf      The output buffer.
+ * @param   cbBuf       The size of the output buffer.
+ * @param   pszFormat   The format string.
+ * @param   va          Format arguments.
+ */
+BS3_DECL(size_t) Bs3StrPrintfV_c16(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, va_list va);
+/** @copydoc Bs3StrPrintfV_c16  */
+BS3_DECL(size_t) Bs3StrPrintfV_c32(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, va_list va);
+/** @copydoc Bs3StrPrintfV_c16  */
+BS3_DECL(size_t) Bs3StrPrintfV_c64(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, va_list va);
+#define Bs3StrPrintfV BS3_CMN_NM(Bs3StrPrintfV) /**< Selects #Bs3StrPrintfV_c16, #Bs3StrPrintfV_c32 or #Bs3StrPrintfV_c64. */
+
+/**
+ * Formats a string into a buffer.
+ *
+ * See #Bs3Format_c16 for supported format types.
+ *
+ * @returns The length of the formatted string (excluding terminator).
+ *          This will be higher or equal to @c cbBuf in case of an overflow.
+ * @param   pszBuf      The output buffer.
+ * @param   cbBuf       The size of the output buffer.
+ * @param   pszFormat   The format string.
+ * @param   ...         Format arguments.
+ */
+BS3_DECL(size_t) Bs3StrPrintf_c16(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, ...);
+/** @copydoc Bs3StrPrintf_c16  */
+BS3_DECL(size_t) Bs3StrPrintf_c32(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, ...);
+/** @copydoc Bs3StrPrintf_c16  */
+BS3_DECL(size_t) Bs3StrPrintf_c64(char BS3_FAR *pszBuf, size_t cbBuf, const char BS3_FAR *pszFormat, ...);
+#define Bs3StrPrintf BS3_CMN_NM(Bs3StrPrintf) /**< Selects #Bs3StrPrintf_c16, #Bs3StrPrintf_c32 or #Bs3StrPrintf_c64. */
 
 
