Re: [PATCH v2 10/14] For each exclude pattern, store information about where it came from

2012-12-26 Thread Adam Spiers
On Thu, Sep 20, 2012 at 02:31:57PM -0700, Junio C Hamano wrote:
 Adam Spiers g...@adamspiers.org writes:

   void add_exclude(const char *string, const char *base,
  -int baselen, struct exclude_list *el)
  +int baselen, struct exclude_list *el, const char *src, int 
  srcpos)
   {
  struct exclude *x;
  size_t len;
  @@ -341,6 +341,8 @@ void add_exclude(const char *string, const char *base,
  x-base = base;
  x-baselen = baselen;
  x-flags = flags;
  +   x-src = src;
  +   x-srcpos = srcpos;

 Hrm, don't all elements x in el share the same src, even if
 their srcpos may be different?

No not currently - please see the other mail I just sent to the
[PATCH v2 00/14] thread.
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH v2 10/14] For each exclude pattern, store information about where it came from

2012-09-20 Thread Adam Spiers
For exclude patterns read in from files, the filename is stored together
with the corresponding line number (counting starting at 1).

For exclude patterns provided on the command line, the sequence number
is negative, with counting starting at -1, so for example the 2nd
pattern provided via --exclude would be numbered -2.  This allows any
future consumers of that data to easily distinguish between exclude
patterns from files vs. from the CLI.

Signed-off-by: Adam Spiers g...@adamspiers.org
---
 builtin/clean.c|  2 +-
 builtin/ls-files.c |  3 ++-
 dir.c  | 25 +++--
 dir.h  |  5 -
 4 files changed, 26 insertions(+), 9 deletions(-)

diff --git a/builtin/clean.c b/builtin/clean.c
index 69c1cda..893dd7a 100644
--- a/builtin/clean.c
+++ b/builtin/clean.c
@@ -99,7 +99,7 @@ int cmd_clean(int argc, const char **argv, const char *prefix)
 
for (i = 0; i  exclude_list.nr; i++)
add_exclude(exclude_list.items[i].string, , 0,
-   dir.exclude_list[EXC_CMDL]);
+   dir.exclude_list[EXC_CMDL], --exclude option, 
-(i+1));
 
pathspec = get_pathspec(prefix, argv);
 
diff --git a/builtin/ls-files.c b/builtin/ls-files.c
index d226456..64b1969 100644
--- a/builtin/ls-files.c
+++ b/builtin/ls-files.c
@@ -35,6 +35,7 @@ static int error_unmatch;
 static char *ps_matched;
 static const char *with_tree;
 static int exc_given;
+static int exclude_args;
 
 static const char *tag_cached = ;
 static const char *tag_unmerged = ;
@@ -423,7 +424,7 @@ static int option_parse_exclude(const struct option *opt,
struct exclude_list *list = opt-value;
 
exc_given = 1;
-   add_exclude(arg, , 0, list);
+   add_exclude(arg, , 0, list, --exclude option, --exclude_args);
 
return 0;
 }
