diff options
author | Andrew Tridgell <tridge@samba.org> | 1999-12-21 04:54:30 +0000 |
---|---|---|
committer | Andrew Tridgell <tridge@samba.org> | 1999-12-21 04:54:30 +0000 |
commit | 69d24d869bf97978b31a51fe8e8d08cac4874d67 (patch) | |
tree | 30ec2bcdc8491098dd9b3f0c4e3432092b73f23a /source3/tdb | |
parent | 0c4b1ea0140ed5418fcbde3077d424ffa08a2dcf (diff) | |
download | samba-69d24d869bf97978b31a51fe8e8d08cac4874d67.tar.gz samba-69d24d869bf97978b31a51fe8e8d08cac4874d67.tar.bz2 samba-69d24d869bf97978b31a51fe8e8d08cac4874d67.zip |
first cut at using the tdb code for the connections structure, the
SWAT status page and smbstatus. It made the code _much_ simpler, I
wish we'd done a database module a long time ago!
(This used to be commit 4951755413c11d4c5b9af4699a6e622056d52433)
Diffstat (limited to 'source3/tdb')
-rw-r--r-- | source3/tdb/README | 9 | ||||
-rw-r--r-- | source3/tdb/tdb.c | 39 | ||||
-rw-r--r-- | source3/tdb/tdb.h | 1 |
3 files changed, 44 insertions, 5 deletions
diff --git a/source3/tdb/README b/source3/tdb/README index fc99a68acc..3c0059c5cb 100644 --- a/source3/tdb/README +++ b/source3/tdb/README @@ -11,7 +11,7 @@ Compilation ----------- add HAVE_MMAP=1 to use mmap instead of read/write -add TDB_DEBUG for verbose debug info +add TDB_DEBUG=1 for verbose debug info add NOLOCK=1 to disable locking code Testing @@ -21,6 +21,12 @@ Compile tdbtest.c and link with gdbm for testing. tdbtest will perform identical operations via tdb and gdbm then make sure the result is the same +Also included is tdbtool, which allows simple database manipulation +on the commandline. + +tdbtest and tdbtool are not built as part of Samba, but are included +for completeness. + Interface --------- @@ -31,3 +37,4 @@ The interface is very similar to gdbm except for the following: - no tdbm_reorganise() function - no tdbm_sync() function. No operations are cached in the library anyway - added a tdb_traverse() function for traversing the whole database + diff --git a/source3/tdb/tdb.c b/source3/tdb/tdb.c index dacecf9572..01d2e740f7 100644 --- a/source3/tdb/tdb.c +++ b/source3/tdb/tdb.c @@ -102,10 +102,39 @@ static tdb_off tdb_hash_top(TDB_CONTEXT *tdb, unsigned hash) return ret; } + +/* check for an out of bounds access - if it is out of bounds then + see if the database has been expanded by someone else and expand + if necessary */ +static int tdb_oob(TDB_CONTEXT *tdb, tdb_off offset) +{ + struct stat st; + if (offset < tdb->map_size) return 0; + + fstat(tdb->fd, &st); + if (st.st_size <= tdb->map_size) return -1; + +#if HAVE_MMAP + if (tdb->map_ptr) { + munmap(tdb->map_ptr, tdb->map_size); + tdb->map_ptr = NULL; + } +#endif + + tdb->map_size = st.st_size; +#if HAVE_MMAP + tdb->map_ptr = (void *)mmap(NULL, tdb->map_size, + tdb->read_only?PROT_READ:PROT_READ|PROT_WRITE, + MAP_SHARED | MAP_FILE, tdb->fd, 0); +#endif + return 0; +} + + /* write a lump of data at a specified offset */ static int tdb_write(TDB_CONTEXT *tdb, tdb_off offset, char *buf, tdb_len len) { - if (offset + len > tdb->map_size) { + if (tdb_oob(tdb, offset + len) != 0) { /* oops - trying to write beyond the end of the database! */ #if TDB_DEBUG printf("write error of length %u at offset %u (max %u)\n", @@ -128,7 +157,7 @@ static int tdb_write(TDB_CONTEXT *tdb, tdb_off offset, char *buf, tdb_len len) /* read a lump of data at a specified offset */ static int tdb_read(TDB_CONTEXT *tdb, tdb_off offset, char *buf, tdb_len len) { - if (offset + len > tdb->map_size) { + if (tdb_oob(tdb, offset + len) != 0) { /* oops - trying to read beyond the end of the database! */ #if TDB_DEBUG printf("read error of length %u at offset %u (max %u)\n", @@ -514,6 +543,7 @@ int tdb_exists(TDB_CONTEXT *tdb, TDB_DATA key) /* traverse the entire database - calling fn(tdb, key, data) on each element. return -1 on error or the record count traversed + if fn is NULL then it is not called a non-zero return value from fn() indicates that the traversal should stop */ int tdb_traverse(TDB_CONTEXT *tdb, int (*fn)(TDB_CONTEXT *tdb, TDB_DATA key, TDB_DATA dbuf)) @@ -552,7 +582,7 @@ int tdb_traverse(TDB_CONTEXT *tdb, int (*fn)(TDB_CONTEXT *tdb, TDB_DATA key, TDB dbuf.dsize = rec.data_len; count++; - if (fn(tdb, key, dbuf) != 0) { + if (fn && fn(tdb, key, dbuf) != 0) { /* they want us to stop traversing */ free(data); return count; @@ -915,9 +945,10 @@ TDB_CONTEXT *tdb_open(char *name, int hash_size, int flags, mode_t mode) /* map the database and fill in the return structure */ tdb.name = (char *)strdup(name); tdb.map_size = st.st_size; + tdb.read_only = ((flags & O_ACCMODE) == O_RDONLY); #if HAVE_MMAP tdb.map_ptr = (void *)mmap(NULL, st.st_size, - (flags & O_ACCMODE) == O_RDONLY? PROT_READ : PROT_READ|PROT_WRITE, + tdb.read_only? PROT_READ : PROT_READ|PROT_WRITE, MAP_SHARED | MAP_FILE, tdb.fd, 0); #endif tdb.header = header; diff --git a/source3/tdb/tdb.h b/source3/tdb/tdb.h index 316338606b..111b804f71 100644 --- a/source3/tdb/tdb.h +++ b/source3/tdb/tdb.h @@ -39,6 +39,7 @@ typedef struct { void *map_ptr; /* where it is currently mapped */ int fd; /* open file descriptor for the database */ tdb_len map_size; /* how much space has been mapped */ + int read_only; /* opened read-only */ int write_locked; /* set if we have the db locked */ struct tdb_header header; /* a cached copy of the header */ } TDB_CONTEXT; |