VirtualBox

Changeset 106925 in vbox for trunk


Ignore:
Timestamp:
Nov 11, 2024 11:59:38 AM (6 months ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
165851
Message:

/Config.kmk,SUPDrv: Introduced a VBOX_WITH_MINIMAL_HARDENING build config for windows hosts where we only require the process image and any r0 modules to be signed with the same certificate as the driver. This changeset implements the latter part. jiraref:VBP-1449

Location:
trunk
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/Config.kmk

    r106920 r106925  
    11471147## @name Hardening
    11481148## @{
     1149
    11491150# Enables hardening.
    1150 # Most developers will want to disable this in their LocalConfig.kmk.
    1151 VBOX_WITH_HARDENING = 1
     1151# Most developers will want to disable this in their LocalConfig.kmk (VBOX_WITHOUT_HARDENING := 1).
     1152ifndef VBOX_WITH_DRIVERLESS_FORCED # No need for hardening when not using the driver.
     1153 VBOX_WITH_HARDENING := 1
     1154endif
     1155# Enables minimal driver hardening (windows only).
     1156if !defined(VBOX_WITH_HARDENING) && !defined(VBOX_WITH_DRIVERLESS_FORCED)
     1157 if1of ($(KBUILD_TARGET).$(KBUILD_TARGET_ARCH), win.arm64)
     1158  VBOX_WITH_MINIMAL_HARDENING := 1
     1159 endif
     1160endif
    11521161# Where the application files are (going to be) installed.
    11531162#VBOX_PATH_APP_PRIVATE       = /usr/lib/virtualbox
     
    13651374  VBOX_WITH_JXPCOM :=
    13661375 endif
    1367 
    1368  ifdef VBOX_WITH_DRIVERLESS_FORCED
    1369   # No need for hardening when not using the driver.
    1370   VBOX_WITH_HARDENING :=
    1371  endif
    13721376endif
    13731377
     
    13921396 VBOX_WITH_INTERNAL_NETWORKING =
    13931397 VBOX_WITH_PDM_ASYNC_COMPLETION =
    1394  VBOX_WITH_HARDENING =
     1398 VBOX_WITHOUT_HARDENING = 1
    13951399endif
    13961400
     
    14071411 VBOX_WITH_DOCS =
    14081412 VBOX_WITH_PDM_ASYNC_COMPLETION =
    1409  VBOX_WITH_HARDENING =
     1413 VBOX_WITHOUT_HARDENING = 1
    14101414endif
    14111415
     
    14191423 VBOX_WITH_DOCS =
    14201424 VBOX_WITH_EHCI =
    1421  VBOX_WITH_HARDENING =
     1425 VBOX_WITHOUT_HARDENING = 1
    14221426 VBOX_WITH_HEADLESS =
    14231427 VBOX_WITH_HGCM =
  • trunk/src/VBox/HostDrivers/Support/Makefile.kmk

    r106893 r106925  
    716716
    717717  VBoxDrv_DEFS           := IN_RT_R0 IN_SUP_R0 SUPDRV_WITH_RELEASE_LOGGER VBOX_SVN_REV=$(VBOX_SVN_REV)
     718  ifdef VBOX_WITH_MINIMAL_R0
     719   VBoxDrv_DEFS          += VBOX_WITH_MINIMAL_R0
     720  endif
     721  ifdef VBOX_WITH_MINIMAL_HARDENING
     722   VBoxDrv_DEFS          += VBOX_WITH_MINIMAL_HARDENING
     723  endif
    718724  ifdef VBOX_WITH_DTRACE_R0DRV
    719725   VBoxDrv_DEFS          += VBOX_WITH_DTRACE VBOX_WITH_DTRACE_R0DRV
     
    798804  VBoxDrv_SOURCES.win.amd64 = \
    799805        win/SUPDrvA-win.asm
    800   ifdef VBOX_WITH_HARDENING
     806  if defined(VBOX_WITH_HARDENING) || defined(VBOX_WITH_MINIMAL_HARDENING)
    801807   VBoxDrv_SOURCES.win   += \
    802808        win/SUPHardenedVerifyImage-win.cpp \
    803         win/SUPHardenedVerifyProcess-win.cpp \
    804809        $(VBOX_SUP_WIN_CERTS_FILE)
     810   ifdef VBOX_WITH_HARDENING
     811    VBoxDrv_SOURCES.win  += \
     812        win/SUPHardenedVerifyProcess-win.cpp
     813   endif
    805814   ifdef VBOX_WITHOUT_WINDOWS_KERNEL_CODE_SIGNING_CERT
    806815    VBoxDrv_DEFS.win     += VBOX_WITHOUT_WINDOWS_KERNEL_CODE_SIGNING_CERT
  • trunk/src/VBox/HostDrivers/Support/win/SUPDrv-win.cpp

    r106625 r106925  
    7171#endif
    7272
    73 #ifdef VBOX_WITH_HARDENING
     73#if defined(VBOX_WITH_HARDENING) || defined(VBOX_WITH_MINIMAL_HARDENING)
    7474# include "SUPHardenedVerify-win.h"
    7575#endif
     
    458458#endif
    459459
     460#if defined(VBOX_WITH_HARDENING) || defined(VBOX_WITH_MINIMAL_HARDENING)
     461/** Combined windows NT version number.  See SUP_MAKE_NT_VER_COMBINED. */
     462uint32_t                            g_uNtVerCombined = 0;
     463#endif
    460464#ifdef VBOX_WITH_HARDENING
    461465/** Pointer to the stub device instance. */
     
    468472/** Cookie returned by ObRegisterCallbacks for the callbacks. */
    469473static PVOID                        g_pvObCallbacksCookie = NULL;
    470 /** Combined windows NT version number.  See SUP_MAKE_NT_VER_COMBINED. */
    471 uint32_t                            g_uNtVerCombined = 0;
    472474/** Pointer to ObGetObjectType if available.. */
    473475static PFNOBGETOBJECTTYPE           g_pfnObGetObjectType = NULL;
     
    653655
    654656    /*
    655      * Figure out if we can use NonPagedPoolNx or not.
     657     * Initialize the Nt version and figure out if we can use NonPagedPoolNx or not.
    656658     */
    657659    ULONG ulMajorVersion, ulMinorVersion, ulBuildNumber;
    658660    PsGetVersion(&ulMajorVersion, &ulMinorVersion, &ulBuildNumber, NULL);
     661#if defined(VBOX_WITH_HARDENING) || defined(VBOX_WITH_MINIMAL_HARDENING)
     662    g_uNtVerCombined = SUP_MAKE_NT_VER_COMBINED(ulMajorVersion, ulMinorVersion, ulBuildNumber, 0, 0);
     663#endif
    659664    if (ulMajorVersion > 6 || (ulMajorVersion == 6 && ulMinorVersion >= 2)) /* >= 6.2 (W8)*/
    660665        g_enmNonPagedPoolType = NonPagedPoolNx;
     
    22002205
    22012206
     2207# ifdef VBOX_WITH_MINIMAL_HARDENING
     2208/**
     2209 * Performs pre-opening of .r0 image checks.
     2210 * 
     2211 * When minimal hardening is enabled, we require the images loaded to be signed
     2212 * by the build certificate, thus liminiting what we load to things we have
     2213 * built ourselves.
     2214 */
     2215static int supdrvOSLdrCheckBeforeOpen(PUNICODE_STRING pUniStrPath, HANDLE *phImage)
     2216{
     2217    /*
     2218     * Open the image file, denying write accesses.
     2219     */
     2220    *phImage = RTNT_INVALID_HANDLE_VALUE;
     2221    IO_STATUS_BLOCK     Ios   = RTNT_IO_STATUS_BLOCK_INITIALIZER;
     2222
     2223    OBJECT_ATTRIBUTES   ObjAttr;
     2224    InitializeObjectAttributes(&ObjAttr, pUniStrPath, OBJ_CASE_INSENSITIVE, NULL /*hRootDir*/, NULL /*pSecDesc*/);
     2225    ObjAttr.Attributes |= OBJ_KERNEL_HANDLE;
     2226
     2227    NTSTATUS rcNt = NtCreateFile(phImage,
     2228                                 GENERIC_READ | SYNCHRONIZE,
     2229                                 &ObjAttr,
     2230                                 &Ios,
     2231                                 NULL /* Allocation Size*/,
     2232                                 FILE_ATTRIBUTE_NORMAL,
     2233                                 FILE_SHARE_READ,
     2234                                 FILE_OPEN,
     2235                                 FILE_NON_DIRECTORY_FILE | FILE_SYNCHRONOUS_IO_NONALERT,
     2236                                 NULL /*EaBuffer*/,
     2237                                 0 /*EaLength*/);
     2238    if (NT_SUCCESS(rcNt))
     2239        rcNt = Ios.Status;
     2240    int rc;
     2241    if (NT_SUCCESS(rcNt))
     2242    {
     2243        /*
     2244         * Verify the image, requiring the a build certificate.
     2245         */
     2246        PRTERRINFOSTATIC pErrInfo = (PRTERRINFOSTATIC)RTMemAllocZ(sizeof(*pErrInfo));
     2247        bool             fIgnored = false;
     2248        rc = supHardenedWinVerifyImageByHandle(*phImage, pUniStrPath->Buffer, SUPHNTVI_F_REQUIRE_BUILD_CERT,
     2249                                               fIgnored, &fIgnored, pErrInfo ? RTErrInfoInitStatic(pErrInfo) : NULL);
     2250        if (RT_SUCCESS(rc))
     2251            Log(("VBoxDrv: '%ls' checks out fine (%d)\n", pUniStrPath->Buffer, rc));
     2252        else
     2253            SUPR0Printf("VBoxDrv: Checking '%ls' failed: %Rrc%#RTeim\n", pUniStrPath->Buffer, rc, &pErrInfo->Core);
     2254        RTMemFree(pErrInfo);
     2255
     2256        if (RT_FAILURE(rc))
     2257        {
     2258            NtClose(*phImage);
     2259            *phImage = RTNT_INVALID_HANDLE_VALUE;
     2260        }
     2261    }
     2262    else
     2263        rc = RTErrConvertFromNtStatus(rcNt);
     2264    return rc;
     2265}
     2266# endif /* VBOX_WITH_MINIMAL_HARDENING */
     2267
     2268
    22022269#define MY_SystemLoadGdiDriverInSystemSpaceInformation  54
    22032270#define MY_SystemUnloadGdiDriverInformation             27
     
    22492316    {
    22502317        /*
    2251          * Try load it.
     2318         * Pre-screen it.
    22522319         */
    22532320        MYSYSTEMGDIDRIVERINFO Info;
    22542321        RtlInitUnicodeString(&Info.Name, pwcsFilename);
    2255         Info.ImageAddress           = NULL;
    2256         Info.SectionPointer         = NULL;
    2257         Info.EntryPointer           = NULL;
    2258         Info.ExportSectionPointer   = NULL;
    2259         Info.ImageLength            = 0;
    2260 
    2261         NTSTATUS rcNt = ZwSetSystemInformation(MY_SystemLoadGdiDriverInSystemSpaceInformation, &Info, sizeof(Info));
    2262         if (NT_SUCCESS(rcNt))
    2263         {
    2264             pImage->pvImage = Info.ImageAddress;
    2265             pImage->pvNtSectionObj = Info.SectionPointer;
    2266             Log(("ImageAddress=%p SectionPointer=%p ImageLength=%#x cbImageBits=%#x rcNt=%#x '%ls'\n",
    2267                  Info.ImageAddress, Info.SectionPointer, Info.ImageLength, pImage->cbImageBits, rcNt, Info.Name.Buffer));
     2322# ifdef VBOX_WITH_MINIMAL_HARDENING
     2323        HANDLE hImage = NULL;
     2324        rc = supdrvOSLdrCheckBeforeOpen(&Info.Name, &hImage);
     2325        if (RT_SUCCESS(rc))
     2326# endif
     2327        {
     2328            /*
     2329             * Try load it.
     2330             */
     2331            Info.ImageAddress           = NULL;
     2332            Info.SectionPointer         = NULL;
     2333            Info.EntryPointer           = NULL;
     2334            Info.ExportSectionPointer   = NULL;
     2335            Info.ImageLength            = 0;
     2336
     2337            NTSTATUS rcNt = ZwSetSystemInformation(MY_SystemLoadGdiDriverInSystemSpaceInformation, &Info, sizeof(Info));
     2338            if (NT_SUCCESS(rcNt))
     2339            {
     2340                pImage->pvImage = Info.ImageAddress;
     2341                pImage->pvNtSectionObj = Info.SectionPointer;
     2342                Log(("ImageAddress=%p SectionPointer=%p ImageLength=%#x cbImageBits=%#x rcNt=%#x '%ls'\n",
     2343                     Info.ImageAddress, Info.SectionPointer, Info.ImageLength, pImage->cbImageBits, rcNt, Info.Name.Buffer));
    22682344# ifdef DEBUG_bird
    2269             SUPR0Printf("ImageAddress=%p SectionPointer=%p ImageLength=%#x cbImageBits=%#x rcNt=%#x '%ls'\n",
    2270                         Info.ImageAddress, Info.SectionPointer, Info.ImageLength, pImage->cbImageBits, rcNt, Info.Name.Buffer);
     2345                SUPR0Printf("ImageAddress=%p SectionPointer=%p ImageLength=%#x cbImageBits=%#x rcNt=%#x '%ls'\n",
     2346                            Info.ImageAddress, Info.SectionPointer, Info.ImageLength, pImage->cbImageBits, rcNt, Info.Name.Buffer);
    22712347# endif
    2272             if (pImage->cbImageBits == Info.ImageLength)
    2273             {
    2274                 /*
    2275                  * Lock down the entire image, just to be on the safe side.
    2276                  */
    2277                 rc = RTR0MemObjLockKernel(&pImage->hMemLock, pImage->pvImage, pImage->cbImageBits, RTMEM_PROT_READ);
    2278                 if (RT_FAILURE(rc))
     2348                if (pImage->cbImageBits == Info.ImageLength)
    22792349                {
    2280                     pImage->hMemLock = NIL_RTR0MEMOBJ;
     2350                    /*
     2351                     * Lock down the entire image, just to be on the safe side.
     2352                     */
     2353                    rc = RTR0MemObjLockKernel(&pImage->hMemLock, pImage->pvImage, pImage->cbImageBits, RTMEM_PROT_READ);
     2354                    if (RT_FAILURE(rc))
     2355                    {
     2356                        pImage->hMemLock = NIL_RTR0MEMOBJ;
     2357                        supdrvOSLdrUnload(pDevExt, pImage);
     2358                    }
     2359                }
     2360                else
     2361                {
    22812362                    supdrvOSLdrUnload(pDevExt, pImage);
     2363                    rc = VERR_LDR_MISMATCH_NATIVE;
    22822364                }
    22832365            }
    22842366            else
    22852367            {
    2286                 supdrvOSLdrUnload(pDevExt, pImage);
    2287                 rc = VERR_LDR_MISMATCH_NATIVE;
    2288             }
    2289         }
    2290         else
    2291         {
    2292             Log(("rcNt=%#x '%ls'\n", rcNt, pwcsFilename));
    2293             SUPR0Printf("VBoxDrv: rcNt=%x '%ws'\n", rcNt, pwcsFilename);
    2294             switch (rcNt)
    2295             {
    2296                 case /* 0xc0000003 */ STATUS_INVALID_INFO_CLASS:
     2368                Log(("rcNt=%#x '%ls'\n", rcNt, pwcsFilename));
     2369                SUPR0Printf("VBoxDrv: rcNt=%x '%ws'\n", rcNt, pwcsFilename);
     2370                switch (rcNt)
     2371                {
     2372                    case /* 0xc0000003 */ STATUS_INVALID_INFO_CLASS:
    22972373# ifdef RT_ARCH_AMD64
    2298                     /* Unwind will crash and BSOD, so no fallback here! */
    2299                     rc = VERR_NOT_IMPLEMENTED;
     2374                        /* Unwind will crash and BSOD, so no fallback here! */
     2375                        rc = VERR_NOT_IMPLEMENTED;
    23002376# else
    2301                     /*
    2302                      * Use the old way of loading the modules.
    2303                      *
    2304                      * Note! We do *NOT* try class 26 because it will probably
    2305                      *       not work correctly on terminal servers and such.
    2306                      */
    2307                     rc = VERR_NOT_SUPPORTED;
     2377                        /*
     2378                         * Use the old way of loading the modules.
     2379                         *
     2380                         * Note! We do *NOT* try class 26 because it will probably
     2381                         *       not work correctly on terminal servers and such.
     2382                         */
     2383                        rc = VERR_NOT_SUPPORTED;
    23082384# endif
    2309                     break;
    2310                 case /* 0xc0000034 */ STATUS_OBJECT_NAME_NOT_FOUND:
    2311                     rc = VERR_MODULE_NOT_FOUND;
    2312                     break;
    2313                 case /* 0xC0000263 */ STATUS_DRIVER_ENTRYPOINT_NOT_FOUND:
    2314                     rc = VERR_LDR_IMPORTED_SYMBOL_NOT_FOUND;
    2315                     break;
    2316                 case /* 0xC0000428 */ STATUS_INVALID_IMAGE_HASH:
    2317                     rc = VERR_LDR_IMAGE_HASH;
    2318                     break;
    2319                 case /* 0xC000010E */ STATUS_IMAGE_ALREADY_LOADED:
    2320                     Log(("WARNING: see @bugref{4853} for cause of this failure on Windows 7 x64\n"));
    2321                     rc = VERR_ALREADY_LOADED;
    2322                     break;
    2323                 default:
    2324                     rc = VERR_LDR_GENERAL_FAILURE;
    2325                     break;
    2326             }
    2327 
    2328             pImage->pvNtSectionObj = NULL;
     2385                        break;
     2386                    case /* 0xc0000034 */ STATUS_OBJECT_NAME_NOT_FOUND:
     2387                        rc = VERR_MODULE_NOT_FOUND;
     2388                        break;
     2389                    case /* 0xC0000263 */ STATUS_DRIVER_ENTRYPOINT_NOT_FOUND:
     2390                        rc = VERR_LDR_IMPORTED_SYMBOL_NOT_FOUND;
     2391                        break;
     2392                    case /* 0xC0000428 */ STATUS_INVALID_IMAGE_HASH:
     2393                        rc = VERR_LDR_IMAGE_HASH;
     2394                        break;
     2395                    case /* 0xC000010E */ STATUS_IMAGE_ALREADY_LOADED:
     2396                        Log(("WARNING: see @bugref{4853} for cause of this failure on Windows 7 x64\n"));
     2397                        rc = VERR_ALREADY_LOADED;
     2398                        break;
     2399                    default:
     2400                        rc = VERR_LDR_GENERAL_FAILURE;
     2401                        break;
     2402                }
     2403
     2404                pImage->pvNtSectionObj = NULL;
     2405            }
     2406# ifdef VBOX_WITH_MINIMAL_HARDENING
     2407            NtClose(hImage);
     2408# endif
    23292409        }
    23302410    }
     
    54705550     */
    54715551
    5472     /* The NT version. */
    5473     ULONG uMajor, uMinor, uBuild;
    5474     PsGetVersion(&uMajor, &uMinor, &uBuild, NULL);
    5475     g_uNtVerCombined = SUP_MAKE_NT_VER_COMBINED(uMajor, uMinor, uBuild, 0, 0);
    5476 
    54775552    /* Resolve methods we want but isn't available everywhere. */
    54785553    UNICODE_STRING RoutineName;
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette