diff -urN vbox-clean-bk\src\VBox\Runtime/Makefile.kmk vbox-clean\src\VBox\Runtime/Makefile.kmk
--- vbox-clean-bk\src\VBox\Runtime/Makefile.kmk	2015-09-23 07:14:02.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/Makefile.kmk	2015-09-27 00:14:52.000000000 +0300
@@ -894,6 +894,7 @@
 	generic/RTProcIsRunningByName-generic.cpp \
 	generic/RTThreadGetNativeState-generic.cpp \
 	os2/RTErrConvertFromOS2.cpp \
+	r3/os2/fileaio-os2.cpp \
 	r3/generic/allocex-r3-generic.cpp \
 	r3/os2/filelock-os2.cpp \
 	r3/os2/mp-os2.cpp \
@@ -2108,27 +2109,24 @@
 	generic/RTAssertShouldPanic-generic.cpp \
 	generic/RTLogWriteDebugger-generic.cpp \
 	generic/RTLogWriteStdOut-stub-generic.cpp \
-	generic/RTMpCpuId-generic.cpp \
-	generic/RTMpCpuIdFromSetIndex-generic.cpp \
-	generic/RTMpCpuIdToSetIndex-generic.cpp \
-	generic/RTMpIsCpuPossible-generic.cpp \
-	generic/RTMpGetCount-generic.cpp \
-	generic/RTMpGetMaxCpuId-generic.cpp \
-	generic/RTMpGetOnlineCount-generic.cpp \
-	generic/RTMpGetOnlineSet-generic.cpp \
-	generic/RTMpGetSet-generic.cpp \
-	generic/RTMpIsCpuOnline-generic.cpp \
 	generic/RTTimerCreate-generic.cpp \
 	generic/mppresent-generic.cpp \
+	generic/RTMpOnPair-generic.cpp \
 	os2/RTErrConvertFromOS2.cpp \
 	os2/rtSemWaitOs2ConvertTimeout.cpp \
 	os2/sys0.asm \
+	win/amd64/ASMGetCS.asm \
+	win/amd64/ASMGetDS.asm \
+	win/amd64/ASMGetES.asm \
+	win/amd64/ASMGetFS.asm \
+	win/amd64/ASMGetGS.asm \
+	win/amd64/ASMGetSS.asm \
 	r0drv/generic/RTMpIsCpuWorkPending-r0drv-generic.cpp \
-	r0drv/generic/RTMpOn-r0drv-generic.cpp \
 	r0drv/generic/mpnotification-r0drv-generic.cpp \
 	r0drv/generic/threadctxhooks-r0drv-generic.cpp \
 	r0drv/memobj-r0drv.cpp \
 	r0drv/powernotification-r0drv.c \
+	r0drv/os2/mp-r0drv-os2.cpp \
 	r0drv/os2/alloc-r0drv-os2.cpp \
 	r0drv/os2/assert-r0drv-os2.cpp \
 	r0drv/os2/assertA-r0drv-os2.asm \
@@ -2143,6 +2141,7 @@
 	r0drv/os2/semevent-r0drv-os2.cpp \
 	r0drv/os2/semeventmulti-r0drv-os2.cpp \
 	r0drv/os2/semfastmutex-r0drv-os2.cpp \
+	r0drv/os2/semmutex-r0drv-os2.cpp \
 	r0drv/os2/spinlock-r0drv-os2.cpp \
 	r0drv/os2/thread-r0drv-os2.cpp \
 	r0drv/os2/thread2-r0drv-os2.cpp \
diff -urN vbox-clean-bk\src\VBox\Runtime/os2/asm-os2.cpp vbox-clean\src\VBox\Runtime/os2/asm-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/os2/asm-os2.cpp	1970-01-01 03:00:00.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/os2/asm-os2.cpp	2015-09-27 00:12:10.000000000 +0300
@@ -0,0 +1,51 @@
+/* $Id: asm-os2.cpp 3 2015-07-31 15:39:00Z dmik $ */
+/*******************************************************************************
+*   Header Files                                                               *
+*******************************************************************************/
+//#include <iprt/asm.h>
+#include "internal/iprt.h"
+
+#include <iprt/string.h>
+#include <iprt/param.h>
+
+#if 1
+
+RTDECL(uint8_t) ASMAtomicXchgU8(volatile uint8_t *pu8, uint8_t u8)
+{
+    uint8_t u8Ret = *pu8;
+    *pu8 = u8;
+    return u8Ret;
+}
+
+#if defined(RT_ARCH_AMD64) || defined(RT_ARCH_X86)
+RTDECL(void) ASMNopPause(void)
+{
+}
+#endif
+
+RTDECL(int) ASMBitFirstSet(const volatile void *pvBitmap, uint32_t cBits)
+{
+    uint32_t           iBit = 0;
+    uint8_t volatile *pu8 = (uint8_t volatile *)pvBitmap;
+    while (iBit < cBits)
+    {
+        uint8_t u8 = *pu8;
+        if (u8 != 0)
+        {
+            while (!(u8 & 1))
+            {
+                u8 >>= 1;
+                iBit++;
+            }
+            if (iBit >= cBits)
+                return -1;
+            return iBit;
+        }
+
+        iBit += 8;
+        pu8++;
+    }
+    return -1;
+}
+
+#endif
diff -urN vbox-clean-bk\src\VBox\Runtime/r0drv/os2/memobj-r0drv-os2.cpp vbox-clean\src\VBox\Runtime/r0drv/os2/memobj-r0drv-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r0drv/os2/memobj-r0drv-os2.cpp	2015-09-23 07:14:04.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r0drv/os2/memobj-r0drv-os2.cpp	2015-09-27 00:19:24.000000000 +0300
@@ -514,8 +514,10 @@
         case RTR0MEMOBJTYPE_PHYS:
             return pMemOs2->Core.u.Phys.PhysBase + (iPage << PAGE_SHIFT);
 
-        case RTR0MEMOBJTYPE_RES_VIRT:
         case RTR0MEMOBJTYPE_MAPPING:
+            return rtR0MemObjNativeGetPagePhysAddr(pMemOs2->Core.uRel.Child.pParent, iPage);
+
+        case RTR0MEMOBJTYPE_RES_VIRT:
         default:
             return NIL_RTHCPHYS;
     }