diff --git a/dir.c b/dir.c
index 904a7f3..705546f 100644
--- a/dir.c
+++ b/dir.c
@@ -311,7 +311,7 @@ static int no_wildcard(const char *string)
 }
 
 void add_exclude(const char *string, const char *base,
-int baselen, struct exclude_list *el)
+int baselen, struct exclude_list *el, const char *src, int 
srcpos)
 {
struct exclude *x;
size_t len;
@@ -341,6 +341,8 @@ void add_exclude(const char *string, const char *base,
x-base = base;
x-baselen = baselen;
x-flags = flags;
+   x-src = src;
+   x-srcpos = srcpos;
if (!strchr(string, '/'))
x-flags |= EXC_FLAG_NODIR;
x-nowildcardlen = simple_length(string);
@@ -393,7 +395,7 @@ int add_excludes_from_file_to_list(const char *fname,
   int check_index)
 {
struct stat st;
-   int fd, i;
+   int fd, i, lineno = 1;
size_t size = 0;
char *buf, *entry;
 
@@ -438,8 +440,9 @@ int add_excludes_from_file_to_list(const char *fname,
if (buf[i] == '\n') {
if (entry != buf + i  entry[0] != '#') {
buf[i - (i  buf[i-1] == '\r')] = 0;
-   add_exclude(entry, base, baselen, el);
+   add_exclude(entry, base, baselen, el, fname, 
lineno);
}
+   lineno++;
entry = buf + i + 1;
}
}
@@ -474,8 +477,10 @@ static void prep_exclude(struct dir_struct *dir, const 
char *base, int baselen)
!strncmp(dir-basebuf, base, stk-baselen))
break;
dir-exclude_stack = stk-prev;
-   while (stk-exclude_ix  el-nr)
-   free(el-excludes[--el-nr]);
+   while (stk-exclude_ix  el-nr) {
+   struct exclude *exclude = el-excludes[--el-nr];
+   free(exclude);
+   }
free(stk-filebuf);
free(stk);
}
@@ -502,7 +507,15 @@ static void prep_exclude(struct dir_struct *dir, const 
char *base, int baselen)
memcpy(dir-basebuf + current, base + current,
   stk-baselen - current);
strcpy(dir-basebuf + stk-baselen, dir-exclude_per_dir);
-   add_excludes_from_file_to_list(dir-basebuf,
+
+   /* dir-basebuf gets reused by the traversal, but we
+* need fname to remain unchanged to ensure the src
+* member of each struct exclude correctly back-references
+* its source file.
+*/
+   char *fname = strdup(dir-basebuf);
+
+   add_excludes_from_file_to_list(fname,
   dir-basebuf, stk-baselen,
   stk-filebuf, el, 1);
dir-exclude_stack = stk;
diff --git a/dir.h b/dir.h
index 19beddb..ebb0367 100644
--- a/dir.h
+++ b/dir.h
@@ -31,6 +31,9 @@ struct exclude_list {
int baselen;
 

Re: [PATCH v2 10/14] For each exclude pattern, store information about where it came from

2012-09-20 Thread Junio C Hamano
Adam Spiers g...@adamspiers.org writes:

  void add_exclude(const char *string, const char *base,
 -  int baselen, struct exclude_list *el)
 +  int baselen, struct exclude_list *el, const char *src, int 
 srcpos)
  {
   struct exclude *x;
   size_t len;
 @@ -341,6 +341,8 @@ void add_exclude(const char *string, const char *base,
   x-base = base;
   x-baselen = baselen;
   x-flags = flags;
 + x-src = src;
 + x-srcpos = srcpos;

Hrm, don't all elements x in el share the same src, even if
their srcpos may be different?

   if (!strchr(string, '/'))
   x-flags |= EXC_FLAG_NODIR;
   x-nowildcardlen = simple_length(string);
 @@ -393,7 +395,7 @@ int add_excludes_from_file_to_list(const char *fname,
  int check_index)
  {
   struct stat st;
 - int fd, i;
 + int fd, i, lineno = 1;
   size_t size = 0;
   char *buf, *entry;
  
 @@ -438,8 +440,9 @@ int add_excludes_from_file_to_list(const char *fname,
   if (buf[i] == '\n') {
   if (entry != buf + i  entry[0] != '#') {
   buf[i - (i  buf[i-1] == '\r')] = 0;
 - add_exclude(entry, base, baselen, el);
 + add_exclude(entry, base, baselen, el, fname, 
 lineno);
   }
 + lineno++;
   entry = buf + i + 1;
   }
   }
 @@ -474,8 +477,10 @@ static void prep_exclude(struct dir_struct *dir, const 
 char *base, int baselen)
   !strncmp(dir-basebuf, base, stk-baselen))
   break;
   dir-exclude_stack = stk-prev;
 - while (stk-exclude_ix  el-nr)
 - free(el-excludes[--el-nr]);
 + while (stk-exclude_ix  el-nr) {
 + struct exclude *exclude = el-excludes[--el-nr];
 + free(exclude);
 + }
   free(stk-filebuf);
   free(stk);
   }
 @@ -502,7 +507,15 @@ static void prep_exclude(struct dir_struct *dir, const 
 char *base, int baselen)
   memcpy(dir-basebuf + current, base + current,
  stk-baselen - current);
   strcpy(dir-basebuf + stk-baselen, dir-exclude_per_dir);
 - add_excludes_from_file_to_list(dir-basebuf,
 +
 + /* dir-basebuf gets reused by the traversal, but we
 +  * need fname to remain unchanged to ensure the src
 +  * member of each struct exclude correctly back-references
 +  * its source file.
 +  */
 + char *fname = strdup(dir-basebuf);


/*
 * We try to format our multi-line comments
 * like this.
 *
 * By the way, who owns x-src and who is responsible for
 * freeing it when the exclude-stack is popped to make them
 * no longer necessary?
 *
 * Oh, by the way, that is a decl-after-statement.
 */

 +
 + add_excludes_from_file_to_list(fname,
  dir-basebuf, stk-baselen,
  stk-filebuf, el, 1);
   dir-exclude_stack = stk;
 diff --git a/dir.h b/dir.h
 index 19beddb..ebb0367 100644
 --- a/dir.h
 +++ b/dir.h
 @@ -31,6 +31,9 @@ struct exclude_list {
   int baselen;
   int to_exclude;
   int flags;
 + const char *src;
 + int srcpos; /* counting starts from 1 for line numbers in 
 ignore files,
 +and from -1 decrementing for patterns from CLI 
 (--exclude) */
   } **excludes;
  };
  
 @@ -123,7 +126,7 @@ extern int add_excludes_from_file_to_list(const char 
 *fname, const char *base, i
 char **buf_p, struct exclude_list 
 *el, int check_index);
  extern void add_excludes_from_file(struct dir_struct *, const char *fname);
  extern void add_exclude(const char *string, const char *base,
 - int baselen, struct exclude_list *el);
 + int baselen, struct exclude_list *el, const char *src, 
 int srcpos);
  extern void free_excludes(struct exclude_list *el);
  extern int file_exists(const char *);
--
To unsubscribe from this list: send the line unsubscribe git in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html