Home | History | Annotate | Download | only in src
      1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "sandbox/win/src/target_interceptions.h"
      6 
      7 #include "sandbox/win/src/interception_agent.h"
      8 #include "sandbox/win/src/sandbox_factory.h"
      9 #include "sandbox/win/src/sandbox_nt_util.h"
     10 #include "sandbox/win/src/target_services.h"
     11 
     12 namespace sandbox {
     13 
     14 SANDBOX_INTERCEPT NtExports g_nt;
     15 
     16 // Hooks NtMapViewOfSection to detect the load of DLLs. If hot patching is
     17 // required for this dll, this functions patches it.
     18 NTSTATUS WINAPI TargetNtMapViewOfSection(
     19     NtMapViewOfSectionFunction orig_MapViewOfSection, HANDLE section,
     20     HANDLE process, PVOID *base, ULONG_PTR zero_bits, SIZE_T commit_size,
     21     PLARGE_INTEGER offset, PSIZE_T view_size, SECTION_INHERIT inherit,
     22     ULONG allocation_type, ULONG protect) {
     23   NTSTATUS ret = orig_MapViewOfSection(section, process, base, zero_bits,
     24                                        commit_size, offset, view_size, inherit,
     25                                        allocation_type, protect);
     26 
     27   static int s_load_count = 0;
     28   if (1 == s_load_count) {
     29     SandboxFactory::GetTargetServices()->GetState()->SetKernel32Loaded();
     30     s_load_count = 2;
     31   }
     32 
     33   do {
     34     if (!NT_SUCCESS(ret))
     35       break;
     36 
     37     if (!InitHeap())
     38       break;
     39 
     40     if (!IsSameProcess(process))
     41       break;
     42 
     43     if (!IsValidImageSection(section, base, offset, view_size))
     44       break;
     45 
     46     UINT image_flags;
     47     UNICODE_STRING* module_name =
     48         GetImageInfoFromModule(reinterpret_cast<HMODULE>(*base), &image_flags);
     49     UNICODE_STRING* file_name = GetBackingFilePath(*base);
     50 
     51     if ((!module_name) && (image_flags & MODULE_HAS_CODE)) {
     52       // If the module has no exports we retrieve the module name from the
     53       // full path of the mapped section.
     54       module_name = ExtractModuleName(file_name);
     55     }
     56 
     57     InterceptionAgent* agent = InterceptionAgent::GetInterceptionAgent();
     58 
     59     if (agent) {
     60       if (!agent->OnDllLoad(file_name, module_name, *base)) {
     61         // Interception agent is demanding to un-map the module.
     62         g_nt.UnmapViewOfSection(process, *base);
     63         ret = STATUS_UNSUCCESSFUL;
     64       }
     65     }
     66 
     67     if (module_name)
     68       operator delete(module_name, NT_ALLOC);
     69 
     70     if (file_name)
     71       operator delete(file_name, NT_ALLOC);
     72 
     73   } while (false);
     74 
     75   if (!s_load_count)
     76     s_load_count = 1;
     77 
     78   return ret;
     79 }
     80 
     81 NTSTATUS WINAPI TargetNtUnmapViewOfSection(
     82     NtUnmapViewOfSectionFunction orig_UnmapViewOfSection, HANDLE process,
     83     PVOID base) {
     84   NTSTATUS ret = orig_UnmapViewOfSection(process, base);
     85 
     86   if (!NT_SUCCESS(ret))
     87     return ret;
     88 
     89   if (!IsSameProcess(process))
     90     return ret;
     91 
     92   InterceptionAgent* agent = InterceptionAgent::GetInterceptionAgent();
     93 
     94   if (agent)
     95     agent->OnDllUnload(base);
     96 
     97   return ret;
     98 }
     99 
    100 }  // namespace sandbox
    101