1 :
2 : /*
3 : * Copyright 2008 The Android Open Source Project
4 : *
5 : * Use of this source code is governed by a BSD-style license that can be
6 : * found in the LICENSE file.
7 : */
8 :
9 :
10 : #ifndef SkWriter32_DEFINED
11 : #define SkWriter32_DEFINED
12 :
13 : #include "SkTypes.h"
14 :
15 : #include "SkScalar.h"
16 : #include "SkPoint.h"
17 : #include "SkRect.h"
18 :
19 : class SkStream;
20 : class SkWStream;
21 :
22 : class SkWriter32 : SkNoncopyable {
23 : public:
24 0 : SkWriter32(size_t minSize)
25 : : fMinSize(minSize),
26 : fSize(0),
27 : fSingleBlock(NULL),
28 : fSingleBlockSize(0),
29 : fHead(NULL),
30 0 : fTail(NULL) {
31 0 : }
32 : ~SkWriter32();
33 :
34 : /**
35 : * Returns the single block backing the writer, or NULL if the memory is
36 : * to be dynamically allocated.
37 : */
38 : void* getSingleBlock() const { return fSingleBlock; }
39 :
40 : /**
41 : * Specify the single block to back the writer, rathern than dynamically
42 : * allocating the memory. If block == NULL, then the writer reverts to
43 : * dynamic allocation (and resets).
44 : */
45 : void reset(void* block, size_t size);
46 :
47 0 : bool writeBool(bool value) {
48 0 : this->writeInt(value);
49 0 : return value;
50 : }
51 :
52 0 : void writeInt(int32_t value) {
53 0 : *(int32_t*)this->reserve(sizeof(value)) = value;
54 0 : }
55 :
56 0 : void write8(int32_t value) {
57 0 : *(int32_t*)this->reserve(sizeof(value)) = value & 0xFF;
58 0 : }
59 :
60 0 : void write16(int32_t value) {
61 0 : *(int32_t*)this->reserve(sizeof(value)) = value & 0xFFFF;
62 0 : }
63 :
64 0 : void write32(int32_t value) {
65 0 : *(int32_t*)this->reserve(sizeof(value)) = value;
66 0 : }
67 :
68 0 : void writeScalar(SkScalar value) {
69 0 : *(SkScalar*)this->reserve(sizeof(value)) = value;
70 0 : }
71 :
72 0 : void writePoint(const SkPoint& pt) {
73 0 : *(SkPoint*)this->reserve(sizeof(pt)) = pt;
74 0 : }
75 :
76 0 : void writeRect(const SkRect& rect) {
77 0 : *(SkRect*)this->reserve(sizeof(rect)) = rect;
78 0 : }
79 :
80 : // write count bytes (must be a multiple of 4)
81 0 : void writeMul4(const void* values, size_t size) {
82 0 : this->write(values, size);
83 0 : }
84 :
85 : /**
86 : * Write size bytes from values. size must be a multiple of 4, though
87 : * values need not be 4-byte aligned.
88 : */
89 0 : void write(const void* values, size_t size) {
90 0 : SkASSERT(SkAlign4(size) == size);
91 : // if we could query how much is avail in the current block, we might
92 : // copy that much, and then alloc the rest. That would reduce the waste
93 : // in the current block
94 0 : memcpy(this->reserve(size), values, size);
95 0 : }
96 :
97 : void writePad(const void* src, size_t size);
98 :
99 : /**
100 : * Writes a string to the writer, which can be retrieved with
101 : * SkReader32::readString().
102 : * The length can be specified, or if -1 is passed, it will be computed by
103 : * calling strlen(). The length must be < 0xFFFF
104 : */
105 : void writeString(const char* str, size_t len = (size_t)-1);
106 :
107 : /**
108 : * Computes the size (aligned to multiple of 4) need to write the string
109 : * in a call to writeString(). If the length is not specified, it will be
110 : * computed by calling strlen().
111 : */
112 : static size_t WriteStringSize(const char* str, size_t len = (size_t)-1);
113 :
114 : // return the current offset (will always be a multiple of 4)
115 0 : uint32_t size() const { return fSize; }
116 : void reset();
117 : uint32_t* reserve(size_t size); // size MUST be multiple of 4
118 :
119 : // return the address of the 4byte int at the specified offset (which must
120 : // be a multiple of 4. This does not allocate any new space, so the returned
121 : // address is only valid for 1 int.
122 : uint32_t* peek32(size_t offset);
123 :
124 : // copy into a single buffer (allocated by caller). Must be at least size()
125 : void flatten(void* dst) const;
126 :
127 : // read from the stream, and write up to length bytes. Return the actual
128 : // number of bytes written.
129 : size_t readFromStream(SkStream*, size_t length);
130 :
131 : bool writeToStream(SkWStream*);
132 :
133 : private:
134 : size_t fMinSize;
135 : uint32_t fSize;
136 :
137 : char* fSingleBlock;
138 : uint32_t fSingleBlockSize;
139 :
140 : struct Block;
141 : Block* fHead;
142 : Block* fTail;
143 :
144 : Block* newBlock(size_t bytes);
145 : };
146 :
147 : #endif
|