tdb: Use tdb_parse_record in tdb_update_hash
authorVolker Lendecke <vl@samba.org>
Mon, 19 Dec 2011 12:39:04 +0000 (13:39 +0100)
committerVolker Lendecke <vl@samba.org>
Sun, 25 Dec 2011 12:31:58 +0000 (13:31 +0100)
This avoids a tdb_fetch, thus a malloc/memcpy/free in the tdb_store path

lib/tdb/common/tdb.c

index ac2a482ebac2e7c820888c8ad383ff6b268f53c7..c0f934ab83aeed86de1bf5203294541ac45a4f7f 100644 (file)
@@ -124,6 +124,19 @@ tdb_off_t tdb_find_lock_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t has
 
 static TDB_DATA _tdb_fetch(struct tdb_context *tdb, TDB_DATA key);
 
+static int tdb_update_hash_cmp(TDB_DATA key, TDB_DATA data, void *private_data)
+{
+       TDB_DATA *dbuf = (TDB_DATA *)private_data;
+
+       if (dbuf->dsize != data.dsize) {
+               return -1;
+       }
+       if (memcmp(dbuf->dptr, data.dptr, data.dsize) != 0) {
+               return -1;
+       }
+       return 0;
+}
+
 /* update an entry in place - this only works if the new data size
    is <= the old data size and the key exists.
    on failure return -1.
@@ -141,18 +154,9 @@ static int tdb_update_hash(struct tdb_context *tdb, TDB_DATA key, uint32_t hash,
         * surprisingly common (eg. with a ldb re-index). */
        if (rec.key_len == key.dsize && 
            rec.data_len == dbuf.dsize &&
-           rec.full_hash == hash) {
-               TDB_DATA data = _tdb_fetch(tdb, key);
-               if (data.dsize == dbuf.dsize &&
-                   memcmp(data.dptr, dbuf.dptr, data.dsize) == 0) {
-                       if (data.dptr) {
-                               free(data.dptr);
-                       }
-                       return 0;
-               }
-               if (data.dptr) {
-                       free(data.dptr);
-               }
+           rec.full_hash == hash &&
+           tdb_parse_record(tdb, key, tdb_update_hash_cmp, &dbuf) == 0) {
+               return 0;
        }
 
        /* must be long enough key, data and tailer */