diff -urN vbox-clean-bk\src\VBox\Runtime/r0drv/os2/mp-r0drv-os2.cpp vbox-clean\src\VBox\Runtime/r0drv/os2/mp-r0drv-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r0drv/os2/mp-r0drv-os2.cpp	1970-01-01 03:00:00.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r0drv/os2/mp-r0drv-os2.cpp	2015-09-25 21:31:48.000000000 +0300
@@ -0,0 +1,312 @@
+/* $Id: mp-r0drv-freebsd.c 56290 2015-06-09 14:01:31Z vboxsync $ */
+/** @file
+ * IPRT - Multiprocessor, Ring-0 Driver, OS/2.
+ */
+
+/*
+ * Copyright (C) 2008-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 "the-os2-kernel.h"
+
+#include <iprt/mp.h>
+#include <iprt/err.h>
+#include <iprt/asm.h>
+#include <iprt/cpuset.h>
+#include "r0drv/mp-r0drv.h"
+
+
+RTDECL(RTCPUID) RTMpCpuId(void)
+{
+    return 0; // curcpu;
+}
+
+
+RTDECL(int) RTMpCurSetIndex(void)
+{
+    return 0; // curcpu;
+}
+
+
+RTDECL(int) RTMpCurSetIndexAndId(PRTCPUID pidCpu)
+{
+    return *pidCpu = 0; //curcpu;
+}
+
+
+RTDECL(int) RTMpCpuIdToSetIndex(RTCPUID idCpu)
+{
+    return idCpu < RTCPUSET_MAX_CPUS ? (int)idCpu : -1;
+}
+
+
+RTDECL(RTCPUID) RTMpCpuIdFromSetIndex(int iCpu)
+{
+    return (unsigned)iCpu < RTCPUSET_MAX_CPUS ? iCpu : NIL_RTCPUID;
+}
+
+
+RTDECL(RTCPUID) RTMpGetMaxCpuId(void)
+{
+    return 0; //mp_maxid;
+}
+
+
+RTDECL(bool) RTMpIsCpuPossible(RTCPUID idCpu)
+{
+    return idCpu <= 1; // mp_maxid;
+}
+
+
+RTDECL(PRTCPUSET) RTMpGetSet(PRTCPUSET pSet)
+{
+    RTCPUID idCpu;
+
+    RTCpuSetEmpty(pSet);
+    idCpu = RTMpGetMaxCpuId();
+    do
+    {
+        if (RTMpIsCpuPossible(idCpu))
+            RTCpuSetAdd(pSet, idCpu);
+    } while (idCpu-- > 0);
+    return pSet;
+}
+
+
+RTDECL(RTCPUID) RTMpGetCount(void)
+{
+    return 1; //mp_maxid + 1;
+}
+
+
+RTDECL(RTCPUID) RTMpGetCoreCount(void)
+{
+    return 1; //mp_maxid + 1;
+}
+
+RTDECL(bool) RTMpIsCpuOnline(RTCPUID idCpu)
+{
+    //return idCpu <= mp_maxid
+    //    && !CPU_ABSENT(idCpu);
+    return idCpu == 0;
+}
+
+
+RTDECL(PRTCPUSET) RTMpGetOnlineSet(PRTCPUSET pSet)
+{
+    RTCPUID idCpu;
+
+    RTCpuSetEmpty(pSet);
+    idCpu = RTMpGetMaxCpuId();
+    do
+    {
+        if (RTMpIsCpuOnline(idCpu))
+            RTCpuSetAdd(pSet, idCpu);
+    } while (idCpu-- > 0);
+
+    return pSet;
+}
+
+
+RTDECL(RTCPUID) RTMpGetOnlineCount(void)
+{
+    return 1; // mp_ncpus;
+}
+
+
+/**
+ * Wrapper between the native FreeBSD per-cpu callback and PFNRTWORKER
+ * for the RTMpOnAll API.
+ *
+ * @param   pvArg   Pointer to the RTMPARGS package.
+ */
+RTDECL(void) rtmpOnAllOS2Wrapper(void *pvArg)
+{
+    PRTMPARGS pArgs = (PRTMPARGS)pvArg;
+    pArgs->pfnWorker(0, pArgs->pvUser1, pArgs->pvUser2);
+}
+
+
+RTDECL(int) RTMpOnAll(PFNRTMPWORKER pfnWorker, void *pvUser1, void *pvUser2)
+{
+    RTMPARGS Args;
+    Args.pfnWorker = pfnWorker;
+    Args.pvUser1 = pvUser1;
+    Args.pvUser2 = pvUser2;
+    Args.idCpu = NIL_RTCPUID;
+    Args.cHits = 0;
+    // smp_rendezvous(NULL, rtmpOnAllOS2Wrapper, smp_no_rendevous_barrier, &Args);
+    rtmpOnAllOS2Wrapper(&Args);
+    return VINF_SUCCESS;
+}
+
+
+/**
+ * Wrapper between the native FreeBSD per-cpu callback and PFNRTWORKER
+ * for the RTMpOnOthers API.
+ *
+ * @param   pvArg   Pointer to the RTMPARGS package.
+ */
+RTDECL(void) rtmpOnOthersOS2Wrapper(void *pvArg)
+{
+    PRTMPARGS pArgs = (PRTMPARGS)pvArg;
+    RTCPUID idCpu = 0; // curcpu;
+    if (pArgs->idCpu != idCpu)
+        pArgs->pfnWorker(idCpu, pArgs->pvUser1, pArgs->pvUser2);
+}
+
+
+RTDECL(int) RTMpOnOthers(PFNRTMPWORKER pfnWorker, void *pvUser1, void *pvUser2)
+{
+    /* Will panic if no rendezvousing cpus, so check up front. */
+    if (RTMpGetOnlineCount() > 1)
+    {
+#if 0
+#if __FreeBSD_version >= 900000
+        cpuset_t    Mask;
+#elif  __FreeBSD_version >= 700000
+        cpumask_t   Mask;
+#endif
+        RTMPARGS    Args;
+
+        Args.pfnWorker = pfnWorker;
+        Args.pvUser1 = pvUser1;
+        Args.pvUser2 = pvUser2;
+        Args.idCpu = RTMpCpuId();
+        Args.cHits = 0;
+#if __FreeBSD_version >= 700000
+# if __FreeBSD_version >= 900000
+    Mask = all_cpus;
+    CPU_CLR(curcpu, &Mask);
+# else
+    Mask = ~(cpumask_t)curcpu;
+# endif
+        smp_rendezvous_cpus(Mask, NULL, rtmpOnOthersFreeBSDWrapper, smp_no_rendevous_barrier, &Args);
+#else
+        smp_rendezvous(NULL, rtmpOnOthersFreeBSDWrapper, NULL, &Args);
+#endif
+#endif
+        return VERR_CPU_NOT_FOUND;
+    }
+    return VINF_SUCCESS;
+}
+
+
+/**
+ * Wrapper between the native FreeBSD per-cpu callback and PFNRTWORKER
+ * for the RTMpOnSpecific API.
+ *
+ * @param   pvArg   Pointer to the RTMPARGS package.
+ */
+RTDECL(void) rtmpOnSpecificOS2Wrapper(void *pvArg)
+{
+    PRTMPARGS   pArgs = (PRTMPARGS)pvArg;
+    RTCPUID     idCpu = 0; // curcpu;
+    if (pArgs->idCpu == idCpu)
+    {
+        pArgs->pfnWorker(idCpu, pArgs->pvUser1, pArgs->pvUser2);
+        ASMAtomicIncU32(&pArgs->cHits);
+    }
+}
+
+
+RTDECL(int) RTMpOnSpecific(RTCPUID idCpu, PFNRTMPWORKER pfnWorker, void *pvUser1, void *pvUser2)
+{
+#if 0
+#if __FreeBSD_version >= 900000
+    cpuset_t    Mask;
+#elif  __FreeBSD_version >= 700000
+    cpumask_t   Mask;
+#endif
+#endif
+    RTMPARGS    Args;
+
+    /* Will panic if no rendezvousing cpus, so make sure the cpu is online. */
+    if (!RTMpIsCpuOnline(idCpu))
+        return VERR_CPU_NOT_FOUND;
+
+    Args.pfnWorker = pfnWorker;
+    Args.pvUser1 = pvUser1;
+    Args.pvUser2 = pvUser2;
+    Args.idCpu = idCpu;
+    Args.cHits = 0;
+#if 0
+#if __FreeBSD_version >= 700000
+# if __FreeBSD_version >= 900000
+    CPU_SETOF(idCpu, &Mask);
+# else
+    Mask = (cpumask_t)1 << idCpu;
+# endif
+    smp_rendezvous_cpus(Mask, NULL, rtmpOnSpecificFreeBSDWrapper, smp_no_rendevous_barrier, &Args);
+#else
+    smp_rendezvous(NULL, rtmpOnSpecificFreeBSDWrapper, NULL, &Args);
+#endif
+#endif
+    rtmpOnSpecificOS2Wrapper(&Args);
+    return Args.cHits == 1
+         ? VINF_SUCCESS
+         : VERR_CPU_NOT_FOUND;
+}
+
+
+/**
+ * Dummy callback for RTMpPokeCpu.
+ * @param   pvArg   Ignored
+ */
+RTDECL(void) rtmpOS2PokeCallback(void *pvArg)
+{
+    NOREF(pvArg);
+}
+
+
+RTDECL(int) RTMpPokeCpu(RTCPUID idCpu)
+{
+#if 0
+#if __FreeBSD_version >= 900000
+    cpuset_t    Mask;
+#elif  __FreeBSD_version >= 700000
+    cpumask_t   Mask;
+#endif
+#endif
+    /* Will panic if no rendezvousing cpus, so make sure the cpu is online. */
+    if (!RTMpIsCpuOnline(idCpu))
+        return VERR_CPU_NOT_FOUND;
+#if 0
+# if __FreeBSD_version >= 900000
+    CPU_SETOF(idCpu, &Mask);
+# else
+    Mask = (cpumask_t)1 << idCpu;
+# endif
+    smp_rendezvous_cpus(Mask, NULL, rtmpFreeBSDPokeCallback, smp_no_rendevous_barrier, NULL);
+#endif
+    rtmpOS2PokeCallback(NULL);
+
+    return VINF_SUCCESS;
+}
+
+
+RTDECL(bool) RTMpOnAllIsConcurrentSafe(void)
+{
+    return false; // true
+}
diff -urN vbox-clean-bk\src\VBox\Runtime/r0drv/os2/semmutex-r0drv-os2.cpp vbox-clean\src\VBox\Runtime/r0drv/os2/semmutex-r0drv-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r0drv/os2/semmutex-r0drv-os2.cpp	1970-01-01 03:00:00.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r0drv/os2/semmutex-r0drv-os2.cpp	2015-09-26 02:26:14.000000000 +0300
@@ -0,0 +1,275 @@
+/* $Id: semmutex-r0drv-nt.cpp 56290 2015-06-09 14:01:31Z vboxsync $ */
+/** @file
+ * IPRT - Mutex Semaphores, Ring-0 Driver, NT.
+ */
+
+/*
+ * Copyright (C) 2006-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                                                               *
+*******************************************************************************/
+#define RTSEMMUTEX_WITHOUT_REMAPPING
+#include "the-os2-kernel.h"
+
+#include "internal/iprt.h"
+#include <iprt/semaphore.h>
+#include <iprt/alloc.h>
+#include <iprt/assert.h>
+#include <iprt/asm.h>
+#include <iprt/err.h>
+#include <iprt/mem.h>
+#include <iprt/lockvalidator.h>
+
+#include "internal/magics.h"
+
+
+/*******************************************************************************
+*   Structures and Typedefs                                                    *
+*******************************************************************************/
+/**
+ * NT mutex semaphore.
+ */
+typedef struct RTSEMMUTEXINTERNAL
+{
+    /** Magic value (RTSEMMUTEX_MAGIC). */
+    uint32_t volatile   u32Magic;
+    /* Owner                     */
+    uint32_t            fOwned;
+    /* KEE Mutex Semaphore       */
+    MutexLock_t		Mutex;
+//#ifdef RT_USE_FAST_MUTEX
+//    /** The fast mutex object. */
+//    FAST_MUTEX          Mutex;
+//#else
+//    /** The NT Mutex object.   */
+//    KMUTEX              Mutex;
+//#endif
+} RTSEMMUTEXINTERNAL, *PRTSEMMUTEXINTERNAL;
+
+
+
+RTDECL(int)  RTSemMutexCreate(PRTSEMMUTEX phMutexSem)
+{
+    return RTSemMutexCreateEx(phMutexSem, 0 /*fFlags*/, NIL_RTLOCKVALCLASS, RTLOCKVAL_SUB_CLASS_NONE, NULL);
+}
+
+
+RTDECL(int) RTSemMutexCreateEx(PRTSEMMUTEX phMutexSem, uint32_t fFlags,
+                               RTLOCKVALCLASS hClass, uint32_t uSubClass, const char *pszNameFmt, ...)
+{
+    AssertReturn(!(fFlags & ~RTSEMMUTEX_FLAGS_NO_LOCK_VAL), VERR_INVALID_PARAMETER);
+
+    AssertCompile(sizeof(RTSEMMUTEXINTERNAL) > sizeof(void *));
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)RTMemAlloc(sizeof(*pThis));
+
+    if (!pThis)
+        return VERR_NO_MEMORY;
+
+    pThis->u32Magic = RTSEMMUTEX_MAGIC;
+    KernAllocMutexLock(&pThis->Mutex);
+    /* Owned by someone flag */
+    pThis->fOwned = 0;
+//#ifdef RT_USE_FAST_MUTEX
+//    ExInitializeFastMutex(&pThis->Mutex);
+//#else
+//    KeInitializeMutex(&pThis->Mutex, 0);
+//#endif
+
+    *phMutexSem = pThis;
+    return VINF_SUCCESS;
+}
+
+
+RTDECL(int) RTSemMutexDestroy(RTSEMMUTEX hMutexSem)
+{
+    /*
+     * Validate input.
+     */
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+    if (pThis == NIL_RTSEMMUTEX)
+        return VINF_SUCCESS;
+    AssertPtrReturn(pThis, VERR_INVALID_HANDLE);
+    AssertReturn(pThis->u32Magic == RTSEMMUTEX_MAGIC, VERR_INVALID_HANDLE);
+
+    /*
+     * Invalidate it and signal the object just in case.
+     */
+    AssertReturn(ASMAtomicCmpXchgU32(&pThis->u32Magic, RTSEMMUTEX_MAGIC_DEAD, RTSEMMUTEX_MAGIC), VERR_INVALID_HANDLE);
+    KernFreeMutexLock(&pThis->Mutex); // ???
+    pThis->fOwned = 0;
+    RTMemFree(pThis);
+    return VINF_SUCCESS;
+}
+
+
+/**
+ * Internal worker for RTSemMutexRequest and RTSemMutexRequestNoResume
+ *
+ * @returns IPRT status code.
+ * @param   hMutexSem            The mutex handle.
+ * @param   cMillies            The timeout.
+ * @param   fInterruptible      Whether it's interruptible
+ *                              (RTSemMutexRequestNoResume) or not
+ *                              (RTSemMutexRequest).
+ */
+static int rtR0SemMutexRequest(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, BOOL fInterruptible)
+{
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+
+    /*
+     * Validate and convert input.
+     */
+    if (!pThis)
+        return VERR_INVALID_HANDLE;
+
+    AssertPtrReturn(pThis, VERR_INVALID_HANDLE);
+    AssertReturn(pThis->u32Magic == RTSEMMUTEX_MAGIC, VERR_INVALID_HANDLE);
+
+    /*
+     * Get the mutex.
+     */	
+    int       rc;
+    ULONGLONG Timeout = 0;
+    ULONG     fBlock  = BLOCK_EXCLUSIVE_MUTEX;
+
+    if (! fInterruptible)
+        fBlock |= BLOCK_UNINTERRUPTABLE;
+
+    if (cMillies == RT_INDEFINITE_WAIT)
+        //rcNt = KeWaitForSingleObject(&pThis->Mutex, Executive, KernelMode, fInterruptible, NULL);
+        cMillies = SEM_INDEFINITE_WAIT;
+    else
+    {
+        Timeout = (ULONG)cMillies;
+        //Timeout.QuadPart = -(int64_t)cMillies * 10000;
+        //rcNt = KeWaitForSingleObject(&pThis->Mutex, Executive, KernelMode, fInterruptible, &Timeout);
+    }
+
+    ULONG ulData = (ULONG)VERR_INTERNAL_ERROR;
+
+    rc = KernBlock((ULONG)pThis, (ULONG)Timeout, fBlock,
+                       &pThis->Mutex,
+                       &ulData);
+    switch (rc)
+    {
+        case NO_ERROR:
+            rc = (int)ulData;
+            Assert(rc == VINF_SUCCESS || rc == VERR_SEM_DESTROYED);
+
+        if (pThis->u32Magic == RTSEMMUTEX_MAGIC)
+	    {
+	        pThis->fOwned = 1;
+                rc = VINF_SUCCESS;
+	    }
+
+            rc = VERR_SEM_DESTROYED;
+            break;
+
+        case ERROR_TIMEOUT:
+            Assert(Timeout != SEM_INDEFINITE_WAIT);
+            //ASMAtomicDecU32(&pThis->cWaiters); // !!!
+            rc = VERR_TIMEOUT;
+            break;
+
+        case ERROR_INTERRUPT:
+            Assert(fInterruptible == RTSEMWAIT_FLAGS_INTERRUPTIBLE);
+            //ASMAtomicDecU32(&pThis->cWaiters); // !!!
+            rc = VERR_INTERRUPTED;
+            break;
+
+        default:
+            AssertMsgFailed(("rc=%d\n", rc));
+            rc = VERR_GENERAL_FAILURE;
+            break;
+    }
+    return rc;
+}
+
+
+RTDECL(int) RTSemMutexRequest(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies)
+{
+    return rtR0SemMutexRequest(hMutexSem, cMillies, FALSE /*fInterruptible*/);
+}
+
+
+RTDECL(int) RTSemMutexRequestDebug(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL)
+{
+    return RTSemMutexRequest(hMutexSem, cMillies);
+}
+
+
+RTDECL(int) RTSemMutexRequestNoResume(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies)
+{
+    return rtR0SemMutexRequest(hMutexSem, cMillies, TRUE /*fInterruptible*/);
+}
+
+
+RTDECL(int) RTSemMutexRequestNoResumeDebug(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, RTHCUINTPTR uId, RT_SRC_POS_DECL)
+{
+    return RTSemMutexRequestNoResume(hMutexSem, cMillies);
+}
+
+
+RTDECL(int) RTSemMutexRelease(RTSEMMUTEX hMutexSem)
+{
+    /*
+     * Validate input.
+     */
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+    AssertPtrReturn(pThis, VERR_INVALID_HANDLE);
+    AssertReturn(pThis->u32Magic == RTSEMMUTEX_MAGIC, VERR_INVALID_HANDLE);
+
+    /*
+     * Release the mutex.
+     */
+//#ifdef RT_USE_FAST_MUTEX
+//    ExReleaseFastMutex(&pThis->Mutex);
+//#else
+//    KeReleaseMutex(&pThis->Mutex, FALSE /*Wait*/);
+//#endif
+    KernReleaseExclusiveMutex(&pThis->Mutex);
+    /* Owned by someone flag */
+    pThis->fOwned = 0;
+
+    return VINF_SUCCESS;
+}
+
+
+RTDECL(bool) RTSemMutexIsOwned(RTSEMMUTEX hMutexSem)
+{
+    /*
+     * Validate.
+     */
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+    AssertPtrReturn(pThis, false);
+    AssertReturn(pThis->u32Magic == RTSEMMUTEX_MAGIC, false);
+
+//#ifdef RT_USE_FAST_MUTEX
+//    return pThis->Mutex && pThis->Mutex->Owner != NULL;
+//#else
+//    return KeReadStateMutex(&pThis->Mutex) == 1;
+//#endif
+    return pThis && (pThis->fOwned != 0);
+}
+
diff -urN vbox-clean-bk\src\VBox\Runtime/r0drv/os2/thread-r0drv-os2.cpp vbox-clean\src\VBox\Runtime/r0drv/os2/thread-r0drv-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r0drv/os2/thread-r0drv-os2.cpp	2015-09-23 07:14:04.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r0drv/os2/thread-r0drv-os2.cpp	2015-09-27 00:20:24.000000000 +0300
@@ -76,6 +76,7 @@
             AssertMsgFailed(("%d\n", rc));
             return VERR_NO_TRANSLATION;
     }
