diff options
159 files changed, 28196 insertions, 957 deletions
@@ -148,6 +148,14 @@ ./examples/h5_ref2reg.c ./examples/h5_shared_mesg.c ./examples/ph5example.c +./examples/h5_vds.c +./examples/h5_vds-exc.c +./examples/h5_vds-exclim.c +./examples/h5_vds-eiger.c +./examples/h5_vds-simpleIO.c +./examples/h5_vds-percival.c +./examples/h5_vds-percival-unlim.c +./examples/h5_vds-percival-unlim-maxmin.c ./examples/testh5cc.sh.in ./examples/README @@ -506,6 +514,7 @@ ./src/H5Dscatgath.c ./src/H5Dselect.c ./src/H5Dtest.c +./src/H5Dvirtual.c ./src/H5E.c ./src/H5Edefin.h ./src/H5Edeprec.c @@ -988,6 +997,7 @@ ./test/test_filters_be.h5 ./test/gen_filters.c ./test/chunk_info.c +./test/vds.c ./test/testfiles/err_compat_1 ./test/testfiles/err_compat_2 @@ -1062,9 +1072,9 @@ ./tools/h5dump/testh5dump.sh.in ./tools/h5dump/testh5dumppbits.sh.in ./tools/h5dump/testh5dumpxml.sh.in +./tools/h5dump/testh5dumpvds.sh.in ./tools/h5dump/binread.c - ./tools/h5import/Makefile.am ./tools/h5import/Makefile.in ./tools/h5import/h5import.h @@ -1153,10 +1163,12 @@ ./tools/h5repack/testh5repack_detect_szip.c # h5ls sources +./tools/h5ls/CMakeTestsVDS.cmake ./tools/h5ls/Makefile.am ./tools/h5ls/Makefile.in ./tools/h5ls/h5ls.c ./tools/h5ls/testh5ls.sh.in +./tools/h5ls/testh5lsvds.sh.in # h5copy sources ./tools/h5copy/testh5copy.sh.in @@ -1208,6 +1220,19 @@ ./tools/misc/testfiles/h5mkgrp_help.txt ./tools/misc/testfiles/h5mkgrp_version.txt.in ./tools/misc/h5perf_gentest.c +./tools/misc/vds/Makefile.am +./tools/misc/vds/Makefile.in +./tools/misc/vds/UC_1.h +./tools/misc/vds/UC_1_one_dim_gen.c +./tools/misc/vds/UC_2.h +./tools/misc/vds/UC_2_two_dims_gen.c +./tools/misc/vds/UC_3.h +./tools/misc/vds/UC_3_gaps_gen.c +./tools/misc/vds/UC_4.h +./tools/misc/vds/UC_4_printf_gen.c +./tools/misc/vds/UC_5.h +./tools/misc/vds/UC_5_stride_gen.c +./tools/misc/vds/UC_common.h # h5stat sources ./tools/h5stat/Makefile.am @@ -1628,6 +1653,43 @@ ./tools/testfiles/pbits/tpbitsOverlapped.ddl ./tools/testfiles/packedbits.h5 +# h5dump vds validation +./tools/testfiles/vds/tvds-1.ddl +./tools/testfiles/vds/tvds-2.ddl +./tools/testfiles/vds/tvds-3_1.ddl +./tools/testfiles/vds/tvds-3_2.ddl +./tools/testfiles/vds/tvds-4.ddl +./tools/testfiles/vds/tvds-5.ddl +./tools/testfiles/vds/tvds_layout-1.ddl +./tools/testfiles/vds/tvds_layout-2.ddl +./tools/testfiles/vds/tvds_layout-3_1.ddl +./tools/testfiles/vds/tvds_layout-3_2.ddl +./tools/testfiles/vds/tvds_layout-4.ddl +./tools/testfiles/vds/tvds_layout-5.ddl +./tools/testfiles/vds/1_a.h5 +./tools/testfiles/vds/1_b.h5 +./tools/testfiles/vds/1_c.h5 +./tools/testfiles/vds/1_d.h5 +./tools/testfiles/vds/1_e.h5 +./tools/testfiles/vds/1_f.h5 +./tools/testfiles/vds/1_vds.h5 +./tools/testfiles/vds/2_a.h5 +./tools/testfiles/vds/2_b.h5 +./tools/testfiles/vds/2_c.h5 +./tools/testfiles/vds/2_d.h5 +./tools/testfiles/vds/2_e.h5 +./tools/testfiles/vds/2_vds.h5 +./tools/testfiles/vds/3_1_vds.h5 +./tools/testfiles/vds/3_2_vds.h5 +./tools/testfiles/vds/4_0.h5 +./tools/testfiles/vds/4_1.h5 +./tools/testfiles/vds/4_2.h5 +./tools/testfiles/vds/4_vds.h5 +./tools/testfiles/vds/5_a.h5 +./tools/testfiles/vds/5_b.h5 +./tools/testfiles/vds/5_c.h5 +./tools/testfiles/vds/5_vds.h5 + # h5dump h5import validation ./tools/testfiles/out3.h5import ./tools/testfiles/tordergr.h5 @@ -1704,7 +1766,13 @@ ./tools/testfiles/thlinks-nodangle-1.ls ./tools/testfiles/tudlink-1.ls - +# h5ls vds validation +./tools/testfiles/vds/tvds-1.ls +./tools/testfiles/vds/tvds-2.ls +./tools/testfiles/vds/tvds-3_1.ls +./tools/testfiles/vds/tvds-3_2.ls +./tools/testfiles/vds/tvds-4.ls +./tools/testfiles/vds/tvds-5.ls #additional test input and output for h5dump XML ./tools/testfiles/tall.h5.xml @@ -2019,6 +2087,10 @@ ./tools/h5diff/testfiles/tmptest.he5 ./tools/h5diff/testfiles/h5diff_tmp2.txt ./tools/h5diff/testfiles/tmpSingleSiteBethe.output.h5 +#vds +./tools/h5diff/testfiles/h5diff_v1.txt +./tools/h5diff/testfiles/h5diff_v2.txt +./tools/h5diff/testfiles/h5diff_v3.txt #test files for h5repack ./tools/h5repack/testfiles/README @@ -2393,6 +2465,7 @@ ./tools/h5dump/CMakeTests.cmake ./tools/h5dump/CMakeTestsPBITS.cmake ./tools/h5dump/CMakeTestsXML.cmake +./tools/h5dump/CMakeTestsVDS.cmake ./tools/h5import/CMakeLists.txt ./tools/h5import/CMakeTests.cmake ./tools/h5jam/CMakeLists.txt @@ -2406,6 +2479,7 @@ ./tools/lib/CMakeLists.txt ./tools/misc/CMakeLists.txt ./tools/misc/CMakeTests.cmake +./tools/misc/vds/CMakeLists.txt ./tools/perform/CMakeLists.txt ./tools/perform/CMakeTests.cmake @@ -41,6 +41,7 @@ $Source = ""; "H5D_mpio_no_collective_cause_t" => "Dn", "H5D_mpio_actual_chunk_opt_mode_t" => "Do", "H5D_space_status_t" => "Ds", + "H5D_vds_view_t" => "Dv", "H5FD_mpio_xfer_t" => "Dt", "herr_t" => "e", "H5E_direction_t" => "Ed", @@ -30978,7 +30978,7 @@ else fi -ac_config_files="$ac_config_files src/libhdf5.settings Makefile src/Makefile test/Makefile test/testcheck_version.sh test/testerror.sh test/H5srcdir_str.h test/testlibinfo.sh test/testlinks_env.sh test/test_plugin.sh testpar/Makefile tools/Makefile tools/h5dump/Makefile tools/h5dump/testh5dump.sh tools/h5dump/testh5dumppbits.sh tools/h5dump/testh5dumpxml.sh tools/h5ls/testh5ls.sh tools/h5import/Makefile tools/h5import/h5importtestutil.sh tools/h5diff/Makefile tools/h5diff/testh5diff.sh tools/h5diff/testph5diff.sh tools/h5jam/Makefile tools/h5jam/testh5jam.sh tools/h5repack/Makefile tools/h5repack/h5repack.sh tools/h5repack/h5repack_plugin.sh tools/h5ls/Makefile tools/h5copy/Makefile tools/h5copy/testh5copy.sh tools/lib/Makefile tools/misc/Makefile tools/misc/h5cc tools/misc/testh5mkgrp.sh tools/misc/testh5repart.sh tools/h5stat/testh5stat.sh tools/h5stat/Makefile tools/perform/Makefile examples/Makefile examples/run-c-ex.sh examples/testh5cc.sh c++/Makefile c++/src/Makefile c++/src/h5c++ c++/test/Makefile c++/test/H5srcdir_str.h c++/examples/Makefile c++/examples/run-c++-ex.sh c++/examples/testh5c++.sh fortran/Makefile fortran/src/h5fc fortran/src/Makefile fortran/src/H5fort_type_defines.h fortran/test/Makefile fortran/testpar/Makefile fortran/examples/Makefile fortran/examples/run-fortran-ex.sh fortran/examples/testh5fc.sh hl/Makefile hl/src/Makefile hl/test/Makefile hl/test/H5srcdir_str.h hl/tools/Makefile hl/tools/gif2h5/Makefile hl/tools/gif2h5/h52giftest.sh hl/examples/Makefile hl/examples/run-hlc-ex.sh hl/c++/Makefile hl/c++/src/Makefile hl/c++/test/Makefile hl/c++/examples/Makefile hl/c++/examples/run-hlc++-ex.sh hl/fortran/Makefile hl/fortran/src/Makefile hl/fortran/test/Makefile hl/fortran/examples/Makefile hl/fortran/examples/run-hlfortran-ex.sh" +ac_config_files="$ac_config_files src/libhdf5.settings Makefile src/Makefile test/Makefile test/testcheck_version.sh test/testerror.sh test/H5srcdir_str.h test/testlibinfo.sh test/testlinks_env.sh test/test_plugin.sh testpar/Makefile tools/Makefile tools/h5dump/Makefile tools/h5dump/testh5dump.sh tools/h5dump/testh5dumppbits.sh tools/h5dump/testh5dumpvds.sh tools/h5dump/testh5dumpxml.sh tools/h5ls/testh5ls.sh tools/h5ls/testh5lsvds.sh tools/h5import/Makefile tools/h5import/h5importtestutil.sh tools/h5diff/Makefile tools/h5diff/testh5diff.sh tools/h5diff/testph5diff.sh tools/h5jam/Makefile tools/h5jam/testh5jam.sh tools/h5repack/Makefile tools/h5repack/h5repack.sh tools/h5repack/h5repack_plugin.sh tools/h5ls/Makefile tools/h5copy/Makefile tools/h5copy/testh5copy.sh tools/lib/Makefile tools/misc/Makefile tools/misc/h5cc tools/misc/testh5mkgrp.sh tools/misc/testh5repart.sh tools/misc/vds/Makefile tools/h5stat/testh5stat.sh tools/h5stat/Makefile tools/perform/Makefile examples/Makefile examples/run-c-ex.sh examples/testh5cc.sh c++/Makefile c++/src/Makefile c++/src/h5c++ c++/test/Makefile c++/test/H5srcdir_str.h c++/examples/Makefile c++/examples/run-c++-ex.sh c++/examples/testh5c++.sh fortran/Makefile fortran/src/h5fc fortran/src/Makefile fortran/src/H5fort_type_defines.h fortran/test/Makefile fortran/testpar/Makefile fortran/examples/Makefile fortran/examples/run-fortran-ex.sh fortran/examples/testh5fc.sh hl/Makefile hl/src/Makefile hl/test/Makefile hl/test/H5srcdir_str.h hl/tools/Makefile hl/tools/gif2h5/Makefile hl/tools/gif2h5/h52giftest.sh hl/examples/Makefile hl/examples/run-hlc-ex.sh hl/c++/Makefile hl/c++/src/Makefile hl/c++/test/Makefile hl/c++/examples/Makefile hl/c++/examples/run-hlc++-ex.sh hl/fortran/Makefile hl/fortran/src/Makefile hl/fortran/test/Makefile hl/fortran/examples/Makefile hl/fortran/examples/run-hlfortran-ex.sh" cat >confcache <<\_ACEOF @@ -32237,8 +32237,10 @@ do "tools/h5dump/Makefile") CONFIG_FILES="$CONFIG_FILES tools/h5dump/Makefile" ;; "tools/h5dump/testh5dump.sh") CONFIG_FILES="$CONFIG_FILES tools/h5dump/testh5dump.sh" ;; "tools/h5dump/testh5dumppbits.sh") CONFIG_FILES="$CONFIG_FILES tools/h5dump/testh5dumppbits.sh" ;; + "tools/h5dump/testh5dumpvds.sh") CONFIG_FILES="$CONFIG_FILES tools/h5dump/testh5dumpvds.sh" ;; "tools/h5dump/testh5dumpxml.sh") CONFIG_FILES="$CONFIG_FILES tools/h5dump/testh5dumpxml.sh" ;; "tools/h5ls/testh5ls.sh") CONFIG_FILES="$CONFIG_FILES tools/h5ls/testh5ls.sh" ;; + "tools/h5ls/testh5lsvds.sh") CONFIG_FILES="$CONFIG_FILES tools/h5ls/testh5lsvds.sh" ;; "tools/h5import/Makefile") CONFIG_FILES="$CONFIG_FILES tools/h5import/Makefile" ;; "tools/h5import/h5importtestutil.sh") CONFIG_FILES="$CONFIG_FILES tools/h5import/h5importtestutil.sh" ;; "tools/h5diff/Makefile") CONFIG_FILES="$CONFIG_FILES tools/h5diff/Makefile" ;; @@ -32257,6 +32259,7 @@ do "tools/misc/h5cc") CONFIG_FILES="$CONFIG_FILES tools/misc/h5cc" ;; "tools/misc/testh5mkgrp.sh") CONFIG_FILES="$CONFIG_FILES tools/misc/testh5mkgrp.sh" ;; "tools/misc/testh5repart.sh") CONFIG_FILES="$CONFIG_FILES tools/misc/testh5repart.sh" ;; + "tools/misc/vds/Makefile") CONFIG_FILES="$CONFIG_FILES tools/misc/vds/Makefile" ;; "tools/h5stat/testh5stat.sh") CONFIG_FILES="$CONFIG_FILES tools/h5stat/testh5stat.sh" ;; "tools/h5stat/Makefile") CONFIG_FILES="$CONFIG_FILES tools/h5stat/Makefile" ;; "tools/perform/Makefile") CONFIG_FILES="$CONFIG_FILES tools/perform/Makefile" ;; diff --git a/configure.ac b/configure.ac index b441cad..33f18f7 100644 --- a/configure.ac +++ b/configure.ac @@ -187,7 +187,7 @@ AC_SUBST([PAC_C_MAX_REAL_PRECISION]) ## ---------------------------------------------------------------------- ## Some platforms have broken basename, and/or xargs programs. Check ## that it actually does what it's supposed to do. Catch this early -## since configure and scripts relies upon them heavily and there's +## since configure and scripts relies upon them heavily and there's ## no use continuing if it's broken. ## AC_MSG_CHECKING([if basename works]) @@ -335,7 +335,7 @@ AC_ARG_ENABLE([unsupported], [Allow unsupported combinations of configure options])], [ALLOW_UNSUPPORTED=$enableval]) -case "X-$ALLOW_UNSUPPORTED" in +case "X-$ALLOW_UNSUPPORTED" in X-|X-no) AC_MSG_RESULT([no]) ;; @@ -416,7 +416,7 @@ if test "X$HDF_FORTRAN" = "Xyes"; then [cat fortran/src/H5config_f.inc | sed '1d;s%^/\* \(.*\) \*/%\1%;s/#define /#define H5_/;s/#undef /#undef H5_/' >fortran/src/H5config_f.inc.tmp; mv -f fortran/src/H5config_f.inc.tmp fortran/src/H5config_f.inc]) AC_SUBST([FC]) HDF_FORTRAN=yes - + HDF5_INTERFACES="$HDF5_INTERFACES fortran" ## -------------------------------------------------------------------- @@ -441,7 +441,7 @@ if test "X$HDF_FORTRAN" = "Xyes"; then ## -------------------------------------------------------------------- ## Check for a Fortran compiler and how to include modules. - ## + ## AC_PROG_FC([PAC_FC_SEARCH_LIST],) AC_F9X_MODS @@ -631,8 +631,8 @@ if test "X$HDF_CXX" = "Xyes"; then # Checking if C++ can handle namespaces PAC_PROG_CXX_NAMESPACE - - # Checking if C++ has offsetof extension + + # Checking if C++ has offsetof extension PAC_PROG_CXX_OFFSETOF # if C++ can handle static cast @@ -781,7 +781,7 @@ if test "X${HDF_FORTRAN}" = "Xyes" && test "X${enable_shared}" != "Xno"; then H5_FORTRAN_SHARED="yes" ## Disable fortran shared libraries on Mac. (MAM - 03/30/11) - + case "`uname`" in Darwin*) H5_FORTRAN_SHARED="no" @@ -790,7 +790,7 @@ if test "X${HDF_FORTRAN}" = "Xyes" && test "X${enable_shared}" != "Xno"; then esac ## Report results of check(s) - + if test "X${H5_FORTRAN_SHARED}" = "Xno"; then AC_MSG_RESULT([no]) AC_MSG_WARN([$CHECK_WARN]) @@ -826,7 +826,7 @@ LT_INIT([dlopen,win32-dll]) ## ---------------------------------------------------------------------- ## Check if we should install only statically linked executables. ## This check needs to occur after libtool is initialized because -## we check a libtool cache value and may issue a warning based +## we check a libtool cache value and may issue a warning based ## on its result. AC_MSG_CHECKING([if we should install only statically linked executables]) AC_ARG_ENABLE([static_exec], @@ -895,7 +895,7 @@ esac AC_SUBST([AM_MAKEFLAGS]) AM_MAKEFLAGS="" ## Don't run test if MAKE is defined but is the empty string -if test -n "${MAKE-make}"; then +if test -n "${MAKE-make}"; then AC_MSG_CHECKING([whether make will build with undefined variables]) @@ -1047,11 +1047,11 @@ fi ## ---------------------------------------------------------------------- ## Use the macro _AC_SYS_LARGEFILE_MACRO_VALUE to test defines -## that might need to be set for largefile support to behave +## that might need to be set for largefile support to behave ## correctly. This macro is defined in acsite.m4 and overrides ## the version provided by Autoconf (as of v2.65). The custom -## macro additionally adds the appropriate defines to AM_CPPFLAGS -## so that later configure checks have them visible. +## macro additionally adds the appropriate defines to AM_CPPFLAGS +## so that later configure checks have them visible. ## Check for _FILE_OFFSET_BITS _AC_SYS_LARGEFILE_MACRO_VALUE([_FILE_OFFSET_BITS], [64], @@ -1072,16 +1072,16 @@ fi ## case "$host_cpu-$host_vendor-$host_os" in *linux*) - ## Make available various LFS-related routines using the following + ## Make available various LFS-related routines using the following ## _LARGEFILE*_SOURCE macros. AM_CPPFLAGS="-D_LARGEFILE64_SOURCE -D_LARGEFILE_SOURCE $AM_CPPFLAGS" ## Add POSIX support on Linux systems, so <features.h> defines ## __USE_POSIX, which is required to get the prototype for fdopen - ## defined correctly in <stdio.h>. + ## defined correctly in <stdio.h>. ## ## This flag was removed from h5cc as of 2009-10-17 when it was found - ## that the flag broke compiling netCDF-4 code with h5cc, but kept in + ## that the flag broke compiling netCDF-4 code with h5cc, but kept in ## H5_CPPFLAGS because fdopen and HDfdopen fail without it. HDfdopen ## is used only by H5_debug_mask which is used only when debugging in ## H5_init_library (all in H5.c). When the flag was removed this was @@ -1108,7 +1108,7 @@ case "$host_cpu-$host_vendor-$host_os" in ## correctly in <stdio.h> ## Linking to the bsd-compat library is required as per the gcc manual: ## http://www.gnu.org/s/libc/manual/html_node/Feature-Test-Macros.html - ## however, we do not do this since it breaks the big test on some + ## however, we do not do this since it breaks the big test on some ## older platforms. H5_CPPFLAGS="-D_BSD_SOURCE $H5_CPPFLAGS" @@ -1119,7 +1119,7 @@ case "$host_cpu-$host_vendor-$host_os" in ;; esac -## Need to add the AM_ and H5_ into CFLAGS/CPPFLAGS to make them visible +## Need to add the AM_ and H5_ into CFLAGS/CPPFLAGS to make them visible ## for configure checks. ## Note: Both will be restored by the end of configure. CPPFLAGS="$H5_CPPFLAGS $AM_CPPFLAGS $CPPFLAGS" @@ -1430,17 +1430,17 @@ case $withval in fi ;; esac - + saved_CPPFLAGS="$CPPFLAGS" saved_AM_CPPFLAGS="$AM_CPPFLAGS" saved_LDFLAGS="$LDFLAGS" saved_AM_LDFLAGS="$AM_LDFLAGS" - + if test -n "$szlib_inc"; then CPPFLAGS="$CPPFLAGS -I$szlib_inc" AM_CPPFLAGS="$AM_CPPFLAGS -I$szlib_inc" fi - + AC_CHECK_HEADERS([szlib.h], [HAVE_SZLIB_H="yes"], [CPPFLAGS="$saved_CPPFLAGS"; AM_CPPFLAGS="$saved_AM_CPPFLAGS"] [unset HAVE_SZLIB]) @@ -1449,7 +1449,7 @@ case $withval in LDFLAGS="$LDFLAGS -L$szlib_lib" AM_LDFLAGS="$AM_LDFLAGS -L$szlib_lib" fi - + if test "x$HAVE_SZLIB" = "xyes" -a "x$HAVE_SZLIB_H" = "xyes"; then AC_CHECK_LIB([sz], [SZ_BufftoBuffCompress],, [LDFLAGS="$saved_LDFLAGS"; AM_LDFLAGS="$saved_AM_LDFLAGS"; unset HAVE_SZLIB]) @@ -1466,7 +1466,7 @@ if test "x$HAVE_SZLIB" = "xyes" -a "x$HAVE_SZLIB_H" = "xyes"; then AC_MSG_CHECKING([for szlib encoder]) ## Set LD_LIBRARY_PATH so encoder test can find the library and run. - ## Also add LL_PATH substitution to Makefiles so they can use the + ## Also add LL_PATH substitution to Makefiles so they can use the ## path as well, for testing examples. if test -z "$LD_LIBRARY_PATH"; then export LD_LIBRARY_PATH="$szlib_lib" @@ -1489,25 +1489,25 @@ if test "x$HAVE_SZLIB" = "xyes" -a "x$HAVE_SZLIB_H" = "xyes"; then ]])] , [hdf5_cv_szlib_can_encode=yes], [hdf5_cv_szlib_can_encode=no],)] ) - - AC_DEFINE([HAVE_FILTER_SZIP], [1], + + AC_DEFINE([HAVE_FILTER_SZIP], [1], [Define if support for szip filter is enabled]) USE_FILTER_SZIP="yes" if test ${hdf5_cv_szlib_can_encode} = "yes"; then AC_MSG_RESULT([yes]) - fi + fi if test ${hdf5_cv_szlib_can_encode} = "no"; then AC_MSG_RESULT([no]) - fi - + fi + ## Add "szip" to external filter list if test ${hdf5_cv_szlib_can_encode} = "yes"; then if test "X$EXTERNAL_FILTERS" != "X"; then EXTERNAL_FILTERS="${EXTERNAL_FILTERS}," fi EXTERNAL_FILTERS="${EXTERNAL_FILTERS}szip(encoder)" - fi + fi if test ${hdf5_cv_szlib_can_encode} = "no"; then if test "X$EXTERNAL_FILTERS" != "X"; then EXTERNAL_FILTERS="${EXTERNAL_FILTERS}," @@ -1560,7 +1560,7 @@ case "X-$THREADSAFE" in AC_MSG_RESULT([no]) ;; X-yes) - THREADSAFE=yes + THREADSAFE=yes AC_MSG_RESULT([yes]) ;; *) @@ -1867,7 +1867,7 @@ for hdf5_cv_printf_ll in l ll L q unknown; do done]) AC_MSG_RESULT([%${hdf5_cv_printf_ll}d and %${hdf5_cv_printf_ll}u]) -AC_DEFINE_UNQUOTED([PRINTF_LL_WIDTH], ["$hdf5_cv_printf_ll"], +AC_DEFINE_UNQUOTED([PRINTF_LL_WIDTH], ["$hdf5_cv_printf_ll"], [Width for printf() for type `long long' or `__int64', use `ll']) @@ -2186,7 +2186,7 @@ if test -n "$PARALLEL"; then fi ## If RUNSERIAL or RUNPARALLEL is the word `none' then replace it with - ## the empty string. This means that no launch commands were requested, + ## the empty string. This means that no launch commands were requested, ## so we will not use any launch commands. if test "X$RUNSERIAL" = "Xnone"; then RUNSERIAL="" @@ -2252,7 +2252,7 @@ if test -n "$PARALLEL"; then fi ;; esac - + if test -n "$mpe_inc"; then saved_CPPFLAGS="$CPPFLAGS" saved_AM_CPPFLAGS="$AM_CPPFLAGS" @@ -2262,7 +2262,7 @@ if test -n "$PARALLEL"; then else AC_CHECK_HEADERS([mpe.h],, [unset MPE]) fi - + if test -n "$mpe_lib"; then saved_LDFLAGS="$LDFLAGS" saved_AM_LDFLAGS="$AM_LDFLAGS" @@ -2347,12 +2347,12 @@ AC_DEFINE_UNQUOTED([DEFAULT_PLUGINDIR], ["$default_plugindir"], ## Decide whether the presence of user's exception handling functions is ## checked and data conversion exceptions are returned. This is mainly ## for the speed optimization of hard conversions. Soft conversions can -## actually benefit little. +## actually benefit little. ## AC_MSG_CHECKING([whether exception handling functions is checked during data conversions]) AC_ARG_ENABLE([dconv-exception], [AS_HELP_STRING([--enable-dconv-exception], - [if exception handling functions is checked during + [if exception handling functions is checked during data conversions [default=yes]])], [DCONV_EXCEPTION=$enableval], [DCONV_EXCEPTION=yes]) @@ -2406,9 +2406,9 @@ esac ## ---------------------------------------------------------------------- ## Set the flag to indicate that the machine is using a special algorithm to convert -## 'long double' to '(unsigned) long' values. (This flag should only be set for -## the IBM Power6 Linux. When the bit sequence of long double is -## 0x4351ccf385ebc8a0bfcc2a3c3d855620, the converted value of (unsigned)long +## 'long double' to '(unsigned) long' values. (This flag should only be set for +## the IBM Power6 Linux. When the bit sequence of long double is +## 0x4351ccf385ebc8a0bfcc2a3c3d855620, the converted value of (unsigned)long ## is 0x004733ce17af227f, not the same as the library's conversion to 0x004733ce17af2282. ## The machine's conversion gets the correct value. We define the macro and disable ## this kind of test until we figure out what algorithm they use. @@ -2429,12 +2429,12 @@ else unsigned char s[16]; unsigned char s2[8]; int ret = 1; - + if(sizeof(long double) == 16 && sizeof(long) == 8) { - /*make sure the long double type has 16 bytes in size and + /*make sure the long double type has 16 bytes in size and * 11 bits of exponent. If it is, - *the bit sequence should be like below. It's not - *a decent way to check but this info isn't available. */ + *the bit sequence should be like below. It's not + *a decent way to check but this info isn't available. */ memcpy(s, &ld, 16); if(s[0]==0x43 && s[1]==0x51 && s[2]==0xcc && s[3]==0xf3 && s[4]==0x85 && s[5]==0xeb && s[6]==0xc8 && s[7]==0xa0 && @@ -2468,8 +2468,8 @@ else if(s2[0]==0x00 && s2[1]==0x47 && s2[2]==0x33 && s2[3]==0xce && s2[4]==0x17 && s2[5]==0xaf && s2[6]==0x22 && s2[7]==0x7f) ret = 0; - } - } + } + } exit(ret); ]])] , [hdf5_cv_ldouble_to_long_special=yes], [hdf5_cv_ldouble_to_long_special=no],)]) @@ -2485,10 +2485,10 @@ fi ## ---------------------------------------------------------------------- ## Set the flag to indicate that the machine is using a special algorithm -## to convert some values of '(unsigned) long' to 'long double' values. -## (This flag should be off for all machines, except for IBM Power6 Linux, -## when the bit sequences are 003fff..., 007fff..., 00ffff..., 01ffff..., -## ..., 7fffff..., the compiler uses a unknown algorithm. We define a +## to convert some values of '(unsigned) long' to 'long double' values. +## (This flag should be off for all machines, except for IBM Power6 Linux, +## when the bit sequences are 003fff..., 007fff..., 00ffff..., 01ffff..., +## ..., 7fffff..., the compiler uses a unknown algorithm. We define a ## macro and skip the test for now until we know about the algorithm. ## AC_MSG_CHECKING([if using special algorithm to convert (unsigned) long to long double values]) @@ -2506,17 +2506,17 @@ else unsigned long ull; unsigned char s[16]; int flag=0, ret=1; - + /*Determine if long double has 16 byte in size, 11 bit exponent, and - *the bias is 0x3ff */ - if(sizeof(long double) == 16) { + *the bias is 0x3ff */ + if(sizeof(long double) == 16) { ld = 1.0L; memcpy(s, &ld, 16); if(s[0]==0x3f && s[1]==0xf0 && s[2]==0x00 && s[3]==0x00 && - s[4]==0x00 && s[5]==0x00 && s[6]==0x00 && s[7]==0x00) - flag = 1; + s[4]==0x00 && s[5]==0x00 && s[6]==0x00 && s[7]==0x00) + flag = 1; } - + if(flag==1 && sizeof(long)==8) { ll = 0x003fffffffffffffL; ld = (long double)ll; @@ -2532,7 +2532,7 @@ else s[8]==0xbf && s[9]==0xf0 && s[10]==0x00 && s[11]==0x00 && s[12]==0x00 && s[13]==0x00 && s[14]==0x00 && s[15]==0x00) ret = 0; - } + } if(flag==1 && sizeof(unsigned long)==8) { ull = 0xffffffffffffffffUL; ld = (long double)ull; @@ -2550,7 +2550,7 @@ else s[8]==0xbf && s[9]==0xf0 && s[10]==0x00 && s[11]==0x00 && s[12]==0x00 && s[13]==0x00 && s[14]==0x00 && s[15]==0x00) ret = 0; - } + } exit(ret); ]])] , [hdf5_cv_long_to_ldouble_special=yes], [hdf5_cv_long_to_ldouble_special=no],)]) @@ -3099,8 +3099,10 @@ AC_CONFIG_FILES([src/libhdf5.settings tools/h5dump/Makefile tools/h5dump/testh5dump.sh tools/h5dump/testh5dumppbits.sh + tools/h5dump/testh5dumpvds.sh tools/h5dump/testh5dumpxml.sh tools/h5ls/testh5ls.sh + tools/h5ls/testh5lsvds.sh tools/h5import/Makefile tools/h5import/h5importtestutil.sh tools/h5diff/Makefile @@ -3119,6 +3121,7 @@ AC_CONFIG_FILES([src/libhdf5.settings tools/misc/h5cc tools/misc/testh5mkgrp.sh tools/misc/testh5repart.sh + tools/misc/vds/Makefile tools/h5stat/testh5stat.sh tools/h5stat/Makefile tools/perform/Makefile diff --git a/examples/CMakeLists.txt b/examples/CMakeLists.txt index 7953161..8849ce7 100644 --- a/examples/CMakeLists.txt +++ b/examples/CMakeLists.txt @@ -34,6 +34,14 @@ set (examples h5_extlink h5_elink_unix2win h5_shared_mesg + h5_vds + h5_vds-exc + h5_vds-exclim + h5_vds-eiger + h5_vds-simpleIO + h5_vds-percival + h5_vds-percival-unlim + h5_vds-percival-unlim-maxmin ) foreach (example ${examples}) diff --git a/examples/CMakeTests.cmake b/examples/CMakeTests.cmake index 42b42b3..2cf82b8 100644 --- a/examples/CMakeTests.cmake +++ b/examples/CMakeTests.cmake @@ -46,6 +46,18 @@ blue/prefix_target.h5 red/prefix_target.h5 u2w/u2w_target.h5 + vds.h5 + vds-excalibur.h5 + vds-exclim.h5 + vds-percival.h5 + vds-percival-unlim.h5 + vds-percival-unlim-maxmin.h5 + a.h5 + b.h5 + c.h5 + d.h5 + vds-simpleIO.h5 + vds-eiger.h5 ) if (NOT "${last_test}" STREQUAL "") set_tests_properties (EXAMPLES-clear-objects PROPERTIES DEPENDS ${last_test}) diff --git a/examples/Makefile.am b/examples/Makefile.am index 5d0da93..883b99d 100644 --- a/examples/Makefile.am +++ b/examples/Makefile.am @@ -37,7 +37,9 @@ EXAMPLE_PROG = h5_write h5_read h5_extend_write h5_chunk_read h5_compound \ h5_crtgrpd h5_subset h5_cmprss h5_rdwt h5_crtgrpar h5_extend \ h5_crtatt h5_crtgrp h5_crtdat \ h5_group h5_select h5_attribute h5_mount h5_reference h5_drivers \ - h5_ref2reg h5_extlink h5_elink_unix2win h5_shared_mesg + h5_ref2reg h5_extlink h5_elink_unix2win h5_shared_mesg h5_vds h5_vds-exc \ + h5_vds-exclim h5_vds-eiger h5_vds-simpleIO h5_vds-percival \ + h5_vds-percival-unlim h5_vds-percival-unlim-maxmin TEST_SCRIPT=testh5cc.sh TEST_EXAMPLES_SCRIPT=$(INSTALL_SCRIPT_FILES) @@ -48,7 +50,9 @@ INSTALL_FILES = h5_write.c h5_read.c h5_extend_write.c h5_chunk_read.c \ h5_extend.c h5_crtatt.c h5_crtgrp.c h5_crtdat.c \ h5_compound.c h5_group.c h5_select.c h5_attribute.c h5_mount.c \ h5_reference.c h5_drivers.c h5_extlink.c h5_elink_unix2win.c \ - h5_ref2reg.c h5_shared_mesg.c ph5example.c + h5_ref2reg.c h5_shared_mesg.c ph5example.c h5_vds.c h5_vds-exc.c \ + h5_vds-exclim.c h5_vds-eiger.c h5_vds-simpleIO.c h5_vds-percival.c \ + h5_vds-percival-unlim.c h5_vds-percival-unlim-maxmin.c @@ -117,6 +121,14 @@ h5_dtransform: $(srcdir)/h5_dtransform.c h5_extlink: $(srcdir)/h5_extlink.c $(EXTLINK_DIRS) h5_elink_unix2win: $(srcdir)/h5_elink_unix2win.c $(EXTLINK_DIRS) h5_shared_mesg: $(srcdir)/h5_shared_mesg.c +h5_vds: $(srcdir)/h5_vds.c +h5_vds-exc: $(srcdir)/h5_vds-exc.c +h5_vds-exclim: $(srcdir)/h5_vds-exclim.c +h5_vds-eiger: $(srcdir)/h5_vds-eiger.c +h5_vds-simpleIO: $(srcdir)/h5_vds-simpleIO.c +h5_vds-percival: $(srcdir)/h5_vds-percival.c +h5_vds-percival-unlim: $(srcdir)/h5_vds-percival-unlim.c +h5_vds-percival-unlim-maxmin: $(srcdir)/h5_vds-percival-unlim-maxmin.c if BUILD_SHARED_SZIP_CONDITIONAL LD_LIBRARY_PATH=$(LL_PATH) diff --git a/examples/Makefile.in b/examples/Makefile.in index 94a0b54..c403545 100644 --- a/examples/Makefile.in +++ b/examples/Makefile.in @@ -633,7 +633,9 @@ EXAMPLE_PROG = h5_write h5_read h5_extend_write h5_chunk_read h5_compound \ h5_crtgrpd h5_subset h5_cmprss h5_rdwt h5_crtgrpar h5_extend \ h5_crtatt h5_crtgrp h5_crtdat \ h5_group h5_select h5_attribute h5_mount h5_reference h5_drivers \ - h5_ref2reg h5_extlink h5_elink_unix2win h5_shared_mesg + h5_ref2reg h5_extlink h5_elink_unix2win h5_shared_mesg h5_vds h5_vds-exc \ + h5_vds-exclim h5_vds-eiger h5_vds-simpleIO h5_vds-percival \ + h5_vds-percival-unlim h5_vds-percival-unlim-maxmin TEST_SCRIPT = testh5cc.sh TEST_EXAMPLES_SCRIPT = $(INSTALL_SCRIPT_FILES) @@ -645,7 +647,9 @@ INSTALL_FILES = h5_write.c h5_read.c h5_extend_write.c h5_chunk_read.c \ h5_extend.c h5_crtatt.c h5_crtgrp.c h5_crtdat.c \ h5_compound.c h5_group.c h5_select.c h5_attribute.c h5_mount.c \ h5_reference.c h5_drivers.c h5_extlink.c h5_elink_unix2win.c \ - h5_ref2reg.c h5_shared_mesg.c ph5example.c + h5_ref2reg.c h5_shared_mesg.c ph5example.c h5_vds.c h5_vds-exc.c \ + h5_vds-exclim.c h5_vds-eiger.c h5_vds-simpleIO.c h5_vds-percival.c \ + h5_vds-percival-unlim.c h5_vds-percival-unlim-maxmin.c # The external link examples demonstrate how to use paths; they need @@ -1098,6 +1102,14 @@ h5_dtransform: $(srcdir)/h5_dtransform.c h5_extlink: $(srcdir)/h5_extlink.c $(EXTLINK_DIRS) h5_elink_unix2win: $(srcdir)/h5_elink_unix2win.c $(EXTLINK_DIRS) h5_shared_mesg: $(srcdir)/h5_shared_mesg.c +h5_vds: $(srcdir)/h5_vds.c +h5_vds-exc: $(srcdir)/h5_vds-exc.c +h5_vds-exclim: $(srcdir)/h5_vds-exclim.c +h5_vds-eiger: $(srcdir)/h5_vds-eiger.c +h5_vds-simpleIO: $(srcdir)/h5_vds-simpleIO.c +h5_vds-percival: $(srcdir)/h5_vds-percival.c +h5_vds-percival-unlim: $(srcdir)/h5_vds-percival-unlim.c +h5_vds-percival-unlim-maxmin: $(srcdir)/h5_vds-percival-unlim-maxmin.c # How to create EXAMPLEDIR if it doesn't already exist $(EXAMPLEDIR): diff --git a/examples/h5_vds-eiger.c b/examples/h5_vds-eiger.c new file mode 100644 index 0000000..ea22243 --- /dev/null +++ b/examples/h5_vds-eiger.c @@ -0,0 +1,177 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Eiger use case. Every 5 frames 10x10 are in the source + dataset "/A" in file with the name f-<#>.h5 + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds-eiger.h5" +#define DATASET "VDS-Eiger" +#define VDSDIM0 5 +#define VDSDIM1 10 +#define VDSDIM2 10 +#define DIM0 5 +#define DIM1 10 +#define DIM2 10 +#define RANK 3 + +int +main (void) +{ + hid_t file, src_space, vspace, + dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + vdsdims_max[3] = {H5S_UNLIMITED, VDSDIM1, VDSDIM1}, + dims[3] = {DIM0, DIM1, DIM2}, + start[3], /* Hyperslab parameters */ + stride[3], + count[3], + block[3]; + hsize_t start_out[3], /* Hyperslab parameter out */ + stride_out[3], + count_out[3], + block_out[3]; + int i; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + + + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + vspace = H5Screate_simple (RANK, vdsdims, vdsdims_max); + + /* Create dataspaces for the source dataset. */ + src_space = H5Screate_simple (RANK, dims, NULL); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = DIM0; + stride[1] = 1; + stride[2] = 1; + count[0] = H5S_UNLIMITED; + count[1] = 1; + count[2] = 1; + block[0] = DIM0; + block[1] = DIM1; + block[2] = DIM2; + + /* + * Build the mappings + * + */ + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, stride, count, block); + status = H5Pset_virtual (dcpl, vspace, "f-%b.h5", "/A", src_space); + + + + /* Create a virtual dataset */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, vspace, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (vspace); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %d\n", (int)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset "); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if(H5Sget_select_type(src_space) == H5S_SEL_ALL) { + printf("H5S_ALL \n"); + } +/* EIP read data back */ + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } + + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + + return 0; +} + diff --git a/examples/h5_vds-exc.c b/examples/h5_vds-exc.c new file mode 100644 index 0000000..88d8f61 --- /dev/null +++ b/examples/h5_vds-exc.c @@ -0,0 +1,215 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Excalibur use case with k=2 and m=3. + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds-exc.h5" +#define DATASET "VDS-Excalibur" +#define VDSDIM0 0 +#define VDSDIM1 15 +#define VDSDIM2 6 +#define KDIM0 0 +#define KDIM1 2 +#define KDIM2 6 +#define NDIM0 0 +#define NDIM1 3 +#define NDIM2 6 +#define RANK 3 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5", + "d.h5", + "e.h5", + "f.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C", + "D", + "E", + "F" +}; + +int +main (void) +{ + hid_t file, space, ksrc_space, nsrc_space, vspace, + src_space, + dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + vdsdims_max[3] = {H5S_UNLIMITED,VDSDIM1, VDSDIM2}, + kdims[3] = {KDIM0, KDIM1, KDIM2}, + kdims_max[3] = {H5S_UNLIMITED, KDIM1, KDIM2}, + ndims[3] = {NDIM0, NDIM1, NDIM2}, + ndims_max[3] = {H5S_UNLIMITED, NDIM1, NDIM2}, + start[3], /* Hyperslab parameters */ + stride[3], + count[3], + block[3]; + hsize_t start_out[3], + stride_out[3], + count_out[3], + block_out[3]; + int k = 2; + int n = 3; + int i; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + + + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + space = H5Screate_simple (RANK, vdsdims, vdsdims_max); + /* Create dataspaces for A, C, and E datasets. */ + ksrc_space = H5Screate_simple (RANK, kdims, kdims_max); + /* Create dataspaces for B, D, and F datasets. */ + nsrc_space = H5Screate_simple (RANK, ndims, ndims_max); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + count[0] = H5S_UNLIMITED; + count[1] = 1; + count[2] = 1; + block[0] = 1; + block[1] = k; + block[2] = VDSDIM2; + + /* + * Build the mappings for A, C and E source datasets. + * + */ + for (i = 0; i < 3; i++) { + start[1] = (hsize_t)((k+n)*i); + status = H5Sselect_hyperslab (space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Pset_virtual (dcpl, space, SRC_FILE[2*i], SRC_DATASET[2*i], ksrc_space); + } + + /* Reinitialize block[1] */ + block[1] = n; + /* + * Build the mappings for B, D and F source datasets. + * + */ + for (i = 0; i < 3; i++) { + start[1] = (hsize_t)(k+(k+n)*i); + status = H5Sselect_hyperslab (space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Pset_virtual (dcpl, space, SRC_FILE[2*i+1], SRC_DATASET[2*i+1], nsrc_space); + } + + /* Create a virtual dataset */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, space, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (space); + status = H5Sclose (nsrc_space); + status = H5Sclose (ksrc_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf("Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset "); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if(H5Sget_select_type(src_space) == H5S_SEL_ALL) { + printf("H5S_ALL \n"); + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } +/* EIP read data back */ + + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + + return 0; +} + diff --git a/examples/h5_vds-exclim.c b/examples/h5_vds-exclim.c new file mode 100644 index 0000000..4933471 --- /dev/null +++ b/examples/h5_vds-exclim.c @@ -0,0 +1,222 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Excalibur use case with k=2 and m=3 and only 3 planes in + Z-direction (i.e., not unlimited). + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds-exclim.h5" +#define DATASET "VDS-Excaliburlim" +#define VDSDIM0 3 +#define VDSDIM1 15 +#define VDSDIM2 6 +#define KDIM0 3 +#define KDIM1 2 +#define KDIM2 6 +#define NDIM0 3 +#define NDIM1 3 +#define NDIM2 6 +#define RANK 3 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5", + "d.h5", + "e.h5", + "f.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C", + "D", + "E", + "F" +}; + +int +main (void) +{ + hid_t file, space, ksrc_space, nsrc_space, vspace, + src_space, + dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + kdims[3] = {KDIM0, KDIM1, KDIM2}, + ndims[3] = {NDIM0, NDIM1, NDIM2}, + start[3], /* Hyperslab parameters */ + stride[3], + count[3], + block[3]; + hsize_t start_out[3], + stride_out[3], + count_out[3], + block_out[3]; + int k = 2; + int n = 3; + int i; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + + + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + space = H5Screate_simple (RANK, vdsdims, NULL); + /* Create dataspaces for A, C, and E datasets. */ + ksrc_space = H5Screate_simple (RANK, kdims, NULL); + /* Create dataspaces for B, D, and F datasets. */ + nsrc_space = H5Screate_simple (RANK, ndims, NULL); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + count[0] = VDSDIM0; + count[1] = 1; + count[2] = 1; + block[0] = 1; + block[1] = k; + block[2] = VDSDIM2; + + /* + * Build the mappings for A, C and E source datasets. + * + */ + status = H5Sselect_hyperslab (ksrc_space, H5S_SELECT_SET, start, NULL, count, block); + for (i = 0; i < 3; i++) { + start[1] = (hsize_t)((k+n)*i); + status = H5Sselect_hyperslab (space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Pset_virtual (dcpl, space, SRC_FILE[2*i], SRC_DATASET[2*i], ksrc_space); + } + + /* Reinitialize start[0] and block[1] */ + start[0] = 0; + block[1] = n; + /* + * Build the mappings for B, D and F source datasets. + * + */ + status = H5Sselect_hyperslab (nsrc_space, H5S_SELECT_SET, start, NULL, count, block); + for (i = 0; i < 3; i++) { + start[1] = (hsize_t)(k+(k+n)*i); + status = H5Sselect_hyperslab (space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Pset_virtual (dcpl, space, SRC_FILE[2*i+1], SRC_DATASET[2*i+1], nsrc_space); + } + + /* Create a virtual dataset */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, space, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (space); + status = H5Sclose (nsrc_space); + status = H5Sclose (ksrc_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf("Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset \n"); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if(H5Sget_select_type(src_space) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%d, %d, %d] \n", (int)start_out[0], (int)start_out[1], (int)start_out[2]); + printf(" stride = [%d, %d, %d] \n", (int)stride_out[0], (int)stride_out[1], (int)stride_out[2]); + printf(" count = [%d, %d, %d] \n", (int)count_out[0], (int)count_out[1], (int)count_out[2]); + printf(" block = [%d, %d, %d] \n", (int)block_out[0], (int)block_out[1], (int)block_out[2]); + } + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } +/* EIP read data back */ + + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + + return 0; +} + diff --git a/examples/h5_vds-percival-unlim-maxmin.c b/examples/h5_vds-percival-unlim-maxmin.c new file mode 100644 index 0000000..a6eecfb --- /dev/null +++ b/examples/h5_vds-percival-unlim-maxmin.c @@ -0,0 +1,309 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Percival use case. Every fifth 10x10 plane in VDS is stored in + the corresponding 3D unlimited dataset. + There are 4 source datasets total. + Each of the source datasets is extended to different sizes. + VDS access property can be used to get max and min extent. + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define VFILE "vds-percival-unlim-maxmin.h5" +#define DATASET "VDS-Percival-unlim-maxmin" +#define VDSDIM0 H5S_UNLIMITED +#define VDSDIM1 10 +#define VDSDIM2 10 + +#define DIM0 H5S_UNLIMITED +#define DIM0_1 4 /* Initial size of the source datasets */ +#define DIM1 10 +#define DIM2 10 +#define RANK 3 +#define PLANE_STRIDE 4 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5", + "d.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C", + "D" +}; + +int +main (void) +{ + hid_t vfile, file, src_space, mem_space, vspace, + vdset, dset; /* Handles */ + hid_t dcpl, dapl; + herr_t status; + hsize_t vdsdims[3] = {4*DIM0_1, VDSDIM1, VDSDIM2}, + vdsdims_max[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + dims[3] = {DIM0_1, DIM1, DIM2}, + memdims[3] = {DIM0_1, DIM1, DIM2}, + extdims[3] = {0, DIM1, DIM2}, /* Dimensions of the extended source datasets */ + chunk_dims[3] = {DIM0_1, DIM1, DIM2}, + dims_max[3] = {DIM0, DIM1, DIM2}, + vdsdims_out[3], + vdsdims_max_out[3], + start[3], /* Hyperslab parameters */ + stride[3], + count[3], + src_count[3], + block[3]; + hsize_t start_out[3], /* Hyperslab parameter out */ + stride_out[3], + count_out[3], + block_out[3]; + int i, j; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + int wdata[DIM0_1*DIM1*DIM2]; + + /* + * Create source files and datasets. This step is optional. + */ + for (i=0; i < PLANE_STRIDE; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < DIM0_1*DIM1*DIM2; j++) wdata[j] = i+1; + + /* + * Create the source files and datasets. Write data to each dataset and + * close all resources. + */ + + file = H5Fcreate (SRC_FILE[i], H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + src_space = H5Screate_simple (RANK, dims, dims_max); + dcpl = H5Pcreate(H5P_DATASET_CREATE); + status = H5Pset_chunk (dcpl, RANK, chunk_dims); + dset = H5Dcreate2 (file, SRC_DATASET[i], H5T_NATIVE_INT, src_space, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Dwrite (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + wdata); + status = H5Sclose (src_space); + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + vfile = H5Fcreate (VFILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + vspace = H5Screate_simple (RANK, vdsdims, vdsdims_max); + + /* Create dataspaces for the source dataset. */ + src_space = H5Screate_simple (RANK, dims, dims_max); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = PLANE_STRIDE; /* we will select every fifth plane in VDS */ + stride[1] = 1; + stride[2] = 1; + count[0] = H5S_UNLIMITED; + count[1] = 1; + count[2] = 1; + src_count[0] = H5S_UNLIMITED; + src_count[1] = 1; + src_count[2] = 1; + block[0] = 1; + block[1] = DIM1; + block[2] = DIM2; + + /* + * Build the mappings + * + */ + status = H5Sselect_hyperslab (src_space, H5S_SELECT_SET, start, NULL, src_count, block); + for (i=0; i < PLANE_STRIDE; i++) { + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, stride, count, block); + status = H5Pset_virtual (dcpl, vspace, SRC_FILE[i], SRC_DATASET[i], src_space); + start[0]++; + } + + H5Sselect_none(vspace); + + /* Create a virtual dataset */ + vdset = H5Dcreate2 (vfile, DATASET, H5T_NATIVE_INT, vspace, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (vspace); + status = H5Sclose (src_space); + status = H5Pclose (dcpl); + + /* Let's add data to the source datasets and check new dimensions for VDS */ + /* We will add only one plane to the first source dataset, two planes to the + second one, three to the third, and four to the forth. */ + + for (i=0; i < PLANE_STRIDE; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < (i+1)*DIM1*DIM2; j++) wdata[j] = 10*(i+1); + + /* + * Open the source files and datasets. Appen data to each dataset and + * close all resources. + */ + + file = H5Fopen (SRC_FILE[i], H5F_ACC_RDWR, H5P_DEFAULT); + dset = H5Dopen2 (file, SRC_DATASET[i], H5P_DEFAULT); + extdims[0] = DIM0_1+i+1; + status = H5Dset_extent (dset, extdims); + src_space = H5Dget_space (dset); + start[0] = DIM0_1; + start[1] = 0; + start[2] = 0; + count[0] = 1; + count[1] = 1; + count[2] = 1; + block[0] = i+1; + block[1] = DIM1; + block[2] = DIM2; + + memdims[0] = i+1; + mem_space = H5Screate_simple(RANK, memdims, NULL); + status = H5Sselect_hyperslab (src_space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Dwrite (dset, H5T_NATIVE_INT, mem_space, src_space, H5P_DEFAULT, + wdata); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + status = H5Dclose (vdset); + status = H5Fclose (vfile); + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + vfile = H5Fopen (VFILE, H5F_ACC_RDONLY, H5P_DEFAULT); + + /* + * Open VDS using different access properties to use max or + * min extents depending on the sizes of the underlying datasets + */ + dapl = H5Pcreate (H5P_DATASET_ACCESS); + + for(i = 0; i < 2; i++) { + status = H5Pset_virtual_view (dapl, i ? H5D_VDS_LAST_AVAILABLE : H5D_VDS_FIRST_MISSING); + vdset = H5Dopen2 (vfile, DATASET, dapl); + + /* Let's get space of the VDS and its dimension; we should get 32(or 20)x10x10 */ + vspace = H5Dget_space (vdset); + H5Sget_simple_extent_dims (vspace, vdsdims_out, vdsdims_max_out); + printf ("VDS dimensions, bounds = H5D_VDS_%s: ", i ? "LAST_AVAILABLE" : "FIRST_MISSING"); + for (j=0; j<RANK; j++) + printf (" %d ", (int)vdsdims_out[j]); + printf ("\n"); + + /* Close */ + status = H5Dclose (vdset); + status = H5Sclose (vspace); + } + + status = H5Pclose (dapl); + + vdset = H5Dopen2 (vfile, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (vdset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset \n"); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if (H5Sget_select_type(src_space) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(src_space)) { + status = H5Sget_regular_hyperslab (src_space, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (vdset); + status = H5Fclose (vfile); + return 0; +} + diff --git a/examples/h5_vds-percival-unlim.c b/examples/h5_vds-percival-unlim.c new file mode 100644 index 0000000..b5f3ebd --- /dev/null +++ b/examples/h5_vds-percival-unlim.c @@ -0,0 +1,352 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Percival use case. Every fifth 10x10 plane in VDS is stored in + the corresponding 3D unlimited dataset. + There are 4 source datasets total. + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define VFILE "vds-percival-unlim.h5" +#define DATASET "VDS-Percival-unlim" +#define VDSDIM0 H5S_UNLIMITED +#define VDSDIM1 10 +#define VDSDIM2 10 + +#define DIM0 H5S_UNLIMITED +#define DIM0_1 10 /* Initial size of the datasets */ +#define DIM1 10 +#define DIM2 10 +#define RANK 3 +#define PLANE_STRIDE 4 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5", + "d.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C", + "D" +}; + +int +main (void) +{ + hid_t vfile, file, src_space, mem_space, vspace, + vdset, dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[3] = {4*DIM0_1, VDSDIM1, VDSDIM2}, + vdsdims_max[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + dims[3] = {DIM0_1, DIM1, DIM2}, + extdims[3] = {2*DIM0_1, DIM1, DIM2}, + chunk_dims[3] = {DIM0_1, DIM1, DIM2}, + dims_max[3] = {DIM0, DIM1, DIM2}, + vdsdims_out[3], + vdsdims_max_out[3], + start[3], /* Hyperslab parameters */ + stride[3], + count[3], + src_count[3], + block[3]; + hsize_t start_out[3], /* Hyperslab parameter out */ + stride_out[3], + count_out[3], + block_out[3]; + int i, j, k; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + int wdata[DIM0_1*DIM1*DIM2]; + int rdata[80][10][10]; + int a_rdata[20][10][10]; + + /* + * Create source files and datasets. This step is optional. + */ + for (i=0; i < PLANE_STRIDE; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < DIM0_1*DIM1*DIM2; j++) wdata[j] = i+1; + + /* + * Create the source files and datasets. Write data to each dataset and + * close all resources. + */ + + file = H5Fcreate (SRC_FILE[i], H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + src_space = H5Screate_simple (RANK, dims, dims_max); + dcpl = H5Pcreate(H5P_DATASET_CREATE); + status = H5Pset_chunk (dcpl, RANK, chunk_dims); + dset = H5Dcreate2 (file, SRC_DATASET[i], H5T_NATIVE_INT, src_space, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Dwrite (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + wdata); + status = H5Sclose (src_space); + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + vfile = H5Fcreate (VFILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + vspace = H5Screate_simple (RANK, vdsdims, vdsdims_max); + + /* Create dataspaces for the source dataset. */ + src_space = H5Screate_simple (RANK, dims, dims_max); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = PLANE_STRIDE; /* we will select every fifth plane in VDS */ + stride[1] = 1; + stride[2] = 1; + count[0] = H5S_UNLIMITED; + count[1] = 1; + count[2] = 1; + src_count[0] = H5S_UNLIMITED; + src_count[1] = 1; + src_count[2] = 1; + block[0] = 1; + block[1] = DIM1; + block[2] = DIM2; + + /* + * Build the mappings + * + */ + status = H5Sselect_hyperslab (src_space, H5S_SELECT_SET, start, NULL, src_count, block); + for (i=0; i < PLANE_STRIDE; i++) { + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, stride, count, block); + status = H5Pset_virtual (dcpl, vspace, SRC_FILE[i], SRC_DATASET[i], src_space); + start[0]++; + } + + H5Sselect_none(vspace); + + /* Create a virtual dataset */ + vdset = H5Dcreate2 (vfile, DATASET, H5T_NATIVE_INT, vspace, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (vspace); + status = H5Sclose (src_space); + status = H5Pclose (dcpl); + /* Let's get space of the VDS and its dimension; we should get 40x10x10 */ + vspace = H5Dget_space (vdset); + H5Sget_simple_extent_dims (vspace, vdsdims_out, vdsdims_max_out); + printf ("VDS dimensions first time \n"); + printf (" Current: "); + for (i=0; i<RANK; i++) + printf (" %d ", (int)vdsdims_out[i]); + printf ("\n"); + + /* Let's add data to the source datasets and check new dimensions for VDS */ + + for (i=0; i < PLANE_STRIDE; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < DIM0_1*DIM1*DIM2; j++) wdata[j] = 10*(i+1); + + /* + * Create the source files and datasets. Write data to each dataset and + * close all resources. + */ + + file = H5Fopen (SRC_FILE[i], H5F_ACC_RDWR, H5P_DEFAULT); + dset = H5Dopen2 (file, SRC_DATASET[i], H5P_DEFAULT); + status = H5Dset_extent (dset, extdims); + src_space = H5Dget_space (dset); + start[0] = DIM0_1; + start[1] = 0; + start[2] = 0; + count[0] = 1; + count[1] = 1; + count[2] = 1; + block[0] = DIM0_1; + block[1] = DIM1; + block[2] = DIM2; + + mem_space = H5Screate_simple(RANK, dims, NULL); + status = H5Sselect_hyperslab (src_space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Dwrite (dset, H5T_NATIVE_INT, mem_space, src_space, H5P_DEFAULT, + wdata); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + status = H5Dclose (vdset); + status = H5Fclose (vfile); + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + vfile = H5Fopen (VFILE, H5F_ACC_RDONLY, H5P_DEFAULT); + vdset = H5Dopen2 (vfile, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (vdset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset \n"); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if (H5Sget_select_type(src_space) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(src_space)) { + status = H5Sget_regular_hyperslab (src_space, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } + /* + * Read data from VDS. + */ + vspace = H5Dget_space (vdset); + H5Sget_simple_extent_dims (vspace, vdsdims_out, vdsdims_max_out); + printf ("VDS dimensions second time \n"); + printf (" Current: "); + for (i=0; i<RANK; i++) + printf (" %d ", (int)vdsdims_out[i]); + printf ("\n"); + + /* Read all VDS data */ + + //EIP We should be able to do it by using H5S_ALL instead of making selection + // or using H5Sselect_all from vspace. + start[0] = 0; + start[1] = 0; + start[2] = 0; + count[0] = 1; + count[1] = 1; + count[2] = 1; + block[0] = vdsdims_out[0]; + block[1] = vdsdims_out[1]; + block[2] = vdsdims_out[2]; + + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, NULL, count, block); + mem_space = H5Screate_simple(RANK, vdsdims_out, NULL); + status = H5Dread (vdset, H5T_NATIVE_INT, mem_space, vspace, H5P_DEFAULT, + rdata); + printf (" All data: \n"); + for (i=0; i < (int)vdsdims_out[0]; i++) { + for (j=0; j < (int)vdsdims_out[1]; j++) { + printf ("(%d, %d, 0)", i, j); + for (k=0; k < (int)vdsdims_out[2]; k++) + printf (" %d ", rdata[i][j][k]); + printf ("\n"); + } + } + /* Read VDS, but only data mapeed to dataset a.h5 */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = PLANE_STRIDE; + stride[1] = 1; + stride[2] = 1; + count[0] = 2*DIM0_1; + count[1] = 1; + count[2] = 1; + block[0] = 1; + block[1] = vdsdims_out[1]; + block[2] = vdsdims_out[2]; + dims[0] = 2*DIM0_1; + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, stride, count, block); + mem_space = H5Screate_simple(RANK, dims, NULL); + status = H5Dread (vdset, H5T_NATIVE_INT, mem_space, vspace, H5P_DEFAULT, + a_rdata); + printf (" All data: \n"); + for (i=0; i < 2*DIM0_1; i++) { + for (j=0; j < (int)vdsdims_out[1]; j++) { + printf ("(%d, %d, 0)", i, j); + for (k=0; k < (int)vdsdims_out[2]; k++) + printf (" %d ", a_rdata[i][j][k]); + printf ("\n"); + } + } + /* + * Close and release resources. + */ + status = H5Sclose(mem_space); + status = H5Pclose (dcpl); + status = H5Dclose (vdset); + status = H5Fclose (vfile); + return 0; +} + diff --git a/examples/h5_vds-percival.c b/examples/h5_vds-percival.c new file mode 100644 index 0000000..757bb69 --- /dev/null +++ b/examples/h5_vds-percival.c @@ -0,0 +1,242 @@ +/************************************************************ + + This example illustrates the concept of the virtual dataset. + Percival use case. Every fifth 10x10 plane in VDS is stored in + the corresponding 3D unlimited dataset. + EIP: For now we will use finite dimension. + There are 4 source datasets total. + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds-percival.h5" +#define DATASET "VDS-Percival" +/* later +#define VDSDIM0 H5S_UNLIMITED +*/ +#define VDSDIM0 40 +#define VDSDIM1 10 +#define VDSDIM2 10 +/* later +#define DIM0 H5S_UNLIMITED +*/ +#define DIM0 10 +#define DIM1 10 +#define DIM2 10 +#define RANK 3 +#define PLANE_STRIDE 4 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5", + "d.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C", + "D" +}; + +int +main (void) +{ + hid_t file, src_space, vspace, + dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + vdsdims_max[3] = {VDSDIM0, VDSDIM1, VDSDIM2}, + dims[3] = {DIM0, DIM1, DIM2}, + dims_max[3] = {DIM0, DIM1, DIM2}, + start[3], /* Hyperslab start parameter for VDS */ + stride[3], + count[3], + src_count[3], + block[3]; + hsize_t start_out[3], /* Hyperslab parameter out */ + stride_out[3], + count_out[3], + block_out[3]; + int i, j; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + int wdata[DIM0*DIM1*DIM2]; + + /* + * Create source files and datasets. This step is optional. + */ + for (i=0; i < PLANE_STRIDE; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < DIM0*DIM1*DIM2; j++) wdata[j] = i+1; + + /* + * Create the source files and datasets. Write data to each dataset and + * close all resources. + */ + + file = H5Fcreate (SRC_FILE[i], H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + src_space = H5Screate_simple (RANK, dims, NULL); + dset = H5Dcreate2 (file, SRC_DATASET[i], H5T_NATIVE_INT, src_space, H5P_DEFAULT, + H5P_DEFAULT, H5P_DEFAULT); + status = H5Dwrite (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + wdata); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + vspace = H5Screate_simple (RANK, vdsdims, vdsdims_max); + + /* Create dataspaces for the source dataset. */ + src_space = H5Screate_simple (RANK, dims, dims_max); + + /* Create VDS creation property */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* Initialize hyperslab values */ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = PLANE_STRIDE; /* we will select every fifth plane in VDS */ + stride[1] = 1; + stride[2] = 1; +/* later + count[0] = H5S_UNLIMITED; +*/ + count[0] = VDSDIM0/4; + count[1] = 1; + count[2] = 1; +/* later + src_count[0] = H5S_UNLIMITED; +*/ + src_count[0] = DIM0; + src_count[1] = 1; + src_count[2] = 1; + block[0] = 1; + block[1] = DIM1; + block[2] = DIM2; + + /* + * Build the mappings + * + */ + status = H5Sselect_hyperslab (src_space, H5S_SELECT_SET, start, NULL, src_count, block); + for (i=0; i < PLANE_STRIDE; i++) { + status = H5Sselect_hyperslab (vspace, H5S_SELECT_SET, start, stride, count, block); + status = H5Pset_virtual (dcpl, vspace, SRC_FILE[i], SRC_DATASET[i], src_space); + start[0]++; + } + + H5Sselect_none(vspace); + + /* Create a virtual dataset */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, vspace, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (vspace); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + /* + * Now we begin the read section of this example. + */ + + /* + * Open file and dataset using the default properties. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset \n"); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + /* Get source file name */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset */ + printf(" Selection in the source dataset \n"); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + if (H5Sget_select_type(src_space) == H5S_SEL_HYPERSLABS) { + if (H5Sis_regular_hyperslab(src_space)) { + status = H5Sget_regular_hyperslab (src_space, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1], (unsigned long long)start_out[2]); + printf(" stride = [%llu, %llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1], (unsigned long long)stride_out[2]); + printf(" count = [%llu, %llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1], (unsigned long long)count_out[2]); + printf(" block = [%llu, %llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1], (unsigned long long)block_out[2]); + } + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + return 0; +} + diff --git a/examples/h5_vds-simpleIO.c b/examples/h5_vds-simpleIO.c new file mode 100644 index 0000000..b707ae4 --- /dev/null +++ b/examples/h5_vds-simpleIO.c @@ -0,0 +1,184 @@ +/************************************************************ + + This example illustrates the concept of virtual dataset I/O + The program creates 2-dim source dataset and writes + data to it. Then it creates 2-dim virtual dataset that has + the same dimesnion sizes and maps the all elements of the + virtual dataset to all elements of the source dataset. + Then VDS is read back. + + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds-simpleIO.h5" +#define DATASET "VDS" +#define DIM1 6 +#define DIM0 4 +#define RANK 2 + +#define SRC_FILE "a.h5" +#define SRC_DATASET "/A" + + +int +main (void) +{ + hid_t file, space, src_space, vspace, dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[2] = {DIM0, DIM1}, /* Virtual dataset dimension */ + dims[2] = {DIM0, DIM1}; /* Source dataset dimensions */ + int wdata[DIM0][DIM1], /* Write buffer for source dataset */ + rdata[DIM0][DIM1], /* Read buffer for virtual dataset */ + i, j; + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + /* + * Initialize data. + */ + for (i = 0; i < DIM0; i++) + for (j = 0; j < DIM1; j++) wdata[i][j] = i+1; + + /* + * Create the source file and the dataset. Write data to the source dataset + * and close all resources. + */ + + file = H5Fcreate (SRC_FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + space = H5Screate_simple (RANK, dims, NULL); + dset = H5Dcreate2 (file, SRC_DATASET, H5T_NATIVE_INT, space, H5P_DEFAULT, + H5P_DEFAULT, H5P_DEFAULT); + status = H5Dwrite (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + wdata[0]); + status = H5Sclose (space); + status = H5Dclose (dset); + status = H5Fclose (file); + + /* Create file in which virtual dataset will be stored. */ + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + vspace = H5Screate_simple (RANK, vdsdims, NULL); + + /* Set VDS creation property. */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + + /* + * Build the mappings. + * Selections in the source datasets are H5S_ALL. + * In the virtual dataset we select the first, the second and the third rows + * and map each row to the data in the corresponding source dataset. + */ + src_space = H5Screate_simple (RANK, dims, NULL); + status = H5Pset_virtual (dcpl, vspace, SRC_FILE, SRC_DATASET, src_space); + + /* Create a virtual dataset. */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, vspace, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (vspace); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + /* + * Now we begin the read section of this example. + */ + + /* + * Open the file and virtual dataset. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find the number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset "); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + + /* Make sure it is ALL selection and then print selection. */ + if(H5Sget_select_type(vspace) == H5S_SEL_ALL) { + printf("Selection is H5S_ALL \n"); + } + /* Get source file name. */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name. */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset. */ + printf(" Selection in the source dataset "); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + + /* Make sure it is ALL selection and then print selection. */ + if(H5Sget_select_type(src_space) == H5S_SEL_ALL) { + printf("Selection is H5S_ALL \n"); + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + } + /* + * Read the data using the default properties. + */ + status = H5Dread (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + rdata[0]); + + /* + * Output the data to the screen. + */ + printf (" VDS Data:\n"); + for (i=0; i<DIM0; i++) { + printf (" ["); + for (j=0; j<DIM1; j++) + printf (" %3d", rdata[i][j]); + printf ("]\n"); + } + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + + return 0; +} + diff --git a/examples/h5_vds.c b/examples/h5_vds.c new file mode 100644 index 0000000..1e502c6 --- /dev/null +++ b/examples/h5_vds.c @@ -0,0 +1,267 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/************************************************************ + + This example illustrates the concept of virtual dataset. + The program creates three 1-dim source datasets and writes + data to them. Then it creates a 2-dim virtual dataset and + maps the first three rows of the virtual dataset to the data + in the source datasets. Elements of a row are mapped to all + elements of the corresponding source dataset. + The fourth row is not mapped and will be filled with the fill + values when virtual dataset is read back. + + The program closes all datasets, and then reopens the virtual + dataset, and finds and prints its creation properties. + Then it reads the values. + + This file is intended for use with HDF5 Library version 1.10 + + ************************************************************/ +/* EIP Add link to the picture */ + +#include "hdf5.h" +#include <stdio.h> +#include <stdlib.h> + +#define FILE "vds.h5" +#define DATASET "VDS" +#define VDSDIM1 6 +#define VDSDIM0 4 +#define DIM0 6 +#define RANK1 1 +#define RANK2 2 + +const char *SRC_FILE[] = { + "a.h5", + "b.h5", + "c.h5" +}; + +const char *SRC_DATASET[] = { + "A", + "B", + "C" +}; + +int +main (void) +{ + hid_t file, space, src_space, vspace, dset; /* Handles */ + hid_t dcpl; + herr_t status; + hsize_t vdsdims[2] = {VDSDIM0, VDSDIM1}, /* Virtual datasets dimension */ + dims[1] = {DIM0}, /* Source datasets dimensions */ + start[2], /* Hyperslab parameters */ + stride[2], + count[2], + block[2]; + hsize_t start_out[2], + stride_out[2], + count_out[2], + block_out[2]; + int wdata[DIM0], /* Write buffer for source dataset */ + rdata[VDSDIM0][VDSDIM1], /* Read buffer for virtual dataset */ + i, j, k, l; + int fill_value = -1; /* Fill value for VDS */ + H5D_layout_t layout; /* Storage layout */ + size_t num_map; /* Number of mappings */ + ssize_t len; /* Length of the string; also a return value */ + char *filename; + char *dsetname; + hsize_t nblocks; + hsize_t *buf; /* Buffer to hold hyperslab coordinates */ + + /* + * Create source files and datasets. This step is optional. + */ + for (i=0; i < 3; i++) { + /* + * Initialize data for i-th source dataset. + */ + for (j = 0; j < DIM0; j++) wdata[j] = i+1; + + /* + * Create the source files and datasets. Write data to each dataset and + * close all resources. + */ + + file = H5Fcreate (SRC_FILE[i], H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + space = H5Screate_simple (RANK1, dims, NULL); + dset = H5Dcreate2 (file, SRC_DATASET[i], H5T_NATIVE_INT, space, H5P_DEFAULT, + H5P_DEFAULT, H5P_DEFAULT); + status = H5Dwrite (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + wdata); + status = H5Sclose (space); + status = H5Dclose (dset); + status = H5Fclose (file); + } + + /* Create file in which virtual dataset will be stored. */ + file = H5Fcreate (FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + + /* Create VDS dataspace. */ + space = H5Screate_simple (RANK2, vdsdims, NULL); + + /* Set VDS creation property. */ + dcpl = H5Pcreate (H5P_DATASET_CREATE); + status = H5Pset_fill_value (dcpl, H5T_NATIVE_INT, &fill_value); + + /* Initialize hyperslab values. */ + start[0] = 0; + start[1] = 0; + count[0] = 1; + count[1] = 1; + block[0] = 1; + block[1] = VDSDIM1; + + /* + * Build the mappings. + * Selections in the source datasets are H5S_ALL. + * In the virtual dataset we select the first, the second and the third rows + * and map each row to the data in the corresponding source dataset. + */ + src_space = H5Screate_simple (RANK1, dims, NULL); + for (i = 0; i < 3; i++) { + start[0] = (hsize_t)i; + /* Select i-th row in the virtual dataset; selection in the source datasets is the same. */ + status = H5Sselect_hyperslab (space, H5S_SELECT_SET, start, NULL, count, block); + status = H5Pset_virtual (dcpl, space, SRC_FILE[i], SRC_DATASET[i], src_space); + } + + /* Create a virtual dataset. */ + dset = H5Dcreate2 (file, DATASET, H5T_NATIVE_INT, space, H5P_DEFAULT, + dcpl, H5P_DEFAULT); + status = H5Sclose (space); + status = H5Sclose (src_space); + status = H5Dclose (dset); + status = H5Fclose (file); + + /* + * Now we begin the read section of this example. + */ + + /* + * Open the file and virtual dataset. + */ + file = H5Fopen (FILE, H5F_ACC_RDONLY, H5P_DEFAULT); + dset = H5Dopen2 (file, DATASET, H5P_DEFAULT); + + /* + * Get creation property list and mapping properties. + */ + dcpl = H5Dget_create_plist (dset); + + /* + * Get storage layout. + */ + layout = H5Pget_layout (dcpl); + if (H5D_VIRTUAL == layout) + printf(" Dataset has a virtual layout \n"); + else + printf(" Wrong layout found \n"); + + /* + * Find the number of mappings. + */ + status = H5Pget_virtual_count (dcpl, &num_map); + printf(" Number of mappings is %lu\n", (unsigned long)num_map); + + /* + * Get mapping parameters for each mapping. + */ + for (i = 0; i < (int)num_map; i++) { + printf(" Mapping %d \n", i); + printf(" Selection in the virtual dataset "); + /* Get selection in the virttual dataset */ + vspace = H5Pget_virtual_vspace (dcpl, (size_t)i); + + /* Make sure that this is a hyperslab selection and then print information. */ + if (H5Sget_select_type(vspace) == H5S_SEL_HYPERSLABS) { + nblocks = H5Sget_select_hyper_nblocks (vspace); + buf = (hsize_t *)malloc(sizeof(hsize_t)*2*RANK2*nblocks); + status = H5Sget_select_hyper_blocklist (vspace, (hsize_t)0, nblocks, buf); + for (l=0; l<nblocks; l++) { + printf("("); + for (k=0; k<RANK2-1; k++) + printf("%d,", (int)buf[k]); + printf("%d ) - (", (int)buf[k]); + for (k=0; k<RANK2-1; k++) + printf("%d,", (int)buf[RANK2+k]); + printf("%d)\n", (int)buf[RANK2+k]); + } + /* We also can use new APIs to get start, stride, count and block */ + if (H5Sis_regular_hyperslab(vspace)) { + status = H5Sget_regular_hyperslab (vspace, start_out, stride_out, count_out, block_out); + printf(" start = [%llu, %llu] \n", (unsigned long long)start_out[0], (unsigned long long)start_out[1]); + printf(" stride = [%llu, %llu] \n", (unsigned long long)stride_out[0], (unsigned long long)stride_out[1]); + printf(" count = [%llu, %llu] \n", (unsigned long long)count_out[0], (unsigned long long)count_out[1]); + printf(" block = [%llu, %llu] \n", (unsigned long long)block_out[0], (unsigned long long)block_out[1]); + } + } + /* Get source file name. */ + len = H5Pget_virtual_filename (dcpl, (size_t)i, NULL, 0); + filename = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_filename (dcpl, (size_t)i, filename, len+1); + printf(" Source filename %s\n", filename); + + /* Get source dataset name. */ + len = H5Pget_virtual_dsetname (dcpl, (size_t)i, NULL, 0); + dsetname = (char *)malloc((size_t)len*sizeof(char)+1); + H5Pget_virtual_dsetname (dcpl, (size_t)i, dsetname, len+1); + printf(" Source dataset name %s\n", dsetname); + + /* Get selection in the source dataset. */ + printf(" Selection in the source dataset "); + src_space = H5Pget_virtual_srcspace (dcpl, (size_t)i); + + /* Make sure it is ALL selection and then print the coordinates. */ + if(H5Sget_select_type(src_space) == H5S_SEL_ALL) { + printf("(0) - (%d) \n", DIM0-1); + } + H5Sclose(vspace); + H5Sclose(src_space); + free(filename); + free(dsetname); + free(buf); + } + + /* + * Read the data using the default properties. + */ + status = H5Dread (dset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, + rdata[0]); + + /* + * Output the data to the screen. + */ + printf (" VDS Data:\n"); + for (i=0; i<VDSDIM0; i++) { + printf (" ["); + for (j=0; j<VDSDIM1; j++) + printf (" %3d", rdata[i][j]); + printf ("]\n"); + } + /* + * Close and release resources. + */ + status = H5Pclose (dcpl); + status = H5Dclose (dset); + status = H5Fclose (file); + + return 0; +} + diff --git a/examples/run-c-ex.sh.in b/examples/run-c-ex.sh.in index 6b5d0f7..1661344 100644 --- a/examples/run-c-ex.sh.in +++ b/examples/run-c-ex.sh.in @@ -125,7 +125,23 @@ then RunTest h5_elink_unix2win &&\ rm h5_elink_unix2win &&\ RunTest h5_shared_mesg &&\ - rm h5_shared_mesg); then + rm h5_shared_mesg &&\ + RunTest h5_vds-eiger &&\ + rm h5_vds-eiger &&\ + RunTest h5_vds-exclim &&\ + rm h5_vds-exclim &&\ + RunTest h5_vds-exc &&\ + rm h5_vds-exc &&\ + RunTest h5_vds-simpleIO &&\ + rm h5_vds-simpleIO &&\ + RunTest h5_vds-percival &&\ + rm h5_vds-percival &&\ + RunTest h5_vds-percival-unlim &&\ + rm h5_vds-percival-unlim &&\ + RunTest h5_vds-percival-unlim-maxmin&&\ + rm h5_vds-percival-unlim-maxmin &&\ + RunTest h5_vds &&\ + rm h5_vds); then EXIT_VALUE=${EXIT_SUCCESS} else EXIT_VALUE=${EXIT_FAILURE} diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index dc6ba0a..0e555c2 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -118,6 +118,7 @@ set (H5D_SRCS ${HDF5_SRC_DIR}/H5Dscatgath.c ${HDF5_SRC_DIR}/H5Dselect.c ${HDF5_SRC_DIR}/H5Dtest.c + ${HDF5_SRC_DIR}/H5Dvirtual.c ) set (H5D_HDRS @@ -323,14 +323,9 @@ hid_t H5Dopen2(hid_t loc_id, const char *name, hid_t dapl_id) { H5D_t *dset = NULL; - H5G_loc_t loc; /* Object location of group */ - H5G_loc_t dset_loc; /* Object location of dataset */ - H5G_name_t path; /* Dataset group hier. path */ - H5O_loc_t oloc; /* Dataset object location */ - H5O_type_t obj_type; /* Type of object at location */ - hbool_t loc_found = FALSE; /* Location at 'name' found */ - hid_t dxpl_id = H5AC_ind_dxpl_id; /* dxpl to use to open datset */ - hid_t ret_value; + H5G_loc_t loc; /* Object location of group */ + hid_t dxpl_id = H5AC_ind_dxpl_id; /* dxpl to use to open datset */ + hid_t ret_value; FUNC_ENTER_API(FAIL) H5TRACE3("i", "i*si", loc_id, name, dapl_id); @@ -348,41 +343,18 @@ H5Dopen2(hid_t loc_id, const char *name, hid_t dapl_id) if(TRUE != H5P_isa_class(dapl_id, H5P_DATASET_ACCESS)) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not dataset access property list") - /* Set up dataset location to fill in */ - dset_loc.oloc = &oloc; - dset_loc.path = &path; - H5G_loc_reset(&dset_loc); - - /* Find the dataset object */ - if(H5G_loc_find(&loc, name, &dset_loc, dapl_id, dxpl_id) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_NOTFOUND, FAIL, "not found") - loc_found = TRUE; - - /* Check that the object found is the correct type */ - if(H5O_obj_type(&oloc, &obj_type, dxpl_id) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get object type") - if(obj_type != H5O_TYPE_DATASET) - HGOTO_ERROR(H5E_DATASET, H5E_BADTYPE, FAIL, "not a dataset") - /* Open the dataset */ - if(NULL == (dset = H5D_open(&dset_loc, dapl_id, dxpl_id))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "can't open dataset") + if(NULL == (dset = H5D__open_name(&loc, name, dapl_id, dxpl_id))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open dataset") /* Register an atom for the dataset */ if((ret_value = H5I_register(H5I_DATASET, dset, TRUE)) < 0) HGOTO_ERROR(H5E_ATOM, H5E_CANTREGISTER, FAIL, "can't register dataset atom") done: - if(ret_value < 0) { - if(dset) { - if(H5D_close(dset) < 0) - HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release dataset") - } /* end if */ - else { - if(loc_found && H5G_loc_free(&dset_loc) < 0) - HDONE_ERROR(H5E_DATASET, H5E_CANTRELEASE, FAIL, "can't free location") - } /* end else */ - } /* end if */ + if(ret_value < 0) + if(dset && H5D_close(dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release dataset") FUNC_LEAVE_API(ret_value) } /* end H5Dopen2() */ diff --git a/src/H5Ddeprec.c b/src/H5Ddeprec.c index 3da6b95..cd2bc84 100644 --- a/src/H5Ddeprec.c +++ b/src/H5Ddeprec.c @@ -226,15 +226,10 @@ hid_t H5Dopen1(hid_t loc_id, const char *name) { H5D_t *dset = NULL; - H5G_loc_t loc; /* Object location of group */ - H5G_loc_t dset_loc; /* Object location of dataset */ - H5G_name_t path; /* Dataset group hier. path */ - H5O_loc_t oloc; /* Dataset object location */ - H5O_type_t obj_type; /* Type of object at location */ - hbool_t loc_found = FALSE; /* Location at 'name' found */ - hid_t dapl_id = H5P_DATASET_ACCESS_DEFAULT; /* dapl to use to open dataset */ - hid_t dxpl_id = H5AC_ind_dxpl_id; /* dxpl to use to open datset */ - hid_t ret_value; + H5G_loc_t loc; /* Object location of group */ + hid_t dapl_id = H5P_DATASET_ACCESS_DEFAULT; /* dapl to use to open dataset */ + hid_t dxpl_id = H5AC_ind_dxpl_id; /* dxpl to use to open datset */ + hid_t ret_value; FUNC_ENTER_API(FAIL) H5TRACE2("i", "i*s", loc_id, name); @@ -245,41 +240,18 @@ H5Dopen1(hid_t loc_id, const char *name) if(!name || !*name) HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no name") - /* Set up dataset location to fill in */ - dset_loc.oloc = &oloc; - dset_loc.path = &path; - H5G_loc_reset(&dset_loc); - - /* Find the dataset object */ - if(H5G_loc_find(&loc, name, &dset_loc, H5P_DEFAULT, dxpl_id) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_NOTFOUND, FAIL, "not found") - loc_found = TRUE; - - /* Check that the object found is the correct type */ - if(H5O_obj_type(&oloc, &obj_type, dxpl_id) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get object type") - if(obj_type != H5O_TYPE_DATASET) - HGOTO_ERROR(H5E_DATASET, H5E_BADTYPE, FAIL, "not a dataset") - /* Open the dataset */ - if(NULL == (dset = H5D_open(&dset_loc, dapl_id, dxpl_id))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "can't open dataset") + if(NULL == (dset = H5D__open_name(&loc, name, dapl_id, dxpl_id))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open dataset") /* Register an atom for the dataset */ if((ret_value = H5I_register(H5I_DATASET, dset, TRUE)) < 0) HGOTO_ERROR(H5E_ATOM, H5E_CANTREGISTER, FAIL, "can't register dataset atom") done: - if(ret_value < 0) { - if(dset != NULL) { - if(H5D_close(dset) < 0) - HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release dataset") - } /* end if */ - else { - if(loc_found && H5G_loc_free(&dset_loc) < 0) - HDONE_ERROR(H5E_SYM, H5E_CANTRELEASE, FAIL, "can't free location") - } /* end else */ - } /* end if */ + if(ret_value < 0) + if(dset && H5D_close(dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release dataset") FUNC_LEAVE_API(ret_value) } /* end H5Dopen1() */ diff --git a/src/H5Dint.c b/src/H5Dint.c index 53cd86a..97f4fc5 100644 --- a/src/H5Dint.c +++ b/src/H5Dint.c @@ -1091,7 +1091,7 @@ H5D__create(H5F_t *file, hid_t type_id, const H5S_t *space, hid_t dcpl_id, HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, NULL, "unable to initialize I/O operations") /* Create the layout information for the new dataset */ - if((new_dset->shared->layout.ops->construct)(file, new_dset) < 0) + if(new_dset->shared->layout.ops->construct && (new_dset->shared->layout.ops->construct)(file, new_dset) < 0) HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, NULL, "unable to construct layout information") /* Update the dataset's object header info. */ @@ -1144,6 +1144,69 @@ done: } /* end H5D__create() */ +/*------------------------------------------------------------------------- + * Function: H5D__open_name + * + * Purpose: Opens an existing dataset by name. + * + * Return: Success: Ptr to a new dataset. + * Failure: NULL + * + * Programmer: Neil Fortner + * Friday, March 6, 2015 + * + *------------------------------------------------------------------------- + */ +H5D_t * +H5D__open_name(const H5G_loc_t *loc, const char *name, hid_t dapl_id, + hid_t dxpl_id) +{ + H5D_t *dset = NULL; + H5G_loc_t dset_loc; /* Object location of dataset */ + H5G_name_t path; /* Dataset group hier. path */ + H5O_loc_t oloc; /* Dataset object location */ + H5O_type_t obj_type; /* Type of object at location */ + hbool_t loc_found = FALSE; /* Location at 'name' found */ + H5D_t *ret_value; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* Check args */ + HDassert(loc); + HDassert(name); + + /* Set up dataset location to fill in */ + dset_loc.oloc = &oloc; + dset_loc.path = &path; + H5G_loc_reset(&dset_loc); + + /* Find the dataset object */ + if(H5G_loc_find(loc, name, &dset_loc, dapl_id, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_NOTFOUND, NULL, "not found") + loc_found = TRUE; + + /* Check that the object found is the correct type */ + if(H5O_obj_type(&oloc, &obj_type, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, NULL, "can't get object type") + if(obj_type != H5O_TYPE_DATASET) + HGOTO_ERROR(H5E_DATASET, H5E_BADTYPE, NULL, "not a dataset") + + /* Open the dataset */ + if(NULL == (dset = H5D_open(&dset_loc, dapl_id, dxpl_id))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, NULL, "can't open dataset") + + /* Set return value */ + ret_value = dset; + +done: + if(!ret_value) + if(loc_found && H5G_loc_free(&dset_loc) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTRELEASE, NULL, "can't free location") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__open_name() */ + + /* *------------------------------------------------------------------------- * Function: H5D_open @@ -1342,6 +1405,10 @@ H5D__open_oid(H5D_t *dataset, hid_t dapl_id, hid_t dxpl_id) fill_prop->alloc_time = H5D_ALLOC_TIME_INCR; break; + case H5D_VIRTUAL: + fill_prop->alloc_time = H5D_ALLOC_TIME_INCR; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1356,7 +1423,8 @@ H5D__open_oid(H5D_t *dataset, hid_t dapl_id, hid_t dxpl_id) alloc_time_state = 0; if((dataset->shared->layout.type == H5D_COMPACT && fill_prop->alloc_time == H5D_ALLOC_TIME_EARLY) || (dataset->shared->layout.type == H5D_CONTIGUOUS && fill_prop->alloc_time == H5D_ALLOC_TIME_LATE) - || (dataset->shared->layout.type == H5D_CHUNKED && fill_prop->alloc_time == H5D_ALLOC_TIME_INCR)) + || (dataset->shared->layout.type == H5D_CHUNKED && fill_prop->alloc_time == H5D_ALLOC_TIME_INCR) + || (dataset->shared->layout.type == H5D_VIRTUAL && fill_prop->alloc_time == H5D_ALLOC_TIME_INCR)) alloc_time_state = 1; /* Set revised fill value properties, if they are different from the defaults */ @@ -1486,6 +1554,34 @@ H5D_close(H5D_t *dataset) dataset->shared->layout.storage.u.compact.buf = H5MM_xfree(dataset->shared->layout.storage.u.compact.buf); break; + case H5D_VIRTUAL: + { + size_t i, j; + + HDassert(dataset->shared->layout.storage.u.virt.list || (dataset->shared->layout.storage.u.virt.list_nused == 0)); + + /* Close source datasets */ + for(i = 0; i < dataset->shared->layout.storage.u.virt.list_nused; i++) { + /* Close source dataset */ + if(dataset->shared->layout.storage.u.virt.list[i].source_dset.dset) { + HDassert(dataset->shared->layout.storage.u.virt.list[i].source_dset.dset != dataset); + if(H5D_close(dataset->shared->layout.storage.u.virt.list[i].source_dset.dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to close source dataset") + dataset->shared->layout.storage.u.virt.list[i].source_dset.dset = NULL; + } /* end if */ + + /* Close sub datasets */ + for(j = 0; j < dataset->shared->layout.storage.u.virt.list[i].sub_dset_nused; j++) + if(dataset->shared->layout.storage.u.virt.list[i].sub_dset[j].dset) { + HDassert(dataset->shared->layout.storage.u.virt.list[i].sub_dset[j].dset != dataset); + if(H5D_close(dataset->shared->layout.storage.u.virt.list[i].sub_dset[j].dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to close source dataset") + dataset->shared->layout.storage.u.virt.list[i].sub_dset[j].dset = NULL; + } /* end if */ + } /* end for */ + } /* end block */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1495,13 +1591,6 @@ H5D_close(H5D_t *dataset) #endif /* NDEBUG */ } /* end switch */ /*lint !e788 All appropriate cases are covered */ - /* - * Release datatype, dataspace and creation property list -- there isn't - * much we can do if one of these fails, so we just continue. - */ - free_failed = (unsigned)(H5I_dec_ref(dataset->shared->type_id) < 0 || H5S_close(dataset->shared->space) < 0 || - H5I_dec_ref(dataset->shared->dcpl_id) < 0); - /* Remove the dataset from the list of opened objects in the file */ if(H5FO_top_decr(dataset->oloc.file, dataset->oloc.addr) < 0) HGOTO_ERROR(H5E_DATASET, H5E_CANTRELEASE, FAIL, "can't decrement count for object") @@ -1514,6 +1603,13 @@ H5D_close(H5D_t *dataset) HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release object header") /* + * Release datatype, dataspace and creation property list -- there isn't + * much we can do if one of these fails, so we just continue. + */ + free_failed = (unsigned)(H5I_dec_ref(dataset->shared->type_id) < 0 || H5S_close(dataset->shared->space) < 0 || + H5I_dec_ref(dataset->shared->dcpl_id) < 0); + + /* * Free memory. Before freeing the memory set the file pointer to NULL. * We always check for a null file pointer in other H5D functions to be * sure we're not accessing an already freed dataset (see the HDassert() @@ -1730,6 +1826,15 @@ H5D__alloc_storage(const H5D_t *dset, hid_t dxpl_id, H5D_time_alloc_t time_alloc } /* end if */ break; + case H5D_VIRTUAL: + /* No-op, as the raw data is stored elsewhere and the global + * heap object containing the mapping information is created + * when the layout message is encoded. We may wish to move the + * creation of the global heap object here at some point, but we + * will have to make sure is it always created before the + * dataset is closed. */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1849,6 +1954,9 @@ H5D__init_storage(const H5D_t *dset, hbool_t full_overwrite, hsize_t old_dim[], break; } /* end block */ + case H5D_VIRTUAL: + /* No-op, as the raw data is stored elsewhere */ + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1905,6 +2013,12 @@ H5D__get_storage_size(H5D_t *dset, hid_t dxpl_id, hsize_t *storage_size) *storage_size = dset->shared->layout.storage.u.compact.size; break; + case H5D_VIRTUAL: + /* Just set to 0, as virtual datasets do not actually store raw data + */ + *storage_size = 0; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1941,6 +2055,7 @@ H5D__get_offset(const H5D_t *dset) HDassert(dset); switch(dset->shared->layout.type) { + case H5D_VIRTUAL: case H5D_CHUNKED: case H5D_COMPACT: break; @@ -2206,6 +2321,7 @@ H5D__set_extent(H5D_t *dset, const hsize_t *size, hid_t dxpl_id) { hsize_t curr_dims[H5S_MAX_RANK]; /* Current dimension sizes */ htri_t changed; /* Whether the dataspace changed size */ + size_t u, v; /* Local index variable */ herr_t ret_value = SUCCEED; /* Return value */ FUNC_ENTER_PACKAGE_TAG(dxpl_id, dset->oloc.addr, FAIL) @@ -2241,10 +2357,9 @@ H5D__set_extent(H5D_t *dset, const hsize_t *size, hid_t dxpl_id) hbool_t shrink = FALSE; /* Flag to indicate a dimension has shrank */ hbool_t expand = FALSE; /* Flag to indicate a dimension has grown */ hbool_t update_chunks = FALSE; /* Flag to indicate chunk cache update is needed */ - unsigned u; /* Local index variable */ /* Determine if we are shrinking and/or expanding any dimensions */ - for(u = 0; u < dset->shared->ndims; u++) { + for(u = 0; u < (size_t)dset->shared->ndims; u++) { /* Check for various status changes */ if(size[u] < curr_dims[u]) shrink = TRUE; @@ -2305,6 +2420,30 @@ H5D__set_extent(H5D_t *dset, const hsize_t *size, hid_t dxpl_id) HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "unable to update cached chunk indices") } /* end if */ + /* Operations for virtual datasets */ + if(H5D_VIRTUAL == dset->shared->layout.type) { + /* Check that the dimensions of the VDS are large enough */ + if(H5D_virtual_check_min_dims(dset) < 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "virtual dataset dimensions not large enough to contain all limited dimensions in all selections") + + /* Patch the virtual selection dataspaces */ + for(u = 0; u < dset->shared->layout.storage.u.virt.list_nused; u++) { + /* Patch extent */ + if(H5S_set_extent(dset->shared->layout.storage.u.virt.list[u].source_dset.virtual_select, size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + dset->shared->layout.storage.u.virt.list[u].virtual_space_status = H5O_VIRTUAL_STATUS_CORRECT; + + /* Patch sub-source datasets */ + for(v = 0; v < dset->shared->layout.storage.u.virt.list[u].sub_dset_nalloc; v++) + if(H5S_set_extent(dset->shared->layout.storage.u.virt.list[u].sub_dset[v].virtual_select, size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + } /* end for */ + + /* Mark virtual datasets as not fully initialized so internal + * selections are recalculated (at next I/O operation) */ + dset->shared->layout.storage.u.virt.init = FALSE; + } /* end if */ + /* Allocate space for the new parts of the dataset, if appropriate */ if(expand && dset->shared->dcpl_cache.fill.alloc_time == H5D_ALLOC_TIME_EARLY) if(H5D__alloc_storage(dset, dxpl_id, H5D_ALLOC_EXTEND, FALSE, curr_dims) < 0) @@ -2748,6 +2887,11 @@ H5D_get_space(H5D_t *dset) FUNC_ENTER_NOAPI_NOINIT + /* If the layout is virtual, update the extent */ + if(dset->shared->layout.type == H5D_VIRTUAL) + if(H5D__virtual_set_extent_unlim(dset, H5AC_ind_dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to update virtual dataset extent") + /* Read the data space message and return a data space object */ if(NULL == (space = H5S_copy(dset->shared->space, FALSE, TRUE))) HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to get data space") @@ -2815,3 +2959,4 @@ done: FUNC_LEAVE_NOAPI(ret_value) } /* end H5D_get_type() */ + diff --git a/src/H5Dio.c b/src/H5Dio.c index f9e8f37..3126b92 100644 --- a/src/H5Dio.c +++ b/src/H5Dio.c @@ -52,9 +52,6 @@ /********************/ /* Internal I/O routines */ -static herr_t H5D__write(H5D_t *dataset, hid_t mem_type_id, - const H5S_t *mem_space, const H5S_t *file_space, hid_t dset_xfer_plist, - const void *buf); static herr_t H5D__pre_write(H5D_t *dset, hbool_t direct_write, hid_t mem_type_id, const H5S_t *mem_space, const H5S_t *file_space, hid_t dxpl_id, const void *buf); @@ -581,7 +578,7 @@ done: * *------------------------------------------------------------------------- */ -static herr_t +herr_t H5D__write(H5D_t *dataset, hid_t mem_type_id, const H5S_t *mem_space, const H5S_t *file_space, hid_t dxpl_id, const void *buf) { @@ -614,7 +611,7 @@ H5D__write(H5D_t *dataset, hid_t mem_type_id, const H5S_t *mem_space, char fake_char; /* Temporary variable for NULL buffer pointers */ herr_t ret_value = SUCCEED; /* Return value */ - FUNC_ENTER_STATIC_TAG(dxpl_id, dataset->oloc.addr, FAIL) + FUNC_ENTER_PACKAGE_TAG(dxpl_id, dataset->oloc.addr, FAIL) /* check args */ HDassert(dataset && dataset->oloc.file); diff --git a/src/H5Dlayout.c b/src/H5Dlayout.c index 01898f2..85882fe 100644 --- a/src/H5Dlayout.c +++ b/src/H5Dlayout.c @@ -104,6 +104,10 @@ H5D__layout_set_io_ops(const H5D_t *dataset) dataset->shared->layout.ops = H5D_LOPS_COMPACT; break; + case H5D_VIRTUAL: + dataset->shared->layout.ops = H5D_LOPS_VIRTUAL; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -169,6 +173,11 @@ H5D__layout_meta_size(const H5F_t *f, const H5O_layout_t *layout, hbool_t includ ret_value += H5F_SIZEOF_ADDR(f); /* Address of data */ break; + case H5D_VIRTUAL: + ret_value += H5F_SIZEOF_ADDR(f); /* Address of global heap */ + ret_value += 4; /* Global heap index */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -382,68 +391,55 @@ H5D__layout_oh_read(H5D_t *dataset, hid_t dxpl_id, hid_t dapl_id, H5P_genplist_t if(H5D_CHUNKED == dataset->shared->layout.type) dataset->shared->layout.u.chunk.ndims++; - switch(dataset->shared->layout.type) { - case H5D_CONTIGUOUS: - { - hsize_t tmp_size; /* Temporary holder for raw data size */ - size_t tmp_sieve_buf_size; /* Temporary holder for sieve buffer size */ - - /* Compute the size of the contiguous storage for versions of the - * layout message less than version 3 because versions 1 & 2 would - * truncate the dimension sizes to 32-bits of information. - QAK 5/26/04 - */ - if(dataset->shared->layout.version < 3) { - hssize_t snelmts; /* Temporary holder for number of elements in dataspace */ - hsize_t nelmts; /* Number of elements in dataspace */ - size_t dt_size; /* Size of datatype */ - - /* Retrieve the number of elements in the dataspace */ - if((snelmts = H5S_GET_EXTENT_NPOINTS(dataset->shared->space)) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to retrieve number of elements in dataspace") - nelmts = (hsize_t)snelmts; - - /* Get the datatype's size */ - if(0 == (dt_size = H5T_GET_SIZE(dataset->shared->type))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to retrieve size of datatype") - - /* Compute the size of the dataset's contiguous storage */ - tmp_size = nelmts * dt_size; - - /* Check for overflow during multiplication */ - if(nelmts != (tmp_size / dt_size)) - HGOTO_ERROR(H5E_DATASET, H5E_OVERFLOW, FAIL, "size of dataset's storage overflowed") - - /* Assign the dataset's contiguous storage size */ - dataset->shared->layout.storage.u.contig.size = tmp_size; - } else - tmp_size = dataset->shared->layout.storage.u.contig.size; - - /* Get the sieve buffer size for the file */ - tmp_sieve_buf_size = H5F_SIEVE_BUF_SIZE(dataset->oloc.file); - - /* Adjust the sieve buffer size to the smaller one between the dataset size and the buffer size - * from the file access property. (SLU - 2012/3/30) */ - if(tmp_size < tmp_sieve_buf_size) - dataset->shared->cache.contig.sieve_buf_size = tmp_size; - else - dataset->shared->cache.contig.sieve_buf_size = tmp_sieve_buf_size; - } - break; - - case H5D_CHUNKED: - /* Initialize the chunk cache for the dataset */ - if(H5D__chunk_init(dataset->oloc.file, dxpl_id, dataset, dapl_id) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "can't initialize chunk cache") - break; - - case H5D_COMPACT: - break; + if(H5D_CONTIGUOUS == dataset->shared->layout.type) { + hsize_t tmp_size; /* Temporary holder for raw data size */ + size_t tmp_sieve_buf_size; /* Temporary holder for sieve buffer size */ + + /* Compute the size of the contiguous storage for versions of the + * layout message less than version 3 because versions 1 & 2 would + * truncate the dimension sizes to 32-bits of information. - QAK 5/26/04 + */ + if(dataset->shared->layout.version < 3) { + hssize_t snelmts; /* Temporary holder for number of elements in dataspace */ + hsize_t nelmts; /* Number of elements in dataspace */ + size_t dt_size; /* Size of datatype */ + + /* Retrieve the number of elements in the dataspace */ + if((snelmts = H5S_GET_EXTENT_NPOINTS(dataset->shared->space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to retrieve number of elements in dataspace") + nelmts = (hsize_t)snelmts; + + /* Get the datatype's size */ + if(0 == (dt_size = H5T_GET_SIZE(dataset->shared->type))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to retrieve size of datatype") + + /* Compute the size of the dataset's contiguous storage */ + tmp_size = nelmts * dt_size; + + /* Check for overflow during multiplication */ + if(nelmts != (tmp_size / dt_size)) + HGOTO_ERROR(H5E_DATASET, H5E_OVERFLOW, FAIL, "size of dataset's storage overflowed") + + /* Assign the dataset's contiguous storage size */ + dataset->shared->layout.storage.u.contig.size = tmp_size; + } /* end if */ + else + tmp_size = dataset->shared->layout.storage.u.contig.size; + + /* Get the sieve buffer size for the file */ + tmp_sieve_buf_size = H5F_SIEVE_BUF_SIZE(dataset->oloc.file); + + /* Adjust the sieve buffer size to the smaller one between the dataset size and the buffer size + * from the file access property. (SLU - 2012/3/30) */ + if(tmp_size < tmp_sieve_buf_size) + dataset->shared->cache.contig.sieve_buf_size = tmp_size; + else + dataset->shared->cache.contig.sieve_buf_size = tmp_sieve_buf_size; + } /* end if */ - case H5D_LAYOUT_ERROR: - case H5D_NLAYOUTS: - default: - HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "unknown storage method") - } /* end switch */ /*lint !e788 All appropriate cases are covered */ + /* Initialize the layout information for the new dataset */ + if(dataset->shared->layout.ops->init && (dataset->shared->layout.ops->init)(dataset->oloc.file, dxpl_id, dataset, dapl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to initialize layout information") done: FUNC_LEAVE_NOAPI(ret_value) diff --git a/src/H5Doh.c b/src/H5Doh.c index abf76d0..2e52102 100644 --- a/src/H5Doh.c +++ b/src/H5Doh.c @@ -398,6 +398,17 @@ H5O__dset_bh_info(H5F_t *f, hid_t dxpl_id, H5O_t *oh, H5_ih_info_t *bh_info) if(H5D__chunk_bh_info(f, dxpl_id, &layout, &pline, &(bh_info->index_size)) < 0) HGOTO_ERROR(H5E_OHDR, H5E_CANTGET, FAIL, "can't determine chunked dataset btree info") } /* end if */ + else if(layout.type == H5D_VIRTUAL + && (layout.storage.u.virt.serial_list_hobjid.addr != HADDR_UNDEF)) { + size_t virtual_heap_size; + + /* Get size of global heap object for virtual dataset */ + if(H5HG_get_obj_size(f, dxpl_id, &(layout.storage.u.virt.serial_list_hobjid), &virtual_heap_size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get global heap size for virtual dataset mapping") + + /* Return heap size */ + bh_info->heap_size = (hsize_t)virtual_heap_size; + } /* end if */ /* Check for External File List message in the object header */ if((exists = H5O_msg_exists_oh(oh, H5O_EFL_ID)) < 0) diff --git a/src/H5Dpkg.h b/src/H5Dpkg.h index 1476229..44e119c 100644 --- a/src/H5Dpkg.h +++ b/src/H5Dpkg.h @@ -519,6 +519,7 @@ H5_DLLVAR const H5D_layout_ops_t H5D_LOPS_CONTIG[1]; H5_DLLVAR const H5D_layout_ops_t H5D_LOPS_EFL[1]; H5_DLLVAR const H5D_layout_ops_t H5D_LOPS_COMPACT[1]; H5_DLLVAR const H5D_layout_ops_t H5D_LOPS_CHUNK[1]; +H5_DLLVAR const H5D_layout_ops_t H5D_LOPS_VIRTUAL[1]; /* Chunked layout operations */ H5_DLLVAR const H5D_chunk_ops_t H5D_COPS_BTREE[1]; @@ -535,6 +536,8 @@ H5_DLL H5D_t *H5D__create(H5F_t *file, hid_t type_id, const H5S_t *space, H5_DLL H5D_t *H5D__create_named(const H5G_loc_t *loc, const char *name, hid_t type_id, const H5S_t *space, hid_t lcpl_id, hid_t dcpl_id, hid_t dapl_id, hid_t dxpl_id); +H5_DLL H5D_t *H5D__open_name(const H5G_loc_t *loc, const char *name, + hid_t dapl_id, hid_t dxpl_id); H5_DLL herr_t H5D__get_space_status(H5D_t *dset, H5D_space_status_t *allocation, hid_t dxpl_id); H5_DLL herr_t H5D__alloc_storage(const H5D_t *dset, hid_t dxpl_id, H5D_time_alloc_t time_alloc, @@ -557,6 +560,9 @@ H5_DLL herr_t H5D__flush_real(H5D_t *dataset, hid_t dxpl_id); H5_DLL herr_t H5D__read(H5D_t *dataset, hid_t mem_type_id, const H5S_t *mem_space, const H5S_t *file_space, hid_t dset_xfer_plist, void *buf/*out*/); +H5_DLL herr_t H5D__write(H5D_t *dataset, hid_t mem_type_id, + const H5S_t *mem_space, const H5S_t *file_space, hid_t dset_xfer_plist, + const void *buf); /* Functions that perform direct serial I/O operations */ H5_DLL herr_t H5D__select_read(const H5D_io_info_t *io_info, @@ -605,7 +611,6 @@ H5_DLL herr_t H5D__contig_copy(H5F_t *f_src, const H5O_storage_contig_t *storage H5_DLL herr_t H5D__contig_delete(H5F_t *f, hid_t dxpl_id, const H5O_storage_t *store); - /* Functions that operate on chunked dataset storage */ H5_DLL htri_t H5D__chunk_cacheable(const H5D_io_info_t *io_info, haddr_t caddr, hbool_t write_op); @@ -652,6 +657,17 @@ H5_DLL herr_t H5D__compact_copy(H5F_t *f_src, H5O_storage_compact_t *storage_src H5F_t *f_dst, H5O_storage_compact_t *storage_dst, H5T_t *src_dtype, H5O_copy_t *cpy_info, hid_t dxpl_id); +/* Functions that operate on virtual dataset storage */ +H5_DLL herr_t H5D__virtual_copy_layout(H5O_layout_t *layout); +H5_DLL herr_t H5D__virtual_set_extent_unlim(const H5D_t *dset, hid_t dxpl_id); +H5_DLL herr_t H5D__virtual_reset_layout(H5O_layout_t *layout); +H5_DLL herr_t H5D__virtual_delete(H5F_t *f, hid_t dxpl_id, H5O_storage_t *storage); +H5_DLL herr_t H5D__virtual_copy(H5F_t *f_src, H5O_layout_t *layout_dst, + hid_t dxpl_id); +H5_DLL herr_t H5D__virtual_init(H5F_t *f, hid_t dxpl_id, const H5D_t *dset, + hid_t dapl_id); +H5_DLL hbool_t H5D__virtual_is_space_alloc(const H5O_storage_t *storage); + /* Functions that operate on EFL (External File List)*/ H5_DLL hbool_t H5D__efl_is_space_alloc(const H5O_storage_t *storage); H5_DLL herr_t H5D__efl_bh_info(H5F_t *f, hid_t dxpl_id, H5O_efl_t *efl, diff --git a/src/H5Dprivate.h b/src/H5Dprivate.h index 55e5b47..d3a23eb 100644 --- a/src/H5Dprivate.h +++ b/src/H5Dprivate.h @@ -52,6 +52,8 @@ #define H5D_ACS_DATA_CACHE_NUM_SLOTS_NAME "rdcc_nslots" /* Size of raw data chunk cache(slots) */ #define H5D_ACS_DATA_CACHE_BYTE_SIZE_NAME "rdcc_nbytes" /* Size of raw data chunk cache(bytes) */ #define H5D_ACS_PREEMPT_READ_CHUNKS_NAME "rdcc_w0" /* Preemption read chunks first */ +#define H5D_ACS_VDS_VIEW_NAME "vds_view" /* VDS view option */ +#define H5D_ACS_VDS_PRINTF_GAP_NAME "vds_printf_gap" /* VDS printf gap size */ /* ======== Data transfer properties ======== */ #define H5D_XFER_MAX_TEMP_BUF_NAME "max_temp_buf" /* Maximum temp buffer size */ @@ -106,6 +108,9 @@ #define H5D_VLEN_FREE NULL #define H5D_VLEN_FREE_INFO NULL +/* Default virtual dataset list size */ +#define H5D_VIRTUAL_DEF_LIST_SIZE 8 + /****************************/ /* Library Private Typedefs */ @@ -174,6 +179,19 @@ H5_DLL herr_t H5D_vlen_reclaim(hid_t type_id, H5S_t *space, hid_t plist_id, /* Functions that operate on chunked storage */ H5_DLL herr_t H5D_chunk_idx_reset(H5O_storage_chunk_t *storage, hbool_t reset_addr); +/* Functions that operate on virtual storage */ +H5_DLL herr_t H5D_virtual_check_mapping_pre(const H5S_t *vspace, + const H5S_t *src_space, H5O_virtual_space_status_t space_status); +H5_DLL herr_t H5D_virtual_check_mapping_post( + const H5O_storage_virtual_ent_t *ent); +H5_DLL herr_t H5D_virtual_check_min_dims(const H5D_t *dset); +H5_DLL herr_t H5D_virtual_update_min_dims(H5O_layout_t *layout, size_t idx); +H5_DLL herr_t H5D_virtual_parse_source_name(const char *source_name, + H5O_storage_virtual_name_seg_t **parsed_name, size_t *static_strlen, + size_t *nsubs); +H5_DLL void H5D_virtual_free_parsed_name( + H5O_storage_virtual_name_seg_t *name_seg); + /* Functions that operate on indexed storage */ H5_DLL herr_t H5D_btree_debug(H5F_t *f, hid_t dxpl_id, haddr_t addr, FILE * stream, int indent, int fwidth, unsigned ndims, const uint32_t *dim); diff --git a/src/H5Dpublic.h b/src/H5Dpublic.h index 1b5fed7..a1f87e3 100644 --- a/src/H5Dpublic.h +++ b/src/H5Dpublic.h @@ -51,7 +51,8 @@ typedef enum H5D_layout_t { H5D_COMPACT = 0, /*raw data is very small */ H5D_CONTIGUOUS = 1, /*the default */ H5D_CHUNKED = 2, /*slow and fancy */ - H5D_NLAYOUTS = 3 /*this one must be last! */ + H5D_VIRTUAL = 3, /*actual data is stored in other datasets */ + H5D_NLAYOUTS = 4 /*this one must be last! */ } H5D_layout_t; /* Types of chunk index data structures */ @@ -93,6 +94,13 @@ typedef enum H5D_fill_value_t { H5D_FILL_VALUE_USER_DEFINED =2 } H5D_fill_value_t; +/* Values for VDS bounds option */ +typedef enum H5D_vds_view_t { + H5D_VDS_ERROR = -1, + H5D_VDS_FIRST_MISSING = 0, + H5D_VDS_LAST_AVAILABLE = 1 +} H5D_vds_view_t; + /********************/ /* Public Variables */ /********************/ diff --git a/src/H5Dvirtual.c b/src/H5Dvirtual.c new file mode 100644 index 0000000..10e53c9 --- /dev/null +++ b/src/H5Dvirtual.c @@ -0,0 +1,2727 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by The HDF Group. * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * Programmer: Neil Fortner <nfortne2@hdfgroup.org> + * Wednesday, January 28, 2015 + * + * Purpose: + * Virtual Dataset (VDS) functions. Creates a layout type which allows + * definition of a virtual dataset, where the actual dataset is stored in + * other datasets (called source datasets). The mappings between the + * virtual and source datasets are specified by hyperslab or "all" + * dataspace selections. Point selections are not currently supported. + * Overlaps in the mappings in the virtual dataset result in undefined + * behaviour. + * + * Mapping selections may be unlimited, in which case the size of the + * virtual dataset is determined by the size of the source dataset(s). + * Names for the source datasets may also be generated procedurally, in + * which case the virtual selection should be unlimited with an unlimited + * count and the source selection should be limited with a size equal to + * that of the virtual selection with the unlimited count set to 1. + * + * Source datasets are opened lazily (only when needed for I/O or to + * determine the size of the virtual dataset), and are currently held open + * until the virtual dataset is closed. + */ + +/****************/ +/* Module Setup */ +/****************/ + +#define H5D_PACKAGE /* Suppress error about including H5Dpkg */ + + +/***********/ +/* Headers */ +/***********/ +#include "H5private.h" /* Generic Functions */ +#include "H5Dpkg.h" /* Dataset functions */ +#include "H5Eprivate.h" /* Error handling */ +#include "H5Fprivate.h" /* Files */ +#include "H5FLprivate.h" /* Free Lists */ +#include "H5Gprivate.h" /* Groups */ +#include "H5HGprivate.h" /* Global Heaps */ +#include "H5Iprivate.h" /* IDs */ +#include "H5MMprivate.h" /* Memory management */ +#include "H5Oprivate.h" /* Object headers */ +#include "H5Sprivate.h" /* Dataspaces */ + + +/****************/ +/* Local Macros */ +/****************/ + +/* Default size for sub_dset array */ +#define H5D_VIRTUAL_DEF_SUB_DSET_SIZE 128 + + +/******************/ +/* Local Typedefs */ +/******************/ + + +/********************/ +/* Local Prototypes */ +/********************/ + +/* Layout operation callbacks */ +static herr_t H5D__virtual_read(H5D_io_info_t *io_info, const H5D_type_info_t + *type_info, hsize_t nelmts, const H5S_t *file_space, const H5S_t *mem_space, + H5D_chunk_map_t *fm); +static herr_t H5D__virtual_write(H5D_io_info_t *io_info, + const H5D_type_info_t *type_info, hsize_t nelmts, const H5S_t *file_space, + const H5S_t *mem_space, H5D_chunk_map_t *fm); +static herr_t H5D__virtual_flush(H5D_t *dset, hid_t dxpl_id); + +/* Other functions */ +static herr_t H5D__virtual_open_source_dset(const H5D_t *vdset, + H5O_storage_virtual_ent_t *virtual_ent, + H5O_storage_virtual_srcdset_t *source_dset, hid_t dxpl_id); +static herr_t H5D__virtual_reset_source_dset( + H5O_storage_virtual_ent_t *virtual_ent, + H5O_storage_virtual_srcdset_t *source_dset); +static herr_t H5D__virtual_str_append(const char *src, size_t src_len, char **p, + char **buf, size_t *buf_size); +static herr_t H5D__virtual_copy_parsed_name( + H5O_storage_virtual_name_seg_t **dst, H5O_storage_virtual_name_seg_t *src); +static herr_t H5D__virtual_build_source_name(char *source_name, + const H5O_storage_virtual_name_seg_t *parsed_name, size_t static_strlen, + size_t nsubs, hsize_t blockno, char **built_name); +static herr_t H5D__virtual_init_all(const H5D_t *dset, hid_t dxpl_id); +static herr_t H5D__virtual_pre_io(H5D_io_info_t *io_info, + H5O_storage_virtual_t *storage, const H5S_t *file_space, + const H5S_t *mem_space, hsize_t *tot_nelmts); +static herr_t H5D__virtual_post_io(H5O_storage_virtual_t *storage); +static herr_t H5D__virtual_read_one(H5D_io_info_t *io_info, + const H5D_type_info_t *type_info, const H5S_t *file_space, + H5O_storage_virtual_srcdset_t *source_dset); +static herr_t H5D__virtual_write_one(H5D_io_info_t *io_info, + const H5D_type_info_t *type_info, const H5S_t *file_space, + H5O_storage_virtual_srcdset_t *source_dset); + + +/*********************/ +/* Package Variables */ +/*********************/ + +/* Contiguous storage layout I/O ops */ +const H5D_layout_ops_t H5D_LOPS_VIRTUAL[1] = {{ + NULL, + H5D__virtual_init, + H5D__virtual_is_space_alloc, + NULL, + H5D__virtual_read, + H5D__virtual_write, +#ifdef H5_HAVE_PARALLEL + NULL, + NULL, +#endif /* H5_HAVE_PARALLEL */ + NULL, + NULL, + H5D__virtual_flush, + NULL +}}; + + +/*******************/ +/* Local Variables */ +/*******************/ + +/* Declare a free list to manage the H5O_storage_virtual_name_seg_t struct */ +H5FL_DEFINE(H5O_storage_virtual_name_seg_t); + + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_check_mapping_pre + * + * Purpose: Checks that the provided virtual and source selections are + * legal for use as a VDS mapping, prior to creating the rest + * of the mapping entry. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * August 12, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_virtual_check_mapping_pre(const H5S_t *vspace, const H5S_t *src_space, + H5O_virtual_space_status_t space_status) +{ + H5S_sel_type select_type; /* Selection type */ + hsize_t nelmts_vs; /* Number of elements in virtual selection */ + hsize_t nelmts_ss; /* Number of elements in source selection */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Check for point selections (currently unsupported) */ + if(H5S_SEL_ERROR == (select_type = H5S_GET_SELECT_TYPE(vspace))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get selection type") + if(select_type == H5S_SEL_POINTS) + HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "point selections not currently supported with virtual datasets") + if(H5S_SEL_ERROR == (select_type = H5S_GET_SELECT_TYPE(src_space))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get selection type") + if(select_type == H5S_SEL_POINTS) + HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "point selections not currently supported with virtual datasets") + + /* Get number of elements in spaces */ + nelmts_vs = (hsize_t)H5S_GET_SELECT_NPOINTS(vspace); + nelmts_ss = (hsize_t)H5S_GET_SELECT_NPOINTS(src_space); + + /* Check for unlimited vspace */ + if(nelmts_vs == H5S_UNLIMITED) { + /* Check for unlimited src_space */ + if(nelmts_ss == H5S_UNLIMITED) { + hsize_t nenu_vs; /* Number of elements in the non-unlimited dimensions of vspace */ + hsize_t nenu_ss; /* Number of elements in the non-unlimited dimensions of src_space */ + + /* Non-printf unlimited selection. Make sure both selections have + * the same number of elements in the non-unlimited dimension. Note + * we can always check this even if the space status is invalid + * because unlimited selections are never dependent on the extent. + */ + if(H5S_get_select_num_elem_non_unlim(vspace, &nenu_vs) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "can't get number of elements in non-unlimited dimension") + if(H5S_get_select_num_elem_non_unlim(src_space, &nenu_ss) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "can't get number of elements in non-unlimited dimension") + if(nenu_vs != nenu_ss) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "numbers of elemnts in the non-unlimited dimensions is different for source and virtual spaces") + } /* end if */ + /* We will handle the printf case after parsing the source names */ + } /* end if */ + else if(space_status != H5O_VIRTUAL_STATUS_INVALID) + /* Limited selections. Check number of points is the same. */ + if(nelmts_vs != nelmts_ss) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "virtual and source space selections have different numbers of elements") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D_virtual_check_mapping_pre() */ + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_check_mapping_post + * + * Purpose: Checks that the provided virtual dataset mapping entry is + * legal, after the mapping is otherwise complete. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * August 12, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_virtual_check_mapping_post(const H5O_storage_virtual_ent_t *ent) +{ + hsize_t nelmts_vs; /* Number of elements in virtual selection */ + hsize_t nelmts_ss; /* Number of elements in source selection */ + H5S_t *tmp_space = NULL; /* Temporary dataspace */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Get number of elements in spaces */ + nelmts_vs = (hsize_t)H5S_GET_SELECT_NPOINTS(ent->source_dset.virtual_select); + nelmts_ss = (hsize_t)H5S_GET_SELECT_NPOINTS(ent->source_select); + + /* Check for printf selection */ + if((nelmts_vs == H5S_UNLIMITED) && (nelmts_ss != H5S_UNLIMITED)) { + /* Make sure there at least one %b substitution in the source file or + * dataset name */ + if((ent->psfn_nsubs == 0) && (ent->psdn_nsubs == 0)) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "unlimited virtual selection, limited source selection, and no printf specifiers in source names") + + /* Make sure virtual space uses hyperslab selection */ + if(H5S_GET_SELECT_TYPE(ent->source_dset.virtual_select) != H5S_SEL_HYPERSLABS) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "virtual selection with printf mapping must be hyperslab") + + /* Check that the number of elements in one block in the virtual + * selection matches the total number of elements in the source + * selection, if the source space status is not invalid (virtual space + * status does not matter here because it is unlimited) */ + if(ent->source_space_status != H5O_VIRTUAL_STATUS_INVALID) { + /* Get first block in virtual selection */ + if(NULL == (tmp_space = H5S_hyper_get_unlim_block(ent->source_dset.virtual_select, (hsize_t)0))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get first block in virtual selection") + + /* Check number of points */ + nelmts_vs = (hsize_t)H5S_GET_SELECT_NPOINTS(tmp_space); + if(nelmts_vs != nelmts_ss) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "virtual (single block) and source space selections have different numbers of elements") + } /* end if */ + } /* end if */ + else + /* Make sure there are no printf substitutions */ + if((ent->psfn_nsubs > 0) || (ent->psdn_nsubs > 0)) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "printf specifier(s) in source name(s) without an unlimited virtual selection and limited source selection") + +done: + /* Free temporary space */ + if(tmp_space) + if(H5S_close(tmp_space) < 0) + HDONE_ERROR(H5E_PLIST, H5E_CLOSEERROR, FAIL, "can't close dataspace") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D_virtual_check_mapping_post() */ + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_update_min_dims + * + * Purpose: Updates the virtual layout's "min_dims" field to take into + * account the "idx"th entry in the mapping list. The entry + * must be complete, though top level field list_nused (and + * of course min_dims) does not need to take it into account. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 10, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_virtual_update_min_dims(H5O_layout_t *layout, size_t idx) +{ + H5S_sel_type sel_type; + int rank; + hsize_t bounds_start[H5S_MAX_RANK]; + hsize_t bounds_end[H5S_MAX_RANK]; + int i; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_NOAPI(FAIL) + + HDassert(layout); + HDassert(layout->type == H5D_VIRTUAL); + HDassert(idx < layout->storage.u.virt.list_nalloc); + + /* Get type of selection */ + if(H5S_SEL_ERROR == (sel_type = H5S_GET_SELECT_TYPE(layout->storage.u.virt.list[idx].source_dset.virtual_select))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection type") + + /* Do not update min_dims for "all" or "none" selections */ + if((sel_type == H5S_SEL_ALL) || (sel_type == H5S_SEL_NONE)) + HGOTO_DONE(SUCCEED) + + /* Get rank of vspace */ + if((rank = H5S_GET_EXTENT_NDIMS(layout->storage.u.virt.list[idx].source_dset.virtual_select)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get number of dimensions") + + /* Get selection bounds */ + if(H5S_SELECT_BOUNDS(layout->storage.u.virt.list[idx].source_dset.virtual_select, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection bounds") + + /* Update min_dims */ + for(i = 0; i < rank; i++) + /* Don't check unlimited dimensions in the selection */ + if((i != layout->storage.u.virt.list[idx].unlim_dim_virtual) + && (bounds_end[i] >= layout->storage.u.virt.min_dims[i])) + layout->storage.u.virt.min_dims[i] = bounds_end[i] + (hsize_t)1; + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D_virtual_update_min_dims() */ + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_check_min_dims + * + * Purpose: Checks if the dataset's dimensions are at least the + * calculated minimum dimensions from the mappings. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * August 13, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_virtual_check_min_dims(const H5D_t *dset) +{ + int rank; + hsize_t dims[H5S_MAX_RANK]; + int i; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_NOAPI(FAIL) + + HDassert(dset); + HDassert(dset->shared); + HDassert(dset->shared->layout.type == H5D_VIRTUAL); + + /* Get rank of dataspace */ + if((rank = H5S_GET_EXTENT_NDIMS(dset->shared->space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get number of dimensions") + + /* Get VDS dimensions */ + if(H5S_get_simple_extent_dims(dset->shared->space, dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get VDS dimensions") + + /* Verify that dimensions are larger than min_dims */ + for(i = 0; i < rank; i++) + if(dims[i] < dset->shared->layout.storage.u.virt.min_dims[i]) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "virtual dataset dimensions not large enough to contain all limited dimensions in all selections") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D_virtual_check_min_dims() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_copy_layout + * + * Purpose: Deep copies virtual storage layout message in memory. + * This function assumes that the top-level struct has + * already been copied (so the source struct retains + * ownership of the fields passed to this function). + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 10, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_copy_layout(H5O_layout_t *layout) +{ + H5O_storage_virtual_ent_t *orig_list = NULL; + hid_t orig_source_fapl; + hid_t orig_source_dapl; + H5P_genplist_t *plist; + size_t i; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_PACKAGE + + HDassert(layout); + HDassert(layout->type == H5D_VIRTUAL); + + /* Save original entry list and top-level property lists and reset in layout + * so the originals aren't closed on error */ + orig_source_fapl = layout->storage.u.virt.source_fapl; + layout->storage.u.virt.source_fapl = -1; + orig_source_dapl = layout->storage.u.virt.source_dapl; + layout->storage.u.virt.source_dapl = -1; + orig_list = layout->storage.u.virt.list; + layout->storage.u.virt.list = NULL; + + /* Copy entry list */ + if(layout->storage.u.virt.list_nused > 0) { + HDassert(orig_list); + + /* Allocate memory for the list */ + if(NULL == (layout->storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_calloc(layout->storage.u.virt.list_nused * sizeof(H5O_storage_virtual_ent_t)))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTALLOC, FAIL, "unable to allocate memory for virtual dataset entry list") + layout->storage.u.virt.list_nalloc = layout->storage.u.virt.list_nused; + + /* Copy the list entries, though set source_dset.dset and sub_dset to + * NULL */ + for(i = 0; i < layout->storage.u.virt.list_nused; i++) { + /* Copy virtual selection */ + if(NULL == (layout->storage.u.virt.list[i].source_dset.virtual_select + = H5S_copy(orig_list[i].source_dset.virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Copy original source names */ + if(NULL == (layout->storage.u.virt.list[i].source_file_name + = HDstrdup(orig_list[i].source_file_name))) + HGOTO_ERROR(H5E_DATASET, H5E_RESOURCE, FAIL, "unable to duplicate source file name") + if(NULL == (layout->storage.u.virt.list[i].source_dset_name + = HDstrdup(orig_list[i].source_dset_name))) + HGOTO_ERROR(H5E_DATASET, H5E_RESOURCE, FAIL, "unable to duplicate source dataset name") + + /* Copy source selection */ + if(NULL == (layout->storage.u.virt.list[i].source_select + = H5S_copy(orig_list[i].source_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy source selection") + + /* Initialize clipped selections */ + if(orig_list[i].unlim_dim_virtual < 0) { + layout->storage.u.virt.list[i].source_dset.clipped_source_select = layout->storage.u.virt.list[i].source_select; + layout->storage.u.virt.list[i].source_dset.clipped_virtual_select = layout->storage.u.virt.list[i].source_dset.virtual_select; + } /* end if */ + + /* Copy parsed names */ + if(H5D__virtual_copy_parsed_name(&layout->storage.u.virt.list[i].parsed_source_file_name, orig_list[i].parsed_source_file_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy parsed source file name") + layout->storage.u.virt.list[i].psfn_static_strlen = orig_list[i].psfn_static_strlen; + layout->storage.u.virt.list[i].psfn_nsubs = orig_list[i].psfn_nsubs; + if(H5D__virtual_copy_parsed_name(&layout->storage.u.virt.list[i].parsed_source_dset_name, orig_list[i].parsed_source_dset_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy parsed source dataset name") + layout->storage.u.virt.list[i].psdn_static_strlen = orig_list[i].psdn_static_strlen; + layout->storage.u.virt.list[i].psdn_nsubs = orig_list[i].psdn_nsubs; + + /* Copy source names in source dset or add reference as appropriate + */ + if(orig_list[i].source_dset.file_name) { + if(orig_list[i].source_dset.file_name + == orig_list[i].source_file_name) + layout->storage.u.virt.list[i].source_dset.file_name = layout->storage.u.virt.list[i].source_file_name; + else if(orig_list[i].parsed_source_file_name + && (orig_list[i].source_dset.file_name + != orig_list[i].parsed_source_file_name->name_segment)) { + HDassert(layout->storage.u.virt.list[i].parsed_source_file_name); + HDassert(layout->storage.u.virt.list[i].parsed_source_file_name->name_segment); + layout->storage.u.virt.list[i].source_dset.file_name = layout->storage.u.virt.list[i].parsed_source_file_name->name_segment; + } /* end if */ + else + if(NULL == (layout->storage.u.virt.list[i].source_dset.file_name + = HDstrdup(orig_list[i].source_dset.file_name))) + HGOTO_ERROR(H5E_DATASET, H5E_RESOURCE, FAIL, "unable to duplicate source file name") + } /* end if */ + if(orig_list[i].source_dset.dset_name) { + if(orig_list[i].source_dset.dset_name + == orig_list[i].source_dset_name) + layout->storage.u.virt.list[i].source_dset.dset_name = layout->storage.u.virt.list[i].source_dset_name; + else if(orig_list[i].parsed_source_dset_name + && (orig_list[i].source_dset.dset_name + != orig_list[i].parsed_source_dset_name->name_segment)) { + HDassert(layout->storage.u.virt.list[i].parsed_source_dset_name); + HDassert(layout->storage.u.virt.list[i].parsed_source_dset_name->name_segment); + layout->storage.u.virt.list[i].source_dset.dset_name = layout->storage.u.virt.list[i].parsed_source_dset_name->name_segment; + } /* end if */ + else + if(NULL == (layout->storage.u.virt.list[i].source_dset.dset_name + = HDstrdup(orig_list[i].source_dset.dset_name))) + HGOTO_ERROR(H5E_DATASET, H5E_RESOURCE, FAIL, "unable to duplicate source dataset name") + } /* end if */ + + /* Copy other fields in entry */ + layout->storage.u.virt.list[i].unlim_dim_source = orig_list[i].unlim_dim_source; + layout->storage.u.virt.list[i].unlim_dim_virtual = orig_list[i].unlim_dim_virtual; + layout->storage.u.virt.list[i].unlim_extent_source = orig_list[i].unlim_extent_source; + layout->storage.u.virt.list[i].unlim_extent_virtual = orig_list[i].unlim_extent_virtual; + layout->storage.u.virt.list[i].clip_size_source = orig_list[i].clip_size_source; + layout->storage.u.virt.list[i].clip_size_virtual = orig_list[i].clip_size_virtual; + layout->storage.u.virt.list[i].source_space_status = orig_list[i].source_space_status; + layout->storage.u.virt.list[i].virtual_space_status = orig_list[i].virtual_space_status; + } /* end for */ + } /* end if */ + else { + /* Zero out other fields related to list, just to be sure */ + layout->storage.u.virt.list = NULL; + layout->storage.u.virt.list_nalloc = 0; + } /* end else */ + + /* Copy property lists */ + if(orig_source_fapl >= 0) { + if(NULL == (plist = (H5P_genplist_t *)H5I_object_verify(orig_source_fapl, H5I_GENPROP_LST))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a property list") + if((layout->storage.u.virt.source_fapl = H5P_copy_plist(plist, FALSE)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy fapl") + } /* end if */ + if(orig_source_dapl >= 0) { + if(NULL == (plist = (H5P_genplist_t *)H5I_object_verify(orig_source_dapl, H5I_GENPROP_LST))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a property list") + if((layout->storage.u.virt.source_dapl = H5P_copy_plist(plist, FALSE)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy dapl") + } /* end if */ + + /* New layout is not fully initialized */ + layout->storage.u.virt.init = FALSE; + +done: + /* Release allocated resources on failure */ + if(ret_value < 0) + if(H5D__virtual_reset_layout(layout) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "unable to reset virtual layout") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_copy_layout() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_reset_layout + * + * Purpose: Frees internal structures in a virtual storage layout + * message in memory. This function is safe to use on + * incomplete structures (for recovery from failure) provided + * the internal structures are initialized with all bytes set + * to 0. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 11, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_reset_layout(H5O_layout_t *layout) +{ + size_t i, j; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_PACKAGE + + HDassert(layout); + HDassert(layout->type == H5D_VIRTUAL); + + /* Free the list entries. Note we always attempt to free everything even in + * the case of a failure. Because of this, and because we free the list + * afterwards, we do not need to zero out the memory in the list. */ + for(i = 0; i < layout->storage.u.virt.list_nused; i++) { + /* Free source_dset */ + if(H5D__virtual_reset_source_dset(&layout->storage.u.virt.list[i], &layout->storage.u.virt.list[i].source_dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "unable to reset source dataset") + + /* Free original source names */ + (void)H5MM_xfree(layout->storage.u.virt.list[i].source_file_name); + (void)H5MM_xfree(layout->storage.u.virt.list[i].source_dset_name); + + /* Free sub_dset */ + for(j = 0; j < layout->storage.u.virt.list[i].sub_dset_nalloc; j++) + if(H5D__virtual_reset_source_dset(&layout->storage.u.virt.list[i], &layout->storage.u.virt.list[i].sub_dset[j]) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "unable to reset source dataset") + layout->storage.u.virt.list[i].sub_dset = (H5O_storage_virtual_srcdset_t *)H5MM_xfree(layout->storage.u.virt.list[i].sub_dset); + + /* Free source_select */ + if(layout->storage.u.virt.list[i].source_select) + if(H5S_close(layout->storage.u.virt.list[i].source_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release source selection") + + /* Free parsed_source_file_name */ + H5D_virtual_free_parsed_name(layout->storage.u.virt.list[i].parsed_source_file_name); + + /* Free parsed_source_dset_name */ + H5D_virtual_free_parsed_name(layout->storage.u.virt.list[i].parsed_source_dset_name); + } /* end for */ + + /* Free the list */ + layout->storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_xfree(layout->storage.u.virt.list); + layout->storage.u.virt.list_nalloc = (size_t)0; + layout->storage.u.virt.list_nused = (size_t)0; + (void)HDmemset(layout->storage.u.virt.min_dims, 0, sizeof(layout->storage.u.virt.min_dims)); + + /* Close access property lists */ + if(layout->storage.u.virt.source_fapl >= 0) + if(H5I_dec_ref(layout->storage.u.virt.source_fapl) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "can't close source fapl") + if(layout->storage.u.virt.source_dapl >= 0) + if(H5I_dec_ref(layout->storage.u.virt.source_dapl) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "can't close source dapl") + + /* The list is no longer initialized */ + layout->storage.u.virt.init = FALSE; + + /* Note the lack of a done: label. This is because there are no HGOTO_ERROR + * calls. If one is added, a done: label must also be added */ + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_reset_layout() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_copy + * + * Purpose: Copy virtual storage raw data from SRC file to DST file. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_copy(H5F_t H5_ATTR_UNUSED *f_dst, H5O_layout_t *layout_dst, + hid_t H5_ATTR_UNUSED dxpl_id) +{ + herr_t ret_value = SUCCEED; + + FUNC_ENTER_PACKAGE + + /* Copy message in memory */ + if(H5D__virtual_copy_layout(layout_dst) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual layout") + +#ifdef NOT_YET + /* Check for copy to the same file */ + if(f_dst == f_src) { + /* Increase reference count on global heap object */ + if((heap_rc = H5HG_link(f_dst, dxpl_id, (H5HG_t *)&(layout_dst->u.virt.serial_list_hobjid), 1)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTMODIFY, FAIL, "unable to adjust global heap refence count") + } /* end if */ + else +#endif /* NOT_YET */ + { + /* Reset global heap id so a new heap object is created when the message + * is flushed */ + layout_dst->storage.u.virt.serial_list_hobjid.addr = HADDR_UNDEF; + layout_dst->storage.u.virt.serial_list_hobjid.idx = (size_t)0; + } /* end block/else */ + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_copy() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_delete + * + * Purpose: Delete the file space for a virtual dataset + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_delete(H5F_t *f, hid_t dxpl_id, H5O_storage_t *storage) +{ +#ifdef NOT_YET + int heap_rc; /* Reference count of global heap object */ +#endif /* NOT_YET */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* check args */ + HDassert(f); + HDassert(storage); + HDassert(storage->type == H5D_VIRTUAL); + + /* Check for global heap block */ + if(storage->u.virt.serial_list_hobjid.addr != HADDR_UNDEF) { +#ifdef NOT_YET + /* Unlink the global heap block */ + if((heap_rc = H5HG_link(f, dxpl_id, (H5HG_t *)&(storage->u.virt.serial_list_hobjid), -1)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTMODIFY, FAIL, "unable to adjust global heap refence count") + if(heap_rc == 0) +#endif /* NOT_YET */ + /* Delete the global heap block */ + if(H5HG_remove(f, dxpl_id, (H5HG_t *)&(storage->u.virt.serial_list_hobjid)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTREMOVE, FAIL, "unable to remove heap object") + } /* end if */ + + /* Clear global heap ID in storage */ + storage->u.virt.serial_list_hobjid.addr = HADDR_UNDEF; + storage->u.virt.serial_list_hobjid.idx = 0; + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_delete */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_open_source_dset + * + * Purpose: Attempts to open a source dataset. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * March 6, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_open_source_dset(const H5D_t *vdset, + H5O_storage_virtual_ent_t *virtual_ent, + H5O_storage_virtual_srcdset_t *source_dset, hid_t dxpl_id) +{ + H5F_t *src_file = NULL; /* Source file */ + hbool_t src_file_open = FALSE; /* Whether we have opened and need to close src_file */ + H5G_loc_t src_root_loc; /* Object location of source file root group */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(vdset); + HDassert(source_dset); + HDassert(!source_dset->dset); + HDassert(source_dset->file_name); + HDassert(source_dset->dset_name); + + /* Check if we need to open the source file */ + if(HDstrcmp(source_dset->file_name, ".")) { + /* Open the source file */ + if(NULL == (src_file = H5F_open(source_dset->file_name, H5F_INTENT(vdset->oloc.file) & H5F_ACC_RDWR, H5P_FILE_CREATE_DEFAULT, vdset->shared->layout.storage.u.virt.source_fapl, dxpl_id))) + H5E_clear_stack(NULL); /* Quick hack until proper support for H5Fopen with missing file is implemented */ + else + src_file_open = TRUE; + } /* end if */ + else + /* Source file is ".", use the virtual dataset's file */ + src_file = vdset->oloc.file; + + if(src_file) { + /* Set up the root group in the destination file */ + if(NULL == (src_root_loc.oloc = H5G_oloc(H5G_rootof(src_file)))) + HGOTO_ERROR(H5E_DATASET, H5E_BADVALUE, FAIL, "unable to get object location for root group") + if(NULL == (src_root_loc.path = H5G_nameof(H5G_rootof(src_file)))) + HGOTO_ERROR(H5E_DATASET, H5E_BADVALUE, FAIL, "unable to get path for root group") + + /* Open the source dataset */ + if(NULL == (source_dset->dset = H5D__open_name(&src_root_loc, source_dset->dset_name, vdset->shared->layout.storage.u.virt.source_dapl, dxpl_id))) { + H5E_clear_stack(NULL); /* Quick hack until proper support for H5Dopen with missing file is implemented */ + + /* Dataset does not exist */ + source_dset->dset_exists = FALSE; + } /* end if */ + else { + /* Dataset exists */ + source_dset->dset_exists = TRUE; + + /* Patch the source selection if necessary */ + if(virtual_ent->source_space_status != H5O_VIRTUAL_STATUS_CORRECT) { + if(H5S_extent_copy(virtual_ent->source_select, source_dset->dset->shared->space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy source dataspace extent") + virtual_ent->source_space_status = H5O_VIRTUAL_STATUS_CORRECT; + } /* end if */ + } /* end else */ + } /* end if */ + +done: + /* Close source file */ + if(src_file_open) + if(H5F_try_close(src_file) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTCLOSEFILE, FAIL, "can't close source file") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_open_source_dset() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_reset_source_dset + * + * Purpose: Frees space reference by a source dataset struct. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 20, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_reset_source_dset(H5O_storage_virtual_ent_t *virtual_ent, + H5O_storage_virtual_srcdset_t *source_dset) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(source_dset); + + /* Free dataset */ + if(source_dset->dset) { + if(H5D_close(source_dset->dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to close source dataset") + source_dset->dset = NULL; + } /* end if */ + + /* Free file name */ + if(virtual_ent->parsed_source_file_name + && (source_dset->file_name + != virtual_ent->parsed_source_file_name->name_segment)) + source_dset->file_name = (char *)H5MM_xfree(source_dset->file_name); + else + HDassert((source_dset->file_name == virtual_ent->source_file_name) + || (virtual_ent->parsed_source_file_name + && (source_dset->file_name + == virtual_ent->parsed_source_file_name->name_segment)) + || !source_dset->file_name); + + /* Free dataset name */ + if(virtual_ent->parsed_source_dset_name + && (source_dset->dset_name + != virtual_ent->parsed_source_dset_name->name_segment)) + source_dset->dset_name = (char *)H5MM_xfree(source_dset->dset_name); + else + HDassert((source_dset->dset_name == virtual_ent->source_dset_name) + || (virtual_ent->parsed_source_dset_name + && (source_dset->dset_name + == virtual_ent->parsed_source_dset_name->name_segment)) + || !source_dset->dset_name); + + /* Free clipped virtual selection */ + if(source_dset->clipped_virtual_select) { + if(source_dset->clipped_virtual_select != source_dset->virtual_select) + if(H5S_close(source_dset->clipped_virtual_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual selection") + source_dset->clipped_virtual_select = NULL; + } /* end if */ + + /* Free virtual selection */ + if(source_dset->virtual_select) { + if(H5S_close(source_dset->virtual_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release virtual selection") + source_dset->virtual_select = NULL; + } /* end if */ + + /* Free clipped source selection */ + if(source_dset->clipped_source_select) { + if(source_dset->clipped_source_select != virtual_ent->source_select) + if(H5S_close(source_dset->clipped_source_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source selection") + source_dset->clipped_source_select = NULL; + } /* end if */ + + /* The projected memory space should never exist when this function is + * called */ + HDassert(!source_dset->projected_mem_space); + + /* Note the lack of a done: label. This is because there are no HGOTO_ERROR + * calls. If one is added, a done: label must also be added */ + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_reset_source_dset() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_str_append + * + * Purpose: Appends src_len bytes of the string src to the position *p + * in the buffer *buf (allocating *buf if necessary). + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 19, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_str_append(const char *src, size_t src_len, char **p, char **buf, + size_t *buf_size) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(src); + HDassert(src_len > 0); + HDassert(p); + HDassert(buf); + HDassert(*p >= *buf); + HDassert(buf_size); + + /* Allocate or extend buffer if necessary */ + if(!*buf) { + HDassert(!*p); + HDassert(*buf_size == 0); + + /* Allocate buffer */ + if(NULL == (*buf = (char *)H5MM_malloc(src_len + (size_t)1))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate name segment struct") + *buf_size = src_len + (size_t)1; + *p = *buf; + } /* end if */ + else { + size_t p_offset = (size_t)(*p - *buf); /* Offset of p within buf */ + + /* Extend buffer if necessary */ + if((p_offset + src_len + (size_t)1) > *buf_size) { + char *tmp_buf; + size_t tmp_buf_size; + + /* Calculate new size of buffer */ + tmp_buf_size = MAX(p_offset + src_len + (size_t)1, + *buf_size * (size_t)2); + + /* Reallocate buffer */ + if(NULL == (tmp_buf = (char *)H5MM_realloc(*buf, tmp_buf_size))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to reallocate name segment buffer") + *buf = tmp_buf; + *buf_size = tmp_buf_size; + *p = *buf + p_offset; + } /* end if */ + } /* end else */ + + /* Copy string to *p. Note that since src in not NULL terminated, we must + * use memcpy */ + (void)HDmemcpy(*p, src, src_len); + + /* Advance *p */ + *p += src_len; + + /* Add NULL terminator */ + **p = '\0'; + +done: + FUNC_LEAVE_NOAPI(ret_value); +} /* end H5D__virtual_str_append() */ + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_parse_source_name + * + * Purpose: Parses a source file or dataset name. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 18, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_virtual_parse_source_name(const char *source_name, + H5O_storage_virtual_name_seg_t **parsed_name, size_t *static_strlen, + size_t *nsubs) +{ + H5O_storage_virtual_name_seg_t *tmp_parsed_name = NULL; + H5O_storage_virtual_name_seg_t **tmp_parsed_name_p = &tmp_parsed_name; + size_t tmp_static_strlen; + size_t tmp_strlen; + size_t tmp_nsubs = 0; + const char *p; + const char *pct; + char *name_seg_p = NULL; + size_t name_seg_size = 0; + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Sanity check */ + HDassert(source_name); + HDassert(parsed_name); + HDassert(static_strlen); + HDassert(nsubs); + + /* Initialize p and tmp_static_strlen */ + p = source_name; + tmp_static_strlen = tmp_strlen = HDstrlen(source_name); + + /* Iterate over name */ + /* Note this will not work with UTF-8! We should support this eventually + * -NAF 5/18/2015 */ + while((pct = HDstrchr(p, '%'))) { + HDassert(pct >= p); + + /* Allocate name segment struct if necessary */ + if(!*tmp_parsed_name_p) + if(NULL == (*tmp_parsed_name_p = H5FL_CALLOC(H5O_storage_virtual_name_seg_t))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate name segment struct") + + /* Check for type of format specifier */ + if(pct[1] == 'b') { + /* Check for blank string before specifier */ + if(pct != p) + /* Append string to name segment */ + if(H5D__virtual_str_append(p, (size_t)(pct - p), &name_seg_p, &(*tmp_parsed_name_p)->name_segment, + &name_seg_size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to append name segment") + + /* Update other variables */ + tmp_parsed_name_p = &(*tmp_parsed_name_p)->next; + tmp_static_strlen -= 2; + tmp_nsubs++; + name_seg_p = NULL; + name_seg_size = 0; + } /* end if */ + else if(pct[1] == '%') { + /* Append string to name segment (include first '%') */ + if(H5D__virtual_str_append(p, (size_t)(pct - p) + (size_t)1, &name_seg_p, &(*tmp_parsed_name_p)->name_segment, +&name_seg_size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to append name segment") + + /* Update other variables */ + tmp_static_strlen -= 1; + } /* end else */ + else + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid format specifier") + + p = pct + 2; + } /* end while */ + + /* Copy last segment of name, if any, unless the parsed name was not + * allocated */ + if(tmp_parsed_name) { + HDassert(p >= source_name); + if(*p == '\0') + HDassert((size_t)(p - source_name) == tmp_strlen); + else { + HDassert((size_t)(p - source_name) < tmp_strlen); + + /* Allocate name segment struct if necessary */ + if(!*tmp_parsed_name_p) + if(NULL == (*tmp_parsed_name_p = H5FL_CALLOC(H5O_storage_virtual_name_seg_t))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate name segment struct") + + /* Append string to name segment */ + if(H5D__virtual_str_append(p, tmp_strlen - (size_t)(p - source_name), &name_seg_p, &(*tmp_parsed_name_p)->name_segment, + &name_seg_size) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to append name segment") + } /* end else */ + } /* end if */ + + /* Set return values */ + *parsed_name = tmp_parsed_name; + tmp_parsed_name = NULL; + *static_strlen = tmp_static_strlen; + *nsubs = tmp_nsubs; + +done: + if(tmp_parsed_name) { + HDassert(ret_value < 0); + H5D_virtual_free_parsed_name(tmp_parsed_name); + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D_virtual_parse_source_name() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_copy_parsed_name + * + * Purpose: Deep copies a parsed source file or dataset name. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 19, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_copy_parsed_name(H5O_storage_virtual_name_seg_t **dst, + H5O_storage_virtual_name_seg_t *src) +{ + H5O_storage_virtual_name_seg_t *tmp_dst = NULL; + H5O_storage_virtual_name_seg_t *p_src = src; + H5O_storage_virtual_name_seg_t **p_dst = &tmp_dst; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(dst); + + /* Walk over parsed name, duplicating it */ + while(p_src) { + /* Allocate name segment struct */ + if(NULL == (*p_dst = H5FL_CALLOC(H5O_storage_virtual_name_seg_t))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate name segment struct") + + /* Duplicate name segment */ + if(p_src->name_segment) { + if(NULL == ((*p_dst)->name_segment = HDstrdup(p_src->name_segment))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to duplicate name segment") + } /* end if */ + + /* Advance pointers */ + p_src = p_src->next; + p_dst = &(*p_dst)->next; + } /* end while */ + + /* Set dst */ + *dst = tmp_dst; + tmp_dst = NULL; + +done: + if(tmp_dst) { + HDassert(ret_value < 0); + H5D_virtual_free_parsed_name(tmp_dst); + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_copy_parsed_name() */ + + +/*------------------------------------------------------------------------- + * Function: H5D_virtual_free_parsed_name + * + * Purpose: Frees the provided parsed name. + * + * Return: void + * + * Programmer: Neil Fortner + * May 19, 2015 + * + *------------------------------------------------------------------------- + */ +void +H5D_virtual_free_parsed_name(H5O_storage_virtual_name_seg_t *name_seg) +{ + H5O_storage_virtual_name_seg_t *next_seg; + + FUNC_ENTER_NOAPI_NOERR + + /* Walk name segments, freeing them */ + while(name_seg) { + (void)H5MM_xfree(name_seg->name_segment); + next_seg = name_seg->next; + (void)H5FL_FREE(H5O_storage_virtual_name_seg_t, name_seg); + name_seg = next_seg; + } /* end while */ + + FUNC_LEAVE_NOAPI_VOID +} /* end H5D_virtual_free_parsed_name() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_build_source_name + * + * Purpose: Builds a source file or dataset name from a parsed name. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 18, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_build_source_name(char *source_name, + const H5O_storage_virtual_name_seg_t *parsed_name, size_t static_strlen, + size_t nsubs, hsize_t blockno, char **built_name) +{ + char *tmp_name = NULL; /* Name buffer */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(source_name); + HDassert(built_name); + + /* Check for static name */ + if(nsubs == 0) { + if(parsed_name) + *built_name = parsed_name->name_segment; + else + *built_name = source_name; + } /* end if */ + else { + const H5O_storage_virtual_name_seg_t *name_seg = parsed_name; + char *p; + hsize_t blockno_down = blockno; + size_t blockno_len = 1; + size_t name_len; + size_t name_len_rem; + size_t seg_len; + size_t nsubs_rem = nsubs; + + HDassert(parsed_name); + + /* Calculate length of printed block number */ + do { + blockno_down /= (hsize_t)10; + if(blockno_down == 0) + break; + blockno_len++; + } while(1); + + /* Calculate length of name buffer */ + name_len_rem = name_len = static_strlen + (nsubs * blockno_len) + (size_t)1; + + /* Allocate name buffer */ + if(NULL == (tmp_name = (char *)H5MM_malloc(name_len))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate name buffer") + p = tmp_name; + + /* Build name */ + do { + /* Add name segment */ + if(name_seg->name_segment) { + seg_len = HDstrlen(name_seg->name_segment); + HDassert(seg_len > 0); + HDassert(seg_len < name_len_rem); + HDstrncpy(p, name_seg->name_segment, name_len_rem); + name_len_rem -= seg_len; + p += seg_len; + } /* end if */ + + /* Add block number */ + if(nsubs_rem > 0) { + HDassert(blockno_len < name_len_rem); + if(HDsnprintf(p, name_len_rem, "%llu", (long long unsigned)blockno) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "unable to write block number to string") + name_len_rem -= blockno_len; + p += blockno_len; + nsubs_rem--; + } /* end if */ + + /* Advance name_seg */ + name_seg = name_seg->next; + } while(name_seg); + + /* Assign built_name */ + *built_name = tmp_name; + tmp_name = NULL; + } /* end else */ + +done: + if(tmp_name) { + HDassert(ret_value < 0); + H5MM_free(tmp_name); + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_build_source_name() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_set_extent_unlim + * + * Purpose: Sets the extent of the virtual dataset by checking the + * extents of source datasets where an unlimited selection + * matching. Dimensions that are not unlimited in any + * virtual mapping selections are not affected. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * April 22, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_set_extent_unlim(const H5D_t *dset, hid_t dxpl_id) +{ + H5O_storage_virtual_t *storage; + hsize_t new_dims[H5S_MAX_RANK]; + hsize_t curr_dims[H5S_MAX_RANK]; + hsize_t clip_size; + int rank; + hbool_t changed = FALSE; /* Whether the VDS extent changed */ + size_t i, j; + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* Sanity check */ + HDassert(dset); + HDassert(dset->shared->layout.storage.type == H5D_VIRTUAL); + storage = &dset->shared->layout.storage.u.virt; + HDassert((storage->view == H5D_VDS_FIRST_MISSING) || (storage->view == H5D_VDS_LAST_AVAILABLE)); + + /* Get rank of VDS */ + if((rank = H5S_GET_EXTENT_NDIMS(dset->shared->space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get number of dimensions") + + /* Initialize new_dims to HSIZE_UNDEF */ + for(i = 0; i < (size_t)rank; i++) + new_dims[i] = HSIZE_UNDEF; + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nalloc; i++) + /* Check for unlimited dimension */ + if(storage->list[i].unlim_dim_virtual >= 0) { + /* Check for "printf" source dataset resolution */ + if(storage->list[i].unlim_dim_source >= 0 ) { + /* Non-printf mapping */ + /* Open source dataset */ + if(!storage->list[i].source_dset.dset) + if(H5D__virtual_open_source_dset(dset, &storage->list[i], &storage->list[i].source_dset, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + + /* Check if source dataset is open */ + if(storage->list[i].source_dset.dset) { + /* Retrieve current source dataset extent and patch mapping + */ + if(H5S_extent_copy(storage->list[i].source_select, storage->list[i].source_dset.dset->shared->space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy source dataspace extent") + + /* Get source space dimenstions */ + if(H5S_get_simple_extent_dims(storage->list[i].source_select, curr_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get source space dimensions") + + /* Check if the source extent in the unlimited dimension + * changed since the last time the VDS extent/mapping + * was updated */ + if(curr_dims[storage->list[i].unlim_dim_source] + == storage->list[i].unlim_extent_source) + /* Use cached result for clip size */ + clip_size = storage->list[i].clip_size_virtual; + else { + /* Get size that virtual selection would be clipped to + * to match size of source selection within source + * extent */ + clip_size = H5S_hyper_get_clip_extent_match(storage->list[i].source_dset.virtual_select, storage->list[i].source_select, curr_dims[storage->list[i].unlim_dim_source], storage->view == H5D_VDS_FIRST_MISSING); + + /* If we are setting the extent by the last available + * data, clip virtual_select and source_select. Note + * that if we used the cached clip_size above or it + * happens to be the same, the virtual selection will + * already be clipped to the correct size. Likewise, + * if we used the cached clip_size the source selection + * will already be correct. */ + if(storage->view == H5D_VDS_LAST_AVAILABLE) { + if(clip_size != storage->list[i].clip_size_virtual) { + /* Close previous clipped virtual selection, if + * any */ + if(storage->list[i].source_dset.clipped_virtual_select) { + HDassert(storage->list[i].source_dset.clipped_virtual_select + != storage->list[i].source_dset.virtual_select); + if(H5S_close(storage->list[i].source_dset.clipped_virtual_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual dataspace") + } /* end if */ + + /* Copy virtual selection */ + if(NULL == (storage->list[i].source_dset.clipped_virtual_select = H5S_copy(storage->list[i].source_dset.virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Clip virtual selection */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_virtual_select, clip_size)) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + } /* end if */ + + /* Close previous clipped source selection, if any + */ + if(storage->list[i].source_dset.clipped_source_select) { + HDassert(storage->list[i].source_dset.clipped_source_select + != storage->list[i].source_select); + if(H5S_close(storage->list[i].source_dset.clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source dataspace") + } /* end if */ + + /* Copy source selection */ + if(NULL == (storage->list[i].source_dset.clipped_source_select = H5S_copy(storage->list[i].source_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy source selection") + + /* Clip source selection */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_source_select, curr_dims[storage->list[i].unlim_dim_source])) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + } /* end if */ + + /* Update cached values unlim_extent_source and + * clip_size_virtual */ + storage->list[i].unlim_extent_source = curr_dims[storage->list[i].unlim_dim_source]; + storage->list[i].clip_size_virtual = clip_size; + } /* end else */ + } /* end if */ + else + clip_size = 0; + } /* end if */ + else { + /* printf mapping */ + hsize_t first_missing = 0; /* First missing dataset in the current block of missing datasets */ + + /* Search for source datasets */ + HDassert(storage->printf_gap != HSIZE_UNDEF); + for(j = 0; j <= (storage->printf_gap + first_missing); j++) { + /* Check for running out of space in sub_dset array */ + if(j >= (hsize_t)storage->list[i].sub_dset_nalloc) { + if(storage->list[i].sub_dset_nalloc == 0) { + /* Allocate sub_dset */ + if(NULL == (storage->list[i].sub_dset = (H5O_storage_virtual_srcdset_t *)H5MM_calloc(H5D_VIRTUAL_DEF_SUB_DSET_SIZE * sizeof(H5O_storage_virtual_srcdset_t)))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate sub dataset array") + storage->list[i].sub_dset_nalloc = H5D_VIRTUAL_DEF_SUB_DSET_SIZE; + } /* end if */ + else { + H5O_storage_virtual_srcdset_t *tmp_sub_dset; + + /* Extend sub_dset */ + if(NULL == (tmp_sub_dset = (H5O_storage_virtual_srcdset_t *)H5MM_realloc(storage->list[i].sub_dset, 2 * storage->list[i].sub_dset_nalloc * sizeof(H5O_storage_virtual_srcdset_t)))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to extend sub dataset array") + storage->list[i].sub_dset = tmp_sub_dset; + + /* Clear new space in sub_dset */ + (void)HDmemset(&storage->list[i].sub_dset[storage->list[i].sub_dset_nalloc], 0, storage->list[i].sub_dset_nalloc * sizeof(H5O_storage_virtual_srcdset_t)); + + /* Update sub_dset_nalloc */ + storage->list[i].sub_dset_nalloc *= 2; + } /* end else */ + } /* end if */ + + /* Check if the dataset was already opened */ + if(storage->list[i].sub_dset[j].dset_exists) + first_missing = j + 1; + else { + /* Resolve file name */ + if(!storage->list[i].sub_dset[j].file_name) + if(H5D__virtual_build_source_name(storage->list[i].source_file_name, storage->list[i].parsed_source_file_name, storage->list[i].psfn_static_strlen, storage->list[i].psfn_nsubs, j, &storage->list[i].sub_dset[j].file_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to build source file name") + + /* Resolve dset name */ + if(!storage->list[i].sub_dset[j].dset_name) + if(H5D__virtual_build_source_name(storage->list[i].source_dset_name, storage->list[i].parsed_source_dset_name, storage->list[i].psdn_static_strlen, storage->list[i].psdn_nsubs, j, &storage->list[i].sub_dset[j].dset_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to build source dataset name") + + /* Resolve virtual selection for block */ + if(!storage->list[i].sub_dset[j].virtual_select) + if(NULL == (storage->list[i].sub_dset[j].virtual_select = H5S_hyper_get_unlim_block(storage->list[i].source_dset.virtual_select, j))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get block in unlimited selection") + + /* Initialize clipped selections */ + if(!storage->list[i].sub_dset[j].clipped_source_select) + storage->list[i].sub_dset[j].clipped_source_select = storage->list[i].source_select; + if(!storage->list[i].sub_dset[j].clipped_virtual_select) + storage->list[i].sub_dset[j].clipped_virtual_select = storage->list[i].sub_dset[j].virtual_select; + + /* Open source dataset */ + if(H5D__virtual_open_source_dset(dset, &storage->list[i], &storage->list[i].sub_dset[j], dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + + if(storage->list[i].sub_dset[j].dset) { + /* Update first_missing */ + first_missing = j + 1; + + /* Close source dataset so we don't have huge + * numbers of datasets open */ + if(H5D_close(storage->list[i].sub_dset[j].dset) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to close source dataset") + storage->list[i].sub_dset[j].dset = NULL; + } /* end if */ + } /* end else */ + } /* end for */ + + /* Check if the size changed */ + if((first_missing == (hsize_t)storage->list[i].sub_dset_nused) + && (storage->list[i].clip_size_virtual != HSIZE_UNDEF)) + /* Use cached clip_size */ + clip_size = storage->list[i].clip_size_virtual; + else { + /* Check for no datasets */ + if(first_missing == 0) + /* Set clip size to 0 */ + clip_size = (hsize_t)0; + else { + hsize_t bounds_start[H5S_MAX_RANK]; + hsize_t bounds_end[H5S_MAX_RANK]; + + /* Get clip size from selection */ + if(storage->view == H5D_VDS_LAST_AVAILABLE) { + /* Get bounds from last valid virtual selection */ + if(H5S_SELECT_BOUNDS(storage->list[i].sub_dset[first_missing - (hsize_t)1].virtual_select, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection bounds") + + /* Set clip_size to bounds_end in unlimited + * dimension */ + clip_size = bounds_end[storage->list[i].unlim_dim_virtual] + + (hsize_t)1; + } /* end if */ + else { + /* Get bounds from first missing virtual selection + */ + if(H5S_SELECT_BOUNDS(storage->list[i].sub_dset[first_missing].virtual_select, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection bounds") + + /* Set clip_size to bounds_start in unlimited + * dimension */ + clip_size = bounds_start[storage->list[i].unlim_dim_virtual]; + } /* end else */ + } /* end else */ + + /* Set sub_dset_nused and clip_size_virtual */ + storage->list[i].sub_dset_nused = (size_t)first_missing; + storage->list[i].clip_size_virtual = clip_size; + } /* end else */ + } /* end else */ + + /* Update new_dims */ + if((new_dims[storage->list[i].unlim_dim_virtual] == HSIZE_UNDEF) + || (storage->view == H5D_VDS_FIRST_MISSING ? (clip_size + < (hsize_t)new_dims[storage->list[i].unlim_dim_virtual]) + : (clip_size + > (hsize_t)new_dims[storage->list[i].unlim_dim_virtual]))) + new_dims[storage->list[i].unlim_dim_virtual] = clip_size; + } /* end if */ + + /* Get current VDS dimensions */ + if(H5S_get_simple_extent_dims(dset->shared->space, curr_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get VDS dimensions") + + /* Calculate new extent */ + for(i = 0; i < (size_t)rank; i++) { + if(new_dims[i] == HSIZE_UNDEF) + new_dims[i] = curr_dims[i]; + else if(new_dims[i] < storage->min_dims[i]) + new_dims[i] = storage->min_dims[i]; + if(new_dims[i] != curr_dims[i]) + changed = TRUE; + } /* end for */ + + /* Update extent if it changed */ + if(changed) { + /* Update VDS extent */ + if(H5S_set_extent(dset->shared->space, new_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + + /* Mark the space as dirty, for later writing to the file */ + if(H5F_INTENT(dset->oloc.file) & H5F_ACC_RDWR) + if(H5D__mark(dset, dxpl_id, H5D_MARK_SPACE) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTSET, FAIL, "unable to mark dataspace as dirty") + } /* end if */ + + /* If we did not change the VDS dimensions, there is nothing more to update + */ + if(changed || (!storage->init && (storage->view == H5D_VDS_FIRST_MISSING))) { + /* Iterate over mappings again to update source selections and virtual + * mapping extents */ + for(i = 0; i < storage->list_nalloc; i++) { + /* If there is an unlimited dimension, we are setting extent by the + * minimum of mappings, and the virtual extent in the unlimited + * dimension has changed since the last time the VDS extent/mapping + * was updated, we must adjust the selections */ + if((storage->list[i].unlim_dim_virtual >= 0) + && (storage->view == H5D_VDS_FIRST_MISSING) + && (new_dims[storage->list[i].unlim_dim_virtual] + != storage->list[i].unlim_extent_virtual)) { + /* Check for "printf" style mapping */ + if(storage->list[i].unlim_dim_source >= 0) { + /* Non-printf mapping */ + /* Close previous clipped virtual selection, if any */ + if(storage->list[i].source_dset.clipped_virtual_select) { + HDassert(storage->list[i].source_dset.clipped_virtual_select + != storage->list[i].source_dset.virtual_select); + if(H5S_close(storage->list[i].source_dset.clipped_virtual_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual dataspace") + } /* end if */ + + /* Copy virtual selection */ + if(NULL == (storage->list[i].source_dset.clipped_virtual_select = H5S_copy(storage->list[i].source_dset.virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Clip space to virtual extent */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_virtual_select, new_dims[storage->list[i].unlim_dim_source])) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* Get size that source selection will be clipped to to + * match size of virtual selection */ + clip_size = H5S_hyper_get_clip_extent(storage->list[i].source_select, storage->list[i].source_dset.clipped_virtual_select, FALSE); + + /* Check if the clip size changed */ + if(clip_size != storage->list[i].clip_size_source) { + /* Close previous clipped source selection, if any */ + if(storage->list[i].source_dset.clipped_source_select) { + HDassert(storage->list[i].source_dset.clipped_source_select + != storage->list[i].source_select); + if(H5S_close(storage->list[i].source_dset.clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source dataspace") + } /* end if */ + + /* Copy source selection */ + if(NULL == (storage->list[i].source_dset.clipped_source_select = H5S_copy(storage->list[i].source_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy source selection") + + /* Clip source selection */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_source_select, clip_size)) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* Update cached value clip_size_source */ + storage->list[i].clip_size_source = clip_size; + } /* end if */ + } /* end if */ + else { + /* printf mapping */ + hsize_t first_inc_block; + hbool_t partial_block; + + /* Get index of first incomplete block in virtual + * selection */ + first_inc_block = H5S_hyper_get_first_inc_block(storage->list[i].source_dset.virtual_select, new_dims[storage->list[i].unlim_dim_virtual], &partial_block); + + /* Iterate over sub datasets */ + for(j = 0; j < storage->list[i].sub_dset_nalloc; j++) { + /* Close previous clipped source selection, if any */ + if(storage->list[i].sub_dset[j].clipped_source_select + != storage->list[i].source_select) { + if(storage->list[i].sub_dset[j].clipped_source_select) + if(H5S_close(storage->list[i].sub_dset[j].clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source dataspace") + + /* Initialize clipped source selection to point to + * base source selection */ + storage->list[i].sub_dset[j].clipped_source_select = storage->list[i].source_select; + } /* end if */ + + /* Close previous clipped virtual selection, if any */ + if(storage->list[i].sub_dset[j].clipped_virtual_select + != storage->list[i].sub_dset[j].virtual_select) { + if(storage->list[i].sub_dset[j].clipped_virtual_select) + if(H5S_close(storage->list[i].sub_dset[j].clipped_virtual_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual dataspace") + + /* Initialize clipped virtual selection to point to + * unclipped virtual selection */ + storage->list[i].sub_dset[j].clipped_virtual_select = storage->list[i].sub_dset[j].virtual_select; + } /* end if */ + + /* Only initialize clipped selections if it is a + * complete block, for incomplete blocks defer to + * H5D__virtual_pre_io() as we may not have a valid + * source extent here. For unused blocks we will never + * need clipped selections (until the extent is + * recalculated in this function). */ + if(j >= (size_t)first_inc_block) { + /* Clear clipped source and virtual selections */ + storage->list[i].sub_dset[j].clipped_source_select = NULL; + storage->list[i].sub_dset[j].clipped_virtual_select = NULL; + } /* end if */ + } /* end for */ + } /* end else */ + + /* Update cached value unlim_extent_virtual */ + storage->list[i].unlim_extent_virtual = new_dims[storage->list[i].unlim_dim_virtual]; + } /* end if */ + + /* Update top level virtual_select and clipped_virtual_select + * extents */ + if(H5S_set_extent(storage->list[i].source_dset.virtual_select, new_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + if((storage->list[i].source_dset.clipped_virtual_select + != storage->list[i].source_dset.virtual_select) + && storage->list[i].source_dset.clipped_virtual_select) + if(H5S_set_extent(storage->list[i].source_dset.clipped_virtual_select, new_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + + /* Update sub dataset virtual_select and clipped_virtual_select + * extents */ + for(j = 0; j < storage->list[i].sub_dset_nalloc; j++) + if(storage->list[i].sub_dset[j].virtual_select) { + if(H5S_set_extent(storage->list[i].sub_dset[j].virtual_select, new_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + if((storage->list[i].sub_dset[j].clipped_virtual_select + != storage->list[i].sub_dset[j].virtual_select) + && storage->list[i].sub_dset[j].clipped_virtual_select) + if(H5S_set_extent(storage->list[i].sub_dset[j].clipped_virtual_select, new_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + } /* end if */ + else + HDassert(!storage->list[i].sub_dset[j].clipped_virtual_select); + } /* end for */ + } /* end if */ + + /* Mark layout as fully initialized */ + storage->init = TRUE; + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_set_extent_unlim() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_init_all + * + * Purpose: Finishes initializing layout in preparation for I/O. + * Only necessary if H5D__virtual_set_extent_unlim() has not + * been called yet. Initializes clipped_virtual_select and + * clipped_source_select for all mappings in this layout. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * August 10, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_init_all(const H5D_t *dset, hid_t dxpl_id) +{ + H5O_storage_virtual_t *storage; + hsize_t virtual_dims[H5S_MAX_RANK]; + hsize_t source_dims[H5S_MAX_RANK]; + hsize_t clip_size; + size_t i, j; + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(dset); + HDassert(dset->shared->layout.storage.type == H5D_VIRTUAL); + storage = &dset->shared->layout.storage.u.virt; + HDassert((storage->view == H5D_VDS_FIRST_MISSING) || (storage->view == H5D_VDS_LAST_AVAILABLE)); + + /* Get current VDS dimensions */ + if(H5S_get_simple_extent_dims(dset->shared->space, virtual_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get VDS dimensions") + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nalloc; i++) + /* Check for unlimited dimension */ + if(storage->list[i].unlim_dim_virtual >= 0) { + /* Check for "printf" source dataset resolution */ + if(storage->list[i].unlim_dim_source >= 0 ) { + /* Non-printf mapping */ + /* Open source dataset */ + if(!storage->list[i].source_dset.dset) + if(H5D__virtual_open_source_dset(dset, &storage->list[i], &storage->list[i].source_dset, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + + /* Check if source dataset is open */ + if(storage->list[i].source_dset.dset) { + /* Retrieve current source dataset extent and patch mapping + */ + if(H5S_extent_copy(storage->list[i].source_select, storage->list[i].source_dset.dset->shared->space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy source dataspace extent") + + /* Get source space dimenstions */ + if(H5S_get_simple_extent_dims(storage->list[i].source_select, source_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get source space dimensions") + + /* Get size that source selection would be clipped to to + * match size of virtual selection */ + clip_size = H5S_hyper_get_clip_extent_match(storage->list[i].source_select, storage->list[i].source_dset.virtual_select, virtual_dims[storage->list[i].unlim_dim_virtual], FALSE); + + /* Close previous clipped virtual selection, if any */ + if(storage->list[i].source_dset.clipped_virtual_select) { + HDassert(storage->list[i].source_dset.clipped_virtual_select + != storage->list[i].source_dset.virtual_select); + if(H5S_close(storage->list[i].source_dset.clipped_virtual_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual dataspace") + } /* end if */ + + /* Copy virtual selection */ + if(NULL == (storage->list[i].source_dset.clipped_virtual_select = H5S_copy(storage->list[i].source_dset.virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Close previous clipped source selection, if any */ + if(storage->list[i].source_dset.clipped_source_select) { + HDassert(storage->list[i].source_dset.clipped_source_select + != storage->list[i].source_select); + if(H5S_close(storage->list[i].source_dset.clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source dataspace") + } /* end if */ + + /* Copy source selection */ + if(NULL == (storage->list[i].source_dset.clipped_source_select = H5S_copy(storage->list[i].source_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy source selection") + + /* Check if the clip size is within the current extent of + * the source dataset */ + if(clip_size <= source_dims[storage->list[i].unlim_dim_source]) { + /* Clip virtual selection to extent */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_virtual_select, virtual_dims[storage->list[i].unlim_dim_virtual])) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* Clip source selection to clip_size */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_source_select, clip_size)) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + } /* end if */ + else { + /* Get size that virtual selection will be clipped to to + * match size of source selection within source extent + */ + clip_size = H5S_hyper_get_clip_extent_match(storage->list[i].source_dset.virtual_select, storage->list[i].source_select, source_dims[storage->list[i].unlim_dim_source], FALSE); + + /* Clip virtual selection to clip_size */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_virtual_select, clip_size)) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* Clip source selection to extent */ + if(H5S_hyper_clip_unlim(storage->list[i].source_dset.clipped_source_select, source_dims[storage->list[i].unlim_dim_source])) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + } /* end else */ + } /* end if */ + else { + HDassert(!storage->list[i].source_dset.clipped_virtual_select); + HDassert(!storage->list[i].source_dset.clipped_source_select); + } /* end else */ + } /* end if */ + else { + /* printf mapping */ + size_t sub_dset_max; + hbool_t partial_block; + + /* Get number of sub-source datasets in current extent */ + sub_dset_max = (size_t)H5S_hyper_get_first_inc_block(storage->list[i].source_dset.virtual_select, virtual_dims[storage->list[i].unlim_dim_virtual], &partial_block); + if(partial_block) + sub_dset_max++; + + /* Allocate or grow the sub_dset array if necessary */ + if(!storage->list[i].sub_dset) { + /* Allocate sub_dset array */ + if(NULL == (storage->list[i].sub_dset = (H5O_storage_virtual_srcdset_t *)H5MM_calloc(sub_dset_max * sizeof(H5O_storage_virtual_srcdset_t)))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to allocate sub dataset array") + + /* Update sub_dset_nalloc */ + storage->list[i].sub_dset_nalloc = sub_dset_max; + } /* end if */ + else if(sub_dset_max > storage->list[i].sub_dset_nalloc) { + H5O_storage_virtual_srcdset_t *tmp_sub_dset; + + /* Extend sub_dset array */ + if(NULL == (tmp_sub_dset = (H5O_storage_virtual_srcdset_t *)H5MM_realloc(storage->list[i].sub_dset, sub_dset_max * sizeof(H5O_storage_virtual_srcdset_t)))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "unable to extend sub dataset array") + storage->list[i].sub_dset = tmp_sub_dset; + + /* Clear new space in sub_dset */ + (void)HDmemset(&storage->list[i].sub_dset[storage->list[i].sub_dset_nalloc], 0, (sub_dset_max - storage->list[i].sub_dset_nalloc) * sizeof(H5O_storage_virtual_srcdset_t)); + + /* Update sub_dset_nalloc */ + storage->list[i].sub_dset_nalloc = sub_dset_max; + } /* end if */ + + /* Iterate over sub dsets */ + for(j = 0; j < sub_dset_max; j++) { + /* Resolve file name */ + if(!storage->list[i].sub_dset[j].file_name) + if(H5D__virtual_build_source_name(storage->list[i].source_file_name, storage->list[i].parsed_source_file_name, storage->list[i].psfn_static_strlen, storage->list[i].psfn_nsubs, j, &storage->list[i].sub_dset[j].file_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to build source file name") + + /* Resolve dset name */ + if(!storage->list[i].sub_dset[j].dset_name) + if(H5D__virtual_build_source_name(storage->list[i].source_dset_name, storage->list[i].parsed_source_dset_name, storage->list[i].psdn_static_strlen, storage->list[i].psdn_nsubs, j, &storage->list[i].sub_dset[j].dset_name) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to build source dataset name") + + /* Resolve virtual selection for block */ + if(!storage->list[i].sub_dset[j].virtual_select) + if(NULL == (storage->list[i].sub_dset[j].virtual_select = H5S_hyper_get_unlim_block(storage->list[i].source_dset.virtual_select, j))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get block in unlimited selection") + + /* Close previous clipped source selection, if any */ + if(storage->list[i].sub_dset[j].clipped_source_select + != storage->list[i].source_select) { + if(storage->list[i].sub_dset[j].clipped_source_select) + if(H5S_close(storage->list[i].sub_dset[j].clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped source dataspace") + + /* Initialize clipped source selection to point to base + * source selection */ + storage->list[i].sub_dset[j].clipped_source_select = storage->list[i].source_select; + } /* end if */ + + /* Close previous clipped virtual selection, if any */ + if(storage->list[i].sub_dset[j].clipped_virtual_select + != storage->list[i].sub_dset[j].virtual_select) { + if(storage->list[i].sub_dset[j].clipped_virtual_select) + if(H5S_close(storage->list[i].sub_dset[j].clipped_virtual_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release clipped virtual dataspace") + + /* Initialize clipped virtual selection to point to + * unclipped virtual selection */ + storage->list[i].sub_dset[j].clipped_virtual_select = storage->list[i].sub_dset[j].virtual_select; + } /* end if */ + + /* Clear clipped selections if this is a partial block, + * defer calculation of real clipped selections to + * H5D__virtual_pre_io() as we may not have a valid source + * extent here */ + if((j == (sub_dset_max - 1)) && partial_block) { + /* Clear clipped source and virtual selections */ + storage->list[i].sub_dset[j].clipped_source_select = NULL; + storage->list[i].sub_dset[j].clipped_virtual_select = NULL; + } /* end else */ + /* Note we do not need to open the source file, this will + * happen later in H5D__virtual_pre_io() */ + } /* end for */ + + /* Update sub_dset_nused */ + storage->list[i].sub_dset_nused = sub_dset_max; + } /* end else */ + } /* end if */ + else { + /* Limited mapping, just make sure the clipped selections were + * already set. Again, no need to open the source file. */ + HDassert(storage->list[i].source_dset.clipped_virtual_select); + HDassert(storage->list[i].source_dset.clipped_source_select); + } /* end else */ + + /* Mark layout as fully initialized */ + storage->init = TRUE; + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_init_all() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_init + * + * Purpose: Initialize the virtual layout information for a dataset. + * This is called when the dataset is initialized. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * Thursday, April 30, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5D__virtual_init(H5F_t *f, hid_t H5_ATTR_UNUSED dxpl_id, const H5D_t *dset, + hid_t dapl_id) +{ + H5O_storage_virtual_t *storage; /* Convenience pointer */ + H5P_genplist_t *dapl; /* Data access property list object pointer */ + hssize_t old_offset[H5O_LAYOUT_NDIMS]; /* Old selection offset (unused) */ + size_t i; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* Sanity check */ + HDassert(dset); + storage = &dset->shared->layout.storage.u.virt; + HDassert(storage->list || (storage->list_nused == 0)); + + /* Check that the dimensions of the VDS are large enough */ + if(H5D_virtual_check_min_dims(dset) < 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "virtual dataset dimensions not large enough to contain all limited dimensions in all selections") + + /* Patch the virtual selection dataspaces. Note we always patch the space + * status because this layout could be from an old version held in the + * object header message code. We cannot update that held message because + * the layout message is constant, so just overwrite the values here (and + * invalidate other fields by setting storage->init to FALSE below). Also + * remove offset from selections. We only have to update + * source_space_status and virtual_space_status because others will be based + * on these and should therefore already have been normalized. */ + for(i = 0; i < storage->list_nused; i++) { + HDassert(storage->list[i].sub_dset_nalloc == 0); + + /* Patch extent */ + if(H5S_extent_copy(storage->list[i].source_dset.virtual_select, dset->shared->space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy virtual dataspace extent") + storage->list[i].virtual_space_status = H5O_VIRTUAL_STATUS_CORRECT; + + /* Mark source extent as invalid */ + storage->list[i].source_space_status = H5O_VIRTUAL_STATUS_INVALID; + + /* Normalize offsets, toss out old offset values */ + if(H5S_hyper_normalize_offset(storage->list[i].source_dset.virtual_select, old_offset) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_BADSELECT, FAIL, "unable to normalize dataspace by offset") + if(H5S_hyper_normalize_offset(storage->list[i].source_select, old_offset) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_BADSELECT, FAIL, "unable to normalize dataspace by offset") + } /* end for */ + + /* Get dataset access property list */ + if(NULL == (dapl = (H5P_genplist_t *)H5I_object(dapl_id))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for dapl ID") + + /* Get view option */ + if(H5P_get(dapl, H5D_ACS_VDS_VIEW_NAME, &storage->view) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get virtual view option") + + /* Get printf gap if view is H5D_VDS_LAST_AVAILABLE, otherwise set to 0 */ + if(storage->view == H5D_VDS_LAST_AVAILABLE) { + if(H5P_get(dapl, H5D_ACS_VDS_PRINTF_GAP_NAME, &storage->printf_gap) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get virtual printf gap") + } /* end if */ + else + storage->printf_gap = (hsize_t)0; + + /* Retrieve VDS file FAPL to layout */ + if((storage->source_fapl = H5F_get_access_plist(f, FALSE)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get fapl") + + /* Copy DAPL to layout */ + if((storage->source_dapl = H5P_copy_plist(dapl, FALSE)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy dapl") + + /* Mark layout as not fully initialized (must be done prior to I/O for + * unlimited/printf selections) */ + storage->init = FALSE; + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_init() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_is_space_alloc + * + * Purpose: Query if space is allocated for layout + * + * Return: TRUE if space is allocated + * FALSE if it is not + * Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +hbool_t +H5D__virtual_is_space_alloc(const H5O_storage_t H5_ATTR_UNUSED *storage) +{ + hbool_t ret_value; /* Return value */ + + FUNC_ENTER_PACKAGE_NOERR + + /* Just return TRUE, since the global heap object containing the mappings is + * created when the layout message is encoded, and nothing else needs to be + * allocated for virtual datasets. This also ensures that the library never + * assumes (falsely) that no data is present in the dataset, causing errors. + */ + ret_value = TRUE; + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_is_space_alloc() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_pre_io + * + * Purpose: Project all virtual mappings onto mem_space, with the + * results stored in projected_mem_space for each mapping. + * Opens all source datasets if possible. The total number + * of elements is stored in tot_nelmts. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * June 3, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_pre_io(H5D_io_info_t *io_info, + H5O_storage_virtual_t *storage, const H5S_t *file_space, + const H5S_t *mem_space, hsize_t *tot_nelmts) +{ + hssize_t select_nelmts; /* Number of elements in selection */ + hsize_t bounds_start[H5S_MAX_RANK]; /* Selection bounds start */ + hsize_t bounds_end[H5S_MAX_RANK]; /* Selection bounds end */ + int rank; + hbool_t bounds_init = FALSE; /* Whether bounds_start, bounds_end, and rank are valid */ + size_t i, j, k; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(storage); + HDassert(mem_space); + HDassert(file_space); + HDassert(tot_nelmts); + + /* Initialize layout if necessary */ + if(!storage->init) + if(H5D__virtual_init_all(io_info->dset, io_info->dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "can't initialize virtual layout") + + /* Initialize tot_nelmts */ + *tot_nelmts = 0; + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nused; i++) { + /* Sanity check that the virtual space has been patched by now */ + HDassert(storage->list[i].virtual_space_status == H5O_VIRTUAL_STATUS_CORRECT); + + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + hbool_t partial_block; + + HDassert(storage->list[i].unlim_dim_virtual >= 0); + + /* Get selection bounds if necessary */ + if(!bounds_init) { + /* Get rank of VDS */ + if((rank = H5S_GET_EXTENT_NDIMS(io_info->dset->shared->space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get number of dimensions") + + /* Get selection bounds */ + if(H5S_SELECT_BOUNDS(file_space, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection bounds") + + /* Adjust bounds_end to represent the extent just enclosing them + * (add 1) */ + for(j = 0; j < (size_t)rank; j++) + bounds_end[j]++; + + /* Bounds are now initialized */ + bounds_init = TRUE; + } /* end if */ + + /* Get index of first block in virtual selection */ + storage->list[i].sub_dset_io_start = (size_t)H5S_hyper_get_first_inc_block(storage->list[i].source_dset.virtual_select, bounds_start[storage->list[i].unlim_dim_virtual], NULL); + + /* Get index of first block outside of virtual selection */ + storage->list[i].sub_dset_io_end = (size_t)H5S_hyper_get_first_inc_block(storage->list[i].source_dset.virtual_select, bounds_end[storage->list[i].unlim_dim_virtual], &partial_block); + if(partial_block) + storage->list[i].sub_dset_io_end++; + if(storage->list[i].sub_dset_io_end > storage->list[i].sub_dset_nused) + storage->list[i].sub_dset_io_end = storage->list[i].sub_dset_nused; + + /* Iterate over sub-source dsets */ + for(j = storage->list[i].sub_dset_io_start; + j < storage->list[i].sub_dset_io_end; j++) { + /* Check for clipped virtual selection */ + if(!storage->list[i].sub_dset[j].clipped_virtual_select) { + hsize_t start[H5S_MAX_RANK]; + /* This should only be NULL if this is a partial block */ + HDassert((j == (storage->list[i].sub_dset_io_end - 1)) + && partial_block); + + /* If the source space status is not correct, we must try to + * open the source dataset to patch it */ + if(storage->list[i].source_space_status != H5O_VIRTUAL_STATUS_CORRECT) { + HDassert(!storage->list[i].sub_dset[j].dset); + if(H5D__virtual_open_source_dset(io_info->dset, &storage->list[i], &storage->list[i].sub_dset[j], io_info->dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + } /* end if */ + + /* If we obtained a valid source space, we must create + * clipped source and virtual selections, otherwise we + * cannot do this and we will leave them NULL. This doesn't + * hurt anything because we can't do I/O because the dataset + * must not have been found. */ + if(storage->list[i].source_space_status == H5O_VIRTUAL_STATUS_CORRECT) { + hsize_t tmp_dims[H5S_MAX_RANK]; + hsize_t vbounds_end[H5S_MAX_RANK]; + + /* Get bounds of virtual selection */ + if(H5S_SELECT_BOUNDS(storage->list[i].sub_dset[j].virtual_select, tmp_dims, vbounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "unable to get selection bounds") + + HDassert(bounds_init); + + /* Convert bounds to extent (add 1) */ + for(k = 0; k < (size_t)rank; k++) + vbounds_end[k]++; + + /* Temporarily set extent of virtual selection to bounds */ + if(H5S_set_extent(storage->list[i].sub_dset[j].virtual_select, vbounds_end) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + + /* Get current VDS dimensions */ + if(H5S_get_simple_extent_dims(io_info->dset->shared->space, tmp_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get VDS dimensions") + + /* Copy virtual selection */ + if(NULL == (storage->list[i].sub_dset[j].clipped_virtual_select = H5S_copy(storage->list[i].sub_dset[j].virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Clip virtual selection to real virtual extent */ + (void)HDmemset(start, 0, sizeof(start)); + if(H5S_select_hyperslab(storage->list[i].sub_dset[j].clipped_virtual_select, H5S_SELECT_AND, start, NULL, tmp_dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTSELECT, FAIL, "unable to clip hyperslab") + + /* Project intersection of virtual space and clipped + * virtual space onto source space (create + * clipped_source_select) */ + if(H5S_select_project_intersection(storage->list[i].sub_dset[j].virtual_select, storage->list[i].source_select, storage->list[i].sub_dset[j].clipped_virtual_select, &storage->list[i].sub_dset[j].clipped_source_select) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "can't project virtual intersection onto memory space") + + /* Set extents of virtual_select and + * clipped_virtual_select to virtual extent */ + if(H5S_set_extent(storage->list[i].sub_dset[j].virtual_select, tmp_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + if(H5S_set_extent(storage->list[i].sub_dset[j].clipped_virtual_select, tmp_dims) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to modify size of data space") + } /* end if */ + } /* end if */ + + /* Only continue if we managed to obtain a + * clipped_virtual_select */ + if(storage->list[i].sub_dset[j].clipped_virtual_select) { + /* Project intersection of file space and mapping virtual space + * onto memory space */ + if(H5S_select_project_intersection(file_space, mem_space, storage->list[i].sub_dset[j].clipped_virtual_select, &storage->list[i].sub_dset[j].projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "can't project virtual intersection onto memory space") + + /* Check number of elements selected */ + if((select_nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(storage->list[i].sub_dset[j].projected_mem_space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") + + /* Check if anything is selected */ + if(select_nelmts > (hssize_t)0) { + /* Open source dataset */ + if(!storage->list[i].sub_dset[j].dset) + /* Try to open dataset */ + if(H5D__virtual_open_source_dset(io_info->dset, &storage->list[i], &storage->list[i].sub_dset[j], io_info->dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + + /* If the source dataset is not open, mark the selected + * elements as zero so projected_mem_space is freed */ + if(!storage->list[i].sub_dset[j].dset) + select_nelmts = (hssize_t)0; + } /* end if */ + + /* If there are not elements selected in this mapping, free + * projected_mem_space, otherwise update tot_nelmts */ + if(select_nelmts == (hssize_t)0) { + if(H5S_close(storage->list[i].sub_dset[j].projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected memory space") + storage->list[i].sub_dset[j].projected_mem_space = NULL; + } /* end if */ + else + *tot_nelmts += (hsize_t)select_nelmts; + } /* end if */ + } /* end for */ + } /* end if */ + else { + if(storage->list[i].source_dset.clipped_virtual_select) { + /* Project intersection of file space and mapping virtual space onto + * memory space */ + if(H5S_select_project_intersection(file_space, mem_space, storage->list[i].source_dset.clipped_virtual_select, &storage->list[i].source_dset.projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "can't project virtual intersection onto memory space") + + /* Check number of elements selected, add to tot_nelmts */ + if((select_nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(storage->list[i].source_dset.projected_mem_space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") + + /* Check if anything is selected */ + if(select_nelmts > (hssize_t)0) { + /* Open source dataset */ + if(!storage->list[i].source_dset.dset) + /* Try to open dataset */ + if(H5D__virtual_open_source_dset(io_info->dset, &storage->list[i], &storage->list[i].source_dset, io_info->dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTOPENOBJ, FAIL, "unable to open source dataset") + + /* If the source dataset is not open, mark the selected elements + * as zero so projected_mem_space is freed */ + if(!storage->list[i].source_dset.dset) + select_nelmts = (hssize_t)0; + } /* end if */ + + /* If there are not elements selected in this mapping, free + * projected_mem_space, otherwise update tot_nelmts */ + if(select_nelmts == (hssize_t)0) { + if(H5S_close(storage->list[i].source_dset.projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected memory space") + storage->list[i].source_dset.projected_mem_space = NULL; + } /* end if */ + else + *tot_nelmts += (hsize_t)select_nelmts; + } /* end if */ + else { + /* If there is no clipped_dim_virtual, this must be an unlimited + * selection whose dataset was not found in the last call to + * H5Dget_space(). Do not attempt to open it as this might + * affect the extent and we are not going to recalculate it + * here. */ + HDassert(storage->list[i].unlim_dim_virtual >= 0); + HDassert(!storage->list[i].source_dset.dset); + } /* end else */ + } /* end else */ + } /* end for */ + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_pre_io() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_post_io + * + * Purpose: Frees memory structures allocated by H5D__virtual_pre_io. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * June 4, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_post_io(H5O_storage_virtual_t *storage) +{ + size_t i, j; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(storage); + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nused; i++) + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + /* Iterate over sub-source dsets */ + for(j = storage->list[i].sub_dset_io_start; + j < storage->list[i].sub_dset_io_end; j++) + /* Close projected memory space */ + if(storage->list[i].sub_dset[j].projected_mem_space) { + if(H5S_close(storage->list[i].sub_dset[j].projected_mem_space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close temporary space") + storage->list[i].sub_dset[j].projected_mem_space = NULL; + } /* end if */ + } /* end if */ + else + /* Close projected memory space */ + if(storage->list[i].source_dset.projected_mem_space) { + if(H5S_close(storage->list[i].source_dset.projected_mem_space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close temporary space") + storage->list[i].source_dset.projected_mem_space = NULL; + } /* end if */ + + /* Note the lack of a done: label. This is because there are no HGOTO_ERROR + * calls. If one is added, a done: label must also be added */ + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_post_io() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_read_one + * + * Purpose: Read from a singe source dataset in a virtual dataset. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 15, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_read_one(H5D_io_info_t *io_info, const H5D_type_info_t *type_info, + const H5S_t *file_space, H5O_storage_virtual_srcdset_t *source_dset) +{ + H5S_t *projected_src_space = NULL; /* File space for selection in a single source dataset */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + HDassert(source_dset); + + /* Only perform I/O if there is a projected memory space, otherwise there + * were no elements in the projection or the source dataset could not be + * opened */ + if(source_dset->projected_mem_space) { + HDassert(source_dset->dset); + HDassert(source_dset->clipped_source_select); + + /* Project intersection of file space and mapping virtual space onto + * mapping source space */ + if(H5S_select_project_intersection(source_dset->clipped_virtual_select, source_dset->clipped_source_select, file_space, &projected_src_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "can't project virtual intersection onto source space") + + /* Perform read on source dataset */ + if(H5D__read(source_dset->dset, type_info->dst_type_id, source_dset->projected_mem_space, projected_src_space, io_info->dxpl_id, io_info->u.rbuf) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "can't read source dataset") + + /* Close projected_src_space */ + if(H5S_close(projected_src_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected source space") + projected_src_space = NULL; + } /* end if */ + +done: + /* Release allocated resources on failure */ + if(projected_src_space) { + HDassert(ret_value < 0); + if(H5S_close(projected_src_space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected source space") + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_read_one() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_read + * + * Purpose: Read from a virtual dataset. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_read(H5D_io_info_t *io_info, const H5D_type_info_t *type_info, + hsize_t nelmts, const H5S_t *file_space, const H5S_t *mem_space, + H5D_chunk_map_t H5_ATTR_UNUSED *fm) +{ + H5O_storage_virtual_t *storage; /* Convenient pointer into layout struct */ + hsize_t tot_nelmts; /* Total number of elements mapped to mem_space */ + H5S_t *fill_space = NULL; /* Space to fill with fill value */ + size_t i, j; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(io_info); + HDassert(io_info->u.rbuf); + HDassert(type_info); + HDassert(mem_space); + HDassert(file_space); + + storage = &io_info->dset->shared->layout.storage.u.virt; + HDassert((storage->view == H5D_VDS_FIRST_MISSING) || (storage->view == H5D_VDS_LAST_AVAILABLE)); + +#ifdef H5_HAVE_PARALLEL + /* Parallel reads are not supported (yet) */ + if(H5F_HAS_FEATURE(io_info->dset->oloc.file, H5FD_FEAT_HAS_MPI)) + HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "parallel reads not supported on virtual datasets") +#endif /* H5_HAVE_PARALLEL */ + + /* Prepare for I/O operation */ + if(H5D__virtual_pre_io(io_info, storage, file_space, mem_space, &tot_nelmts) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "unable to prepare for I/O operation") + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nused; i++) { + /* Sanity check that the virtual space has been patched by now */ + HDassert(storage->list[i].virtual_space_status == H5O_VIRTUAL_STATUS_CORRECT); + + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + /* Iterate over sub-source dsets */ + for(j = storage->list[i].sub_dset_io_start; + j < storage->list[i].sub_dset_io_end; j++) + if(H5D__virtual_read_one(io_info, type_info, file_space, &storage->list[i].sub_dset[j]) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "unable to read source dataset") + } /* end if */ + else + /* Read from source dataset */ + if(H5D__virtual_read_one(io_info, type_info, file_space, &storage->list[i].source_dset) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "unable to read source dataset") + } /* end for */ + + /* Fill unmapped part of buffer with fill value */ + if(tot_nelmts < nelmts) { + H5D_fill_value_t fill_status; /* Fill value status */ + + /* Check the fill value status */ + if(H5P_is_fill_value_defined(&io_info->dset->shared->dcpl_cache.fill, &fill_status) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't tell if fill value defined") + + /* Always write fill value to memory buffer unless it is undefined */ + if(fill_status != H5D_FILL_VALUE_UNDEFINED) { + /* Start with fill space equal to memory space */ + if(NULL == (fill_space = H5S_copy(mem_space, FALSE, TRUE))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy memory selection") + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nused; i++) + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + /* Iterate over sub-source dsets */ + for(j = storage->list[i].sub_dset_io_start; + j < storage->list[i].sub_dset_io_end; j++) + if(storage->list[i].sub_dset[j].projected_mem_space) + if(H5S_select_subtract(fill_space, storage->list[i].sub_dset[j].projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "unable to clip fill selection") + } /* end if */ + else + if(storage->list[i].source_dset.projected_mem_space) + /* Subtract projected memory space from fill space */ + if(H5S_select_subtract(fill_space, storage->list[i].source_dset.projected_mem_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "unable to clip fill selection") + + /* Write fill values to memory buffer */ + if(H5D__fill(io_info->dset->shared->dcpl_cache.fill.buf, io_info->dset->shared->type, io_info->u.rbuf, type_info->mem_type, fill_space, io_info->dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "filling buf failed") + +#ifndef NDEBUG + /* Make sure the total number of elements written (including fill + * values) >= nelmts */ + { + hssize_t select_nelmts; /* Number of elements in selection */ + + /* Get number of elements in fill dataspace */ + if((select_nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(fill_space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") + + /* Verify number of elements is correct. Note that since we + * don't check for overlap we can't assert that these are equal + */ + HDassert((tot_nelmts + (hsize_t)select_nelmts) >= nelmts); + } /* end block */ +#endif /* NDEBUG */ + } /* end if */ + } /* end if */ + +done: + /* Cleanup I/O operation */ + if(H5D__virtual_post_io(storage) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't cleanup I/O operation") + + /* Close fill space */ + if(fill_space) + if(H5S_close(fill_space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close fill space") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_read() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_write_one + * + * Purpose: Write to a singe source dataset in a virtual dataset. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 15, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_write_one(H5D_io_info_t *io_info, const H5D_type_info_t *type_info, + const H5S_t *file_space, H5O_storage_virtual_srcdset_t *source_dset) +{ + H5S_t *projected_src_space = NULL; /* File space for selection in a single source dataset */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + HDassert(source_dset); + + /* Only perform I/O if there is a projected memory space, otherwise there + * were no elements in the projection */ + if(source_dset->projected_mem_space) { + HDassert(source_dset->dset); + HDassert(source_dset->clipped_source_select); + + /* In the future we may wish to extent this implementation to extend + * source datasets if a write to a virtual dataset goes past the current + * extent in the unlimited dimension. -NAF */ + /* Project intersection of file space and mapping virtual space onto + * mapping source space */ + if(H5S_select_project_intersection(source_dset->virtual_select, source_dset->clipped_source_select, file_space, &projected_src_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "can't project virtual intersection onto source space") + + /* Perform write on source dataset */ + if(H5D__write(source_dset->dset, type_info->dst_type_id, source_dset->projected_mem_space, projected_src_space, io_info->dxpl_id, io_info->u.wbuf) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "can't write to source dataset") + + /* Close projected_src_space */ + if(H5S_close(projected_src_space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected source space") + projected_src_space = NULL; + } /* end if */ + +done: + /* Release allocated resources on failure */ + if(projected_src_space) { + HDassert(ret_value < 0); + if(H5S_close(projected_src_space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't close projected source space") + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_write_one() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_write + * + * Purpose: Write to a virtual dataset. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_write(H5D_io_info_t *io_info, const H5D_type_info_t *type_info, + hsize_t nelmts, const H5S_t *file_space, const H5S_t *mem_space, + H5D_chunk_map_t H5_ATTR_UNUSED *fm) +{ + H5O_storage_virtual_t *storage; /* Convenient pointer into layout struct */ + hsize_t tot_nelmts; /* Total number of elements mapped to mem_space */ + size_t i, j; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(io_info); + HDassert(io_info->u.wbuf); + HDassert(type_info); + HDassert(mem_space); + HDassert(file_space); + + storage = &io_info->dset->shared->layout.storage.u.virt; + HDassert((storage->view == H5D_VDS_FIRST_MISSING) || (storage->view == H5D_VDS_LAST_AVAILABLE)); + +#ifdef H5_HAVE_PARALLEL + /* Parallel writes are not supported (yet) */ + if(H5F_HAS_FEATURE(io_info->dset->oloc.file, H5FD_FEAT_HAS_MPI)) + HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "parallel writes not supported on virtual datasets") +#endif /* H5_HAVE_PARALLEL */ + + /* Prepare for I/O operation */ + if(H5D__virtual_pre_io(io_info, storage, file_space, mem_space, &tot_nelmts) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCLIP, FAIL, "unable to prepare for I/O operation") + + /* Fail if there are unmapped parts of the selection as they would not be + * written */ + if(tot_nelmts != nelmts) + HGOTO_ERROR(H5E_DATASPACE, H5E_BADVALUE, FAIL, "write requested to unmapped portion of virtual dataset") + + /* Iterate over mappings */ + for(i = 0; i < storage->list_nused; i++) { + /* Sanity check that virtual space has been patched by now */ + HDassert(storage->list[i].virtual_space_status == H5O_VIRTUAL_STATUS_CORRECT); + + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + /* Iterate over sub-source dsets */ + for(j = storage->list[i].sub_dset_io_start; + j < storage->list[i].sub_dset_io_end; j++) + if(H5D__virtual_write_one(io_info, type_info, file_space, &storage->list[i].sub_dset[j]) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "unable to write to source dataset") + } /* end if */ + else + /* Write to source dataset */ + if(H5D__virtual_write_one(io_info, type_info, file_space, &storage->list[i].source_dset) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "unable to write to source dataset") + } /* end for */ + +done: + /* Cleanup I/O operation */ + if(H5D__virtual_post_io(storage) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "can't cleanup I/O operation") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_write() */ + + +/*------------------------------------------------------------------------- + * Function: H5D__virtual_flush + * + * Purpose: Writes all dirty data to disk. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * February 6, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5D__virtual_flush(H5D_t *dset, hid_t dxpl_id) +{ + H5O_storage_virtual_t *storage; /* Convenient pointer into layout struct */ + size_t i, j; /* Local index variables */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(dset); + + storage = &dset->shared->layout.storage.u.virt; + + /* Flush only open datasets */ + for(i = 0; i < storage->list_nused; i++) + /* Check for "printf" source dataset resolution */ + if(storage->list[i].psfn_nsubs || storage->list[i].psdn_nsubs) { + /* Iterate over sub-source dsets */ + for(j = 0; j < storage->list[i].sub_dset_nused; j++) + if(storage->list[i].sub_dset[j].dset) + /* Flush source dataset */ + if(H5D__flush_real(storage->list[i].sub_dset[j].dset, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_WRITEERROR, FAIL, "unable to flush source dataset") + } /* end if */ + else + if(storage->list[i].source_dset.dset) + /* Flush source dataset */ + if(H5D__flush_real(storage->list[i].source_dset.dset, dxpl_id) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "unable to write to source dataset") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5D__virtual_flush() */ + diff --git a/src/H5Edefin.h b/src/H5Edefin.h index 183f72c..066c35d 100644 --- a/src/H5Edefin.h +++ b/src/H5Edefin.h @@ -194,6 +194,7 @@ hid_t H5E_CANTSELECT_g = FAIL; /* Can't select hyperslab */ hid_t H5E_CANTNEXT_g = FAIL; /* Can't move to next iterator location */ hid_t H5E_BADSELECT_g = FAIL; /* Invalid selection */ hid_t H5E_CANTCOMPARE_g = FAIL; /* Can't compare objects */ +hid_t H5E_CANTAPPEND_g = FAIL; /* Can't append object */ /* Argument errors */ hid_t H5E_UNINITIALIZED_g = FAIL; /* Information is uinitialized */ diff --git a/src/H5Einit.h b/src/H5Einit.h index 9724748..35049b2 100644 --- a/src/H5Einit.h +++ b/src/H5Einit.h @@ -740,6 +740,11 @@ if((msg = H5E_create_msg(cls, H5E_MINOR, "Can't compare objects"))==NULL) HGOTO_ERROR(H5E_ERROR, H5E_CANTINIT, FAIL, "error message initialization failed") if((H5E_CANTCOMPARE_g = H5I_register(H5I_ERROR_MSG, msg, FALSE))<0) HGOTO_ERROR(H5E_ERROR, H5E_CANTREGISTER, FAIL, "can't register error message") +assert(H5E_CANTAPPEND_g==(-1)); +if((msg = H5E_create_msg(cls, H5E_MINOR, "Can't append object"))==NULL) + HGOTO_ERROR(H5E_ERROR, H5E_CANTINIT, FAIL, "error message initialization failed") +if((H5E_CANTAPPEND_g = H5I_register(H5I_ERROR_MSG, msg, FALSE))<0) + HGOTO_ERROR(H5E_ERROR, H5E_CANTREGISTER, FAIL, "can't register error message") /* Argument errors */ assert(H5E_UNINITIALIZED_g==(-1)); diff --git a/src/H5Epubgen.h b/src/H5Epubgen.h index e79106f..8b60079 100644 --- a/src/H5Epubgen.h +++ b/src/H5Epubgen.h @@ -328,12 +328,14 @@ H5_DLLVAR hid_t H5E_CANTRECV_g; /* Can't receive data */ #define H5E_CANTNEXT (H5OPEN H5E_CANTNEXT_g) #define H5E_BADSELECT (H5OPEN H5E_BADSELECT_g) #define H5E_CANTCOMPARE (H5OPEN H5E_CANTCOMPARE_g) +#define H5E_CANTAPPEND (H5OPEN H5E_CANTAPPEND_g) H5_DLLVAR hid_t H5E_CANTCLIP_g; /* Can't clip hyperslab region */ H5_DLLVAR hid_t H5E_CANTCOUNT_g; /* Can't count elements */ H5_DLLVAR hid_t H5E_CANTSELECT_g; /* Can't select hyperslab */ H5_DLLVAR hid_t H5E_CANTNEXT_g; /* Can't move to next iterator location */ H5_DLLVAR hid_t H5E_BADSELECT_g; /* Invalid selection */ H5_DLLVAR hid_t H5E_CANTCOMPARE_g; /* Can't compare objects */ +H5_DLLVAR hid_t H5E_CANTAPPEND_g; /* Can't append object */ /* Argument errors */ #define H5E_UNINITIALIZED (H5OPEN H5E_UNINITIALIZED_g) diff --git a/src/H5Eterm.h b/src/H5Eterm.h index 5db503c..bf39a6b 100644 --- a/src/H5Eterm.h +++ b/src/H5Eterm.h @@ -195,7 +195,8 @@ H5E_CANTCOUNT_g= H5E_CANTSELECT_g= H5E_CANTNEXT_g= H5E_BADSELECT_g= -H5E_CANTCOMPARE_g= +H5E_CANTCOMPARE_g= +H5E_CANTAPPEND_g= /* Argument errors */ H5E_UNINITIALIZED_g= diff --git a/src/H5Fint.c b/src/H5Fint.c index 0e77349..c9e1ac0 100644 --- a/src/H5Fint.c +++ b/src/H5Fint.c @@ -1653,6 +1653,9 @@ done: * then increments the pointer to the first byte after the * address. An undefined value is stored as all 1's. * + * Note this function is almost identical to H5F_size_encode. + * Changes should be made in both places. + * * Return: void * * Programmer: Robb Matzke @@ -1725,6 +1728,9 @@ H5F_addr_encode(const H5F_t *f, uint8_t **pp/*in,out*/, haddr_t addr) * If the value read is all 1's then the address is returned * with an undefined value. * + * Note this function is almost identical to H5F_size_decode. + * Changes should be made in both places. + * * Return: void * * Programmer: Robb Matzke @@ -1815,6 +1821,127 @@ H5F_addr_decode(const H5F_t *f, const uint8_t **pp/*in,out*/, haddr_t *addr_p/*o /*------------------------------------------------------------------------- + * Function: H5F_size_encode + * + * Purpose: Encodes a size into the buffer pointed to by *PP and then + * increments the pointer to the first byte after the size. + * An undefined value is stored as all 1's. If size cannot + * be HSIZE_UNDEF, then you can use H5F_ENCODE_LENGTH + * instead. + * + * Note this function is almost identical to H5F_addr_encode + * and H5F_addr_encode_len. Changes should be made in both + * places. + * + * Return: void + * + * Programmer: Neil Fortner + * Friday, April 10, 2015 + * + *------------------------------------------------------------------------- + */ +void +H5F_size_encode(const H5F_t *f, uint8_t **pp/*in,out*/, hsize_t size) +{ + unsigned u; /* Local index variable */ + + /* Use FUNC_ENTER_NOAPI_NOINIT_NOERR here to avoid performance issues */ + FUNC_ENTER_NOAPI_NOINIT_NOERR + + HDassert(f); + HDassert(pp && *pp); + + if(size != HSIZE_UNDEF) { + for(u = 0; u < H5F_SIZEOF_SIZE(f); u++) { + *(*pp)++ = (uint8_t)(size & 0xff); + size >>= 8; + } /* end for */ + HDassert("overflow" && 0 == size); + } /* end if */ + else { + for(u = 0; u < H5F_SIZEOF_SIZE(f); u++) + *(*pp)++ = 0xff; + } /* end else */ + + FUNC_LEAVE_NOAPI_VOID +} /* end H5F_size_encode() */ + + +/*------------------------------------------------------------------------- + * Function: H5F_size_decode + * + * Purpose: Decodes a size from the buffer pointed to by *PP and + * updates the pointer to point to the next byte after the + * size. + * + * If the value read is all 1's then the size is returned + * with an undefined value. If size cannot be HSIZE_UNDEF, + * then you can use H5F_DECODE_LENGTH instead. + * + * Note this function is almost identical to H5F_addr_decode + * and H5F_addr_decode_len. Changes should be made in both + * places. + * + * Return: void + * + * Programmer: Neil Fortner + * Friday, April 10, 2015 + * + *------------------------------------------------------------------------- + */ +void +H5F_size_decode(const H5F_t *f, const uint8_t **pp/*in,out*/, + hsize_t *size_p/*out*/) +{ + hbool_t all_zero = TRUE; /* True if address was all zeroes */ + unsigned u; /* Local index variable */ + + /* Use FUNC_ENTER_NOAPI_NOINIT_NOERR here to avoid performance issues */ + FUNC_ENTER_NOAPI_NOINIT_NOERR + + HDassert(f); + HDassert(pp && *pp); + HDassert(size_p); + + /* Reset value in destination */ + *size_p = 0; + + /* Decode bytes from size */ + for(u = 0; u < H5F_SIZEOF_SIZE(f); u++) { + uint8_t c; /* Local decoded byte */ + + /* Get decoded byte (and advance pointer) */ + c = *(*pp)++; + + /* Check for non-undefined size byte value */ + if(c != 0xff) + all_zero = FALSE; + + if(u < sizeof(*size_p)) { + haddr_t tmp = c; /* Local copy of size, for casting */ + + /* Shift decoded byte to correct position */ + tmp <<= (u * 8); /*use tmp to get casting right */ + + /* Merge into already decoded bytes */ + *size_p |= tmp; + } /* end if */ + else + if(!all_zero) + HDassert(0 == **pp); /*overflow */ + } /* end for */ + + /* If 'all_zero' is still TRUE, the size_p was entirely composed of '0xff' + * bytes, which is the encoded form of 'HSIZE_UNDEF', so set the destination + * to that value */ + if(all_zero) + *size_p = HSIZE_UNDEF; + + FUNC_LEAVE_NOAPI_VOID +} /* end H5F_size_decode() */ + + +/*------------------------------------------------------------------------- * Function: H5F_set_grp_btree_shared * * Purpose: Set the grp_btree_shared field with a valid ref-count pointer. diff --git a/src/H5Fprivate.h b/src/H5Fprivate.h index 36d7429..1533d2c 100644 --- a/src/H5Fprivate.h +++ b/src/H5Fprivate.h @@ -667,6 +667,12 @@ H5_DLL void H5F_addr_encode_len(size_t addr_len, uint8_t **pp, haddr_t addr); H5_DLL void H5F_addr_decode(const H5F_t *f, const uint8_t **pp, haddr_t *addr_p); H5_DLL void H5F_addr_decode_len(size_t addr_len, const uint8_t **pp, haddr_t *addr_p); +/* Size-related functions */ +H5_DLL void H5F_size_encode(const H5F_t *f, uint8_t **pp/*in,out*/, + hsize_t size); +H5_DLL void H5F_size_decode(const H5F_t *f, const uint8_t **pp/*in,out*/, + hsize_t *size_p/*out*/); + /* File access property list callbacks */ H5_DLL herr_t H5P_facc_close(hid_t dxpl_id, void *close_data); @@ -721,6 +721,50 @@ done: /*------------------------------------------------------------------------- + * Function: H5HG_get_obj_size + * + * Purpose: Returns the size of a global heap object. + * Return: Success: Non-negative + * + * Failure: Negative + * + * Programmer: Neil Fortner + * Thursday, February 12, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5HG_get_obj_size(H5F_t *f, hid_t dxpl_id, H5HG_t *hobj, size_t *obj_size) +{ + H5HG_heap_t *heap = NULL; /* Pointer to global heap object */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI_TAG(dxpl_id, H5AC__GLOBALHEAP_TAG, FAIL) + + /* Check args */ + HDassert(f); + HDassert(hobj); + HDassert(obj_size); + + /* Load the heap */ + if(NULL == (heap = H5HG_protect(f, dxpl_id, hobj->addr, H5AC__READ_ONLY_FLAG))) + HGOTO_ERROR(H5E_HEAP, H5E_CANTPROTECT, FAIL, "unable to protect global heap") + + HDassert(hobj->idx < heap->nused); + HDassert(heap->obj[hobj->idx].begin); + + /* Set object size */ + *obj_size = heap->obj[hobj->idx].size; + +done: + if(heap && H5AC_unprotect(f, dxpl_id, H5AC_GHEAP, hobj->addr, heap, H5AC__NO_FLAGS_SET) < 0) + HDONE_ERROR(H5E_HEAP, H5E_CANTUNPROTECT, FAIL, "unable to release object header") + + FUNC_LEAVE_NOAPI_TAG(ret_value, FAIL) +} /* end H5HG_get_obj_size() */ + + +/*------------------------------------------------------------------------- * Function: H5HG_remove * * Purpose: Removes the specified object from the global heap. diff --git a/src/H5HGprivate.h b/src/H5HGprivate.h index 3765c47..ad0da76 100644 --- a/src/H5HGprivate.h +++ b/src/H5HGprivate.h @@ -60,6 +60,7 @@ H5_DLL herr_t H5HG_insert(H5F_t *f, hid_t dxpl_id, size_t size, void *obj, H5HG_t *hobj/*out*/); H5_DLL void *H5HG_read(H5F_t *f, hid_t dxpl_id, H5HG_t *hobj, void *object, size_t *buf_size/*out*/); H5_DLL int H5HG_link(H5F_t *f, hid_t dxpl_id, const H5HG_t *hobj, int adjust); +H5_DLL herr_t H5HG_get_obj_size(H5F_t *f, hid_t dxpl_id, H5HG_t *hobj, size_t *obj_size); H5_DLL herr_t H5HG_remove(H5F_t *f, hid_t dxpl_id, H5HG_t *hobj); /* Support routines */ diff --git a/src/H5Olayout.c b/src/H5Olayout.c index 8821694..6018539 100644 --- a/src/H5Olayout.c +++ b/src/H5Olayout.c @@ -100,6 +100,7 @@ H5O_layout_decode(H5F_t *f, hid_t H5_ATTR_UNUSED dxpl_id, H5O_t H5_ATTR_UNUSED * unsigned H5_ATTR_UNUSED mesg_flags, unsigned H5_ATTR_UNUSED *ioflags, const uint8_t *p) { H5O_layout_t *mesg = NULL; + uint8_t *heap_block = NULL; unsigned u; void *ret_value; /* Return value */ @@ -190,7 +191,7 @@ H5O_layout_decode(H5F_t *f, hid_t H5_ATTR_UNUSED dxpl_id, H5O_t H5_ATTR_UNUSED * } /* end if */ else { /* Layout class */ - mesg->type = (H5D_layout_t)*p++; + mesg->type = mesg->storage.type = (H5D_layout_t)*p++; /* Interpret the rest of the message according to the layout class */ switch(mesg->type) { @@ -241,6 +242,137 @@ H5O_layout_decode(H5F_t *f, hid_t H5_ATTR_UNUSED dxpl_id, H5O_t H5_ATTR_UNUSED * mesg->ops = H5D_LOPS_CHUNK; break; + case H5D_VIRTUAL: + /* Heap information */ + H5F_addr_decode(f, &p, &(mesg->storage.u.virt.serial_list_hobjid.addr)); + UINT32DECODE(p, mesg->storage.u.virt.serial_list_hobjid.idx); + + /* Initialize other fields */ + mesg->storage.u.virt.list_nused = 0; + mesg->storage.u.virt.list = NULL; + mesg->storage.u.virt.list_nalloc = 0; + mesg->storage.u.virt.view = H5D_VDS_ERROR; + mesg->storage.u.virt.printf_gap = HSIZE_UNDEF; + mesg->storage.u.virt.source_fapl = -1; + mesg->storage.u.virt.source_dapl = -1; + mesg->storage.u.virt.init = FALSE; + + /* Decode heap block if it exists */ + if(mesg->storage.u.virt.serial_list_hobjid.addr != HADDR_UNDEF) { + const uint8_t *heap_block_p; + size_t block_size = 0; + size_t tmp_size; + hsize_t tmp_hsize; + uint32_t stored_chksum; + uint32_t computed_chksum; + size_t i; + + /* Read heap */ + if(NULL == (heap_block = (uint8_t *)H5HG_read(f, dxpl_id, &(mesg->storage.u.virt.serial_list_hobjid), NULL, &block_size))) + HGOTO_ERROR(H5E_OHDR, H5E_READERROR, NULL, "Unable to read global heap block") + + heap_block_p = (const uint8_t *)heap_block; + + /* Number of entries */ + H5F_DECODE_LENGTH(f, heap_block_p, tmp_hsize) + + /* Allocate entry list */ + if(NULL == (mesg->storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_calloc((size_t)tmp_hsize * sizeof(H5O_storage_virtual_ent_t)))) + HGOTO_ERROR(H5E_OHDR, H5E_RESOURCE, NULL, "unable to allocate heap block") + mesg->storage.u.virt.list_nalloc = (size_t)tmp_hsize; + mesg->storage.u.virt.list_nused = (size_t)tmp_hsize; + + /* Decode each entry */ + for(i = 0; i < mesg->storage.u.virt.list_nused; i++) { + /* Source file name */ + tmp_size = HDstrlen((const char *)heap_block_p) + 1; + if(NULL == (mesg->storage.u.virt.list[i].source_file_name = (char *)H5MM_malloc(tmp_size))) + HGOTO_ERROR(H5E_OHDR, H5E_RESOURCE, NULL, "unable to allocate memory for source file name") + (void)HDmemcpy(mesg->storage.u.virt.list[i].source_file_name, heap_block_p, tmp_size); + heap_block_p += tmp_size; + + /* Source dataset name */ + tmp_size = HDstrlen((const char *)heap_block_p) + 1; + if(NULL == (mesg->storage.u.virt.list[i].source_dset_name = (char *)H5MM_malloc(tmp_size))) + HGOTO_ERROR(H5E_OHDR, H5E_RESOURCE, NULL, "unable to allocate memory for source dataset name") + (void)HDmemcpy(mesg->storage.u.virt.list[i].source_dset_name, heap_block_p, tmp_size); + heap_block_p += tmp_size; + + /* Source selection */ + if(H5S_SELECT_DESERIALIZE(f, &mesg->storage.u.virt.list[i].source_select, &heap_block_p) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTDECODE, NULL, "can't decode source space selection") + + /* Virtual selection */ + if(H5S_SELECT_DESERIALIZE(f, &mesg->storage.u.virt.list[i].source_dset.virtual_select, &heap_block_p) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTDECODE, NULL, "can't decode virtual space selection") + + /* Parse source file and dataset names for "printf" + * style format specifiers */ + if(H5D_virtual_parse_source_name(mesg->storage.u.virt.list[i].source_file_name, &mesg->storage.u.virt.list[i].parsed_source_file_name, &mesg->storage.u.virt.list[i].psfn_static_strlen, &mesg->storage.u.virt.list[i].psfn_nsubs) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTINIT, NULL, "can't parse source file name") + if(H5D_virtual_parse_source_name(mesg->storage.u.virt.list[i].source_dset_name, &mesg->storage.u.virt.list[i].parsed_source_dset_name, &mesg->storage.u.virt.list[i].psdn_static_strlen, &mesg->storage.u.virt.list[i].psdn_nsubs) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTINIT, NULL, "can't parse source dataset name") + + /* Set source names in source_dset struct */ + if((mesg->storage.u.virt.list[i].psfn_nsubs == 0) + && (mesg->storage.u.virt.list[i].psdn_nsubs == 0)) { + if(mesg->storage.u.virt.list[i].parsed_source_file_name) + mesg->storage.u.virt.list[i].source_dset.file_name = mesg->storage.u.virt.list[i].parsed_source_file_name->name_segment; + else + mesg->storage.u.virt.list[i].source_dset.file_name = mesg->storage.u.virt.list[i].source_file_name; + if(mesg->storage.u.virt.list[i].parsed_source_dset_name) + mesg->storage.u.virt.list[i].source_dset.dset_name = mesg->storage.u.virt.list[i].parsed_source_dset_name->name_segment; + else + mesg->storage.u.virt.list[i].source_dset.dset_name = mesg->storage.u.virt.list[i].source_dset_name; + } /* end if */ + + /* unlim_dim fields */ + mesg->storage.u.virt.list[i].unlim_dim_source = H5S_get_select_unlim_dim(mesg->storage.u.virt.list[i].source_select); + mesg->storage.u.virt.list[i].unlim_dim_virtual = H5S_get_select_unlim_dim(mesg->storage.u.virt.list[i].source_dset.virtual_select); + mesg->storage.u.virt.list[i].unlim_extent_source = HSIZE_UNDEF; + mesg->storage.u.virt.list[i].unlim_extent_virtual = HSIZE_UNDEF; + mesg->storage.u.virt.list[i].clip_size_source = HSIZE_UNDEF; + mesg->storage.u.virt.list[i].clip_size_virtual = HSIZE_UNDEF; + + /* Clipped selections */ + if(mesg->storage.u.virt.list[i].unlim_dim_virtual < 0) { + mesg->storage.u.virt.list[i].source_dset.clipped_source_select = mesg->storage.u.virt.list[i].source_select; + mesg->storage.u.virt.list[i].source_dset.clipped_virtual_select = mesg->storage.u.virt.list[i].source_dset.virtual_select; + } /* end if */ + + /* Check mapping for validity (do both pre and post + * checks here, since we had to allocate the entry list + * before decoding the selections anyways) */ + if(H5D_virtual_check_mapping_pre(mesg->storage.u.virt.list[i].source_dset.virtual_select, mesg->storage.u.virt.list[i].source_select, H5O_VIRTUAL_STATUS_INVALID) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_BADVALUE, NULL, "invalid mapping selections") + if(H5D_virtual_check_mapping_post(&mesg->storage.u.virt.list[i]) < 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "invalid mapping entry") + + /* Update min_dims */ + if(H5D_virtual_update_min_dims(mesg, i) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTINIT, NULL, "unable to update virtual dataset minimum dimensions") + } /* end for */ + + /* Read stored checksum */ + UINT32DECODE(heap_block_p, stored_chksum) + + /* Compute checksum */ + computed_chksum = H5_checksum_metadata(heap_block, block_size - (size_t)4, 0); + + /* Verify checksum */ + if(stored_chksum != computed_chksum) + HGOTO_ERROR(H5E_OHDR, H5E_BADVALUE, NULL, "incorrect metadata checksum for global heap block") + + /* Verify that the heap block size is correct */ + if((size_t)(heap_block_p - heap_block) != block_size) + HGOTO_ERROR(H5E_OHDR, H5E_BADVALUE, NULL, "incorrect heap block size") + } /* end if */ + + /* Set the layout operations */ + mesg->ops = H5D_LOPS_VIRTUAL; + + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -253,8 +385,14 @@ H5O_layout_decode(H5F_t *f, hid_t H5_ATTR_UNUSED dxpl_id, H5O_t H5_ATTR_UNUSED * done: if(ret_value == NULL) - if(mesg) + if(mesg) { + if(mesg->type == H5D_VIRTUAL) + if(H5D__virtual_reset_layout(mesg) < 0) + HDONE_ERROR(H5E_OHDR, H5E_CANTFREE, NULL, "unable to reset virtual layout") mesg = H5FL_FREE(H5O_layout_t, mesg); + } /* end if */ + + heap_block = (uint8_t *)H5MM_xfree(heap_block); FUNC_LEAVE_NOAPI(ret_value) } /* end H5O_layout_decode() */ @@ -294,6 +432,8 @@ static herr_t H5O_layout_encode(H5F_t *f, hbool_t H5_ATTR_UNUSED disable_shared, uint8_t *p, const void *_mesg) { const H5O_layout_t *mesg = (const H5O_layout_t *) _mesg; + uint8_t *heap_block = NULL; + size_t *str_size = NULL; unsigned u; herr_t ret_value = SUCCEED; /* Return value */ @@ -344,6 +484,106 @@ H5O_layout_encode(H5F_t *f, hbool_t H5_ATTR_UNUSED disable_shared, uint8_t *p, c UINT32ENCODE(p, mesg->u.chunk.dim[u]); break; + case H5D_VIRTUAL: + /* Create heap block if it has not been created yet */ + /* Note that we assume here that the contents of the heap block + * cannot change! If this ever stops being the case we must change + * this code to allow overwrites of the heap block. -NAF */ + if((mesg->storage.u.virt.serial_list_hobjid.addr == HADDR_UNDEF) + && (mesg->storage.u.virt.list_nused > 0)) { + uint8_t *heap_block_p; + size_t block_size; + hssize_t select_serial_size; + hsize_t tmp_hsize; + uint32_t chksum; + size_t i; + + /* Allocate array for caching results of strlen */ + if(NULL == (str_size = (size_t *)H5MM_malloc(2 * mesg->storage.u.virt.list_nused *sizeof(size_t)))) + HGOTO_ERROR(H5E_OHDR, H5E_RESOURCE, FAIL, "unable to allocate string length array") + + /* + * Calculate heap block size + */ + /* Number of entries */ + block_size = H5F_SIZEOF_SIZE(f); + + /* Calculate size of each entry */ + for(i = 0; i < mesg->storage.u.virt.list_nused; i++) { + HDassert(mesg->storage.u.virt.list[i].source_file_name); + HDassert(mesg->storage.u.virt.list[i].source_dset_name); + HDassert(mesg->storage.u.virt.list[i].source_select); + HDassert(mesg->storage.u.virt.list[i].source_dset.virtual_select); + + /* Source file name */ + str_size[2 * i] = HDstrlen(mesg->storage.u.virt.list[i].source_file_name) + (size_t)1; + block_size += str_size[2 * i]; + + /* Source dset name */ + str_size[(2 * i) + 1] = HDstrlen(mesg->storage.u.virt.list[i].source_dset_name) + (size_t)1; + block_size += str_size[(2 * i) + 1]; + + /* Source selection */ + if((select_serial_size = H5S_SELECT_SERIAL_SIZE(f, mesg->storage.u.virt.list[i].source_select)) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTENCODE, FAIL, "unable to check dataspace selection size") + block_size += (size_t)select_serial_size; + + /* Virtual dataset selection */ + if((select_serial_size = H5S_SELECT_SERIAL_SIZE(f, mesg->storage.u.virt.list[i].source_dset.virtual_select)) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTENCODE, FAIL, "unable to check dataspace selection size") + block_size += (size_t)select_serial_size; + } /* end for */ + + /* Checksum */ + block_size += 4; + + /* Allocate heap block */ + if(NULL == (heap_block = (uint8_t *)H5MM_malloc(block_size))) + HGOTO_ERROR(H5E_OHDR, H5E_RESOURCE, FAIL, "unable to allocate heap block") + + /* + * Encode heap block + */ + heap_block_p = heap_block; + + /* Number of entries */ + tmp_hsize = (hsize_t)mesg->storage.u.virt.list_nused; + H5F_ENCODE_LENGTH(f, heap_block_p, tmp_hsize) + + /* Encode each entry */ + for(i = 0; i < mesg->storage.u.virt.list_nused; i++) { + /* Source file name */ + (void)HDmemcpy((char *)heap_block_p, mesg->storage.u.virt.list[i].source_file_name, str_size[2 * i]); + heap_block_p += str_size[2 * i]; + + /* Source dataset name */ + (void)HDmemcpy((char *)heap_block_p, mesg->storage.u.virt.list[i].source_dset_name, str_size[(2 * i) + 1]); + heap_block_p += str_size[(2 * i) + 1]; + + /* Source selection */ + if(H5S_SELECT_SERIALIZE(f, mesg->storage.u.virt.list[i].source_select, &heap_block_p) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "unable to serialize source selection") + + /* Virtual selection */ + if(H5S_SELECT_SERIALIZE(f, mesg->storage.u.virt.list[i].source_dset.virtual_select, &heap_block_p) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "unable to serialize virtual selection") + } /* end for */ + + /* Checksum */ + chksum = H5_checksum_metadata(heap_block, block_size - (size_t)4, 0); + UINT32ENCODE(heap_block_p, chksum) + + /* Insert block into global heap */ + if(H5HG_insert(f, H5AC_ind_dxpl_id, block_size, heap_block, &((H5O_layout_t *)mesg)->storage.u.virt.serial_list_hobjid) < 0) /* Casting away const OK --NAF */ + HGOTO_ERROR(H5E_OHDR, H5E_CANTINSERT, FAIL, "unable to insert virtual dataset heap block") + } /* end if */ + + /* Heap information */ + H5F_addr_encode(f, &p, mesg->storage.u.virt.serial_list_hobjid.addr); + UINT32ENCODE(p, mesg->storage.u.virt.serial_list_hobjid.idx); + + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -351,6 +591,9 @@ H5O_layout_encode(H5F_t *f, hbool_t H5_ATTR_UNUSED disable_shared, uint8_t *p, c } /* end switch */ done: + heap_block = (uint8_t *)H5MM_xfree(heap_block); + str_size = (size_t *)H5MM_xfree(str_size); + FUNC_LEAVE_NOAPI(ret_value) } /* end H5O_layout_encode() */ @@ -403,6 +646,11 @@ H5O_layout_copy(const void *_mesg, void *_dest) if(dest->type == H5D_CHUNKED && dest->storage.u.chunk.ops) H5D_chunk_idx_reset(&dest->storage.u.chunk, FALSE); + /* Deep copy the entry list for virtual datasets */ + if(mesg->type == H5D_VIRTUAL) + if(H5D__virtual_copy_layout(dest) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, NULL, "unable to copy virtual layout") + /* Set return value */ ret_value = dest; @@ -468,19 +716,25 @@ static herr_t H5O_layout_reset(void *_mesg) { H5O_layout_t *mesg = (H5O_layout_t *)_mesg; + herr_t ret_value = SUCCEED; /* Return value */ - FUNC_ENTER_NOAPI_NOINIT_NOERR + FUNC_ENTER_NOAPI_NOINIT if(mesg) { /* Free the compact storage buffer */ if(H5D_COMPACT == mesg->type) mesg->storage.u.compact.buf = H5MM_xfree(mesg->storage.u.compact.buf); + else if(H5D_VIRTUAL == mesg->type) + /* Free the virtual entry list */ + if(H5D__virtual_reset_layout(mesg) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTFREE, FAIL, "unable to reset virtual layout") /* Reset the message */ mesg->type = H5D_CONTIGUOUS; } /* end if */ - FUNC_LEAVE_NOAPI(SUCCEED) +done: + FUNC_LEAVE_NOAPI(ret_value) } /* end H5O_layout_reset() */ @@ -560,6 +814,12 @@ H5O_layout_delete(H5F_t *f, hid_t dxpl_id, H5O_t *open_oh, void *_mesg) HGOTO_ERROR(H5E_OHDR, H5E_CANTFREE, FAIL, "unable to free raw data") break; + case H5D_VIRTUAL: /* Virtual dataset */ + /* Free the file space virtual dataset */ + if(H5D__virtual_delete(f, dxpl_id, &mesg->storage) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTFREE, FAIL, "unable to free raw data") + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -647,6 +907,13 @@ H5O_layout_copy_file(H5F_t *file_src, void *mesg_src, H5F_t *file_dst, } /* end if */ break; + case H5D_VIRTUAL: + /* Copy virtual layout. Always copy so the memory fields get copied + * properly. */ + if(H5D__virtual_copy(file_dst, layout_dst, dxpl_id) < 0) + HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, NULL, "unable to copy virtual storage") + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -686,7 +953,7 @@ H5O_layout_debug(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id, const vo FILE * stream, int indent, int fwidth) { const H5O_layout_t *mesg = (const H5O_layout_t *) _mesg; - unsigned u; + size_t u; FUNC_ENTER_NOAPI_NOINIT_NOERR @@ -709,7 +976,7 @@ H5O_layout_debug(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id, const vo "Number of dimensions:", (unsigned long)(mesg->u.chunk.ndims)); HDfprintf(stream, "%*s%-*s {", indent, "", fwidth, "Size:"); - for(u = 0; u < mesg->u.chunk.ndims; u++) + for(u = 0; u < (size_t)mesg->u.chunk.ndims; u++) HDfprintf(stream, "%s%lu", u ? ", " : "", (unsigned long)(mesg->u.chunk.dim[u])); HDfprintf(stream, "}\n"); @@ -746,6 +1013,26 @@ H5O_layout_debug(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id, const vo "Data Size:", mesg->storage.u.compact.size); break; + case H5D_VIRTUAL: + HDfprintf(stream, "%*s%-*s %s\n", indent, "", fwidth, + "Type:", "Virtual"); + HDfprintf(stream, "%*s%-*s %a\n", indent, "", fwidth, + "Global heap address:", mesg->storage.u.virt.serial_list_hobjid.addr); + HDfprintf(stream, "%*s%-*s %Zu\n", indent, "", fwidth, + "Global heap index:", mesg->storage.u.virt.serial_list_hobjid.idx); + for(u = 0; u < mesg->storage.u.virt.list_nused; u++) { + HDfprintf(stream, "%*sMapping %u:\n", indent, "", u); + HDfprintf(stream, "%*s%-*s %s\n", indent + 3, "", fwidth - 3, + "Virtual selection:", "<Not yet implemented>"); + HDfprintf(stream, "%*s%-*s %s\n", indent + 3, "", fwidth - 3, + "Source file name:", mesg->storage.u.virt.list[u].source_file_name); + HDfprintf(stream, "%*s%-*s %s\n", indent + 3, "", fwidth - 3, + "Source dataset name:", mesg->storage.u.virt.list[u].source_dset_name); + HDfprintf(stream, "%*s%-*s %s\n", indent + 3, "", fwidth - 3, + "Source selection:", "<Not yet implemented>"); + } /* end for */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: diff --git a/src/H5Oprivate.h b/src/H5Oprivate.h index dbe74f7..77a11cd 100644 --- a/src/H5Oprivate.h +++ b/src/H5Oprivate.h @@ -38,6 +38,7 @@ #include "H5private.h" /* Generic Functions */ #include "H5ACprivate.h" /* Metadata cache */ #include "H5Fprivate.h" /* File access */ +#include "H5HGprivate.h" /* Global Heaps */ #include "H5SLprivate.h" /* Skip lists */ #include "H5Tprivate.h" /* Datatype functions */ #include "H5Zprivate.h" /* I/O pipeline filters */ @@ -376,7 +377,8 @@ typedef struct H5O_efl_t { * for larger chunk dimensions, stores chunk indices into their own * message (the "layout index" message), adds features for compact/dense * storage of elements and/or chunk records, adds features for abbreviating - * the storage used for partial chunks on boundaries, etc. + * the storage used for partial chunks on boundaries, adds the virtual + * layout type, etc. */ #define H5O_LAYOUT_VERSION_4 4 @@ -414,12 +416,88 @@ typedef struct H5O_storage_compact_t { void *buf; /* Buffer for compact dataset */ } H5O_storage_compact_t; +typedef struct H5O_storage_virtual_srcdset_t { + /* Stored */ + struct H5S_t *virtual_select; /* Selection in the virtual dataset that is mapped to source selection */ + + /* Not stored */ + char *file_name; /* Source file name used for virtual dataset mapping */ + char *dset_name; /* Source dataset name used for virtual dataset mapping */ + struct H5S_t *clipped_source_select; /* Clipped version of source_select */ + struct H5S_t *clipped_virtual_select; /* Clipped version of virtual_select */ + struct H5D_t *dset; /* Source dataset */ + hbool_t dset_exists; /* Whether the dataset exists (was opened successfully) */ + + /* Temporary - only used during I/O operation, NULL at all other times */ + struct H5S_t *projected_mem_space; /* Selection within mem_space for this mapping */ +} H5O_storage_virtual_srcdset_t; + +typedef struct H5O_storage_virtual_name_seg_t { + char *name_segment; /* String for this name segment */ + struct H5O_storage_virtual_name_seg_t *next; /* Next name segment */ +} H5O_storage_virtual_name_seg_t; + +typedef enum H5O_virtual_space_status_t { + H5O_VIRTUAL_STATUS_INVALID = 0, /* Space extent is invalid */ + H5O_VIRTUAL_STATUS_SEL_BOUNDS, /* Space extent set to bounds of selection */ + H5O_VIRTUAL_STATUS_USER, /* Space extent provided by application */ + H5O_VIRTUAL_STATUS_CORRECT /* Space extent matches dataset */ +} H5O_virtual_space_status_t; + +typedef struct H5O_storage_virtual_ent_t { + /* Stored */ + H5O_storage_virtual_srcdset_t source_dset; /* Information about the source dataset */ + char *source_file_name; /* Original (unparsed) source file name */ + char *source_dset_name; /* Original (unparsed) source dataset name */ + struct H5S_t *source_select; /* Selection in the source dataset for mapping */ + + /* Not stored */ + H5O_storage_virtual_srcdset_t *sub_dset; /* Array of sub-source dataset info structs */ + size_t sub_dset_nalloc; /* Number of slots allocated in sub_dset */ + size_t sub_dset_nused; /* Number of slots "used" in sub_dset - essentially the farthest sub dataset in the extent */ + size_t sub_dset_io_start; /* First element in sub_dset involved in current I/O op. Field has no meaning and may be uninitialized at all other times */ + size_t sub_dset_io_end; /* First element in sub_dset outside of current I/O op. Field has no meaning and may be uninitialized at all other times */ + H5O_storage_virtual_name_seg_t *parsed_source_file_name; /* Parsed version of source_dset.file_name */ + size_t psfn_static_strlen; /* Length of parsed_source_file_name without block number substitutions */ + size_t psfn_nsubs; /* Number of block number substitutions in parsed_source_file_name */ + H5O_storage_virtual_name_seg_t *parsed_source_dset_name; /* Parsed version of source_dset.dset_name */ + size_t psdn_static_strlen; /* Length of parsed_source_dset_name without block number substitutions */ + size_t psdn_nsubs; /* Number of block number substitutions in parsed_source_dset_name */ + int unlim_dim_source; /* Unlimited dimension in source_select */ + int unlim_dim_virtual; /* Unlimited dimension in virtual_select */ + hsize_t unlim_extent_source; /* Extent of unlimited dimension in source dset last time virtual_select was patched to match selection */ + hsize_t unlim_extent_virtual; /* Extent of unlimited dimension in virtual dset last time source_select was patched to match selection */ + hsize_t clip_size_virtual; /* Size selection would be clipped to in virtual selection, ignoring other mappings, when source extent == unlim_extent_source */ + hsize_t clip_size_source; /* Size selection would be clipped to in source selection when virtual extent == unlim_extent_virtual */ + H5O_virtual_space_status_t source_space_status; /* Extent patching status of source_select */ + H5O_virtual_space_status_t virtual_space_status; /* Extent patching status of virtual_select */ +} H5O_storage_virtual_ent_t; + +typedef struct H5O_storage_virtual_t { + /* Stored in message */ + H5HG_t serial_list_hobjid; /* Global heap ID for the list of virtual mapping entries stored on disk */ + + /* Stored in heap */ + size_t list_nused; /* Number of array elements used in list */ + H5O_storage_virtual_ent_t *list; /* Array of virtual dataset mapping entries */ + + /* Not stored */ + size_t list_nalloc; /* Number of slots allocated */ + hsize_t min_dims[H5S_MAX_RANK]; /* Minimum extent of VDS (maximum of all non-unlimited selection bounds) */ + H5D_vds_view_t view; /* Method for calculating the extent of the virtual dataset with unlimited selections */ + hsize_t printf_gap; /* Maximum number of sequential missing source datasets before terminating the search for more */ + hid_t source_fapl; /* FAPL to use to open source files */ + hid_t source_dapl; /* DAPL to use to open source datasets */ + hbool_t init; /* Whether all information has been completely initialized */ +} H5O_storage_virtual_t; + typedef struct H5O_storage_t { H5D_layout_t type; /* Type of layout */ union { H5O_storage_contig_t contig; /* Information for contiguous storage */ H5O_storage_chunk_t chunk; /* Information for chunked storage */ H5O_storage_compact_t compact; /* Information for compact storage */ + H5O_storage_virtual_t virt; /* Information for virtual storage */ } u; } H5O_storage_t; diff --git a/src/H5Osdspace.c b/src/H5Osdspace.c index 8d357c2..50fba0b 100644 --- a/src/H5Osdspace.c +++ b/src/H5Osdspace.c @@ -312,7 +312,7 @@ H5O_sdspace_copy(const void *_mesg, void *_dest) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "memory allocation failed") /* Copy extent information */ - if(H5S_extent_copy(dest, mesg, TRUE) < 0) + if(H5S_extent_copy_real(dest, mesg, TRUE) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, NULL, "can't copy extent") /* Set return value */ @@ -467,7 +467,7 @@ H5O_sdspace_pre_copy_file(H5F_t H5_ATTR_UNUSED *file_src, const void *mesg_src, HGOTO_ERROR(H5E_DATASPACE, H5E_NOSPACE, FAIL, "dataspace extent allocation failed") /* Create a copy of the dataspace extent */ - if(H5S_extent_copy(udata->src_space_extent, src_space_extent, TRUE) < 0) + if(H5S_extent_copy_real(udata->src_space_extent, src_space_extent, TRUE) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, FAIL, "can't copy extent") } /* end if */ diff --git a/src/H5Pdapl.c b/src/H5Pdapl.c index 93d16bb..94ae0b4 100644 --- a/src/H5Pdapl.c +++ b/src/H5Pdapl.c @@ -61,6 +61,16 @@ #define H5D_ACS_PREEMPT_READ_CHUNKS_DEF H5D_CHUNK_CACHE_W0_DEFAULT #define H5D_ACS_PREEMPT_READ_CHUNKS_ENC H5P__encode_double #define H5D_ACS_PREEMPT_READ_CHUNKS_DEC H5P__decode_double +/* Definitions for VDS view option */ +#define H5D_ACS_VDS_VIEW_SIZE sizeof(H5D_vds_view_t) +#define H5D_ACS_VDS_VIEW_DEF H5D_VDS_LAST_AVAILABLE +#define H5D_ACS_VDS_VIEW_ENC H5P__dacc_vds_view_enc +#define H5D_ACS_VDS_VIEW_DEC H5P__dacc_vds_view_dec +/* Definitions for VDS printf gap */ +#define H5D_ACS_VDS_PRINTF_GAP_SIZE sizeof(hsize_t) +#define H5D_ACS_VDS_PRINTF_GAP_DEF (hsize_t)0 +#define H5D_ACS_VDS_PRINTF_GAP_ENC H5P__encode_hsize_t +#define H5D_ACS_VDS_PRINTF_GAP_DEC H5P__decode_hsize_t /******************/ /* Local Typedefs */ @@ -79,6 +89,10 @@ /* Property class callbacks */ static herr_t H5P__dacc_reg_prop(H5P_genclass_t *pclass); +/* Property list callbacks */ +static herr_t H5P__dacc_vds_view_enc(const void *value, void **pp, size_t *size); +static herr_t H5P__dacc_vds_view_dec(const void **pp, void *value); + /*********************/ /* Package Variables */ @@ -133,6 +147,8 @@ H5P__dacc_reg_prop(H5P_genclass_t *pclass) size_t rdcc_nslots = H5D_ACS_DATA_CACHE_NUM_SLOTS_DEF; /* Default raw data chunk cache # of slots */ size_t rdcc_nbytes = H5D_ACS_DATA_CACHE_BYTE_SIZE_DEF; /* Default raw data chunk cache # of bytes */ double rdcc_w0 = H5D_ACS_PREEMPT_READ_CHUNKS_DEF; /* Default raw data chunk cache dirty ratio */ + H5D_vds_view_t virtual_view = H5D_ACS_VDS_VIEW_DEF; /* Default VDS view option */ + hsize_t printf_gap = H5D_ACS_VDS_PRINTF_GAP_DEF; /* Default VDS printf gap */ herr_t ret_value = SUCCEED; /* Return value */ FUNC_ENTER_STATIC @@ -152,6 +168,18 @@ H5P__dacc_reg_prop(H5P_genclass_t *pclass) NULL, NULL, NULL, H5D_ACS_PREEMPT_READ_CHUNKS_ENC, H5D_ACS_PREEMPT_READ_CHUNKS_DEC, NULL, NULL, NULL, NULL) < 0) HGOTO_ERROR(H5E_PLIST, H5E_CANTINSERT, FAIL, "can't insert property into class") + /* Register the VDS view option */ + if(H5P_register_real(pclass, H5D_ACS_VDS_VIEW_NAME, H5D_ACS_VDS_VIEW_SIZE, &virtual_view, + NULL, NULL, NULL, H5D_ACS_VDS_VIEW_ENC, H5D_ACS_VDS_VIEW_DEC, + NULL, NULL, NULL, NULL) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINSERT, FAIL, "can't insert property into class") + + /* Register the VDS printf gap */ + if(H5P_register_real(pclass, H5D_ACS_VDS_PRINTF_GAP_NAME, H5D_ACS_VDS_PRINTF_GAP_SIZE, &printf_gap, + NULL, NULL, NULL, H5D_ACS_VDS_PRINTF_GAP_ENC, H5D_ACS_VDS_PRINTF_GAP_DEC, + NULL, NULL, NULL, NULL) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINSERT, FAIL, "can't insert property into class") + done: FUNC_LEAVE_NOAPI(ret_value) } /* end H5P__dacc_reg_prop() */ @@ -282,5 +310,255 @@ H5Pget_chunk_cache(hid_t dapl_id, size_t *rdcc_nslots, size_t *rdcc_nbytes, doub done: FUNC_LEAVE_API(ret_value) -} +} /* end H5Pget_chunk_cache() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pset_virtual_view + * + * Purpose: Takes the access property list for the virtual dataset, + * dapl_id, and the flag, view, and sets the VDS view + * according to the flag value. The view will include all + * data before the first missing mapped data found if the + * flag is set to H5D_VDS_FIRST_MISSING or to include all + * available mapped data if the flag is set to + * H5D_VDS_LAST_AVAIALBLE. Missing mapped data will be + * filled with the fill value according to the VDS creation + * property settings. For VDS with unlimited mappings, the + * view defines the extent. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 4, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pset_virtual_view(hid_t plist_id, H5D_vds_view_t view) +{ + H5P_genplist_t *plist; /* Property list pointer */ + herr_t ret_value = SUCCEED; /* return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "iDv", plist_id, view); + + /* Check argument */ + if((view != H5D_VDS_FIRST_MISSING) && (view != H5D_VDS_LAST_AVAILABLE)) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a valid bounds option") + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(plist_id, H5P_DATASET_ACCESS))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Update property list */ + if(H5P_set(plist, H5D_ACS_VDS_VIEW_NAME, &view) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "unable to set value") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pset_virtual_view() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_view + * + * Purpose: Takes the access property list for the virtual dataset, + * dapl_id, and gets the flag, view, set by the + * H5Pset_virtual_view call. The possible values of view are + * H5D_VDS_FIRST_MISSING or H5D_VDS_LAST_AVAIALBLE. + * + * Return: Success: H5D_VDS_FIRST_MISSING or + * H5D_VDS_LAST_AVAILABLE + * Failure: H5D_VDS_ERROR + * + * Programmer: Neil Fortner + * May 4, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pget_virtual_view(hid_t plist_id, H5D_vds_view_t *view) +{ + H5P_genplist_t *plist; /* Property list pointer */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "i*Dv", plist_id, view); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(plist_id, H5P_DATASET_ACCESS))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, H5D_VDS_ERROR, "can't find object for ID") + + /* Get value from property list */ + if(view) + if(H5P_get(plist, H5D_ACS_VDS_VIEW_NAME, view) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, H5D_VDS_ERROR, "unable to get value") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_view() */ + + +/*------------------------------------------------------------------------- + * Function: H5P__dacc_vds_view_enc + * + * Purpose: Callback routine which is called whenever the vds view + * property in the dataset access property list is encoded. + * + * Return: Success: Non-negative + * Failure: Negative + * + * Programmer: Neil Fortner + * Tuesday, May 5, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5P__dacc_vds_view_enc(const void *value, void **_pp, size_t *size) +{ + const H5D_vds_view_t *view = (const H5D_vds_view_t *)value; /* Create local alias for values */ + uint8_t **pp = (uint8_t **)_pp; + + FUNC_ENTER_STATIC_NOERR + + /* Sanity check */ + HDassert(view); + HDassert(size); + + if(NULL != *pp) + /* Encode EDC property */ + *(*pp)++ = (uint8_t)*view; + + /* Size of EDC property */ + (*size)++; + + FUNC_LEAVE_NOAPI(SUCCEED) +} /* end H5P__dacc_vds_view_enc() */ + + +/*------------------------------------------------------------------------- + * Function: H5P__dacc_vds_view_dec + * + * Purpose: Callback routine which is called whenever the vds view + * property in the dataset access property list is encoded. + * + * Return: Success: Non-negative + * Failure: Negative + * + * Programmer: Neil Fortner + * Tuesday, May 5, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5P__dacc_vds_view_dec(const void **_pp, void *_value) +{ + H5D_vds_view_t *view = (H5D_vds_view_t *)_value; + const uint8_t **pp = (const uint8_t **)_pp; + + FUNC_ENTER_STATIC_NOERR + + /* Sanity checks */ + HDassert(pp); + HDassert(*pp); + HDassert(view); + + /* Decode EDC property */ + *view = (H5D_vds_view_t)*(*pp)++; + + FUNC_LEAVE_NOAPI(SUCCEED) +} /* end H5P__dacc_vds_view_dec() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pset_virtual_printf_gap + * + * Purpose: Sets the access property list for the virtual dataset, + * dapl_id, to instruct the library to stop looking for the + * mapped data stored in the files and/or datasets with the + * printf-style names after not finding gap_size files and/or + * datasets. The found source files and datasets will + * determine the extent of the unlimited VDS with the printf + * -style mappings. + * + * For example, if regularly spaced blocks of VDS are mapped + * to datasets with the names d-1, d-2, d-3, ..., d-N, ..., + * and d-2 dataset is missing and gap_size is set to 0, then + * VDS will contain only data found in d-1. If d-2 and d-3 + * are missing and gap_size is set to 2, then VDS will + * contain the data from d-1, d-3, ..., d-N, .... The blocks + * that are mapped to d-2 and d-3 will be filled according to + * the VDS fill value setting. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 21, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pset_virtual_printf_gap(hid_t plist_id, hsize_t gap_size) +{ + H5P_genplist_t *plist; /* Property list pointer */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "ih", plist_id, gap_size); + + /* Check argument */ + if(gap_size == HSIZE_UNDEF) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a valid printf gap size") + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(plist_id, H5P_DATASET_ACCESS))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Update property list */ + if(H5P_set(plist, H5D_ACS_VDS_PRINTF_GAP_NAME, &gap_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "unable to set value") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pset_virtual_printf_gap() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_printf_gap + * + * Purpose: Gets the maximum number of missing printf-style files + * and/or datasets for determining the extent of the + * unlimited VDS, gap_size, using the access property list + * for the virtual dataset, dapl_id. The default library + * value for gap_size is 0. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * May 21, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pget_virtual_printf_gap(hid_t plist_id, hsize_t *gap_size) +{ + H5P_genplist_t *plist; /* Property list pointer */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "i*h", plist_id, gap_size); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(plist_id, H5P_DATASET_ACCESS))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, H5D_VDS_ERROR, "can't find object for ID") + + /* Get value from property list */ + if(gap_size) + if(H5P_get(plist, H5D_ACS_VDS_PRINTF_GAP_NAME, gap_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, H5D_VDS_ERROR, "unable to get value") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_printf_gap() */ diff --git a/src/H5Pdcpl.c b/src/H5Pdcpl.c index 9bf58e4..69645a4 100644 --- a/src/H5Pdcpl.c +++ b/src/H5Pdcpl.c @@ -41,7 +41,9 @@ #include "H5FLprivate.h" /* Free Lists */ #include "H5Iprivate.h" /* IDs */ #include "H5MMprivate.h" /* Memory management */ +#include "H5Oprivate.h" /* Object headers */ #include "H5Ppkg.h" /* Property lists */ +#include "H5Sprivate.h" /* Dataspaces */ #include "H5Tprivate.h" /* Datatypes */ #include "H5Zpkg.h" /* Data filters */ @@ -55,13 +57,16 @@ #define H5D_DEF_STORAGE_CONTIG_INIT {HADDR_UNDEF, (hsize_t)0} #define H5D_DEF_STORAGE_CHUNK_INIT {H5D_CHUNK_IDX_BTREE, HADDR_UNDEF, NULL, {{HADDR_UNDEF, NULL}}} #define H5D_DEF_LAYOUT_CHUNK_INIT {(unsigned)0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, (uint32_t)0, (hsize_t)0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}} +#define H5D_DEF_STORAGE_VIRTUAL_INIT {{HADDR_UNDEF, 0}, 0, NULL, 0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, H5D_VDS_ERROR, HSIZE_UNDEF, -1, -1, FALSE} #ifdef H5_HAVE_C99_DESIGNATED_INITIALIZER #define H5D_DEF_STORAGE_COMPACT {H5D_COMPACT, { .compact = H5D_DEF_STORAGE_COMPACT_INIT }} #define H5D_DEF_STORAGE_CONTIG {H5D_CONTIGUOUS, { .contig = H5D_DEF_STORAGE_CONTIG_INIT }} #define H5D_DEF_STORAGE_CHUNK {H5D_CHUNKED, { .chunk = H5D_DEF_STORAGE_CHUNK_INIT }} +#define H5D_DEF_STORAGE_VIRTUAL {H5D_VIRTUAL, { .virt = H5D_DEF_STORAGE_VIRTUAL_INIT }} #define H5D_DEF_LAYOUT_COMPACT {H5D_COMPACT, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, H5D_DEF_STORAGE_COMPACT} #define H5D_DEF_LAYOUT_CONTIG {H5D_CONTIGUOUS, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, H5D_DEF_STORAGE_CONTIG} #define H5D_DEF_LAYOUT_CHUNK {H5D_CHUNKED, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, H5D_DEF_STORAGE_CHUNK} +#define H5D_DEF_LAYOUT_VIRTUAL {H5D_VIRTUAL, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, H5D_DEF_STORAGE_VIRTUAL} #else /* H5_HAVE_C99_DESIGNATED_INITIALIZER */ /* Note that the compact & chunked layout initialization values are using the * contiguous layout initialization in the union, because the contiguous @@ -71,6 +76,7 @@ #define H5D_DEF_LAYOUT_COMPACT {H5D_COMPACT, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, {H5D_CONTIGUOUS, H5D_DEF_STORAGE_CONTIG_INIT}} #define H5D_DEF_LAYOUT_CONTIG {H5D_CONTIGUOUS, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, {H5D_CONTIGUOUS, H5D_DEF_STORAGE_CONTIG_INIT}} #define H5D_DEF_LAYOUT_CHUNK {H5D_CHUNKED, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, {H5D_CONTIGUOUS, H5D_DEF_STORAGE_CONTIG_INIT}} +#define H5D_DEF_LAYOUT_VIRTUAL {H5D_VIRTUAL, H5O_LAYOUT_VERSION_3, NULL, {H5D_DEF_LAYOUT_CHUNK_INIT}, {H5D_CONTIGUOUS, H5D_DEF_STORAGE_CONTIG_INIT}} #endif /* H5_HAVE_C99_DESIGNATED_INITIALIZER */ /* ======== Dataset creation properties ======== */ @@ -79,7 +85,9 @@ #define H5D_CRT_LAYOUT_DEF H5D_DEF_LAYOUT_CONTIG #define H5D_CRT_LAYOUT_ENC H5P__dcrt_layout_enc #define H5D_CRT_LAYOUT_DEC H5P__dcrt_layout_dec +#define H5D_CRT_LAYOUT_DEL H5P__dcrt_layout_del #define H5D_CRT_LAYOUT_CMP H5P__dcrt_layout_cmp +#define H5D_CRT_LAYOUT_CLOSE H5P__dcrt_layout_close /* Definitions for fill value. size=0 means fill value will be 0 as * library default; size=-1 means fill value is undefined. */ #define H5D_CRT_FILL_VALUE_SIZE sizeof(H5O_fill_t) @@ -128,7 +136,9 @@ static herr_t H5P__dcrt_close(hid_t dxpl_id, void *close_data); /* Property callbacks */ static herr_t H5P__dcrt_layout_enc(const void *value, void **pp, size_t *size); static herr_t H5P__dcrt_layout_dec(const void **pp, void *value); +static herr_t H5P__dcrt_layout_del(hid_t prop_id, const char *name, size_t size, void *value); static int H5P__dcrt_layout_cmp(const void *value1, const void *value2, size_t size); +static herr_t H5P__dcrt_layout_close(const char *name, size_t size, void *value); static herr_t H5P__fill_value_enc(const void *value, void **pp, size_t *size); static herr_t H5P__fill_value_dec(const void **pp, void *value); static herr_t H5P__dcrt_ext_file_list_enc(const void *value, void **pp, size_t *size); @@ -183,10 +193,12 @@ static const H5O_efl_t H5D_def_efl_g = H5D_CRT_EXT_FILE_LIST_DEF; static const H5O_layout_t H5D_def_layout_compact_g = H5D_DEF_LAYOUT_COMPACT; static const H5O_layout_t H5D_def_layout_contig_g = H5D_DEF_LAYOUT_CONTIG; static const H5O_layout_t H5D_def_layout_chunk_g = H5D_DEF_LAYOUT_CHUNK; +static const H5O_layout_t H5D_def_layout_virtual_g = H5D_DEF_LAYOUT_VIRTUAL; #else /* H5_HAVE_C99_DESIGNATED_INITIALIZER */ static H5O_layout_t H5D_def_layout_compact_g = H5D_DEF_LAYOUT_COMPACT; static H5O_layout_t H5D_def_layout_contig_g = H5D_DEF_LAYOUT_CONTIG; static H5O_layout_t H5D_def_layout_chunk_g = H5D_DEF_LAYOUT_CHUNK; +static H5O_layout_t H5D_def_layout_virtual_g = H5D_DEF_LAYOUT_VIRTUAL; static hbool_t H5P_dcrt_def_layout_init_g = FALSE; #endif /* H5_HAVE_C99_DESIGNATED_INITIALIZER */ @@ -213,7 +225,7 @@ H5P__dcrt_reg_prop(H5P_genclass_t *pclass) /* Register the storage layout property */ if(H5P_register_real(pclass, H5D_CRT_LAYOUT_NAME, H5D_CRT_LAYOUT_SIZE, &H5D_def_layout_g, NULL, NULL, NULL, H5D_CRT_LAYOUT_ENC, H5D_CRT_LAYOUT_DEC, - NULL, NULL, H5D_CRT_LAYOUT_CMP, NULL) < 0) + H5D_CRT_LAYOUT_DEL, NULL, H5D_CRT_LAYOUT_CMP, H5D_CRT_LAYOUT_CLOSE) < 0) HGOTO_ERROR(H5E_PLIST, H5E_CANTINSERT, FAIL, "can't insert property into class") /* Register the fill value property */ @@ -314,6 +326,11 @@ H5P__dcrt_copy(hid_t dst_plist_id, hid_t src_plist_id, void H5_ATTR_UNUSED *copy dst_layout.storage.u.chunk.ops = NULL; break; + case H5D_VIRTUAL: + dst_layout.storage.u.virt.serial_list_hobjid.addr = HADDR_UNDEF; + dst_layout.storage.u.virt.serial_list_hobjid.idx = 0; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -421,8 +438,12 @@ H5P__dcrt_layout_enc(const void *value, void **_pp, size_t *size) { const H5O_layout_t *layout = (const H5O_layout_t *)value; /* Create local aliases for values */ uint8_t **pp = (uint8_t **)_pp; + uint8_t *tmp_p; + size_t tmp_size; + size_t u; /* Local index variable */ + herr_t ret_value = SUCCEED; /* Return value */ - FUNC_ENTER_STATIC_NOERR + FUNC_ENTER_STATIC /* Sanity check */ HDassert(layout); @@ -434,16 +455,84 @@ H5P__dcrt_layout_enc(const void *value, void **_pp, size_t *size) /* If layout is chunked, encode chunking structure */ if(H5D_CHUNKED == layout->type) { - unsigned u; /* Local index variable */ - /* Encode rank */ *(*pp)++ = (uint8_t)layout->u.chunk.ndims; /* Encode chunk dims */ HDcompile_assert(sizeof(uint32_t) == sizeof(layout->u.chunk.dim[0])); - for(u = 0; u < layout->u.chunk.ndims; u++) + for(u = 0; u < (size_t)layout->u.chunk.ndims; u++) UINT32ENCODE(*pp, layout->u.chunk.dim[u]) } /* end if */ + else if(H5D_VIRTUAL == layout->type) { + uint64_t nentries = (uint64_t)layout->storage.u.virt.list_nused; + + /* Encode number of entries */ + UINT64ENCODE(*pp, nentries) + *size += (size_t)8; + + /* Iterate over entries */ + for(u = 0; u < layout->storage.u.virt.list_nused; u++) { + /* Source file name */ + tmp_size = HDstrlen(layout->storage.u.virt.list[u].source_file_name) + (size_t)1; + (void)HDmemcpy(*pp, layout->storage.u.virt.list[u].source_file_name, tmp_size); + *pp += tmp_size; + *size += tmp_size; + + /* Source dataset name */ + tmp_size = HDstrlen(layout->storage.u.virt.list[u].source_dset_name) + (size_t)1; + (void)HDmemcpy(*pp, layout->storage.u.virt.list[u].source_dset_name, tmp_size); + *pp += tmp_size; + *size += tmp_size; + + /* Source selection. Note that we are not passing the real + * allocated size because we do no know it. H5P__encode should + * have verified that the buffer is large enough for the entire + * list before we get here. */ + tmp_size = (size_t)-1; + tmp_p = *pp; + if(H5S_encode(layout->storage.u.virt.list[u].source_select, pp, &tmp_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTENCODE, FAIL, "unable to serialize source selection") + *size += (size_t)(*pp - tmp_p); + + /* Virtual dataset selection. Same notes as above apply. */ + tmp_size = (size_t)-1; + tmp_p = *pp; + if(H5S_encode(layout->storage.u.virt.list[u].source_dset.virtual_select, pp, &tmp_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTENCODE, FAIL, "unable to serialize virtual selection") + *size += (size_t)(*pp - tmp_p); + } /* end for */ + } /* end if */ + } /* end if */ + else if(H5D_VIRTUAL == layout->type) { + /* Calculate size of virtual layout info */ + /* number of entries */ + *size += (size_t)8; + + /* NULL pointer to pass to H5S_encode */ + tmp_p = NULL; + + /* Iterate over entries */ + for(u = 0; u < layout->storage.u.virt.list_nused; u++) { + /* Source file name */ + tmp_size = HDstrlen(layout->storage.u.virt.list[u].source_file_name) + (size_t)1; + *size += tmp_size; + + /* Source dataset name */ + tmp_size = HDstrlen(layout->storage.u.virt.list[u].source_dset_name) + (size_t)1; + *size += tmp_size; + + /* Source selection */ + tmp_size = (size_t)0; + if(H5S_encode(layout->storage.u.virt.list[u].source_select, &tmp_p, &tmp_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTENCODE, FAIL, "unable to serialize source selection") + *size += tmp_size; + + /* Virtual dataset selection */ + tmp_size = (size_t)0; + if(H5S_encode(layout->storage.u.virt.list[u].source_dset.virtual_select, &tmp_p, &tmp_size) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTENCODE, FAIL, "unable to serialize virtual selection") + *size += tmp_size; + } /* end for */ } /* end if */ /* Size of layout type */ @@ -455,7 +544,8 @@ H5P__dcrt_layout_enc(const void *value, void **_pp, size_t *size) *size += layout->u.chunk.ndims * sizeof(uint32_t); } /* end if */ - FUNC_LEAVE_NOAPI(SUCCEED) +done: + FUNC_LEAVE_NOAPI(ret_value) } /* end H5P__dcrt_layout_enc() */ @@ -478,7 +568,7 @@ static herr_t H5P__dcrt_layout_dec(const void **_pp, void *value) { const H5O_layout_t *layout; /* Storage layout */ - H5O_layout_t chunk_layout; /* Layout structure for chunk info */ + H5O_layout_t tmp_layout; /* Temporary local layout structure */ H5D_layout_t type; /* Layout type */ const uint8_t **pp = (const uint8_t **)_pp; herr_t ret_value = SUCCEED; /* Return value */ @@ -518,19 +608,113 @@ H5P__dcrt_layout_dec(const void **_pp, void *value) unsigned u; /* Local index variable */ /* Initialize to default values */ - chunk_layout = H5D_def_layout_chunk_g; + tmp_layout = H5D_def_layout_chunk_g; /* Set rank & dimensions */ - chunk_layout.u.chunk.ndims = (unsigned)ndims; + tmp_layout.u.chunk.ndims = (unsigned)ndims; for(u = 0; u < ndims; u++) - UINT32DECODE(*pp, chunk_layout.u.chunk.dim[u]) + UINT32DECODE(*pp, tmp_layout.u.chunk.dim[u]) /* Point at the newly set up struct */ - layout = &chunk_layout; + layout = &tmp_layout; } /* end else */ } break; + case H5D_VIRTUAL: + { + uint64_t nentries; /* Number of VDS mappings */ + + /* Decode number of entries */ + UINT64DECODE(*pp, nentries) + + if(nentries == (uint64_t)0) + /* Just use the default struct */ + layout = &H5D_def_layout_virtual_g; + else { + size_t tmp_size; + size_t u; /* Local index variable */ + + /* Initialize to default values */ + tmp_layout = H5D_def_layout_virtual_g; + + /* Allocate entry list */ + if(NULL == (tmp_layout.storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_calloc((size_t)nentries * sizeof(H5O_storage_virtual_ent_t)))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTALLOC, FAIL, "unable to allocate heap block") + tmp_layout.storage.u.virt.list_nalloc = (size_t)nentries; + tmp_layout.storage.u.virt.list_nused = (size_t)nentries; + + /* Decode each entry */ + for(u = 0; u < (size_t)nentries; u++) { + /* Source file name */ + tmp_size = HDstrlen((const char *)*pp) + 1; + if(NULL == (tmp_layout.storage.u.virt.list[u].source_file_name = (char *)H5MM_malloc(tmp_size))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTALLOC, FAIL, "unable to allocate memory for source file name") + (void)HDmemcpy(tmp_layout.storage.u.virt.list[u].source_file_name, *pp, tmp_size); + *pp += tmp_size; + + /* Source dataset name */ + tmp_size = HDstrlen((const char *)*pp) + 1; + if(NULL == (tmp_layout.storage.u.virt.list[u].source_dset_name = (char *)H5MM_malloc(tmp_size))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTALLOC, FAIL, "unable to allocate memory for source dataset name") + (void)HDmemcpy(tmp_layout.storage.u.virt.list[u].source_dset_name, *pp, tmp_size); + *pp += tmp_size; + + /* Source selection */ + if(NULL == (tmp_layout.storage.u.virt.list[u].source_select = H5S_decode(pp))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTDECODE, FAIL, "can't decode source space selection") + tmp_layout.storage.u.virt.list[u].source_space_status = H5O_VIRTUAL_STATUS_USER; + + /* Virtual selection */ + if(NULL == (tmp_layout.storage.u.virt.list[u].source_dset.virtual_select = H5S_decode(pp))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTDECODE, FAIL, "can't decode virtual space selection") + tmp_layout.storage.u.virt.list[u].virtual_space_status = H5O_VIRTUAL_STATUS_USER; + + /* Parse source file and dataset names for "printf" + * style format specifiers */ + if(H5D_virtual_parse_source_name(tmp_layout.storage.u.virt.list[u].source_file_name, &tmp_layout.storage.u.virt.list[u].parsed_source_file_name, &tmp_layout.storage.u.virt.list[u].psfn_static_strlen, &tmp_layout.storage.u.virt.list[u].psfn_nsubs) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't parse source file name") + if(H5D_virtual_parse_source_name(tmp_layout.storage.u.virt.list[u].source_dset_name, &tmp_layout.storage.u.virt.list[u].parsed_source_dset_name, &tmp_layout.storage.u.virt.list[u].psdn_static_strlen, &tmp_layout.storage.u.virt.list[u].psdn_nsubs) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't parse source dataset name") + + /* Set source names in source_dset struct */ + if((tmp_layout.storage.u.virt.list[u].psfn_nsubs == 0) + && (tmp_layout.storage.u.virt.list[u].psdn_nsubs == 0)) { + if(tmp_layout.storage.u.virt.list[u].parsed_source_file_name) + tmp_layout.storage.u.virt.list[u].source_dset.file_name = tmp_layout.storage.u.virt.list[u].parsed_source_file_name->name_segment; + else + tmp_layout.storage.u.virt.list[u].source_dset.file_name = tmp_layout.storage.u.virt.list[u].source_file_name; + if(tmp_layout.storage.u.virt.list[u].parsed_source_dset_name) + tmp_layout.storage.u.virt.list[u].source_dset.dset_name = tmp_layout.storage.u.virt.list[u].parsed_source_dset_name->name_segment; + else + tmp_layout.storage.u.virt.list[u].source_dset.dset_name = tmp_layout.storage.u.virt.list[u].source_dset_name; + } /* end if */ + + /* unlim_dim fields */ + tmp_layout.storage.u.virt.list[u].unlim_dim_source = H5S_get_select_unlim_dim(tmp_layout.storage.u.virt.list[u].source_select); + tmp_layout.storage.u.virt.list[u].unlim_dim_virtual = H5S_get_select_unlim_dim(tmp_layout.storage.u.virt.list[u].source_dset.virtual_select); + tmp_layout.storage.u.virt.list[u].unlim_extent_source = HSIZE_UNDEF; + tmp_layout.storage.u.virt.list[u].unlim_extent_virtual = HSIZE_UNDEF; + tmp_layout.storage.u.virt.list[u].clip_size_source = HSIZE_UNDEF; + tmp_layout.storage.u.virt.list[u].clip_size_virtual = HSIZE_UNDEF; + + /* Clipped selections */ + if(tmp_layout.storage.u.virt.list[u].unlim_dim_virtual < 0) { + tmp_layout.storage.u.virt.list[u].source_dset.clipped_source_select = tmp_layout.storage.u.virt.list[u].source_select; + tmp_layout.storage.u.virt.list[u].source_dset.clipped_virtual_select = tmp_layout.storage.u.virt.list[u].source_dset.virtual_select; + } /* end if */ + + /* Update min_dims */ + if(H5D_virtual_update_min_dims(&tmp_layout, u) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "unable to update virtual dataset minimum dimensions") + } /* end for */ + + /* Point at the newly set up struct */ + layout = &tmp_layout; + } /* end else */ + } /* end block */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -546,6 +730,41 @@ done: /*------------------------------------------------------------------------- + * Function: H5P__dcrt_layout_del + * + * Purpose: Frees memory used to store the layout property + * + * Return: Success: Non-negative + * Failure: Negative + * + * Programmer: Neil Fortner + * Tuesday, Feb 10, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5P__dcrt_layout_del(hid_t H5_ATTR_UNUSED prop_id, + const char H5_ATTR_UNUSED *name, size_t H5_ATTR_UNUSED size, + void *value) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(value); + + /* Reset the old layout */ + if(((H5O_layout_t *)value)->type == H5D_VIRTUAL) /* Temp hack until proper fix is in trunk */ + if(H5O_msg_reset(H5O_LAYOUT_ID, value) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTFREE, FAIL, "can't release layout message") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5P__dcrt_layout_del() */ + + +/*------------------------------------------------------------------------- * Function: H5P__dcrt_layout_cmp * * Purpose: Callback routine which is called whenever the layout @@ -605,6 +824,51 @@ H5P__dcrt_layout_cmp(const void *_layout1, const void *_layout2, size_t H5_ATTR_ } /* end case */ break; + case H5D_VIRTUAL: + { + htri_t equal; + int strcmp_ret; + size_t u; /* Local index variable */ + + /* Compare number of mappings */ + if(layout1->storage.u.virt.list_nused < layout2->storage.u.virt.list_nused) HGOTO_DONE(-1) + if(layout1->storage.u.virt.list_nused > layout2->storage.u.virt.list_nused) HGOTO_DONE(1) + + /* Iterate over mappings */ + for(u = 0; u < layout1->storage.u.virt.list_nused; u++) { + /* Compare virtual spaces. Note we cannot tell which is + * "greater", so just return 1 if different, -1 on failure. + */ + if((equal = H5S_extent_equal(layout1->storage.u.virt.list[u].source_dset.virtual_select, layout2->storage.u.virt.list[u].source_dset.virtual_select)) < 0) HGOTO_DONE(-1) + if(!equal) + HGOTO_DONE(1) + if((equal = H5S_select_shape_same(layout1->storage.u.virt.list[u].source_dset.virtual_select, layout2->storage.u.virt.list[u].source_dset.virtual_select)) < 0) HGOTO_DONE(-1) + if(!equal) + HGOTO_DONE(1) + + /* Compare source file names */ + strcmp_ret = HDstrcmp(layout1->storage.u.virt.list[u].source_file_name, layout2->storage.u.virt.list[u].source_file_name); + if(strcmp_ret < 0) HGOTO_DONE(-1) + if(strcmp_ret > 0) HGOTO_DONE(1) + + /* Compare source dataset names */ + strcmp_ret = HDstrcmp(layout1->storage.u.virt.list[u].source_dset_name, layout2->storage.u.virt.list[u].source_dset_name); + if(strcmp_ret < 0) HGOTO_DONE(-1) + if(strcmp_ret > 0) HGOTO_DONE(1) + + /* Compare source spaces. Note we cannot tell which is + * "greater", so just return 1 if different, -1 on failure. + */ + if((equal = H5S_extent_equal(layout1->storage.u.virt.list[u].source_select, layout2->storage.u.virt.list[u].source_select)) < 0) HGOTO_DONE(-1) + if(!equal) + HGOTO_DONE(1) + if((equal = H5S_select_shape_same(layout1->storage.u.virt.list[u].source_select, layout2->storage.u.virt.list[u].source_select)) < 0) HGOTO_DONE(-1) + if(!equal) + HGOTO_DONE(1) + } /* end for */ + } /* end block */ + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -617,6 +881,40 @@ done: /*------------------------------------------------------------------------- + * Function: H5P__dcrt_layout_close + * + * Purpose: Frees memory used to store the layout property + * + * Return: Success: Non-negative + * Failure: Negative + * + * Programmer: Neil Fortner + * Tuesday, Feb 10, 2015 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5P__dcrt_layout_close(const char H5_ATTR_UNUSED *name, + size_t H5_ATTR_UNUSED size, void *value) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(value); + + /* Reset the old layout */ + if(((H5O_layout_t *)value)->type == H5D_VIRTUAL) /* Temp hack until proper fix is in trunk */ + if(H5O_msg_reset(H5O_LAYOUT_ID, value) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTFREE, FAIL, "can't release layout message") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5P__dcrt_layout_close() */ + + +/*------------------------------------------------------------------------- * Function: H5P__fill_value_enc * * Purpose: Callback routine which is called whenever the fill value @@ -1110,6 +1408,7 @@ done: static herr_t H5P__set_layout(H5P_genplist_t *plist, const H5O_layout_t *layout) { + H5O_layout_t old_layout; /* Layout propertry already on list */ unsigned alloc_time_state; /* State of allocation time property */ herr_t ret_value = SUCCEED; /* return value */ @@ -1141,6 +1440,10 @@ H5P__set_layout(H5P_genplist_t *plist, const H5O_layout_t *layout) fill.alloc_time = H5D_ALLOC_TIME_INCR; break; + case H5D_VIRTUAL: + fill.alloc_time = H5D_ALLOC_TIME_INCR; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1152,6 +1455,14 @@ H5P__set_layout(H5P_genplist_t *plist, const H5O_layout_t *layout) HGOTO_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "can't set space allocation time") } /* end if */ + /* Get the old layout */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &old_layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get layout") + + /* Reset the old layout before overwriting it */ + if(H5O_msg_reset(H5O_LAYOUT_ID, &old_layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTFREE, FAIL, "can't release layout message") + /* Set layout value */ if(H5P_set(plist, H5D_CRT_LAYOUT_NAME, layout) < 0) HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't set layout") @@ -1181,13 +1492,18 @@ H5P__init_def_layout(void) const H5O_layout_chunk_t def_layout_chunk = H5D_DEF_LAYOUT_CHUNK_INIT; const H5O_storage_compact_t def_store_compact = H5D_DEF_STORAGE_COMPACT_INIT; const H5O_storage_chunk_t def_store_chunk = H5D_DEF_STORAGE_CHUNK_INIT; + const H5O_storage_virtual_t def_store_virtual = H5D_DEF_STORAGE_VIRTUAL_INIT; FUNC_ENTER_STATIC_NOERR /* Initialize the default layout info for non-contigous layouts */ + H5D_def_layout_compact_g.storage.type = H5D_COMPACT; H5D_def_layout_compact_g.storage.u.compact = def_store_compact; H5D_def_layout_chunk_g.u.chunk = def_layout_chunk; + H5D_def_layout_chunk_g.storage.type = H5D_CHUNKED; H5D_def_layout_chunk_g.storage.u.chunk = def_store_chunk; + H5D_def_layout_virtual_g.storage.type = H5D_VIRTUAL; + H5D_def_layout_virtual_g.storage.u.virt = def_store_virtual; /* Note that we've initialized the default values */ H5P_dcrt_def_layout_init_g = TRUE; @@ -1257,6 +1573,10 @@ H5Pset_layout(hid_t plist_id, H5D_layout_t layout_type) layout = &H5D_def_layout_chunk_g; break; + case H5D_VIRTUAL: + layout = &H5D_def_layout_virtual_g; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: @@ -1462,6 +1782,528 @@ done: /*------------------------------------------------------------------------- + * Function: H5Pset_virtual + * + * Purpose: Maps elements of the virtual dataset described by the + * virtual dataspace identifier vspace_id to the elements of + * the source dataset described by the source dataset + * dataspace identifier src_space_id. The source dataset is + * identified by the name of the file where it is located, + * src_file_name, and the name of the dataset, src_dset_name. + * + * As a side effect, the layout method is changed to + * H5D_VIRTUAL. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * Friday, February 13, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pset_virtual(hid_t dcpl_id, hid_t vspace_id, const char *src_file_name, + const char *src_dset_name, hid_t src_space_id) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information for setting chunk info */ + H5S_t *vspace; /* Virtual dataset space selection */ + H5S_t *src_space; /* Source dataset space selection */ + hbool_t new_layout = FALSE; /* Whether we are adding a new virtual layout message to plist */ + H5O_storage_virtual_ent_t *ent = NULL; /* Convenience pointer to new VDS entry */ + hbool_t adding_entry = FALSE; /* Whether we are in the middle of adding an entry */ + H5O_storage_virtual_ent_t *old_list = NULL; /* List pointer previously on property list */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE5("e", "ii*s*si", dcpl_id, vspace_id, src_file_name, src_dset_name, + src_space_id); + + /* Check arguments */ + if(!src_file_name) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "source file name not provided") + if(!src_dset_name) + HGOTO_ERROR(H5E_ARGS, H5E_BADRANGE, FAIL, "source dataset name not provided") + if(NULL == (vspace = (H5S_t *)H5I_object_verify(vspace_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") + if(NULL == (src_space = (H5S_t *)H5I_object_verify(src_space_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") + + /* Check selections for validity */ + if(H5D_virtual_check_mapping_pre(vspace, src_space, H5O_VIRTUAL_STATUS_USER) < 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid mapping selections") + +#ifndef H5_HAVE_C99_DESIGNATED_INITIALIZER + /* If the compiler doesn't support C99 designated initializers, check if + * the default layout structs have been initialized yet or not. *ick* -QAK + */ + if(!H5P_dcrt_def_layout_init_g) + if(H5P__init_def_layout() < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't initialize default layout info") +#endif /* H5_HAVE_C99_DESIGNATED_INITIALIZER */ + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Get the current layout */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get layout") + + /* If the layout was not already virtual, Start with default virtual layout. + * Otherwise, add the mapping to the current list. */ + if(layout.type == H5D_VIRTUAL) + /* Save old list pointer for error recovery */ + old_list = layout.storage.u.virt.list; + else { + new_layout = TRUE; + HDmemcpy(&layout, &H5D_def_layout_virtual_g, sizeof(H5D_def_layout_virtual_g)); + + HDassert(layout.storage.u.virt.list_nalloc == 0); + } /* end else */ + + /* Expand list if necessary */ + if(layout.storage.u.virt.list_nalloc == 0) { + /* Allocate initial entry list */ + if(NULL == (layout.storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_calloc(H5D_VIRTUAL_DEF_LIST_SIZE * sizeof(H5O_storage_virtual_ent_t)))) + HGOTO_ERROR(H5E_PLIST, H5E_RESOURCE, FAIL, "can't allocate virtual dataset mapping list") + adding_entry = TRUE; + layout.storage.u.virt.list_nalloc = H5D_VIRTUAL_DEF_LIST_SIZE; + } /* end if */ + else if(layout.storage.u.virt.list_nused + == layout.storage.u.virt.list_nalloc) { + /* Double size of entry list. Make sure to zero out new memory. */ + if(NULL == (layout.storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_realloc(layout.storage.u.virt.list, (size_t)2 * layout.storage.u.virt.list_nalloc * sizeof(H5O_storage_virtual_ent_t)))) + HGOTO_ERROR(H5E_PLIST, H5E_RESOURCE, FAIL, "can't reallocate virtual dataset mapping list") + adding_entry = TRUE; + (void)HDmemset(layout.storage.u.virt.list + layout.storage.u.virt.list_nalloc, 0, layout.storage.u.virt.list_nalloc * sizeof(H5O_storage_virtual_ent_t)); + layout.storage.u.virt.list_nalloc *= (size_t)2; + } /* end if */ + + /* Add virtual dataset mapping entry */ + ent = &layout.storage.u.virt.list[layout.storage.u.virt.list_nused]; + if(NULL == (ent->source_dset.virtual_select = H5S_copy(vspace, FALSE, TRUE))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + adding_entry = TRUE; + if(NULL == (ent->source_file_name = HDstrdup(src_file_name))) + HGOTO_ERROR(H5E_PLIST, H5E_RESOURCE, FAIL, "can't duplicate source file name") + if(NULL == (ent->source_dset_name = HDstrdup(src_dset_name))) + HGOTO_ERROR(H5E_PLIST, H5E_RESOURCE, FAIL, "can't duplicate source file name") + if(NULL == (ent->source_select = H5S_copy(src_space, FALSE, TRUE))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTCOPY, FAIL, "unable to copy source selection") + if(H5D_virtual_parse_source_name(ent->source_file_name, &ent->parsed_source_file_name, &ent->psfn_static_strlen, &ent->psfn_nsubs) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't parse source file name") + if(H5D_virtual_parse_source_name(ent->source_dset_name, &ent->parsed_source_dset_name, &ent->psdn_static_strlen, &ent->psdn_nsubs) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "can't parse source dataset name") + if((ent->psfn_nsubs == 0) && (ent->psdn_nsubs == 0)) { + if(ent->parsed_source_file_name) + ent->source_dset.file_name = ent->parsed_source_file_name->name_segment; + else + ent->source_dset.file_name = ent->source_file_name; + if(ent->parsed_source_dset_name) + ent->source_dset.dset_name = ent->parsed_source_dset_name->name_segment; + else + ent->source_dset.dset_name = ent->source_dset_name; + } /* end if */ + ent->unlim_dim_source = H5S_get_select_unlim_dim(src_space); + ent->unlim_dim_virtual = H5S_get_select_unlim_dim(vspace); + if(ent->unlim_dim_virtual < 0) { + ent->source_dset.clipped_source_select = ent->source_select; + ent->source_dset.clipped_virtual_select = ent->source_dset.virtual_select; + } /* end if */ + ent->unlim_extent_source = HSIZE_UNDEF; + ent->unlim_extent_virtual = HSIZE_UNDEF; + ent->clip_size_source = HSIZE_UNDEF; + ent->clip_size_virtual = HSIZE_UNDEF; + ent->source_space_status = H5O_VIRTUAL_STATUS_USER; + ent->virtual_space_status = H5O_VIRTUAL_STATUS_USER; + + /* Check entry for validity */ + if(H5D_virtual_check_mapping_post(ent) < 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid mapping entry") + + /* Update min_dims */ + if(H5D_virtual_update_min_dims(&layout, layout.storage.u.virt.list_nused) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTINIT, FAIL, "unable to update virtual dataset minimum dimensions") + + /* Finish adding entry */ + layout.storage.u.virt.list_nused++; + +done: + /* Only need to do things if we started to add an entry */ + if(adding_entry) { + hbool_t free_list = FALSE; + + /* Set VDS layout information in property list. If we are adding a new + * layout, use H5P__set_layout so other fields are initialized properly. + * If we are extending the layout, just use H5P_set directly so we don't + * mess with anything else. Put this after the done: label because the + * original list may no longer be valid due to the use of realloc(), so + * we want to make sure the list is available if possible. */ + if(new_layout) { + if(H5P__set_layout(plist, &layout) < 0) { + HDONE_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "can't set layout") + free_list = TRUE; + } /* end if */ + } /* end if */ + else + if(H5P_set(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) { + HDONE_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "can't set layout") + if(old_list != layout.storage.u.virt.list) + free_list = TRUE; + } /* end if */ + + /* Check if the entry has been partly allocated but not added to the + * property list or not included in list_nused */ + if(ret_value < 0) { + /* Free incomplete entry if present */ + if(ent) { + ent->source_file_name = (char *)H5MM_xfree(ent->source_file_name); + ent->source_dset_name = (char *)H5MM_xfree(ent->source_dset_name); + if(ent->source_dset.virtual_select && H5S_close(ent->source_dset.virtual_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release virtual selection") + ent->source_dset.virtual_select = NULL; + if(ent->source_select && H5S_close(ent->source_select) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release source selection") + ent->source_select = NULL; + H5D_virtual_free_parsed_name(ent->parsed_source_file_name); + ent->parsed_source_file_name = NULL; + H5D_virtual_free_parsed_name(ent->parsed_source_dset_name); + ent->parsed_source_dset_name = NULL; + } /* end if */ + + /* Free list if necessary */ + if(free_list) + layout.storage.u.virt.list = (H5O_storage_virtual_ent_t *)H5MM_xfree(layout.storage.u.virt.list); + } /* end if */ + } /* end if */ + + FUNC_LEAVE_API(ret_value) +} /* end H5Pset_virtual() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_count + * + * Purpose: Gets the number of mappings for the virtual dataset that + * has a creation property list specified by the dcpl_id + * parameter. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * Friday, February 13, 2015 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Pget_virtual_count(hid_t dcpl_id, size_t *count/*out*/) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "ix", dcpl_id, count); + + if(count) { + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Retrieve the layout property */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "can't get layout") + if(H5D_VIRTUAL != layout.type) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a virtual storage layout") + + /* Return the number of mappings */ + *count = layout.storage.u.virt.list_nused; + } /* end if */ + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_count() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_vspace + * + * Purpose: Takes the dataset creation property list for the virtual + * dataset, dcpl_id, and the mapping index, index, and + * returns a dataspace identifier for the selection within + * the virtual dataset used in the mapping. + * + * Return: Returns a dataspace identifier if successful; otherwise + * returns a negative value. + * + * Programmer: Neil Fortner + * Friday, February 13, 2015 + * + *------------------------------------------------------------------------- + */ +hid_t +H5Pget_virtual_vspace(hid_t dcpl_id, size_t index) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information */ + H5S_t *space = NULL; /* Dataspace pointer */ + hid_t ret_value; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("i", "iz", dcpl_id, index); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Retrieve the layout property */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "can't get layout") + if(H5D_VIRTUAL != layout.type) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a virtual storage layout") + + /* Get the virtual space */ + if(index >= layout.storage.u.virt.list_nused) + HGOTO_ERROR(H5E_ARGS, H5E_BADRANGE, FAIL, "invalid index (out of range)") + HDassert(layout.storage.u.virt.list_nused <= layout.storage.u.virt.list_nalloc); + if(NULL == (space = H5S_copy(layout.storage.u.virt.list[index].source_dset.virtual_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTCOPY, FAIL, "unable to copy virtual selection") + + /* Register ID */ + if((ret_value = H5I_register(H5I_DATASPACE, space, TRUE)) < 0) + HGOTO_ERROR(H5E_ATOM, H5E_CANTREGISTER, FAIL, "unable to register data space") + +done: + /* Free space on failure */ + if((ret_value < 0) && space) + if(H5S_close(space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release source selection") + + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_vspace() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_srcspace + * + * Purpose: Takes the dataset creation property list for the virtual + * dataset, dcpl_id, and the mapping index, index, and + * returns a dataspace identifier for the selection within + * the source dataset used in the mapping. + * + * Return: Returns a dataspace identifier if successful; otherwise + * returns a negative value. + * + * Programmer: Neil Fortner + * Saturday, February 14, 2015 + * + *------------------------------------------------------------------------- + */ +hid_t +H5Pget_virtual_srcspace(hid_t dcpl_id, size_t index) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information */ + H5S_t *space = NULL; /* Dataspace pointer */ + hid_t ret_value; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE2("i", "iz", dcpl_id, index); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Retrieve the layout property */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "can't get layout") + if(H5D_VIRTUAL != layout.type) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a virtual storage layout") + + /* Check index */ + if(index >= layout.storage.u.virt.list_nused) + HGOTO_ERROR(H5E_ARGS, H5E_BADRANGE, FAIL, "invalid index (out of range)") + HDassert(layout.storage.u.virt.list_nused <= layout.storage.u.virt.list_nalloc); + + /* Attempt to open source dataset and patch extent if extent status is not + * H5O_VIRTUAL_STATUS_CORRECT? -NAF */ + /* If source space status is H5O_VIRTUAL_STATUS_INVALID, patch with bounds + * of selection */ + if((layout.storage.u.virt.list[index].source_space_status + == H5O_VIRTUAL_STATUS_INVALID) + && (layout.storage.u.virt.list[index].unlim_dim_source < 0)) { + hsize_t bounds_start[H5S_MAX_RANK]; + hsize_t bounds_end[H5S_MAX_RANK]; + int rank; + int i; + + /* Get rank of source space */ + if((rank = H5S_GET_EXTENT_NDIMS(layout.storage.u.virt.list[index].source_select)) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get source space rank") + + /* Get bounds of selection */ + if(H5S_SELECT_BOUNDS(layout.storage.u.virt.list[index].source_select, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTGET, FAIL, "can't get selection bounds") + + /* Adjust bounds to extent */ + for(i = 0; i < rank; i++) + bounds_end[i]++; + + /* Set extent */ + if(H5S_set_extent_simple(layout.storage.u.virt.list[index].source_select, (unsigned)rank, bounds_end, NULL) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_CANTSET, FAIL, "can't set source space extent") + + /* Update source space status */ + layout.storage.u.virt.list[index].source_space_status = H5O_VIRTUAL_STATUS_SEL_BOUNDS; + } /* end if */ + + /* Get the source space */ + if(NULL == (space = H5S_copy(layout.storage.u.virt.list[index].source_select, FALSE, TRUE))) + HGOTO_ERROR(H5E_PLIST, H5E_CANTCOPY, FAIL, "unable to copy source selection") + + /* Register ID */ + if((ret_value = H5I_register(H5I_DATASPACE, space, TRUE)) < 0) + HGOTO_ERROR(H5E_ATOM, H5E_CANTREGISTER, FAIL, "unable to register data space") + +done: + /* Free space on failure */ + if((ret_value < 0) && space) + if(H5S_close(space) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CLOSEERROR, FAIL, "unable to release source selection") + + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_srcspace() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_filename + * + * Purpose: Takes the dataset creation property list for the virtual + * dataset, dcpl_id, and the mapping index, index, and + * retrieves a name of a file for a source dataset used in + * the mapping. + * + * Up to size characters of the filename are returned in + * name; additional characters, if any, are not returned to + * the user application. + * + * If the length of the filename, which determines the + * required value of size, is unknown, a preliminary call to + * H5Pget_virtual_filename with the last two parameters set + * to NULL can be made. The return value of this call will + * be the size in bytes of the filename. That value, plus 1 + * for a NULL terminator, is then assigned to size for a + * second H5Pget_virtual_filename call, which will retrieve + * the actual filename. + * + * Return: Returns the length of the name if successful, otherwise + * returns a negative value. + * + * Programmer: Neil Fortner + * Saturday, February 14, 2015 + * + *------------------------------------------------------------------------- + */ +ssize_t +H5Pget_virtual_filename(hid_t dcpl_id, size_t index, char *name/*out*/, + size_t size) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information */ + ssize_t ret_value; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE4("Zs", "izxz", dcpl_id, index, name, size); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Retrieve the layout property */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "can't get layout") + if(H5D_VIRTUAL != layout.type) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a virtual storage layout") + + /* Get the virtual filename */ + if(index >= layout.storage.u.virt.list_nused) + HGOTO_ERROR(H5E_ARGS, H5E_BADRANGE, FAIL, "invalid index (out of range)") + HDassert(layout.storage.u.virt.list_nused <= layout.storage.u.virt.list_nalloc); + HDassert(layout.storage.u.virt.list[index].source_file_name); + if(name && (size > 0)) + (void)HDstrncpy(name, layout.storage.u.virt.list[index].source_file_name, size); + ret_value = (ssize_t)HDstrlen(layout.storage.u.virt.list[index].source_file_name); + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_filename() */ + + +/*------------------------------------------------------------------------- + * Function: H5Pget_virtual_dsetname + * + * Purpose: Takes the dataset creation property list for the virtual + * dataset, dcpl_id, and the mapping index, index, and + * retrieves the name of a source dataset used in the mapping. + * + * Up to size characters of the name are returned in name; + * additional characters, if any, are not returned to the + * user application. + * + * If the length of the filename, which determines the + * required value of size, is unknown, a preliminary call to + * H5Pget_virtual_dsetname with the last two parameters set + * to NULL can be made. The return value of this call will + * be the size in bytes of the filename. That value, plus 1 + * for a NULL terminator, is then assigned to size for a + * second H5Pget_virtual_dsetname call, which will retrieve + * the actual filename. + * + * Return: Returns the length of the name if successful, otherwise + * returns a negative value. + * + * Programmer: Neil Fortner + * Saturday, February 14, 2015 + * + *------------------------------------------------------------------------- + */ +ssize_t +H5Pget_virtual_dsetname(hid_t dcpl_id, size_t index, char *name/*out*/, + size_t size) +{ + H5P_genplist_t *plist; /* Property list pointer */ + H5O_layout_t layout; /* Layout information */ + ssize_t ret_value; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE4("Zs", "izxz", dcpl_id, index, name, size); + + /* Get the plist structure */ + if(NULL == (plist = H5P_object_verify(dcpl_id, H5P_DATASET_CREATE))) + HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "can't find object for ID") + + /* Retrieve the layout property */ + if(H5P_get(plist, H5D_CRT_LAYOUT_NAME, &layout) < 0) + HGOTO_ERROR(H5E_PLIST, H5E_BADVALUE, FAIL, "can't get layout") + if(H5D_VIRTUAL != layout.type) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "not a virtual storage layout") + + /* Get the virtual filename */ + if(index >= layout.storage.u.virt.list_nused) + HGOTO_ERROR(H5E_ARGS, H5E_BADRANGE, FAIL, "invalid index (out of range)") + HDassert(layout.storage.u.virt.list_nused <= layout.storage.u.virt.list_nalloc); + HDassert(layout.storage.u.virt.list[index].source_dset_name); + if(name && (size > 0)) + (void)HDstrncpy(name, layout.storage.u.virt.list[index].source_dset_name, size); + ret_value = (ssize_t)HDstrlen(layout.storage.u.virt.list[index].source_dset_name); + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Pget_virtual_dsetname() */ + + +/*------------------------------------------------------------------------- * Function: H5Pset_external * * Purpose: Adds an external file to the list of external files. PLIST_ID @@ -2302,6 +3144,10 @@ H5Pset_alloc_time(hid_t plist_id, H5D_alloc_time_t alloc_time) alloc_time = H5D_ALLOC_TIME_INCR; break; + case H5D_VIRTUAL: + alloc_time = H5D_ALLOC_TIME_INCR; + break; + case H5D_LAYOUT_ERROR: case H5D_NLAYOUTS: default: diff --git a/src/H5Ppublic.h b/src/H5Ppublic.h index f56692c..4929621 100644 --- a/src/H5Ppublic.h +++ b/src/H5Ppublic.h @@ -354,6 +354,15 @@ H5_DLL herr_t H5Pset_layout(hid_t plist_id, H5D_layout_t layout); H5_DLL H5D_layout_t H5Pget_layout(hid_t plist_id); H5_DLL herr_t H5Pset_chunk(hid_t plist_id, int ndims, const hsize_t dim[/*ndims*/]); H5_DLL int H5Pget_chunk(hid_t plist_id, int max_ndims, hsize_t dim[]/*out*/); +H5_DLL herr_t H5Pset_virtual(hid_t dcpl_id, hid_t vspace_id, + const char *src_file_name, const char *src_dset_name, hid_t src_space_id); +H5_DLL herr_t H5Pget_virtual_count(hid_t dcpl_id, size_t *count/*out*/); +H5_DLL hid_t H5Pget_virtual_vspace(hid_t dcpl_id, size_t index); +H5_DLL hid_t H5Pget_virtual_srcspace(hid_t dcpl_id, size_t index); +H5_DLL ssize_t H5Pget_virtual_filename(hid_t dcpl_id, size_t index, + char *name/*out*/, size_t size); +H5_DLL ssize_t H5Pget_virtual_dsetname(hid_t dcpl_id, size_t index, + char *name/*out*/, size_t size); H5_DLL herr_t H5Pset_external(hid_t plist_id, const char *name, off_t offset, hsize_t size); H5_DLL int H5Pget_external_count(hid_t plist_id); @@ -384,6 +393,10 @@ H5_DLL herr_t H5Pget_chunk_cache(hid_t dapl_id, size_t *rdcc_nslots/*out*/, size_t *rdcc_nbytes/*out*/, double *rdcc_w0/*out*/); +H5_DLL herr_t H5Pset_virtual_view(hid_t plist_id, H5D_vds_view_t view); +H5_DLL herr_t H5Pget_virtual_view(hid_t plist_id, H5D_vds_view_t *view); +H5_DLL herr_t H5Pset_virtual_printf_gap(hid_t plist_id, hsize_t gap_size); +H5_DLL herr_t H5Pget_virtual_printf_gap(hid_t plist_id, hsize_t *gap_size); /* Dataset xfer property list (DXPL) routines */ H5_DLL herr_t H5Pset_data_transform(hid_t plist_id, const char* expression); @@ -275,7 +275,7 @@ H5R_create(void *_ref, H5G_loc_t *loc, const char *name, H5R_type_t ref_type, H5 HDmemset(ref, 0, H5R_DSET_REG_REF_BUF_SIZE); /* Get the amount of space required to serialize the selection */ - if((buf_size = H5S_SELECT_SERIAL_SIZE(space)) < 0) + if((buf_size = H5S_SELECT_SERIAL_SIZE(loc->oloc->file, space)) < 0) HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "Invalid amount of space for serializing selection") /* Increase buffer size to allow for the dataset OID */ @@ -291,7 +291,7 @@ H5R_create(void *_ref, H5G_loc_t *loc, const char *name, H5R_type_t ref_type, H5 H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr); /* Serialize the selection into heap buffer */ - if(H5S_SELECT_SERIALIZE(space, &p) < 0) + if(H5S_SELECT_SERIALIZE(loc->oloc->file, space, &p) < 0) HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCOPY, FAIL, "Unable to serialize selection") /* Save the serialized buffer for later */ @@ -668,7 +668,7 @@ H5R_get_region(H5F_t *file, hid_t dxpl_id, const void *_ref) HGOTO_ERROR(H5E_DATASPACE, H5E_NOTFOUND, NULL, "not found") /* Unserialize the selection */ - if(H5S_SELECT_DESERIALIZE(&ret_value, &p) < 0) + if(H5S_SELECT_DESERIALIZE(file, &ret_value, &p) < 0) HGOTO_ERROR(H5E_REFERENCE, H5E_CANTDECODE, NULL, "can't deserialize selection") done: @@ -52,11 +52,7 @@ /********************/ /* Local Prototypes */ /********************/ -static herr_t H5S_set_extent_simple (H5S_t *space, unsigned rank, - const hsize_t *dims, const hsize_t *max); static htri_t H5S_is_simple(const H5S_t *sdim); -static herr_t H5S_encode(H5S_t *obj, unsigned char *buf, size_t *nalloc); -static H5S_t *H5S_decode(const unsigned char *buf); /*********************/ @@ -479,7 +475,40 @@ H5Sextent_copy(hid_t dst_id,hid_t src_id) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") /* Copy */ - if(H5S_extent_copy(&(dst->extent), &(src->extent), TRUE) < 0) + if(H5S_extent_copy(dst, src) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, FAIL, "can't copy extent") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Sextent_copy() */ + + +/*------------------------------------------------------------------------- + * Function: H5S_extent_copy + * + * Purpose: Copies a dataspace extent + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * Monday, February 23, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5S_extent_copy(H5S_t *dst, const H5S_t *src) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + HDassert(dst); + HDassert(src); + + /* Copy extent */ + if(H5S_extent_copy_real(&(dst->extent), &(src->extent), TRUE) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, FAIL, "can't copy extent") /* If the selection is 'all', update the number of elements selected in the @@ -489,12 +518,12 @@ H5Sextent_copy(hid_t dst_id,hid_t src_id) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") done: - FUNC_LEAVE_API(ret_value) -} /* end H5Sextent_copy() */ + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_extent_copy() */ /*------------------------------------------------------------------------- - * Function: H5S_extent_copy + * Function: H5S_extent_copy_real * * Purpose: Copies a dataspace extent * @@ -508,7 +537,7 @@ done: *------------------------------------------------------------------------- */ herr_t -H5S_extent_copy(H5S_extent_t *dst, const H5S_extent_t *src, hbool_t copy_max) +H5S_extent_copy_real(H5S_extent_t *dst, const H5S_extent_t *src, hbool_t copy_max) { unsigned u; herr_t ret_value = SUCCEED; /* Return value */ @@ -561,7 +590,7 @@ H5S_extent_copy(H5S_extent_t *dst, const H5S_extent_t *src, hbool_t copy_max) done: FUNC_LEAVE_NOAPI(ret_value) -} /* end H5S_extent_copy() */ +} /* end H5S_extent_copy_real() */ /*------------------------------------------------------------------------- @@ -597,7 +626,7 @@ H5S_copy(const H5S_t *src, hbool_t share_selection, hbool_t copy_max) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "memory allocation failed") /* Copy the source dataspace's extent */ - if(H5S_extent_copy(&(dst->extent), &(src->extent), copy_max) < 0) + if(H5S_extent_copy_real(&(dst->extent), &(src->extent), copy_max) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, NULL, "can't copy extent") /* Copy the source dataspace's selection */ @@ -1262,14 +1291,14 @@ done: * *------------------------------------------------------------------------- */ -static herr_t +herr_t H5S_set_extent_simple(H5S_t *space, unsigned rank, const hsize_t *dims, const hsize_t *max) { unsigned u; /* Local index variable */ herr_t ret_value = SUCCEED; /* Return value */ - FUNC_ENTER_NOAPI_NOINIT + FUNC_ENTER_NOAPI(FAIL) /* Check args */ HDassert(rank <= H5S_MAX_RANK); @@ -1475,7 +1504,7 @@ H5Sencode(hid_t obj_id, void *buf, size_t *nalloc) if (NULL==(dspace=(H5S_t *)H5I_object_verify(obj_id, H5I_DATASPACE))) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") - if(H5S_encode(dspace, (unsigned char *)buf, nalloc)<0) + if(H5S_encode(dspace, (unsigned char **)&buf, nalloc)<0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTENCODE, FAIL, "can't encode datatype") done: @@ -1499,8 +1528,8 @@ done: * *------------------------------------------------------------------------- */ -static herr_t -H5S_encode(H5S_t *obj, unsigned char *buf, size_t *nalloc) +herr_t +H5S_encode(H5S_t *obj, unsigned char **p, size_t *nalloc) { size_t extent_size; /* Size of serialized dataspace extent */ hssize_t sselect_size; /* Signed size of serialized dataspace selection */ @@ -1519,34 +1548,34 @@ H5S_encode(H5S_t *obj, unsigned char *buf, size_t *nalloc) HGOTO_ERROR(H5E_DATASPACE, H5E_BADSIZE, FAIL, "can't find dataspace size") /* Find out the size of buffer needed for selection */ - if((sselect_size = H5S_SELECT_SERIAL_SIZE(obj)) < 0) + if((sselect_size = H5S_SELECT_SERIAL_SIZE(f, obj)) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_BADSIZE, FAIL, "can't find dataspace selection size") H5_CHECKED_ASSIGN(select_size, size_t, sselect_size, hssize_t); /* Verify the size of buffer. If it's not big enough, simply return the * right size without filling the buffer. */ - if(!buf || *nalloc < (extent_size + select_size + 1 + 1 + 1 + 4)) + if(!*p || *nalloc < (extent_size + select_size + 1 + 1 + 1 + 4)) *nalloc = extent_size + select_size + 1 + 1 + 1 + 4; else { /* Encode the type of the information */ - *buf++ = H5O_SDSPACE_ID; + *(*p)++ = H5O_SDSPACE_ID; /* Encode the version of the dataspace information */ - *buf++ = H5S_ENCODE_VERSION; + *(*p)++ = H5S_ENCODE_VERSION; /* Encode the "size of size" information */ - *buf++ = (unsigned char)H5F_SIZEOF_SIZE(f); + *(*p)++ = (unsigned char)H5F_SIZEOF_SIZE(f); /* Encode size of extent information. Pointer is actually moved in this macro. */ - UINT32ENCODE(buf, extent_size); + UINT32ENCODE(*p, extent_size); /* Encode the extent part of dataspace */ - if(H5O_msg_encode(f, H5O_SDSPACE_ID, TRUE, buf, obj) < 0) + if(H5O_msg_encode(f, H5O_SDSPACE_ID, TRUE, *p, obj) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTENCODE, FAIL, "can't encode extent space") - buf += extent_size; + *p += extent_size; /* Encode the selection part of dataspace. */ - if(H5S_SELECT_SERIALIZE(obj, &buf) < 0) + if(H5S_SELECT_SERIALIZE(f, obj, p) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTENCODE, FAIL, "can't encode select space") } /* end else */ @@ -1587,7 +1616,7 @@ H5Sdecode(const void *buf) if(buf == NULL) HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "empty buffer") - if((ds = H5S_decode((const unsigned char *)buf)) == NULL) + if((ds = H5S_decode((const unsigned char **)&buf)) == NULL) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDECODE, FAIL, "can't decode object") /* Register the type and return the ID */ @@ -1615,8 +1644,8 @@ done: * *------------------------------------------------------------------------- */ -static H5S_t* -H5S_decode(const unsigned char *buf) +H5S_t* +H5S_decode(const unsigned char **p) { H5S_t *ds; H5S_extent_t *extent; @@ -1628,28 +1657,28 @@ H5S_decode(const unsigned char *buf) FUNC_ENTER_NOAPI_NOINIT /* Decode the type of the information */ - if(*buf++ != H5O_SDSPACE_ID) + if(*(*p)++ != H5O_SDSPACE_ID) HGOTO_ERROR(H5E_DATASPACE, H5E_BADMESG, NULL, "not an encoded dataspace") /* Decode the version of the dataspace information */ - if(*buf++ != H5S_ENCODE_VERSION) + if(*(*p)++ != H5S_ENCODE_VERSION) HGOTO_ERROR(H5E_DATASPACE, H5E_VERSION, NULL, "unknown version of encoded dataspace") /* Decode the "size of size" information */ - sizeof_size = *buf++; + sizeof_size = *(*p)++; /* Allocate "fake" file structure */ if(NULL == (f = H5F_fake_alloc(sizeof_size))) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTALLOC, NULL, "can't allocate fake file struct") /* Decode size of extent information */ - UINT32DECODE(buf, extent_size); + UINT32DECODE(*p, extent_size); /* Decode the extent part of dataspace */ /* (pass mostly bogus file pointer and bogus DXPL) */ - if((extent = (H5S_extent_t *)H5O_msg_decode(f, H5P_DEFAULT, NULL, H5O_SDSPACE_ID, buf))==NULL) + if((extent = (H5S_extent_t *)H5O_msg_decode(f, H5P_DEFAULT, NULL, H5O_SDSPACE_ID, *p))==NULL) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDECODE, NULL, "can't decode object") - buf += extent_size; + *p += extent_size; /* Copy the extent into dataspace structure */ if((ds = H5FL_CALLOC(H5S_t))==NULL) @@ -1665,7 +1694,7 @@ H5S_decode(const unsigned char *buf) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTSET, NULL, "unable to set all selection") /* Decode the select part of dataspace. I believe this part always exists. */ - if(H5S_SELECT_DESERIALIZE(&ds, &buf) < 0) + if(H5S_SELECT_DESERIALIZE(f, &ds, p) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDECODE, NULL, "can't decode space selection") /* Set return value */ diff --git a/src/H5Sall.c b/src/H5Sall.c index 7eab8b3..7e33980 100644 --- a/src/H5Sall.c +++ b/src/H5Sall.c @@ -38,11 +38,14 @@ static herr_t H5S_all_get_seq_list(const H5S_t *space, unsigned flags, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); static herr_t H5S_all_release(H5S_t *space); static htri_t H5S_all_is_valid(const H5S_t *space); -static hssize_t H5S_all_serial_size(const H5S_t *space); -static herr_t H5S_all_serialize(const H5S_t *space, uint8_t **p); -static herr_t H5S_all_deserialize(H5S_t *space, const uint8_t **p); +static hssize_t H5S_all_serial_size(const H5F_t *f, const H5S_t *space); +static herr_t H5S_all_serialize(const H5F_t *f, const H5S_t *space, + uint8_t **p); +static herr_t H5S_all_deserialize(const H5F_t *f, H5S_t *space, + uint32_t version, uint8_t flags, const uint8_t **p); static herr_t H5S_all_bounds(const H5S_t *space, hsize_t *start, hsize_t *end); static herr_t H5S_all_offset(const H5S_t *space, hsize_t *off); +static int H5S_all_unlim_dim(const H5S_t *space); static htri_t H5S_all_is_contiguous(const H5S_t *space); static htri_t H5S_all_is_single(const H5S_t *space); static htri_t H5S_all_is_regular(const H5S_t *space); @@ -74,6 +77,8 @@ const H5S_select_class_t H5S_sel_all[1] = {{ H5S_all_deserialize, H5S_all_bounds, H5S_all_offset, + H5S_all_unlim_dim, + NULL, H5S_all_is_contiguous, H5S_all_is_single, H5S_all_is_regular, @@ -463,8 +468,9 @@ H5S_all_is_valid (const H5S_t H5_ATTR_UNUSED *space) Determine the number of bytes needed to store the serialized "all" selection information. USAGE - hssize_t H5S_all_serial_size(space) - H5S_t *space; IN: Dataspace pointer to query + hssize_t H5S_all_serial_size(f, space) + H5F_t *f IN: File pointer + H5S_t *space; IN: Dataspace pointer to query RETURNS The number of bytes required on success, negative on an error. DESCRIPTION @@ -476,7 +482,8 @@ H5S_all_is_valid (const H5S_t H5_ATTR_UNUSED *space) REVISION LOG --------------------------------------------------------------------------*/ static hssize_t -H5S_all_serial_size (const H5S_t H5_ATTR_UNUSED *space) +H5S_all_serial_size(const H5F_t H5_ATTR_UNUSED *f, + const H5S_t H5_ATTR_UNUSED *space) { FUNC_ENTER_NOAPI_NOINIT_NOERR @@ -496,7 +503,8 @@ H5S_all_serial_size (const H5S_t H5_ATTR_UNUSED *space) PURPOSE Serialize the current selection into a user-provided buffer. USAGE - herr_t H5S_all_serialize(space, p) + herr_t H5S_all_serialize(f, space, p) + H5F_t *f IN: File pointer const H5S_t *space; IN: Dataspace with selection to serialize uint8_t **p; OUT: Pointer to buffer to put serialized selection. Will be advanced to end of @@ -512,7 +520,8 @@ H5S_all_serial_size (const H5S_t H5_ATTR_UNUSED *space) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_all_serialize (const H5S_t *space, uint8_t **p) +H5S_all_serialize(const H5F_t H5_ATTR_UNUSED *f, const H5S_t *space, + uint8_t **p) { FUNC_ENTER_NOAPI_NOINIT_NOERR @@ -537,8 +546,11 @@ H5S_all_serialize (const H5S_t *space, uint8_t **p) Deserialize the current selection from a user-provided buffer. USAGE herr_t H5S_all_deserialize(space, p) + H5F_t *f IN: File pointer H5S_t *space; IN/OUT: Dataspace pointer to place selection into + uint32_t version IN: Selection version + uint8_t flags IN: Selection flags uint8 **p; OUT: Pointer to buffer holding serialized selection. Will be advanced to end of serialized selection. @@ -553,7 +565,9 @@ H5S_all_serialize (const H5S_t *space, uint8_t **p) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_all_deserialize(H5S_t *space, const uint8_t H5_ATTR_UNUSED **p) +H5S_all_deserialize(const H5F_t H5_ATTR_UNUSED *f, H5S_t *space, + uint32_t H5_ATTR_UNUSED version, uint8_t H5_ATTR_UNUSED flags, + const uint8_t H5_ATTR_UNUSED **p) { herr_t ret_value = SUCCEED; /* return value */ @@ -659,6 +673,36 @@ H5S_all_offset(const H5S_t H5_ATTR_UNUSED *space, hsize_t *offset) /*-------------------------------------------------------------------------- NAME + H5S_all_unlim_dim + PURPOSE + Return unlimited dimension of selection, or -1 if none + USAGE + int H5S_all_unlim_dim(space) + H5S_t *space; IN: Dataspace pointer to check + RETURNS + Unlimited dimension of selection, or -1 if none (never fails). + DESCRIPTION + Returns the index of the unlimited dimension in this selection, or -1 + if the selection has no unlimited dimension. "All" selections are + always unlimited in every dimension, though this is not reflected in + other calls, where the selection is "clipped" against the current + extent, so for consistency this function always returns -1. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static int +H5S_all_unlim_dim(const H5S_t H5_ATTR_UNUSED *space) +{ + FUNC_ENTER_NOAPI_NOERR + + FUNC_LEAVE_NOAPI(-1) +} /* end H5S_all_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME H5S_all_is_contiguous PURPOSE Check if a "all" selection is contiguous within the dataspace extent. @@ -976,6 +1020,7 @@ H5S_all_get_seq_list(const H5S_t H5_ATTR_UNUSED *space, unsigned H5_ATTR_UNUSED /* Determine the actual number of elements to use */ H5_CHECK_OVERFLOW(iter->elmt_left,hsize_t,size_t); elem_used=MIN(maxelem,(size_t)iter->elmt_left); + HDassert(elem_used > 0); /* Compute the offset in the dataset */ off[0]=iter->u.all.byte_offset; diff --git a/src/H5Shyper.c b/src/H5Shyper.c index 51b5ab6..88a3d21 100644 --- a/src/H5Shyper.c +++ b/src/H5Shyper.c @@ -45,6 +45,10 @@ static herr_t H5S_hyper_generate_spans(H5S_t *space); #ifdef NEW_HYPERSLAB_API static herr_t H5S_select_select (H5S_t *space1, H5S_seloper_t op, H5S_t *space2); #endif /*NEW_HYPERSLAB_API*/ +static void H5S__hyper_get_clip_diminfo(hsize_t start, hsize_t stride, + hsize_t *count, hsize_t *block, hsize_t clip_size); +static hsize_t H5S__hyper_get_clip_extent_real(const H5S_t *clip_space, + hsize_t num_slices, hbool_t incl_trail); /* Selection callbacks */ static herr_t H5S_hyper_copy(H5S_t *dst, const H5S_t *src, hbool_t share_selection); @@ -53,11 +57,16 @@ static herr_t H5S_hyper_get_seq_list(const H5S_t *space, unsigned flags, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); static herr_t H5S_hyper_release(H5S_t *space); static htri_t H5S_hyper_is_valid(const H5S_t *space); -static hssize_t H5S_hyper_serial_size(const H5S_t *space); -static herr_t H5S_hyper_serialize(const H5S_t *space, uint8_t **p); -static herr_t H5S_hyper_deserialize(H5S_t *space, const uint8_t **p); +static hssize_t H5S_hyper_serial_size(const H5F_t *f, const H5S_t *space); +static herr_t H5S_hyper_serialize(const H5F_t *f, const H5S_t *space, + uint8_t **p); +static herr_t H5S_hyper_deserialize(const H5F_t *f, H5S_t *space, + uint32_t version, uint8_t flags, const uint8_t **p); static herr_t H5S_hyper_bounds(const H5S_t *space, hsize_t *start, hsize_t *end); static herr_t H5S_hyper_offset(const H5S_t *space, hsize_t *offset); +static int H5S_hyper_unlim_dim(const H5S_t *space); +static herr_t H5S_hyper_num_elem_non_unlim(const H5S_t *space, + hsize_t *num_elem_non_unlim); static htri_t H5S_hyper_is_contiguous(const H5S_t *space); static htri_t H5S_hyper_is_single(const H5S_t *space); static htri_t H5S_hyper_is_regular(const H5S_t *space); @@ -94,6 +103,8 @@ const H5S_select_class_t H5S_sel_hyper[1] = {{ H5S_hyper_deserialize, H5S_hyper_bounds, H5S_hyper_offset, + H5S_hyper_unlim_dim, + H5S_hyper_num_elem_non_unlim, H5S_hyper_is_contiguous, H5S_hyper_is_single, H5S_hyper_is_regular, @@ -248,6 +259,7 @@ H5S_hyper_iter_init(H5S_sel_iter_t *iter, const H5S_t *space) /* Check args */ HDassert(space && H5S_SEL_HYPERSLABS == H5S_GET_SELECT_TYPE(space)); HDassert(iter); + HDassert(space->select.sel_info.hslab->unlim_dim < 0); /* Initialize the number of points to iterate over */ iter->elmt_left = space->select.num_elem; @@ -1644,6 +1656,8 @@ H5S_hyper_copy (H5S_t *dst, const H5S_t *src, hbool_t share_selection) dst_hslab->app_diminfo[u]=src_hslab->app_diminfo[u]; } /* end for */ } /* end if */ + dst_hslab->unlim_dim = src_hslab->unlim_dim; + dst_hslab->num_elem_non_unlim = src_hslab->num_elem_non_unlim; dst->select.sel_info.hslab->span_lst=src->select.sel_info.hslab->span_lst; /* Check if there is hyperslab span information to copy */ @@ -1759,6 +1773,10 @@ H5S_hyper_is_valid (const H5S_t *space) HDassert(space); + /* Check for unlimited selection */ + if(space->select.sel_info.hslab->unlim_dim >= 0) + HGOTO_DONE(FALSE) + /* Check for a "regular" hyperslab selection */ if(space->select.sel_info.hslab->diminfo_valid) { const H5S_hyper_dim_t *diminfo=space->select.sel_info.hslab->opt_diminfo; /* local alias for diminfo */ @@ -1863,6 +1881,14 @@ H5S_get_select_hyper_nblocks(H5S_t *space) FUNC_ENTER_NOAPI_NOINIT_NOERR HDassert(space); + HDassert(space->select.sel_info.hslab->unlim_dim < 0); + + /* Check for unlimited selection */ + if((space->select.sel_info.hslab->unlim_dim >= 0) + && space->select.sel_info.hslab->app_diminfo[space->select.sel_info.hslab->unlim_dim].count == H5S_UNLIMITED) { + HDassert(space->select.sel_info.hslab->diminfo_valid); + HGOTO_DONE(H5S_UNLIMITED) + } /* end if */ /* Check for a "regular" hyperslab selection */ if(space->select.sel_info.hslab->diminfo_valid) { @@ -1875,6 +1901,7 @@ H5S_get_select_hyper_nblocks(H5S_t *space) else ret_value = H5S_hyper_span_nblocks(space->select.sel_info.hslab->span_lst); +done: FUNC_LEAVE_NOAPI(ret_value) } /* H5S_get_select_hyper_nblocks() */ @@ -1910,6 +1937,8 @@ H5Sget_select_hyper_nblocks(hid_t spaceid) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a data space") if(H5S_GET_SELECT_TYPE(space) != H5S_SEL_HYPERSLABS) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a hyperslab selection") + if(space->select.sel_info.hslab->unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot get number of blocks for unlimited selection") ret_value = (hssize_t)H5S_get_select_hyper_nblocks(space); @@ -1925,8 +1954,9 @@ done: Determine the number of bytes needed to store the serialized hyperslab selection information. USAGE - hssize_t H5S_hyper_serial_size(space) - H5S_t *space; IN: Dataspace pointer to query + hssize_t H5S_hyper_serial_size(f, space) + H5F_t *f IN: File pointer + H5S_t *space; IN: Dataspace pointer to query RETURNS The number of bytes required on success, negative on an error. DESCRIPTION @@ -1938,7 +1968,7 @@ done: REVISION LOG --------------------------------------------------------------------------*/ static hssize_t -H5S_hyper_serial_size(const H5S_t *space) +H5S_hyper_serial_size(const H5F_t *f, const H5S_t *space) { unsigned u; /* Counter */ hsize_t block_count; /* block counter for regular hyperslabs */ @@ -1948,24 +1978,41 @@ H5S_hyper_serial_size(const H5S_t *space) HDassert(space); - /* Basic number of bytes required to serialize hyperslab selection: - * <type (4 bytes)> + <version (4 bytes)> + <padding (4 bytes)> + - * <length (4 bytes)> + <rank (4 bytes)> + <# of blocks (4 bytes)> = 24 bytes - */ - ret_value = 24; + /* Check for version (right now, an unlimited dimension is the only thing + * that would bump the version) */ + if(space->select.sel_info.hslab->unlim_dim >= 0) + /* Version 2 */ + /* Size required is always: + * <type (4 bytes)> + <version (4 bytes)> + <flags (1 byte)> + + * <length (4 bytes)> + <rank (4 bytes)> + + * (4 * <rank> * <start/stride/count/block (sizeof_size bytes)>) = + * 17 + (4 * sizeof_size) bytes + */ + ret_value = (hssize_t)17 + ((hssize_t)4 * (hssize_t)space->extent.rank + * (hssize_t)H5F_SIZEOF_SIZE(f)); + else { + /* Version 1 */ + /* Basic number of bytes required to serialize hyperslab selection: + * <type (4 bytes)> + <version (4 bytes)> + <padding (4 bytes)> + + * <length (4 bytes)> + <rank (4 bytes)> + <# of blocks (4 bytes)> + * = 24 bytes + */ + ret_value = 24; - /* Check for a "regular" hyperslab selection */ - if(space->select.sel_info.hslab->diminfo_valid) { - /* Check each dimension */ - for(block_count = 1, u = 0; u < space->extent.rank; u++) - block_count *= space->select.sel_info.hslab->opt_diminfo[u].count; - } /* end if */ - else - /* Spin through hyperslab spans, adding 8 * rank bytes for each block */ - block_count = H5S_hyper_span_nblocks(space->select.sel_info.hslab->span_lst); + /* Check for a "regular" hyperslab selection */ + if(space->select.sel_info.hslab->diminfo_valid) { + /* Check each dimension */ + for(block_count = 1, u = 0; u < space->extent.rank; u++) + block_count *= space->select.sel_info.hslab->opt_diminfo[u].count; + } /* end if */ + else + /* Spin through hyperslab spans, adding 8 * rank bytes for each + * block */ + block_count = H5S_hyper_span_nblocks(space->select.sel_info.hslab->span_lst); - H5_CHECK_OVERFLOW((8 * space->extent.rank * block_count), hsize_t, hssize_t); - ret_value += (hssize_t)(8 * block_count * space->extent.rank); + H5_CHECK_OVERFLOW((8 * space->extent.rank * block_count), hsize_t, hssize_t); + ret_value += (hssize_t)(8 * block_count * space->extent.rank); + } /* end else */ FUNC_LEAVE_NOAPI(ret_value) } /* end H5S_hyper_serial_size() */ @@ -1994,7 +2041,8 @@ H5S_hyper_serial_size(const H5S_t *space) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_hyper_serialize_helper (const H5S_hyper_span_info_t *spans, hsize_t *start, hsize_t *end, hsize_t rank, uint8_t **p) +H5S_hyper_serialize_helper (const H5S_hyper_span_info_t *spans, + hsize_t *start, hsize_t *end, hsize_t rank, uint8_t **p) { H5S_hyper_span_t *curr; /* Pointer to current hyperslab span */ hsize_t u; /* Index variable */ @@ -2056,6 +2104,7 @@ done: Serialize the current selection into a user-provided buffer. USAGE herr_t H5S_hyper_serialize(space, p) + H5F_t *f IN: File pointer const H5S_t *space; IN: Dataspace with selection to serialize uint8_t **p; OUT: Pointer to buffer to put serialized selection. Will be advanced to end of @@ -2071,7 +2120,7 @@ done: REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_hyper_serialize (const H5S_t *space, uint8_t **p) +H5S_hyper_serialize(const H5F_t *f, const H5S_t *space, uint8_t **p) { const H5S_hyper_dim_t *diminfo; /* Alias for dataspace's diminfo information */ hsize_t tmp_count[H5O_LAYOUT_NDIMS]; /* Temporary hyperslab counts */ @@ -2081,6 +2130,8 @@ H5S_hyper_serialize (const H5S_t *space, uint8_t **p) hsize_t temp_off; /* Offset in a given dimension */ uint8_t *lenp; /* pointer to length location for later storage */ uint32_t len = 0; /* number of bytes used */ + uint32_t version; /* Version number */ + uint8_t flags = 0; /* Flags for message */ hsize_t block_count; /* block counter for regular hyperslabs */ unsigned fast_dim; /* Rank of the fastest changing dimension for the dataspace */ unsigned ndims; /* Rank of the dataspace */ @@ -2090,10 +2141,21 @@ H5S_hyper_serialize (const H5S_t *space, uint8_t **p) HDassert(space); + /* Calculate version */ + if(space->select.sel_info.hslab->unlim_dim >= 0) { + version = 2; + flags |= H5S_SELECT_FLAG_UNLIM; + } /* end if */ + else + version = 1; + /* Store the preamble information */ - UINT32ENCODE(*p, (uint32_t)H5S_GET_SELECT_TYPE(space)); /* Store the type of selection */ - UINT32ENCODE(*p, (uint32_t)1); /* Store the version number */ - UINT32ENCODE(*p, (uint32_t)0); /* Store the un-used padding */ + UINT32ENCODE(*p, (uint32_t)H5S_GET_SELECT_TYPE(space)); /* Store the type of selection */ + UINT32ENCODE(*p, version); /* Store the version number */ + if(version >= 2) + *(*p)++ = flags; /* Store the flags */ + else + UINT32ENCODE(*p, (uint32_t)0); /* Store the un-used padding */ lenp = *p; /* keep the pointer to the length location for later */ *p += 4; /* skip over space for length */ @@ -2101,8 +2163,23 @@ H5S_hyper_serialize (const H5S_t *space, uint8_t **p) UINT32ENCODE(*p, (uint32_t)space->extent.rank); len += 4; + /* If there is an unlimited dimension, only encode opt_unlim_diminfo */ + if(flags & H5S_SELECT_FLAG_UNLIM) { + unsigned i; + + HDassert(H5S_UNLIMITED == HSIZE_UNDEF); + + /* Iterate over dimensions */ + for(i = 0; i < space->extent.rank; i++) { + /* Encode start/stride/block/count */ + H5F_size_encode(f, p, space->select.sel_info.hslab->opt_diminfo[i].start); + H5F_size_encode(f, p, space->select.sel_info.hslab->opt_diminfo[i].stride); + H5F_size_encode(f, p, space->select.sel_info.hslab->opt_diminfo[i].count); + H5F_size_encode(f, p, space->select.sel_info.hslab->opt_diminfo[i].block); + } /* end for */ + } /* end if */ /* Check for a "regular" hyperslab selection */ - if(space->select.sel_info.hslab->diminfo_valid) { + else if(space->select.sel_info.hslab->diminfo_valid) { unsigned u; /* Local counting variable */ /* Set some convienence values */ @@ -2219,8 +2296,11 @@ H5S_hyper_serialize (const H5S_t *space, uint8_t **p) Deserialize the current selection from a user-provided buffer. USAGE herr_t H5S_hyper_deserialize(space, p) + H5F_t *f IN: File pointer H5S_t *space; IN/OUT: Dataspace pointer to place selection into + uint32_t version IN: Selection version + uint8_t flags IN: Selection flags uint8 **p; OUT: Pointer to buffer holding serialized selection. Will be advanced to end of serialized selection. @@ -2235,7 +2315,8 @@ H5S_hyper_serialize (const H5S_t *space, uint8_t **p) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_hyper_deserialize (H5S_t *space, const uint8_t **p) +H5S_hyper_deserialize(const H5F_t *f, H5S_t *space, + uint32_t H5_ATTR_UNUSED version, uint8_t flags, const uint8_t **p) { unsigned rank; /* rank of points */ size_t num_elem=0; /* number of elements in selection */ @@ -2262,32 +2343,54 @@ H5S_hyper_deserialize (H5S_t *space, const uint8_t **p) /* Deserialize slabs to select */ /* (The header and rank have already beed decoded) */ rank = space->extent.rank; /* Retrieve rank from space */ - UINT32DECODE(*p,num_elem); /* decode the number of points */ - /* Set the count & stride for all blocks */ - for(tcount=count,tstride=stride,j=0; j<rank; j++,tstride++,tcount++) { - *tcount=1; - *tstride=1; - } /* end for */ + /* If there is an unlimited dimension, only encode opt_unlim_diminfo */ + if(flags & H5S_SELECT_FLAG_UNLIM) { + HDassert(H5S_UNLIMITED == HSIZE_UNDEF); + HDassert(version >= 2); + + /* Iterate over dimensions */ + for(i = 0; i < space->extent.rank; i++) { + /* Decode start/stride/block/count */ + H5F_size_decode(f, p, &start[i]); + H5F_size_decode(f, p, &stride[i]); + H5F_size_decode(f, p, &count[i]); + H5F_size_decode(f, p, &block[i]); + } /* end for */ - /* Retrieve the coordinates from the buffer */ - for(i=0; i<num_elem; i++) { - /* Decode the starting points */ - for(tstart=start,j=0; j<rank; j++,tstart++) - UINT32DECODE(*p, *tstart); + /* Select the hyperslab to the current selection */ + if((ret_value = H5S_select_hyperslab(space, H5S_SELECT_SET, start, stride, count, block)) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") + } /* end if */ + else { + /* decode the number of points */ + UINT32DECODE(*p,num_elem); - /* Decode the ending points */ - for(tend=end,j=0; j<rank; j++,tend++) - UINT32DECODE(*p, *tend); + /* Set the count & stride for all blocks */ + for(tcount=count,tstride=stride,j=0; j<rank; j++,tstride++,tcount++) { + *tcount=1; + *tstride=1; + } /* end for */ - /* Change the ending points into blocks */ - for(tblock=block,tstart=start,tend=end,j=0; j<rank; j++,tstart++,tend++,tblock++) - *tblock=(*tend-*tstart)+1; + /* Retrieve the coordinates from the buffer */ + for(i=0; i<num_elem; i++) { + /* Decode the starting points */ + for(tstart=start,j=0; j<rank; j++,tstart++) + UINT32DECODE(*p, *tstart); - /* Select or add the hyperslab to the current selection */ - if((ret_value=H5S_select_hyperslab(space,(i==0 ? H5S_SELECT_SET : H5S_SELECT_OR),start,stride,count,block))<0) - HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") - } /* end for */ + /* Decode the ending points */ + for(tend=end,j=0; j<rank; j++,tend++) + UINT32DECODE(*p, *tend); + + /* Change the ending points into blocks */ + for(tblock=block,tstart=start,tend=end,j=0; j<rank; j++,tstart++,tend++,tblock++) + *tblock=(*tend-*tstart)+1; + + /* Select or add the hyperslab to the current selection */ + if((ret_value=H5S_select_hyperslab(space,(i==0 ? H5S_SELECT_SET : H5S_SELECT_OR),start,stride,count,block))<0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") + } /* end for */ + } /* end else */ done: FUNC_LEAVE_NOAPI(ret_value) @@ -2437,6 +2540,7 @@ H5S_get_select_hyper_blocklist(H5S_t *space, hbool_t internal, hsize_t startbloc HDassert(space); HDassert(buf); + HDassert(space->select.sel_info.hslab->unlim_dim < 0); /* Check for a "regular" hyperslab selection */ if(space->select.sel_info.hslab->diminfo_valid) { @@ -2460,11 +2564,19 @@ H5S_get_select_hyper_blocklist(H5S_t *space, hbool_t internal, hsize_t startbloc */ diminfo = space->select.sel_info.hslab->opt_diminfo; else - /* - * Use the "application dimension information" to pass back to the user - * the blocks they set, not the optimized, internal information. - */ - diminfo = space->select.sel_info.hslab->app_diminfo; + if(space->select.sel_info.hslab->unlim_dim >= 0) + /* + * There is an unlimited dimension so we must use opt_diminfo as + * it has been "clipped" to the current extent. + */ + diminfo = space->select.sel_info.hslab->opt_diminfo; + else + /* + * Use the "application dimension information" to pass back to + * the user the blocks they set, not the optimized, internal + * information. + */ + diminfo = space->select.sel_info.hslab->app_diminfo; /* Build the tables of count sizes as well as the initial offset */ for(u = 0; u < ndims; u++) { @@ -2601,6 +2713,8 @@ H5Sget_select_hyper_blocklist(hid_t spaceid, hsize_t startblock, HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a data space") if(H5S_GET_SELECT_TYPE(space)!=H5S_SEL_HYPERSLABS) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a hyperslab selection") + if(space->select.sel_info.hslab->unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot get blocklist for unlimited selection") /* Go get the correct number of blocks */ if(numblocks > 0) @@ -2743,7 +2857,10 @@ H5S_hyper_bounds(const H5S_t *space, hsize_t *start, hsize_t *end) start[i] = diminfo[i].start + (hsize_t)space->select.offset[i]; /* Compute the largest location in this dimension */ - end[i] = diminfo[i].start + diminfo[i].stride * (diminfo[i].count - 1) + (diminfo[i].block - 1) + (hsize_t)space->select.offset[i]; + if((int)i == space->select.sel_info.hslab->unlim_dim) + end[i] = H5S_UNLIMITED; + else + end[i] = diminfo[i].start + diminfo[i].stride * (diminfo[i].count - 1) + (diminfo[i].block - 1) + (hsize_t)space->select.offset[i]; } /* end for */ } /* end if */ else { @@ -2866,6 +2983,75 @@ done: /*-------------------------------------------------------------------------- NAME + H5S_hyper_unlim_dim + PURPOSE + Return unlimited dimension of selection, or -1 if none + USAGE + int H5S_hyper_unlim_dim(space) + H5S_t *space; IN: Dataspace pointer to check + RETURNS + Unlimited dimension of selection, or -1 if none (never fails). + DESCRIPTION + Returns the index of the unlimited dimension of the selection, or -1 + if the selection has no unlimited dimension. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static int +H5S_hyper_unlim_dim(const H5S_t *space) +{ + FUNC_ENTER_NOAPI_NOERR + + FUNC_LEAVE_NOAPI(space->select.sel_info.hslab->unlim_dim) +} /* end H5S_hyper_get_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_num_elem_non_unlim + PURPOSE + Return number of elements in the non-unlimited dimensions + USAGE + herr_t H5S_hyper_num_elem_non_unlim(space,num_elem_non_unlim) + H5S_t *space; IN: Dataspace pointer to check + hsize_t *num_elem_non_unlim; OUT: Number of elements in the non-unlimited dimensions + RETURNS + Non-negative on success/Negative on failure + DESCRIPTION + Returns the number of elements in a slice through the non-unlimited + dimensions of the selection. Fails if the selection has no unlimited + dimension. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static herr_t +H5S_hyper_num_elem_non_unlim(const H5S_t *space, hsize_t *num_elem_non_unlim) +{ + herr_t ret_value = SUCCEED; + + FUNC_ENTER_NOAPI(FAIL) + + /* Sanity check */ + HDassert(space); + HDassert(num_elem_non_unlim); + + /* Get number of elements in the non-unlimited dimensions */ + if(space->select.sel_info.hslab->unlim_dim >= 0) + *num_elem_non_unlim = space->select.sel_info.hslab->num_elem_non_unlim; + else + HGOTO_ERROR(H5E_DATASPACE, H5E_BADVALUE, FAIL, "selection has no unlimited dimension") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_num_elem_non_unlim() */ + + +/*-------------------------------------------------------------------------- + NAME H5S_hyper_is_contiguous PURPOSE Check if a hyperslab selection is contiguous within the dataspace extent. @@ -3193,13 +3379,15 @@ H5S_hyper_release(H5S_t *space) space->select.num_elem = 0; /* Release irregular hyperslab information */ - if(space->select.sel_info.hslab->span_lst != NULL) { - if(H5S_hyper_free_span_info(space->select.sel_info.hslab->span_lst) < 0) - HGOTO_ERROR(H5E_INTERNAL, H5E_CANTFREE, FAIL, "failed to release hyperslab spans") - } /* end if */ + if(space->select.sel_info.hslab) { + if(space->select.sel_info.hslab->span_lst != NULL) { + if(H5S_hyper_free_span_info(space->select.sel_info.hslab->span_lst) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_CANTFREE, FAIL, "failed to release hyperslab spans") + } /* end if */ - /* Release space for the hyperslab selection information */ - space->select.sel_info.hslab = H5FL_FREE(H5S_hyper_sel_t, space->select.sel_info.hslab); + /* Release space for the hyperslab selection information */ + space->select.sel_info.hslab = H5FL_FREE(H5S_hyper_sel_t, space->select.sel_info.hslab); + } /* end if */ done: FUNC_LEAVE_NOAPI(ret_value) @@ -3574,6 +3762,9 @@ H5S_hyper_add_span_element(H5S_t *space, unsigned rank, hsize_t *coords) /* Reset "regular" hyperslab flag */ space->select.sel_info.hslab->diminfo_valid = FALSE; + /* Set unlim_dim */ + space->select.sel_info.hslab->unlim_dim = -1; + /* Set # of elements in selection */ space->select.num_elem = 1; } /* end if */ @@ -4283,6 +4474,9 @@ H5S_hyper_project_simple(const H5S_t *base_space, H5S_t *new_space, hsize_t *off if(NULL == (new_space->select.sel_info.hslab = H5FL_MALLOC(H5S_hyper_sel_t))) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab info") + /* Set unlim_dim */ + new_space->select.sel_info.hslab->unlim_dim = -1; + /* Check for a "regular" hyperslab selection */ if(base_space->select.sel_info.hslab->diminfo_valid) { unsigned base_space_dim; /* Current dimension in the base dataspace */ @@ -4833,7 +5027,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add span 'a' with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Advance span 'a', leave span 'b' */ H5S_hyper_recover_span(&recover_a,&span_a,span_a->next); @@ -4848,7 +5042,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add lower part of span 'a' with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_b->low-1,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Check for overlaps between upper part of span 'a' and lower part of span 'b' */ @@ -4859,7 +5053,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(span_a->down==NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_b->low,span_a->high,NULL,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ /* If there are down spans, check for the overlap in them and add to each appropriate list */ else { @@ -4876,7 +5070,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_not_b!=NULL) { /* Merge/add overlapped part with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_b->low,span_a->high,down_a_not_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_not_b); @@ -4886,7 +5080,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_and_b!=NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_b->low,span_a->high,down_a_and_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_and_b); @@ -4896,7 +5090,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_b_not_a!=NULL) { /* Merge/add overlapped part with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_a->high,down_b_not_a,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_b_not_a); @@ -4935,7 +5129,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add lower part of span 'a' with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_b->low-1,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Check for overlaps between middle part of span 'a' and span 'b' */ @@ -4946,7 +5140,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(span_a->down==NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_b->low,span_b->high,NULL,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ /* If there are down spans, check for the overlap in them and add to each appropriate list */ else { @@ -4963,7 +5157,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_not_b!=NULL) { /* Merge/add overlapped part with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_b->low,span_b->high,down_a_not_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_not_b); @@ -4973,7 +5167,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_and_b!=NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_b->low,span_b->high,down_a_and_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_and_b); @@ -4983,7 +5177,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_b_not_a!=NULL) { /* Merge/add overlapped part with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_b->high,down_b_not_a,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_b_not_a); @@ -5014,7 +5208,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(span_a->low>span_b->low) { /* Merge/add lower part of span 'b' with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_a->low-1,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ else { /* Keep going, nothing to split off */ @@ -5029,7 +5223,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(span_a->down==NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_a->low,span_a->high,NULL,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ /* If there are down spans, check for the overlap in them and add to each appropriate list */ else { @@ -5046,7 +5240,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_not_b!=NULL) { /* Merge/add overlapped part with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_a->high,down_a_not_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_not_b); @@ -5056,7 +5250,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_and_b!=NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_a->low,span_a->high,down_a_and_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_and_b); @@ -5066,7 +5260,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_b_not_a!=NULL) { /* Merge/add overlapped part with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_a->low,span_a->high,down_b_not_a,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_b_not_a); @@ -5106,7 +5300,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add lower part of span 'b' with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_a->low-1,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ else { /* Keep going, nothing to split off */ @@ -5121,7 +5315,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(span_a->down==NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_a->low,span_b->high,NULL,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") } /* end if */ /* If there are down spans, check for the overlap in them and add to each appropriate list */ else { @@ -5138,7 +5332,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_not_b!=NULL) { /* Merge/add overlapped part with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_b->high,down_a_not_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_not_b); @@ -5148,7 +5342,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_a_and_b!=NULL) { /* Merge/add overlapped part with/to a_and_b list */ if(H5S_hyper_append_span(&last_a_and_b,a_and_b,span_a->low,span_b->high,down_a_and_b,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_a_and_b); @@ -5158,7 +5352,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s if(down_b_not_a!=NULL) { /* Merge/add overlapped part with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_a->low,span_b->high,down_b_not_a,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Release the down span tree generated */ H5S_hyper_free_span_info(down_b_not_a); @@ -5187,7 +5381,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add span 'b' with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_b->high,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Advance span 'b', leave span 'a' */ H5S_hyper_recover_span(&recover_b,&span_b,span_b->next); @@ -5201,7 +5395,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add span 'a' with/to a_not_b list */ if(H5S_hyper_append_span(&last_a_not_b,a_not_b,span_a->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Advance to the next 'a' span */ H5S_hyper_recover_span(&recover_a,&span_a,span_a->next); @@ -5214,7 +5408,7 @@ H5S_hyper_clip_spans (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_info_t *b_s /* Merge/add span 'b' with/to b_not_a list */ if(H5S_hyper_append_span(&last_b_not_a,b_not_a,span_b->low,span_b->high,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") /* Advance to the next 'b' span */ H5S_hyper_recover_span(&recover_b,&span_b,span_b->next); @@ -5296,7 +5490,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf if(span_a->high<span_b->low) { /* Merge/add span 'a' with/to the merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Advance span 'a' */ H5S_hyper_recover_span(&recover_a,&span_a,span_a->next); @@ -5311,19 +5505,19 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf if(H5S_hyper_cmp_spans(span_a->down,span_b->down)==TRUE) { /* Merge/add copy of span 'a' with/to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* Merge/add lower part of span 'a' with/to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_b->low-1,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Get merged span tree for overlapped section */ tmp_spans=H5S_hyper_merge_spans_helper(span_a->down,span_b->down); /* Merge/add overlapped section to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_a->high,tmp_spans,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Release merged span tree for overlapped section */ H5S_hyper_free_span_info(tmp_spans); @@ -5360,19 +5554,19 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf if(H5S_hyper_cmp_spans(span_a->down,span_b->down)==TRUE) { /* Merge/add copy of lower & middle parts of span 'a' to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_b->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* Merge/add lower part of span 'a' to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_b->low-1,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Get merged span tree for overlapped section */ tmp_spans=H5S_hyper_merge_spans_helper(span_a->down,span_b->down); /* Merge/add overlapped section to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_b->high,tmp_spans,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Release merged span tree for overlapped section */ H5S_hyper_free_span_info(tmp_spans); @@ -5400,14 +5594,14 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf if(H5S_hyper_cmp_spans(span_a->down,span_b->down)==TRUE) { /* Merge/add copy of lower & middle parts of span 'b' to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* Check if there is a lower part of span 'b' */ if(span_a->low>span_b->low) { /* Merge/add lower part of span 'b' to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_a->low-1,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* No lower part of span 'b' , keep going... */ @@ -5418,7 +5612,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf /* Merge/add overlapped section to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_a->high,tmp_spans,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Release merged span tree for overlapped section */ H5S_hyper_free_span_info(tmp_spans); @@ -5455,14 +5649,14 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf if(H5S_hyper_cmp_spans(span_a->down,span_b->down)==TRUE) { /* Merge/add copy of span 'b' to merged spans if so */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_b->high,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* Check if there is a lower part of span 'b' */ if(span_a->low>span_b->low) { /* Merge/add lower part of span 'b' to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_a->low-1,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") } /* end if */ else { /* No lower part of span 'b' , keep going... */ @@ -5473,7 +5667,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf /* Merge/add overlapped section to merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_b->high,tmp_spans,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Release merged span tree for overlapped section */ H5S_hyper_free_span_info(tmp_spans); @@ -5499,7 +5693,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf else { /* Merge/add span 'b' with the merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_b->high,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Advance span 'b' */ H5S_hyper_recover_span(&recover_b,&span_b,span_b->next); @@ -5511,7 +5705,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf while(span_a!=NULL) { /* Merge/add all 'a' spans into the merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_a->low,span_a->high,span_a->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Advance to next 'a' span, until all processed */ H5S_hyper_recover_span(&recover_a,&span_a,span_a->next); @@ -5523,7 +5717,7 @@ H5S_hyper_merge_spans_helper (H5S_hyper_span_info_t *a_spans, H5S_hyper_span_inf while(span_b!=NULL) { /* Merge/add all 'b' spans into the merged spans */ if(H5S_hyper_append_span(&prev_span_merge,&merged_spans,span_b->low,span_b->high,span_b->down,NULL)==FAIL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab span") + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, NULL, "can't allocate hyperslab span") /* Advance to next 'b' span, until all processed */ H5S_hyper_recover_span(&recover_b,&span_b,span_b->next); @@ -6029,6 +6223,15 @@ H5S_hyper_generate_spans(H5S_t *space) /* Get the diminfo */ for(u=0; u<space->extent.rank; u++) { + /* Check for unlimited dimension and return error */ + /* These should be able to be converted to assertions once everything + * that calls this function checks for unlimited selections first + * (especially the new hyperslab API) -NAF */ + if(space->select.sel_info.hslab->opt_diminfo[u].count == H5S_UNLIMITED) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "can't generate spans with unlimited count") + if(space->select.sel_info.hslab->opt_diminfo[u].block == H5S_UNLIMITED) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "can't generate spans with unlimited block") + tmp_start[u]=space->select.sel_info.hslab->opt_diminfo[u].start; tmp_stride[u]=space->select.sel_info.hslab->opt_diminfo[u].stride; tmp_count[u]=space->select.sel_info.hslab->opt_diminfo[u].count; @@ -6316,6 +6519,7 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, const hsize_t *opt_count; /* Optimized count information */ const hsize_t *opt_block; /* Optimized block information */ unsigned u; /* Counters */ + int unlim_dim = -1; /* Unlimited dimension in selection, of -1 if none */ herr_t ret_value=SUCCEED; /* Return value */ FUNC_ENTER_NOAPI(FAIL) @@ -6334,6 +6538,18 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, if(block==NULL) block = _ones; + /* Check for unlimited dimension */ + for(u = 0; u<space->extent.rank; u++) + if((count[u] == H5S_UNLIMITED) || (block[u] == H5S_UNLIMITED)) { + if(unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot have more than one unlimited dimension in selection") + else { + if(count[u] == block[u] /* == H5S_UNLIMITED */) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "count and block cannot both be unlimited") + unlim_dim = (int)u; + } /* end else */ + } /* end if */ + /* * Check new selection. */ @@ -6382,7 +6598,7 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, opt_block = int_block; for(u=0; u<space->extent.rank; u++) { /* contiguous hyperslabs have the block size equal to the stride */ - if(stride[u]==block[u]) { + if((stride[u] == block[u]) && (count[u] != H5S_UNLIMITED)) { int_count[u]=1; int_stride[u]=1; if(block[u]==1) @@ -6394,7 +6610,8 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, if(count[u]==1) int_stride[u]=1; else { - HDassert(stride[u] > block[u]); + HDassert((stride[u] > block[u]) || ((stride[u] == block[u]) + && (count[u] == H5S_UNLIMITED))); int_stride[u]=stride[u]; } /* end else */ int_count[u]=count[u]; @@ -6403,6 +6620,32 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, } /* end for */ } /* end else */ + /* Check for operating on unlimited selection */ + if((H5S_GET_SELECT_TYPE(space) == H5S_SEL_HYPERSLABS) + && (space->select.sel_info.hslab->unlim_dim >= 0) + && (op != H5S_SELECT_SET)) + { + /* Check for invalid operation */ + if(unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot modify unlimited selection with another unlimited selection") + if(!((op == H5S_SELECT_AND) || (op == H5S_SELECT_NOTA))) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "unsupported operation on unlimited selection") + HDassert(space->select.sel_info.hslab->diminfo_valid); + + /* Clip unlimited selection to include new selection */ + if(H5S_hyper_clip_unlim(space, + start[space->select.sel_info.hslab->unlim_dim] + + ((opt_count[space->select.sel_info.hslab->unlim_dim] + - (hsize_t)1) + * opt_stride[space->select.sel_info.hslab->unlim_dim]) + + opt_block[space->select.sel_info.hslab->unlim_dim]) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* If an empty space was returned it must be "none" */ + HDassert((space->select.num_elem > (hsize_t)0) + || (space->select.type->type == H5S_SEL_NONE)); + } /* end if */ + /* Fixup operation for non-hyperslab selections */ switch(H5S_GET_SELECT_TYPE(space)) { case H5S_SEL_NONE: /* No elements selected in dataspace */ @@ -6522,16 +6765,64 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, space->select.num_elem *= (opt_count[u] * opt_block[u]); } /* end for */ + /* Save unlim_dim */ + space->select.sel_info.hslab->unlim_dim = unlim_dim; + /* Indicate that the dimension information is valid */ space->select.sel_info.hslab->diminfo_valid = TRUE; /* Indicate that there's no slab information */ space->select.sel_info.hslab->span_lst = NULL; + + /* Handle unlimited selections */ + if(unlim_dim >= 0) { + /* Calculate num_elem_non_unlim */ + space->select.sel_info.hslab->num_elem_non_unlim = (hsize_t)1; + for(u = 0; u < space->extent.rank; u++) + if((int)u != unlim_dim) + space->select.sel_info.hslab->num_elem_non_unlim *= (opt_count[u] * opt_block[u]); + + /* Set num_elem */ + if(space->select.num_elem != (hsize_t)0) + space->select.num_elem = H5S_UNLIMITED; + } /* end if */ } /* end if */ else if(op >= H5S_SELECT_OR && op <= H5S_SELECT_NOTA) { /* Sanity check */ HDassert(H5S_GET_SELECT_TYPE(space) == H5S_SEL_HYPERSLABS); + /* Handle unlimited selections */ + if(unlim_dim >= 0) { + hsize_t bounds_start[H5S_MAX_RANK]; + hsize_t bounds_end[H5S_MAX_RANK]; + hsize_t tmp_count = opt_count[unlim_dim]; + hsize_t tmp_block = opt_block[unlim_dim]; + + /* Check for invalid operation */ + if(space->select.sel_info.hslab->unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot modify unlimited selection with another unlimited selection") + if(!((op == H5S_SELECT_AND) || (op == H5S_SELECT_NOTB))) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "unsupported operation with unlimited selection") + + /* Get bounds of existing selection */ + if(H5S_hyper_bounds(space, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTGET, FAIL, "can't get selection bounds") + + /* Patch count and block to remove unlimited and include the + * existing selection */ + H5S__hyper_get_clip_diminfo(start[unlim_dim], opt_stride[unlim_dim], &tmp_count, &tmp_block, bounds_end[unlim_dim] + (hsize_t)1); + HDassert((tmp_count == 1) || (opt_count != _ones)); + HDassert((tmp_block == 1) || (opt_block != _ones)); + if(opt_count != _ones) { + HDassert(opt_count == int_count); + int_count[unlim_dim] = tmp_count; + } /* end if */ + if(opt_block != _ones) { + HDassert(opt_block == int_block); + int_block[unlim_dim] = tmp_block; + } /* end if */ + } /* end if */ + /* Check if there's no hyperslab span information currently */ if(NULL == space->select.sel_info.hslab->span_lst) if(H5S_hyper_generate_spans(space) < 0) @@ -6878,6 +7169,9 @@ H5S_generate_hyperslab (H5S_t *space, H5S_seloper_t op, /* Allocate space for the hyperslab selection information */ if((space->select.sel_info.hslab=H5FL_MALLOC(H5S_hyper_sel_t))==NULL) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab info") + + /* Set unlim_dim */ + space->select.sel_info.hslab->unlim_dim = -1; } /* end if */ /* Combine tmp_space (really space) & new_space, with the result in space */ @@ -6925,6 +7219,7 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, const hsize_t *opt_count; /* Optimized count information */ const hsize_t *opt_block; /* Optimized block information */ unsigned u; /* Counters */ + int unlim_dim = -1; /* Unlimited dimension in selection, of -1 if none */ herr_t ret_value=SUCCEED; /* Return value */ FUNC_ENTER_NOAPI(FAIL) @@ -6943,6 +7238,18 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, if(block==NULL) block = _ones; + /* Check for unlimited dimension */ + for(u = 0; u<space->extent.rank; u++) + if((count[u] == H5S_UNLIMITED) || (block[u] == H5S_UNLIMITED)) { + if(unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot have more than one unlimited dimension in selection") + else { + if(count[u] == block[u] /* == H5S_UNLIMITED */) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "count and block cannot both be unlimited") + unlim_dim = (int)u; + } /* end else */ + } /* end if */ + /* * Check new selection. */ @@ -6987,7 +7294,7 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, opt_block = int_block; for(u=0; u<space->extent.rank; u++) { /* contiguous hyperslabs have the block size equal to the stride */ - if(stride[u]==block[u]) { + if((stride[u] == block[u]) && (count[u] != H5S_UNLIMITED)) { int_count[u]=1; int_stride[u]=1; if(block[u]==1) @@ -6999,7 +7306,8 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, if(count[u]==1) int_stride[u]=1; else { - HDassert(stride[u] > block[u]); + HDassert((stride[u] > block[u]) || ((stride[u] == block[u]) + && (count[u] == H5S_UNLIMITED))); int_stride[u]=stride[u]; } /* end else */ int_count[u]=count[u]; @@ -7008,6 +7316,32 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, } /* end for */ } /* end else */ + /* Check for operating on unlimited selection */ + if((H5S_GET_SELECT_TYPE(space) == H5S_SEL_HYPERSLABS) + && (space->select.sel_info.hslab->unlim_dim >= 0) + && (op != H5S_SELECT_SET)) + { + /* Check for invalid operation */ + if(unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot modify unlimited selection with another unlimited selection") + if(!((op == H5S_SELECT_AND) || (op == H5S_SELECT_NOTA))) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "unsupported operation on unlimited selection") + HDassert(space->select.sel_info.hslab->diminfo_valid); + + /* Clip unlimited selection to include new selection */ + if(H5S_hyper_clip_unlim(space, + start[space->select.sel_info.hslab->unlim_dim] + + ((opt_count[space->select.sel_info.hslab->unlim_dim] + - (hsize_t)1) + * opt_stride[space->select.sel_info.hslab->unlim_dim]) + + opt_block[space->select.sel_info.hslab->unlim_dim]) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "failed to clip unlimited selection") + + /* If an empty space was returned it must be "none" */ + HDassert((space->select.num_elem > (hsize_t)0) + || (space->select.type->type == H5S_SEL_NONE)); + } /* end if */ + /* Fixup operation for non-hyperslab selections */ switch(H5S_GET_SELECT_TYPE(space)) { case H5S_SEL_NONE: /* No elements selected in dataspace */ @@ -7099,8 +7433,8 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't release hyperslab") /* Allocate space for the hyperslab selection information */ - if((space->select.sel_info.hslab=H5FL_MALLOC(H5S_hyper_sel_t))==NULL) - HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab info") + if(NULL == (space->select.sel_info.hslab = H5FL_MALLOC(H5S_hyper_sel_t))) + HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab info") /* Save the diminfo */ space->select.num_elem=1; @@ -7118,33 +7452,81 @@ H5S_select_hyperslab (H5S_t *space, H5S_seloper_t op, space->select.num_elem*=(opt_count[u]*opt_block[u]); } /* end for */ + /* Save unlim_dim */ + space->select.sel_info.hslab->unlim_dim = unlim_dim; + /* Indicate that the dimension information is valid */ - space->select.sel_info.hslab->diminfo_valid=TRUE; + space->select.sel_info.hslab->diminfo_valid = TRUE; /* Indicate that there's no slab information */ - space->select.sel_info.hslab->span_lst=NULL; + space->select.sel_info.hslab->span_lst = NULL; + + /* Handle unlimited selections */ + if(unlim_dim >= 0) { + /* Calculate num_elem_non_unlim */ + space->select.sel_info.hslab->num_elem_non_unlim = (hsize_t)1; + for(u = 0; u < space->extent.rank; u++) + if((int)u != unlim_dim) + space->select.sel_info.hslab->num_elem_non_unlim *= (opt_count[u] * opt_block[u]); + + /* Set num_elem */ + if(space->select.num_elem != (hsize_t)0) + space->select.num_elem = H5S_UNLIMITED; + } /* end if */ } /* end if */ else if(op>=H5S_SELECT_OR && op<=H5S_SELECT_NOTA) { /* Sanity check */ HDassert(H5S_GET_SELECT_TYPE(space) == H5S_SEL_HYPERSLABS); + /* Handle unlimited selections */ + if(unlim_dim >= 0) { + hsize_t bounds_start[H5S_MAX_RANK]; + hsize_t bounds_end[H5S_MAX_RANK]; + hsize_t tmp_count = opt_count[unlim_dim]; + hsize_t tmp_block = opt_block[unlim_dim]; + + /* Check for invalid operation */ + if(space->select.sel_info.hslab->unlim_dim >= 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "cannot modify unlimited selection with another unlimited selection") + if(!((op == H5S_SELECT_AND) || (op == H5S_SELECT_NOTB))) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "unsupported operation with unlimited selection") + + /* Get bounds of existing selection */ + if(H5S_hyper_bounds(space, bounds_start, bounds_end) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTGET, FAIL, "can't get selection bounds") + + /* Patch count and block to remove unlimited and include the + * existing selection */ + H5S__hyper_get_clip_diminfo(start[unlim_dim], opt_stride[unlim_dim], &tmp_count, &tmp_block, bounds_end[unlim_dim] + (hsize_t)1); + HDassert((tmp_count == 1) || (opt_count != _ones)); + HDassert((tmp_block == 1) || (opt_block != _ones)); + if(opt_count != _ones) { + HDassert(opt_count == int_count); + int_count[unlim_dim] = tmp_count; + } /* end if */ + if(opt_block != _ones) { + HDassert(opt_block == int_block); + int_block[unlim_dim] = tmp_block; + } /* end if */ + } /* end if */ + /* Check if there's no hyperslab span information currently */ - if(space->select.sel_info.hslab->span_lst==NULL) - if(H5S_hyper_generate_spans(space)<0) + if(NULL == space->select.sel_info.hslab->span_lst) + if(H5S_hyper_generate_spans(space) < 0) HGOTO_ERROR(H5E_DATASPACE, H5E_UNINITIALIZED, FAIL, "dataspace does not have span tree") + /* Indicate that the regular dimensions are no longer valid */ + space->select.sel_info.hslab->diminfo_valid = FALSE; + /* Add in the new hyperslab information */ if(H5S_generate_hyperslab (space, op, start, opt_stride, opt_count, opt_block)<0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINSERT, FAIL, "can't generate hyperslabs") - - /* Indicate that the regular dimensions are no longer valid */ - space->select.sel_info.hslab->diminfo_valid=FALSE; } /* end if */ else HGOTO_ERROR(H5E_ARGS, H5E_UNSUPPORTED, FAIL, "invalid selection operation") /* Set selection type */ - space->select.type=H5S_sel_hyper; + space->select.type = H5S_sel_hyper; done: FUNC_LEAVE_NOAPI(ret_value) @@ -7333,6 +7715,9 @@ H5S_combine_select (H5S_t *space1, H5S_seloper_t op, H5S_t *space2) if((new_space->select.sel_info.hslab=H5FL_CALLOC(H5S_hyper_sel_t))==NULL) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "can't allocate hyperslab info") + /* Set unlim_dim */ + new_space->select.sel_info.hslab->unlim_dim = -1; + /* Combine space1 & space2, with the result in new_space */ if(H5S_operate_hyperslab(new_space,space1->select.sel_info.hslab->span_lst,op,space2->select.sel_info.hslab->span_lst,FALSE,&span2_owned)<0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, NULL, "can't clip hyperslab information") @@ -7462,6 +7847,9 @@ H5S_select_select (H5S_t *space1, H5S_seloper_t op, H5S_t *space2) if((space1->select.sel_info.hslab=H5FL_CALLOC(H5S_hyper_sel_t))==NULL) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab info") + /* Set unlim_dim */ + space1->select.sel_info.hslab->unlim_dim = -1; + /* Combine tmp_spans (from space1) & spans from space2, with the result in space1 */ if(H5S_operate_hyperslab(space1,tmp_spans,op,space2->select.sel_info.hslab->span_lst,FALSE,&span2_owned)<0) HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "can't clip hyperslab information") @@ -8734,6 +9122,7 @@ H5S_hyper_get_seq_list(const H5S_t *space, unsigned H5_ATTR_UNUSED flags, H5S_se HDassert(nelem); HDassert(off); HDassert(len); + HDassert(space->select.sel_info.hslab->unlim_dim < 0); /* Check for the special case of just one H5Sselect_hyperslab call made */ if(space->select.sel_info.hslab->diminfo_valid) { @@ -8794,7 +9183,7 @@ H5S_hyper_get_seq_list(const H5S_t *space, unsigned H5_ATTR_UNUSED flags, H5S_se /* Make certain that we don't write too many */ actual_elem = MIN3(leftover, (size_t)iter->elmt_left, maxelem); - /* initialize row sizes for each dimension */ + /* Initialize row sizes for each dimension */ elem_size = iter->elmt_size; for(i = (int)fast_dim, acc = elem_size; i >= 0; i--) { slab[i] = acc; @@ -8863,6 +9252,1086 @@ H5S_hyper_get_seq_list(const H5S_t *space, unsigned H5_ATTR_UNUSED flags, H5S_se /*-------------------------------------------------------------------------- NAME + H5S__hyper_project_intersection + PURPOSE + Projects the intersection of of the selections of src_space and + src_intersect_space within the selection of src_space as a selection + within the selection of dst_space + USAGE + herr_t H5S__hyper_project_intersection(src_space,dst_space,src_intersect_space,proj_space) + H5S_t *src_space; IN: Selection that is mapped to dst_space, and intersected with src_intersect_space + H5S_t *dst_space; IN: Selection that is mapped to src_space, and which contains the result + H5S_t *src_intersect_space; IN: Selection whose intersection with src_space is projected to dst_space to obtain the result + H5S_t *proj_space; OUT: Will contain the result (intersection of src_intersect_space and src_space projected from src_space to dst_space) after the operation + RETURNS + Non-negative on success/Negative on failure. + DESCRIPTION + Projects the intersection of of the selections of src_space and + src_intersect_space within the selection of src_space as a selection + within the selection of dst_space. The result is placed in the + selection of proj_space. Note src_space, dst_space, and + src_intersect_space do not need to use hyperslab selections, but they + cannot use point selections. The result is always a hyperslab + selection. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S__hyper_project_intersection(const H5S_t *src_space, const H5S_t *dst_space, + const H5S_t *src_intersect_space, H5S_t *proj_space) +{ + hsize_t ss_off[H5S_PROJECT_INTERSECT_NSEQS]; /* Offset array for src_space */ + size_t ss_len[H5S_PROJECT_INTERSECT_NSEQS]; /* Length array for src_space */ + size_t ss_nseq; /* Number of sequences for src_space */ + size_t ss_nelem; /* Number of elements for src_space */ + size_t ss_i = (size_t)0; /* Index into offset/length arrays for src_space */ + hbool_t advance_ss = FALSE; /* Whether to advance ss_i on the next iteration */ + H5S_sel_iter_t ss_iter; /* Selection iterator for src_space */ + hbool_t ss_iter_init = FALSE; /* Whether ss_iter is initialized */ + hsize_t ss_sel_off = (hsize_t)0; /* Offset within src_space selection */ + hsize_t ds_off[H5S_PROJECT_INTERSECT_NSEQS]; /* Offset array for dst_space */ + size_t ds_len[H5S_PROJECT_INTERSECT_NSEQS]; /* Length array for dst_space */ + size_t ds_nseq; /* Number of sequences for dst_space */ + size_t ds_nelem; /* Number of elements for dst_space */ + size_t ds_i = (size_t)0; /* Index into offset/length arrays for dst_space */ + H5S_sel_iter_t ds_iter; /* Selection iterator for dst_space */ + hbool_t ds_iter_init = FALSE; /* Whether ds_iter is initialized */ + hsize_t ds_sel_off = (hsize_t)0; /* Offset within dst_space selection */ + hsize_t sis_off[H5S_PROJECT_INTERSECT_NSEQS]; /* Offset array for src_intersect_space */ + size_t sis_len[H5S_PROJECT_INTERSECT_NSEQS]; /* Length array for src_intersect_space */ + size_t sis_nseq; /* Number of sequences for src_intersect_space */ + size_t sis_nelem; /* Number of elements for src_intersect_space */ + size_t sis_i = (size_t)0; /* Index into offset/length arrays for src_intersect_space */ + hbool_t advance_sis = FALSE; /* Whether to advance sis_i on the next iteration */ + H5S_sel_iter_t sis_iter; /* Selection iterator for src_intersect_space */ + hbool_t sis_iter_init = FALSE; /* Whether sis_iter is initialized */ + hsize_t int_sel_off; /* Offset within intersected selections (ss/sis and ds/ps) */ + size_t int_len; /* Length of segment in intersected selections */ + hsize_t proj_off; /* Segment offset in proj_space */ + size_t proj_len; /* Segment length in proj_space */ + size_t proj_len_rem; /* Remaining length in proj_space for segment */ + hsize_t proj_down_dims[H5S_MAX_RANK]; /* "Down" dimensions in proj_space */ + H5S_hyper_span_info_t *curr_span_tree[H5S_MAX_RANK]; /* Current span tree being built (in each dimension) */ + H5S_hyper_span_t *prev_span[H5S_MAX_RANK]; /* Previous span in tree (in each dimension) */ + hsize_t curr_span_up_dim[H5S_MAX_RANK]; /* "Up" dimensions for current span */ + unsigned proj_rank; /* Rank of proj_space */ + hsize_t low; /* Low value of span */ + hsize_t high; /* High value of span */ + size_t span_len; /* Length of span */ + size_t nelem; /* Number of elements returned for get_seq_list op */ + unsigned i; /* Local index variable */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* Check parameters */ + HDassert(src_space); + HDassert(dst_space); + HDassert(src_intersect_space); + HDassert(proj_space); + + /* Assert that src_space and src_intersect_space have same extent and there + * are no point selections */ + HDassert(H5S_GET_EXTENT_NDIMS(src_space) + == H5S_GET_EXTENT_NDIMS(src_intersect_space)); + HDassert(!HDmemcmp(src_space->extent.size, src_intersect_space->extent.size, + (size_t)H5S_GET_EXTENT_NDIMS(src_space) + * sizeof(src_space->extent.size[0]))); + HDassert(H5S_GET_SELECT_TYPE(src_space) != H5S_SEL_POINTS); + HDassert(H5S_GET_SELECT_TYPE(dst_space) != H5S_SEL_POINTS); + HDassert(H5S_GET_SELECT_TYPE(src_intersect_space) != H5S_SEL_POINTS); + + /* Initialize prev_space, curr_span_tree, and curr_span_up_dim */ + for(i = 0; i < H5S_MAX_RANK; i++) { + curr_span_tree[i] = NULL; + prev_span[i] = NULL; + curr_span_up_dim[i] = (hsize_t)0; + } /* end for */ + + /* Save rank of projected space */ + proj_rank = proj_space->extent.rank; + HDassert(proj_rank > 0); + + /* Get numbers of elements */ + ss_nelem = (size_t)H5S_GET_SELECT_NPOINTS(src_space); + ds_nelem = (size_t)H5S_GET_SELECT_NPOINTS(dst_space); + sis_nelem = (size_t)H5S_GET_SELECT_NPOINTS(src_intersect_space); + HDassert(ss_nelem == ds_nelem); + + /* Calculate proj_down_dims (note loop relies on unsigned i wrapping around) + */ + if(H5VM_array_down(proj_rank, proj_space->extent.size, proj_down_dims) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTSET, FAIL, "can't compute 'down' chunk size value") + + /* Remove current selection from proj_space */ + if(H5S_SELECT_RELEASE(proj_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't release selection") + + /* If any selections are empty, skip to the end so "none" is selected */ + if((ss_nelem == 0) || (ds_nelem == 0) || (sis_nelem == 0)) + goto loop_end; + + /* Allocate space for the hyperslab selection information (note this sets + * diminfo_valid to FALSE, diminfo arrays to 0, and span list to NULL) */ + if((proj_space->select.sel_info.hslab = H5FL_CALLOC(H5S_hyper_sel_t)) == NULL) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "can't allocate hyperslab info") + + /* Set selection type */ + proj_space->select.type = H5S_sel_hyper; + + /* Set unlim_dim */ + proj_space->select.sel_info.hslab->unlim_dim = -1; + + /* Initialize source space iterator */ + if(H5S_select_iter_init(&ss_iter, src_space, (size_t)1) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator") + ss_iter_init = TRUE; + + /* Get sequence list for source space */ + if(H5S_SELECT_GET_SEQ_LIST(src_space, 0u, &ss_iter, H5S_PROJECT_INTERSECT_NSEQS, ss_nelem, &ss_nseq, &nelem, ss_off, ss_len) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed") + ss_nelem -= nelem; + HDassert(ss_nseq > 0); + + /* Initialize destination space iterator */ + if(H5S_select_iter_init(&ds_iter, dst_space, (size_t)1) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator") + ds_iter_init = TRUE; + + /* Get sequence list for destination space */ + if(H5S_SELECT_GET_SEQ_LIST(dst_space, 0u, &ds_iter, H5S_PROJECT_INTERSECT_NSEQS, ds_nelem, &ds_nseq, &nelem, ds_off, ds_len) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator") + ds_nelem -= nelem; + HDassert(ds_nseq > 0); + + /* Initialize source intersect space iterator */ + if(H5S_select_iter_init(&sis_iter, src_intersect_space, (size_t)1) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator") + sis_iter_init = TRUE; + + /* Get sequence list for source intersect space */ + if(H5S_SELECT_GET_SEQ_LIST(src_intersect_space, 0u, &sis_iter, H5S_PROJECT_INTERSECT_NSEQS, sis_nelem, &sis_nseq, &nelem, sis_off, sis_len) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed") + sis_nelem -= nelem; + HDassert(sis_nseq > 0); + + /* Loop until we run out of sequences in either the source or source + * intersect space */ + while(1) { + while(advance_ss || (ss_off[ss_i] + ss_len[ss_i] <= sis_off[sis_i])) { + /* Either we finished the current source sequence or the + * sequences do not intersect. Advance source space. */ + ss_sel_off += (hsize_t)ss_len[ss_i]; + if(++ss_i == ss_nseq) { + if(ss_nelem > 0) { + /* Try to grab more sequences from src_space */ + if(H5S_SELECT_GET_SEQ_LIST(src_space, 0u, &ss_iter, H5S_PROJECT_INTERSECT_NSEQS, ss_nelem, &ss_nseq, &nelem, ss_off, ss_len) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed") + HDassert(ss_len[0] > 0); + + /* Update ss_nelem */ + HDassert(nelem > 0); + HDassert(nelem <= ss_nelem); + ss_nelem -= nelem; + + /* Reset source space index */ + ss_i = 0; + } /* end if */ + else + /* There are no more sequences in src_space, so we can exit + * the loop. Use goto instead of break so we exit the outer + * loop. */ + goto loop_end; + } /* end if */ + + /* Reset advance_ss */ + advance_ss = FALSE; + } /* end if */ + if(advance_sis + || (sis_off[sis_i] + sis_len[sis_i] <= ss_off[ss_i])) { + do { + /* Either we finished the current source intersect sequence or + * the sequences do not intersect. Advance source intersect + * space. */ + if(++sis_i == sis_nseq) { + if(sis_nelem > 0) { + /* Try to grab more sequences from src_intersect_space + */ + if(H5S_SELECT_GET_SEQ_LIST(src_intersect_space, 0u, &sis_iter, H5S_PROJECT_INTERSECT_NSEQS, sis_nelem, &sis_nseq, &nelem, sis_off, sis_len) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed") + HDassert(sis_len[0] > 0); + + /* Update ss_nelem */ + HDassert(nelem > 0); + HDassert(nelem <= sis_nelem); + sis_nelem -= nelem; + + /* Reset source space index */ + sis_i = 0; + } /* end if */ + else + /* There are no more sequences in src_intersect_space, + * so we can exit the loop. Use goto instead of break + * so we exit the outer loop. */ + goto loop_end; + } /* end if */ + } while(sis_off[sis_i] + sis_len[sis_i] <= ss_off[ss_i]); + + /* Reset advance_sis */ + advance_sis = FALSE; + } /* end if */ + else { + /* Sequences intersect, add intersection to projected space */ + /* Calculate intersection sequence in terms of offset within source + * selection and advance any sequences we complete */ + if(ss_off[ss_i] >= sis_off[sis_i]) + int_sel_off = ss_sel_off; + else + int_sel_off = sis_off[sis_i] - ss_off[ss_i] + ss_sel_off; + if((ss_off[ss_i] + (hsize_t)ss_len[ss_i]) <= (sis_off[sis_i] + + (hsize_t)sis_len[sis_i])) { + int_len = (size_t)((hsize_t)ss_len[ss_i] + ss_sel_off - int_sel_off); + advance_ss = TRUE; + } /* end if */ + else + int_len = (size_t)(sis_off[sis_i] + (hsize_t)sis_len[sis_i] - ss_off[ss_i] + ss_sel_off - int_sel_off); + if((ss_off[ss_i] + (hsize_t)ss_len[ss_i]) >= (sis_off[sis_i] + + (hsize_t)sis_len[sis_i])) + advance_sis = TRUE; + + /* Project intersection sequence to destination selection */ + while(int_len > (size_t)0) { + while(ds_sel_off + (hsize_t)ds_len[ds_i] <= int_sel_off) { + /* Intersection is not projected to this destination + * sequence, advance destination space */ + ds_sel_off += (hsize_t)ds_len[ds_i]; + if(++ds_i == ds_nseq) { + HDassert(ds_nelem > 0); + + /* Try to grab more sequences from dst_space */ + if(H5S_SELECT_GET_SEQ_LIST(dst_space, 0u, &ds_iter, H5S_PROJECT_INTERSECT_NSEQS, ds_nelem, &ds_nseq, &nelem, ds_off, ds_len) < 0) + HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed") + HDassert(ds_len[0] > 0); + + /* Update ss_nelem */ + HDassert(nelem > 0); + HDassert(nelem <= ds_nelem); + ds_nelem -= nelem; + + /* Reset source space index */ + ds_i = 0; + } /* end if */ + } /* end while */ + + /* Add sequence to projected space */ + HDassert(ds_sel_off <= int_sel_off); + proj_off = ds_off[ds_i] + int_sel_off - ds_sel_off; + proj_len = proj_len_rem = (size_t)MIN(int_len, + (size_t)(ds_sel_off + (hsize_t)ds_len[ds_i] + - int_sel_off)); + + /* Add to span tree */ + while(proj_len_rem > (size_t)0) { + /* Check for more than one full row (in every dim) and + * append multiple spans at once? -NAF */ + /* Append spans in higher dimensions if we're going ouside + * the plane of the span currently being built (i.e. it's + * finished being built) */ + for(i = proj_rank - 1; ((i > 0) + && ((proj_off / proj_down_dims[i - 1]) + != curr_span_up_dim[i - 1])); i--) { + if(curr_span_tree[i]) { + HDassert(prev_span[i]); + + /* Append complete lower dimension span tree to + * current dimension */ + low = curr_span_up_dim[i - 1] % proj_space->extent.size[i - 1]; + if(H5S_hyper_append_span(&prev_span[i - 1], &curr_span_tree[i - 1], low, low, curr_span_tree[i], NULL) < 0) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") + + /* Reset lower dimension's span tree and previous + * span since we just committed it and will start + * over with a new one */ + if(H5S_hyper_free_span_info(curr_span_tree[i]) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTFREE, FAIL, "can't free span info") + curr_span_tree[i] = NULL; + prev_span[i] = NULL; + } /* end if */ + + /* Update curr_span_up_dim */ + curr_span_up_dim[i - 1] = proj_off / proj_down_dims[i - 1]; + } /* end for */ + + /* Compute bounds for new span in lowest dimension */ + low = proj_off % proj_space->extent.size[proj_rank - 1]; + span_len = MIN(proj_len_rem, + (size_t)(proj_space->extent.size[proj_rank - 1] + - low)); + HDassert(proj_len_rem >= span_len); + high = low + (hsize_t)span_len - (hsize_t)1; + + /* Append span in lowest dimension */ + if(H5S_hyper_append_span(&prev_span[proj_rank - 1], &curr_span_tree[proj_rank - 1], low, high, NULL, NULL) < 0) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") + + /* Update remaining offset and length */ + proj_off += (hsize_t)span_len; + proj_len_rem -= span_len; + } /* end while */ + + /* Update intersection sequence */ + int_sel_off += (hsize_t)proj_len; + int_len -= proj_len; + } /* end while */ + } /* end else */ + } /* end while */ + +loop_end: + /* Add remaining spans to span tree */ + for(i = proj_rank - 1; i > 0; i--) + if(curr_span_tree[i]) { + HDassert(prev_span[i]); + + /* Append remaining span tree to higher dimension */ + low = curr_span_up_dim[i - 1] % proj_space->extent.size[i - 1]; + if(H5S_hyper_append_span(&prev_span[i - 1], &curr_span_tree[i - 1], low, low, curr_span_tree[i], NULL) < 0) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTAPPEND, FAIL, "can't allocate hyperslab span") + + /* Reset span tree */ + if(H5S_hyper_free_span_info(curr_span_tree[i]) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTFREE, FAIL, "can't free span info") + curr_span_tree[i] = NULL; + } /* end if */ + + /* Add span tree to proj_space */ + if(curr_span_tree[0]) { + proj_space->select.sel_info.hslab->span_lst = curr_span_tree[0]; + curr_span_tree[0] = NULL; + + /* Set the number of elements in current selection */ + proj_space->select.num_elem = H5S_hyper_spans_nelem(proj_space->select.sel_info.hslab->span_lst); + + /* Attempt to rebuild "optimized" start/stride/count/block information. + * from resulting hyperslab span tree */ + if(H5S_hyper_rebuild(proj_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOUNT, FAIL, "can't rebuild hyperslab info") + } /* end if */ + else + /* If we did not add anything to proj_space, select none instead */ + if(H5S_select_none(proj_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't convert selection") + +done: + /* Release source selection iterator */ + if(ss_iter_init) + if(H5S_SELECT_ITER_RELEASE(&ss_iter) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator") + + /* Release destination selection iterator */ + if(ds_iter_init) + if(H5S_SELECT_ITER_RELEASE(&ds_iter) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator") + + /* Release source intersect selection iterator */ + if(sis_iter_init) + if(H5S_SELECT_ITER_RELEASE(&sis_iter) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator") + + /* Cleanup on error */ + if(ret_value < 0) { + /* Remove current selection from proj_space */ + if(H5S_SELECT_RELEASE(proj_space) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't release selection") + + /* Free span trees */ + for(i = 0; i < proj_rank; i++) + if(curr_span_tree[i]) { + if(H5S_hyper_free_span_info(curr_span_tree[i]) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTFREE, FAIL, "can't free span info") + curr_span_tree[i] = NULL; + } /* end if */ + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S__hyper_project_intersection() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S__hyper_subtract + PURPOSE + Subtract one hyperslab selection from another + USAGE + herr_t H5S__hyper_subtract(space,subtract_space) + H5S_t *space; IN/OUT: Selection to be operated on + H5S_t *subtract_space; IN: Selection that will be subtracted from space + RETURNS + Non-negative on success/Negative on failure. + DESCRIPTION + Removes any and all portions of space that are also present in + subtract_space. In essence, performs an A_NOT_B operation with the + two selections. + + Note this function basically duplicates a subset of the functionality + of H5S_select_select(). It should probably be removed when that + function is enabled. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S__hyper_subtract(H5S_t *space, H5S_t *subtract_space) +{ + H5S_hyper_span_info_t *a_not_b = NULL; /* Span tree for hyperslab spans in old span tree and not in new span tree */ + H5S_hyper_span_info_t *a_and_b = NULL; /* Span tree for hyperslab spans in both old and new span trees */ + H5S_hyper_span_info_t *b_not_a = NULL; /* Span tree for hyperslab spans in new span tree and not in old span tree */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI_NOINIT + + /* Check args */ + HDassert(space); + HDassert(subtract_space); + + /* Check that the space selections both have span trees */ + if(space->select.sel_info.hslab->span_lst == NULL) + if(H5S_hyper_generate_spans(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNINITIALIZED, FAIL, "dataspace does not have span tree") + if(subtract_space->select.sel_info.hslab->span_lst == NULL) + if(H5S_hyper_generate_spans(subtract_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNINITIALIZED, FAIL, "dataspace does not have span tree") + + /* Generate lists of spans which overlap and don't overlap */ + if(H5S_hyper_clip_spans(space->select.sel_info.hslab->span_lst, subtract_space->select.sel_info.hslab->span_lst, &a_not_b, &a_and_b, &b_not_a)<0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "can't clip hyperslab information") + + /* Reset the other dataspace selection information */ + if(H5S_SELECT_RELEASE(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't release selection") + + /* Allocate space for the hyperslab selection information */ + if((space->select.sel_info.hslab = H5FL_CALLOC(H5S_hyper_sel_t)) == NULL) + HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate hyperslab info") + + /* Set unlim_dim */ + space->select.sel_info.hslab->unlim_dim = -1; + + /* Check for anything returned in a_not_b */ + if(a_not_b) { + /* Update spans in space */ + space->select.sel_info.hslab->span_lst = a_not_b; + a_not_b = NULL; + + /* Update number of elements */ + space->select.num_elem = H5S_hyper_spans_nelem(space->select.sel_info.hslab->span_lst); + + /* Attempt to rebuild "optimized" start/stride/count/block information. + * from resulting hyperslab span tree */ + if(H5S_hyper_rebuild(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOUNT, FAIL, "can't rebuild hyperslab info") + } /* end if */ + else { + H5S_hyper_span_info_t *spans; /* Empty hyperslab span tree */ + + /* Set number of elements */ + space->select.num_elem = 0; + + /* Allocate a span info node */ + if(NULL == (spans = H5FL_MALLOC(H5S_hyper_span_info_t))) + HGOTO_ERROR(H5E_RESOURCE, H5E_CANTALLOC, FAIL, "can't allocate hyperslab span") + + /* Set the reference count */ + spans->count = 1; + + /* Reset the scratch pad space */ + spans->scratch = 0; + + /* Set to empty tree */ + spans->head = NULL; + + /* Set pointer to empty span tree */ + space->select.sel_info.hslab->span_lst = spans; + } /* end if */ + +done: + /* Free span trees */ + if(a_and_b) + H5S_hyper_free_span_info(a_and_b); + if(b_not_a) + H5S_hyper_free_span_info(b_not_a); + if(a_not_b) { + HDassert(ret_value < 0); + H5S_hyper_free_span_info(b_not_a); + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S__hyper_subtract() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S__hyper_get_clip_diminfo + PURPOSE + Calculates the count and block required to clip the specified + unlimited dimension to include clip_size. The returned selection may + extent beyond clip_size. + USAGE + void H5S__hyper_get_clip_diminfo(start,stride,count,block,clip_size) + hsize_t start; IN: Start of hyperslab in unlimited dimension + hsize_t stride; IN: Stride of hyperslab in unlimited dimension + hsize_t *count; IN/OUT: Count of hyperslab in unlimited dimension + hsize_t *block; IN/OUT: Block of hyperslab in unlimited dimension + hsize_t clip_size; IN: Extent that hyperslab will be clipped to + RETURNS + Non-negative on success/Negative on failure. + DESCRIPTION + This function recalculates the internal description of the hyperslab + to make the unlimited dimension extend to the specified extent. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +void +H5S__hyper_get_clip_diminfo(hsize_t start, hsize_t stride, hsize_t *count, + hsize_t *block, hsize_t clip_size) +{ + FUNC_ENTER_PACKAGE_NOERR + + /* Check for selection outside clip size */ + if(start >= clip_size) { + if(*block == H5S_UNLIMITED) + *block = 0; + else + *count = 0; + } /* end if */ + /* Check for single block in unlimited dimension */ + else if((*block == H5S_UNLIMITED) || (*block == stride)) { + /* Calculate actual block size for this clip size */ + *block = clip_size - start; + *count = (hsize_t)1; + } /* end if */ + else { + HDassert(*count == H5S_UNLIMITED); + + /* Calculate initial count (last block may be partial) */ + *count = (clip_size - start + stride - (hsize_t)1) / stride; + HDassert(*count > (hsize_t)0); + } /* end else */ + + FUNC_LEAVE_NOAPI_VOID +} /* end H5S_hyper_get_clip_diminfo() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_clip_unlim + PURPOSE + Clips the unlimited dimension of the hyperslab selection to the + specified size + USAGE + void H5S_hyper_clip_unlim(space,clip_size) + H5S_t *space, IN/OUT: Unlimited space to clip + hsize_t clip_size; IN: Extent that hyperslab will be clipped to + RETURNS + Non-negative on success/Negative on failure. + DESCRIPTION + This function changes the unlimited selection into a limited selection + with the extent of the formerly unlimited dimension specified by + * clip_size. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this function does not take the offset into account. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S_hyper_clip_unlim(H5S_t *space, hsize_t clip_size) +{ + H5S_hyper_sel_t *hslab; /* Convenience pointer to hyperslab info */ + hsize_t orig_count; /* Original count in unlimited dimension */ + int orig_unlim_dim; /* Original unliminted dimension */ + H5S_hyper_dim_t *diminfo; /* Convenience pointer to opt_diminfo in unlimited dimension */ + herr_t ret_value = SUCCEED; + + FUNC_ENTER_NOAPI(FAIL) + + /* Check parameters */ + HDassert(space); + hslab = space->select.sel_info.hslab; + HDassert(hslab); + HDassert(hslab->unlim_dim >= 0); + HDassert(!hslab->span_lst); + + /* Save original unlimited dimension */ + orig_unlim_dim = hslab->unlim_dim; + + diminfo = &hslab->opt_diminfo[orig_unlim_dim]; + + /* Save original count in unlimited dimension */ + orig_count = diminfo->count; + + /* Get initial diminfo */ + H5S__hyper_get_clip_diminfo(diminfo->start, diminfo->stride, &diminfo->count, &diminfo->block, clip_size); + + /* Selection is no longer unlimited */ + space->select.sel_info.hslab->unlim_dim = -1; + + /* Check for nothing returned */ + if((diminfo->block == 0) || (diminfo->count == 0)) { + /* Convert to "none" selection */ + if(H5S_select_none(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't convert selection") + } /* end if */ + /* Check for single block in unlimited dimension */ + else if(orig_count == (hsize_t)1) { + /* Calculate number of elements */ + space->select.num_elem = diminfo->block * hslab->num_elem_non_unlim; + + /* Mark that opt_diminfo is valid */ + hslab->diminfo_valid = TRUE; + } /* end if */ + else { + /* Calculate number of elements */ + space->select.num_elem = diminfo->count * diminfo->block + * hslab->num_elem_non_unlim; + + /* Check if last block is partial. If superset is set, just keep the + * last block complete to speed computation. */ + HDassert(clip_size > diminfo->start); + if(((diminfo->stride * (diminfo->count - (hsize_t)1)) + diminfo->block) + > (clip_size - diminfo->start)) { + hsize_t start[H5S_MAX_RANK]; + hsize_t block[H5S_MAX_RANK]; + unsigned i; + + /* Last block is partial, need to construct compound selection */ + /* Fill start with zeros */ + HDmemset(start, 0, sizeof(start)); + + /* Set block to clip_size in unlimited dimension, H5S_MAX_SIZE in + * others so only unlimited dimension is clipped */ + for(i = 0; i < space->extent.rank; i++) + if((int)i == orig_unlim_dim) + block[i] = clip_size; + else + block[i] = H5S_MAX_SIZE; + + /* Generate span tree in selection */ + if(!hslab->span_lst) + if(H5S_hyper_generate_spans(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to generate span tree") + + /* Indicate that the regular dimensions are no longer valid */ + hslab->diminfo_valid = FALSE; + + /* "And" selection with calculated block to perform clip operation + */ + if(H5S_generate_hyperslab(space, H5S_SELECT_AND, start, _ones, _ones, block) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINSERT, FAIL, "can't generate hyperslabs") + } /* end if */ + else + /* Last block is complete, simply mark that opt_diminfo is valid */ + hslab->diminfo_valid = TRUE; + } /* end else */ + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_clip_unlim() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S__hyper_get_clip_extent_real + PURPOSE + Gets the extent a space should be clipped to in order to contain the + specified number of slices in the unlimited dimension + USAGE + hsize_t H5S__hyper_get_clip_extent_real(clip_space,num_slices,incl_trail) + const H5S_t *clip_space, IN: Space that clip size will be calculated based on + hsize_t num_slizes, IN: Number of slices clip_space should contain when clipped + hbool_t incl_trail; IN: Whether to include trailing unselected space + RETURNS + Clip extent to match num_slices (never fails) + DESCRIPTION + Calculates and returns the extent that clip_space should be clipped to + (via H5S_hyper_clip_unlim) in order for it to contain num_slices + slices in the unlimited dimension. If the clipped selection would end + immediately before a section of unselected space (i.e. at the end of a + block), then if incl_trail is TRUE, the returned clip extent is + selected to include that trailing "blank" space, otherwise it is + selected to end at the end before the blank space. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this assumes the offset has been normalized. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static hsize_t +H5S__hyper_get_clip_extent_real(const H5S_t *clip_space, hsize_t num_slices, + hbool_t incl_trail) +{ + const H5S_hyper_dim_t *diminfo; /* Convenience pointer to opt_unlim_diminfo in unlimited dimension */ + hsize_t count; + hsize_t rem_slices; + hsize_t ret_value; /* Return value */ + + FUNC_ENTER_STATIC_NOERR + + /* Check parameters */ + HDassert(clip_space); + HDassert(clip_space->select.sel_info.hslab); + HDassert(clip_space->select.sel_info.hslab->unlim_dim >= 0); + + diminfo = &clip_space->select.sel_info.hslab->opt_diminfo[clip_space->select.sel_info.hslab->unlim_dim]; + + if(num_slices == 0) + ret_value = incl_trail ? diminfo->start : 0; + else if((diminfo->block == H5S_UNLIMITED) + || (diminfo->block == diminfo->stride)) + /* Unlimited block, just set the extent large enough for the block size + * to match num_slices */ + ret_value = diminfo->start + num_slices; + else { + /* Unlimited count, need to match extent so a block (possibly) gets cut + * off so the number of slices matches num_slices */ + HDassert(diminfo->count == H5S_UNLIMITED); + + /* Calculate number of complete blocks in clip_space */ + count = num_slices / diminfo->block; + + /* Calculate slices remaining */ + rem_slices = num_slices - (count * diminfo->block); + + if(rem_slices > 0) + /* Must end extent in middle of partial block (or beginning of empty + * block if include_trailing_space and rem_slices == 0) */ + ret_value = diminfo->start + (count * diminfo->stride) + rem_slices; + else { + if(incl_trail) + /* End extent just before first missing block */ + ret_value = diminfo->start + (count * diminfo->stride); + else + /* End extent at end of last block */ + ret_value = diminfo->start + ((count - (hsize_t)1) + * diminfo->stride) + diminfo->block; + } /* end else */ + } /* end else */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S__hyper_get_clip_extent_real() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_get_clip_extent + PURPOSE + Gets the extent a space should be clipped to in order to contain the + same number of elements as another space + USAGE + hsize_t H5S__hyper_get_clip_extent(clip_space,match_space,incl_trail) + const H5S_t *clip_space, IN: Space that clip size will be calculated based on + const H5S_t *match_space, IN: Space containing the same number of elements as clip_space should after clipping + hbool_t incl_trail; IN: Whether to include trailing unselected space + RETURNS + Calculated clip extent (never fails) + DESCRIPTION + Calculates and returns the extent that clip_space should be clipped to + (via H5S_hyper_clip_unlim) in order for it to contain the same number + of elements as match_space. If the clipped selection would end + immediately before a section of unselected space (i.e. at the end of a + block), then if incl_trail is TRUE, the returned clip extent is + selected to include that trailing "blank" space, otherwise it is + selected to end at the end before the blank space. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this assumes the offset has been normalized. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +hsize_t +H5S_hyper_get_clip_extent(const H5S_t *clip_space, const H5S_t *match_space, + hbool_t incl_trail) +{ + hsize_t num_slices; /* Number of slices in unlimited dimension */ + hsize_t ret_value; /* Return value */ + + FUNC_ENTER_NOAPI_NOERR + + /* Check parameters */ + HDassert(clip_space); + HDassert(match_space); + HDassert(clip_space->select.sel_info.hslab->unlim_dim >= 0); + + /* Check for "none" match space */ + if(match_space->select.type->type == H5S_SEL_NONE) + num_slices = (hsize_t)0; + else { + HDassert(match_space->select.type->type == H5S_SEL_HYPERSLABS); + HDassert(match_space->select.sel_info.hslab); + + /* Calculate number of slices */ + num_slices = match_space->select.num_elem + / clip_space->select.sel_info.hslab->num_elem_non_unlim; + HDassert((match_space->select.num_elem + % clip_space->select.sel_info.hslab->num_elem_non_unlim) == 0); + } /* end else */ + + /* Call "real" get_clip_extent function */ + ret_value = H5S__hyper_get_clip_extent_real(clip_space, num_slices, incl_trail); + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_get_clip_extent() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_get_clip_extent_match + PURPOSE + Gets the extent a space should be clipped to in order to contain the + same number of elements as another unlimited space that has been + clipped to a different extent + USAGE + hsize_t H5S__hyper_get_clip_extent_match(clip_space,match_space,match_clip_size,incl_trail) + const H5S_t *clip_space, IN: Space that clip size will be calculated based on + const H5S_t *match_space, IN: Space that, after being clipped to match_clip_size, contains the same number of elements as clip_space should after clipping + hsize_t match_clip_size, IN: Extent match_space would be clipped to to match the number of elements in clip_space + hbool_t incl_trail; IN: Whether to include trailing unselected space + RETURNS + Calculated clip extent (never fails) + DESCRIPTION + Calculates and returns the extent that clip_space should be clipped to + (via H5S_hyper_clip_unlim) in order for it to contain the same number + of elements as match_space would have after being clipped to + match_clip_size. If the clipped selection would end immediately + before a section of unselected space (i.e. at the end of a block), + then if incl_trail is TRUE, the returned clip extent is selected to + include that trailing "blank" space, otherwise it is selected to end + at the end before the blank space. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this assumes the offset has been normalized. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +hsize_t +H5S_hyper_get_clip_extent_match(const H5S_t *clip_space, + const H5S_t *match_space, hsize_t match_clip_size, hbool_t incl_trail) +{ + const H5S_hyper_dim_t *match_diminfo; /* Convenience pointer to opt_unlim_diminfo in unlimited dimension in match_space */ + hsize_t count; /* Temporary count */ + hsize_t block; /* Temporary block */ + hsize_t num_slices; /* Number of slices in unlimited dimension */ + hsize_t ret_value; /* Return value */ + + FUNC_ENTER_NOAPI_NOERR + + /* Check parameters */ + HDassert(clip_space); + HDassert(match_space); + HDassert(clip_space->select.sel_info.hslab); + HDassert(match_space->select.sel_info.hslab); + HDassert(clip_space->select.sel_info.hslab->unlim_dim >= 0); + HDassert(match_space->select.sel_info.hslab->unlim_dim >= 0); + HDassert(clip_space->select.sel_info.hslab->num_elem_non_unlim + == match_space->select.sel_info.hslab->num_elem_non_unlim); + + match_diminfo = &match_space->select.sel_info.hslab->opt_diminfo[match_space->select.sel_info.hslab->unlim_dim]; + + /* Get initial count and block */ + count = match_diminfo->count; + block = match_diminfo->block; + H5S__hyper_get_clip_diminfo(match_diminfo->start, match_diminfo->stride, &count, &block, match_clip_size); + + /* Calculate number of slices */ + /* Check for nothing returned */ + if((block == 0) || (count == 0)) + num_slices = (hsize_t)0; + /* Check for single block in unlimited dimension */ + else if(count == (hsize_t)1) + num_slices = block; + else { + /* Calculate initial num_slices */ + num_slices = block * count; + + /* Check for partial last block */ + HDassert(match_clip_size >= match_diminfo->start); + if(((match_diminfo->stride * (count - (hsize_t)1)) + block) + > (match_clip_size - match_diminfo->start)) { + /* Subtract slices missing from last block */ + HDassert((((match_diminfo->stride * (count - (hsize_t)1)) + block) + - (match_clip_size - match_diminfo->start)) < num_slices); + num_slices -= ((match_diminfo->stride * (count - (hsize_t)1)) + + block) - (match_clip_size - match_diminfo->start); + } /* end if */ + } /* end else */ + + /* Call "real" get_clip_extent function */ + ret_value = H5S__hyper_get_clip_extent_real(clip_space, num_slices, incl_trail); + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_get_clip_extent_match() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_get_unlim_block + PURPOSE + Get the nth block in the unlimited dimension + USAGE + H5S_t *H5S_hyper_get_unlim_block(space,block_index) + const H5S_t *space, IN: Space with unlimited selection + hsize_t block_index, IN: Index of block to return in unlimited dimension + hbool_t incl_trail; IN: Whether to include trailing unselected space + RETURNS + New space on success/NULL on failure. + DESCRIPTION + Returns a space containing only the block_indexth block in the + unlimited dimension on space. All blocks in all other dimensions are + preserved. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this assumes the offset has been normalized. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +H5S_t * +H5S_hyper_get_unlim_block(const H5S_t *space, hsize_t block_index) +{ + H5S_hyper_sel_t *hslab; /* Convenience pointer to hyperslab info */ + H5S_t *space_out = NULL; + hsize_t start[H5S_MAX_RANK]; + hsize_t stride[H5S_MAX_RANK]; + hsize_t count[H5S_MAX_RANK]; + hsize_t block[H5S_MAX_RANK]; + unsigned i; + H5S_t *ret_value = NULL; + + FUNC_ENTER_NOAPI(NULL) + + /* Check parameters */ + HDassert(space); + hslab = space->select.sel_info.hslab; + HDassert(hslab); + HDassert(hslab->unlim_dim >= 0); + HDassert(hslab->opt_diminfo[hslab->unlim_dim].count == H5S_UNLIMITED); + + /* Set start to select block_indexth block in unlimited dimension and set + * count to 1 in that dimension to only select that block. Copy all other + * diminfo parameters. */ + for(i = 0; i < space->extent.rank; i++) { + if((int)i == hslab->unlim_dim){ + start[i] = hslab->opt_diminfo[i].start + (block_index + * hslab->opt_diminfo[i].stride); + count[i] = (hsize_t)1; + } /* end if */ + else { + start[i] = hslab->opt_diminfo[i].start; + count[i] = hslab->opt_diminfo[i].count; + } /* end else */ + stride[i] = hslab->opt_diminfo[i].stride; + block[i] = hslab->opt_diminfo[i].block; + } /* end for */ + + /* Create output space, copy extent */ + if(NULL == (space_out = H5S_create(H5S_SIMPLE))) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCREATE, NULL, "unable to create output dataspace") + if(H5S_extent_copy_real(&space_out->extent, &space->extent, TRUE) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, NULL, "unable to copy destination space extent") + + /* Set offset to zeros */ + (void)HDmemset(space_out->select.offset, 0, (size_t)space_out->extent.rank * sizeof(space_out->select.offset[0])); + space_out->select.offset_changed = FALSE; + + /* Select block as defined by start/stride/count/block computed above */ + if(H5S_select_hyperslab(space_out, H5S_SELECT_SET, start, stride, count, block) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, NULL, "can't select hyperslab") + + /* Set return value */ + ret_value = space_out; + +done: + /* Free space on error */ + if(!ret_value) + if(space_out && H5S_close(space_out) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, NULL, "unable to release dataspace") + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_get_unlim_block */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_hyper_get_first_inc_block + PURPOSE + Get the index of the first incomplete block in the specified extent + USAGE + hsize_t H5S_hyper_get_first_inc_block(space,clip_size,partial) + const H5S_t *space, IN: Space with unlimited selection + hsize_t clip_size, IN: Extent space would be clipped to + hbool_t *partial; OUT: Whether the ret_valueth block (first incomplete block) is partial + RETURNS + Index of first incomplete block in clip_size (never fails). + DESCRIPTION + Calculates and returns the index (as would be passed to + H5S_hyper_get_unlim_block()) of the first block in the unlimited + dimension of space which would be incomplete or missing when space is + clipped to clip_size. partial is set to TRUE if the first incomplete + block is partial, and FALSE if the first incomplete block is missing. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Note this assumes the offset has been normalized. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +hsize_t +H5S_hyper_get_first_inc_block(const H5S_t *space, hsize_t clip_size, + hbool_t *partial) +{ + H5S_hyper_sel_t *hslab; /* Convenience pointer to hyperslab info */ + H5S_hyper_dim_t *diminfo; /* Convenience pointer to opt_diminfo in unlimited dimension */ + hsize_t ret_value; + + FUNC_ENTER_NOAPI_NOERR + + /* Check parameters */ + HDassert(space); + hslab = space->select.sel_info.hslab; + HDassert(hslab); + HDassert(hslab->unlim_dim >= 0); + HDassert(hslab->opt_diminfo[hslab->unlim_dim].count == H5S_UNLIMITED); + + diminfo = &hslab->opt_diminfo[hslab->unlim_dim]; + + /* Check for selection outside of clip_size */ + if(diminfo->start >= clip_size) { + ret_value = 0; + if(partial) + partial = FALSE; + } /* end if */ + else { + /* Calculate index of first incomplete block */ + ret_value = (clip_size - diminfo->start + diminfo->stride + - diminfo->block) / diminfo->stride; + + if(partial) { + /* Check for partial block */ + if((diminfo->stride * ret_value) < (clip_size - diminfo->start)) + *partial = TRUE; + else + *partial = FALSE; + } /* end if */ + } /* end else */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_hyper_get_first_inc_block */ + + +/*-------------------------------------------------------------------------- + NAME H5Sis_regular_hyperslab PURPOSE Determine if a hyperslab selection is regular diff --git a/src/H5Snone.c b/src/H5Snone.c index a67880e..23433a1 100644 --- a/src/H5Snone.c +++ b/src/H5Snone.c @@ -39,11 +39,14 @@ static herr_t H5S_none_get_seq_list(const H5S_t *space, unsigned flags, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); static herr_t H5S_none_release(H5S_t *space); static htri_t H5S_none_is_valid(const H5S_t *space); -static hssize_t H5S_none_serial_size(const H5S_t *space); -static herr_t H5S_none_serialize(const H5S_t *space, uint8_t **p); -static herr_t H5S_none_deserialize(H5S_t *space, const uint8_t **p); +static hssize_t H5S_none_serial_size(const H5F_t *f, const H5S_t *space); +static herr_t H5S_none_serialize(const H5F_t *f, const H5S_t *space, + uint8_t **p); +static herr_t H5S_none_deserialize(const H5F_t *f, H5S_t *space, + uint32_t version, uint8_t flags, const uint8_t **p); static herr_t H5S_none_bounds(const H5S_t *space, hsize_t *start, hsize_t *end); static herr_t H5S_none_offset(const H5S_t *space, hsize_t *off); +static int H5S_none_unlim_dim(const H5S_t *space); static htri_t H5S_none_is_contiguous(const H5S_t *space); static htri_t H5S_none_is_single(const H5S_t *space); static htri_t H5S_none_is_regular(const H5S_t *space); @@ -75,6 +78,8 @@ const H5S_select_class_t H5S_sel_none[1] = {{ H5S_none_deserialize, H5S_none_bounds, H5S_none_offset, + H5S_none_unlim_dim, + NULL, H5S_none_is_contiguous, H5S_none_is_single, H5S_none_is_regular, @@ -431,8 +436,9 @@ H5S_none_is_valid(const H5S_t H5_ATTR_UNUSED *space) Determine the number of bytes needed to store the serialized "none" selection information. USAGE - hssize_t H5S_none_serial_size(space) - H5S_t *space; IN: Dataspace pointer to query + hssize_t H5S_none_serial_size(f, space) + H5F_t *f IN: File pointer + H5S_t *space; IN: Dataspace pointer to query RETURNS The number of bytes required on success, negative on an error. DESCRIPTION @@ -444,7 +450,8 @@ H5S_none_is_valid(const H5S_t H5_ATTR_UNUSED *space) REVISION LOG --------------------------------------------------------------------------*/ static hssize_t -H5S_none_serial_size(const H5S_t H5_ATTR_UNUSED *space) +H5S_none_serial_size(const H5F_t H5_ATTR_UNUSED *f, + const H5S_t H5_ATTR_UNUSED *space) { FUNC_ENTER_NOAPI_NOINIT_NOERR @@ -464,7 +471,8 @@ H5S_none_serial_size(const H5S_t H5_ATTR_UNUSED *space) PURPOSE Serialize the current selection into a user-provided buffer. USAGE - herr_t H5S_none_serialize(space, p) + herr_t H5S_none_serialize(f, space, p) + H5F_t *f IN: File pointer const H5S_t *space; IN: Dataspace with selection to serialize uint8_t **p; OUT: Pointer to buffer to put serialized selection. Will be advanced to end of @@ -480,7 +488,7 @@ H5S_none_serial_size(const H5S_t H5_ATTR_UNUSED *space) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_none_serialize(const H5S_t *space, uint8_t **p) +H5S_none_serialize(const H5F_t H5_ATTR_UNUSED *f, const H5S_t *space, uint8_t **p) { FUNC_ENTER_NOAPI_NOINIT_NOERR @@ -502,9 +510,12 @@ H5S_none_serialize(const H5S_t *space, uint8_t **p) PURPOSE Deserialize the current selection from a user-provided buffer. USAGE - herr_t H5S_none_deserialize(space, p) + herr_t H5S_none_deserialize(f, space, version, flags, p) + H5F_t *f IN: File pointer H5S_t *space; IN/OUT: Dataspace pointer to place selection into + uint32_t version IN: Selection version + uint8_t flags IN: Selection flags uint8 **p; OUT: Pointer to buffer holding serialized selection. Will be advanced to end of serialized selection. @@ -519,7 +530,9 @@ H5S_none_serialize(const H5S_t *space, uint8_t **p) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_none_deserialize(H5S_t *space, const uint8_t H5_ATTR_UNUSED **p) +H5S_none_deserialize(const H5F_t H5_ATTR_UNUSED *f, H5S_t *space, + uint32_t H5_ATTR_UNUSED version, uint8_t H5_ATTR_UNUSED flags, + const uint8_t H5_ATTR_UNUSED **p) { herr_t ret_value = SUCCEED; /* return value */ @@ -610,6 +623,34 @@ H5S_none_offset(const H5S_t H5_ATTR_UNUSED *space, hsize_t H5_ATTR_UNUSED *offse /*-------------------------------------------------------------------------- NAME + H5S_none_unlim_dim + PURPOSE + Return unlimited dimension of selection, or -1 if none + USAGE + int H5S_none_unlim_dim(space) + H5S_t *space; IN: Dataspace pointer to check + RETURNS + Unlimited dimension of selection, or -1 if none (never fails). + DESCRIPTION + Returns the index of the unlimited dimension in this selection, or -1 + if the selection has no unlimited dimension. "None" selections cannot + have an unlimited dimension, so this function always returns -1. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static int +H5S_none_unlim_dim(const H5S_t H5_ATTR_UNUSED *space) +{ + FUNC_ENTER_NOAPI_NOERR + + FUNC_LEAVE_NOAPI(-1) +} /* end H5S_none_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME H5S_none_is_contiguous PURPOSE Check if a "none" selection is contiguous within the dataspace extent. diff --git a/src/H5Spkg.h b/src/H5Spkg.h index 5f84717..f719201 100644 --- a/src/H5Spkg.h +++ b/src/H5Spkg.h @@ -34,6 +34,13 @@ #define H5S_VALID_MAX 0x01 #define H5S_VALID_PERM 0x02 +/* Flags for serialization of selections */ +#define H5S_SELECT_FLAG_UNLIM 0x01 +#define H5S_SELECT_FLAG_BITS (H5S_SELECT_FLAG_UNLIM) + +/* Length of stack-allocated sequences for "project intersect" routines */ +#define H5S_PROJECT_INTERSECT_NSEQS 256 + /* Initial version of the dataspace information */ #define H5O_SDSPACE_VERSION_1 1 @@ -48,6 +55,10 @@ * and 'size' callbacks for places to change when updating this. */ #define H5O_SDSPACE_VERSION_LATEST H5O_SDSPACE_VERSION_2 +/* Maximum dimension size (highest value that is not a special value e.g. + * H5S_UNLIMITED) */ +#define H5S_MAX_SIZE ((hsize_t)(hssize_t)(-2)) + /* * Dataspace extent information @@ -113,6 +124,8 @@ typedef struct { * are only used for re-gurgitating the original values used to set the * hyperslab to the application when it queries the hyperslab selection * information. */ + int unlim_dim; /* Dimension where selection is unlimited, or -1 if none */ + hsize_t num_elem_non_unlim; /* # of elements in a "slice" excluding the unlimited dimension */ H5S_hyper_span_info_t *span_lst; /* List of hyperslab span information */ } H5S_hyper_sel_t; @@ -128,15 +141,22 @@ typedef herr_t (*H5S_sel_release_func_t)(H5S_t *space); /* Method to determine if current selection is valid for dataspace */ typedef htri_t (*H5S_sel_is_valid_func_t)(const H5S_t *space); /* Method to determine number of bytes required to store current selection */ -typedef hssize_t (*H5S_sel_serial_size_func_t)(const H5S_t *space); +typedef hssize_t (*H5S_sel_serial_size_func_t)(const H5F_t *f, const H5S_t *space); /* Method to store current selection in "serialized" form (a byte sequence suitable for storing on disk) */ -typedef herr_t (*H5S_sel_serialize_func_t)(const H5S_t *space, uint8_t **p); -/* Method to store create selection from "serialized" form (a byte sequence suitable for storing on disk) */ -typedef herr_t (*H5S_sel_deserialize_func_t)(H5S_t *space, const uint8_t **p); +typedef herr_t (*H5S_sel_serialize_func_t)(const H5F_t *f, const H5S_t *space, + uint8_t **p); +/* Method to create selection from "serialized" form (a byte sequence suitable for storing on disk) */ +typedef herr_t (*H5S_sel_deserialize_func_t)(const H5F_t *f, H5S_t *space, + uint32_t version, uint8_t flags, const uint8_t **p); /* Method to determine smallest n-D bounding box containing the current selection */ typedef herr_t (*H5S_sel_bounds_func_t)(const H5S_t *space, hsize_t *start, hsize_t *end); /* Method to determine linear offset of initial element in selection within dataspace */ typedef herr_t (*H5S_sel_offset_func_t)(const H5S_t *space, hsize_t *offset); +/* Method to get unlimited dimension of selection (or -1 for none) */ +typedef int (*H5S_sel_unlim_dim_func_t)(const H5S_t *space); +/* Method to get the number of elements in a slice through the unlimited dimension */ +typedef herr_t (*H5S_sel_num_elem_non_unlim_func_t)(const H5S_t *space, + hsize_t *num_elem_non_unlim); /* Method to determine if current selection is contiguous */ typedef htri_t (*H5S_sel_is_contiguous_func_t)(const H5S_t *space); /* Method to determine if current selection is a single block */ @@ -166,6 +186,8 @@ typedef struct { H5S_sel_deserialize_func_t deserialize; /* Method to store create selection from "serialized" form (a byte sequence suitable for storing on disk) */ H5S_sel_bounds_func_t bounds; /* Method to determine to smallest n-D bounding box containing the current selection */ H5S_sel_offset_func_t offset; /* Method to determine linear offset of initial element in selection within dataspace */ + H5S_sel_unlim_dim_func_t unlim_dim; /* Method to get unlimited dimension of selection (or -1 for none) */ + H5S_sel_num_elem_non_unlim_func_t num_elem_non_unlim; /* Method to get the number of elements in a slice through the unlimited dimension */ H5S_sel_is_contiguous_func_t is_contiguous; /* Method to determine if current selection is contiguous */ H5S_sel_is_single_func_t is_single; /* Method to determine if current selection is a single block */ H5S_sel_is_regular_func_t is_regular; /* Method to determine if current selection is "regular" */ @@ -245,10 +267,14 @@ H5_DLLVAR const H5S_select_class_t H5S_sel_point[1]; /* Extent functions */ H5_DLL herr_t H5S_extent_release(H5S_extent_t *extent); -H5_DLL herr_t H5S_extent_copy(H5S_extent_t *dst, const H5S_extent_t *src, +H5_DLL herr_t H5S_extent_copy_real(H5S_extent_t *dst, const H5S_extent_t *src, hbool_t copy_max); /* Operations on selections */ +H5_DLL herr_t H5S__hyper_project_intersection(const H5S_t *src_space, + const H5S_t *dst_space, const H5S_t *src_intersect_space, + H5S_t *proj_space); +H5_DLL herr_t H5S__hyper_subtract(H5S_t *space, H5S_t *subtract_space); /* Testing functions */ #ifdef H5S_TESTING diff --git a/src/H5Spoint.c b/src/H5Spoint.c index 20a60bb..d10b600 100644 --- a/src/H5Spoint.c +++ b/src/H5Spoint.c @@ -40,11 +40,14 @@ static herr_t H5S_point_get_seq_list(const H5S_t *space, unsigned flags, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); static herr_t H5S_point_release(H5S_t *space); static htri_t H5S_point_is_valid(const H5S_t *space); -static hssize_t H5S_point_serial_size(const H5S_t *space); -static herr_t H5S_point_serialize(const H5S_t *space, uint8_t **p); -static herr_t H5S_point_deserialize(H5S_t *space, const uint8_t **p); +static hssize_t H5S_point_serial_size(const H5F_t *f, const H5S_t *space); +static herr_t H5S_point_serialize(const H5F_t *f, const H5S_t *space, + uint8_t **p); +static herr_t H5S_point_deserialize(const H5F_t *f, H5S_t *space, + uint32_t version, uint8_t flags, const uint8_t **p); static herr_t H5S_point_bounds(const H5S_t *space, hsize_t *start, hsize_t *end); static herr_t H5S_point_offset(const H5S_t *space, hsize_t *off); +static int H5S_point_unlim_dim(const H5S_t *space); static htri_t H5S_point_is_contiguous(const H5S_t *space); static htri_t H5S_point_is_single(const H5S_t *space); static htri_t H5S_point_is_regular(const H5S_t *space); @@ -76,6 +79,8 @@ const H5S_select_class_t H5S_sel_point[1] = {{ H5S_point_deserialize, H5S_point_bounds, H5S_point_offset, + H5S_point_unlim_dim, + NULL, H5S_point_is_contiguous, H5S_point_is_single, H5S_point_is_regular, @@ -759,7 +764,8 @@ done: information. USAGE hssize_t H5S_point_serial_size(space) - H5S_t *space; IN: Dataspace pointer to query + H5F_t *f IN: File pointer + H5S_t *space; IN: Dataspace pointer to query RETURNS The number of bytes required on success, negative on an error. DESCRIPTION @@ -771,7 +777,7 @@ done: REVISION LOG --------------------------------------------------------------------------*/ static hssize_t -H5S_point_serial_size (const H5S_t *space) +H5S_point_serial_size(const H5F_t H5_ATTR_UNUSED *f, const H5S_t *space) { H5S_pnt_node_t *curr; /* Point information nodes */ hssize_t ret_value; /* return value */ @@ -805,6 +811,7 @@ H5S_point_serial_size (const H5S_t *space) Serialize the current selection into a user-provided buffer. USAGE herr_t H5S_point_serialize(space, p) + H5F_t *f IN: File pointer const H5S_t *space; IN: Dataspace with selection to serialize uint8_t **p; OUT: Pointer to buffer to put serialized selection. Will be advanced to end of @@ -820,7 +827,8 @@ H5S_point_serial_size (const H5S_t *space) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_point_serialize (const H5S_t *space, uint8_t **p) +H5S_point_serialize(const H5F_t H5_ATTR_UNUSED *f, const H5S_t *space, + uint8_t **p) { H5S_pnt_node_t *curr; /* Point information nodes */ uint8_t *lenp; /* pointer to length location for later storage */ @@ -873,8 +881,11 @@ H5S_point_serialize (const H5S_t *space, uint8_t **p) Deserialize the current selection from a user-provided buffer. USAGE herr_t H5S_point_deserialize(space, p) + H5F_t *f IN: File pointer H5S_t *space; IN/OUT: Dataspace pointer to place selection into + uint32_t version IN: Selection version + uint8_t flags IN: Selection flags uint8 **p; OUT: Pointer to buffer holding serialized selection. Will be advanced to end of serialized selection. @@ -889,7 +900,9 @@ H5S_point_serialize (const H5S_t *space, uint8_t **p) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_point_deserialize (H5S_t *space, const uint8_t **p) +H5S_point_deserialize(const H5F_t H5_ATTR_UNUSED *f, H5S_t *space, + uint32_t H5_ATTR_UNUSED version, uint8_t H5_ATTR_UNUSED flags, + const uint8_t **p) { H5S_seloper_t op=H5S_SELECT_SET; /* Selection operation */ unsigned rank; /* Rank of points */ @@ -1186,6 +1199,35 @@ done: /*-------------------------------------------------------------------------- NAME + H5S_point_unlim_dim + PURPOSE + Return unlimited dimension of selection, or -1 if none + USAGE + int H5S_point_unlim_dim(space) + H5S_t *space; IN: Dataspace pointer to check + RETURNS + Unlimited dimension of selection, or -1 if none (never fails). + DESCRIPTION + Returns the index of the unlimited dimension in this selection, or -1 + if the selection has no unlimited dimension. Currently point + selections cannot have an unlimited dimension, so this function always + returns -1. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +static int +H5S_point_unlim_dim(const H5S_t H5_ATTR_UNUSED *space) +{ + FUNC_ENTER_NOAPI_NOERR + + FUNC_LEAVE_NOAPI(-1) +} /* end H5S_point_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME H5S_point_is_contiguous PURPOSE Check if a point selection is contiguous within the dataspace extent. diff --git a/src/H5Sprivate.h b/src/H5Sprivate.h index 7b7b8c6..8918a4f 100644 --- a/src/H5Sprivate.h +++ b/src/H5Sprivate.h @@ -125,8 +125,8 @@ typedef struct H5S_sel_iter_t { #define H5S_SELECT_GET_SEQ_LIST(S,FLAGS,ITER,MAXSEQ,MAXBYTES,NSEQ,NBYTES,OFF,LEN) ((*(S)->select.type->get_seq_list)(S,FLAGS,ITER,MAXSEQ,MAXBYTES,NSEQ,NBYTES,OFF,LEN)) #define H5S_SELECT_VALID(S) ((*(S)->select.type->is_valid)(S)) #define H5S_SELECT_RELEASE(S) ((*(S)->select.type->release)(S)) -#define H5S_SELECT_SERIAL_SIZE(S) ((*(S)->select.type->serial_size)(S)) -#define H5S_SELECT_SERIALIZE(S,BUF) ((*(S)->select.type->serialize)(S,BUF)) +#define H5S_SELECT_SERIAL_SIZE(F,S) ((*(S)->select.type->serial_size)(F,S)) +#define H5S_SELECT_SERIALIZE(F,S,BUF) ((*(S)->select.type->serialize)(F,S,BUF)) #define H5S_SELECT_BOUNDS(S,START,END) ((*(S)->select.type->bounds)(S,START,END)) #define H5S_SELECT_OFFSET(S, OFFSET) ((*(S)->select.type->offset)(S, OFFSET)) #define H5S_SELECT_IS_CONTIGUOUS(S) ((*(S)->select.type->is_contiguous)(S)) @@ -151,8 +151,8 @@ typedef struct H5S_sel_iter_t { #define H5S_SELECT_GET_SEQ_LIST(S,FLAGS,ITER,MAXSEQ,MAXBYTES,NSEQ,NBYTES,OFF,LEN) (H5S_select_get_seq_list(S,FLAGS,ITER,MAXSEQ,MAXBYTES,NSEQ,NBYTES,OFF,LEN)) #define H5S_SELECT_VALID(S) (H5S_select_valid(S)) #define H5S_SELECT_RELEASE(S) (H5S_select_release(S)) -#define H5S_SELECT_SERIAL_SIZE(S) (H5S_select_serial_size(S)) -#define H5S_SELECT_SERIALIZE(S,BUF) (H5S_select_serialize(S,BUF)) +#define H5S_SELECT_SERIAL_SIZE(F,S) (H5S_select_serial_size(F,S)) +#define H5S_SELECT_SERIALIZE(F,S,BUF) (H5S_select_serialize(F,S,BUF)) #define H5S_SELECT_BOUNDS(S,START,END) (H5S_get_select_bounds(S,START,END)) #define H5S_SELECT_OFFSET(S, OFFSET) (H5S_get_select_offset(S, OFFSET)) #define H5S_SELECT_IS_CONTIGUOUS(S) (H5S_select_is_contiguous(S)) @@ -171,7 +171,7 @@ typedef struct H5S_sel_iter_t { #endif /* H5S_PACKAGE */ /* Handle these two callbacks in a special way, since they have prologs that need to be executed */ #define H5S_SELECT_COPY(DST,SRC,SHARE) (H5S_select_copy(DST,SRC,SHARE)) -#define H5S_SELECT_DESERIALIZE(S,BUF) (H5S_select_deserialize(S,BUF)) +#define H5S_SELECT_DESERIALIZE(F,S,BUF) (H5S_select_deserialize(F,S,BUF)) /* Operations on dataspaces */ @@ -190,10 +190,14 @@ H5_DLL herr_t H5S_append(H5F_t *f, hid_t dxpl_id, struct H5O_t *oh, H5S_t *ds); H5_DLL H5S_t *H5S_read(const struct H5O_loc_t *loc, hid_t dxpl_id); H5_DLL htri_t H5S_set_extent(H5S_t *space, const hsize_t *size); H5_DLL herr_t H5S_set_extent_real(H5S_t *space, const hsize_t *size); +H5_DLL herr_t H5S_set_extent_simple(H5S_t *space, unsigned rank, + const hsize_t *dims, const hsize_t *max); H5_DLL H5S_t *H5S_create(H5S_class_t type); H5_DLL H5S_t *H5S_create_simple(unsigned rank, const hsize_t dims[/*rank*/], const hsize_t maxdims[/*rank*/]); H5_DLL herr_t H5S_set_latest_version(H5S_t *ds); +H5_DLL herr_t H5S_encode(H5S_t *obj, unsigned char **p, size_t *nalloc); +H5_DLL H5S_t *H5S_decode(const unsigned char **p); H5_DLL herr_t H5S_debug(H5F_t *f, hid_t dxpl_id, const void *_mesg, FILE *stream, int indent, int fwidth); #ifndef H5_NO_DEPRECATED_SYMBOLS @@ -204,9 +208,11 @@ H5_DLL int H5S_extend(H5S_t *space, const hsize_t *size); H5_DLL hsize_t H5S_extent_nelem(const H5S_extent_t *ext); H5_DLL int H5S_extent_get_dims(const H5S_extent_t *ext, hsize_t dims[], hsize_t max_dims[]); H5_DLL htri_t H5S_extent_equal(const H5S_t *ds1, const H5S_t *ds2); +H5_DLL herr_t H5S_extent_copy(H5S_t *dst, const H5S_t *src); /* Operations on selections */ -H5_DLL herr_t H5S_select_deserialize(H5S_t **space, const uint8_t **p); +H5_DLL herr_t H5S_select_deserialize(const H5F_t *f, H5S_t **space, + const uint8_t **p); H5_DLL H5S_sel_type H5S_get_select_type(const H5S_t *space); H5_DLL herr_t H5S_select_iterate(void *buf, hid_t type_id, const H5S_t *space, H5D_operator_t op, void *operator_data); @@ -216,6 +222,9 @@ H5_DLL htri_t H5S_select_valid(const H5S_t *space); H5_DLL hssize_t H5S_get_select_npoints(const H5S_t *space); H5_DLL herr_t H5S_get_select_bounds(const H5S_t *space, hsize_t *start, hsize_t *end); H5_DLL herr_t H5S_get_select_offset(const H5S_t *space, hsize_t *offset); +H5_DLL int H5S_get_select_unlim_dim(const H5S_t *space); +H5_DLL herr_t H5S_get_select_num_elem_non_unlim(const H5S_t *space, + hsize_t *num_elem_non_unlim); H5_DLL herr_t H5S_select_offset(H5S_t *space, const hssize_t *offset); H5_DLL herr_t H5S_select_copy(H5S_t *dst, const H5S_t *src, hbool_t share_selection); H5_DLL htri_t H5S_select_shape_same(const H5S_t *space1, const H5S_t *space2); @@ -226,14 +235,19 @@ H5_DLL herr_t H5S_select_release(H5S_t *ds); H5_DLL herr_t H5S_select_get_seq_list(const H5S_t *space, unsigned flags, H5S_sel_iter_t *iter, size_t maxseq, size_t maxbytes, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); -H5_DLL hssize_t H5S_select_serial_size(const H5S_t *space); -H5_DLL herr_t H5S_select_serialize(const H5S_t *space, uint8_t **p); +H5_DLL hssize_t H5S_select_serial_size(const H5F_t *f, const H5S_t *space); +H5_DLL herr_t H5S_select_serialize(const H5F_t *f, const H5S_t *space, + uint8_t **p); H5_DLL htri_t H5S_select_is_contiguous(const H5S_t *space); H5_DLL htri_t H5S_select_is_single(const H5S_t *space); H5_DLL htri_t H5S_select_is_regular(const H5S_t *space); H5_DLL herr_t H5S_select_adjust_u(H5S_t *space, const hsize_t *offset); H5_DLL herr_t H5S_select_project_scalar(const H5S_t *space, hsize_t *offset); H5_DLL herr_t H5S_select_project_simple(const H5S_t *space, H5S_t *new_space, hsize_t *offset); +H5_DLL herr_t H5S_select_project_intersection(const H5S_t *src_space, + const H5S_t *dst_space, const H5S_t *src_intersect_space, + H5S_t **new_space_ptr); +H5_DLL herr_t H5S_select_subtract(H5S_t *space, H5S_t *subtract_space); /* Operations on all selections */ H5_DLL herr_t H5S_select_all(H5S_t *space, hbool_t rel_prev); @@ -259,6 +273,15 @@ H5_DLL htri_t H5S_hyper_intersect_block (H5S_t *space, hsize_t *start, hsize_t * H5_DLL herr_t H5S_hyper_adjust_s(H5S_t *space, const hssize_t *offset); H5_DLL htri_t H5S_hyper_normalize_offset(H5S_t *space, hssize_t *old_offset); H5_DLL herr_t H5S_hyper_denormalize_offset(H5S_t *space, const hssize_t *old_offset); +H5_DLL herr_t H5S_hyper_clip_unlim(H5S_t *space, hsize_t clip_size); +H5_DLL hsize_t H5S_hyper_get_clip_extent(const H5S_t *clip_space, + const H5S_t *match_space, hbool_t incl_trail); +H5_DLL hsize_t H5S_hyper_get_clip_extent_match(const H5S_t *clip_space, + const H5S_t *match_space, hsize_t match_clip_size, hbool_t incl_trail); +H5_DLL H5S_t *H5S_hyper_get_unlim_block(const H5S_t *space, + hsize_t block_index); +H5_DLL hsize_t H5S_hyper_get_first_inc_block(const H5S_t *space, + hsize_t clip_size, hbool_t *partial); /* Operations on selection iterators */ H5_DLL herr_t H5S_select_iter_init(H5S_sel_iter_t *iter, const H5S_t *space, size_t elmt_size); diff --git a/src/H5Spublic.h b/src/H5Spublic.h index 37d3866..721c4bf 100644 --- a/src/H5Spublic.h +++ b/src/H5Spublic.h @@ -25,7 +25,7 @@ /* Define atomic datatypes */ #define H5S_ALL (hid_t)0 -#define H5S_UNLIMITED ((hsize_t)(hssize_t)(-1)) +#define H5S_UNLIMITED HSIZE_UNDEF /* Define user-level maximum number of dimensions */ #define H5S_MAX_RANK 32 diff --git a/src/H5Sselect.c b/src/H5Sselect.c index e04ae16..e965dba 100644 --- a/src/H5Sselect.c +++ b/src/H5Sselect.c @@ -63,7 +63,9 @@ static herr_t H5S_select_iter_next_block(H5S_sel_iter_t *iter); herr_t H5S_select_offset(H5S_t *space, const hssize_t *offset) { - FUNC_ENTER_NOAPI_NOINIT_NOERR + herr_t ret_value = SUCCEED; + + FUNC_ENTER_NOAPI(FAIL) /* Check args */ HDassert(space); @@ -76,7 +78,8 @@ H5S_select_offset(H5S_t *space, const hssize_t *offset) /* Indicate that the offset was changed */ space->select.offset_changed = TRUE; - FUNC_LEAVE_NOAPI(SUCCEED) +done: + FUNC_LEAVE_NOAPI(ret_value) } /* H5S_select_offset() */ @@ -218,7 +221,7 @@ H5S_select_get_seq_list(const H5S_t *space, unsigned flags, *------------------------------------------------------------------------- */ hssize_t -H5S_select_serial_size(const H5S_t *space) +H5S_select_serial_size(const H5F_t *f, const H5S_t *space) { hssize_t ret_value; /* Return value */ @@ -227,7 +230,7 @@ H5S_select_serial_size(const H5S_t *space) HDassert(space); /* Call the selection type's serial_size function */ - ret_value=(*space->select.type->serial_size)(space); + ret_value=(*space->select.type->serial_size)(f, space); FUNC_LEAVE_NOAPI(ret_value) } /* end H5S_select_serial_size() */ @@ -258,7 +261,7 @@ H5S_select_serial_size(const H5S_t *space) REVISION LOG --------------------------------------------------------------------------*/ herr_t -H5S_select_serialize(const H5S_t *space, uint8_t **p) +H5S_select_serialize(const H5F_t *f, const H5S_t *space, uint8_t **p) { herr_t ret_value=SUCCEED; /* Return value */ @@ -268,7 +271,7 @@ H5S_select_serialize(const H5S_t *space, uint8_t **p) HDassert(p); /* Call the selection type's serialize function */ - ret_value=(*space->select.type->serialize)(space,p); + ret_value = (*space->select.type->serialize)(f, space, p); FUNC_LEAVE_NOAPI(ret_value) } /* end H5S_select_serialize() */ @@ -450,11 +453,13 @@ H5S_select_valid(const H5S_t *space) REVISION LOG --------------------------------------------------------------------------*/ herr_t -H5S_select_deserialize (H5S_t **space, const uint8_t **p) +H5S_select_deserialize(const H5F_t *f, H5S_t **space, const uint8_t **p) { H5S_t *tmp_space; /* Pointer to actual dataspace to use, either *space or a newly allocated one */ uint32_t sel_type; /* Pointer to the selection type */ + uint32_t version; /* Version number */ + uint8_t flags = 0; /* Flags */ herr_t ret_value=FAIL; /* return value */ FUNC_ENTER_NOAPI(FAIL) @@ -472,8 +477,23 @@ H5S_select_deserialize (H5S_t **space, const uint8_t **p) /* Decode selection type */ UINT32DECODE(*p, sel_type); - /* Skip over the remainder of the header */ - *p += 12; + /* Decode version */ + UINT32DECODE(*p, version); + + if(version >= (uint32_t)2) { + /* Decode flags */ + flags = *(*p)++; + + /* Check for unknown flags */ + if(flags & ~H5S_SELECT_FLAG_BITS) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTLOAD, FAIL, "unknown flag for selection") + + /* Skip over the remainder of the header */ + *p += 4; + } /* end if */ + else + /* Skip over the remainder of the header */ + *p += 8; /* Decode and check or patch rank for point and hyperslab selections */ if((sel_type == H5S_SEL_POINTS) || (sel_type == H5S_SEL_HYPERSLABS)) { @@ -482,9 +502,14 @@ H5S_select_deserialize (H5S_t **space, const uint8_t **p) /* Decode the rank of the point selection */ UINT32DECODE(*p,rank); - if(!*space) + if(!*space) { + hsize_t dims[H5S_MAX_RANK]; + /* Patch the rank of the allocated dataspace */ - tmp_space->extent.rank = rank; + (void)HDmemset(dims, 0, (size_t)rank * sizeof(dims[0])); + if(H5S_set_extent_simple(tmp_space, rank, dims, NULL) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "can't set dimensions") + } /* end if */ else /* Verify the rank of the provided dataspace */ if(rank != tmp_space->extent.rank) @@ -494,19 +519,19 @@ H5S_select_deserialize (H5S_t **space, const uint8_t **p) /* Make routine for selection type */ switch(sel_type) { case H5S_SEL_POINTS: /* Sequence of points selected */ - ret_value = (*H5S_sel_point->deserialize)(tmp_space, p); + ret_value = (*H5S_sel_point->deserialize)(f, tmp_space, version, flags, p); break; case H5S_SEL_HYPERSLABS: /* Hyperslab selection defined */ - ret_value = (*H5S_sel_hyper->deserialize)(tmp_space, p); + ret_value = (*H5S_sel_hyper->deserialize)(f, tmp_space, version, flags, p); break; case H5S_SEL_ALL: /* Entire extent selected */ - ret_value = (*H5S_sel_all->deserialize)(tmp_space, p); + ret_value = (*H5S_sel_all->deserialize)(f, tmp_space, version, flags, p); break; case H5S_SEL_NONE: /* Nothing selected */ - ret_value = (*H5S_sel_none->deserialize)(tmp_space, p); + ret_value = (*H5S_sel_none->deserialize)(f, tmp_space, version, flags, p); break; default: @@ -668,6 +693,89 @@ H5S_get_select_offset(const H5S_t *space, hsize_t *offset) /*-------------------------------------------------------------------------- NAME + H5S_get_select_unlim_dim + PURPOSE + Gets the unlimited dimension in the selection, or -1 if there is no + unlimited dimension. + USAGE + int H5S_get_select_unlim_dim(space) + const H5S_t *space; IN: Dataspace pointer of selection to query + RETURNS + Unlimited dimension in the selection, or -1 if there is no unlimited + dimension (never fails) + DESCRIPTION + Gets the unlimited dimension in the selection, or -1 if there is no + unlimited dimension. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + Currently only implemented for hyperslab selections, all others + simply return -1. + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +int +H5S_get_select_unlim_dim(const H5S_t *space) +{ + herr_t ret_value; /* return value */ + + FUNC_ENTER_NOAPI_NOINIT_NOERR + + /* Check args */ + HDassert(space); + + ret_value = (*space->select.type->unlim_dim)(space); + + FUNC_LEAVE_NOAPI(ret_value) +} /* H5S_get_select_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_get_select_num_elem_non_unlim + PURPOSE + Gets the number of elements in the non-unlimited dimensions + USAGE + herr_t H5S_get_select_num_elem_non_unlim(space,num_elem_non_unlim) + H5S_t *space; IN: Dataspace pointer to check + hsize_t *num_elem_non_unlim; OUT: Number of elements in the non-unlimited dimensions + RETURNS + Non-negative on success/Negative on failure + DESCRIPTION + Returns the number of elements in a slice through the non-unlimited + dimensions of the selection. Fails if the selection has no unlimited + dimension. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S_get_select_num_elem_non_unlim(const H5S_t *space, + hsize_t *num_elem_non_unlim) +{ + herr_t ret_value = SUCCEED; /* return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Check args */ + HDassert(space); + HDassert(num_elem_non_unlim); + + /* Check for selection callback */ + if(!space->select.type->num_elem_non_unlim) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "selection type has no num_elem_non_unlim callback") + + /* Make selection callback */ + if((*space->select.type->num_elem_non_unlim)(space, num_elem_non_unlim) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOUNT, FAIL, "can't get number of elements in non-unlimited dimension") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* H5S_get_select_unlim_dim() */ + + +/*-------------------------------------------------------------------------- + NAME H5S_select_is_contiguous PURPOSE Determines if a selection is contiguous in the dataspace @@ -2101,3 +2209,193 @@ done: FUNC_LEAVE_NOAPI(ret_value) } /* H5S_select_fill() */ + +/*-------------------------------------------------------------------------- + NAME + H5S_select_project_intersection + + PURPOSE + Projects the intersection of of the selections of src_space and + src_intersect_space within the selection of src_space as a selection + within the selection of dst_space + + USAGE + herr_t H5S_select_project_intersection(src_space,dst_space,src_intersect_space,proj_space) + H5S_t *src_space; IN: Selection that is mapped to dst_space, and intersected with src_intersect_space + H5S_t *dst_space; IN: Selection that is mapped to src_space, and which contains the result + H5S_t *src_intersect_space; IN: Selection whose intersection with src_space is projected to dst_space to obtain the result + H5S_t *proj_space; OUT: Will contain the result (intersection of src_intersect_space and src_space projected from src_space to dst_space) after the operation + + RETURNS + Non-negative on success/Negative on failure. + + DESCRIPTION + Projects the intersection of of the selections of src_space and + src_intersect_space within the selection of src_space as a selection + within the selection of dst_space. The result is placed in the + selection of proj_space. + + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S_select_project_intersection(const H5S_t *src_space, const H5S_t *dst_space, + const H5S_t *src_intersect_space, H5S_t **new_space_ptr) +{ + H5S_t *new_space = NULL; /* New dataspace constructed */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Sanity checks */ + HDassert(src_space); + HDassert(dst_space); + HDassert(src_intersect_space); + HDassert(new_space_ptr); + + /* Create new space, using dst extent. Start with "all" selection. */ + if(NULL == (new_space = H5S_create(H5S_SIMPLE))) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCREATE, FAIL, "unable to create output dataspace") + if(H5S_extent_copy_real(&new_space->extent, &dst_space->extent, TRUE) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, FAIL, "unable to copy destination space extent") + + /* Set offset to zeros */ + (void)HDmemset(new_space->select.offset, 0, (size_t)new_space->extent.rank * sizeof(new_space->select.offset[0])); + new_space->select.offset_changed = FALSE; + + /* If the intersecting space is "all", the intersection must be equal to the + * source space and the projection must be equal to the destination space */ + if(src_intersect_space->select.type->type == H5S_SEL_ALL) { + /* Copy the destination selection. */ + if(H5S_select_copy(new_space, dst_space, FALSE) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCOPY, FAIL, "can't copy destination space selection") + } /* end if */ + /* If any of the spaces are "none", the projection must also be "none" */ + else if((src_intersect_space->select.type->type == H5S_SEL_NONE) + || (src_space->select.type->type == H5S_SEL_NONE) + || (dst_space->select.type->type == H5S_SEL_NONE)) { + /* Change to "none" selection */ + if(H5S_select_none(new_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") + } /* end if */ + /* If any of the spaces use point selection, fall back to general algorithm + */ + else if((src_intersect_space->select.type->type == H5S_SEL_POINTS) + || (src_space->select.type->type == H5S_SEL_POINTS) + || (dst_space->select.type->type == H5S_SEL_POINTS)) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "point selections not currently supported") + else { + HDassert(src_intersect_space->select.type->type == H5S_SEL_HYPERSLABS); + /* Intersecting space is hyperslab selection. Call the hyperslab + * routine to project to another hyperslab selection. */ + if(H5S__hyper_project_intersection(src_space, dst_space, src_intersect_space, new_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "can't project hyperslab ondot destination selection") + } /* end else */ + + /* load the address of the new space into *new_space_ptr */ + *new_space_ptr = new_space; + +done: + /* Cleanup on error */ + if(ret_value < 0) { + if(new_space && H5S_close(new_space) < 0) + HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release dataspace") + } /* end if */ + + FUNC_LEAVE_NOAPI(ret_value) +} /* H5S_select_project_intersection() */ + + +/*-------------------------------------------------------------------------- + NAME + H5S_select_subtract + + PURPOSE + Subtract one selection from another + + USAGE + herr_t H5S_select_subtract(space,subtract_space) + H5S_t *space; IN/OUT: Selection to be operated on + H5S_t *subtract_space; IN: Selection that will be subtracted from space + + RETURNS + Non-negative on success/Negative on failure. + + DESCRIPTION + Removes any and all portions of space that are also present in + subtract_space. In essence, performs an A_NOT_B operation with the + two selections. + + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5S_select_subtract(H5S_t *space, H5S_t *subtract_space) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + + /* Sanity checks */ + HDassert(space); + HDassert(subtract_space); + + /* If either space is using the none selection, then we do not need to do + * anything */ + if((space->select.type->type != H5S_SEL_NONE) + && (subtract_space->select.type->type != H5S_SEL_NONE)) { + /* If subtract_space is using the all selection, set space to none */ + if(subtract_space->select.type->type == H5S_SEL_ALL) { + /* Change to "none" selection */ + if(H5S_select_none(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTDELETE, FAIL, "can't change selection") + } /* end if */ + else { + /* Check for point selection in subtract_space, convert to + * hyperslab */ + if(subtract_space->select.type->type == H5S_SEL_POINTS) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "point selections not currently supported") + + /* Check for point or all selection in space, convert to hyperslab + */ + if(space->select.type->type == H5S_SEL_ALL) { + /* Convert current "all" selection to "real" hyperslab selection */ + /* Then allow operation to proceed */ + hsize_t tmp_start[H5O_LAYOUT_NDIMS]; /* Temporary start information */ + hsize_t tmp_stride[H5O_LAYOUT_NDIMS]; /* Temporary stride information */ + hsize_t tmp_count[H5O_LAYOUT_NDIMS]; /* Temporary count information */ + hsize_t tmp_block[H5O_LAYOUT_NDIMS]; /* Temporary block information */ + unsigned i; /* Local index variable */ + + /* Fill in temporary information for the dimensions */ + for(i = 0; i < space->extent.rank; i++) { + tmp_start[i] = 0; + tmp_stride[i] = 1; + tmp_count[i] = 1; + tmp_block[i] = space->extent.size[i]; + } /* end for */ + + /* Convert to hyperslab selection */ + if(H5S_select_hyperslab(space, H5S_SELECT_SET, tmp_start, tmp_stride, tmp_count, tmp_block) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTSELECT, FAIL, "can't convert selection") + } /* end if */ + else if(space->select.type->type == H5S_SEL_POINTS) + HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, "point selections not currently supported") + + HDassert(space->select.type->type == H5S_SEL_HYPERSLABS); + HDassert(subtract_space->select.type->type == H5S_SEL_HYPERSLABS); + + /* Both spaces are now hyperslabs, perform the operation */ + if(H5S__hyper_subtract(space, subtract_space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCLIP, FAIL, "can't subtract hyperslab") + } /* end else */ + } /* end if */ + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* H5S_select_subtract() */ + diff --git a/src/H5err.txt b/src/H5err.txt index 5a38cdf..e0ebf5e 100644 --- a/src/H5err.txt +++ b/src/H5err.txt @@ -217,6 +217,7 @@ MINOR, DSPACE, H5E_CANTSELECT, Can't select hyperslab MINOR, DSPACE, H5E_CANTNEXT, Can't move to next iterator location MINOR, DSPACE, H5E_BADSELECT, Invalid selection MINOR, DSPACE, H5E_CANTCOMPARE, Can't compare objects +MINOR, DSPACE, H5E_CANTAPPEND, Can't append object # Property list errors MINOR, PLIST, H5E_CANTGET, Can't get value diff --git a/src/H5public.h b/src/H5public.h index 8c7da05..603c187 100644 --- a/src/H5public.h +++ b/src/H5public.h @@ -176,6 +176,7 @@ H5_GCC_DIAG_ON(long-long) #else # error "nothing appropriate for hsize_t" #endif +#define HSIZE_UNDEF ((hsize_t)(hssize_t)(-1)) /* * File addresses have their own types. diff --git a/src/H5trace.c b/src/H5trace.c index e6a091c..66b3a0c 100644 --- a/src/H5trace.c +++ b/src/H5trace.c @@ -524,6 +524,10 @@ H5_trace(const double *returning, const char *func, const char *type, ...) fprintf(out, "H5D_CHUNKED"); break; + case H5D_VIRTUAL: + fprintf(out, "H5D_VIRTUAL"); + break; + case H5D_NLAYOUTS: fprintf(out, "H5D_NLAYOUTS"); break; @@ -676,6 +680,36 @@ H5_trace(const double *returning, const char *func, const char *type, ...) } /* end else */ break; + case 'v': + if(ptr) { + if(vp) + fprintf(out, "0x%lx", (unsigned long)vp); + else + fprintf(out, "NULL"); + } /* end if */ + else { + H5D_vds_view_t view = (H5D_vds_view_t)va_arg(ap, int); + + switch(view) { + case H5D_VDS_ERROR: + fprintf(out, "H5D_VDS_ERROR"); + break; + + case H5D_VDS_FIRST_MISSING: + fprintf(out, "H5D_VDS_FIRST_MISSING"); + break; + + case H5D_VDS_LAST_AVAILABLE: + fprintf(out, "H5D_VDS_LAST_AVAILABLE"); + break; + + default: + fprintf(out, "%ld", (long)view); + break; + } /* end switch */ + } /* end else */ + break; + default: fprintf (out, "BADTYPE(D%c)", type[1]); goto error; diff --git a/src/Makefile.am b/src/Makefile.am index b6c4dad..662b9a8 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -50,7 +50,7 @@ libhdf5_la_SOURCES= H5.c H5checksum.c H5dbg.c H5system.c H5timer.c H5trace.c \ H5D.c H5Dbtree.c H5Dchunk.c H5Dcompact.c H5Dcontig.c H5Ddbg.c \ H5Ddeprec.c H5Defl.c H5Dfill.c H5Dint.c \ H5Dio.c H5Dlayout.c \ - H5Dmpio.c H5Doh.c H5Dscatgath.c H5Dselect.c H5Dtest.c \ + H5Dmpio.c H5Doh.c H5Dscatgath.c H5Dselect.c H5Dtest.c H5Dvirtual.c \ H5E.c H5Edeprec.c H5Eint.c \ H5EA.c H5EAcache.c H5EAdbg.c H5EAdblkpage.c H5EAdblock.c H5EAhdr.c \ H5EAiblock.c H5EAint.c H5EAsblock.c H5EAstat.c H5EAtest.c \ diff --git a/src/Makefile.in b/src/Makefile.in index e5a991f..08662f7 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -156,23 +156,23 @@ am_libhdf5_la_OBJECTS = H5.lo H5checksum.lo H5dbg.lo H5system.lo \ H5Cmpio.lo H5CS.lo H5D.lo H5Dbtree.lo H5Dchunk.lo \ H5Dcompact.lo H5Dcontig.lo H5Ddbg.lo H5Ddeprec.lo H5Defl.lo \ H5Dfill.lo H5Dint.lo H5Dio.lo H5Dlayout.lo H5Dmpio.lo H5Doh.lo \ - H5Dscatgath.lo H5Dselect.lo H5Dtest.lo H5E.lo H5Edeprec.lo \ - H5Eint.lo H5EA.lo H5EAcache.lo H5EAdbg.lo H5EAdblkpage.lo \ - H5EAdblock.lo H5EAhdr.lo H5EAiblock.lo H5EAint.lo \ - H5EAsblock.lo H5EAstat.lo H5EAtest.lo H5F.lo H5Fint.lo \ - H5Faccum.lo H5Fcwfs.lo H5Fdbg.lo H5Fdeprec.lo H5Fefc.lo \ - H5Ffake.lo H5Fio.lo H5Fmount.lo H5Fmpi.lo H5Fquery.lo \ - H5Fsfile.lo H5Fsuper.lo H5Fsuper_cache.lo H5Ftest.lo H5FA.lo \ - H5FAcache.lo H5FAdbg.lo H5FAdblock.lo H5FAdblkpage.lo \ - H5FAhdr.lo H5FAstat.lo H5FAtest.lo H5FD.lo H5FDcore.lo \ - H5FDdirect.lo H5FDfamily.lo H5FDint.lo H5FDlog.lo H5FDmpi.lo \ - H5FDmpio.lo H5FDmulti.lo H5FDsec2.lo H5FDspace.lo H5FDstdio.lo \ - H5FL.lo H5FO.lo H5FS.lo H5FScache.lo H5FSdbg.lo H5FSsection.lo \ - H5FSstat.lo H5FStest.lo H5G.lo H5Gbtree2.lo H5Gcache.lo \ - H5Gcompact.lo H5Gdense.lo H5Gdeprec.lo H5Gent.lo H5Gint.lo \ - H5Glink.lo H5Gloc.lo H5Gname.lo H5Gnode.lo H5Gobj.lo H5Goh.lo \ - H5Groot.lo H5Gstab.lo H5Gtest.lo H5Gtraverse.lo H5HF.lo \ - H5HFbtree2.lo H5HFcache.lo H5HFdbg.lo H5HFdblock.lo \ + H5Dscatgath.lo H5Dselect.lo H5Dtest.lo H5Dvirtual.lo H5E.lo \ + H5Edeprec.lo H5Eint.lo H5EA.lo H5EAcache.lo H5EAdbg.lo \ + H5EAdblkpage.lo H5EAdblock.lo H5EAhdr.lo H5EAiblock.lo \ + H5EAint.lo H5EAsblock.lo H5EAstat.lo H5EAtest.lo H5F.lo \ + H5Fint.lo H5Faccum.lo H5Fcwfs.lo H5Fdbg.lo H5Fdeprec.lo \ + H5Fefc.lo H5Ffake.lo H5Fio.lo H5Fmount.lo H5Fmpi.lo \ + H5Fquery.lo H5Fsfile.lo H5Fsuper.lo H5Fsuper_cache.lo \ + H5Ftest.lo H5FA.lo H5FAcache.lo H5FAdbg.lo H5FAdblock.lo \ + H5FAdblkpage.lo H5FAhdr.lo H5FAstat.lo H5FAtest.lo H5FD.lo \ + H5FDcore.lo H5FDdirect.lo H5FDfamily.lo H5FDint.lo H5FDlog.lo \ + H5FDmpi.lo H5FDmpio.lo H5FDmulti.lo H5FDsec2.lo H5FDspace.lo \ + H5FDstdio.lo H5FL.lo H5FO.lo H5FS.lo H5FScache.lo H5FSdbg.lo \ + H5FSsection.lo H5FSstat.lo H5FStest.lo H5G.lo H5Gbtree2.lo \ + H5Gcache.lo H5Gcompact.lo H5Gdense.lo H5Gdeprec.lo H5Gent.lo \ + H5Gint.lo H5Glink.lo H5Gloc.lo H5Gname.lo H5Gnode.lo H5Gobj.lo \ + H5Goh.lo H5Groot.lo H5Gstab.lo H5Gtest.lo H5Gtraverse.lo \ + H5HF.lo H5HFbtree2.lo H5HFcache.lo H5HFdbg.lo H5HFdblock.lo \ H5HFdtable.lo H5HFhdr.lo H5HFhuge.lo H5HFiblock.lo H5HFiter.lo \ H5HFman.lo H5HFsection.lo H5HFspace.lo H5HFstat.lo H5HFtest.lo \ H5HFtiny.lo H5HG.lo H5HGcache.lo H5HGdbg.lo H5HGquery.lo \ @@ -766,7 +766,7 @@ libhdf5_la_SOURCES = H5.c H5checksum.c H5dbg.c H5system.c H5timer.c H5trace.c \ H5D.c H5Dbtree.c H5Dchunk.c H5Dcompact.c H5Dcontig.c H5Ddbg.c \ H5Ddeprec.c H5Defl.c H5Dfill.c H5Dint.c \ H5Dio.c H5Dlayout.c \ - H5Dmpio.c H5Doh.c H5Dscatgath.c H5Dselect.c H5Dtest.c \ + H5Dmpio.c H5Doh.c H5Dscatgath.c H5Dselect.c H5Dtest.c H5Dvirtual.c \ H5E.c H5Edeprec.c H5Eint.c \ H5EA.c H5EAcache.c H5EAdbg.c H5EAdblkpage.c H5EAdblock.c H5EAhdr.c \ H5EAiblock.c H5EAint.c H5EAsblock.c H5EAstat.c H5EAtest.c \ @@ -1019,6 +1019,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Dscatgath.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Dselect.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Dtest.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Dvirtual.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5E.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5EA.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5EAcache.Plo@am__quote@ diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index f33c2df..dc79cdb 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -246,6 +246,7 @@ set (H5_TESTS cross_read freespace mf + vds farray earray btree2 diff --git a/test/CMakeTests.cmake b/test/CMakeTests.cmake index 5fe51ed..40c0f44 100644 --- a/test/CMakeTests.cmake +++ b/test/CMakeTests.cmake @@ -427,6 +427,7 @@ add_test ( tstint2.h5 unregister_filter_1.h5 unregister_filter_2.h5 + vds_1.h5 WORKING_DIRECTORY ${HDF5_TEST_BINARY_DIR}/H5TEST ) diff --git a/test/Makefile.am b/test/Makefile.am index b5ebcf3..7588dc0 100644 --- a/test/Makefile.am +++ b/test/Makefile.am @@ -46,7 +46,7 @@ TEST_PROG= testhdf5 lheap ohdr stab gheap cache cache_api cache_tagging \ big mtime fillval mount flush1 flush2 app_ref enum \ set_extent ttsafe enc_dec_plist enc_dec_plist_with_endianess\ getname vfd ntypes dangle dtransform reserved cross_read \ - freespace mf farray earray btree2 fheap file_image unregister + freespace mf vds farray earray btree2 fheap file_image unregister # List programs to be built when testing here. error_test and err_compat are # built at the same time as the other tests, but executed by testerror.sh. @@ -150,7 +150,8 @@ CHECK_CLEANFILES+=accum.h5 cmpd_dset.h5 compact_dataset.h5 dataset.h5 dset_offse earray.h5 efc[0-5].h5 log_vfd_out.log \ new_multi_file_v16-r.h5 new_multi_file_v16-s.h5 \ split_get_file_image_test-m.h5 split_get_file_image_test-r.h5 \ - file_image_core_test.h5.copy unregister_filter_1.h5 unregister_filter_2.h5 + file_image_core_test.h5.copy unregister_filter_1.h5 unregister_filter_2.h5 \ + vds_virt.h5 vds_src_[0-1].h5 # Sources for testhdf5 executable testhdf5_SOURCES=testhdf5.c tarray.c tattr.c tchecksum.c tconfig.c tfile.c \ diff --git a/test/Makefile.in b/test/Makefile.in index e8877d7..22237fa 100644 --- a/test/Makefile.in +++ b/test/Makefile.in @@ -195,9 +195,9 @@ am__EXEEXT_1 = testhdf5$(EXEEXT) lheap$(EXEEXT) ohdr$(EXEEXT) \ enc_dec_plist_with_endianess$(EXEEXT) getname$(EXEEXT) \ vfd$(EXEEXT) ntypes$(EXEEXT) dangle$(EXEEXT) \ dtransform$(EXEEXT) reserved$(EXEEXT) cross_read$(EXEEXT) \ - freespace$(EXEEXT) mf$(EXEEXT) farray$(EXEEXT) earray$(EXEEXT) \ - btree2$(EXEEXT) fheap$(EXEEXT) file_image$(EXEEXT) \ - unregister$(EXEEXT) + freespace$(EXEEXT) mf$(EXEEXT) vds$(EXEEXT) farray$(EXEEXT) \ + earray$(EXEEXT) btree2$(EXEEXT) fheap$(EXEEXT) \ + file_image$(EXEEXT) unregister$(EXEEXT) @HAVE_SHARED_CONDITIONAL_TRUE@am__EXEEXT_2 = plugin$(EXEEXT) am__EXEEXT_3 = gen_bad_ohdr$(EXEEXT) gen_bogus$(EXEEXT) \ gen_cross$(EXEEXT) gen_deflate$(EXEEXT) gen_filters$(EXEEXT) \ @@ -520,6 +520,10 @@ unregister_SOURCES = unregister.c unregister_OBJECTS = unregister.$(OBJEXT) unregister_LDADD = $(LDADD) unregister_DEPENDENCIES = libh5test.la $(LIBHDF5) +vds_SOURCES = vds.c +vds_OBJECTS = vds.$(OBJEXT) +vds_LDADD = $(LDADD) +vds_DEPENDENCIES = libh5test.la $(LIBHDF5) vfd_SOURCES = vfd.c vfd_OBJECTS = vfd.$(OBJEXT) vfd_LDADD = $(LDADD) @@ -575,7 +579,7 @@ SOURCES = $(libdynlib1_la_SOURCES) $(libdynlib2_la_SOURCES) \ mount.c mtime.c ntypes.c objcopy.c ohdr.c plugin.c pool.c \ reserved.c set_extent.c space_overflow.c stab.c \ tcheck_version.c $(testhdf5_SOURCES) testmeta.c \ - $(ttsafe_SOURCES) unlink.c unregister.c vfd.c + $(ttsafe_SOURCES) unlink.c unregister.c vds.c vfd.c DIST_SOURCES = $(am__libdynlib1_la_SOURCES_DIST) \ $(am__libdynlib2_la_SOURCES_DIST) \ $(am__libdynlib3_la_SOURCES_DIST) $(libh5test_la_SOURCES) \ @@ -594,7 +598,7 @@ DIST_SOURCES = $(am__libdynlib1_la_SOURCES_DIST) \ mount.c mtime.c ntypes.c objcopy.c ohdr.c plugin.c pool.c \ reserved.c set_extent.c space_overflow.c stab.c \ tcheck_version.c $(testhdf5_SOURCES) testmeta.c \ - $(ttsafe_SOURCES) unlink.c unregister.c vfd.c + $(ttsafe_SOURCES) unlink.c unregister.c vds.c vfd.c am__can_run_installinfo = \ case $$AM_UPDATE_INFO_DIR in \ n|no|NO) false;; \ @@ -1109,7 +1113,8 @@ CHECK_CLEANFILES = *.chkexe *.chklog *.clog *.clog2 accum.h5 \ earray.h5 efc[0-5].h5 log_vfd_out.log new_multi_file_v16-r.h5 \ new_multi_file_v16-s.h5 split_get_file_image_test-m.h5 \ split_get_file_image_test-r.h5 file_image_core_test.h5.copy \ - unregister_filter_1.h5 unregister_filter_2.h5 + unregister_filter_1.h5 unregister_filter_2.h5 vds_virt.h5 \ + vds_src_[0-1].h5 # Test script for error_test and err_compat TEST_SCRIPT = testerror.sh testlibinfo.sh testcheck_version.sh \ @@ -1131,7 +1136,7 @@ TEST_PROG = testhdf5 lheap ohdr stab gheap cache cache_api cache_tagging \ big mtime fillval mount flush1 flush2 app_ref enum \ set_extent ttsafe enc_dec_plist enc_dec_plist_with_endianess\ getname vfd ntypes dangle dtransform reserved cross_read \ - freespace mf farray earray btree2 fheap file_image unregister + freespace mf vds farray earray btree2 fheap file_image unregister # These programs generate test files for the tests. They don't need to be @@ -1617,6 +1622,10 @@ unregister$(EXEEXT): $(unregister_OBJECTS) $(unregister_DEPENDENCIES) $(EXTRA_un @rm -f unregister$(EXEEXT) $(AM_V_CCLD)$(LINK) $(unregister_OBJECTS) $(unregister_LDADD) $(LIBS) +vds$(EXEEXT): $(vds_OBJECTS) $(vds_DEPENDENCIES) $(EXTRA_vds_DEPENDENCIES) + @rm -f vds$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(vds_OBJECTS) $(vds_LDADD) $(LIBS) + vfd$(EXEEXT): $(vfd_OBJECTS) $(vfd_DEPENDENCIES) $(EXTRA_vfd_DEPENDENCIES) @rm -f vfd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(vfd_OBJECTS) $(vfd_LDADD) $(LIBS) @@ -1736,6 +1745,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tvltypes.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/unlink.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/unregister.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vds.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/vfd.Po@am__quote@ .c.o: @@ -2262,6 +2272,13 @@ mf.log: mf$(EXEEXT) --log-file $$b.log --trs-file $$b.trs \ $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ "$$tst" $(AM_TESTS_FD_REDIRECT) +vds.log: vds$(EXEEXT) + @p='vds$(EXEEXT)'; \ + b='vds'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) farray.log: farray$(EXEEXT) @p='farray$(EXEEXT)'; \ b='farray'; \ diff --git a/test/h5test.c b/test/h5test.c index fefacda..aa99c1f 100644 --- a/test/h5test.c +++ b/test/h5test.c @@ -93,7 +93,7 @@ static const char *multi_letters = "msbrglo"; static herr_t h5_errors(hid_t estack, void *client_data); static char * h5_fixname_real(const char *base_name, hid_t fapl, const char *suffix, - char *fullname, size_t size); + char *fullname, size_t size, hbool_t nest_printf); /*------------------------------------------------------------------------- @@ -122,69 +122,94 @@ h5_errors(hid_t estack, void H5_ATTR_UNUSED *client_data) /*------------------------------------------------------------------------- - * Function: h5_cleanup + * Function: h5_cleanup_files * - * Purpose: Cleanup temporary test files. + * Purpose: Cleanup temporary test files (always). * base_name contains the list of test file names. - * The file access property list is also closed. * - * Return: Non-zero if cleanup actions were performed; zero otherwise. + * Return: void * - * Programmer: Albert Cheng + * Programmer: Neil Fortner + * June 1, 2015 + * Original: Albert Cheng * May 28, 1998 * *------------------------------------------------------------------------- */ -int -h5_cleanup(const char *base_name[], hid_t fapl) +void +h5_cleanup_files(const char *base_name[], hid_t fapl) { - int retval = 0; + int i; - if(GetTestCleanup()) { - int i; + for(i = 0; base_name[i]; i++) { + char filename[1024]; + char temp[2048]; + hid_t driver; + + if(NULL == h5_fixname(base_name[i], fapl, filename, sizeof(filename))) + continue; + + driver = H5Pget_driver(fapl); - for(i = 0; base_name[i]; i++) { - char filename[1024]; - char temp[2048]; - hid_t driver; + if(driver == H5FD_FAMILY) { + int j; - if(NULL == h5_fixname(base_name[i], fapl, filename, sizeof(filename))) - continue; + for(j = 0; /*void*/; j++) { + HDsnprintf(temp, sizeof temp, filename, j); - driver = H5Pget_driver(fapl); + if(HDaccess(temp, F_OK) < 0) + break; - if(driver == H5FD_FAMILY) { - int j; + HDremove(temp); + } /* end for */ + } else if(driver == H5FD_CORE) { + hbool_t backing; /* Whether the core file has backing store */ - for(j = 0; /*void*/; j++) { - HDsnprintf(temp, sizeof temp, filename, j); + H5Pget_fapl_core(fapl, NULL, &backing); - if(HDaccess(temp, F_OK) < 0) - break; + /* If the file was stored to disk with bacing store, remove it */ + if(backing) + HDremove(filename); + } else if (driver == H5FD_MULTI) { + H5FD_mem_t mt; - HDremove(temp); - } /* end for */ - } else if(driver == H5FD_CORE) { - hbool_t backing; /* Whether the core file has backing store */ + HDassert(HDstrlen(multi_letters)==H5FD_MEM_NTYPES); - H5Pget_fapl_core(fapl, NULL, &backing); + for(mt = H5FD_MEM_DEFAULT; mt < H5FD_MEM_NTYPES; H5_INC_ENUM(H5FD_mem_t,mt)) { + HDsnprintf(temp, sizeof temp, "%s-%c.h5", filename, multi_letters[mt]); + HDremove(temp); /*don't care if it fails*/ + } /* end for */ + } else { + HDremove(filename); + } + } /* end for */ - /* If the file was stored to disk with bacing store, remove it */ - if(backing) - HDremove(filename); - } else if (driver == H5FD_MULTI) { - H5FD_mem_t mt; + return; +} /* end h5_cleanup_files() */ - HDassert(HDstrlen(multi_letters)==H5FD_MEM_NTYPES); - for(mt = H5FD_MEM_DEFAULT; mt < H5FD_MEM_NTYPES; H5_INC_ENUM(H5FD_mem_t,mt)) { - HDsnprintf(temp, sizeof temp, "%s-%c.h5", filename, multi_letters[mt]); - HDremove(temp); /*don't care if it fails*/ - } /* end for */ - } else { - HDremove(filename); - } - } /* end for */ +/*------------------------------------------------------------------------- + * Function: h5_cleanup + * + * Purpose: Cleanup temporary test files. + * base_name contains the list of test file names. + * The file access property list is also closed. + * + * Return: Non-zero if cleanup actions were performed; zero otherwise. + * + * Programmer: Albert Cheng + * May 28, 1998 + * + *------------------------------------------------------------------------- + */ +int +h5_cleanup(const char *base_name[], hid_t fapl) +{ + int retval = 0; + + if(GetTestCleanup()) { + /* Clean up files in base_name */ + h5_cleanup_files(base_name, fapl); retval = 1; } /* end if */ @@ -270,7 +295,7 @@ h5_reset(void) char * h5_fixname(const char *base_name, hid_t fapl, char *fullname, size_t size) { - return (h5_fixname_real(base_name, fapl, ".h5", fullname, size)); + return (h5_fixname_real(base_name, fapl, ".h5", fullname, size, FALSE)); } @@ -290,7 +315,33 @@ h5_fixname(const char *base_name, hid_t fapl, char *fullname, size_t size) char * h5_fixname_no_suffix(const char *base_name, hid_t fapl, char *fullname, size_t size) { - return (h5_fixname_real(base_name, fapl, NULL, fullname, size)); + return (h5_fixname_real(base_name, fapl, NULL, fullname, size, FALSE)); +} + + +/*------------------------------------------------------------------------- + * Function: h5_fixname_printf + * + * Purpose: Same as h5_fixname but returns a filename that can be passed + * through a printf-style function once before being passed to the file + * driver. Basically, replaces all % characters used by the file + * driver with %%. + * + * Return: Success: The FULLNAME pointer. + * + * Failure: NULL if BASENAME or FULLNAME is the null + * pointer or if FULLNAME isn't large enough for + * the result. + * + * Programmer: Neil Fortner + * Wednesday, July 15, 2015 + * + *------------------------------------------------------------------------- + */ +char * +h5_fixname_printf(const char *base_name, hid_t fapl, char *fullname, size_t size) +{ + return (h5_fixname_real(base_name, fapl, ".h5", fullname, size, TRUE)); } @@ -318,7 +369,7 @@ h5_fixname_no_suffix(const char *base_name, hid_t fapl, char *fullname, size_t s */ static char * h5_fixname_real(const char *base_name, hid_t fapl, const char *_suffix, - char *fullname, size_t size) + char *fullname, size_t size, hbool_t nest_printf) { const char *prefix = NULL; char *ptr, last = '\0'; @@ -339,7 +390,7 @@ h5_fixname_real(const char *base_name, hid_t fapl, const char *_suffix, if(suffix) { if(H5FD_FAMILY == driver) - suffix = "%05d.h5"; + suffix = nest_printf ? "%%05d.h5" : "%05d.h5"; else if (H5FD_MULTI == driver) suffix = NULL; } diff --git a/test/h5test.h b/test/h5test.h index 5b203c6..9d097af 100644 --- a/test/h5test.h +++ b/test/h5test.h @@ -124,8 +124,10 @@ extern "C" { /* Generally useful testing routines */ H5TEST_DLL int h5_cleanup(const char *base_name[], hid_t fapl); +H5TEST_DLL void h5_cleanup_files(const char *base_name[], hid_t fapl); H5TEST_DLL char *h5_fixname(const char *base_name, hid_t fapl, char *fullname, size_t size); H5TEST_DLL char *h5_fixname_no_suffix(const char *base_name, hid_t fapl, char *fullname, size_t size); +H5TEST_DLL char *h5_fixname_printf(const char *base_name, hid_t fapl, char *fullname, size_t size); H5TEST_DLL hid_t h5_fileaccess(void); H5TEST_DLL void h5_no_hwconv(void); H5TEST_DLL const char *h5_rmprefix(const char *filename); diff --git a/test/trefer.c b/test/trefer.c index df4ea76..cb0f44e 100644 --- a/test/trefer.c +++ b/test/trefer.c @@ -521,6 +521,8 @@ test_reference_region(void) uint8_t *tu8; /* Temporary pointer to uint8 data */ H5O_type_t obj_type; /* Type of object */ int i, j; /* counting variables */ + hssize_t hssize_ret; /* hssize_t return value */ + htri_t tri_ret; /* htri_t return value */ herr_t ret; /* Generic return value */ haddr_t addr = HADDR_UNDEF; /* test for undefined reference */ hid_t dset_NA; /* Dataset id for undefined reference */ @@ -614,6 +616,24 @@ test_reference_region(void) ret = H5Rcreate(&wbuf[1], fid1, "/Dataset2", H5R_DATASET_REGION, sid2); CHECK(ret, FAIL, "H5Rcreate"); + /* Select unlimited hyperslab for third reference */ + start[0] = 1; start[1] = 8; + stride[0] = 4; stride[1] = 1; + count[0] = H5S_UNLIMITED; count[1] = 1; + block[0] = 2; block[1] = 2; + ret = H5Sselect_hyperslab(sid2, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + + hssize_ret = H5Sget_select_npoints(sid2); + VERIFY(hssize_ret, (hssize_t)H5S_UNLIMITED, "H5Sget_select_npoints"); + + /* Store third dataset region */ + ret = H5Rcreate(&wbuf[2], fid1, "/Dataset2", H5R_DATASET_REGION, sid2); + CHECK(ret, FAIL, "H5Rcreate"); + ret = H5Rget_obj_type2(dset1, H5R_DATASET_REGION, &wbuf[0], &obj_type); + CHECK(ret, FAIL, "H5Rget_obj_type2"); + VERIFY(obj_type, H5O_TYPE_DATASET, "H5Rget_obj_type2"); + /* Write selection to disk */ ret = H5Dwrite(dset1, H5T_STD_REF_DSETREG, H5S_ALL, H5S_ALL, H5P_DEFAULT, wbuf); CHECK(ret, FAIL, "H5Dwrite"); @@ -805,6 +825,31 @@ test_reference_region(void) ret = H5Sclose(sid2); CHECK(ret, FAIL, "H5Sclose"); + /* Get the unlimited selection */ + sid2 = H5Rget_region(dset1, H5R_DATASET_REGION, &rbuf[2]); + CHECK(sid2, FAIL, "H5Rget_region"); + + /* Verify correct hyperslab selected */ + hssize_ret = H5Sget_select_npoints(sid2); + VERIFY(hssize_ret, (hssize_t)H5S_UNLIMITED, "H5Sget_select_npoints"); + tri_ret = H5Sis_regular_hyperslab(sid2); + CHECK(tri_ret, FAIL, "H5Sis_regular_hyperslab"); + VERIFY(tri_ret, TRUE, "H5Sis_regular_hyperslab Result"); + ret = H5Sget_regular_hyperslab(sid2, start, stride, count, block); + CHECK(ret, FAIL, "H5Sget_regular_hyperslab"); + VERIFY(start[0], (hsize_t)1, "Hyperslab Coordinates"); + VERIFY(start[1], (hsize_t)8, "Hyperslab Coordinates"); + VERIFY(stride[0], (hsize_t)4, "Hyperslab Coordinates"); + VERIFY(stride[1], (hsize_t)1, "Hyperslab Coordinates"); + VERIFY(count[0], H5S_UNLIMITED, "Hyperslab Coordinates"); + VERIFY(count[1], (hsize_t)1, "Hyperslab Coordinates"); + VERIFY(block[0], (hsize_t)2, "Hyperslab Coordinates"); + VERIFY(block[1], (hsize_t)2, "Hyperslab Coordinates"); + + /* Close region space */ + ret = H5Sclose(sid2); + CHECK(ret, FAIL, "H5Sclose"); + /* Close first space */ ret = H5Sclose(sid1); CHECK(ret, FAIL, "H5Sclose"); diff --git a/test/tselect.c b/test/tselect.c index bdcdb2b..2062e73 100644 --- a/test/tselect.c +++ b/test/tselect.c @@ -13230,6 +13230,439 @@ test_hyper_regular(void) /**************************************************************** ** +** test_hyper_unlim(): Tests unlimited hyperslab selections +** +****************************************************************/ +static void +test_hyper_unlim_check(hid_t sid, hsize_t *dims, hssize_t enpoints, + hssize_t enblocks, hsize_t *eblock1, hsize_t *eblock2) +{ + hid_t lim_sid; + hsize_t start[3]; + H5S_sel_type sel_type; + hssize_t npoints; + hssize_t nblocks; + hsize_t blocklist[12]; + herr_t ret; + + HDassert(enblocks <= 2); + + /* Copy sid to lim_sid */ + lim_sid = H5Scopy(sid); + CHECK(lim_sid, FAIL, "H5Scopy"); + + /* "And" lim_sid with dims to create limited selection */ + HDmemset(start, 0, sizeof(start)); + ret = H5Sselect_hyperslab(lim_sid, H5S_SELECT_AND, start, NULL, dims, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + + /* Check number of elements */ + npoints = H5Sget_select_npoints(lim_sid); + CHECK(npoints, FAIL, "H5Sget_select_npoints"); + VERIFY(npoints, enpoints, "H5Sget_select_npoints"); + + /* Get selection type */ + sel_type = H5Sget_select_type(lim_sid); + CHECK(sel_type, H5S_SEL_ERROR, "H5Sget_select_type"); + + /* Only examine blocks for hyperslab selection */ + if(sel_type == H5S_SEL_HYPERSLABS) { + /* Get number of blocks */ + nblocks = H5Sget_select_hyper_nblocks(lim_sid); + CHECK(nblocks, FAIL, "H5Sget_select_hyper_nblocks"); + VERIFY(nblocks, enblocks, "H5Sget_select_hyper_nblocks"); + + if(nblocks > 0) { + /* Get blocklist */ + ret = H5Sget_select_hyper_blocklist(lim_sid, (hsize_t)0, (hsize_t)nblocks, blocklist); + CHECK(ret, FAIL, "H5Sget_select_hyper_blocklist"); + + /* Verify blocklist */ + if(nblocks == (hssize_t)1) { + if(HDmemcmp(blocklist, eblock1, 6 * sizeof(eblock1[0]))) + ERROR("H5Sget_select_hyper_blocklist"); + } /* end if */ + else { + HDassert(nblocks == (hssize_t)2); + if(HDmemcmp(blocklist, eblock1, 6 * sizeof(eblock1[0]))) { + if(HDmemcmp(blocklist, eblock2, 6 * sizeof(eblock2[0]))) + ERROR("H5Sget_select_hyper_blocklist"); + if(HDmemcmp(&blocklist[6], eblock1, 6 * sizeof(eblock1[0]))) + ERROR("H5Sget_select_hyper_blocklist"); + } /* end if */ + else + if(HDmemcmp(&blocklist[6], eblock2, 6 * sizeof(eblock2[0]))) + ERROR("H5Sget_select_hyper_blocklist"); + } /* end else */ + } /* end if */ + } /* end if */ + else + if(sel_type != H5S_SEL_NONE) + ERROR("H5Sget_select_type"); + + /* Close the limited dataspace */ + ret = H5Sclose(lim_sid); + CHECK(ret, FAIL, "H5Sclose"); +} /* end test_hyper_unlim_check() */ + +static void +test_hyper_unlim(void) +{ + hid_t sid; + hsize_t dims[3] = {4, 4, 7}; + hsize_t mdims[3] = {4, H5S_UNLIMITED, 7}; + hsize_t start[3] = {1, 2, 1}; + hsize_t stride[3] = {1, 1, 3}; + hsize_t count[3] = {1, 1, 2}; + hsize_t block[3] = {2, H5S_UNLIMITED, 2}; + hsize_t start2[3]; + hsize_t count2[3]; + hsize_t eblock1[6] = {1, 2, 1, 2, 3, 2}; + hsize_t eblock2[6] = {1, 2, 4, 2, 3, 5}; + hssize_t offset[3] = {0, -1, 0}; + hssize_t ssize_out; + herr_t ret; + + /* Output message about test being performed */ + MESSAGE(6, ("Testing unlimited hyperslab selections\n")); + + /* Create dataspace */ + sid = H5Screate_simple(3, dims, mdims); + CHECK(sid, FAIL, "H5Screate_simple"); + + /* Select unlimited hyperslab */ + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + + /* Check with unlimited dimension clipped to 4 */ + test_hyper_unlim_check(sid, dims, (hssize_t)16, (hssize_t)2, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 3 */ + dims[1] = 3; + eblock1[4] = 2; + eblock2[4] = 2; + test_hyper_unlim_check(sid, dims, (hssize_t)8, (hssize_t)2, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 2 */ + dims[1] = 2; + test_hyper_unlim_check(sid, dims, (hssize_t)0, (hssize_t)0, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 1 */ + dims[1] = 1; + test_hyper_unlim_check(sid, dims, (hssize_t)0, (hssize_t)0, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 7 */ + dims[1] = 7; + eblock1[4] = 6; + eblock2[4] = 6; + test_hyper_unlim_check(sid, dims, (hssize_t)40, (hssize_t)2, eblock1, eblock2); + + /* Set offset of selection */ + ret = H5Soffset_simple(sid, offset); + CHECK(ret, FAIL, "H5Soffset_simple"); + + /* Check with adjusted offset (should not affect result) */ + test_hyper_unlim_check(sid, dims, (hssize_t)40, (hssize_t)2, eblock1, eblock2); + + /* Reset offset of selection */ + offset[1] = (hssize_t)0; + ret = H5Soffset_simple(sid, offset); + CHECK(ret, FAIL, "H5Soffset_simple"); + + /* + * Now try with multiple blocks in unlimited dimension + */ + stride[1] = 3; + stride[2] = 1; + count[1] = H5S_UNLIMITED; + count[2] = 1; + block[1] = 2; + + /* Select unlimited hyperslab */ + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + + /* Check with new selection */ + eblock1[1] = 2; + eblock1[4] = 3; + eblock2[1] = 5; + eblock2[2] = 1; + eblock2[4] = 6; + eblock2[5] = 2; + test_hyper_unlim_check(sid, dims, (hssize_t)16, (hssize_t)2, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 3 */ + dims[1] = 3; + eblock1[4] = 2; + test_hyper_unlim_check(sid, dims, (hssize_t)4, (hssize_t)1, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 4 */ + dims[1] = 4; + eblock1[4] = 3; + test_hyper_unlim_check(sid, dims, (hssize_t)8, (hssize_t)1, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 5 */ + dims[1] = 5; + eblock1[4] = 3; + test_hyper_unlim_check(sid, dims, (hssize_t)8, (hssize_t)1, eblock1, eblock2); + + /* Check with unlimited dimension clipped to 6 */ + dims[1] = 6; + eblock1[4] = 3; + eblock2[4] = 5; + test_hyper_unlim_check(sid, dims, (hssize_t)12, (hssize_t)2, eblock1, eblock2); + + /* Set offset of selection */ + offset[1] = (hssize_t)-1; + ret = H5Soffset_simple(sid, offset); + CHECK(ret, FAIL, "H5Soffset_simple"); + + /* Check with adjusted offset (should not affect result) */ + test_hyper_unlim_check(sid, dims, (hssize_t)12, (hssize_t)2, eblock1, eblock2); + + /* Set offset of selection */ + offset[1] = (hssize_t)3; + ret = H5Soffset_simple(sid, offset); + CHECK(ret, FAIL, "H5Soffset_simple"); + + /* Check with adjusted offset (should not affect result) */ + test_hyper_unlim_check(sid, dims, (hssize_t)12, (hssize_t)2, eblock1, eblock2); + + /* Reset offset of selection */ + offset[1] = (hssize_t)0; + ret = H5Soffset_simple(sid, offset); + CHECK(ret, FAIL, "H5Soffset_simple"); + + /* + * Now try invalid operations + */ + H5E_BEGIN_TRY { + /* Try multiple unlimited dimensions */ + start[0] = 1; + start[1] = 2; + start[2] = 1; + stride[0] = 1; + stride[1] = 3; + stride[2] = 3; + count[0] = 1; + count[1] = H5S_UNLIMITED; + count[2] = H5S_UNLIMITED; + block[0] = 2; + block[1] = 2; + block[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + + /* Try unlimited count and block */ + count[2] = 2; + block[1] = H5S_UNLIMITED; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + } H5E_END_TRY + + /* Try operations with two unlimited selections */ + block[1] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + H5E_BEGIN_TRY { + ret = H5Sselect_hyperslab(sid, H5S_SELECT_OR, start, NULL, count, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_AND, start, NULL, count, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_XOR, start, NULL, count, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTB, start, NULL, count, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTA, start, NULL, count, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + } H5E_END_TRY + + /* Try invalid combination operations */ + H5E_BEGIN_TRY { + ret = H5Sselect_hyperslab(sid, H5S_SELECT_OR, start, NULL, block, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_XOR, start, NULL, block, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTB, start, NULL, block, NULL); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + } H5E_END_TRY + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, NULL, block, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + H5E_BEGIN_TRY { + ret = H5Sselect_hyperslab(sid, H5S_SELECT_OR, start, stride, count, block); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_XOR, start, stride, count, block); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTA, start, stride, count, block); + VERIFY(ret, FAIL, "H5Sselect_hyperslab"); + } H5E_END_TRY + + /* + * Now test valid combination operations + */ + /* unlim AND non-unlim */ + count[0] = 1; + count[1] = H5S_UNLIMITED; + count[2] = 2; + block[0] = 2; + block[1] = 2; + block[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + start2[0] = 2; + start2[1] = 2; + start2[2] = 0; + count2[0] = 5; + count2[1] = 4; + count2[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_AND, start2, NULL, count2, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + eblock1[0] = 2; + eblock1[3] = 2; + eblock1[1] = 2; + eblock1[4] = 3; + eblock1[2] = 1; + eblock1[5] = 1; + eblock2[0] = 2; + eblock2[3] = 2; + eblock2[1] = 5; + eblock2[4] = 5; + eblock2[2] = 1; + eblock2[5] = 1; + dims[0] = 50; + dims[1] = 50; + dims[2] = 50; + test_hyper_unlim_check(sid, dims, (hssize_t)3, (hssize_t)2, eblock1, eblock2); + + /* unlim NOTA non-unlim */ + count[0] = 1; + count[1] = H5S_UNLIMITED; + count[2] = 2; + block[0] = 2; + block[1] = 2; + block[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + start2[0] = 1; + start2[1] = 5; + start2[2] = 2; + count2[0] = 2; + count2[1] = 2; + count2[2] = 6; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTA, start2, NULL, count2, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + eblock1[0] = 1; + eblock1[3] = 2; + eblock1[1] = 5; + eblock1[4] = 6; + eblock1[2] = 3; + eblock1[5] = 3; + eblock2[0] = 1; + eblock2[3] = 2; + eblock2[1] = 5; + eblock2[4] = 6; + eblock2[2] = 6; + eblock2[5] = 7; + dims[0] = 50; + dims[1] = 50; + dims[2] = 50; + test_hyper_unlim_check(sid, dims, (hssize_t)12, (hssize_t)2, eblock1, eblock2); + + /* non-unlim AND unlim */ + start2[0] = 2; + start2[1] = 2; + start2[2] = 0; + count2[0] = 5; + count2[1] = 4; + count2[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start2, NULL, count2, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + count[0] = 1; + count[1] = H5S_UNLIMITED; + count[2] = 2; + block[0] = 2; + block[1] = 2; + block[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_AND, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + eblock1[0] = 2; + eblock1[3] = 2; + eblock1[1] = 2; + eblock1[4] = 3; + eblock1[2] = 1; + eblock1[5] = 1; + eblock2[0] = 2; + eblock2[3] = 2; + eblock2[1] = 5; + eblock2[4] = 5; + eblock2[2] = 1; + eblock2[5] = 1; + dims[0] = 50; + dims[1] = 50; + dims[2] = 50; + test_hyper_unlim_check(sid, dims, (hssize_t)3, (hssize_t)2, eblock1, eblock2); + + /* non-unlim NOTB unlim */ + start2[0] = 1; + start2[1] = 5; + start2[2] = 2; + count2[0] = 2; + count2[1] = 2; + count2[2] = 6; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start2, NULL, count2, NULL); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + count[0] = 1; + count[1] = H5S_UNLIMITED; + count[2] = 2; + block[0] = 2; + block[1] = 2; + block[2] = 2; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_NOTB, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + eblock1[0] = 1; + eblock1[3] = 2; + eblock1[1] = 5; + eblock1[4] = 6; + eblock1[2] = 3; + eblock1[5] = 3; + eblock2[0] = 1; + eblock2[3] = 2; + eblock2[1] = 5; + eblock2[4] = 6; + eblock2[2] = 6; + eblock2[5] = 7; + dims[0] = 50; + dims[1] = 50; + dims[2] = 50; + test_hyper_unlim_check(sid, dims, (hssize_t)12, (hssize_t)2, eblock1, eblock2); + + /* Test H5Sget_select_npoints() */ + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + ssize_out = H5Sget_select_npoints(sid); + VERIFY(ssize_out, (hssize_t)H5S_UNLIMITED, "H5Sget_select_npoints"); + + /* Test H5Sget_select_hyper_nblocks() */ + ssize_out = H5Sget_select_hyper_nblocks(sid); + VERIFY(ssize_out, (hssize_t)H5S_UNLIMITED, "H5Sget_select_hyper_nblocks"); + + /* Test H5Sget_select_bounds() */ + ret = H5Sget_select_bounds(sid, start2, count2); + CHECK(ret, FAIL, "H5Sget_select_bounds"); + VERIFY(start2[0], start[0], "H5Sget_select_bounds"); + VERIFY(start2[1], start[1], "H5Sget_select_bounds"); + VERIFY(start2[2], start[2], "H5Sget_select_bounds"); + VERIFY(count2[0], start[0] + (stride[0] * (count[0] - (hsize_t)1)) + block[0] - (hsize_t)1, "H5Sget_select_bounds"); + VERIFY(count2[1], H5S_UNLIMITED, "H5Sget_select_bounds"); + VERIFY(count2[2], start[2] + (stride[2] * (count[2] - (hsize_t)1)) + block[2] - (hsize_t)1, "H5Sget_select_bounds"); + + /* Close the dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); +} /* end test_hyper_unlim() */ + +/**************************************************************** +** ** test_select(): Main H5S selection testing routine. ** ****************************************************************/ @@ -13392,6 +13825,9 @@ test_select(void) /* Test 'regular' hyperslab query routines */ test_hyper_regular(); + /* Test unlimited hyperslab selections */ + test_hyper_unlim(); + } /* test_select() */ diff --git a/test/vds.c b/test/vds.c new file mode 100644 index 0000000..5cdcef4 --- /dev/null +++ b/test/vds.c @@ -0,0 +1,11146 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by The HDF Group. * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * Programmer: Neil Fortner <nfortne2@hdfgroup.org> + * Monday, February 16, 2015 + * + * Purpose: Tests datasets with virtual layout. + */ +#include "h5test.h" +#include "H5srcdir.h" +#include "H5Dprivate.h" /* For H5D_VIRTUAL_DEF_LIST_SIZE */ + +typedef enum { + TEST_API_BASIC, + TEST_API_COPY_PLIST, + TEST_API_ENCDEC_PLIST, + TEST_API_CREATE_DSET, + TEST_API_REOPEN_DSET, + TEST_API_REOPEN_FILE, + TEST_API_NTESTS +} test_api_config_t; + +const char *FILENAME[] = { + "vds_virt_0", + "vds_virt_1", + "vds_src_0", + "vds_src_1", + "vds%_src", + NULL +}; + +/* I/O test config flags */ +#define TEST_IO_CLOSE_SRC 0x01u +#define TEST_IO_DIFFERENT_FILE 0x02u +#define TEST_IO_REOPEN_VIRT 0x04u +#define TEST_IO_NTESTS 0x08u + +#define LIST_DOUBLE_SIZE (H5D_VIRTUAL_DEF_LIST_SIZE + 1) + +#define FILENAME_BUF_SIZE 1024 + + +/*------------------------------------------------------------------------- + * Function: vds_select_equal + * + * Purpose: Helper function to check if the selections in the two + * provided dataspaces are the same. + * + * Return: Success: 0 + * + * Failure: -1 + * + * Programmer: Neil Fortner + * Monday, March 2, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static htri_t +vds_select_equal(hid_t space1, hid_t space2) +{ + H5S_sel_type type1; + H5S_sel_type type2; + hsize_t *buf1 = NULL; + hsize_t *buf2 = NULL; + size_t i; + htri_t ret_value = TRUE; + + /* Get and compare selection types */ + if((type1 = H5Sget_select_type(space1)) < 0) + TEST_ERROR + if((type2 = H5Sget_select_type(space2)) < 0) + TEST_ERROR + if(type1 != type2) + return FALSE; + + /* Check selection type */ + switch(type1) { + case H5S_SEL_NONE: + case H5S_SEL_ALL: + break; + + case H5S_SEL_POINTS: + { + int rank1; + int rank2; + hssize_t npoints1; + hssize_t npoints2; + + /* Get and compare rank */ + if((rank1 = H5Sget_simple_extent_ndims(space1)) < 0) + TEST_ERROR + if((rank2 = H5Sget_simple_extent_ndims(space2)) < 0) + TEST_ERROR + if(rank1 != rank2) + return FALSE; + + /* Get and compare number of points */ + if((npoints1 = H5Sget_select_elem_npoints(space1)) < 0) + TEST_ERROR + if((npoints2 = H5Sget_select_elem_npoints(space2)) < 0) + TEST_ERROR + if(npoints1 != npoints2) + return FALSE; + + /* Allocate point lists. Do not return directly afer + * allocating, to make sure buffers are freed. */ + if(NULL == (buf1 = (hsize_t *)HDmalloc((size_t)rank1 * (size_t)npoints1 * sizeof(hsize_t)))) + TEST_ERROR + if(NULL == (buf2 = (hsize_t *)HDmalloc((size_t)rank1 * (size_t)npoints1 * sizeof(hsize_t)))) + TEST_ERROR + + /* Get and compare point lists */ + if(H5Sget_select_elem_pointlist(space1, (hsize_t)0, (hsize_t)npoints1, buf1) < 0) + TEST_ERROR + if(H5Sget_select_elem_pointlist(space2, (hsize_t)0, (hsize_t)npoints1, buf2) < 0) + TEST_ERROR + for(i = 0; i < ((size_t)rank1 * (size_t)npoints1); i++) + if(buf1[i] != buf2[i]) { + ret_value = FALSE; + break; + } /* end if */ + + /* Free buffers */ + HDfree(buf1); + buf1 = NULL; + HDfree(buf2); + buf2 = NULL; + } /* end block */ + + break; + + case H5S_SEL_HYPERSLABS: + { + int rank1; + int rank2; + hssize_t nblocks1; + hssize_t nblocks2; + + /* Get and compare rank */ + if((rank1 = H5Sget_simple_extent_ndims(space1)) < 0) + TEST_ERROR + if((rank2 = H5Sget_simple_extent_ndims(space2)) < 0) + TEST_ERROR + if(rank1 != rank2) + return FALSE; + + /* Get and compare number of blocks */ + if((nblocks1 = H5Sget_select_hyper_nblocks(space1)) < 0) + TEST_ERROR + if((nblocks2 = H5Sget_select_hyper_nblocks(space2)) < 0) + TEST_ERROR + if(nblocks1 != nblocks2) + return FALSE; + + /* Allocate block lists. Do not return directly afer + * allocating, to make sure buffers are freed. */ + if(NULL == (buf1 = (hsize_t *)HDmalloc((size_t)2 * (size_t)rank1 * (size_t)nblocks1 * sizeof(*buf1)))) + TEST_ERROR + if(NULL == (buf2 = (hsize_t *)HDmalloc((size_t)2 * (size_t)rank1 * (size_t)nblocks1 * sizeof(*buf2)))) + TEST_ERROR + + /* Get and compare block lists */ + if(H5Sget_select_hyper_blocklist(space1, (hsize_t)0, (hsize_t)nblocks1, buf1) < 0) + TEST_ERROR + if(H5Sget_select_hyper_blocklist(space2, (hsize_t)0, (hsize_t)nblocks1, buf2) < 0) + TEST_ERROR + for(i = 0; i < ((size_t)2 * (size_t)rank1 * (size_t)nblocks1); i++) + if(buf1[i] != buf2[i]) { + ret_value = FALSE; + break; + } /* end if */ + + /* Free buffers */ + HDfree(buf1); + buf1 = NULL; + HDfree(buf2); + buf2 = NULL; + } /* end block */ + + break; + + case H5S_SEL_ERROR: + case H5S_SEL_N: + default: + TEST_ERROR + } /* end switch */ + + return ret_value; + +error: + if(buf1) + HDfree(buf1); + if(buf2) + HDfree(buf2); + + return -1; +} /* end vds_select_equal() */ + + +/*------------------------------------------------------------------------- + * Function: vds_check_mapping + * + * Purpose: Helper function to check if the ith virtual mapping in the + * provided dcpl is the same as that described by the other + * parameters. + * + * Return: Success: 0 + * + * Failure: -1 + * + * Programmer: Neil Fortner + * Monday, March 2, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static int +vds_check_mapping(hid_t dcpl, size_t i, hid_t vspace, hid_t srcspace, + const char *filename, const char *dsetname) +{ + hid_t space_out = -1; + char name_out[32]; + htri_t tri_ret; + ssize_t str_len; + + HDassert(dcpl >= 0); + HDassert(vspace >= 0); + HDassert(srcspace >= 0); + HDassert(filename); + HDassert(dsetname); + + /* Check vspace */ + if((space_out = H5Pget_virtual_vspace(dcpl, i)) < 0) + TEST_ERROR + if((tri_ret = H5Sextent_equal(space_out, vspace)) < 0) + TEST_ERROR + if(!tri_ret) + TEST_ERROR + if((tri_ret = vds_select_equal(space_out, vspace)) < 0) + TEST_ERROR + if(!tri_ret) + TEST_ERROR + if(H5Sclose(space_out) < 0) + TEST_ERROR + space_out = -1; + + /* Check srcspace */ + if((space_out = H5Pget_virtual_srcspace(dcpl, i)) < 0) + TEST_ERROR + if((tri_ret = vds_select_equal(space_out, srcspace)) < 0) + TEST_ERROR + if(!tri_ret) + TEST_ERROR + if(H5Sclose(space_out) < 0) + TEST_ERROR + space_out = -1; + + /* Check filename */ + if((str_len = H5Pget_virtual_filename(dcpl, i, NULL, (size_t)0)) < 0) + TEST_ERROR + if((size_t)str_len != HDstrlen(filename)) + TEST_ERROR + HDassert((size_t)str_len < sizeof(name_out)); + if((str_len = H5Pget_virtual_filename(dcpl, i, name_out, sizeof(name_out))) < 0) + TEST_ERROR + if((size_t)str_len != HDstrlen(filename)) + TEST_ERROR + if(HDstrncmp(name_out, filename, (size_t)str_len + 1) != 0) + TEST_ERROR + + /* Check dsetname */ + if((str_len = H5Pget_virtual_dsetname(dcpl, i, NULL, (size_t)0)) < 0) + TEST_ERROR + if((size_t)str_len != HDstrlen(dsetname)) + TEST_ERROR + HDassert((size_t)str_len < sizeof(name_out)); + if((str_len = H5Pget_virtual_dsetname(dcpl, i, name_out, sizeof(name_out))) < 0) + TEST_ERROR + if((size_t)str_len != HDstrlen(dsetname)) + TEST_ERROR + if(HDstrncmp(name_out, dsetname, (size_t)str_len + 1) != 0) + TEST_ERROR + + return 0; + +error: + H5E_BEGIN_TRY { + if(space_out >= 0) + (void)H5Sclose(space_out); + } H5E_END_TRY + + return -1; +} /* end vds_check_mapping() */ + + +/*------------------------------------------------------------------------- + * Function: test_api + * + * Purpose: Tests API functions related to virtual datasets. + * + * Return: Success: 0 + * + * Failure: number of errors + * + * Programmer: Neil Fortner + * Monday, February 16, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +/* Helper function to get DCPL for examination depending on config */ +static int +test_api_get_ex_dcpl(test_api_config_t config, hid_t fapl, hid_t dcpl, + hid_t *ex_dcpl, hid_t vspace, char *filename, hsize_t exp_meta_size) +{ + hid_t file = -1; /* File */ + hid_t dset = -1; /* Virtual dataset */ + void *plist_buf = NULL; /* Serialized property list buffer */ + H5O_info_t oinfo; /* Object info struct */ + htri_t tri_ret; + + HDassert((config >= TEST_API_BASIC) && (config < TEST_API_NTESTS)); + HDassert(fapl >= 0); + HDassert(dcpl >= 0); + HDassert(ex_dcpl); + HDassert(*ex_dcpl < 0); + HDassert(vspace >= 0); + HDassert(filename); + + /* Take different action depending on test configuration */ + if(config >= TEST_API_CREATE_DSET) { + /* Create file and dataset */ + if((file = H5Fcreate(filename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + if((dset = H5Dcreate2(file, "vdset", H5T_NATIVE_INT, vspace, H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Reopen dataset if requested */ + if(config >= TEST_API_REOPEN_DSET) { + /* Close dataset */ + if(H5Dclose(dset) < 0) + TEST_ERROR + dset = -1; + + /* Reopen file if requested */ + if(config == TEST_API_REOPEN_FILE) { + if(H5Fclose(file) < 0) + TEST_ERROR + file = -1; + if((file = H5Fopen(filename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Open dataset */ + if((dset = H5Dopen2(file, "vdset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get DCPL from dataset */ + if((*ex_dcpl = H5Dget_create_plist(dset)) < 0) + TEST_ERROR + + /* Test H5Dget_offset() (just returns HADDR_UNDEF) */ + if(HADDR_UNDEF != H5Dget_offset(dset)) + TEST_ERROR + + /* Test H5Oget_info returns correct metadata size */ + if(H5Oget_info(dset, &oinfo) < 0) + TEST_ERROR + if(oinfo.meta_size.obj.index_size != (hsize_t)0) + TEST_ERROR + if(config == TEST_API_REOPEN_FILE) { + if(oinfo.meta_size.obj.heap_size != exp_meta_size) { printf("%llu\n", (long long unsigned)oinfo.meta_size.obj.heap_size); + TEST_ERROR } + } /* end if */ + else + if((oinfo.meta_size.obj.heap_size != exp_meta_size) + && (oinfo.meta_size.obj.heap_size != (hsize_t)0)) + TEST_ERROR + if(oinfo.meta_size.attr.index_size != (hsize_t)0) + TEST_ERROR + if(oinfo.meta_size.attr.index_size != (hsize_t)0) + TEST_ERROR + + /* Close dataset */ + if(H5Dclose(dset) < 0) + TEST_ERROR + dset = -1; + + /* Delete dataset */ + if(H5Ldelete(file, "vdset", H5P_DEFAULT) < 0) + TEST_ERROR + + /* Close file */ + if(H5Fclose(file) < 0) + TEST_ERROR + file = -1; + } /* end if */ + else if(config == TEST_API_COPY_PLIST) { + /* Copy property list */ + if((*ex_dcpl = H5Pcopy(dcpl)) < 0) + TEST_ERROR + } /* end if */ + else if(config == TEST_API_ENCDEC_PLIST) { + size_t plist_buf_size; + + /* Encode property list to plist_buf */ + if(H5Pencode(dcpl, NULL, &plist_buf_size) < 0) + TEST_ERROR + if(NULL == (plist_buf = HDmalloc(plist_buf_size))) + TEST_ERROR + if(H5Pencode(dcpl, plist_buf, &plist_buf_size) < 0) + TEST_ERROR + + /* Decode serialized property list to *ex_dcpl */ + if((*ex_dcpl = H5Pdecode(plist_buf)) < 0) + TEST_ERROR + + /* Free plist_buf */ + HDfree(plist_buf); + plist_buf = NULL; + } /* end if */ + else { + /* Simply copy the id to ex_dcpl and increment the ref count so ex_dcpl + * can be closed */ + if(H5Iinc_ref(dcpl) < 0) + TEST_ERROR + *ex_dcpl = dcpl; + } /* end else */ + + /* Verify examination DCPL is equal to original DCPL. Do not compare the + * plist to itselt, and do not do the comparison if we reopened the file, + * because in that case the extent of the source dset will not be corrent. + */ + if((*ex_dcpl != dcpl) && (config != TEST_API_REOPEN_FILE)) { + if((tri_ret = H5Pequal(dcpl, *ex_dcpl)) < 0) + TEST_ERROR + if(!tri_ret) + TEST_ERROR + } /* end if */ + + return 0; + +error: + H5E_BEGIN_TRY { + if(file >= 0) + (void)H5Fclose(file); + if(dset >= 0) + (void)H5Dclose(dset); + } H5E_END_TRY; + if(plist_buf) + HDfree(plist_buf); + + return -1; +} /* end test_api_get_ex_dcpl() */ + +/* Main test function */ +static int +test_api(test_api_config_t config, hid_t fapl) +{ + char filename[FILENAME_BUF_SIZE]; + hid_t dcpl = -1; /* Dataset creation property list */ + hid_t ex_dcpl = -1; /* Temporary dcpl for examination */ + hid_t srcspace[4] = {-1, -1, -1, -1}; /* Source dataspaces */ + hid_t vspace[LIST_DOUBLE_SIZE]; /* Virtual dset dataspaces */ + const char *src_file[4] = {"src_file1", "src_file2.", "src_file3..", "src_file4..."}; /* Source file names (different lengths) */ + const char *src_dset[4] = {"src_dset1....", "src_dset2.....", "src_dset3......", "src_dset4......."}; /* Source dataset names (different lengths) */ + char tmp_filename[32]; + char tmp_dsetname[32]; + hsize_t dims[2] = {10, 20}; /* Data space current size */ + hsize_t start[2]; /* Hyperslab start */ + hsize_t stride[2]; /* Hyperslab stride */ + hsize_t count[2]; /* Hyperslab count */ + hsize_t block[2]; /* Hyperslab block */ + hsize_t coord[10]; /* Point selection array */ + size_t size_out; + herr_t ret; + unsigned i; + + /* Initialize vspace */ + for(i = 0; i < (unsigned)(sizeof(vspace) / sizeof(vspace[0])); i++) + vspace[i] = -1; + + switch(config) { + case TEST_API_BASIC: + TESTING("virtual dataset API functions") + break; + case TEST_API_COPY_PLIST: + TESTING("virtual dataset API functions with copied plists") + break; + case TEST_API_ENCDEC_PLIST: + TESTING("virtual dataset API functions with encoded and decoded plists") + break; + case TEST_API_CREATE_DSET: + TESTING("virtual dataset create") + break; + case TEST_API_REOPEN_DSET: + TESTING("virtual dataset create with reopened dataset") + break; + case TEST_API_REOPEN_FILE: + TESTING("virtual dataset create with reopened file") + break; + case TEST_API_NTESTS: + default: + TEST_ERROR + } /* end switch */ + + h5_fixname(FILENAME[0], fapl, filename, sizeof filename); + + /* Create DCPL */ + if((dcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + + + /* + * Test 1: All - all selection + */ + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all (should not be necessary, but just to be sure) */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + if(H5Sselect_all(vspace[0]) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], src_file[0], src_dset[0], srcspace[0]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)68) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)1) + TEST_ERROR + + /* Check that the mapping in the DCPL is correct */ + if(vds_check_mapping(ex_dcpl, (size_t)0, vspace[0], srcspace[0], src_file[0], src_dset[0]) < 0) + TEST_ERROR + + /* Close */ + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + + /* + * Test 2: Hyper - hyper selection + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select regular hyperslab in source space */ + start[0] = 2; + start[1] = 1; + stride[0] = 3; + stride[1] = 5; + count[0] = 2; + count[1] = 3; + block[0] = 2; + block[1] = 4; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Select composite hyperslab in virtual space */ + count[0] = 1; + count[1] = 1; + block[0] = 5; + block[1] = 6; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + start[0] = 7; + start[1] = 0; + block[0] = 1; + block[1] = 18; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_OR, start, NULL, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], src_file[0], src_dset[0], srcspace[0]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)212) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)1) + TEST_ERROR + + /* Check that the mapping in the DCPL is correct */ + if(vds_check_mapping(ex_dcpl, (size_t)0, vspace[0], srcspace[0], src_file[0], src_dset[0]) < 0) + TEST_ERROR + + /* Close */ + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + +#ifdef VDS_POINT_SELECTIONS /* VDS does not currently support point selections */ + /* + * Test 3: Point - point selection + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select points in source space */ + coord[0] = 5; + coord[1] = 15; + coord[2] = 7; + coord[3] = 19; + coord[4] = 8; + coord[5] = 0; + coord[6] = 2; + coord[7] = 14; + coord[8] = 8; + coord[9] = 18; + if(H5Sselect_elements(srcspace[0], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Select points in virtual space */ + coord[0] = 3; + coord[1] = 12; + coord[2] = 7; + coord[3] = 11; + coord[4] = 4; + coord[5] = 9; + coord[6] = 7; + coord[7] = 11; + coord[8] = 5; + coord[9] = 5; + if(H5Sselect_elements(vspace[0], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], src_file[0], src_dset[0], srcspace[0]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)0) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)1) + TEST_ERROR + + /* Check that the mapping in the DCPL is correct */ + if(vds_check_mapping(ex_dcpl, (size_t)0, vspace[0], srcspace[0], src_file[0], src_dset[0]) < 0) + TEST_ERROR + + /* Close */ + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + + /* + * Test 4: Point - hyper selection + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslab in source space */ + start[0] = 2; + start[1] = 7; + count[0] = 1; + count[1] = 1; + block[0] = 1; + block[1] = 5; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + + /* Select points in virtual space */ + coord[0] = 1; + coord[1] = 1; + coord[2] = 4; + coord[3] = 17; + coord[4] = 3; + coord[5] = 9; + coord[6] = 5; + coord[7] = 13; + coord[8] = 7; + coord[9] = 16; + if(H5Sselect_elements(vspace[0], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], src_file[0], src_dset[0], srcspace[0]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)0) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)1) + TEST_ERROR + + /* Check that the mapping in the DCPL is correct */ + if(vds_check_mapping(ex_dcpl, (size_t)0, vspace[0], srcspace[0], src_file[0], src_dset[0]) < 0) + TEST_ERROR + + /* Close */ + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + + /* + * Test 5: All previous mappings together + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create dataspaces */ + for(i = 0; i < 4; i++) { + /* Create source dataspace */ + if((srcspace[i] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[i] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + } /* end for */ + + /* Select all (should not be necessary, but just to be sure) */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + if(H5Sselect_all(vspace[0]) < 0) + TEST_ERROR + + /* Select regular hyperslab in source space */ + start[0] = 2; + start[1] = 1; + stride[0] = 3; + stride[1] = 5; + count[0] = 2; + count[1] = 3; + block[0] = 2; + block[1] = 4; + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Select composite hyperslab in virtual space */ + count[0] = 1; + count[1] = 1; + block[0] = 5; + block[1] = 6; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + start[0] = 7; + start[1] = 0; + block[0] = 1; + block[1] = 18; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, NULL, count, block) < 0) + TEST_ERROR + + /* Select points in source space */ + coord[0] = 5; + coord[1] = 15; + coord[2] = 7; + coord[3] = 19; + coord[4] = 8; + coord[5] = 0; + coord[6] = 2; + coord[7] = 14; + coord[8] = 8; + coord[9] = 18; + if(H5Sselect_elements(srcspace[2], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Select points in virtual space */ + coord[0] = 3; + coord[1] = 12; + coord[2] = 7; + coord[3] = 11; + coord[4] = 4; + coord[5] = 9; + coord[6] = 7; + coord[7] = 11; + coord[8] = 5; + coord[9] = 5; + if(H5Sselect_elements(vspace[2], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Select hyperslab in source space */ + start[0] = 2; + start[1] = 7; + count[0] = 1; + count[1] = 1; + block[0] = 1; + block[1] = 5; + if(H5Sselect_hyperslab(srcspace[3], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + + /* Select points in virtual space */ + coord[0] = 1; + coord[1] = 1; + coord[2] = 4; + coord[3] = 17; + coord[4] = 3; + coord[5] = 9; + coord[6] = 5; + coord[7] = 13; + coord[8] = 7; + coord[9] = 16; + if(H5Sselect_elements(vspace[3], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + for(i = 0; i < 4; i++) + if(H5Pset_virtual(dcpl, vspace[i], src_file[i], src_dset[i], srcspace[i]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)0) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)4) + TEST_ERROR + + /* Check that the mappings in the DCPL are correct */ + for(i = 0; i < 4; i++) + if(vds_check_mapping(ex_dcpl, (size_t)i, vspace[i], srcspace[i], src_file[i], src_dset[i]) < 0) + TEST_ERROR + + /* Close */ + for(i = 0; i < 4; i++) { + if(H5Sclose(srcspace[i]) < 0) + TEST_ERROR + srcspace[i] = -1; + if(H5Sclose(vspace[i]) < 0) + TEST_ERROR + vspace[i] = -1; + } /* end for */ + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + +#else /* VDS_POINT_SELECTIONS */ + + /* + * Test 3: Verify point selections fail + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select points in source space */ + coord[0] = 5; + coord[1] = 15; + coord[2] = 7; + coord[3] = 19; + coord[4] = 8; + coord[5] = 0; + coord[6] = 2; + coord[7] = 14; + coord[8] = 8; + coord[9] = 18; + if(H5Sselect_elements(srcspace[0], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Select points in virtual space */ + coord[0] = 3; + coord[1] = 12; + coord[2] = 7; + coord[3] = 11; + coord[4] = 4; + coord[5] = 9; + coord[6] = 7; + coord[7] = 11; + coord[8] = 5; + coord[9] = 5; + if(H5Sselect_elements(vspace[0], H5S_SELECT_SET, (size_t)5, coord) < 0) + TEST_ERROR + + /* Attempt to add virtual layout mapping */ + H5E_BEGIN_TRY { + ret = H5Pset_virtual(dcpl, vspace[0], src_file[0], src_dset[0], srcspace[0]); + } H5E_END_TRY + if(ret >= 0) + TEST_ERROR +#endif /* VDS_POINT_SELECTIONS */ + + + /* + * Test 6: Enough Selections to trigger doubling of mapping list + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[0] = 1; + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all in source space (should not be necessary, but just to be sure) */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + + /* Init virtual space extent */ + dims[0] = LIST_DOUBLE_SIZE; + + /* Init hyperslab values */ + start[0] = 0; + start[1] = 0; + count[0] = 1; + count[1] = 1; + block[0] = 1; + block[1] = 20; + + /* Build virtual layout */ + for(i = 0; i < LIST_DOUBLE_SIZE; i++) { + /* Create virtual dataspace */ + if((vspace[i] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select row in virual dataspace */ + start[0] = (hsize_t)i; + if(H5Sselect_hyperslab(vspace[i], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + + /* Create file and dataset names */ + (void)HDsnprintf(tmp_filename, sizeof(tmp_filename), "src_file%u", i); + tmp_filename[sizeof(tmp_filename) - 1] = '\0'; + (void)HDsnprintf(tmp_dsetname, sizeof(tmp_dsetname), "src_dset%u", i); + tmp_dsetname[sizeof(tmp_dsetname) - 1] = '\0'; + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[i], tmp_filename, tmp_dsetname, srcspace[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)696) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)LIST_DOUBLE_SIZE) + TEST_ERROR + + /* Verify virtual layout */ + for(i = 0; i < LIST_DOUBLE_SIZE; i++) { + /* Generate source file name */ + (void)HDsnprintf(tmp_filename, sizeof(tmp_filename), "src_file%u", i); + tmp_filename[sizeof(tmp_filename) - 1] = '\0'; + + /* Generate source dset name */ + (void)HDsnprintf(tmp_dsetname, sizeof(tmp_dsetname), "src_dset%u", i); + tmp_dsetname[sizeof(tmp_dsetname) - 1] = '\0'; + + /* Check that the mapping in the DCPL is correct */ + if(vds_check_mapping(ex_dcpl, (size_t)i, vspace[i], srcspace[0], tmp_filename, tmp_dsetname) < 0) + TEST_ERROR + } /* end if */ + + /* Close */ + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + for(i = 0; i < LIST_DOUBLE_SIZE; i++) { + if(H5Sclose(vspace[i]) < 0) + TEST_ERROR + vspace[i] = -1; + } /* end for */ + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + + /* + * Test 7: Empty VDS + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all (should not be necessary, but just to be sure) */ + if(H5Sselect_all(vspace[0]) < 0) + TEST_ERROR + + /* Get examination DCPL */ + if(test_api_get_ex_dcpl(config, fapl, dcpl, &ex_dcpl, vspace[0], filename, (hsize_t)0) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_count */ + if(H5Pget_virtual_count(ex_dcpl, &size_out) < 0) + TEST_ERROR + if(size_out != (size_t)0) + TEST_ERROR + + /* Close */ + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Pclose(ex_dcpl) < 0) + TEST_ERROR + ex_dcpl = -1; + + + /* Close */ + if(H5Pclose(dcpl) < 0) + TEST_ERROR + dcpl = -1; + + PASSED(); + return 0; + +error: + H5E_BEGIN_TRY { + for(i = 0; i < (sizeof(srcspace) / sizeof(srcspace[0])); i++) { + if(srcspace[i] >= 0) + (void)H5Sclose(srcspace[i]); + } /* end for */ + for(i = 0; i < (sizeof(vspace) / sizeof(vspace[0])); i++) { + if(vspace[i] >= 0) + (void)H5Sclose(vspace[i]); + } /* end for */ + if(dcpl >= 0) + (void)H5Pclose(dcpl); + if(ex_dcpl >= 0) + (void)H5Pclose(ex_dcpl); + } H5E_END_TRY; + + return 1; +} /* end test_api() */ + + +/*------------------------------------------------------------------------- + * Function: test_basic_io + * + * Purpose: Tests VDS I/O without unlimited selections or + * pattern-matching file/dataset strings + * + * Return: Success: 0 + * + * Failure: number of errors + * + * Programmer: Neil Fortner + * Tuesday, March 3, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static int +test_basic_io(unsigned config, hid_t fapl) +{ + char srcfilename[FILENAME_BUF_SIZE]; + char srcfilename_map[FILENAME_BUF_SIZE]; + char vfilename[FILENAME_BUF_SIZE]; + char vfilename2[FILENAME_BUF_SIZE]; + char srcfilenamepct[FILENAME_BUF_SIZE]; + char srcfilenamepct_map[FILENAME_BUF_SIZE]; + const char *srcfilenamepct_map_orig = "vds%%_src"; + hid_t srcfile[4] = {-1, -1, -1, -1}; /* Files with source dsets */ + hid_t vfile = -1; /* File with virtual dset */ + hid_t vfile2 = -1; /* File with copied virtual dset */ + hid_t dcpl = -1; /* Dataset creation property list */ + hid_t srcspace[4] = {-1, -1, -1, -1}; /* Source dataspaces */ + hid_t vspace[4] = {-1, -1, -1, -1}; /* Virtual dset dataspaces */ + hid_t memspace = -1; /* Memory dataspace */ + hid_t srcdset[4] = {-1, -1, -1, -1}; /* Source datsets */ + hid_t vdset = -1; /* Virtual dataset */ + hsize_t dims[4] = {10, 26, 0, 0}; /* Data space current size */ + hsize_t start[4]; /* Hyperslab start */ + hsize_t stride[4]; /* Hyperslab stride */ + hsize_t count[4]; /* Hyperslab count */ + hsize_t block[4]; /* Hyperslab block */ + hssize_t offset[2] = {0, 0}; /* Selection offset */ + int buf[10][26]; /* Write and expected read buffer */ + int rbuf[10][26]; /* Read buffer */ + int rbuf99[9][9]; /* 9x9 Read buffer */ + int evbuf[10][26]; /* Expected VDS "buffer" */ + int erbuf[10][26]; /* Expected read buffer */ + int fill = -1; /* Fill value */ + herr_t ret; /* Generic return value */ + int i, j; + + TESTING("basic virtual dataset I/O") + + h5_fixname(FILENAME[0], fapl, vfilename, sizeof vfilename); + h5_fixname(FILENAME[1], fapl, vfilename2, sizeof vfilename2); + h5_fixname(FILENAME[2], fapl, srcfilename, sizeof srcfilename); + h5_fixname_printf(FILENAME[2], fapl, srcfilename_map, sizeof srcfilename_map); + h5_fixname(FILENAME[4], fapl, srcfilenamepct, sizeof srcfilenamepct); + h5_fixname_printf(srcfilenamepct_map_orig, fapl, srcfilenamepct_map, sizeof srcfilenamepct_map); + + /* Create DCPL */ + if((dcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + + /* Set fill value */ + if(H5Pset_fill_value(dcpl, H5T_NATIVE_INT, &fill) < 0) + TEST_ERROR + + /* + * Test 1: All - all selection + */ + /* Create source dataspace */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all (should not be necessary, but just to be sure) */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + if(H5Sselect_all(vspace[0]) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset", srcspace[0]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source dataset */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdset and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Reopen srcdset and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(srcdset[0], H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* + * Test 2: 2 Source datasets, hyperslab virtual mappings, '%' in source + * dataset name, also test H5Ocopy() + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 13; + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all in source space (should not be necessary, but just to be sure) + */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + start[1] = 13; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "%%src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2%%", srcspace[0]) < 0) + TEST_ERROR + + /* Reset dims */ + dims[1] = 26; + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "%src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2%", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source datasets */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "%src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2%", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source datasets */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + if(H5Dread(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Test H5Ocopy() to same file */ + /* Copy virtual dataset */ + if(H5Ocopy(vfile, "v_dset", vfile, "v_dset2", H5P_DEFAULT, H5P_DEFAULT) < 0) + TEST_ERROR + + /* Close v_dset */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data directly to source datasets */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Open v_dset2 */ + if((vdset = H5Dopen2(vfile, "v_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Read data through copied virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "%src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2%", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Only copy to a different file if the source datasets are in a different + * file */ + if(config & TEST_IO_DIFFERENT_FILE) { + /* Close v_dset2 */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + + /* Create file to copy virtual dataset to */ + if((vfile2 = H5Fcreate(vfilename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Copy virtual dataset */ + if(H5Ocopy(vfile, "v_dset", vfile2, "v_dset3", H5P_DEFAULT, H5P_DEFAULT) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data directly to source datasets */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen copied virtual file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile2) < 0) + TEST_ERROR + vfile2 = -1; + if((vfile2 = H5Fopen(vfilename2, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Open v_dset3 */ + if((vdset = H5Dopen2(vfile2, "v_dset3", H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Read data through copied virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "%src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2%", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Close copied virtual file */ + if(H5Fclose(vfile2) < 0) + TEST_ERROR + vfile2 = -1; + } /* end if */ + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 3: 2 Source datasets, hyperslab virtual mappings with offsets + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 13; + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all in source space (should not be necessary, but just to be sure) + */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + start[0] = 0; + start[1] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + offset[1] = -3; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "%%src_dset1", srcspace[0]) < 0) + TEST_ERROR + offset[1] = 10; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2%%", srcspace[0]) < 0) + TEST_ERROR + + /* Reset dims */ + dims[1] = 26; + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "%src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2%", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source datasets */ + offset[1] = -3; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + offset[1] = 10; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "%src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2%", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source datasets */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + offset[1] = -3; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Dread(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + offset[1] = 10; + if(H5Soffset_simple(vspace[0], offset) < 0) + TEST_ERROR + if(H5Dread(srcdset[1], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* + * Test 4: 2 Source datasets, hyperslab virtual mappings on one mapping at a + * time, '%' in source file name + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 13; + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select all in source space (should not be necessary, but just to be sure) + */ + if(H5Sselect_all(srcspace[0]) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + start[1] = 13; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilenamepct_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilenamepct_map : ".", "src_dset2", srcspace[0]) < 0) + TEST_ERROR + + /* Reset dims */ + dims[1] = 26; + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilenamepct, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source datasets */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read first source dataset through virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, vspace[0], vspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != (j < (int)(sizeof(buf[0]) / sizeof(buf[0][0]) / 2) + ? buf[i][j] : 0)) + TEST_ERROR + + /* Read second source dataset through virtual dataset */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(vdset, H5T_NATIVE_INT, vspace[1], vspace[1], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != (j < (int)(sizeof(buf[0]) / sizeof(buf[0][0]) / 2) + ? 0 : buf[i][j])) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write first source dataset through virtual dataset */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, vspace[0], vspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write second source dataset through virtual dataset */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, vspace[1], vspace[1], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilenamepct, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source datasets */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + if(H5Dread(srcdset[0], H5T_NATIVE_INT, vspace[0], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + if(H5Dread(srcdset[1], H5T_NATIVE_INT, vspace[1], H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != (j < (int)(sizeof(buf[0]) / sizeof(buf[0][0]) / 2) + ? (buf[i][j] - (int)(sizeof(buf) / sizeof(buf[0][0]))) + : buf[i][j])) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 5: 2 Source datasets, hyperslab virtual mappings and selections + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspaces */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((srcspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in source space */ + start[0] = 0; + start[1] = 0; + count[0] = 10; + count[1] = 13; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 13; + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + start[0] = 0; + start[1] = 0; + count[0] = 5; + count[1] = 26; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[0] = 5; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[1]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[1], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source datasets */ + /* Write first dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update evbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + evbuf[i][j] = buf[2 * i][j]; + for(/* j = 13 */; j < 26; j++) + evbuf[i][j] = buf[2 * i + 1][j - 13]; + } /* end for */ + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, H5S_ALL, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update evbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + evbuf[i + 5][j] = buf[2 * i][j + 13]; + for(/* j = 13 */; j < 26; j++) + evbuf[i + 5][j] = buf[2 * i + 1][j]; + } /* end for */ + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset by hyperslab */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read first slice */ + if(H5Dread(vdset, H5T_NATIVE_INT, vspace[0], srcspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + erbuf[i][j] = evbuf[2 * i][j]; + for(/* j = 13 */; j < 26; j++) + erbuf[i][j] = evbuf[2 * i + 1][j - 13]; + } /* end for */ + + /* Read second slice */ + if(H5Dread(vdset, H5T_NATIVE_INT, vspace[1], srcspace[1], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + erbuf[i + 5][j] = evbuf[2 * i][j + 13]; + for(/* j = 13 */; j < 26; j++) + erbuf[i + 5][j] = evbuf[2 * i + 1][j]; + } /* end for */ + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset */ + /* Write first slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, vspace[0], srcspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update evbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + evbuf[2 * i][j] = buf[i][j]; + for(/* j = 13 */; j < 26; j++) + evbuf[2 * i + 1][j - 13] = buf[i][j]; + } /* end for */ + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write second slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, vspace[1], srcspace[1], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update evbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + evbuf[2 * i][j + 13] = buf[i + 5][j]; + for(/* j = 13 */; j < 26; j++) + evbuf[2 * i + 1][j] = buf[i + 5][j]; + } /* end for */ + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source datasets */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read first dataset */ + if(H5Dread(srcdset[0], H5T_NATIVE_INT, srcspace[0], srcspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + erbuf[2 * i][j] = evbuf[i][j]; + for(/* j = 13 */; j < 26; j++) + erbuf[2 * i + 1][j - 13] = evbuf[i][j]; + } /* end for */ + + /* Read second dataset */ + if(H5Dread(srcdset[1], H5T_NATIVE_INT, srcspace[1], srcspace[1], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) { + for(j = 0; j < 13; j++) + erbuf[2 * i][j + 13] = evbuf[i + 5][j]; + for(/* j = 13 */; j < 26; j++) + erbuf[2 * i + 1][j] = evbuf[i + 5][j]; + } /* end for */ + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(srcspace[1]) < 0) + TEST_ERROR + srcspace[1] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 6: 2 Source datasets, checkerboard/stripe pattern to trigger + * sequence list refresh internally + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create memory dataspace */ + if((memspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[1] = 52; + if((vspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspace and file space for second operation (srcspace[1]) + */ + if((srcspace[0] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + if((srcspace[1] = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Reset dims */ + dims[1] = 26; + + /* Select hyperslabs (stripe) in source space and file space for second + * operation (srcspace[1]) */ + start[0] = 0; + start[1] = 0; + stride[0] = 1; + stride[1] = 2; + count[0] = 1; + count[1] = 26; + block[0] = 10; + block[1] = 1; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 1; + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Select hyperslabs (checkerboard) in virtual spaces */ + start[0] = 0; + start[1] = 0; + stride[0] = 2; + stride[1] = 2; + count[0] = 5; + count[1] = 26; + block[0] = 1; + block[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 1; + start[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 0; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 1; + start[1] = 0; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[0]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Write data directly to source datasets */ + /* Write first dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i += 2) + for(j = 0; j < 26; j++) + erbuf[i][j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 1; i < 10; i += 2) + for(j = 0; j < 26; j++) + erbuf[i][j] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset by hyperslab */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read first stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Read second stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, srcspace[1], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i += 2) + for(j = 0; j < 26; j++) { + erbuf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + erbuf[i + 1][j] -= (int)(sizeof(buf) / sizeof(buf[0][0])); + } /* end for */ + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset */ + /* Write first slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i += 2) + for(j = 0; j < 26; j++) + erbuf[i][j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write second slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, srcspace[1], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 1; i < 10; i += 2) + for(j = 0; j < 26; j++) + erbuf[i][j] = buf[i][j]; + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source datasets */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read first dataset */ + if(H5Dread(srcdset[0], H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i += 2) + for(j = 0; j < 26; j++) { + erbuf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + erbuf[i + 1][j] -= (int)(sizeof(buf) / sizeof(buf[0][0])); + } /* end for */ + + /* Read second dataset */ + if(H5Dread(srcdset[1], H5T_NATIVE_INT, memspace, srcspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(srcspace[1]) < 0) + TEST_ERROR + srcspace[1] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + if(H5Sclose(memspace) < 0) + TEST_ERROR + memspace = -1; + + + /* + * Test 7: 1 Source dataset, two mappings, 4 dimensional virtual dataset + * and 3 dimensional source dataset + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create memory dataspace */ + if((memspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[0] = 3; + dims[1] = 3; + dims[2] = 3; + dims[3] = 3; + if((vspace[0] = H5Screate_simple(4, dims, NULL)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(4, dims, NULL)) < 0) + TEST_ERROR + + /* Create source dataspaces */ + dims[0] = 2; + dims[1] = 4; + dims[2] = 4; + if((srcspace[0] = H5Screate_simple(3, dims, NULL)) < 0) + TEST_ERROR + if((srcspace[1] = H5Screate_simple(3, dims, NULL)) < 0) + TEST_ERROR + + /* Reset dims */ + dims[0] = 10; + dims[1] = 26; + + /* Select hyperslabs (stripes) in source spaces */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + stride[0] = 1; + stride[1] = 2; + stride[2] = 1; + count[0] = 1; + count[1] = 2; + count[2] = 1; + block[0] = 2; + block[1] = 1; + block[2] = 4; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 1; + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Select hyperslabs (corners) in first virtual space */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + start[3] = 0; + stride[0] = 2; + stride[1] = 2; + stride[2] = 2; + stride[3] = 2; + count[0] = 2; + count[1] = 2; + count[2] = 2; + count[3] = 2; + block[0] = 1; + block[1] = 1; + block[2] = 1; + block[3] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Select hyperslabs ("+" pattern) in second virtual space */ + start[0] = 1; + start[1] = 1; + start[2] = 0; + start[3] = 0; + stride[0] = 2; + stride[1] = 2; + stride[2] = 2; + stride[3] = 2; + count[0] = 1; + count[1] = 1; + count[2] = 2; + count[3] = 2; + block[0] = 1; + block[1] = 1; + block[2] = 1; + block[3] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 0; + start[2] = 1; + count[1] = 2; + count[2] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 0; + start[1] = 1; + count[0] = 2; + count[1] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 1; + count[0] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 0; + start[3] = 1; + count[1] = 2; + count[3] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_OR, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[1]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source dataset */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] = (i * (int)(sizeof(buf[0]) / sizeof(buf[0][0]))) + j; + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + count[0] = 2; + count[1] = 16; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Write data directly to source dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close srcdset and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + count[0] = 9; + count[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Read data through virtual dataset by hyperslab */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select stripe */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + start[3] = 0; + count[0] = 3; + count[1] = 3; + count[2] = 1; + count[3] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Read first stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + HDmemset(erbuf, 0, sizeof(erbuf)); + for(i = 0; i < 9; i++) + for(j = 0; j < 3; j++) + erbuf[i][j] = fill; + erbuf[0][0] = buf[0][0]; + erbuf[0][2] = buf[0][1]; + erbuf[2][0] = buf[0][8]; + erbuf[2][2] = buf[0][9]; + erbuf[6][0] = buf[1][0]; + erbuf[6][2] = buf[1][1]; + erbuf[8][0] = buf[1][8]; + erbuf[8][2] = buf[1][9]; + erbuf[4][0] = buf[0][13]; + erbuf[4][2] = buf[0][14]; + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select stripe */ + start[0] = 0; + start[1] = 0; + start[2] = 1; + start[3] = 0; + count[0] = 3; + count[1] = 3; + count[2] = 1; + count[3] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 3; + count[0] = 9; + count[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Read second stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 9; i++) + for(j = 3; j < 6; j++) + erbuf[i][j] = fill; + erbuf[1][3] = buf[0][4]; + erbuf[1][5] = buf[0][5]; + erbuf[3][3] = buf[0][6]; + erbuf[3][4] = buf[0][7]; + erbuf[3][5] = buf[0][12]; + erbuf[4][3] = buf[0][15]; + erbuf[4][5] = buf[1][4]; + erbuf[5][3] = buf[1][7]; + erbuf[5][4] = buf[1][12]; + erbuf[5][5] = buf[1][13]; + erbuf[7][3] = buf[1][14]; + erbuf[7][5] = buf[1][15]; + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if((j >= 3) && (j < 6)) { + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != 0) + TEST_ERROR + + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select stripe */ + start[0] = 0; + start[1] = 0; + start[2] = 2; + start[3] = 0; + count[0] = 3; + count[1] = 3; + count[2] = 1; + count[3] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 6; + count[0] = 9; + count[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Read third stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 9; i++) + for(j = 6; j < 9; j++) + erbuf[i][j] = fill; + erbuf[0][6] = buf[0][2]; + erbuf[0][8] = buf[0][3]; + erbuf[2][6] = buf[0][10]; + erbuf[2][8] = buf[0][11]; + erbuf[6][6] = buf[1][2]; + erbuf[6][8] = buf[1][3]; + erbuf[8][6] = buf[1][10]; + erbuf[8][8] = buf[1][11]; + erbuf[4][6] = buf[1][5]; + erbuf[4][8] = buf[1][6]; + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if((j >= 6) && (j < 9)) { + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != 0) + TEST_ERROR + + /* Now read entire VDS */ + /* Set memory space extent to 9x9, select all in order to reach part of the + * code in H5S_select_subtract() */ + dims[0] = 9; + dims[1] = 9; + if(H5Sset_extent_simple(memspace, 2, dims, NULL) < 0) + TEST_ERROR + if(H5Sselect_all(memspace) < 0) + TEST_ERROR + + /* Read third stripe pattern */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf99[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(rbuf99) / sizeof(rbuf99[0])); i++) + for(j = 0; j < (int)(sizeof(rbuf99[0]) / sizeof(rbuf99[0][0])); j++) + if(rbuf99[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Write data through virtual dataset by hyperslab */ + /* Select stripe (only select mapped elements) */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + start[3] = 0; + stride[0] = 2; + stride[1] = 2; + stride[2] = 1; + stride[3] = 2; + count[0] = 2; + count[1] = 2; + count[2] = 1; + count[3] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride ,count, NULL) < 0) + TEST_ERROR + start[0] = 1; + start[1] = 1; + start[2] = 0; + start[3] = 0; + stride[0] = 1; + stride[1] = 1; + stride[2] = 1; + stride[3] = 2; + count[0] = 1; + count[1] = 1; + count[2] = 1; + count[3] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_OR, start, stride ,count, NULL) < 0) + TEST_ERROR + + /* Reset extent of memspace, select hyperslab */ + dims[0] = 10; + dims[1] = 26; + if(H5Sset_extent_simple(memspace, 2, dims, NULL) < 0) + TEST_ERROR + start[0] = 0; + start[1] = 0; + count[0] = 1; + count[1] = 10; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Write data through virtual dataset by hyperslab */ + /* Write first stripe pattern */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + HDmemset(erbuf, 0, sizeof(erbuf)); + erbuf[0][0] = buf[0][0]; + erbuf[0][1] = buf[0][1]; + erbuf[0][8] = buf[0][2]; + erbuf[0][9] = buf[0][3]; + erbuf[1][0] = buf[0][6]; + erbuf[1][1] = buf[0][7]; + erbuf[1][8] = buf[0][8]; + erbuf[1][9] = buf[0][9]; + erbuf[0][13] = buf[0][4]; + erbuf[0][14] = buf[0][5]; + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Select stripe (only select mapped elements) */ + start[0] = 0; + start[1] = 1; + start[2] = 1; + start[3] = 0; + stride[0] = 1; + stride[1] = 1; + stride[2] = 1; + stride[3] = 2; + count[0] = 3; + count[1] = 1; + count[2] = 1; + count[3] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride ,count, NULL) < 0) + TEST_ERROR + start[0] = 1; + start[1] = 0; + start[2] = 1; + start[3] = 0; + stride[0] = 1; + stride[1] = 2; + stride[2] = 1; + stride[3] = 1; + count[0] = 1; + count[1] = 2; + count[2] = 1; + count[3] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_OR, start, stride ,count, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + count[0] = 1; + count[1] = 12; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Write second slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + erbuf[0][4] = buf[0][0]; + erbuf[0][5] = buf[0][1]; + erbuf[0][6] = buf[0][2]; + erbuf[0][7] = buf[0][3]; + erbuf[0][12] = buf[0][4]; + erbuf[0][15] = buf[0][5]; + erbuf[1][4] = buf[0][6]; + erbuf[1][7] = buf[0][7]; + erbuf[1][12] = buf[0][8]; + erbuf[1][13] = buf[0][9]; + erbuf[1][14] = buf[0][10]; + erbuf[1][15] = buf[0][11]; + + /* Adjust write buffer */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + buf[i][j] += (int)(sizeof(buf) / sizeof(buf[0][0])); + + /* Select stripe (only select mapped elements) */ + start[0] = 0; + start[1] = 0; + start[2] = 2; + start[3] = 0; + stride[0] = 2; + stride[1] = 2; + stride[2] = 1; + stride[3] = 2; + count[0] = 2; + count[1] = 2; + count[2] = 1; + count[3] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride ,count, NULL) < 0) + TEST_ERROR + start[0] = 1; + start[1] = 1; + start[2] = 2; + start[3] = 0; + stride[0] = 1; + stride[1] = 1; + stride[2] = 1; + stride[3] = 2; + count[0] = 1; + count[1] = 1; + count[2] = 1; + count[3] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_OR, start, stride ,count, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + count[0] = 1; + count[1] = 10; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Write third slice */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, vspace[0], H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + erbuf[0][2] = buf[0][0]; + erbuf[0][3] = buf[0][1]; + erbuf[0][10] = buf[0][2]; + erbuf[0][11] = buf[0][3]; + erbuf[1][2] = buf[0][6]; + erbuf[1][3] = buf[0][7]; + erbuf[1][10] = buf[0][8]; + erbuf[1][11] = buf[0][9]; + erbuf[1][5] = buf[0][4]; + erbuf[1][6] = buf[0][5]; + + /* Reopen srcdset and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDONLY, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read data directly from source dataset */ + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + count[0] = 2; + count[1] = 16; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL ,count, NULL) < 0) + TEST_ERROR + + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read dataset */ + if(H5Dread(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)(sizeof(buf) / sizeof(buf[0])); i++) + for(j = 0; j < (int)(sizeof(buf[0]) / sizeof(buf[0][0])); j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Now try writing to whole VDS (should fail due to unmapped elements) */ + count[0] = 9; + count[1] = 9; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + H5E_BEGIN_TRY { + ret = H5Dwrite(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]); + } H5E_END_TRY + if(ret >= 0) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(srcspace[1]) < 0) + TEST_ERROR + srcspace[1] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + if(H5Sclose(memspace) < 0) + TEST_ERROR + memspace = -1; + + + /* Close */ + if(H5Pclose(dcpl) < 0) + TEST_ERROR + dcpl = -1; + + PASSED(); + return 0; + +error: + H5E_BEGIN_TRY { + for(i = 0; i < (int)(sizeof(srcdset) / sizeof(srcdset[0])); i++) { + if(srcdset[i] >= 0) + (void)H5Dclose(srcdset[i]); + } /* end for */ + if(vdset >= 0) + (void)H5Dclose(vdset); + for(i = 0; i < (int)(sizeof(srcfile) / sizeof(srcfile[0])); i++) { + if(srcfile[i] >= 0) + (void)H5Fclose(srcfile[i]); + } /* end for */ + if(vfile >= 0) + (void)H5Fclose(vfile); + if(vfile2 >= 0) + (void)H5Fclose(vfile2); + for(i = 0; i < (int)(sizeof(srcspace) / sizeof(srcspace[0])); i++) { + if(srcspace[i] >= 0) + (void)H5Sclose(srcspace[i]); + } /* end for */ + for(i = 0; i < (int)(sizeof(vspace) / sizeof(vspace[0])); i++) { + if(vspace[i] >= 0) + (void)H5Sclose(vspace[i]); + } /* end for */ + if(memspace >= 0) + (void)H5Sclose(memspace); + if(dcpl >= 0) + (void)H5Pclose(dcpl); + } H5E_END_TRY; + + return 1; +} /* end test_basic_io() */ + + +/*------------------------------------------------------------------------- + * Function: test_unlim + * + * Purpose: Tests VDS with unlimited selections + * + * Return: Success: 0 + * + * Failure: number of errors + * + * Programmer: Neil Fortner + * Thursday, April 30, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static int +test_unlim(unsigned config, hid_t fapl) +{ + char srcfilename[FILENAME_BUF_SIZE]; + char srcfilename_map[FILENAME_BUF_SIZE]; + char vfilename[FILENAME_BUF_SIZE]; + hid_t srcfile[4] = {-1, -1, -1, -1}; /* Files with source dsets */ + hid_t vfile = -1; /* File with virtual dset */ + hid_t dcpl = -1; /* Dataset creation property list */ + hid_t srcdcpl = -1; /* DCPL for source dset */ + hid_t dapl = -1; /* Dataset access property list */ + hid_t srcspace[4] = {-1, -1, -1, -1}; /* Source dataspaces */ + hid_t vspace[4] = {-1, -1, -1, -1}; /* Virtual dset dataspaces */ + hid_t memspace = -1; /* Memory dataspace */ + hid_t filespace = -1; /* File dataspace */ + hid_t srcdset[4] = {-1, -1, -1, -1}; /* Source datsets */ + hid_t vdset = -1; /* Virtual dataset */ + hsize_t dims[2] = {10, 10}; /* Data space current size */ + hsize_t mdims[2] = {10, 20}; /* Data space maximum size */ + hsize_t cdims[2] = {4, 4}; /* Chunk dimensions */ + hsize_t start[4]; /* Hyperslab start */ + hsize_t stride[4]; /* Hyperslab stride */ + hsize_t count[4]; /* Hyperslab count */ + hsize_t block[4]; /* Hyperslab block */ + int buf[10][20]; /* Write and expected read buffer */ + int rbuf[10][20]; /* Read buffer */ + int erbuf[10][20]; /* Expected read buffer */ + int ndims; /* Number of dimensions */ + int fill = -1; /* Fill value */ + H5D_vds_view_t virtual_view; /* Virtual view property */ + int i, j; + + TESTING("virtual dataset I/O with unlimited selections") + + h5_fixname(FILENAME[0], fapl, vfilename, sizeof vfilename); + h5_fixname(FILENAME[2], fapl, srcfilename, sizeof srcfilename); + h5_fixname_printf(FILENAME[2], fapl, srcfilename_map, sizeof srcfilename_map); + + /* Create DCPLs */ + if((dcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + if((srcdcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + + /* Set fill value */ + if(H5Pset_fill_value(dcpl, H5T_NATIVE_INT, &fill) < 0) + TEST_ERROR + + /* Set chunk dimensions */ + if(H5Pset_chunk(srcdcpl, 2, cdims) < 0) + TEST_ERROR + + /* Create DAPL */ + if((dapl = H5Pcreate(H5P_DATASET_ACCESS)) < 0) + TEST_ERROR + + /* Create memory space */ + if((memspace = H5Screate_simple(2, mdims, NULL)) < 0) + TEST_ERROR + + + /* + * Test 1: 2 Source datasets, single unlimited hyperslab virtual mappings + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[0] = 5; + mdims[0] = 5; + if((srcspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + mdims[0] = 10; + + /* Select hyperslab in source space */ + start[0] = 0; + start[1] = 0; + count[0] = 5; + count[1] = H5S_UNLIMITED; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[0] = 5; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[0]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write data directly to source datasets */ + /* Select hyperslab in memory */ + start[0] = 0; + count[1] = 10; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Write first dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 10; j++) + erbuf[i][j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 10; j++) + erbuf[i + 5][j] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Test H5Pget_virtual_view() */ + if(H5Pget_virtual_view(dapl, &virtual_view) < 0) + TEST_ERROR + if(virtual_view != H5D_VDS_LAST_AVAILABLE) + TEST_ERROR + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_view() */ + if(H5Pget_virtual_view(dapl, &virtual_view) < 0) + TEST_ERROR + if(virtual_view != H5D_VDS_FIRST_MISSING) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[0] */ + dims[0] = 5; + dims[1] = 15; + if(H5Dset_extent(srcdset[0], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[0])) < 0) + TEST_ERROR + start[1] = 10; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Close srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Note that since we are using + * H5D_VDS_FIRST_MISSING and we only extended one source dataset the + * dimensions will not have changed. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Update erbuf to reflect new data that is now visible due to the change to + * H5D_VDS_LAST_AVAILABLE */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 10] = buf[i][j]; + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 15) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[0] = 5; + dims[1] = 20; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 10; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[1])) < 0) + TEST_ERROR + start[1] = 10; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 10; j++) + erbuf[i + 5][j + 10] = buf[i][j]; + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 20) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Now just read middle 2 rows */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + start[0] = 4; + count[0] = 2; + count[1] = 20; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, memspace, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data - algorithmically check for only 2 middle rows being + * read so we don't have to wipe out erbuf and then restore it afterwards */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if((i == 4) || (i == 5)) { + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != 0) + TEST_ERROR + + /* Now test reopening virtual dataset without calling H5Dget_space, if + * REOPEN_VIRT flag set */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Now try setting extent manually */ + /* Shrink to 18 */ + dims[1] = 18; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Shrink to 15 */ + dims[1] = 15; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + } /* end if */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 15) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now test reopening virtual dataset without calling H5Dget_space, if + * REOPEN_VIRT flag set */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now try setting extent manually */ + /* Grow to 18 */ + dims[1] = 18; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Grow to 20 */ + dims[1] = 20; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 2: 2 Source datasets, interleaved slices, single element wide + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[0] = 10; + dims[1] = 10; + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 5; + mdims[1] = 10; + if((srcspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + mdims[1] = 20; + + /* Select hyperslab in source space */ + start[0] = 0; + start[1] = 0; + count[0] = 10; + count[1] = H5S_UNLIMITED; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + stride[0] = 1; + stride[1] = 2; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 0; + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[0]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write data directly to source datasets */ + /* Select hyperslab in memory */ + count[0] = 10; + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Write first dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][2 * j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][(2 * j) + 1] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[0] */ + dims[1] = 7; + if(H5Dset_extent(srcdset[0], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[0])) < 0) + TEST_ERROR + start[1] = 5; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 0; + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf to reflect only new data that is now visible under + * H5D_VDS_FIRST_MISSING (first slice) */ + for(i = 0; i < 10; i++) + erbuf[i][10] = buf[i][0]; + + /* Close srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Note that since we are using + * H5D_VDS_FIRST_MISSING and we only extended one source dataset the + * dimension will only have changed to add one more slice. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 11) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Update erbuf to reflect new data that is now visible due to the change to + * H5D_VDS_LAST_AVAILABLE (second new slice) */ + for(i = 0; i < 10; i++) + erbuf[i][12] = buf[i][1]; + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 13) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[1] = 10; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[1])) < 0) + TEST_ERROR + start[1] = 5; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 0; + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][(2 * j) + 11] = buf[i][j]; + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 20) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Now just read middle 2 rows */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + start[0] = 4; + count[0] = 2; + count[1] = 20; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[0] = 0; + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, memspace, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data - algorithmically check for only 2 middle rows being + * read so we don't have to wipe out erbuf and then restore it afterwards */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if((i == 4) || (i == 5)) { + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != 0) + TEST_ERROR + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Update erbuf to reflect new data that is no longer visible due to the + * change to H5D_VDS_FIRST_MISSING */ + for(i = 0; i < 10; i++) + for(j = 15; j < 20; j += 2) + erbuf[i][j] = fill; + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 14) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 3: 3 Source datasets, interleaved slices, two elements wide + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[0] = 10; + dims[1] = 10; + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[2] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspaces */ + dims[1] = 4; + mdims[1] = 8; + if((srcspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + dims[1] = 4; + mdims[1] = 6; + if((srcspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + dims[1] = 2; + mdims[1] = 6; + if((srcspace[2] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + mdims[1] = 20; + + /* Select hyperslab in source spaces */ + start[0] = 0; + start[1] = 0; + count[0] = 10; + count[1] = H5S_UNLIMITED; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Sselect_hyperslab(srcspace[2], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + stride[0] = 1; + stride[1] = 6; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 2; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 2; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 4; + if(H5Sselect_hyperslab(vspace[2], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 0; + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[1]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[2], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset3", srcspace[2]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[1], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[2] = H5Dcreate2(srcfile[0], "src_dset3", H5T_NATIVE_INT, srcspace[2], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write data directly to source datasets */ + /* Select hyperslab in memory */ + count[0] = 10; + count[1] = 4; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Write first dataset */ + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 2; j++) { + erbuf[i][6 * j] = buf[i][2 * j]; + erbuf[i][(6 * j) + 1] = buf[i][(2 * j) + 1]; + } /* end for */ + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 2; j++) { + erbuf[i][(6 * j) + 2] = buf[i][2 * j]; + erbuf[i][(6 * j) + 3] = buf[i][(2 * j) + 1]; + } /* end for */ + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Select hyperslab in memory */ + count[0] = 10; + count[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Write third dataset */ + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) { + erbuf[i][4] = buf[i][0]; + erbuf[i][5] = buf[i][1]; + } /* end for */ + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[0] */ + dims[1] = 7; + if(H5Dset_extent(srcdset[0], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[0])) < 0) + TEST_ERROR + start[1] = 4; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 0; + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Close srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Note that since we are using + * H5D_VDS_FIRST_MISSING the size will not have changed. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Update erbuf to reflect new data that is now visible due to the change to + * H5D_VDS_LAST_AVAILABLE */ + for(i = 0; i < 10; i++) { + erbuf[i][12] = buf[i][0]; + erbuf[i][13] = buf[i][1]; + erbuf[i][18] = buf[i][2]; + } /* end for */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 19) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[2] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[2] = H5Dopen2(srcfile[0], "src_dset3", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[2] */ + dims[1] = 5; + if(H5Dset_extent(srcdset[2], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[2])) < 0) + TEST_ERROR + start[1] = 2; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 0; + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) { + erbuf[i][10] = buf[i][0]; + erbuf[i][11] = buf[i][1]; + erbuf[i][16] = buf[i][2]; + } /* end for */ + + /* Close srcdset[2] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Note that the dimensions will not have + * changed. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 19) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 14) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[1] = 6; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset */ + count[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[1])) < 0) + TEST_ERROR + start[1] = 4; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[1] = 0; + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) { + erbuf[i][14] = buf[i][0]; + erbuf[i][15] = buf[i][1]; + } /* end for */ + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 17) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 19) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now just read middle 2 rows */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + start[0] = 4; + count[0] = 2; + count[1] = 19; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[0] = 0; + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Verify read data - algorithmically check for only 2 middle rows being + * read */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else if((i == 4) || (i == 5)) { + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != 0) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(srcspace[1]) < 0) + TEST_ERROR + srcspace[1] = -1; + if(H5Sclose(srcspace[2]) < 0) + TEST_ERROR + srcspace[2] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 4: 2 Source datasets, offset starts + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspaces */ + dims[0] = 5; + dims[1] = 0; + mdims[0] = 5; + if((srcspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + dims[1] = 5; + if((srcspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + mdims[0] = 10; + + /* Select hyperslab in source spaces */ + start[0] = 0; + start[1] = 0; + count[0] = 5; + count[1] = H5S_UNLIMITED; + if(H5Sselect_hyperslab(srcspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + start[1] = 10; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + start[0] = 5; + start[1] = 0; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset1", srcspace[0]) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset2", srcspace[1]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace[1], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write data directly to second source dataset */ + /* Select hyperslab in memory */ + start[0] = 0; + start[1] = 0; + count[0] = 5; + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Write second dataset */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i + 5][j] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[0] */ + dims[0] = 5; + dims[1] = 5; + if(H5Dset_extent(srcdset[0], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[0] */ + start[0] = 0; + start[1] = 0; + count[0] = 5; + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 10] = buf[i][j]; + + /* Close srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 15) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace[0]) < 0) + TEST_ERROR + srcspace[0] = -1; + if(H5Sclose(srcspace[1]) < 0) + TEST_ERROR + srcspace[1] = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* Close */ + if(H5Pclose(dcpl) < 0) + TEST_ERROR + dcpl = -1; + if(H5Pclose(srcdcpl) < 0) + TEST_ERROR + dcpl = -1; + if(H5Pclose(dapl) < 0) + TEST_ERROR + dapl = -1; + if(H5Sclose(memspace) < 0) + TEST_ERROR + memspace = -1; + + PASSED(); + return 0; + +error: + H5E_BEGIN_TRY { + for(i = 0; i < (int)(sizeof(srcdset) / sizeof(srcdset[0])); i++) { + if(srcdset[i] >= 0) + (void)H5Dclose(srcdset[i]); + } /* end for */ + if(vdset >= 0) + (void)H5Dclose(vdset); + for(i = 0; i < (int)(sizeof(srcfile) / sizeof(srcfile[0])); i++) { + if(srcfile[i] >= 0) + (void)H5Fclose(srcfile[i]); + } /* end for */ + if(vfile >= 0) + (void)H5Fclose(vfile); + for(i = 0; i < (int)(sizeof(srcspace) / sizeof(srcspace[0])); i++) { + if(srcspace[i] >= 0) + (void)H5Sclose(srcspace[i]); + } /* end for */ + for(i = 0; i < (int)(sizeof(vspace) / sizeof(vspace[0])); i++) { + if(vspace[i] >= 0) + (void)H5Sclose(vspace[i]); + } /* end for */ + if(filespace >= 0) + (void)H5Sclose(filespace); + if(memspace >= 0) + (void)H5Sclose(memspace); + if(dcpl >= 0) + (void)H5Pclose(dcpl); + if(srcdcpl >= 0) + (void)H5Pclose(srcdcpl); + if(dapl >= 0) + (void)H5Pclose(dapl); + } H5E_END_TRY; + + return 1; +} /* end test_unlim() */ + + +/*------------------------------------------------------------------------- + * Function: test_printf + * + * Purpose: Tests VDS with unlimited selections and printf style + * source dataset resolution + * + * Return: Success: 0 + * + * Failure: number of errors + * + * Programmer: Neil Fortner + * Tuesday, May 26, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static int +test_printf(unsigned config, hid_t fapl) +{ + char srcfilename[FILENAME_BUF_SIZE]; + char srcfilename_map[FILENAME_BUF_SIZE]; + char srcfilename2[FILENAME_BUF_SIZE]; + char srcfilename2_map[FILENAME_BUF_SIZE]; + char vfilename[FILENAME_BUF_SIZE]; + char printf_srcfilename_map[FILENAME_BUF_SIZE]; + const char *printf_srcfilename_map_orig = "vds_src_%b"; + char srcfilenamepct[FILENAME_BUF_SIZE]; + char srcfilenamepct_map[FILENAME_BUF_SIZE]; + const char *srcfilenamepct_map_orig = "vds%%_src"; + hid_t srcfile[4] = {-1, -1, -1, -1}; /* Files with source dsets */ + hid_t vfile = -1; /* File with virtual dset */ + hid_t dcpl = -1; /* Dataset creation property list */ + hid_t dapl = -1; /* Dataset access property list */ + hid_t srcspace = -1; /* Source dataspace */ + hid_t vspace[2] = {-1, -1}; /* Virtual dset dataspaces */ + hid_t memspace = -1; /* Memory dataspace */ + hid_t filespace = -1; /* File dataspace */ + hid_t srcdset[6] = {-1, -1, -1, -1, -1, -1}; /* Source datsets */ + hid_t vdset = -1; /* Virtual dataset */ + hsize_t dims[2] = {10, 0}; /* Data space current size */ + hsize_t mdims[2] = {10, 20}; /* Data space maximum size */ + hsize_t start[2] = {0, 0}; /* Hyperslab start */ + hsize_t stride[2]; /* Hyperslab stride */ + hsize_t count[2]; /* Hyperslab count */ + hsize_t block[2]; /* Hyperslab block */ + int buf[10][20]; /* Write and expected read buffer */ + int rbuf[10][20]; /* Read buffer */ + int erbuf[10][20]; /* Expected read buffer */ + int ndims; /* Number of dimensions */ + int fill = -1; /* Fill value */ + hsize_t gap_size; /* Gap size property */ + int i, j; + + TESTING("virtual dataset I/O with printf source") + + h5_fixname(FILENAME[0], fapl, vfilename, sizeof vfilename); + h5_fixname(FILENAME[2], fapl, srcfilename, sizeof srcfilename); + h5_fixname_printf(FILENAME[2], fapl, srcfilename_map, sizeof srcfilename_map); + h5_fixname(FILENAME[3], fapl, srcfilename2, sizeof srcfilename2); + h5_fixname_printf(FILENAME[2], fapl, srcfilename2_map, sizeof srcfilename2_map); + h5_fixname_printf(printf_srcfilename_map_orig, fapl, printf_srcfilename_map, sizeof printf_srcfilename_map); + h5_fixname(FILENAME[4], fapl, srcfilenamepct, sizeof srcfilenamepct); + h5_fixname_printf(srcfilenamepct_map_orig, fapl, srcfilenamepct_map, sizeof srcfilenamepct_map); + + /* Create DCPL */ + if((dcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + + /* Set fill value */ + if(H5Pset_fill_value(dcpl, H5T_NATIVE_INT, &fill) < 0) + TEST_ERROR + + /* Create DAPL */ + if((dapl = H5Pcreate(H5P_DATASET_ACCESS)) < 0) + TEST_ERROR + + /* Create memory space */ + if((memspace = H5Screate_simple(2, mdims, NULL)) < 0) + TEST_ERROR + + + /* + * Test 1: 1 Source dataset mapping, 10x5 blocks + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspace */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 5; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual space */ + stride[0] = 1; + stride[1] = 5; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 5; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset%b", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 2 source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 5] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 3rd source dataset */ + if((srcdset[2] = H5Dcreate2(srcfile[0], "src_dset2", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[2] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 10] = buf[i][j]; + + /* Close srcdset[2] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 15) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now try with different selections */ + count[0] = 10; + for(start[1] = (hsize_t)0; start[1] < (hsize_t)5; start[1]++) + for(count[1] = (hsize_t)1; count[1] < (hsize_t)11; count[1]++) { + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in file space */ + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((j < (int)start[1]) || (j >= (int)(start[1] + count[1]))) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + } /* end for */ + start[1] = 0; + + /* Now try writing through VDS */ + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Select hyperslab in file space */ + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write data through VDS */ + if(H5Dwrite(vdset, H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dopen2(srcfile[0], "src_dset0", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile[0], "src_dset1", H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[2] = H5Dopen2(srcfile[0], "src_dset2", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Read srcdset[0] */ + count[0] = 10; + count[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dread(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + if(rbuf[i][j] != buf[i][j]) + TEST_ERROR + + /* Read srcdset[1] */ + if(H5Dread(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + if(rbuf[i][j] != buf[i][j + 5]) + TEST_ERROR + + /* Read srcdset[2] */ + if(H5Dread(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + if(rbuf[i][j] != buf[i][j + 10]) + TEST_ERROR + + /* Close */ + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* + * Test 2: 1 Source dataset mapping, 10x1 blocks, test printf gap setting, + * '%' in source file name + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 1; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual space */ + stride[0] = 1; + stride[1] = 1; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilenamepct_map : ".", "src_dset%b", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilenamepct, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilenamepct, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create source datasets in a pattern with increasing gaps: + * XX-X--X---X----X */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset1", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[2] = H5Dcreate2(srcfile[0], "src_dset3", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[3] = H5Dcreate2(srcfile[0], "src_dset6", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[4] = H5Dcreate2(srcfile[0], "src_dset10", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[5] = H5Dcreate2(srcfile[0], "src_dset15", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][0] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][1] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[2] */ + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][3] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[3] */ + if(H5Dwrite(srcdset[3], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][6] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[4] */ + if(H5Dwrite(srcdset[4], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][10] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[5] */ + if(H5Dwrite(srcdset[5], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][15] = buf[i][0]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + for(i = 0; i < 6; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 2) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Test H5Pget_virtual_printf_gap() */ + if(H5Pget_virtual_printf_gap(dapl, &gap_size) < 0) + TEST_ERROR + if(gap_size != (hsize_t)0) + TEST_ERROR + + /* Close VDS and reopen with printf gap set to 1, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)1) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Test H5Pget_virtual_printf_gap() */ + if(H5Pget_virtual_printf_gap(dapl, &gap_size) < 0) + TEST_ERROR + if(gap_size != (hsize_t)1) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 4) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with printf gap set to 2, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)2) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 7) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with printf gap set to 3, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)3) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 11) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with printf gap set to 4, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)4) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 16) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 2) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reset dapl */ + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)0) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + for(i = 0; i < 6; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* Next 2 tests are always run with a different source file, so only run if + * that config option is set (so they're not run twice with the same + * configuration) */ + if(config & TEST_IO_DIFFERENT_FILE) { + /* + * Test 3: 1 Source dataset mapping, 10x5 blocks, printf source file + */ + /* Clean up files so the source files do not exist yet */ + h5_cleanup_files(FILENAME, fapl); + + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 5; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual space */ + stride[0] = 1; + stride[1] = 5; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 5; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], printf_srcfilename_map, "src_dset", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Create 2 source files, one source dataset */ + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcfile[1] = H5Fcreate(srcfilename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j] = buf[i][j]; + + /* Close srcdset and srcfiles if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile[1] if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if((srcfile[1] = H5Fopen(srcfilename2, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 2nd source dataset */ + if((srcdset[1] = H5Dcreate2(srcfile[1], "src_dset", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 5] = buf[i][j]; + + /* Close srcdset[1] and srcfile[1] if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* + * Test 4: 1 Source dataset mapping, 10x5 blocks, printf source file and + * source dset, extra %%s in source dataset name + */ + /* Clean up files so the source files do not exist yet */ + h5_cleanup_files(FILENAME, fapl); + + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 5; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual space */ + stride[0] = 1; + stride[1] = 5; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 5; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], printf_srcfilename_map, "%%src%%_dset%%%b", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Create 2 source files, one source dataset */ + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + if((srcdset[0] = H5Dcreate2(srcfile[0], "%src%_dset%0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcfile[1] = H5Fcreate(srcfilename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j] = buf[i][j]; + + /* Close srcdset and srcfiles if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile[1] if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if((srcfile[1] = H5Fopen(srcfilename2, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 2nd source dataset */ + if((srcdset[1] = H5Dcreate2(srcfile[1], "%src%_dset%1", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 5] = buf[i][j]; + + /* Close srcdset[1] and srcfile[1] if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + if(H5Fclose(srcfile[1]) < 0) + TEST_ERROR + srcfile[1] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + } /* end if */ + + + /* + * Test 5: 2 Source mappings, interleaved slices, single element wide, + * hyperslab selection in source, extra %%s in source dataset names + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[0] = 10; + dims[1] = 10; + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace (2 elements wide) */ + dims[1] = 2; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslab in source space */ + count[0] = 10; + count[1] = 1; + if(H5Sselect_hyperslab(srcspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + stride[0] = 1; + stride[1] = 2; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 1; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[1] = 0; + + /* Add virtual layout mappings */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "%bsrc_dset_a%b%%", srcspace) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_b%b%%%%", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 2 source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "0src_dset_a0%", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset_b0%%", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + block[0] = 10; + block[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][0] = buf[i][0]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][1] = buf[i][0]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 2) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 3rd source dataset */ + if((srcdset[2] = H5Dcreate2(srcfile[0], "src_dset_b1%%", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[2] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][3] = buf[i][0]; + + /* Close srcdset[2] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 4) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Make sure that the 4th slice is no longer + * visible due to the change to H5D_VDS_FIRST_MISSING. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 2) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 4th source dataset */ + if((srcdset[3] = H5Dcreate2(srcfile[0], "2src_dset_a2%", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[3] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[3], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][4] = buf[i][0]; + + /* Close srcdset[3] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[3]) < 0) + TEST_ERROR + srcdset[3] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 2) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Make sure that the 4th slice is now visible + * due to the change to H5D_VDS_LAST_AVAILABLE. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 4) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with printf_gap set to 1, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)1) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Make sure that the 6th slice is now visible + * due to the change to printf_gap. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reset dapl */ + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)0) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + for(i = 0; i < 4; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 6: 2 Source mappings, side-by-side, 5x5 and 5x10 blocks + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + dims[0] = 10; + dims[1] = 10; + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace (1 dimensional) */ + dims[0] = 50; + if((srcspace = H5Screate_simple(1, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslab in source space */ + count[0] = 25; + if(H5Sselect_hyperslab(srcspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual spaces */ + stride[0] = 1; + stride[1] = 5; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 5; + block[1] = 5; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 5; + stride[1] = 10; + block[1] = 10; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + start[0] = 0; + + /* Add virtual layout mappings (select ALL in source space for second + * mapping) */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_a%b", srcspace) < 0) + TEST_ERROR + if(H5Sselect_all(srcspace) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_b%b", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 2 source datasets */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset_a0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dcreate2(srcfile[0], "src_dset_b0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + block[0] = 5; + block[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + count[0] = 25; + if(H5Sselect_hyperslab(srcspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, srcspace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i][j] = buf[i][j]; + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + block[1] = 10; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Sselect_all(srcspace) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, srcspace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 10; j++) + erbuf[i + 5][j] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. Make sure that the 4th slice is no longer + * visible due to the change to H5D_VDS_FIRST_MISSING. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 5) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 3rd source dataset */ + if((srcdset[2] = H5Dcreate2(srcfile[0], "src_dset_a1", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[2] */ + block[1] = 5; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Sselect_hyperslab(srcspace, H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, srcspace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 5] = buf[i][j]; + + /* Close srcdset[2] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with view set to H5D_VDS_LAST_AVAILABLE, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions. There should be no change. */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile[0] = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 4th source dataset */ + if((srcdset[3] = H5Dcreate2(srcfile[0], "src_dset_a2", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[3] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[3], H5T_NATIVE_INT, memspace, srcspace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 5; i++) + for(j = 0; j < 5; j++) + erbuf[i][j + 10] = buf[i][j]; + + /* Close srcdset[3] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[3]) < 0) + TEST_ERROR + srcdset[3] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 15) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now test reopening virtual dataset without calling H5Dget_space, if + * REOPEN_VIRT flag set */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now try setting extent manually */ + /* Shrink to 12 */ + dims[1] = 12; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Shrink to 10 */ + dims[1] = 12; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + } /* end if */ + + /* Close VDS and reopen with view set to H5D_VDS_FIRST_MISSING, reopen file + * as well if config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_view(dapl, H5D_VDS_FIRST_MISSING) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now test reopening virtual dataset without calling H5Dget_space, if + * REOPEN_VIRT flag set */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Now try setting extent manually */ + /* Grow to 12 */ + dims[1] = 12; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Grow to 15 */ + dims[1] = 15; + if(H5Dset_extent(vdset, dims) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + } /* end if */ + + /* Reset dapl */ + if(H5Pset_virtual_view(dapl, H5D_VDS_LAST_AVAILABLE) < 0) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + for(i = 0; i < 4; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + if(H5Sclose(vspace[1]) < 0) + TEST_ERROR + vspace[1] = -1; + + + /* + * Test 7: 1 Source dataset mapping, 10x1 blocks, test reallocating sub_dset + * array + */ + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create virtual dataspaces */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + + /* Create source dataspace */ + dims[1] = 1; + if((srcspace = H5Screate_simple(2, dims, NULL)) < 0) + TEST_ERROR + + /* Select hyperslabs in virtual space */ + stride[0] = 1; + stride[1] = 1; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 10; + block[1] = 1; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + + /* Add virtual layout mapping */ + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilenamepct_map : ".", "src_dset%b", srcspace) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile[0] = H5Fcreate(srcfilenamepct, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile[0] = vfile; + if(H5Iinc_ref(srcfile[0]) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, dapl)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 0) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile[0] = H5Fopen(srcfilenamepct, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create 1 source dataset */ + if((srcdset[0] = H5Dcreate2(srcfile[0], "src_dset0", H5T_NATIVE_INT, srcspace, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 10; i++) + erbuf[i][0] = buf[i][0]; + + /* Close srcdset[0] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 1) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Close VDS and reopen with printf gap set to 127, reopen file as well if + * config option specified */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)127) < 0) + TEST_ERROR + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + } /* end if */ + if((vdset = H5Dopen2(vfile, "v_dset", dapl)) < 0) + TEST_ERROR + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 1) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 20) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reset dapl */ + if(H5Pset_virtual_printf_gap(dapl, (hsize_t)0) < 0) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + if(H5Dclose(srcdset[0]) < 0) + TEST_ERROR + srcdset[0] = -1; + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile[0]) < 0) + TEST_ERROR + srcfile[0] = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if(H5Sclose(srcspace) < 0) + TEST_ERROR + srcspace = -1; + if(H5Sclose(vspace[0]) < 0) + TEST_ERROR + vspace[0] = -1; + + + /* Close */ + if(H5Pclose(dcpl) < 0) + TEST_ERROR + dcpl = -1; + if(H5Pclose(dapl) < 0) + TEST_ERROR + dapl = -1; + if(H5Sclose(memspace) < 0) + TEST_ERROR + memspace = -1; + + PASSED(); + return 0; + +error: + H5E_BEGIN_TRY { + for(i = 0; i < (int)(sizeof(srcdset) / sizeof(srcdset[0])); i++) { + if(srcdset[i] >= 0) + (void)H5Dclose(srcdset[i]); + } /* end for */ + if(vdset >= 0) + (void)H5Dclose(vdset); + for(i = 0; i < (int)(sizeof(srcfile) / sizeof(srcfile[0])); i++) { + if(srcfile[i] >= 0) + (void)H5Fclose(srcfile[i]); + } /* end for */ + if(vfile >= 0) + (void)H5Fclose(vfile); + if(srcspace >= 0) + (void)H5Sclose(srcspace); + for(i = 0; i < (int)(sizeof(vspace) / sizeof(vspace[0])); i++) { + if(vspace[i] >= 0) + (void)H5Sclose(vspace[i]); + } /* end for */ + if(filespace >= 0) + (void)H5Sclose(filespace); + if(memspace >= 0) + (void)H5Sclose(memspace); + if(dcpl >= 0) + (void)H5Pclose(dcpl); + if(dapl >= 0) + (void)H5Pclose(dapl); + } H5E_END_TRY; + + return 1; +} /* end test_printf() */ + + +/*------------------------------------------------------------------------- + * Function: test_all + * + * Purpose: Tests fixed, unlimited, and printf selections in the same + * VDS + * + * Return: Success: 0 + * + * Failure: number of errors + * + * Programmer: Neil Fortner + * Friday, August 14, 2015 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static int +test_all(unsigned config, hid_t fapl) +{ + char vfilename[FILENAME_BUF_SIZE]; + char srcfilename[FILENAME_BUF_SIZE]; + char srcfilename_map[FILENAME_BUF_SIZE]; + hid_t srcfile = -1; /* File with source dsets */ + hid_t vfile = -1; /* File with virtual dset */ + hid_t dcpl = -1; /* Dataset creation property list */ + hid_t srcdcpl = -1; /* DCPL for source dset */ + hid_t srcspace[3] = {-1, -1, -1}; /* Source dataspaces */ + hid_t vspace[3] = {-1, -1, -1}; /* Virtual dset dataspaces */ + hid_t memspace = -1; /* Memory dataspace */ + hid_t filespace = -1; /* File dataspace */ + hid_t srcdset[5] = {-1, -1, -1, -1, -1}; /* Source datsets */ + hid_t vdset = -1; /* Virtual dataset */ + hsize_t dims[2] = {6, 6}; /* Data space current size */ + hsize_t mdims[2] = {10, 10}; /* Data space maximum size */ + hsize_t cdims[2] = {2, 2}; /* Chunk dimensions */ + hsize_t start[2]; /* Hyperslab start */ + hsize_t stride[2]; /* Hyperslab stride */ + hsize_t count[2]; /* Hyperslab count */ + hsize_t block[2]; /* Hyperslab block */ + int buf[10][10]; /* Write and expected read buffer */ + int rbuf[10][10]; /* Read buffer */ + int erbuf[10][10]; /* Expected read buffer */ + int ndims; /* Number of dimensions */ + int fill = -1; /* Fill value */ + int i, j; + + TESTING("virtual dataset I/O with mixed selection types") + + h5_fixname(FILENAME[0], fapl, vfilename, sizeof vfilename); + h5_fixname(FILENAME[2], fapl, srcfilename, sizeof srcfilename); + h5_fixname_printf(FILENAME[2], fapl, srcfilename_map, sizeof srcfilename_map); + + /* Create DCPLs */ + if((dcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + if((srcdcpl = H5Pcreate(H5P_DATASET_CREATE)) < 0) + TEST_ERROR + + /* Set fill value */ + if(H5Pset_fill_value(dcpl, H5T_NATIVE_INT, &fill) < 0) + TEST_ERROR + + /* Set chunk dimensions */ + if(H5Pset_chunk(srcdcpl, 2, cdims) < 0) + TEST_ERROR + + /* Create memory space */ + if((memspace = H5Screate_simple(2, mdims, NULL)) < 0) + TEST_ERROR + + /* Clear virtual layout in DCPL */ + if(H5Pset_layout(dcpl, H5D_VIRTUAL) < 0) + TEST_ERROR + + /* Create fixed mapping */ + if((vspace[0] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + start[0] = 3; + start[1] = 3; + count[0] = 3; + count[1] = 3; + if(H5Sselect_hyperslab(vspace[0], H5S_SELECT_SET, start, NULL, count, NULL) < 0) + TEST_ERROR + if((srcspace[0] = H5Screate_simple(2, count, NULL)) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[0], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_fixed", srcspace[0]) < 0) + TEST_ERROR + + /* Create unlimited mapping */ + if((vspace[1] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + start[0] = 3; + start[1] = 0; + count[0] = 1; + count[1] = 1; + block[0] = H5S_UNLIMITED; + block[1] = 3; + if(H5Sselect_hyperslab(vspace[1], H5S_SELECT_SET, start, NULL, count, block) < 0) + TEST_ERROR + dims[0] = 0; + dims[1] = 3; + if((srcspace[1] = H5Screate_simple(2, dims, block)) < 0) + TEST_ERROR + start[0] = 0; + if(H5Sselect_hyperslab(srcspace[1], H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[1], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_unlim", srcspace[1]) < 0) + TEST_ERROR + + /* Create printf mapping */ + if((vspace[2] = H5Screate_simple(2, dims, mdims)) < 0) + TEST_ERROR + start[0] = 0; + start[1] = 2; + stride[0] = 1; + stride[1] = 3; + count[0] = 1; + count[1] = H5S_UNLIMITED; + block[0] = 3; + block[1] = 2; + if(H5Sselect_hyperslab(vspace[2], H5S_SELECT_SET, start, stride, count, block) < 0) + TEST_ERROR + if((srcspace[2] = H5Screate_simple(2, block, NULL)) < 0) + TEST_ERROR + if(H5Pset_virtual(dcpl, vspace[2], config & TEST_IO_DIFFERENT_FILE ? srcfilename_map : ".", "src_dset_printf_%b", srcspace[2]) < 0) + TEST_ERROR + + /* Create virtual file */ + if((vfile = H5Fcreate(vfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + + /* Create source file if requested */ + if(config & TEST_IO_DIFFERENT_FILE) { + if((srcfile = H5Fcreate(srcfilename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) + TEST_ERROR + } /* end if */ + else { + srcfile = vfile; + if(H5Iinc_ref(srcfile) < 0) + TEST_ERROR + } /* end if */ + + /* Create virtual dataset */ + if((vdset = H5Dcreate2(vfile, "v_dset", H5T_NATIVE_INT, vspace[0], H5P_DEFAULT, dcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Close srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 6) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Reopen srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create fixed source dataset */ + if((srcdset[0] = H5Dcreate2(srcfile, "src_dset_fixed", H5T_NATIVE_INT, srcspace[0], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Create unlimited source_dataset */ + if((srcdset[1] = H5Dcreate2(srcfile, "src_dset_unlim", H5T_NATIVE_INT, srcspace[1], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Populate write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] = (i * (int)mdims[1]) + j; + + /* Initialize erbuf */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + erbuf[i][j] = fill; + + /* Write to srcdset[0] */ + start[0] = 0; + start[1] = 0; + block[0] = 3; + block[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[0], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 3; i++) + for(j = 0; j < 3; j++) + erbuf[i + 3][j + 3] = buf[i][j]; + + /* Close srcdsets and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + for(i = 0; i < 2; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 6) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((i >= (int)dims[0]) || (j >= (int)dims[1])) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile, "src_dset_unlim", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[0] = 2; + dims[1] = 3; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[1] */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 2; i++) + for(j = 0; j < 3; j++) + erbuf[i + 3][j] = buf[i][j]; + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 6) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((i >= (int)dims[0]) || (j >= (int)dims[1])) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create first printf source dataset */ + if((srcdset[2] = H5Dcreate2(srcfile, "src_dset_printf_0", H5T_NATIVE_INT, srcspace[2], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[2] */ + start[0] = 0; + start[1] = 0; + block[0] = 3; + block[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[2], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 3; i++) + for(j = 0; j < 2; j++) + erbuf[i][j + 2] = buf[i][j]; + + /* Close srcdset[2] srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[2]) < 0) + TEST_ERROR + srcdset[2] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 6) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((i >= (int)dims[0]) || (j >= (int)dims[1])) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile, "src_dset_unlim", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[0] = 3; + dims[1] = 3; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset[1] */ + start[0] = 0; + start[1] = 0; + block[0] = 1; + block[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[1])) < 0) + TEST_ERROR + start[0] = 2; + start[1] = 0; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 3; i++) + erbuf[5][i] = buf[0][i]; + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 6) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((i >= (int)dims[0]) || (j >= (int)dims[1])) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create second printf source dataset, this time without using srcdcpl */ + if((srcdset[3] = H5Dcreate2(srcfile, "src_dset_printf_1", H5T_NATIVE_INT, srcspace[2], H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[3] */ + start[0] = 0; + start[1] = 0; + block[0] = 3; + block[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[3], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 3; i++) + for(j = 0; j < 2; j++) + erbuf[i][j + 5] = buf[i][j]; + + /* Close srcdset[3] srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[3]) < 0) + TEST_ERROR + srcdset[3] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 6) + TEST_ERROR + if(dims[1] != 7) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if((i >= (int)dims[0]) || (j >= (int)dims[1])) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(config & TEST_IO_DIFFERENT_FILE) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((srcdset[1] = H5Dopen2(srcfile, "src_dset_unlim", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Extend srcdset[1] */ + dims[0] = 7; + dims[1] = 3; + if(H5Dset_extent(srcdset[1], dims) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to new area of srcdset[1] */ + start[0] = 0; + start[1] = 0; + block[0] = 4; + block[1] = 3; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if((filespace = H5Dget_space(srcdset[1])) < 0) + TEST_ERROR + start[0] = 3; + start[1] = 0; + if(H5Sselect_hyperslab(filespace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[1], H5T_NATIVE_INT, memspace, filespace, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 4; i++) + for(j = 0; j < 3; j++) + erbuf[i + 6][j] = buf[i][j]; + + /* Close srcdset[1] and srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[1]) < 0) + TEST_ERROR + srcdset[1] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 7) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) { + if(j >= (int)dims[1]) { + if(rbuf[i][j] != 0) + TEST_ERROR + } /* end if */ + else + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + } /* end for */ + + /* Reopen srcfile if config option specified */ + if((config & TEST_IO_CLOSE_SRC) && (config & TEST_IO_DIFFERENT_FILE)) + if((srcfile = H5Fopen(srcfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + + /* Create third printf source dataset */ + if((srcdset[4] = H5Dcreate2(srcfile, "src_dset_printf_2", H5T_NATIVE_INT, srcspace[2], H5P_DEFAULT, srcdcpl, H5P_DEFAULT)) < 0) + TEST_ERROR + + /* Adjust write buffer */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + buf[i][j] += (int)mdims[0] * (int)mdims[1]; + + /* Write to srcdset[4] */ + start[0] = 0; + start[1] = 0; + block[0] = 3; + block[1] = 2; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, block, NULL) < 0) + TEST_ERROR + if(H5Dwrite(srcdset[4], H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, buf[0]) < 0) + TEST_ERROR + + /* Update erbuf */ + for(i = 0; i < 3; i++) + for(j = 0; j < 2; j++) + erbuf[i][j + 8] = buf[i][j]; + + /* Close srcdset[4] srcfile if config option specified */ + if(config & TEST_IO_CLOSE_SRC) { + if(H5Dclose(srcdset[4]) < 0) + TEST_ERROR + srcdset[4] = -1; + if(config & TEST_IO_DIFFERENT_FILE) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + } /* end if */ + + /* Reopen virtual dataset and file if config option specified */ + if(config & TEST_IO_REOPEN_VIRT) { + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + if((vfile = H5Fopen(vfilename, H5F_ACC_RDWR, fapl)) < 0) + TEST_ERROR + if((vdset = H5Dopen2(vfile, "v_dset", H5P_DEFAULT)) < 0) + TEST_ERROR + } /* end if */ + + /* Get VDS space */ + if((filespace = H5Dget_space(vdset)) < 0) + TEST_ERROR + + /* Get VDS space dimensions */ + if((ndims = H5Sget_simple_extent_ndims(filespace)) < 0) + TEST_ERROR + if(ndims != 2) + TEST_ERROR + if(H5Sget_simple_extent_dims(filespace, dims, mdims) < 0) + TEST_ERROR + if(dims[0] != 10) + TEST_ERROR + if(dims[1] != 10) + TEST_ERROR + if(mdims[0] != 10) + TEST_ERROR + if(mdims[1] != 10) + TEST_ERROR + + /* Close filespace */ + if(H5Sclose(filespace) < 0) + TEST_ERROR + + /* Read data through virtual dataset */ + /* Reset rbuf */ + HDmemset(rbuf[0], 0, sizeof(rbuf)); + + /* Select hyperslab in memory space */ + start[0] = 0; + start[1] = 0; + if(H5Sselect_hyperslab(memspace, H5S_SELECT_SET, start, NULL, dims, NULL) < 0) + TEST_ERROR + + /* Read data */ + if(H5Dread(vdset, H5T_NATIVE_INT, memspace, H5S_ALL, H5P_DEFAULT, rbuf[0]) < 0) + TEST_ERROR + + /* Verify read data */ + for(i = 0; i < (int)mdims[0]; i++) + for(j = 0; j < (int)mdims[1]; j++) + if(rbuf[i][j] != erbuf[i][j]) + TEST_ERROR + + /* Close */ + if(!(config & TEST_IO_CLOSE_SRC)) { + for(i = 0; i < 5; i++) { + if(H5Dclose(srcdset[i]) < 0) + TEST_ERROR + srcdset[i] = -1; + } /* end for */ + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + else if(!(config & TEST_IO_DIFFERENT_FILE)) { + if(H5Fclose(srcfile) < 0) + TEST_ERROR + srcfile = -1; + } /* end if */ + if(H5Dclose(vdset) < 0) + TEST_ERROR + vdset = -1; + if(H5Fclose(vfile) < 0) + TEST_ERROR + vfile = -1; + for(i = 0; i < (int)(sizeof(srcspace) / sizeof(srcspace[0])); i++) { + if(H5Sclose(srcspace[i]) < 0) + TEST_ERROR + srcspace[i] = -1; + } /* end for */ + for(i = 0; i < (int)(sizeof(vspace) / sizeof(vspace[0])); i++) { + if(H5Sclose(vspace[i]) < 0) + TEST_ERROR + vspace[i] = -1; + } /* end for */ + if(H5Pclose(dcpl) < 0) + TEST_ERROR + dcpl = -1; + if(H5Pclose(srcdcpl) < 0) + TEST_ERROR + srcdcpl = -1; + if(H5Sclose(memspace) < 0) + TEST_ERROR + memspace = -1; + + PASSED(); + return 0; + +error: + H5E_BEGIN_TRY { + for(i = 0; i < (int)(sizeof(srcdset) / sizeof(srcdset[0])); i++) { + if(srcdset[i] >= 0) + (void)H5Dclose(srcdset[i]); + } /* end for */ + if(vdset >= 0) + (void)H5Dclose(vdset); + if(srcfile >= 0) + (void)H5Fclose(srcfile); + if(vfile >= 0) + (void)H5Fclose(vfile); + for(i = 0; i < (int)(sizeof(srcspace) / sizeof(srcspace[0])); i++) { + if(srcspace[i] >= 0) + (void)H5Sclose(srcspace[i]); + } /* end for */ + for(i = 0; i < (int)(sizeof(vspace) / sizeof(vspace[0])); i++) { + if(vspace[i] >= 0) + (void)H5Sclose(vspace[i]); + } /* end for */ + if(filespace >= 0) + (void)H5Sclose(filespace); + if(memspace >= 0) + (void)H5Sclose(memspace); + if(dcpl >= 0) + (void)H5Pclose(dcpl); + if(srcdcpl >= 0) + (void)H5Pclose(srcdcpl); + } H5E_END_TRY; + + return 1; +} /* end test_printf() */ + + +/*------------------------------------------------------------------------- + * Function: main + * + * Purpose: Tests datasets with virtual layout + * + * Return: Success: exit(0) + * + * Failure: exit(1) + * + * Programmer: Neil Fortner + * Tuesday, February 17, 2015 + * + *------------------------------------------------------------------------- + */ +int +main(void) +{ + char filename[FILENAME_BUF_SIZE]; + hid_t fapl; + int test_api_config; + unsigned bit_config; + int nerrors = 0; + + /* Testing setup */ + h5_reset(); + fapl = h5_fileaccess(); + + h5_fixname(FILENAME[0], fapl, filename, sizeof filename); + + for(test_api_config = (int)TEST_API_BASIC; test_api_config < (int)TEST_API_NTESTS; test_api_config++) + nerrors += test_api((test_api_config_t)test_api_config, fapl); + for(bit_config = 0; bit_config < TEST_IO_NTESTS; bit_config++) { + printf("Config: %s%s%s\n", bit_config & TEST_IO_CLOSE_SRC ? "closed source dataset, " : "", bit_config & TEST_IO_DIFFERENT_FILE ? "different source file" : "same source file", bit_config & TEST_IO_REOPEN_VIRT ? ", reopen virtual file" : ""); + nerrors += test_basic_io(bit_config, fapl); + nerrors += test_unlim(bit_config, fapl); + nerrors += test_printf(bit_config, fapl); + nerrors += test_all(bit_config, fapl); + } /* end for */ + + /* Verify symbol table messages are cached */ + nerrors += (h5_verify_cached_stabs(FILENAME, fapl) < 0 ? 1 : 0); + + if(nerrors) + goto error; + printf("All virtual dataset tests passed.\n"); +// h5_cleanup(FILENAME, fapl); + + return 0; + +error: + nerrors = MAX(1, nerrors); + printf("***** %d VIRTUAL DATASET TEST%s FAILED! *****\n", + nerrors, 1 == nerrors ? "" : "S"); + return 1; +} /* end main() */ + diff --git a/tools/h5diff/CMakeTests.cmake b/tools/h5diff/CMakeTests.cmake index c650dbe..33d0971 100644 --- a/tools/h5diff/CMakeTests.cmake +++ b/tools/h5diff/CMakeTests.cmake @@ -4,7 +4,7 @@ ### T E S T I N G ### ############################################################################## ############################################################################## - + # -------------------------------------------------------------------- # Copy all the HDF5 files from the test directory into the source directory # -------------------------------------------------------------------- @@ -50,6 +50,30 @@ ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/compounds_array_vlen2.h5 ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/non_comparables1.h5 ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/non_comparables2.h5 + # tools/testfiles/vds + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_d.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_e.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_f.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_d.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_e.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/3_1_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/3_2_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_0.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_1.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_2.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_vds.h5 ) set (LIST_OTHER_TEST_FILES @@ -231,6 +255,9 @@ ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_710.txt ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_80.txt ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_90.txt + ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_v1.txt + ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_v2.txt + ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_v3.txt ) # Make testfiles dir under build dir @@ -283,7 +310,7 @@ ARGS -E copy_if_different ${HDF5_TOOLS_H5DIFF_SOURCE_DIR}/testfiles/h5diff_104w.txt ${PROJECT_BINARY_DIR}/testfiles/h5diff_104.txt ) endif (WIN32) - + ############################################################################## ############################################################################## ### T H E T E S T S M A C R O S ### @@ -399,7 +426,7 @@ ############################################################################## # -------------------------------------------------------------------- - # test file names + # test file names # -------------------------------------------------------------------- set (FILE1 h5diff_basic1.h5) set (FILE2 h5diff_basic2.h5) @@ -425,7 +452,7 @@ set (DANGLE_LINK_FILE2 h5diff_danglelinks2.h5) set (GRP_RECURSE_FILE1 h5diff_grp_recurse1.h5) set (GRP_RECURSE_FILE2 h5diff_grp_recurse2.h5) - # group recursive - same structure via external links through files + # group recursive - same structure via external links through files set (GRP_RECURSE1_EXT h5diff_grp_recurse_ext1.h5) set (GRP_RECURSE2_EXT1 h5diff_grp_recurse_ext2-1.h5) set (GRP_RECURSE2_EXT2 h5diff_grp_recurse_ext2-2.h5) @@ -447,13 +474,20 @@ # attrs with verbose option level set (ATTR_VERBOSE_LEVEL_FILE1 h5diff_attr_v_level1.h5) set (ATTR_VERBOSE_LEVEL_FILE2 h5diff_attr_v_level2.h5) +# VDS tests + set (FILEV1 1_vds.h5) + set (FILEV2 2_vds.h5) + set (FILEV3_1 3_1_vds.h5) + set (FILEV3_2 3_2_vds.h5) + set (FILEV4 4_vds.h5) + set (FILEV5 5_vds.h5) if (HDF5_ENABLE_USING_MEMCHECKER) # Remove any output file left over from previous test run add_test ( NAME H5DIFF-clearall-objects COMMAND ${CMAKE_COMMAND} - -E remove + -E remove h5diff_10.out h5diff_10.out.err h5diff_100.out @@ -800,6 +834,12 @@ h5diff_80.out.err h5diff_90.out h5diff_90.out.err + h5diff_v1.out + h5diff_v1.out.err + h5diff_v2.out + h5diff_v2.out.err + h5diff_v3.out + h5diff_v3.out.err ) set_tests_properties (H5DIFF-clearall-objects PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles") if (NOT "${last_test}" STREQUAL "") @@ -816,13 +856,13 @@ ADD_H5_TEST (h5diff_10 0 -h) # 1.1 normal mode -ADD_H5_TEST (h5diff_11 1 ${FILE1} ${FILE2}) +ADD_H5_TEST (h5diff_11 1 ${FILE1} ${FILE2}) # 1.2 normal mode with objects ADD_H5_TEST (h5diff_12 1 ${FILE1} ${FILE2} g1/dset1 g1/dset2) # 1.3 report mode -ADD_H5_TEST (h5diff_13 1 -r ${FILE1} ${FILE2}) +ADD_H5_TEST (h5diff_13 1 -r ${FILE1} ${FILE2}) # 1.4 report mode with objects ADD_H5_TEST (h5diff_14 1 -r ${FILE1} ${FILE2} g1/dset1 g1/dset2) @@ -840,7 +880,7 @@ ADD_H5_TEST (h5diff_16_2 1 --verbose --relative=0.02 ${FILE1} ${FILE1} g1/dset7 ADD_H5_TEST (h5diff_16_3 1 -v -p 0.02 ${FILE1} ${FILE1} g1/dset9 g1/dset10) # 1.7 verbose mode -ADD_H5_TEST (h5diff_17 1 -v ${FILE1} ${FILE2}) +ADD_H5_TEST (h5diff_17 1 -v ${FILE1} ${FILE2}) # 1.7 test 32-bit INFINITY ADD_H5_TEST (h5diff_171 0 -v ${FILE1} ${FILE1} /g1/fp19 /g1/fp19_COPY) @@ -848,8 +888,8 @@ ADD_H5_TEST (h5diff_171 0 -v ${FILE1} ${FILE1} /g1/fp19 /g1/fp19_COPY) # 1.7 test 64-bit INFINITY ADD_H5_TEST (h5diff_172 0 -v ${FILE1} ${FILE1} /g1/fp20 /g1/fp20_COPY) -# 1.8 quiet mode -ADD_H5_TEST (h5diff_18 1 -q ${FILE1} ${FILE2}) +# 1.8 quiet mode +ADD_H5_TEST (h5diff_18 1 -q ${FILE1} ${FILE2}) # 1.8 -v and -q ADD_H5_TEST (h5diff_18_1 2 -v -q ${FILE1} ${FILE2}) @@ -878,7 +918,7 @@ ADD_H5_TEST (h5diff_23 0 -v ${FILE3} ${FILE3} g1 g1) ADD_H5_TEST (h5diff_24 0 -v ${FILE3} ${FILE3} t1 t1) # 2.5 -ADD_H5_TEST (h5diff_25 0 -v ${FILE3} ${FILE3} l1 l1) +ADD_H5_TEST (h5diff_25 0 -v ${FILE3} ${FILE3} l1 l1) # 2.6 ADD_H5_TEST (h5diff_26 0 -v ${FILE3} ${FILE3} g1 g2) @@ -920,7 +960,7 @@ ADD_H5_TEST (h5diff_57 0 -v ${FILE4} ${FILE4} dset7a dset7b) # 5.8 (region reference) ADD_H5_TEST (h5diff_58 1 -v ${FILE7} ${FILE8} refreg) -# test for both dset and attr with same type but with different size +# test for both dset and attr with same type but with different size # ( HDDFV-7942 ) ADD_H5_TEST (h5diff_59 0 -v ${FILE4} ${FILE4} dset11a dset11b) @@ -929,13 +969,13 @@ ADD_H5_TEST (h5diff_59 0 -v ${FILE4} ${FILE4} dset11a dset11b) # ############################################################################## # 6.0: Check if the command line number of arguments is less than 3 -ADD_H5_TEST (h5diff_600 1 ${FILE1}) +ADD_H5_TEST (h5diff_600 1 ${FILE1}) -# 6.1: Check if non-exist object name is specified +# 6.1: Check if non-exist object name is specified ADD_H5_TEST (h5diff_601 2 ${FILE1} ${FILE1} nono_obj) # ############################################################################## -# # -d +# # -d # ############################################################################## # 6.3: negative value @@ -953,7 +993,7 @@ ADD_H5_TEST (h5diff_606 1 -d 0x1 ${FILE1} ${FILE2} g1/dset3 g1/dset4) # 6.7: string ADD_H5_TEST (h5diff_607 1 -d "1" ${FILE1} ${FILE2} g1/dset3 g1/dset4) -# 6.8: use system epsilon +# 6.8: use system epsilon ADD_H5_TEST (h5diff_608 1 --use-system-epsilon ${FILE1} ${FILE2} g1/dset3 g1/dset4) # 6.9: number larger than biggest difference @@ -1032,12 +1072,12 @@ ADD_H5_TEST (h5diff_631 0 -v --use-system-epsilon ${FILE1} ${FILE1} g1/fp18 g1/f # ############################################################################## # 7. attributes # ############################################################################## -ADD_H5_TEST (h5diff_70 1 -v ${FILE5} ${FILE6}) +ADD_H5_TEST (h5diff_70 1 -v ${FILE5} ${FILE6}) # ################################################## # attrs with verbose option level # ################################################## -ADD_H5_TEST (h5diff_700 1 -v1 ${FILE5} ${FILE6}) +ADD_H5_TEST (h5diff_700 1 -v1 ${FILE5} ${FILE6}) ADD_H5_TEST (h5diff_701 1 -v2 ${FILE5} ${FILE6}) ADD_H5_TEST (h5diff_702 1 --verbose=1 ${FILE5} ${FILE6}) ADD_H5_TEST (h5diff_703 1 --verbose=2 ${FILE5} ${FILE6}) @@ -1054,7 +1094,7 @@ ADD_H5_TEST (h5diff_706 1 -v2 ${ATTR_VERBOSE_LEVEL_FILE1} ${ATTR_VERBOSE_LEVEL_F # different attr number , same attr name (intersected) ADD_H5_TEST (h5diff_707 1 -v2 ${ATTR_VERBOSE_LEVEL_FILE1} ${ATTR_VERBOSE_LEVEL_FILE2} /g2) -# different attr number , all different attr name +# different attr number , all different attr name ADD_H5_TEST (h5diff_708 1 -v2 ${ATTR_VERBOSE_LEVEL_FILE1} ${ATTR_VERBOSE_LEVEL_FILE2} /g3) # when no attributes exist in both objects @@ -1066,31 +1106,31 @@ ADD_H5_TEST (h5diff_710 1 -v2 ${ATTR_VERBOSE_LEVEL_FILE1} ${ATTR_VERBOSE_LEVEL_F # ############################################################################## # 8. all dataset datatypes # ############################################################################## -ADD_H5_TEST (h5diff_80 1 -v ${FILE7} ${FILE8}) +ADD_H5_TEST (h5diff_80 1 -v ${FILE7} ${FILE8}) # 9. compare a file with itself ADD_H5_TEST (h5diff_90 0 -v ${FILE2} ${FILE2}) # 10. read by hyperslab, print indexes -ADD_H5_TEST (h5diff_100 1 -v ${FILE9} ${FILE10}) +ADD_H5_TEST (h5diff_100 1 -v ${FILE9} ${FILE10}) # 11. floating point comparison -ADD_H5_TEST (h5diff_101 1 -v ${FILE1} ${FILE1} g1/d1 g1/d2) +ADD_H5_TEST (h5diff_101 1 -v ${FILE1} ${FILE1} g1/d1 g1/d2) -ADD_H5_TEST (h5diff_102 1 -v ${FILE1} ${FILE1} g1/fp1 g1/fp2) +ADD_H5_TEST (h5diff_102 1 -v ${FILE1} ${FILE1} g1/fp1 g1/fp2) -# with --use-system-epsilon for double value. expect less differences +# with --use-system-epsilon for double value. expect less differences ADD_H5_TEST (h5diff_103 1 -v --use-system-epsilon ${FILE1} ${FILE1} g1/d1 -g1/d2) +g1/d2) # with --use-system-epsilon for float value. expect less differences ADD_H5_TEST (h5diff_104 1 -v --use-system-epsilon ${FILE1} ${FILE1} g1/fp1 g1/fp2) # not comparable -c flag -ADD_H5_TEST (h5diff_200 0 ${FILE2} ${FILE2} g2/dset1 g2/dset2) +ADD_H5_TEST (h5diff_200 0 ${FILE2} ${FILE2} g2/dset1 g2/dset2) -ADD_H5_TEST (h5diff_201 0 -c ${FILE2} ${FILE2} g2/dset1 g2/dset2) +ADD_H5_TEST (h5diff_201 0 -c ${FILE2} ${FILE2} g2/dset1 g2/dset2) ADD_H5_TEST (h5diff_202 0 -c ${FILE2} ${FILE2} g2/dset2 g2/dset3) @@ -1106,9 +1146,9 @@ ADD_H5_TEST (h5diff_206 0 -c ${FILE2} ${FILE2} g2/dset7 g2/dset8) ADD_H5_TEST (h5diff_207 0 -c ${FILE2} ${FILE2} g2/dset8 g2/dset9) # not comparable in dataspace of zero dimension size -ADD_H5_TEST (h5diff_208 0 -c ${FILE19} ${FILE20}) +ADD_H5_TEST (h5diff_208 0 -c ${FILE19} ${FILE20}) -# non-comparable dataset with comparable attribute, and other comparable datasets. +# non-comparable dataset with comparable attribute, and other comparable datasets. # All the rest comparables should display differences. ADD_H5_TEST (h5diff_220 1 -c non_comparables1.h5 non_comparables2.h5 /g1) @@ -1221,28 +1261,28 @@ ADD_H5_TEST (h5diff_425 1 --follow-symlinks -v ${FILE17} ${FILE17} /ext_link_to_ ADD_H5_TEST (h5diff_450 1 --follow-symlinks -v ${DANGLE_LINK_FILE1} ${DANGLE_LINK_FILE2}) # dangling links --follow-symlinks and --no-dangling-links (FILE to FILE) -ADD_H5_TEST (h5diff_451 2 --follow-symlinks -v --no-dangling-links ${DANGLE_LINK_FILE1} ${DANGLE_LINK_FILE2}) +ADD_H5_TEST (h5diff_451 2 --follow-symlinks -v --no-dangling-links ${DANGLE_LINK_FILE1} ${DANGLE_LINK_FILE2}) # try --no-dangling-links without --follow-symlinks options ADD_H5_TEST (h5diff_452 2 --no-dangling-links ${FILE13} ${FILE13}) # dangling link found for soft links (FILE to FILE) -ADD_H5_TEST (h5diff_453 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13}) +ADD_H5_TEST (h5diff_453 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13}) # dangling link found for soft links (obj to obj) -ADD_H5_TEST (h5diff_454 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13} /softlink_dset2 /softlink_noexist) +ADD_H5_TEST (h5diff_454 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13} /softlink_dset2 /softlink_noexist) # dangling link found for soft links (obj to obj) Both dangle links -ADD_H5_TEST (h5diff_455 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13} /softlink_noexist /softlink_noexist) +ADD_H5_TEST (h5diff_455 2 --follow-symlinks -v --no-dangling-links ${FILE13} ${FILE13} /softlink_noexist /softlink_noexist) # dangling link found for ext links (FILE to FILE) -ADD_H5_TEST (h5diff_456 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15}) +ADD_H5_TEST (h5diff_456 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15}) # dangling link found for ext links (obj to obj). target file exist -ADD_H5_TEST (h5diff_457 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15} /ext_link_dset1 /ext_link_noexist1) +ADD_H5_TEST (h5diff_457 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15} /ext_link_dset1 /ext_link_noexist1) # dangling link found for ext links (obj to obj). target file NOT exist -ADD_H5_TEST (h5diff_458 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15} /ext_link_dset1 /ext_link_noexist2) +ADD_H5_TEST (h5diff_458 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15} /ext_link_dset1 /ext_link_noexist2) # dangling link found for ext links (obj to obj). Both dangle links ADD_H5_TEST (h5diff_459 2 --follow-symlinks -v --no-dangling-links ${FILE15} ${FILE15} /ext_link_noexist1 /ext_link_noexist2) @@ -1261,9 +1301,9 @@ ADD_H5_TEST (h5diff_468 0 -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_dan ADD_H5_TEST (h5diff_469 1 -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_link2) #--------------------------------------------------- -# dangling links without follow symlink +# dangling links without follow symlink # (HDFFV-7998) -# test - soft dangle links (same and different paths), +# test - soft dangle links (same and different paths), # - external dangle links (same and different paths) ADD_H5_TEST (h5diff_471 1 -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5) ADD_H5_TEST (h5diff_472 0 -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /soft_link1) @@ -1275,7 +1315,7 @@ ADD_H5_TEST (h5diff_475 1 -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_ # ############################################################################## # # test for group diff recursivly # ############################################################################## -# root +# root ADD_H5_TEST (h5diff_500 1 -v ${GRP_RECURSE_FILE1} ${GRP_RECURSE_FILE2} / /) ADD_H5_TEST (h5diff_501 1 -v --follow-symlinks ${GRP_RECURSE_FILE1} ${GRP_RECURSE_FILE2} / /) @@ -1309,7 +1349,7 @@ ADD_H5_TEST (h5diff_513 1 -v ${GRP_RECURSE_FILE1} ${GRP_RECURSE_FILE2} /slink_gr ADD_H5_TEST (h5diff_514 1 -v --follow-symlinks ${GRP_RECURSE_FILE1} ${GRP_RECURSE_FILE2} /slink_grp10 /slink_grp11) ############################################################################### -# Test for group recursive diff via multi-linked external links +# Test for group recursive diff via multi-linked external links # With follow-symlinks, file $GRP_RECURSE1_EXT and $GRP_RECURSE2_EXT1 should # be same with the external links. ############################################################################### @@ -1332,7 +1372,7 @@ ADD_H5_TEST (h5diff_480 0 -v --exclude-path /group1/dset3 ${EXCLUDE_FILE1_1} ${E ADD_H5_TEST (h5diff_481 1 -v ${EXCLUDE_FILE1_1} ${EXCLUDE_FILE1_2}) # -# Different structure, different names. +# Different structure, different names. # # Exclude all the different objects. Expect return - same ADD_H5_TEST (h5diff_482 0 -v --exclude-path "/group1" --exclude-path "/dset1" ${EXCLUDE_FILE2_1} ${EXCLUDE_FILE2_2}) @@ -1364,10 +1404,10 @@ ADD_H5_TEST (h5diff_530 0 -v ${COMP_VL_STRS_FILE} ${COMP_VL_STRS_FILE} /group / ADD_H5_TEST (h5diff_540 1 -v ${COMPS_ARRAY_VLEN_FILE1} ${COMPS_ARRAY_VLEN_FILE2}) # ############################################################################## -# # Test mutually exclusive options +# # Test mutually exclusive options # ############################################################################## # -# Test with -d , -p and --use-system-epsilon. +# Test with -d , -p and --use-system-epsilon. ADD_H5_TEST (h5diff_640 1 -v -d 5 -p 0.05 --use-system-epsilon ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) ADD_H5_TEST (h5diff_641 1 -v -d 5 -p 0.05 ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) ADD_H5_TEST (h5diff_642 1 -v -p 0.05 -d 5 ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) @@ -1375,3 +1415,9 @@ ADD_H5_TEST (h5diff_643 1 -v -d 5 --use-system-epsilon ${FILE1} ${FILE2} /g1/dse ADD_H5_TEST (h5diff_644 1 -v --use-system-epsilon -d 5 ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) ADD_H5_TEST (h5diff_645 1 -v -p 0.05 --use-system-epsilon ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) ADD_H5_TEST (h5diff_646 1 -v --use-system-epsilon -p 0.05 ${FILE1} ${FILE2} /g1/dset3 /g1/dset4) + +# VDS +ADD_H5_TEST (h5diff_v1 0 -v ${FILEV1} ${FILEV2}) +ADD_H5_TEST (h5diff_v2 0 -r ${FILEV1} ${FILEV2}) +ADD_H5_TEST (h5diff_v3 0 -c ${FILEV1} ${FILEV2}) + diff --git a/tools/h5diff/testfiles/h5diff_v1.txt b/tools/h5diff/testfiles/h5diff_v1.txt new file mode 100644 index 0000000..31a3eae --- /dev/null +++ b/tools/h5diff/testfiles/h5diff_v1.txt @@ -0,0 +1,18 @@ + +file1 file2 +--------------------------------------- + x x / + x x /vds_dset + +group : </> and </> +0 differences found +dataset: </vds_dset> and </vds_dset> +Not comparable: </vds_dset> or </vds_dset> is an empty dataset +Not comparable: </vds_dset> has rank 3, dimensions [5x18x8], max dimensions [18446744073709551615x18x8] +and </vds_dset> has rank 3, dimensions [6x8x14], max dimensions [18446744073709551615x8x14] +0 differences found +-------------------------------- +Some objects are not comparable +-------------------------------- +Use -c for a list of objects without details of differences. +EXIT CODE: 0 diff --git a/tools/h5diff/testfiles/h5diff_v2.txt b/tools/h5diff/testfiles/h5diff_v2.txt new file mode 100644 index 0000000..aa327b1 --- /dev/null +++ b/tools/h5diff/testfiles/h5diff_v2.txt @@ -0,0 +1,7 @@ +dataset: </vds_dset> and </vds_dset> +0 differences found +-------------------------------- +Some objects are not comparable +-------------------------------- +Use -c for a list of objects. +EXIT CODE: 0 diff --git a/tools/h5diff/testfiles/h5diff_v3.txt b/tools/h5diff/testfiles/h5diff_v3.txt new file mode 100644 index 0000000..8c5d2a2 --- /dev/null +++ b/tools/h5diff/testfiles/h5diff_v3.txt @@ -0,0 +1,4 @@ +Not comparable: </vds_dset> or </vds_dset> is an empty dataset +Not comparable: </vds_dset> has rank 3, dimensions [5x18x8], max dimensions [18446744073709551615x18x8] +and </vds_dset> has rank 3, dimensions [6x8x14], max dimensions [18446744073709551615x8x14] +EXIT CODE: 0 diff --git a/tools/h5diff/testh5diff.sh.in b/tools/h5diff/testh5diff.sh.in index 3be0b80..07fa7ba 100644 --- a/tools/h5diff/testh5diff.sh.in +++ b/tools/h5diff/testh5diff.sh.in @@ -120,6 +120,29 @@ $SRC_H5DIFF_TESTFILES/h5diff_attr_v_level2.h5 $SRC_H5DIFF_TESTFILES/h5diff_enum_invalid_values.h5 $SRC_H5DIFF_TESTFILES/non_comparables1.h5 $SRC_H5DIFF_TESTFILES/non_comparables2.h5 +$SRC_TOOLS_TESTFILES/vds/1_a.h5 +$SRC_TOOLS_TESTFILES/vds/1_b.h5 +$SRC_TOOLS_TESTFILES/vds/1_c.h5 +$SRC_TOOLS_TESTFILES/vds/1_d.h5 +$SRC_TOOLS_TESTFILES/vds/1_e.h5 +$SRC_TOOLS_TESTFILES/vds/1_f.h5 +$SRC_TOOLS_TESTFILES/vds/1_vds.h5 +$SRC_TOOLS_TESTFILES/vds/2_a.h5 +$SRC_TOOLS_TESTFILES/vds/2_b.h5 +$SRC_TOOLS_TESTFILES/vds/2_c.h5 +$SRC_TOOLS_TESTFILES/vds/2_d.h5 +$SRC_TOOLS_TESTFILES/vds/2_e.h5 +$SRC_TOOLS_TESTFILES/vds/2_vds.h5 +$SRC_TOOLS_TESTFILES/vds/3_1_vds.h5 +$SRC_TOOLS_TESTFILES/vds/3_2_vds.h5 +$SRC_TOOLS_TESTFILES/vds/4_0.h5 +$SRC_TOOLS_TESTFILES/vds/4_1.h5 +$SRC_TOOLS_TESTFILES/vds/4_2.h5 +$SRC_TOOLS_TESTFILES/vds/4_vds.h5 +$SRC_TOOLS_TESTFILES/vds/5_a.h5 +$SRC_TOOLS_TESTFILES/vds/5_b.h5 +$SRC_TOOLS_TESTFILES/vds/5_c.h5 +$SRC_TOOLS_TESTFILES/vds/5_vds.h5 " LIST_OTHER_TEST_FILES=" @@ -331,10 +354,10 @@ COPY_TESTFILES_TO_TESTDIR() INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then - $CP -f $tstfile $TESTDIR + $CP -f $tstfile $TESTDIR if [ $? -ne 0 ]; then echo "Error: FAILED to copy $tstfile ." - + # Comment out this to CREATE expected file exit $EXIT_FAILURE fi @@ -362,23 +385,23 @@ CLEAN_TESTFILES_AND_TESTDIR() while [ $# -gt 0 ]; do case "$1" in -p) # reset the tool name and bin to run ph5diff tests - TESTNAME=ph5diff - H5DIFF=ph5diff # The tool name - H5DIFF_BIN=`pwd`/$H5DIFF - pmode=yes - shift - ;; + TESTNAME=ph5diff + H5DIFF=ph5diff # The tool name + H5DIFF_BIN=`pwd`/$H5DIFF + pmode=yes + shift + ;; -h) # print help page - echo "$0 [-p] [-h]" - echo " -p run ph5diff tests" - echo " -h print help page" - shift - exit 0 - ;; + echo "$0 [-p] [-h]" + echo " -p run ph5diff tests" + echo " -h print help page" + shift + exit 0 + ;; *) # unknown option echo "$0: Unknown option ($1)" - exit 1 - ;; + exit 1 + ;; esac done @@ -429,11 +452,11 @@ TOOLTEST() { # Run test. TESTING $H5DIFF $@ ( - #echo "#############################" - #echo "Expected output for '$H5DIFF $@'" - #echo "#############################" - cd $TESTDIR - eval $RUNCMD $H5DIFF_BIN "$@" + #echo "#############################" + #echo "Expected output for '$H5DIFF $@'" + #echo "#############################" + cd $TESTDIR + eval $RUNCMD $H5DIFF_BIN "$@" ) >$actual 2>$actual_err EXIT_CODE=$? # save actual and actual_err in case they are needed later. @@ -442,9 +465,9 @@ TOOLTEST() { cp $actual_err $actual_err_sav STDERR_FILTER $actual_err cat $actual_err >> $actual - # don't add exit code check in pmode, as it causes failure. (exit code + # don't add exit code check in pmode, as it causes failure. (exit code # is from mpirun not tool) - # if any problem occurs relate to an exit code, it will be caught in + # if any problem occurs relate to an exit code, it will be caught in # serial mode, so the test is fullfilled. if test $h5haveexitcode = 'yes' -a -z "$pmode"; then echo "EXIT CODE: $EXIT_CODE" >> $actual @@ -462,7 +485,7 @@ TOOLTEST() { nerrors="`expr $nerrors + 1`" test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' else - # parallel mode output are often of different ordering from serial + # parallel mode output are often of different ordering from serial # output. If the sorted expected and actual files compare the same, # it is safe to assume the actual output match the expected file. expect_sorted=expect_sorted @@ -473,44 +496,44 @@ TOOLTEST() { # is done by serial mode. grep -v "EXIT CODE:" $expect_sorted > $expect_sorted.noexit mv $expect_sorted.noexit $expect_sorted - if $CMP $expect_sorted $actual_sorted; then - echo " PASSED" - else - echo "*FAILED*" - nerrors="`expr $nerrors + 1`" - if test yes = "$verbose"; then - echo "====Expected result ($expect_sorted) differs from actual result ($actual_sorted)" - $DIFF $expect_sorted $actual_sorted |sed 's/^/ /' - echo "====The actual output ($actual_sav)" - sed 's/^/ /' < $actual_sav - echo "====The actual stderr ($actual_err_sav)" - sed 's/^/ /' < $actual_err_sav - echo "====End of actual stderr ($actual_err_sav)" - echo "" - fi - fi + if $CMP $expect_sorted $actual_sorted; then + echo " PASSED" + else + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" + if test yes = "$verbose"; then + echo "====Expected result ($expect_sorted) differs from actual result ($actual_sorted)" + $DIFF $expect_sorted $actual_sorted |sed 's/^/ /' + echo "====The actual output ($actual_sav)" + sed 's/^/ /' < $actual_sav + echo "====The actual stderr ($actual_err_sav)" + sed 's/^/ /' < $actual_err_sav + echo "====End of actual stderr ($actual_err_sav)" + echo "" + fi + fi fi # Clean up output file if test -z "$HDF5_NOCLEANUP"; then - rm -f $actual $actual_err $actual_sav $actual_err_sav - rm -f $actual_sorted $expect_sorted + rm -f $actual $actual_err $actual_sav $actual_err_sav + rm -f $actual_sorted $expect_sorted fi } # Print a "SKIP" message SKIP() { - TESTING $H5DIFF $@ - echo " -SKIP-" + TESTING $H5DIFF $@ + echo " -SKIP-" } ############################################################################## -# The tests +# The tests # To avoid the printing of the complete full path of the test file, that hides -# all the other parameters for long paths, the printing of the command line +# all the other parameters for long paths, the printing of the command line # is done first in # TESTING with the name only of the test file $TOOL, not its full path $TESTFILE ############################################################################## @@ -525,13 +548,13 @@ COPY_TESTFILES_TO_TESTDIR TOOLTEST h5diff_10.txt -h # 1.1 normal mode -TOOLTEST h5diff_11.txt h5diff_basic1.h5 h5diff_basic2.h5 +TOOLTEST h5diff_11.txt h5diff_basic1.h5 h5diff_basic2.h5 # 1.2 normal mode with objects TOOLTEST h5diff_12.txt h5diff_basic1.h5 h5diff_basic2.h5 g1/dset1 g1/dset2 # 1.3 report mode -TOOLTEST h5diff_13.txt -r h5diff_basic1.h5 h5diff_basic2.h5 +TOOLTEST h5diff_13.txt -r h5diff_basic1.h5 h5diff_basic2.h5 # 1.4 report mode with objects TOOLTEST h5diff_14.txt -r h5diff_basic1.h5 h5diff_basic2.h5 g1/dset1 g1/dset2 @@ -549,7 +572,7 @@ TOOLTEST h5diff_16_2.txt --verbose --relative=0.02 h5diff_basic1.h5 h5diff_basic TOOLTEST h5diff_16_3.txt -v -p 0.02 h5diff_basic1.h5 h5diff_basic1.h5 g1/dset9 g1/dset10 # 1.7 verbose mode -TOOLTEST h5diff_17.txt -v h5diff_basic1.h5 h5diff_basic2.h5 +TOOLTEST h5diff_17.txt -v h5diff_basic1.h5 h5diff_basic2.h5 # 1.7 test 32-bit INFINITY TOOLTEST h5diff_171.txt -v h5diff_basic1.h5 h5diff_basic1.h5 /g1/fp19 /g1/fp19_COPY @@ -557,8 +580,8 @@ TOOLTEST h5diff_171.txt -v h5diff_basic1.h5 h5diff_basic1.h5 /g1/fp19 /g1/fp19_C # 1.7 test 64-bit INFINITY TOOLTEST h5diff_172.txt -v h5diff_basic1.h5 h5diff_basic1.h5 /g1/fp20 /g1/fp20_COPY -# 1.8 quiet mode -TOOLTEST h5diff_18.txt -q h5diff_basic1.h5 h5diff_basic2.h5 +# 1.8 quiet mode +TOOLTEST h5diff_18.txt -q h5diff_basic1.h5 h5diff_basic2.h5 # 1.8 -v and -q TOOLTEST h5diff_18_1.txt -v -q h5diff_basic1.h5 h5diff_basic2.h5 @@ -588,7 +611,7 @@ TOOLTEST h5diff_23.txt -v h5diff_types.h5 h5diff_types.h5 g1 g1 TOOLTEST h5diff_24.txt -v h5diff_types.h5 h5diff_types.h5 t1 t1 # 2.5 -TOOLTEST h5diff_25.txt -v h5diff_types.h5 h5diff_types.h5 l1 l1 +TOOLTEST h5diff_25.txt -v h5diff_types.h5 h5diff_types.h5 l1 l1 # 2.6 TOOLTEST h5diff_26.txt -v h5diff_types.h5 h5diff_types.h5 g1 g2 @@ -642,7 +665,7 @@ TOOLTEST h5diff_57.txt -v h5diff_dtypes.h5 h5diff_dtypes.h5 dset7a dset7b # 5.8 (region reference) TOOLTEST h5diff_58.txt -v h5diff_dset1.h5 h5diff_dset2.h5 refreg -# test for both dset and attr with same type but with different size +# test for both dset and attr with same type but with different size # ( HDDFV-7942 ) TOOLTEST h5diff_59.txt -v h5diff_dtypes.h5 h5diff_dtypes.h5 dset11a dset11b @@ -652,14 +675,14 @@ TOOLTEST h5diff_59.txt -v h5diff_dtypes.h5 h5diff_dtypes.h5 dset11a dset11b # 6.0: Check if the command line number of arguments is less than 3 -TOOLTEST h5diff_600.txt h5diff_basic1.h5 +TOOLTEST h5diff_600.txt h5diff_basic1.h5 -# 6.1: Check if non-exist object name is specified +# 6.1: Check if non-exist object name is specified TOOLTEST h5diff_601.txt h5diff_basic1.h5 h5diff_basic1.h5 nono_obj # ############################################################################## -# # -d +# # -d # ############################################################################## @@ -678,7 +701,7 @@ TOOLTEST h5diff_606.txt -d 0x1 h5diff_basic1.h5 h5diff_basic2.h5 g1/dset3 g1/dse # 6.7: string TOOLTEST h5diff_607.txt -d "1" h5diff_basic1.h5 h5diff_basic2.h5 g1/dset3 g1/dset4 -# 6.8: use system epsilon +# 6.8: use system epsilon TOOLTEST h5diff_608.txt --use-system-epsilon h5diff_basic1.h5 h5diff_basic2.h5 g1/dset3 g1/dset4 # 6.9: number larger than biggest difference @@ -762,7 +785,7 @@ TOOLTEST h5diff_631.txt -v --use-system-epsilon h5diff_basic1.h5 h5diff_basic1.h # ############################################################################## # 7. attributes # ############################################################################## -TOOLTEST h5diff_70.txt -v h5diff_attr1.h5 h5diff_attr2.h5 +TOOLTEST h5diff_70.txt -v h5diff_attr1.h5 h5diff_attr2.h5 # temporary test to verify HDF5-8625 TOOLTEST h5diff_tmp1.txt tmptest2.he5 tmptest.he5 # temporary test to verify HDF5-8639 @@ -772,10 +795,10 @@ TOOLTEST h5diff_tmp2.txt tmpSingleSiteBethe.output.h5 tmpSingleSiteBethe.referen # attrs with verbose option level # ################################################## -TOOLTEST h5diff_700.txt -v1 h5diff_attr1.h5 h5diff_attr2.h5 -TOOLTEST h5diff_701.txt -v2 h5diff_attr1.h5 h5diff_attr2.h5 -TOOLTEST h5diff_702.txt --verbose=1 h5diff_attr1.h5 h5diff_attr2.h5 -TOOLTEST h5diff_703.txt --verbose=2 h5diff_attr1.h5 h5diff_attr2.h5 +TOOLTEST h5diff_700.txt -v1 h5diff_attr1.h5 h5diff_attr2.h5 +TOOLTEST h5diff_701.txt -v2 h5diff_attr1.h5 h5diff_attr2.h5 +TOOLTEST h5diff_702.txt --verbose=1 h5diff_attr1.h5 h5diff_attr2.h5 +TOOLTEST h5diff_703.txt --verbose=2 h5diff_attr1.h5 h5diff_attr2.h5 # same attr number , all same attr name TOOLTEST h5diff_704.txt -v2 h5diff_attr_v_level1.h5 h5diff_attr_v_level2.h5 /g @@ -789,7 +812,7 @@ TOOLTEST h5diff_706.txt -v2 h5diff_attr_v_level1.h5 h5diff_attr_v_level2.h5 /nty # different attr number , same attr name (intersected) TOOLTEST h5diff_707.txt -v2 h5diff_attr_v_level1.h5 h5diff_attr_v_level2.h5 /g2 -# different attr number , all different attr name +# different attr number , all different attr name TOOLTEST h5diff_708.txt -v2 h5diff_attr_v_level1.h5 h5diff_attr_v_level2.h5 /g3 # when no attributes exist in both objects @@ -801,32 +824,32 @@ TOOLTEST h5diff_710.txt -v2 h5diff_attr_v_level1.h5 h5diff_attr_v_level2.h5 # ############################################################################## # 8. all dataset datatypes # ############################################################################## -TOOLTEST h5diff_80.txt -v h5diff_dset1.h5 h5diff_dset2.h5 +TOOLTEST h5diff_80.txt -v h5diff_dset1.h5 h5diff_dset2.h5 # 9. compare a file with itself TOOLTEST h5diff_90.txt -v h5diff_basic2.h5 h5diff_basic2.h5 # 10. read by hyperslab, print indexes -TOOLTEST h5diff_100.txt -v h5diff_hyper1.h5 h5diff_hyper2.h5 +TOOLTEST h5diff_100.txt -v h5diff_hyper1.h5 h5diff_hyper2.h5 # 11. floating point comparison # double value -TOOLTEST h5diff_101.txt -v h5diff_basic1.h5 h5diff_basic1.h5 g1/d1 g1/d2 +TOOLTEST h5diff_101.txt -v h5diff_basic1.h5 h5diff_basic1.h5 g1/d1 g1/d2 # float value -TOOLTEST h5diff_102.txt -v h5diff_basic1.h5 h5diff_basic1.h5 g1/fp1 g1/fp2 +TOOLTEST h5diff_102.txt -v h5diff_basic1.h5 h5diff_basic1.h5 g1/fp1 g1/fp2 -# with --use-system-epsilon for double value -TOOLTEST h5diff_103.txt -v --use-system-epsilon h5diff_basic1.h5 h5diff_basic1.h5 g1/d1 g1/d2 +# with --use-system-epsilon for double value +TOOLTEST h5diff_103.txt -v --use-system-epsilon h5diff_basic1.h5 h5diff_basic1.h5 g1/d1 g1/d2 # with --use-system-epsilon for float value -TOOLTEST h5diff_104.txt -v --use-system-epsilon h5diff_basic1.h5 h5diff_basic1.h5 g1/fp1 g1/fp2 +TOOLTEST h5diff_104.txt -v --use-system-epsilon h5diff_basic1.h5 h5diff_basic1.h5 g1/fp1 g1/fp2 # not comparable -c flag -TOOLTEST h5diff_200.txt h5diff_basic2.h5 h5diff_basic2.h5 g2/dset1 g2/dset2 +TOOLTEST h5diff_200.txt h5diff_basic2.h5 h5diff_basic2.h5 g2/dset1 g2/dset2 -TOOLTEST h5diff_201.txt -c h5diff_basic2.h5 h5diff_basic2.h5 g2/dset1 g2/dset2 +TOOLTEST h5diff_201.txt -c h5diff_basic2.h5 h5diff_basic2.h5 g2/dset1 g2/dset2 TOOLTEST h5diff_202.txt -c h5diff_basic2.h5 h5diff_basic2.h5 g2/dset2 g2/dset3 @@ -842,9 +865,9 @@ TOOLTEST h5diff_206.txt -c h5diff_basic2.h5 h5diff_basic2.h5 g2/dset7 g2/dset8 TOOLTEST h5diff_207.txt -c h5diff_basic2.h5 h5diff_basic2.h5 g2/dset8 g2/dset9 # not comparable in dataspace of zero dimension size -TOOLTEST h5diff_208.txt -c h5diff_dset_zero_dim_size1.h5 h5diff_dset_zero_dim_size2.h5 +TOOLTEST h5diff_208.txt -c h5diff_dset_zero_dim_size1.h5 h5diff_dset_zero_dim_size2.h5 -# non-comparable dataset with comparable attribute, and other comparable datasets. +# non-comparable dataset with comparable attribute, and other comparable datasets. # Also test non-compatible attributes with different type, dimention, rank. # All the comparables should display differences. TOOLTEST h5diff_220.txt -c non_comparables1.h5 non_comparables2.h5 /g1 @@ -862,7 +885,7 @@ TOOLTEST h5diff_222.txt -c non_comparables1.h5 non_comparables2.h5 TOOLTEST h5diff_223.txt -c non_comparables1.h5 non_comparables2.h5 /diffobjtypes # swap files TOOLTEST h5diff_224.txt -c non_comparables2.h5 non_comparables1.h5 /diffobjtypes - + # ############################################################################## # # Links compare without --follow-symlinks nor --no-dangling-links # ############################################################################## @@ -958,28 +981,28 @@ TOOLTEST h5diff_425.txt --follow-symlinks -v h5diff_ext2softlink_src.h5 h5diff_e TOOLTEST h5diff_450.txt --follow-symlinks -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 # dangling links --follow-symlinks and --no-dangling-links (FILE to FILE) -TOOLTEST h5diff_451.txt --follow-symlinks -v --no-dangling-links h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 +TOOLTEST h5diff_451.txt --follow-symlinks -v --no-dangling-links h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 # try --no-dangling-links without --follow-symlinks options TOOLTEST h5diff_452.txt --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 # dangling link found for soft links (FILE to FILE) -TOOLTEST h5diff_453.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 +TOOLTEST h5diff_453.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 # dangling link found for soft links (obj to obj) -TOOLTEST h5diff_454.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 /softlink_dset2 /softlink_noexist +TOOLTEST h5diff_454.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 /softlink_dset2 /softlink_noexist # dangling link found for soft links (obj to obj) Both dangle links -TOOLTEST h5diff_455.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 /softlink_noexist /softlink_noexist +TOOLTEST h5diff_455.txt --follow-symlinks -v --no-dangling-links h5diff_softlinks.h5 h5diff_softlinks.h5 /softlink_noexist /softlink_noexist # dangling link found for ext links (FILE to FILE) -TOOLTEST h5diff_456.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 +TOOLTEST h5diff_456.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 # dangling link found for ext links (obj to obj). target file exist -TOOLTEST h5diff_457.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 /ext_link_dset1 /ext_link_noexist1 +TOOLTEST h5diff_457.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 /ext_link_dset1 /ext_link_noexist1 # dangling link found for ext links (obj to obj). target file NOT exist -TOOLTEST h5diff_458.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 /ext_link_dset1 /ext_link_noexist2 +TOOLTEST h5diff_458.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 /ext_link_dset1 /ext_link_noexist2 # dangling link found for ext links (obj to obj). Both dangle links TOOLTEST h5diff_459.txt --follow-symlinks -v --no-dangling-links h5diff_extlink_src.h5 h5diff_extlink_src.h5 /ext_link_noexist1 /ext_link_noexist2 @@ -993,14 +1016,14 @@ TOOLTEST h5diff_466.txt -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_dangl # soft link vs. soft dangling TOOLTEST h5diff_467.txt -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /soft_link2 # ext dangling vs. ext dangling -TOOLTEST h5diff_468.txt -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_link4 +TOOLTEST h5diff_468.txt -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_link4 # ext link vs. ext dangling TOOLTEST h5diff_469.txt -v --follow-symlinks h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_link2 #---------------------------------------- -# dangling links without follow symlink +# dangling links without follow symlink # (HDFFV-7998) -# test - soft dangle links (same and different paths), +# test - soft dangle links (same and different paths), # - external dangle links (same and different paths) TOOLTEST h5diff_471.txt -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 TOOLTEST h5diff_472.txt -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /soft_link1 @@ -1011,7 +1034,7 @@ TOOLTEST h5diff_475.txt -v h5diff_danglelinks1.h5 h5diff_danglelinks2.h5 /ext_li # ############################################################################## # # test for group diff recursivly # ############################################################################## -# root +# root TOOLTEST h5diff_500.txt -v h5diff_grp_recurse1.h5 h5diff_grp_recurse2.h5 / / TOOLTEST h5diff_501.txt -v --follow-symlinks h5diff_grp_recurse1.h5 h5diff_grp_recurse2.h5 / / @@ -1045,7 +1068,7 @@ TOOLTEST h5diff_513.txt -v h5diff_grp_recurse1.h5 h5diff_grp_recurse2.h5 /slink_ TOOLTEST h5diff_514.txt -v --follow-symlinks h5diff_grp_recurse1.h5 h5diff_grp_recurse2.h5 /slink_grp10 /slink_grp11 ############################################################################### -# Test for group recursive diff via multi-linked external links +# Test for group recursive diff via multi-linked external links # With follow-symlinks, file h5diff_grp_recurse_ext1.h5 and h5diff_grp_recurse_ext2-1.h5 should # be same with the external links. ############################################################################### @@ -1068,7 +1091,7 @@ TOOLTEST h5diff_480.txt -v --exclude-path /group1/dset3 h5diff_exclude1-1.h5 h5d TOOLTEST h5diff_481.txt -v h5diff_exclude1-1.h5 h5diff_exclude1-2.h5 # -# Different structure, different names. +# Different structure, different names. # # Exclude all the different objects. Expect return - same TOOLTEST h5diff_482.txt -v --exclude-path "/group1" --exclude-path "/dset1" h5diff_exclude2-1.h5 h5diff_exclude2-2.h5 @@ -1099,9 +1122,9 @@ TOOLTEST h5diff_530.txt -v h5diff_comp_vl_strs.h5 h5diff_comp_vl_strs.h5 /group TOOLTEST h5diff_540.txt -v compounds_array_vlen1.h5 compounds_array_vlen2.h5 # ############################################################################## -# # Test mutually exclusive options +# # Test mutually exclusive options # ############################################################################## -# Test with -d , -p and --use-system-epsilon. +# Test with -d , -p and --use-system-epsilon. TOOLTEST h5diff_640.txt -v -d 5 -p 0.05 --use-system-epsilon h5diff_basic1.h5 h5diff_basic2.h5 /g1/dset3 /g1/dset4 TOOLTEST h5diff_641.txt -v -d 5 -p 0.05 h5diff_basic1.h5 h5diff_basic2.h5 /g1/dset3 /g1/dset4 TOOLTEST h5diff_642.txt -v -p 0.05 -d 5 h5diff_basic1.h5 h5diff_basic2.h5 /g1/dset3 /g1/dset4 @@ -1110,6 +1133,13 @@ TOOLTEST h5diff_644.txt -v --use-system-epsilon -d 5 h5diff_basic1.h5 h5diff_bas TOOLTEST h5diff_645.txt -v -p 0.05 --use-system-epsilon h5diff_basic1.h5 h5diff_basic2.h5 /g1/dset3 /g1/dset4 TOOLTEST h5diff_646.txt -v --use-system-epsilon -p 0.05 h5diff_basic1.h5 h5diff_basic2.h5 /g1/dset3 /g1/dset4 +# ############################################################################## +# VDS tests +# ############################################################################## +TOOLTEST h5diff_v1.txt -v 1_vds.h5 2_vds.h5 +TOOLTEST h5diff_v2.txt -r 1_vds.h5 2_vds.h5 +TOOLTEST h5diff_v3.txt -c 1_vds.h5 2_vds.h5 + # ############################################################################## # # END diff --git a/tools/h5dump/CMakeLists.txt b/tools/h5dump/CMakeLists.txt index 47ba7a8..be08e2a 100644 --- a/tools/h5dump/CMakeLists.txt +++ b/tools/h5dump/CMakeLists.txt @@ -39,6 +39,8 @@ if (BUILD_TESTING) include (CMakeTestsPBITS.cmake) + include (CMakeTestsVDS.cmake) + include (CMakeTestsXML.cmake) endif (BUILD_TESTING) diff --git a/tools/h5dump/CMakeTestsVDS.cmake b/tools/h5dump/CMakeTestsVDS.cmake new file mode 100644 index 0000000..58287fa --- /dev/null +++ b/tools/h5dump/CMakeTestsVDS.cmake @@ -0,0 +1,238 @@ + +############################################################################## +############################################################################## +### T E S T I N G ### +############################################################################## +############################################################################## + + # -------------------------------------------------------------------- + # VDS + # -------------------------------------------------------------------- + #-- Copy all the HDF5 files from the test directory into the source directory + set (HDF5_REFERENCE_VDS + tvds-1.ddl + tvds-2.ddl + tvds-3_1.ddl + tvds-3_2.ddl + tvds-4.ddl + tvds-5.ddl + tvds_layout-1.ddl + tvds_layout-2.ddl + tvds_layout-3_1.ddl + tvds_layout-3_2.ddl + tvds_layout-4.ddl + tvds_layout-5.ddl + ) + set (HDF5_REFERENCE_TEST_VDS + 1_a.h5 + 1_b.h5 + 1_c.h5 + 1_d.h5 + 1_e.h5 + 1_f.h5 + 1_vds.h5 + 2_a.h5 + 2_b.h5 + 2_c.h5 + 2_d.h5 + 2_e.h5 + 2_vds.h5 + 3_1_vds.h5 + 3_2_vds.h5 + 4_0.h5 + 4_1.h5 + 4_2.h5 + 4_vds.h5 + 5_a.h5 + 5_b.h5 + 5_c.h5 + 5_vds.h5 + ) + set (HDF5_ERROR_REFERENCE_VDS + ) + + foreach (vds_h5_file ${HDF5_REFERENCE_TEST_VDS}) + GET_FILENAME_COMPONENT(fname "${vds_h5_file}" NAME) + set (dest "${PROJECT_BINARY_DIR}/testfiles/vds/${fname}") + #message (STATUS " Copying ${vds_h5_file}") + add_custom_command ( + TARGET h5dump + POST_BUILD + COMMAND ${CMAKE_COMMAND} + ARGS -E copy_if_different ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/${vds_h5_file} ${dest} + ) + endforeach (vds_h5_file ${HDF5_REFERENCE_TEST_VDS}) + + + foreach (ddl_vds ${HDF5_REFERENCE_VDS}) + GET_FILENAME_COMPONENT(fname "${ddl_vds}" NAME) + set (ddldest "${PROJECT_BINARY_DIR}/testfiles/vds/${fname}") + #message (STATUS " Copying ${ddl_vds}") + add_custom_command ( + TARGET h5dump + POST_BUILD + COMMAND ${CMAKE_COMMAND} + ARGS -E copy_if_different ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/${ddl_vds} ${ddldest} + ) + endforeach (ddl_vds ${HDF5_REFERENCE_VDS}) + + foreach (ddl_vds ${HDF5_ERROR_REFERENCE_VDS}) + GET_FILENAME_COMPONENT(fname "${ddl_vds}" NAME) + set (ddldest "${PROJECT_BINARY_DIR}/testfiles/vds/${fname}") + #message (STATUS " Copying ${ddl_vds}") + add_custom_command ( + TARGET h5dump + POST_BUILD + COMMAND ${CMAKE_COMMAND} + ARGS -E copy_if_different ${PROJECT_SOURCE_DIR}/errfiles/${ddl_vds} ${ddldest} + ) + endforeach (ddl_vds ${HDF5_ERROR_REFERENCE_VDS}) + +############################################################################## +############################################################################## +### T H E T E S T S M A C R O S ### +############################################################################## +############################################################################## + + MACRO (ADD_H5_VDS_TEST resultfile resultcode) + # If using memchecker add tests without using scripts + if (HDF5_ENABLE_USING_MEMCHECKER) + add_test (NAME H5DUMP-${resultfile} COMMAND $<TARGET_FILE:h5dump> ${ARGN}) + set_tests_properties (H5DUMP-${resultfile} PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfilesvds") + if (NOT ${resultcode} STREQUAL "0") + set_tests_properties (H5DUMP-${resultfile} PROPERTIES WILL_FAIL "true") + endif (NOT ${resultcode} STREQUAL "0") + if (NOT "${last_vds_test}" STREQUAL "") + set_tests_properties (H5DUMP-${resultfile} PROPERTIES DEPENDS ${last_VDS_test}) + endif (NOT "${last_vds_test}" STREQUAL "") + else (HDF5_ENABLE_USING_MEMCHECKER) + add_test ( + NAME H5DUMP-${resultfile}-clear-objects + COMMAND ${CMAKE_COMMAND} + -E remove ${resultfile}.out ${resultfile}.out.err + ) + set_tests_properties (H5DUMP-${resultfile}-clear-objects PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles/vds") + add_test ( + NAME H5DUMP-${resultfile} + COMMAND "${CMAKE_COMMAND}" + -D "TEST_PROGRAM=$<TARGET_FILE:h5dump>" + -D "TEST_ARGS:STRING=${ARGN}" + -D "TEST_FOLDER=${PROJECT_BINARY_DIR}/testfiles/vds" + -D "TEST_OUTPUT=${resultfile}.out" + -D "TEST_EXPECT=${resultcode}" + -D "TEST_REFERENCE=${resultfile}.ddl" + -P "${HDF_RESOURCES_EXT_DIR}/runTest.cmake" + ) + set_tests_properties (H5DUMP-${resultfile} PROPERTIES DEPENDS "H5DUMP-${resultfile}-clear-objects") + endif (HDF5_ENABLE_USING_MEMCHECKER) + ENDMACRO (ADD_H5_VDS_TEST file) + + MACRO (ADD_H5_VDS_LAYOUT resultfile resultcode) + # If using memchecker add tests without using scripts + if (HDF5_ENABLE_USING_MEMCHECKER) + add_test (NAME H5DUMP-${resultfile} COMMAND $<TARGET_FILE:h5dump> -p ${ARGN}) + set_tests_properties (H5DUMP-${resultfile} PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfilesvds") + if (NOT ${resultcode} STREQUAL "0") + set_tests_properties (H5DUMP-${resultfile} PROPERTIES WILL_FAIL "true") + endif (NOT ${resultcode} STREQUAL "0") + if (NOT "${last_vds_test}" STREQUAL "") + set_tests_properties (H5DUMP-${resultfile} PROPERTIES DEPENDS ${last_VDS_test}) + endif (NOT "${last_vds_test}" STREQUAL "") + else (HDF5_ENABLE_USING_MEMCHECKER) + add_test ( + NAME H5DUMP-${resultfile}-clear-objects + COMMAND ${CMAKE_COMMAND} + -E remove ${resultfile}.out ${resultfile}.out.err + ) + set_tests_properties (H5DUMP-${resultfile}-clear-objects PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles/vds") + add_test ( + NAME H5DUMP-${resultfile} + COMMAND "${CMAKE_COMMAND}" + -D "TEST_PROGRAM=$<TARGET_FILE:h5dump>" + -D "TEST_ARGS:STRING=-p;${ARGN}" + -D "TEST_FOLDER=${PROJECT_BINARY_DIR}/testfiles/vds" + -D "TEST_OUTPUT=${resultfile}.out" + -D "TEST_EXPECT=${resultcode}" + -D "TEST_REFERENCE=${resultfile}.ddl" + -P "${HDF_RESOURCES_EXT_DIR}/runTest.cmake" + ) + set_tests_properties (H5DUMP-${resultfile} PROPERTIES DEPENDS "H5DUMP-${resultfile}-clear-objects") + endif (HDF5_ENABLE_USING_MEMCHECKER) + ENDMACRO (ADD_H5_VDS_LAYOUT file) + +############################################################################## +############################################################################## +### T H E T E S T S ### +############################################################################## +############################################################################## + + if (HDF5_ENABLE_USING_MEMCHECKER) + # Remove any output file left over from previous test run + add_test ( + NAME H5DUMP_VDS-clearall-objects + COMMAND ${CMAKE_COMMAND} + -E remove + tvds-1.out + tvds-1.out.err + tvds-2.out + tvds-2.out.err + tvds-3_1.out + tvds-3_1.out.err + tvds-3_2.out + tvds-3_2.out.err + tvds-4.out + tvds-4.out.err + tvds-5.out + tvds-5.out.err + tvds_layout-1.out + tvds_layout-1.out.err + tvds_layout-2.out + tvds_layout-2.out.err + tvds_layout-3_1.out + tvds_layout-3_1.out.err + tvds_layout-3_2.out + tvds_layout-3_2.out.err + tvds_layout-4.out + tvds_layout-4.out.err + tvds_layout-5.out + tvds_layout-5.out.err + ) + set_tests_properties (H5DUMP_VDS-clearall-objects PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles/vds") + if (NOT "${last_vds_test}" STREQUAL "") + set_tests_properties (H5DUMP_VDS-clearall-objects PROPERTIES DEPENDS ${last_vds_test}) + endif (NOT "${last_vds_test}" STREQUAL "") + set (last_VDS_test "H5DUMP_VDS-clearall-objects") + endif (HDF5_ENABLE_USING_MEMCHECKER) + +# See which filters are usable (and skip tests for filters we +# don't have). Do this by searching H5pubconf.h to see which +# filters are defined. + +# detect whether the encoder is present. + if (H5_HAVE_FILTER_DEFLATE) + set (USE_FILTER_DEFLATE "true") + endif (H5_HAVE_FILTER_DEFLATE) + + if (H5_HAVE_FILTER_SZIP) + set (USE_FILTER_SZIP "true") + endif (H5_HAVE_FILTER_SZIP) + + # Data read + if (USE_FILTER_DEFLATE) + ADD_H5_VDS_TEST (tvds-1 0 --enable-error-stack 1_vds.h5) + ADD_H5_VDS_TEST (tvds-2 0 --enable-error-stack 2_vds.h5) + ADD_H5_VDS_TEST (tvds-3_1 0 --enable-error-stack 3_1_vds.h5) + ADD_H5_VDS_TEST (tvds-3_2 0 --enable-error-stack 3_2_vds.h5) + ADD_H5_VDS_TEST (tvds-4 0 --enable-error-stack 4_vds.h5) + ADD_H5_VDS_TEST (tvds-5 0 --enable-error-stack 5_vds.h5) + endif (USE_FILTER_DEFLATE) + + # Layout read + if (USE_FILTER_DEFLATE) + ADD_H5_VDS_LAYOUT (tvds_layout-1 0 --enable-error-stack 1_vds.h5) + ADD_H5_VDS_LAYOUT (tvds_layout-2 0 --enable-error-stack 2_vds.h5) + ADD_H5_VDS_LAYOUT (tvds_layout-3_1 0 --enable-error-stack 3_1_vds.h5) + ADD_H5_VDS_LAYOUT (tvds_layout-3_2 0 --enable-error-stack 3_2_vds.h5) + ADD_H5_VDS_LAYOUT (tvds_layout-4 0 --enable-error-stack 4_vds.h5) + ADD_H5_VDS_LAYOUT (tvds_layout-5 0 --enable-error-stack 5_vds.h5) + endif (USE_FILTER_DEFLATE) diff --git a/tools/h5dump/Makefile.am b/tools/h5dump/Makefile.am index cee4801..93ba195 100644 --- a/tools/h5dump/Makefile.am +++ b/tools/h5dump/Makefile.am @@ -25,7 +25,7 @@ AM_CPPFLAGS+=-I$(top_srcdir)/src -I$(top_srcdir)/tools/lib # Test programs and scripts TEST_PROG=h5dumpgentest -TEST_SCRIPT=testh5dump.sh testh5dumppbits.sh testh5dumpxml.sh +TEST_SCRIPT=testh5dump.sh testh5dumppbits.sh testh5dumpvds.sh testh5dumpxml.sh check_PROGRAMS=$(TEST_PROG) binread check_SCRIPTS=$(TEST_SCRIPT) diff --git a/tools/h5dump/Makefile.in b/tools/h5dump/Makefile.in index cfb268c..9ac80d7 100644 --- a/tools/h5dump/Makefile.in +++ b/tools/h5dump/Makefile.in @@ -99,8 +99,8 @@ DIST_COMMON = $(top_srcdir)/config/commence.am \ $(top_srcdir)/config/conclude.am $(srcdir)/Makefile.in \ $(srcdir)/Makefile.am $(top_srcdir)/bin/mkinstalldirs \ $(srcdir)/testh5dump.sh.in $(srcdir)/testh5dumppbits.sh.in \ - $(srcdir)/testh5dumpxml.sh.in $(top_srcdir)/bin/depcomp \ - $(top_srcdir)/bin/test-driver + $(srcdir)/testh5dumpvds.sh.in $(srcdir)/testh5dumpxml.sh.in \ + $(top_srcdir)/bin/depcomp $(top_srcdir)/bin/test-driver check_PROGRAMS = $(am__EXEEXT_1) binread$(EXEEXT) bin_PROGRAMS = h5dump$(EXEEXT) TESTS = $(am__EXEEXT_1) $(TEST_SCRIPT) @@ -113,7 +113,8 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(SHELL) $(top_srcdir)/bin/mkinstalldirs CONFIG_HEADER = $(top_builddir)/src/H5config.h \ $(top_builddir)/fortran/src/H5config_f.inc -CONFIG_CLEAN_FILES = testh5dump.sh testh5dumppbits.sh testh5dumpxml.sh +CONFIG_CLEAN_FILES = testh5dump.sh testh5dumppbits.sh testh5dumpvds.sh \ + testh5dumpxml.sh CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(bindir)" am__EXEEXT_1 = h5dumpgentest$(EXEEXT) @@ -692,7 +693,7 @@ CHECK_CLEANFILES = *.chkexe *.chklog *.clog *.clog2 *.h5 *.bin # Test programs and scripts TEST_PROG = h5dumpgentest -TEST_SCRIPT = testh5dump.sh testh5dumppbits.sh testh5dumpxml.sh +TEST_SCRIPT = testh5dump.sh testh5dumppbits.sh testh5dumpvds.sh testh5dumpxml.sh check_SCRIPTS = $(TEST_SCRIPT) SCRIPT_DEPEND = h5dump$(EXEEXT) @@ -764,6 +765,8 @@ testh5dump.sh: $(top_builddir)/config.status $(srcdir)/testh5dump.sh.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ testh5dumppbits.sh: $(top_builddir)/config.status $(srcdir)/testh5dumppbits.sh.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +testh5dumpvds.sh: $(top_builddir)/config.status $(srcdir)/testh5dumpvds.sh.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ testh5dumpxml.sh: $(top_builddir)/config.status $(srcdir)/testh5dumpxml.sh.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-binPROGRAMS: $(bin_PROGRAMS) diff --git a/tools/h5dump/errfiles/tdset-2.err b/tools/h5dump/errfiles/tdset-2.err index d9b92f3..775351e 100644 --- a/tools/h5dump/errfiles/tdset-2.err +++ b/tools/h5dump/errfiles/tdset-2.err @@ -1,17 +1,20 @@ HDF5-DIAG: Error detected in HDF5 (version (number)) thread (IDs): - #000: (file name) line (number) in H5Dopen2(): not found + #000: (file name) line (number) in H5Dopen2(): unable to open dataset + major: Dataset + minor: Can't open object + #001: (file name) line (number) in H5D__open_name(): not found major: Dataset minor: Object not found - #001: (file name) line (number) in H5G_loc_find(): can't find object + #002: (file name) line (number) in H5G_loc_find(): can't find object major: Symbol table minor: Object not found - #002: (file name) line (number) in H5G_traverse(): internal path traversal failed + #003: (file name) line (number) in H5G_traverse(): internal path traversal failed major: Symbol table minor: Object not found - #003: (file name) line (number) in H5G_traverse_real(): traversal operator failed + #004: (file name) line (number) in H5G_traverse_real(): traversal operator failed major: Symbol table minor: Callback failed - #004: (file name) line (number) in H5G_loc_find_cb(): object 'dset3' doesn't exist + #005: (file name) line (number) in H5G_loc_find_cb(): object 'dset3' doesn't exist major: Symbol table minor: Object not found HDF5-DIAG: Error detected in HDF5 (version (number)) thread (IDs): diff --git a/tools/h5dump/errfiles/tperror.err b/tools/h5dump/errfiles/tperror.err index 19a7a73..29f9e7f 100644 --- a/tools/h5dump/errfiles/tperror.err +++ b/tools/h5dump/errfiles/tperror.err @@ -1,17 +1,20 @@ HDF5-DIAG: Error detected in HDF5 (version (number)) thread (IDs): - #000: (file name) line (number) in H5Dopen2(): not found + #000: (file name) line (number) in H5Dopen2(): unable to open dataset + major: Dataset + minor: Can't open object + #001: (file name) line (number) in H5D__open_name(): not found major: Dataset minor: Object not found - #001: (file name) line (number) in H5G_loc_find(): can't find object + #002: (file name) line (number) in H5G_loc_find(): can't find object major: Symbol table minor: Object not found - #002: (file name) line (number) in H5G_traverse(): internal path traversal failed + #003: (file name) line (number) in H5G_traverse(): internal path traversal failed major: Symbol table minor: Object not found - #003: (file name) line (number) in H5G_traverse_real(): traversal operator failed + #004: (file name) line (number) in H5G_traverse_real(): traversal operator failed major: Symbol table minor: Callback failed - #004: (file name) line (number) in H5G_loc_find_cb(): object 'bogus' doesn't exist + #005: (file name) line (number) in H5G_loc_find_cb(): object 'bogus' doesn't exist major: Symbol table minor: Object not found HDF5-DIAG: Error detected in HDF5 (version (number)) thread (IDs): diff --git a/tools/h5dump/errfiles/tslink-D.err b/tools/h5dump/errfiles/tslink-D.err index b98e324..924e9cf 100644 --- a/tools/h5dump/errfiles/tslink-D.err +++ b/tools/h5dump/errfiles/tslink-D.err @@ -1,25 +1,28 @@ HDF5-DIAG: Error detected in HDF5 (version (number)) thread (IDs): - #000: (file name) line (number) in H5Dopen2(): not found + #000: (file name) line (number) in H5Dopen2(): unable to open dataset + major: Dataset + minor: Can't open object + #001: (file name) line (number) in H5D__open_name(): not found major: Dataset minor: Object not found - #001: (file name) line (number) in H5G_loc_find(): can't find object + #002: (file name) line (number) in H5G_loc_find(): can't find object major: Symbol table minor: Object not found - #002: (file name) line (number) in H5G_traverse(): internal path traversal failed + #003: (file name) line (number) in H5G_traverse(): internal path traversal failed major: Symbol table minor: Object not found - #003: (file name) line (number) in H5G_traverse_real(): special link traversal failed + #004: (file name) line (number) in H5G_traverse_real(): special link traversal failed major: Links minor: Link traversal failure - #004: (file name) line (number) in H5G__traverse_special(): symbolic link traversal failed + #005: (file name) line (number) in H5G__traverse_special(): symbolic link traversal failed major: Links minor: Link traversal failure - #005: (file name) line (number) in H5G_traverse_slink(): unable to follow symbolic link + #006: (file name) line (number) in H5G_traverse_slink(): unable to follow symbolic link major: Symbol table minor: Object not found - #006: (file name) line (number) in H5G_traverse_real(): traversal operator failed + #007: (file name) line (number) in H5G_traverse_real(): traversal operator failed major: Symbol table minor: Callback failed - #007: (file name) line (number) in H5G_traverse_slink_cb(): component not found + #008: (file name) line (number) in H5G_traverse_slink_cb(): component not found major: Symbol table minor: Object not found diff --git a/tools/h5dump/testh5dumpvds.sh.in b/tools/h5dump/testh5dumpvds.sh.in new file mode 100644 index 0000000..b15606f --- /dev/null +++ b/tools/h5dump/testh5dumpvds.sh.in @@ -0,0 +1,505 @@ +#! /bin/sh +# +# 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 files COPYING and Copyright.html. COPYING can be found at the root +# of the source code distribution tree; Copyright.html can be found at the +# root level of an installed copy of the electronic HDF5 document set and +# is linked from the top-level documents page. It can also be found at +# http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have +# access to either file, you may request a copy from help@hdfgroup.org. +# +# Tests for the h5dump tool with vds type files + +srcdir=@srcdir@ + +# Determine which filters are available +USE_FILTER_SZIP="@USE_FILTER_SZIP@" +USE_FILTER_DEFLATE="@USE_FILTER_DEFLATE@" + +TESTNAME=h5dump +EXIT_SUCCESS=0 +EXIT_FAILURE=1 + +DUMPER=h5dump # The tool name +DUMPER_BIN=`pwd`/$DUMPER # The path of the tool binary + +H5DIFF=../h5diff/h5diff # The h5diff tool name +H5DIFF_BIN=`pwd`/$H5DIFF # The path of the h5diff tool binary + +H5IMPORT=../h5import/h5import # The h5import tool name +H5IMPORT_BIN=`pwd`/$H5IMPORT # The path of the h5import tool binary + +RM='rm -rf' +CMP='cmp -s' +DIFF='diff -c' +CP='cp' +DIRNAME='dirname' +LS='ls' +AWK='awk' + +nerrors=0 +verbose=yes + +# source dirs +SRC_TOOLS="$srcdir/../" + +SRC_TOOLS_TESTFILES="$SRC_TOOLS/testfiles" +# testfiles source dirs for tools +SRC_H5LS_TESTFILES="$SRC_TOOLS_TESTFILES" +SRC_H5DUMP_TESTFILES="$SRC_TOOLS_TESTFILES" +SRC_H5DUMP_ERRORFILES="$srcdir/errfiles" +SRC_H5DIFF_TESTFILES="$SRC_TOOLS/h5diff/testfiles" +SRC_H5COPY_TESTFILES="$SRC_TOOLS/h5copy/testfiles" +SRC_H5REPACK_TESTFILES="$SRC_TOOLS/h5repack/testfiles" +SRC_H5JAM_TESTFILES="$SRC_TOOLS/h5jam/testfiles" +SRC_H5STAT_TESTFILES="$SRC_TOOLS/h5stat/testfiles" +SRC_H5IMPORT_TESTFILES="$SRC_TOOLS/h5import/testfiles" + +TEST_P_DIR=./testfiles +TESTDIR=./testfiles/vds +test -d $TEST_P_DIR || mkdir -p $TEST_P_DIR +test -d $TESTDIR || mkdir -p $TESTDIR + +###################################################################### +# test files +# -------------------------------------------------------------------- +# All the test files copy from source directory to test directory +# NOTE: Keep this framework to add/remove test files. +# Any test files from other tools can be used in this framework. +# This list are also used for checking exist. +# Comment '#' without space can be used. +# -------------------------------------------------------------------- +LIST_HDF5_TEST_FILES=" +$SRC_H5DUMP_TESTFILES/vds/1_a.h5 +$SRC_H5DUMP_TESTFILES/vds/1_b.h5 +$SRC_H5DUMP_TESTFILES/vds/1_c.h5 +$SRC_H5DUMP_TESTFILES/vds/1_d.h5 +$SRC_H5DUMP_TESTFILES/vds/1_e.h5 +$SRC_H5DUMP_TESTFILES/vds/1_f.h5 +$SRC_H5DUMP_TESTFILES/vds/1_vds.h5 +$SRC_H5DUMP_TESTFILES/vds/2_a.h5 +$SRC_H5DUMP_TESTFILES/vds/2_b.h5 +$SRC_H5DUMP_TESTFILES/vds/2_c.h5 +$SRC_H5DUMP_TESTFILES/vds/2_d.h5 +$SRC_H5DUMP_TESTFILES/vds/2_e.h5 +$SRC_H5DUMP_TESTFILES/vds/2_vds.h5 +$SRC_H5DUMP_TESTFILES/vds/3_1_vds.h5 +$SRC_H5DUMP_TESTFILES/vds/3_2_vds.h5 +$SRC_H5DUMP_TESTFILES/vds/4_0.h5 +$SRC_H5DUMP_TESTFILES/vds/4_1.h5 +$SRC_H5DUMP_TESTFILES/vds/4_2.h5 +$SRC_H5DUMP_TESTFILES/vds/4_vds.h5 +$SRC_H5DUMP_TESTFILES/vds/5_a.h5 +$SRC_H5DUMP_TESTFILES/vds/5_b.h5 +$SRC_H5DUMP_TESTFILES/vds/5_c.h5 +$SRC_H5DUMP_TESTFILES/vds/5_vds.h5 +" + +LIST_OTHER_TEST_FILES=" +$SRC_H5DUMP_TESTFILES/vds/tvds-1.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds-2.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds-3_1.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds-3_2.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds-4.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds-5.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-1.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-2.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-3_1.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-3_2.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-4.ddl +$SRC_H5DUMP_TESTFILES/vds/tvds_layout-5.ddl +" + +LIST_ERROR_TEST_FILES=" +" + +# +# copy test files and expected output files from source dirs to test dir +# +COPY_TESTFILES="$LIST_HDF5_TEST_FILES $LIST_OTHER_TEST_FILES $LIST_ERROR_TEST_FILES" + +COPY_TESTFILES_TO_TESTDIR() +{ + # copy test files. Used -f to make sure get a new copy + for tstfile in $COPY_TESTFILES + do + # ignore '#' comment + echo $tstfile | tr -d ' ' | grep '^#' > /dev/null + RET=$? + if [ $RET -eq 1 ]; then + # skip cp if srcdir is same as destdir + # this occurs when build/test performed in source dir and + # make cp fail + SDIR=`$DIRNAME $tstfile` + INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` + INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` + if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then + $CP -f $tstfile $TESTDIR + if [ $? -ne 0 ]; then + echo "Error: FAILED to copy $tstfile ." + + # Comment out this to CREATE expected file + exit $EXIT_FAILURE + fi + fi + fi + done +} + +CLEAN_TESTFILES_AND_TESTDIR() +{ + # skip rm if srcdir is same as destdir + # this occurs when build/test performed in source dir and + # make cp fail + SDIR=`$DIRNAME $tstfile` + INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` + INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` + if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then + $RM $TESTDIR + fi +} + +# Print a line-line message left justified in a field of 70 characters +# beginning with the word "Testing". +# +TESTING() { + SPACES=" " + echo "Testing $* $SPACES" | cut -c1-70 | tr -d '\012' +} + +# Source in the output filter function definitions. +. $srcdir/../../bin/output_filter.sh + +# Run a test and print PASS or *FAIL*. If a test fails then increment +# the `nerrors' global variable and (if $verbose is set) display the +# difference between the actual output and the expected output. The +# expected output is given as the first argument to this function and +# the actual output file is calculated by replacing the `.ddl' with +# `.out'. The actual output is not removed if $HDF5_NOCLEANUP has a +# non-zero value. +# +TOOLTEST() { + expect="$TESTDIR/$1" + actual="$TESTDIR/`basename $1 .ddl`.out" + actual_err="$TESTDIR/`basename $1 .ddl`.err" + actual_sav=${actual}-sav + actual_err_sav=${actual_err}-sav + shift + + # Run test. + TESTING $DUMPER $@ + ( + cd $TESTDIR + $RUNSERIAL $DUMPER_BIN "$@" + ) >$actual 2>$actual_err + + # save actual and actual_err in case they are needed later. + cp $actual $actual_sav + STDOUT_FILTER $actual + cp $actual_err $actual_err_sav + STDERR_FILTER $actual_err + cat $actual_err >> $actual + + if [ ! -f $expect ]; then + # Create the expect file if it doesn't yet exist. + echo " CREATED" + cp $actual $expect + elif $CMP $expect $actual; then + echo " PASSED" + else + echo "*FAILED*" + echo " Expected result (*.ddl) differs from actual result (*.out)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' + fi + + # Clean up output file + if test -z "$HDF5_NOCLEANUP"; then + rm -f $actual $actual_err $actual_sav $actual_err_sav $actual_ext + fi + +} + + +# same as TOOLTEST1 but compares generated file to expected output +# and compares the generated data file to the expected data file +# used for the binary tests that expect a full path in -o without -b +TOOLTEST2() { + + expectdata="$TESTDIR/$1" + expect="$TESTDIR/`basename $1 .exp`.ddl" + actualdata="$TESTDIR/`basename $1 .exp`.txt" + actual="$TESTDIR/`basename $1 .exp`.out" + actual_err="$TESTDIR/`basename $1 .exp`.err" + shift + + # Run test. + TESTING $DUMPER $@ + ( + cd $TESTDIR + $RUNSERIAL $DUMPER_BIN "$@" + ) >$actual 2>$actual_err + cat $actual_err >> $actual + + if [ ! -f $expect ]; then + # Create the expect file if it doesn't yet exist. + echo " CREATED" + cp $actual $expect + elif $CMP $expect $actual; then + if [ ! -f $expectdata ]; then + # Create the expect data file if it doesn't yet exist. + echo " CREATED" + cp $actualdata $expectdata + elif $CMP $expectdata $actualdata; then + echo " PASSED" + else + echo "*FAILED*" + echo " Expected datafile (*.exp) differs from actual datafile (*.txt)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expectdata $actualdata |sed 's/^/ /' + fi + else + echo "*FAILED*" + echo " Expected result (*.ddl) differs from actual result (*.out)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' + fi + + # Clean up output file + if test -z "$HDF5_NOCLEANUP"; then + rm -f $actual $actualdata $actual_err + fi + +} + +# same as TOOLTEST but filters error stack outp +# Extract file name, line number, version and thread IDs because they may be different +TOOLTEST3() { + + expect="$TESTDIR/$1" + actual="$TESTDIR/`basename $1 .ddl`.out" + actual_err="$TESTDIR/`basename $1 .ddl`.err" + actual_ext="$TESTDIR/`basename $1 .ddl`.ext" + actual_sav=${actual}-sav + actual_err_sav=${actual_err}-sav + shift + + # Run test. + TESTING $DUMPER $@ + ( + cd $TESTDIR + $RUNSERIAL $DUMPER_BIN "$@" + ) >$actual 2>$actual_err + + # save actual and actual_err in case they are needed later. + cp $actual $actual_sav + STDOUT_FILTER $actual + cp $actual_err $actual_err_sav + STDERR_FILTER $actual_err + + # Extract file name, line number, version and thread IDs because they may be different + sed -e 's/thread [0-9]*/thread (IDs)/' -e 's/: .*\.c /: (file name) /' \ + -e 's/line [0-9]*/line (number)/' \ + -e 's/v[1-9]*\.[0-9]*\./version (number)\./' \ + -e 's/[1-9]*\.[0-9]*\.[0-9]*[^)]*/version (number)/' \ + -e 's/H5Eget_auto[1-2]*/H5Eget_auto(1 or 2)/' \ + -e 's/H5Eset_auto[1-2]*/H5Eset_auto(1 or 2)/' \ + $actual_err > $actual_ext + cat $actual_ext >> $actual + + if [ ! -f $expect ]; then + # Create the expect file if it doesn't yet exist. + echo " CREATED" + cp $actual $expect + elif $CMP $expect $actual; then + echo " PASSED" + else + echo "*FAILED*" + echo " Expected result (*.ddl) differs from actual result (*.out)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' + fi + + # Clean up output file + if test -z "$HDF5_NOCLEANUP"; then + rm -f $actual $actual_err $actual_sav $actual_err_sav + fi + +} + +# same as TOOLTEST3 but filters error stack output and compares to an error file +# Extract file name, line number, version and thread IDs because they may be different +TOOLTEST4() { + + expect="$TESTDIR/$1" + expect_err="$TESTDIR/`basename $1 .ddl`.err" + actual="$TESTDIR/`basename $1 .ddl`.out" + actual_err="$TESTDIR/`basename $1 .ddl`.oerr" + actual_ext="$TESTDIR/`basename $1 .ddl`.ext" + actual_sav=${actual}-sav + actual_err_sav=${actual_err}-sav + shift + + # Run test. + TESTING $DUMPER $@ + ( + cd $TESTDIR + $RUNSERIAL $DUMPER_BIN "$@" + ) >$actual 2>$actual_err + + # save actual and actual_err in case they are needed later. + cp $actual $actual_sav + STDOUT_FILTER $actual + cp $actual_err $actual_err_sav + STDERR_FILTER $actual_err + + # Extract file name, line number, version and thread IDs because they may be different + sed -e 's/thread [0-9]*/thread (IDs)/' -e 's/: .*\.c /: (file name) /' \ + -e 's/line [0-9]*/line (number)/' \ + -e 's/v[1-9]*\.[0-9]*\./version (number)\./' \ + -e 's/[1-9]*\.[0-9]*\.[0-9]*[^)]*/version (number)/' \ + -e 's/H5Eget_auto[1-2]*/H5Eget_auto(1 or 2)/' \ + -e 's/H5Eset_auto[1-2]*/H5Eset_auto(1 or 2)/' \ + $actual_err > $actual_ext + #cat $actual_ext >> $actual + + if [ ! -f $expect ]; then + # Create the expect file if it doesn't yet exist. + echo " CREATED" + cp $actual $expect + elif $CMP $expect $actual; then + if $CMP $expect_err $actual_ext; then + echo " PASSED" + else + echo "*FAILED*" + echo " Expected result (*.err) differs from actual result (*.oerr)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect_err $actual_ext |sed 's/^/ /' + fi + else + echo "*FAILED*" + echo " Expected result (*.ddl) differs from actual result (*.out)" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' + fi + + # Clean up output file + if test -z "$HDF5_NOCLEANUP"; then + rm -f $actual $actual_err $actual_sav $actual_err_sav + fi + +} + +# Print a "SKIP" message +SKIP() { + TESTING $DUMPER $@ + echo " -SKIP-" +} + +# Print a line-line message left justified in a field of 70 characters +# +PRINT_H5DIFF() { + SPACES=" " + echo " Running h5diff $* $SPACES" | cut -c1-70 | tr -d '\012' +} + + +# Call the h5diff tool +# +DIFFTEST() +{ + PRINT_H5DIFF $@ + ( + cd $TESTDIR + $RUNSERIAL $H5DIFF_BIN "$@" -q + ) + RET=$? + if [ $RET != 0 ] ; then + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" + else + echo " PASSED" + fi + +} + +# Print a line-line message left justified in a field of 70 characters +# beginning with the word "Verifying". +# +PRINT_H5IMPORT() { + SPACES=" " + echo " Running h5import $* $SPACES" | cut -c1-70 | tr -d '\012' +} + +# Call the h5import tool +# +IMPORTTEST() +{ + # remove the output hdf5 file if it exists + hdf5_file="$TESTDIR/$5" + if [ -f $hdf5_file ]; then + rm -f $hdf5_file + fi + + PRINT_H5IMPORT $@ + ( + cd $TESTDIR + $RUNSERIAL $H5IMPORT_BIN "$@" + ) + RET=$? + if [ $RET != 0 ] ; then + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" + else + echo " PASSED" + fi + +} + + +############################################################################## +############################################################################## +### T H E T E S T S ### +############################################################################## +############################################################################## +# prepare for test +COPY_TESTFILES_TO_TESTDIR + +####### test for dataset vds ###### + + # Data read +if test $USE_FILTER_DEFLATE = "yes" ; then + TOOLTEST tvds-1.ddl --enable-error-stack 1_vds.h5 + TOOLTEST tvds-2.ddl --enable-error-stack 2_vds.h5 + TOOLTEST tvds-3_1.ddl --enable-error-stack 3_1_vds.h5 + TOOLTEST tvds-3_2.ddl --enable-error-stack 3_2_vds.h5 + TOOLTEST tvds-4.ddl --enable-error-stack 4_vds.h5 + TOOLTEST tvds-5.ddl --enable-error-stack 5_vds.h5 +fi + + # Layout read +if test $USE_FILTER_DEFLATE = "yes" ; then + TOOLTEST tvds_layout-1.ddl -p --enable-error-stack 1_vds.h5 + TOOLTEST tvds_layout-2.ddl -p --enable-error-stack 2_vds.h5 + TOOLTEST tvds_layout-3_1.ddl -p --enable-error-stack 3_1_vds.h5 + TOOLTEST tvds_layout-3_2.ddl -p --enable-error-stack 3_2_vds.h5 + TOOLTEST tvds_layout-4.ddl -p --enable-error-stack 4_vds.h5 + TOOLTEST tvds_layout-5.ddl -p --enable-error-stack 5_vds.h5 +fi + +# Clean up temporary files/directories +CLEAN_TESTFILES_AND_TESTDIR + +# Report test results and exit +if test $nerrors -eq 0 ; then + echo "All $TESTNAME tests passed." + exit $EXIT_SUCCESS +else + echo "$TESTNAME tests failed with $nerrors errors." + exit $EXIT_FAILURE +fi diff --git a/tools/h5ls/CMakeLists.txt b/tools/h5ls/CMakeLists.txt index 4e96db2..6e7f00c 100644 --- a/tools/h5ls/CMakeLists.txt +++ b/tools/h5ls/CMakeLists.txt @@ -23,6 +23,8 @@ if (BUILD_TESTING) include (CMakeTests.cmake) + include (CMakeTestsVDS.cmake) + endif (BUILD_TESTING) ############################################################################## diff --git a/tools/h5ls/CMakeTestsVDS.cmake b/tools/h5ls/CMakeTestsVDS.cmake new file mode 100644 index 0000000..1ef3f20 --- /dev/null +++ b/tools/h5ls/CMakeTestsVDS.cmake @@ -0,0 +1,149 @@ + +############################################################################## +############################################################################## +### T E S T I N G ### +############################################################################## +############################################################################## + + # -------------------------------------------------------------------- + # Copy all the test files from source directory to test directory + # -------------------------------------------------------------------- + set (LIST_HDF5_TEST_FILES + 1_a.h5 + 1_b.h5 + 1_c.h5 + 1_d.h5 + 1_e.h5 + 1_f.h5 + 1_vds.h5 + 2_a.h5 + 2_b.h5 + 2_c.h5 + 2_d.h5 + 2_e.h5 + 2_vds.h5 + 3_1_vds.h5 + 3_2_vds.h5 + 4_0.h5 + 4_1.h5 + 4_2.h5 + 4_vds.h5 + 5_a.h5 + 5_b.h5 + 5_c.h5 + 5_vds.h5 + ) + + set (LIST_OTHER_TEST_FILES + tvds-1.ls + tvds-2.ls + tvds-3_1.ls + tvds-3_2.ls + tvds-4.ls + tvds-5.ls + ) + + file (MAKE_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles") + + # copy the list of test files + foreach (listfiles ${LIST_HDF5_TEST_FILES} ${LIST_OTHER_TEST_FILES}) + GET_FILENAME_COMPONENT(fname "${listfiles}" NAME) + set (dest "${PROJECT_BINARY_DIR}/testfiles/vds/${fname}") + #message (STATUS " Copying ${listfiles} to ${dest}") + add_custom_command ( + TARGET h5ls + POST_BUILD + COMMAND ${CMAKE_COMMAND} + ARGS -E copy_if_different ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/${listfiles} ${dest} + ) + endforeach (listfiles ${LIST_HDF5_TEST_FILES} ${LIST_OTHER_TEST_FILES}) + + +############################################################################## +############################################################################## +### T H E T E S T S M A C R O S ### +############################################################################## +############################################################################## + + MACRO (ADD_H5_VDS_TEST resultfile resultcode) + # If using memchecker add tests without using scripts + if (HDF5_ENABLE_USING_MEMCHECKER) + add_test (NAME H5LS-${resultfile} COMMAND $<TARGET_FILE:h5ls> ${ARGN}) + set_tests_properties (H5LS-${resultfile} PROPERTIES WORKING_DIRECTORY "${PROJECT_BINARY_DIR}/testfiles/vds") + if (${resultcode} STREQUAL "1") + set_tests_properties (H5LS-${resultfile} PROPERTIES WILL_FAIL "true") + endif (${resultcode} STREQUAL "1") + if (NOT "${last_test}" STREQUAL "") + set_tests_properties (H5LS-${resultfile} PROPERTIES DEPENDS ${last_test}) + endif (NOT "${last_test}" STREQUAL "") + else (HDF5_ENABLE_USING_MEMCHECKER) + add_test ( + NAME H5LS-${resultfile}-clear-objects + COMMAND ${CMAKE_COMMAND} + -E remove ./testfiles/${resultfile}.out ./testfiles/vds/${resultfile}.out.err + ) + add_test ( + NAME H5LS-${resultfile} + COMMAND "${CMAKE_COMMAND}" + -D "TEST_PROGRAM=$<TARGET_FILE:h5ls>" + -D "TEST_ARGS=${ARGN}" + -D "TEST_FOLDER=${PROJECT_BINARY_DIR}/testfiles/vds" + -D "TEST_OUTPUT=${resultfile}.out" + -D "TEST_EXPECT=${resultcode}" + -D "TEST_REFERENCE=${resultfile}.ls" + -P "${HDF_RESOURCES_EXT_DIR}/runTest.cmake" + ) + set_tests_properties (H5LS-${resultfile} PROPERTIES DEPENDS "H5LS_VDS-${resultfile}-clear-objects") + endif (HDF5_ENABLE_USING_MEMCHECKER) + ENDMACRO (ADD_H5_VDS_TEST file) + +############################################################################## +############################################################################## +### T H E T E S T S ### +############################################################################## +############################################################################## + + if (HDF5_ENABLE_USING_MEMCHECKER) + # Remove any output file left over from previous test run + add_test ( + NAME H5LS_VDS-clearall-objects + COMMAND ${CMAKE_COMMAND} + -E remove + tvds-1.out + tvds-1.out.err + tvds-2.out + tvds-2.out.err + tvds-3_1.out + tvds-3_1.out.err + tvds-3_2.out + tvds-3_2.out.err + tvds-4.out + tvds-4.out.err + tvds-5.out + tvds-5.out.err + tvds_layout-1.out + tvds_layout-1.out.err + tvds_layout-2.out + tvds_layout-2.out.err + tvds_layout-3_1.out + tvds_layout-3_1.out.err + tvds_layout-3_2.out + tvds_layout-3_2.out.err + tvds_layout-4.out + tvds_layout-4.out.err + tvds_layout-5.out + tvds_layout-5.out.err + ) + if (NOT "${last_test}" STREQUAL "") + set_tests_properties (H5LS_VDS-clearall-objects PROPERTIES DEPENDS ${last_test}) + endif (NOT "${last_test}" STREQUAL "") + set (last_test "H5LS_VDS-clearall-objects") + endif (HDF5_ENABLE_USING_MEMCHECKER) + + ADD_H5_VDS_TEST (tvds-1 0 -w80 -v -S 1_vds.h5) + ADD_H5_VDS_TEST (tvds-2 0 -w80 -v -S 2_vds.h5) + ADD_H5_VDS_TEST (tvds-3_1 0 -w80 -v -S 3_1_vds.h5) + ADD_H5_VDS_TEST (tvds-3_2 0 -w80 -v -S 3_2_vds.h5) + ADD_H5_VDS_TEST (tvds-4 0 -w80 -v -S 4_vds.h5) + ADD_H5_VDS_TEST (tvds-5 0 -w80 -v -S 5_vds.h5) + diff --git a/tools/h5ls/Makefile.am b/tools/h5ls/Makefile.am index 408ce93..54a06f1 100644 --- a/tools/h5ls/Makefile.am +++ b/tools/h5ls/Makefile.am @@ -24,7 +24,7 @@ include $(top_srcdir)/config/commence.am AM_CPPFLAGS+=-I$(top_srcdir)/src -I$(top_srcdir)/tools/lib # Test programs and scripts -TEST_SCRIPT=testh5ls.sh +TEST_SCRIPT=testh5ls.sh testh5lsvds.sh check_SCRIPTS=$(TEST_SCRIPT) SCRIPT_DEPEND=h5ls$(EXEEXT) diff --git a/tools/h5ls/Makefile.in b/tools/h5ls/Makefile.in index b23d07f..1229bae 100644 --- a/tools/h5ls/Makefile.in +++ b/tools/h5ls/Makefile.in @@ -98,8 +98,8 @@ host_triplet = @host@ DIST_COMMON = $(top_srcdir)/config/commence.am \ $(top_srcdir)/config/conclude.am $(srcdir)/Makefile.in \ $(srcdir)/Makefile.am $(top_srcdir)/bin/mkinstalldirs \ - $(srcdir)/testh5ls.sh.in $(top_srcdir)/bin/depcomp \ - $(top_srcdir)/bin/test-driver + $(srcdir)/testh5ls.sh.in $(srcdir)/testh5lsvds.sh.in \ + $(top_srcdir)/bin/depcomp $(top_srcdir)/bin/test-driver bin_PROGRAMS = h5ls$(EXEEXT) TESTS = $(TEST_SCRIPT) subdir = tools/h5ls @@ -111,7 +111,7 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ mkinstalldirs = $(SHELL) $(top_srcdir)/bin/mkinstalldirs CONFIG_HEADER = $(top_builddir)/src/H5config.h \ $(top_builddir)/fortran/src/H5config_f.inc -CONFIG_CLEAN_FILES = testh5ls.sh +CONFIG_CLEAN_FILES = testh5ls.sh testh5lsvds.sh CONFIG_CLEAN_VPATH_FILES = am__installdirs = "$(DESTDIR)$(bindir)" PROGRAMS = $(bin_PROGRAMS) @@ -674,7 +674,7 @@ TRACE = perl $(top_srcdir)/bin/trace CHECK_CLEANFILES = *.chkexe *.chklog *.clog *.clog2 # Test programs and scripts -TEST_SCRIPT = testh5ls.sh +TEST_SCRIPT = testh5ls.sh testh5lsvds.sh check_SCRIPTS = $(TEST_SCRIPT) SCRIPT_DEPEND = h5ls$(EXEEXT) @@ -740,6 +740,8 @@ $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) $(am__aclocal_m4_deps): testh5ls.sh: $(top_builddir)/config.status $(srcdir)/testh5ls.sh.in cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ +testh5lsvds.sh: $(top_builddir)/config.status $(srcdir)/testh5lsvds.sh.in + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ diff --git a/tools/h5ls/h5ls.c b/tools/h5ls/h5ls.c index fe128fa..98e3009 100644 --- a/tools/h5ls/h5ls.c +++ b/tools/h5ls/h5ls.c @@ -1847,6 +1847,32 @@ dataset_list2(hid_t dset, const char H5_ATTR_UNUSED *name) h5tools_str_append(&buffer, "\n"); } /* end if */ break; + case H5D_VIRTUAL: + { + size_t vmaps; + + H5Pget_virtual_count(dcpl, &vmaps); + + if (vmaps) { + size_t next; + ssize_t ssize_out; + + h5tools_str_append(&buffer, " %-10s {%ld} Source {\n", "Maps:", vmaps); + for (next = 0; next < (unsigned) vmaps; next++) { + ssize_out = H5Pget_virtual_filename(dcpl, next, NULL, 0); + H5Pget_virtual_filename(dcpl, next, f_name, sizeof(f_name)); + ssize_out = H5Pget_virtual_dsetname(dcpl, next, NULL, 0); + H5Pget_virtual_dsetname(dcpl, next, dset_name, sizeof(dset_name)); + h5tools_str_append(&buffer, " %-10s ", " "); + print_string(&buffer, f_name, TRUE); + h5tools_str_append(&buffer, " "); + print_string(&buffer, dset_name, TRUE); + h5tools_str_append(&buffer, "\n"); + } + h5tools_str_append(&buffer, " %-10s}\n", " "); + } + } + break; default: break; } diff --git a/tools/h5ls/testh5lsvds.sh.in b/tools/h5ls/testh5lsvds.sh.in new file mode 100644 index 0000000..d194992 --- /dev/null +++ b/tools/h5ls/testh5lsvds.sh.in @@ -0,0 +1,258 @@ +#! /bin/sh +# +# 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 files COPYING and Copyright.html. COPYING can be found at the root +# of the source code distribution tree; Copyright.html can be found at the +# root level of an installed copy of the electronic HDF5 document set and +# is linked from the top-level documents page. It can also be found at +# http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have +# access to either file, you may request a copy from help@hdfgroup.org. +# +# Tests for the h5ls tool + +srcdir=@srcdir@ + +TESTNAME=h5ls +EXIT_SUCCESS=0 +EXIT_FAILURE=1 + +H5LS=h5ls # The tool name +H5LS_BIN=`pwd`/$H5LS # The path of the tool binary + +RM='rm -rf' +CMP='cmp -s' +DIFF='diff -c' +CP='cp' +NLINES=20 # Max. lines of output to display if test fails +DIRNAME='dirname' +LS='ls' +AWK='awk' + +WORDS_BIGENDIAN="@WORDS_BIGENDIAN@" + +nerrors=0 +verbose=yes +h5haveexitcode=yes # default is yes + +# source dirs +SRC_TOOLS="$srcdir/.." +SRC_TOOLS_TESTFILES="$SRC_TOOLS/testfiles" + +# testfiles source dirs for tools +SRC_H5LS_TESTFILES="$SRC_TOOLS_TESTFILES" +SRC_H5DUMP_TESTFILES="$SRC_TOOLS_TESTFILES" +SRC_H5DIFF_TESTFILES="$SRC_TOOLS/h5diff/testfiles" +SRC_H5COPY_TESTFILES="$SRC_TOOLS/h5copy/testfiles" +SRC_H5REPACK_TESTFILES="$SRC_TOOLS/h5repack/testfiles" +SRC_H5JAM_TESTFILES="$SRC_TOOLS/h5jam/testfiles" +SRC_H5STAT_TESTFILES="$SRC_TOOLS/h5stat/testfiles" +SRC_H5IMPORT_TESTFILES="$SRC_TOOLS/h5import/testfiles" + +TEST_P_DIR=./testfiles +TESTDIR=./testfiles/vds +test -d $TEST_P_DIR || mkdir -p $TEST_P_DIR +test -d $TESTDIR || mkdir $TESTDIR + +###################################################################### +# test files +# -------------------------------------------------------------------- +# All the test files copy from source directory to test directory +# NOTE: Keep this framework to add/remove test files. +# Any test files from other tools can be used in this framework. +# This list are also used for checking exist. +# Comment '#' without space can be used. +# -------------------------------------------------------------------- +LIST_HDF5_TEST_FILES=" +$SRC_H5LS_TESTFILES/vds/1_a.h5 +$SRC_H5LS_TESTFILES/vds/1_b.h5 +$SRC_H5LS_TESTFILES/vds/1_c.h5 +$SRC_H5LS_TESTFILES/vds/1_d.h5 +$SRC_H5LS_TESTFILES/vds/1_e.h5 +$SRC_H5LS_TESTFILES/vds/1_f.h5 +$SRC_H5LS_TESTFILES/vds/1_vds.h5 +$SRC_H5LS_TESTFILES/vds/2_a.h5 +$SRC_H5LS_TESTFILES/vds/2_b.h5 +$SRC_H5LS_TESTFILES/vds/2_c.h5 +$SRC_H5LS_TESTFILES/vds/2_d.h5 +$SRC_H5LS_TESTFILES/vds/2_e.h5 +$SRC_H5LS_TESTFILES/vds/2_vds.h5 +$SRC_H5LS_TESTFILES/vds/3_1_vds.h5 +$SRC_H5LS_TESTFILES/vds/3_2_vds.h5 +$SRC_H5LS_TESTFILES/vds/4_0.h5 +$SRC_H5LS_TESTFILES/vds/4_1.h5 +$SRC_H5LS_TESTFILES/vds/4_2.h5 +$SRC_H5LS_TESTFILES/vds/4_vds.h5 +$SRC_H5LS_TESTFILES/vds/5_a.h5 +$SRC_H5LS_TESTFILES/vds/5_b.h5 +$SRC_H5LS_TESTFILES/vds/5_c.h5 +$SRC_H5LS_TESTFILES/vds/5_vds.h5 +" + +LIST_OTHER_TEST_FILES=" +$SRC_H5LS_TESTFILES/vds/tvds-1.ls +$SRC_H5LS_TESTFILES/vds/tvds-2.ls +$SRC_H5LS_TESTFILES/vds/tvds-3_1.ls +$SRC_H5LS_TESTFILES/vds/tvds-3_2.ls +$SRC_H5LS_TESTFILES/vds/tvds-4.ls +$SRC_H5LS_TESTFILES/vds/tvds-5.ls +" + + +# RUNSERIAL is used. Check if it can return exit code from executalbe correctly. +if [ -n "$RUNSERIAL_NOEXITCODE" ]; then + echo "***Warning*** Serial Exit Code is not passed back to shell corretly." + echo "***Warning*** Exit code checking is skipped." + h5haveexitcode=no +fi + +# +# copy test files and expected output files from source dirs to test dir +# +COPY_TESTFILES="$LIST_HDF5_TEST_FILES $LIST_OTHER_TEST_FILES" + +COPY_TESTFILES_TO_TESTDIR() +{ + # copy test files. Used -f to make sure get a new copy + for tstfile in $COPY_TESTFILES + do + # ignore '#' comment + echo $tstfile | tr -d ' ' | grep '^#' > /dev/null + RET=$? + if [ $RET -eq 1 ]; then + # skip cp if srcdir is same as destdir + # this occurs when build/test performed in source dir and + # make cp fail + SDIR=`$DIRNAME $tstfile` + INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` + INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` + if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then + $CP -f $tstfile $TESTDIR + if [ $? -ne 0 ]; then + echo "Error: FAILED to copy $tstfile ." + + # Comment out this to CREATE expected file + exit $EXIT_FAILURE + fi + fi + fi + done +} + +CLEAN_TESTFILES_AND_TESTDIR() +{ + # skip rm if srcdir is same as destdir + # this occurs when build/test performed in source dir and + # make cp fail + SDIR=`$DIRNAME $tstfile` + INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` + INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` + if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then + $RM $TESTDIR + fi +} + +# Print a line-line message left justified in a field of 70 characters +# beginning with the word "Testing". +TESTING() { + SPACES=" " + echo "Testing $* $SPACES" |cut -c1-70 |tr -d '\012' +} + +# Source in the output filter function definitions. +. $srcdir/../../bin/output_filter.sh + +# Run a test and print PASS or *FAIL*. For now, if h5ls can complete +# with exit status 0, consider it pass. If a test fails then increment +# the `nerrors' global variable and (if $verbose is set) display up to $NLINS +# lines of the actual output from the tool test. The actual output is not +# removed if $HDF5_NOCLEANUP has a non-zero value. +# Arguemnts: +# $1 -- actual output filename to use +# $2 and on -- argument for the h5ls tool +TOOLTEST() { + expect="$TESTDIR/$1" + actual="$TESTDIR/`basename $1 .ls`.out" + actual_err="$TESTDIR/`basename $1 .ls`.err" + actual_sav=${actual}-sav + actual_err_sav=${actual_err}-sav + shift + retvalexpect=$1 + shift + + # Run test. + # Stderr is included in stdout so that the diff can detect + # any unexpected output from that stream too. + TESTING $H5LS $@ + ( + cd $TESTDIR + $RUNSERIAL $H5LS_BIN "$@" + ) >$actual 2>$actual_err + + exitcode=$? + # save actual and actual_err in case they are needed later. + cp $actual $actual_sav + STDOUT_FILTER $actual + cp $actual_err $actual_err_sav + STDERR_FILTER $actual_err + cat $actual_err >> $actual + if [ $h5haveexitcode = 'yes' -a $exitcode -ne $retvalexpect ]; then + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" + if [ yes = "$verbose" ]; then + echo "test returned with exit code $exitcode" + echo "test output: (up to $NLINES lines)" + head -$NLINES $actual + echo "***end of test output***" + echo "" + fi + elif [ ! -f $expect ]; then + # Create the expect file if it doesn't yet exist. + echo " CREATED" + cp $actual $expect + elif $CMP $expect $actual; then + echo " PASSED" + else + echo "*FAILED*" + echo " Expected result differs from actual result" + nerrors="`expr $nerrors + 1`" + test yes = "$verbose" && $DIFF $expect $actual |sed 's/^/ /' + fi + + # Clean up output file + if test -z "$HDF5_NOCLEANUP"; then + rm -f $actual $actual_err $actual_sav $actual_err_sav + fi +} + +############################################################################## +############################################################################## +### T H E T E S T S ### +############################################################################## +############################################################################## +# prepare for test +COPY_TESTFILES_TO_TESTDIR + +####### test for dataset vds ###### + +TOOLTEST tvds-1.ls 0 -w80 -v -S 1_vds.h5 +TOOLTEST tvds-2.ls 0 -w80 -v -S 2_vds.h5 +TOOLTEST tvds-3_1.ls 0 -w80 -v -S 3_1_vds.h5 +TOOLTEST tvds-3_2.ls 0 -w80 -v -S 3_2_vds.h5 +TOOLTEST tvds-4.ls 0 -w80 -v -S 4_vds.h5 +TOOLTEST tvds-5.ls 0 -w80 -v -S 5_vds.h5 + +# Clean up temporary files/directories +CLEAN_TESTFILES_AND_TESTDIR + +if test $nerrors -eq 0 ; then + echo "All $TESTNAME tests passed." + exit $EXIT_SUCCESS +else + echo "$TESTNAME tests failed with $nerrors errors." + exit $EXIT_FAILURE +fi diff --git a/tools/h5repack/CMakeTests.cmake b/tools/h5repack/CMakeTests.cmake index dee97ed..caad5c1 100644 --- a/tools/h5repack/CMakeTests.cmake +++ b/tools/h5repack/CMakeTests.cmake @@ -14,14 +14,14 @@ multi family ) - + if (DIRECT_VFD) set (VFD_LIST ${VFD_LIST} direct) endif (DIRECT_VFD) MACRO (ADD_VFD_TEST vfdname resultcode) add_test ( - NAME H5REPACK-VFD-${vfdname}-h5repacktest + NAME H5REPACK-VFD-${vfdname}-h5repacktest COMMAND "${CMAKE_COMMAND}" -D "TEST_PROGRAM=$<TARGET_FILE:h5repacktest>" -D "TEST_ARGS:STRING=" @@ -37,7 +37,7 @@ set (last_test "H5REPACK-VFD-${vfdname}-h5repacktest") ENDMACRO (ADD_VFD_TEST) endif (HDF5_TEST_VFD) - + # -------------------------------------------------------------------- # Copy all the HDF5 files from the source directory into the test directory # -------------------------------------------------------------------- @@ -77,6 +77,30 @@ ${HDF5_TOOLS_SRC_DIR}/testfiles/tfamily00008.h5 ${HDF5_TOOLS_SRC_DIR}/testfiles/tfamily00009.h5 ${HDF5_TOOLS_SRC_DIR}/testfiles/tfamily00010.h5 + # tools/testfiles/vds + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_d.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_e.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_f.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/1_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_d.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_e.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/2_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/3_1_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/3_2_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_0.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_1.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_2.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/4_vds.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_a.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_b.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_c.h5 + ${HDF5_TOOLS_SRC_DIR}/testfiles/vds/5_vds.h5 ) set (LIST_OTHER_TEST_FILES @@ -346,7 +370,7 @@ add_test ( NAME H5REPACK_UD-${testname}-clearall-objects COMMAND ${CMAKE_COMMAND} - -E remove + -E remove testfiles/out-${testname}.${resultfile} testfiles/${testname}.${resultfile}.out testfiles/${testname}.${resultfile}.out.err @@ -392,7 +416,7 @@ ############################################################################## # -------------------------------------------------------------------- - # test file names + # test file names # -------------------------------------------------------------------- set (INFO_FILE testfiles/h5repack.info) @@ -415,12 +439,18 @@ set (FILE18 h5repack_layout2.h5) set (FILE_REF h5repack_refs.h5) set (FILE_ATTR_REF h5repack_attr_refs.h5) - + set (FILEV1 1_vds.h5) + set (FILEV2 2_vds.h5) + set (FILEV3_1 3_1_vds.h5) + set (FILEV3_2 3_2_vds.h5) + set (FILEV4 4_vds.h5) + set (FILEV5 5_vds.h5) + # Remove any output file left over from previous test run add_test ( NAME H5REPACK-clearall-objects COMMAND ${CMAKE_COMMAND} - -E remove + -E remove ./testfiles/h5dump-help.out ./testfiles/h5repack_filters.h5-gzip_verbose_filters.out ./testfiles/h5repack_filters.h5-gzip_verbose_filters.out.err @@ -555,12 +585,41 @@ ./testfiles/out-meta_short_N.meta_short.h5 ./testfiles/out-meta_long_M.meta_long.h5 ./testfiles/out-meta_long_N.meta_long.h5 - # from the h5repacktst + ./testfiles/1_vds.h5-vds_dset_compa-v.out + ./testfiles/1_vds.h5-vds_dset_compa-v.out.err + ./testfiles/1_vds.h5-vds_dset_conti-v.out + ./testfiles/1_vds.h5-vds_dset_conti-v.out.err + ./testfiles/2_vds.h5-vds_null_compa-v.out + ./testfiles/2_vds.h5-vds_null_compa-v.out.err + ./testfiles/2_vds.h5-vds_null_conti-v.out + ./testfiles/2_vds.h5-vds_null_conti-v.out.err + ./testfiles/4_vds.h5-vds_compa-v.out + ./testfiles/4_vds.h5-vds_compa-v.out.err + ./testfiles/4_vds.h5-vds_compa_compa-v.out + ./testfiles/4_vds.h5-vds_compa_compa-v.out.err + ./testfiles/4_vds.h5-vds_compa_conti-v.out + ./testfiles/4_vds.h5-vds_compa_conti-v.out.err + ./testfiles/4_vds.h5-vds_conti-v.out + ./testfiles/4_vds.h5-vds_conti-v.out.err + ./testfiles/4_vds.h5-vds_conti_compa-v.out + ./testfiles/4_vds.h5-vds_conti_compa-v.out.err + ./testfiles/4_vds.h5-vds_conti_conti-v.out + ./testfiles/4_vds.h5-vds_conti_conti-v.out.err + ./testfiles/out-vds_compa.4_vds.h5 + ./testfiles/out-vds_compa_compa.4_vds.h5 + ./testfiles/out-vds_compa_conti.4_vds.h5 + ./testfiles/out-vds_conti.4_vds.h5 + ./testfiles/out-vds_conti_compa.4_vds.h5 + ./testfiles/out-vds_conti_conti.4_vds.h5 + ./testfiles/out-vds_dset_compa.1_vds.h5 + ./testfiles/out-vds_dset_conti.1_vds.h5 + ./testfiles/out-vds_null_compa.2_vds.h5 + ./testfiles/out-vds_null_conti.2_vds.h5 h5repack_attr.h5 h5repack_attr_out.h5 h5repack_attr_refs.h5 h5repack_big.h5 - h5repack_deflate.h5 + h5repack_deflate.h5 h5repack_deflate_out.h5 h5repack_early2.h5 h5repack_early.h5 @@ -588,7 +647,7 @@ h5repack_refs.h5 h5repack_shuffle.h5 h5repack_shuffle_out.h5 - h5repack_soffset.h5 + h5repack_soffset.h5 h5repack_soffset_out.h5 h5repack_szip.h5 h5repack_szip_out.h5 @@ -628,14 +687,14 @@ # Each run generates "<file>.out.h5" and the tool h5diff is used to # compare the input and output files # -# the tests are the same as the program h5repacktst, but run from the CLI +# the tests are the same as the program h5repacktst, but run from the CLI # # See which filters are usable (and skip tests for filters we # don't have). Do this by searching H5pubconf.h to see which # filters are defined. -# detect whether the encoder is present. +# detect whether the encoder is present. set (USE_FILTER_SZIP_ENCODER "no") if (HDF5_ENABLE_SZIP_ENCODING) set (USE_FILTER_SZIP_ENCODER ${testh5repack_detect_szip}) @@ -649,7 +708,7 @@ set (USE_FILTER_SZIP "true") endif (H5_HAVE_FILTER_SZIP) -# copy files (these files have no filters) +# copy files (these files have no filters) ADD_H5_TEST (fill "TEST" ${FILE0}) ADD_H5_TEST (objs "TEST" ${FILE1}) ADD_H5_TEST (attr "TEST" ${FILE2}) @@ -666,8 +725,8 @@ set (TESTTYPE "SKIP") endif (NOT USE_FILTER_DEFLATE) ADD_H5_TEST (gzip_individual ${TESTTYPE} ${arg}) - -# gzip for all + +# gzip for all set (arg ${FILE4} -f GZIP=1) set (TESTTYPE "TEST") if (NOT USE_FILTER_DEFLATE) @@ -681,7 +740,7 @@ if (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) - ADD_H5_TEST (szip_individual ${TESTTYPE} ${arg}) + ADD_H5_TEST (szip_individual ${TESTTYPE} ${arg}) # szip for all set (arg ${FILE4} -f SZIP=8,NN) @@ -689,16 +748,16 @@ if (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) - ADD_H5_TEST (szip_all ${TESTTYPE} ${arg}) + ADD_H5_TEST (szip_all ${TESTTYPE} ${arg}) # shuffle with individual object set (arg ${FILE4} -f dset2:SHUF -l dset2:CHUNK=20x10) - ADD_H5_TEST (shuffle_individual "TEST" ${arg}) + ADD_H5_TEST (shuffle_individual "TEST" ${arg}) # shuffle for all set (arg ${FILE4} -f SHUF) ADD_H5_TEST (shuffle_all "TEST" ${arg}) - + # fletcher32 with individual object set (arg ${FILE4} -f dset2:FLET -l dset2:CHUNK=20x10) ADD_H5_TEST (fletcher_individual "TEST" ${arg}) @@ -722,7 +781,7 @@ set (TESTTYPE "SKIP") endif (NOT USE_FILTER_DEFLATE) ADD_H5_CMP_TEST (gzip_verbose_filters "O?...ing file[^\n]+\n" ${TESTTYPE} 0 ${arg}) - + ########################################################### # the following tests assume the input files have filters ########################################################### @@ -734,7 +793,7 @@ set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) ADD_H5_TEST (szip_copy ${TESTTYPE} ${arg}) - + # szip remove set (arg ${FILE7} --filter=dset_szip:NONE) set (TESTTYPE "TEST") @@ -742,7 +801,7 @@ set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP) ADD_H5_TEST (szip_remove ${TESTTYPE} ${arg}) - + # deflate copy set (arg ${FILE8}) set (TESTTYPE "TEST") @@ -758,7 +817,7 @@ set (TESTTYPE "SKIP") endif (NOT USE_FILTER_DEFLATE) ADD_H5_TEST (deflate_remove ${TESTTYPE} ${arg}) - + # shuffle copy set (arg ${FILE9}) ADD_H5_TEST (shuffle_copy "TEST" ${arg}) @@ -813,14 +872,14 @@ if (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP OR NOT USE_FILTER_DEFLATE) set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_SZIP OR NOT USE_FILTER_DEFLATE) - ADD_H5_TEST (deflate_convert ${TESTTYPE} ${arg}) + ADD_H5_TEST (deflate_convert ${TESTTYPE} ${arg}) set (arg ${FILE7} -f dset_szip:GZIP=1) set (TESTTYPE "TEST") if (NOT USE_FILTER_SZIP OR NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_DEFLATE) set (TESTTYPE "SKIP") endif (NOT USE_FILTER_SZIP OR NOT USE_FILTER_SZIP_ENCODER OR NOT USE_FILTER_DEFLATE) - ADD_H5_TEST (szip_convert ${TESTTYPE} ${arg}) + ADD_H5_TEST (szip_convert ${TESTTYPE} ${arg}) #limit set (arg ${FILE4} -f GZIP=1 -m 1024) @@ -836,7 +895,7 @@ if (NOT USE_FILTER_DEFLATE) set (TESTTYPE "SKIP") endif (NOT USE_FILTER_DEFLATE) - ADD_H5_TEST (deflate_file ${TESTTYPE} ${arg}) + ADD_H5_TEST (deflate_file ${TESTTYPE} ${arg}) ######################################################### # layout options (these files have no filters) @@ -865,18 +924,18 @@ ADD_H5_VERIFY_TEST (contig_small_compa "TEST" 0 ${FILE18} contig_small COMPACT -l contig_small:COMPA) ADD_H5_VERIFY_TEST (contig_small_fixed_compa "TEST" 0 ${FILE18} chunked_small_fixed COMPACT -l chunked_small_fixed:COMPA) -#--------------------------------------------------------------------------- -# Test file contains chunked datasets (need multiple dsets) with +#--------------------------------------------------------------------------- +# Test file contains chunked datasets (need multiple dsets) with # unlimited max dims. (HDFFV-7933) # Use first dset to test. #--------------------------------------------------------------------------- # chunk to chunk - specify chunk dim bigger than any current dim ADD_H5_VERIFY_TEST (chunk2chunk "TEST" 0 h5repack_layout3.h5 chunk_unlimit1 CHUNK -l chunk_unlimit1:CHUNK=100x300) -# chunk to contiguous +# chunk to contiguous ADD_H5_VERIFY_TEST (chunk2conti "TEST" 0 h5repack_layout3.h5 chunk_unlimit1 CONTI -l chunk_unlimit1:CONTI) -# chunk to compact - convert big dataset (should be > 64k) for this purpose, +# chunk to compact - convert big dataset (should be > 64k) for this purpose, # should remain as original layout (chunk) ADD_H5_VERIFY_TEST (chunk2compa "TEST" 0 h5repack_layout3.h5 chunk_unlimit1 CHUNK -l chunk_unlimit1:COMPA) @@ -884,7 +943,7 @@ # Test -f for some specific cases. Chunked dataset with unlimited max dims. # (HDFFV-8012) #-------------------------------------------------------------------------- -# - should not fail +# - should not fail # - should not change max dims from unlimit # chunk dim is bigger than dataset dim. ( dset size < 64k ) @@ -900,13 +959,13 @@ ADD_H5_TEST (error4 "TEST" h5repack_layout3.h5 -f NONE) #-------------------------------------------------------------------------- -# Test base: Convert CHUNK to CONTI for a chunked dataset with small dataset +# Test base: Convert CHUNK to CONTI for a chunked dataset with small dataset # (dset size < 64K) and with unlimited max dims on a condition as follow. # (HDFFV-8214) #-------------------------------------------------------------------------- # chunk dim is bigger than dataset dim. should succeed. ADD_H5_VERIFY_TEST (ckdim_biger "TEST" 0 h5repack_layout3.h5 chunk_unlimit2 CONTI -l chunk_unlimit2:CONTI) -# chunk dim is smaller than dataset dim. should succeed. +# chunk dim is smaller than dataset dim. should succeed. ADD_H5_VERIFY_TEST (ckdim_smaller "TEST" 0 h5repack_layout3.h5 chunk_unlimit3 CONTI -l chunk_unlimit3:CONTI) @@ -975,11 +1034,11 @@ ADD_H5_TEST (bug1814 "TEST" ${FILE_REF}) # test attribute with various references (bug1797 / HDFFV-5932) -# the references in attribute of compund or vlen datatype +# the references in attribute of compund or vlen datatype ADD_H5_TEST (HDFFV-5932 "TEST" ${FILE_ATTR_REF}) -# Add test for memory leak in attirbute. This test is verified by CTEST. -# 1. leak from vlen string +# Add test for memory leak in attirbute. This test is verified by CTEST. +# 1. leak from vlen string # 2. leak from compound type without reference member # (HDFFV-7840, ) # Note: this test is experimental for sharing test file among tools @@ -989,6 +1048,26 @@ ADD_H5_TEST_META (meta_short h5repack_layout.h5 -M 8192) ADD_H5_TEST_META (meta_long h5repack_layout.h5 --metadata_block_size=8192) +# VDS tests + +######################################################### +# layout options +######################################################### + ADD_H5_VERIFY_TEST (vds_dset_conti "TEST" 0 ${FILEV1} vds_dset CONTIGUOUS -l vds_dset:CONTI) + ADD_H5_VERIFY_TEST (vds_null_conti "TEST" 1 ${FILEV2} null CONTIGUOUS -l CONTI) + ADD_H5_VERIFY_TEST (vds_dset_compa "TEST" 0 ${FILEV1} vds_dset COMPACT -l vds_dset:COMPA) + ADD_H5_VERIFY_TEST (vds_null_compa "TEST" 1 ${FILEV2} null COMPACT -l COMPA) + +################################################################ +# layout conversions +############################################################### + ADD_H5_VERIFY_TEST (vds_compa_conti "TEST" 0 ${FILEV4} vds_dset CONTIGUOUS -l vds_dset:CONTI) + ADD_H5_VERIFY_TEST (vds_compa_compa "TEST" 0 ${FILEV4} vds_dset COMPACT -l vds_dset:COMPA) + ADD_H5_VERIFY_TEST (vds_conti_compa "TEST" 0 ${FILEV4} vds_dset COMPACT -l vds_dset:COMPA) + ADD_H5_VERIFY_TEST (vds_conti_conti "TEST" 0 ${FILEV4} vds_dset CONTIGUOUS -l vds_dset:CONTI) + ADD_H5_VERIFY_TEST (vds_compa "TEST" 0 ${FILEV4} vds_dset COMPACT -l vds_dset:COMPA) + ADD_H5_VERIFY_TEST (vds_conti "TEST" 0 ${FILEV4} vds_dset CONTIGUOUS -l vds_dset:CONTI) + ############################################################################## ### P L U G I N T E S T S ############################################################################## diff --git a/tools/h5repack/h5repack.sh.in b/tools/h5repack/h5repack.sh.in index 4a32491..478ca36 100644 --- a/tools/h5repack/h5repack.sh.in +++ b/tools/h5repack/h5repack.sh.in @@ -18,7 +18,7 @@ # Modification: # Pedro Vicente Nunes, 11/15/2006 # Added $FILEN variables for file names -# +# srcdir=@srcdir@ @@ -32,7 +32,7 @@ EXIT_FAILURE=1 H5REPACK=h5repack # The tool name H5REPACK_BIN=`pwd`/$H5REPACK # The path of the tool binary -H5DIFF=../h5diff/h5diff # The h5diff tool name +H5DIFF=../h5diff/h5diff # The h5diff tool name H5DIFF_BIN=`pwd`/$H5DIFF # The path of the h5diff tool binary H5DUMP=../h5dump/h5dump # The h5dump tool name @@ -45,8 +45,8 @@ DIRNAME='dirname' LS='ls' AWK='awk' -H5DETECTSZIP=testh5repack_detect_szip -H5DETECTSZIP_BIN=`pwd`/$H5DETECTSZIP +H5DETECTSZIP=testh5repack_detect_szip +H5DETECTSZIP_BIN=`pwd`/$H5DETECTSZIP nerrors=0 @@ -113,6 +113,29 @@ $SRC_TOOLS_TESTFILES/tfamily00007.h5 $SRC_TOOLS_TESTFILES/tfamily00008.h5 $SRC_TOOLS_TESTFILES/tfamily00009.h5 $SRC_TOOLS_TESTFILES/tfamily00010.h5 +$SRC_TOOLS_TESTFILES/vds/1_a.h5 +$SRC_TOOLS_TESTFILES/vds/1_b.h5 +$SRC_TOOLS_TESTFILES/vds/1_c.h5 +$SRC_TOOLS_TESTFILES/vds/1_d.h5 +$SRC_TOOLS_TESTFILES/vds/1_e.h5 +$SRC_TOOLS_TESTFILES/vds/1_f.h5 +$SRC_TOOLS_TESTFILES/vds/1_vds.h5 +$SRC_TOOLS_TESTFILES/vds/2_a.h5 +$SRC_TOOLS_TESTFILES/vds/2_b.h5 +$SRC_TOOLS_TESTFILES/vds/2_c.h5 +$SRC_TOOLS_TESTFILES/vds/2_d.h5 +$SRC_TOOLS_TESTFILES/vds/2_e.h5 +$SRC_TOOLS_TESTFILES/vds/2_vds.h5 +$SRC_TOOLS_TESTFILES/vds/3_1_vds.h5 +$SRC_TOOLS_TESTFILES/vds/3_2_vds.h5 +$SRC_TOOLS_TESTFILES/vds/4_0.h5 +$SRC_TOOLS_TESTFILES/vds/4_1.h5 +$SRC_TOOLS_TESTFILES/vds/4_2.h5 +$SRC_TOOLS_TESTFILES/vds/4_vds.h5 +$SRC_TOOLS_TESTFILES/vds/5_a.h5 +$SRC_TOOLS_TESTFILES/vds/5_b.h5 +$SRC_TOOLS_TESTFILES/vds/5_c.h5 +$SRC_TOOLS_TESTFILES/vds/5_vds.h5 " LIST_OTHER_TEST_FILES=" @@ -148,10 +171,10 @@ COPY_TESTFILES_TO_TESTDIR() INODE_SDIR=`$LS -i -d $SDIR | $AWK -F' ' '{print $1}'` INODE_DDIR=`$LS -i -d $TESTDIR | $AWK -F' ' '{print $1}'` if [ "$INODE_SDIR" != "$INODE_DDIR" ]; then - $CP -f $tstfile $TESTDIR + $CP -f $tstfile $TESTDIR if [ $? -ne 0 ]; then echo "Error: FAILED to copy $tstfile ." - + # Comment out this to CREATE expected file exit $EXIT_FAILURE fi @@ -203,12 +226,12 @@ SKIP() { # Call the h5diff tool # -DIFFTEST() +DIFFTEST() { VERIFY h5diff output $@ ( cd $TESTDIR - $RUNSERIAL $H5DIFF_BIN -q "$@" + $RUNSERIAL $H5DIFF_BIN -q "$@" ) RET=$? if [ $RET != 0 ] ; then @@ -217,7 +240,7 @@ DIFFTEST() else echo " PASSED" fi - + } # Call h5repack @@ -225,7 +248,7 @@ DIFFTEST() # call TOOLTEST_MAIN and delete $output file -TOOLTEST() +TOOLTEST() { echo $@ infile=$2 @@ -251,7 +274,7 @@ TOOLTEST() } #------------------------------------------ -# Verifying layouts of a dataset +# Verifying layouts of a dataset VERIFY_LAYOUT_DSET() { layoutfile=layout-$1.$2 @@ -263,9 +286,9 @@ VERIFY_LAYOUT_DSET() shift shift shift - + TESTING $H5REPACK $@ - ( + ( cd $TESTDIR $RUNSERIAL $H5REPACK_BIN "$@" $infile $outfile ) @@ -277,7 +300,7 @@ VERIFY_LAYOUT_DSET() echo " PASSED" DIFFTEST $infile $outfile fi - + #--------------------------------- # check the layout from a dataset VERIFY "a dataset layout" @@ -309,9 +332,9 @@ VERIFY_LAYOUT_ALL() shift shift shift - + TESTING $H5REPACK $@ - ( + ( cd $TESTDIR $RUNSERIAL $H5REPACK_BIN "$@" $infile $outfile ) @@ -323,8 +346,8 @@ VERIFY_LAYOUT_ALL() echo " PASSED" DIFFTEST $infile $outfile fi - - + + #--------------------------------- # check the layout from a dataset # check if the other layouts still exsit @@ -351,7 +374,7 @@ VERIFY_LAYOUT_ALL() echo " PASSED" fi fi - else + else # if COMPACT if [ $expectlayout = "COMPACT" ]; then TESTING $H5DUMP_BIN -pH $outfile @@ -403,7 +426,7 @@ VERIFY_LAYOUT_ALL() # same as TOOLTEST, but it uses the old syntax -i input_file -o output_file # -TOOLTEST0() +TOOLTEST0() { infile=$2 outfile=out-$1.$2 @@ -431,7 +454,7 @@ TOOLTEST0() # same as TOOLTEST, but it uses without -i -o options # used to test the family driver, where these files reside # -TOOLTEST1() +TOOLTEST1() { infile=$2 outfile=out-$1.$2 @@ -446,19 +469,19 @@ TOOLTEST1() ) RET=$? if [ $RET != 0 ] ; then - echo "*FAILED*" - nerrors="`expr $nerrors + 1`" + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" else - echo " PASSED" - DIFFTEST $infile $outfile + echo " PASSED" + DIFFTEST $infile $outfile fi rm -f $outfile } - + # This is same as TOOLTEST() with comparing display output # from -v option # -TOOLTESTV() +TOOLTESTV() { expect="$TESTDIR/$2.tst" actual="$TESTDIR/`basename $2 .ddl`.out" @@ -468,7 +491,7 @@ TOOLTESTV() outfile=out-$1.$2 shift shift - + # Run test. TESTING $H5REPACK $@ ( @@ -477,11 +500,11 @@ TOOLTESTV() ) >$actual 2>$actual_err RET=$? if [ $RET != 0 ] ; then - echo "*FAILED*" - nerrors="`expr $nerrors + 1`" + echo "*FAILED*" + nerrors="`expr $nerrors + 1`" else - echo " PASSED" - DIFFTEST $infile $outfile + echo " PASSED" + DIFFTEST $infile $outfile fi # display output compare @@ -497,15 +520,15 @@ TOOLTESTV() nerrors="`expr $nerrors + 1`" test yes = "$verbose" && diff -c $expect $actual |sed 's/^/ /' fi - + rm -f $actual $actual_err rm -f $outfile } - + # This is same as TOOLTESTV() with comparing h5dump output # from -pH option # -TOOLTEST_DUMP() +TOOLTEST_DUMP() { infile=$2 outfile=out-$1.$2 @@ -515,7 +538,7 @@ TOOLTEST_DUMP() shift shift - + # Run test. TESTING $H5REPACK $@ ( @@ -531,12 +554,12 @@ TOOLTEST_DUMP() VERIFY h5dump output $@ ( cd $TESTDIR - $RUNSERIAL $H5DUMP_BIN -pH $outfile + $RUNSERIAL $H5DUMP_BIN -pH $outfile ) >$actual 2>$actual_err cat $actual_err >> $actual RET=$? - + fi if cmp -s $expect $actual; then @@ -547,7 +570,7 @@ TOOLTEST_DUMP() nerrors="`expr $nerrors + 1`" test yes = "$verbose" && diff -c $expect $actual |sed 's/^/ /' fi - + rm -f $actual $actual_err rm -f $outfile } @@ -611,14 +634,14 @@ TOOLTEST_META() # verify sizes. MESSAGE "Verify the sizes of both output files ($size1 vs $size2)" if [ $size1 -lt $size2 ]; then - # pass - echo " PASSED" + # pass + echo " PASSED" else - #fail - echo "*FAILED*" + #fail + echo "*FAILED*" nerrors="`expr $nerrors + 1`" fi - + rm -f $outfile } # ADD_HELP_TEST @@ -648,7 +671,7 @@ TOOLTEST_HELP() { echo " Expected output (*.txt) differs from actual output (*.out)" nerrors="`expr $nerrors + 1`" fi - + # Clean up output file if test -z "$HDF5_NOCLEANUP"; then rm -f $actual $actual_err @@ -674,28 +697,28 @@ STDOUT_FILTER() { # Each run generates "<file>.out.h5" and the tool h5diff is used to # compare the input and output files # -# the tests are the same as the program h5repacktst, but run from the CLI +# the tests are the same as the program h5repacktst, but run from the CLI # # See which filters are usable (and skip tests for filters we # don't have). Do this by searching H5pubconf.h to see which # filters are defined. -# detect whether the encoder is present. +# detect whether the encoder is present. USE_FILTER_SZIP_ENCODER="no"; if test $USE_FILTER_SZIP = "yes"; then USE_FILTER_SZIP_ENCODER=`$RUNSERIAL $H5DETECTSZIP_BIN` fi ############################################################################## -### T H E T E S T S +### T H E T E S T S ############################################################################## # prepare for test COPY_TESTFILES_TO_TESTDIR TOOLTEST_HELP h5repack-help.txt -h -# copy files (these files have no filters) +# copy files (these files have no filters) TOOLTEST fill h5repack_fill.h5 TOOLTEST objs h5repack_objs.h5 TOOLTEST attr h5repack_attr.h5 @@ -719,8 +742,8 @@ if test $USE_FILTER_DEFLATE != "yes" ; then else TOOLTEST gzip_individual $arg fi - -# gzip for all + +# gzip for all arg="h5repack_layout.h5 -f GZIP=1" if test $USE_FILTER_DEFLATE != "yes" ; then SKIP $arg @@ -733,7 +756,7 @@ arg="h5repack_layout.h5 -f dset2:SZIP=8,EC -l dset2:CHUNK=20x10" if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" ; then SKIP $arg else - TOOLTEST szip_individual $arg + TOOLTEST szip_individual $arg fi # szip for all @@ -741,18 +764,18 @@ arg="h5repack_layout.h5 -f SZIP=8,NN" if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" ; then SKIP $arg else - TOOLTEST szip_all $arg + TOOLTEST szip_all $arg fi # shuffle with individual object arg="h5repack_layout.h5 -f dset2:SHUF -l dset2:CHUNK=20x10" -TOOLTEST shuffle_individual $arg - +TOOLTEST shuffle_individual $arg + # shuffle for all arg="h5repack_layout.h5 -f SHUF" TOOLTEST shuffle_all $arg - + # fletcher32 with individual object arg="h5repack_layout.h5 -f dset2:FLET -l dset2:CHUNK=20x10" TOOLTEST fletcher_individual $arg @@ -777,7 +800,7 @@ else # compare output TOOLTESTV gzip_verbose_filters $arg fi - + ########################################################### # the following tests assume the input files have filters ########################################################### @@ -789,7 +812,7 @@ if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" ; then else TOOLTEST szip_copy $arg fi - + # szip remove arg="h5repack_szip.h5 --filter=dset_szip:NONE" if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" ; then @@ -797,7 +820,7 @@ if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" ; then else TOOLTEST szip_remove $arg fi - + # deflate copy arg="h5repack_deflate.h5" if test $USE_FILTER_DEFLATE != "yes" ; then @@ -813,7 +836,7 @@ if test $USE_FILTER_DEFLATE != "yes" ; then else TOOLTEST deflate_remove $arg fi - + # shuffle copy arg="h5repack_shuffle.h5" TOOLTEST shuffle_copy $arg @@ -868,14 +891,14 @@ arg="h5repack_deflate.h5 -f dset_deflate:SZIP=8,NN" if test $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_SZIP != "yes" -o $USE_FILTER_DEFLATE != "yes" ; then SKIP $arg else - TOOLTEST deflate_convert $arg + TOOLTEST deflate_convert $arg fi arg="h5repack_szip.h5 -f dset_szip:GZIP=1" if test $USE_FILTER_SZIP != "yes" -o $USE_FILTER_SZIP_ENCODER != "yes" -o $USE_FILTER_DEFLATE != "yes" ; then SKIP $arg else - TOOLTEST szip_convert $arg + TOOLTEST szip_convert $arg fi @@ -890,9 +913,9 @@ fi #file arg="h5repack_layout.h5 -e h5repack.info" if test $USE_FILTER_DEFLATE != "yes" ; then - SKIP $arg + SKIP $arg else - TOOLTEST deflate_file $arg + TOOLTEST deflate_file $arg fi ######################################################### @@ -937,18 +960,18 @@ VERIFY_LAYOUT_DSET contig_small_compa h5repack_layout2.h5 contig_small COMPACT - VERIFY_LAYOUT_DSET contig_small_fixed_compa h5repack_layout2.h5 chunked_small_fixed COMPACT -l chunked_small_fixed:COMPA -#--------------------------------------------------------------------------- -# Test file contains chunked datasets (need multiple dsets) with +#--------------------------------------------------------------------------- +# Test file contains chunked datasets (need multiple dsets) with # unlimited max dims. (HDFFV-7933) # Use first dset to test. #--------------------------------------------------------------------------- # chunk to chunk - specify chunk dim bigger than any current dim VERIFY_LAYOUT_DSET chunk2chunk h5repack_layout3.h5 chunk_unlimit1 CHUNK -l chunk_unlimit1:CHUNK=100x300 -# chunk to contiguous +# chunk to contiguous VERIFY_LAYOUT_DSET chunk2conti h5repack_layout3.h5 chunk_unlimit1 CONTI -l chunk_unlimit1:CONTI -# chunk to compact - convert big dataset (should be > 64k) for this purpose, +# chunk to compact - convert big dataset (should be > 64k) for this purpose, # should remain as original layout (chunk) VERIFY_LAYOUT_DSET chunk2compa h5repack_layout3.h5 chunk_unlimit1 CHUNK -l chunk_unlimit1:COMPA @@ -956,7 +979,7 @@ VERIFY_LAYOUT_DSET chunk2compa h5repack_layout3.h5 chunk_unlimit1 CHUNK -l chunk # Test -f for some specific cases. Chunked dataset with unlimited max dims. # (HDFFV-8012) #-------------------------------------------------------------------------- -# - should not fail +# - should not fail # - should not change max dims from unlimit # chunk dim is bigger than dataset dim. ( dset size < 64k ) @@ -972,14 +995,14 @@ VERIFY_LAYOUT_DSET error3 h5repack_layout3.h5 chunk_unlimit3 H5S_UNLIMITED -f ch TOOLTEST error4 h5repack_layout3.h5 -f NONE #-------------------------------------------------------------------------- -# Test base: Convert CHUNK to CONTI for a chunked dataset with small dataset +# Test base: Convert CHUNK to CONTI for a chunked dataset with small dataset # (dset size < 64K) and with unlimited max dims on a condition as follow. # (HDFFV-8214) #-------------------------------------------------------------------------- # chunk dim is bigger than dataset dim. should succeed. VERIFY_LAYOUT_DSET ckdim_biger h5repack_layout3.h5 chunk_unlimit2 CONTI -l chunk_unlimit2:CONTI -# chunk dim is smaller than dataset dim. should succeed. +# chunk dim is smaller than dataset dim. should succeed. VERIFY_LAYOUT_DSET ckdim_smaller h5repack_layout3.h5 chunk_unlimit3 CONTI -l chunk_unlimit3:CONTI @@ -1022,7 +1045,7 @@ if test $USE_FILTER_DEFLATE != "yes" ; then SKIP $arg else TOOLTEST0 old_style_layout_short_switches $arg -fi +fi # add a userblock to file arg="h5repack_objs.h5 -u ublock.bin -b 2048" @@ -1049,20 +1072,40 @@ TOOLTEST1 family tfamily%05d.h5 TOOLTEST bug1814 h5repack_refs.h5 # test attribute with various references (bug1797 / HDFFV-5932) -# the references in attribute of compund or vlen datatype -TOOLTEST HDFFV-5932 h5repack_attr_refs.h5 +# the references in attribute of compund or vlen datatype +TOOLTEST HDFFV-5932 h5repack_attr_refs.h5 -# Add test for memory leak in attirbute. This test is verified by CTEST. -# 1. leak from vlen string +# Add test for memory leak in attirbute. This test is verified by CTEST. +# 1. leak from vlen string # 2. leak from compound type without reference member # (HDFFV-7840, ) # Note: this test is experimental for sharing test file among tools TOOLTEST HDFFV-7840 h5diff_attr1.h5 -# tests for metadata block size option +# tests for metadata block size option TOOLTEST_META meta_short h5repack_layout.h5 -M 8192 TOOLTEST_META meta_long h5repack_layout.h5 --metadata_block_size=8192 +# VDS tests + +######################################################### +# layout options +######################################################### +VERIFY_LAYOUT_DSET vds_dset_conti 1_vds.h5 vds_dset CONTIGUOUS -l vds_dset:CONTI +VERIFY_LAYOUT_ALL vds_null_conti 2_vds.h5 CONTIGUOUS -l CONTI +VERIFY_LAYOUT_DSET vds_dset_compa 1_vds.h5 vds_dset COMPACT -l vds_dset:COMPA +VERIFY_LAYOUT_ALL vds_null_compa 2_vds.h5 COMPACT -l COMPA + +################################################################ +# layout conversions +############################################################### +VERIFY_LAYOUT_DSET vds_compa_conti 4_vds.h5 vds_dset CONTIGUOUS -l vds_dset:CONTI +VERIFY_LAYOUT_DSET vds_compa_compa 4_vds.h5 vds_dset COMPACT -l vds_dset:COMPA +VERIFY_LAYOUT_DSET vds_conti_compa 4_vds.h5 vds_dset COMPACT -l vds_dset:COMPA +VERIFY_LAYOUT_DSET vds_conti_conti 4_vds.h5 vds_dset CONTIGUOUS -l vds_dset:CONTI +VERIFY_LAYOUT_DSET vds_compa 4_vds.h5 vds_dset COMPACT -l vds_dset:COMPA +VERIFY_LAYOUT_DSET vds_conti 4_vds.h5 vds_dset CONTIGUOUS -l vds_dset:CONTI + # Clean up temporary files/directories CLEAN_TESTFILES_AND_TESTDIR diff --git a/tools/h5stat/h5stat.c b/tools/h5stat/h5stat.c index c19aba5..ac6ca23 100644 --- a/tools/h5stat/h5stat.c +++ b/tools/h5stat/h5stat.c @@ -1342,8 +1342,8 @@ print_dataset_info(const iter_t *iter) printf("Dataset layout information:\n"); for(u = 0; u < H5D_NLAYOUTS; u++) - printf("\tDataset layout counts[%s]: %lu\n", (u == 0 ? "COMPACT" : - (u == 1 ? "CONTIG" : "CHUNKED")), iter->dset_layouts[u]); + printf("\tDataset layout counts[%s]: %lu\n", (u == H5D_COMPACT ? "COMPACT" : + (u == H5D_CONTIGUOUS ? "CONTIG" : (u == H5D_CHUNKED ? "CHUNKED" : "VIRTUAL"))), iter->dset_layouts[u]); printf("\tNumber of external files : %lu\n", iter->nexternal); printf("Dataset filters information:\n"); diff --git a/tools/h5stat/testfiles/h5stat_dims1.ddl b/tools/h5stat/testfiles/h5stat_dims1.ddl index c285ea4..07b2900 100644 --- a/tools/h5stat/testfiles/h5stat_dims1.ddl +++ b/tools/h5stat/testfiles/h5stat_dims1.ddl @@ -31,6 +31,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 23 Dataset layout counts[CHUNKED]: 0 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_dims2.ddl b/tools/h5stat/testfiles/h5stat_dims2.ddl index 769749e..dbccd05 100644 --- a/tools/h5stat/testfiles/h5stat_dims2.ddl +++ b/tools/h5stat/testfiles/h5stat_dims2.ddl @@ -22,6 +22,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 23 Dataset layout counts[CHUNKED]: 0 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_filters-d.ddl b/tools/h5stat/testfiles/h5stat_filters-d.ddl index 2e0bd64..6e6dd61 100644 --- a/tools/h5stat/testfiles/h5stat_filters-d.ddl +++ b/tools/h5stat/testfiles/h5stat_filters-d.ddl @@ -18,6 +18,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 1 Dataset layout counts[CONTIG]: 2 Dataset layout counts[CHUNKED]: 12 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 2 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_filters-dT.ddl b/tools/h5stat/testfiles/h5stat_filters-dT.ddl index 9ef3e82..b14ca9f 100644 --- a/tools/h5stat/testfiles/h5stat_filters-dT.ddl +++ b/tools/h5stat/testfiles/h5stat_filters-dT.ddl @@ -18,6 +18,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 1 Dataset layout counts[CONTIG]: 2 Dataset layout counts[CHUNKED]: 12 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 2 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_filters.ddl b/tools/h5stat/testfiles/h5stat_filters.ddl index 24522cd..1a4fd72 100644 --- a/tools/h5stat/testfiles/h5stat_filters.ddl +++ b/tools/h5stat/testfiles/h5stat_filters.ddl @@ -56,6 +56,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 1 Dataset layout counts[CONTIG]: 2 Dataset layout counts[CHUNKED]: 12 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 2 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_links2.ddl b/tools/h5stat/testfiles/h5stat_links2.ddl index 09bf937..4622884 100644 --- a/tools/h5stat/testfiles/h5stat_links2.ddl +++ b/tools/h5stat/testfiles/h5stat_links2.ddl @@ -64,6 +64,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 23 Dataset layout counts[CHUNKED]: 0 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_newgrat.ddl b/tools/h5stat/testfiles/h5stat_newgrat.ddl index 33d756b..e305f58 100644 --- a/tools/h5stat/testfiles/h5stat_newgrat.ddl +++ b/tools/h5stat/testfiles/h5stat_newgrat.ddl @@ -54,6 +54,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 1 Dataset layout counts[CHUNKED]: 0 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_numattrs2.ddl b/tools/h5stat/testfiles/h5stat_numattrs2.ddl index 1313aec..ccb23c1 100644 --- a/tools/h5stat/testfiles/h5stat_numattrs2.ddl +++ b/tools/h5stat/testfiles/h5stat_numattrs2.ddl @@ -65,6 +65,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 23 Dataset layout counts[CHUNKED]: 0 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/h5stat/testfiles/h5stat_tsohm.ddl b/tools/h5stat/testfiles/h5stat_tsohm.ddl index 37de79b..4cf33fc 100644 --- a/tools/h5stat/testfiles/h5stat_tsohm.ddl +++ b/tools/h5stat/testfiles/h5stat_tsohm.ddl @@ -53,6 +53,7 @@ Dataset layout information: Dataset layout counts[COMPACT]: 0 Dataset layout counts[CONTIG]: 0 Dataset layout counts[CHUNKED]: 3 + Dataset layout counts[VIRTUAL]: 0 Number of external files : 0 Dataset filters information: Number of datasets with: diff --git a/tools/lib/h5tools.h b/tools/lib/h5tools.h index d6c3720..6512f9b 100644 --- a/tools/lib/h5tools.h +++ b/tools/lib/h5tools.h @@ -81,7 +81,7 @@ #define FLETCHER32 "CHECKSUM FLETCHER32" #define SZIP "COMPRESSION SZIP" #define NBIT "COMPRESSION NBIT" -#define SCALEOFFSET "COMPRESSION SCALEOFFSET" +#define SCALEOFFSET "COMPRESSION SCALEOFFSET" #define SCALEOFFSET_MINBIT "MIN BITS" #define STORAGE_LAYOUT "STORAGE_LAYOUT" #define CONTIGUOUS "CONTIGUOUS" @@ -93,6 +93,16 @@ #define PACKED_BITS "PACKED_BITS" #define PACKED_OFFSET "OFFSET" #define PACKED_LENGTH "LENGTH" +#define VDS_VIRTUAL "VIRTUAL" +#define VDS_MAPPING "MAPPING" +#define VDS_SOURCE "SOURCE" +#define VDS_REG_HYPERSLAB "SELECTION REGULAR_HYPERSLAB" +#define VDS_IRR_HYPERSLAB "SELECTION IRREGULAR_HYPERSLAB" +#define VDS_POINT "POINT" +#define VDS_SRC_FILE "FILE" +#define VDS_SRC_DATASET "DATASET" +#define VDS_NONE "SELECTION NONE" +#define VDS_ALL "SELECTION ALL" #define BEGIN "{" #define END "}" @@ -182,6 +192,15 @@ typedef struct h5tools_dump_header_t { const char *dataspacedimbegin; const char *dataspacedimend; + const char *virtualselectionbegin; + const char *virtualselectionend; + const char *virtualselectionblockbegin; + const char *virtualselectionblockend; + const char *virtualfilenamebegin; + const char *virtualfilenameend; + const char *virtualdatasetnamebegin; + const char *virtualdatasetnameend; + } h5tools_dump_header_t; /* diff --git a/tools/lib/h5tools_dump.c b/tools/lib/h5tools_dump.c index 26cac47..3a06d3a 100644 --- a/tools/lib/h5tools_dump.c +++ b/tools/lib/h5tools_dump.c @@ -179,6 +179,15 @@ BLOCK, /*blockbegin */ "", /*dataspacedescriptionend */ "(", /*dataspacedimbegin */ ")", /*dataspacedimend */ + +"", /*virtualselectionbegin */ +"", /*virtualselectionend */ +"{", /*virtualselectionblockbegin */ +"}", /*virtualselectionblockend */ +"\"", /*virtualfilenamebeginbegin */ +"\"", /*virtualfilenamebeginend */ +"\"", /*virtualdatasetnamebegin */ +"\"", /*virtualdtatasetnameend */ }; const h5tools_dump_header_t* h5tools_dump_header_format; @@ -216,6 +225,14 @@ void h5tools_print_dims(h5tools_str_t *buffer, hsize_t *s, int dims); void h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, h5tools_context_t *ctx, struct subset_t *sset, int dims); +void h5tools_print_virtual_selection(hid_t vspace, hid_t dcpl_id, size_t index, + FILE *stream, const h5tool_format_t *info, + h5tools_context_t *ctx/*in,out*/, + h5tools_str_t *buffer/*string into which to render */, + hsize_t *curr_pos/*total data element position*/, + size_t ncols, hsize_t region_elmt_counter/*element counter*/, + hsize_t elmt_counter); + void h5tools_dump_init(void) { @@ -368,7 +385,7 @@ h5tools_dump_simple_data(FILE *stream, const h5tool_format_t *info, hid_t contai } ctx->need_prefix = TRUE; - + if(FALSE == dimension_break) elmt_counter = 0; } /* end for (i = 0; i < nelmts... */ @@ -810,7 +827,7 @@ h5tools_print_region_data_points(hid_t region_space, hid_t region_id, HGOTO_ERROR(FAIL, H5E_tools_min_id_g, "Could not allocate buffer for dims"); dims1[0] = npoints; - + /* Create dataspace for reading buffer */ if((mem_space = H5Screate_simple(1, dims1, NULL)) < 0) HGOTO_ERROR(FAIL, H5E_tools_min_id_g, "H5Screate_simple failed"); @@ -1457,7 +1474,7 @@ h5tools_dump_simple_subset(FILE *stream, const h5tool_format_t *info, h5tools_co if((f_space = H5Dget_space(dset)) < 0) H5E_THROW(FAIL, H5E_tools_min_id_g, "H5Dget_space failed"); - + if((sndims = H5Sget_simple_extent_ndims(f_space)) < 0) H5E_THROW(FAIL, H5E_tools_min_id_g, "H5Sget_simple_extent_ndims failed"); ctx->ndims = (unsigned)sndims; @@ -1522,6 +1539,7 @@ h5tools_dump_simple_dset(FILE *stream, const h5tool_format_t *info, h5tools_cont /* Hyperslab info */ hsize_t hs_offset[H5S_MAX_RANK]; /* starting offset */ hsize_t hs_size[H5S_MAX_RANK]; /* size this pass */ + //hsize_t hs_count[H5S_MAX_RANK]; /* size this pass */ hsize_t hs_nelmts; /* elements in request */ /* VL data special information */ @@ -1604,9 +1622,11 @@ h5tools_dump_simple_dset(FILE *stream, const h5tool_format_t *info, h5tools_cont hs_size[i] = MIN(total_size[i] - hs_offset[i], sm_size[i]); ctx->p_max_idx[i] = ctx->p_min_idx[i] + hs_size[i]; hs_nelmts *= hs_size[i]; +// hs_count[i] = 1; } H5Sselect_hyperslab(f_space, H5S_SELECT_SET, hs_offset, NULL, hs_size, NULL); +// H5Sselect_hyperslab(f_space, H5S_SELECT_SET, hs_offset, NULL, hs_count, hs_size); H5Sselect_hyperslab(sm_space, H5S_SELECT_SET, zero, NULL, &hs_nelmts, NULL); } else { @@ -1743,7 +1763,7 @@ CATCH *------------------------------------------------------------------------- */ int -h5tools_dump_dset(FILE *stream, const h5tool_format_t *info, h5tools_context_t *ctx, +h5tools_dump_dset(FILE *stream, const h5tool_format_t *info, h5tools_context_t *ctx, hid_t dset, struct subset_t *sset) { hid_t f_space = -1; @@ -1819,7 +1839,7 @@ done: *------------------------------------------------------------------------- */ int -h5tools_dump_mem(FILE *stream, const h5tool_format_t *info, h5tools_context_t *ctx, +h5tools_dump_mem(FILE *stream, const h5tool_format_t *info, h5tools_context_t *ctx, hid_t obj_id, hid_t type, hid_t space, void *mem) { HERR_INIT(int, SUCCEED) @@ -1898,18 +1918,18 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ } else h5tools_str_append(buffer, "\"%s\"", obj->objname); - } + } else { error_msg("unknown committed type.\n"); h5tools_setstatus(EXIT_FAILURE); } return ret_value; - } - + } + if (info->line_ncols > 0) ncols = info->line_ncols; - + switch (type_class) { case H5T_INTEGER: if (H5Tequal(type, H5T_STD_I8BE) == TRUE) { @@ -2231,7 +2251,7 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ HERROR(H5E_tools_g, H5E_tools_min_id_g, "H5Tset_order failed"); } /* end if */ else if(order == H5T_ORDER_BE) { - if(H5Tset_order(str_type, H5T_ORDER_BE) < 0) + if(H5Tset_order(str_type, H5T_ORDER_BE) < 0) HERROR(H5E_tools_g, H5E_tools_min_id_g, "H5Tset_order failed"); } /* end if */ @@ -2262,7 +2282,7 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ HERROR(H5E_tools_g, H5E_tools_min_id_g, "H5Tset_order failed"); } /* end if */ else if(order == H5T_ORDER_BE) { - if(H5Tset_order(str_type, H5T_ORDER_BE) < 0) + if(H5Tset_order(str_type, H5T_ORDER_BE) < 0) HERROR(H5E_tools_g, H5E_tools_min_id_g, "H5Tset_order failed"); } /* end if */ @@ -2336,9 +2356,9 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ h5tools_str_reset(buffer); h5tools_str_append(buffer, "OPAQUE_TAG \"%s\";", ttag); h5tools_render_element(stream, info, ctx, buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + H5free_memory(ttag); - } + } ctx->indent_level--; ctx->need_prefix = TRUE; @@ -2352,7 +2372,7 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ if((snmembers = H5Tget_nmembers(type)) < 0) H5E_THROW(FAIL, H5E_tools_min_id_g, "H5Tget_nmembers failed"); nmembers = (unsigned)snmembers; - + h5tools_str_append(buffer, "H5T_COMPOUND %s", h5tools_dump_header_format->structblockbegin); h5tools_render_element(stream, info, ctx, buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -2407,7 +2427,7 @@ h5tools_print_datatype(FILE *stream, h5tools_str_t *buffer, const h5tool_format_ h5tools_str_reset(buffer); h5tools_print_datatype(stream, buffer, info, ctx, super, TRUE); - + if(H5Tclose(super) < 0) HERROR(H5E_tools_g, H5E_tools_min_id_g, "H5Tclose failed"); @@ -2595,7 +2615,7 @@ h5tools_print_enum(FILE *stream, h5tools_str_t *buffer, const h5tool_format_t *i if (info->line_ncols > 0) ncols = info->line_ncols; - + if((snmembs = H5Tget_nmembers(type)) < 0) H5E_THROW(FAIL, H5E_tools_min_id_g, "H5Tget_nmembers failed"); nmembs = (unsigned)snmembs; @@ -2735,7 +2755,7 @@ h5tools_dump_datatype(FILE *stream, const h5tool_format_t *info, ncols = info->line_ncols; ctx->need_prefix = TRUE; - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s ", h5tools_dump_header_format->datatypebegin, @@ -2757,7 +2777,7 @@ h5tools_dump_datatype(FILE *stream, const h5tool_format_t *info, /*------------------------------------------------------------------------- * Function: dump_dataspace * - * Purpose: Dump the dataspace. + * Purpose: Dump the dataspace. * * Return: void * @@ -2783,7 +2803,7 @@ h5tools_dump_dataspace(FILE *stream, const h5tool_format_t *info, ncols = info->line_ncols; ctx->need_prefix = TRUE; - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s ", h5tools_dump_header_format->dataspacebegin); @@ -2833,7 +2853,7 @@ h5tools_dump_oid(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s %d %s", OBJID, BEGIN, oid, END); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -2841,7 +2861,79 @@ h5tools_dump_oid(FILE *stream, const h5tool_format_t *info, h5tools_str_close(&buffer); } +/*------------------------------------------------------------------------- + * Function: print_virtual_selection + * + * Purpose: Print the virtual dataset selection. + * + * Return: void + *------------------------------------------------------------------------- + */ +void +h5tools_print_virtual_selection(hid_t vspace, hid_t dcpl_id, size_t index, + FILE *stream, const h5tool_format_t *info, + h5tools_context_t *ctx/*in,out*/, + h5tools_str_t *buffer/*string into which to render */, + hsize_t *curr_pos/*total data element position*/, + size_t ncols, hsize_t region_elmt_counter/*element counter*/, + hsize_t elmt_counter) +{ + switch(H5Sget_select_type(vspace)) { + case H5S_SEL_NONE: /* Nothing selected */ + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(buffer); + h5tools_str_append(buffer, "%s", VDS_NONE); + break; + case H5S_SEL_POINTS: /* Sequence of points selected */ + h5tools_str_reset(buffer); + h5tools_str_append(buffer, "%s %s ", VDS_POINT, h5tools_dump_header_format->virtualselectionblockbegin); + h5tools_str_dump_space_points(buffer, vspace, info); + h5tools_str_append(buffer, " %s", h5tools_dump_header_format->virtualselectionblockend); + break; + case H5S_SEL_HYPERSLABS: /* "New-style" hyperslab selection defined */ + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + h5tools_str_reset(buffer); + if (H5Sis_regular_hyperslab(vspace)) { + h5tools_str_append(buffer, "%s %s ", VDS_REG_HYPERSLAB, h5tools_dump_header_format->virtualselectionblockbegin); + h5tools_render_element(stream, info, ctx, buffer, curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + h5tools_str_reset(buffer); + h5tools_str_dump_space_slabs(buffer, vspace, info, ctx); + } + else { + h5tools_str_append(buffer, "%s %s ", VDS_IRR_HYPERSLAB, h5tools_dump_header_format->virtualselectionblockbegin); + h5tools_render_element(stream, info, ctx, buffer, curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + ctx->indent_level++; + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(buffer); + h5tools_str_dump_space_blocks(buffer, vspace, info); + ctx->indent_level--; + } + h5tools_render_element(stream, info, ctx, buffer, curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(buffer); + h5tools_str_append(buffer, "%s", h5tools_dump_header_format->virtualselectionblockend); + break; + case H5S_SEL_ALL: /* Entire extent selected */ + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(buffer); + h5tools_str_append(buffer, "%s", VDS_ALL); + break; + default: + h5tools_str_append(buffer, "Unknown Selection"); + } + h5tools_render_element(stream, info, ctx, buffer, curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); +} /*------------------------------------------------------------------------- * Function: dump_fill_value @@ -2925,19 +3017,18 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, */ ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s", STORAGE_LAYOUT, BEGIN); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - ctx->indent_level++; - - ctx->need_prefix = TRUE; - h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - stl = H5Pget_layout(dcpl_id); switch (stl) { case H5D_CHUNKED: + ctx->indent_level++; + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s ", CHUNKED); @@ -3000,8 +3091,13 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, h5tools_str_append(&buffer, "SIZE " HSIZE_T_FORMAT, storage_size); } h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + ctx->indent_level--; break; case H5D_COMPACT: + ctx->indent_level++; + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s", COMPACT); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); @@ -3012,6 +3108,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "SIZE " HSIZE_T_FORMAT, storage_size); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + ctx->indent_level--; break; case H5D_CONTIGUOUS: { @@ -3023,7 +3120,11 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, * EXTERNAL_FILE *------------------------------------------------------------------------- */ + ctx->indent_level++; if (next) { + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s", CONTIGUOUS); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); @@ -3059,6 +3160,9 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, else { haddr_t ioffset; + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s", CONTIGUOUS); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); @@ -3078,6 +3182,107 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, h5tools_str_append(&buffer, "OFFSET "H5_PRINTF_HADDR_FMT, ioffset); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); } + ctx->indent_level--; + } + break; + case H5D_VIRTUAL: + { + size_t vmaps; + + H5Pget_virtual_count(dcpl_id, &vmaps); + + if (vmaps) { + size_t next; + ssize_t ssize_out; + + ctx->indent_level++; + for (next = 0; next < (unsigned) vmaps; next++) { + hid_t virtual_vspace = H5Pget_virtual_vspace(dcpl_id, next); + hid_t virtual_srcspace = H5Pget_virtual_srcspace(dcpl_id, next); + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s %ld %s ", VDS_MAPPING, next, BEGIN); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level++; + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s %s", VDS_VIRTUAL, BEGIN); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level++; + + h5tools_print_virtual_selection(virtual_vspace, dcpl_id, next, stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level--; + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s", END); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s %s", VDS_SOURCE, BEGIN); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level++; + + ssize_out = H5Pget_virtual_filename(dcpl_id, next, NULL, 0); + H5Pget_virtual_filename(dcpl_id, next, name, sizeof(name)); + ssize_out = H5Pget_virtual_dsetname(dcpl_id, next, NULL, 0); + H5Pget_virtual_dsetname(dcpl_id, next, dsetname, sizeof(dsetname)); + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s %s", VDS_SRC_FILE, h5tools_dump_header_format->virtualfilenamebegin); + h5tools_str_append(&buffer, "%s", name); + h5tools_str_append(&buffer, "%s", h5tools_dump_header_format->virtualfilenameend); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s %s", VDS_SRC_DATASET, h5tools_dump_header_format->virtualdatasetnamebegin); + h5tools_str_append(&buffer, "%s", dsetname); + h5tools_str_append(&buffer, "%s", h5tools_dump_header_format->virtualdatasetnameend); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + h5tools_print_virtual_selection(virtual_srcspace, dcpl_id, next, stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level--; + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s", END); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + + ctx->indent_level--; + + ctx->need_prefix = TRUE; + h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); + + h5tools_str_reset(&buffer); + h5tools_str_append(&buffer, "%s", END); + h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); + } + ctx->indent_level--; + } } break; default: @@ -3086,8 +3291,6 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t) ncols, (hsize_t) 0, (hsize_t) 0); }/*switch*/ - ctx->indent_level--; - ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); @@ -3102,7 +3305,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s", FILTERS, BEGIN); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3114,13 +3317,13 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, cd_nelmts = NELMTS(cd_values); filtn = H5Pget_filter2(dcpl_id, (unsigned)i, &filt_flags, &cd_nelmts, cd_values, sizeof(f_name), f_name, NULL); - - if (filtn < 0) - continue; /* nothing to print for invalid filter */ + + if (filtn < 0) + continue; /* nothing to print for invalid filter */ ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); switch(filtn) { case H5Z_FILTER_DEFLATE: @@ -3184,7 +3387,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, if(szip_options_mask & H5_SZIP_RAW_OPTION_MASK) { ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "HEADER %s", "RAW"); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3209,11 +3412,11 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, break; default: /* filters do not have to be available for showing registered filter info. - see HDFFV-8346 for details. --xcao@hdfgroup.org + see HDFFV-8346 for details. --xcao@hdfgroup.org if(H5Zfilter_avail(filtn)) h5tools_str_append(&buffer, "%s %s", "USER_REGISTERED_FILTER", BEGIN); else - */ + */ h5tools_str_append(&buffer, "%s %s", "USER_DEFINED_FILTER", BEGIN); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3221,15 +3424,15 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "FILTER_ID %d", filtn); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + if(f_name[0] != '\0') { ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "COMMENT %s", f_name); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3237,7 +3440,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, if (cd_nelmts) { ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s ","PARAMS", BEGIN); for (j=0; j<cd_nelmts; j++) @@ -3249,7 +3452,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s",END); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3261,7 +3464,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "NONE"); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3270,7 +3473,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s",END); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3281,7 +3484,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, */ ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s", FILLVALUE, BEGIN); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3290,10 +3493,10 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "FILL_TIME "); - + H5Pget_fill_time(dcpl_id, &ft); switch(ft) { case H5D_FILL_TIME_ALLOC: @@ -3313,7 +3516,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s ", "VALUE "); H5Pfill_value_defined(dcpl_id, &fvstatus); @@ -3329,7 +3532,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s", END); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3340,7 +3543,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, */ ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "ALLOCATION_TIME %s", BEGIN); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3349,7 +3552,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); H5Pget_alloc_time(dcpl_id, &at); switch(at) { @@ -3372,7 +3575,7 @@ h5tools_dump_dcpl(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s", END); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3422,7 +3625,7 @@ h5tools_dump_comment(FILE *stream, const h5tool_format_t *info, comment[cmt_bufsize] = '\0'; /* necessary because null char is not returned */ ctx->need_prefix = TRUE; - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "COMMENT \"%s\"", comment); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); @@ -3437,7 +3640,7 @@ h5tools_dump_comment(FILE *stream, const h5tool_format_t *info, /*------------------------------------------------------------------------- * Function: dump_attribute * - * Purpose: Dump the attribute. + * Purpose: Dump the attribute. * * Return: void * @@ -3446,7 +3649,7 @@ h5tools_dump_comment(FILE *stream, const h5tool_format_t *info, */ void h5tools_dump_attribute(FILE *stream, const h5tool_format_t *info, - h5tools_context_t *ctx, const char *attr_name, hid_t attr_id, + h5tools_context_t *ctx, const char *attr_name, hid_t attr_id, int display_index, int display_char) { h5tools_str_t buffer; /* string into which to render */ @@ -3465,7 +3668,7 @@ h5tools_dump_attribute(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, curr_pos, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s \"%s\" %s", h5tools_dump_header_format->attributebegin, attr_name, @@ -3474,7 +3677,7 @@ h5tools_dump_attribute(FILE *stream, const h5tool_format_t *info, if(attr_id < 0) { error_msg("unable to open attribute \"%s\"\n", attr_name); - } + } else { hid_t type, space; @@ -3501,7 +3704,7 @@ h5tools_dump_attribute(FILE *stream, const h5tool_format_t *info, ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); - + h5tools_str_reset(&buffer); if (HDstrlen(h5tools_dump_header_format->attributeblockend)) { @@ -3557,36 +3760,36 @@ void h5tools_print_packed_bits(h5tools_str_t *buffer, hid_t type) { int packed_bits_size = 0; - + hid_t n_type = h5tools_get_native_type(type); if(H5Tget_class(n_type)==H5T_INTEGER) { if(H5Tequal(n_type, H5T_NATIVE_SCHAR) == TRUE) { packed_bits_size = 8 * sizeof(char); - } + } else if(H5Tequal(n_type, H5T_NATIVE_UCHAR) == TRUE) { packed_bits_size = 8 * sizeof(unsigned char); - } + } else if(H5Tequal(n_type, H5T_NATIVE_SHORT) == TRUE) { packed_bits_size = 8 * sizeof(short); - } + } else if(H5Tequal(n_type, H5T_NATIVE_USHORT) == TRUE) { packed_bits_size = 8 * sizeof(unsigned short); - } + } else if(H5Tequal(n_type, H5T_NATIVE_INT) == TRUE) { packed_bits_size = 8 * sizeof(int); - } + } else if(H5Tequal(n_type, H5T_NATIVE_UINT) == TRUE) { packed_bits_size = 8 * sizeof(unsigned int); - } + } else if(H5Tequal(n_type, H5T_NATIVE_LONG) == TRUE) { packed_bits_size = 8 * sizeof(long); - } + } else if(H5Tequal(n_type, H5T_NATIVE_ULONG) == TRUE) { packed_bits_size = 8 * sizeof(unsigned long); - } + } else if(H5Tequal(n_type, H5T_NATIVE_LLONG) == TRUE) { packed_bits_size = 8 * sizeof(long long); - } + } else if(H5Tequal(n_type, H5T_NATIVE_ULLONG) == TRUE) { packed_bits_size = 8 * sizeof(unsigned long long); } @@ -3627,25 +3830,25 @@ h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, HDmemset(&buffer, 0, sizeof(h5tools_str_t)); if (info->line_ncols > 0) ncols = info->line_ncols; - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->subsettingbegin, h5tools_dump_header_format->subsettingblockbegin); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); ctx->indent_level++; - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); - + h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s ", h5tools_dump_header_format->startbegin, h5tools_dump_header_format->startblockbegin); h5tools_print_dims(&buffer, sset->start.data, dims); h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->startend, h5tools_dump_header_format->startblockend); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); @@ -3654,7 +3857,7 @@ h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, h5tools_print_dims(&buffer, sset->stride.data, dims); h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->strideend, h5tools_dump_header_format->strideblockend); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); @@ -3668,7 +3871,7 @@ h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->countend, h5tools_dump_header_format->countblockend); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, info, ctx, (hsize_t)0, 0); @@ -3682,7 +3885,7 @@ h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->blockend, h5tools_dump_header_format->blockblockend); h5tools_render_element(stream, info, ctx, &buffer, &curr_pos, (size_t)ncols, (hsize_t)0, (hsize_t)0); - + ctx->indent_level--; h5tools_str_close(&buffer); @@ -3699,7 +3902,7 @@ h5tools_dump_subsetting_header(FILE *stream, const h5tool_format_t *info, */ void h5tools_dump_data(FILE *stream, const h5tool_format_t *info, - h5tools_context_t *ctx, hid_t obj_id, int obj_data, struct subset_t *sset, + h5tools_context_t *ctx, hid_t obj_id, int obj_data, struct subset_t *sset, int display_index, int display_char) { H5S_class_t space_type; @@ -3762,10 +3965,10 @@ h5tools_dump_data(FILE *stream, const h5tool_format_t *info, h5tools_dump_subsetting_header(stream, &outputformat, ctx, sset, H5Sget_simple_extent_ndims(f_space)); H5Sclose(f_space); - + ctx->indent_level++; } - + ctx->need_prefix = TRUE; h5tools_str_reset(&buffer); h5tools_str_append(&buffer, "%s %s", h5tools_dump_header_format->databegin, h5tools_dump_header_format->datablockbegin); @@ -3791,7 +3994,7 @@ h5tools_dump_data(FILE *stream, const h5tool_format_t *info, datactx.indent_level++; datactx.need_prefix = TRUE; h5tools_simple_prefix(stream, info, &datactx, (hsize_t)0, 0); - + string_dataformat = *info; string_dataformat.idx_fmt = "\""; string_dataformat.line_multi_new = 1; @@ -3859,7 +4062,7 @@ h5tools_dump_data(FILE *stream, const h5tool_format_t *info, datactx.indent_level++; datactx.need_prefix = TRUE; h5tools_simple_prefix(stream, info, &datactx, (hsize_t)0, 0); - + string_dataformat = *info; string_dataformat.idx_fmt = "\""; string_dataformat.line_multi_new = 1; @@ -3886,7 +4089,7 @@ h5tools_dump_data(FILE *stream, const h5tool_format_t *info, H5Dvlen_reclaim(p_type, space, H5P_DEFAULT, buf); HDfree(buf); - } + } else status = SUCCEED; @@ -3916,10 +4119,10 @@ h5tools_dump_data(FILE *stream, const h5tool_format_t *info, if (sset && obj_data) { ctx->indent_level--; - + ctx->need_prefix = TRUE; h5tools_simple_prefix(stream, &outputformat, ctx, (hsize_t)0, 0); - + h5tools_str_reset(&buffer); if(HDstrlen(h5tools_dump_header_format->subsettingblockend)) { h5tools_str_append(&buffer, "%s", h5tools_dump_header_format->subsettingblockend); diff --git a/tools/lib/h5tools_str.c b/tools/lib/h5tools_str.c index b61ed34..249708e 100644 --- a/tools/lib/h5tools_str.c +++ b/tools/lib/h5tools_str.c @@ -413,9 +413,9 @@ h5tools_str_region_prefix(h5tools_str_t *str, const h5tool_format_t *info, } /*------------------------------------------------------------------------- - * Function: h5tools_str_dump_region_blocks + * Function: h5tools_str_dump_space_slabs * - * Purpose: Prints information about a dataspace region by appending + * Purpose: Prints information about a dataspace selection by appending * the information to the specified string. * * Return: none @@ -426,19 +426,85 @@ h5tools_str_region_prefix(h5tools_str_t *str, const h5tool_format_t *info, *------------------------------------------------------------------------- */ void -h5tools_str_dump_region_blocks(h5tools_str_t *str, hid_t region, +h5tools_str_dump_space_slabs(h5tools_str_t *str, hid_t rspace, + const h5tool_format_t *info, h5tools_context_t *ctx) +{ + hsize_t start[H5S_MAX_RANK]; + hsize_t stride[H5S_MAX_RANK]; + hsize_t count[H5S_MAX_RANK]; + hsize_t block[H5S_MAX_RANK]; + int j; + int ndims = H5Sget_simple_extent_ndims(rspace); + + H5Sget_regular_hyperslab(rspace, start, stride, count, block); + + /* Print hyperslab information */ + + /* Start coordinates */ + h5tools_str_append(str, "%s%s ", info->line_indent, START); + for (j = 0; j < ndims; j++) + h5tools_str_append(str, "%s" HSIZE_T_FORMAT, j ? "," : "(", start[j]); + h5tools_str_append(str, ")"); + h5tools_str_append(str, "%s", "\n"); + h5tools_str_indent(str, info, ctx); + + /* Stride coordinates */ + h5tools_str_append(str, "%s ", STRIDE); + for (j = 0; j < ndims; j++) + h5tools_str_append(str, "%s" HSIZE_T_FORMAT, j ? "," : "(", stride[j]); + h5tools_str_append(str, ")"); + h5tools_str_append(str, "%s", "\n"); + h5tools_str_indent(str, info, ctx); + + /* Count coordinates */ + h5tools_str_append(str, "%s ", COUNT); + for (j = 0; j < ndims; j++) { + if(count[j] == H5S_UNLIMITED) + h5tools_str_append(str, "%s%s", j ? "," : "(","H5S_UNLIMITED"); + else + h5tools_str_append(str, "%s" HSIZE_T_FORMAT, j ? "," : "(", count[j]); + } + h5tools_str_append(str, ")"); + h5tools_str_append(str, "%s", "\n"); + h5tools_str_indent(str, info, ctx); + + /* Block coordinates */ + h5tools_str_append(str, "%s ", BLOCK); + for (j = 0; j < ndims; j++) { + if(block[j] == H5S_UNLIMITED) + h5tools_str_append(str, "%s%s", j ? "," : "(","H5S_UNLIMITED"); + else + h5tools_str_append(str, "%s" HSIZE_T_FORMAT, j ? "," : "(", block[j]); + } + h5tools_str_append(str, ")"); +} + +/*------------------------------------------------------------------------- + * Function: h5tools_str_dump_space_blocks + * + * Purpose: Prints information about a dataspace selection by appending + * the information to the specified string. + * + * Return: none + * + * In/Out: + * h5tools_str_t *str + *------------------------------------------------------------------------- + */ +void +h5tools_str_dump_space_blocks(h5tools_str_t *str, hid_t rspace, const h5tool_format_t *info) { hssize_t nblocks; hsize_t alloc_size; hsize_t *ptdata; - int ndims = H5Sget_simple_extent_ndims(region); + int ndims = H5Sget_simple_extent_ndims(rspace); /* - * This function fails if the region does not have blocks. + * This function fails if the rspace does not have blocks. */ H5E_BEGIN_TRY { - nblocks = H5Sget_select_hyper_nblocks(region); + nblocks = H5Sget_select_hyper_nblocks(rspace); } H5E_END_TRY; /* Print block information */ @@ -449,13 +515,12 @@ h5tools_str_dump_region_blocks(h5tools_str_t *str, hid_t region, HDassert(alloc_size == (hsize_t) ((size_t) alloc_size)); /*check for overflow*/ ptdata = (hsize_t *)HDmalloc((size_t) alloc_size); H5_CHECK_OVERFLOW(nblocks, hssize_t, hsize_t); - H5Sget_select_hyper_blocklist(region, (hsize_t)0, (hsize_t)nblocks, ptdata); + H5Sget_select_hyper_blocklist(rspace, (hsize_t)0, (hsize_t)nblocks, ptdata); for (i = 0; i < nblocks; i++) { int j; - h5tools_str_append(str, info->dset_blockformat_pre, i ? "," OPTIONAL_LINE_BREAK " " : "", - (unsigned long)i); + h5tools_str_append(str, info->dset_blockformat_pre, i ? "," OPTIONAL_LINE_BREAK " " : "", (unsigned long)i); /* Start coordinates and opposite corner */ for (j = 0; j < ndims; j++) @@ -474,32 +539,31 @@ h5tools_str_dump_region_blocks(h5tools_str_t *str, hid_t region, } /*------------------------------------------------------------------------- - * Function: h5tools_str_dump_region_points + * Function: h5tools_str_dump_space_points * - * Purpose: Prints information about a dataspace region by appending + * Purpose: Prints information about a dataspace selection by appending * the information to the specified string. * * Return: none * * In/Out: - * h5tools_context_t *ctx * h5tools_str_t *str *------------------------------------------------------------------------- */ void -h5tools_str_dump_region_points(h5tools_str_t *str, hid_t region, +h5tools_str_dump_space_points(h5tools_str_t *str, hid_t rspace, const h5tool_format_t *info) { hssize_t npoints; hsize_t alloc_size; hsize_t *ptdata; - int ndims = H5Sget_simple_extent_ndims(region); + int ndims = H5Sget_simple_extent_ndims(rspace); /* - * This function fails if the region does not have points. + * This function fails if the rspace does not have points. */ H5E_BEGIN_TRY { - npoints = H5Sget_select_elem_npoints(region); + npoints = H5Sget_select_elem_npoints(rspace); } H5E_END_TRY; /* Print point information */ @@ -510,7 +574,7 @@ h5tools_str_dump_region_points(h5tools_str_t *str, hid_t region, HDassert(alloc_size == (hsize_t) ((size_t) alloc_size)); /*check for overflow*/ ptdata = (hsize_t *)HDmalloc((size_t) alloc_size); H5_CHECK_OVERFLOW(npoints, hssize_t, hsize_t); - H5Sget_select_elem_pointlist(region, (hsize_t)0, (hsize_t)npoints, ptdata); + H5Sget_select_elem_pointlist(rspace, (hsize_t)0, (hsize_t)npoints, ptdata); for (i = 0; i < npoints; i++) { int j; @@ -1234,9 +1298,9 @@ h5tools_str_sprint_region(h5tools_str_t *str, const h5tool_format_t *info, region_type = H5Sget_select_type(region); if(region_type==H5S_SEL_POINTS) - h5tools_str_dump_region_points(str, region, info); + h5tools_str_dump_space_points(str, region, info); else - h5tools_str_dump_region_blocks(str, region, info); + h5tools_str_dump_space_blocks(str, region, info); h5tools_str_append(str, "}"); @@ -1382,23 +1446,23 @@ h5tools_str_is_zero(const void *_mem, size_t size) char * h5tools_str_replace ( const char *string, const char *substr, const char *replacement ) { - char *tok = NULL; - char *newstr = NULL; - char *oldstr = NULL; - char *head = NULL; - - if ( substr == NULL || replacement == NULL ) - return HDstrdup (string); - - newstr = HDstrdup (string); - head = newstr; - while ( (tok = HDstrstr ( head, substr ))){ - oldstr = newstr; - newstr = HDmalloc ( HDstrlen ( oldstr ) - HDstrlen ( substr ) + HDstrlen ( replacement ) + 1 ); + char *tok = NULL; + char *newstr = NULL; + char *oldstr = NULL; + char *head = NULL; + + if ( substr == NULL || replacement == NULL ) + return HDstrdup (string); + + newstr = HDstrdup (string); + head = newstr; + while ( (tok = HDstrstr ( head, substr ))){ + oldstr = newstr; + newstr = HDmalloc ( HDstrlen ( oldstr ) - HDstrlen ( substr ) + HDstrlen ( replacement ) + 1 ); if ( newstr == NULL ){ - HDfree (oldstr); - return NULL; + HDfree (oldstr); + return NULL; } HDmemcpy ( newstr, oldstr, tok - oldstr ); HDmemcpy ( newstr + (tok - oldstr), replacement, HDstrlen ( replacement ) ); diff --git a/tools/lib/h5tools_str.h b/tools/lib/h5tools_str.h index 38697c6..6173b89 100644 --- a/tools/lib/h5tools_str.h +++ b/tools/lib/h5tools_str.h @@ -40,8 +40,9 @@ H5TOOLS_DLL char *h5tools_str_prefix(h5tools_str_t *str, const h5tool_format_ H5TOOLS_DLL char *h5tools_str_region_prefix(h5tools_str_t *str, const h5tool_format_t *info, hsize_t elmtno, hsize_t *ptdata, unsigned ndims, hsize_t max_idx[], h5tools_context_t *ctx); -H5TOOLS_DLL void h5tools_str_dump_region_blocks(h5tools_str_t *, hid_t, const h5tool_format_t *); -H5TOOLS_DLL void h5tools_str_dump_region_points(h5tools_str_t *, hid_t, const h5tool_format_t *); +H5TOOLS_DLL void h5tools_str_dump_space_slabs(h5tools_str_t *, hid_t, const h5tool_format_t *, h5tools_context_t *ctx); +H5TOOLS_DLL void h5tools_str_dump_space_blocks(h5tools_str_t *, hid_t, const h5tool_format_t *); +H5TOOLS_DLL void h5tools_str_dump_space_points(h5tools_str_t *, hid_t, const h5tool_format_t *); H5TOOLS_DLL void h5tools_str_sprint_region(h5tools_str_t *str, const h5tool_format_t *info, hid_t container, void *vp); H5TOOLS_DLL char *h5tools_str_sprint(h5tools_str_t *str, const h5tool_format_t *info, diff --git a/tools/misc/CMakeLists.txt b/tools/misc/CMakeLists.txt index d53cdc8..088dbdf 100644 --- a/tools/misc/CMakeLists.txt +++ b/tools/misc/CMakeLists.txt @@ -52,6 +52,9 @@ if (BUILD_TESTING) target_link_libraries (h5repart_gentest ${HDF5_LIB_TARGET} ${HDF5_TOOLS_LIB_TARGET}) set_target_properties (h5repart_gentest PROPERTIES FOLDER generator/tools) #add_test (NAME h5repart_gentest COMMAND $<TARGET_FILE:h5repart_gentest>) + + add_subdirectory (${HDF5_TOOLS_MISC_SOURCE_DIR}/vds) + endif (HDF5_BUILD_GENERATORS) add_executable (h5repart_test ${HDF5_TOOLS_MISC_SOURCE_DIR}/repart_test.c) diff --git a/tools/misc/Makefile.am b/tools/misc/Makefile.am index 882f8f2..fdfe8f7 100644 --- a/tools/misc/Makefile.am +++ b/tools/misc/Makefile.am @@ -20,10 +20,12 @@ include $(top_srcdir)/config/commence.am +SUBDIRS=vds + # Include src directory AM_CPPFLAGS+=-I$(top_srcdir)/src -I$(top_srcdir)/tools/lib -#test script and program +#test scripts and programs TEST_PROG=h5repart_gentest talign TEST_SCRIPT=testh5repart.sh testh5mkgrp.sh diff --git a/tools/misc/Makefile.in b/tools/misc/Makefile.in index 3e6b688..e114aee 100644 --- a/tools/misc/Makefile.in +++ b/tools/misc/Makefile.in @@ -222,11 +222,27 @@ SOURCES = h5debug.c h5mkgrp.c h5repart.c h5repart_gentest.c \ repart_test.c talign.c DIST_SOURCES = h5debug.c h5mkgrp.c h5repart.c h5repart_gentest.c \ repart_test.c talign.c +RECURSIVE_TARGETS = all-recursive check-recursive cscopelist-recursive \ + ctags-recursive dvi-recursive html-recursive info-recursive \ + install-data-recursive install-dvi-recursive \ + install-exec-recursive install-html-recursive \ + install-info-recursive install-pdf-recursive \ + install-ps-recursive install-recursive installcheck-recursive \ + installdirs-recursive pdf-recursive ps-recursive \ + tags-recursive uninstall-recursive am__can_run_installinfo = \ case $$AM_UPDATE_INFO_DIR in \ n|no|NO) false;; \ *) (install-info --version) >/dev/null 2>&1;; \ esac +RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ + distclean-recursive maintainer-clean-recursive +am__recursive_targets = \ + $(RECURSIVE_TARGETS) \ + $(RECURSIVE_CLEAN_TARGETS) \ + $(am__extra_recursive_targets) +AM_RECURSIVE_TARGETS = $(am__recursive_targets:-recursive=) TAGS CTAGS \ + check recheck distdir am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) $(LISP) # Read a list of newline-separated strings from the standard input, # and print each of them once, without duplicates. Input order is @@ -402,7 +418,6 @@ am__set_TESTS_bases = \ bases=`for i in $$bases; do echo $$i; done | sed 's/\.log$$//'`; \ bases=`echo $$bases` RECHECK_LOGS = $(TEST_LOGS) -AM_RECURSIVE_TARGETS = check recheck TEST_SUITE_LOG = test-suite.log LOG_DRIVER = $(SHELL) $(top_srcdir)/bin/test-driver LOG_COMPILE = $(LOG_COMPILER) $(AM_LOG_FLAGS) $(LOG_FLAGS) @@ -421,7 +436,33 @@ am__test_logs2 = $(am__test_logs1:@EXEEXT@.log=.log) TEST_LOGS = $(am__test_logs2:.sh.log=.log) SH_LOG_DRIVER = $(SHELL) $(top_srcdir)/bin/test-driver SH_LOG_COMPILE = $(SH_LOG_COMPILER) $(AM_SH_LOG_FLAGS) $(SH_LOG_FLAGS) +DIST_SUBDIRS = $(SUBDIRS) DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +am__relativize = \ + dir0=`pwd`; \ + sed_first='s,^\([^/]*\)/.*$$,\1,'; \ + sed_rest='s,^[^/]*/*,,'; \ + sed_last='s,^.*/\([^/]*\)$$,\1,'; \ + sed_butlast='s,/*[^/]*$$,,'; \ + while test -n "$$dir1"; do \ + first=`echo "$$dir1" | sed -e "$$sed_first"`; \ + if test "$$first" != "."; then \ + if test "$$first" = ".."; then \ + dir2=`echo "$$dir0" | sed -e "$$sed_last"`/"$$dir2"; \ + dir0=`echo "$$dir0" | sed -e "$$sed_butlast"`; \ + else \ + first2=`echo "$$dir2" | sed -e "$$sed_first"`; \ + if test "$$first2" = "$$first"; then \ + dir2=`echo "$$dir2" | sed -e "$$sed_rest"`; \ + else \ + dir2="../$$dir2"; \ + fi; \ + dir0="$$dir0"/"$$first"; \ + fi; \ + fi; \ + dir1=`echo "$$dir1" | sed -e "$$sed_rest"`; \ + done; \ + reldir="$$dir2" ACLOCAL = @ACLOCAL@ ADD_PARALLEL_FILES = @ADD_PARALLEL_FILES@ AMTAR = @AMTAR@ @@ -712,8 +753,9 @@ TRACE = perl $(top_srcdir)/bin/trace # and scd_family*.h5 were created by setting the HDF5_NOCLEANUP variable. CHECK_CLEANFILES = *.chkexe *.chklog *.clog *.clog2 *.h5 \ ../testfiles/fst_family*.h5 ../testfiles/scd_family*.h5 +SUBDIRS = vds -#test script and program +#test scripts and programs TEST_PROG = h5repart_gentest talign TEST_SCRIPT = testh5repart.sh testh5mkgrp.sh check_SCRIPTS = $(TEST_SCRIPT) @@ -758,7 +800,7 @@ TEST_PROG_CHKEXE = $(TEST_PROG:=.chkexe_) TEST_PROG_PARA_CHKEXE = $(TEST_PROG_PARA:=.chkexe_) TEST_SCRIPT_CHKSH = $(TEST_SCRIPT:=.chkexe_) TEST_SCRIPT_PARA_CHKSH = $(TEST_SCRIPT_PARA:=.chkexe_) -all: all-am +all: all-recursive .SUFFIXES: .SUFFIXES: .c .lo .log .o .obj .sh .sh$(EXEEXT) .trs @@ -957,14 +999,61 @@ mostlyclean-libtool: clean-libtool: -rm -rf .libs _libs +# This directory's subdirectories are mostly independent; you can cd +# into them and run 'make' without going through this Makefile. +# To change the values of 'make' variables: instead of editing Makefiles, +# (1) if the variable is set in 'config.status', edit 'config.status' +# (which will cause the Makefiles to be regenerated when you run 'make'); +# (2) otherwise, pass the desired values on the 'make' command line. +$(am__recursive_targets): + @fail=; \ + if $(am__make_keepgoing); then \ + failcom='fail=yes'; \ + else \ + failcom='exit 1'; \ + fi; \ + dot_seen=no; \ + target=`echo $@ | sed s/-recursive//`; \ + case "$@" in \ + distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \ + *) list='$(SUBDIRS)' ;; \ + esac; \ + for subdir in $$list; do \ + echo "Making $$target in $$subdir"; \ + if test "$$subdir" = "."; then \ + dot_seen=yes; \ + local_target="$$target-am"; \ + else \ + local_target="$$target"; \ + fi; \ + ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ + || eval $$failcom; \ + done; \ + if test "$$dot_seen" = "no"; then \ + $(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \ + fi; test -z "$$fail" + ID: $(am__tagged_files) $(am__define_uniq_tagged_files); mkid -fID $$unique -tags: tags-am +tags: tags-recursive TAGS: tags tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) set x; \ here=`pwd`; \ + if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \ + include_option=--etags-include; \ + empty_fix=.; \ + else \ + include_option=--include; \ + empty_fix=; \ + fi; \ + list='$(SUBDIRS)'; for subdir in $$list; do \ + if test "$$subdir" = .; then :; else \ + test ! -f $$subdir/TAGS || \ + set "$$@" "$$include_option=$$here/$$subdir/TAGS"; \ + fi; \ + done; \ $(am__define_uniq_tagged_files); \ shift; \ if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ @@ -977,7 +1066,7 @@ tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) $$unique; \ fi; \ fi -ctags: ctags-am +ctags: ctags-recursive CTAGS: ctags ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) @@ -990,7 +1079,7 @@ GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ && $(am__cd) $(top_srcdir) \ && gtags -i $(GTAGS_ARGS) "$$here" -cscopelist: cscopelist-am +cscopelist: cscopelist-recursive cscopelist-am: $(am__tagged_files) list='$(am__tagged_files)'; \ @@ -1198,24 +1287,50 @@ distdir: $(DISTFILES) || exit 1; \ fi; \ done + @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ + if test "$$subdir" = .; then :; else \ + $(am__make_dryrun) \ + || test -d "$(distdir)/$$subdir" \ + || $(MKDIR_P) "$(distdir)/$$subdir" \ + || exit 1; \ + dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ + $(am__relativize); \ + new_distdir=$$reldir; \ + dir1=$$subdir; dir2="$(top_distdir)"; \ + $(am__relativize); \ + new_top_distdir=$$reldir; \ + echo " (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) top_distdir="$$new_top_distdir" distdir="$$new_distdir" \\"; \ + echo " am__remove_distdir=: am__skip_length_check=: am__skip_mode_fix=: distdir)"; \ + ($(am__cd) $$subdir && \ + $(MAKE) $(AM_MAKEFLAGS) \ + top_distdir="$$new_top_distdir" \ + distdir="$$new_distdir" \ + am__remove_distdir=: \ + am__skip_length_check=: \ + am__skip_mode_fix=: \ + distdir) \ + || exit 1; \ + fi; \ + done check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(check_SCRIPTS) $(MAKE) $(AM_MAKEFLAGS) check-TESTS -check: check-am +check: check-recursive all-am: Makefile $(PROGRAMS) $(SCRIPTS) all-local -installdirs: +installdirs: installdirs-recursive +installdirs-am: for dir in "$(DESTDIR)$(bindir)" "$(DESTDIR)$(bindir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done -install: install-am -install-exec: install-exec-am -install-data: install-data-am -uninstall: uninstall-am +install: install-recursive +install-exec: install-exec-recursive +install-data: install-data-recursive +uninstall: uninstall-recursive install-am: all-am @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am -installcheck: installcheck-am +installcheck: installcheck-recursive install-strip: if test -z '$(STRIP)'; then \ $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ @@ -1242,85 +1357,85 @@ distclean-generic: maintainer-clean-generic: @echo "This command is intended for maintainers to use" @echo "it deletes files that may require special tools to rebuild." -clean: clean-am +clean: clean-recursive clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ clean-libtool mostlyclean-am -distclean: distclean-am +distclean: distclean-recursive -rm -rf ./$(DEPDIR) -rm -f Makefile distclean-am: clean-am distclean-compile distclean-generic \ distclean-tags -dvi: dvi-am +dvi: dvi-recursive dvi-am: -html: html-am +html: html-recursive html-am: -info: info-am +info: info-recursive info-am: install-data-am: -install-dvi: install-dvi-am +install-dvi: install-dvi-recursive install-dvi-am: install-exec-am: install-binPROGRAMS install-binSCRIPTS \ install-exec-local -install-html: install-html-am +install-html: install-html-recursive install-html-am: -install-info: install-info-am +install-info: install-info-recursive install-info-am: install-man: -install-pdf: install-pdf-am +install-pdf: install-pdf-recursive install-pdf-am: -install-ps: install-ps-am +install-ps: install-ps-recursive install-ps-am: installcheck-am: -maintainer-clean: maintainer-clean-am +maintainer-clean: maintainer-clean-recursive -rm -rf ./$(DEPDIR) -rm -f Makefile maintainer-clean-am: distclean-am maintainer-clean-generic -mostlyclean: mostlyclean-am +mostlyclean: mostlyclean-recursive mostlyclean-am: mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool mostlyclean-local -pdf: pdf-am +pdf: pdf-recursive pdf-am: -ps: ps-am +ps: ps-recursive ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-binSCRIPTS \ uninstall-local -.MAKE: check-am install-am install-strip +.MAKE: $(am__recursive_targets) check-am install-am install-strip -.PHONY: CTAGS GTAGS TAGS all all-am all-local check check-TESTS \ - check-am clean clean-binPROGRAMS clean-checkPROGRAMS \ - clean-generic clean-libtool cscopelist-am ctags ctags-am \ - distclean distclean-compile distclean-generic \ +.PHONY: $(am__recursive_targets) CTAGS GTAGS TAGS all all-am all-local \ + check check-TESTS check-am clean clean-binPROGRAMS \ + clean-checkPROGRAMS clean-generic clean-libtool cscopelist-am \ + ctags ctags-am distclean distclean-compile distclean-generic \ distclean-libtool distclean-tags distdir dvi dvi-am html \ html-am info info-am install install-am install-binPROGRAMS \ install-binSCRIPTS install-data install-data-am install-dvi \ @@ -1328,10 +1443,10 @@ uninstall-am: uninstall-binPROGRAMS uninstall-binSCRIPTS \ install-html install-html-am install-info install-info-am \ install-man install-pdf install-pdf-am install-ps \ install-ps-am install-strip installcheck installcheck-am \ - installdirs maintainer-clean maintainer-clean-generic \ - mostlyclean mostlyclean-compile mostlyclean-generic \ - mostlyclean-libtool mostlyclean-local pdf pdf-am ps ps-am \ - recheck tags tags-am uninstall uninstall-am \ + installdirs installdirs-am maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool mostlyclean-local pdf \ + pdf-am ps ps-am recheck tags tags-am uninstall uninstall-am \ uninstall-binPROGRAMS uninstall-binSCRIPTS uninstall-local diff --git a/tools/misc/vds/CMakeLists.txt b/tools/misc/vds/CMakeLists.txt new file mode 100644 index 0000000..dcf883c --- /dev/null +++ b/tools/misc/vds/CMakeLists.txt @@ -0,0 +1,28 @@ +cmake_minimum_required (VERSION 3.1.0) +PROJECT (HDF5_TOOLS_MISC_VDS) + +#----------------------------------------------------------------------------- +# Setup include Directories +#----------------------------------------------------------------------------- +INCLUDE_DIRECTORIES (${HDF5_TOOLS_SRC_DIR}/lib) + +MACRO (ADD_H5_GENERATOR genfile) + add_executable (${genfile} ${HDF5_TOOLS_MISC_VDS_SOURCE_DIR}/${genfile}.c) + TARGET_NAMING (${genfile} STATIC) + TARGET_C_PROPERTIES (${genfile} STATIC " " " ") + target_link_libraries (${genfile} ${HDF5_LIB_TARGET} ${HDF5_TOOLS_LIB_TARGET}) + set_target_properties (${genfile} PROPERTIES FOLDER generator/tools) +ENDMACRO (ADD_H5_GENERATOR genfile) + +# generator executables +set (H5_GENERATORS + UC_1_one_dim_gen + UC_2_two_dims_gen + UC_3_gaps_gen + UC_4_printf_gen + UC_5_stride_gen +) + +foreach (gen ${H5_GENERATORS}) + ADD_H5_GENERATOR (${gen}) +endforeach (gen ${H5_GENERATORS}) diff --git a/tools/misc/vds/Makefile.am b/tools/misc/vds/Makefile.am new file mode 100644 index 0000000..f1ef80c --- /dev/null +++ b/tools/misc/vds/Makefile.am @@ -0,0 +1,38 @@ +# +# 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 files COPYING and Copyright.html. COPYING can be found at the root +# of the source code distribution tree; Copyright.html can be found at the +# root level of an installed copy of the electronic HDF5 document set and +# is linked from the top-level documents page. It can also be found at +# http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have +# access to either file, you may request a copy from help@hdfgroup.org. +## +## Makefile.am +## Run automake to generate a Makefile.in from this file. +# +# HDF5 Library Makefile(.in) +# + +include $(top_srcdir)/config/commence.am + +# Include src directory +AM_CPPFLAGS+=-I$(top_srcdir)/src -I$(top_srcdir)/tools/lib + +#test scripts and programs +TEST_PROG=UC_1_one_dim_gen UC_2_two_dims_gen UC_3_gaps_gen UC_4_printf_gen \ + UC_5_stride_gen + +check_PROGRAMS=$(TEST_PROG) + +# Temporary files. +CHECK_CLEANFILES+=*.h5 + +# All programs rely on hdf5 library and h5tools library +LDADD=$(LIBH5TOOLS) $(LIBHDF5) + +include $(top_srcdir)/config/conclude.am diff --git a/tools/misc/vds/Makefile.in b/tools/misc/vds/Makefile.in new file mode 100644 index 0000000..9fa9426 --- /dev/null +++ b/tools/misc/vds/Makefile.in @@ -0,0 +1,1422 @@ +# Makefile.in generated by automake 1.14.1 from Makefile.am. +# @configure_input@ + +# Copyright (C) 1994-2013 Free Software Foundation, Inc. + +# This Makefile.in is free software; the Free Software Foundation +# gives unlimited permission to copy and/or distribute it, +# with or without modifications, as long as this notice is preserved. + +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY, to the extent permitted by law; without +# even the implied warranty of MERCHANTABILITY or FITNESS FOR A +# PARTICULAR PURPOSE. + +@SET_MAKE@ + +# +# 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 files COPYING and Copyright.html. COPYING can be found at the root +# of the source code distribution tree; Copyright.html can be found at the +# root level of an installed copy of the electronic HDF5 document set and +# is linked from the top-level documents page. It can also be found at +# http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have +# access to either file, you may request a copy from help@hdfgroup.org. +# +# HDF5 Library Makefile(.in) +# +VPATH = @srcdir@ +am__is_gnu_make = test -n '$(MAKEFILE_LIST)' && test -n '$(MAKELEVEL)' +am__make_running_with_option = \ + case $${target_option-} in \ + ?) ;; \ + *) echo "am__make_running_with_option: internal error: invalid" \ + "target option '$${target_option-}' specified" >&2; \ + exit 1;; \ + esac; \ + has_opt=no; \ + sane_makeflags=$$MAKEFLAGS; \ + if $(am__is_gnu_make); then \ + sane_makeflags=$$MFLAGS; \ + else \ + case $$MAKEFLAGS in \ + *\\[\ \ ]*) \ + bs=\\; \ + sane_makeflags=`printf '%s\n' "$$MAKEFLAGS" \ + | sed "s/$$bs$$bs[$$bs $$bs ]*//g"`;; \ + esac; \ + fi; \ + skip_next=no; \ + strip_trailopt () \ + { \ + flg=`printf '%s\n' "$$flg" | sed "s/$$1.*$$//"`; \ + }; \ + for flg in $$sane_makeflags; do \ + test $$skip_next = yes && { skip_next=no; continue; }; \ + case $$flg in \ + *=*|--*) continue;; \ + -*I) strip_trailopt 'I'; skip_next=yes;; \ + -*I?*) strip_trailopt 'I';; \ + -*O) strip_trailopt 'O'; skip_next=yes;; \ + -*O?*) strip_trailopt 'O';; \ + -*l) strip_trailopt 'l'; skip_next=yes;; \ + -*l?*) strip_trailopt 'l';; \ + -[dEDm]) skip_next=yes;; \ + -[JT]) skip_next=yes;; \ + esac; \ + case $$flg in \ + *$$target_option*) has_opt=yes; break;; \ + esac; \ + done; \ + test $$has_opt = yes +am__make_dryrun = (target_option=n; $(am__make_running_with_option)) +am__make_keepgoing = (target_option=k; $(am__make_running_with_option)) +pkgdatadir = $(datadir)/@PACKAGE@ +pkgincludedir = $(includedir)/@PACKAGE@ +pkglibdir = $(libdir)/@PACKAGE@ +pkglibexecdir = $(libexecdir)/@PACKAGE@ +am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd +install_sh_DATA = $(install_sh) -c -m 644 +install_sh_PROGRAM = $(install_sh) -c +install_sh_SCRIPT = $(install_sh) -c +INSTALL_HEADER = $(INSTALL_DATA) +transform = $(program_transform_name) +NORMAL_INSTALL = : +PRE_INSTALL = : +POST_INSTALL = : +NORMAL_UNINSTALL = : +PRE_UNINSTALL = : +POST_UNINSTALL = : +build_triplet = @build@ +host_triplet = @host@ +DIST_COMMON = $(top_srcdir)/config/commence.am \ + $(top_srcdir)/config/conclude.am $(srcdir)/Makefile.in \ + $(srcdir)/Makefile.am $(top_srcdir)/bin/mkinstalldirs \ + $(top_srcdir)/bin/depcomp $(top_srcdir)/bin/test-driver +check_PROGRAMS = $(am__EXEEXT_1) +TESTS = $(am__EXEEXT_1) +subdir = tools/misc/vds +ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 +am__aclocal_m4_deps = $(top_srcdir)/m4/aclocal_cxx.m4 \ + $(top_srcdir)/m4/aclocal_fc.m4 $(top_srcdir)/configure.ac +am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ + $(ACLOCAL_M4) +mkinstalldirs = $(SHELL) $(top_srcdir)/bin/mkinstalldirs +CONFIG_HEADER = $(top_builddir)/src/H5config.h \ + $(top_builddir)/fortran/src/H5config_f.inc +CONFIG_CLEAN_FILES = +CONFIG_CLEAN_VPATH_FILES = +am__EXEEXT_1 = UC_1_one_dim_gen$(EXEEXT) UC_2_two_dims_gen$(EXEEXT) \ + UC_3_gaps_gen$(EXEEXT) UC_4_printf_gen$(EXEEXT) \ + UC_5_stride_gen$(EXEEXT) +UC_1_one_dim_gen_SOURCES = UC_1_one_dim_gen.c +UC_1_one_dim_gen_OBJECTS = UC_1_one_dim_gen.$(OBJEXT) +UC_1_one_dim_gen_LDADD = $(LDADD) +UC_1_one_dim_gen_DEPENDENCIES = $(LIBH5TOOLS) $(LIBHDF5) +AM_V_lt = $(am__v_lt_@AM_V@) +am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) +am__v_lt_0 = --silent +am__v_lt_1 = +UC_2_two_dims_gen_SOURCES = UC_2_two_dims_gen.c +UC_2_two_dims_gen_OBJECTS = UC_2_two_dims_gen.$(OBJEXT) +UC_2_two_dims_gen_LDADD = $(LDADD) +UC_2_two_dims_gen_DEPENDENCIES = $(LIBH5TOOLS) $(LIBHDF5) +UC_3_gaps_gen_SOURCES = UC_3_gaps_gen.c +UC_3_gaps_gen_OBJECTS = UC_3_gaps_gen.$(OBJEXT) +UC_3_gaps_gen_LDADD = $(LDADD) +UC_3_gaps_gen_DEPENDENCIES = $(LIBH5TOOLS) $(LIBHDF5) +UC_4_printf_gen_SOURCES = UC_4_printf_gen.c +UC_4_printf_gen_OBJECTS = UC_4_printf_gen.$(OBJEXT) +UC_4_printf_gen_LDADD = $(LDADD) +UC_4_printf_gen_DEPENDENCIES = $(LIBH5TOOLS) $(LIBHDF5) +UC_5_stride_gen_SOURCES = UC_5_stride_gen.c +UC_5_stride_gen_OBJECTS = UC_5_stride_gen.$(OBJEXT) +UC_5_stride_gen_LDADD = $(LDADD) +UC_5_stride_gen_DEPENDENCIES = $(LIBH5TOOLS) $(LIBHDF5) +AM_V_P = $(am__v_P_@AM_V@) +am__v_P_ = $(am__v_P_@AM_DEFAULT_V@) +am__v_P_0 = false +am__v_P_1 = : +AM_V_GEN = $(am__v_GEN_@AM_V@) +am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) +am__v_GEN_0 = @echo " GEN " $@; +am__v_GEN_1 = +AM_V_at = $(am__v_at_@AM_V@) +am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) +am__v_at_0 = @ +am__v_at_1 = +DEFAULT_INCLUDES = -I.@am__isrc@ -I$(top_builddir)/src -I$(top_builddir)/fortran/src +depcomp = $(SHELL) $(top_srcdir)/bin/depcomp +am__depfiles_maybe = depfiles +am__mv = mv -f +COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ + $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) +LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ + $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ + $(AM_CFLAGS) $(CFLAGS) +AM_V_CC = $(am__v_CC_@AM_V@) +am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) +am__v_CC_0 = @echo " CC " $@; +am__v_CC_1 = +CCLD = $(CC) +LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ + $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ + $(AM_LDFLAGS) $(LDFLAGS) -o $@ +AM_V_CCLD = $(am__v_CCLD_@AM_V@) +am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) +am__v_CCLD_0 = @echo " CCLD " $@; +am__v_CCLD_1 = +SOURCES = UC_1_one_dim_gen.c UC_2_two_dims_gen.c UC_3_gaps_gen.c \ + UC_4_printf_gen.c UC_5_stride_gen.c +DIST_SOURCES = UC_1_one_dim_gen.c UC_2_two_dims_gen.c UC_3_gaps_gen.c \ + UC_4_printf_gen.c UC_5_stride_gen.c +am__can_run_installinfo = \ + case $$AM_UPDATE_INFO_DIR in \ + n|no|NO) false;; \ + *) (install-info --version) >/dev/null 2>&1;; \ + esac +am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) $(LISP) +# Read a list of newline-separated strings from the standard input, +# and print each of them once, without duplicates. Input order is +# *not* preserved. +am__uniquify_input = $(AWK) '\ + BEGIN { nonempty = 0; } \ + { items[$$0] = 1; nonempty = 1; } \ + END { if (nonempty) { for (i in items) print i; }; } \ +' +# Make sure the list of sources is unique. This is necessary because, +# e.g., the same source file might be shared among _SOURCES variables +# for different programs/libraries. +am__define_uniq_tagged_files = \ + list='$(am__tagged_files)'; \ + unique=`for i in $$list; do \ + if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ + done | $(am__uniquify_input)` +ETAGS = etags +CTAGS = ctags +am__tty_colors_dummy = \ + mgn= red= grn= lgn= blu= brg= std=; \ + am__color_tests=no +am__tty_colors = { \ + $(am__tty_colors_dummy); \ + if test "X$(AM_COLOR_TESTS)" = Xno; then \ + am__color_tests=no; \ + elif test "X$(AM_COLOR_TESTS)" = Xalways; then \ + am__color_tests=yes; \ + elif test "X$$TERM" != Xdumb && { test -t 1; } 2>/dev/null; then \ + am__color_tests=yes; \ + fi; \ + if test $$am__color_tests = yes; then \ + red='[0;31m'; \ + grn='[0;32m'; \ + lgn='[1;32m'; \ + blu='[1;34m'; \ + mgn='[0;35m'; \ + brg='[1m'; \ + std='[m'; \ + fi; \ +} +am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; +am__vpath_adj = case $$p in \ + $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ + *) f=$$p;; \ + esac; +am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; +am__install_max = 40 +am__nobase_strip_setup = \ + srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` +am__nobase_strip = \ + for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" +am__nobase_list = $(am__nobase_strip_setup); \ + for p in $$list; do echo "$$p $$p"; done | \ + sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ + $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ + if (++n[$$2] == $(am__install_max)) \ + { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ + END { for (dir in files) print dir, files[dir] }' +am__base_list = \ + sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ + sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' +am__uninstall_files_from_dir = { \ + test -z "$$files" \ + || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ + || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ + $(am__cd) "$$dir" && rm -f $$files; }; \ + } +am__recheck_rx = ^[ ]*:recheck:[ ]* +am__global_test_result_rx = ^[ ]*:global-test-result:[ ]* +am__copy_in_global_log_rx = ^[ ]*:copy-in-global-log:[ ]* +# A command that, given a newline-separated list of test names on the +# standard input, print the name of the tests that are to be re-run +# upon "make recheck". +am__list_recheck_tests = $(AWK) '{ \ + recheck = 1; \ + while ((rc = (getline line < ($$0 ".trs"))) != 0) \ + { \ + if (rc < 0) \ + { \ + if ((getline line2 < ($$0 ".log")) < 0) \ + recheck = 0; \ + break; \ + } \ + else if (line ~ /$(am__recheck_rx)[nN][Oo]/) \ + { \ + recheck = 0; \ + break; \ + } \ + else if (line ~ /$(am__recheck_rx)[yY][eE][sS]/) \ + { \ + break; \ + } \ + }; \ + if (recheck) \ + print $$0; \ + close ($$0 ".trs"); \ + close ($$0 ".log"); \ +}' +# A command that, given a newline-separated list of test names on the +# standard input, create the global log from their .trs and .log files. +am__create_global_log = $(AWK) ' \ +function fatal(msg) \ +{ \ + print "fatal: making $@: " msg | "cat >&2"; \ + exit 1; \ +} \ +function rst_section(header) \ +{ \ + print header; \ + len = length(header); \ + for (i = 1; i <= len; i = i + 1) \ + printf "="; \ + printf "\n\n"; \ +} \ +{ \ + copy_in_global_log = 1; \ + global_test_result = "RUN"; \ + while ((rc = (getline line < ($$0 ".trs"))) != 0) \ + { \ + if (rc < 0) \ + fatal("failed to read from " $$0 ".trs"); \ + if (line ~ /$(am__global_test_result_rx)/) \ + { \ + sub("$(am__global_test_result_rx)", "", line); \ + sub("[ ]*$$", "", line); \ + global_test_result = line; \ + } \ + else if (line ~ /$(am__copy_in_global_log_rx)[nN][oO]/) \ + copy_in_global_log = 0; \ + }; \ + if (copy_in_global_log) \ + { \ + rst_section(global_test_result ": " $$0); \ + while ((rc = (getline line < ($$0 ".log"))) != 0) \ + { \ + if (rc < 0) \ + fatal("failed to read from " $$0 ".log"); \ + print line; \ + }; \ + printf "\n"; \ + }; \ + close ($$0 ".trs"); \ + close ($$0 ".log"); \ +}' +# Restructured Text title. +am__rst_title = { sed 's/.*/ & /;h;s/./=/g;p;x;s/ *$$//;p;g' && echo; } +# Solaris 10 'make', and several other traditional 'make' implementations, +# pass "-e" to $(SHELL), and POSIX 2008 even requires this. Work around it +# by disabling -e (using the XSI extension "set +e") if it's set. +am__sh_e_setup = case $$- in *e*) set +e;; esac +# Default flags passed to test drivers. +am__common_driver_flags = \ + --color-tests "$$am__color_tests" \ + --enable-hard-errors "$$am__enable_hard_errors" \ + --expect-failure "$$am__expect_failure" +# To be inserted before the command running the test. Creates the +# directory for the log if needed. Stores in $dir the directory +# containing $f, in $tst the test, in $log the log. Executes the +# developer- defined test setup AM_TESTS_ENVIRONMENT (if any), and +# passes TESTS_ENVIRONMENT. Set up options for the wrapper that +# will run the test scripts (or their associated LOG_COMPILER, if +# thy have one). +am__check_pre = \ +$(am__sh_e_setup); \ +$(am__vpath_adj_setup) $(am__vpath_adj) \ +$(am__tty_colors); \ +srcdir=$(srcdir); export srcdir; \ +case "$@" in \ + */*) am__odir=`echo "./$@" | sed 's|/[^/]*$$||'`;; \ + *) am__odir=.;; \ +esac; \ +test "x$$am__odir" = x"." || test -d "$$am__odir" \ + || $(MKDIR_P) "$$am__odir" || exit $$?; \ +if test -f "./$$f"; then dir=./; \ +elif test -f "$$f"; then dir=; \ +else dir="$(srcdir)/"; fi; \ +tst=$$dir$$f; log='$@'; \ +if test -n '$(DISABLE_HARD_ERRORS)'; then \ + am__enable_hard_errors=no; \ +else \ + am__enable_hard_errors=yes; \ +fi; \ +case " $(XFAIL_TESTS) " in \ + *[\ \ ]$$f[\ \ ]* | *[\ \ ]$$dir$$f[\ \ ]*) \ + am__expect_failure=yes;; \ + *) \ + am__expect_failure=no;; \ +esac; \ +$(AM_TESTS_ENVIRONMENT) $(TESTS_ENVIRONMENT) +# A shell command to get the names of the tests scripts with any registered +# extension removed (i.e., equivalently, the names of the test logs, with +# the '.log' extension removed). The result is saved in the shell variable +# '$bases'. This honors runtime overriding of TESTS and TEST_LOGS. Sadly, +# we cannot use something simpler, involving e.g., "$(TEST_LOGS:.log=)", +# since that might cause problem with VPATH rewrites for suffix-less tests. +# See also 'test-harness-vpath-rewrite.sh' and 'test-trs-basic.sh'. +am__set_TESTS_bases = \ + bases='$(TEST_LOGS)'; \ + bases=`for i in $$bases; do echo $$i; done | sed 's/\.log$$//'`; \ + bases=`echo $$bases` +RECHECK_LOGS = $(TEST_LOGS) +AM_RECURSIVE_TARGETS = check recheck +TEST_SUITE_LOG = test-suite.log +LOG_DRIVER = $(SHELL) $(top_srcdir)/bin/test-driver +LOG_COMPILE = $(LOG_COMPILER) $(AM_LOG_FLAGS) $(LOG_FLAGS) +am__set_b = \ + case '$@' in \ + */*) \ + case '$*' in \ + */*) b='$*';; \ + *) b=`echo '$@' | sed 's/\.log$$//'`; \ + esac;; \ + *) \ + b='$*';; \ + esac +am__test_logs1 = $(TESTS:=.log) +am__test_logs2 = $(am__test_logs1:@EXEEXT@.log=.log) +TEST_LOGS = $(am__test_logs2:.sh.log=.log) +SH_LOG_DRIVER = $(SHELL) $(top_srcdir)/bin/test-driver +SH_LOG_COMPILE = $(SH_LOG_COMPILER) $(AM_SH_LOG_FLAGS) $(SH_LOG_FLAGS) +DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) +ACLOCAL = @ACLOCAL@ +ADD_PARALLEL_FILES = @ADD_PARALLEL_FILES@ +AMTAR = @AMTAR@ + +# H5_CFLAGS holds flags that should be used when building hdf5, +# but which should not be exported to h5cc for building other programs. +# AM_CFLAGS is an automake construct which should be used by Makefiles +# instead of CFLAGS, as CFLAGS is reserved solely for the user to define. +# This applies to FCFLAGS, CXXFLAGS, CPPFLAGS, and LDFLAGS as well. +AM_CFLAGS = @AM_CFLAGS@ @H5_CFLAGS@ + +# Include src directory +AM_CPPFLAGS = @AM_CPPFLAGS@ @H5_CPPFLAGS@ -I$(top_srcdir)/src \ + -I$(top_srcdir)/tools/lib +AM_CXXFLAGS = @AM_CXXFLAGS@ @H5_CXXFLAGS@ +AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ +AM_FCFLAGS = @AM_FCFLAGS@ @H5_FCFLAGS@ +AM_LDFLAGS = @AM_LDFLAGS@ @H5_LDFLAGS@ +AM_MAKEFLAGS = @AM_MAKEFLAGS@ +AR = @AR@ +AUTOCONF = @AUTOCONF@ +AUTOHEADER = @AUTOHEADER@ +AUTOMAKE = @AUTOMAKE@ +AWK = @AWK@ +BYTESEX = @BYTESEX@ +CC = @CC@ +CCDEPMODE = @CCDEPMODE@ +CC_VERSION = @CC_VERSION@ +CFLAGS = @CFLAGS@ +CLEARFILEBUF = @CLEARFILEBUF@ +CODESTACK = @CODESTACK@ +CONFIG_DATE = @CONFIG_DATE@ +CONFIG_MODE = @CONFIG_MODE@ +CONFIG_USER = @CONFIG_USER@ +CPP = @CPP@ +CPPFLAGS = @CPPFLAGS@ +CXX = @CXX@ +CXXCPP = @CXXCPP@ +CXXDEPMODE = @CXXDEPMODE@ +CXXFLAGS = @CXXFLAGS@ +CXX_VERSION = @CXX_VERSION@ +CYGPATH_W = @CYGPATH_W@ +DEBUG_PKG = @DEBUG_PKG@ +DEFAULT_API_VERSION = @DEFAULT_API_VERSION@ +DEFS = @DEFS@ +DEPDIR = @DEPDIR@ +DEPRECATED_SYMBOLS = @DEPRECATED_SYMBOLS@ +DIRECT_VFD = @DIRECT_VFD@ +DLLTOOL = @DLLTOOL@ +DSYMUTIL = @DSYMUTIL@ +DUMPBIN = @DUMPBIN@ +ECHO_C = @ECHO_C@ +ECHO_N = @ECHO_N@ +ECHO_T = @ECHO_T@ +EGREP = @EGREP@ +EXEEXT = @EXEEXT@ +EXTERNAL_FILTERS = @EXTERNAL_FILTERS@ + +# Make sure that these variables are exported to the Makefiles +F9XMODEXT = @F9XMODEXT@ +F9XMODFLAG = @F9XMODFLAG@ +F9XSUFFIXFLAG = @F9XSUFFIXFLAG@ +FC = @FC@ +FCFLAGS = @FCFLAGS@ +FCFLAGS_f90 = @FCFLAGS_f90@ +FCLIBS = @FCLIBS@ +FC_VERSION = @FC_VERSION@ +FGREP = @FGREP@ +FORTRAN_C_LONG_DOUBLE_IS_UNIQUE = @FORTRAN_C_LONG_DOUBLE_IS_UNIQUE@ +FORTRAN_HAVE_C_LONG_DOUBLE = @FORTRAN_HAVE_C_LONG_DOUBLE@ +FORTRAN_SIZEOF_LONG_DOUBLE = @FORTRAN_SIZEOF_LONG_DOUBLE@ +FSEARCH_DIRS = @FSEARCH_DIRS@ +GREP = @GREP@ +H5CONFIG_F_IKIND = @H5CONFIG_F_IKIND@ +H5CONFIG_F_NUM_IKIND = @H5CONFIG_F_NUM_IKIND@ +H5CONFIG_F_NUM_RKIND = @H5CONFIG_F_NUM_RKIND@ +H5CONFIG_F_RKIND = @H5CONFIG_F_RKIND@ +H5CONFIG_F_RKIND_SIZEOF = @H5CONFIG_F_RKIND_SIZEOF@ +H5_CFLAGS = @H5_CFLAGS@ +H5_CPPFLAGS = @H5_CPPFLAGS@ +H5_CXXFLAGS = @H5_CXXFLAGS@ +H5_FCFLAGS = @H5_FCFLAGS@ +H5_FORTRAN_SHARED = @H5_FORTRAN_SHARED@ +H5_LDFLAGS = @H5_LDFLAGS@ +H5_VERSION = @H5_VERSION@ +HADDR_T = @HADDR_T@ +HAVE_DMALLOC = @HAVE_DMALLOC@ +HAVE_Fortran_INTEGER_SIZEOF_16 = @HAVE_Fortran_INTEGER_SIZEOF_16@ +HAVE_PTHREAD = @HAVE_PTHREAD@ +HDF5_HL = @HDF5_HL@ +HDF5_INTERFACES = @HDF5_INTERFACES@ +HDF_CXX = @HDF_CXX@ +HDF_FORTRAN = @HDF_FORTRAN@ +HID_T = @HID_T@ +HL = @HL@ +HL_FOR = @HL_FOR@ +HSIZE_T = @HSIZE_T@ +HSSIZE_T = @HSSIZE_T@ +INSTALL = @INSTALL@ +INSTALL_DATA = @INSTALL_DATA@ +INSTALL_PROGRAM = @INSTALL_PROGRAM@ +INSTALL_SCRIPT = @INSTALL_SCRIPT@ +INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ +INSTRUMENT = @INSTRUMENT@ +INSTRUMENT_LIBRARY = @INSTRUMENT_LIBRARY@ +LD = @LD@ +LDFLAGS = @LDFLAGS@ +LIBOBJS = @LIBOBJS@ +LIBS = @LIBS@ +LIBTOOL = @LIBTOOL@ +LIPO = @LIPO@ +LL_PATH = @LL_PATH@ +LN_S = @LN_S@ +LTLIBOBJS = @LTLIBOBJS@ +LT_STATIC_EXEC = @LT_STATIC_EXEC@ +MAINT = @MAINT@ +MAKEINFO = @MAKEINFO@ +MANIFEST_TOOL = @MANIFEST_TOOL@ +MKDIR_P = @MKDIR_P@ +MPE = @MPE@ +NM = @NM@ +NMEDIT = @NMEDIT@ +OBJDUMP = @OBJDUMP@ +OBJECT_NAMELEN_DEFAULT_F = @OBJECT_NAMELEN_DEFAULT_F@ +OBJEXT = @OBJEXT@ +OTOOL = @OTOOL@ +OTOOL64 = @OTOOL64@ +PACKAGE = @PACKAGE@ +PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ +PACKAGE_NAME = @PACKAGE_NAME@ +PACKAGE_STRING = @PACKAGE_STRING@ +PACKAGE_TARNAME = @PACKAGE_TARNAME@ +PACKAGE_URL = @PACKAGE_URL@ +PACKAGE_VERSION = @PACKAGE_VERSION@ +PAC_C_MAX_REAL_PRECISION = @PAC_C_MAX_REAL_PRECISION@ +PAC_FC_ALL_INTEGER_KINDS = @PAC_FC_ALL_INTEGER_KINDS@ +PAC_FC_ALL_INTEGER_KINDS_SIZEOF = @PAC_FC_ALL_INTEGER_KINDS_SIZEOF@ +PAC_FC_ALL_REAL_KINDS = @PAC_FC_ALL_REAL_KINDS@ +PAC_FC_ALL_REAL_KINDS_SIZEOF = @PAC_FC_ALL_REAL_KINDS_SIZEOF@ +PAC_FC_MAX_REAL_PRECISION = @PAC_FC_MAX_REAL_PRECISION@ +PAC_FORTRAN_NATIVE_DOUBLE_KIND = @PAC_FORTRAN_NATIVE_DOUBLE_KIND@ +PAC_FORTRAN_NATIVE_DOUBLE_SIZEOF = @PAC_FORTRAN_NATIVE_DOUBLE_SIZEOF@ +PAC_FORTRAN_NATIVE_INTEGER_KIND = @PAC_FORTRAN_NATIVE_INTEGER_KIND@ +PAC_FORTRAN_NATIVE_INTEGER_SIZEOF = @PAC_FORTRAN_NATIVE_INTEGER_SIZEOF@ +PAC_FORTRAN_NATIVE_REAL_KIND = @PAC_FORTRAN_NATIVE_REAL_KIND@ +PAC_FORTRAN_NATIVE_REAL_SIZEOF = @PAC_FORTRAN_NATIVE_REAL_SIZEOF@ +PARALLEL = @PARALLEL@ +PATH_SEPARATOR = @PATH_SEPARATOR@ +RANLIB = @RANLIB@ +ROOT = @ROOT@ +RUNPARALLEL = @RUNPARALLEL@ +RUNSERIAL = @RUNSERIAL@ +R_INTEGER = @R_INTEGER@ +R_LARGE = @R_LARGE@ +SEARCH = @SEARCH@ +SED = @SED@ +SET_MAKE = @SET_MAKE@ +SHELL = @SHELL@ +SIZE_T = @SIZE_T@ +STATIC_EXEC = @STATIC_EXEC@ +STATIC_SHARED = @STATIC_SHARED@ +STRICT_FORMAT_CHECKS = @STRICT_FORMAT_CHECKS@ +STRIP = @STRIP@ +TESTPARALLEL = @TESTPARALLEL@ +THREADSAFE = @THREADSAFE@ +TIME = @TIME@ +TR = @TR@ +TRACE_API = @TRACE_API@ +UNAME_INFO = @UNAME_INFO@ +USE_FILTER_DEFLATE = @USE_FILTER_DEFLATE@ +USE_FILTER_SZIP = @USE_FILTER_SZIP@ +USINGMEMCHECKER = @USINGMEMCHECKER@ +VERSION = @VERSION@ +WORDS_BIGENDIAN = @WORDS_BIGENDIAN@ +abs_builddir = @abs_builddir@ +abs_srcdir = @abs_srcdir@ +abs_top_builddir = @abs_top_builddir@ +abs_top_srcdir = @abs_top_srcdir@ +ac_ct_AR = @ac_ct_AR@ +ac_ct_CC = @ac_ct_CC@ +ac_ct_CXX = @ac_ct_CXX@ +ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ +ac_ct_FC = @ac_ct_FC@ +am__include = @am__include@ +am__leading_dot = @am__leading_dot@ +am__quote = @am__quote@ +am__tar = @am__tar@ +am__untar = @am__untar@ +bindir = @bindir@ +build = @build@ +build_alias = @build_alias@ +build_cpu = @build_cpu@ +build_os = @build_os@ +build_vendor = @build_vendor@ +builddir = @builddir@ +datadir = @datadir@ +datarootdir = @datarootdir@ + +# Install directories that automake doesn't know about +docdir = $(exec_prefix)/doc +dvidir = @dvidir@ +enable_shared = @enable_shared@ +enable_static = @enable_static@ +exec_prefix = @exec_prefix@ +host = @host@ +host_alias = @host_alias@ +host_cpu = @host_cpu@ +host_os = @host_os@ +host_vendor = @host_vendor@ +htmldir = @htmldir@ +includedir = @includedir@ +infodir = @infodir@ +install_sh = @install_sh@ +libdir = @libdir@ +libexecdir = @libexecdir@ +localedir = @localedir@ +localstatedir = @localstatedir@ +mandir = @mandir@ +mkdir_p = @mkdir_p@ +oldincludedir = @oldincludedir@ +pdfdir = @pdfdir@ +prefix = @prefix@ +program_transform_name = @program_transform_name@ +psdir = @psdir@ +sbindir = @sbindir@ +sharedstatedir = @sharedstatedir@ +srcdir = @srcdir@ +sysconfdir = @sysconfdir@ +target_alias = @target_alias@ +top_build_prefix = @top_build_prefix@ +top_builddir = @top_builddir@ +top_srcdir = @top_srcdir@ + +# Shell commands used in Makefiles +RM = rm -f +CP = cp + +# Some machines need a command to run executables; this is that command +# so that our tests will run. +# We use RUNEXEC instead of RUNSERIAL directly because it may be that +# some tests need to be run with a different command. Older versions +# of the makefiles used the command +# $(LIBTOOL) --mode=execute +# in some directories, for instance. +RUNEXEC = $(RUNSERIAL) + +# Libraries to link to while building +LIBHDF5 = $(top_builddir)/src/libhdf5.la +LIBH5TEST = $(top_builddir)/test/libh5test.la +LIBH5F = $(top_builddir)/fortran/src/libhdf5_fortran.la +LIBH5FTEST = $(top_builddir)/fortran/test/libh5test_fortran.la +LIBH5CPP = $(top_builddir)/c++/src/libhdf5_cpp.la +LIBH5TOOLS = $(top_builddir)/tools/lib/libh5tools.la +LIBH5_HL = $(top_builddir)/hl/src/libhdf5_hl.la +LIBH5F_HL = $(top_builddir)/hl/fortran/src/libhdf5hl_fortran.la +LIBH5CPP_HL = $(top_builddir)/hl/c++/src/libhdf5_hl_cpp.la + +# Note that in svn revision 19400 the '/' after DESTDIR in H5* variables below +# has been removed. According to the official description of DESTDIR by Gnu at +# http://www.gnu.org/prep/standards/html_node/DESTDIR.html, DESTDIR is +# prepended to the normal and complete install path that it precedes for the +# purpose of installing in a temporary directory which is useful for building +# rpms and other packages. The '/' after ${DESTDIR} will be followed by another +# '/' at the beginning of the normal install path. When DESTDIR is empty the +# path then begins with '//', which is incorrect and causes problems at least for +# Cygwin. + +# Scripts used to build examples +# If only shared libraries have been installed, have h5cc build examples with +# shared libraries instead of static libraries +H5CC = ${DESTDIR}$(bindir)/h5cc +H5CC_PP = ${DESTDIR}$(bindir)/h5pcc +H5FC = ${DESTDIR}$(bindir)/h5fc +H5FC_PP = ${DESTDIR}$(bindir)/h5pfc +H5CPP = ${DESTDIR}$(bindir)/h5c++ +ACLOCAL_AMFLAGS = "-I m4" + +# The trace script; this is used on source files from the C library to +# insert tracing macros. +TRACE = perl $(top_srcdir)/bin/trace + +# .chkexe files are used to mark tests that have run successfully. +# .chklog files are output from those tests. +# *.clog and *.clog2 are from the MPE option. + +# Temporary files. +CHECK_CLEANFILES = *.chkexe *.chklog *.clog *.clog2 *.h5 + +#test scripts and programs +TEST_PROG = UC_1_one_dim_gen UC_2_two_dims_gen UC_3_gaps_gen UC_4_printf_gen \ + UC_5_stride_gen + + +# All programs rely on hdf5 library and h5tools library +LDADD = $(LIBH5TOOLS) $(LIBHDF5) + +# Automake needs to be taught how to build lib, progs, and tests targets. +# These will be filled in automatically for the most part (e.g., +# lib_LIBRARIES are built for lib target), but EXTRA_LIB, EXTRA_PROG, and +# EXTRA_TEST variables are supplied to allow the user to force targets to +# be built at certain times. +LIB = $(lib_LIBRARIES) $(lib_LTLIBRARIES) $(noinst_LIBRARIES) \ + $(noinst_LTLIBRARIES) $(check_LIBRARIES) $(check_LTLIBRARIES) $(EXTRA_LIB) + +PROGS = $(bin_PROGRAMS) $(bin_SCRIPTS) $(noinst_PROGRAMS) $(noinst_SCRIPTS) \ + $(EXTRA_PROG) + +chk_TESTS = $(check_PROGRAMS) $(check_SCRIPTS) $(EXTRA_TEST) +TEST_EXTENSIONS = .sh +SH_LOG_COMPILER = $(SHELL) +AM_SH_LOG_FLAGS = +TEST_PROG_CHKEXE = $(TEST_PROG:=.chkexe_) +TEST_PROG_PARA_CHKEXE = $(TEST_PROG_PARA:=.chkexe_) +TEST_SCRIPT_CHKSH = $(TEST_SCRIPT:=.chkexe_) +TEST_SCRIPT_PARA_CHKSH = $(TEST_SCRIPT_PARA:=.chkexe_) +all: all-am + +.SUFFIXES: +.SUFFIXES: .c .lo .log .o .obj .sh .sh$(EXEEXT) .trs +$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(top_srcdir)/config/commence.am $(top_srcdir)/config/conclude.am $(am__configure_deps) + @for dep in $?; do \ + case '$(am__configure_deps)' in \ + *$$dep*) \ + ( cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh ) \ + && { if test -f $@; then exit 0; else break; fi; }; \ + exit 1;; \ + esac; \ + done; \ + echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign tools/misc/vds/Makefile'; \ + $(am__cd) $(top_srcdir) && \ + $(AUTOMAKE) --foreign tools/misc/vds/Makefile +.PRECIOUS: Makefile +Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status + @case '$?' in \ + *config.status*) \ + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \ + *) \ + echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \ + cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \ + esac; +$(top_srcdir)/config/commence.am $(top_srcdir)/config/conclude.am: + +$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh + +$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) + cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh +$(am__aclocal_m4_deps): + +clean-checkPROGRAMS: + @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ + echo " rm -f" $$list; \ + rm -f $$list || exit $$?; \ + test -n "$(EXEEXT)" || exit 0; \ + list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ + echo " rm -f" $$list; \ + rm -f $$list + +UC_1_one_dim_gen$(EXEEXT): $(UC_1_one_dim_gen_OBJECTS) $(UC_1_one_dim_gen_DEPENDENCIES) $(EXTRA_UC_1_one_dim_gen_DEPENDENCIES) + @rm -f UC_1_one_dim_gen$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(UC_1_one_dim_gen_OBJECTS) $(UC_1_one_dim_gen_LDADD) $(LIBS) + +UC_2_two_dims_gen$(EXEEXT): $(UC_2_two_dims_gen_OBJECTS) $(UC_2_two_dims_gen_DEPENDENCIES) $(EXTRA_UC_2_two_dims_gen_DEPENDENCIES) + @rm -f UC_2_two_dims_gen$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(UC_2_two_dims_gen_OBJECTS) $(UC_2_two_dims_gen_LDADD) $(LIBS) + +UC_3_gaps_gen$(EXEEXT): $(UC_3_gaps_gen_OBJECTS) $(UC_3_gaps_gen_DEPENDENCIES) $(EXTRA_UC_3_gaps_gen_DEPENDENCIES) + @rm -f UC_3_gaps_gen$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(UC_3_gaps_gen_OBJECTS) $(UC_3_gaps_gen_LDADD) $(LIBS) + +UC_4_printf_gen$(EXEEXT): $(UC_4_printf_gen_OBJECTS) $(UC_4_printf_gen_DEPENDENCIES) $(EXTRA_UC_4_printf_gen_DEPENDENCIES) + @rm -f UC_4_printf_gen$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(UC_4_printf_gen_OBJECTS) $(UC_4_printf_gen_LDADD) $(LIBS) + +UC_5_stride_gen$(EXEEXT): $(UC_5_stride_gen_OBJECTS) $(UC_5_stride_gen_DEPENDENCIES) $(EXTRA_UC_5_stride_gen_DEPENDENCIES) + @rm -f UC_5_stride_gen$(EXEEXT) + $(AM_V_CCLD)$(LINK) $(UC_5_stride_gen_OBJECTS) $(UC_5_stride_gen_LDADD) $(LIBS) + +mostlyclean-compile: + -rm -f *.$(OBJEXT) + +distclean-compile: + -rm -f *.tab.c + +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UC_1_one_dim_gen.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UC_2_two_dims_gen.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UC_3_gaps_gen.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UC_4_printf_gen.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/UC_5_stride_gen.Po@am__quote@ + +.c.o: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $< + +.c.obj: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'` +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'` + +.c.lo: +@am__fastdepCC_TRUE@ $(AM_V_CC)$(LTCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $< +@am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Plo +@AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< + +mostlyclean-libtool: + -rm -f *.lo + +clean-libtool: + -rm -rf .libs _libs + +ID: $(am__tagged_files) + $(am__define_uniq_tagged_files); mkid -fID $$unique +tags: tags-am +TAGS: tags + +tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) + set x; \ + here=`pwd`; \ + $(am__define_uniq_tagged_files); \ + shift; \ + if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ + test -n "$$unique" || unique=$$empty_fix; \ + if test $$# -gt 0; then \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + "$$@" $$unique; \ + else \ + $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ + $$unique; \ + fi; \ + fi +ctags: ctags-am + +CTAGS: ctags +ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) + $(am__define_uniq_tagged_files); \ + test -z "$(CTAGS_ARGS)$$unique" \ + || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ + $$unique + +GTAGS: + here=`$(am__cd) $(top_builddir) && pwd` \ + && $(am__cd) $(top_srcdir) \ + && gtags -i $(GTAGS_ARGS) "$$here" +cscopelist: cscopelist-am + +cscopelist-am: $(am__tagged_files) + list='$(am__tagged_files)'; \ + case "$(srcdir)" in \ + [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ + *) sdir=$(subdir)/$(srcdir) ;; \ + esac; \ + for i in $$list; do \ + if test -f "$$i"; then \ + echo "$(subdir)/$$i"; \ + else \ + echo "$$sdir/$$i"; \ + fi; \ + done >> $(top_builddir)/cscope.files + +distclean-tags: + -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags + +# Recover from deleted '.trs' file; this should ensure that +# "rm -f foo.log; make foo.trs" re-run 'foo.test', and re-create +# both 'foo.log' and 'foo.trs'. Break the recipe in two subshells +# to avoid problems with "make -n". +.log.trs: + rm -f $< $@ + $(MAKE) $(AM_MAKEFLAGS) $< + +# Leading 'am--fnord' is there to ensure the list of targets does not +# expand to empty, as could happen e.g. with make check TESTS=''. +am--fnord $(TEST_LOGS) $(TEST_LOGS:.log=.trs): $(am__force_recheck) +am--force-recheck: + @: + +$(TEST_SUITE_LOG): $(TEST_LOGS) + @$(am__set_TESTS_bases); \ + am__f_ok () { test -f "$$1" && test -r "$$1"; }; \ + redo_bases=`for i in $$bases; do \ + am__f_ok $$i.trs && am__f_ok $$i.log || echo $$i; \ + done`; \ + if test -n "$$redo_bases"; then \ + redo_logs=`for i in $$redo_bases; do echo $$i.log; done`; \ + redo_results=`for i in $$redo_bases; do echo $$i.trs; done`; \ + if $(am__make_dryrun); then :; else \ + rm -f $$redo_logs && rm -f $$redo_results || exit 1; \ + fi; \ + fi; \ + if test -n "$$am__remaking_logs"; then \ + echo "fatal: making $(TEST_SUITE_LOG): possible infinite" \ + "recursion detected" >&2; \ + else \ + am__remaking_logs=yes $(MAKE) $(AM_MAKEFLAGS) $$redo_logs; \ + fi; \ + if $(am__make_dryrun); then :; else \ + st=0; \ + errmsg="fatal: making $(TEST_SUITE_LOG): failed to create"; \ + for i in $$redo_bases; do \ + test -f $$i.trs && test -r $$i.trs \ + || { echo "$$errmsg $$i.trs" >&2; st=1; }; \ + test -f $$i.log && test -r $$i.log \ + || { echo "$$errmsg $$i.log" >&2; st=1; }; \ + done; \ + test $$st -eq 0 || exit 1; \ + fi + @$(am__sh_e_setup); $(am__tty_colors); $(am__set_TESTS_bases); \ + ws='[ ]'; \ + results=`for b in $$bases; do echo $$b.trs; done`; \ + test -n "$$results" || results=/dev/null; \ + all=` grep "^$$ws*:test-result:" $$results | wc -l`; \ + pass=` grep "^$$ws*:test-result:$$ws*PASS" $$results | wc -l`; \ + fail=` grep "^$$ws*:test-result:$$ws*FAIL" $$results | wc -l`; \ + skip=` grep "^$$ws*:test-result:$$ws*SKIP" $$results | wc -l`; \ + xfail=`grep "^$$ws*:test-result:$$ws*XFAIL" $$results | wc -l`; \ + xpass=`grep "^$$ws*:test-result:$$ws*XPASS" $$results | wc -l`; \ + error=`grep "^$$ws*:test-result:$$ws*ERROR" $$results | wc -l`; \ + if test `expr $$fail + $$xpass + $$error` -eq 0; then \ + success=true; \ + else \ + success=false; \ + fi; \ + br='==================='; br=$$br$$br$$br$$br; \ + result_count () \ + { \ + if test x"$$1" = x"--maybe-color"; then \ + maybe_colorize=yes; \ + elif test x"$$1" = x"--no-color"; then \ + maybe_colorize=no; \ + else \ + echo "$@: invalid 'result_count' usage" >&2; exit 4; \ + fi; \ + shift; \ + desc=$$1 count=$$2; \ + if test $$maybe_colorize = yes && test $$count -gt 0; then \ + color_start=$$3 color_end=$$std; \ + else \ + color_start= color_end=; \ + fi; \ + echo "$${color_start}# $$desc $$count$${color_end}"; \ + }; \ + create_testsuite_report () \ + { \ + result_count $$1 "TOTAL:" $$all "$$brg"; \ + result_count $$1 "PASS: " $$pass "$$grn"; \ + result_count $$1 "SKIP: " $$skip "$$blu"; \ + result_count $$1 "XFAIL:" $$xfail "$$lgn"; \ + result_count $$1 "FAIL: " $$fail "$$red"; \ + result_count $$1 "XPASS:" $$xpass "$$red"; \ + result_count $$1 "ERROR:" $$error "$$mgn"; \ + }; \ + { \ + echo "$(PACKAGE_STRING): $(subdir)/$(TEST_SUITE_LOG)" | \ + $(am__rst_title); \ + create_testsuite_report --no-color; \ + echo; \ + echo ".. contents:: :depth: 2"; \ + echo; \ + for b in $$bases; do echo $$b; done \ + | $(am__create_global_log); \ + } >$(TEST_SUITE_LOG).tmp || exit 1; \ + mv $(TEST_SUITE_LOG).tmp $(TEST_SUITE_LOG); \ + if $$success; then \ + col="$$grn"; \ + else \ + col="$$red"; \ + test x"$$VERBOSE" = x || cat $(TEST_SUITE_LOG); \ + fi; \ + echo "$${col}$$br$${std}"; \ + echo "$${col}Testsuite summary for $(PACKAGE_STRING)$${std}"; \ + echo "$${col}$$br$${std}"; \ + create_testsuite_report --maybe-color; \ + echo "$$col$$br$$std"; \ + if $$success; then :; else \ + echo "$${col}See $(subdir)/$(TEST_SUITE_LOG)$${std}"; \ + if test -n "$(PACKAGE_BUGREPORT)"; then \ + echo "$${col}Please report to $(PACKAGE_BUGREPORT)$${std}"; \ + fi; \ + echo "$$col$$br$$std"; \ + fi; \ + $$success || exit 1 +recheck: all $(check_PROGRAMS) + @test -z "$(TEST_SUITE_LOG)" || rm -f $(TEST_SUITE_LOG) + @set +e; $(am__set_TESTS_bases); \ + bases=`for i in $$bases; do echo $$i; done \ + | $(am__list_recheck_tests)` || exit 1; \ + log_list=`for i in $$bases; do echo $$i.log; done`; \ + log_list=`echo $$log_list`; \ + $(MAKE) $(AM_MAKEFLAGS) $(TEST_SUITE_LOG) \ + am__force_recheck=am--force-recheck \ + TEST_LOGS="$$log_list"; \ + exit $$? +UC_1_one_dim_gen.log: UC_1_one_dim_gen$(EXEEXT) + @p='UC_1_one_dim_gen$(EXEEXT)'; \ + b='UC_1_one_dim_gen'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +UC_2_two_dims_gen.log: UC_2_two_dims_gen$(EXEEXT) + @p='UC_2_two_dims_gen$(EXEEXT)'; \ + b='UC_2_two_dims_gen'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +UC_3_gaps_gen.log: UC_3_gaps_gen$(EXEEXT) + @p='UC_3_gaps_gen$(EXEEXT)'; \ + b='UC_3_gaps_gen'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +UC_4_printf_gen.log: UC_4_printf_gen$(EXEEXT) + @p='UC_4_printf_gen$(EXEEXT)'; \ + b='UC_4_printf_gen'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +UC_5_stride_gen.log: UC_5_stride_gen$(EXEEXT) + @p='UC_5_stride_gen$(EXEEXT)'; \ + b='UC_5_stride_gen'; \ + $(am__check_pre) $(LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_LOG_DRIVER_FLAGS) $(LOG_DRIVER_FLAGS) -- $(LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +.sh.log: + @p='$<'; \ + $(am__set_b); \ + $(am__check_pre) $(SH_LOG_DRIVER) --test-name "$$f" \ + --log-file $$b.log --trs-file $$b.trs \ + $(am__common_driver_flags) $(AM_SH_LOG_DRIVER_FLAGS) $(SH_LOG_DRIVER_FLAGS) -- $(SH_LOG_COMPILE) \ + "$$tst" $(AM_TESTS_FD_REDIRECT) +@am__EXEEXT_TRUE@.sh$(EXEEXT).log: +@am__EXEEXT_TRUE@ @p='$<'; \ +@am__EXEEXT_TRUE@ $(am__set_b); \ +@am__EXEEXT_TRUE@ $(am__check_pre) $(SH_LOG_DRIVER) --test-name "$$f" \ +@am__EXEEXT_TRUE@ --log-file $$b.log --trs-file $$b.trs \ +@am__EXEEXT_TRUE@ $(am__common_driver_flags) $(AM_SH_LOG_DRIVER_FLAGS) $(SH_LOG_DRIVER_FLAGS) -- $(SH_LOG_COMPILE) \ +@am__EXEEXT_TRUE@ "$$tst" $(AM_TESTS_FD_REDIRECT) + +distdir: $(DISTFILES) + @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ + list='$(DISTFILES)'; \ + dist_files=`for file in $$list; do echo $$file; done | \ + sed -e "s|^$$srcdirstrip/||;t" \ + -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ + case $$dist_files in \ + */*) $(MKDIR_P) `echo "$$dist_files" | \ + sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ + sort -u` ;; \ + esac; \ + for file in $$dist_files; do \ + if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ + if test -d $$d/$$file; then \ + dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ + if test -d "$(distdir)/$$file"; then \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ + cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ + find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ + fi; \ + cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ + else \ + test -f "$(distdir)/$$file" \ + || cp -p $$d/$$file "$(distdir)/$$file" \ + || exit 1; \ + fi; \ + done +check-am: all-am + $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) + $(MAKE) $(AM_MAKEFLAGS) check-TESTS +check: check-am +all-am: Makefile all-local +installdirs: +install: install-am +install-exec: install-exec-am +install-data: install-data-am +uninstall: uninstall-am + +install-am: all-am + @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am + +installcheck: installcheck-am +install-strip: + if test -z '$(STRIP)'; then \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + install; \ + else \ + $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ + install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ + "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ + fi +mostlyclean-generic: + -test -z "$(TEST_LOGS)" || rm -f $(TEST_LOGS) + -test -z "$(TEST_LOGS:.log=.trs)" || rm -f $(TEST_LOGS:.log=.trs) + -test -z "$(TEST_SUITE_LOG)" || rm -f $(TEST_SUITE_LOG) + +clean-generic: + +distclean-generic: + -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) + -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) + +maintainer-clean-generic: + @echo "This command is intended for maintainers to use" + @echo "it deletes files that may require special tools to rebuild." +clean: clean-am + +clean-am: clean-checkPROGRAMS clean-generic clean-libtool \ + mostlyclean-am + +distclean: distclean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +distclean-am: clean-am distclean-compile distclean-generic \ + distclean-tags + +dvi: dvi-am + +dvi-am: + +html: html-am + +html-am: + +info: info-am + +info-am: + +install-data-am: + +install-dvi: install-dvi-am + +install-dvi-am: + +install-exec-am: + +install-html: install-html-am + +install-html-am: + +install-info: install-info-am + +install-info-am: + +install-man: + +install-pdf: install-pdf-am + +install-pdf-am: + +install-ps: install-ps-am + +install-ps-am: + +installcheck-am: + +maintainer-clean: maintainer-clean-am + -rm -rf ./$(DEPDIR) + -rm -f Makefile +maintainer-clean-am: distclean-am maintainer-clean-generic + +mostlyclean: mostlyclean-am + +mostlyclean-am: mostlyclean-compile mostlyclean-generic \ + mostlyclean-libtool mostlyclean-local + +pdf: pdf-am + +pdf-am: + +ps: ps-am + +ps-am: + +uninstall-am: + +.MAKE: check-am install-am install-strip + +.PHONY: CTAGS GTAGS TAGS all all-am all-local check check-TESTS \ + check-am clean clean-checkPROGRAMS clean-generic clean-libtool \ + cscopelist-am ctags ctags-am distclean distclean-compile \ + distclean-generic distclean-libtool distclean-tags distdir dvi \ + dvi-am html html-am info info-am install install-am \ + install-data install-data-am install-dvi install-dvi-am \ + install-exec install-exec-am install-html install-html-am \ + install-info install-info-am install-man install-pdf \ + install-pdf-am install-ps install-ps-am install-strip \ + installcheck installcheck-am installdirs maintainer-clean \ + maintainer-clean-generic mostlyclean mostlyclean-compile \ + mostlyclean-generic mostlyclean-libtool mostlyclean-local pdf \ + pdf-am ps ps-am recheck tags tags-am uninstall uninstall-am + + +# List all build rules defined by HDF5 Makefiles as "PHONY" targets here. +# This tells the Makefiles that these targets are not files to be built but +# commands that should be executed even if a file with the same name already +# exists. +.PHONY: build-check-clean build-check-p build-check-s build-lib build-progs \ + build-tests check-clean check-install check-p check-s check-vfd \ + install-doc lib progs tests uninstall-doc _exec_check-s _test help + +help: + @$(top_srcdir)/bin/makehelp + +# lib/progs/tests targets recurse into subdirectories. build-* targets +# build files in this directory. +build-lib: $(LIB) +build-progs: $(LIB) $(PROGS) +build-tests: $(LIB) $(PROGS) $(chk_TESTS) + +# General rule for recursive building targets. +# BUILT_SOURCES contain targets that need to be built before anything else +# in the directory (e.g., for Fortran type detection) +lib progs tests check-s check-p :: $(BUILT_SOURCES) + @$(MAKE) $(AM_MAKEFLAGS) build-$@ || exit 1; + @for d in X $(SUBDIRS); do \ + if test $$d != X && test $$d != .; then \ + (set -x; cd $$d && $(MAKE) $(AM_MAKEFLAGS) $@) || exit 1; \ + fi; \ + done + +# General rule for recursive cleaning targets. Like the rule above, +# but doesn't require building BUILT_SOURCES. +check-clean :: + @$(MAKE) $(AM_MAKEFLAGS) build-$@ || exit 1; + @for d in X $(SUBDIRS); do \ + if test $$d != X && test $$d != .; then \ + (set -x; cd $$d && $(MAKE) $(AM_MAKEFLAGS) $@) || exit 1; \ + fi; \ + done + +# Tell Automake to build tests when the user types `make all' (this is +# not its default behavior). Also build EXTRA_LIB and EXTRA_PROG since +# Automake won't build them automatically, either. +all-local: $(EXTRA_LIB) $(EXTRA_PROG) $(chk_TESTS) + +# make install-doc doesn't do anything outside of doc directory, but +# Makefiles should recognize it. +# UPDATE: docs no longer reside in this build tree, so this target +# is depreciated. +install-doc uninstall-doc: + @echo "Nothing to be done." + +# clean up files generated by tests so they can be re-run. +build-check-clean: + $(RM) -rf $(CHECK_CLEANFILES) + +# run check-clean whenever mostlyclean is run +mostlyclean-local: build-check-clean + +# check-install is just a synonym for installcheck +check-install: installcheck + +# Run each test in order, passing $(TEST_FLAGS) to the program. +# Since tests are done in a shell loop, "make -i" does apply inside it. +# Set HDF5_Make_Ignore to a non-blank string to ignore errors inside the loop. +# The timestamps give a rough idea how much time the tests use. +# +# Note that targets in chk_TESTS (defined above) will be built when the user +# types 'make tests' or 'make check', but only programs in TEST_PROG, +# TEST_PROG_PARA, or TEST_SCRIPT will actually be executed. +check-TESTS: test + +test _test: + @$(MAKE) build-check-s + @$(MAKE) build-check-p + +# Actual execution of check-s. +build-check-s: $(LIB) $(PROGS) $(chk_TESTS) + @if test -n "$(TEST_PROG)$(TEST_SCRIPT)"; then \ + echo "===Serial tests in `echo ${PWD} | sed -e s:.*/::` begin `date`==="; \ + fi + @$(MAKE) $(AM_MAKEFLAGS) _exec_check-s + @if test -n "$(TEST_PROG)$(TEST_SCRIPT)"; then \ + echo "===Serial tests in `echo ${PWD} | sed -e s:.*/::` ended `date`===";\ + fi + +_exec_check-s: $(TEST_PROG_CHKEXE) $(TEST_SCRIPT_CHKSH) + +# The dummy.chkexe here prevents the target from being +# empty if there are no tests in the current directory. +# $${log} is the log file. +# $${tname} is the name of test. +$(TEST_PROG_CHKEXE) $(TEST_PROG_PARA_CHKEXE) dummy.chkexe_: + @if test "X$@" != "X.chkexe_" && test "X$@" != "Xdummy.chkexe_"; then \ + tname=$(@:.chkexe_=)$(EXEEXT);\ + log=$(@:.chkexe_=.chklog); \ + echo "============================"; \ + if $(top_srcdir)/bin/newer $(@:.chkexe_=.chkexe) $${tname}; then \ + echo "No need to test $${tname} again."; \ + else \ + echo "============================" > $${log}; \ + if test "X$(FORTRAN_API)" = "Xyes"; then \ + echo "Fortran API: Testing $(HDF5_DRIVER) $${tname} $(TEST_FLAGS)"; \ + echo "Fortran API: $(HDF5_DRIVER) $${tname} $(TEST_FLAGS) Test Log" >> $${log}; \ + elif test "X$(CXX_API)" = "Xyes"; then \ + echo "C++ API: Testing $(HDF5_DRIVER) $${tname} $(TEST_FLAGS)"; \ + echo "C++ API: $(HDF5_DRIVER) $${tname} $(TEST_FLAGS) Test Log" >> $${log};\ + else \ + echo "Testing $(HDF5_DRIVER) $${tname} $(TEST_FLAGS)"; \ + echo "$(HDF5_DRIVER) $${tname} $(TEST_FLAGS) Test Log" >> $${log}; \ + fi; \ + echo "============================" >> $${log}; \ + srcdir="$(srcdir)" \ + $(TIME) $(RUNEXEC) ./$${tname} $(TEST_FLAGS) >> $${log} 2>&1 \ + && touch $(@:.chkexe_=.chkexe) || \ + (test $$HDF5_Make_Ignore && echo "*** Error ignored") || \ + (cat $${log} && false) || exit 1; \ + echo "" >> $${log}; \ + echo "Finished testing $${tname} $(TEST_FLAGS)" >> $${log}; \ + echo "============================" >> $${log}; \ + echo "Finished testing $${tname} $(TEST_FLAGS)"; \ + cat $${log}; \ + fi; \ + fi + +# The dummysh.chkexe here prevents the target from being +# empty if there are no tests in the current directory. +# $${log} is the log file. +# $${tname} is the name of test. +$(TEST_SCRIPT_CHKSH) $(TEST_SCRIPT_PARA_CHKSH) dummysh.chkexe_: + @if test "X$@" != "X.chkexe_" && test "X$@" != "Xdummysh.chkexe_"; then \ + cmd=$(@:.chkexe_=);\ + tname=`basename $$cmd`;\ + chkname=`basename $(@:.chkexe_=.chkexe)`;\ + log=`basename $(@:.chkexe_=.chklog)`; \ + echo "============================"; \ + if $(top_srcdir)/bin/newer $${chkname} $$cmd $(SCRIPT_DEPEND); then \ + echo "No need to test $${tname} again."; \ + else \ + echo "============================" > $${log}; \ + if test "X$(FORTRAN_API)" = "Xyes"; then \ + echo "Fortran API: Testing $${tname} $(TEST_FLAGS)"; \ + echo "Fortran API: $${tname} $(TEST_FLAGS) Test Log" >> $${log}; \ + elif test "X$(CXX_API)" = "Xyes"; then \ + echo "C++ API: Testing $${tname} $(TEST_FLAGS)"; \ + echo "C++ API: $${tname} $(TEST_FLAGS) Test Log" >> $${log}; \ + else \ + echo "Testing $${tname} $(TEST_FLAGS)"; \ + echo "$${tname} $(TEST_FLAGS) Test Log" >> $${log}; \ + fi; \ + echo "============================" >> $${log}; \ + RUNSERIAL="$(RUNSERIAL)" RUNPARALLEL="$(RUNPARALLEL)" \ + srcdir="$(srcdir)" \ + $(TIME) $(SHELL) $$cmd $(TEST_FLAGS) >> $${log} 2>&1 \ + && touch $${chkname} || \ + (test $$HDF5_Make_Ignore && echo "*** Error ignored") || \ + (cat $${log} && false) || exit 1; \ + echo "" >> $${log}; \ + echo "Finished testing $${tname} $(TEST_FLAGS)" >> $${log}; \ + echo "============================" >> $${log}; \ + echo "Finished testing $${tname} $(TEST_FLAGS)"; \ + cat $${log}; \ + fi; \ + echo "============================"; \ + fi + +# Actual execution of check-p. +build-check-p: $(LIB) $(PROGS) $(chk_TESTS) + @if test -n "$(TEST_PROG_PARA)$(TEST_SCRIPT_PARA)"; then \ + echo "===Parallel tests in `echo ${PWD} | sed -e s:.*/::` begin `date`==="; \ + fi + @if test -n "$(TEST_PROG_PARA)"; then \ + echo "**** Hint ****"; \ + echo "Parallel test files reside in the current directory" \ + "by default."; \ + echo "Set HDF5_PARAPREFIX to use another directory. E.g.,"; \ + echo " HDF5_PARAPREFIX=/PFS/user/me"; \ + echo " export HDF5_PARAPREFIX"; \ + echo " make check"; \ + echo "**** end of Hint ****"; \ + fi + @for test in $(TEST_PROG_PARA) dummy; do \ + if test $$test != dummy; then \ + $(MAKE) $(AM_MAKEFLAGS) $$test.chkexe_ \ + RUNEXEC="$(RUNPARALLEL)" || exit 1; \ + fi; \ + done + @for test in $(TEST_SCRIPT_PARA) dummy; do \ + if test $$test != dummy; then \ + $(MAKE) $(AM_MAKEFLAGS) $$test.chkexe_ || exit 1; \ + fi; \ + done + @if test -n "$(TEST_PROG_PARA)$(TEST_SCRIPT_PARA)"; then \ + echo "===Parallel tests in `echo ${PWD} | sed -e s:.*/::` ended `date`===";\ + fi + +# Run test with different Virtual File Driver +check-vfd: $(LIB) $(PROGS) $(chk_TESTS) + @for vfd in $(VFD_LIST) dummy; do \ + if test $$vfd != dummy; then \ + echo "============================"; \ + echo "Testing Virtual File Driver $$vfd"; \ + echo "============================"; \ + $(MAKE) $(AM_MAKEFLAGS) check-clean || exit 1; \ + HDF5_DRIVER=$$vfd $(MAKE) $(AM_MAKEFLAGS) check || exit 1; \ + fi; \ + done + +# Tell versions [3.59,3.63) of GNU make to not export all variables. +# Otherwise a system limit (for SysV at least) may be exceeded. +.NOEXPORT: diff --git a/tools/misc/vds/UC_1.h b/tools/misc/vds/UC_1.h new file mode 100644 index 0000000..29df72b --- /dev/null +++ b/tools/misc/vds/UC_1.h @@ -0,0 +1,150 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef UC_1_H +#define UC_1_H + +#include "hdf5.h" + +#include "UC_common.h" + +/* + * Definitions for VDS use case 1 + * + * Datasets have a single unlimited dimension and two fixed dimensions. They + * are mapped along a single dimension in the VDS with no gaps between them. + */ + +/* virtual dataset <---> source dataset mapping and sizes + + ***************** --+ + * A * K + ***************** --+ + * * | + * B * N + * * | + ***************** --+ + * C * + ***************** + * * + * D * + * * + ***************** + * E * + ***************** + * * + * F * + * * + ***************** + + | | + +-------M-------+ + + + dim[0] + / + / + / + -----> dim[2] + | + | + | + dim[1] + + */ + + +#define UC_1_N_SOURCES 6 + +/* Dataset dimensions */ +#define UC_1_SM_HEIGHT 2 /* K */ +#define UC_1_LG_HEIGHT 4 /* N */ +#define UC_1_SM_LG_HEIGHT 6 /* SM_HEIGHT + LG_HEIGHT */ +#define UC_1_FULL_HEIGHT 18 /* (3 * K) + (3 * N) */ +#define UC_1_HALF_HEIGHT 9 +#define UC_1_WIDTH 8 /* M */ +#define UC_1_HALF_WIDTH 4 + +#define UC_1_N_MAX_PLANES H5S_UNLIMITED /* max number of planes */ +#define UC_1_N_TEST_PLANES 5 /* number of planes we write */ + +/* Dataset datatypes */ +#define UC_1_SOURCE_DATATYPE H5T_STD_I32LE +#define UC_1_VDS_DATATYPE H5T_STD_I32LE + +/* Starting size of datasets, both source and VDS */ +static hsize_t UC_1_DIMS[UC_1_N_SOURCES][RANK] = { + {0, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {0, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {0, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {0, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {0, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {0, UC_1_LG_HEIGHT, UC_1_WIDTH} +}; +static hsize_t UC_1_VDS_DIMS[RANK] = {0, UC_1_FULL_HEIGHT, UC_1_WIDTH}; + +/* Maximum size of datasets, both source and VDS */ +static hsize_t UC_1_MAX_DIMS[UC_1_N_SOURCES][RANK] = { + {UC_1_N_MAX_PLANES, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {UC_1_N_MAX_PLANES, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {UC_1_N_MAX_PLANES, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {UC_1_N_MAX_PLANES, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {UC_1_N_MAX_PLANES, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {UC_1_N_MAX_PLANES, UC_1_LG_HEIGHT, UC_1_WIDTH} +}; +static hsize_t UC_1_VDS_MAX_DIMS[RANK] = {UC_1_N_MAX_PLANES, UC_1_FULL_HEIGHT, UC_1_WIDTH}; + +/* Planes */ +static hsize_t UC_1_PLANES[UC_1_N_SOURCES][RANK] = { + {1, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {1, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {1, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {1, UC_1_LG_HEIGHT, UC_1_WIDTH}, + {1, UC_1_SM_HEIGHT, UC_1_WIDTH}, + {1, UC_1_LG_HEIGHT, UC_1_WIDTH} +}; +static hsize_t UC_1_VDS_PLANE[RANK] = {1, UC_1_FULL_HEIGHT, UC_1_WIDTH}; + +/* File names for source datasets */ +static char UC_1_FILE_NAMES[UC_1_N_SOURCES][NAME_LEN] = { + {"1_a.h5"}, + {"1_b.h5"}, + {"1_c.h5"}, + {"1_d.h5"}, + {"1_e.h5"}, + {"1_f.h5"} +}; + +/* VDS file name */ +static char UC_1_VDS_FILE_NAME[NAME_LEN] = "1_vds.h5"; + +/* Dataset names */ +static char UC_1_SOURCE_DSET_NAME[NAME_LEN] = "source_dset"; +static char UC_1_SOURCE_DSET_PATH[NAME_LEN] = "/source_dset"; +static char UC_1_VDS_DSET_NAME[NAME_LEN] = "vds_dset"; + +/* Fill values */ +static hsize_t UC_1_FILL_VALUES[UC_1_N_SOURCES] = { + -1, + -2, + -3, + -4, + -5, + -6 +}; +static int UC_1_VDS_FILL_VALUE = -9; + +#endif /* UC_1_H */ + diff --git a/tools/misc/vds/UC_1_one_dim_gen.c b/tools/misc/vds/UC_1_one_dim_gen.c new file mode 100644 index 0000000..a78268b --- /dev/null +++ b/tools/misc/vds/UC_1_one_dim_gen.c @@ -0,0 +1,239 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * File/dataset generator for VDS use case 1 + * + * See the header file for a description. + */ + +#include <stdio.h> +#include <stdlib.h> + +#include "hdf5.h" + +#include "UC_common.h" +#include "UC_1.h" + + +int +main(int argc, char *argv[]) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t src_dcplid = -1; /* source dataset property list ID */ + + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + hid_t msid = -1; /* memory dataspace ID */ + hid_t fsid = -1; /* file dataspace ID */ + + hsize_t extent[RANK]; /* dataset extents */ + hsize_t start[RANK]; /* starting point for hyperslab */ + int map_start = -1; /* starting point in the VDS map */ + + int *buffer = NULL; /* data buffer */ + hsize_t count = 0; /* number of elements in a plane */ + int n_planes = -1; /* number of planes to write */ + int value = -1; /* value written to datasets */ + + int i; /* iterator */ + int j; /* iterator */ + int k; /* iterator */ + + + /* Start by creating the virtual dataset (VDS) dataspace and creation + * property list. The individual source datasets are then created + * and the VDS map (stored in the VDS property list) is updated. + */ + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_1_VDS_DATATYPE, + &UC_1_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_1_VDS_DIMS, + UC_1_VDS_MAX_DIMS)) < 0) + UC_ERROR + + /************************************ + * Create source files and datasets * + ************************************/ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + map_start = 0; + + for(i = 0; i < UC_1_N_SOURCES; i++) { + + /* Create source dataset dcpl */ + if((src_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_chunk(src_dcplid, RANK, UC_1_PLANES[i]) < 0) + UC_ERROR + if(H5Pset_fill_value(src_dcplid, UC_1_SOURCE_DATATYPE, + &UC_1_FILL_VALUES[i]) < 0) + UC_ERROR + if(0 != i % 2) + if(H5Pset_deflate(src_dcplid, COMPRESSION_LEVEL) < 0) + UC_ERROR + + /* Create source file, dataspace, and dataset */ + if((fid = H5Fcreate(UC_1_FILE_NAMES[i], H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + if((src_sid = H5Screate_simple(RANK, UC_1_DIMS[i], + UC_1_MAX_DIMS[i])) < 0) + UC_ERROR + if((did = H5Dcreate2(fid, UC_1_SOURCE_DSET_NAME, + UC_1_SOURCE_DATATYPE, src_sid, + H5P_DEFAULT, src_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* Set the dataset's extent (will eventually vary with i) */ + extent[0] = UC_1_N_TEST_PLANES; + extent[1] = UC_1_PLANES[i][1]; + extent[2] = UC_1_PLANES[i][2]; + if(H5Dset_extent(did, extent) < 0) + UC_ERROR + + /* Create a data buffer that represents a plane */ + count = UC_1_PLANES[i][1] * UC_1_PLANES[i][2]; + if(NULL == (buffer = (int *)malloc(count * sizeof(int)))) + UC_ERROR + + /* Create the memory dataspace */ + if((msid = H5Screate_simple(RANK, UC_1_PLANES[i], NULL)) < 0) + UC_ERROR + + /* Get the file dataspace */ + if((fsid = H5Dget_space(did)) < 0) + UC_ERROR + + /* Write planes to the dataset, number will eventually vary with i */ + n_planes = UC_1_N_TEST_PLANES; + for(j = 0; j < n_planes; j++) { + + value = ((i + 1) * 10) + j; + for(k = 0; k < count; k++) + buffer[k] = value; + + start[0] = j; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(fsid, H5S_SELECT_SET, start, NULL, UC_1_PLANES[i], NULL) < 0) + UC_ERROR + if(H5Dwrite(did, H5T_NATIVE_INT, msid, fsid, H5P_DEFAULT, buffer) < 0) + UC_ERROR + + } /* end for */ + + /* set up hyperslabs for source and destination datasets */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_1_MAX_DIMS[i], NULL) < 0) + UC_ERROR + start[0] = 0; + start[1] = map_start; + start[2] = 0; + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, start, NULL, + UC_1_MAX_DIMS[i], NULL) < 0) + UC_ERROR + map_start += UC_1_PLANES[i][1]; + + /* Add VDS mapping */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_1_FILE_NAMES[i], + UC_1_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + + /* close */ + if(H5Sclose(src_sid) < 0) + UC_ERROR + if(H5Pclose(src_dcplid) < 0) + UC_ERROR + if(H5Sclose(msid) < 0) + UC_ERROR + if(H5Sclose(fsid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + free(buffer); + + } /* end for */ + + + /******************* + * Create VDS file * + *******************/ + + /* file */ + if((fid = H5Fcreate(UC_1_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* dataset */ + if((did = H5Dcreate2(fid, UC_1_VDS_DSET_NAME, UC_1_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return EXIT_SUCCESS; + +error: + + H5E_BEGIN_TRY { + if(src_sid >= 0) + (void)H5Sclose(src_sid); + if(src_dcplid >= 0) + (void)H5Pclose(src_dcplid); + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + if(msid >= 0) + (void)H5Sclose(msid); + if(fsid >= 0) + (void)H5Sclose(fsid); + if(buffer != NULL) + free(buffer); + } H5E_END_TRY + + return EXIT_FAILURE; + +} /* end main */ + diff --git a/tools/misc/vds/UC_2.h b/tools/misc/vds/UC_2.h new file mode 100644 index 0000000..3e4e4fd --- /dev/null +++ b/tools/misc/vds/UC_2.h @@ -0,0 +1,151 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef UC_2_H +#define UC_2_H + +#include "hdf5.h" + +/* + * Definitions for VDS use case 2 + * + * Datasets have a single unlimited dimension and two fixed dimensions. They + * are mapped along two dimensions in the VDS with no gaps between them. + */ + +/* virtual dataset <---> source dataset mapping and sizes + + ********************************** + * A * * + ***************** D * + * * * + * B * * + * ****************** + ***************** E * + * C * * + ********************************** + + + dim[0] + / + / + / + -----> dim[2] + | + | + | + dim[1] + + */ + +#define UC_2_N_SOURCES 5 + +/* Dataset dimensions */ +#define UC_2_A_HEIGHT 2 +#define UC_2_B_HEIGHT 4 +#define UC_2_AB_HEIGHT 6 /* For hyperslab start position */ +#define UC_2_C_HEIGHT 2 +#define UC_2_D_HEIGHT 5 +#define UC_2_E_HEIGHT 3 +#define UC_2_FULL_HEIGHT 8 /* A+B+C and D+E */ +#define UC_2_WIDTH 7 +#define UC_2_FULL_WIDTH 14 /* 2*width */ + +#define UC_2_N_PLANES_IN_SERIES 3 /* number of planes in a series of sub-images */ +#define UC_2_N_MAX_PLANES H5S_UNLIMITED /* max number of planes */ +#define UC_2_N_TEST_PLANES 6 /* number of planes we write */ + +/* Dataset datatypes */ +#define UC_2_SOURCE_DATATYPE H5T_STD_I32LE +#define UC_2_VDS_DATATYPE H5T_STD_I32LE + +/* Starting size of datasets, both source and VDS */ +static hsize_t UC_2_DIMS[UC_2_N_SOURCES][RANK] = { + {0, UC_2_A_HEIGHT, UC_2_WIDTH}, + {0, UC_2_B_HEIGHT, UC_2_WIDTH}, + {0, UC_2_C_HEIGHT, UC_2_WIDTH}, + {0, UC_2_D_HEIGHT, UC_2_WIDTH}, + {0, UC_2_E_HEIGHT, UC_2_WIDTH} +}; +static hsize_t UC_2_VDS_DIMS[RANK] = {0, UC_2_FULL_HEIGHT, UC_2_FULL_WIDTH}; + +/* Maximum size of datasets, both source and VDS */ +static hsize_t UC_2_MAX_DIMS[UC_2_N_SOURCES][RANK] = { + {UC_2_N_MAX_PLANES, UC_2_A_HEIGHT, UC_2_WIDTH}, + {UC_2_N_MAX_PLANES, UC_2_B_HEIGHT, UC_2_WIDTH}, + {UC_2_N_MAX_PLANES, UC_2_C_HEIGHT, UC_2_WIDTH}, + {UC_2_N_MAX_PLANES, UC_2_D_HEIGHT, UC_2_WIDTH}, + {UC_2_N_MAX_PLANES, UC_2_E_HEIGHT, UC_2_WIDTH} +}; +static hsize_t UC_2_VDS_MAX_DIMS[RANK] = {UC_2_N_MAX_PLANES, UC_2_FULL_HEIGHT, UC_2_FULL_WIDTH}; + +/* Positions of source datasets in the VDS */ +static hsize_t UC_2_POSITIONS[UC_2_N_SOURCES][RANK] = { + /* A */ {0, 0, 0}, + /* B */ {0, UC_2_A_HEIGHT, 0}, + /* C */ {0, UC_2_AB_HEIGHT, 0}, + /* D */ {0, 0, UC_2_WIDTH}, + /* E */ {0, UC_2_D_HEIGHT, UC_2_WIDTH} +}; + +/* Planes */ +static hsize_t UC_2_PLANES[UC_2_N_SOURCES][RANK] = { + {1, UC_2_A_HEIGHT, UC_2_WIDTH}, + {1, UC_2_B_HEIGHT, UC_2_WIDTH}, + {1, UC_2_C_HEIGHT, UC_2_WIDTH}, + {1, UC_2_D_HEIGHT, UC_2_WIDTH}, + {1, UC_2_E_HEIGHT, UC_2_WIDTH} +}; +static hsize_t UC_2_VDS_SUB_IMAGE[RANK] = {1, UC_2_FULL_HEIGHT, UC_2_WIDTH}; +static hsize_t UC_2_VDS_PLANE[RANK] = {1, UC_2_FULL_HEIGHT, UC_2_FULL_WIDTH}; + +/* Chunk dimensions */ +static hsize_t UC_2_CHUNK_DIMS[UC_2_N_SOURCES][RANK] = { + {UC_2_N_PLANES_IN_SERIES, UC_2_A_HEIGHT, UC_2_WIDTH}, + {UC_2_N_PLANES_IN_SERIES, UC_2_B_HEIGHT, UC_2_WIDTH}, + {UC_2_N_PLANES_IN_SERIES, UC_2_C_HEIGHT, UC_2_WIDTH}, + {UC_2_N_PLANES_IN_SERIES, UC_2_D_HEIGHT, UC_2_WIDTH}, + {UC_2_N_PLANES_IN_SERIES, UC_2_E_HEIGHT, UC_2_WIDTH} +}; + +/* File names for source datasets */ +static char UC_2_FILE_NAMES[UC_2_N_SOURCES][NAME_LEN] = { + {"2_a.h5"}, + {"2_b.h5"}, + {"2_c.h5"}, + {"2_d.h5"}, + {"2_e.h5"} +}; + +/* VDS file name */ +#define UC_2_VDS_FILE_NAME "2_vds.h5" + +/* Dataset names */ +#define UC_2_SOURCE_DSET_NAME "source_dset" +#define UC_2_SOURCE_DSET_PATH "/source_dset" +#define UC_2_VDS_DSET_NAME "vds_dset" + +/* Fill values */ +static hsize_t UC_2_FILL_VALUES[UC_2_N_SOURCES] = { + -1, + -2, + -3, + -4, + -5 +}; +static int UC_2_VDS_FILL_VALUE = -9; + +#endif /* UC_2_H */ + diff --git a/tools/misc/vds/UC_2_two_dims_gen.c b/tools/misc/vds/UC_2_two_dims_gen.c new file mode 100644 index 0000000..b5fd319 --- /dev/null +++ b/tools/misc/vds/UC_2_two_dims_gen.c @@ -0,0 +1,230 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * File/dataset generator for VDS use case 2 + * + * See the header file for a description. + */ + + +#include <stdlib.h> + +#include "hdf5.h" + +#include "UC_common.h" +#include "UC_2.h" + +int +main(int argc, char *argv[]) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t src_dcplid = -1; /* source dataset property list ID */ + + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + hid_t msid = -1; /* memory dataspace ID */ + hid_t fsid = -1; /* file dataspace ID */ + + hsize_t start[RANK]; /* starting point for hyperslab */ + hsize_t extent[RANK]; /* dataset extents */ + + int *buffer = NULL; /* data buffer */ + int value = -1; /* value written to datasets */ + hsize_t count = 0; /* number of elements in a plane */ + int n_planes = -1; /* number of planes to write */ + + int i; /* iterator */ + int j; /* iterator */ + int k; /* iterator */ + + + /* Start by creating the virtual dataset (VDS) dataspace and creation + * property list. The individual source datasets are then created + * and the VDS map (stored in the VDS property list) is updated. + */ + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_2_VDS_DATATYPE, + &UC_2_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_2_VDS_DIMS, + UC_2_VDS_MAX_DIMS)) < 0) + UC_ERROR + + /************************************ + * Create source files and datasets * + ************************************/ + + start[0] = 0; + start[1] = 0; + start[2] = 0; + + for(i = 0; i < UC_2_N_SOURCES; i++) { + + /* source dataset dcpl */ + if((src_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_chunk(src_dcplid, RANK, UC_2_CHUNK_DIMS[i]) < 0) + UC_ERROR + if(H5Pset_fill_value(src_dcplid, UC_2_SOURCE_DATATYPE, + &UC_2_FILL_VALUES[i]) < 0) + UC_ERROR + if(H5Pset_deflate(src_dcplid, COMPRESSION_LEVEL) < 0) + UC_ERROR + + /* Create source file, dataspace, and dataset */ + if((fid = H5Fcreate(UC_2_FILE_NAMES[i], H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + if((src_sid = H5Screate_simple(RANK, UC_2_DIMS[i], + UC_2_MAX_DIMS[i])) < 0) + UC_ERROR + if((did = H5Dcreate2(fid, UC_2_SOURCE_DSET_NAME, + UC_2_SOURCE_DATATYPE, src_sid, + H5P_DEFAULT, src_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* Set the dataset's extent (will eventually vary with i) */ + extent[0] = UC_2_N_TEST_PLANES; + extent[1] = UC_2_PLANES[i][1]; + extent[2] = UC_2_PLANES[i][2]; + if(H5Dset_extent(did, extent) < 0) + UC_ERROR + + /* Create a data buffer that represents a plane */ + count = UC_2_PLANES[i][1] * UC_2_PLANES[i][2]; + if(NULL == (buffer = (int *)malloc(count * sizeof(int)))) + UC_ERROR + + /* Create the memory dataspace */ + if((msid = H5Screate_simple(RANK, UC_2_PLANES[i], NULL)) < 0) + UC_ERROR + + /* Get the file dataspace */ + if((fsid = H5Dget_space(did)) < 0) + UC_ERROR + + /* Write planes to the dataset, number will eventually vary with i */ + n_planes = UC_2_N_TEST_PLANES; + for(j = 0; j < n_planes; j++) { + + value = ((i + 1) * 10) + j; + for(k = 0; k < count; k++) + buffer[k] = value; + + start[0] = j; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(fsid, H5S_SELECT_SET, start, NULL, UC_2_PLANES[i], NULL) < 0) + UC_ERROR + if(H5Dwrite(did, H5T_NATIVE_INT, msid, fsid, H5P_DEFAULT, buffer) < 0) + UC_ERROR + + } /* end for */ + + /* set up hyperslabs for source and destination datasets */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_2_MAX_DIMS[i], NULL) < 0) + UC_ERROR + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, UC_2_POSITIONS[i], NULL, + UC_2_MAX_DIMS[i], NULL) < 0) + UC_ERROR + + /* Add VDS mapping */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_2_FILE_NAMES[i], + UC_2_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + + /* close */ + if(H5Sclose(msid) < 0) + UC_ERROR + if(H5Sclose(fsid) < 0) + UC_ERROR + if(H5Sclose(src_sid) < 0) + UC_ERROR + if(H5Pclose(src_dcplid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + free(buffer); + + } /* end for */ + + /******************************* + * Create VDS file and dataset * + *******************************/ + + /* file */ + if((fid = H5Fcreate(UC_2_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* dataset */ + if((did = H5Dcreate2(fid, UC_2_VDS_DSET_NAME, UC_2_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return EXIT_SUCCESS; + +error: + + H5E_BEGIN_TRY { + if(src_sid >= 0) + (void)H5Sclose(src_sid); + if(src_dcplid >= 0) + (void)H5Pclose(src_dcplid); + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + if(msid >= 0) + (void)H5Sclose(msid); + if(fsid >= 0) + (void)H5Sclose(fsid); + if(buffer != NULL) + free(buffer); + } H5E_END_TRY + + return EXIT_FAILURE; + +} /* end main() */ + diff --git a/tools/misc/vds/UC_3.h b/tools/misc/vds/UC_3.h new file mode 100644 index 0000000..a27c3cf --- /dev/null +++ b/tools/misc/vds/UC_3.h @@ -0,0 +1,78 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef UC_3_H +#define UC_3_H + +#include "hdf5.h" + +#include "UC_1.h" +#include "UC_2.h" + +/* + * Definitions for VDS use case 3 + * + * Datasets have a single unlimited dimension and one or two fixed + * dimensions (they are reused from use cases 1 and 2). In this use case, + * the datasets are mapped in the VDS with gaps between them. + */ + +/* VDS dimensions + * Height and width are large enough to encompass the + * mapped source datasets with gaps. + */ +#define UC_31_VDS_HEIGHT 25 /* full height + 7 (gaps of 1) */ +#define UC_31_VDS_WIDTH 8 /* full width + 0 (no gaps) */ +#define UC_32_VDS_HEIGHT 13 /* full height + 5 */ +#define UC_32_VDS_WIDTH 19 /* full width + 5 */ +#define UC_31_GAP 1 + +/* VDS datatypes */ +#define UC_31_VDS_DATATYPE H5T_STD_I32LE +#define UC_32_VDS_DATATYPE H5T_STD_I32LE + +/* Starting size of virtual datasets */ +static hsize_t UC_31_VDS_DIMS[RANK] = {0, UC_31_VDS_HEIGHT, UC_31_VDS_WIDTH}; +static hsize_t UC_32_VDS_DIMS[RANK] = {0, UC_32_VDS_HEIGHT, UC_32_VDS_WIDTH}; + +/* Maximum size of virtual datasets */ +static hsize_t UC_31_VDS_MAX_DIMS[RANK] = {UC_1_N_MAX_PLANES, UC_31_VDS_HEIGHT, UC_31_VDS_WIDTH}; +static hsize_t UC_32_VDS_MAX_DIMS[RANK] = {UC_2_N_MAX_PLANES, UC_32_VDS_HEIGHT, UC_32_VDS_WIDTH}; + +/* Positions of mapped source datasets */ +static hsize_t UC_32_POSITIONS[UC_2_N_SOURCES][RANK] = { + /* A */ {0, 1, 1}, + /* B */ {0, 4, 0}, + /* C */ {0, 11, 4}, + /* D */ {0, 1, 9}, + /* E */ {0, 8, 12} +}; + +/* Planes */ +static hsize_t UC_31_VDS_PLANE[RANK] = {1, UC_31_VDS_HEIGHT, UC_31_VDS_WIDTH}; +static hsize_t UC_32_VDS_PLANE[RANK] = {1, UC_32_VDS_HEIGHT, UC_32_VDS_WIDTH}; + +/* VDS file names */ +#define UC_31_VDS_FILE_NAME "3_1_vds.h5" +#define UC_32_VDS_FILE_NAME "3_2_vds.h5" + +/* Dataset name */ +#define UC_3_VDS_DSET_NAME "vds_dset" + +/* Fill value */ +static int UC_3_VDS_FILL_VALUE = -9; + +#endif /* UC_3_H */ + diff --git a/tools/misc/vds/UC_3_gaps_gen.c b/tools/misc/vds/UC_3_gaps_gen.c new file mode 100644 index 0000000..1f150c1 --- /dev/null +++ b/tools/misc/vds/UC_3_gaps_gen.c @@ -0,0 +1,255 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * File/dataset generator for VDS use case 3 + * + * See the header file for a description. + */ + +#include <stdlib.h> +#include <string.h> + +#include <hdf5.h> + +#include "UC_common.h" +#include "UC_3.h" + +/* Create the VDS that uses use case 1 files */ +herr_t +create_3_1_vds(void) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + + hsize_t start[RANK]; /* source starting point for hyperslab */ + hsize_t position[RANK]; /* vds mapping positions */ + + int i; /* iterator */ + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_31_VDS_DATATYPE, + &UC_3_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_31_VDS_DIMS, + UC_31_VDS_MAX_DIMS)) < 0) + UC_ERROR + + /* Set starting positions */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + + position[0] = 0; + position[1] = UC_31_GAP; + position[2] = 0; + + /****************************** + * Create source-VDS mappings * + ******************************/ + for(i = 0; i < UC_1_N_SOURCES; i++) { + + if((src_sid = H5Screate_simple(RANK, UC_1_DIMS[i], + UC_1_MAX_DIMS[i])) < 0) + UC_ERROR + + /* set up hyperslabs for source and destination datasets */ + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_1_MAX_DIMS[i], NULL) < 0) + UC_ERROR + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, position, + NULL, UC_1_MAX_DIMS[i], NULL) < 0) + UC_ERROR + position[1] += UC_1_DIMS[i][1] + UC_31_GAP; + + /* Add VDS mapping */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_1_FILE_NAMES[i], + UC_1_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + if(H5Sclose(src_sid) < 0) + UC_ERROR + + } /* end for */ + + /******************************* + * Create VDS file and dataset * + *******************************/ + + /* file */ + if((fid = H5Fcreate(UC_31_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* dataset */ + if((did = H5Dcreate2(fid, UC_3_VDS_DSET_NAME, UC_31_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return 0; + +error: + + H5E_BEGIN_TRY { + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + } H5E_END_TRY + + return -1; + +} /* end create_3_1_vds() */ + +/* Create the VDS that uses use case 2 files */ +herr_t +create_3_2_vds(void) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + + hsize_t start[RANK]; /* source starting point for hyperslab */ + + int i; /* iterator */ + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_32_VDS_DATATYPE, + &UC_3_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_32_VDS_DIMS, + UC_32_VDS_MAX_DIMS)) < 0) + UC_ERROR + + /* Set starting positions */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + + /****************************** + * Create source-VDS mappings * + ******************************/ + for(i = 0; i < UC_2_N_SOURCES; i++) { + + if((src_sid = H5Screate_simple(RANK, UC_2_DIMS[i], + UC_2_MAX_DIMS[i])) < 0) + UC_ERROR + + /* set up hyperslabs for source and destination datasets */ + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_2_MAX_DIMS[i], NULL) < 0) + UC_ERROR + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, UC_32_POSITIONS[i], + NULL, UC_2_MAX_DIMS[i], NULL) < 0) + UC_ERROR + + /* Add VDS mapping */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_2_FILE_NAMES[i], + UC_2_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + if(H5Sclose(src_sid) < 0) + UC_ERROR + + } /* end for */ + + /******************************* + * Create VDS file and dataset * + *******************************/ + + /* file */ + if((fid = H5Fcreate(UC_32_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* dataset */ + if((did = H5Dcreate2(fid, UC_3_VDS_DSET_NAME, UC_32_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return 0; + +error: + + H5E_BEGIN_TRY { + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + } H5E_END_TRY + + return -1; + +} /* end create_3_2_vds() */ + +int +main(int argc, char *argv[]) +{ + + if(create_3_1_vds() < 0) + UC_ERROR + + if(create_3_2_vds() < 0) + UC_ERROR + + return EXIT_SUCCESS; + +error: + + return EXIT_FAILURE; + +} /* end main() */ + diff --git a/tools/misc/vds/UC_4.h b/tools/misc/vds/UC_4.h new file mode 100644 index 0000000..ce74e63 --- /dev/null +++ b/tools/misc/vds/UC_4.h @@ -0,0 +1,86 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef UC_4_H +#define UC_4_H + +#include "hdf5.h" + +#include "UC_common.h" + +/* + * Definitions for VDS use case 4 + * + * Source datasets have three fixed dimensions. In this use case, the + * datasets are mapped consecutively in the VDS along a single dimension with + * no gaps between them. Datasets are automatically loaded using a + * printf-like format string for the file name. + */ + +/* virtual dataset <---> source dataset mapping and sizes */ + +#define UC_4_N_SOURCES 3 + +/* Dataset dimensions */ +#define UC_4_SRC_PLANES 3 +#define UC_4_HEIGHT 4 +#define UC_4_WIDTH 4 + +/* max number of planes for VDS (sources are finite) */ +#define UC_4_VDS_MAX_PLANES H5S_UNLIMITED +#define UC_4_N_TEST_PLANES 9 /* number of planes in the VDS */ + +/* Dataset datatypes */ +#define UC_4_SOURCE_DATATYPE H5T_STD_I32LE +#define UC_4_VDS_DATATYPE H5T_STD_I32LE + +/* Starting size of datasets, both source and VDS */ +static hsize_t UC_4_SOURCE_DIMS[RANK] = {0, UC_4_HEIGHT, UC_4_WIDTH}; +static hsize_t UC_4_VDS_DIMS[RANK] = {0, UC_4_HEIGHT, UC_4_WIDTH}; + +/* Max size of datasets, both source and VDS */ +static hsize_t UC_4_SOURCE_MAX_DIMS[RANK] = {UC_4_SRC_PLANES, UC_4_HEIGHT, UC_4_WIDTH}; +static hsize_t UC_4_VDS_MAX_DIMS[RANK] = {UC_4_VDS_MAX_PLANES, UC_4_HEIGHT, UC_4_WIDTH}; + +/* Planes (both source and VDS) */ +static hsize_t UC_4_PLANE[RANK] = {1, UC_4_HEIGHT, UC_4_WIDTH}; + +/* File names for source datasets */ +static char UC_4_FILE_NAMES[UC_4_N_SOURCES][NAME_LEN] = { + {"4_0.h5"}, + {"4_1.h5"}, + {"4_2.h5"} +}; +static char UC_4_MAPPING_FILE_NAME[NAME_LEN] = "4_%b.h5"; + +/* VDS file name */ +static char UC_4_VDS_FILE_NAME[NAME_LEN] = "4_vds.h5"; + +/* Dataset names */ +static char UC_4_SOURCE_DSET_NAME[NAME_LEN] = "source_dset"; +static char UC_4_SOURCE_DSET_PATH[NAME_LEN] = "/source_dset"; +static char UC_4_VDS_DSET_NAME[NAME_LEN] = "vds_dset"; + +/* Fill values */ +static hsize_t UC_4_FILL_VALUES[UC_4_N_SOURCES] = { + -1, + -2, + -3 +}; +static int UC_4_VDS_FILL_VALUE = -9; + +#endif /* UC_4_H */ + + diff --git a/tools/misc/vds/UC_4_printf_gen.c b/tools/misc/vds/UC_4_printf_gen.c new file mode 100644 index 0000000..c8e111a --- /dev/null +++ b/tools/misc/vds/UC_4_printf_gen.c @@ -0,0 +1,219 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * File/dataset generator for VDS use case 4 + * + * See the header file for a description. + */ + +#include <stdlib.h> + +#include <hdf5.h> + +#include "UC_common.h" +#include "UC_4.h" + +int +main(int argc, char *argv[]) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t src_dcplid = -1; /* source dataset property list ID */ + + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + hid_t msid = -1; /* memory dataspace ID */ + hid_t fsid = -1; /* file dataspace ID */ + + /* Hyperslab arrays */ + hsize_t start[RANK] = {0, 0, 0}; + hsize_t count[RANK] = {H5S_UNLIMITED, 1, 1}; + + int *buffer = NULL; /* data buffer */ + int value = -1; /* value written to datasets */ + + hsize_t n = 0; /* number of elements in a plane */ + + int i; /* iterator */ + int j; /* iterator */ + int k; /* iterator */ + + /************************************ + * Create source files and datasets * + ************************************/ + + /* Create source dataspace ID */ + if((src_sid = H5Screate_simple(RANK, UC_4_SOURCE_DIMS, + UC_4_SOURCE_MAX_DIMS)) < 0) + UC_ERROR + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_4_SOURCE_MAX_DIMS, NULL) < 0) + UC_ERROR + + /* Create source files and datasets */ + for(i = 0; i < UC_4_N_SOURCES; i++) { + + /* source dataset dcpl */ + if((src_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_chunk(src_dcplid, RANK, UC_4_PLANE) < 0) + UC_ERROR + if(H5Pset_fill_value(src_dcplid, UC_4_SOURCE_DATATYPE, + &UC_4_FILL_VALUES[i]) < 0) + UC_ERROR + if(H5Pset_deflate(src_dcplid, COMPRESSION_LEVEL) < 0) + UC_ERROR + + /* Create source file and dataset */ + if((fid = H5Fcreate(UC_4_FILE_NAMES[i], H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + if((did = H5Dcreate2(fid, UC_4_SOURCE_DSET_NAME, + UC_4_SOURCE_DATATYPE, src_sid, + H5P_DEFAULT, src_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* Set the dataset's extent */ + if(H5Dset_extent(did, UC_4_SOURCE_MAX_DIMS) < 0) + UC_ERROR + + /* Create a data buffer that represents a plane */ + n = UC_4_PLANE[1] * UC_4_PLANE[2]; + if(NULL == (buffer = (int *)malloc(n * sizeof(int)))) + UC_ERROR + + /* Create the memory dataspace */ + if((msid = H5Screate_simple(RANK, UC_4_PLANE, NULL)) < 0) + UC_ERROR + + /* Get the file dataspace */ + if((fsid = H5Dget_space(did)) < 0) + UC_ERROR + + /* Write planes to the dataset */ + for(j = 0; j < UC_4_SRC_PLANES; j++) { + + value = ((i + 1) * 10) + j; + for(k = 0; k < n; k++) + buffer[k] = value; + + start[0] = j; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(fsid, H5S_SELECT_SET, start, NULL, UC_4_PLANE, NULL) < 0) + UC_ERROR + if(H5Dwrite(did, H5T_NATIVE_INT, msid, fsid, H5P_DEFAULT, buffer) < 0) + UC_ERROR + + } /* end for */ + + /* close */ + if(H5Sclose(msid) < 0) + UC_ERROR + if(H5Sclose(fsid) < 0) + UC_ERROR + if(H5Pclose(src_dcplid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + free(buffer); + + } /* end for */ + + /******************* + * Create VDS file * + *******************/ + + /* Create file */ + if((fid = H5Fcreate(UC_4_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_4_VDS_DATATYPE, + &UC_4_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_4_VDS_DIMS, + UC_4_VDS_MAX_DIMS)) < 0) + UC_ERROR + start[0] = 0; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, start, + UC_4_SOURCE_MAX_DIMS, count, UC_4_SOURCE_MAX_DIMS) < 0) + UC_ERROR + + /* Add VDS mapping - The mapped file name uses a printf-like + * naming scheme that automatically maps new files. + */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_4_MAPPING_FILE_NAME, + UC_4_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + + /* Create dataset */ + if((did = H5Dcreate2(fid, UC_4_VDS_DSET_NAME, UC_4_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Sclose(src_sid) < 0) + UC_ERROR + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return EXIT_SUCCESS; + +error: + + H5E_BEGIN_TRY { + if(src_sid >= 0) + (void)H5Sclose(src_sid); + if(src_dcplid >= 0) + (void)H5Pclose(src_dcplid); + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + if(msid >= 0) + (void)H5Sclose(msid); + if(fsid >= 0) + (void)H5Sclose(fsid); + if(buffer != NULL) + free(buffer); + } H5E_END_TRY + + return EXIT_FAILURE; + +} /* end main() */ + diff --git a/tools/misc/vds/UC_5.h b/tools/misc/vds/UC_5.h new file mode 100644 index 0000000..b22b177 --- /dev/null +++ b/tools/misc/vds/UC_5.h @@ -0,0 +1,83 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef UC_5_H +#define UC_5_H + +#include <hdf5.h> + +#include "UC_common.h" + +/* + * Definitions for VDS use case 5 + * + * Source datasets have one unlimited dimension and two fixed dimensions. In + * this use case, the datasets are mapped in the VDS so that alternating + * planes in the source are interleaved in the VDS. + */ + +/* virtual dataset <---> source dataset mapping and sizes */ + +#define UC_5_N_SOURCES 3 + +/* Dataset dimensions */ +#define UC_5_SRC_PLANES 3 +#define UC_5_HEIGHT 4 +#define UC_5_WIDTH 4 + +/* max number of planes for datasets */ +#define UC_5_MAX_PLANES H5S_UNLIMITED +#define UC_5_N_TEST_PLANES 9 /* number of planes in VDS */ + +/* Dataset datatypes */ +#define UC_5_SOURCE_DATATYPE H5T_STD_I32LE +#define UC_5_VDS_DATATYPE H5T_STD_I32LE + +/* Starting size of datasets, both source and VDS */ +static hsize_t UC_5_SOURCE_DIMS[RANK] = {0, UC_5_HEIGHT, UC_5_WIDTH}; +static hsize_t UC_5_VDS_DIMS[RANK] = {0, UC_5_HEIGHT, UC_5_WIDTH}; + +/* Max size of datasets, both source and VDS */ +static hsize_t UC_5_SOURCE_MAX_DIMS[RANK] = {UC_5_MAX_PLANES, UC_5_HEIGHT, UC_5_WIDTH}; +static hsize_t UC_5_VDS_MAX_DIMS[RANK] = {UC_5_MAX_PLANES, UC_5_HEIGHT, UC_5_WIDTH}; + +/* Planes (both source and VDS) */ +static hsize_t UC_5_PLANE[RANK] = {1, UC_5_HEIGHT, UC_5_WIDTH}; + +/* File names for source datasets */ +static char UC_5_FILE_NAMES[UC_5_N_SOURCES][NAME_LEN] = { + {"5_a.h5"}, + {"5_b.h5"}, + {"5_c.h5"} +}; + +/* VDS file name */ +static char UC_5_VDS_FILE_NAME[NAME_LEN] = "5_vds.h5"; + +/* Dataset names */ +static char UC_5_SOURCE_DSET_NAME[NAME_LEN] = "source_dset"; +static char UC_5_SOURCE_DSET_PATH[NAME_LEN] = "/source_dset"; +static char UC_5_VDS_DSET_NAME[NAME_LEN] = "vds_dset"; + +/* Fill values */ +static hsize_t UC_5_FILL_VALUES[UC_5_N_SOURCES] = { + -1, + -2, + -3 +}; +static int UC_5_VDS_FILL_VALUE = -9; + +#endif /* UC_5_H */ + diff --git a/tools/misc/vds/UC_5_stride_gen.c b/tools/misc/vds/UC_5_stride_gen.c new file mode 100644 index 0000000..984aadc --- /dev/null +++ b/tools/misc/vds/UC_5_stride_gen.c @@ -0,0 +1,243 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * File/dataset generator for VDS use case 5 + * + * See the header file for a description. + */ + +#include <stdlib.h> + +#include <hdf5.h> + +#include "UC_common.h" +#include "UC_5.h" + +int +main(int argc, char *argv[]) +{ + hid_t src_sid = -1; /* source dataset's dataspace ID */ + hid_t src_dcplid = -1; /* source dataset property list ID */ + + hid_t vds_sid = -1; /* VDS dataspace ID */ + hid_t vds_dcplid = -1; /* VDS dataset property list ID */ + + hid_t fid = -1; /* HDF5 file ID */ + hid_t did = -1; /* dataset ID */ + hid_t msid = -1; /* memory dataspace ID */ + hid_t fsid = -1; /* file dataspace ID */ + + hsize_t extent[RANK]; /* source dataset extents */ + hsize_t start[RANK]; /* starting point for hyperslab */ + hsize_t stride[RANK]; /* hypserslab stride */ + hsize_t count[RANK]; /* hypserslab count */ + int map_start = -1; /* starting point in the VDS map */ + + int *buffer = NULL; /* data buffer */ + int value = -1; /* value written to datasets */ + + hsize_t n = 0; /* number of elements in a plane */ + + int i; /* iterator */ + int j; /* iterator */ + int k; /* iterator */ + + /* Start by creating the virtual dataset (VDS) dataspace and creation + * property list. The individual source datasets are then created + * and the VDS map (stored in the VDS property list) is updated. + */ + + /* Create VDS dcpl */ + if((vds_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_fill_value(vds_dcplid, UC_5_VDS_DATATYPE, + &UC_5_VDS_FILL_VALUE) < 0) + UC_ERROR + + /* Create VDS dataspace */ + if((vds_sid = H5Screate_simple(RANK, UC_5_VDS_DIMS, + UC_5_VDS_MAX_DIMS)) < 0) + UC_ERROR + + /********************************* + * Map source files and datasets * + *********************************/ + + /* Hyperslab array setup */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + map_start = 0; + + stride[0] = UC_5_N_SOURCES; + stride[1] = 1; + stride[2] = 1; + + count[0] = H5S_UNLIMITED; + count[1] = 1; + count[2] = 1; + + extent[0] = UC_5_SRC_PLANES; + extent[1] = UC_5_HEIGHT; + extent[2] = UC_5_WIDTH; + + for(i = 0; i < UC_5_N_SOURCES; i++) { + + /* source dataset dcpl */ + if((src_dcplid = H5Pcreate(H5P_DATASET_CREATE)) < 0) + UC_ERROR + if(H5Pset_chunk(src_dcplid, RANK, UC_5_PLANE) < 0) + UC_ERROR + if(H5Pset_fill_value(src_dcplid, UC_5_SOURCE_DATATYPE, + &UC_5_FILL_VALUES[i]) < 0) + UC_ERROR + if(H5Pset_deflate(src_dcplid, COMPRESSION_LEVEL) < 0) + UC_ERROR + + /* Create source file, dataspace, and dataset */ + if((fid = H5Fcreate(UC_5_FILE_NAMES[i], H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + if((src_sid = H5Screate_simple(RANK, UC_5_SOURCE_DIMS, + UC_5_SOURCE_MAX_DIMS)) < 0) + UC_ERROR + if((did = H5Dcreate2(fid, UC_5_SOURCE_DSET_NAME, + UC_5_SOURCE_DATATYPE, src_sid, + H5P_DEFAULT, src_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* Set the dataset's extent */ + if(H5Dset_extent(did, extent) < 0) + UC_ERROR + + /* Create a data buffer that represents a plane */ + n = UC_5_PLANE[1] * UC_5_PLANE[2]; + if(NULL == (buffer = (int *)malloc(n * sizeof(int)))) + UC_ERROR + + /* Create the memory dataspace */ + if((msid = H5Screate_simple(RANK, UC_5_PLANE, NULL)) < 0) + UC_ERROR + + /* Get the file dataspace */ + if((fsid = H5Dget_space(did)) < 0) + UC_ERROR + + /* Write planes to the dataset */ + for(j = 0; j < UC_5_SRC_PLANES; j++) { + + value = ((i + 1) * 10) + j; + for(k = 0; k < n; k++) + buffer[k] = value; + + start[0] = j; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(fsid, H5S_SELECT_SET, start, NULL, UC_5_PLANE, NULL) < 0) + UC_ERROR + if(H5Dwrite(did, H5T_NATIVE_INT, msid, fsid, H5P_DEFAULT, buffer) < 0) + UC_ERROR + + } /* end for */ + + /* set up hyperslabs for source and destination datasets */ + start[0] = 0; + start[1] = 0; + start[2] = 0; + if(H5Sselect_hyperslab(src_sid, H5S_SELECT_SET, start, NULL, + UC_5_SOURCE_MAX_DIMS, NULL) < 0) + UC_ERROR + start[0] = map_start; + if(H5Sselect_hyperslab(vds_sid, H5S_SELECT_SET, start, stride, + count, UC_5_PLANE) < 0) + UC_ERROR + map_start += 1; + + /* Add VDS mapping */ + if(H5Pset_virtual(vds_dcplid, vds_sid, UC_5_FILE_NAMES[i], + UC_5_SOURCE_DSET_PATH, src_sid) < 0) + UC_ERROR + + /* close */ + if(H5Sclose(msid) < 0) + UC_ERROR + if(H5Sclose(fsid) < 0) + UC_ERROR + if(H5Sclose(src_sid) < 0) + UC_ERROR + if(H5Pclose(src_dcplid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + free(buffer); + + } /* end for */ + + /******************* + * Create VDS file * + *******************/ + + /* file */ + if((fid = H5Fcreate(UC_5_VDS_FILE_NAME, H5F_ACC_TRUNC, + H5P_DEFAULT, H5P_DEFAULT)) < 0) + UC_ERROR + + /* dataset */ + if((did = H5Dcreate2(fid, UC_5_VDS_DSET_NAME, UC_5_VDS_DATATYPE, vds_sid, + H5P_DEFAULT, vds_dcplid, H5P_DEFAULT)) < 0) + UC_ERROR + + /* close */ + if(H5Pclose(vds_dcplid) < 0) + UC_ERROR + if(H5Sclose(vds_sid) < 0) + UC_ERROR + if(H5Dclose(did) < 0) + UC_ERROR + if(H5Fclose(fid) < 0) + UC_ERROR + + return EXIT_SUCCESS; + +error: + + H5E_BEGIN_TRY { + if(src_sid >= 0) + (void)H5Sclose(src_sid); + if(src_dcplid >= 0) + (void)H5Pclose(src_dcplid); + if(vds_sid >= 0) + (void)H5Sclose(vds_sid); + if(vds_dcplid >= 0) + (void)H5Pclose(vds_dcplid); + if(fid >= 0) + (void)H5Fclose(fid); + if(did >= 0) + (void)H5Dclose(did); + if(msid >= 0) + (void)H5Sclose(msid); + if(fsid >= 0) + (void)H5Sclose(fsid); + if(buffer != NULL) + free(buffer); + } H5E_END_TRY + + return EXIT_FAILURE; + +} /* end main() */ + diff --git a/tools/misc/vds/UC_common.h b/tools/misc/vds/UC_common.h new file mode 100644 index 0000000..0e61016 --- /dev/null +++ b/tools/misc/vds/UC_common.h @@ -0,0 +1,41 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * 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 files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef USE_CASE_COMMON_H +#define USE_CASE_COMMON_H + +/****************************************** + * Symbols used across multiple use cases * + ******************************************/ + +/* All datasets are 3D */ +#define RANK 3 + +/* Lengths of string identifiers (file, dataset names, etc.) */ +#define NAME_LEN 32 + +/* Compression level */ +#define COMPRESSION_LEVEL 7 + +/* Booleans */ +#define TRUE 1 +#define FALSE 0 + +/* Testing macros */ +#define AT() printf (" at %s:%d in %s()...\n", __FILE__, __LINE__, __func__); +#define UC_ERROR {puts("*ERROR*"); fflush(stdout); AT(); goto error;} + +#endif /* USE_CASE_COMMON_H */ + diff --git a/tools/testfiles/vds/1_a.h5 b/tools/testfiles/vds/1_a.h5 Binary files differnew file mode 100644 index 0000000..533728f --- /dev/null +++ b/tools/testfiles/vds/1_a.h5 diff --git a/tools/testfiles/vds/1_b.h5 b/tools/testfiles/vds/1_b.h5 Binary files differnew file mode 100644 index 0000000..4195588 --- /dev/null +++ b/tools/testfiles/vds/1_b.h5 diff --git a/tools/testfiles/vds/1_c.h5 b/tools/testfiles/vds/1_c.h5 Binary files differnew file mode 100644 index 0000000..cc6c2c7 --- /dev/null +++ b/tools/testfiles/vds/1_c.h5 diff --git a/tools/testfiles/vds/1_d.h5 b/tools/testfiles/vds/1_d.h5 Binary files differnew file mode 100644 index 0000000..20bea0b --- /dev/null +++ b/tools/testfiles/vds/1_d.h5 diff --git a/tools/testfiles/vds/1_e.h5 b/tools/testfiles/vds/1_e.h5 Binary files differnew file mode 100644 index 0000000..43e9cea --- /dev/null +++ b/tools/testfiles/vds/1_e.h5 diff --git a/tools/testfiles/vds/1_f.h5 b/tools/testfiles/vds/1_f.h5 Binary files differnew file mode 100644 index 0000000..c49843e --- /dev/null +++ b/tools/testfiles/vds/1_f.h5 diff --git a/tools/testfiles/vds/1_vds.h5 b/tools/testfiles/vds/1_vds.h5 Binary files differnew file mode 100644 index 0000000..59c76ea --- /dev/null +++ b/tools/testfiles/vds/1_vds.h5 diff --git a/tools/testfiles/vds/2_a.h5 b/tools/testfiles/vds/2_a.h5 Binary files differnew file mode 100644 index 0000000..bba7854 --- /dev/null +++ b/tools/testfiles/vds/2_a.h5 diff --git a/tools/testfiles/vds/2_b.h5 b/tools/testfiles/vds/2_b.h5 Binary files differnew file mode 100644 index 0000000..a30ff72 --- /dev/null +++ b/tools/testfiles/vds/2_b.h5 diff --git a/tools/testfiles/vds/2_c.h5 b/tools/testfiles/vds/2_c.h5 Binary files differnew file mode 100644 index 0000000..bec8e65 --- /dev/null +++ b/tools/testfiles/vds/2_c.h5 diff --git a/tools/testfiles/vds/2_d.h5 b/tools/testfiles/vds/2_d.h5 Binary files differnew file mode 100644 index 0000000..605ff85 --- /dev/null +++ b/tools/testfiles/vds/2_d.h5 diff --git a/tools/testfiles/vds/2_e.h5 b/tools/testfiles/vds/2_e.h5 Binary files differnew file mode 100644 index 0000000..a033de1 --- /dev/null +++ b/tools/testfiles/vds/2_e.h5 diff --git a/tools/testfiles/vds/2_vds.h5 b/tools/testfiles/vds/2_vds.h5 Binary files differnew file mode 100644 index 0000000..85f075a --- /dev/null +++ b/tools/testfiles/vds/2_vds.h5 diff --git a/tools/testfiles/vds/3_1_vds.h5 b/tools/testfiles/vds/3_1_vds.h5 Binary files differnew file mode 100644 index 0000000..9661907 --- /dev/null +++ b/tools/testfiles/vds/3_1_vds.h5 diff --git a/tools/testfiles/vds/3_2_vds.h5 b/tools/testfiles/vds/3_2_vds.h5 Binary files differnew file mode 100644 index 0000000..c39fee4 --- /dev/null +++ b/tools/testfiles/vds/3_2_vds.h5 diff --git a/tools/testfiles/vds/4_0.h5 b/tools/testfiles/vds/4_0.h5 Binary files differnew file mode 100644 index 0000000..3f5b594 --- /dev/null +++ b/tools/testfiles/vds/4_0.h5 diff --git a/tools/testfiles/vds/4_1.h5 b/tools/testfiles/vds/4_1.h5 Binary files differnew file mode 100644 index 0000000..0b91398 --- /dev/null +++ b/tools/testfiles/vds/4_1.h5 diff --git a/tools/testfiles/vds/4_2.h5 b/tools/testfiles/vds/4_2.h5 Binary files differnew file mode 100644 index 0000000..0ea8f8e --- /dev/null +++ b/tools/testfiles/vds/4_2.h5 diff --git a/tools/testfiles/vds/4_vds.h5 b/tools/testfiles/vds/4_vds.h5 Binary files differnew file mode 100644 index 0000000..de3457a --- /dev/null +++ b/tools/testfiles/vds/4_vds.h5 diff --git a/tools/testfiles/vds/5_a.h5 b/tools/testfiles/vds/5_a.h5 Binary files differnew file mode 100644 index 0000000..189e3b1 --- /dev/null +++ b/tools/testfiles/vds/5_a.h5 diff --git a/tools/testfiles/vds/5_b.h5 b/tools/testfiles/vds/5_b.h5 Binary files differnew file mode 100644 index 0000000..49b85ac --- /dev/null +++ b/tools/testfiles/vds/5_b.h5 diff --git a/tools/testfiles/vds/5_c.h5 b/tools/testfiles/vds/5_c.h5 Binary files differnew file mode 100644 index 0000000..5ea371e --- /dev/null +++ b/tools/testfiles/vds/5_c.h5 diff --git a/tools/testfiles/vds/5_vds.h5 b/tools/testfiles/vds/5_vds.h5 Binary files differnew file mode 100644 index 0000000..bee4974 --- /dev/null +++ b/tools/testfiles/vds/5_vds.h5 diff --git a/tools/testfiles/vds/tvds-1.ddl b/tools/testfiles/vds/tvds-1.ddl new file mode 100644 index 0000000..47fd413 --- /dev/null +++ b/tools/testfiles/vds/tvds-1.ddl @@ -0,0 +1,100 @@ +HDF5 "1_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 5, 18, 8 ) / ( H5S_UNLIMITED, 18, 8 ) } + DATA { + (0,0,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,2,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,3,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,6,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,7,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,8,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,9,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,10,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,11,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,12,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,13,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,14,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,15,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,16,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,17,0): 60, 60, 60, 60, 60, 60, 60, 60, + (1,0,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,2,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,3,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,6,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,7,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,8,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,9,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,10,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,11,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,12,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,13,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,14,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,15,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,16,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,17,0): 61, 61, 61, 61, 61, 61, 61, 61, + (2,0,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,2,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,3,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,6,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,7,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,8,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,9,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,10,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,11,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,12,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,13,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,14,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,15,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,16,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,17,0): 62, 62, 62, 62, 62, 62, 62, 62, + (3,0,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,2,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,3,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,6,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,7,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,8,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,9,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,10,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,11,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,12,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,13,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,14,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,15,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,16,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,17,0): 63, 63, 63, 63, 63, 63, 63, 63, + (4,0,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,2,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,3,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,6,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,7,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,8,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,9,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,10,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,11,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,12,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,13,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,14,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,15,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,16,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,17,0): 64, 64, 64, 64, 64, 64, 64, 64 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-1.ls b/tools/testfiles/vds/tvds-1.ls new file mode 100644 index 0000000..61c9e46 --- /dev/null +++ b/tools/testfiles/vds/tvds-1.ls @@ -0,0 +1,14 @@ +Opened "1_vds.h5" with sec2 driver. +vds_dset Dataset {5/Inf, 18/18, 8/8} + Location: 1:800 + Links: 1 + Maps: {6} Source { + 1_a.h5 /source_dset + 1_b.h5 /source_dset + 1_c.h5 /source_dset + 1_d.h5 /source_dset + 1_e.h5 /source_dset + 1_f.h5 /source_dset + } + Storage: 2880 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds-2.ddl b/tools/testfiles/vds/tvds-2.ddl new file mode 100644 index 0000000..5f2ae16 --- /dev/null +++ b/tools/testfiles/vds/tvds-2.ddl @@ -0,0 +1,58 @@ +HDF5 "2_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 6, 8, 14 ) / ( H5S_UNLIMITED, 8, 14 ) } + DATA { + (0,0,0): 10, 10, 10, 10, 10, 10, 10, 40, 40, 40, 40, 40, 40, 40, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 40, 40, 40, 40, 40, 40, 40, + (0,2,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,3,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 50, 50, 50, 50, 50, 50, 50, + (0,6,0): 30, 30, 30, 30, 30, 30, 30, 50, 50, 50, 50, 50, 50, 50, + (0,7,0): 30, 30, 30, 30, 30, 30, 30, 50, 50, 50, 50, 50, 50, 50, + (1,0,0): 11, 11, 11, 11, 11, 11, 11, 41, 41, 41, 41, 41, 41, 41, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 41, 41, 41, 41, 41, 41, 41, + (1,2,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,3,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 51, 51, 51, 51, 51, 51, 51, + (1,6,0): 31, 31, 31, 31, 31, 31, 31, 51, 51, 51, 51, 51, 51, 51, + (1,7,0): 31, 31, 31, 31, 31, 31, 31, 51, 51, 51, 51, 51, 51, 51, + (2,0,0): 12, 12, 12, 12, 12, 12, 12, 42, 42, 42, 42, 42, 42, 42, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 42, 42, 42, 42, 42, 42, 42, + (2,2,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,3,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 52, 52, 52, 52, 52, 52, 52, + (2,6,0): 32, 32, 32, 32, 32, 32, 32, 52, 52, 52, 52, 52, 52, 52, + (2,7,0): 32, 32, 32, 32, 32, 32, 32, 52, 52, 52, 52, 52, 52, 52, + (3,0,0): 13, 13, 13, 13, 13, 13, 13, 43, 43, 43, 43, 43, 43, 43, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 43, 43, 43, 43, 43, 43, 43, + (3,2,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,3,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 53, 53, 53, 53, 53, 53, 53, + (3,6,0): 33, 33, 33, 33, 33, 33, 33, 53, 53, 53, 53, 53, 53, 53, + (3,7,0): 33, 33, 33, 33, 33, 33, 33, 53, 53, 53, 53, 53, 53, 53, + (4,0,0): 14, 14, 14, 14, 14, 14, 14, 44, 44, 44, 44, 44, 44, 44, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 44, 44, 44, 44, 44, 44, 44, + (4,2,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,3,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 54, 54, 54, 54, 54, 54, 54, + (4,6,0): 34, 34, 34, 34, 34, 34, 34, 54, 54, 54, 54, 54, 54, 54, + (4,7,0): 34, 34, 34, 34, 34, 34, 34, 54, 54, 54, 54, 54, 54, 54, + (5,0,0): 15, 15, 15, 15, 15, 15, 15, 45, 45, 45, 45, 45, 45, 45, + (5,1,0): 15, 15, 15, 15, 15, 15, 15, 45, 45, 45, 45, 45, 45, 45, + (5,2,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,3,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,4,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,5,0): 25, 25, 25, 25, 25, 25, 25, 55, 55, 55, 55, 55, 55, 55, + (5,6,0): 35, 35, 35, 35, 35, 35, 35, 55, 55, 55, 55, 55, 55, 55, + (5,7,0): 35, 35, 35, 35, 35, 35, 35, 55, 55, 55, 55, 55, 55, 55 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-2.ls b/tools/testfiles/vds/tvds-2.ls new file mode 100644 index 0000000..49fe05f --- /dev/null +++ b/tools/testfiles/vds/tvds-2.ls @@ -0,0 +1,13 @@ +Opened "2_vds.h5" with sec2 driver. +vds_dset Dataset {6/Inf, 8/8, 14/14} + Location: 1:800 + Links: 1 + Maps: {5} Source { + 2_a.h5 /source_dset + 2_b.h5 /source_dset + 2_c.h5 /source_dset + 2_d.h5 /source_dset + 2_e.h5 /source_dset + } + Storage: 2688 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds-3_1.ddl b/tools/testfiles/vds/tvds-3_1.ddl new file mode 100644 index 0000000..7d7d8b6 --- /dev/null +++ b/tools/testfiles/vds/tvds-3_1.ddl @@ -0,0 +1,135 @@ +HDF5 "3_1_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 5, 25, 8 ) / ( H5S_UNLIMITED, 25, 8 ) } + DATA { + (0,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,6,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,7,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,9,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,10,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,12,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,13,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,14,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,15,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,17,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,18,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,20,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,21,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,22,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,23,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,2,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,6,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,7,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,9,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,10,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,12,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,13,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,14,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,15,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,17,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,18,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,20,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,21,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,22,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,23,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,2,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,6,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,7,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,9,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,10,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,12,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,13,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,14,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,15,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,17,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,18,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,20,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,21,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,22,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,23,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,2,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,6,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,7,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,9,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,10,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,12,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,13,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,14,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,15,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,17,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,18,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,20,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,21,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,22,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,23,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,2,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,6,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,7,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,9,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,10,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,12,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,13,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,14,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,15,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,17,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,18,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,20,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,21,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,22,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,23,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,24,0): -9, -9, -9, -9, -9, -9, -9, -9 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-3_1.ls b/tools/testfiles/vds/tvds-3_1.ls new file mode 100644 index 0000000..fe24002 --- /dev/null +++ b/tools/testfiles/vds/tvds-3_1.ls @@ -0,0 +1,14 @@ +Opened "3_1_vds.h5" with sec2 driver. +vds_dset Dataset {5/Inf, 25/25, 8/8} + Location: 1:800 + Links: 1 + Maps: {6} Source { + 1_a.h5 /source_dset + 1_b.h5 /source_dset + 1_c.h5 /source_dset + 1_d.h5 /source_dset + 1_e.h5 /source_dset + 1_f.h5 /source_dset + } + Storage: 4000 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds-3_2.ddl b/tools/testfiles/vds/tvds-3_2.ddl new file mode 100644 index 0000000..baec6f0 --- /dev/null +++ b/tools/testfiles/vds/tvds-3_2.ddl @@ -0,0 +1,166 @@ +HDF5 "3_2_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 6, 13, 19 ) / ( H5S_UNLIMITED, 13, 19 ) } + DATA { + (0,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (0,0,15): -9, -9, -9, -9, + (0,1,0): -9, 10, 10, 10, 10, 10, 10, 10, -9, 40, 40, 40, 40, 40, 40, + (0,1,15): 40, -9, -9, -9, + (0,2,0): -9, 10, 10, 10, 10, 10, 10, 10, -9, 40, 40, 40, 40, 40, 40, + (0,2,15): 40, -9, -9, -9, + (0,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 40, 40, 40, 40, 40, 40, + (0,3,15): 40, -9, -9, -9, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, 40, 40, 40, 40, 40, 40, + (0,4,15): 40, -9, -9, -9, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, 40, 40, 40, 40, 40, 40, + (0,5,15): 40, -9, -9, -9, + (0,6,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, -9, -9, -9, -9, -9, -9, + (0,6,15): -9, -9, -9, -9, + (0,7,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, -9, -9, -9, -9, -9, -9, + (0,7,15): -9, -9, -9, -9, + (0,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,8,15): 50, 50, 50, 50, + (0,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,9,15): 50, 50, 50, 50, + (0,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,10,15): 50, 50, 50, 50, + (0,11,0): -9, -9, -9, -9, 30, 30, 30, 30, 30, 30, 30, -9, -9, -9, -9, + (0,11,15): -9, -9, -9, -9, + (0,12,0): -9, -9, -9, -9, 30, 30, 30, 30, 30, 30, 30, -9, -9, -9, -9, + (0,12,15): -9, -9, -9, -9, + (1,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (1,0,15): -9, -9, -9, -9, + (1,1,0): -9, 11, 11, 11, 11, 11, 11, 11, -9, 41, 41, 41, 41, 41, 41, + (1,1,15): 41, -9, -9, -9, + (1,2,0): -9, 11, 11, 11, 11, 11, 11, 11, -9, 41, 41, 41, 41, 41, 41, + (1,2,15): 41, -9, -9, -9, + (1,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 41, 41, 41, 41, 41, 41, + (1,3,15): 41, -9, -9, -9, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, 41, 41, 41, 41, 41, 41, + (1,4,15): 41, -9, -9, -9, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, 41, 41, 41, 41, 41, 41, + (1,5,15): 41, -9, -9, -9, + (1,6,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, -9, -9, -9, -9, -9, -9, + (1,6,15): -9, -9, -9, -9, + (1,7,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, -9, -9, -9, -9, -9, -9, + (1,7,15): -9, -9, -9, -9, + (1,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,8,15): 51, 51, 51, 51, + (1,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,9,15): 51, 51, 51, 51, + (1,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,10,15): 51, 51, 51, 51, + (1,11,0): -9, -9, -9, -9, 31, 31, 31, 31, 31, 31, 31, -9, -9, -9, -9, + (1,11,15): -9, -9, -9, -9, + (1,12,0): -9, -9, -9, -9, 31, 31, 31, 31, 31, 31, 31, -9, -9, -9, -9, + (1,12,15): -9, -9, -9, -9, + (2,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (2,0,15): -9, -9, -9, -9, + (2,1,0): -9, 12, 12, 12, 12, 12, 12, 12, -9, 42, 42, 42, 42, 42, 42, + (2,1,15): 42, -9, -9, -9, + (2,2,0): -9, 12, 12, 12, 12, 12, 12, 12, -9, 42, 42, 42, 42, 42, 42, + (2,2,15): 42, -9, -9, -9, + (2,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 42, 42, 42, 42, 42, 42, + (2,3,15): 42, -9, -9, -9, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, 42, 42, 42, 42, 42, 42, + (2,4,15): 42, -9, -9, -9, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, 42, 42, 42, 42, 42, 42, + (2,5,15): 42, -9, -9, -9, + (2,6,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, -9, -9, -9, -9, -9, -9, + (2,6,15): -9, -9, -9, -9, + (2,7,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, -9, -9, -9, -9, -9, -9, + (2,7,15): -9, -9, -9, -9, + (2,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,8,15): 52, 52, 52, 52, + (2,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,9,15): 52, 52, 52, 52, + (2,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,10,15): 52, 52, 52, 52, + (2,11,0): -9, -9, -9, -9, 32, 32, 32, 32, 32, 32, 32, -9, -9, -9, -9, + (2,11,15): -9, -9, -9, -9, + (2,12,0): -9, -9, -9, -9, 32, 32, 32, 32, 32, 32, 32, -9, -9, -9, -9, + (2,12,15): -9, -9, -9, -9, + (3,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (3,0,15): -9, -9, -9, -9, + (3,1,0): -9, 13, 13, 13, 13, 13, 13, 13, -9, 43, 43, 43, 43, 43, 43, + (3,1,15): 43, -9, -9, -9, + (3,2,0): -9, 13, 13, 13, 13, 13, 13, 13, -9, 43, 43, 43, 43, 43, 43, + (3,2,15): 43, -9, -9, -9, + (3,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 43, 43, 43, 43, 43, 43, + (3,3,15): 43, -9, -9, -9, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, 43, 43, 43, 43, 43, 43, + (3,4,15): 43, -9, -9, -9, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, 43, 43, 43, 43, 43, 43, + (3,5,15): 43, -9, -9, -9, + (3,6,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, -9, -9, -9, -9, -9, -9, + (3,6,15): -9, -9, -9, -9, + (3,7,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, -9, -9, -9, -9, -9, -9, + (3,7,15): -9, -9, -9, -9, + (3,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,8,15): 53, 53, 53, 53, + (3,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,9,15): 53, 53, 53, 53, + (3,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,10,15): 53, 53, 53, 53, + (3,11,0): -9, -9, -9, -9, 33, 33, 33, 33, 33, 33, 33, -9, -9, -9, -9, + (3,11,15): -9, -9, -9, -9, + (3,12,0): -9, -9, -9, -9, 33, 33, 33, 33, 33, 33, 33, -9, -9, -9, -9, + (3,12,15): -9, -9, -9, -9, + (4,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (4,0,15): -9, -9, -9, -9, + (4,1,0): -9, 14, 14, 14, 14, 14, 14, 14, -9, 44, 44, 44, 44, 44, 44, + (4,1,15): 44, -9, -9, -9, + (4,2,0): -9, 14, 14, 14, 14, 14, 14, 14, -9, 44, 44, 44, 44, 44, 44, + (4,2,15): 44, -9, -9, -9, + (4,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 44, 44, 44, 44, 44, 44, + (4,3,15): 44, -9, -9, -9, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, 44, 44, 44, 44, 44, 44, + (4,4,15): 44, -9, -9, -9, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, 44, 44, 44, 44, 44, 44, + (4,5,15): 44, -9, -9, -9, + (4,6,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, -9, -9, -9, -9, -9, -9, + (4,6,15): -9, -9, -9, -9, + (4,7,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, -9, -9, -9, -9, -9, -9, + (4,7,15): -9, -9, -9, -9, + (4,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,8,15): 54, 54, 54, 54, + (4,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,9,15): 54, 54, 54, 54, + (4,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,10,15): 54, 54, 54, 54, + (4,11,0): -9, -9, -9, -9, 34, 34, 34, 34, 34, 34, 34, -9, -9, -9, -9, + (4,11,15): -9, -9, -9, -9, + (4,12,0): -9, -9, -9, -9, 34, 34, 34, 34, 34, 34, 34, -9, -9, -9, -9, + (4,12,15): -9, -9, -9, -9, + (5,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (5,0,15): -9, -9, -9, -9, + (5,1,0): -9, 15, 15, 15, 15, 15, 15, 15, -9, 45, 45, 45, 45, 45, 45, + (5,1,15): 45, -9, -9, -9, + (5,2,0): -9, 15, 15, 15, 15, 15, 15, 15, -9, 45, 45, 45, 45, 45, 45, + (5,2,15): 45, -9, -9, -9, + (5,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 45, 45, 45, 45, 45, 45, + (5,3,15): 45, -9, -9, -9, + (5,4,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, 45, 45, 45, 45, 45, 45, + (5,4,15): 45, -9, -9, -9, + (5,5,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, 45, 45, 45, 45, 45, 45, + (5,5,15): 45, -9, -9, -9, + (5,6,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, -9, -9, -9, -9, -9, -9, + (5,6,15): -9, -9, -9, -9, + (5,7,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, -9, -9, -9, -9, -9, -9, + (5,7,15): -9, -9, -9, -9, + (5,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,8,15): 55, 55, 55, 55, + (5,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,9,15): 55, 55, 55, 55, + (5,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,10,15): 55, 55, 55, 55, + (5,11,0): -9, -9, -9, -9, 35, 35, 35, 35, 35, 35, 35, -9, -9, -9, -9, + (5,11,15): -9, -9, -9, -9, + (5,12,0): -9, -9, -9, -9, 35, 35, 35, 35, 35, 35, 35, -9, -9, -9, -9, + (5,12,15): -9, -9, -9, -9 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-3_2.ls b/tools/testfiles/vds/tvds-3_2.ls new file mode 100644 index 0000000..a4ad84f --- /dev/null +++ b/tools/testfiles/vds/tvds-3_2.ls @@ -0,0 +1,13 @@ +Opened "3_2_vds.h5" with sec2 driver. +vds_dset Dataset {6/Inf, 13/13, 19/19} + Location: 1:800 + Links: 1 + Maps: {5} Source { + 2_a.h5 /source_dset + 2_b.h5 /source_dset + 2_c.h5 /source_dset + 2_d.h5 /source_dset + 2_e.h5 /source_dset + } + Storage: 5928 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds-4.ddl b/tools/testfiles/vds/tvds-4.ddl new file mode 100644 index 0000000..1832724 --- /dev/null +++ b/tools/testfiles/vds/tvds-4.ddl @@ -0,0 +1,46 @@ +HDF5 "4_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 9, 4, 4 ) / ( H5S_UNLIMITED, 4, 4 ) } + DATA { + (0,0,0): 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, + (0,3,0): 10, 10, 10, 10, + (1,0,0): 11, 11, 11, 11, + (1,1,0): 11, 11, 11, 11, + (1,2,0): 11, 11, 11, 11, + (1,3,0): 11, 11, 11, 11, + (2,0,0): 12, 12, 12, 12, + (2,1,0): 12, 12, 12, 12, + (2,2,0): 12, 12, 12, 12, + (2,3,0): 12, 12, 12, 12, + (3,0,0): 20, 20, 20, 20, + (3,1,0): 20, 20, 20, 20, + (3,2,0): 20, 20, 20, 20, + (3,3,0): 20, 20, 20, 20, + (4,0,0): 21, 21, 21, 21, + (4,1,0): 21, 21, 21, 21, + (4,2,0): 21, 21, 21, 21, + (4,3,0): 21, 21, 21, 21, + (5,0,0): 22, 22, 22, 22, + (5,1,0): 22, 22, 22, 22, + (5,2,0): 22, 22, 22, 22, + (5,3,0): 22, 22, 22, 22, + (6,0,0): 30, 30, 30, 30, + (6,1,0): 30, 30, 30, 30, + (6,2,0): 30, 30, 30, 30, + (6,3,0): 30, 30, 30, 30, + (7,0,0): 31, 31, 31, 31, + (7,1,0): 31, 31, 31, 31, + (7,2,0): 31, 31, 31, 31, + (7,3,0): 31, 31, 31, 31, + (8,0,0): 32, 32, 32, 32, + (8,1,0): 32, 32, 32, 32, + (8,2,0): 32, 32, 32, 32, + (8,3,0): 32, 32, 32, 32 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-4.ls b/tools/testfiles/vds/tvds-4.ls new file mode 100644 index 0000000..176529b --- /dev/null +++ b/tools/testfiles/vds/tvds-4.ls @@ -0,0 +1,9 @@ +Opened "4_vds.h5" with sec2 driver. +vds_dset Dataset {9/Inf, 4/4, 4/4} + Location: 1:800 + Links: 1 + Maps: {1} Source { + 4_%b.h5 /source_dset + } + Storage: 576 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds-5.ddl b/tools/testfiles/vds/tvds-5.ddl new file mode 100644 index 0000000..f59017b --- /dev/null +++ b/tools/testfiles/vds/tvds-5.ddl @@ -0,0 +1,46 @@ +HDF5 "5_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 9, 4, 4 ) / ( H5S_UNLIMITED, 4, 4 ) } + DATA { + (0,0,0): 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, + (0,3,0): 10, 10, 10, 10, + (1,0,0): 20, 20, 20, 20, + (1,1,0): 20, 20, 20, 20, + (1,2,0): 20, 20, 20, 20, + (1,3,0): 20, 20, 20, 20, + (2,0,0): 30, 30, 30, 30, + (2,1,0): 30, 30, 30, 30, + (2,2,0): 30, 30, 30, 30, + (2,3,0): 30, 30, 30, 30, + (3,0,0): 11, 11, 11, 11, + (3,1,0): 11, 11, 11, 11, + (3,2,0): 11, 11, 11, 11, + (3,3,0): 11, 11, 11, 11, + (4,0,0): 21, 21, 21, 21, + (4,1,0): 21, 21, 21, 21, + (4,2,0): 21, 21, 21, 21, + (4,3,0): 21, 21, 21, 21, + (5,0,0): 31, 31, 31, 31, + (5,1,0): 31, 31, 31, 31, + (5,2,0): 31, 31, 31, 31, + (5,3,0): 31, 31, 31, 31, + (6,0,0): 12, 12, 12, 12, + (6,1,0): 12, 12, 12, 12, + (6,2,0): 12, 12, 12, 12, + (6,3,0): 12, 12, 12, 12, + (7,0,0): 22, 22, 22, 22, + (7,1,0): 22, 22, 22, 22, + (7,2,0): 22, 22, 22, 22, + (7,3,0): 22, 22, 22, 22, + (8,0,0): 32, 32, 32, 32, + (8,1,0): 32, 32, 32, 32, + (8,2,0): 32, 32, 32, 32, + (8,3,0): 32, 32, 32, 32 + } + } +} +} diff --git a/tools/testfiles/vds/tvds-5.ls b/tools/testfiles/vds/tvds-5.ls new file mode 100644 index 0000000..5f98e84 --- /dev/null +++ b/tools/testfiles/vds/tvds-5.ls @@ -0,0 +1,11 @@ +Opened "5_vds.h5" with sec2 driver. +vds_dset Dataset {9/Inf, 4/4, 4/4} + Location: 1:800 + Links: 1 + Maps: {3} Source { + 5_a.h5 /source_dset + 5_b.h5 /source_dset + 5_c.h5 /source_dset + } + Storage: 576 logical bytes, 0 allocated bytes + Type: 32-bit little-endian integer diff --git a/tools/testfiles/vds/tvds_layout-1.ddl b/tools/testfiles/vds/tvds_layout-1.ddl new file mode 100644 index 0000000..5d8a62c --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-1.ddl @@ -0,0 +1,232 @@ +HDF5 "1_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 5, 18, 8 ) / ( H5S_UNLIMITED, 18, 8 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_a.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 1 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,2,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + MAPPING 2 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,6,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_c.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 3 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,8,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_d.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + MAPPING 4 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,12,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_e.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 5 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,14,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_f.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,2,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,3,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,6,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,7,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,8,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,9,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,10,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,11,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,12,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,13,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,14,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,15,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,16,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,17,0): 60, 60, 60, 60, 60, 60, 60, 60, + (1,0,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,2,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,3,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,6,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,7,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,8,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,9,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,10,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,11,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,12,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,13,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,14,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,15,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,16,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,17,0): 61, 61, 61, 61, 61, 61, 61, 61, + (2,0,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,2,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,3,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,6,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,7,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,8,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,9,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,10,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,11,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,12,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,13,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,14,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,15,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,16,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,17,0): 62, 62, 62, 62, 62, 62, 62, 62, + (3,0,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,2,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,3,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,6,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,7,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,8,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,9,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,10,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,11,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,12,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,13,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,14,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,15,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,16,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,17,0): 63, 63, 63, 63, 63, 63, 63, 63, + (4,0,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,2,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,3,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,6,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,7,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,8,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,9,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,10,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,11,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,12,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,13,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,14,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,15,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,16,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,17,0): 64, 64, 64, 64, 64, 64, 64, 64 + } + } +} +} diff --git a/tools/testfiles/vds/tvds_layout-2.ddl b/tools/testfiles/vds/tvds_layout-2.ddl new file mode 100644 index 0000000..af6b718 --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-2.ddl @@ -0,0 +1,170 @@ +HDF5 "2_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 6, 8, 14 ) / ( H5S_UNLIMITED, 8, 14 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + SOURCE { + FILE "2_a.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + } + MAPPING 1 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,2,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,7) + } + } + SOURCE { + FILE "2_b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,7) + } + } + } + MAPPING 2 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,6,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + SOURCE { + FILE "2_c.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + } + MAPPING 3 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,0,7) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,5,7) + } + } + SOURCE { + FILE "2_d.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,5,7) + } + } + } + MAPPING 4 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,5,7) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,3,7) + } + } + SOURCE { + FILE "2_e.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,3,7) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): 10, 10, 10, 10, 10, 10, 10, 40, 40, 40, 40, 40, 40, 40, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 40, 40, 40, 40, 40, 40, 40, + (0,2,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,3,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 40, 40, 40, 40, 40, 40, 40, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 50, 50, 50, 50, 50, 50, 50, + (0,6,0): 30, 30, 30, 30, 30, 30, 30, 50, 50, 50, 50, 50, 50, 50, + (0,7,0): 30, 30, 30, 30, 30, 30, 30, 50, 50, 50, 50, 50, 50, 50, + (1,0,0): 11, 11, 11, 11, 11, 11, 11, 41, 41, 41, 41, 41, 41, 41, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 41, 41, 41, 41, 41, 41, 41, + (1,2,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,3,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 41, 41, 41, 41, 41, 41, 41, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 51, 51, 51, 51, 51, 51, 51, + (1,6,0): 31, 31, 31, 31, 31, 31, 31, 51, 51, 51, 51, 51, 51, 51, + (1,7,0): 31, 31, 31, 31, 31, 31, 31, 51, 51, 51, 51, 51, 51, 51, + (2,0,0): 12, 12, 12, 12, 12, 12, 12, 42, 42, 42, 42, 42, 42, 42, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 42, 42, 42, 42, 42, 42, 42, + (2,2,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,3,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 42, 42, 42, 42, 42, 42, 42, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 52, 52, 52, 52, 52, 52, 52, + (2,6,0): 32, 32, 32, 32, 32, 32, 32, 52, 52, 52, 52, 52, 52, 52, + (2,7,0): 32, 32, 32, 32, 32, 32, 32, 52, 52, 52, 52, 52, 52, 52, + (3,0,0): 13, 13, 13, 13, 13, 13, 13, 43, 43, 43, 43, 43, 43, 43, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 43, 43, 43, 43, 43, 43, 43, + (3,2,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,3,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 43, 43, 43, 43, 43, 43, 43, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 53, 53, 53, 53, 53, 53, 53, + (3,6,0): 33, 33, 33, 33, 33, 33, 33, 53, 53, 53, 53, 53, 53, 53, + (3,7,0): 33, 33, 33, 33, 33, 33, 33, 53, 53, 53, 53, 53, 53, 53, + (4,0,0): 14, 14, 14, 14, 14, 14, 14, 44, 44, 44, 44, 44, 44, 44, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 44, 44, 44, 44, 44, 44, 44, + (4,2,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,3,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 44, 44, 44, 44, 44, 44, 44, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 54, 54, 54, 54, 54, 54, 54, + (4,6,0): 34, 34, 34, 34, 34, 34, 34, 54, 54, 54, 54, 54, 54, 54, + (4,7,0): 34, 34, 34, 34, 34, 34, 34, 54, 54, 54, 54, 54, 54, 54, + (5,0,0): 15, 15, 15, 15, 15, 15, 15, 45, 45, 45, 45, 45, 45, 45, + (5,1,0): 15, 15, 15, 15, 15, 15, 15, 45, 45, 45, 45, 45, 45, 45, + (5,2,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,3,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,4,0): 25, 25, 25, 25, 25, 25, 25, 45, 45, 45, 45, 45, 45, 45, + (5,5,0): 25, 25, 25, 25, 25, 25, 25, 55, 55, 55, 55, 55, 55, 55, + (5,6,0): 35, 35, 35, 35, 35, 35, 35, 55, 55, 55, 55, 55, 55, 55, + (5,7,0): 35, 35, 35, 35, 35, 35, 35, 55, 55, 55, 55, 55, 55, 55 + } + } +} +} diff --git a/tools/testfiles/vds/tvds_layout-3_1.ddl b/tools/testfiles/vds/tvds_layout-3_1.ddl new file mode 100644 index 0000000..968327d --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-3_1.ddl @@ -0,0 +1,267 @@ +HDF5 "3_1_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 5, 25, 8 ) / ( H5S_UNLIMITED, 25, 8 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,1,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_a.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 1 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,4,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + MAPPING 2 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,9,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_c.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 3 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,12,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_d.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + MAPPING 4 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,17,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + SOURCE { + FILE "1_e.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,8) + } + } + } + MAPPING 5 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,20,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + SOURCE { + FILE "1_f.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,8) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,1,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, 10, 10, 10, 10, + (0,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,6,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,7,0): 20, 20, 20, 20, 20, 20, 20, 20, + (0,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,9,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,10,0): 30, 30, 30, 30, 30, 30, 30, 30, + (0,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,12,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,13,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,14,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,15,0): 40, 40, 40, 40, 40, 40, 40, 40, + (0,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,17,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,18,0): 50, 50, 50, 50, 50, 50, 50, 50, + (0,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (0,20,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,21,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,22,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,23,0): 60, 60, 60, 60, 60, 60, 60, 60, + (0,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,1,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,2,0): 11, 11, 11, 11, 11, 11, 11, 11, + (1,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,6,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,7,0): 21, 21, 21, 21, 21, 21, 21, 21, + (1,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,9,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,10,0): 31, 31, 31, 31, 31, 31, 31, 31, + (1,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,12,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,13,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,14,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,15,0): 41, 41, 41, 41, 41, 41, 41, 41, + (1,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,17,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,18,0): 51, 51, 51, 51, 51, 51, 51, 51, + (1,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (1,20,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,21,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,22,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,23,0): 61, 61, 61, 61, 61, 61, 61, 61, + (1,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,1,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,2,0): 12, 12, 12, 12, 12, 12, 12, 12, + (2,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,6,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,7,0): 22, 22, 22, 22, 22, 22, 22, 22, + (2,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,9,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,10,0): 32, 32, 32, 32, 32, 32, 32, 32, + (2,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,12,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,13,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,14,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,15,0): 42, 42, 42, 42, 42, 42, 42, 42, + (2,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,17,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,18,0): 52, 52, 52, 52, 52, 52, 52, 52, + (2,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (2,20,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,21,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,22,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,23,0): 62, 62, 62, 62, 62, 62, 62, 62, + (2,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,1,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,2,0): 13, 13, 13, 13, 13, 13, 13, 13, + (3,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,6,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,7,0): 23, 23, 23, 23, 23, 23, 23, 23, + (3,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,9,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,10,0): 33, 33, 33, 33, 33, 33, 33, 33, + (3,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,12,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,13,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,14,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,15,0): 43, 43, 43, 43, 43, 43, 43, 43, + (3,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,17,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,18,0): 53, 53, 53, 53, 53, 53, 53, 53, + (3,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (3,20,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,21,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,22,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,23,0): 63, 63, 63, 63, 63, 63, 63, 63, + (3,24,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,0,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,1,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,2,0): 14, 14, 14, 14, 14, 14, 14, 14, + (4,3,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,6,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,7,0): 24, 24, 24, 24, 24, 24, 24, 24, + (4,8,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,9,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,10,0): 34, 34, 34, 34, 34, 34, 34, 34, + (4,11,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,12,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,13,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,14,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,15,0): 44, 44, 44, 44, 44, 44, 44, 44, + (4,16,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,17,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,18,0): 54, 54, 54, 54, 54, 54, 54, 54, + (4,19,0): -9, -9, -9, -9, -9, -9, -9, -9, + (4,20,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,21,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,22,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,23,0): 64, 64, 64, 64, 64, 64, 64, 64, + (4,24,0): -9, -9, -9, -9, -9, -9, -9, -9 + } + } +} +} diff --git a/tools/testfiles/vds/tvds_layout-3_2.ddl b/tools/testfiles/vds/tvds_layout-3_2.ddl new file mode 100644 index 0000000..7e14ec2 --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-3_2.ddl @@ -0,0 +1,278 @@ +HDF5 "3_2_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 6, 13, 19 ) / ( H5S_UNLIMITED, 13, 19 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,1,1) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + SOURCE { + FILE "2_a.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + } + MAPPING 1 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,4,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,7) + } + } + SOURCE { + FILE "2_b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,7) + } + } + } + MAPPING 2 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,11,4) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + SOURCE { + FILE "2_c.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,2,7) + } + } + } + MAPPING 3 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,1,9) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,5,7) + } + } + SOURCE { + FILE "2_d.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,5,7) + } + } + } + MAPPING 4 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,8,12) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,3,7) + } + } + SOURCE { + FILE "2_e.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,3,7) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (0,0,15): -9, -9, -9, -9, + (0,1,0): -9, 10, 10, 10, 10, 10, 10, 10, -9, 40, 40, 40, 40, 40, 40, + (0,1,15): 40, -9, -9, -9, + (0,2,0): -9, 10, 10, 10, 10, 10, 10, 10, -9, 40, 40, 40, 40, 40, 40, + (0,2,15): 40, -9, -9, -9, + (0,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 40, 40, 40, 40, 40, 40, + (0,3,15): 40, -9, -9, -9, + (0,4,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, 40, 40, 40, 40, 40, 40, + (0,4,15): 40, -9, -9, -9, + (0,5,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, 40, 40, 40, 40, 40, 40, + (0,5,15): 40, -9, -9, -9, + (0,6,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, -9, -9, -9, -9, -9, -9, + (0,6,15): -9, -9, -9, -9, + (0,7,0): 20, 20, 20, 20, 20, 20, 20, -9, -9, -9, -9, -9, -9, -9, -9, + (0,7,15): -9, -9, -9, -9, + (0,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,8,15): 50, 50, 50, 50, + (0,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,9,15): 50, 50, 50, 50, + (0,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 50, 50, 50, + (0,10,15): 50, 50, 50, 50, + (0,11,0): -9, -9, -9, -9, 30, 30, 30, 30, 30, 30, 30, -9, -9, -9, -9, + (0,11,15): -9, -9, -9, -9, + (0,12,0): -9, -9, -9, -9, 30, 30, 30, 30, 30, 30, 30, -9, -9, -9, -9, + (0,12,15): -9, -9, -9, -9, + (1,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (1,0,15): -9, -9, -9, -9, + (1,1,0): -9, 11, 11, 11, 11, 11, 11, 11, -9, 41, 41, 41, 41, 41, 41, + (1,1,15): 41, -9, -9, -9, + (1,2,0): -9, 11, 11, 11, 11, 11, 11, 11, -9, 41, 41, 41, 41, 41, 41, + (1,2,15): 41, -9, -9, -9, + (1,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 41, 41, 41, 41, 41, 41, + (1,3,15): 41, -9, -9, -9, + (1,4,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, 41, 41, 41, 41, 41, 41, + (1,4,15): 41, -9, -9, -9, + (1,5,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, 41, 41, 41, 41, 41, 41, + (1,5,15): 41, -9, -9, -9, + (1,6,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, -9, -9, -9, -9, -9, -9, + (1,6,15): -9, -9, -9, -9, + (1,7,0): 21, 21, 21, 21, 21, 21, 21, -9, -9, -9, -9, -9, -9, -9, -9, + (1,7,15): -9, -9, -9, -9, + (1,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,8,15): 51, 51, 51, 51, + (1,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,9,15): 51, 51, 51, 51, + (1,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 51, 51, 51, + (1,10,15): 51, 51, 51, 51, + (1,11,0): -9, -9, -9, -9, 31, 31, 31, 31, 31, 31, 31, -9, -9, -9, -9, + (1,11,15): -9, -9, -9, -9, + (1,12,0): -9, -9, -9, -9, 31, 31, 31, 31, 31, 31, 31, -9, -9, -9, -9, + (1,12,15): -9, -9, -9, -9, + (2,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (2,0,15): -9, -9, -9, -9, + (2,1,0): -9, 12, 12, 12, 12, 12, 12, 12, -9, 42, 42, 42, 42, 42, 42, + (2,1,15): 42, -9, -9, -9, + (2,2,0): -9, 12, 12, 12, 12, 12, 12, 12, -9, 42, 42, 42, 42, 42, 42, + (2,2,15): 42, -9, -9, -9, + (2,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 42, 42, 42, 42, 42, 42, + (2,3,15): 42, -9, -9, -9, + (2,4,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, 42, 42, 42, 42, 42, 42, + (2,4,15): 42, -9, -9, -9, + (2,5,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, 42, 42, 42, 42, 42, 42, + (2,5,15): 42, -9, -9, -9, + (2,6,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, -9, -9, -9, -9, -9, -9, + (2,6,15): -9, -9, -9, -9, + (2,7,0): 22, 22, 22, 22, 22, 22, 22, -9, -9, -9, -9, -9, -9, -9, -9, + (2,7,15): -9, -9, -9, -9, + (2,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,8,15): 52, 52, 52, 52, + (2,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,9,15): 52, 52, 52, 52, + (2,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 52, 52, 52, + (2,10,15): 52, 52, 52, 52, + (2,11,0): -9, -9, -9, -9, 32, 32, 32, 32, 32, 32, 32, -9, -9, -9, -9, + (2,11,15): -9, -9, -9, -9, + (2,12,0): -9, -9, -9, -9, 32, 32, 32, 32, 32, 32, 32, -9, -9, -9, -9, + (2,12,15): -9, -9, -9, -9, + (3,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (3,0,15): -9, -9, -9, -9, + (3,1,0): -9, 13, 13, 13, 13, 13, 13, 13, -9, 43, 43, 43, 43, 43, 43, + (3,1,15): 43, -9, -9, -9, + (3,2,0): -9, 13, 13, 13, 13, 13, 13, 13, -9, 43, 43, 43, 43, 43, 43, + (3,2,15): 43, -9, -9, -9, + (3,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 43, 43, 43, 43, 43, 43, + (3,3,15): 43, -9, -9, -9, + (3,4,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, 43, 43, 43, 43, 43, 43, + (3,4,15): 43, -9, -9, -9, + (3,5,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, 43, 43, 43, 43, 43, 43, + (3,5,15): 43, -9, -9, -9, + (3,6,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, -9, -9, -9, -9, -9, -9, + (3,6,15): -9, -9, -9, -9, + (3,7,0): 23, 23, 23, 23, 23, 23, 23, -9, -9, -9, -9, -9, -9, -9, -9, + (3,7,15): -9, -9, -9, -9, + (3,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,8,15): 53, 53, 53, 53, + (3,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,9,15): 53, 53, 53, 53, + (3,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 53, 53, 53, + (3,10,15): 53, 53, 53, 53, + (3,11,0): -9, -9, -9, -9, 33, 33, 33, 33, 33, 33, 33, -9, -9, -9, -9, + (3,11,15): -9, -9, -9, -9, + (3,12,0): -9, -9, -9, -9, 33, 33, 33, 33, 33, 33, 33, -9, -9, -9, -9, + (3,12,15): -9, -9, -9, -9, + (4,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (4,0,15): -9, -9, -9, -9, + (4,1,0): -9, 14, 14, 14, 14, 14, 14, 14, -9, 44, 44, 44, 44, 44, 44, + (4,1,15): 44, -9, -9, -9, + (4,2,0): -9, 14, 14, 14, 14, 14, 14, 14, -9, 44, 44, 44, 44, 44, 44, + (4,2,15): 44, -9, -9, -9, + (4,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 44, 44, 44, 44, 44, 44, + (4,3,15): 44, -9, -9, -9, + (4,4,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, 44, 44, 44, 44, 44, 44, + (4,4,15): 44, -9, -9, -9, + (4,5,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, 44, 44, 44, 44, 44, 44, + (4,5,15): 44, -9, -9, -9, + (4,6,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, -9, -9, -9, -9, -9, -9, + (4,6,15): -9, -9, -9, -9, + (4,7,0): 24, 24, 24, 24, 24, 24, 24, -9, -9, -9, -9, -9, -9, -9, -9, + (4,7,15): -9, -9, -9, -9, + (4,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,8,15): 54, 54, 54, 54, + (4,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,9,15): 54, 54, 54, 54, + (4,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 54, 54, 54, + (4,10,15): 54, 54, 54, 54, + (4,11,0): -9, -9, -9, -9, 34, 34, 34, 34, 34, 34, 34, -9, -9, -9, -9, + (4,11,15): -9, -9, -9, -9, + (4,12,0): -9, -9, -9, -9, 34, 34, 34, 34, 34, 34, 34, -9, -9, -9, -9, + (4,12,15): -9, -9, -9, -9, + (5,0,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, + (5,0,15): -9, -9, -9, -9, + (5,1,0): -9, 15, 15, 15, 15, 15, 15, 15, -9, 45, 45, 45, 45, 45, 45, + (5,1,15): 45, -9, -9, -9, + (5,2,0): -9, 15, 15, 15, 15, 15, 15, 15, -9, 45, 45, 45, 45, 45, 45, + (5,2,15): 45, -9, -9, -9, + (5,3,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, 45, 45, 45, 45, 45, 45, + (5,3,15): 45, -9, -9, -9, + (5,4,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, 45, 45, 45, 45, 45, 45, + (5,4,15): 45, -9, -9, -9, + (5,5,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, 45, 45, 45, 45, 45, 45, + (5,5,15): 45, -9, -9, -9, + (5,6,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, -9, -9, -9, -9, -9, -9, + (5,6,15): -9, -9, -9, -9, + (5,7,0): 25, 25, 25, 25, 25, 25, 25, -9, -9, -9, -9, -9, -9, -9, -9, + (5,7,15): -9, -9, -9, -9, + (5,8,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,8,15): 55, 55, 55, 55, + (5,9,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,9,15): 55, 55, 55, 55, + (5,10,0): -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, -9, 55, 55, 55, + (5,10,15): 55, 55, 55, 55, + (5,11,0): -9, -9, -9, -9, 35, 35, 35, 35, 35, 35, 35, -9, -9, -9, -9, + (5,11,15): -9, -9, -9, -9, + (5,12,0): -9, -9, -9, -9, 35, 35, 35, 35, 35, 35, 35, -9, -9, -9, -9, + (5,12,15): -9, -9, -9, -9 + } + } +} +} diff --git a/tools/testfiles/vds/tvds_layout-4.ddl b/tools/testfiles/vds/tvds_layout-4.ddl new file mode 100644 index 0000000..018644e --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-4.ddl @@ -0,0 +1,78 @@ +HDF5 "4_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 9, 4, 4 ) / ( H5S_UNLIMITED, 4, 4 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (3,1,1) + COUNT (H5S_UNLIMITED,1,1) + BLOCK (3,4,4) + } + } + SOURCE { + FILE "4_%b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (3,4,4) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, + (0,3,0): 10, 10, 10, 10, + (1,0,0): 11, 11, 11, 11, + (1,1,0): 11, 11, 11, 11, + (1,2,0): 11, 11, 11, 11, + (1,3,0): 11, 11, 11, 11, + (2,0,0): 12, 12, 12, 12, + (2,1,0): 12, 12, 12, 12, + (2,2,0): 12, 12, 12, 12, + (2,3,0): 12, 12, 12, 12, + (3,0,0): 20, 20, 20, 20, + (3,1,0): 20, 20, 20, 20, + (3,2,0): 20, 20, 20, 20, + (3,3,0): 20, 20, 20, 20, + (4,0,0): 21, 21, 21, 21, + (4,1,0): 21, 21, 21, 21, + (4,2,0): 21, 21, 21, 21, + (4,3,0): 21, 21, 21, 21, + (5,0,0): 22, 22, 22, 22, + (5,1,0): 22, 22, 22, 22, + (5,2,0): 22, 22, 22, 22, + (5,3,0): 22, 22, 22, 22, + (6,0,0): 30, 30, 30, 30, + (6,1,0): 30, 30, 30, 30, + (6,2,0): 30, 30, 30, 30, + (6,3,0): 30, 30, 30, 30, + (7,0,0): 31, 31, 31, 31, + (7,1,0): 31, 31, 31, 31, + (7,2,0): 31, 31, 31, 31, + (7,3,0): 31, 31, 31, 31, + (8,0,0): 32, 32, 32, 32, + (8,1,0): 32, 32, 32, 32, + (8,2,0): 32, 32, 32, 32, + (8,3,0): 32, 32, 32, 32 + } + } +} +} diff --git a/tools/testfiles/vds/tvds_layout-5.ddl b/tools/testfiles/vds/tvds_layout-5.ddl new file mode 100644 index 0000000..b43629a --- /dev/null +++ b/tools/testfiles/vds/tvds_layout-5.ddl @@ -0,0 +1,118 @@ +HDF5 "5_vds.h5" { +GROUP "/" { + DATASET "vds_dset" { + DATATYPE H5T_STD_I32LE + DATASPACE SIMPLE { ( 9, 4, 4 ) / ( H5S_UNLIMITED, 4, 4 ) } + STORAGE_LAYOUT { + MAPPING 0 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (3,1,1) + COUNT (H5S_UNLIMITED,1,1) + BLOCK (1,4,4) + } + } + SOURCE { + FILE "5_a.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,4) + } + } + } + MAPPING 1 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (1,0,0) + STRIDE (3,1,1) + COUNT (H5S_UNLIMITED,1,1) + BLOCK (1,4,4) + } + } + SOURCE { + FILE "5_b.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,4) + } + } + } + MAPPING 2 { + VIRTUAL { + SELECTION REGULAR_HYPERSLAB { + START (2,0,0) + STRIDE (3,1,1) + COUNT (H5S_UNLIMITED,1,1) + BLOCK (1,4,4) + } + } + SOURCE { + FILE "5_c.h5" + DATASET "/source_dset" + SELECTION REGULAR_HYPERSLAB { + START (0,0,0) + STRIDE (1,1,1) + COUNT (1,1,1) + BLOCK (H5S_UNLIMITED,4,4) + } + } + } + } + FILTERS { + NONE + } + FILLVALUE { + FILL_TIME H5D_FILL_TIME_IFSET + VALUE -9 + } + ALLOCATION_TIME { + H5D_ALLOC_TIME_INCR + } + DATA { + (0,0,0): 10, 10, 10, 10, + (0,1,0): 10, 10, 10, 10, + (0,2,0): 10, 10, 10, 10, + (0,3,0): 10, 10, 10, 10, + (1,0,0): 20, 20, 20, 20, + (1,1,0): 20, 20, 20, 20, + (1,2,0): 20, 20, 20, 20, + (1,3,0): 20, 20, 20, 20, + (2,0,0): 30, 30, 30, 30, + (2,1,0): 30, 30, 30, 30, + (2,2,0): 30, 30, 30, 30, + (2,3,0): 30, 30, 30, 30, + (3,0,0): 11, 11, 11, 11, + (3,1,0): 11, 11, 11, 11, + (3,2,0): 11, 11, 11, 11, + (3,3,0): 11, 11, 11, 11, + (4,0,0): 21, 21, 21, 21, + (4,1,0): 21, 21, 21, 21, + (4,2,0): 21, 21, 21, 21, + (4,3,0): 21, 21, 21, 21, + (5,0,0): 31, 31, 31, 31, + (5,1,0): 31, 31, 31, 31, + (5,2,0): 31, 31, 31, 31, + (5,3,0): 31, 31, 31, 31, + (6,0,0): 12, 12, 12, 12, + (6,1,0): 12, 12, 12, 12, + (6,2,0): 12, 12, 12, 12, + (6,3,0): 12, 12, 12, 12, + (7,0,0): 22, 22, 22, 22, + (7,1,0): 22, 22, 22, 22, + (7,2,0): 22, 22, 22, 22, + (7,3,0): 22, 22, 22, 22, + (8,0,0): 32, 32, 32, 32, + (8,1,0): 32, 32, 32, 32, + (8,2,0): 32, 32, 32, 32, + (8,3,0): 32, 32, 32, 32 + } + } +} +} |