Skip to content

Commit 24e4750

Browse files
SyntevoAlexdscho
authored andcommitted
pathspec: add new function to parse file
This will be used to support the new option '--pathspec-from-file' in `git add`, `git-commit`, `git reset` etc. Note also that we specifically handle CR/LF line endings to support Windows better. To simplify code, file is first parsed into `argv_array`. This allows to avoid refactoring `parse_pathspec()`. I considered adding `nul_term_line` to `flags` instead, but decided that it doesn't fit there. The new code is mostly taken from `cmd_update_index()` and `split_mail_conv()`. Co-authored-by: Johannes Schindelin <[email protected]> Signed-off-by: Alexandr Miloslavskiy <[email protected]> Signed-off-by: Junio C Hamano <[email protected]>
1 parent add9770 commit 24e4750

File tree

2 files changed

+48
-0
lines changed

2 files changed

+48
-0
lines changed

pathspec.c

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
#include "dir.h"
44
#include "pathspec.h"
55
#include "attr.h"
6+
#include "argv-array.h"
7+
#include "quote.h"
68

79
/*
810
* Finds which of the given pathspecs match items in the index.
@@ -613,6 +615,42 @@ void parse_pathspec(struct pathspec *pathspec,
613615
}
614616
}
615617

618+
void parse_pathspec_file(struct pathspec *pathspec, unsigned magic_mask,
619+
unsigned flags, const char *prefix,
620+
const char *file, int nul_term_line)
621+
{
622+
struct argv_array parsed_file = ARGV_ARRAY_INIT;
623+
strbuf_getline_fn getline_fn = nul_term_line ? strbuf_getline_nul :
624+
strbuf_getline;
625+
struct strbuf buf = STRBUF_INIT;
626+
struct strbuf unquoted = STRBUF_INIT;
627+
FILE *in;
628+
629+
if (!strcmp(file, "-"))
630+
in = stdin;
631+
else
632+
in = xfopen(file, "r");
633+
634+
while (getline_fn(&buf, in) != EOF) {
635+
if (!nul_term_line && buf.buf[0] == '"') {
636+
strbuf_reset(&unquoted);
637+
if (unquote_c_style(&unquoted, buf.buf, NULL))
638+
die(_("line is badly quoted: %s"), buf.buf);
639+
strbuf_swap(&buf, &unquoted);
640+
}
641+
argv_array_push(&parsed_file, buf.buf);
642+
strbuf_reset(&buf);
643+
}
644+
645+
strbuf_release(&unquoted);
646+
strbuf_release(&buf);
647+
if (in != stdin)
648+
fclose(in);
649+
650+
parse_pathspec(pathspec, magic_mask, flags, prefix, parsed_file.argv);
651+
argv_array_clear(&parsed_file);
652+
}
653+
616654
void copy_pathspec(struct pathspec *dst, const struct pathspec *src)
617655
{
618656
int i, j;

pathspec.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,16 @@ void parse_pathspec(struct pathspec *pathspec,
8585
unsigned flags,
8686
const char *prefix,
8787
const char **args);
88+
/*
89+
* Same as parse_pathspec() but uses file as input.
90+
* When 'file' is exactly "-" it uses 'stdin' instead.
91+
*/
92+
void parse_pathspec_file(struct pathspec *pathspec,
93+
unsigned magic_mask,
94+
unsigned flags,
95+
const char *prefix,
96+
const char *file,
97+
int nul_term_line);
8898
void copy_pathspec(struct pathspec *dst, const struct pathspec *src);
8999
void clear_pathspec(struct pathspec *);
90100

0 commit comments

Comments
 (0)