+   return VINF_SUCCESS;
 }
 
 
diff -urN vbox-clean-bk\src\VBox\Runtime/r3/os2/fileaio-os2.cpp vbox-clean\src\VBox\Runtime/r3/os2/fileaio-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r3/os2/fileaio-os2.cpp	1970-01-01 03:00:00.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r3/os2/fileaio-os2.cpp	2015-09-26 23:59:38.000000000 +0300
@@ -0,0 +1,564 @@
+/* $Id: fileaio-os2.cpp 56290 2015-06-09 14:01:31Z dmik $ */
+/** @file
+ * IPRT - File async I/O, native implementation for the Windows host platform.
+ */
+
+/*
+ * Copyright (C) 2006-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                                                               *
+*******************************************************************************/
+#define LOG_GROUP RTLOGGROUP_DIR
+
+#include <iprt/asm.h>
+#include <iprt/file.h>
+#include <iprt/mem.h>
+#include <iprt/assert.h>
+#include <iprt/string.h>
+#include <iprt/err.h>
+#include <iprt/log.h>
+#include "internal/fileaio.h"
+
+#define  INCL_DOSERRORS
+#define  INCL_DOSFILEMGR
+#include <os2.h>
+
+
+/*******************************************************************************
+*   Structures and Typedefs                                                    *
+*******************************************************************************/
+
+/**
+ * Transfer direction.
+ */
+typedef enum TRANSFERDIRECTION
+{
+    TRANSFERDIRECTION_INVALID = 0,
+    /** Read. */
+    TRANSFERDIRECTION_READ,
+    /** Write. */
+    TRANSFERDIRECTION_WRITE,
+    /** The usual 32-bit hack. */
+    TRANSFERDIRECTION_32BIT_HACK = 0x7fffffff
+} TRANSFERDIRECTION;
+
+/**
+ * Async I/O completion context state.
+ */
+typedef struct RTFILEAIOCTXINTERNAL
+{
+    /** handle to I/O completion port. */
+    HFILE             hIoCompletionPort;
+    /** Current number of requests pending. */
+    volatile int32_t  cRequests;
+    /** Flag whether the thread was woken up. */
+    volatile bool     fWokenUp;
+    /** Flag whether the thread is currently waiting. */
+    volatile bool     fWaiting;
+    /** Flags given during creation. */
+    uint32_t          fFlags;
+    /** Magic value (RTFILEAIOCTX_MAGIC). */
+    uint32_t          u32Magic;
+} RTFILEAIOCTXINTERNAL;
+/** Pointer to an internal context structure. */
+typedef RTFILEAIOCTXINTERNAL *PRTFILEAIOCTXINTERNAL;
+
+/**
+ * Async I/O request state.
+ */
+typedef struct RTFILEAIOREQINTERNAL
+{
+    /** Overlapped structure. */
+    // -- OVERLAPPED            Overlapped;
+    LONGLONG		  llOff;
+    /** Current state the request is in. */
+    RTFILEAIOREQSTATE     enmState;
+    /** The file handle. */
+    HFILE                 hFile;
+    /** Kind of transfer Read/Write. */
+    TRANSFERDIRECTION     enmTransferDirection;
+    /** Number of bytes to transfer. */
+    size_t                cbTransfer;
+    /** Pointer to the buffer. */
+    void                 *pvBuf;
+    /** Opaque user data. */
+    void                 *pvUser;
+    /** Flag whether the request completed. */
+    bool                  fCompleted;
+    /** Number of bytes transferred successfully. */
+    size_t                cbTransfered;
+    /** Error code of the completed request. */
+    int                   Rc;
+    /** Completion context we are assigned to. */
+    PRTFILEAIOCTXINTERNAL pCtxInt;
+    /** Magic value  (RTFILEAIOREQ_MAGIC). */
+    uint32_t              u32Magic;
+} RTFILEAIOREQINTERNAL;
+/** Pointer to an internal request structure. */
+typedef RTFILEAIOREQINTERNAL *PRTFILEAIOREQINTERNAL;
+
+/*******************************************************************************
+*   Defined Constants And Macros                                               *
+*******************************************************************************/
+/** Id for the wakeup event. */
+#define AIO_CONTEXT_WAKEUP_EVENT 1
+/** Converts a pointer to an OVERLAPPED structure to a internal request. */
+#define OVERLAPPED_2_RTFILEAIOREQINTERNAL(pOverlapped) ( (PRTFILEAIOREQINTERNAL)((uintptr_t)(pOverlapped) - RT_OFFSETOF(RTFILEAIOREQINTERNAL, Overlapped)) )
+
+RTR3DECL(int) RTFileAioGetLimits(PRTFILEAIOLIMITS pAioLimits)
+{
+    int rcBSD = 0;
+    AssertPtrReturn(pAioLimits, VERR_INVALID_POINTER);
+
+    /* No limits known. */
+    pAioLimits->cReqsOutstandingMax = RTFILEAIO_UNLIMITED_REQS;
+    pAioLimits->cbBufferAlignment   = 0;
+
+    //return VINF_SUCCESS;
+    return VERR_NOT_IMPLEMENTED;
+}
+
+RTR3DECL(int) RTFileAioReqCreate(PRTFILEAIOREQ phReq)
+{
+    AssertPtrReturn(phReq, VERR_INVALID_POINTER);
+
+    PRTFILEAIOREQINTERNAL pReqInt = (PRTFILEAIOREQINTERNAL)RTMemAllocZ(sizeof(RTFILEAIOREQINTERNAL));
+
+    if (RT_UNLIKELY(!pReqInt))
+        return VERR_NO_MEMORY;
+
+    pReqInt->pCtxInt    = NULL;
+    pReqInt->fCompleted = false;
+    pReqInt->u32Magic   = RTFILEAIOREQ_MAGIC;
+    RTFILEAIOREQ_SET_STATE(pReqInt, COMPLETED);
+
+    *phReq = (RTFILEAIOREQ)pReqInt;
+
+    return VINF_SUCCESS;
+}
+
+RTDECL(int) RTFileAioReqDestroy(RTFILEAIOREQ hReq)
+{
+    /*
+     * Validate the handle and ignore nil.
+     */
+    if (hReq == NIL_RTFILEAIOREQ)
+        return VINF_SUCCESS;
+
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN(pReqInt);
+    RTFILEAIOREQ_NOT_STATE_RETURN_RC(pReqInt, SUBMITTED, VERR_FILE_AIO_IN_PROGRESS);
+
+    /*
+     * Trash the magic and free it.
+     */
+    ASMAtomicUoWriteU32(&pReqInt->u32Magic, ~RTFILEAIOREQ_MAGIC);
+    RTMemFree(pReqInt);
+
+    return VINF_SUCCESS;
+}
+
+/**
+ * Worker setting up the request.
+ */
+DECLINLINE(int) rtFileAioReqPrepareTransfer(RTFILEAIOREQ hReq, RTFILE hFile,
+                                            TRANSFERDIRECTION enmTransferDirection,
+                                            RTFOFF off, void *pvBuf, size_t cbTransfer,
+                                            void *pvUser)
+{
+    /*
+     * Validate the input.
+     */
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN(pReqInt);
+    RTFILEAIOREQ_NOT_STATE_RETURN_RC(pReqInt, SUBMITTED, VERR_FILE_AIO_IN_PROGRESS);
+    Assert(hFile != NIL_RTFILE);
+    AssertPtr(pvBuf);
+    Assert(off >= 0);
+    Assert(cbTransfer > 0);
+
+    pReqInt->enmTransferDirection  = enmTransferDirection;
+    pReqInt->hFile                 = (HFILE)RTFileToNative(hFile);
+    // pReqInt->Overlapped.Offset     = (ULONG)(off & 0xffffffff);
+    // pReqInt->Overlapped.OffsetHigh = (ULONG)(off >> 32);
+    pReqInt->llOff		   = off;
+    pReqInt->cbTransfer            = cbTransfer;
+    pReqInt->pvBuf                 = pvBuf;
+    pReqInt->pvUser                = pvUser;
+    pReqInt->fCompleted            = false;
+
+    return VINF_SUCCESS;
+}
+
+RTDECL(int) RTFileAioReqPrepareRead(RTFILEAIOREQ hReq, RTFILE hFile, RTFOFF off,
+                                    void *pvBuf, size_t cbRead, void *pvUser)
+{
+    return rtFileAioReqPrepareTransfer(hReq, hFile, TRANSFERDIRECTION_READ,
+                                       off, pvBuf, cbRead, pvUser);
+}
+
+RTDECL(int) RTFileAioReqPrepareWrite(RTFILEAIOREQ hReq, RTFILE hFile, RTFOFF off,
+                                     void const *pvBuf, size_t cbWrite, void *pvUser)
+{
+    return rtFileAioReqPrepareTransfer(hReq, hFile, TRANSFERDIRECTION_WRITE,
+                                        off, (void *)pvBuf, cbWrite, pvUser);
+}
+
+RTDECL(int) RTFileAioReqPrepareFlush(RTFILEAIOREQ hReq, RTFILE hFile, void *pvUser)
+{
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN(pReqInt);
+    RTFILEAIOREQ_NOT_STATE_RETURN_RC(pReqInt, SUBMITTED, VERR_FILE_AIO_IN_PROGRESS);
+    AssertReturn(hFile != NIL_RTFILE, VERR_INVALID_HANDLE);
+
+    return VERR_NOT_SUPPORTED;
+}
+
+RTDECL(void *) RTFileAioReqGetUser(RTFILEAIOREQ hReq)
+{
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN_RC(pReqInt, NULL);
+
+    return pReqInt->pvUser;
+}
+
+RTDECL(int) RTFileAioReqCancel(RTFILEAIOREQ hReq)
+{
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN(pReqInt);
+    RTFILEAIOREQ_STATE_RETURN_RC(pReqInt, SUBMITTED, VERR_FILE_AIO_NOT_SUBMITTED);
+
+    /**
+     * @todo r=aeichner It is not possible to cancel specific
+     * requests on Windows before Vista.
+     * CancelIo cancels all requests for a file issued by the
+     * calling thread and CancelIoEx which does what we need
+     * is only available from Vista and up.
+     * The solution is to return VERR_FILE_AIO_IN_PROGRESS
+     * if the request didn't completed yet (checked above).
+     * Shouldn't be a big issue because a request is normally
+     * only canceled if it exceeds a timeout which is quite huge.
+     */
+    return VERR_FILE_AIO_COMPLETED;
+}
+
+RTDECL(int) RTFileAioReqGetRC(RTFILEAIOREQ hReq, size_t *pcbTransfered)
+{
+    int rc = VINF_SUCCESS;
+    PRTFILEAIOREQINTERNAL pReqInt = hReq;
+    RTFILEAIOREQ_VALID_RETURN(pReqInt);
+    RTFILEAIOREQ_NOT_STATE_RETURN_RC(pReqInt, SUBMITTED, VERR_FILE_AIO_IN_PROGRESS);
+    RTFILEAIOREQ_NOT_STATE_RETURN_RC(pReqInt, PREPARED, VERR_FILE_AIO_NOT_SUBMITTED);
+
+    rc = pReqInt->Rc;
+    if (pcbTransfered && RT_SUCCESS(rc))
+        *pcbTransfered = pReqInt->cbTransfered;
+
+    return rc;
+}
+
+RTDECL(int) RTFileAioCtxCreate(PRTFILEAIOCTX phAioCtx, uint32_t cAioReqsMax,
+                               uint32_t fFlags)
+{
+    PRTFILEAIOCTXINTERNAL pCtxInt;
+    AssertPtrReturn(phAioCtx, VERR_INVALID_POINTER);
+    AssertReturn(!(fFlags & ~RTFILEAIOCTX_FLAGS_VALID_MASK), VERR_INVALID_PARAMETER);
+
+    pCtxInt = (PRTFILEAIOCTXINTERNAL)RTMemAllocZ(sizeof(RTFILEAIOCTXINTERNAL));
+
+    if (RT_UNLIKELY(!pCtxInt))
+        return VERR_NO_MEMORY;
+
+    //pCtxInt->hIoCompletionPort = CreateIoCompletionPort(INVALID_HANDLE_VALUE,
+    //                                                    NULL,
+    //                                                    0,
+    //                                                    0);
+    //if (RT_UNLIKELY(!pCtxInt->hIoCompletionPort))
+    //{
+    //    RTMemFree(pCtxInt);
+    //    //fprintf(stderr, "%s: exit\n", __FUNCTION__);
+    //    return VERR_NO_MEMORY;
+    //}
+
+    pCtxInt->fFlags   = fFlags;
+    pCtxInt->u32Magic = RTFILEAIOCTX_MAGIC;
+
+    *phAioCtx = (RTFILEAIOCTX)pCtxInt;
+
+    return VINF_SUCCESS;
+}
+
+RTDECL(int) RTFileAioCtxDestroy(RTFILEAIOCTX hAioCtx)
+{
+    /* Validate the handle and ignore nil. */
+    if (hAioCtx == NIL_RTFILEAIOCTX)
+        return VINF_SUCCESS;
+
+    PRTFILEAIOCTXINTERNAL pCtxInt = hAioCtx;
+    RTFILEAIOCTX_VALID_RETURN(pCtxInt);
+
+    /* Cannot destroy a busy context. */
+    if (RT_UNLIKELY(pCtxInt->cRequests))
+        return VERR_FILE_AIO_BUSY;
+
+    // CloseHandle(pCtxInt->hIoCompletionPort);
+
+    if (pCtxInt && pCtxInt->hIoCompletionPort)
+        DosClose(pCtxInt->hIoCompletionPort);
+
+    ASMAtomicUoWriteU32(&pCtxInt->u32Magic, RTFILEAIOCTX_MAGIC_DEAD);
+
+    if (pCtxInt)
+        RTMemFree(pCtxInt);
+
+    return VINF_SUCCESS;
+}
+
+RTDECL(int) RTFileAioCtxAssociateWithFile(RTFILEAIOCTX hAioCtx, RTFILE hFile)
+{
+    int rc = VINF_SUCCESS;
+    PRTFILEAIOCTXINTERNAL pCtxInt = hAioCtx;
+    RTFILEAIOCTX_VALID_RETURN(pCtxInt);
+
+    // HFILE hTemp = CreateIoCompletionPort((HFILE)RTFileToNative(hFile), pCtxInt->hIoCompletionPort, 0, 1);
+    //if (hTemp != pCtxInt->hIoCompletionPort)
+    //    rc = RTErrConvertFromWin32(GetLastError());
+    ////    rc = RTErrConvertFromOs2(rc);
+
+    return rc;
+}
+
+RTDECL(uint32_t) RTFileAioCtxGetMaxReqCount(RTFILEAIOCTX hAioCtx)
+{
+    return RTFILEAIO_UNLIMITED_REQS;
+}
+
+RTDECL(int) RTFileAioCtxSubmit(RTFILEAIOCTX hAioCtx, PRTFILEAIOREQ pahReqs, size_t cReqs)
+{
+    /*
+     * Parameter validation.
+     */
+    int rc = VINF_SUCCESS;
+    PRTFILEAIOCTXINTERNAL pCtxInt = hAioCtx;
+    RTFILEAIOCTX_VALID_RETURN(pCtxInt);
+    AssertReturn(cReqs > 0,  VERR_INVALID_PARAMETER);
+    Assert(cReqs <= INT32_MAX);
+    AssertPtrReturn(pahReqs, VERR_INVALID_POINTER);
+    size_t i;
+
+    for (i = 0; i < cReqs; i++)
+    {
+        PRTFILEAIOREQINTERNAL pReqInt = pahReqs[i];
+	ULONG cbActual;
+        //BOOL fSucceeded;
+
+        Assert(pReqInt->cbTransfer == (ULONG)pReqInt->cbTransfer);
+        if (pReqInt->enmTransferDirection == TRANSFERDIRECTION_READ)
+        {
+            //fSucceeded = ReadFile(pReqInt->hFile, pReqInt->pvBuf,
+            //                      (ULONG)pReqInt->cbTransfer, NULL,
+            //                      &pReqInt->Overlapped);
+	    rc = DosRead(pReqInt->hFile, pReqInt->pvBuf,
+	                 (ULONG)pReqInt->cbTransfer, &cbActual);
+        }
+        else if (pReqInt->enmTransferDirection == TRANSFERDIRECTION_WRITE)
+        {
+            //fSucceeded = WriteFile(pReqInt->hFile, pReqInt->pvBuf,
+            //                       (ULONG)pReqInt->cbTransfer, NULL,
+            //                       &pReqInt->Overlapped);
+	    rc = DosWrite(pReqInt->hFile, pReqInt->pvBuf,
+	                 (ULONG)pReqInt->cbTransfer, &cbActual);
+        }
+        else
+        {
+            //fSucceeded = false;
+	        rc = VERR_INVALID_PARAMETER;
+            AssertMsgFailed(("Invalid transfer direction\n"));
+        }
+
+        if (rc == NO_ERROR)
+	    rc = DosSetFilePtrL(pReqInt->hFile, cbActual, 
+	                        FILE_BEGIN, &pReqInt->llOff);
+
+        if (RT_UNLIKELY(rc))
+        {
+            RTFILEAIOREQ_SET_STATE(pReqInt, COMPLETED);
+            //rc = RTErrConvertFromWin32(GetLastError());
+	    ////rc = RTErrConvertFromOS2(rc);
+            ////pReqInt->Rc = rc;
+            break;
+        }
+        RTFILEAIOREQ_SET_STATE(pReqInt, SUBMITTED);
+    }
+
+    ASMAtomicAddS32(&pCtxInt->cRequests, (int32_t)i);
+
+    return rc;
+}
+
+RTDECL(int) RTFileAioCtxWait(RTFILEAIOCTX hAioCtx, size_t cMinReqs, RTMSINTERVAL cMillies,
+                             PRTFILEAIOREQ pahReqs, size_t cReqs, uint32_t *pcReqs)
+{
+    /*
+     * Validate the parameters, making sure to always set pcReqs.
+     */
+    AssertPtrReturn(pcReqs, VERR_INVALID_POINTER);
+    *pcReqs = 0; /* always set */
+    PRTFILEAIOCTXINTERNAL pCtxInt = hAioCtx;
+    RTFILEAIOCTX_VALID_RETURN(pCtxInt);
+    AssertPtrReturn(pahReqs, VERR_INVALID_POINTER);
+    AssertReturn(cReqs != 0, VERR_INVALID_PARAMETER);
+    AssertReturn(cReqs >= cMinReqs, VERR_OUT_OF_RANGE);
+
+    /*
+     * Can't wait if there are no requests around.
+     */
+    if (   RT_UNLIKELY(ASMAtomicUoReadS32(&pCtxInt->cRequests) == 0)
+        && !(pCtxInt->fFlags & RTFILEAIOCTX_FLAGS_WAIT_WITHOUT_PENDING_REQUESTS))
+        return VERR_FILE_AIO_NO_REQUEST;
+
+    /* Wait for at least one. */
+    if (!cMinReqs)
+        cMinReqs = 1;
+
+    /*
+     * Loop until we're woken up, hit an error (incl timeout), or
+     * have collected the desired number of requests.
+     */
+    int rc = VINF_SUCCESS;
+    int cRequestsCompleted = 0;
+    while (   !pCtxInt->fWokenUp
+           && cMinReqs > 0)
+    {
+        uint64_t     StartNanoTS = 0;
+        ULONG        dwTimeout = cMillies; // == RT_INDEFINITE_WAIT ? INFINITE : cMillies;
+        //cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies
+        ULONG        cbTransfered;
+        //LPOVERLAPPED pOverlapped;
+        //ULONG       lCompletionKey;
+        BOOL         fSucceeded = TRUE;
+
+        if (cMillies != RT_INDEFINITE_WAIT)
+            StartNanoTS = RTTimeNanoTS();
+
+        ASMAtomicXchgBool(&pCtxInt->fWaiting, true);
+        //fSucceeded = GetQueuedCompletionStatus(pCtxInt->hIoCompletionPort,
+        //                                       &cbTransfered,
+        //                                       &lCompletionKey,
+        //                                       &pOverlapped,
+        //                                       dwTimeout);
+        ASMAtomicXchgBool(&pCtxInt->fWaiting, false);
+        if (   !fSucceeded )
+           // && !pOverlapped)
+        {
+            /* The call failed to dequeue a completion packet, includes VERR_TIMEOUT */
+            // RTErrConvertFromWin32(GetLastError());
+            rc = NO_ERROR; //// RTErrConvertFromOs2(rc);
+            break;
+        }
+
+        /* Check if we got woken up. */
+        //if (lCompletionKey == AIO_CONTEXT_WAKEUP_EVENT)
+        //{
+            //Assert(fSucceeded && !pOverlapped);
+            //break;
+        //}
+
+        /* A request completed. */
+        //PRTFILEAIOREQINTERNAL pReqInt = OVERLAPPED_2_RTFILEAIOREQINTERNAL(pOverlapped);
+        //AssertPtr(pReqInt);
+        //Assert(pReqInt->u32Magic == RTFILEAIOREQ_MAGIC);
+
+        /* Mark the request as finished. */
+        //RTFILEAIOREQ_SET_STATE(pReqInt, COMPLETED);
+
+        //pReqInt->cbTransfered = cbTransfered;
+        if  (! fSucceeded) // (fSucceeded)
+        //    pReqInt->Rc = VINF_SUCCESS;
+        //else
+        {
+            //ULONG errCode = GetLastError();
+            //pReqInt->Rc = RTErrConvertFromWin32(errCode);
+            ////pReqInt->Rc = RTErrConvertFromOs2(rc);
+            //if (pReqInt->Rc == VERR_UNRESOLVED_ERROR)
+            //    LogRel(("AIO/win: Request %#p returned rc=%Rrc (native %u\n)", pReqInt, pReqInt->Rc, errCode));
+        }
+
+        //pahReqs[cRequestsCompleted++] = (RTFILEAIOREQ)pReqInt;
+
+        /* Update counter. */
+        cMinReqs--;
+
+        if (cMillies != RT_INDEFINITE_WAIT)
+        {
+            /* Recalculate timeout. */
+            uint64_t NanoTS = RTTimeNanoTS();
+            uint64_t cMilliesElapsed = (NanoTS - StartNanoTS) / 1000000;
+            if (cMilliesElapsed < cMillies)
+                cMillies -= cMilliesElapsed;
+            else
+                cMillies = 0;
+        }
+    }
+
+    /*
+     * Update the context state and set the return value.
+     */
+    //*pcReqs = cRequestsCompleted;
+    //ASMAtomicSubS32(&pCtxInt->cRequests, cRequestsCompleted);
+
+    /*
+     * Clear the wakeup flag and set rc.
+     */
+    //bool fWokenUp = ASMAtomicXchgBool(&pCtxInt->fWokenUp, false);
+
+    //if (    fWokenUp
+    //    &&  RT_SUCCESS(rc))
+    //    rc = VERR_INTERRUPTED;
+
+    return rc;
+}
+
+RTDECL(int) RTFileAioCtxWakeup(RTFILEAIOCTX hAioCtx)
+{
+    int rc = VINF_SUCCESS;
+    PRTFILEAIOCTXINTERNAL pCtxInt = hAioCtx;
+    RTFILEAIOCTX_VALID_RETURN(pCtxInt);
+
+    bool fWokenUp = ASMAtomicXchgBool(&pCtxInt->fWokenUp, true);
+    bool fWaiting = ASMAtomicReadBool(&pCtxInt->fWaiting);
+
+    if (   !fWokenUp
+        && fWaiting)
+    {
+        //BOOL fSucceeded = PostQueuedCompletionStatus(pCtxInt->hIoCompletionPort,
+        //                                             0, AIO_CONTEXT_WAKEUP_EVENT,
+        //                                             NULL);
+        //
+        //if (!fSucceeded)
+        //    rc = RTErrConvertFromWin32(GetLastError());
+        ////  rc = RTErrConvertFromOs2(rc);
+    }
+
+    return rc;
+}
diff -urN vbox-clean-bk\src\VBox\Runtime/r3/os2/sems-os2.cpp vbox-clean\src\VBox\Runtime/r3/os2/sems-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r3/os2/sems-os2.cpp	2015-09-23 07:14:06.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r3/os2/sems-os2.cpp	2015-09-26 23:56:40.000000000 +0300
@@ -33,15 +33,81 @@
 #include <os2.h>
 #undef RT_MAX
 
