Coverage Report

Created: 2018-09-25 14:53

/src/mozilla-central/gfx/2d/RecordedEvent.h
Line
Count
Source (jump to first uncovered line)
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
#ifndef MOZILLA_GFX_RECORDEDEVENT_H_
8
#define MOZILLA_GFX_RECORDEDEVENT_H_
9
10
#include "2D.h"
11
#include <ostream>
12
#include <sstream>
13
#include <cstring>
14
#include <vector>
15
16
namespace mozilla {
17
namespace gfx {
18
19
struct PathOp;
20
class PathRecording;
21
22
const uint32_t kMagicInt = 0xc001feed;
23
24
// A change in major revision means a change in event binary format, causing
25
// loss of backwards compatibility. Old streams will not work in a player
26
// using a newer major revision. And new streams will not work in a player
27
// using an older major revision.
28
const uint16_t kMajorRevision = 10;
29
// A change in minor revision means additions of new events. New streams will
30
// not play in older players.
31
const uint16_t kMinorRevision = 0;
32
33
struct ReferencePtr
34
{
35
  ReferencePtr()
36
    : mLongPtr(0)
37
0
  {}
38
39
  MOZ_IMPLICIT ReferencePtr(const void* aLongPtr)
40
    : mLongPtr(uint64_t(aLongPtr))
41
0
  {}
42
43
  template <typename T>
44
  MOZ_IMPLICIT ReferencePtr(const RefPtr<T>& aPtr)
45
    : mLongPtr(uint64_t(aPtr.get()))
46
0
  {}
Unexecuted instantiation: mozilla::gfx::ReferencePtr::ReferencePtr<mozilla::gfx::PathRecording>(RefPtr<mozilla::gfx::PathRecording> const&)
Unexecuted instantiation: mozilla::gfx::ReferencePtr::ReferencePtr<mozilla::gfx::SourceSurface>(RefPtr<mozilla::gfx::SourceSurface> const&)
Unexecuted instantiation: mozilla::gfx::ReferencePtr::ReferencePtr<mozilla::gfx::FilterNode>(RefPtr<mozilla::gfx::FilterNode> const&)
Unexecuted instantiation: mozilla::gfx::ReferencePtr::ReferencePtr<mozilla::gfx::GradientStops>(RefPtr<mozilla::gfx::GradientStops> const&)
47
48
0
  ReferencePtr &operator =(const void* aLongPtr) {
49
0
    mLongPtr = uint64_t(aLongPtr);
50
0
    return *this;
51
0
  }
52
53
  template <typename T>
54
0
  ReferencePtr &operator =(const RefPtr<T>& aPtr) {
55
0
    mLongPtr = uint64_t(aPtr.get());
56
0
    return *this;
57
0
  }
58
59
0
  operator void*() const {
60
0
    return (void*)mLongPtr;
61
0
  }
62
63
  uint64_t mLongPtr;
64
};
65
66
struct RecordedFontDetails
67
{
68
  uint64_t fontDataKey;
69
  uint32_t size;
70
  uint32_t index;
71
};
72
73
// Used by the Azure drawing debugger (player2d)
74
inline std::string StringFromPtr(ReferencePtr aPtr)
75
0
{
76
0
  std::stringstream stream;
77
0
  stream << aPtr;
78
0
  return stream.str();
79
0
}
80
81
class Translator
82
{
83
public:
84
0
  virtual ~Translator() {}
85
86
  virtual DrawTarget *LookupDrawTarget(ReferencePtr aRefPtr) = 0;
87
  virtual Path *LookupPath(ReferencePtr aRefPtr) = 0;
88
  virtual SourceSurface *LookupSourceSurface(ReferencePtr aRefPtr) = 0;
89
  virtual FilterNode *LookupFilterNode(ReferencePtr aRefPtr) = 0;
90
  virtual GradientStops *LookupGradientStops(ReferencePtr aRefPtr) = 0;
91
  virtual ScaledFont *LookupScaledFont(ReferencePtr aRefPtr) = 0;
92
  virtual UnscaledFont* LookupUnscaledFont(ReferencePtr aRefPtr) = 0;
93
  virtual NativeFontResource *LookupNativeFontResource(uint64_t aKey) = 0;
94
0
  virtual already_AddRefed<SourceSurface> LookupExternalSurface(uint64_t aKey) { return nullptr; }
95
  virtual void AddDrawTarget(ReferencePtr aRefPtr, DrawTarget *aDT) = 0;
96
  virtual void RemoveDrawTarget(ReferencePtr aRefPtr) = 0;
97
  virtual void AddPath(ReferencePtr aRefPtr, Path *aPath) = 0;
98
  virtual void RemovePath(ReferencePtr aRefPtr) = 0;
99
  virtual void AddSourceSurface(ReferencePtr aRefPtr, SourceSurface *aPath) = 0;
100
  virtual void RemoveSourceSurface(ReferencePtr aRefPtr) = 0;
101
  virtual void AddFilterNode(mozilla::gfx::ReferencePtr aRefPtr, FilterNode *aSurface) = 0;
102
  virtual void RemoveFilterNode(mozilla::gfx::ReferencePtr aRefPtr) = 0;
103
  virtual void AddGradientStops(ReferencePtr aRefPtr, GradientStops *aPath) = 0;
104
  virtual void RemoveGradientStops(ReferencePtr aRefPtr) = 0;
105
  virtual void AddScaledFont(ReferencePtr aRefPtr, ScaledFont *aScaledFont) = 0;
106
  virtual void RemoveScaledFont(ReferencePtr aRefPtr) = 0;
107
  virtual void AddUnscaledFont(ReferencePtr aRefPtr, UnscaledFont* aUnscaledFont) = 0;
108
  virtual void RemoveUnscaledFont(ReferencePtr aRefPtr) = 0;
109
  virtual void AddNativeFontResource(uint64_t aKey,
110
                                     NativeFontResource *aNativeFontResource) = 0;
111
112
  virtual already_AddRefed<DrawTarget> CreateDrawTarget(ReferencePtr aRefPtr,
113
                                                        const IntSize &aSize,
114
                                                        SurfaceFormat aFormat);
115
  virtual DrawTarget *GetReferenceDrawTarget() = 0;
116
0
  virtual void* GetFontContext() { return nullptr; }
117
};
118
119
struct ColorPatternStorage
120
{
121
  Color mColor;
122
};
123
124
struct LinearGradientPatternStorage
125
{
126
  Point mBegin;
127
  Point mEnd;
128
  ReferencePtr mStops;
129
  Matrix mMatrix;
130
};
131
132
struct RadialGradientPatternStorage
133
{
134
  Point mCenter1;
135
  Point mCenter2;
136
  Float mRadius1;
137
  Float mRadius2;
138
  ReferencePtr mStops;
139
  Matrix mMatrix;
140
};
141
142
struct SurfacePatternStorage
143
{
144
  ExtendMode mExtend;
145
  SamplingFilter mSamplingFilter;
146
  ReferencePtr mSurface;
147
  Matrix mMatrix;
148
  IntRect mSamplingRect;
149
};
150
151
struct PatternStorage
152
{
153
  PatternType mType;
154
  union {
155
    char *mStorage;
156
    char mColor[sizeof(ColorPatternStorage)];
157
    char mLinear[sizeof(LinearGradientPatternStorage)];
158
    char mRadial[sizeof(RadialGradientPatternStorage)];
159
    char mSurface[sizeof(SurfacePatternStorage)];
160
  };
161
};
162
163
164
/* SizeCollector and MemWriter are used
165
 * in a pair to first collect the size of the
166
 * event that we're going to write and then
167
 * to write it without checking each individual
168
 * size. */
169
struct SizeCollector {
170
0
  SizeCollector() : mTotalSize(0) {}
171
0
    void write(const char*, size_t s) {
172
0
      mTotalSize += s;
173
0
    }
174
  size_t mTotalSize;
175
};
176
177
struct MemWriter {
178
0
  explicit MemWriter(char* aPtr) : mPtr(aPtr) {}
179
0
    void write(const char* aData, size_t aSize) {
180
0
       memcpy(mPtr, aData, aSize);
181
0
       mPtr += aSize;
182
0
    }
183
  char* mPtr;
184
};
185
186
struct MemStream {
187
  char *mData;
188
  size_t mLength;
189
  size_t mCapacity;
190
0
  void Resize(size_t aSize) {
191
0
    mLength = aSize;
192
0
    if (mLength > mCapacity) {
193
0
      mCapacity = mCapacity * 2;
194
0
      // check if the doubled capacity is enough
195
0
      // otherwise use double mLength
196
0
      if (mLength > mCapacity) {
197
0
        mCapacity = mLength * 2;
198
0
      }
199
0
      mData = (char*)realloc(mData, mCapacity);
200
0
    }
201
0
  }
202
203
0
  void write(const char* aData, size_t aSize) {
204
0
    Resize(mLength + aSize);
205
0
    memcpy(mData + mLength - aSize, aData, aSize);
206
0
  }
207
208
0
  MemStream() : mData(nullptr), mLength(0), mCapacity(0) {}
209
0
  ~MemStream() { free(mData); }
210
};
211
212
class EventStream {
213
public:
214
  virtual void write(const char* aData, size_t aSize) = 0;
215
  virtual void read(char* aOut, size_t aSize) = 0;
216
};
217
218
class RecordedEvent {
219
public:
220
  enum EventType {
221
    DRAWTARGETCREATION = 0,
222
    DRAWTARGETDESTRUCTION,
223
    FILLRECT,
224
    STROKERECT,
225
    STROKELINE,
226
    CLEARRECT,
227
    COPYSURFACE,
228
    SETTRANSFORM,
229
    PUSHCLIP,
230
    PUSHCLIPRECT,
231
    POPCLIP,
232
    FILL,
233
    FILLGLYPHS,
234
    MASK,
235
    STROKE,
236
    DRAWSURFACE,
237
    DRAWSURFACEWITHSHADOW,
238
    PATHCREATION,
239
    PATHDESTRUCTION,
240
    SOURCESURFACECREATION,
241
    SOURCESURFACEDESTRUCTION,
242
    GRADIENTSTOPSCREATION,
243
    GRADIENTSTOPSDESTRUCTION,
244
    SNAPSHOT,
245
    SCALEDFONTCREATION,
246
    SCALEDFONTDESTRUCTION,
247
    MASKSURFACE,
248
    FILTERNODECREATION,
249
    FILTERNODEDESTRUCTION,
250
    DRAWFILTER,
251
    FILTERNODESETATTRIBUTE,
252
    FILTERNODESETINPUT,
253
    CREATESIMILARDRAWTARGET,
254
    CREATECLIPPEDDRAWTARGET,
255
    FONTDATA,
256
    FONTDESC,
257
    PUSHLAYER,
258
    PUSHLAYERWITHBLEND,
259
    POPLAYER,
260
    UNSCALEDFONTCREATION,
261
    UNSCALEDFONTDESTRUCTION,
262
    INTOLUMINANCE,
263
    EXTERNALSURFACECREATION,
264
  };
265
  static const uint32_t kTotalEventTypes = RecordedEvent::FILTERNODESETINPUT + 1;
266
267
0
  virtual ~RecordedEvent() {}
268
269
  static std::string GetEventName(EventType aType);
270
271
  /**
272
   * Play back this event using the translator. Note that derived classes should
273
   * only return false when there is a fatal error, as it will probably mean the
274
   * translation will abort.
275
   * @param aTranslator Translator to be used for retrieving other referenced
276
   *                    objects and making playback decisions.
277
   * @return true unless a fatal problem has occurred and playback should abort.
278
   */
279
0
  virtual bool PlayEvent(Translator *aTranslator) const { return true; }
280
281
  virtual void RecordToStream(std::ostream& aStream) const = 0;
282
  virtual void RecordToStream(EventStream& aStream) const = 0;
283
  virtual void RecordToStream(MemStream& aStream) const = 0;
284
285
0
  virtual void OutputSimpleEventInfo(std::stringstream &aStringStream) const { }
286
287
  template<class S>
288
  void RecordPatternData(S &aStream, const PatternStorage &aPatternStorage) const;
289
  template<class S>
290
  void ReadPatternData(S &aStream, PatternStorage &aPatternStorage) const;
291
  void StorePattern(PatternStorage &aDestination, const Pattern &aSource) const;
292
  template<class S>
293
  void RecordStrokeOptions(S &aStream, const StrokeOptions &aStrokeOptions) const;
294
  template<class S>
295
  void ReadStrokeOptions(S &aStream, StrokeOptions &aStrokeOptions);
296
297
  virtual std::string GetName() const = 0;
298
299
  virtual ReferencePtr GetObjectRef() const = 0;
300
301
0
  virtual ReferencePtr GetDestinedDT() { return nullptr; }
302
303
  void OutputSimplePatternInfo(const PatternStorage &aStorage, std::stringstream &aOutput) const;
304
305
  template<class S>
306
  static RecordedEvent *LoadEvent(S &aStream, EventType aType);
307
  static RecordedEvent *LoadEventFromStream(std::istream &aStream, EventType aType);
308
  static RecordedEvent *LoadEventFromStream(EventStream& aStream, EventType aType);
309
310
  // An alternative to LoadEvent that avoids a heap allocation for the event.
311
  // This accepts a callable `f' that will take a RecordedEvent* as a single parameter
312
  template<class S, class F>
313
  static bool DoWithEvent(S &aStream, EventType aType, F f);
314
315
  EventType GetType() const { return (EventType)mType; }
316
protected:
317
  friend class DrawEventRecorderPrivate;
318
  friend class DrawEventRecorderFile;
319
  friend class DrawEventRecorderMemory;
320
  static void RecordUnscaledFont(UnscaledFont *aUnscaledFont, std::ostream *aOutput);
321
  static void RecordUnscaledFont(UnscaledFont *aUnscaledFont, MemStream &aOutput);
322
  template<class S>
323
  static void RecordUnscaledFontImpl(UnscaledFont *aUnscaledFont, S &aOutput);
324
325
  MOZ_IMPLICIT RecordedEvent(int32_t aType) : mType(aType)
326
0
  {}
327
328
  int32_t mType;
329
  std::vector<Float> mDashPatternStorage;
330
};
331
332
} // namespace gfx
333
} // namespace mozilla
334
335
#endif