SHOGUN
v2.0.0
|
00001 /* 00002 * This program is free software; you can redistribute it and/or modify 00003 * it under the terms of the GNU General Public License as published by 00004 * the Free Software Foundation; either version 3 of the License, or 00005 * (at your option) any later version. 00006 * 00007 * Written (W) 2010 Soeren Sonnenburg 00008 * Copyright (C) 2010 Berlin Institute of Technology 00009 */ 00010 00011 #include <shogun/lib/config.h> 00012 #ifdef HAVE_HDF5 00013 00014 #include <shogun/io/SerializableHdf5File.h> 00015 #include <shogun/io/SerializableHdf5Reader00.h> 00016 00017 #define NOT_OPEN ((hid_t) -1) 00018 00019 #define STR_KEY_FILETYPE "filetype" 00020 #define STR_FILETYPE_00 \ 00021 "_SHOGUN_SERIALIZABLE_HDF5_FILE_V_00_" 00022 00023 using namespace shogun; 00024 00025 CSerializableHdf5File::type_item_t::type_item_t(const char* name_) 00026 { 00027 rank = 0; 00028 dims[0] = dims[1] = 0; 00029 dspace = dtype = dset = NOT_OPEN; 00030 vltype = NULL; 00031 y = x = sub_y = 0; 00032 sparse_ptr = NULL; 00033 name = name_; 00034 } 00035 00036 CSerializableHdf5File::type_item_t::~type_item_t() 00037 { 00038 if (dset >= 0) H5Dclose(dset); 00039 if (dtype >= 0) H5Tclose(dtype); 00040 if (dspace >= 0) H5Sclose(dspace); 00041 if (vltype != NULL) SG_FREE(vltype); 00042 /* Do not delete SPARSE_PTR */ 00043 } 00044 00045 hid_t 00046 CSerializableHdf5File::sizeof_sparsetype() { 00047 return H5Tget_size(TYPE_INDEX) + H5Tget_size(H5T_STD_REF_OBJ); 00048 } 00049 hid_t 00050 CSerializableHdf5File::new_sparsetype() 00051 { 00052 hid_t result = H5Tcreate(H5T_COMPOUND, sizeof_sparsetype()); 00053 00054 if (H5Tinsert(result, STR_SPARSE_FPTR, H5Tget_size(TYPE_INDEX), 00055 H5T_STD_REF_OBJ) < 0) 00056 return NOT_OPEN; 00057 00058 return result; 00059 } 00060 hobj_ref_t* 00061 CSerializableHdf5File::get_ref_sparstype(void* sparse_buf) { 00062 return (hobj_ref_t*) 00063 ((char*) sparse_buf + H5Tget_size(TYPE_INDEX)); 00064 } 00065 00066 hid_t 00067 CSerializableHdf5File::new_sparseentrytype(EPrimitiveType ptype) 00068 { 00069 hid_t result = H5Tcreate(H5T_COMPOUND, 00070 TSGDataType::sizeof_sparseentry(ptype)); 00071 if (result < 0) return NOT_OPEN; 00072 00073 if (H5Tinsert(result, STR_SPARSEENTRY_FINDEX, 00074 HOFFSET(SGSparseVectorEntry<char>, feat_index), TYPE_INDEX) 00075 < 0) return NOT_OPEN; 00076 if (H5Tinsert(result, STR_SPARSEENTRY_ENTRY, TSGDataType 00077 ::offset_sparseentry(ptype), 00078 ptype2hdf5(ptype)) < 0) return NOT_OPEN; 00079 00080 return result; 00081 } 00082 00083 hid_t 00084 CSerializableHdf5File::ptype2hdf5(EPrimitiveType ptype) 00085 { 00086 switch (ptype) { 00087 case PT_BOOL: 00088 switch (sizeof (bool)) { 00089 case 1: return H5T_NATIVE_UINT8; 00090 case 2: return H5T_NATIVE_UINT16; 00091 case 4: return H5T_NATIVE_UINT32; 00092 case 8: return H5T_NATIVE_UINT64; 00093 default: break; 00094 } 00095 break; 00096 case PT_CHAR: return H5T_NATIVE_CHAR; break; 00097 case PT_INT8: return H5T_NATIVE_INT8; break; 00098 case PT_UINT8: return H5T_NATIVE_UINT8; break; 00099 case PT_INT16: return H5T_NATIVE_INT16; break; 00100 case PT_UINT16: return H5T_NATIVE_UINT16; break; 00101 case PT_INT32: return H5T_NATIVE_INT32; break; 00102 case PT_UINT32: return H5T_NATIVE_UINT32; break; 00103 case PT_INT64: return H5T_NATIVE_INT64; break; 00104 case PT_UINT64: return H5T_NATIVE_UINT64; break; 00105 case PT_FLOAT32: return H5T_NATIVE_FLOAT; break; 00106 case PT_FLOAT64: return H5T_NATIVE_DOUBLE; break; 00107 case PT_FLOATMAX: return H5T_NATIVE_LDOUBLE; break; 00108 case PT_SGOBJECT: return NOT_OPEN; break; 00109 } 00110 00111 return NOT_OPEN; 00112 } 00113 00114 hid_t 00115 CSerializableHdf5File::new_stype2hdf5(EStructType stype, 00116 EPrimitiveType ptype) 00117 { 00118 hid_t result = ptype2hdf5(ptype); 00119 00120 switch (stype) { 00121 case ST_NONE: result = H5Tcopy(result); break; 00122 case ST_STRING: result = H5Tvlen_create(result); break; 00123 case ST_SPARSE: result = new_sparsetype(); break; 00124 default: break; 00125 } 00126 00127 return result; 00128 } 00129 00130 bool 00131 CSerializableHdf5File::index2string( 00132 char* dest, size_t n, EContainerType ctype, index_t y, index_t x) 00133 { 00134 switch (ctype) { 00135 case CT_NDARRAY: SG_SNOTIMPLEMENTED; 00136 case CT_SCALAR: return false; 00137 case CT_VECTOR: case CT_SGVECTOR: snprintf(dest, n, "y%u", y); break; 00138 case CT_MATRIX: case CT_SGMATRIX: snprintf(dest, n, "y%u_x%u", y, x); break; 00139 default: return false; 00140 } 00141 00142 return true; 00143 } 00144 00145 bool 00146 CSerializableHdf5File::isequal_stype2hdf5(EStructType stype, 00147 EPrimitiveType ptype, 00148 hid_t htype) 00149 { 00150 hid_t pbuf = ptype2hdf5(ptype), pbuf2 = NOT_OPEN; 00151 00152 bool to_close = false; 00153 switch (stype) { 00154 case ST_NONE: break; 00155 case ST_STRING: 00156 to_close = true; pbuf = H5Tvlen_create(pbuf); break; 00157 case ST_SPARSE: 00158 to_close = true; pbuf = new_sparsetype(); 00159 pbuf2 = new_sparseentrytype(ptype); break; 00160 } 00161 00162 bool result = (H5Tequal(htype, pbuf) > 0) 00163 || (pbuf2 >= 0 && H5Tequal(htype, pbuf2) > 0); 00164 00165 if (pbuf2 >= 0 && H5Tclose(pbuf2) < 0) return false; 00166 if (to_close && H5Tclose(pbuf) < 0) return false; 00167 return result; 00168 } 00169 00170 bool 00171 CSerializableHdf5File::dspace_select(EContainerType ctype, index_t y, 00172 index_t x) 00173 { 00174 type_item_t* m = m_stack_type.back(); 00175 00176 if (H5Sselect_none(m->dspace) < 0) return false; 00177 00178 hsize_t coord[2]; 00179 switch (ctype) { 00180 case CT_NDARRAY: SG_NOTIMPLEMENTED; 00181 case CT_SCALAR: return false; 00182 case CT_MATRIX: case CT_SGMATRIX: coord[1] = x; /* break; */ 00183 case CT_VECTOR: case CT_SGVECTOR: coord[0] = y; break; 00184 default: return false; 00185 } 00186 if (H5Sselect_elements(m->dspace, H5S_SELECT_SET, 1, coord) < 0) 00187 return false; 00188 00189 return true; 00190 } 00191 00192 bool 00193 CSerializableHdf5File::attr_write_scalar( 00194 hid_t datatype, const char* name, const void* val) 00195 { 00196 hid_t dspace; 00197 if ((dspace = H5Screate_simple(0, NULL, NULL)) < 0) return false; 00198 hid_t dtype; 00199 if ((dtype = H5Tcopy(datatype)) < 0) return false; 00200 hid_t attr; 00201 if ((attr = H5Acreate2( 00202 m_stack_h5stream.back(), name, dtype, dspace, 00203 H5P_DEFAULT, H5P_DEFAULT)) < 0) return false; 00204 00205 if (H5Awrite(attr, datatype, val) < 0) return false; 00206 00207 if (H5Aclose(attr) < 0) return false; 00208 if (H5Tclose(dtype) < 0) return false; 00209 if (H5Sclose(dspace) < 0) return false; 00210 00211 return true; 00212 } 00213 00214 bool 00215 CSerializableHdf5File::attr_write_string( 00216 const char* name, const char* val) 00217 { 00218 hid_t dtype; 00219 if ((dtype = H5Tcopy(H5T_C_S1)) < 0) return false; 00220 if (H5Tset_size(dtype, strlen(val)+1) < 0) return false; 00221 00222 if (!attr_write_scalar(dtype, name, val)) return false; 00223 00224 if (H5Tclose(dtype) < 0) return false; 00225 00226 return true; 00227 } 00228 00229 bool 00230 CSerializableHdf5File::attr_exists(const char* name) 00231 { 00232 return H5Aexists(m_stack_h5stream.back(), name) > 0; 00233 } 00234 00235 size_t 00236 CSerializableHdf5File::attr_get_size(const char* name) 00237 { 00238 if (!attr_exists(name)) return 0; 00239 00240 hid_t attr; 00241 if ((attr = H5Aopen(m_stack_h5stream.back(), name, H5P_DEFAULT)) 00242 < 0) return 0; 00243 00244 hid_t dtype; 00245 if ((dtype = H5Aget_type(attr)) < 0) return 0; 00246 00247 size_t result = H5Tget_size(dtype); 00248 00249 if (H5Tclose(dtype) < 0) return 0; 00250 if (H5Aclose(attr) < 0) return 0; 00251 00252 return result; 00253 } 00254 00255 bool 00256 CSerializableHdf5File::attr_read_scalar( 00257 hid_t datatype, const char* name, void* val) 00258 { 00259 if (!attr_exists(name)) return false; 00260 00261 hid_t attr; 00262 if ((attr = H5Aopen(m_stack_h5stream.back(), name, H5P_DEFAULT)) 00263 < 0) return false; 00264 00265 hid_t dspace; 00266 if ((dspace = H5Aget_space(attr)) < 0) return false; 00267 if (H5Sget_simple_extent_type(dspace) != H5S_SCALAR) return false; 00268 00269 hid_t dtype; 00270 if ((dtype = H5Aget_type(attr)) < 0) return false; 00271 if (H5Tequal(datatype, dtype) <= 0) return false; 00272 00273 if (H5Aread(attr, datatype, val) < 0) return false; 00274 00275 if (H5Tclose(dtype) < 0) return false; 00276 if (H5Sclose(dspace) < 0) return false; 00277 if (H5Aclose(attr) < 0) return false; 00278 00279 return true; 00280 } 00281 00282 bool 00283 CSerializableHdf5File::attr_read_string( 00284 const char* name, char* val, size_t n) 00285 { 00286 size_t size = attr_get_size(name); 00287 if (size == 0 || size > n) return false; 00288 00289 hid_t dtype; 00290 if ((dtype = H5Tcopy(H5T_C_S1)) < 0) return false; 00291 if (H5Tset_size(dtype, size) < 0) return false; 00292 00293 if (!attr_read_scalar(dtype, name, val)) return false; 00294 00295 if (H5Tclose(dtype) < 0) return false; 00296 00297 return true; 00298 } 00299 00300 bool 00301 CSerializableHdf5File::group_create(const char* name, 00302 const char* prefix) 00303 { 00304 hid_t ngroup; 00305 string_t gname; 00306 00307 snprintf(gname, STRING_LEN, "%s%s", prefix, name); 00308 00309 m_stack_h5stream.push_back( 00310 ngroup = H5Gcreate2(m_stack_h5stream.back(), gname, H5P_DEFAULT, 00311 H5P_DEFAULT, H5P_DEFAULT)); 00312 if (ngroup < 0) return false; 00313 00314 return true; 00315 } 00316 00317 bool 00318 CSerializableHdf5File::group_open(const char* name, 00319 const char* prefix) 00320 { 00321 hid_t group; 00322 string_t gname; 00323 00324 snprintf(gname, STRING_LEN, "%s%s", prefix, name); 00325 00326 m_stack_h5stream.push_back( 00327 group = H5Gopen2(m_stack_h5stream.back(), gname, H5P_DEFAULT)); 00328 if (group < 0) return false; 00329 00330 return true; 00331 } 00332 00333 bool 00334 CSerializableHdf5File::group_close() 00335 { 00336 if (H5Gclose(m_stack_h5stream.back()) < 0) return false; 00337 m_stack_h5stream.pop_back(); 00338 00339 return true; 00340 } 00341 00342 CSerializableHdf5File::CSerializableHdf5File() 00343 :CSerializableFile() { init(""); } 00344 00345 CSerializableHdf5File::CSerializableHdf5File(const char* fname, char rw) 00346 :CSerializableFile() 00347 { 00348 CSerializableFile::init(NULL, rw, fname); 00349 init(fname); 00350 } 00351 00352 CSerializableHdf5File::~CSerializableHdf5File() 00353 { 00354 while (m_stack_type.get_num_elements() > 0) { 00355 delete m_stack_type.back(); m_stack_type.pop_back(); 00356 } 00357 00358 close(); 00359 } 00360 00361 CSerializableFile::TSerializableReader* 00362 CSerializableHdf5File::new_reader(char* dest_version, size_t n) 00363 { 00364 if (!attr_read_string(STR_KEY_FILETYPE, dest_version, n)) 00365 return NULL; 00366 00367 if (strcmp(STR_FILETYPE_00, dest_version) == 0) 00368 return new SerializableHdf5Reader00(this); 00369 00370 return NULL; 00371 } 00372 00373 void 00374 CSerializableHdf5File::init(const char* fname) 00375 { 00376 if (m_filename == NULL || *m_filename == '\0') { 00377 SG_WARNING("Filename not given for opening file!\n"); 00378 close(); return; 00379 } 00380 00381 hid_t h5stream = NOT_OPEN; 00382 switch (m_task) { 00383 case 'w': 00384 h5stream = H5Fcreate(fname, H5F_ACC_TRUNC, H5P_DEFAULT, 00385 H5P_DEFAULT); 00386 break; 00387 case 'r': 00388 h5stream = H5Fopen(fname, H5F_ACC_RDONLY, H5P_DEFAULT); 00389 break; 00390 default: 00391 SG_WARNING("Could not open file `%s', unknown mode!\n", 00392 m_filename); 00393 close(); return; 00394 } 00395 00396 if (h5stream < 0) { 00397 SG_WARNING("Could not open file `%s'!\n", m_filename); 00398 close(); return; 00399 } 00400 00401 m_stack_h5stream.push_back(h5stream); 00402 switch (m_task) { 00403 case 'w': 00404 if (!attr_write_string(STR_KEY_FILETYPE, STR_FILETYPE_00)) { 00405 SG_WARNING("%s: Could not open file for writing during " 00406 "writing filetype!\n", fname); 00407 close(); return; 00408 } 00409 break; 00410 case 'r': break; 00411 default: break; 00412 } 00413 } 00414 00415 void 00416 CSerializableHdf5File::close() 00417 { 00418 while (m_stack_h5stream.get_num_elements() > 1) { 00419 if (m_stack_h5stream.back() >= 0) 00420 H5Gclose(m_stack_h5stream.back()); 00421 m_stack_h5stream.pop_back(); 00422 } 00423 00424 if (m_stack_h5stream.get_num_elements() == 1) { 00425 if (m_stack_h5stream.back() >= 0) 00426 H5Fclose(m_stack_h5stream.back()); 00427 m_stack_h5stream.pop_back(); 00428 } 00429 } 00430 00431 bool 00432 CSerializableHdf5File::is_opened() 00433 { 00434 return m_stack_h5stream.get_num_elements() > 0; 00435 } 00436 00437 bool 00438 CSerializableHdf5File::write_scalar_wrapped( 00439 const TSGDataType* type, const void* param) 00440 { 00441 type_item_t* m = m_stack_type.back(); 00442 00443 switch (type->m_stype) { 00444 case ST_NONE: 00445 if (m->y != 0 || m->x != 0) return true; 00446 break; 00447 case ST_STRING: 00448 if (m->sub_y == 0) 00449 m->vltype[m->x*m->dims[1] + m->y].p = (void*) param; 00450 00451 if ((m->sub_y 00452 < (index_t) m->vltype[m->x*m->dims[1] + m->y].len-1) 00453 || ((type->m_ctype == CT_VECTOR || type->m_ctype == CT_SGVECTOR) && m->y 00454 < (index_t) m->dims[0]-1) 00455 || ((type->m_ctype == CT_MATRIX || type->m_ctype==CT_SGMATRIX) 00456 && (m->x < (index_t) m->dims[0]-1 00457 || m->y < (index_t) m->dims[1]-1))) 00458 return true; 00459 break; 00460 case ST_SPARSE: 00461 if (m->sub_y != 0) return true; 00462 break; 00463 default: return false; 00464 } 00465 00466 hid_t mem_type_id; 00467 if ((mem_type_id = new_stype2hdf5(type->m_stype, type->m_ptype) 00468 ) < 0) return false; 00469 00470 switch (type->m_stype) { 00471 case ST_NONE: 00472 if (H5Dwrite(m->dset, mem_type_id, H5S_ALL, H5S_ALL, 00473 H5P_DEFAULT, param) < 0) return false; 00474 break; 00475 case ST_STRING: 00476 if (H5Dwrite(m->dset, mem_type_id, H5S_ALL, H5S_ALL, 00477 H5P_DEFAULT, m->vltype) < 0) return false; 00478 break; 00479 case ST_SPARSE: 00480 if (H5Dwrite(m->dset, m->dtype, H5S_ALL, H5S_ALL, 00481 H5P_DEFAULT, m->sparse_ptr) < 0) return false; 00482 break; 00483 default: return false; 00484 } 00485 00486 if (H5Tclose(mem_type_id) < 0) return false; 00487 00488 return true; 00489 } 00490 00491 bool 00492 CSerializableHdf5File::write_cont_begin_wrapped( 00493 const TSGDataType* type, index_t len_real_y, index_t len_real_x) 00494 { 00495 hbool_t bool_buf = true; 00496 00497 if (type->m_ptype != PT_SGOBJECT) return true; 00498 00499 if (!attr_write_scalar(H5T_NATIVE_HBOOL, STR_IS_CONT, &bool_buf)) 00500 return false; 00501 00502 string_t ctype_buf; 00503 type->to_string(ctype_buf, STRING_LEN); 00504 if (!attr_write_string(STR_CTYPE_NAME, ctype_buf)) return false; 00505 00506 switch (type->m_ctype) { 00507 case CT_NDARRAY: 00508 SG_NOTIMPLEMENTED; 00509 case CT_SCALAR: 00510 SG_ERROR("write_cont_begin_wrapped(): Implementation error " 00511 "during writing Hdf5File!"); 00512 return false; 00513 case CT_MATRIX: case CT_SGMATRIX: 00514 if (!attr_write_scalar(TYPE_INDEX, STR_LENGTH_X, &len_real_x)) 00515 return false; 00516 /* break; */ 00517 case CT_VECTOR: case CT_SGVECTOR: 00518 if (!attr_write_scalar(TYPE_INDEX, STR_LENGTH_Y, &len_real_y)) 00519 return false; 00520 break; 00521 default: return false; 00522 } 00523 00524 return true; 00525 } 00526 00527 bool 00528 CSerializableHdf5File::write_cont_end_wrapped( 00529 const TSGDataType* type, index_t len_real_y, index_t len_real_x) 00530 { 00531 return true; 00532 } 00533 00534 bool 00535 CSerializableHdf5File::write_string_begin_wrapped( 00536 const TSGDataType* type, index_t length) 00537 { 00538 type_item_t* m = m_stack_type.back(); 00539 00540 m->vltype[m->x*m->dims[1] + m->y].len = length; 00541 00542 return true; 00543 } 00544 00545 bool 00546 CSerializableHdf5File::write_string_end_wrapped( 00547 const TSGDataType* type, index_t length) 00548 { 00549 return true; 00550 } 00551 00552 bool 00553 CSerializableHdf5File::write_stringentry_begin_wrapped( 00554 const TSGDataType* type, index_t y) 00555 { 00556 type_item_t* m = m_stack_type.back(); 00557 00558 m->sub_y = y; 00559 00560 return true; 00561 } 00562 00563 bool 00564 CSerializableHdf5File::write_stringentry_end_wrapped( 00565 const TSGDataType* type, index_t y) 00566 { 00567 return true; 00568 } 00569 00570 bool 00571 CSerializableHdf5File::write_sparse_begin_wrapped( 00572 const TSGDataType* type, index_t length) 00573 { 00574 type_item_t* m_prev = m_stack_type.back(); 00575 00576 if(!dspace_select(type->m_ctype, m_prev->y, m_prev->x)) 00577 return false; 00578 00579 type_item_t* m = new type_item_t(m_stack_type.back()->name); 00580 m_stack_type.push_back(m); 00581 00582 /* ************************************************************ */ 00583 00584 if (m_prev->y == 0 && m_prev->x == 0) { 00585 hbool_t bool_buf = true; 00586 if (!group_create(m->name, STR_GROUP_PREFIX)) return false; 00587 00588 if (!attr_write_scalar(H5T_NATIVE_HBOOL, STR_IS_SPARSE, 00589 &bool_buf)) return false; 00590 } else { 00591 if (!group_open(m->name, STR_GROUP_PREFIX)) return false; 00592 if (!attr_exists(STR_IS_SPARSE)) return false; 00593 } 00594 00595 m->rank = 1; m->dims[0] = length; 00596 if (m->dims[0] == 0) m->dspace = H5Screate(H5S_NULL); 00597 00598 if (m->dspace < 0 && (m->dspace = H5Screate_simple( 00599 m->rank, m->dims, NULL)) < 0) 00600 return false; 00601 if ((m->dtype = new_sparseentrytype(type->m_ptype)) < 0) 00602 return false; 00603 00604 string_t name; 00605 index2string(name, STRING_LEN, type->m_ctype, m_prev->y, 00606 m_prev->x); 00607 if ((m->dset = H5Dcreate2( 00608 m_stack_h5stream.back(), name, m->dtype, m->dspace, 00609 H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) 00610 return false; 00611 00612 /* ************************************************************ */ 00613 00614 char* buf = SG_MALLOC(char, sizeof_sparsetype()); 00615 00616 hid_t mem_type_id; 00617 if ((mem_type_id = new_sparsetype()) < 0) return false; 00618 00619 hid_t mem_space_id; 00620 if ((mem_space_id = H5Screate_simple(0, NULL, NULL)) < 0) 00621 return false; 00622 00623 hobj_ref_t* sparse_ref = get_ref_sparstype(buf); 00624 if (H5Rcreate(sparse_ref, m_stack_h5stream.back(), name, 00625 H5R_OBJECT, -1) < 0) return false; 00626 00627 if (H5Dwrite(m_prev->dset, mem_type_id, mem_space_id, 00628 m_prev->dspace, H5P_DEFAULT, buf) < 0) return false; 00629 00630 if (H5Sclose(mem_space_id) < 0) return false; 00631 if (H5Tclose(mem_type_id) < 0) return false; 00632 00633 delete buf; 00634 00635 return true; 00636 } 00637 00638 bool 00639 CSerializableHdf5File::write_sparse_end_wrapped( 00640 const TSGDataType* type, index_t length) 00641 { 00642 if (!group_close()) return false; 00643 delete m_stack_type.back(); m_stack_type.pop_back(); 00644 00645 return true; 00646 } 00647 00648 bool 00649 CSerializableHdf5File::write_sparseentry_begin_wrapped( 00650 const TSGDataType* type, const SGSparseVectorEntry<char>* first_entry, 00651 index_t feat_index, index_t y) 00652 { 00653 type_item_t* m = m_stack_type.back(); 00654 00655 m->sparse_ptr = (SGSparseVectorEntry<char>*) first_entry; 00656 m->sub_y = y; 00657 00658 return true; 00659 } 00660 00661 bool 00662 CSerializableHdf5File::write_sparseentry_end_wrapped( 00663 const TSGDataType* type, const SGSparseVectorEntry<char>* first_entry, 00664 index_t feat_index, index_t y) 00665 { 00666 return true; 00667 } 00668 00669 bool 00670 CSerializableHdf5File::write_item_begin_wrapped( 00671 const TSGDataType* type, index_t y, index_t x) 00672 { 00673 type_item_t* m = m_stack_type.back(); 00674 m->y = y; m->x = x; 00675 00676 if (type->m_ptype != PT_SGOBJECT) return true; 00677 00678 string_t name; 00679 if (!index2string(name, STRING_LEN, type->m_ctype, y, x)) 00680 return false; 00681 if (!group_create(name, "")) return false; 00682 00683 return true; 00684 } 00685 00686 bool 00687 CSerializableHdf5File::write_item_end_wrapped( 00688 const TSGDataType* type, index_t y, index_t x) 00689 { 00690 if (type->m_ptype == PT_SGOBJECT) 00691 if (!group_close()) return false; 00692 00693 return true; 00694 } 00695 00696 bool 00697 CSerializableHdf5File::write_sgserializable_begin_wrapped( 00698 const TSGDataType* type, const char* sgserializable_name, 00699 EPrimitiveType generic) 00700 { 00701 hbool_t bool_buf = true; 00702 00703 if (!attr_write_scalar(H5T_NATIVE_HBOOL, STR_IS_SGSERIALIZABLE, 00704 &bool_buf)) return false; 00705 00706 if (*sgserializable_name == '\0') { 00707 if (!attr_write_scalar(H5T_NATIVE_HBOOL, STR_IS_NULL, 00708 &bool_buf)) 00709 return false; 00710 return true; 00711 } 00712 00713 if (!attr_write_string(STR_INSTANCE_NAME, sgserializable_name)) 00714 return false; 00715 00716 if (generic != PT_NOT_GENERIC) { 00717 string_t buf; 00718 TSGDataType::ptype_to_string(buf, generic, STRING_LEN); 00719 if (!attr_write_string(STR_GENERIC_NAME, buf)) return false; 00720 } 00721 00722 return true; 00723 } 00724 00725 bool 00726 CSerializableHdf5File::write_sgserializable_end_wrapped( 00727 const TSGDataType* type, const char* sgserializable_name, 00728 EPrimitiveType generic) 00729 { 00730 return true; 00731 } 00732 00733 bool 00734 CSerializableHdf5File::write_type_begin_wrapped( 00735 const TSGDataType* type, const char* name, const char* prefix) 00736 { 00737 type_item_t* m = new type_item_t(name); m_stack_type.push_back(m); 00738 00739 if (type->m_ptype == PT_SGOBJECT) { 00740 if (!group_create(name, "")) return false; 00741 return true; 00742 } 00743 00744 switch (type->m_ctype) { 00745 case CT_NDARRAY: 00746 SG_NOTIMPLEMENTED; 00747 case CT_SCALAR: 00748 m->rank = 0; 00749 if (type->m_stype == ST_STRING) m->vltype = SG_MALLOC(hvl_t, 1); 00750 break; 00751 case CT_VECTOR: case CT_SGVECTOR: 00752 m->rank = 1; m->dims[0] = *type->m_length_y; 00753 if (m->dims[0] == 0) m->dspace = H5Screate(H5S_NULL); 00754 if (type->m_stype == ST_STRING) 00755 m->vltype = SG_MALLOC(hvl_t, m->dims[0]); 00756 break; 00757 case CT_MATRIX: case CT_SGMATRIX: 00758 m->rank = 2; 00759 m->dims[0] = *type->m_length_x; m->dims[1] = *type->m_length_y; 00760 if (m->dims[0] *m->dims[1] == 0) 00761 m->dspace = H5Screate(H5S_NULL); 00762 if (type->m_stype == ST_STRING) 00763 m->vltype = SG_MALLOC(hvl_t, m->dims[0] *m->dims[1]); 00764 break; 00765 default: return false; 00766 } 00767 00768 if (m->dspace < 0 && (m->dspace = H5Screate_simple( 00769 m->rank, m->dims, NULL)) < 0) 00770 return false; 00771 if ((m->dtype = new_stype2hdf5(type->m_stype, type->m_ptype)) < 0) 00772 return false; 00773 00774 if ((m->dset = H5Dcreate2( 00775 m_stack_h5stream.back(), name, m->dtype, m->dspace, 00776 H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) 00777 return false; 00778 00779 return true; 00780 } 00781 00782 bool 00783 CSerializableHdf5File::write_type_end_wrapped( 00784 const TSGDataType* type, const char* name, const char* prefix) 00785 { 00786 if (type->m_ptype == PT_SGOBJECT) 00787 if (!group_close()) return false; 00788 00789 delete m_stack_type.back(); m_stack_type.pop_back(); 00790 return true; 00791 } 00792 00793 #endif /* HAVE_HDF5 */