mirror of
https://github.com/mozilla/gecko-dev.git
synced 2025-02-05 22:05:40 +00:00
Bug 570096: Implement serialization of a grab-bag of gfx types. r=joe
This commit is contained in:
parent
6af3d8672d
commit
ac67f4dbc4
@ -44,7 +44,12 @@
|
||||
#include "prtypes.h"
|
||||
#include "nsStringGlue.h"
|
||||
#include "nsTArray.h"
|
||||
#include "gfx3DMatrix.h"
|
||||
#include "gfxColor.h"
|
||||
#include "gfxMatrix.h"
|
||||
#include "gfxPattern.h"
|
||||
#include "nsRect.h"
|
||||
#include "nsRegion.h"
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning( disable : 4800 )
|
||||
@ -53,6 +58,8 @@
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
typedef gfxPattern::GraphicsFilter GraphicsFilterType;
|
||||
|
||||
// XXX there are out of place and might be generally useful. Could
|
||||
// move to nscore.h or something.
|
||||
struct void_t {
|
||||
@ -250,6 +257,7 @@ struct ParamTraits<nsTArray<E> >
|
||||
return false;
|
||||
}
|
||||
|
||||
aResult->SetCapacity(length);
|
||||
for (PRUint32 index = 0; index < length; index++) {
|
||||
E* element = aResult->AppendElement();
|
||||
if (!(element && ReadParam(aMsg, aIter, element))) {
|
||||
@ -331,6 +339,98 @@ struct ParamTraits<gfxMatrix>
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<gfx3DMatrix>
|
||||
{
|
||||
typedef gfx3DMatrix paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
#define Wr(_f) WriteParam(msg, param. _f)
|
||||
Wr(_11); Wr(_12); Wr(_13); Wr(_14);
|
||||
Wr(_21); Wr(_22); Wr(_23); Wr(_24);
|
||||
Wr(_31); Wr(_32); Wr(_33); Wr(_34);
|
||||
Wr(_41); Wr(_42); Wr(_43); Wr(_44);
|
||||
#undef Wr
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
#define Rd(_f) ReadParam(msg, iter, &result-> _f)
|
||||
return (Rd(_11) && Rd(_12) && Rd(_13) && Rd(_14) &&
|
||||
Rd(_21) && Rd(_22) && Rd(_23) && Rd(_24) &&
|
||||
Rd(_31) && Rd(_32) && Rd(_33) && Rd(_34) &&
|
||||
Rd(_41) && Rd(_42) && Rd(_43) && Rd(_44));
|
||||
#undef Rd
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<mozilla::GraphicsFilterType>
|
||||
{
|
||||
typedef mozilla::GraphicsFilterType paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
switch (param) {
|
||||
case gfxPattern::FILTER_FAST:
|
||||
case gfxPattern::FILTER_GOOD:
|
||||
case gfxPattern::FILTER_BEST:
|
||||
case gfxPattern::FILTER_NEAREST:
|
||||
case gfxPattern::FILTER_BILINEAR:
|
||||
case gfxPattern::FILTER_GAUSSIAN:
|
||||
WriteParam(msg, int32(param));
|
||||
return;
|
||||
|
||||
default:
|
||||
NS_RUNTIMEABORT("not reached");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
int32 filter;
|
||||
if (!ReadParam(msg, iter, &filter))
|
||||
return false;
|
||||
|
||||
switch (filter) {
|
||||
case gfxPattern::FILTER_FAST:
|
||||
case gfxPattern::FILTER_GOOD:
|
||||
case gfxPattern::FILTER_BEST:
|
||||
case gfxPattern::FILTER_NEAREST:
|
||||
case gfxPattern::FILTER_BILINEAR:
|
||||
case gfxPattern::FILTER_GAUSSIAN:
|
||||
*result = paramType(filter);
|
||||
return true;
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
};
|
||||
template<>
|
||||
struct ParamTraits<gfxRGBA>
|
||||
{
|
||||
typedef gfxRGBA paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
WriteParam(msg, param.r);
|
||||
WriteParam(msg, param.g);
|
||||
WriteParam(msg, param.b);
|
||||
WriteParam(msg, param.a);
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
return (ReadParam(msg, iter, &result->r) &&
|
||||
ReadParam(msg, iter, &result->g) &&
|
||||
ReadParam(msg, iter, &result->b) &&
|
||||
ReadParam(msg, iter, &result->a));
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<mozilla::void_t>
|
||||
{
|
||||
@ -357,6 +457,91 @@ struct ParamTraits<mozilla::null_t>
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<nsIntPoint>
|
||||
{
|
||||
typedef nsIntPoint paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
WriteParam(msg, param.x);
|
||||
WriteParam(msg, param.y);
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
return (ReadParam(msg, iter, &result->x) &&
|
||||
ReadParam(msg, iter, &result->y));
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<nsIntRect>
|
||||
{
|
||||
typedef nsIntRect paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
WriteParam(msg, param.x);
|
||||
WriteParam(msg, param.y);
|
||||
WriteParam(msg, param.width);
|
||||
WriteParam(msg, param.height);
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
return (ReadParam(msg, iter, &result->x) &&
|
||||
ReadParam(msg, iter, &result->y) &&
|
||||
ReadParam(msg, iter, &result->width) &&
|
||||
ReadParam(msg, iter, &result->height));
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<nsIntRegion>
|
||||
{
|
||||
typedef nsIntRegion paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
nsIntRegionRectIterator it(param);
|
||||
while (const nsIntRect* r = it.Next())
|
||||
WriteParam(msg, *r);
|
||||
// empty rects are sentinel values because nsRegions will never
|
||||
// contain them
|
||||
WriteParam(msg, nsIntRect());
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
nsIntRect rect;
|
||||
while (ReadParam(msg, iter, &rect)) {
|
||||
if (rect.IsEmpty())
|
||||
return true;
|
||||
result->Or(*result, rect);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct ParamTraits<nsIntSize>
|
||||
{
|
||||
typedef nsIntSize paramType;
|
||||
|
||||
static void Write(Message* msg, const paramType& param)
|
||||
{
|
||||
WriteParam(msg, param.width);
|
||||
WriteParam(msg, param.height);
|
||||
}
|
||||
|
||||
static bool Read(const Message* msg, void** iter, paramType* result)
|
||||
{
|
||||
return (ReadParam(msg, iter, &result->width) &&
|
||||
ReadParam(msg, iter, &result->height));
|
||||
}
|
||||
};
|
||||
|
||||
} /* namespace IPC */
|
||||
|
||||
#endif /* __IPC_GLUE_IPCMESSAGEUTILS_H__ */
|
||||
|
@ -36,6 +36,8 @@
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
|
||||
#include "nsRegion.h"
|
||||
|
||||
#include "mozilla/ipc/IOThreadChild.h"
|
||||
|
||||
#include "IPDLUnitTestProcessChild.h"
|
||||
@ -52,6 +54,10 @@ IPDLUnitTestProcessChild::Init()
|
||||
IPDLUnitTestChildInit(IOThreadChild::channel(),
|
||||
ParentHandle(),
|
||||
IOThreadChild::message_loop());
|
||||
|
||||
if (NS_FAILED(nsRegion::InitStatic()))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -10,6 +10,8 @@
|
||||
#include "base/command_line.h"
|
||||
#include "base/string_util.h"
|
||||
|
||||
#include "nsRegion.h"
|
||||
|
||||
#include "IPDLUnitTestSubprocess.h"
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
@ -130,6 +132,9 @@ IPDLUnitTestMain(void* aData)
|
||||
}
|
||||
gIPDLUnitTestName = testString;
|
||||
|
||||
if (NS_FAILED(nsRegion::InitStatic()))
|
||||
fail("initializing nsRegion");
|
||||
|
||||
printf(MOZ_IPDL_TESTINFO_LABEL "| running test | %s\n", gIPDLUnitTestName);
|
||||
|
||||
std::vector<std::string> testCaseArgs;
|
||||
|
@ -1,6 +1,7 @@
|
||||
include protocol PTestDataStructuresSub;
|
||||
|
||||
using mozilla::null_t;
|
||||
using nsIntRegion;
|
||||
|
||||
namespace mozilla {
|
||||
namespace _foo {
|
||||
@ -177,6 +178,11 @@ parent:
|
||||
|
||||
sync Test17(Op[] ops);
|
||||
|
||||
// test that the ParamTraits<nsTArray>::Read() workaround for
|
||||
// nsTArray's incorrect memmove() semantics works properly
|
||||
// (nsIntRegion isn't memmove()able)
|
||||
sync Test18(nsIntRegion[] ops);
|
||||
|
||||
state START:
|
||||
send Start goto TEST1;
|
||||
|
||||
@ -196,7 +202,8 @@ state TEST13: recv Test13 goto TEST14;
|
||||
state TEST14: recv Test14 goto TEST15;
|
||||
state TEST15: recv Test15 goto TEST16;
|
||||
state TEST16: recv Test16 goto TEST17;
|
||||
state TEST17: recv Test17 goto DEAD;
|
||||
state TEST17: recv Test17 goto TEST18;
|
||||
state TEST18: recv Test18 goto DEAD;
|
||||
|
||||
state DEAD:
|
||||
recv __delete__;
|
||||
|
@ -1,7 +1,11 @@
|
||||
#include "mozilla/unused.h"
|
||||
|
||||
#include "TestDataStructures.h"
|
||||
|
||||
#include "IPDLUnitTests.h" // fail etc.
|
||||
|
||||
typedef nsTArray<nsIntRegion> RegionArray;
|
||||
|
||||
namespace mozilla {
|
||||
namespace _ipdltest {
|
||||
|
||||
@ -424,6 +428,19 @@ bool TestDataStructuresParent::RecvTest17(const nsTArray<Op>& sa)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool TestDataStructuresParent::RecvTest18(const RegionArray& ra)
|
||||
{
|
||||
for (RegionArray::index_type i = 0; i < ra.Length(); ++i) {
|
||||
nsIntRegionRectIterator it(ra[i]);
|
||||
// if |ra| has been realloc()d and given a different allocator
|
||||
// chunk, this next line will nondeterministically crash or
|
||||
// iloop
|
||||
while (const nsIntRect* sr = it.Next()) unused << sr;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// child
|
||||
|
||||
@ -459,6 +476,7 @@ TestDataStructuresChild::RecvStart()
|
||||
Test15();
|
||||
Test16();
|
||||
Test17();
|
||||
Test18();
|
||||
|
||||
for (uint32 i = 0; i < nactors; ++i)
|
||||
if (!PTestDataStructuresSubChild::Send__delete__(mKids[i]))
|
||||
@ -897,5 +915,27 @@ TestDataStructuresChild::Test17()
|
||||
printf(" passed %s\n", __FUNCTION__);
|
||||
}
|
||||
|
||||
void
|
||||
TestDataStructuresChild::Test18()
|
||||
{
|
||||
const int nelements = 1000;
|
||||
RegionArray ra;
|
||||
// big enough to hopefully force a realloc to a different chunk of
|
||||
// memory on the receiving side, if the workaround isn't working
|
||||
// correctly. But SetCapacity() here because we don't want to
|
||||
// crash on the sending side.
|
||||
ra.SetCapacity(nelements);
|
||||
for (int i = 0; i < nelements; ++i) {
|
||||
nsIntRegion r;
|
||||
r = r.Or(nsIntRect(0, 0, 10, 10), nsIntRect(10, 10, 10, 10));
|
||||
ra.AppendElement(r);
|
||||
}
|
||||
|
||||
if (!SendTest18(ra))
|
||||
fail("sending Test18");
|
||||
|
||||
printf(" passed %s\n", __FUNCTION__);
|
||||
}
|
||||
|
||||
} // namespace _ipdltest
|
||||
} // namespace mozilla
|
||||
|
@ -158,6 +158,9 @@ protected:
|
||||
NS_OVERRIDE
|
||||
virtual bool RecvTest17(const nsTArray<Op>& sa);
|
||||
|
||||
NS_OVERRIDE
|
||||
virtual bool RecvTest18(const nsTArray<nsIntRegion>& ra);
|
||||
|
||||
NS_OVERRIDE
|
||||
virtual void ActorDestroy(ActorDestroyReason why)
|
||||
{
|
||||
@ -224,6 +227,7 @@ private:
|
||||
void Test15();
|
||||
void Test16();
|
||||
void Test17();
|
||||
void Test18();
|
||||
|
||||
nsTArray<PTestDataStructuresSubChild*> mKids;
|
||||
};
|
||||
|
Loading…
x
Reference in New Issue
Block a user