00001
00002 #include <mobject.h>
00003 #include "magic/marchive.h"
00004
00008
00009 CArchive::CArchive (const char* filnam, int md) {
00010 in=NULL;
00011 out=NULL;
00012 indent=0;
00013 arcfile=filnam;
00014 mode = md;
00015 attribs = NULL;
00016 if (mode&ARC_SAVE)
00017 opensave();
00018 else
00019 if (mode&ARC_RECORD)
00020 openrecord ();
00021 else
00022 openload();
00023 }
00024
00025 CArchive::~CArchive () {
00026 delete in;
00027 delete out;
00028 delete attribs;
00029 }
00030
00031 int CArchive::open (const char* filename, int flag) {
00032 delete out;
00033 delete in;
00034 if (fbuf.is_open())
00035 fbuf.close ();
00036
00037 filebuf* succ=NULL;
00038 String filname = arcfile;
00039 if (filename)
00040 filname = filename;
00041 succ = fbuf.open (filname, ios::IOSBINARY | ((flag==ARC_LOAD)? (ios::in|ios::nocreate) : ios::out));
00042 if (!succ || !fbuf.is_open ()) {
00043
00044 errst = 1;
00045 return 0;
00046 }
00047 return 1;
00048 }
00049
00050 int CArchive::opensave (const char* filename) {
00051 if (!open (filename, ARC_SAVE)) {
00052 errst = 1;
00053 return 0;
00054 }
00055 out = new ostream (&fbuf);
00056 if (!out) {
00057 errst = 1;
00058
00059 return 0;
00060 }
00061 return 1;
00062 }
00063
00064 int CArchive::openload (const char* filename) {
00065 if (!open (filename, ARC_LOAD)) {
00066 errst=1;
00067 return 0;
00068 }
00069 in = new istream (&fbuf);
00070 if (!in) {
00071 errst = 1;
00072
00073 return 0;
00074 }
00075 return 1;
00076 }
00077
00078 int CArchive::openrecord () {
00079 attribs = new Array<String>;
00080 }
00081
00082 void CArchive::close () {
00083 fbuf.close ();
00084 delete in;
00085 delete out;
00086 in = NULL;
00087 out = NULL;
00088 }
00089
00090 #define CHECKRECORD(rtype,var) \
00091 if (mode&ARC_RECORD) {\
00092 if (nextname.isempty())\
00093 nextname = "?";\
00094 attribs->add (new String (format ("%s %s", #rtype, (CONSTR)nextname)));\
00095 return *this;\
00096 }
00097
00098
00099 CArchive& CArchive::operator<< (int i) {
00100 CHECKRECORD (int, i);
00101
00102 operator<< ((long) i);
00103 return *this;
00104 }
00105
00106 CArchive& CArchive::operator<< (long i) {
00107 CHECKRECORD (long, int (i));
00108
00109 if (mode&ARC_TEXT) {
00110 for (int j=0; j<indent; j++) *out << "\t";
00111 *out << i << "\n";
00112 } else
00113 out->write ((char*) &i, sizeof(i));
00114 return *this;
00115 }
00116
00117 CArchive& CArchive::operator<< (char i) {
00118 CHECKRECORD (char, i);
00119 if (out) out->write ((char*) &i, sizeof(i)); return *this;
00120 }
00121
00122 CArchive& CArchive::operator<< (float i) {
00123 CHECKRECORD (float, i);
00124 operator<< ((double) i);
00125 return *this;
00126 }
00127
00128 CArchive& CArchive::operator<< (double i) {
00129 CHECKRECORD (double, float(i));
00130 if (mode&ARC_TEXT) {
00131 for (int j=0; j<indent; j++) *out << "\t";
00132 *out << i << "\n";
00133 } else
00134 out->write ((char*) &i, sizeof(i));
00135 return *this;
00136 }
00137
00138 CArchive& CArchive::write (const char* p, int n) {
00139 CHECKRECORD (char*, p);
00140 if (mode&ARC_TEXT) {
00141 for (int i=0; i<indent; i++) *out << "\t";
00142 String str, str2 (p, n);
00143 str.hexcode (str2);
00144 *out << str << "\n";
00145 } else
00146 out->write (p, n);
00147 return *this;
00148 }
00149
00150 CArchive& CArchive::operator>> (long& i) {
00151 if (in) in->read ((char*) &i, sizeof(i)); return *this;
00152 }
00153
00154 CArchive& CArchive::operator>> (char& i) {
00155 if (mode&ARC_TEXT) {
00156 ;
00157 } else
00158 in->read ((char*) &i, sizeof(i));
00159 return *this;
00160 }
00161
00162 CArchive& CArchive::operator>> (double& i) {
00163 if (in) in->read ((char*) &i, sizeof(i)); return *this;
00164 }
00165 CArchive& CArchive::read (char* p, int n) {
00166 if (in) in->read (p, n); return *this;
00167 }
00168
00169 CArchive& operator<< (CArchive& out, const char* str) {
00170 out.name (str);
00171 return out;
00172 }
00173