Merge branch 'bw/attr-pathspec'
The pathspec mechanism learned to further limit the paths that match the pattern to those that have specified attributes attached via the gitattributes mechanism. * bw/attr-pathspec: pathspec: allow escaped query values pathspec: allow querying for attributes
This commit is contained in:
43
dir.c
43
dir.c
@ -9,6 +9,7 @@
|
||||
*/
|
||||
#include "cache.h"
|
||||
#include "dir.h"
|
||||
#include "attr.h"
|
||||
#include "refs.h"
|
||||
#include "wildmatch.h"
|
||||
#include "pathspec.h"
|
||||
@ -134,7 +135,8 @@ static size_t common_prefix_len(const struct pathspec *pathspec)
|
||||
PATHSPEC_LITERAL |
|
||||
PATHSPEC_GLOB |
|
||||
PATHSPEC_ICASE |
|
||||
PATHSPEC_EXCLUDE);
|
||||
PATHSPEC_EXCLUDE |
|
||||
PATHSPEC_ATTR);
|
||||
|
||||
for (n = 0; n < pathspec->nr; n++) {
|
||||
size_t i = 0, len = 0, item_len;
|
||||
@ -209,6 +211,36 @@ int within_depth(const char *name, int namelen,
|
||||
#define DO_MATCH_DIRECTORY (1<<1)
|
||||
#define DO_MATCH_SUBMODULE (1<<2)
|
||||
|
||||
static int match_attrs(const char *name, int namelen,
|
||||
const struct pathspec_item *item)
|
||||
{
|
||||
int i;
|
||||
|
||||
git_check_attr(name, item->attr_check);
|
||||
for (i = 0; i < item->attr_match_nr; i++) {
|
||||
const char *value;
|
||||
int matched;
|
||||
enum attr_match_mode match_mode;
|
||||
|
||||
value = item->attr_check->items[i].value;
|
||||
match_mode = item->attr_match[i].match_mode;
|
||||
|
||||
if (ATTR_TRUE(value))
|
||||
matched = (match_mode == MATCH_SET);
|
||||
else if (ATTR_FALSE(value))
|
||||
matched = (match_mode == MATCH_UNSET);
|
||||
else if (ATTR_UNSET(value))
|
||||
matched = (match_mode == MATCH_UNSPECIFIED);
|
||||
else
|
||||
matched = (match_mode == MATCH_VALUE &&
|
||||
!strcmp(item->attr_match[i].value, value));
|
||||
if (!matched)
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Does 'match' match the given name?
|
||||
* A match is found if
|
||||
@ -261,6 +293,9 @@ static int match_pathspec_item(const struct pathspec_item *item, int prefix,
|
||||
strncmp(item->match, name - prefix, item->prefix))
|
||||
return 0;
|
||||
|
||||
if (item->attr_match_nr && !match_attrs(name, namelen, item))
|
||||
return 0;
|
||||
|
||||
/* If the match was just the prefix, we matched */
|
||||
if (!*match)
|
||||
return MATCHED_RECURSIVELY;
|
||||
@ -339,7 +374,8 @@ static int do_match_pathspec(const struct pathspec *ps,
|
||||
PATHSPEC_LITERAL |
|
||||
PATHSPEC_GLOB |
|
||||
PATHSPEC_ICASE |
|
||||
PATHSPEC_EXCLUDE);
|
||||
PATHSPEC_EXCLUDE |
|
||||
PATHSPEC_ATTR);
|
||||
|
||||
if (!ps->nr) {
|
||||
if (!ps->recursive ||
|
||||
@ -1361,7 +1397,8 @@ static int simplify_away(const char *path, int pathlen,
|
||||
PATHSPEC_LITERAL |
|
||||
PATHSPEC_GLOB |
|
||||
PATHSPEC_ICASE |
|
||||
PATHSPEC_EXCLUDE);
|
||||
PATHSPEC_EXCLUDE |
|
||||
PATHSPEC_ATTR);
|
||||
|
||||
for (i = 0; i < pathspec->nr; i++) {
|
||||
const struct pathspec_item *item = &pathspec->items[i];
|
||||
|
Reference in New Issue
Block a user