Lots of performance improvements & a couple new internal API interfaces.
Description:
Performance Improvements:
- Cached file offset & length sizes in shared file struct, to avoid
constantly looking them up in the FCPL.
- Generic property improvements:
- Added "revision" number to generic property classes to speed
up comparisons.
- Changed method of storing properties from using a hash-table
to the TBBT routines in the library.
- Share the propery names between classes and the lists derived
from them.
- Removed redundant 'def_value' buffer from each property.
- Switching code to use a "copy on write" strategy for
properties in each list, where the properties in each list
are shared with the properties in the class, until a
property's value is changed in a list.
- Fixed error in layout code which was allocating too many buffers.
- Redefined public macros of the form (H5open()/H5check, <variable>)
internally to only be (<variable>), avoiding innumerable useless
calls to H5open() and H5check_version().
- Reuse already zeroed buffers in H5F_contig_fill instead of
constantly re-zeroing them.
- Don't write fill values if writing entire dataset.
- Use gettimeofday() system call instead of time() system when
checking the modification time of a dataset.
- Added reference counted string API and use it for tracking the
names of objects opening in a file (for the ID->name code).
- Removed redundant H5P_get() calls in B-tree routines.
- Redefine H5T datatype macros internally to the library, to avoid
calling H5check redundantly.
- Keep dataspace information for dataset locally instead of reading
from disk each time. Added new module to track open objects
in a file, to allow this (which will be useful eventually for
some FPH5 metadata caching issues).
- Remove H5AC_find macro which was inlining metadata cache lookups,
and call function instead.
- Remove redundant memset() calls from H5G_namei() routine.
- Remove redundant checking of object type when locating objects
in metadata cache and rely on the address only.
- Create default dataset object to use when default dataset creation
property list is used to create datasets, bypassing querying
for all the property list values.
- Use default I/O vector size when performing raw data with the
default dataset transfer property list, instead of querying for
I/O vector size.
- Remove H5P_DEFAULT internally to the library, replacing it with
more specific default property list based on the type of
property list needed.
- Remove redundant memset() calls in object header message (H5O*)
routines.
- Remove redunant memset() calls in data I/O routines.
- Split free-list allocation routines into malloc() and calloc()-
like routines, instead of one combined routine.
- Remove lots of indirection in H5O*() routines.
- Simplify metadata cache entry comparison routine (used when
flushing entire cache out).
- Only enable metadata cache statistics when H5AC_DEBUG is turned
on, instead of always tracking them.
- Simplify address comparison macro (H5F_addr_eq).
- Remove redundant metadata cache entry protections during dataset
creation by protecting the object header once and making all
the modifications necessary for the dataset creation before
unprotecting it.
- Reduce # of "number of element in extent" computations performed
by computing and storing the value during dataspace creation.
- Simplify checking for group location's file information, when file
has not been involving in file-mounting operations.
- Use binary encoding for modification time, instead of ASCII.
- Hoist H5HL_peek calls (to get information in a local heap)
out of loops in many group routine.
- Use static variable for iterators of selections, instead of
dynamically allocation them each time.
- Lookup & insert new entries in one step, avoiding traversing
group's B-tree twice.
- Fixed memory leak in H5Gget_objname_idx() routine (tangential to
performance improvements, but fixed along the way).
- Use free-list for reference counted strings.
- Don't bother copying object names into cached group entries,
since they are re-created when an object is opened.
The benchmark I used to measure these results created several thousand
small (2K) datasets in a file and wrote out the data for them. This is
Elena's "regular.c" benchmark.
These changes resulted in approximately ~4.3x speedup of the
development branch when compared to the previous code in the
development branch and ~1.4x speedup compared to the release
branch.
Additionally, these changes reduce the total memory used (code and
data) by the development branch by ~800KB, bringing the development
branch back into the same ballpark as the release branch.
I'll send out a more detailed description of the benchmark results
as a followup note.
New internal API routines:
Added "reference counted strings" API for tracking strings that get
used by multiple owners without duplicating the strings.
Added "ternary search tree" API for text->object mappings.
Platforms tested:
Tested h5committest {arabica (fortran), eirene (fortran, C++)
modi4 (parallel, fortran)}
Other platforms/configurations tested?
FreeBSD 4.7 (sleipnir) serial & parallel
Solaris 2.6 (baldric) serial
206 lines
8.0 KiB
Makefile
206 lines
8.0 KiB
Makefile
## HDF5 Library Test Makefile(.in)
|
|
##
|
|
## Copyright (C) 1997, 2002
|
|
## National Center for Supercomputing Applications.
|
|
## All rights reserved.
|
|
##
|
|
##
|
|
top_srcdir=@top_srcdir@
|
|
top_builddir=..
|
|
srcdir=@srcdir@
|
|
@COMMENCE@
|
|
|
|
## Add include directory to the C preprocessor flags and the h5test and hdf5
|
|
## libraries to the library list.
|
|
CPPFLAGS=-I. -I$(srcdir) -I../src -I$(top_srcdir)/src @CPPFLAGS@
|
|
|
|
## These are our main targets. They should be listed in the order to be
|
|
## executed, generally most specific tests to least specific tests.
|
|
TEST_PROGS=testhdf5 lheap ohdr stab gheap hyperslab istore bittests dtypes \
|
|
dsets cmpd_dset extend external links unlink big mtime fillval mount \
|
|
flush1 flush2 enum gass_write gass_read gass_append set_extent \
|
|
srb_write srb_append srb_read ttsafe stream_test getname file_handle \
|
|
ntypes
|
|
|
|
TIMINGS=testmeta
|
|
|
|
## The libh5test.a library provides common support code for the tests. We link
|
|
## this library statically because some systems can only link executables to
|
|
## a single shared library and libhdf5 is much bigger than libh5test.
|
|
LIBHDF5=../src/libhdf5.la
|
|
LIB=libh5test.la
|
|
LIB_SRC=h5test.c
|
|
LIB_OBJ=$(LIB_SRC:.c=.lo)
|
|
PUB_LIB=
|
|
|
|
## Temporary files. These files are the ones created by setting the
|
|
## HDF5_NOCLEANUP environment variable and running `make test' without
|
|
## specifying a file prefix or low-level driver. Changing the file
|
|
## prefix or low-level driver with environment variables will influence
|
|
## the temporary file name in ways that the makefile is not aware of.
|
|
MOSTLYCLEAN=cmpd_dset.h5 compact_dataset.h5 dataset.h5 extend.h5 istore.h5 \
|
|
tfile1.h5 tfile2.h5 tfile3.h5 th5s1.h5 lheap.h5 ohdr.h5 stab1.h5 \
|
|
stab2.h5 extern_1.h5 extern_2.h5 extern_3.h5 extern_1a.raw \
|
|
extern_1b.raw extern_2a.raw extern_2b.raw extern_3a.raw \
|
|
extern_3b.raw extern_4a.raw extern_4b.raw gheap0.h5 gheap1.h5 \
|
|
gheap2.h5 gheap3.h5 gheap4.h5 links.h5 links[1-3].h5 big.data \
|
|
big[0-9][0-9][0-9][0-9][0-9].h5 dtypes[1-3].h5 tattr.h5 \
|
|
tselect.h5 mtime.h5 unlink.h5 fillval_[0-9].h5 fillval.raw \
|
|
mount_[0-9].h5 testmeta.h5 ttime.h5 trefer[1-3].h5 tvltypes.h5 \
|
|
tvlstr.h5 flush.h5 enum1.h5 titerate.h5 ttsafe.h5 tarray1.h5 \
|
|
tgenprop.h5 tmisc.h5 tmisc2a.h5 tmisc2b.h5 tmisc3.h5 tmisc4a.h5 \
|
|
tmisc4b.h5 tmisc5.h5 tmisc6.h5 tmisc7.h5 tmisc8.h5 \
|
|
set_extent_read.h5 set_extent_create.h5 getname.h5 getname1.h5 \
|
|
getname2.h5 getname3.h5 sec2_file.h5 family_file000[0-3][0-9].h5 \
|
|
multi_file-[rs].h5 core_file new_move_[ab].h5
|
|
|
|
CLEAN=$(TIMINGS)
|
|
|
|
## Source and object files for programs... The TEST_SRC list contains all the
|
|
## source files and is used for things like dependencies, archiving, etc. The
|
|
## other source lists are for the individual tests, the files of which may
|
|
## overlap with other tests.
|
|
|
|
TEST_SRC=big.c bittests.c cmpd_dset.c dsets.c dtypes.c extend.c \
|
|
external.c fillval.c flush1.c flush2.c gheap.c h5test.c hyperslab.c \
|
|
istore.c lheap.c links.c mount.c mtime.c ohdr.c stab.c tarray.c \
|
|
tattr.c tconfig.c testhdf5.c testmeta.c tfile.c tgenprop.c th5s.c \
|
|
titerate.c tmeta.c trefer.c trefstr.c tselect.c ttime.c ttbbt.c \
|
|
ttst.c tvltypes.c tvlstr.c tmisc.c unlink.c enum.c ttsafe.c \
|
|
ttsafe_dcreate.c ttsafe_error.c ttsafe_cancel.c ttsafe_acreate.c \
|
|
gass_write.c gass_read.c gass_append.c srb_read.c srb_write.c \
|
|
srb_append.c stream_test.c set_extent.c getname.c file_handle.c \
|
|
ntypes.c
|
|
|
|
TEST_OBJ=$(TEST_SRC:.c=.lo)
|
|
|
|
## Private header files (not to be installed)...
|
|
PRIVATE_HDR=testhdf5.h ttsafe.h
|
|
|
|
## Additional targets
|
|
.PHONY: timings _timings
|
|
timings _timings: $(TIMINGS)
|
|
@for timing in $(TIMINGS) dummy; do \
|
|
if test $$timing != dummy; then \
|
|
echo "Running $$timing $(TEST_FLAGS)"; \
|
|
$(RUNTEST) ./$$timing $(TEST_FLAGS) || exit 1; \
|
|
fi; \
|
|
done;
|
|
|
|
## How to build the tests... They all depend on the test and hdf5 libraries.
|
|
$(TEST_PROGS): $(LIB) $(LIBHDF5)
|
|
|
|
TESTHDF5_OBJ=testhdf5.lo tarray.lo tattr.lo tconfig.lo tfile.lo tgenprop.lo \
|
|
th5s.lo titerate.lo tmeta.lo ttime.lo trefer.lo trefstr.lo tselect.lo \
|
|
ttbbt.lo ttst.lo tvltypes.lo tvlstr.lo tmisc.lo
|
|
|
|
TTS_OBJ=ttsafe.lo ttsafe_dcreate.lo ttsafe_error.lo ttsafe_cancel.lo \
|
|
ttsafe_acreate.lo
|
|
|
|
testhdf5: $(TESTHDF5_OBJ)
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ $(TESTHDF5_OBJ) $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
lheap: lheap.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ lheap.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
ohdr: ohdr.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ ohdr.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
stab: stab.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ stab.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
gheap: gheap.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ gheap.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
dsets: dsets.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ dsets.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
bittests: bittests.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ bittests.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
dtypes: dtypes.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ dtypes.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
hyperslab: hyperslab.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ hyperslab.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
istore: istore.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ istore.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
cmpd_dset: cmpd_dset.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ cmpd_dset.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
extend: extend.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ extend.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
external: external.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ external.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
big: big.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ big.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
links: links.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ links.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
mtime: mtime.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ mtime.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
unlink: unlink.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ unlink.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
fillval: fillval.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ fillval.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
mount: mount.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ mount.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
flush1: flush1.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ flush1.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
flush2: flush2.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ flush2.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
enum: enum.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ enum.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
ttsafe: $(TTS_OBJ)
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ $(TTS_OBJ) $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
gass_write: gass_write.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ gass_write.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
gass_read: gass_read.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ gass_read.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
gass_append: gass_append.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ gass_append.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
set_extent: set_extent.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ set_extent.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
srb_read: srb_read.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ srb_read.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
srb_write: srb_write.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ srb_write.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
srb_append: srb_append.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ srb_append.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
stream_test: stream_test.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ stream_test.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
testmeta: testmeta.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ testmeta.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
getname: getname.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ getname.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
file_handle: file_handle.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ file_handle.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
ntypes: ntypes.lo
|
|
@$(LT_LINK_EXE) $(CFLAGS) -o $@ ntypes.lo $(LIB) $(LIBHDF5) $(LDFLAGS) $(LIBS)
|
|
|
|
@CONCLUDE@
|