/src/xpdf-4.05/xpdf/Object.cc
Line | Count | Source |
1 | | //======================================================================== |
2 | | // |
3 | | // Object.cc |
4 | | // |
5 | | // Copyright 1996-2003 Glyph & Cog, LLC |
6 | | // |
7 | | //======================================================================== |
8 | | |
9 | | #include <aconf.h> |
10 | | |
11 | | #include <stddef.h> |
12 | | #include "gmempp.h" |
13 | | #include "Object.h" |
14 | | #include "Array.h" |
15 | | #include "Dict.h" |
16 | | #include "Error.h" |
17 | | #include "Stream.h" |
18 | | #include "XRef.h" |
19 | | |
20 | | //------------------------------------------------------------------------ |
21 | | // Object |
22 | | //------------------------------------------------------------------------ |
23 | | |
24 | | const char *objTypeNames[numObjTypes] = { |
25 | | "boolean", |
26 | | "integer", |
27 | | "real", |
28 | | "string", |
29 | | "name", |
30 | | "null", |
31 | | "array", |
32 | | "dictionary", |
33 | | "stream", |
34 | | "ref", |
35 | | "cmd", |
36 | | "error", |
37 | | "eof", |
38 | | "none" |
39 | | }; |
40 | | |
41 | | #ifdef DEBUG_OBJECT_MEM |
42 | | #if MULTITHREADED |
43 | | GAtomicCounter Object::numAlloc[numObjTypes] = |
44 | | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; |
45 | | #else |
46 | | long Object::numAlloc[numObjTypes] = |
47 | | {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; |
48 | | #endif |
49 | | #endif // DEBUG_OBJECT_MEM |
50 | | |
51 | 489k | Object *Object::initArray(XRef *xref) { |
52 | 489k | initObj(objArray); |
53 | 489k | array = new Array(xref); |
54 | 489k | return this; |
55 | 489k | } |
56 | | |
57 | 379k | Object *Object::initDict(XRef *xref) { |
58 | 379k | initObj(objDict); |
59 | 379k | dict = new Dict(xref); |
60 | 379k | return this; |
61 | 379k | } |
62 | | |
63 | 955 | Object *Object::initDict(Dict *dictA) { |
64 | 955 | initObj(objDict); |
65 | 955 | dict = dictA; |
66 | 955 | dict->incRef(); |
67 | 955 | return this; |
68 | 955 | } |
69 | | |
70 | 93.2k | Object *Object::initStream(Stream *streamA) { |
71 | 93.2k | initObj(objStream); |
72 | 93.2k | stream = streamA; |
73 | 93.2k | return this; |
74 | 93.2k | } |
75 | | |
76 | 36.5M | Object *Object::copy(Object *obj) { |
77 | 36.5M | *obj = *this; |
78 | 36.5M | switch (type) { |
79 | 430k | case objString: |
80 | 430k | obj->string = string->copy(); |
81 | 430k | break; |
82 | 3.36M | case objName: |
83 | 3.36M | obj->name = copyString(name); |
84 | 3.36M | break; |
85 | 12.0k | case objArray: |
86 | 12.0k | array->incRef(); |
87 | 12.0k | break; |
88 | 186k | case objDict: |
89 | 186k | dict->incRef(); |
90 | 186k | break; |
91 | 111k | case objStream: |
92 | 111k | obj->stream = stream->copy(); |
93 | 111k | break; |
94 | 10.4M | case objCmd: |
95 | 10.4M | obj->cmd = copyString(cmd); |
96 | 10.4M | break; |
97 | 22.0M | default: |
98 | 22.0M | break; |
99 | 36.5M | } |
100 | | #ifdef DEBUG_OBJECT_MEM |
101 | | #if MULTITHREADED |
102 | | gAtomicIncrement(&numAlloc[type]); |
103 | | #else |
104 | | ++numAlloc[type]; |
105 | | #endif |
106 | | #endif |
107 | 36.5M | return obj; |
108 | 36.5M | } |
109 | | |
110 | 248k | Object *Object::fetch(XRef *xref, Object *obj, int recursion) { |
111 | 248k | return (type == objRef && xref) ? |
112 | 177k | xref->fetch(ref.num, ref.gen, obj, recursion) : copy(obj); |
113 | 248k | } |
114 | | |
115 | 94.5M | void Object::free() { |
116 | 94.5M | switch (type) { |
117 | 1.18M | case objString: |
118 | 1.18M | delete string; |
119 | 1.18M | break; |
120 | 8.07M | case objName: |
121 | 8.07M | gfree(name); |
122 | 8.07M | break; |
123 | 461k | case objArray: |
124 | 461k | if (!array->decRef()) { |
125 | 449k | delete array; |
126 | 449k | } |
127 | 461k | break; |
128 | 501k | case objDict: |
129 | 501k | if (!dict->decRef()) { |
130 | 314k | delete dict; |
131 | 314k | } |
132 | 501k | break; |
133 | 196k | case objStream: |
134 | 196k | delete stream; |
135 | 196k | break; |
136 | 31.4M | case objCmd: |
137 | 31.4M | gfree(cmd); |
138 | 31.4M | break; |
139 | 52.6M | default: |
140 | 52.6M | break; |
141 | 94.5M | } |
142 | | #ifdef DEBUG_OBJECT_MEM |
143 | | #if MULTITHREADED |
144 | | gAtomicDecrement(&numAlloc[type]); |
145 | | #else |
146 | | --numAlloc[type]; |
147 | | #endif |
148 | | #endif |
149 | 94.5M | type = objNone; |
150 | 94.5M | } |
151 | | |
152 | 15.6k | const char *Object::getTypeName() { |
153 | 15.6k | return objTypeNames[type]; |
154 | 15.6k | } |
155 | | |
156 | 0 | void Object::print(FILE *f) { |
157 | 0 | Object obj; |
158 | 0 | int i; |
159 | |
|
160 | 0 | switch (type) { |
161 | 0 | case objBool: |
162 | 0 | fprintf(f, "%s", booln ? "true" : "false"); |
163 | 0 | break; |
164 | 0 | case objInt: |
165 | 0 | fprintf(f, "%d", intg); |
166 | 0 | break; |
167 | 0 | case objReal: |
168 | 0 | fprintf(f, "%g", real); |
169 | 0 | break; |
170 | 0 | case objString: |
171 | 0 | fprintf(f, "("); |
172 | 0 | fwrite(string->getCString(), 1, string->getLength(), f); |
173 | 0 | fprintf(f, ")"); |
174 | 0 | break; |
175 | 0 | case objName: |
176 | 0 | fprintf(f, "/%s", name); |
177 | 0 | break; |
178 | 0 | case objNull: |
179 | 0 | fprintf(f, "null"); |
180 | 0 | break; |
181 | 0 | case objArray: |
182 | 0 | fprintf(f, "["); |
183 | 0 | for (i = 0; i < arrayGetLength(); ++i) { |
184 | 0 | if (i > 0) |
185 | 0 | fprintf(f, " "); |
186 | 0 | arrayGetNF(i, &obj); |
187 | 0 | obj.print(f); |
188 | 0 | obj.free(); |
189 | 0 | } |
190 | 0 | fprintf(f, "]"); |
191 | 0 | break; |
192 | 0 | case objDict: |
193 | 0 | fprintf(f, "<<"); |
194 | 0 | for (i = 0; i < dictGetLength(); ++i) { |
195 | 0 | fprintf(f, " /%s ", dictGetKey(i)); |
196 | 0 | dictGetValNF(i, &obj); |
197 | 0 | obj.print(f); |
198 | 0 | obj.free(); |
199 | 0 | } |
200 | 0 | fprintf(f, " >>"); |
201 | 0 | break; |
202 | 0 | case objStream: |
203 | 0 | fprintf(f, "<stream>"); |
204 | 0 | break; |
205 | 0 | case objRef: |
206 | 0 | fprintf(f, "%d %d R", ref.num, ref.gen); |
207 | 0 | break; |
208 | 0 | case objCmd: |
209 | 0 | fprintf(f, "%s", cmd); |
210 | 0 | break; |
211 | 0 | case objError: |
212 | 0 | fprintf(f, "<error>"); |
213 | 0 | break; |
214 | 0 | case objEOF: |
215 | 0 | fprintf(f, "<EOF>"); |
216 | 0 | break; |
217 | 0 | case objNone: |
218 | 0 | fprintf(f, "<none>"); |
219 | 0 | break; |
220 | 0 | } |
221 | 0 | } |
222 | | |
223 | 0 | void Object::memCheck(FILE *f) { |
224 | | #ifdef DEBUG_OBJECT_MEM |
225 | | int i; |
226 | | long t; |
227 | | |
228 | | t = 0; |
229 | | for (i = 0; i < numObjTypes; ++i) { |
230 | | t += numAlloc[i]; |
231 | | } |
232 | | if (t > 0) { |
233 | | fprintf(f, "Allocated objects:\n"); |
234 | | for (i = 0; i < numObjTypes; ++i) { |
235 | | if (numAlloc[i] > 0) { |
236 | | fprintf(f, " %-20s: %6ld\n", objTypeNames[i], numAlloc[i]); |
237 | | } |
238 | | } |
239 | | } |
240 | | #endif |
241 | 0 | } |