+#include <iprt/time.h>
+#include <iprt/mem.h>
+#include <iprt/thread.h>
 #include <iprt/semaphore.h>
+#include <iprt/lockvalidator.h>
 #include <iprt/assert.h>
 #include <iprt/err.h>
 
+#include "internal/magics.h"
 
 /** Converts semaphore to OS/2 handle. */
 #define SEM2HND(Sem) ((LHANDLE)(uintptr_t)Sem)
 
 
+/*******************************************************************************
+*   Defined Constants And Macros                                               *
+*******************************************************************************/
+struct RTSEMEVENTMULTIINTERNAL
+{
+    /** Magic value (RTSEMEVENTMULTI_MAGIC). */
+    uint32_t            u32Magic;
+    /** The event handle. */
+    HEV                 hev;
+#ifdef RTSEMEVENT_STRICT
+    /** Signallers. */
+    RTLOCKVALRECSHRD    Signallers;
+    /** Indicates that lock validation should be performed. */
+    bool volatile       fEverHadSignallers;
+#endif
+};
+
+typedef R3R0PTRTYPE(struct RTSEMEVENTMULTIINTERNAL) RTSEMEVENTMULTIINTERNAL;
+typedef R3R0PTRTYPE(struct RTSEMEVENTMULTIINTERNAL *) PRTSEMEVENTMULTIINTERNAL;
+
+/*  */
+struct RTSEMEVENTINTERNAL
+{
+    /** Magic value (RTSEMEVENT_MAGIC). */
+    uint32_t            u32Magic;
+    /** The event handle. */
+    HEV                 hev;
+#ifdef RTSEMEVENT_STRICT
+    /** Signallers. */
+    RTLOCKVALRECSHRD    Signallers;
+    /** Indicates that lock validation should be performed. */
+    bool volatile       fEverHadSignallers;
+#endif
+    /** The creation flags. */
+    uint32_t            fFlags;
+};
+
+typedef R3R0PTRTYPE(struct RTSEMEVENTINTERNAL) RTSEMEVENTINTERNAL;
+typedef R3R0PTRTYPE(struct RTSEMEVENTINTERNAL *) PRTSEMEVENTINTERNAL;
+
+/** Posix internal representation of a Mutex semaphore. */
+struct RTSEMMUTEXINTERNAL
+{
+    /** Magic value (RTSEMMUTEX_MAGIC). */
+    uint32_t                u32Magic;
+    /** Recursion count. */
+    uint32_t volatile       cRecursions;
+    /** The owner thread. */
+    RTNATIVETHREAD volatile hNativeOwner;
+    /** The mutex handle. */
+    HMTX                    hMtx;
+#ifdef RTSEMMUTEX_STRICT
+    /** Lock validator record associated with this mutex. */
+    RTLOCKVALRECEXCL        ValidatorRec;
+#endif
+};
+
+typedef R3R0PTRTYPE(struct RTSEMMUTEXINTERNAL) RTSEMMUTEXINTERNAL;
+typedef R3R0PTRTYPE(struct RTSEMMUTEXINTERNAL *) PRTSEMMUTEXINTERNAL;
+
+RTDECL(int)  RTErrConvertFromOS2(unsigned uNativeCode);
 
 RTDECL(int)  RTSemEventCreate(PRTSEMEVENT phEventSem)
 {
@@ -58,11 +124,18 @@
      * Create the semaphore.
      * (Auto reset, not signaled, private event object.)
      */
-    HEV hev;
+    HEV hev = NULLHANDLE;
+    PRTSEMEVENTINTERNAL pThis = (PRTSEMEVENTINTERNAL)RTMemAlloc(sizeof(*pThis));
+
+    if (! pThis)
+        return VERR_NO_MEMORY;
+
     int rc = DosCreateEventSem(NULL, &hev, DCE_AUTORESET | DCE_POSTONE, 0);
-    if (!rc)
+    if (! rc)
     {
-        *phEventSem = (RTSEMEVENT)(void *)hev;
+        *phEventSem = (RTSEMEVENT)pThis;
+        pThis->hev = hev;
+        pThis->u32Magic = RTSEMEVENT_MAGIC;
         return VINF_SUCCESS;
     }
     return RTErrConvertFromOS2(rc);
@@ -77,9 +150,16 @@
     /*
      * Close semaphore handle.
      */
-    int rc = DosCloseEventSem(SEM2HND(hEventSem));
-    if (!rc)
+    PRTSEMEVENTINTERNAL pThis = (PRTSEMEVENTINTERNAL)hEventSem;
+
+    int rc = DosCloseEventSem(pThis->hev);
+
+    if (! rc)
+    {
+        RTMemFree(pThis);
         return VINF_SUCCESS;
+    }
+
     AssertMsgFailed(("Destroy hEventSem %p failed, rc=%d\n", hEventSem, rc));
     return RTErrConvertFromOS2(rc);
 }
