gecko-dev/ipc/glue/CrossProcessSemaphore.h
Ryan Hunt 084c9b6f4c Allocate TextureReadLock at TextureClient creation and drop file handles immediately after. (bug 1416726, r=aosmond)
This changes the lifecycle and API for TextureReadLock to fix file descriptor exhaustion
crashes. These changes are partially superficial and mostly align the API of TextureReadLocks
with their actual usage.

The changes are:

1. Create the TextureReadLock in the TextureClient constructor so it's available before IPC creation
    a. This is superficial as EnableReadLock was always called before IPC creation
2. Send the ReadLockDescriptor in the PTextureConstructor message and close the file handle
3. Receive the ReadLockDescriptor in TextureHost and close the file handle
4. Send a boolean flag in layer transactions if the texture is read locked instead of a descriptor
5. Use a boolean flag in TextureHost to determine if the ReadLock must be unlocked instead of a nullptr

I believe that we can remove the InitReadLocks code from LayerTransaction as that was added to
prevent file descriptor limits in IPDL messages and is no longer needed with this change. But
that is a non-essential change and this patch is already big enough.

MozReview-Commit-ID: DzHujrOQejH

--HG--
extra : rebase_source : 3bdd7c9bc8edfdc386faad8a9e59ad7dc18ed91d
2018-03-12 08:10:13 -05:00

104 lines
2.8 KiB
C++

/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef mozilla_CrossProcessSemaphore_h
#define mozilla_CrossProcessSemaphore_h
#include "base/process.h"
#include "mozilla/TimeStamp.h"
#include "mozilla/Maybe.h"
#if !defined(OS_WIN) && !defined(OS_MACOSX)
#include <pthread.h>
#include <semaphore.h>
#include "SharedMemoryBasic.h"
#include "mozilla/Atomics.h"
#endif
namespace IPC {
template<typename T>
struct ParamTraits;
} // namespace IPC
//
// Provides:
//
// - CrossProcessSemaphore, a semaphore that can be shared across processes
namespace mozilla {
#if defined(OS_WIN)
typedef HANDLE CrossProcessSemaphoreHandle;
#elif !defined(OS_MACOSX)
typedef mozilla::ipc::SharedMemoryBasic::Handle CrossProcessSemaphoreHandle;
#else
// Stub for other platforms. We can't use uintptr_t here since different
// processes could disagree on its size.
typedef uintptr_t CrossProcessSemaphoreHandle;
#endif
class CrossProcessSemaphore
{
public:
/**
* CrossProcessSemaphore
* @param name A name which can reference this lock (currently unused)
**/
static CrossProcessSemaphore* Create(const char* aName, uint32_t aInitialValue);
/**
* CrossProcessSemaphore
* @param handle A handle of an existing cross process semaphore that can be
* opened.
*/
static CrossProcessSemaphore* Create(CrossProcessSemaphoreHandle aHandle);
~CrossProcessSemaphore();
/**
* Decrements the current value of the semaphore. This will block if the
* current value of the semaphore is 0, up to a maximum of aWaitTime (if
* specified).
* Returns true if the semaphore was succesfully decremented, false otherwise.
**/
bool Wait(const Maybe<TimeDuration>& aWaitTime = Nothing());
/**
* Increments the current value of the semaphore.
**/
void Signal();
/**
* ShareToProcess
* This function is called to generate a serializable structure that can
* be sent to the specified process and opened on the other side.
*
* @returns A handle that can be shared to another process
*/
CrossProcessSemaphoreHandle ShareToProcess(base::ProcessId aTargetPid);
void CloseHandle();
private:
friend struct IPC::ParamTraits<CrossProcessSemaphore>;
CrossProcessSemaphore();
CrossProcessSemaphore(const CrossProcessSemaphore&);
CrossProcessSemaphore &operator=(const CrossProcessSemaphore&);
#if defined(OS_WIN)
explicit CrossProcessSemaphore(HANDLE aSemaphore);
HANDLE mSemaphore;
#elif !defined(OS_MACOSX)
RefPtr<mozilla::ipc::SharedMemoryBasic> mSharedBuffer;
sem_t* mSemaphore;
mozilla::Atomic<int32_t>* mRefCount;
#endif
};
} // namespace mozilla
#endif