00001
00002
00003
00004
00005
00006
00007
00008
00009 #include <aconf.h>
00010
00011 #ifdef USE_GCC_PRAGMAS
00012 #pragma implementation
00013 #endif
00014
00015 #include <stddef.h>
00016 #include "Object.h"
00017 #include "Array.h"
00018 #include "Dict.h"
00019 #include "Error.h"
00020 #include "Stream.h"
00021 #include "XRef.h"
00022
00023
00024
00025
00026
00027 const char *objTypeNames[numObjTypes] = {
00028 "boolean",
00029 "integer",
00030 "real",
00031 "string",
00032 "name",
00033 "null",
00034 "array",
00035 "dictionary",
00036 "stream",
00037 "ref",
00038 "cmd",
00039 "error",
00040 "eof",
00041 "none"
00042 };
00043
00044 #ifdef DEBUG_MEM
00045 int Object::numAlloc[numObjTypes] =
00046 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
00047 #endif
00048
00049 Object *Object::initArray(XRef *xref) {
00050 initObj(objArray);
00051 array = new Array(xref);
00052 return this;
00053 }
00054
00055 Object *Object::initDict(XRef *xref) {
00056 initObj(objDict);
00057 dict = new Dict(xref);
00058 return this;
00059 }
00060
00061 Object *Object::initStream(Stream *streamA) {
00062 initObj(objStream);
00063 stream = streamA;
00064 return this;
00065 }
00066
00067 Object *Object::copy(Object *obj) {
00068 *obj = *this;
00069 switch (type) {
00070 case objString:
00071 obj->string = string->copy();
00072 break;
00073 case objName:
00074 obj->name = copyString(name);
00075 break;
00076 case objArray:
00077 array->incRef();
00078 break;
00079 case objDict:
00080 dict->incRef();
00081 break;
00082 case objStream:
00083 stream->incRef();
00084 break;
00085 case objCmd:
00086 obj->cmd = copyString(cmd);
00087 break;
00088 default:
00089 break;
00090 }
00091 #ifdef DEBUG_MEM
00092 ++numAlloc[type];
00093 #endif
00094 return obj;
00095 }
00096
00097 Object *Object::fetch(XRef *xref, Object *obj) {
00098 return (type == objRef && xref) ?
00099 xref->fetch(ref.num, ref.gen, obj) : copy(obj);
00100 }
00101
00102 void Object::free() {
00103 switch (type) {
00104 case objString:
00105 delete string;
00106 break;
00107 case objName:
00108 gfree(name);
00109 break;
00110 case objArray:
00111 if (!array->decRef()) {
00112 delete array;
00113 }
00114 break;
00115 case objDict:
00116 if (!dict->decRef()) {
00117 delete dict;
00118 }
00119 break;
00120 case objStream:
00121 if (!stream->decRef()) {
00122 delete stream;
00123 }
00124 break;
00125 case objCmd:
00126 gfree(cmd);
00127 break;
00128 default:
00129 break;
00130 }
00131 #ifdef DEBUG_MEM
00132 --numAlloc[type];
00133 #endif
00134 type = objNone;
00135 }
00136
00137 const char *Object::getTypeName() {
00138 return objTypeNames[type];
00139 }
00140
00141 void Object::print(FILE *f) {
00142 Object obj;
00143 int i;
00144
00145 switch (type) {
00146 case objBool:
00147 fprintf(f, "%s", booln ? "true" : "false");
00148 break;
00149 case objInt:
00150 fprintf(f, "%d", intg);
00151 break;
00152 case objReal:
00153 fprintf(f, "%g", real);
00154 break;
00155 case objString:
00156 fprintf(f, "(");
00157 fwrite(string->getCString(), 1, string->getLength(), stdout);
00158 fprintf(f, ")");
00159 break;
00160 case objName:
00161 fprintf(f, "/%s", name);
00162 break;
00163 case objNull:
00164 fprintf(f, "null");
00165 break;
00166 case objArray:
00167 fprintf(f, "[");
00168 for (i = 0; i < arrayGetLength(); ++i) {
00169 if (i > 0)
00170 fprintf(f, " ");
00171 arrayGetNF(i, &obj);
00172 obj.print(f);
00173 obj.free();
00174 }
00175 fprintf(f, "]");
00176 break;
00177 case objDict:
00178 fprintf(f, "<<");
00179 for (i = 0; i < dictGetLength(); ++i) {
00180 fprintf(f, " /%s ", dictGetKey(i));
00181 dictGetValNF(i, &obj);
00182 obj.print(f);
00183 obj.free();
00184 }
00185 fprintf(f, " >>");
00186 break;
00187 case objStream:
00188 fprintf(f, "<stream>");
00189 break;
00190 case objRef:
00191 fprintf(f, "%d %d R", ref.num, ref.gen);
00192 break;
00193 case objCmd:
00194 fprintf(f, "%s", cmd);
00195 break;
00196 case objError:
00197 fprintf(f, "<error>");
00198 break;
00199 case objEOF:
00200 fprintf(f, "<EOF>");
00201 break;
00202 case objNone:
00203 fprintf(f, "<none>");
00204 break;
00205 }
00206 }
00207
00208 void Object::memCheck(FILE *f) {
00209 #ifdef DEBUG_MEM
00210 int i;
00211 int t;
00212
00213 t = 0;
00214 for (i = 0; i < numObjTypes; ++i)
00215 t += numAlloc[i];
00216 if (t > 0) {
00217 fprintf(f, "Allocated objects:\n");
00218 for (i = 0; i < numObjTypes; ++i) {
00219 if (numAlloc[i] > 0)
00220 fprintf(f, " %-20s: %6d\n", objTypeNames[i], numAlloc[i]);
00221 }
00222 }
00223 #endif
00224 (void)f;
00225 }