// Copyright (c) 2006-2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

// For information about interceptions as a whole see
// http://dev.chromium.org/developers/design-documents/sandbox .

#include "sandbox/src/interception_agent.h"

#include "sandbox/src/interception_internal.h"
#include "sandbox/src/interceptors.h"
#include "sandbox/src/eat_resolver.h"
#include "sandbox/src/sidestep_resolver.h"
#include "sandbox/src/sandbox_nt_util.h"

namespace {

// Returns true if target lies between base and base + range.
bool IsWithinRange(const void* base, size_t range, const void* target) {
  const char* end = reinterpret_cast<const char*>(base) + range;
  return reinterpret_cast<const char*>(target) < end;
}

}  // namespace

namespace sandbox {

// This is the list of all imported symbols from ntdll.dll.
SANDBOX_INTERCEPT NtExports g_nt;

// The list of intercepted functions back-pointers.
SANDBOX_INTERCEPT OriginalFunctions g_originals;

// Memory buffer mapped from the parent, with the list of interceptions.
SANDBOX_INTERCEPT SharedMemory* g_interceptions = NULL;

InterceptionAgent* InterceptionAgent::GetInterceptionAgent() {
  static InterceptionAgent* s_singleton = NULL;
  if (!s_singleton) {
    if (!g_interceptions)
      return NULL;

    size_t array_bytes = g_interceptions->num_intercepted_dlls * sizeof(void*);
    s_singleton = reinterpret_cast<InterceptionAgent*>(
        new(NT_ALLOC) char[array_bytes + sizeof(InterceptionAgent)]);

    bool success = s_singleton->Init(g_interceptions);
    if (!success) {
      operator delete(s_singleton, NT_ALLOC);
      s_singleton = NULL;
    }
  }
  return s_singleton;
}

bool InterceptionAgent::Init(SharedMemory* shared_memory) {
  interceptions_ = shared_memory;
  for (int i = 0 ; i < shared_memory->num_intercepted_dlls; i++)
    dlls_[i] = NULL;
  return true;
}

bool InterceptionAgent::DllMatch(const UNICODE_STRING* full_path,
                                 const UNICODE_STRING* name,
                                 const DllPatchInfo* dll_info) {
  UNICODE_STRING current_name;
  current_name.Length = static_cast<USHORT>(g_nt.wcslen(dll_info->dll_name) *
                                            sizeof(wchar_t));
  current_name.MaximumLength = current_name.Length;
  current_name.Buffer = const_cast<wchar_t*>(dll_info->dll_name);

  BOOLEAN case_insensitive = TRUE;
  if (full_path &&
      !g_nt.RtlCompareUnicodeString(&current_name, full_path, case_insensitive))
    return true;

  if (name &&
      !g_nt.RtlCompareUnicodeString(&current_name, name, case_insensitive))
    return true;

  return false;
}

bool InterceptionAgent::OnDllLoad(const UNICODE_STRING* full_path,
                                  const UNICODE_STRING* name,
                                  void* base_address) {
  DllPatchInfo* dll_info = interceptions_->dll_list;
  int i = 0;
  for (; i < interceptions_->num_intercepted_dlls; i++) {
    if (DllMatch(full_path, name, dll_info))
      break;

    dll_info = reinterpret_cast<DllPatchInfo*>(
                   reinterpret_cast<char*>(dll_info) + dll_info->record_bytes);
  }

  // Return now if the dll is not in our list of interest.
  if (i == interceptions_->num_intercepted_dlls)
    return true;

  // The dll must be unloaded.
  if (dll_info->unload_module)
    return false;

  // Purify causes this condition to trigger.
  if (dlls_[i])
    return true;

  size_t buffer_bytes = offsetof(DllInterceptionData, thunks) +
                        dll_info->num_functions * sizeof(ThunkData);
  dlls_[i] = reinterpret_cast<DllInterceptionData*>(
                 new(NT_PAGE, base_address) char[buffer_bytes]);

  DCHECK_NT(dlls_[i]);
  if (!dlls_[i])
    return true;

  dlls_[i]->data_bytes = buffer_bytes;
  dlls_[i]->num_thunks = 0;
  dlls_[i]->base = base_address;
  dlls_[i]->used_bytes = offsetof(DllInterceptionData, thunks);

  VERIFY(PatchDll(dll_info, dlls_[i]));

  ULONG old_protect;
  SIZE_T real_size = buffer_bytes;
  void* to_protect = dlls_[i];
  VERIFY_SUCCESS(g_nt.ProtectVirtualMemory(NtCurrentProcess, &to_protect,
                                           &real_size, PAGE_EXECUTE_READ,
                                           &old_protect));
  return true;
}

void InterceptionAgent::OnDllUnload(void* base_address) {
  for (int i = 0; i < interceptions_->num_intercepted_dlls; i++) {
    if (dlls_[i] && dlls_[i]->base == base_address) {
      operator delete(dlls_[i], NT_PAGE);
      dlls_[i] = NULL;
      break;
    }
  }
}

// TODO(rvargas): We have to deal with prebinded dlls. I see two options: change
// the timestamp of the patched dll, or modify the info on the prebinded dll.
// the first approach messes matching of debug symbols, the second one is more
// complicated.
bool InterceptionAgent::PatchDll(const DllPatchInfo* dll_info,
                                 DllInterceptionData* thunks) {
  DCHECK_NT(NULL != thunks);
  DCHECK_NT(NULL != dll_info);

  const FunctionInfo* function = reinterpret_cast<const FunctionInfo*>(
      reinterpret_cast<const char*>(dll_info) + dll_info->offset_to_functions);

  for (int i = 0; i < dll_info->num_functions; i++) {
    if (!IsWithinRange(dll_info, dll_info->record_bytes, function->function)) {
      NOTREACHED_NT();
      return false;
    }

    ResolverThunk* resolver = GetResolver(function->type);
    if (!resolver)
      return false;

    const char* interceptor = function->function +
                              g_nt.strlen(function->function) + 1;

    if (!IsWithinRange(function, function->record_bytes, interceptor) ||
        !IsWithinRange(dll_info, dll_info->record_bytes, interceptor)) {
      NOTREACHED_NT();
      return false;
    }

    NTSTATUS ret = resolver->Setup(thunks->base,
                                   interceptions_->interceptor_base,
                                   function->function,
                                   interceptor,
                                   function->interceptor_address,
                                   &thunks->thunks[i],
                                   sizeof(ThunkData),
                                   NULL);
    if (!NT_SUCCESS(ret)) {
      NOTREACHED_NT();
      return false;
    }

    DCHECK_NT(!g_originals[function->id]);
    g_originals[function->id] = &thunks->thunks[i];

    thunks->num_thunks++;
    thunks->used_bytes += sizeof(ThunkData);

    function = reinterpret_cast<const FunctionInfo*>(
        reinterpret_cast<const char*>(function) + function->record_bytes);
  }

  return true;
}

// This method is called from within the loader lock
ResolverThunk* InterceptionAgent::GetResolver(InterceptionType type) {
  static EatResolverThunk* eat_resolver = NULL;
  static SidestepResolverThunk* sidestep_resolver = NULL;
  static SmartSidestepResolverThunk* smart_sidestep_resolver = NULL;

  if (!eat_resolver)
    eat_resolver = new(NT_ALLOC) EatResolverThunk;

#if !defined(_WIN64)
  // Sidestep is not supported for x64.
  if (!sidestep_resolver)
    sidestep_resolver = new(NT_ALLOC) SidestepResolverThunk;

  if (!smart_sidestep_resolver)
    smart_sidestep_resolver = new(NT_ALLOC) SmartSidestepResolverThunk;
#endif

  switch (type) {
    case INTERCEPTION_EAT:
      return eat_resolver;
    case INTERCEPTION_SIDESTEP:
      return sidestep_resolver;
    case INTERCEPTION_SMART_SIDESTEP:
      return smart_sidestep_resolver;
    default:
      NOTREACHED_NT();
  }

  return NULL;
}

}  // namespace sandbox
