2010-05-13 08:52:59 -07:00
|
|
|
// vim:set ts=4 sts=4 sw=4 et cin:
|
2010-02-19 19:46:54 -08:00
|
|
|
/* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 4 -*-
|
2012-05-21 04:12:37 -07:00
|
|
|
* 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/. */
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2010-05-13 08:52:59 -07:00
|
|
|
#include "base/basictypes.h"
|
2010-02-19 19:46:54 -08:00
|
|
|
#include "gfxSharedImageSurface.h"
|
2010-05-13 08:52:59 -07:00
|
|
|
#include "cairo.h"
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2010-05-13 08:52:59 -07:00
|
|
|
#define MOZ_ALIGN_WORD(x) (((x) + 3) & ~3)
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
using namespace mozilla::ipc;
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2010-10-25 13:25:01 -07:00
|
|
|
static const cairo_user_data_key_t SHM_KEY = {0};
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
struct SharedImageInfo {
|
2012-08-22 08:56:38 -07:00
|
|
|
int32_t width;
|
|
|
|
int32_t height;
|
|
|
|
int32_t format;
|
2011-01-04 08:40:54 -08:00
|
|
|
};
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2010-05-13 08:52:59 -07:00
|
|
|
static SharedImageInfo*
|
2011-01-04 08:40:54 -08:00
|
|
|
GetShmInfoPtr(const Shmem& aShmem)
|
2010-02-19 19:46:54 -08:00
|
|
|
{
|
2010-05-13 08:52:59 -07:00
|
|
|
return reinterpret_cast<SharedImageInfo*>
|
|
|
|
(aShmem.get<char>() + aShmem.Size<char>() - sizeof(SharedImageInfo));
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
gfxSharedImageSurface::~gfxSharedImageSurface()
|
2010-02-19 19:46:54 -08:00
|
|
|
{
|
2011-01-11 13:34:31 -08:00
|
|
|
MOZ_COUNT_DTOR(gfxSharedImageSurface);
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
|
|
|
|
2011-09-28 23:19:26 -07:00
|
|
|
/*static*/ bool
|
2011-01-04 08:40:54 -08:00
|
|
|
gfxSharedImageSurface::IsSharedImage(gfxASurface* aSurface)
|
2010-02-19 19:46:54 -08:00
|
|
|
{
|
2011-01-04 08:40:54 -08:00
|
|
|
return (aSurface
|
|
|
|
&& aSurface->GetType() == gfxASurface::SurfaceTypeImage
|
|
|
|
&& aSurface->GetData(&SHM_KEY));
|
|
|
|
}
|
2010-02-19 19:46:54 -08:00
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
gfxSharedImageSurface::gfxSharedImageSurface(const gfxIntSize& aSize,
|
|
|
|
gfxImageFormat aFormat,
|
|
|
|
const Shmem& aShmem)
|
|
|
|
{
|
2011-01-11 13:34:31 -08:00
|
|
|
MOZ_COUNT_CTOR(gfxSharedImageSurface);
|
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
mSize = aSize;
|
|
|
|
mFormat = aFormat;
|
|
|
|
mStride = ComputeStride(aSize, aFormat);
|
|
|
|
mShmem = aShmem;
|
2011-01-05 11:42:09 -08:00
|
|
|
mData = aShmem.get<unsigned char>();
|
2010-05-13 08:52:59 -07:00
|
|
|
cairo_surface_t *surface =
|
2011-01-05 11:42:09 -08:00
|
|
|
cairo_image_surface_create_for_data(mData,
|
2010-05-13 08:52:59 -07:00
|
|
|
(cairo_format_t)mFormat,
|
|
|
|
mSize.width,
|
|
|
|
mSize.height,
|
|
|
|
mStride);
|
2011-01-04 08:40:54 -08:00
|
|
|
if (surface) {
|
|
|
|
cairo_surface_set_user_data(surface, &SHM_KEY, this, NULL);
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
2011-01-04 08:40:54 -08:00
|
|
|
Init(surface);
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
void
|
|
|
|
gfxSharedImageSurface::WriteShmemInfo()
|
2010-02-19 19:46:54 -08:00
|
|
|
{
|
2011-01-04 08:40:54 -08:00
|
|
|
SharedImageInfo* shmInfo = GetShmInfoPtr(mShmem);
|
|
|
|
shmInfo->width = mSize.width;
|
|
|
|
shmInfo->height = mSize.height;
|
|
|
|
shmInfo->format = mFormat;
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
/*static*/ size_t
|
|
|
|
gfxSharedImageSurface::GetAlignedSize(const gfxIntSize& aSize, long aStride)
|
2010-02-19 19:46:54 -08:00
|
|
|
{
|
2011-01-04 08:40:54 -08:00
|
|
|
return MOZ_ALIGN_WORD(sizeof(SharedImageInfo) + aSize.height * aStride);
|
2010-02-19 19:46:54 -08:00
|
|
|
}
|
2010-06-04 06:58:22 -07:00
|
|
|
|
2011-01-04 08:40:54 -08:00
|
|
|
/*static*/ already_AddRefed<gfxSharedImageSurface>
|
|
|
|
gfxSharedImageSurface::Open(const Shmem& aShmem)
|
2010-06-04 06:58:22 -07:00
|
|
|
{
|
2011-01-04 08:40:54 -08:00
|
|
|
SharedImageInfo* shmInfo = GetShmInfoPtr(aShmem);
|
|
|
|
gfxIntSize size(shmInfo->width, shmInfo->height);
|
|
|
|
if (!CheckSurfaceSize(size))
|
2012-07-30 07:20:58 -07:00
|
|
|
return nullptr;
|
2011-01-04 08:40:54 -08:00
|
|
|
|
|
|
|
nsRefPtr<gfxSharedImageSurface> s =
|
|
|
|
new gfxSharedImageSurface(size,
|
|
|
|
(gfxImageFormat)shmInfo->format,
|
|
|
|
aShmem);
|
|
|
|
// We didn't create this Shmem and so don't free it on errors
|
2012-07-30 07:20:58 -07:00
|
|
|
return (s->CairoStatus() != 0) ? nullptr : s.forget();
|
2010-06-04 06:58:22 -07:00
|
|
|
}
|