diff options
author | Sergey Poznyakoff <gray@gnu.org> | 2018-05-30 14:34:24 +0300 |
---|---|---|
committer | Sergey Poznyakoff <gray@gnu.org> | 2018-05-30 14:34:24 +0300 |
commit | 156f33c8aa5b5c113987c353bbd32c70f02f6a9d (patch) | |
tree | cca8dde609d34b202c1b7d0a5148cfa38b129ba9 /src | |
parent | 60605e947884726fe14c8896fa5c766f6e99742a (diff) | |
download | gdbm-156f33c8aa5b5c113987c353bbd32c70f02f6a9d.tar.gz gdbm-156f33c8aa5b5c113987c353bbd32c70f02f6a9d.tar.bz2 |
Avoid unnecessary memory reallocations during caching
* src/findkey.c (_gdbm_read_entry): Reallocate cache_entry->ca_data.dptr only
if necessary.
* src/gdbmdefs.h (data_cache_elem): New member: dsize
* src/gdbmdelete.c: Don't free cache_entry->ca_data.dptr
* src/gdbmopen.c (_gdbm_init_cache): Initialize ca_data.dsize
Diffstat (limited to 'src')
-rw-r--r-- | src/findkey.c | 39 | ||||
-rw-r--r-- | src/gdbmdefs.h | 11 | ||||
-rw-r--r-- | src/gdbmdelete.c | 7 | ||||
-rw-r--r-- | src/gdbmopen.c | 1 |
4 files changed, 38 insertions, 20 deletions
diff --git a/src/findkey.c b/src/findkey.c index 9c8fd71..5560b28 100644 --- a/src/findkey.c +++ b/src/findkey.c | |||
@@ -46,6 +46,7 @@ _gdbm_read_entry (GDBM_FILE dbf, int elem_loc) | |||
46 | int rc; | 46 | int rc; |
47 | int key_size; | 47 | int key_size; |
48 | int data_size; | 48 | int data_size; |
49 | size_t dsize; | ||
49 | off_t file_pos; | 50 | off_t file_pos; |
50 | data_cache_elem *data_ca; | 51 | data_cache_elem *data_ca; |
51 | 52 | ||
@@ -62,24 +63,44 @@ _gdbm_read_entry (GDBM_FILE dbf, int elem_loc) | |||
62 | /* Set sizes and pointers. */ | 63 | /* Set sizes and pointers. */ |
63 | key_size = dbf->bucket->h_table[elem_loc].key_size; | 64 | key_size = dbf->bucket->h_table[elem_loc].key_size; |
64 | data_size = dbf->bucket->h_table[elem_loc].data_size; | 65 | data_size = dbf->bucket->h_table[elem_loc].data_size; |
66 | dsize = key_size + data_size; | ||
65 | data_ca = &dbf->cache_entry->ca_data; | 67 | data_ca = &dbf->cache_entry->ca_data; |
66 | 68 | ||
67 | /* Set up the cache. */ | 69 | /* Set up the cache. */ |
68 | if (data_ca->dptr != NULL) free (data_ca->dptr); | ||
69 | data_ca->key_size = key_size; | 70 | data_ca->key_size = key_size; |
70 | data_ca->data_size = data_size; | 71 | data_ca->data_size = data_size; |
71 | data_ca->elem_loc = elem_loc; | 72 | data_ca->elem_loc = elem_loc; |
72 | data_ca->hash_val = dbf->bucket->h_table[elem_loc].hash_value; | 73 | data_ca->hash_val = dbf->bucket->h_table[elem_loc].hash_value; |
73 | 74 | ||
74 | if (key_size + data_size == 0) | 75 | if (dsize <= data_ca->dsize) |
75 | data_ca->dptr = (char *) malloc (1); | 76 | { |
77 | if (data_ca->dsize == 0) | ||
78 | { | ||
79 | data_ca->dptr = malloc (1); | ||
80 | if (data_ca->dptr) | ||
81 | data_ca->dsize = 1; | ||
82 | else | ||
83 | { | ||
84 | GDBM_SET_ERRNO2 (dbf, GDBM_MALLOC_ERROR, FALSE, GDBM_DEBUG_LOOKUP); | ||
85 | _gdbm_fatal (dbf, _("malloc error")); | ||
86 | return NULL; | ||
87 | } | ||
88 | } | ||
89 | } | ||
76 | else | 90 | else |
77 | data_ca->dptr = (char *) malloc (key_size + data_size); | ||
78 | if (data_ca->dptr == NULL) | ||
79 | { | 91 | { |
80 | GDBM_SET_ERRNO2 (dbf, GDBM_MALLOC_ERROR, FALSE, GDBM_DEBUG_LOOKUP); | 92 | char *p = realloc (data_ca->dptr, dsize); |
81 | _gdbm_fatal (dbf, _("malloc error")); | 93 | if (p) |
82 | return NULL; | 94 | { |
95 | data_ca->dptr = p; | ||
96 | data_ca->dsize = dsize; | ||
97 | } | ||
98 | else | ||
99 | { | ||
100 | GDBM_SET_ERRNO2 (dbf, GDBM_MALLOC_ERROR, FALSE, GDBM_DEBUG_LOOKUP); | ||
101 | _gdbm_fatal (dbf, _("malloc error")); | ||
102 | return NULL; | ||
103 | } | ||
83 | } | 104 | } |
84 | 105 | ||
85 | /* Read into the cache. */ | 106 | /* Read into the cache. */ |
diff --git a/src/gdbmdefs.h b/src/gdbmdefs.h index 4ae646f..af6f09c 100644 --- a/src/gdbmdefs.h +++ b/src/gdbmdefs.h | |||
@@ -149,11 +149,12 @@ typedef struct | |||
149 | 149 | ||
150 | typedef struct | 150 | typedef struct |
151 | { | 151 | { |
152 | int hash_val; | 152 | int hash_val; |
153 | int data_size; | 153 | int data_size; |
154 | int key_size; | 154 | int key_size; |
155 | char *dptr; | 155 | char *dptr; |
156 | int elem_loc; | 156 | size_t dsize; |
157 | int elem_loc; | ||
157 | } data_cache_elem; | 158 | } data_cache_elem; |
158 | 159 | ||
159 | typedef struct | 160 | typedef struct |
diff --git a/src/gdbmdelete.c b/src/gdbmdelete.c index 5660d3a..ff13a1a 100644 --- a/src/gdbmdelete.c +++ b/src/gdbmdelete.c | |||
@@ -88,12 +88,7 @@ gdbm_delete (GDBM_FILE dbf, datum key) | |||
88 | /* Set the flags. */ | 88 | /* Set the flags. */ |
89 | dbf->bucket_changed = TRUE; | 89 | dbf->bucket_changed = TRUE; |
90 | 90 | ||
91 | /* Clear out the data cache for the current bucket. */ | 91 | /* Invalidate data cache for the current bucket. */ |
92 | if (dbf->cache_entry->ca_data.dptr != NULL) | ||
93 | { | ||
94 | free (dbf->cache_entry->ca_data.dptr); | ||
95 | dbf->cache_entry->ca_data.dptr = NULL; | ||
96 | } | ||
97 | dbf->cache_entry->ca_data.hash_val = -1; | 92 | dbf->cache_entry->ca_data.hash_val = -1; |
98 | dbf->cache_entry->ca_data.key_size = 0; | 93 | dbf->cache_entry->ca_data.key_size = 0; |
99 | dbf->cache_entry->ca_data.elem_loc = -1; | 94 | dbf->cache_entry->ca_data.elem_loc = -1; |
diff --git a/src/gdbmopen.c b/src/gdbmopen.c index 31d8fea..03cc4f4 100644 --- a/src/gdbmopen.c +++ b/src/gdbmopen.c | |||
@@ -663,6 +663,7 @@ _gdbm_init_cache (GDBM_FILE dbf, size_t size) | |||
663 | return -1; | 663 | return -1; |
664 | } | 664 | } |
665 | dbf->bucket_cache[index].ca_data.dptr = NULL; | 665 | dbf->bucket_cache[index].ca_data.dptr = NULL; |
666 | dbf->bucket_cache[index].ca_data.dsize = 0; | ||
666 | _gdbm_cache_entry_invalidate (dbf, index); | 667 | _gdbm_cache_entry_invalidate (dbf, index); |
667 | } | 668 | } |
668 | dbf->bucket = dbf->bucket_cache[0].ca_bucket; | 669 | dbf->bucket = dbf->bucket_cache[0].ca_bucket; |