Mercurial > hg > octave-nkf
annotate src/ls-oct-binary.cc @ 8920:eb63fbe60fab
update copyright notices
author | John W. Eaton <jwe@octave.org> |
---|---|
date | Sat, 07 Mar 2009 10:41:27 -0500 |
parents | 25bc2d31e1bf |
children | cd96d29c5efa |
rev | line source |
---|---|
4634 | 1 /* |
2 | |
8920 | 3 Copyright (C) 1996, 1997, 2003, 2004, 2005, 2006, 2007, 2008 John W. Eaton |
4634 | 4 |
5 This file is part of Octave. | |
6 | |
7 Octave is free software; you can redistribute it and/or modify it | |
8 under the terms of the GNU General Public License as published by the | |
7016 | 9 Free Software Foundation; either version 3 of the License, or (at your |
10 option) any later version. | |
4634 | 11 |
12 Octave is distributed in the hope that it will be useful, but WITHOUT | |
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
15 for more details. | |
16 | |
17 You should have received a copy of the GNU General Public License | |
7016 | 18 along with Octave; see the file COPYING. If not, see |
19 <http://www.gnu.org/licenses/>. | |
4634 | 20 |
21 */ | |
22 | |
23 #ifdef HAVE_CONFIG_H | |
24 #include <config.h> | |
25 #endif | |
26 | |
27 #include <cfloat> | |
28 #include <cstring> | |
29 #include <cctype> | |
30 | |
31 #include <fstream> | |
32 #include <iomanip> | |
33 #include <iostream> | |
34 #include <string> | |
4726 | 35 #include <vector> |
4634 | 36 |
37 #include "byte-swap.h" | |
38 #include "data-conv.h" | |
39 #include "file-ops.h" | |
40 #include "glob-match.h" | |
41 #include "lo-mappers.h" | |
42 #include "mach-info.h" | |
43 #include "oct-env.h" | |
44 #include "oct-time.h" | |
45 #include "quit.h" | |
46 #include "str-vec.h" | |
8377
25bc2d31e1bf
improve OCTAVE_LOCAL_BUFFER
Jaroslav Hajek <highegg@gmail.com>
parents:
7336
diff
changeset
|
47 #include "oct-locbuf.h" |
4634 | 48 |
49 #include "Cell.h" | |
50 #include "defun.h" | |
51 #include "error.h" | |
52 #include "gripes.h" | |
53 #include "load-save.h" | |
54 #include "oct-obj.h" | |
55 #include "oct-map.h" | |
56 #include "ov-cell.h" | |
57 #include "pager.h" | |
58 #include "pt-exp.h" | |
59 #include "sysdep.h" | |
60 #include "unwind-prot.h" | |
61 #include "utils.h" | |
62 #include "variables.h" | |
63 #include "version.h" | |
64 #include "dMatrix.h" | |
65 | |
66 #include "ls-utils.h" | |
67 #include "ls-oct-binary.h" | |
68 | |
69 // Extract one value (scalar, matrix, string, etc.) from stream IS and | |
70 // place it in TC, returning the name of the variable. If the value | |
71 // is tagged as global in the file, return TRUE in GLOBAL. If SWAP | |
72 // is TRUE, swap bytes after reading. | |
73 // | |
74 // The data is expected to be in the following format: | |
75 // | |
76 // Header (one per file): | |
77 // ===================== | |
78 // | |
79 // object type bytes | |
80 // ------ ---- ----- | |
81 // magic number string 10 | |
82 // | |
83 // float format integer 1 | |
84 // | |
85 // | |
86 // Data (one set for each item): | |
87 // ============================ | |
88 // | |
89 // object type bytes | |
90 // ------ ---- ----- | |
91 // name_length integer 4 | |
92 // | |
93 // name string name_length | |
94 // | |
95 // doc_length integer 4 | |
96 // | |
97 // doc string doc_length | |
98 // | |
99 // global flag integer 1 | |
100 // | |
4687 | 101 // data type char 1 |
4634 | 102 // |
4687 | 103 // In general "data type" is 255, and in that case the next arguments |
104 // in the data set are | |
4634 | 105 // |
4687 | 106 // object type bytes |
107 // ------ ---- ----- | |
108 // type_length integer 4 | |
4634 | 109 // |
4687 | 110 // type string type_length |
111 // | |
112 // The string "type" is then used with octave_value_typeinfo::lookup_type | |
113 // to create an octave_value of the correct type. The specific load/save | |
114 // function is then called. | |
4634 | 115 // |
4687 | 116 // For backward compatiablity "data type" can also be a value between 1 |
117 // and 7, where this defines a hardcoded octave_value of the type | |
4634 | 118 // |
4687 | 119 // data type octave_value |
120 // --------- ------------ | |
121 // 1 scalar | |
122 // 2 matrix | |
123 // 3 complex scalar | |
124 // 4 complex matrix | |
125 // 5 string (old style storage) | |
126 // 6 range | |
127 // 7 string | |
4634 | 128 // |
4687 | 129 // Except for "data type" equal 5 that requires special treatment, these |
130 // old style "data type" value also cause the specific load/save functions | |
131 // to be called. FILENAME is used for error messages. | |
4634 | 132 |
133 std::string | |
134 read_binary_data (std::istream& is, bool swap, | |
135 oct_mach_info::float_format fmt, | |
136 const std::string& filename, bool& global, | |
137 octave_value& tc, std::string& doc) | |
138 { | |
139 std::string retval; | |
140 | |
6240 | 141 unsigned char tmp = 0; |
4634 | 142 |
5828 | 143 int32_t name_len = 0; |
144 int32_t doc_len = 0; | |
4634 | 145 |
146 doc.resize (0); | |
147 | |
148 // We expect to fail here, at the beginning of a record, so not | |
149 // being able to read another name should not result in an error. | |
150 | |
5760 | 151 is.read (reinterpret_cast<char *> (&name_len), 4); |
4634 | 152 if (! is) |
153 return retval; | |
154 if (swap) | |
4944 | 155 swap_bytes<4> (&name_len); |
4634 | 156 |
157 { | |
158 OCTAVE_LOCAL_BUFFER (char, name, name_len+1); | |
159 name[name_len] = '\0'; | |
5760 | 160 if (! is.read (reinterpret_cast<char *> (name), name_len)) |
4634 | 161 goto data_read_error; |
162 retval = name; | |
163 } | |
164 | |
5760 | 165 is.read (reinterpret_cast<char *> (&doc_len), 4); |
4634 | 166 if (! is) |
167 goto data_read_error; | |
168 if (swap) | |
4944 | 169 swap_bytes<4> (&doc_len); |
4634 | 170 |
171 { | |
172 OCTAVE_LOCAL_BUFFER (char, tdoc, doc_len+1); | |
173 tdoc[doc_len] = '\0'; | |
5760 | 174 if (! is.read (reinterpret_cast<char *> (tdoc), doc_len)) |
4634 | 175 goto data_read_error; |
176 doc = tdoc; | |
177 } | |
178 | |
5760 | 179 if (! is.read (reinterpret_cast<char *> (&tmp), 1)) |
4634 | 180 goto data_read_error; |
181 global = tmp ? 1 : 0; | |
182 | |
183 tmp = 0; | |
5760 | 184 if (! is.read (reinterpret_cast<char *> (&tmp), 1)) |
4634 | 185 goto data_read_error; |
186 | |
4687 | 187 // All cases except 255 kept for backwards compatibility |
4634 | 188 switch (tmp) |
189 { | |
190 case 1: | |
4687 | 191 tc = octave_value_typeinfo::lookup_type ("scalar"); |
4634 | 192 break; |
193 | |
194 case 2: | |
4687 | 195 tc = octave_value_typeinfo::lookup_type ("matrix"); |
4634 | 196 break; |
197 | |
198 case 3: | |
4687 | 199 tc = octave_value_typeinfo::lookup_type ("complex scalar"); |
4634 | 200 break; |
201 | |
202 case 4: | |
4687 | 203 tc = octave_value_typeinfo::lookup_type ("complex matrix"); |
4634 | 204 break; |
205 | |
206 case 5: | |
207 { | |
5775 | 208 // FIXMEX |
4687 | 209 // This is cruft, since its for a save type that is old. Maybe |
210 // this is taking backward compatability too far!! | |
5828 | 211 int32_t len; |
5760 | 212 if (! is.read (reinterpret_cast<char *> (&len), 4)) |
4634 | 213 goto data_read_error; |
214 if (swap) | |
4944 | 215 swap_bytes<4> (&len); |
4634 | 216 OCTAVE_LOCAL_BUFFER (char, s, len+1); |
5760 | 217 if (! is.read (reinterpret_cast<char *> (s), len)) |
4634 | 218 goto data_read_error; |
219 s[len] = '\0'; | |
220 tc = s; | |
4687 | 221 |
222 // Early return, since don't want rest of this function | |
223 return retval; | |
4634 | 224 } |
225 break; | |
226 | |
227 case 6: | |
4687 | 228 tc = octave_value_typeinfo::lookup_type ("range"); |
4634 | 229 break; |
230 | |
231 case 7: | |
4687 | 232 tc = octave_value_typeinfo::lookup_type ("string"); |
233 break; | |
234 | |
235 case 255: | |
4634 | 236 { |
4687 | 237 // Read the saved variable type |
5828 | 238 int32_t len; |
5760 | 239 if (! is.read (reinterpret_cast<char *> (&len), 4)) |
4634 | 240 goto data_read_error; |
241 if (swap) | |
4944 | 242 swap_bytes<4> (&len); |
4687 | 243 OCTAVE_LOCAL_BUFFER (char, s, len+1); |
5760 | 244 if (! is.read (s, len)) |
4687 | 245 goto data_read_error; |
246 s[len] = '\0'; | |
247 std::string typ = s; | |
248 tc = octave_value_typeinfo::lookup_type (typ); | |
4634 | 249 } |
250 break; | |
251 default: | |
4687 | 252 goto data_read_error; |
253 break; | |
254 } | |
255 | |
256 if (!tc.load_binary (is, swap, fmt)) | |
257 { | |
4634 | 258 data_read_error: |
259 error ("load: trouble reading binary file `%s'", filename.c_str ()); | |
260 } | |
261 | |
262 return retval; | |
263 } | |
264 | |
265 // Save the data from TC along with the corresponding NAME, help | |
266 // string DOC, and global flag MARK_AS_GLOBAL on stream OS in the | |
267 // binary format described above for read_binary_data. | |
268 | |
269 bool | |
270 save_binary_data (std::ostream& os, const octave_value& tc, | |
271 const std::string& name, const std::string& doc, | |
272 bool mark_as_global, bool save_as_floats) | |
273 { | |
5828 | 274 int32_t name_len = name.length (); |
4634 | 275 |
5760 | 276 os.write (reinterpret_cast<char *> (&name_len), 4); |
4634 | 277 os << name; |
278 | |
5828 | 279 int32_t doc_len = doc.length (); |
4634 | 280 |
5760 | 281 os.write (reinterpret_cast<char *> (&doc_len), 4); |
4634 | 282 os << doc; |
283 | |
4730 | 284 unsigned char tmp; |
4634 | 285 |
286 tmp = mark_as_global; | |
5760 | 287 os.write (reinterpret_cast<char *> (&tmp), 1); |
4634 | 288 |
4687 | 289 // 255 flags the new binary format |
290 tmp = 255; | |
5760 | 291 os.write (reinterpret_cast<char *> (&tmp), 1); |
4634 | 292 |
4687 | 293 // Write the string corresponding to the octave_value type |
294 std::string typ = tc.type_name (); | |
5828 | 295 int32_t len = typ.length (); |
5760 | 296 os.write (reinterpret_cast<char *> (&len), 4); |
4687 | 297 const char *btmp = typ.data (); |
5760 | 298 os.write (btmp, len); |
4687 | 299 |
300 // The octave_value of tc is const. Make a copy... | |
301 octave_value val = tc; | |
302 | |
303 // Call specific save function | |
304 bool success = val.save_binary (os, save_as_floats); | |
305 | |
306 return (os && success); | |
4634 | 307 } |
308 | |
309 /* | |
310 ;;; Local Variables: *** | |
311 ;;; mode: C++ *** | |
312 ;;; End: *** | |
313 */ | |
314 |