@@ -90,7 +170,9 @@
     /*
      * Wait for condition.
      */
-    int rc = DosWaitEventSem(SEM2HND(hEventSem), cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies);
+    PRTSEMEVENTINTERNAL pThis = (PRTSEMEVENTINTERNAL)hEventSem;
+
+    int rc = DosWaitEventSem(pThis->hev, cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies);
     switch (rc)
     {
         case NO_ERROR:              return VINF_SUCCESS;
@@ -111,7 +193,10 @@
     /*
      * Signal the object.
      */
-    int rc = DosPostEventSem(SEM2HND(hEventSem));
+    PRTSEMEVENTINTERNAL pThis = (PRTSEMEVENTINTERNAL)hEventSem;
+
+    int rc = DosPostEventSem(pThis->hev);
+
     switch (rc)
     {
         case NO_ERROR:
@@ -141,8 +226,247 @@
 
 }
 
+#if 1
+
+RTDECL(int)  RTSemEventMultiCreate(PRTSEMEVENTMULTI phEventMultiSem)
+{
+    return RTSemEventMultiCreateEx(phEventMultiSem, 0 /*fFlags*/, NIL_RTLOCKVALCLASS, NULL);
+}
+
+RTDECL(int)  RTSemEventMultiCreateEx(PRTSEMEVENTMULTI phEventMultiSem, uint32_t fFlags, RTLOCKVALCLASS hClass,
+                                     const char *pszNameFmt, ...)
+{
+    AssertReturn(!(fFlags & ~RTSEMEVENTMULTI_FLAGS_NO_LOCK_VAL), VERR_INVALID_PARAMETER);
+
+    /*
+     * Create the semaphore.
+     * (Manual reset, not signaled, private event object.)
+     */
+    HEV hev = NULLHANDLE;
+    PRTSEMEVENTMULTIINTERNAL pThis = NULL;
+
+    int rc = DosCreateEventSem(NULL, &hev, 0, FALSE);
+
+    if (!rc)
+    {
+        pThis = (PRTSEMEVENTMULTIINTERNAL)RTMemAlloc(sizeof(*pThis));
+        
+        if (! pThis)
+            return VERR_NO_MEMORY;
+
+        pThis->hev = hev;
+        pThis->u32Magic = RTSEMEVENTMULTI_MAGIC;
+        *phEventMultiSem  = (RTSEMEVENTMULTI)pThis;
+        return VINF_SUCCESS;
+    }
+
+    return RTErrConvertFromOS2(rc);
+}
+
+
+RTDECL(int)  RTSemEventMultiDestroy(RTSEMEVENTMULTI hEventMultiSem)
+{
+    if (hEventMultiSem == NIL_RTSEMEVENTMULTI)
+        return VINF_SUCCESS;
+
+    /*
+     * Close semaphore handle.
+     */
+    PRTSEMEVENTMULTIINTERNAL pThis = (PRTSEMEVENTMULTIINTERNAL)hEventMultiSem;
+
+    int rc = DosCloseEventSem(pThis->hev);
+
+    if (!rc)
+    {
+        RTMemFree(pThis);
+        return VINF_SUCCESS;
+    }
+
+    AssertMsgFailed(("Destroy hEventMultiSem %p failed, rc=%d\n", hEventMultiSem, rc));
+    return RTErrConvertFromOS2(rc);
+}
+
+
+RTDECL(int)  RTSemEventMultiSignal(RTSEMEVENTMULTI hEventMultiSem)
+{
+    /*
+     * Signal the object.
+     */
+    PRTSEMEVENTMULTIINTERNAL pThis = (PRTSEMEVENTMULTIINTERNAL)hEventMultiSem;
+
+    int rc = DosPostEventSem(pThis->hev);
+
+    switch (rc)
+    {
+        case NO_ERROR:
+        case ERROR_ALREADY_POSTED:
+        case ERROR_TOO_MANY_POSTS:
+            return VINF_SUCCESS;
+        default:
+            return RTErrConvertFromOS2(rc);
+    }
+}
+
+
+RTDECL(int)  RTSemEventMultiReset(RTSEMEVENTMULTI hEventMultiSem)
+{
+    /*
+     * Reset the object.
+     */
+    PRTSEMEVENTMULTIINTERNAL pThis = (PRTSEMEVENTMULTIINTERNAL)hEventMultiSem;
+    ULONG ulIgnore = 0;
+    int rc = DosResetEventSem(pThis->hev, &ulIgnore);
+    switch (rc)
+    {
+        case NO_ERROR:
+        case ERROR_ALREADY_RESET:
+            return VINF_SUCCESS;
+        default:
+            return RTErrConvertFromOS2(rc);
+    }
+}
+
+
+RTDECL(int)  RTSemEventMultiWaitNoResume(RTSEMEVENTMULTI hEventMultiSem, RTMSINTERVAL cMillies)
+{
+    /*
+     * Wait for condition.
+     */
+    PRTSEMEVENTMULTIINTERNAL pThis = (PRTSEMEVENTMULTIINTERNAL)hEventMultiSem;
+
+    int rc = DosWaitEventSem(pThis->hev, cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies);
+
+    switch (rc)
+    {
+        case NO_ERROR:              return VINF_SUCCESS;
+        case ERROR_SEM_TIMEOUT:
+        case ERROR_TIMEOUT:         return VERR_TIMEOUT;
+        case ERROR_INTERRUPT:       return VERR_INTERRUPTED;
+        default:
+        {
+            AssertMsgFailed(("Wait on hEventMultiSem %p failed, rc=%d\n", hEventMultiSem, rc));
+            rc = RTErrConvertFromOS2(rc);
+            return rc;
+        }
+    }
+}
+
+RTDECL(int) rtSemEventMultiOs2Wait(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout,
+                                       PCRTLOCKVALSRCPOS pSrcPos)
+{
+    /*
+     * Validate input.
+     */
+    PRTSEMEVENTMULTIINTERNAL pThis = (PRTSEMEVENTMULTIINTERNAL)hEventMultiSem;
+
+    AssertPtrReturn(pThis, VERR_INVALID_HANDLE);
+    AssertReturn(pThis->u32Magic == RTSEMEVENTMULTI_MAGIC, VERR_INVALID_HANDLE);
+    AssertReturn(RTSEMWAIT_FLAGS_ARE_VALID(fFlags), VERR_INVALID_PARAMETER);
+
+    /*
+     * Convert the timeout to a millisecond count.
+     */
+    uint64_t    uAbsDeadline;
+    LONG    	dwMsTimeout;
+
+    if (fFlags & RTSEMWAIT_FLAGS_INDEFINITE)
+    {
+        dwMsTimeout  = -1; // INFINITE;
+        uAbsDeadline = UINT64_MAX;
+    }
+    else
+    {
+        if (fFlags & RTSEMWAIT_FLAGS_NANOSECS)
+            uTimeout = uTimeout < UINT64_MAX - UINT32_C(1000000) / 2
+                     ? (uTimeout + UINT32_C(1000000) / 2) / UINT32_C(1000000)
+                     : UINT64_MAX / UINT32_C(1000000);
+        if (fFlags & RTSEMWAIT_FLAGS_ABSOLUTE)
+        {
+            uAbsDeadline = uTimeout;
+            uint64_t u64Now = RTTimeSystemMilliTS();
+            if (u64Now < uTimeout)
+                uTimeout -= u64Now;
+            else
+                uTimeout = 0;
+        }
+        else if (fFlags & RTSEMWAIT_FLAGS_RESUME)
+            uAbsDeadline = RTTimeSystemMilliTS() + uTimeout;
+        else
+            uAbsDeadline = UINT64_MAX;
+
+        dwMsTimeout = (uTimeout < UINT32_MAX)
+                    ? (LONG)uTimeout
+                    : (LONG)-1;
+    }
+
+    /*
+     * Do the wait.
+     */
+    int rc;
+#ifdef RTSEMEVENT_STRICT
+    RTTHREAD hThreadSelf = RTThreadSelfAutoAdopt();
+
+    if ((PRTSEMEVENTMULTIINTERNAL)pThis->fEverHadSignallers)
+    {
+        do
+            // rc = WaitForSingleObjectEx(pThis->hev, 0 /*Timeout*/, TRUE /*fAlertable*/);
+            rc = RTErrConvertFromOS2(DosWaitEventSem(pThis->hev, 0 /*Timeout*/));
+        while (rc == VERR_INTERRUPTED && (fFlags & RTSEMWAIT_FLAGS_RESUME));
+
+        if ((rc != VERR_INTERRUPTED && rc != VERR_TIMEOUT) || dwMsTimeout == 0)
+        {
+            //return rtSemEventWaitHandleStatus(pThis, fFlags, rc);
+            rc = RTErrConvertFromOS2(rc);
+            return rc;
+        }
+
+        int rc9 = RTLockValidatorRecSharedCheckBlocking(&pThis->Signallers, hThreadSelf, pSrcPos, false,
+                                                        dwMsTimeout, RTTHREADSTATE_EVENT_MULTI, true);
+        if (RT_FAILURE(rc9))
+            return rc9;
+    }
+#else
+    RTTHREAD hThreadSelf = RTThreadSelf();
+#endif
+    RTThreadBlocking(hThreadSelf, RTTHREADSTATE_EVENT_MULTI, true);
+
+    //rc = WaitForSingleObjectEx(pThis->hev, dwMsTimeout, TRUE /*fAlertable*/);
+    rc = RTErrConvertFromOS2(DosWaitEventSem(pThis->hev, dwMsTimeout));
+
+    if ((rc == VERR_INTERRUPTED || rc == VERR_TIMEOUT) && (fFlags & RTSEMWAIT_FLAGS_RESUME))
+    {
+        while ( (rc == VERR_INTERRUPTED || rc == VERR_TIMEOUT)
+               && RTTimeSystemMilliTS() < uAbsDeadline)
+            //rc = WaitForSingleObjectEx(pThis->hev, dwMsTimeout, TRUE /*fAlertable*/);
+            rc = RTErrConvertFromOS2(DosWaitEventSem(pThis->hev, dwMsTimeout));
+    }
+
+    RTThreadUnblocked(hThreadSelf, RTTHREADSTATE_EVENT_MULTI);
+
+    // return rtSemEventWaitHandleStatus(pThis, fFlags, rc);
+    return rc;
+}
+
+
+RTDECL(int)  RTSemEventMultiWaitEx(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout)
+{
+#ifndef RTSEMEVENT_STRICT
+    return rtSemEventMultiOs2Wait(hEventMultiSem, fFlags, uTimeout, NULL);
+#else
+    RTLOCKVALSRCPOS SrcPos = RTLOCKVALSRCPOS_INIT_NORMAL_API();
+    return rtSemEventMultiOs2Wait(hEventMultiSem, fFlags, uTimeout, &SrcPos);
+#endif
+}
 
 
+RTDECL(int)  RTSemEventMultiWaitExDebug(RTSEMEVENTMULTI hEventMultiSem, uint32_t fFlags, uint64_t uTimeout,
+                                        RTHCUINTPTR uId, RT_SRC_POS_DECL)
+{
+    RTLOCKVALSRCPOS SrcPos = RTLOCKVALSRCPOS_INIT_DEBUG_API();
+    return rtSemEventMultiOs2Wait(hEventMultiSem, fFlags, uTimeout, &SrcPos);
+}
+
+#else
 
 RTDECL(int)  RTSemEventMultiCreate(PRTSEMEVENTMULTI phEventMultiSem)
 {
@@ -242,6 +566,7 @@
     }
 }
 
