summaryrefslogtreecommitdiffstats
path: root/src/H5AC.c
diff options
context:
space:
mode:
authorRobb Matzke <matzke@llnl.gov>1997-08-12 22:44:46 (GMT)
committerRobb Matzke <matzke@llnl.gov>1997-08-12 22:44:46 (GMT)
commitfb947c34b142578774d5bb657c0b3e2a9b4781c7 (patch)
treec695cac8789bbe5fc92a5324e3027856bf3858bc /src/H5AC.c
parent326981f421b993815657daecc8b37bd732513d82 (diff)
downloadhdf5-fb947c34b142578774d5bb657c0b3e2a9b4781c7.zip
hdf5-fb947c34b142578774d5bb657c0b3e2a9b4781c7.tar.gz
hdf5-fb947c34b142578774d5bb657c0b3e2a9b4781c7.tar.bz2
[svn-r25] ./src/H5AC.c
We sort the cache before a complete flush because it might be more efficient to write things back to disk in order of increasing address. If you want the old way then undef the SORT_BY_ADDR constant at the top of H5AC.c I haven't determined which systems and I/O libraries this helps or hurts. (This is currently off because of a bug I need to track down that causes qsort() to run for a really long time). ./src/H5B.c Fixed a couple more bugs. ./src/H5Eprivate.h ./src/H5Eproto.h Added major H5E_DIRECTORY and minor H5E_EXISTS, H5E_COMPLEN. ./src/H5G.c Added directory-aware functions. The heap and B-tree are created when a directory is created instead of when the first symbol is added. This simplifies symbol table entry caching for the directory since the cached value never changes now. ./src/H5Gnode.c ./src/H5Gprivate.h Fine tuned the B-tree K values for symbol tables assuming an average number of symbols is about 100 per directory. The tuning minimizes storage space. Fixed a return value in H5G_node_cmp(). ./src/H5H.c ./src/H5Hprivate.h Moved some macros the the header file. ./src/H5O.c ./src/H5Ocont.c ./src/H5Onull.c ./src/H5Ostab.c Changed the arguments for the decode method for messages. The second argument is the raw message size. Added a class variable for native message size. Added H5O_reset() to free memory used internally by a message. ./src/H5Oname.c NEW ./src/H5Oprivate.h ./src/Makefile The object name message. ./src/hdf5port.h Added defn for HDstrdup()
Diffstat (limited to 'src/H5AC.c')
-rw-r--r--src/H5AC.c79
1 files changed, 72 insertions, 7 deletions
diff --git a/src/H5AC.c b/src/H5AC.c
index 41e2f88..ce8415e 100644
--- a/src/H5AC.c
+++ b/src/H5AC.c
@@ -27,9 +27,16 @@
#include "H5ACprivate.h"
#include "H5MMprivate.h"
+/*
+ * Sorting the cache by address before flushing is sometimes faster
+ * than flushing in cache order.
+ */
+/* #define SORT_BY_ADDR */
+
#define PABLO_MASK H5AC_mask
static int interface_initialize_g = FALSE; /*initialized?*/
+static H5AC_cache_t *current_cache_g = NULL; /*for sorting */
/*-------------------------------------------------------------------------
@@ -200,6 +207,41 @@ H5AC_find_f (hdf5_file_t *f, const H5AC_class_t *type, haddr_t addr,
/*-------------------------------------------------------------------------
+ * Function: H5AC_compare
+ *
+ * Purpose: Compare two hash entries by address. Unused entries are
+ * all equal to one another and greater than all used entries.
+ *
+ * Return: Success: -1, 0, 1
+ *
+ * Failure: never fails
+ *
+ * Programmer: Robb Matzke
+ * robb@maya.nuance.com
+ * Aug 12 1997
+ *
+ * Modifications:
+ *
+ *-------------------------------------------------------------------------
+ */
+static int
+H5AC_compare (const void *_a, const void *_b)
+{
+ intn a = *((const intn *)_a);
+ intn b = *((const intn *)_b);
+
+ assert (current_cache_g);
+
+ if (NULL==current_cache_g[a].type) return 1;
+ if (NULL==current_cache_g[b].type) return -1;
+
+ if (current_cache_g[a].addr < current_cache_g[b].addr) return -1;
+ if (current_cache_g[a].addr > current_cache_g[b].addr) return 1;
+ return 0;
+}
+
+
+/*-------------------------------------------------------------------------
* Function: H5AC_flush
*
* Purpose: Flushes (and destroys if DESTROY is non-zero) the specified
@@ -226,6 +268,8 @@ H5AC_flush (hdf5_file_t *f, const H5AC_class_t *type, haddr_t addr,
uintn i = H5AC_HASH(addr);
herr_t status;
herr_t (*flush)(hdf5_file_t*,hbool_t,haddr_t,void*)=NULL;
+ H5AC_cache_t *slot;
+ intn *map=NULL;
FUNC_ENTER (H5AC_flush, NULL, FAIL);
@@ -233,22 +277,43 @@ H5AC_flush (hdf5_file_t *f, const H5AC_class_t *type, haddr_t addr,
assert (f->cache);
if (!type || 0==addr) {
+
+#ifdef SORT_BY_ADDR
+ /*
+ * Sort the cache entries by address since flushing them in
+ * ascending order by address may be much more efficient.
+ */
+ map = H5MM_xmalloc (H5AC_NSLOTS * sizeof(intn));
+ for (i=0; i<H5AC_NSLOTS; i++) map[i] = i;
+ assert (NULL==current_cache_g);
+ current_cache_g = f->cache;
+ qsort (map, H5AC_NSLOTS, sizeof(intn), H5AC_compare);
+ current_cache_g = NULL;
+#endif
+
/*
* Look at all cache entries.
*/
for (i=0; i<H5AC_NSLOTS; i++) {
- if (NULL==f->cache[i].type) continue;
- if ((!type || type==f->cache[i].type) &&
- (0==addr || addr==f->cache[i].addr)) {
- flush = f->cache[i].type->flush;
- status = (flush)(f, destroy, f->cache[i].addr,
- f->cache[i].thing);
+#ifdef SORT_BY_ADDR
+ slot = f->cache + map[i];
+ if (NULL==slot->type) break; /*the rest are empty*/
+#else
+ slot = f->cache + i;
+ if (NULL==slot->type) continue;
+#endif
+ if ((!type || type==slot->type) &&
+ (0==addr || addr==slot->addr)) {
+ flush = slot->type->flush;
+ status = (flush)(f, destroy, slot->addr, slot->thing);
if (status<0) {
+ map = H5MM_xfree (map);
HRETURN_ERROR (H5E_CACHE, H5E_CANTFLUSH, FAIL);
}
- if (destroy) f->cache[i].type = NULL;
+ if (destroy) slot->type = NULL;
}
}
+ map = H5MM_xfree (map);
} else if (f->cache[i].type==type && f->cache[i].addr==addr) {
/*