SheafSystem  0.0.0.0
record_set.cc
1 
2 //
3 // Copyright (c) 2014 Limit Point Systems, Inc.
4 //
5 // Licensed under the Apache License, Version 2.0 (the "License");
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 // http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17 
18 // Implementation for class record_set
19 
20 #include "SheafSystem/record_set.h"
21 
22 #include "SheafSystem/data_converter.h"
23 #include "SheafSystem/error_message.h"
24 #include "SheafSystem/namespace_poset.h"
25 #include "SheafSystem/record_index.h"
26 #include "SheafSystem/assert_contract.h"
27 #include "SheafSystem/sheaf_file.h"
28 #include "SheafSystem/record.h"
29 
30 using namespace std;
31 
32 //#define DIAGNOSTIC_OUTPUT
33 //#undef DIAGNOSTIC_OUTPUT
34 
35 // =============================================================================
36 // ANY FACET
37 // =============================================================================
38 
39 
43 clone() const
44 {
45  record_set* result = 0;
46  // Initialized to keep
47  // some compilers from complaining.
48 
49  // Preconditions:
50 
51  // Body:
52 
53  // Class is abstract;
54  // can't create an instance.
55 
56  not_implemented();
57 
58  // Postconditions:
59 
60  ensure(result != 0);
61  ensure(is_same_type(result));
62 
63  // Exit:
64 
65  return result;
66 }
67 
69 bool
71 invariant() const
72 {
73  bool result = true;
74 
75  // Preconditions:
76 
77  // Body:
78 
79  // Must satisfy base class invariant
80 
81  result = result && any::invariant();
82 
83  if(invariant_check())
84  {
85  // Prevent recursive calls to invariant
86 
87  disable_invariant_check();
88 
89  invariance(file().is_open());
90  invariance(!name().empty());
91  invariance(record_buffer_ub() >= 0);
92  invariance(record_buffer_ct() >= 0);
93  invariance(record_buffer_ct() <= record_buffer_ub());
94 
95  // Finished, turn invariant checking back on.
96 
97  enable_invariant_check();
98  }
99 
100  // Postconditions:
101 
102  // Exit
103 
104  return result;
105 }
106 
108 bool
110 is_ancestor_of(const any* other) const
111 {
112 
113  // Preconditions:
114 
115  require(other != 0);
116 
117  // Body:
118 
119  // True if other conforms to this
120 
121  bool result = dynamic_cast<const record_set*>(other) != 0;
122 
123  // Postconditions:
124 
125  return result;
126 
127 }
128 
129 
130 // =============================================================================
131 // RECORD_SET FACET
132 // =============================================================================
133 
136 record_set(const sheaf_file& xfile, int xrecord_buffer_ub, const poset_scaffold& xscaffold)
137  : _file(const_cast<sheaf_file&>(xfile)),
138  _name(xscaffold.structure().name()),
139  _record_buffer_ub(xrecord_buffer_ub),
140  _scaffold(const_cast<poset_scaffold&>(xscaffold))
141 {
142 
143  // Preconditions:
144 
145  require(xfile.is_open());
146  require(xrecord_buffer_ub > 0);
147 
148  // Body:
149 
150  // Set hdf ids to indicate invalid status
151 
157 
158 
159  // No records active.
160 
161  _record_buffer_ct = 0;
162 
163  // Postconditions:
164 
165  ensure(invariant());
166  ensure(!is_open());
167  ensure(record_buffer_ub() == xrecord_buffer_ub);
168  ensure(record_buffer_ct() == 0);
169 }
170 
171 
174 record_set(const record_set& xother)
175  : _file(xother._file), _scaffold(xother._scaffold)
176 {
177 
178  // Preconditions:
179 
180 
181  // Body:
182 
183  not_implemented();
184 
185  // Postconditions:
186 
187  ensure(invariant());
188 }
189 
193 {
194 
195  // Preconditions:
196 
197  // Body:
198 
199 
200  // Postconditions:
201 
202  // Exit:
203 
204  return;
205 }
206 
207 
208 
209 
211 const sheaf::sheaf_file&
213 file() const
214 {
215  return _file;
216 }
217 
218 
219 
220 
222 std::string
224 name() const
225 {
226 
227  // Preconditions:
228 
229  // Body:
230 
231  string result(_name);
232 
233  // Postconditions:
234 
235  ensure(!result.empty());
236 
237  // Exit
238 
239  return result;
240 }
241 
242 
243 
245 std::string
247 alias() const
248 {
249 
250  // Preconditions:
251 
252  // Body:
253 
254  string result(_alias);
255 
256  // Postconditions:
257 
258  // ensure(!scaffold().structure_is_namespace() == (name() == result));
259 
260  // Exit
261 
262  return result;
263 }
264 
265 
266 const std::string&
269 {
270  static const string result(poset_path::reserved_prefix() + "name_space");
271  return result;
272 }
273 
274 const std::string&
277 {
278  static const string result(poset_path::reserved_prefix() + "name_space.");
279  return result;
280 }
281 
282 const std::string&
284 suffix() const
285 {
286  // cout << endl << "Entering record_set::suffix." << endl;
287 
288  // Preconditions:
289 
290 
291  // Body:
292 
293  // Empty in this call, redefined in descendants.
294 
295  static const string result;
296 
297  // Postconditions:
298 
299 
300  // Exit:
301 
302  // cout << "Leaving record_set::suffix." << endl;
303  return result;
304 }
305 
306 std::string
308 data_set_name(const std::string& xname) const
309 {
310  // cout << endl << "Entering record_set::data_set_name." << endl;
311 
312  // Preconditions:
313 
314 
315  // Body:
316 
317  string result;
318  if(scaffold().structure_is_namespace())
319  {
320  result = name_space_prefix() + xname + suffix();
321  }
322  else
323  {
324  result = xname + suffix();
325  }
326 
327  // Postconditions:
328 
329  ensure(scaffold().structure_is_namespace() ? result == name_space_prefix() + xname + suffix() : result == xname + suffix());
330 
331 
332  // Exit:
333 
334  // cout << "Leaving record_set::data_set_name." << endl;
335  return result;
336 }
337 
338 std::string
340 data_set_alias(const std::string& xname) const
341 {
342  // cout << endl << "Entering record_set::data_set_alias." << endl;
343 
344  // Preconditions:
345 
346 
347  // Body:
348 
349  string result;
350  if(scaffold().structure_is_namespace())
351  {
352  result = name_space_alias() + suffix();
353  }
354  else
355  {
356  result = xname + suffix();
357  }
358 
359  // Postconditions:
360 
361  ensure(scaffold().structure_is_namespace() ? result == name_space_alias() + suffix() : result == xname + suffix());
362 
363 
364  // Exit:
365 
366  // cout << "Leaving record_set::data_set_alias." << endl;
367  return result;
368 }
369 
370 
371 std::string
373 poset_name() const
374 {
375  // cout << endl << "Entering attributes_record_set::poset_name." << endl;
376 
377  // Preconditions:
378 
379  // Body:
380 
381  // Skip past namespace prefix, if there is one.
382 
383  string::size_type lprefix_len = name_space_prefix().size();
384 
385  string::size_type lname_begin;
386  if(_name.substr(0, lprefix_len) == name_space_prefix())
387  {
388  lname_begin = lprefix_len;
389  }
390  else
391  {
392  lname_begin = 0;
393  }
394 
395  string::size_type lsuffix_begin = suffix().empty() ? _name.size() : _name.rfind(suffix());
396 
397  // Extract the name.
398 
399  string::size_type lname_len = lsuffix_begin - lname_begin;
400 
401  string result(_name.substr(lname_begin, lname_len));
402 
403  // Postconditions:
404 
405 
406  // Exit:
407 
408  // cout << "Leaving attributes_record_set::poset_name." << endl;
409  return result;
410 }
411 
412 
417 {
418  return _scaffold;
419 }
420 
424 scaffold() const
425 {
426  return _scaffold;
427 }
428 
433 {
434  return _scaffold.type_map();
435 }
436 
437 
438 
442 type_map() const
443 {
444  return _scaffold.type_map();
445 }
446 
448 void
451 {
452  // Preconditions:
453 
454  require(file().is_open());
455 
456  // Body:
457 
458 #ifdef DIAGNOSTIC_OUTPUT
459 
460  cout << "record_set::open: opening dataset " << alias() << endl;
461 #endif
462 
463  // Create the internal HDF data type.
464 
466 
467  // Attempt to open the dataset using its alias.
468  // Need to use alias because if we're reading the namespace,
469  // we don't yet know its name.
470 
471  _hdf_id = H5Dopen1(_file.hdf_id(), _alias.c_str());
472 
473  if(_hdf_id < 0)
474  {
475  // Attempt to open dataset failed.
476 
477  if(file().mode() == sheaf_file::READ_WRITE)
478  {
479  // Open failed and we're writing the file; create the dataset
480 
481 #ifdef DIAGNOSTIC_OUTPUT
482  cout << endl << "record_set::open: open failed, creating dataset " << name() << endl << endl;
483 #endif
484 
486 
487  if(_alias != _name)
488  {
489  // Create a link from the alias to the dataset.
490 
491  create_alias();
492  }
493  }
494  else
495  {
496  // Open failed and we're reading the file;
497  // it is an error if the dataset does not already exist.
498 
499  post_fatal_error_message("dataset doesn't exist");
500  }
501  }
502  else
503  {
504  // Open succeeded;
505  // we're doing either a read the file or
506  // a subsequent (not first) partial write.
507 
508 
509  if( file().mode() == sheaf_file::READ_ONLY)
510  {
511  // We're doing a read.
512 
513  if(_alias != _name)
514  {
515  // Set _name to the primary name of the data set.
516 
518  }
519  }
520 
521 
522  // Read the attributes, if any.
523  // If we're doing a read, this reads and initializes all the attributes.
524  // If we're doing a subsequent partial write, this extends the attributes
525  // in memory to incorporate all those previously written. There doesn't
526  // seem to be any way to directly extend the attributes on disk in HDF.
527 
529  }
530 
531  // Now the dataset is open;
532  // get the dataspace, data type, and extent
533 
534  _ext_dataspace_hdf_id = H5Dget_space(_hdf_id);
535  if(_ext_dataspace_hdf_id < 0)
536  {
537  post_fatal_error_message("unable to get dataspace of open dataset");
538  }
539 
540  _ext_data_type_hdf_id = H5Dget_type(_hdf_id);
541  if(_ext_data_type_hdf_id < 0)
542  {
543  post_fatal_error_message("unable to get data type of open dataset");
544  }
545 
546  int lrank = H5Sget_simple_extent_dims(_ext_dataspace_hdf_id, _ext_dataspace_dims, NULL);
547  if(lrank != ext_dataspace_rank())
548  {
549  post_fatal_error_message("unable to get dimensions of open dataset");
550  }
551 
552  // Postconditions:
553 
554  ensure(invariant());
555  ensure(is_open());
556 
557  // Exit
558 
559  return;
560 }
561 
562 
563 
565 bool
567 is_open() const
568 {
569  bool result;
570 
571  // Preconditions:
572 
573  // Body:
574 
575  result = _hdf_id >= 0;
576 
577  // Postconditions:
578 
579  // Exit
580 
581  return result;
582 }
583 
584 
586 void
589 {
590  // Preconditions:
591 
592  // Body:
593 
594 
595  // Write the attributes.
596 
597  if(file().mode() == sheaf_file::READ_WRITE)
598  {
600  }
601 
602  // Close all the resources allocated for this record set.
603 
604  if(_int_data_type_hdf_id >= 0)
605  H5Tclose(_int_data_type_hdf_id);
606  if(_ext_data_type_hdf_id >= 0)
607  H5Tclose(_ext_data_type_hdf_id);
608  if(_int_dataspace_hdf_id >= 0)
609  H5Sclose(_int_dataspace_hdf_id);
610  if(_ext_dataspace_hdf_id >= 0)
611  H5Sclose(_ext_dataspace_hdf_id);
612  if(_hdf_id >= 0)
613  H5Dclose(_hdf_id);
614 
620 
621  // Postconditions:
622 
623  ensure(!is_open());
624 
625  // Exit
626 
627  return;
628 }
629 
630 
631 
633 int
636 {
637  return _record_buffer_ct;
638 }
639 
641 void
644 {
645  // Preconditions:
646 
647  // Body:
648 
650 
651  // Postconditions:
652 
653 
654  // Exit:
655 
656  return;
657 }
658 
660 void
663 {
664  // Preconditions:
665 
666 
667  // Body:
668 
669  _record_buffer_ct = 0;
670 
671  // Postconditions:
672 
673  ensure(record_buffer_is_empty());
674 
675  // Exit:
676 
677  return;
678 }
679 
680 
681 
683 int
686 {
687  return _record_buffer_ub;
688 }
689 
690 
691 
693 bool
696 {
697  return _record_buffer_ct == 0;
698 }
699 
700 
701 
703 bool
706 {
708 }
709 
710 
711 // =============================================================================
712 // PROTECTED MEMBER FUNCTIONS
713 // =============================================================================
714 
716 hid_t
719 {
720  hid_t result = NOT_AN_HDF_ID;
721 
722  // Preconditions:
723 
724  require(file().mode() == sheaf_file::READ_WRITE);
725 
726  // Body:
727 
728  is_abstract();
729 
730  // Postconditions:
731 
732  ensure(result >= 0);
733 
734  // Exit
735 
736  return result;
737 }
738 
740 void
743 {
744  // Preconditions:
745 
746  require(file().is_open());
747 
748  // Body:
749 
750  is_abstract();
751 
752  // Postconditions:
753 
754  ensure(int_data_type_hdf_id() >= 0);
755 
756  // Exit:
757 
758  return;
759 }
760 
762 void
764 extend_dataset(const hsize_t* xdims, int xdims_ub)
765 {
766  // Preconditions:
767 
768  require(is_open());
769  require(xdims_ub >= ext_dataspace_rank());
770 
771  // Body:
772 
773 #ifdef DIAGNOSTIC_OUTPUT
774 
775  cout << "record_set::extend_dataset: dataspace extent:"
776  << "xdims_ub= " << xdims_ub << "xdims= ";
777  for(int i=0; i<xdims_ub; i++)
778  {
779  cout << " " << xdims[i];
780  }
781  cout << endl;
782 #endif
783 
784  // Extend the dataset to include the selection;
785 
786  herr_t status = H5Dextend(_hdf_id, xdims);
787  if(status < 0)
788  {
789  post_fatal_error_message("can't extend member record dataset");
790  }
791 
792  // Close the old dataspace to prevent resource leaks.
793 
794  status = H5Sclose(_ext_dataspace_hdf_id);
795  if(status < 0)
796  {
797  post_fatal_error_message("can't close member record set dataspace");
798  }
799 
800  // Extending the dataset creates a new dataspace, get it.
801 
802  _ext_dataspace_hdf_id = H5Dget_space(_hdf_id);
803  if(_ext_dataspace_hdf_id < 0)
804  {
805  post_fatal_error_message("can't get extended member record set dataspace");
806  }
807 
808 #ifdef DIAGNOSTIC_OUTPUT
809  cout << "record_set::extend_dataset: dataspace extent:";
810  for(int i=0; i<ext_dataspace_rank(); i++)
811  {
812  cout << " " << _ext_dataspace_dims[i];
813  }
814  cout << endl;
815 #endif
816 
817  // Update the current dimensions
818 
819  int lrank = H5Sget_simple_extent_dims(_ext_dataspace_hdf_id, _ext_dataspace_dims, NULL);
820  if(lrank != ext_dataspace_rank())
821  {
822  post_fatal_error_message("unable to get dimensions of extended dataset");
823  }
824 
825 #ifdef DIAGNOSTIC_OUTPUT
826  cout << "record_set::extend_dataset: dataspace extent:";
827  for(int i=0; i<ext_dataspace_rank(); i++)
828  {
829  cout << " " << _ext_dataspace_dims[i];
830  }
831  cout << endl;
832 #endif
833 
834  // Postconditions:
835 
836  ensure(ext_dataspace_dim(0) >= xdims[0]);
837  ensure(unexecutable("for all 0 <= i < ext_dataspace_rank(): ext_dataspace_dim(i) == xdims[i]"));
838 
840 
841  // Exit
842 
843  return;
844 }
845 
847 void
850 {
851  // Preconditions:
852 
853  require(alias() != name());
854  require(is_open());
855 
856  // Body:
857 
858  // Create a link from the alias to the dataset.
859 
860  herr_t status = H5Glink(file().hdf_id(), H5G_LINK_SOFT, _name.c_str(), _alias.c_str());
861 
862  if(status < 0)
863  {
864  post_fatal_error_message("can't create soft link for alias");
865  }
866 
867  // Postconditions:
868 
869  ensure(unexecutable("link from alias to data set exists"));
870 
871  // Exit
872 
873  return;
874 }
875 
877 void
880 {
881  // Preconditions:
882 
883  require(alias() != name());
884  require(is_open());
885 
886  // Body:
887 
888  // Get the primary name of the dataset.
889 
890  // First have to get the length of the name.
891 
892  H5G_stat_t lstatbuf;
893  hbool_t lfalse = 0;
894  herr_t status = H5Gget_objinfo(file().hdf_id(), _alias.c_str(), lfalse, &lstatbuf);
895  if(status < 0)
896  {
897  post_fatal_error_message("can't get_objinfo for alias");
898  }
899 
900  // Now we can allocate a buffer and get the name.
901 
902  char* lname = new char[lstatbuf.linklen];
903  status = H5Gget_linkval(file().hdf_id(), _alias.c_str(), lstatbuf.linklen, lname);
904  if(status < 0)
905  {
906  post_fatal_error_message("can't get_linkval for alias");
907  }
908 
909  // Set the name.
910 
911  _name = lname;
912 
913  // Clean up.
914 
915  delete [] lname;
916 
917  // Postconditions:
918 
919  ensure(!name().empty());
920 
921  // Exit
922 
923  return;
924 }
925 
926 
927 hid_t
930 {
931  return _hdf_id;
932 }
933 
934 hid_t
937 {
938  return _ext_dataspace_hdf_id;
939 }
940 
941 hid_t
944 {
945  return _ext_data_type_hdf_id;
946 }
947 
948 int
951 {
952  return _ext_dataspace_rank;
953 }
954 
955 
956 
958 hsize_t
961 {
962  hsize_t result;
963 
964  // Preconditions:
965 
966  require(is_open());
967  require((0 <= xi) && (xi < ext_dataspace_rank()));
968 
969  // Body:
970 
971  result = _ext_dataspace_dims[xi];
972 
973  // Postconditions:
974 
975  // Exit
976 
977  return result;
978 }
979 
980 hid_t
983 {
984  return _int_dataspace_hdf_id;
985 }
986 
987 hid_t
990 {
991  return _int_data_type_hdf_id;
992 }
993 
994 
995 
996 const hid_t sheaf::record_set::NOT_AN_HDF_ID = -1;
997 
998 void
1001 {
1002  // Preconditions:
1003 
1004  require(is_open());
1005 
1006  // Body:
1007 
1008  // Stub in this class, just to establish contract;
1009  // intended to be redefined in descendants.
1010 
1011  // Postconditions:
1012 
1013  ensure(unexecutable("all attributes opened, read, and closed"));
1014 
1015  // Exit
1016 
1017  return;
1018 }
1019 
1020 void
1023 {
1024  // Preconditions:
1025 
1026  require(is_open());
1027 
1028  // Body:
1029 
1030  // Stub in this class, just to establish contract;
1031  // intended to be redefined in descendants.
1032 
1033  // Postconditions:
1034 
1035  ensure(unexecutable("all attributes created, written, and closed"));
1036 
1037  // Exit
1038 
1039  return;
1040 }
1041 
1043 void
1045 read_attribute(const char*& xatt_values,
1046  size_type& xatt_ct,
1047  const data_converter* xatt_conv,
1048  const std::string& xatt_name)
1049 {
1050  // Preconditions:
1051 
1052  require(is_open());
1053  require(xatt_values == 0);
1054  require(xatt_ct == 0);
1055  require(xatt_conv != 0);
1056  require(!xatt_name.empty());
1057 
1058 
1059  // Body:
1060 
1061 #ifdef DIAGNOSTIC_OUTPUT
1062 
1063  cout << "record_set::read_attribute poset name: "
1064  << scaffold().structure().name()
1065  << endl;
1066 #endif
1067 
1068  herr_t lstatus;
1069 
1070  // Open the attribute.
1071 
1072  hid_t latt_hdf_id = H5Aopen_name(_hdf_id, xatt_name.c_str());
1073  if(latt_hdf_id >= 0)
1074  {
1075  // Open succeeded; get the attribute data space and extent.
1076 
1077  hid_t latt_dataspace_hdf_id = H5Aget_space(latt_hdf_id);
1078  if(latt_dataspace_hdf_id < 0)
1079  {
1080  string lmsg("Unable to get dataspace for attribute ");
1081  lmsg += xatt_name;
1082  post_fatal_error_message(lmsg.c_str());
1083  }
1084 
1085  hsize_t latt_ct;
1086  lstatus = H5Sget_simple_extent_dims(latt_dataspace_hdf_id, &latt_ct, NULL);
1087  if(lstatus < 0)
1088  {
1089  string lmsg("Unable to get extent for attribute ");
1090  lmsg += xatt_name;
1091  post_fatal_error_message(lmsg.c_str());
1092  }
1093 
1094 
1095  // Create some storage for the types map that HDF can access.
1096  // Client must delete this storage.
1097 
1098  xatt_ct = latt_ct*xatt_conv->internal_size();
1099  xatt_values = new char[xatt_ct];
1100 
1101  // Read the types attribute
1102 
1103  lstatus = H5Aread(latt_hdf_id, xatt_conv->internal_type(), const_cast<char*&>(xatt_values));
1104  if(lstatus < 0)
1105  {
1106  string lmsg("Unable to read attribute ");
1107  lmsg += xatt_name;
1108  post_fatal_error_message(lmsg.c_str());
1109  }
1110 
1111  // Close the attribute and dataspace.
1112 
1113  H5Sclose(latt_dataspace_hdf_id);
1114  H5Aclose(latt_hdf_id);
1115 
1116  }
1117  else
1118  {
1119  // Open failed. Dof tuple count must be 0. Do nothing.
1120  }
1121 
1122  // Postconditions:
1123 
1124  ensure((xatt_values == 0) == (xatt_ct == 0));
1125 
1126  // Exit
1127 
1128  return;
1129 }
1130 
1131 
1133 void
1135 write_attribute(const void* xatt_values,
1136  size_type xatt_ct,
1137  const data_converter* xatt_conv,
1138  const std::string& xatt_name)
1139 {
1140  // Preconditions:
1141 
1142  require(xatt_values != 0);
1143  require(xatt_ct > 0);
1144  require(xatt_conv != 0);
1145  require(!xatt_name.empty());
1146 
1147  // Body:
1148 
1149  herr_t lstatus;
1150 
1151  // Delete any existing version of the attribute.
1152  // Delete will fail if attribute doesn't exist, ignore the return status.
1153 
1156 
1157  lstatus = H5Adelete(_hdf_id, xatt_name.c_str());
1158 
1159  // Create the attribute data space.
1160 
1161  hid_t latt_dataspace_hdf_id = H5Screate(H5S_SIMPLE);
1162  if(latt_dataspace_hdf_id < 0)
1163  {
1164  string lmsg("Unable to create dataspace for attribute ");
1165  lmsg += xatt_name;
1166 
1167  post_fatal_error_message(lmsg.c_str());
1168  }
1169 
1170  // Set the extent of the dataspace.
1171 
1172  hsize_t hatt_ct = xatt_ct;
1173  lstatus = H5Sset_extent_simple(latt_dataspace_hdf_id, 1, &hatt_ct, NULL);
1174  if(lstatus < 0)
1175  {
1176  string lmsg("Unable to set extent for attribute ");
1177  lmsg += xatt_name;
1178  post_fatal_error_message(lmsg.c_str());
1179  }
1180 
1181  // Create the attribute.
1182 
1183  // hid_t latt_hdf_id = H5Acreate(_hdf_id,
1184  hid_t latt_hdf_id = H5Acreate1(_hdf_id,
1185  xatt_name.c_str(),
1186  xatt_conv->external_type(),
1187  latt_dataspace_hdf_id,
1188  H5P_DEFAULT);
1189  if(latt_hdf_id < 0)
1190  {
1191  string lmsg("Unable to create attribute ");
1192  lmsg += xatt_name;
1193  post_fatal_error_message(lmsg.c_str());
1194  }
1195 
1196  // Write the attribute.
1197 
1198  lstatus = H5Awrite(latt_hdf_id, xatt_conv->internal_type(), xatt_values);
1199  if(lstatus < 0)
1200  {
1201  string lmsg("Unable to write attribute ");
1202  lmsg += xatt_name;
1203  post_fatal_error_message(lmsg.c_str());
1204  }
1205 
1206  // Close the attribute and dataspace.
1207 
1208  H5Sclose(latt_dataspace_hdf_id);
1209  latt_dataspace_hdf_id = NOT_AN_HDF_ID;
1210 
1211  H5Aclose(latt_hdf_id);
1212  latt_hdf_id = NOT_AN_HDF_ID;
1213 
1214  // Postconditions:
1215 
1216 
1217  // Exit:
1218 
1219  return;
1220 }
An encapsulation of an HDF file containing sheaf data.
Definition: sheaf_file.h:49
sheaf_file & _file
The file this record_set belongs to.
Definition: record_set.h:385
int _ext_dataspace_rank
The rank of the dataspace for the record_set.
Definition: record_set.h:420
virtual void open()
Opens the record_set.
Definition: record_set.cc:450
hsize_t * _ext_dataspace_dims
The current dimensions of the external dataspace.
Definition: record_set.h:425
void reset_record_buffer_ct()
The set the number of active records in record buffer to 0.
Definition: record_set.cc:662
hid_t external_type() const
The external type identifier.
size_t internal_size() const
The size in bytes of the internal type.
bool record_buffer_is_full() const
True if there are no inactive records in the buffer.
Definition: record_set.cc:705
hsize_t ext_dataspace_dim(int xi)
The dimension of xi-th index of the external dataspace.
Definition: record_set.cc:960
virtual void close()
Closes the record_set.
Definition: record_set.cc:588
std::string data_set_alias(const std::string &xname) const
The data set alias for a poset with name xname.
Definition: record_set.cc:340
virtual void create_int_data_type()=0
Creates a new HDF internal data type. Defined in descendants.
Definition: record_set.cc:742
static const std::string & name_space_prefix()
The reserved, standard prefix for namespace dataser names.
Definition: record_set.cc:276
std::string poset_name() const
The name of the poset this represents, extracted from the name of the dataset.
Definition: record_set.cc:373
record_set(const sheaf_file &xfile, int xrecord_buffer_ub, const poset_scaffold &xscaffold)
Creates an instance attached to the record_set with name xname in the file xfile, using record packet...
Definition: record_set.cc:136
int record_buffer_ct() const
The number of active records in record buffer.
Definition: record_set.cc:635
void extend_dataset(const hsize_t *xdims, int xdims_ub)
Extends the dataset dimensions to at least the dimensions given xdims, an array of length xdims_ub...
Definition: record_set.cc:764
virtual record_set * clone() const
Virtual constructor; makes a new instance of the same type as this. Not implemented since this class ...
Definition: record_set.cc:43
STL namespace.
int _record_buffer_ub
The maximum number of records the buffer can hold.
Definition: record_set.h:441
virtual bool is_ancestor_of(const any *other) const
Conformance test; true if other conforms to this.
Definition: record_set.cc:110
bool record_buffer_is_empty() const
True if there are no active records in the buffer.
Definition: record_set.cc:695
bool is_open() const
True if this record_set is open.
Definition: record_set.cc:567
poset_scaffold & _scaffold
The poset scaffold associated with this.
Definition: record_set.h:400
hid_t int_data_type_hdf_id()
The HDF internal data type id for this record set.
Definition: record_set.cc:989
std::string alias() const
The standard alias for this data set.
Definition: record_set.cc:247
static const std::string & name_space_alias()
The reserved, standard alias for the namespace in the file.
Definition: record_set.cc:268
hid_t _hdf_id
The HDF id for this record set.
Definition: record_set.h:405
virtual bool invariant() const
Class invariant.
Definition: record_set.cc:71
Abstract base class with useful features for all objects.
Definition: any.h:39
std::string _alias
The standard alias for this record_set.
Definition: record_set.h:395
hid_t _ext_data_type_hdf_id
The HDF external data type id for this record set.
Definition: record_set.h:415
A poset specific collection of data converters, various buffers and other data used while transferrin...
hid_t _int_data_type_hdf_id
The HDF internal data type id for this record set.
Definition: record_set.h:452
bool is_open() const
True if this file is open.
Definition: sheaf_file.cc:306
std::string _name
The name of this record_set.
Definition: record_set.h:390
hid_t hdf_id()
The HDF id for this record set.
Definition: record_set.cc:929
hid_t int_dataspace_hdf_id()
The hdf5 id of the internal dataspace associated with the record buffer.
Definition: record_set.cc:982
virtual ~record_set()
Destructor.
Definition: record_set.cc:192
int record_buffer_ub() const
The maximum number of records the buffer can hold.
Definition: record_set.cc:685
int ext_dataspace_rank()
The rank of the dataspace for the record_set.
Definition: record_set.cc:950
hid_t ext_data_type_hdf_id()
The HDF external data type id for this record set.
Definition: record_set.cc:943
unsigned long size_type
An unsigned integral type used to represent sizes and capacities.
Definition: sheaf.h:52
An abstract, indexed collection of records on secondary storage.
Definition: record_set.h:150
std::string data_set_name(const std::string &xname) const
The data set name for a poset with name xname.
Definition: record_set.cc:308
access_mode mode() const
The current access mode.
Definition: sheaf_file.cc:330
static std::string reserved_prefix()
Prefix for identifying member names reserved by the sheaf system.
Definition: poset_path.cc:883
poset_scaffold & scaffold()
Scaffold for constructing poset associated with this record set (mutable version).
Definition: record_set.cc:416
virtual std::string name() const
The name of this poset.
poset_state_handle & structure()
The handle for the poset being transferred. (Name chosen to void name conflict with class poset...
virtual void read_dataset_attributes()
Opens and reads the dataset attribute objects from the file. A stub in this class, intended to be redefined in descendants.
Definition: record_set.cc:1000
std::string name() const
The name of this data set.
Definition: record_set.cc:224
void inc_record_buffer_ct()
The increment the number of active records in record buffer.
Definition: record_set.cc:643
virtual hid_t create_dataset()=0
Creates a new HDF datset. Defined in descendants.
Definition: record_set.cc:718
virtual const std::string & suffix() const
The name suffix for this data set.
Definition: record_set.cc:284
poset_data_type_map & type_map()
Data type map for this poset (mutable version)
const sheaf_file & file() const
The file this record_set belongs to.
Definition: record_set.cc:213
virtual void write_dataset_attributes()
Writes the dataset attribute objects into the file. A stub in this class, intended to be redefined in...
Definition: record_set.cc:1022
Function object to convert between internal and external data formats.
poset_data_type_map & type_map()
Data type map for records in this record set (mutable version)
Definition: record_set.cc:432
void write_attribute(const void *xatt_values, size_type xatt_ct, const data_converter *xatt_conv, const std::string &xatt_name)
Writes the attribute with name xatt_name into the file.
Definition: record_set.cc:1135
hid_t ext_dataspace_hdf_id()
The HDF id for the external dataspace of this record set.
Definition: record_set.cc:936
A poset specific collection of data converters, various buffers and other data used while transferrin...
void create_alias()
Creates a soft link from alias to the data set.
Definition: record_set.cc:849
static const hid_t NOT_AN_HDF_ID
Value indicating an invalid HDf object id. /.
Definition: record_set.h:431
hid_t internal_type() const
The HDF type identifier for the internal type.
void read_attribute(const char *&xatt_values, size_type &xatt_ct, const data_converter *xatt_conv, const std::string &xatt_name)
Reads the attribute with name xatt_name from the file.
Definition: record_set.cc:1045
void set_name_from_alias()
Sets the primary name of the dataset from the alias.
Definition: record_set.cc:879
hid_t _ext_dataspace_hdf_id
The HDF id for the external dataspace of this record set.
Definition: record_set.h:410
int _record_buffer_ct
The number of active records in record buffer.
Definition: record_set.h:436
hid_t _int_dataspace_hdf_id
The hdf5 id of the dataspace associated with the record buffer.
Definition: record_set.h:447