diff options
author | Andrew Tridgell <tridge@samba.org> | 2000-01-05 06:36:36 +0000 |
---|---|---|
committer | Andrew Tridgell <tridge@samba.org> | 2000-01-05 06:36:36 +0000 |
commit | aa7f81552540f5dca2c146f5edd805611d5b390f (patch) | |
tree | 18217f6d3596a3dea080e85e44bc2398ea59c5ad | |
parent | 51ed6e8cec47642641e6b26682fd6f25624b19ae (diff) | |
download | samba-aa7f81552540f5dca2c146f5edd805611d5b390f.tar.gz samba-aa7f81552540f5dca2c146f5edd805611d5b390f.tar.xz samba-aa7f81552540f5dca2c146f5edd805611d5b390f.zip |
implemented talloc() as described on samba-technical. This fixes the
lp_string() bug properly.
we still need to add lp_talloc_free() calls in all the main event
loops, I've only put it in smbd and nmbd thus far.
-rw-r--r-- | source/Makefile.in | 2 | ||||
-rw-r--r-- | source/include/includes.h | 1 | ||||
-rw-r--r-- | source/include/proto.h | 7 | ||||
-rw-r--r-- | source/include/talloc.h | 32 | ||||
-rw-r--r-- | source/lib/talloc.c | 96 | ||||
-rw-r--r-- | source/nmbd/nmbd.c | 3 | ||||
-rw-r--r-- | source/param/loadparm.c | 66 | ||||
-rw-r--r-- | source/script/mkproto.awk | 2 | ||||
-rw-r--r-- | source/smbd/process.c | 3 |
9 files changed, 171 insertions, 41 deletions
diff --git a/source/Makefile.in b/source/Makefile.in index acf7c02c21a..6201e63c886 100644 --- a/source/Makefile.in +++ b/source/Makefile.in @@ -99,7 +99,7 @@ LIB_OBJ = lib/charcnv.o lib/charset.o lib/debug.o lib/fault.o \ lib/util_array.o lib/util_str.o lib/util_sid.o \ lib/util_unistr.o lib/util_file.o \ lib/util.o lib/util_sock.o lib/util_sec.o smbd/ssl.o lib/fnmatch.o \ - tdb/tdb.o + tdb/tdb.o lib/talloc.o UBIQX_OBJ = ubiqx/ubi_BinTree.o ubiqx/ubi_Cache.o ubiqx/ubi_SplayTree.o \ ubiqx/ubi_dLinkList.o ubiqx/ubi_sLinkList.o ubiqx/debugparse.o diff --git a/source/include/includes.h b/source/include/includes.h index 3e9010bf548..7986c12c91a 100644 --- a/source/include/includes.h +++ b/source/include/includes.h @@ -611,6 +611,7 @@ extern int errno; #include "ubi_dLinkList.h" #include "dlinklist.h" #include "../tdb/tdb.h" +#include "talloc.h" #include "interfaces.h" #ifdef HAVE_FNMATCH diff --git a/source/include/proto.h b/source/include/proto.h index bb1d5477dfc..0222e890d21 100644 --- a/source/include/proto.h +++ b/source/include/proto.h @@ -223,6 +223,12 @@ smb_ucs2_t *wsys_getwd(smb_ucs2_t *s); int wsys_chown(const smb_ucs2_t *wfname, uid_t uid, gid_t gid); int wsys_chroot(const smb_ucs2_t *wfname); +/*The following definitions come from lib/talloc.c */ + +TALLOC_CTX *talloc_init(void); +void *talloc(TALLOC_CTX *t, size_t size); +void talloc_destroy(TALLOC_CTX *t); + /*The following definitions come from lib/time.c */ void GetTimeOfDay(struct timeval *tval); @@ -1111,6 +1117,7 @@ void expire_workgroups_and_servers(time_t t); /*The following definitions come from param/loadparm.c */ +void lp_talloc_free(void); char *lp_logfile(void); char *lp_smbrun(void); char *lp_configfile(void); diff --git a/source/include/talloc.h b/source/include/talloc.h new file mode 100644 index 00000000000..df68166a5e1 --- /dev/null +++ b/source/include/talloc.h @@ -0,0 +1,32 @@ +/* + Unix SMB/Netbios implementation. + Version 3.0 + Samba temporary memory allocation functions + Copyright (C) Andrew Tridgell 2000 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +struct talloc_chunk { + struct talloc_chunk *next; + void *ptr; + size_t alloc_size; + size_t total_size; +}; + +typedef struct { + struct talloc_chunk *list; +} TALLOC_CTX; + diff --git a/source/lib/talloc.c b/source/lib/talloc.c new file mode 100644 index 00000000000..518237cde8f --- /dev/null +++ b/source/lib/talloc.c @@ -0,0 +1,96 @@ +/* + Unix SMB/Netbios implementation. + Version 3.0 + Samba temporary memory allocation functions + Copyright (C) Andrew Tridgell 2000 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. +*/ + +/* this is a very simple temporary memory allocator. To use it do the following: + + 1) when you first want to allocate a pool of meomry use + talloc_init() and save the resulting context pointer somewhere + + 2) to allocate memory use talloc() + + 3) when _all_ of the memory allocated using this context is no longer needed + use talloc_destroy() + + talloc does not zero the memory. It guarantees memory of a + TALLOC_ALIGN alignment +*/ + +#include "includes.h" + +#define TALLOC_ALIGN 32 +#define TALLOC_CHUNK_SIZE (0x2000) + +/* initialissa talloc context. */ +TALLOC_CTX *talloc_init(void) +{ + TALLOC_CTX *t; + + t = (TALLOC_CTX *)malloc(sizeof(*t)); + if (!t) return NULL; + + t->list = NULL; + + return t; +} + +/* allocate a bit of memory from the specified pool */ +void *talloc(TALLOC_CTX *t, size_t size) +{ + void *p; + + size = (size + TALLOC_ALIGN) & (~TALLOC_ALIGN-1); + + if (!t->list || (t->list->total_size - t->list->alloc_size) < size) { + struct talloc_chunk *c; + size_t asize = (size + TALLOC_CHUNK_SIZE) & ~(TALLOC_CHUNK_SIZE-1); + + c = (struct talloc_chunk *)malloc(sizeof(*c)); + if (!c) return NULL; + c->next = t->list; + c->ptr = (void *)malloc(asize); + if (!c->ptr) { + free(c); + return NULL; + } + c->alloc_size = 0; + c->total_size = asize; + t->list = c; + } + + p = t->list->ptr + t->list->alloc_size; + t->list->alloc_size += size; + return p; +} + +/* destroy a whole pool */ +void talloc_destroy(TALLOC_CTX *t) +{ + struct talloc_chunk *c; + + while (t->list) { + c = t->list->next; + free(t->list->ptr); + free(t->list); + t->list = c; + } + + free(t); +} diff --git a/source/nmbd/nmbd.c b/source/nmbd/nmbd.c index 751aede3942..5bb3d7fc00d 100644 --- a/source/nmbd/nmbd.c +++ b/source/nmbd/nmbd.c @@ -475,6 +475,9 @@ static void process(void) /* check for new network interfaces */ reload_interfaces(t); + + /* free up temp memory */ + lp_talloc_free(); } } /* process */ diff --git a/source/param/loadparm.c b/source/param/loadparm.c index 6d825541302..b76af546098 100644 --- a/source/param/loadparm.c +++ b/source/param/loadparm.c @@ -1092,55 +1092,43 @@ static void init_locals(void) #define NUMBER_OF_STATIC_STRING_BUFS 20 +static TALLOC_CTX *lp_talloc; + /******************************************************************* a -convenience routine to grab string parameters into a rotating buffer, +free up temporary memory - called from the main loop +********************************************************************/ +void lp_talloc_free(void) +{ + if (!lp_talloc) return; + talloc_destroy(lp_talloc); + lp_talloc = NULL; +} + +/******************************************************************* +convenience routine to grab string parameters into temporary memory and run standard_sub_basic on them. The buffers can be written to by callers without affecting the source string. ********************************************************************/ static char *lp_string(const char *s) { - static char *bufs[NUMBER_OF_STATIC_STRING_BUFS]; - static size_t buflen[NUMBER_OF_STATIC_STRING_BUFS]; - static int next = -1; - char *ret; - int i; - size_t len = s?strlen(s):0; - - if (next == -1) { - /* initialisation */ - for (i=0;i<NUMBER_OF_STATIC_STRING_BUFS;i++) { - bufs[i] = NULL; - buflen[i] = 0; - } - next = 0; - } + size_t len = s?strlen(s):0; + char *ret; - len = MAX(len+100,sizeof(pstring)); /* the +100 is for some - substitution room */ - - if (buflen[next] != len) { - buflen[next] = len; - if (bufs[next]) - free(bufs[next]); - bufs[next] = (char *)malloc(len); - if (!bufs[next]) { - DEBUG(0,("out of memory in lp_string()")); - exit(1); - } - } + if (!lp_talloc) lp_talloc = talloc_init(); + + ret = (char *)talloc(lp_talloc, len + 100); /* leave room for substitution */ - ret = &bufs[next][0]; - next = (next+1)%NUMBER_OF_STATIC_STRING_BUFS; + if (!ret) return NULL; - if (!s) - *ret = 0; - else - StrnCpy(ret,s,len-1); + if (!s) + *ret = 0; + else + StrnCpy(ret,s,len); - trim_string(ret, "\"", "\""); + trim_string(ret, "\"", "\""); - standard_sub_basic(ret); - return(ret); + standard_sub_basic(ret); + return(ret); } @@ -2601,7 +2589,7 @@ BOOL lp_load(char *pszFname,BOOL global_only, BOOL save_defaults, BOOL add_ipc) { pstring n2; BOOL bRetval; - + add_to_file_list(pszFname); bRetval = False; diff --git a/source/script/mkproto.awk b/source/script/mkproto.awk index c24dfac98cc..8ef414266ab 100644 --- a/source/script/mkproto.awk +++ b/source/script/mkproto.awk @@ -98,7 +98,7 @@ END { gotstart = 1; } - if( $0 ~ /^TDB_CONTEXT|^TDB_DATA|^smb_ucs2_t/ ) { + if( $0 ~ /^TDB_CONTEXT|^TDB_DATA|^smb_ucs2_t|^TALLOC_CTX/ ) { gotstart = 1; } diff --git a/source/smbd/process.c b/source/smbd/process.c index 36eb8823406..04432adb969 100644 --- a/source/smbd/process.c +++ b/source/smbd/process.c @@ -1018,6 +1018,9 @@ void smbd_process(void) errno = 0; + /* free up temporary memory */ + lp_talloc_free(); + while(!receive_message_or_smb(InBuffer,BUFFER_SIZE,select_timeout,&got_smb)) { if(!timeout_processing( deadtime, &select_timeout, &last_timeout_processing_time)) |