From 1fb1f6bc0dad00d1eb2d1e2aff34e9d3b2714421 Mon Sep 17 00:00:00 2001 From: Garming Sam Date: Fri, 17 Jan 2014 10:30:37 +1300 Subject: lib/param: handle non-constant strings properly by passing in a memory context Signed-off-by: Garming Sam Change-Id: Ic6bb1c709defd2b0f35fc7b877da0badca385776 Reviewed-by: Andrew Bartlett Reviewed-by: Nadezhda Ivanova --- lib/param/loadparm.c | 30 ++++++++++++++++++++++-------- script/generate_param.py | 31 ++++++++++++++++++------------- source4/nbt_server/wins/winsdb.c | 2 +- source4/param/share_classic.c | 4 ++-- source4/rpc_server/srvsvc/dcesrv_srvsvc.c | 4 ++-- 5 files changed, 45 insertions(+), 26 deletions(-) diff --git a/lib/param/loadparm.c b/lib/param/loadparm.c index 1d5ae9e0ca2..b42855c0fe1 100644 --- a/lib/param/loadparm.c +++ b/lib/param/loadparm.c @@ -207,12 +207,13 @@ static struct loadparm_context *global_loadparm_context; #define lpcfg_global_service(i) global_loadparm_context->services[i] #define FN_GLOBAL_STRING(fn_name,var_name) \ - _PUBLIC_ const char *lpcfg_ ## fn_name(struct loadparm_context *lp_ctx) {\ + _PUBLIC_ char *lpcfg_ ## fn_name(struct loadparm_context *lp_ctx, TALLOC_CTX *ctx) {\ if (lp_ctx == NULL) return NULL; \ if (lp_ctx->s3_fns) { \ - smb_panic( __location__ ": " #fn_name " not implemented because it is an allocated and substiuted string"); \ + SMB_ASSERT(lp_ctx->s3_fns->fn_name); \ + return lp_ctx->s3_fns->fn_name(ctx); \ } \ - return lp_ctx->globals->var_name ? lp_string(lp_ctx->globals->var_name) : ""; \ + return lp_ctx->globals->var_name ? talloc_strdup(ctx, lp_string(lp_ctx->globals->var_name)) : talloc_strdup(ctx, ""); \ } #define FN_GLOBAL_CONST_STRING(fn_name,var_name) \ @@ -258,13 +259,17 @@ static struct loadparm_context *global_loadparm_context; * loadparm_service is shared and lpcfg_service() checks the ->s3_fns * hook */ #define FN_LOCAL_STRING(fn_name,val) \ + _PUBLIC_ char *lpcfg_ ## fn_name(struct loadparm_service *service, \ + struct loadparm_service *sDefault, TALLOC_CTX *ctx) { \ + return(talloc_strdup(ctx, lp_string((const char *)((service != NULL && service->val != NULL) ? service->val : sDefault->val)))); \ + } + +#define FN_LOCAL_CONST_STRING(fn_name,val) \ _PUBLIC_ const char *lpcfg_ ## fn_name(struct loadparm_service *service, \ struct loadparm_service *sDefault) { \ - return(lp_string((const char *)((service != NULL && service->val != NULL) ? service->val : sDefault->val))); \ + return((const char *)((service != NULL && service->val != NULL) ? service->val : sDefault->val)); \ } -#define FN_LOCAL_CONST_STRING(fn_name,val) FN_LOCAL_STRING(fn_name, val) - #define FN_LOCAL_LIST(fn_name,val) \ _PUBLIC_ const char **lpcfg_ ## fn_name(struct loadparm_service *service, \ struct loadparm_service *sDefault) {\ @@ -720,7 +725,7 @@ bool lpcfg_add_home(struct loadparm_context *lp_ctx, || strequal(default_service->path, lp_ctx->sDefault->path)) { service->path = talloc_strdup(service, pszHomedir); } else { - service->path = string_sub_talloc(service, lpcfg_path(default_service, lp_ctx->sDefault), "%H", pszHomedir); + service->path = string_sub_talloc(service, lpcfg_path(default_service, lp_ctx->sDefault, service), "%H", pszHomedir); } if (!(*(service->comment))) { @@ -2421,13 +2426,21 @@ const char *lp_default_path(void) static bool lpcfg_update(struct loadparm_context *lp_ctx) { struct debug_settings settings; - lpcfg_add_auto_services(lp_ctx, lpcfg_auto_services(lp_ctx)); + TALLOC_CTX *tmp_ctx; + + tmp_ctx = talloc_new(lp_ctx); + if (tmp_ctx == NULL) { + return false; + } + + lpcfg_add_auto_services(lp_ctx, lpcfg_auto_services(lp_ctx, tmp_ctx)); if (!lp_ctx->globals->wins_server_list && lp_ctx->globals->we_are_a_wins_server) { lpcfg_do_global_parameter(lp_ctx, "wins server", "127.0.0.1"); } if (!lp_ctx->global) { + TALLOC_FREE(tmp_ctx); return true; } @@ -2456,6 +2469,7 @@ static bool lpcfg_update(struct loadparm_context *lp_ctx) unsetenv("SOCKET_TESTNONBLOCK"); } + TALLOC_FREE(tmp_ctx); return true; } diff --git a/script/generate_param.py b/script/generate_param.py index 4e04b3a45bf..7df097ec3ed 100644 --- a/script/generate_param.py +++ b/script/generate_param.py @@ -177,7 +177,7 @@ def make_lib_proto(path_in, path_out): continue output_string = "" - if parameter['constant'] or parameter['type'] == 'string': + if parameter['constant']: output_string += 'const ' param_type = mapping.get(parameter['type']) if param_type is None: @@ -186,12 +186,20 @@ def make_lib_proto(path_in, path_out): output_string += "lpcfg_%s" % parameter['function'] - if parameter['context'] == 'G': - output_string += '(struct loadparm_context *);\n' - elif parameter['context'] == 'S': - output_string += '(struct loadparm_service *, struct loadparm_service *);\n' + if parameter['type'] == 'string' and not parameter['constant']: + if parameter['context'] == 'G': + output_string += '(struct loadparm_context *, TALLOC_CTX *ctx);\n' + elif parameter['context'] == 'S': + output_string += '(struct loadparm_service *, struct loadparm_service *, TALLOC_CTX *ctx);\n' + else: + raise Exception(parameter['name'] + " has an invalid param type " + parameter['type']) else: - raise Exception(parameter['name'] + " has an invalid param type " + parameter['type']) + if parameter['context'] == 'G': + output_string += '(struct loadparm_context *);\n' + elif parameter['context'] == 'S': + output_string += '(struct loadparm_service *, struct loadparm_service *);\n' + else: + raise Exception(parameter['name'] + " has an invalid param type " + parameter['type']) file_out.write(output_string) @@ -277,9 +285,6 @@ def make_s3_param(path_in, path_out): continue if parameter['context'] != 'G': continue - # STRING isn't handle yet properly - if parameter['type'] == 'string' and not parameter['constant']: - continue output_string = "\t" if parameter['constant'] or parameter['type'] == 'string': output_string += 'const ' @@ -288,7 +293,10 @@ def make_s3_param(path_in, path_out): raise Exception(parameter['name'] + " has an invalid context " + parameter['context']) output_string += param_type - output_string += " (*%s)(void);\n" % parameter['function'] + if parameter['type'] == 'string' and not parameter['constant']: + output_string += " (*%s)(TALLOC_CTX *);\n" % parameter['function'] + else: + output_string += " (*%s)(void);\n" % parameter['function'] file_out.write(output_string) file_out.write("};\n") @@ -321,9 +329,6 @@ def make_s3_param_ctx_table(path_in, path_out): continue if parameter['context'] != 'G': continue - # STRING isn't handle yet properly - if parameter['type'] == 'string' and not parameter['constant']: - continue output_string = "\t.%s" % parameter['function'] output_string += " = lp_%s,\n" % parameter['function'] file_out.write(output_string) diff --git a/source4/nbt_server/wins/winsdb.c b/source4/nbt_server/wins/winsdb.c index 9b1cd2c3bb6..fa9a6154b9a 100644 --- a/source4/nbt_server/wins/winsdb.c +++ b/source4/nbt_server/wins/winsdb.c @@ -994,7 +994,7 @@ struct winsdb_handle *winsdb_connect(TALLOC_CTX *mem_ctx, if (!h->ldb) goto failed; h->caller = caller; - h->hook_script = lpcfg_wins_hook(lp_ctx); + h->hook_script = lpcfg_wins_hook(lp_ctx, h); h->local_owner = talloc_strdup(h, owner); if (!h->local_owner) goto failed; diff --git a/source4/param/share_classic.c b/source4/param/share_classic.c index 74a454e5e16..67ea392824f 100644 --- a/source4/param/share_classic.c +++ b/source4/param/share_classic.c @@ -77,11 +77,11 @@ static char *sclassic_string_option(TALLOC_CTX *mem_ctx, } if (strcmp(opt_name, SHARE_PATH) == 0) { - return lpcfg_path(s, lpcfg_default_service(lp_ctx)); + return lpcfg_path(s, lpcfg_default_service(lp_ctx), mem_ctx); } if (strcmp(opt_name, SHARE_COMMENT) == 0) { - return lpcfg_comment(s, lpcfg_default_service(lp_ctx)); + return lpcfg_comment(s, lpcfg_default_service(lp_ctx), mem_ctx); } if (strcmp(opt_name, SHARE_VOLUME) == 0) { diff --git a/source4/rpc_server/srvsvc/dcesrv_srvsvc.c b/source4/rpc_server/srvsvc/dcesrv_srvsvc.c index 6521aea5039..4fd6d32e303 100644 --- a/source4/rpc_server/srvsvc/dcesrv_srvsvc.c +++ b/source4/rpc_server/srvsvc/dcesrv_srvsvc.c @@ -1464,7 +1464,7 @@ static WERROR dcesrv_srvsvc_NetSrvGetInfo(struct dcesrv_call_state *dce_call, TA info101->version_major = server_info->version_major; info101->version_minor = server_info->version_minor; info101->server_type = dcesrv_common_get_server_type(mem_ctx, dce_call->event_ctx, dce_ctx); - info101->comment = talloc_strdup(mem_ctx, lpcfg_server_string(dce_ctx->lp_ctx)); + info101->comment = lpcfg_server_string(dce_ctx->lp_ctx, mem_ctx); W_ERROR_HAVE_NO_MEMORY(info101->comment); r->out.info->info101 = info101; @@ -1484,7 +1484,7 @@ static WERROR dcesrv_srvsvc_NetSrvGetInfo(struct dcesrv_call_state *dce_call, TA info102->version_major = server_info->version_major; info102->version_minor = server_info->version_minor; info102->server_type = dcesrv_common_get_server_type(mem_ctx, dce_call->event_ctx, dce_ctx); - info102->comment = talloc_strdup(mem_ctx, lpcfg_server_string(dce_ctx->lp_ctx)); + info102->comment = lpcfg_server_string(dce_ctx->lp_ctx, mem_ctx); W_ERROR_HAVE_NO_MEMORY(info102->comment); info102->users = dcesrv_common_get_users(mem_ctx, dce_ctx); -- cgit