The Samba-Bugzilla – Attachment 16418 Details for
Bug 14625
smbd share mode double free crash
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
test code to test theory
0001-TESTCODE-for-memcache-test-of-get_share_mode_lock-de.patch (text/plain), 8.72 KB, created by
Noel Power
on 2021-02-01 14:57:27 UTC
(
hide
)
Description:
test code to test theory
Filename:
MIME Type:
Creator:
Noel Power
Created:
2021-02-01 14:57:27 UTC
Size:
8.72 KB
patch
obsolete
>From d07cf217edc5063f73fdb40e5c295d8af0f3f274 Mon Sep 17 00:00:00 2001 >From: Noel Power <noel.power@suse.com> >Date: Fri, 18 Dec 2020 21:36:52 +0000 >Subject: [PATCH] TESTCODE for memcache test of get_share_mode_lock destruction > >there is a weird Bad talloc magic value - access after free error >The only way I can see this happen is if the underlying >memcache entry is evicted. >--- > lib/util/memcache.c | 1 + > source3/locking/share_mode_lock.c | 20 +++-- > source3/utils/cache-test.c | 117 ++++++++++++++++++++++++++++++ > source3/utils/wscript_build | 6 ++ > 4 files changed, 137 insertions(+), 7 deletions(-) > create mode 100644 source3/utils/cache-test.c > >diff --git a/lib/util/memcache.c b/lib/util/memcache.c >index 1e616bd0e9a..3ccdb46b93a 100644 >--- a/lib/util/memcache.c >+++ b/lib/util/memcache.c >@@ -230,6 +230,7 @@ static void memcache_trim(struct memcache *cache) > } > > while ((cache->size > cache->max_size) && DLIST_TAIL(cache->mru)) { >+ DBG_ERR("evicting a cache item\n"); > memcache_delete_element(cache, DLIST_TAIL(cache->mru)); > } > } >diff --git a/source3/locking/share_mode_lock.c b/source3/locking/share_mode_lock.c >index a97d8d44930..c5ac18dbeb5 100644 >--- a/source3/locking/share_mode_lock.c >+++ b/source3/locking/share_mode_lock.c >@@ -151,7 +151,7 @@ static void share_mode_memcache_delete(struct share_mode_data *d) > { > const DATA_BLOB key = memcache_key(&d->id); > >- DBG_DEBUG("deleting entry for file %s seq %"PRIx64" key %s\n", >+ DBG_ERR("deleting entry for file %s seq %"PRIx64" key %s\n", > d->base_name, > d->sequence_number, > file_id_string(talloc_tos(), &d->id)); >@@ -164,8 +164,9 @@ static void share_mode_memcache_delete(struct share_mode_data *d) > static void share_mode_memcache_store(struct share_mode_data *d) > { > const DATA_BLOB key = memcache_key(&d->id); >+ struct file_id fid = {.devid = 1, .inode = 2, .extid = 0}; > >- DBG_DEBUG("stored entry for file %s seq %"PRIx64" key %s\n", >+ DBG_ERR("stored entry for file %s seq %"PRIx64" key %s\n", > d->base_name, > d->sequence_number, > file_id_string(talloc_tos(), &d->id)); >@@ -231,7 +232,7 @@ static struct share_mode_data *share_mode_memcache_fetch(TALLOC_CTX *mem_ctx, > SHARE_MODE_LOCK_CACHE, > key); > if (ptr == NULL) { >- DEBUG(10,("failed to find entry for key %s\n", >+ DEBUG(0,("failed to find entry for key %s\n", > file_id_string(mem_ctx, &id))); > return NULL; > } >@@ -239,7 +240,7 @@ static struct share_mode_data *share_mode_memcache_fetch(TALLOC_CTX *mem_ctx, > ndr_err = get_blob_sequence_number(blob, &sequence_number); > if (ndr_err != NDR_ERR_SUCCESS) { > /* Bad blob. Remove entry. */ >- DEBUG(10,("bad blob %u key %s\n", >+ DEBUG(0,("bad blob %u deleting key %s\n", > (unsigned int)ndr_err, > file_id_string(mem_ctx, &id))); > memcache_delete(NULL, >@@ -250,7 +251,7 @@ static struct share_mode_data *share_mode_memcache_fetch(TALLOC_CTX *mem_ctx, > > d = (struct share_mode_data *)ptr; > if (d->sequence_number != sequence_number) { >- DBG_DEBUG("seq changed (cached %"PRIx64") (new %"PRIx64") " >+ DBG_ERR("(deleting) seq changed (cached %"PRIx64") (new %"PRIx64") " > "for key %s\n", > d->sequence_number, > sequence_number, >@@ -272,6 +273,10 @@ static struct share_mode_data *share_mode_memcache_fetch(TALLOC_CTX *mem_ctx, > talloc_set_destructor(d, share_mode_data_nofree_destructor); > > /* Remove from the cache. We own it now. */ >+ DBG_ERR("deleted entry for file %s seq %"PRIx64" key %s\n", >+ d->base_name, >+ d->sequence_number, >+ file_id_string(mem_ctx, &id)); > memcache_delete(NULL, > SHARE_MODE_LOCK_CACHE, > key); >@@ -279,7 +284,7 @@ static struct share_mode_data *share_mode_memcache_fetch(TALLOC_CTX *mem_ctx, > /* And reset the destructor to none. */ > talloc_set_destructor(d, NULL); > >- DBG_DEBUG("fetched entry for file %s seq %"PRIx64" key %s\n", >+ DBG_ERR("fetched entry for file %s seq %"PRIx64" key %s\n", > d->base_name, > d->sequence_number, > file_id_string(mem_ctx, &id)); >@@ -381,6 +386,7 @@ static int share_mode_data_destructor(struct share_mode_data *d) > return 0; > } > >+ DBG_ERR("about to unparse\n"); > data = unparse_share_modes(d); > > if (data.dptr == NULL) { >@@ -438,7 +444,7 @@ static int share_mode_data_destructor(struct share_mode_data *d) > * sequence number matches. See parse_share_modes() > * for details. > */ >- >+ DBG_ERR("about to store cache entry\n"); > share_mode_memcache_store(d); > return -1; > } >diff --git a/source3/utils/cache-test.c b/source3/utils/cache-test.c >new file mode 100644 >index 00000000000..738354d9de6 >--- /dev/null >+++ b/source3/utils/cache-test.c >@@ -0,0 +1,117 @@ >+#include "includes.h" >+#include "popt_common.h" >+#include <unistd.h> >+#include "lib/util/memcache.h" >+#include "librpc/gen_ndr/open_files.h" >+#include "include/locking.h" >+#include "smbd/smbd.h" >+#include "lib/util/memcache.h" >+ >+static bool lcl_set_share_mode(struct share_mode_lock *lck, >+ struct files_struct *fsp, >+ uid_t uid, uint64_t mid, uint16_t op_type, >+ uint32_t lease_idx) >+{ >+ struct share_mode_data *d = lck->data; >+ struct share_mode_entry *tmp, *e; >+ >+ if ((lease_idx != UINT32_MAX) && >+ (lease_idx >= d->num_leases)) { >+ return false; >+ } >+ >+ tmp = talloc_realloc(d, d->share_modes, struct share_mode_entry, >+ d->num_share_modes+1); >+ if (tmp == NULL) { >+ return false; >+ } >+ d->share_modes = tmp; >+ e = &d->share_modes[d->num_share_modes]; >+ d->num_share_modes += 1; >+ d->modified = true; >+ >+ ZERO_STRUCTP(e); >+// e->pid = messaging_server_id(fsp->conn->sconn->msg_ctx); >+ e->share_access = fsp->share_access; >+ // e->private_options = fsp->fh->private_options; >+ e->access_mask = fsp->access_mask; >+ e->op_mid = mid; >+ e->op_type = op_type; >+ e->lease_idx = lease_idx; >+ e->time.tv_sec = fsp->open_time.tv_sec; >+ e->time.tv_usec = fsp->open_time.tv_usec; >+// e->share_file_id = fsp->fh->gen_id; >+ e->uid = (uint32_t)uid; >+ e->flags = (fsp->posix_flags & FSP_POSIX_FLAGS_OPEN) ? >+ SHARE_MODE_FLAG_POSIX_OPEN : 0; >+ e->name_hash = fsp->name_hash; >+ >+ return true; >+} >+ >+ >+static void testmemfoo(TALLOC_CTX *ctx, struct file_id fid) >+{ >+ struct share_mode_lock *lck = NULL; >+ struct timespec timespec = {0}; >+ struct smb_filename smb_fname = { >+ .base_name = talloc_strdup(ctx, "."), >+ }; >+ struct files_struct fsp = {0}; >+ int i; >+ smb_fname.st.st_ex_dev = fid.devid; >+ smb_fname.st.st_ex_ino = fid.inode; >+ lck = get_share_mode_lock(talloc_tos(), fid, >+ "/home/data/testshare", &smb_fname, ×pec); >+ DBG_ERR("#1 created lock\n"); >+ DBG_ERR("#1 allocating just one share_mode lock\n"); >+ lcl_set_share_mode(lck, &fsp, 1, 2, 3, >+ UINT32_MAX); >+ DBG_ERR("#1 free-ing lock\n"); >+ TALLOC_FREE(lck); >+ DBG_ERR("#1 freed lock\n"); >+ lck = get_share_mode_lock(talloc_tos(), fid, >+ "/home/data/testshare", &smb_fname, ×pec); >+ DBG_ERR("#2 created lock\n"); >+ DBG_ERR("#2 allocating many many (10000) share_mode locks\n"); >+ for (i = 0; i < 10000; i++) { >+ lcl_set_share_mode(lck, &fsp, i + 2, i + 3, i + 4, >+ UINT32_MAX); >+ } >+ lcl_set_share_mode(lck, &fsp, 2, 3, 4, >+ UINT32_MAX); >+ DBG_ERR("#2 free-ing lock\n"); >+ TALLOC_FREE(lck); >+ DBG_ERR("#2 freed lock\n"); >+} >+ >+int main(int argc, const char *argv[]) >+{ >+ int result; >+ TALLOC_CTX *ctx = talloc_init("testmemcache"); >+ TALLOC_CTX *frame = talloc_stackframe(); >+ int stat_cache_size = 0; >+ struct memcache *cache = NULL; >+ int i; >+ smb_init_locale(); >+ >+ if (!lp_load_client(get_dyn_CONFIGFILE())) { >+ fprintf(stderr, "ERROR: Can't load %s - run testparm to debug it\n", >+ get_dyn_CONFIGFILE()); >+ exit(1); >+ } >+ >+ stat_cache_size = lp_max_stat_cache_size(); >+ fprintf(stderr, "setting memcache size to %d\n", stat_cache_size * 1024); >+ cache = memcache_init(ctx, stat_cache_size * 1024); >+ memcache_set_global(cache); >+ locking_init(); >+ for (i=0; i<1; i++) { >+ struct file_id fid = {.devid = 1 + i, .inode = 2 + i, .extid = 0}; >+ DBG_ERR("## iter %d\n", i); >+ testmemfoo(ctx, fid); >+ } >+ result = 0; >+ TALLOC_FREE(frame); >+ return result; >+} >diff --git a/source3/utils/wscript_build b/source3/utils/wscript_build >index c6d1c29b310..742cf181e37 100644 >--- a/source3/utils/wscript_build >+++ b/source3/utils/wscript_build >@@ -283,3 +283,9 @@ bld.SAMBA3_BINARY('destroy_netlogon_creds_cli', > NETLOGON_CREDS_CLI > ''', > install=False) >+bld.SAMBA3_BINARY('cache-test', >+ source='cache-test.c', >+ deps=''' >+ talloc >+ POPT_SAMBA >+ smbd_base''') >-- >2.26.2 >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Raw
Actions:
View
Attachments on
bug 14625
: 16418 |
16421
|
16427
|
16428
|
16429