Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
MariaDB
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
MariaDB
Commits
aa234851
Commit
aa234851
authored
Jan 13, 2006
by
sasha@asksasha.com
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
patch for replace_regex in mysqltest
parent
96ae7c2e
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
385 additions
and
0 deletions
+385
-0
client/mysqltest.c
client/mysqltest.c
+385
-0
No files found.
client/mysqltest.c
View file @
aa234851
...
...
@@ -181,6 +181,25 @@ static test_file file_stack[MAX_INCLUDE_DEPTH];
static
test_file
*
cur_file
;
static
test_file
*
file_stack_end
;
struct
st_regex
{
char
*
pattern
;
char
*
replace
;
int
icase
;
};
struct
st_replace_regex
{
DYNAMIC_ARRAY
regex_arr
;
char
*
buf
;
char
*
even_buf
;
uint
even_buf_len
;
char
*
odd_buf
;
uint
odd_buf_len
;
};
struct
st_replace_regex
*
glob_replace_regex
=
0
;
static
uint
lineno_stack
[
MAX_INCLUDE_DEPTH
];
static
char
TMPDIR
[
FN_REFLEN
];
static
char
delimiter
[
MAX_DELIMITER
]
=
DEFAULT_DELIMITER
;
...
...
@@ -218,6 +237,9 @@ static int ps_match_re(char *);
static
char
*
ps_eprint
(
int
);
static
void
ps_free_reg
(
void
);
static
int
reg_replace
(
char
**
buf_p
,
int
*
buf_len_p
,
char
*
pattern
,
char
*
replace
,
char
*
string
,
int
icase
);
static
const
char
*
embedded_server_groups
[]
=
{
"server"
,
...
...
@@ -326,6 +348,7 @@ Q_EXIT,
Q_DISABLE_RECONNECT
,
Q_ENABLE_RECONNECT
,
Q_IF
,
Q_DISABLE_PARSING
,
Q_ENABLE_PARSING
,
Q_REPLACE_REGEX
,
Q_UNKNOWN
,
/* Unknown command. */
Q_COMMENT
,
/* Comments, ignored. */
...
...
@@ -419,6 +442,7 @@ const char *command_names[]=
"if"
,
"disable_parsing"
,
"enable_parsing"
,
"replace_regex"
,
0
};
...
...
@@ -460,6 +484,7 @@ struct st_replace *init_replace(my_string *from, my_string *to, uint count,
uint
replace_strings
(
struct
st_replace
*
rep
,
my_string
*
start
,
uint
*
max_length
,
const
char
*
from
);
void
free_replace
();
static
void
free_replace_regex
();
static
int
insert_pointer_name
(
reg1
POINTER_ARRAY
*
pa
,
my_string
name
);
void
free_pointer_array
(
POINTER_ARRAY
*
pa
);
static
int
initialize_replace_buffer
(
void
);
...
...
@@ -1772,6 +1797,165 @@ static char *get_string(char **to_ptr, char **from_ptr,
DBUG_RETURN
(
start
);
}
#define PARSE_REGEX_ARG \
while (p < expr_end) \
{\
char c= *p;\
if (c == '/')\
{\
if (last_c == '\\')\
{\
buf_p[-1]= '/';\
}\
else\
{\
*buf_p++ = 0;\
break;\
} \
} \
else\
*buf_p++ = c;\
\
last_c= c;\
p++;\
} \
static
struct
st_replace_regex
*
init_replace_regex
(
char
*
expr
)
{
struct
st_replace_regex
*
res
;
char
*
buf
,
*
expr_end
;
char
*
p
;
char
*
buf_p
;
uint
expr_len
=
strlen
(
expr
);
char
last_c
=
0
;
struct
st_regex
reg
;
if
(
!
(
res
=
(
struct
st_replace_regex
*
)
my_malloc
(
sizeof
(
*
res
)
+
expr_len
,
MYF
(
MY_FAE
+
MY_WME
))))
return
0
;
my_init_dynamic_array
(
&
res
->
regex_arr
,
sizeof
(
struct
st_regex
),
128
,
128
);
buf
=
(
char
*
)
res
+
sizeof
(
*
res
);
expr_end
=
expr
+
expr_len
;
p
=
expr
;
buf_p
=
buf
;
/* for each regexp substitution statement */
while
(
p
<
expr_end
)
{
bzero
(
&
reg
,
sizeof
(
reg
));
/* find the start of the statement */
while
(
p
<
expr_end
)
{
if
(
*
p
==
'/'
)
break
;
p
++
;
}
if
(
p
==
expr_end
||
++
p
==
expr_end
)
{
if
(
res
->
regex_arr
.
elements
)
break
;
else
goto
err
;
}
/* we found the start */
reg
.
pattern
=
buf_p
;
PARSE_REGEX_ARG
if
(
p
==
expr_end
||
++
p
==
expr_end
)
goto
err
;
/* buf_p now points to the replacement pattern terminated with \0 */
reg
.
replace
=
buf_p
;
PARSE_REGEX_ARG
if
(
p
==
expr_end
)
goto
err
;
/* skip the ending '/' in the statement */
p
++
;
if
(
p
<
expr_end
&&
*
p
==
'i'
)
reg
.
icase
=
1
;
/* done parsing the statement, now place it in regex_arr */
if
(
insert_dynamic
(
&
res
->
regex_arr
,(
gptr
)
&
reg
))
die
(
"Out of memory"
);
}
res
->
odd_buf_len
=
res
->
even_buf_len
=
8192
;
res
->
even_buf
=
(
char
*
)
my_malloc
(
res
->
even_buf_len
,
MYF
(
MY_WME
+
MY_FAE
));
res
->
odd_buf
=
(
char
*
)
my_malloc
(
res
->
odd_buf_len
,
MYF
(
MY_WME
+
MY_FAE
));
res
->
buf
=
res
->
even_buf
;
return
res
;
err:
my_free
((
gptr
)
res
,
0
);
return
0
;
}
/*
TODO: at some point figure out if there is a way to do everything
in one pass
*/
static
int
multi_reg_replace
(
struct
st_replace_regex
*
r
,
char
*
val
)
{
uint
i
;
char
*
in_buf
,
*
out_buf
;
int
*
buf_len_p
;
in_buf
=
val
;
out_buf
=
r
->
even_buf
;
buf_len_p
=
&
r
->
even_buf_len
;
r
->
buf
=
0
;
for
(
i
=
0
;
i
<
r
->
regex_arr
.
elements
;
i
++
)
{
struct
st_regex
re
;
char
*
save_out_buf
=
out_buf
;
get_dynamic
(
&
r
->
regex_arr
,(
gptr
)
&
re
,
i
);
if
(
!
reg_replace
(
&
out_buf
,
buf_len_p
,
re
.
pattern
,
re
.
replace
,
in_buf
,
re
.
icase
))
{
//printf("out_buf=%s\n", out_buf);
/* the buffer has been reallocated, make adjustements */
if
(
save_out_buf
!=
out_buf
)
{
if
(
save_out_buf
==
r
->
even_buf
)
r
->
even_buf
=
out_buf
;
else
r
->
odd_buf
=
out_buf
;
}
r
->
buf
=
out_buf
;
if
(
in_buf
==
val
)
in_buf
=
r
->
odd_buf
;
swap_variables
(
char
*
,
in_buf
,
out_buf
);
buf_len_p
=
(
out_buf
==
r
->
even_buf
)
?
&
r
->
even_buf_len
:
&
r
->
odd_buf_len
;
}
}
return
(
r
->
buf
==
0
);
}
static
void
get_replace_regex
(
struct
st_query
*
q
)
{
char
*
expr
=
q
->
first_argument
;
free_replace_regex
();
if
(
!
(
glob_replace_regex
=
init_replace_regex
(
expr
)))
die
(
"Could not init replace_regex"
);
q
->
last_argument
=
q
->
end
;
}
/*
Get arguments for replace. The syntax is:
...
...
@@ -1824,6 +2008,18 @@ static void get_replace(struct st_query *q)
DBUG_VOID_RETURN
;
}
static
void
free_replace_regex
()
{
if
(
glob_replace_regex
)
{
my_free
(
glob_replace_regex
->
even_buf
,
MYF
(
MY_ALLOW_ZERO_PTR
));
my_free
(
glob_replace_regex
->
odd_buf
,
MYF
(
MY_ALLOW_ZERO_PTR
));
my_free
((
char
*
)
glob_replace_regex
,
MYF
(
0
));
glob_replace_regex
=
0
;
}
}
void
free_replace
()
{
DBUG_ENTER
(
"free_replace"
);
...
...
@@ -2138,6 +2334,7 @@ int connect_n_handle_errors(struct st_query *q, MYSQL* con, const char* host,
err:
free_replace
();
free_replace_regex
();
if
(
ds
==
&
ds_tmp
)
dynstr_free
(
&
ds_tmp
);
return
error
;
...
...
@@ -2986,6 +3183,178 @@ void reject_dump(const char *record_file, char *buf, int size)
str_to_file
(
fn_format
(
reject_file
,
record_file
,
""
,
".reject"
,
2
),
buf
,
size
);
}
static
void
check_regerr
(
my_regex_t
*
r
,
int
err
)
{
char
err_buf
[
1024
];
if
(
err
)
{
my_regerror
(
err
,
r
,
err_buf
,
sizeof
(
err_buf
));
fprintf
(
stderr
,
"Regex error: %s
\n
"
,
err_buf
);
exit
(
1
);
}
}
#define SECURE_REG_BUF if (buf_len < need_buf_len)\
{\
int off= res_p - buf;\
buf= (char*)my_realloc(buf,need_buf_len,MYF(MY_WME+MY_FAE));\
res_p= buf + off;\
buf_len= need_buf_len;\
}\
static
int
reg_replace
(
char
**
buf_p
,
int
*
buf_len_p
,
char
*
pattern
,
char
*
replace
,
char
*
string
,
int
icase
)
{
my_regex_t
r
;
my_regmatch_t
*
subs
;
char
*
buf_end
,
*
replace_end
;
char
*
buf
=
*
buf_p
;
int
len
;
int
buf_len
,
need_buf_len
;
int
cflags
=
REG_EXTENDED
;
int
err_code
;
char
*
res_p
,
*
str_p
,
*
str_end
;
buf_len
=
*
buf_len_p
;
len
=
strlen
(
string
);
str_end
=
string
+
len
;
need_buf_len
=
len
*
2
+
1
;
res_p
=
buf
;
SECURE_REG_BUF
buf_end
=
buf
+
buf_len
;
if
(
icase
)
cflags
|=
REG_ICASE
;
if
((
err_code
=
my_regcomp
(
&
r
,
pattern
,
cflags
,
&
my_charset_latin1
)))
{
check_regerr
(
&
r
,
err_code
);
return
1
;
}
subs
=
(
my_regmatch_t
*
)
my_malloc
(
sizeof
(
my_regmatch_t
)
*
(
r
.
re_nsub
+
1
),
MYF
(
MY_WME
+
MY_FAE
));
*
res_p
=
0
;
str_p
=
string
;
replace_end
=
replace
+
strlen
(
replace
);
while
(
!
err_code
)
{
err_code
=
my_regexec
(
&
r
,
str_p
,
r
.
re_nsub
+
1
,
subs
,
(
str_p
==
string
)
?
REG_NOTBOL
:
0
);
if
(
err_code
&&
err_code
!=
REG_NOMATCH
)
{
check_regerr
(
&
r
,
err_code
);
my_regfree
(
&
r
);
return
1
;
}
if
(
!
err_code
)
{
char
*
expr_p
=
replace
;
int
c
;
need_buf_len
=
(
res_p
-
buf
)
+
subs
[
0
].
rm_so
;
while
(
expr_p
<
replace_end
)
{
int
back_ref_num
=
-
1
;
c
=
*
expr_p
;
if
(
c
==
'\\'
&&
expr_p
+
1
<
replace_end
)
{
back_ref_num
=
expr_p
[
1
]
-
'0'
;
}
if
(
back_ref_num
>=
0
&&
back_ref_num
<=
(
int
)
r
.
re_nsub
)
{
int
start_off
,
end_off
;
if
((
start_off
=
subs
[
back_ref_num
].
rm_so
)
>
-
1
&&
(
end_off
=
subs
[
back_ref_num
].
rm_eo
)
>
-
1
)
{
need_buf_len
+=
(
end_off
-
start_off
);
}
expr_p
+=
2
;
}
else
{
expr_p
++
;
need_buf_len
++
;
}
}
need_buf_len
++
;
SECURE_REG_BUF
if
(
subs
[
0
].
rm_so
)
{
memcpy
(
res_p
,
str_p
,
subs
[
0
].
rm_so
);
res_p
+=
subs
[
0
].
rm_so
;
}
expr_p
=
replace
;
while
(
expr_p
<
replace_end
)
{
int
back_ref_num
=
-
1
;
c
=
*
expr_p
;
if
(
c
==
'\\'
&&
expr_p
+
1
<
replace_end
)
{
back_ref_num
=
expr_p
[
1
]
-
'0'
;
}
if
(
back_ref_num
>=
0
&&
back_ref_num
<=
(
int
)
r
.
re_nsub
)
{
int
start_off
,
end_off
;
if
((
start_off
=
subs
[
back_ref_num
].
rm_so
)
>
-
1
&&
(
end_off
=
subs
[
back_ref_num
].
rm_eo
)
>
-
1
)
{
int
block_len
=
end_off
-
start_off
;
memcpy
(
res_p
,
str_p
+
start_off
,
block_len
);
res_p
+=
block_len
;
}
expr_p
+=
2
;
}
else
{
*
res_p
++
=
*
expr_p
++
;
}
}
if
(
subs
[
0
].
rm_so
==
subs
[
0
].
rm_eo
)
{
if
(
str_p
+
subs
[
0
].
rm_so
>=
str_end
)
break
;
str_p
+=
subs
[
0
].
rm_eo
;
*
res_p
++
=
*
str_p
++
;
}
else
{
str_p
+=
subs
[
0
].
rm_eo
;
}
}
else
/* no match this time */
{
int
left_in_str
=
str_end
-
str_p
;
need_buf_len
=
(
res_p
-
buf
)
+
left_in_str
;
SECURE_REG_BUF
memcpy
(
res_p
,
str_p
,
left_in_str
);
res_p
+=
left_in_str
;
str_p
=
str_end
;
}
}
my_regfree
(
&
r
);
*
res_p
=
0
;
*
buf_p
=
buf
;
*
buf_len_p
=
buf_len
;
return
0
;
}
/* Append the string to ds, with optional replace */
...
...
@@ -2999,6 +3368,16 @@ static void replace_dynstr_append_mem(DYNAMIC_STRING *ds, const char *val,
die
(
"Out of memory in replace"
);
val
=
out_buff
;
}
if
(
glob_replace_regex
)
{
if
(
!
multi_reg_replace
(
glob_replace_regex
,(
char
*
)
val
))
{
val
=
glob_replace_regex
->
buf
;
len
=
strlen
(
val
);
}
}
dynstr_append_mem
(
ds
,
val
,
len
);
}
...
...
@@ -3261,6 +3640,7 @@ static int run_query_normal(MYSQL* mysql, struct st_query* q, int flags)
end:
free_replace
();
free_replace_regex
();
last_result
=
0
;
if
(
ds
==
&
ds_tmp
)
dynstr_free
(
&
ds_tmp
);
...
...
@@ -3717,6 +4097,7 @@ static int run_query_stmt(MYSQL *mysql, struct st_query *q, int flags)
end:
free_replace
();
free_replace_regex
();
last_result
=
0
;
if
(
ds
==
&
ds_tmp
)
dynstr_free
(
&
ds_tmp
);
...
...
@@ -4261,6 +4642,10 @@ int main(int argc, char **argv)
case
Q_REPLACE
:
get_replace
(
q
);
break
;
case
Q_REPLACE_REGEX
:
get_replace_regex
(
q
);
break
;
case
Q_REPLACE_COLUMN
:
get_replace_column
(
q
);
break
;
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment