tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

SharedMemoryPlatform_android.cpp (4053B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
      3 /* This Source Code Form is subject to the terms of the Mozilla Public
      4 * License, v. 2.0. If a copy of the MPL was not distributed with this
      5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      6 
      7 /* This source code was derived from Chromium code, and as such is also subject
      8 * to the [Chromium license](ipc/chromium/src/LICENSE). */
      9 
     10 #include "SharedMemoryPlatform.h"
     11 
     12 #include <errno.h>
     13 #include <fcntl.h>
     14 #include <sys/mman.h>
     15 #include <sys/stat.h>
     16 #include <unistd.h>
     17 
     18 #include <android/sharedmem.h>
     19 
     20 #ifdef MOZ_VALGRIND
     21 #  include <valgrind/valgrind.h>
     22 #endif
     23 
     24 #include "mozilla/Maybe.h"
     25 #include "mozilla/UniquePtrExtensions.h"
     26 #include "prenv.h"
     27 
     28 namespace mozilla::ipc::shared_memory {
     29 
     30 // Right now we do nothing different for freezable shared memory on Android.
     31 static Maybe<PlatformHandle> CreateImpl(size_t aSize, bool aFreezable) {
     32  MOZ_ASSERT(aSize > 0);
     33 
     34  int fd = ASharedMemory_create(nullptr, aSize);
     35  if (fd < 0) {
     36    MOZ_LOG_FMT(gSharedMemoryLog, LogLevel::Warning, "failed to open shm: {}",
     37                strerror(errno));
     38    return Nothing();
     39  }
     40 
     41  return Some(fd);
     42 }
     43 
     44 bool AppendPosixShmPrefix(std::string* str, pid_t pid) { return false; }
     45 bool UsingPosixShm() { return false; }
     46 
     47 bool Platform::Create(MutableHandle& aHandle, size_t aSize) {
     48  if (auto ph = CreateImpl(aSize, false)) {
     49    aHandle.mHandle = std::move(*ph);
     50    aHandle.SetSize(aSize);
     51    return true;
     52  }
     53  return false;
     54 }
     55 
     56 bool Platform::CreateFreezable(FreezableHandle& aHandle, size_t aSize) {
     57  if (auto ph = CreateImpl(aSize, true)) {
     58    aHandle.mHandle = std::move(*ph);
     59    aHandle.SetSize(aSize);
     60    return true;
     61  }
     62  return false;
     63 }
     64 
     65 PlatformHandle Platform::CloneHandle(const PlatformHandle& aHandle) {
     66  const int new_fd = dup(aHandle.get());
     67  if (new_fd < 0) {
     68    MOZ_LOG_FMT(gSharedMemoryLog, LogLevel::Warning,
     69                "failed to duplicate file descriptor: {}", strerror(errno));
     70    return nullptr;
     71  }
     72  return mozilla::UniqueFileHandle(new_fd);
     73 }
     74 
     75 bool Platform::Freeze(FreezableHandle& aHandle) {
     76  if (ASharedMemory_setProt(aHandle.mHandle.get(), PROT_READ) != 0) {
     77    MOZ_LOG_FMT(gSharedMemoryLog, LogLevel::Warning,
     78                "failed to set sharedmem read-only: {}", strerror(errno));
     79    return false;
     80  }
     81  return true;
     82 }
     83 
     84 Maybe<void*> Platform::Map(const HandleBase& aHandle, uint64_t aOffset,
     85                           size_t aSize, void* aFixedAddress, bool aReadOnly) {
     86  // Don't use MAP_FIXED when a fixed_address was specified, since that can
     87  // replace pages that are alread mapped at that address.
     88  void* mem =
     89      mmap(aFixedAddress, aSize, PROT_READ | (aReadOnly ? 0 : PROT_WRITE),
     90           MAP_SHARED, aHandle.mHandle.get(), aOffset);
     91 
     92  if (mem == MAP_FAILED) {
     93    MOZ_LOG_FMT(gSharedMemoryLog, LogLevel::Warning, "call to mmap failed: {}",
     94                strerror(errno));
     95    return Nothing();
     96  }
     97 
     98  if (aFixedAddress && mem != aFixedAddress) {
     99    DebugOnly<bool> munmap_succeeded = munmap(mem, aSize) == 0;
    100    MOZ_ASSERT(munmap_succeeded, "call to munmap failed");
    101    return Nothing();
    102  }
    103 
    104  return Some(mem);
    105 }
    106 
    107 void Platform::Unmap(void* aMemory, size_t aSize) { munmap(aMemory, aSize); }
    108 
    109 bool Platform::Protect(char* aAddr, size_t aSize, Access aAccess) {
    110  int flags = PROT_NONE;
    111  if (aAccess & AccessRead) flags |= PROT_READ;
    112  if (aAccess & AccessWrite) flags |= PROT_WRITE;
    113 
    114  return 0 == mprotect(aAddr, aSize, flags);
    115 }
    116 
    117 void* Platform::FindFreeAddressSpace(size_t aSize) {
    118  void* memory = mmap(nullptr, aSize, PROT_NONE,
    119                      MAP_ANONYMOUS | MAP_NORESERVE | MAP_PRIVATE, -1, 0);
    120  if (memory == MAP_FAILED) {
    121    return nullptr;
    122  }
    123  munmap(memory, aSize);
    124  return memory;
    125 }
    126 
    127 size_t Platform::PageSize() { return sysconf(_SC_PAGESIZE); }
    128 
    129 size_t Platform::AllocationGranularity() { return PageSize(); }
    130 
    131 bool Platform::IsSafeToMap(const PlatformHandle&) { return true; }
    132 
    133 }  // namespace mozilla::ipc::shared_memory