+#endif
 
 RTDECL(void) RTSemEventMultiSetSignaller(RTSEMEVENTMULTI hEventMultiSem, RTTHREAD hThread)
 {
@@ -259,8 +584,6 @@
 }
 
 
-
-#undef RTSemMutexCreate
 RTDECL(int)  RTSemMutexCreate(PRTSEMMUTEX phMutexSem)
 {
     return RTSemMutexCreateEx(phMutexSem, 0 /*fFlags*/, NIL_RTLOCKVALCLASS, RTLOCKVAL_SUB_CLASS_NONE, NULL);
@@ -276,11 +599,19 @@
      * Create the semaphore.
      */
     HMTX hmtx;
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)RTMemAlloc(sizeof(*pThis));
+
+    if (! pThis)
+        return VERR_NO_MEMORY;
+
     int rc = DosCreateMutexSem(NULL, &hmtx, 0, FALSE);
-    if (!rc)
+
+    if (! rc)
     {
         /** @todo implement lock validation of OS/2 mutex semaphores. */
-        *phMutexSem = (RTSEMMUTEX)(void *)hmtx;
+        *phMutexSem = (RTSEMMUTEX)pThis;
+        pThis->hMtx = hmtx;
+        pThis->u32Magic = RTSEMMUTEX_MAGIC;
         return VINF_SUCCESS;
     }
 
