Files
hdf5/c++/test/tattr.cpp
Dana Robinson a00ad2b657 VFD SWMR: Normalization with develop (#765)
* Brings CMake updates from develop

* Brings reduction in pedantic casts from develop

* Purges UFAIL from the library (#637)

* Committing clang-format changes

* Purges UFAIL from the library

* H5HL_insert change requested in PR

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Removes gratuitous (double)x.yF casts (#632)

* Committing clang-format changes

* Removes gratuitous (double)x.yF casts

* Committing clang-format changes

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Committing clang-format changes

* Cleans up a const warning left over from previous constification (#633)

* Committing clang-format changes

* Adds consts to a few global variables

* Cleans up a const warning left over from previous constification

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Formatted source

* Bring over some VOL registration changes

* VOL cleanup

* H5VL_request_status_t substitutions

* H5F.c cleanup

* Minor API tweaks from develop

* Moves H5G package init/teardown to H5Gint.c

* H5G cleanup

* H5M cleanup

* H5SM cleanup

* H5T cleanup

* H5R cleanup

* H5Lpublic.h cleanup

* H5L cleanup

* H5O cleanup

* H5A, H5CS, and H5AC cleanup

* Moved H5A init/teardown code to H5Aint.c

* Moves H5D I/O functions to H5D.c

* H5D cleanup

* Misc minor cleanup

* H5P close cleanup

* H5Tpublic.h cleanup

* Fixes err_compat test

* H5PLpublic.h cleanup

* Updates H5Ppublic.h

* H5Fpublic.h updates

* H5A.c cleanup

* Brings over H5Aexists and related changes

* Brings CMake shell testing changes from develop

* Close callback changes

* H5R and H5Tcommit normalization

* err_compat test works now

* H5O tweaks

* Updates VOL registration code

* Brings over H5VL_create_object

* H5Tconv.c reformatting

* H5T.c tweaks

* Brings datatype and reference updates from develop

* Brings VOL plugin loading changes from develop

* Brings event sets from develop

* Brings async functions over

* Tools changes

* Brings over many tools changes from develop

* Brings VOL flags from develop

* Fixes h5dump double/float tests

* Updates h5repack tests

* Brings h5diff test changes from develop

* Last h5dump changes

* Brings test changes from develop

* Committing clang-format changes

* Tidied h5_testing()

* Brings chunk iteration code + misc from develop

* Updates vds test

* Enables external link parallel test

* Brings updated property lists from develop

* H5G changes from develop

* H5MF cleanup

* Brings vfd_swmr test back into CMake

* Updates threadsafe test

* Updates plist test

* Brings recent changes from develop

* Require a C++11 compiler to build the C++ wrappers (#693)

* Committing clang-format changes

* Requires a C++11 compiler to build the C++ wrappers

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Fix H5FD_mpio_Debug="rw" can report MPI_count instead of bytes (#699)

* Removes pre-C99 build and header cruft (#700)

* Assumes ANSI C headers exist
* Assumes stdbool.h, stdint.h, and inttypes.h are present
* Assumes the C++ compiler can handle stdint.h
* Removes all work-arounds for missing functionality, especially stdbool.h

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Updates release documents

* Brings parallel changes from develop

* Adds a VFD/parallel check program for the VFD SWMR shell test

* Updates MANIFEST

* Disable building VFD SWMR acceptance tests on CMake

* Removes err.h from genall5.c

* Partial cleanup of H5Cpkg.h

* Fixes printf specifiers in H5Cdbg.c

* Java and fortran cmake changes (#694)

* OESS-98 convert plugin option to FetchContent, add tests

* Fixes for pkcfg files because of plugin option

* OESS-98 fix tools test for plugins

* Keep doxygen comments under 100 chars long - format hint

* Whitespace

* HDFFV-11144 - Reclassify CMake messages

* HDFFV-11099/11100 added help text

* Reworked switch statement to compare string instead

* Fix typo

* Update CDash mode

* Correct name of threadsafe

* Correct option name

* Undo accidental commit

* Note LLVM 10 to 11 format default changes

* Update format plugin

* Undo clang-format version 11 changes

* One more correction

* Update supported platforms

* Revert whitespace changes

* Correct whitespace

* Changes from PR#3

* HDFFV-11213 added option to control gcc10 warnings diagnostics

* HDFFV-11212 Use the new references correctly in JNI utility and tests

* format source

* Fix typo

* Add new test file

* HDFFV-11212 - update test and remove unused arg

* Minor non-space formatting changes

* Use H5I_INVALID_ID instead of "-1"

* source formatting

* add missing testfile, update jni function

* Undo commit of debug code

* remove mislocated file

* Fix h5repack test for handling of fapls and id close

* Update h5diff test files usage text

* HDFFV-11212 add new ref tests for JNI export dataset

* src format update

* Remove blank line typo

* src format typo

* long double requires %Lg

* Another long double foramt specifer S.B. %Lg

* issue with t128bit test

* Windows issue with h5dump and type.

* Fix review issues

* refactor function nesting and fix error checks

* format fixes

* Remove untested functions and javadoc quiet comments

* Restore TRY block.

* Change string append errors to memory exception

* revert to H5_JNI_FATAL_ERROR - support functions need work

* Add assertion error for h5util functions

* remove duplicate function

* format fix

* Revert HD function error handling

* Update copyright comments

* GH #386 java folder copyright corrections

* Whitespace

* GH #359 implement and fix tools 1.6 API usage

* remove excessive comments

* Flip inits to correct ifdef section

* rework ifdef to be simpler

* format issue

* Reformat ifdef inits

* remove static attribute

* format compliance

* Update names

* Revert because logic relies on float not being int

* Changes noticed from creating merge of #412

* Double underscore change

* Correct compiler version variable used

* Remove header guard underscores

* Whitespace cleanup

* Split format source and commit changes on repo push

* remove pre-split setting

* Change windows TS to use older VS.

* correct window os name

* HDFFV-11212 JNI export util and Javadoc

* Suggested review changes

* Another change found

* Committing clang-format changes

* HDFFV-11113 long double in tools

* HDFFV-11113 add note

* Disable long double tests for now

* HDFFV-11228 remove arbitrary CMake warning groups.

* Make each flag a string

* Some Javadoc warning fixes

* Updated javadoc fixes

* # WARNING: head commit changed in the meantime

HDFFV-11229 Fix long double usage in tools and java

Changed h5dump and h5ls to just print 128-bit for long double type.
Added test and file for dataset and attributes with all three float
types.

* Committing clang-format changes

* HDFFV-11229 Add release note

* HDFFV-11229 windows testfile needed

* fix typo

* Remove non supported message text

* HDFFV-11229 - change ldouble test to check both native and general

* HDFFV-11229 add second file compare

* HDFFV-11229 fix reference file

* HDFFV-11229 autotools check two refs

* HDFFV-11229 revert back to removal of NATIVE_LDOUBLE in tools output

* Committing clang-format changes

* Update release note

* Update attribute type of ref file

* Change source of ninja for macs

* try port instead of brew

* Recommended is to use brew.

* Undo non long double changes

* remove unneeded file

* Fix perl and doxygen CMake code

* Add "option" command for clang options

* Rework CMake add_custom to use the BYPRODUCTS argument

* Add stamp files to BYPRODUCTS

* Only one copy of file exists

* Fix custom cmmand depends targets

* Fix fortran custom command DEPENDS

* Add LD_LIBRARY_PATH to tests

* Add custom target for DEPENDS

* Add h5detect conditionaly to generated target DEPENDS

* Correct DEPENDS targets

* Parallel builds need the mpi compiler for pkgconfig scripts.

* install only if MPI build

* Fortran target depends

* Remove incorrect source attribute

* doxygen adjustments

* doxygen build updates

* Correct version

* Correct function version - function has been merged to 1.12

* Correct version string for map functions

* Cleanup warnings for tools debug builds

* TRILAB-227 - fix indexing for h5diff selections

* Correct location of pos to index function call

* TRILAB-227 Enable test

* Quote subset args

* Use MATCHES because of AppleClang

* if blocks needed for build modes

* Update list of DT platforms

* VS2019 correctly displays float values

* revert VS2019 change

* Issue #669 remove version from pkgcfg filename

* remove version from h5cc script

* Java reference functions updated

enabled fortran in cmake gcc action yaml file
java reference test changed to correctly test refs
jni reference functions that create ids changed to use jni id logging

* Correct BYPRODUCTS argument

* Correct more genereated files BYPRODUCTS

* BYPRODUCTS must have unique locations

* Fix typo

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Removes alternative function enter/leave macro scheme (#678)

* Committing clang-format changes

* Converted BEGIN_FUNC, etc. macros to FUNC_ENTER

* Rips out the BEGIN_FUNC, etc. macros

* Removes 'end if', etc. comments from H5HL package

* Committing clang-format changes

* Fixes an H5EA iterate issue

* Fixes an issue in the H5FA iterator code

* Further cleanup in bin/trace after macro removal

* Iterator changes in H5EA and H5FA

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Split H5L.c internal code to H5Lint.c (#691)

* Committing clang-format changes

* Splits internal parts of H5L.c to H5Lint.c

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Clean up type size checks in configure.ac (#702)

* Committing clang-format changes

* C++ warning and build fixes (#707)

* Committing clang-format changes

* C++ build and warning updates

* Fixes all warnings on C++ (with gcc 9.3)
* Updates CMake and Autotools C++ builds

* Undo warning clobber

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Removes some DEC Alpha cruft from H5detect and H5private.h (#708)

* Cleans up hsize_t and haddr_t size guessing (#709)

* Cleans up definitions of haddr_t and hsize_t + cruft removal

* Formatted source

* Updates PGI C/C++ configurations (#715)

* Updates PGI C/C++ configurations

Tweaks some settings and configures pgc++ to use C++11

* Updated copyright information

* Adds an Intel C++ configuration file (#716)

* Adds an Intel C++ configuration file

* Committing clang-format changes

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Updates bin/trace script to correctly wrap H5TRACE macros near clang-format column limit (#719)

* Removes clang-format comments from H5O.c call

* Fixes bin/trace to correctly wrap lines near the clang-format limit

* Removed unused variable from bin/trace

* Fixes issue with ccmake that prevents building Fortran (#723)

ccmake runs iteratively, and the check_fortran_source_runs
macros were clobbering a single output file that did not
get updated on further configure iterations

* Updates CMake size_t and ssize_t checks for MacOS

* Moved a little boilerplate over from develop

* Fixes some warnings

* Committing clang-format changes

* Moves gcc warning macros from H5public.h to H5private.h (#724)

* Moves gcc warning suppression macros out of H5public.h

* Update RELEASE.txt

* Formatted source

* Adds __STDC_FORMAT_MACROS before including inttypes.h w/ C++ (#726)

* Adds __STDC_FORMAT_MACROS before including inttypes.h w/ C++

Allows C++ library to be built on older versions of gcc.

* Committing clang-format changes

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>

* Moves H5PacketTable default ctor inside source file (#731)

* Brings (most) H5Xdevelop.h headers from develop

* Trivial H5F and H5O changes during normalization

* Renames buf_ptr back to page_buf to better align with develop

* Removed H5HGtrap.c

* Brings changes from develop

* Normalization (mainly cache) with develop

* Fix Direct VFD Testing in CMake (#742)

* Fixes C++ warnings when passing hsize_t values to printf in test code (#745)

* Organize and align compiler flags (#741)

* OESS-98 convert plugin option to FetchContent, add tests

* Fixes for pkcfg files because of plugin option

* OESS-98 fix tools test for plugins

* Keep doxygen comments under 100 chars long - format hint

* Whitespace

* HDFFV-11144 - Reclassify CMake messages

* HDFFV-11099/11100 added help text

* Reworked switch statement to compare string instead

* Fix typo

* Update CDash mode

* Correct name of threadsafe

* Correct option name

* Undo accidental commit

* Note LLVM 10 to 11 format default changes

* Update format plugin

* Undo clang-format version 11 changes

* One more correction

* Update supported platforms

* Revert whitespace changes

* Correct whitespace

* Changes from PR#3

* HDFFV-11213 added option to control gcc10 warnings diagnostics

* HDFFV-11212 Use the new references correctly in JNI utility and tests

* format source

* Fix typo

* Add new test file

* HDFFV-11212 - update test and remove unused arg

* Minor non-space formatting changes

* Use H5I_INVALID_ID instead of "-1"

* source formatting

* add missing testfile, update jni function

* Undo commit of debug code

* remove mislocated file

* Fix h5repack test for handling of fapls and id close

* Update h5diff test files usage text

* HDFFV-11212 add new ref tests for JNI export dataset

* src format update

* Remove blank line typo

* src format typo

* long double requires %Lg

* Another long double foramt specifer S.B. %Lg

* issue with t128bit test

* Windows issue with h5dump and type.

* Fix review issues

* refactor function nesting and fix error checks

* format fixes

* Remove untested functions and javadoc quiet comments

* Restore TRY block.

* Change string append errors to memory exception

* revert to H5_JNI_FATAL_ERROR - support functions need work

* Add assertion error for h5util functions

* remove duplicate function

* format fix

* Revert HD function error handling

* Update copyright comments

* GH #386 java folder copyright corrections

* Whitespace

* GH #359 implement and fix tools 1.6 API usage

* remove excessive comments

* Flip inits to correct ifdef section

* rework ifdef to be simpler

* format issue

* Reformat ifdef inits

* remove static attribute

* format compliance

* Update names

* Revert because logic relies on float not being int

* Changes noticed from creating merge of #412

* Double underscore change

* Correct compiler version variable used

* Remove header guard underscores

* Whitespace cleanup

* Split format source and commit changes on repo push

* remove pre-split setting

* Change windows TS to use older VS.

* correct window os name

* HDFFV-11212 JNI export util and Javadoc

* Suggested review changes

* Another change found

* Committing clang-format changes

* HDFFV-11113 long double in tools

* HDFFV-11113 add note

* Disable long double tests for now

* HDFFV-11228 remove arbitrary CMake warning groups.

* Make each flag a string

* Some Javadoc warning fixes

* Updated javadoc fixes

* # WARNING: head commit changed in the meantime

HDFFV-11229 Fix long double usage in tools and java

Changed h5dump and h5ls to just print 128-bit for long double type.
Added test and file for dataset and attributes with all three float
types.

* Committing clang-format changes

* HDFFV-11229 Add release note

* HDFFV-11229 windows testfile needed

* fix typo

* Remove non supported message text

* HDFFV-11229 - change ldouble test to check both native and general

* HDFFV-11229 add second file compare

* HDFFV-11229 fix reference file

* HDFFV-11229 autotools check two refs

* HDFFV-11229 revert back to removal of NATIVE_LDOUBLE in tools output

* Committing clang-format changes

* Update release note

* Update attribute type of ref file

* Change source of ninja for macs

* try port instead of brew

* Recommended is to use brew.

* Undo non long double changes

* remove unneeded file

* Fix perl and doxygen CMake code

* Add "option" command for clang options

* Rework CMake add_custom to use the BYPRODUCTS argument

* Add stamp files to BYPRODUCTS

* Only one copy of file exists

* Fix custom cmmand depends targets

* Fix fortran custom command DEPENDS

* Add LD_LIBRARY_PATH to tests

* Add custom target for DEPENDS

* Add h5detect conditionaly to generated target DEPENDS

* Correct DEPENDS targets

* Parallel builds need the mpi compiler for pkgconfig scripts.

* install only if MPI build

* Fortran target depends

* Remove incorrect source attribute

* doxygen adjustments

* doxygen build updates

* Correct version

* Correct function version - function has been merged to 1.12

* Correct version string for map functions

* Cleanup warnings for tools debug builds

* TRILAB-227 - fix indexing for h5diff selections

* Correct location of pos to index function call

* TRILAB-227 Enable test

* Quote subset args

* Use MATCHES because of AppleClang

* if blocks needed for build modes

* Update list of DT platforms

* VS2019 correctly displays float values

* revert VS2019 change

* Issue #669 remove version from pkgcfg filename

* remove version from h5cc script

* Java reference functions updated

enabled fortran in cmake gcc action yaml file
java reference test changed to correctly test refs
jni reference functions that create ids changed to use jni id logging

* Correct BYPRODUCTS argument

* Correct more genereated files BYPRODUCTS

* BYPRODUCTS must have unique locations

* Fix typo

* Fix fortran configure checks

* Rework H5_PAC_C_MAX_REAL_PRECISION setting logic

* Add note about fortran configure change

* Adds a quick for for some egregious chunk_info badness (#722)

* Fixes issue with ccmake that prevents building Fortran (#723)

ccmake runs iteratively, and the check_fortran_source_runs
macros were clobbering a single output file that did not
get updated on further configure iterations

* Fix conflicts with merge

* Move MAX_PRECISION back to HDF5UseFortran.cmake

* Use STREQUAL to test macro argument

* Move C language test to ConfigureChecks from HDF5UseFortran

* MAX_PRECISION defines must be defined

* Organize flags and align autotools and cmake

* Fix comment in no-error-general warnings files.

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Co-authored-by: Dana Robinson <43805+derobins@users.noreply.github.com>

* Committing clang-format changes

* Cache code tidying

* Constification of cache code

* Renaming of static calls in cache

* Fixes H5C mess made by git during merge

* Committing clang-format changes

* Fixes a printf format issue w/ parallel

* Revert "Committing clang-format changes"

This reverts commit 1265fe87fe.

* Turns off clang formatter in H5C while syncing with develop

* Adds a lot of HD prefixes and cleans up err.h usage

* Committing clang-format changes

* Brings cache skip list optimization from develop

* Brings recent changes from develop

Co-authored-by: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
2021-06-17 14:19:24 -07:00

2020 lines
77 KiB
C++

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* Copyright by The HDF Group. *
* Copyright by the Board of Trustees of the University of Illinois. *
* All rights reserved. *
* *
* This file is part of HDF5. The full HDF5 copyright notice, including *
* terms governing use, modification, and redistribution, is contained in *
* the COPYING file, which can be found at the root of the source code *
* distribution tree, or in https://www.hdfgroup.org/licenses. *
* If you do not have access to either file, you may request a copy from *
* help@hdfgroup.org. *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
/*****************************************************************************
FILE
tattr.cpp - HDF5 C++ testing the functionalities associated with the
C attribute interface (H5A)
***************************************************************************/
#include <cfloat>
#include <cmath>
#include <iostream>
using std::cerr;
using std::endl;
#include <string>
#include "H5Cpp.h" // C++ API header file
using namespace H5;
#include "h5test.h"
#include "h5cpputil.h" // C++ utilility header file
const H5std_string FILE_BASIC("tattr_basic.h5");
const H5std_string FILE_COMPOUND("tattr_compound.h5");
const H5std_string FILE_SCALAR("tattr_scalar.h5");
const H5std_string FILE_MULTI("tattr_multi.h5");
const H5std_string FILE_DTYPE("tattr_dtype.h5");
const H5std_string ATTR_TMP_NAME("temp_attr_name");
const H5std_string FATTR_TMP_NAME("temp_fattr_name");
const size_t ATTR_MAX_DIMS = 7;
/* 3-D dataset with fixed dimensions */
const int SPACE1_RANK = 3;
const hsize_t SPACE1_DIM1 = 3;
const hsize_t SPACE1_DIM2 = 15;
const hsize_t SPACE1_DIM3 = 13;
/* Object names */
const H5std_string DSET1_NAME("Dataset1");
const H5std_string GROUP1_NAME("/Group1");
const H5std_string TYPE1_NAME("/Type");
/* Attribute Rank & Dimensions */
const H5std_string ATTR1_NAME("Attr1");
const int ATTR1_RANK = 1;
const hsize_t ATTR1_DIM1 = 3;
int attr_data1[ATTR1_DIM1] = {512, -234, 98123}; /* Test data for 1st attribute */
// File attribute, using the same rank and dimensions as ATTR1_NAME's
const H5std_string FATTR1_NAME("File Attr1");
const H5std_string FATTR2_NAME("File Attr2");
const H5std_string ATTR2_NAME("Attr2");
const int ATTR2_RANK = 2;
const hsize_t ATTR2_DIM1 = 2;
const hsize_t ATTR2_DIM2 = 2;
int attr_data2[ATTR2_DIM1][ATTR2_DIM2] = {{7614, -416}, {197814, -3}}; /* Test data for 2nd attribute */
const H5std_string ATTR3_NAME("Attr3");
const int ATTR3_RANK = 3;
const hsize_t ATTR3_DIM1 = 2;
const hsize_t ATTR3_DIM2 = 2;
const hsize_t ATTR3_DIM3 = 2;
double attr_data3[ATTR3_DIM1][ATTR3_DIM2][ATTR3_DIM3] = {
{{2.3, -26.1}, {0.123, -10.0}}, {{981724.2, -0.91827}, {2.0, 23.0}}}; /* Test data for 3rd attribute */
const H5std_string ATTR4_NAME("Attr4");
const int ATTR4_RANK = 2;
const hsize_t ATTR4_DIM1 = 2;
const hsize_t ATTR4_DIM2 = 2;
const H5std_string ATTR4_FIELDNAME1("i");
const H5std_string ATTR4_FIELDNAME2("d");
const H5std_string ATTR4_FIELDNAME3("c");
size_t attr4_field1_off = 0;
size_t attr4_field2_off = 0;
size_t attr4_field3_off = 0;
struct attr4_struct {
int i;
double d;
char c;
} attr_data4[ATTR4_DIM1][ATTR4_DIM2] = {
{{3, -26.1, 'd'}, {-100000, 0.123, '3'}},
{{-23, 981724.2, 'Q'}, {0, 2.0, '\n'}}}; // Test data for 4th attribute
const H5std_string ATTR5_NAME("Attr5");
const int ATTR5_RANK = 0;
float attr_data5 = -5.123f; // Test data for 5th attribute
/* Info for another attribute */
const H5std_string ATTR1A_NAME("Attr1_a");
int attr_data1a[ATTR1_DIM1] = {256, 11945, -22107};
/*-------------------------------------------------------------------------
* Function: test_attr_basic_write
*
* Purpose Test basic write attribute on both datasets and groups.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_basic_write()
{
hsize_t dims1[] = {SPACE1_DIM1, SPACE1_DIM2, SPACE1_DIM3};
hsize_t dims2[] = {ATTR1_DIM1};
hsize_t dims3[] = {ATTR2_DIM1, ATTR2_DIM2};
int read_data1[ATTR1_DIM1] = {0}; // Buffer for reading 1st attribute
hsize_t i;
// Output message about test being performed
SUBTEST("Basic Attribute Writing Functions");
try {
// Create file
H5File fid1(FILE_BASIC, H5F_ACC_TRUNC);
// Create dataspace for dataset
DataSpace ds_space(SPACE1_RANK, dims1);
/*
* Test attribute with dataset
*/
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, ds_space);
// Create dataspace for attribute
DataSpace att_space(ATTR1_RANK, dims2);
// Create a file attribute
Attribute file_attr2 = fid1.createAttribute(FATTR1_NAME, PredType::NATIVE_INT, att_space);
// Create a file attribute
Attribute file_attr1 = fid1.createAttribute(FATTR2_NAME, PredType::NATIVE_INT, att_space);
// Create an attribute for the dataset
Attribute ds_attr1 = dataset.createAttribute(ATTR1_NAME, PredType::NATIVE_INT, att_space);
// Try creating an attribute that already exists. This should fail
// since two attributes cannot have the same name. If an exception
// is not thrown for this action by createAttribute, then throw an
// invalid action exception.
try {
Attribute invalid_attr = dataset.createAttribute(ATTR1_NAME, PredType::NATIVE_INT, att_space);
// continuation here, that means no exception has been thrown
throw InvalidActionException("H5File::createDataSet",
"Library allowed overwrite of existing dataset");
}
catch (AttributeIException &E) // catching invalid creating attribute
{
} // do nothing, exception expected
// Write attribute information
ds_attr1.write(PredType::NATIVE_INT, attr_data1);
// Read attribute information immediately, without closing attribute
ds_attr1.read(PredType::NATIVE_INT, read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1[%" PRIuHSIZE
"]=%d,read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1[i], i, read_data1[i]);
// Create two more attributes for this dataset, but only write to one.
Attribute ds_attr2 = dataset.createAttribute(ATTR2_NAME, PredType::NATIVE_INT, att_space);
Attribute ds_attr3 = dataset.createAttribute(ATTR3_NAME, PredType::NATIVE_INT, att_space);
// Write attribute information
ds_attr2.write(PredType::NATIVE_INT, attr_data1a);
// Read attribute information immediately, without closing attribute
ds_attr2.read(PredType::NATIVE_INT, read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1a[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1a[%" PRIuHSIZE
"]=%d,read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1a[i], i, read_data1[i]);
// Close both attributes
ds_attr1.close();
ds_attr2.close();
ds_attr3.close();
/*
* Test attribute with group
*/
// Create group in file fid1
Group group = fid1.createGroup(GROUP1_NAME);
// Create dataspace for attribute
DataSpace sid3(ATTR2_RANK, dims3);
// Create an attribute for the group
Attribute gr_attr = group.createAttribute(ATTR2_NAME, PredType::NATIVE_INT, sid3);
// Check storage size for attribute
hsize_t attr_size = gr_attr.getStorageSize();
verify_val(static_cast<long>(attr_size), static_cast<long>(ATTR2_DIM1 * ATTR2_DIM2 * sizeof(int)),
"Attribute::getStorageSize", __LINE__, __FILE__);
// Try to create the same attribute again (should fail)
try {
Attribute invalid_attr = group.createAttribute(ATTR2_NAME, PredType::NATIVE_INT, sid3);
// continuation here, that means no exception has been thrown
throw InvalidActionException("H5Group::createAttribute",
"Attempting to create an existing attribute");
}
catch (AttributeIException &E) // catching invalid creating attribute
{
} // do nothing, exception expected
// Write attribute information
gr_attr.write(PredType::NATIVE_INT, attr_data2);
// Check storage size for attribute
attr_size = gr_attr.getStorageSize();
verify_val(static_cast<long>(attr_size), static_cast<long>(ATTR2_DIM1 * ATTR2_DIM2 * sizeof(int)),
"Attribute::getStorageSize", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_basic_write()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_basic_write()
/*-------------------------------------------------------------------------
* Function: test_attr_getname
*
* Purpose Test getting attribute name.
*
* Description
* Test these functions:
* A. ssize_t Attribute::getName(char* attr_name, size_t buf_size)
* 1. With arbitrary buf_size that is larger than the name size
* 2. With arbitrary buf_size that is smaller than the name's length.
* 3. With a buf_size that equals the name's length.
*
* B. ssize_t Attribute::getName(H5std_string& attr_name, size_t buf_size)
* 1. With buffer smaller than the actual name
* 2. Same test but with retiring overloaded function
* ssize_t Attribute::getName(size_t buf_size, H5std_string& attr_name)
*
* C. H5std_string Attribute::getName()
*
* D. H5std_string Attribute::getName(size_t len)
*
* E. ssize_t Attribute::getName(H5std_string& attr_name, size_t buf_size)
* With buffer size equals the name's length, i.e., buf_size=0
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_getname()
{
// Output message about test being performed
SUBTEST("Testing all overloads of Attribute::getName");
try {
//
// Open the file FILE_BASIC and test getName with its attribute
//
// Open file
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
// Check for existence of attribute FATTR1_NAME
bool attr_exists = fid1.attrExists(FATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
// Open attribute
Attribute fattr1(fid1.openAttribute(FATTR1_NAME));
// A. Get attribute name with
// ssize_t Attribute::getName(char* attr_name, size_t buf_size)
// using different buffer sizes and verify against FATTR1_NAME (3 cases)
// 1. With arbitrary buf_size that is larger than the name size
size_t buf_size = FATTR1_NAME.length() + 10;
char * fattr1_name = new char[buf_size + 1];
HDmemset(fattr1_name, 0, buf_size + 1);
ssize_t name_size = 0; // actual length of attribute name
name_size = fattr1.getName(fattr1_name, buf_size + 1);
CHECK(name_size, FAIL, "Attribute::getName", __LINE__, __FILE__);
verify_val(static_cast<size_t>(name_size), FATTR1_NAME.length(), "Attribute::getName", __LINE__,
__FILE__);
verify_val(const_cast<const char *>(fattr1_name), FATTR1_NAME, "Attribute::getName", __LINE__,
__FILE__);
delete[] fattr1_name;
// 2. With arbitrary buf_size that is smaller than the name's length.
// Let's try 4 first characters in the name.
buf_size = 4;
char short_name[5] = "File"; // to verify the read name
fattr1_name = new char[buf_size + 1];
HDmemset(fattr1_name, 0, buf_size + 1);
name_size = fattr1.getName(fattr1_name, buf_size + 1);
CHECK(name_size, FAIL, "Attribute::getName", __LINE__, __FILE__);
verify_val(static_cast<size_t>(name_size), FATTR1_NAME.size(), "Attribute::getName", __LINE__,
__FILE__);
verify_val(const_cast<const char *>(fattr1_name), const_cast<const char *>(short_name),
"Attribute::getName", __LINE__, __FILE__);
delete[] fattr1_name;
// 3. With a buf_size that equals the name's length.
buf_size = FATTR1_NAME.length();
fattr1_name = new char[buf_size + 1];
HDmemset(fattr1_name, 0, buf_size + 1);
name_size = fattr1.getName(fattr1_name, buf_size + 1);
CHECK(name_size, FAIL, "Attribute::getName", __LINE__, __FILE__);
verify_val(fattr1_name, FATTR1_NAME, "Attribute::getName", __LINE__, __FILE__);
delete[] fattr1_name;
// B. Get attribute name with
// ssize_t Attribute::getName(H5std_string& attr_name, size_t buf_size)
// using buffer smaller than the actual name
buf_size = 4;
H5std_string fattr1_name2;
name_size = fattr1.getName(fattr1_name2, buf_size);
verify_val(fattr1_name2, "File", "Attribute::getName", __LINE__, __FILE__);
// Same test as above, but with deprecated overloaded function
// ssize_t Attribute::getName(size_t buf_size, H5std_string& attr_name)
// using buffer smaller than the actual name
H5std_string fattr1_name2a;
name_size = fattr1.getName(fattr1_name2a, buf_size);
verify_val(fattr1_name2a, "File", "Attribute::getName", __LINE__, __FILE__);
// C. Get file attribute's name with
// H5std_string Attribute::getName()
H5std_string fattr1_name3 = fattr1.getName();
verify_val(fattr1_name3, FATTR1_NAME, "Attribute::getName", __LINE__, __FILE__);
//
// D. Test getName getting part of an attribute's name using
// H5std_string Attribute::getName(len)
//
// Open dataset DSET1_NAME
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Check for existence of attribute
attr_exists = dataset.attrExists(ATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
// Open attribute
Attribute attr1(dataset.openAttribute(ATTR1_NAME));
size_t len = 4;
H5std_string dattr_name1 = attr1.getName(len);
verify_val(dattr_name1, "Attr", "Attribute::getName", __LINE__, __FILE__);
// E. Get dataset's attribute name with
// H5std_string Attribute::getName(H5std_string attr_name, buf_size=0)
H5std_string dattr_name2;
name_size = attr1.getName(dattr_name2);
verify_val(dattr_name2, ATTR1_NAME, "Attribute::getName", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_getname()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_getname()
/*-------------------------------------------------------------------------
* Function: test_attr_rename
*
* Purpose Test renaming attribute function.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_rename()
{
int read_data1[ATTR1_DIM1] = {0}; // Buffer for reading the attribute
hsize_t i;
// Output message about test being performed
SUBTEST("Checking for Existence and Renaming Attribute");
try {
// Open file
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
// Check and rename attribute belonging to a file
// Check for existence of attribute
bool attr_exists = fid1.attrExists(FATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
// Change attribute name
fid1.renameAttr(FATTR1_NAME, FATTR_TMP_NAME);
// Open attribute again
Attribute fattr1(fid1.openAttribute(FATTR_TMP_NAME));
// Verify new attribute name
H5std_string fattr_name = fattr1.getName();
verify_val(fattr_name, FATTR_TMP_NAME, "Attribute::getName", __LINE__, __FILE__);
int num_attrs = fid1.getNumAttrs();
verify_val(num_attrs, 2, "Attribute::getNumAttrs", __LINE__, __FILE__);
// Change first file attribute back to the original name
fid1.renameAttr(FATTR_TMP_NAME, FATTR1_NAME);
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Check and rename attribute belonging to a dataset
// Check for existence of attribute
attr_exists = dataset.attrExists(ATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
// Change attribute name
dataset.renameAttr(ATTR1_NAME, ATTR_TMP_NAME);
// Open attribute again
Attribute attr1(dataset.openAttribute(ATTR_TMP_NAME));
// Verify new attribute name
H5std_string attr_name = attr1.getName();
verify_val(attr_name, ATTR_TMP_NAME, "Attribute::getName", __LINE__, __FILE__);
// Read attribute information immediately, without closing attribute
attr1.read(PredType::NATIVE_INT, read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1[%" PRIuHSIZE
"]=%d,read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1[i], i, read_data1[i]);
// Close attribute
attr1.close();
// Check for existence of second attribute
attr_exists = dataset.attrExists(ATTR2_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
// Open the second attribute
Attribute attr2(dataset.openAttribute(ATTR2_NAME));
// Verify second attribute name
H5std_string attr2_name = attr2.getName();
verify_val(attr2_name, ATTR2_NAME, "Attribute::getName", __LINE__, __FILE__);
// Read attribute information immediately, without closing attribute
attr2.read(PredType::NATIVE_INT, read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1a[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1a[%" PRIuHSIZE
"]=%d,read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1a[i], i, read_data1[i]);
// Close attribute
attr2.close();
// Change first attribute back to the original name
dataset.renameAttr(ATTR_TMP_NAME, ATTR1_NAME);
// Check for existence of attribute after renaming
attr_exists = dataset.attrExists(ATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists", "Attribute should exist but does not");
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_rename()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_rename()
/*-------------------------------------------------------------------------
* Function: test_attr_basic_read
*
* Purpose Test basic read attribute.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_basic_read()
{
hsize_t i, j;
// Output message about test being performed
SUBTEST("Basic Attribute Reading Functions");
try {
// Open file
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Verify the correct number of attributes
int num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 3, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Verify the correct number of attributes another way
H5O_info2_t oinfo;
HDmemset(&oinfo, 0, sizeof(oinfo));
dataset.getObjinfo(oinfo, H5O_INFO_NUM_ATTRS);
verify_val(static_cast<long>(oinfo.num_attrs), 3, "DataSet::getObjinfo", __LINE__, __FILE__);
// Open an attribute for the dataset
Attribute ds_attr = dataset.openAttribute(ATTR1_NAME);
// Read attribute information
int read_data1[ATTR1_DIM1] = {0}; // Buffer for reading 1st attribute
ds_attr.read(PredType::NATIVE_INT, &read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1[%" PRIuHSIZE
"]=%d, read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1[i], i, read_data1[i]);
/*
* Test attribute with group
*/
// Open the group
Group group = fid1.openGroup(GROUP1_NAME);
// Verify the correct number of attributes
num_attrs = group.getNumAttrs();
verify_val(num_attrs, 1, "Group::getNumAttrs", __LINE__, __FILE__);
// Verify the correct number of attributes another way
HDmemset(&oinfo, 0, sizeof(oinfo));
group.getObjinfo(oinfo, H5O_INFO_NUM_ATTRS);
verify_val(static_cast<long>(oinfo.num_attrs), 1, "Group::getObjinfo", __LINE__, __FILE__);
// Open an attribute for the group
Attribute gr_attr = group.openAttribute(ATTR2_NAME);
// Buffer for reading 2nd attribute
int read_data2[ATTR2_DIM1][ATTR2_DIM2] = {{0}};
// Read attribute information
gr_attr.read(PredType::NATIVE_INT, read_data2);
// Verify values read in
for (i = 0; i < ATTR2_DIM1; i++)
for (j = 0; j < ATTR2_DIM2; j++)
if (attr_data2[i][j] != read_data2[i][j]) {
TestErrPrintf("%d: attribute data different: attr_data2[%" PRIuHSIZE "][%" PRIuHSIZE
"]=%d, "
"read_data2[%" PRIuHSIZE "][%" PRIuHSIZE "]=%d\n",
__LINE__, i, j, attr_data2[i][j], i, j, read_data2[i][j]);
}
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_basic_read()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_basic_read()
/*-------------------------------------------------------------------------
* Function: test_attr_compound_write
*
* Purpose Test writing attributes with compound datatype.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_compound_write()
{
// Output message about test being performed
SUBTEST("Multiple Attribute Functions");
try {
// Create file
H5File fid1(FILE_COMPOUND.c_str(), H5F_ACC_TRUNC);
// Create dataspace for dataset
hsize_t dims1[] = {SPACE1_DIM1, SPACE1_DIM2, SPACE1_DIM3};
DataSpace sid1(SPACE1_RANK, dims1);
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, sid1);
// Create the attribute datatype.
CompType comp_type(sizeof(struct attr4_struct));
attr4_field1_off = HOFFSET(struct attr4_struct, i);
comp_type.insertMember(ATTR4_FIELDNAME1, attr4_field1_off, PredType::NATIVE_INT);
attr4_field2_off = HOFFSET(struct attr4_struct, d);
comp_type.insertMember(ATTR4_FIELDNAME2, attr4_field2_off, PredType::NATIVE_DOUBLE);
attr4_field3_off = HOFFSET(struct attr4_struct, c);
comp_type.insertMember(ATTR4_FIELDNAME3, attr4_field3_off, PredType::NATIVE_SCHAR);
// Create dataspace for 1st attribute
hsize_t dims2[] = {ATTR4_DIM1, ATTR4_DIM2};
DataSpace sid2(ATTR4_RANK, dims2);
// Create complex attribute for the dataset
Attribute attr = dataset.createAttribute(ATTR4_NAME, comp_type, sid2);
// Try to create the same attribute again (should fail)
try {
Attribute invalid_attr = dataset.createAttribute(ATTR4_NAME, comp_type, sid2);
}
catch (AttributeIException &E) // catching invalid creating attribute
{
} // do nothing, exception expected
// Write complex attribute data
attr.write(comp_type, attr_data4);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_compound_write()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_compound_write()
/*-------------------------------------------------------------------------
* Function: test_attr_compound_read
*
* Purpose Test reading attributes with compound datatype.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_compound_read()
{
hsize_t dims[ATTR_MAX_DIMS]; // Attribute dimensions
size_t size; // Attribute datatype size as stored in file
size_t offset; // Attribute datatype field offset
struct attr4_struct read_data4[ATTR4_DIM1][ATTR4_DIM2]; // Buffer for reading 4th attribute
// Output message about test being performed
SUBTEST("Basic Attribute Functions");
try {
// Open file
H5File fid1(FILE_COMPOUND, H5F_ACC_RDWR);
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Verify the correct number of attributes
int num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 1, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Verify the correct number of attributes another way
H5O_info2_t oinfo;
HDmemset(&oinfo, 0, sizeof(oinfo));
dataset.getObjinfo(oinfo, H5O_INFO_NUM_ATTRS);
verify_val(static_cast<long>(oinfo.num_attrs), 1, "DataSet::getObjinfo", __LINE__, __FILE__);
// Open 1st attribute for the dataset
Attribute attr = dataset.openAttribute(static_cast<unsigned>(0));
/* Verify Dataspace */
// Get the dataspace of the attribute
DataSpace space = attr.getSpace();
// Get the rank of the dataspace and verify it
int rank = space.getSimpleExtentNdims();
verify_val(rank, ATTR4_RANK, "DataSpace::getSimpleExtentNdims", __LINE__, __FILE__);
// Get the dims of the dataspace and verify them
int ndims = space.getSimpleExtentDims(dims);
verify_val(ndims, ATTR4_RANK, "DataSpace::getSimpleExtentDims", __LINE__, __FILE__);
verify_val(static_cast<long>(dims[0]), static_cast<long>(ATTR4_DIM1),
"DataSpace::getSimpleExtentDims", __LINE__, __FILE__);
verify_val(static_cast<long>(dims[1]), static_cast<long>(ATTR4_DIM2),
"DataSpace::getSimpleExtentDims", __LINE__, __FILE__);
// Get the class of the datatype that is used by attr
H5T_class_t type_class = attr.getTypeClass();
// Verify that the type is of compound datatype
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_COMPOUND), "Attribute::getTypeClass",
__LINE__, __FILE__);
// Get the compound datatype
CompType datatype = attr.getCompType();
// Verify the number of fields in the datatype, which must be 3
int fields = datatype.getNmembers();
verify_val(fields, 3, "CompType::getNmembers", __LINE__, __FILE__);
// Verify that the fields have the same names as when the type
// was created
int j;
for (j = 0; j < fields; j++) {
H5std_string fieldname = datatype.getMemberName(j);
if (!((fieldname == ATTR4_FIELDNAME1) || (fieldname == ATTR4_FIELDNAME2) ||
(fieldname == ATTR4_FIELDNAME3)))
TestErrPrintf("%d:invalid field name for field #%d: %s\n", __LINE__, j, fieldname.c_str());
} /* end for */
offset = datatype.getMemberOffset(0);
verify_val(offset, attr4_field1_off, "DataType::getMemberOffset", __LINE__, __FILE__);
offset = datatype.getMemberOffset(1);
verify_val(offset, attr4_field2_off, "DataType::getMemberOffset", __LINE__, __FILE__);
offset = datatype.getMemberOffset(2);
verify_val(offset, attr4_field3_off, "DataType::getMemberOffset", __LINE__, __FILE__);
/* Verify each field's type, class & size */
// Get and verify the type class of the first member
type_class = datatype.getMemberClass(0);
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_INTEGER), "DataType::getMemberClass",
__LINE__, __FILE__);
// Get and verify the order of this member's type
IntType i_type = datatype.getMemberIntType(0);
H5T_order_t order = i_type.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_INT.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
// Get and verify the size of this member's type
size = i_type.getSize();
verify_val(size, PredType::NATIVE_INT.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Get and verify class, order, and size of the second member's type
type_class = datatype.getMemberClass(1);
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_FLOAT), "DataType::getMemberClass",
__LINE__, __FILE__);
FloatType f_type = datatype.getMemberFloatType(1);
order = f_type.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_DOUBLE.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
size = f_type.getSize();
verify_val(size, PredType::NATIVE_DOUBLE.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Get and verify class, order, and size of the third member's type
type_class = datatype.getMemberClass(2);
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_INTEGER), "DataType::getMemberClass",
__LINE__, __FILE__);
// Note: H5T_INTEGER is correct here!
StrType s_type = datatype.getMemberStrType(2);
order = s_type.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_SCHAR.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
size = s_type.getSize();
verify_val(size, PredType::NATIVE_SCHAR.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Read attribute information
attr.read(datatype, read_data4);
// Verify values read in
hsize_t ii, jj;
for (ii = 0; ii < ATTR4_DIM1; ii++)
for (jj = 0; jj < ATTR4_DIM2; jj++)
if (HDmemcmp(&attr_data4[ii][jj], &read_data4[ii][jj], sizeof(struct attr4_struct)) != 0) {
TestErrPrintf("%d:attribute data different: attr_data4[%" PRIuHSIZE "][%" PRIuHSIZE
"].i=%d, "
"read_data4[%" PRIuHSIZE "][%" PRIuHSIZE "].i=%d\n",
__LINE__, ii, jj, attr_data4[ii][jj].i, ii, jj, read_data4[ii][jj].i);
TestErrPrintf("%d:attribute data different: attr_data4[%" PRIuHSIZE "][%" PRIuHSIZE
"].d=%f, "
"read_data4[%" PRIuHSIZE "][%" PRIuHSIZE "].d=%f\n",
__LINE__, ii, jj, attr_data4[ii][jj].d, ii, jj, read_data4[ii][jj].d);
TestErrPrintf("%d:attribute data different: attr_data4[%" PRIuHSIZE "][%" PRIuHSIZE
"].c=%c, "
"read_data4[%" PRIuHSIZE "][%" PRIuHSIZE "].c=%c\n",
__LINE__, ii, jj, attr_data4[ii][jj].c, ii, jj, read_data4[ii][jj].c);
} /* end if */
// Verify name
H5std_string attr_name = attr.getName();
verify_val(attr_name, ATTR4_NAME, "Attribute::getName", __LINE__, __FILE__);
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_compound_read()", __LINE__, __FILE__, E.getCDetailMsg());
}
try {
// Now, try truncating the file to make sure reference counting is good.
// If any references to ids in the previous block are left unterminated,
// the truncating will fail, because the file will not be closed in
// the file.close() above.
H5File file1(FILE_COMPOUND, H5F_ACC_TRUNC);
PASSED();
} // end try block
catch (FileIException &E) {
issue_fail_msg("test_attr_compound_read()", __LINE__, __FILE__,
"Unable to truncate file, possibly because some objects are left opened");
}
} // test_attr_compound_read()
/*-------------------------------------------------------------------------
* Function: test_attr_scalar_write
*
* Purpose Test scalar attribute writing functionality.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_scalar_write()
{
// Output message about test being performed
SUBTEST("Basic Scalar Attribute Writing Functions");
try {
// Create file
H5File fid1(FILE_SCALAR, H5F_ACC_TRUNC);
// Create dataspace for dataset
hsize_t dims1[] = {SPACE1_DIM1, SPACE1_DIM2, SPACE1_DIM3};
DataSpace sid1(SPACE1_RANK, dims1);
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, sid1);
// Close dataset's dataspace
sid1.close();
// Create dataspace for attribute
DataSpace att_space(ATTR5_RANK, NULL);
// Create an attribute for the dataset
Attribute ds_attr = dataset.createAttribute(ATTR5_NAME, PredType::NATIVE_FLOAT, att_space);
// Try creating an attribute that already exists. This should fail
// since two attributes cannot have the same name. If an exception
// is not thrown for this action by createAttribute, then throw an
// invalid action exception.
try {
Attribute invalid_attr = dataset.createAttribute(ATTR5_NAME, PredType::NATIVE_FLOAT, att_space);
// continuation here, that means no exception has been thrown
throw InvalidActionException("H5File::createDataSet",
"Library allowed overwrite of existing dataset");
}
catch (AttributeIException &E) // catching invalid creating attribute
{
} // do nothing, exception expected
// Write attribute information
ds_attr.write(PredType::NATIVE_FLOAT, &attr_data5);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_scalar_write()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_scalar_write()
/*-------------------------------------------------------------------------
* Function: test_attr_scalar_read
*
* Purpose Test scalar attribute reading functionality.
*
* Return None
*-------------------------------------------------------------------------
*/
/* Epsilon for floating-point comparisons */
#define FP_EPSILON 0.000001F
static void
test_attr_scalar_read()
{
// Output message about test being performed
SUBTEST("Basic Scalar Attribute Reading Functions");
try {
// Open file
H5File fid1(FILE_SCALAR, H5F_ACC_RDWR);
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Verify the correct number of attributes
int num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 1, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Open an attribute for the dataset
Attribute ds_attr = dataset.openAttribute(ATTR5_NAME);
// Read attribute information
float read_data2 = 0.0; // Buffer for reading 1st attribute
ds_attr.read(PredType::NATIVE_FLOAT, &read_data2);
if (abs(read_data2 - attr_data5) > FLT_EPSILON)
TestErrPrintf("%d: attribute data different: read_data2=%f, "
"attr_data5=%f\n",
__LINE__, static_cast<double>(read_data2), static_cast<double>(attr_data5));
// Get the dataspace of the attribute
DataSpace att_space = ds_attr.getSpace();
// Make certain the dataspace is scalar
H5S_class_t space_type = att_space.getSimpleExtentType();
verify_val(static_cast<long>(space_type), static_cast<long>(H5S_SCALAR),
"DataSpace::getSimpleExtentType", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_scalar_read()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_scalar_read()
/*-------------------------------------------------------------------------
* Function: test_attr_mult_write
*
* Purpose Test writing multiple attributes.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_mult_write()
{
// Output message about test being performed
SUBTEST("Multiple Attribute Writing Functions");
try {
// Create file
H5File fid1(FILE_MULTI, H5F_ACC_TRUNC);
// Create dataspace for dataset
hsize_t dims1[] = {SPACE1_DIM1, SPACE1_DIM2, SPACE1_DIM3};
DataSpace ds_space(SPACE1_RANK, dims1);
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, ds_space);
// Create dataspace for 1st attribute
hsize_t dims2[] = {ATTR1_DIM1};
DataSpace att_space(ATTR1_RANK, dims2);
// Create 1st attribute for the dataset
Attribute ds_attr = dataset.createAttribute(ATTR1_NAME, PredType::NATIVE_INT, att_space);
// Write attribute information
ds_attr.write(PredType::NATIVE_INT, attr_data1);
// Create dataspace for 2nd attribute
hsize_t dims3[] = {ATTR2_DIM1, ATTR2_DIM2};
DataSpace att2_space(ATTR2_RANK, dims3);
// Create 2nd attribute for the dataset
Attribute ds_attr2 = dataset.createAttribute(ATTR2_NAME, PredType::NATIVE_INT, att2_space);
// Write 2nd attribute information
ds_attr2.write(PredType::NATIVE_INT, attr_data2);
// Create dataspace for 3rd attribute
hsize_t dims4[] = {ATTR3_DIM1, ATTR3_DIM2, ATTR3_DIM3};
DataSpace att3_space(ATTR3_RANK, dims4);
// Create 3rd attribute for the dataset
Attribute ds_attr3 = dataset.createAttribute(ATTR3_NAME, PredType::NATIVE_DOUBLE, att3_space);
// Try creating an attribute that already exists. This should fail
// since two attributes cannot have the same name. If an exception
// is not thrown for this action by createAttribute, then throw an
// invalid action exception.
try {
Attribute invalid_attr = dataset.createAttribute(ATTR3_NAME, PredType::NATIVE_DOUBLE, att3_space);
// continuation here, that means no exception has been thrown
throw InvalidActionException("DataSet::createAttribute",
"Attempting to create a duplicate attribute");
}
catch (AttributeIException &E) // catching invalid creating attribute
{
} // do nothing, exception expected
// Write 3rd attribute information
ds_attr3.write(PredType::NATIVE_DOUBLE, attr_data3);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_mult_write()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_mult_write()
/*-------------------------------------------------------------------------
* Function: test_attr_mult_read
*
* Purpose Test reading multiple attributes.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_mult_read()
{
int read_data1[ATTR1_DIM1] = {0}; // Buffer for reading 1st attribute
int read_data2[ATTR2_DIM1][ATTR2_DIM2] = {{0}}; // Buffer for reading 2nd attribute
double read_data3[ATTR3_DIM1][ATTR3_DIM2][ATTR3_DIM3] = {{{0}}}; // Buffer for reading 3rd attribute
hsize_t i, j, k;
// Output message about test being performed
SUBTEST("Multiple Attribute Reading Functions");
try {
// Open file
H5File fid1(FILE_MULTI, H5F_ACC_RDWR);
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Verify the correct number of attributes
int num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 3, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Open 1st attribute for the dataset
Attribute attr = dataset.openAttribute(static_cast<unsigned>(0));
/* Verify Dataspace */
// Get the dataspace of the attribute
DataSpace space = attr.getSpace();
// Get the rank of the dataspace and verify it
int rank = space.getSimpleExtentNdims();
verify_val(rank, ATTR1_RANK, "DataSpace::getSimpleExtentNdims", __LINE__, __FILE__);
// Get the dims of the dataspace and verify them
hsize_t dims[ATTR_MAX_DIMS]; // Attribute dimensions
(void)space.getSimpleExtentDims(dims);
if (dims[0] != ATTR1_DIM1)
TestErrPrintf("%d:attribute dimensions different: dims[0]=%d, should be %" PRIuHSIZE "\n",
__LINE__, static_cast<int>(dims[0]), ATTR1_DIM1);
/* Verify Datatype */
// Get the class of the datatype that is used by attr
H5T_class_t type_class = attr.getTypeClass();
// Verify that the type is of integer datatype
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_INTEGER), "Attribute::getTypeClass",
__LINE__, __FILE__);
// Get the integer datatype
IntType i_type1 = attr.getIntType();
// Get and verify the order of this type
H5T_order_t order = i_type1.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_INT.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
// Get and verify the size of this type
size_t size = i_type1.getSize();
verify_val(size, PredType::NATIVE_INT.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Read attribute information
attr.read(PredType::NATIVE_INT, read_data1);
// Verify values read in
for (i = 0; i < ATTR1_DIM1; i++)
if (attr_data1[i] != read_data1[i])
TestErrPrintf("%d: attribute data different: attr_data1[%" PRIuHSIZE
"]=%d,read_data1[%" PRIuHSIZE "]=%d\n",
__LINE__, i, attr_data1[i], i, read_data1[i]);
// Verify Name
H5std_string attr_name = attr.getName();
verify_val(attr_name, ATTR1_NAME, "DataType::getName", __LINE__, __FILE__);
attr.close();
space.close();
// Open 2nd attribute for the dataset
attr = dataset.openAttribute(static_cast<unsigned>(1));
/* Verify Dataspace */
// Get the dataspace of the attribute
space = attr.getSpace();
// Get the rank of the dataspace and verify it
rank = space.getSimpleExtentNdims();
verify_val(rank, ATTR2_RANK, "DataSpace::getSimpleExtentNdims", __LINE__, __FILE__);
// Get the dims of the dataspace and verify them
(void)space.getSimpleExtentDims(dims);
verify_val(static_cast<long>(dims[0]), static_cast<long>(ATTR2_DIM1),
"DataSpace::getSimpleExtentDims", __LINE__, __FILE__);
verify_val(static_cast<long>(dims[1]), static_cast<long>(ATTR2_DIM2),
"DataSpace::getSimpleExtentDims", __LINE__, __FILE__);
/* Verify Datatype */
// Get the class of the datatype that is used by attr
type_class = attr.getTypeClass();
// Verify that the type is of integer datatype
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_INTEGER), "Attribute::getTypeClass",
__LINE__, __FILE__);
// Get the integer datatype
IntType i_type2 = attr.getIntType();
// Get and verify the order of this type
order = i_type2.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_INT.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
// Get and verify the size of this type
size = i_type2.getSize();
verify_val(size, PredType::NATIVE_INT.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Read attribute information
attr.read(PredType::NATIVE_INT, read_data2);
// attr.read(i_type, read_data2);
// Verify values read in
for (i = 0; i < ATTR2_DIM1; i++)
for (j = 0; j < ATTR2_DIM2; j++)
if (attr_data2[i][j] != read_data2[i][j])
TestErrPrintf("%d: attribute data different: attr_data2[%" PRIuHSIZE "][%" PRIuHSIZE
"]=%d, "
"read_data2[%" PRIuHSIZE "][%" PRIuHSIZE "]=%d\n",
__LINE__, i, j, attr_data2[i][j], i, j, read_data2[i][j]);
// Verify Name
attr_name = attr.getName();
verify_val(attr_name, ATTR2_NAME, "DataType::getName", __LINE__, __FILE__);
attr.close();
space.close();
// Open 3rd attribute for the dataset
attr = dataset.openAttribute(static_cast<unsigned>(2));
/* Verify Dataspace */
// Get the dataspace of the attribute
space = attr.getSpace();
// Get the rank of the dataspace and verify it
rank = space.getSimpleExtentNdims();
verify_val(rank, ATTR3_RANK, "DataSpace::getSimpleExtentNdims", __LINE__, __FILE__);
// Get the dims of the dataspace and verify them
(void)space.getSimpleExtentDims(dims);
verify_val(static_cast<long>(dims[0]), static_cast<long>(ATTR3_DIM1), "attribute dimensions",
__FILE__, __LINE__);
verify_val(static_cast<long>(dims[1]), static_cast<long>(ATTR3_DIM2), "attribute dimensions",
__FILE__, __LINE__);
verify_val(static_cast<long>(dims[2]), static_cast<long>(ATTR3_DIM3), "attribute dimensions",
__FILE__, __LINE__);
/* Verify Datatype */
// Get the class of the datatype that is used by attr
type_class = attr.getTypeClass();
// Verify that the type is of compound datatype
verify_val(static_cast<long>(type_class), static_cast<long>(H5T_FLOAT), "Attribute::getTypeClass",
__LINE__, __FILE__);
// Get the double datatype
FloatType f_type = attr.getFloatType();
// Get and verify the order of this type
order = f_type.getOrder();
verify_val(static_cast<long>(order), static_cast<long>(PredType::NATIVE_DOUBLE.getOrder()),
"DataType::getOrder", __LINE__, __FILE__);
// Get and verify the size of this type
size = f_type.getSize();
verify_val(size, PredType::NATIVE_DOUBLE.getSize(), "DataType::getSize", __LINE__, __FILE__);
// Read attribute information
attr.read(PredType::NATIVE_DOUBLE, read_data3);
// Verify values read in
for (i = 0; i < ATTR3_DIM1; i++)
for (j = 0; j < ATTR3_DIM2; j++)
for (k = 0; k < ATTR3_DIM3; k++)
if (abs(attr_data3[i][j][k] - read_data3[i][j][k]) > DBL_EPSILON)
TestErrPrintf("%d: attribute data different: attr_data3[%" PRIuHSIZE "][%" PRIuHSIZE
"][%" PRIuHSIZE "]=%f, "
"read_data3[%" PRIuHSIZE "][%" PRIuHSIZE "][%" PRIuHSIZE "]=%f\n",
__LINE__, i, j, k, attr_data3[i][j][k], i, j, k, read_data3[i][j][k]);
// Verify Name
attr_name = attr.getName();
verify_val(attr_name, ATTR3_NAME, "DataType::getName", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_mult_read()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_mult_read()
/*-------------------------------------------------------------------------
* Function: test_attr_delete
*
* Purpose Test deleting attribute from different hdf5 objects.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_delete()
{
H5std_string attr_name; // Buffer for attribute names
// Output message about test being performed
SUBTEST("Removing Attribute Function");
try {
// Open file.
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
// Get the number of file attributes
int num_attrs = fid1.getNumAttrs();
verify_val(num_attrs, 2, "H5File::getNumAttrs", __LINE__, __FILE__);
// Delete the second file attribute
fid1.removeAttr(FATTR2_NAME);
// Get the number of file attributes
num_attrs = fid1.getNumAttrs();
verify_val(num_attrs, 1, "H5File::getNumAttrs", __LINE__, __FILE__);
// Verify the name of the only file attribute left
Attribute fattr = fid1.openAttribute(static_cast<unsigned>(0));
attr_name = fattr.getName();
verify_val(attr_name, FATTR1_NAME, "Attribute::getName", __LINE__, __FILE__);
fattr.close();
// Test deleting non-existing attribute
// Open the dataset
DataSet dataset = fid1.openDataSet(DSET1_NAME);
// Verify the correct number of attributes
num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 3, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Try to delete bogus attribute, should fail
try {
dataset.removeAttr("Bogus");
// continuation here, that means no exception has been thrown
throw InvalidActionException("DataSet::removeAttr",
"Attempting to remove non-existing attribute");
}
catch (AttributeIException &E) // catching invalid removing attribute
{
} // do nothing, exception expected
// Test deleting dataset's attributes
// Verify the correct number of attributes
num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 3, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Delete middle (2nd) attribute
dataset.removeAttr(ATTR2_NAME);
// Verify the correct number of attributes
num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 2, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Open 1st attribute for the dataset
Attribute attr = dataset.openAttribute(static_cast<unsigned>(0));
// Verify Name
attr_name = attr.getName();
verify_val(attr_name, ATTR1_NAME, "Attribute::getName", __LINE__, __FILE__);
// Close attribute
attr.close();
// Open last (formally 3rd) attribute for the dataset
attr = dataset.openAttribute(static_cast<unsigned>(1));
// Verify Name
attr_name = attr.getName();
verify_val(attr_name, ATTR3_NAME, "Attribute::getName", __LINE__, __FILE__);
attr.close();
// Delete first attribute
dataset.removeAttr(ATTR1_NAME);
// Verify the correct number of attributes
num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 1, "DataSet::getNumAttrs", __LINE__, __FILE__);
// Open the only attribute for the dataset (formally 3rd)
attr = dataset.openAttribute(static_cast<unsigned>(0));
// Verify Name
attr_name = attr.getName();
verify_val(attr_name, ATTR3_NAME, "Attribute::getName", __LINE__, __FILE__);
// Close attribute
attr.close();
// Delete first attribute
dataset.removeAttr(ATTR3_NAME);
// Verify the correct number of attributes
num_attrs = dataset.getNumAttrs();
verify_val(num_attrs, 0, "DataSet::getNumAttrs", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_delete()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_delete()
/*-------------------------------------------------------------------------
* Function: test_attr_dtype_shared
*
* Purpose Test accessing attributes using shared datatypes.
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_dtype_shared()
{
int data = 8; // Data to write
int rdata = 0; // Data read in
#ifndef H5_NO_DEPRECATED_SYMBOLS
H5G_stat_t statbuf; // Object's information
#endif
h5_stat_size_t filesize; // Size of file after modifications
// Output message about test being performed
SUBTEST("Shared Datatypes with Attributes");
try {
// Create a file
H5File fid1(FILE_DTYPE, H5F_ACC_TRUNC);
// Close file
fid1.close();
// Get size of file
h5_stat_size_t empty_filesize; // Size of empty file
empty_filesize = h5_get_file_size(FILE_DTYPE.c_str(), H5P_DEFAULT);
if (empty_filesize < 0)
TestErrPrintf("Line %d: file size wrong!\n", __LINE__);
// Open the file again
fid1.openFile(FILE_DTYPE, H5F_ACC_RDWR);
// Enclosing to work around the issue of unused variables and/or
// objects created by copy constructors stay around until end of
// scope, causing incorrect number of ref counts.
{ // First enclosed block
// Create a datatype to commit and use
IntType dtype(PredType::NATIVE_INT);
// Commit datatype to file
dtype.commit(fid1, TYPE1_NAME);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 1, "DataType::getObjinfo", __LINE__, __FILE__);
#endif
// Create dataspace for dataset
DataSpace dspace;
DataSet dset = fid1.createDataSet(DSET1_NAME, dtype, dspace);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 2, "H5File::getObjinfo", __LINE__, __FILE__);
#endif
// Create attribute on dataset
Attribute attr = dset.createAttribute(ATTR1_NAME, dtype, dspace);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 3, "DataSet::getObjinfo", __LINE__, __FILE__);
#endif
// Close attribute
attr.close();
// Delete attribute
dset.removeAttr(ATTR1_NAME);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 2, "DataSet::getObjinfo after DataSet::removeAttr",
__LINE__, __FILE__);
#endif
// Create attribute on dataset
attr = dset.createAttribute(ATTR1_NAME, dtype, dspace);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 3, "DataSet::createAttribute", __LINE__, __FILE__);
#endif
// Write data into the attribute
attr.write(PredType::NATIVE_INT, &data);
// Close attribute, dataset, dataspace, datatype, and file
attr.close();
dset.close();
dspace.close();
dtype.close();
} // end of first enclosing
fid1.close();
// Open the file again
fid1.openFile(FILE_DTYPE, H5F_ACC_RDWR);
{ // Second enclosed block...
// Open dataset
DataSet *dset2 = new DataSet(fid1.openDataSet(DSET1_NAME));
// Open attribute
Attribute *attr2 = new Attribute(dset2->openAttribute(ATTR1_NAME));
// Read data from the attribute
attr2->read(PredType::NATIVE_INT, &rdata);
verify_val(data, rdata, "Attribute::read", __LINE__, __FILE__);
// Close attribute and dataset
delete attr2;
delete dset2;
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 3, "DataSet::openAttribute", __LINE__, __FILE__);
#endif
} // end of second enclosing
// Unlink the dataset
fid1.unlink(DSET1_NAME);
#ifndef H5_NO_DEPRECATED_SYMBOLS
// Check reference count on named datatype
fid1.getObjinfo(TYPE1_NAME, statbuf);
verify_val(static_cast<int>(statbuf.nlink), 1, "H5File::unlink", __LINE__, __FILE__);
#endif
// Unlink the named datatype
fid1.unlink(TYPE1_NAME);
// Close file
fid1.close();
// Check size of file
filesize = h5_get_file_size(FILE_DTYPE.c_str(), H5P_DEFAULT);
verify_val(static_cast<long>(filesize), static_cast<long>(empty_filesize), "Checking file size",
__LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_dtype_shared()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_dtype_shared()
/*-------------------------------------------------------------------------
* Function: test_string_attr
*
* Purpose Test read/write string attribute.
*
* Return None
*-------------------------------------------------------------------------
*/
/* Info for a string attribute */
const H5std_string ATTR1_FL_STR_NAME("String_attr 1");
const H5std_string ATTR2_FL_STR_NAME("String_attr 2");
const H5std_string ATTR_VL_STR_NAME("String_attr");
const H5std_string ATTRSTR_DATA("String Attribute");
const int ATTR_LEN = 17;
static void
test_string_attr()
{
// Output message about test being performed
SUBTEST("I/O on FL and VL String Attributes");
try {
// Create file
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
//
// Fixed-lenth string attributes
//
// Create a fixed-length string datatype to refer to.
StrType fls_type(0, ATTR_LEN);
// Open the root group.
Group root = fid1.openGroup("/");
// Create dataspace for the attribute.
DataSpace att_space(H5S_SCALAR);
/* Test Attribute::write(...,const void *buf) with Fixed len string */
// Create an attribute for the root group.
Attribute gr_flattr1 = root.createAttribute(ATTR1_FL_STR_NAME, fls_type, att_space);
// Write data to the attribute.
gr_flattr1.write(fls_type, ATTRSTR_DATA.c_str());
/* Test Attribute::write(...,const H5std_string& strg) with FL string */
// Create an attribute for the root group.
Attribute gr_flattr2 = root.createAttribute(ATTR2_FL_STR_NAME, fls_type, att_space);
// Write data to the attribute.
gr_flattr2.write(fls_type, ATTRSTR_DATA);
/* Test Attribute::read(...,void *buf) with FL string */
// Read and verify the attribute string as a string of chars.
char flstring_att_check[ATTR_LEN];
gr_flattr1.read(fls_type, flstring_att_check);
if (HDstrcmp(flstring_att_check, ATTRSTR_DATA.c_str()) != 0)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,flstring_att_check=%s\n",
__LINE__, ATTRSTR_DATA.c_str(), flstring_att_check);
// Read and verify the attribute string as a string of chars; buffer
// is dynamically allocated.
size_t attr_size = gr_flattr1.getInMemDataSize();
char * fl_dyn_string_att_check;
fl_dyn_string_att_check = new char[attr_size + 1];
gr_flattr1.read(fls_type, fl_dyn_string_att_check);
if (HDstrcmp(fl_dyn_string_att_check, ATTRSTR_DATA.c_str()) != 0)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,flstring_att_check=%s\n",
__LINE__, ATTRSTR_DATA.c_str(), fl_dyn_string_att_check);
delete[] fl_dyn_string_att_check;
/* Test Attribute::read(...,H5std_string& strg) with FL string */
// Read and verify the attribute string as an std::string.
H5std_string read_flstr1;
gr_flattr1.read(fls_type, read_flstr1);
if (read_flstr1 != ATTRSTR_DATA)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,read_flstr1=%s\n", __LINE__,
ATTRSTR_DATA.c_str(), read_flstr1.c_str());
// Read and verify the attribute string as a string of chars.
HDstrcpy(flstring_att_check, "");
gr_flattr2.read(fls_type, flstring_att_check);
if (HDstrcmp(flstring_att_check, ATTRSTR_DATA.c_str()) != 0)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,flstring_att_check=%s\n",
__LINE__, ATTRSTR_DATA.c_str(), flstring_att_check);
/* Test Attribute::read(...,H5std_string& strg) with FL string */
// Read and verify the attribute string as an std::string.
H5std_string read_flstr2;
gr_flattr2.read(fls_type, read_flstr2);
if (read_flstr2 != ATTRSTR_DATA)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,read_flstr2=%s\n", __LINE__,
ATTRSTR_DATA.c_str(), read_flstr2.c_str());
//
// Variable-lenth string attributes
//
// Create a variable length string datatype to refer to.
StrType vls_type(0, H5T_VARIABLE);
// Create an attribute for the root group.
Attribute gr_vlattr = root.createAttribute(ATTR_VL_STR_NAME, vls_type, att_space);
// Write data to the attribute.
gr_vlattr.write(vls_type, ATTRSTR_DATA);
/* Test Attribute::read(...,void *buf) with Variable len string */
// Read and verify the attribute string as a string of chars.
char *string_att_check;
gr_vlattr.read(vls_type, &string_att_check);
if (HDstrcmp(string_att_check, ATTRSTR_DATA.c_str()) != 0)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,string_att_check=%s\n",
__LINE__, ATTRSTR_DATA.c_str(), string_att_check);
HDfree(string_att_check);
/* Test Attribute::read(...,H5std_string& strg) with VL string */
// Read and verify the attribute string as an std::string.
H5std_string read_str;
gr_vlattr.read(vls_type, read_str);
if (read_str != ATTRSTR_DATA)
TestErrPrintf("Line %d: Attribute data different: ATTRSTR_DATA=%s,read_str=%s\n", __LINE__,
ATTRSTR_DATA.c_str(), read_str.c_str());
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_string_attr()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_string_attr()
/*-------------------------------------------------------------------------
* Function: test_attr_exists
*
* Purpose Test checking for attribute existence.
*
* Return None
*
* Note
* Additional attrExists tests are in test_attr_rename().
*-------------------------------------------------------------------------
*/
static void
test_attr_exists()
{
// Output message about test being performed
SUBTEST("Check Attribute Existence");
try {
// Open file.
H5File fid1(FILE_BASIC, H5F_ACC_RDWR);
// Open the root group.
Group root = fid1.openGroup("/");
// Check for existence of attribute
bool attr_exists = fid1.attrExists(ATTR1_FL_STR_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists",
"fid1, ATTR1_FL_STR_NAMEAttribute should exist but does not");
// Check for existence of attribute
attr_exists = fid1.attrExists(FATTR1_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists",
"fid1,FATTR2_NAMEAttribute should exist but does not");
// Open a group.
Group group = fid1.openGroup(GROUP1_NAME);
// Check for existence of attribute
attr_exists = group.attrExists(ATTR2_NAME);
if (attr_exists == false)
throw InvalidActionException("H5File::attrExists",
"group, ATTR2_NAMEAttribute should exist but does not");
PASSED();
} // end try block
catch (InvalidActionException &E) {
issue_fail_msg("test_attr_exists()", __LINE__, __FILE__, E.getCDetailMsg());
}
catch (Exception &E) {
issue_fail_msg("test_attr_exists()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_exists()
/*-------------------------------------------------------------------------
* Function: test_attr_dense_create
*
* Purpose Test phase change properties
*
* Return None
*-------------------------------------------------------------------------
*/
const H5std_string FILE_CRTPROPS("tattr_crt_properties.h5");
const int NAME_BUF_SIZE = 1024;
const unsigned MAX_COMPACT_DEF = 8;
const unsigned MIN_DENSE_DEF = 6;
static void
test_attr_dense_create(FileCreatPropList &fcpl, FileAccPropList &fapl)
{
// Output message about test being performed
SUBTEST("Dense Attribute Storage Creation");
try {
// Create file
H5File fid1(FILE_CRTPROPS, H5F_ACC_TRUNC, fcpl, fapl);
// Close file
fid1.close();
// Get size of file
h5_stat_size_t empty_filesize; // Size of empty file
empty_filesize = h5_get_file_size(FILE_CRTPROPS.c_str(), fapl.getId());
if (empty_filesize < 0)
TestErrPrintf("Line %d: file size wrong!\n", __LINE__);
// Re-open file
fid1.openFile(FILE_CRTPROPS, H5F_ACC_RDWR, fapl);
// Create dataspace for dataset
DataSpace ds_space(H5S_SCALAR);
// Create dataset creation property list.
DSetCreatPropList dcpl;
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, ds_space, dcpl);
unsigned max_compact = 0, min_dense = 0;
// Retrieve limits for compact/dense attribute storage
dcpl.getAttrPhaseChange(max_compact, min_dense);
verify_val(max_compact, MAX_COMPACT_DEF, "DSetCreatPropList::getAttrPhaseChange", __LINE__, __FILE__);
verify_val(min_dense, MIN_DENSE_DEF, "DSetCreatPropList::getAttrPhaseChange", __LINE__, __FILE__);
// Set new compact/dense attribute storage limits to some random numbers
dcpl.setAttrPhaseChange(7, 5);
// Retrieve limits for compact/dense attribute storage and verify them
dcpl.getAttrPhaseChange(max_compact, min_dense);
verify_val(max_compact, static_cast<unsigned>(7), "DSetCreatPropList::getAttrPhaseChange", __LINE__,
__FILE__);
verify_val(min_dense, static_cast<unsigned>(5), "DSetCreatPropList::getAttrPhaseChange", __LINE__,
__FILE__);
// Close property list
dcpl.close();
// H5O__is_attr_dense_test - un-usable
// Add attributes, until just before converting to dense storage
char attr_name[NAME_BUF_SIZE];
unsigned attr_num;
for (attr_num = 0; attr_num < max_compact; attr_num++) {
// Create attribute
sprintf(attr_name, "attr %02u", attr_num);
Attribute attr = dataset.createAttribute(attr_name, PredType::NATIVE_UINT, ds_space);
// Write data to the attribute
attr.write(PredType::NATIVE_UINT, &attr_num);
} // end for
// H5O__is_attr_dense_test - un-usable
{ // Add one more attribute, to push into "dense" storage
// Create another attribute
sprintf(attr_name, "attr %02u", attr_num);
Attribute attr = dataset.createAttribute(attr_name, PredType::NATIVE_UINT, ds_space);
// Write data to the attribute
attr.write(PredType::NATIVE_UINT, &attr_num);
}
// Attempt to add attribute again, which should fail
try {
// Create another attribute
sprintf(attr_name, "attr %02u", attr_num);
Attribute attr = dataset.createAttribute(attr_name, PredType::NATIVE_UINT, ds_space);
// continuation here, that means no exception has been thrown
throw InvalidActionException("DataSet::createAttribute",
"Maximum number of attributes has been reached");
}
catch (AttributeIException &E) // catching invalid action
{
} // do nothing, exception expected
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_dense_create()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_dense_create()
/*-------------------------------------------------------------------------
* Function: test_attr_corder_create_basic
*
* Purpose Test creation order properties
*
* Return None
*-------------------------------------------------------------------------
*/
static void
test_attr_corder_create_basic(FileCreatPropList &fcpl, FileAccPropList &fapl)
{
// Output message about test being performed
SUBTEST("Basic Code for Attributes with Creation Order Info");
try {
// Create file
H5File fid1(FILE_CRTPROPS, H5F_ACC_TRUNC, fcpl, fapl);
// Create dataset creation property list.
DSetCreatPropList dcpl;
// Get creation order indexing on object
unsigned crt_order_flags = 0;
crt_order_flags = dcpl.getAttrCrtOrder();
verify_val(static_cast<long>(crt_order_flags), 0, "DSetCreatPropList::getAttrCrtOrder", __LINE__,
__FILE__);
// Setting invalid combination of a attribute order creation order
// indexing on should fail
try {
dcpl.setAttrCrtOrder(H5P_CRT_ORDER_INDEXED);
// continuation here, that means no exception has been thrown
throw InvalidActionException("DSetCreatPropList::getAttrCrtOrder",
"Indexing cannot be set alone, order tracking is required");
}
catch (PropListIException &E) // catching invalid action
{
} // do nothing, exception expected
// Set attribute creation order tracking & indexing for object then
// verify them
dcpl.setAttrCrtOrder(H5P_CRT_ORDER_TRACKED | H5P_CRT_ORDER_INDEXED);
crt_order_flags = dcpl.getAttrCrtOrder();
verify_val(crt_order_flags, static_cast<unsigned>(H5P_CRT_ORDER_TRACKED | H5P_CRT_ORDER_INDEXED),
"DSetCreatPropList::getAttrCrtOrder", __LINE__, __FILE__);
// Create dataspace for dataset
DataSpace ds_space(H5S_SCALAR);
// Create a dataset
DataSet dataset = fid1.createDataSet(DSET1_NAME, PredType::NATIVE_UCHAR, ds_space, dcpl);
// Close dataspace
ds_space.close();
// Check on dataset's attribute storage status.
// NOTE: Wrappers not available yet (H5O__is_attr_empty_test
// and H5O__is_attr_dense_test)
// Close dataset
dataset.close();
// Close property list
dcpl.close();
// Close file
fid1.close();
// Re-open file
fid1.openFile(FILE_CRTPROPS, H5F_ACC_RDWR, fapl);
// Open dataset created previously
dataset = fid1.openDataSet(DSET1_NAME);
// Retrieve dataset creation property list for the dataset
dcpl = dataset.getCreatePlist();
// Query the attribute creation properties
crt_order_flags = dcpl.getAttrCrtOrder();
verify_val(crt_order_flags, static_cast<unsigned>(H5P_CRT_ORDER_TRACKED | H5P_CRT_ORDER_INDEXED),
"DSetCreatPropList::getAttrCrtOrder", __LINE__, __FILE__);
PASSED();
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr_corder_create_basic()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr_corder_create_basic()
/*-------------------------------------------------------------------------
* Function: test_attr
*
* Purpose Main attribute testing routine
*
* Return None
*-------------------------------------------------------------------------
*/
extern "C" void
test_attr()
{
// Output message about test being performed
MESSAGE(5, ("Testing Attributes\n"));
try {
// Create a default file access property list
FileAccPropList fapl;
// Copy the file access property list for new format test
FileAccPropList fapl_new = fapl;
// Set the "use the latest version of the format" bounds for creating
// objects in the file
fapl_new.setLibverBounds(H5F_LIBVER_LATEST, H5F_LIBVER_LATEST);
// Create a default file creation property list
FileCreatPropList fcpl;
// Copy the file creation property list for new format test
FileCreatPropList fcpl_new = fcpl;
// Wrappers for ..._shared_mesg_nindexes are not available, skip
// use_shared test
// Loop over using new group format
unsigned new_format;
for (new_format = FALSE; new_format <= TRUE; new_format++) {
FileAccPropList curr_fapl;
// Set the file access proplist for the type of format
if (new_format) {
MESSAGE(7, ("testing with new file format\n"));
curr_fapl = fapl_new;
}
else {
MESSAGE(7, ("testing with old file format\n"));
curr_fapl = fapl;
}
test_attr_basic_write(); // Test basic H5A writing code
test_attr_getname(); // Test overloads of Attribute::getName
test_attr_rename(); // Test renaming attribute
test_attr_basic_read(); // Test basic H5A reading code
test_attr_compound_write(); // Test complex datatype H5A writing code
test_attr_compound_read(); // Test complex datatype H5A reading code
test_attr_scalar_write(); // Test scalar dataspace H5A writing code
test_attr_scalar_read(); // Test scalar dataspace H5A reading code
test_attr_mult_write(); // Test writing multiple attributes
test_attr_mult_read(); // Test reading multiple attributes
test_attr_delete(); // Test deleting attributes
test_attr_dtype_shared(); // Test using shared datatypes in attributes
test_string_attr(); // Test read/write string attribute
test_attr_exists(); // Test H5Location::attrExists
// Test with new format
if (new_format) {
// Test dense attribute storage creation
test_attr_dense_create(fcpl, curr_fapl);
// Test create objects with attribute creation info
test_attr_corder_create_basic(fcpl, curr_fapl);
}
} // end for
} // end try block
catch (Exception &E) {
issue_fail_msg("test_attr()", __LINE__, __FILE__, E.getCDetailMsg());
}
} // test_attr()
/*-------------------------------------------------------------------------
* Function: cleanup_attr
*
* Purpose Cleanup temporary test files
*
* Return None
*-------------------------------------------------------------------------
*/
extern "C" void
cleanup_attr()
{
HDremove(FILE_BASIC.c_str());
HDremove(FILE_COMPOUND.c_str());
HDremove(FILE_SCALAR.c_str());
HDremove(FILE_MULTI.c_str());
HDremove(FILE_DTYPE.c_str());
HDremove(FILE_CRTPROPS.c_str());
}