OSDN Git Service

grep: honor --textconv for the case rev:path
authorMichael J Gruber <git@drmicha.warpmail.net>
Fri, 10 May 2013 15:10:16 +0000 (17:10 +0200)
committerJunio C Hamano <gitster@pobox.com>
Fri, 10 May 2013 17:27:34 +0000 (10:27 -0700)
Make "grep" honor the "--textconv" option also for the object case, i.e.
when used with an argument "rev:path".

Signed-off-by: Michael J Gruber <git@drmicha.warpmail.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
builtin/grep.c
object.c
object.h
t/t7008-grep-binary.sh

index 00ee57d..bb7f970 100644 (file)
@@ -458,10 +458,10 @@ static int grep_tree(struct grep_opt *opt, const struct pathspec *pathspec,
 }
 
 static int grep_object(struct grep_opt *opt, const struct pathspec *pathspec,
-                      struct object *obj, const char *name)
+                      struct object *obj, const char *name, struct object_context *oc)
 {
        if (obj->type == OBJ_BLOB)
-               return grep_sha1(opt, obj->sha1, name, 0, NULL);
+               return grep_sha1(opt, obj->sha1, name, 0, oc ? oc->path : NULL);
        if (obj->type == OBJ_COMMIT || obj->type == OBJ_TREE) {
                struct tree_desc tree;
                void *data;
@@ -503,7 +503,7 @@ static int grep_objects(struct grep_opt *opt, const struct pathspec *pathspec,
        for (i = 0; i < nr; i++) {
                struct object *real_obj;
                real_obj = deref_tag(list->objects[i].item, NULL, 0);
-               if (grep_object(opt, pathspec, real_obj, list->objects[i].name)) {
+               if (grep_object(opt, pathspec, real_obj, list->objects[i].name, list->objects[i].context)) {
                        hit = 1;
                        if (opt->status_only)
                                break;
@@ -820,12 +820,13 @@ int cmd_grep(int argc, const char **argv, const char *prefix)
        for (i = 0; i < argc; i++) {
                const char *arg = argv[i];
                unsigned char sha1[20];
+               struct object_context oc;
                /* Is it a rev? */
-               if (!get_sha1(arg, sha1)) {
+               if (!get_sha1_with_context(arg, 0, sha1, &oc)) {
                        struct object *object = parse_object_or_die(sha1, arg);
                        if (!seen_dashdash)
                                verify_non_filename(prefix, arg);
-                       add_object_array(object, arg, &list);
+                       add_object_array_with_context(object, arg, &list, xmemdupz(&oc, sizeof(struct object_context)));
                        continue;
                }
                if (!strcmp(arg, "--")) {
index 20703f5..c8ffc9e 100644 (file)
--- a/object.c
+++ b/object.c
@@ -255,12 +255,7 @@ int object_list_contains(struct object_list *list, struct object *obj)
        return 0;
 }
 
-void add_object_array(struct object *obj, const char *name, struct object_array *array)
-{
-       add_object_array_with_mode(obj, name, array, S_IFINVALID);
-}
-
-void add_object_array_with_mode(struct object *obj, const char *name, struct object_array *array, unsigned mode)
+static void add_object_array_with_mode_context(struct object *obj, const char *name, struct object_array *array, unsigned mode, struct object_context *context)
 {
        unsigned nr = array->nr;
        unsigned alloc = array->alloc;
@@ -275,9 +270,28 @@ void add_object_array_with_mode(struct object *obj, const char *name, struct obj
        objects[nr].item = obj;
        objects[nr].name = name;
        objects[nr].mode = mode;
+       objects[nr].context = context;
        array->nr = ++nr;
 }
 
+void add_object_array(struct object *obj, const char *name, struct object_array *array)
+{
+       add_object_array_with_mode(obj, name, array, S_IFINVALID);
+}
+
+void add_object_array_with_mode(struct object *obj, const char *name, struct object_array *array, unsigned mode)
+{
+       add_object_array_with_mode_context(obj, name, array, mode, NULL);
+}
+
+void add_object_array_with_context(struct object *obj, const char *name, struct object_array *array, struct object_context *context)
+{
+       if (context)
+               add_object_array_with_mode_context(obj, name, array, context->mode, context);
+       else
+               add_object_array_with_mode_context(obj, name, array, S_IFINVALID, context);
+}
+
 void object_array_remove_duplicates(struct object_array *array)
 {
        unsigned int ref, src, dst;
index 97d384b..695847d 100644 (file)
--- a/object.h
+++ b/object.h
@@ -13,6 +13,7 @@ struct object_array {
                struct object *item;
                const char *name;
                unsigned mode;
+               struct object_context *context;
        } *objects;
 };
 
@@ -85,6 +86,7 @@ int object_list_contains(struct object_list *list, struct object *obj);
 /* Object array handling .. */
 void add_object_array(struct object *obj, const char *name, struct object_array *array);
 void add_object_array_with_mode(struct object *obj, const char *name, struct object_array *array, unsigned mode);
+void add_object_array_with_context(struct object *obj, const char *name, struct object_array *array, struct object_context *context);
 void object_array_remove_duplicates(struct object_array *);
 
 void clear_object_flags(unsigned flags);
index a91260a..b146406 100755 (executable)
@@ -170,14 +170,10 @@ test_expect_success 'grep --no-textconv does not honor textconv' '
        test_must_fail git grep --no-textconv Qfile
 '
 
-test_expect_failure 'grep --textconv blob honors textconv' '
+test_expect_success 'grep --textconv blob honors textconv' '
        echo "HEAD:a:binaryQfile" >expect &&
        git grep --textconv Qfile HEAD:a >actual &&
        test_cmp expect actual
 '
 
-test_expect_success 'grep --no-textconv blob does not honor textconv' '
-       test_must_fail git grep --no-textconv Qfile HEAD:a
-'
-
 test_done