@@ -296,9 +627,16 @@
     /*
      * Close semaphore handle.
      */
-    int rc = DosCloseMutexSem(SEM2HND(hMutexSem));
-    if (!rc)
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+
+    int rc = DosCloseMutexSem(pThis->hMtx);
+
+    if (! rc)
+    {
+        RTMemFree(pThis);
         return VINF_SUCCESS;
+    }
+
     AssertMsgFailed(("Destroy hMutexSem %p failed, rc=%d\n", hMutexSem, rc));
     return RTErrConvertFromOS2(rc);
 }
@@ -311,24 +649,25 @@
     /*
      * Validate.
      */
-    RTSEMMUTEXINTERNAL *pThis = hMutexSem;
+    RTSEMMUTEXINTERNAL *pThis = (RTSEMMUTEXINTERNAL *)hMutexSem;
     AssertPtrReturn(pThis, RTLOCKVAL_SUB_CLASS_INVALID);
     AssertReturn(pThis->u32Magic == RTSEMMUTEX_MAGIC, RTLOCKVAL_SUB_CLASS_INVALID);
 
-    return RTLockValidatorRecExclSetSubClass(&pThis->ValidatorRec, uSubClass);
+    return RTLockValidatorRecExclSetSubClass(pThis->ValidatorRec, uSubClass);
 #else
     return RTLOCKVAL_SUB_CLASS_INVALID;
 #endif
 }
 
