Trying to understand process mitigation policies that can be set by SetProcessMitigationPolicy function

2

Sorry, if it's too broad of a question. I'm trying to see what exactly SetProcessMitigationPolicy function does in Windows 10, but I can't find much about it online (besides my previous forays into this subject.) I'm testing its PROCESS_MITIGATION_POLICY options one-by-one, and I have some questions about these:

  1. ProcessSystemCallDisablePolicy states that it "Disables the ability to use NTUser/GDI functions at the lowest layer.". So I'm testing it as such:

    PROCESS_MITIGATION_SYSTEM_CALL_DISABLE_POLICY pmscdp = {0};
    pmscdp.DisallowWin32kSystemCalls = 1;
    BOOL bR = ::SetProcessMitigationPolicy(ProcessSystemCallDisablePolicy, &pmscdp, sizeof(pmscdp));
    int err = ::GetLastError();
    
    ::GdiFlush();   //Try to trip it here
    

    But it always fails with error code 19, or ERROR_WRITE_PROTECT.

    So what exactly is it supposed to do and how do I set it?

  2. ProcessExtensionPointDisablePolicy states that it "... prevents legacy extension point DLLs from being loaded into the process."

    PROCESS_MITIGATION_EXTENSION_POINT_DISABLE_POLICY pmepdp = {0};
    pmepdp.DisableExtensionPoints = 1;
    BOOL bR = ::SetProcessMitigationPolicy(ProcessExtensionPointDisablePolicy, &pmepdp, sizeof(pmepdp));
    int err = ::GetLastError();
    

    Sorry for my naivete, but what is the extension point DLL? And how can I test one?

  3. ProcessSignaturePolicy states that it can "restrict image loading to those images that are either signed by Microsoft, by the Windows Store, or by Microsoft, the Windows Store and the Windows Hardware Quality Labs (WHQL)".

    First off, it seems to have no effect on CreateProcess and only works with LoadLibrary-type functions. So if I do this:

    PROCESS_MITIGATION_BINARY_SIGNATURE_POLICY pmbsp = {0};
    pmbsp.MicrosoftSignedOnly = 1;
    //pmbsp.StoreSignedOnly = 1;   //always seems to fail with this flag
    //pmbsp.MitigationOptIn = 1;   //Doesn't seem to have any effect
    BOOL bR = ::SetProcessMitigationPolicy(ProcessSignaturePolicy, &pmbsp, sizeof(pmbsp));
    BOOL err = ::GetLastError();
    

    And then try to load some of my test DLLs:

    HMODULE hModDll = ::LoadLibrary(L".\\Dll1.dll");
    

    The LoadLibrary function fails with the MessageBox that reads:

    Bad Image

    Dll-Name is either not designed to run on Windows or it contains an error. Try installing the program again using the original installation media or contact your system administrator or the software vendor for support. Error status 0xc0000428.

    Interestingly, if I call it on some System32 DLL that is not signed:

    HMODULE hModDll = ::LoadLibrary(L"iologmsg.dll");
    

    it seems to work fine. But if I place a copy of my test Dll1.dll into System32 folder and load it this way:

    HMODULE hModDll = ::LoadLibrary(L"Dll1_.dll");
    

    it still fails with the same message box:

    enter image description here

    This is interesting. How can it tell the difference between iologmsg.dll and Dll1_.dll? Both files aren't signed.

    PS. And that modal message box can throw in a really nasty wrench into the mix if the app (or the service) does not expect any UI to be shown there.

  4. ProcessFontDisablePolicy lastly, I'm totally lost about this one. It states that it "turns off the ability of the process to load non-system fonts."

    So after I enable it in my MFC GUI app:

    PROCESS_MITIGATION_FONT_DISABLE_POLICY  pmfdp = {0};
    pmfdp.DisableNonSystemFonts = 1;
    BOOL bR = ::SetProcessMitigationPolicy(ProcessFontDisablePolicy, &pmfdp, sizeof(pmfdp));
    int err = ::GetLastError();
    

    the app has a Richedit control that I can load a custom font in. So I went online and downloaded a totally random font. Then installed it in Windows Explorer and tried to use it from the app after that policy has been enabled:

    //Set format for the text window
    CHARFORMAT cf = { 0 };
    cf.cbSize = sizeof(cf);
    cf.dwMask = CFM_FACE | CFM_SIZE;
    cf.yHeight = 18 * 20;
    VERIFY(SUCCEEDED(::StringCchCopy(cf.szFaceName, _countof(cf.szFaceName), L"Action Man")));
    VERIFY(SetDefaultCharFormat(cf));
    

    The app was able to display and use that (clearly non-system) font without any issues:

    enter image description here

    So what am I missing here in that policy?

c++
security
winapi
mfc
windows-10
asked on Stack Overflow Dec 31, 2018 by c00000fd

1 Answer

1

This is guessing, but since many links in the function's documentation are 404s, I believe that the following would be valid:

1.Probably not implemented, yet.

2.Only a guess (since the link is also 404), but it might refer to DLLs used in obsolete situtations (like the XP and below login DLL, replaced in Vista with Credential Providers).

3.Windows DLLs are treated as signed (without actually having a digital signature attached), not only because they reside in System32, but because Windows keeps internally a map for them. For your DLLs, it won't work. Also, this has no point in CreateProcess() because the new process cannot interact with yours (without your knowledge) and, therefore, cannot hijack it, where a DLL loaded with LoadLibrary can do anything to ruin your process.

4.It probably refers to fonts not installed by Explorer, but fonts added with AddFontResource.

answered on Stack Overflow Dec 31, 2018 by Michael Chourdakis

User contributions licensed under CC BY-SA 3.0