зеркало из https://github.com/microsoft/git.git
grep: don't call regexec() for fixed strings
Add the new flag "fixed" to struct grep_pat and set it if the pattern is doesn't contain any regex control characters in addition to if the flag -F/--fixed-strings was specified. This gives a nice speed up on msysgit, where regexec() seems to be extra slow. Before (best of five runs): $ time git grep grep v1.6.1 >/dev/null real 0m0.552s user 0m0.000s sys 0m0.000s $ time git grep -F grep v1.6.1 >/dev/null real 0m0.170s user 0m0.000s sys 0m0.015s With the patch: $ time git grep grep v1.6.1 >/dev/null real 0m0.173s user 0m0.000s sys 0m0.000s The difference is much smaller on Linux, but still measurable. Signed-off-by: Rene Scharfe <rene.scharfe@lsrfire.ath.cx> Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Родитель
fb62eb7fab
Коммит
c822255cfc
29
grep.c
29
grep.c
|
@ -28,9 +28,31 @@ void append_grep_pattern(struct grep_opt *opt, const char *pat,
|
|||
p->next = NULL;
|
||||
}
|
||||
|
||||
static int isregexspecial(int c)
|
||||
{
|
||||
return isspecial(c) || c == '$' || c == '(' || c == ')' || c == '+' ||
|
||||
c == '.' || c == '^' || c == '{' || c == '|';
|
||||
}
|
||||
|
||||
static int is_fixed(const char *s)
|
||||
{
|
||||
while (!isregexspecial(*s))
|
||||
s++;
|
||||
return !*s;
|
||||
}
|
||||
|
||||
static void compile_regexp(struct grep_pat *p, struct grep_opt *opt)
|
||||
{
|
||||
int err = regcomp(&p->regexp, p->pattern, opt->regflags);
|
||||
int err;
|
||||
|
||||
if (opt->fixed || is_fixed(p->pattern))
|
||||
p->fixed = 1;
|
||||
if (opt->regflags & REG_ICASE)
|
||||
p->fixed = 0;
|
||||
if (p->fixed)
|
||||
return;
|
||||
|
||||
err = regcomp(&p->regexp, p->pattern, opt->regflags);
|
||||
if (err) {
|
||||
char errbuf[1024];
|
||||
char where[1024];
|
||||
|
@ -159,8 +181,7 @@ void compile_grep_patterns(struct grep_opt *opt)
|
|||
case GREP_PATTERN: /* atom */
|
||||
case GREP_PATTERN_HEAD:
|
||||
case GREP_PATTERN_BODY:
|
||||
if (!opt->fixed)
|
||||
compile_regexp(p, opt);
|
||||
compile_regexp(p, opt);
|
||||
break;
|
||||
default:
|
||||
opt->extended = 1;
|
||||
|
@ -314,7 +335,7 @@ static int match_one_pattern(struct grep_opt *opt, struct grep_pat *p, char *bol
|
|||
}
|
||||
|
||||
again:
|
||||
if (!opt->fixed) {
|
||||
if (!p->fixed) {
|
||||
regex_t *exp = &p->regexp;
|
||||
hit = !regexec(exp, bol, ARRAY_SIZE(pmatch),
|
||||
pmatch, 0);
|
||||
|
|
1
grep.h
1
grep.h
|
@ -30,6 +30,7 @@ struct grep_pat {
|
|||
const char *pattern;
|
||||
enum grep_header_field field;
|
||||
regex_t regexp;
|
||||
unsigned fixed:1;
|
||||
};
|
||||
|
||||
enum grep_expr_node {
|
||||
|
|
Загрузка…
Ссылка в новой задаче