-
-#undef RTSemMutexRequestNoResume
 RTDECL(int)  RTSemMutexRequestNoResume(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies)
 {
     /*
      * Lock mutex semaphore.
      */
-    int rc = DosRequestMutexSem(SEM2HND(hMutexSem), cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies);
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+
+    int rc = DosRequestMutexSem(pThis->hMtx, cMillies == RT_INDEFINITE_WAIT ? SEM_INDEFINITE_WAIT : cMillies);
+
     switch (rc)
     {
         case NO_ERROR:              return VINF_SUCCESS;
@@ -357,9 +696,13 @@
     /*
      * Unlock mutex semaphore.
      */
-    int rc = DosReleaseMutexSem(SEM2HND(hMutexSem));
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+
+    int rc = DosReleaseMutexSem(pThis->hMtx);
+
     if (!rc)
         return VINF_SUCCESS;
+
     AssertMsgFailed(("Release hMutexSem %p failed, rc=%d\n", hMutexSem, rc));
     return RTErrConvertFromOS2(rc);
 }
@@ -373,9 +716,14 @@
     PID     pid;
     TID     tid;
     ULONG   cRecursions;
-    int rc = DosQueryMutexSem(SEM2HND(hMutexSem), &pid, &tid, &cRecursions);
+
+    PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)hMutexSem;
+
+    int rc = DosQueryMutexSem(pThis->hMtx, &pid, &tid, &cRecursions);
+
     if (!rc)
         return cRecursions != 0;
+
     AssertMsgFailed(("DosQueryMutexSem %p failed, rc=%d\n", hMutexSem, rc));
     return rc == ERROR_SEM_OWNER_DIED;
 }
diff -urN vbox-clean-bk\src\VBox\Runtime/r3/os2/thread-os2.cpp vbox-clean\src\VBox\Runtime/r3/os2/thread-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r3/os2/thread-os2.cpp	2015-09-23 07:14:06.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r3/os2/thread-os2.cpp	2015-09-26 23:58:02.000000000 +0300
@@ -30,6 +30,7 @@
 *******************************************************************************/
 #define LOG_GROUP RTLOGGROUP_THREAD
 #define INCL_BASE
+#define INCL_PROCESS
 #include <os2.h>
 #undef RT_MAX
 
@@ -55,13 +56,14 @@
 *   Global Variables                                                           *
 *******************************************************************************/
 /** Pointer to thread local memory which points to the current thread. */
-static PRTTHREADINT *g_ppCurThread;
+static PRTTHREADINT *g_ppCurThread = NULL;
 
 
 /*******************************************************************************
 *   Internal Functions                                                         *
 *******************************************************************************/
 static void rtThreadNativeMain(void *pvArgs);
+static int rtOs2GetThreadOrdinal(void);
 
 
 DECLHIDDEN(int) rtThreadNativeInit(void)
@@ -69,7 +71,7 @@
     /*
      * Allocate thread local memory.
      */
-    PULONG pul;
+    PULONG pul = NULL;
     int rc = DosAllocThreadLocalMemory(1, &pul);
     if (rc)
         return VERR_NO_TLS_FOR_SELF;
@@ -101,6 +103,9 @@
 DECLHIDDEN(int) rtThreadNativeAdopt(PRTTHREADINT pThread)
 {
 
+    if (pThread == NULL)
+        return VERR_FAILED_TO_SET_SELF_TLS;
+
     *g_ppCurThread = pThread;
     return VINF_SUCCESS;
 }
@@ -118,27 +123,36 @@
  */
 static void rtThreadNativeMain(void *pvArgs)
 {
+    int   rc;
     rtThreadOs2BlockSigAlarm();
 
     /*
      * Call common main.
      */
+    RTNATIVETHREAD pNativeThread = RTThreadNativeSelf();
     PRTTHREADINT  pThread = (PRTTHREADINT)pvArgs;
+
+    Assert(pThread == NULL);
     *g_ppCurThread = pThread;
 
+#if 0
 #ifdef fibGetTidPid
-    rtThreadMain(pThread, fibGetTidPid(), &pThread->szName[0]);
+    rc = rtThreadMain(pThread, fibGetTidPid(), &pThread->szName[0]);
 #else
-    rtThreadMain(pThread, _gettid(), &pThread->szName[0]);
+    rc = rtThreadMain(pThread, (unsigned short)_gettid(), &pThread->szName[0]);
+#endif
 #endif
+    rc = rtThreadMain(pThread, pNativeThread, &pThread->szName[0]);
 
     *g_ppCurThread = NULL;
-    _endthread();
+    DosExit(EXIT_THREAD, rc);
 }
 
 
 DECLHIDDEN(int) rtThreadNativeCreate(PRTTHREADINT pThread, PRTNATIVETHREAD pNativeThread)
 {
+    AssertReturn(pThread->cbStack < ~(unsigned)0, VERR_INVALID_PARAMETER);
+
     /*
      * Default stack size.
      */
@@ -148,13 +162,17 @@
     /*
      * Create the thread.
      */
-    int iThreadId = _beginthread(rtThreadNativeMain, NULL, pThread->cbStack, pThread);
-    if (iThreadId > 0)
+    TID    tid = NULL;
+    APIRET rc;
+    rc = DosCreateThread(&tid, (PFNTHREAD)rtThreadNativeMain, (ULONG)pThread, 
+                         CREATE_READY | STACK_SPARSE, pThread->cbStack);
+    if (! rc)
     {
 #ifdef fibGetTidPid
-        *pNativeThread = iThreadId | (fibGetPid() << 16);
+        tid |= (fibGetPid() << 16);
+        *pNativeThread = tid;
 #else
-        *pNativeThread = iThreadId;
+        *pNativeThread = (unsigned short)tid;
 #endif
         return VINF_SUCCESS;
     }
@@ -165,10 +183,12 @@
 RTDECL(RTTHREAD) RTThreadSelf(void)
 {
     PRTTHREADINT pThread = *g_ppCurThread;
+    Assert(pThread == NULL);
+
     if (pThread)
         return (RTTHREAD)pThread;
     /** @todo import alien threads? */
-    return NULL;
+    return (RTTHREAD)NULL;
 }
 
 
@@ -318,3 +338,13 @@
 {
     return VERR_NOT_IMPLEMENTED;
 }
+
+DECLHIDDEN(int) rtOs2GetThreadOrdinal(void)
+{
+   PPIB ppib;
+   PTIB ptib;
+
+   DosGetInfoBlocks(&ptib, &ppib);
+
+   return (int)( ptib->tib_ordinal );
+}
diff -urN vbox-clean-bk\src\VBox\Runtime/r3/os2/time-os2.cpp vbox-clean\src\VBox\Runtime/r3/os2/time-os2.cpp
--- vbox-clean-bk\src\VBox\Runtime/r3/os2/time-os2.cpp	2015-09-23 07:14:06.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/r3/os2/time-os2.cpp	2015-09-26 23:57:50.000000000 +0300
@@ -1,6 +1,6 @@
 /* $Id: time-os2.cpp 3 2015-07-31 15:39:00Z dmik $ */
 /** @file
- * IPRT - Time, POSIX.
+ * IPRT - Time, OS/2.
  */
 
 /*
@@ -35,6 +35,9 @@
 #define LOG_GROUP RTLOGGROUP_TIME
 #include <InnoTekLIBC/FastInfoBlocks.h>
 
+#define  INCL_DOSPROFILE
+#include <os2.h>
+
 #include <iprt/time.h>
 #include "internal/time.h"
 
@@ -42,12 +45,31 @@
 
 RTDECL(uint64_t) RTTimeSystemNanoTS(void)
 {
-    return fibGetMsCount() * UINT64_C(10000000);
+    uint64_t t;
+    static ULONG freq = 0;
+    ULONGLONG time;
+#if 1
+    t = fibGetMsCount() * UINT64_C(1000000);
+#else
+    if (! freq)
+        DosTmrQueryFreq(&freq);
+
+    DosTmrQueryTime((QWORD *)&time);
+    t = (uint64_t)(time * 1000000000) / freq;
+#endif
+
+    return t;
 }
 
 
 RTDECL(uint64_t) RTTimeSystemMilliTS(void)
 {
-    return fibGetMsCount();
+    uint64_t t;
+#if 1
+    t = fibGetMsCount();
+#else
+    t = RTTimeSystemNanoTS() / 1000000;
+#endif
+    return t;
 }
 
diff -urN vbox-clean-bk\src\VBox\Runtime/testcase/Makefile.kmk vbox-clean\src\VBox\Runtime/testcase/Makefile.kmk
--- vbox-clean-bk\src\VBox\Runtime/testcase/Makefile.kmk	2015-09-23 07:14:08.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/testcase/Makefile.kmk	2015-09-27 00:24:36.000000000 +0300
@@ -125,8 +125,13 @@
 	tstRTTemp \
 	tstRTDirCreateUniqueNumbered \
 	tstTermCallbacks \
-	tstThread-1 \
-	tstRTThreadPoke \
+	tstThread-1
+
+ifdef RTTHREAD_POSIX_WITH_POKE
+PROGRAMS += \
+	tstRTThreadPoke
+endif
+PROGRAMS += \
 	tstRTThreadExecutionTime \
 	tstRTTime \
 	tstTime-2 \
diff -urN vbox-clean-bk\src\VBox\Runtime/testcase/tstLdrDisasmTest.cpp vbox-clean\src\VBox\Runtime/testcase/tstLdrDisasmTest.cpp
--- vbox-clean-bk\src\VBox\Runtime/testcase/tstLdrDisasmTest.cpp	2015-09-23 07:14:08.000000000 +0300
+++ vbox-clean\src\VBox\Runtime/testcase/tstLdrDisasmTest.cpp	2015-09-27 00:25:22.000000000 +0300
@@ -38,7 +38,7 @@
 #include <VBox/disopcode.h>
 #include <iprt/string.h>
 
-#if defined(IN_RING0) && !defined(RT_OS_WINDOWS) /* Too lazy to make import libs. */
+#if defined(IN_RING0) && !defined(RT_OS_WINDOWS) && !defined(RT_OS_OS2) /* Too lazy to make import libs. */
 extern "C" DECLIMPORT(int) MyPrintf(const char *pszFormat, ...);
 # define MY_PRINTF(a) MyPrintf a
 #else
