mirror of
https://github.com/samba-team/samba.git
synced 2024-12-22 13:34:15 +03:00
lib/util: Replace buggy string_sub_talloc() with talloc_string_sub() in lib/util
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14658 Signed-off-by: Andrew Bartlett <abartlet@samba.org> Reviewed-by: Volker Lendecke <vl@samba.org> Autobuild-User(master): Volker Lendecke <vl@samba.org> Autobuild-Date(master): Wed Mar 10 08:06:25 UTC 2021 on sn-devel-184
This commit is contained in:
parent
5cdc065211
commit
d7e620ff41
@ -113,60 +113,11 @@ static void string_sub2(char *s,const char *pattern, const char *insert, size_t
|
||||
}
|
||||
}
|
||||
|
||||
void string_sub_once(char *s, const char *pattern,
|
||||
const char *insert, size_t len)
|
||||
{
|
||||
string_sub2( s, pattern, insert, len, true, true, false );
|
||||
}
|
||||
|
||||
void string_sub(char *s,const char *pattern, const char *insert, size_t len)
|
||||
{
|
||||
string_sub2( s, pattern, insert, len, true, false, false );
|
||||
}
|
||||
|
||||
/**
|
||||
* Talloc'ed version of string_sub
|
||||
*/
|
||||
_PUBLIC_ char *string_sub_talloc(TALLOC_CTX *mem_ctx, const char *s,
|
||||
const char *pattern, const char *insert)
|
||||
{
|
||||
const char *p;
|
||||
char *ret;
|
||||
size_t len, alloc_len;
|
||||
|
||||
if (insert == NULL || pattern == NULL || !*pattern || s == NULL)
|
||||
return NULL;
|
||||
|
||||
/* determine length needed */
|
||||
len = strlen(s);
|
||||
|
||||
for (p = strstr(s, pattern); p != NULL;
|
||||
p = strstr(p+strlen(pattern), pattern)) {
|
||||
len += strlen(insert) - strlen(pattern);
|
||||
}
|
||||
|
||||
alloc_len = MAX(len, strlen(s))+1;
|
||||
ret = talloc_array(mem_ctx, char, alloc_len);
|
||||
if (ret == NULL)
|
||||
return NULL;
|
||||
strncpy(ret, s, alloc_len);
|
||||
string_sub(ret, pattern, insert, alloc_len);
|
||||
|
||||
ret = talloc_realloc(mem_ctx, ret, char, len+1);
|
||||
if (ret == NULL)
|
||||
return NULL;
|
||||
|
||||
if (ret[len] != '\0') {
|
||||
DEBUG(0,("Internal error at %s(%d): string not terminated\n",
|
||||
__FILE__, __LINE__));
|
||||
abort();
|
||||
}
|
||||
|
||||
talloc_set_name_const(ret, ret);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
Similar to string_sub() but allows for any character to be substituted.
|
||||
Use with caution!
|
||||
@ -209,3 +160,120 @@ _PUBLIC_ void all_string_sub(char *s,const char *pattern,const char *insert, siz
|
||||
ls = ls + li - lp;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Internal guts of talloc_string_sub and talloc_all_string_sub.
|
||||
* talloc version of string_sub2.
|
||||
*/
|
||||
|
||||
char *talloc_string_sub2(TALLOC_CTX *mem_ctx, const char *src,
|
||||
const char *pattern,
|
||||
const char *insert,
|
||||
bool remove_unsafe_characters,
|
||||
bool replace_once,
|
||||
bool allow_trailing_dollar)
|
||||
{
|
||||
char *p, *in;
|
||||
char *s;
|
||||
char *string;
|
||||
ssize_t ls,lp,li,ld, i;
|
||||
|
||||
if (!insert || !pattern || !*pattern || !src) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
string = talloc_strdup(mem_ctx, src);
|
||||
if (string == NULL) {
|
||||
DEBUG(0, ("talloc_string_sub2: "
|
||||
"talloc_strdup failed\n"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
s = string;
|
||||
|
||||
in = talloc_strdup(mem_ctx, insert);
|
||||
if (!in) {
|
||||
DEBUG(0, ("talloc_string_sub2: ENOMEM\n"));
|
||||
return NULL;
|
||||
}
|
||||
ls = (ssize_t)strlen(s);
|
||||
lp = (ssize_t)strlen(pattern);
|
||||
li = (ssize_t)strlen(insert);
|
||||
ld = li - lp;
|
||||
|
||||
for (i=0;i<li;i++) {
|
||||
switch (in[i]) {
|
||||
case '$':
|
||||
/* allow a trailing $
|
||||
* (as in machine accounts) */
|
||||
if (allow_trailing_dollar && (i == li - 1 )) {
|
||||
break;
|
||||
}
|
||||
|
||||
FALL_THROUGH;
|
||||
case '`':
|
||||
case '"':
|
||||
case '\'':
|
||||
case ';':
|
||||
case '%':
|
||||
case '\r':
|
||||
case '\n':
|
||||
if (remove_unsafe_characters) {
|
||||
in[i] = '_';
|
||||
break;
|
||||
}
|
||||
|
||||
FALL_THROUGH;
|
||||
default:
|
||||
/* ok */
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
while ((p = strstr_m(s,pattern))) {
|
||||
if (ld > 0) {
|
||||
int offset = PTR_DIFF(s,string);
|
||||
string = (char *)talloc_realloc_size(mem_ctx, string,
|
||||
ls + ld + 1);
|
||||
if (!string) {
|
||||
DEBUG(0, ("talloc_string_sub: out of "
|
||||
"memory!\n"));
|
||||
TALLOC_FREE(in);
|
||||
return NULL;
|
||||
}
|
||||
p = string + offset + (p - s);
|
||||
}
|
||||
if (li != lp) {
|
||||
memmove(p+li,p+lp,strlen(p+lp)+1);
|
||||
}
|
||||
memcpy(p, in, li);
|
||||
s = p + li;
|
||||
ls += ld;
|
||||
|
||||
if (replace_once) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
TALLOC_FREE(in);
|
||||
return string;
|
||||
}
|
||||
|
||||
/* Same as string_sub, but returns a talloc'ed string */
|
||||
|
||||
char *talloc_string_sub(TALLOC_CTX *mem_ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert)
|
||||
{
|
||||
return talloc_string_sub2(mem_ctx, src, pattern, insert,
|
||||
true, false, false);
|
||||
}
|
||||
|
||||
char *talloc_all_string_sub(TALLOC_CTX *ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert)
|
||||
{
|
||||
return talloc_string_sub2(ctx, src, pattern, insert,
|
||||
false, false, false);
|
||||
}
|
||||
|
@ -39,12 +39,6 @@
|
||||
**/
|
||||
void string_sub(char *s,const char *pattern, const char *insert, size_t len);
|
||||
|
||||
void string_sub_once(char *s, const char *pattern,
|
||||
const char *insert, size_t len);
|
||||
|
||||
char *string_sub_talloc(TALLOC_CTX *mem_ctx, const char *s,
|
||||
const char *pattern, const char *insert);
|
||||
|
||||
/**
|
||||
Similar to string_sub() but allows for any character to be substituted.
|
||||
Use with caution!
|
||||
@ -53,4 +47,18 @@ char *string_sub_talloc(TALLOC_CTX *mem_ctx, const char *s,
|
||||
**/
|
||||
void all_string_sub(char *s,const char *pattern,const char *insert, size_t len);
|
||||
|
||||
char *talloc_string_sub2(TALLOC_CTX *mem_ctx, const char *src,
|
||||
const char *pattern,
|
||||
const char *insert,
|
||||
bool remove_unsafe_characters,
|
||||
bool replace_once,
|
||||
bool allow_trailing_dollar);
|
||||
char *talloc_string_sub(TALLOC_CTX *mem_ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert);
|
||||
char *talloc_all_string_sub(TALLOC_CTX *ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert);
|
||||
#endif /* _SAMBA_SUBSTITUTE_H_ */
|
||||
|
@ -68,22 +68,22 @@ static bool test_string_sub_special_char(struct torture_context *tctx)
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool test_string_sub_talloc_simple(struct torture_context *tctx)
|
||||
static bool test_talloc_string_sub_simple(struct torture_context *tctx)
|
||||
{
|
||||
char *t;
|
||||
|
||||
t = string_sub_talloc(tctx, "foobla", "foo", "bl");
|
||||
t = talloc_string_sub(tctx, "foobla", "foo", "bl");
|
||||
|
||||
torture_assert_str_equal(tctx, t, "blbla", "invalid sub");
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool test_string_sub_talloc_multiple(struct torture_context *tctx)
|
||||
static bool test_talloc_string_sub_multiple(struct torture_context *tctx)
|
||||
{
|
||||
char *t;
|
||||
|
||||
t = string_sub_talloc(tctx, "fooblafoo", "foo", "aapnootmies");
|
||||
t = talloc_string_sub(tctx, "fooblafoo", "foo", "aapnootmies");
|
||||
|
||||
torture_assert_str_equal(tctx, t, "aapnootmiesblaaapnootmies",
|
||||
"invalid sub");
|
||||
@ -112,11 +112,11 @@ struct torture_suite *torture_local_util_str(TALLOC_CTX *mem_ctx)
|
||||
torture_suite_add_simple_test(suite, "string_sub_special_chars",
|
||||
test_string_sub_special_char);
|
||||
|
||||
torture_suite_add_simple_test(suite, "string_sub_talloc_simple",
|
||||
test_string_sub_talloc_simple);
|
||||
torture_suite_add_simple_test(suite, "talloc_string_sub_simple",
|
||||
test_talloc_string_sub_simple);
|
||||
|
||||
torture_suite_add_simple_test(suite, "string_sub_talloc_multiple",
|
||||
test_string_sub_talloc_multiple);
|
||||
test_talloc_string_sub_multiple);
|
||||
|
||||
return suite;
|
||||
}
|
||||
|
@ -576,21 +576,7 @@ char *realloc_string_sub2(char *string,
|
||||
char *realloc_string_sub(char *string,
|
||||
const char *pattern,
|
||||
const char *insert);
|
||||
char *talloc_string_sub2(TALLOC_CTX *mem_ctx, const char *src,
|
||||
const char *pattern,
|
||||
const char *insert,
|
||||
bool remove_unsafe_characters,
|
||||
bool replace_once,
|
||||
bool allow_trailing_dollar);
|
||||
char *talloc_string_sub(TALLOC_CTX *mem_ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert);
|
||||
void all_string_sub(char *s,const char *pattern,const char *insert, size_t len);
|
||||
char *talloc_all_string_sub(TALLOC_CTX *ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert);
|
||||
char *octal_string(int i);
|
||||
char *string_truncate(char *s, unsigned int length);
|
||||
char *strchr_m(const char *src, char c);
|
||||
|
@ -193,123 +193,6 @@ bool in_list(const char *s, const char *list, bool casesensitive)
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* Internal guts of talloc_string_sub and talloc_all_string_sub.
|
||||
* talloc version of string_sub2.
|
||||
*/
|
||||
|
||||
char *talloc_string_sub2(TALLOC_CTX *mem_ctx, const char *src,
|
||||
const char *pattern,
|
||||
const char *insert,
|
||||
bool remove_unsafe_characters,
|
||||
bool replace_once,
|
||||
bool allow_trailing_dollar)
|
||||
{
|
||||
char *p, *in;
|
||||
char *s;
|
||||
char *string;
|
||||
ssize_t ls,lp,li,ld, i;
|
||||
|
||||
if (!insert || !pattern || !*pattern || !src) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
string = talloc_strdup(mem_ctx, src);
|
||||
if (string == NULL) {
|
||||
DEBUG(0, ("talloc_string_sub2: "
|
||||
"talloc_strdup failed\n"));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
s = string;
|
||||
|
||||
in = talloc_strdup(mem_ctx, insert);
|
||||
if (!in) {
|
||||
DEBUG(0, ("talloc_string_sub2: ENOMEM\n"));
|
||||
return NULL;
|
||||
}
|
||||
ls = (ssize_t)strlen(s);
|
||||
lp = (ssize_t)strlen(pattern);
|
||||
li = (ssize_t)strlen(insert);
|
||||
ld = li - lp;
|
||||
|
||||
for (i=0;i<li;i++) {
|
||||
switch (in[i]) {
|
||||
case '$':
|
||||
/* allow a trailing $
|
||||
* (as in machine accounts) */
|
||||
if (allow_trailing_dollar && (i == li - 1 )) {
|
||||
break;
|
||||
}
|
||||
|
||||
FALL_THROUGH;
|
||||
case '`':
|
||||
case '"':
|
||||
case '\'':
|
||||
case ';':
|
||||
case '%':
|
||||
case '\r':
|
||||
case '\n':
|
||||
if (remove_unsafe_characters) {
|
||||
in[i] = '_';
|
||||
break;
|
||||
}
|
||||
|
||||
FALL_THROUGH;
|
||||
default:
|
||||
/* ok */
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
while ((p = strstr_m(s,pattern))) {
|
||||
if (ld > 0) {
|
||||
int offset = PTR_DIFF(s,string);
|
||||
string = (char *)TALLOC_REALLOC(mem_ctx, string,
|
||||
ls + ld + 1);
|
||||
if (!string) {
|
||||
DEBUG(0, ("talloc_string_sub: out of "
|
||||
"memory!\n"));
|
||||
TALLOC_FREE(in);
|
||||
return NULL;
|
||||
}
|
||||
p = string + offset + (p - s);
|
||||
}
|
||||
if (li != lp) {
|
||||
memmove(p+li,p+lp,strlen(p+lp)+1);
|
||||
}
|
||||
memcpy(p, in, li);
|
||||
s = p + li;
|
||||
ls += ld;
|
||||
|
||||
if (replace_once) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
TALLOC_FREE(in);
|
||||
return string;
|
||||
}
|
||||
|
||||
/* Same as string_sub, but returns a talloc'ed string */
|
||||
|
||||
char *talloc_string_sub(TALLOC_CTX *mem_ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert)
|
||||
{
|
||||
return talloc_string_sub2(mem_ctx, src, pattern, insert,
|
||||
true, false, false);
|
||||
}
|
||||
|
||||
char *talloc_all_string_sub(TALLOC_CTX *ctx,
|
||||
const char *src,
|
||||
const char *pattern,
|
||||
const char *insert)
|
||||
{
|
||||
return talloc_string_sub2(ctx, src, pattern, insert,
|
||||
false, false, false);
|
||||
}
|
||||
|
||||
/**
|
||||
Write an octal as a string.
|
||||
**/
|
||||
|
Loading…
Reference in New Issue
Block a user