* Re: [PATCH] Remove gitenv macro hack
From: Junio C Hamano @ 2005-05-19 23:41 UTC (permalink / raw)
To: Dan Weber; +Cc: Git Mailing List
In-Reply-To: <Pine.LNX.4.62.0505191800280.16809@mirrorlynx.com>
Please do not do this.
I believe we have that in quite a few places. IIRC, it is one
of the Linus-approved GCC extensions and also used extensively
in the kernel source.
./cache.h:39:#define gitenv(e) (getenv(e) ? : gitenv_bc(e))
./commit-tree.c:149: commitgecos = gitenv("GIT_COMMITTER_NAME") ? : realgecos;
./commit-tree.c:150: commitemail = gitenv("GIT_COMMITTER_EMAIL") ? : realemail;
./commit-tree.c:151: gecos = gitenv("GIT_AUTHOR_NAME") ? : realgecos;
./commit-tree.c:152: email = gitenv("GIT_AUTHOR_EMAIL") ? : realemail;
./fsck-cache.c:359: char *git_dir = gitenv(GIT_DIR_ENVIRONMENT) ? : DEFAULT_GIT_DIR_ENVIRONMENT;
./diff.c:35: diff_opts = gitenv("GIT_DIFF_OPTS") ? : diff_opts;
./diff.c:358: prepare_temp_file(other ? : name, &temp[1], two);
./diff.c:398: builtin_diff(name, other ? : name, temp);
./diff.c:717: diff_rename_minimum_score = minimum_score_ ? : MINIMUM_SCORE;
./sha1_file.c:203: const char *alt = gitenv(ALTERNATE_DB_ENVIRONMENT) ? : "";
./sha1_file.c:215: cp = strchr(last, ':') ? : last + strlen(last);
^ permalink raw reply
* Re: [PATCH] Detect renames in diff family.
From: Junio C Hamano @ 2005-05-19 23:32 UTC (permalink / raw)
To: Linus Torvalds; +Cc: Nicolas Pitre, git
In-Reply-To: <Pine.LNX.4.58.0505191516350.2322@ppc970.osdl.org>
Not quite a related topic, but unless we start to support the
copy detection you recommended against, my understanding is that
-M does not do anything useful for git-diff-files. Is there a
good use case for it? I am not advocating for its removal so
please leave the command line option there.
^ permalink raw reply
* Re: gitk-1.0 released
From: Benjamin Herrenschmidt @ 2005-05-19 23:13 UTC (permalink / raw)
To: Paul Mackerras; +Cc: git
In-Reply-To: <17036.36624.911071.810357@cargo.ozlabs.ibm.com>
On Thu, 2005-05-19 at 23:05 +1000, Paul Mackerras wrote:
> I have released a new version of gitk. I got brave and called it 1.0
> and it is at:
>
> http://ozlabs.org/~paulus/gitk-1.0
>
> (that's the actual script itself).
>
> Gitk is a git commit viewer with the following features:
>
> * Clear and compact representation of the commit graph
> * Displays headline, author and date of each commit in the
> summary window
> * Displays the full details of one commit - the comments,
> list of files and colorized diff - in the details window
> * Find function for searching through commits
> * Displays the SHA1 ID of the selected commit and makes it
> the X selection so it can be pasted into other windows
> * Convenient key bindings for scanning through each commit
> in turn
Cool !
Here's a feature request though: beeing able to type/paste a SHA1 in the
SHA1 ID field to "jump" to that commit :)
Ben.
^ permalink raw reply
* Re: [PATCH] Detect renames in diff family.
From: Linus Torvalds @ 2005-05-20 0:10 UTC (permalink / raw)
To: Junio C Hamano; +Cc: Nicolas Pitre, git
In-Reply-To: <7vhdgyyeom.fsf@assigned-by-dhcp.cox.net>
On Thu, 19 May 2005, Junio C Hamano wrote:
>
> Not quite a related topic, but unless we start to support the
> copy detection you recommended against, my understanding is that
> -M does not do anything useful for git-diff-files. Is there a
> good use case for it? I am not advocating for its removal so
> please leave the command line option there.
Hmm.. You're right, but it feels kind of wrong. Clearly we support
removals in diff-files, but you're right, we can never have something show
up as an addition, since we only ever compare against files that are
already mentioned in the cache.
On the other hand, a unmerged entry really _could_ be a new file, could it
not? Even if we right now always report it as "Unmerged path"? If it's a
case of existing in stage 2/3 only, it really should show up as a new file
diff for git-diff-files, no?
Or am I just being confused and/or stupid?
Linus
^ permalink raw reply
* Re: [PATCH] Detect renames in diff family.
From: Junio C Hamano @ 2005-05-20 0:48 UTC (permalink / raw)
To: Linus Torvalds; +Cc: git
In-Reply-To: <Pine.LNX.4.58.0505191656310.2322@ppc970.osdl.org>
>>>>> "LT" == Linus Torvalds <torvalds@osdl.org> writes:
LT> Hmm.. You're right, but it feels kind of wrong. Clearly we
LT> support removals in diff-files, but you're right, we can
LT> never have something show up as an addition, since we only
LT> ever compare against files that are already mentioned in the
LT> cache.
LT> Or am I just being confused and/or stupid?
No, you are not confused nor stupid. We discussed something
related to this about three weeks ago. We ended up not doing
what we discussed, but if we had adopted the convention of the
delayed addition to the cache I described as "magic SHA1" in the
quoted message below, that would have been the "intent to add"
that diff-files would report as an addition.
To: Linus Torvalds <torvalds@osdl.org>
Cc: git@vger.kernel.org
Subject: Re: [PATCH] Really fix git-merge-one-file-script this time.
From: Junio C Hamano <junkio@cox.net>
Date: Sun, 01 May 2005 11:38:15 -0700
Message-ID: <7vzmveu6zs.fsf@assigned-by-dhcp.cox.net>
(... some discussion omitted ...)
I am wondering if the following changes would make sense and
make things easier for you:
* git-merge-one-file-script is changed to register the path
with --cacheinfo using magic SHA1 0{40} instead of using the
resulting file on the filesystem. Do keep the current
behaviour of leaving the merge results of trivial merges
(both kind) in the work tree.
* git-write-tree is changed to refuse to write from a cache
that records the magic SHA1.
* git-ls-files acquires a new option --merged to notice the
magic SHA1 and shows the paths that have such SHA1.
* git-update-cache acquires a new option --resolve to notice
the magic SHA1 and:
- if the named path is not in the work tree anymore, delete
the entry.
- if the named path exists in the work tree, compute the
latest SHA1 for that file and update the entry.
Changes other than the first two listed above are purely
optional, since the Porcelain layer can implement them without
the Plumbing support. Not doing them would keep the Plumbing
somewhat cleaner by not having to know about this magic SHA1
convention. On the other hand, we already use that convention
in git-diff-cache, so it may even be a consistent change to make
these optional changes. Essentially, the magic SHA1 in the
cache means "I know the user wants me to keep an eye on this
path when it matters" [*2*].
[Footnotes]
(... footnote *1* omitted ...)
*2* This convention would also make an implementation of "SCM
add" in the Porcelain layer a bit more efficient. A typical
workflow without such a convention would consist of:
* Create a file and start editing.
* "SCM add" file, causing "git-update-cache --add -- file".
* Do more changes, and review.
* "SCM commit" which does"git-update-cache" changed files,
"git-write-tree" and "git-commit-tree" to commit.
which wastes one extra blob object per "SCM add". My gut
feeling is that more than 80% of the time "SCM add" is followed
by some edit to the added file before "SCM commit", unless it is
the initial import. If we adopt that convention, "SCM add"
would register with --cacheinfo with the magic SHA1 without
creating the useless blob, and "SCM commit" will be written to
lazily pick things up from the work tree.
^ permalink raw reply
* Re: gitk-1.0 released
From: walt @ 2005-05-20 1:10 UTC (permalink / raw)
To: git
In-Reply-To: <17036.36624.911071.810357@cargo.ozlabs.ibm.com>
Paul Mackerras wrote:
> I have released a new version of gitk. I got brave and called it 1.0
> and it is at:
>
> http://ozlabs.org/~paulus/gitk-1.0
.
.
.
Today, gitk works beautifully for me. Yesterday, though, I had a weird
first experience when it opened a very attractive tcl/tk interface which
displayed no text of any kind. I tried fiddling with the two menus you
provide, bit still no success.
I finally just gave up. When I tried gitk again today -- it was magic!
All the kernel tree appeared just as (I suppose) you intended.
As far as I know, I did nothing to change anything since yesterday.
Can you venture a guess why I had sucess today and failure yesterday?
Does gitk perhaps depend on a generated database of some kind before
it will work properly?
^ permalink raw reply
* [PATCH] diff overhaul
From: Junio C Hamano @ 2005-05-20 2:00 UTC (permalink / raw)
To: torvalds; +Cc: git
Diff overhaul.
This patch cleans up the way calls are made into the diff core
from diff-tree family and diff-helper. Earlier, these programs
had "if (generating_patch)" sprinkled all over the place, but
those ugliness are gone and handled uniformly from the diff
core, even when not generating patch format.
This also allowed diff-cache and diff-files to acquire -R
(reverse) option to generate diff in reverse. Users of
diff-tree can swap two trees easily so I did not add -R there.
Also -M<digits-as-mantissa> suggestion made by Linus has been
implemented.
It also fixes minor permission problems with some of the test
scripts (although it should not matter since they are explicitly
run by being the first argument to "sh"), but this being a patch
that may not convey well.
Documentation updates are also included.
Signed-off-by: Junio C Hamano <junkio@cox.net>
---
Documentation/git-diff-cache.txt | 5 +
Documentation/git-diff-files.txt | 5 +
diff-cache.c | 42 ++++-------
diff-files.c | 44 ++++--------
diff-helper.c | 19 +++--
diff-tree.c | 46 ++++--------
diff.c | 142 +++++++++++++++++++++++++++++++--------
diff.h | 4 -
t/t0000-basic.sh | 2
t/t2002-checkout-cache-u.sh | 2
t/t4001-diff-rename.sh | 6 +
11 files changed, 192 insertions(+), 125 deletions(-)
mode changed (100644 --> 100755): t/t0110-environment-names-old.sh
mode changed (100644 --> 100755): t/t1000-read-tree-m-3way.sh
mode changed (100644 --> 100755): t/t2002-checkout-cache-u.sh
mode changed (100644 --> 100755): t/t4000-diff-format.sh
mode changed (100644 --> 100755): t/t4001-diff-rename.sh
diff --git a/Documentation/git-diff-cache.txt b/Documentation/git-diff-cache.txt
--- a/Documentation/git-diff-cache.txt
+++ b/Documentation/git-diff-cache.txt
@@ -9,7 +9,7 @@ git-diff-cache - Compares content and mo
SYNOPSIS
--------
-'git-diff-cache' [-p] [-r] [-z] [-m] [-M] [--cached] <tree-ish>
+'git-diff-cache' [-p] [-r] [-z] [-m] [-M] [-R] [--cached] <tree-ish>
DESCRIPTION
-----------
@@ -36,6 +36,9 @@ OPTIONS
-M::
Detect renames; implies -p.
+-R::
+ Output diff in reverse.
+
--cached::
do not consider the on-disk file at all
diff --git a/Documentation/git-diff-files.txt b/Documentation/git-diff-files.txt
--- a/Documentation/git-diff-files.txt
+++ b/Documentation/git-diff-files.txt
@@ -9,7 +9,7 @@ git-diff-files - Compares files in the w
SYNOPSIS
--------
-'git-diff-files' [-p] [-q] [-r] [-z] [-M] [<pattern>...]
+'git-diff-files' [-p] [-q] [-r] [-z] [-M] [-R] [<pattern>...]
DESCRIPTION
-----------
@@ -26,6 +26,9 @@ OPTIONS
-q::
Remain silent even on nonexisting files
+-R::
+ Output diff in reverse.
+
-M::
Detect renames; implies -p.
diff --git a/diff-cache.c b/diff-cache.c
--- a/diff-cache.c
+++ b/diff-cache.c
@@ -6,15 +6,13 @@ static int generate_patch = 0;
static int match_nonexisting = 0;
static int line_termination = '\n';
static int detect_rename = 0;
+static int reverse_diff = 0;
+static int diff_score_opt = 0;
/* A file entry went away or appeared */
static void show_file(const char *prefix, struct cache_entry *ce, unsigned char *sha1, unsigned int mode)
{
- if (generate_patch)
- diff_addremove(prefix[0], ntohl(mode), sha1, ce->name, NULL);
- else
- printf("%s%06o\tblob\t%s\t%s%c", prefix, ntohl(mode),
- sha1_to_hex(sha1), ce->name, line_termination);
+ diff_addremove(prefix[0], ntohl(mode), sha1, ce->name, NULL);
}
static int get_stat_data(struct cache_entry *ce, unsigned char **sha1p, unsigned int *modep)
@@ -64,7 +62,6 @@ static int show_modified(struct cache_en
{
unsigned int mode, oldmode;
unsigned char *sha1;
- char old_sha1_hex[60];
if (get_stat_data(new, &sha1, &mode) < 0) {
if (report_missing)
@@ -79,15 +76,8 @@ static int show_modified(struct cache_en
mode = ntohl(mode);
oldmode = ntohl(oldmode);
- if (generate_patch)
- diff_change(oldmode, mode,
- old->sha1, sha1, old->name, NULL);
- else {
- strcpy(old_sha1_hex, sha1_to_hex(old->sha1));
- printf("*%06o->%06o\tblob\t%s->%s\t%s%c", oldmode, mode,
- old_sha1_hex, sha1_to_hex(sha1),
- old->name, line_termination);
- }
+ diff_change(oldmode, mode,
+ old->sha1, sha1, old->name, NULL);
return 0;
}
@@ -127,10 +117,7 @@ static int diff_cache(struct cache_entry
break;
/* fallthru */
case 3:
- if (generate_patch)
- diff_unmerge(ce->name);
- else
- printf("U %s%c", ce->name, line_termination);
+ diff_unmerge(ce->name);
break;
default:
@@ -166,7 +153,7 @@ static void mark_merge_entries(void)
}
static char *diff_cache_usage =
-"git-diff-cache [-p] [-r] [-z] [-m] [-M] [--cached] <tree-ish>";
+"git-diff-cache [-p] [-r] [-z] [-m] [-M] [-R] [--cached] <tree-ish>";
int main(int argc, char **argv)
{
@@ -188,14 +175,19 @@ int main(int argc, char **argv)
generate_patch = 1;
continue;
}
- if (!strcmp(arg, "-M")) {
+ if (!strncmp(arg, "-M", 2)) {
generate_patch = detect_rename = 1;
+ diff_score_opt = diff_scoreopt_parse(arg);
continue;
}
if (!strcmp(arg, "-z")) {
line_termination = '\0';
continue;
}
+ if (!strcmp(arg, "-R")) {
+ reverse_diff = 1;
+ continue;
+ }
if (!strcmp(arg, "-m")) {
match_nonexisting = 1;
continue;
@@ -210,8 +202,9 @@ int main(int argc, char **argv)
if (argc != 2 || get_sha1(argv[1], tree_sha1))
usage(diff_cache_usage);
- if (generate_patch)
- diff_setup(detect_rename, 0, 0, 0, 0);
+ diff_setup(detect_rename, diff_score_opt, reverse_diff,
+ (generate_patch ? -1 : line_termination),
+ 0, 0);
mark_merge_entries();
@@ -222,7 +215,6 @@ int main(int argc, char **argv)
die("unable to read tree object %s", argv[1]);
ret = diff_cache(active_cache, active_nr);
- if (generate_patch)
- diff_flush();
+ diff_flush();
return ret;
}
diff --git a/diff-files.c b/diff-files.c
--- a/diff-files.c
+++ b/diff-files.c
@@ -7,11 +7,13 @@
#include "diff.h"
static const char *diff_files_usage =
-"git-diff-files [-p] [-q] [-r] [-z] [-M] [paths...]";
+"git-diff-files [-p] [-q] [-r] [-z] [-M] [-R] [paths...]";
static int generate_patch = 0;
static int line_termination = '\n';
static int detect_rename = 0;
+static int reverse_diff = 0;
+static int diff_score_opt = 0;
static int silent = 0;
static int matches_pathspec(struct cache_entry *ce, char **spec, int cnt)
@@ -31,36 +33,19 @@ static int matches_pathspec(struct cache
static void show_unmerge(const char *path)
{
- if (generate_patch)
- diff_unmerge(path);
- else
- printf("U %s%c", path, line_termination);
+ diff_unmerge(path);
}
static void show_file(int pfx, struct cache_entry *ce)
{
- if (generate_patch)
- diff_addremove(pfx, ntohl(ce->ce_mode), ce->sha1,
- ce->name, NULL);
- else
- printf("%c%06o\t%s\t%s\t%s%c",
- pfx, ntohl(ce->ce_mode), "blob",
- sha1_to_hex(ce->sha1), ce->name, line_termination);
+ diff_addremove(pfx, ntohl(ce->ce_mode), ce->sha1, ce->name, NULL);
}
static void show_modified(int oldmode, int mode,
const unsigned char *old_sha1, const unsigned char *sha1,
char *path)
{
- char old_sha1_hex[41];
- strcpy(old_sha1_hex, sha1_to_hex(old_sha1));
-
- if (generate_patch)
- diff_change(oldmode, mode, old_sha1, sha1, path, NULL);
- else
- printf("*%06o->%06o\tblob\t%s->%s\t%s%c",
- oldmode, mode, old_sha1_hex, sha1_to_hex(sha1), path,
- line_termination);
+ diff_change(oldmode, mode, old_sha1, sha1, path, NULL);
}
int main(int argc, char **argv)
@@ -80,7 +65,10 @@ int main(int argc, char **argv)
; /* no-op */
else if (!strcmp(argv[1], "-z"))
line_termination = 0;
- else if (!strcmp(argv[1], "-M")) {
+ else if (!strcmp(argv[1], "-R"))
+ reverse_diff = 1;
+ else if (!strncmp(argv[1], "-M", 2)) {
+ diff_score_opt = diff_scoreopt_parse(argv[1]);
detect_rename = generate_patch = 1;
}
else
@@ -96,8 +84,9 @@ int main(int argc, char **argv)
exit(1);
}
- if (generate_patch)
- diff_setup(detect_rename, 0, 0, 0, 0);
+ diff_setup(detect_rename, diff_score_opt, reverse_diff,
+ (generate_patch ? -1 : line_termination),
+ 0, 0);
for (i = 0; i < entries; i++) {
struct stat st;
@@ -117,12 +106,12 @@ int main(int argc, char **argv)
i--; /* compensate for loop control increments */
continue;
}
-
+
if (lstat(ce->name, &st) < 0) {
if (errno != ENOENT) {
perror(ce->name);
continue;
- }
+ }
if (silent)
continue;
show_file('-', ce);
@@ -139,7 +128,6 @@ int main(int argc, char **argv)
show_modified(oldmode, mode, ce->sha1, null_sha1,
ce->name);
}
- if (generate_patch)
- diff_flush();
+ diff_flush();
return 0;
}
diff --git a/diff-helper.c b/diff-helper.c
--- a/diff-helper.c
+++ b/diff-helper.c
@@ -7,6 +7,7 @@
#include "diff.h"
static int detect_rename = 0;
+static int diff_score_opt = 0;
static int parse_oneside_change(const char *cp, int *mode,
unsigned char *sha1, char *path)
@@ -19,15 +20,15 @@ static int parse_oneside_change(const ch
cp++;
}
*mode = m;
- if (strncmp(cp, "\tblob\t", 6))
+ if (strncmp(cp, "\tblob\t", 6) && strncmp(cp, " blob ", 6))
return -1;
cp += 6;
if (get_sha1_hex(cp, sha1))
return -1;
cp += 40;
- if (*cp++ != '\t')
+ if ((*cp != '\t') && *cp != ' ')
return -1;
- strcpy(path, cp);
+ strcpy(path, ++cp);
return 0;
}
@@ -63,7 +64,7 @@ static int parse_diff_raw_output(const c
new_mode = (new_mode << 3) | (ch - '0');
cp++;
}
- if (strncmp(cp, "\tblob\t", 6))
+ if (strncmp(cp, "\tblob\t", 6) && strncmp(cp, " blob ", 6))
return -1;
cp += 6;
if (get_sha1_hex(cp, old_sha1))
@@ -75,9 +76,9 @@ static int parse_diff_raw_output(const c
if (get_sha1_hex(cp, new_sha1))
return -1;
cp += 40;
- if (*cp++ != '\t')
+ if ((*cp != '\t') && *cp != ' ')
return -1;
- strcpy(path, cp);
+ strcpy(path, ++cp);
diff_change(old_mode, new_mode, old_sha1, new_sha1, path, 0);
break;
default:
@@ -101,15 +102,17 @@ int main(int ac, const char **av) {
reverse = 1;
else if (av[1][1] == 'z')
line_termination = 0;
- else if (av[1][1] == 'M')
+ else if (av[1][1] == 'M') {
detect_rename = 1;
+ diff_score_opt = diff_scoreopt_parse(av[1]);
+ }
else
usage(diff_helper_usage);
ac--; av++;
}
/* the remaining parameters are paths patterns */
- diff_setup(detect_rename, 0, reverse, av+1, ac-1);
+ diff_setup(detect_rename, diff_score_opt, reverse, -1, av+1, ac-1);
while (1) {
int status;
diff --git a/diff-tree.c b/diff-tree.c
--- a/diff-tree.c
+++ b/diff-tree.c
@@ -11,6 +11,7 @@ static int read_stdin = 0;
static int line_termination = '\n';
static int generate_patch = 0;
static int detect_rename = 0;
+static int diff_score_opt = 0;
static const char *header = NULL;
static const char *header_prefix = "";
@@ -84,21 +85,13 @@ static void show_file(const char *prefix
die("corrupt tree sha %s", sha1_to_hex(sha1));
show_tree(prefix, tree, size, newbase);
-
+
free(tree);
free(newbase);
return;
}
- if (generate_patch) {
- if (!S_ISDIR(mode))
- diff_addremove(prefix[0], mode, sha1, base, path);
- }
- else
- printf("%s%06o\t%s\t%s\t%s%s%c", prefix, mode,
- S_ISDIR(mode) ? "tree" : "blob",
- sha1_to_hex(sha1), base, path,
- line_termination);
+ diff_addremove(prefix[0], mode, sha1, base, path);
}
static int compare_tree_entry(void *tree1, unsigned long size1, void *tree2, unsigned long size2, const char *base)
@@ -107,7 +100,6 @@ static int compare_tree_entry(void *tree
const char *path1, *path2;
const unsigned char *sha1, *sha2;
int cmp, pathlen1, pathlen2;
- char old_sha1_hex[50];
sha1 = extract(tree1, size1, &path1, &mode1);
sha2 = extract(tree2, size2, &path2, &mode2);
@@ -151,17 +143,7 @@ static int compare_tree_entry(void *tree
if (silent)
return 0;
- if (generate_patch) {
- if (!S_ISDIR(mode1))
- diff_change(mode1, mode2, sha1, sha2, base, path1);
- }
- else {
- strcpy(old_sha1_hex, sha1_to_hex(sha1));
- printf("*%06o->%06o\t%s\t%s->%s\t%s%s%c", mode1, mode2,
- S_ISDIR(mode1) ? "tree" : "blob",
- old_sha1_hex, sha1_to_hex(sha2), base, path1,
- line_termination);
- }
+ diff_change(mode1, mode2, sha1, sha2, base, path1);
return 0;
}
@@ -287,11 +269,12 @@ static int diff_tree_sha1_top(const unsi
const unsigned char *new, const char *base)
{
int ret;
- if (generate_patch)
- diff_setup(detect_rename, 0, 0, 0, 0);
+
+ diff_setup(detect_rename, diff_score_opt, 0,
+ (generate_patch ? -1 : line_termination),
+ 0, 0);
ret = diff_tree_sha1(old, new, base);
- if (generate_patch)
- diff_flush();
+ diff_flush();
return ret;
}
@@ -301,15 +284,15 @@ static int diff_root_tree(const unsigned
void *tree;
unsigned long size;
- if (generate_patch)
- diff_setup(detect_rename, 0, 0, 0, 0);
+ diff_setup(detect_rename, diff_score_opt, 0,
+ (generate_patch ? -1 : line_termination),
+ 0, 0);
tree = read_object_with_reference(new, "tree", &size, 0);
if (!tree)
die("unable to read root tree (%s)", sha1_to_hex(new));
retval = diff_tree("", 0, tree, size, base);
free(tree);
- if (generate_patch)
- diff_flush();
+ diff_flush();
return retval;
}
@@ -485,8 +468,9 @@ int main(int argc, char **argv)
recursive = generate_patch = 1;
continue;
}
- if (!strcmp(arg, "-M")) {
+ if (!strncmp(arg, "-M", 2)) {
detect_rename = recursive = generate_patch = 1;
+ diff_score_opt = diff_scoreopt_parse(arg);
continue;
}
if (!strcmp(arg, "-z")) {
diff --git a/diff.c b/diff.c
--- a/diff.c
+++ b/diff.c
@@ -11,6 +11,8 @@
static const char *diff_opts = "-pu";
static unsigned char null_sha1[20] = { 0, };
+#define MAX_SCORE 10000
+#define DEFAULT_MINIMUM_SCORE 5000
static const char *external_diff(void)
{
@@ -55,7 +57,7 @@ static char *sq_expand(const char *src)
const char *cp;
char *bp;
- /* count bytes needed to store the quoted string. */
+ /* count bytes needed to store the quoted string. */
for (cnt = 1, cp = src; *cp; cnt++, cp++)
if (*cp == '\'')
cnt += 3;
@@ -93,7 +95,8 @@ struct diff_spec {
static void builtin_diff(const char *name_a,
const char *name_b,
- struct diff_tempfile *temp)
+ struct diff_tempfile *temp,
+ int rename_score)
{
int i, next_at, cmd_size;
const char *diff_cmd = "diff -L'%s%s' -L'%s%s'";
@@ -149,6 +152,10 @@ static void builtin_diff(const char *nam
printf("new mode %s\n", temp[1].mode);
}
if (strcmp(name_a, name_b)) {
+ if (0 < rename_score)
+ printf("rename similarity index %d%%\n",
+ (int)(0.5+
+ rename_score*100.0/MAX_SCORE));
printf("rename old %s\n", name_a);
printf("rename new %s\n", name_b);
}
@@ -184,7 +191,7 @@ static int work_tree_matches(const char
* file. Practically, this code only helps when we are used
* by diff-cache --cached, which does read the cache before
* calling us.
- */
+ */
if (!active_cache)
return 0;
@@ -302,9 +309,10 @@ static void remove_tempfile_on_signal(in
static int detect_rename;
static int reverse_diff;
+static int diff_raw_output = -1;
static const char **pathspec;
static int speccnt;
-static int diff_rename_minimum_score;
+static int minimum_score;
static int matches_pathspec(const char *name)
{
@@ -334,7 +342,8 @@ static int matches_pathspec(const char *
static void run_external_diff(const char *name,
const char *other,
struct diff_spec *one,
- struct diff_spec *two)
+ struct diff_spec *two,
+ int rename_score)
{
struct diff_tempfile *temp = diff_temp;
pid_t pid;
@@ -395,7 +404,7 @@ static void run_external_diff(const char
* otherwise we use the built-in one.
*/
if (one && two)
- builtin_diff(name, other ? : name, temp);
+ builtin_diff(name, other ? : name, temp, rename_score);
else
printf("* Unmerged path %s\n", name);
exit(0);
@@ -446,7 +455,7 @@ static void hold_diff(const char *name,
die("internal error");
if (!detect_rename) {
- run_external_diff(name, NULL, one, two);
+ run_external_diff(name, NULL, one, two, -1);
return;
}
elem = xmalloc(sizeof(*elem) + strlen(name));
@@ -519,10 +528,10 @@ static void flush_remaining_diff(struct
continue;
if (on_created_list)
run_external_diff(elem->path, NULL,
- &null_file_spec, &elem->it);
+ &null_file_spec, &elem->it, -1);
else
run_external_diff(elem->path, NULL,
- &elem->it, &null_file_spec);
+ &elem->it, &null_file_spec, -1);
}
}
@@ -541,7 +550,6 @@ static int is_exact_match(struct diff_sp
return 0;
}
-#define MINIMUM_SCORE 5000
int estimate_similarity(struct diff_spec_hold *src, struct diff_spec_hold *dst)
{
/* src points at a deleted file and dst points at a created
@@ -549,20 +557,24 @@ int estimate_similarity(struct diff_spec
* say src is renamed to dst.
*
* Compare them and return how similar they are, representing
- * the score as an integer between 0 and 10000. 10000 is
- * reserved for the case where they match exactly.
+ * the score as an integer between 0 and 10000, except
+ * where they match exactly it is considered better than anything
+ * else.
*/
void *delta;
unsigned long delta_size;
+ int score;
delta_size = ((src->size < dst->size) ?
(dst->size - src->size) : (src->size - dst->size));
/* We would not consider rename followed by more than
- * 20% edits; that is, delta_size must be smaller than
- * (src->size + dst->size)/2 * 0.2, which means...
+ * minimum_score/MAX_SCORE edits; that is, delta_size must be smaller
+ * than (src->size + dst->size)/2 * minimum_score/MAX_SCORE,
+ * which means...
*/
- if ((src->size + dst->size) < delta_size * 10)
+
+ if ((src->size+dst->size)*minimum_score < delta_size*MAX_SCORE*2)
return 0;
delta = diff_delta(src->data, src->size,
@@ -573,14 +585,17 @@ int estimate_similarity(struct diff_spec
/* This "delta" is really xdiff with adler32 and all the
* overheads but it is a quick and dirty approximation.
*
- * Now we will give some score to it. Let's say 20% edit gets
- * 5000 points and 0% edit gets 9000 points. That is, every
- * 1/20000 edit gets 1 point penalty. The amount of penalty is:
+ * Now we will give some score to it. 100% edit gets
+ * 0 points and 0% edit gets MAX_SCORE points. That is, every
+ * 1/MAX_SCORE edit gets 1 point penalty. The amount of penalty is:
*
- * (delta_size * 2 / (src->size + dst->size)) * 20000
+ * (delta_size * 2 / (src->size + dst->size)) * MAX_SCORE
*
*/
- return 9000 - (40000 * delta_size / (src->size+dst->size));
+ score = MAX_SCORE-(MAX_SCORE*2*delta_size/(src->size+dst->size));
+ if (score < 0) return 0;
+ if (MAX_SCORE < score) return MAX_SCORE;
+ return score;
}
struct diff_score {
@@ -596,14 +611,15 @@ static int score_compare(const void *a_,
}
static void flush_rename_pair(struct diff_spec_hold *src,
- struct diff_spec_hold *dst)
+ struct diff_spec_hold *dst,
+ int rename_score)
{
src->flags |= MATCHED;
dst->flags |= MATCHED;
free_data(src);
free_data(dst);
run_external_diff(src->path, dst->path,
- &src->it, &dst->it);
+ &src->it, &dst->it, rename_score);
}
static void free_held_diff(struct diff_spec_hold *list)
@@ -637,7 +653,7 @@ void diff_flush(void)
continue;
if (! is_exact_match(src, dst))
continue;
- flush_rename_pair(src, dst);
+ flush_rename_pair(src, dst, MAX_SCORE);
break;
}
}
@@ -670,7 +686,7 @@ void diff_flush(void)
}
c++;
}
- qsort(mx, num_create*num_delete, sizeof(*mx), score_compare);
+ qsort(mx, num_create*num_delete, sizeof(*mx), score_compare);
#if 0
for (c = 0; c < num_create * num_delete; c++) {
@@ -689,9 +705,9 @@ void diff_flush(void)
dst = mx[c].dst;
if ((src->flags & MATCHED) || (dst->flags & MATCHED))
continue;
- if (mx[c].score < diff_rename_minimum_score)
+ if (mx[c].score < minimum_score)
break;
- flush_rename_pair(src, dst);
+ flush_rename_pair(src, dst, mx[c].score);
}
free(mx);
@@ -703,7 +719,26 @@ void diff_flush(void)
createdfile = deletedfile = NULL;
}
+int diff_scoreopt_parse(const char *opt)
+{
+ int diglen, num, scale, i;
+ if (opt[0] != '-' || opt[1] != 'M')
+ return -1; /* that is not -M option */
+ diglen = strspn(opt+2, "0123456789");
+ if (diglen == 0 || strlen(opt+2) != diglen)
+ return 0; /* use default */
+ sscanf(opt+2, "%d", &num);
+ for (i = 0, scale = 1; i < diglen; i++)
+ scale *= 10;
+
+ /* user says num divided by scale and we say internally that
+ * is MAX_SCORE * num / scale.
+ */
+ return MAX_SCORE * num / scale;
+}
+
void diff_setup(int detect_rename_, int minimum_score_, int reverse_diff_,
+ int diff_raw_output_,
const char **pathspec_, int speccnt_)
{
free_held_diff(createdfile);
@@ -713,8 +748,14 @@ void diff_setup(int detect_rename_, int
detect_rename = detect_rename_;
reverse_diff = reverse_diff_;
pathspec = pathspec_;
+ diff_raw_output = diff_raw_output_;
speccnt = speccnt_;
- diff_rename_minimum_score = minimum_score_ ? : MINIMUM_SCORE;
+ minimum_score = minimum_score_ ? : DEFAULT_MINIMUM_SCORE;
+}
+
+static const char *git_object_type(unsigned mode)
+{
+ return S_ISDIR(mode) ? "tree" : "blob";
}
void diff_addremove(int addremove, unsigned mode,
@@ -724,6 +765,21 @@ void diff_addremove(int addremove, unsig
char concatpath[PATH_MAX];
struct diff_spec spec[2], *one, *two;
+ if (0 <= diff_raw_output) {
+ if (!path)
+ path = "";
+ if (reverse_diff)
+ addremove = (addremove == '+' ? '-' : '+');
+ printf("%c%06o %s %s %s%s%c",
+ addremove,
+ mode,
+ git_object_type(mode), sha1_to_hex(sha1),
+ base, path, diff_raw_output);
+ return;
+ }
+ if (S_ISDIR(mode))
+ return;
+
memcpy(spec[0].blob_sha1, sha1, 20);
spec[0].mode = mode;
spec[0].sha1_valid = !!memcmp(sha1, null_sha1, 20);
@@ -750,6 +806,29 @@ void diff_change(unsigned old_mode, unsi
char concatpath[PATH_MAX];
struct diff_spec spec[2];
+ if (0 <= diff_raw_output) {
+ char old_hex[41];
+ strcpy(old_hex, sha1_to_hex(old_sha1));
+
+ if (!path)
+ path = "";
+ if (reverse_diff)
+ printf("*%06o->%06o %s %s->%s %s%s%c",
+ new_mode, old_mode,
+ git_object_type(new_mode),
+ sha1_to_hex(new_sha1), old_hex,
+ base, path, diff_raw_output);
+ else
+ printf("*%06o->%06o %s %s->%s %s%s%c",
+ old_mode, new_mode,
+ git_object_type(new_mode),
+ old_hex, sha1_to_hex(new_sha1),
+ base, path, diff_raw_output);
+ return;
+ }
+ if (S_ISDIR(new_mode))
+ return;
+
if (path) {
strcpy(concatpath, base);
strcat(concatpath, path);
@@ -766,10 +845,15 @@ void diff_change(unsigned old_mode, unsi
/* We do not look at changed files as candidate for
* rename detection ever.
*/
- run_external_diff(path ? concatpath : base, NULL, &spec[0], &spec[1]);
+ run_external_diff(path ? concatpath : base, NULL,
+ &spec[0], &spec[1], -1);
}
void diff_unmerge(const char *path)
{
- run_external_diff(path, NULL, NULL, NULL);
+ if (0 <= diff_raw_output) {
+ printf("U %s%c", path, diff_raw_output);
+ return;
+ }
+ run_external_diff(path, NULL, NULL, NULL, -1);
}
diff --git a/diff.h b/diff.h
--- a/diff.h
+++ b/diff.h
@@ -17,8 +17,10 @@ extern void diff_change(unsigned mode1,
extern void diff_unmerge(const char *path);
+extern int diff_scoreopt_parse(const char *opt);
+
extern void diff_setup(int detect_rename, int minimum_score,
- int reverse,
+ int reverse, int raw_output,
const char **spec, int cnt);
extern void diff_flush(void);
diff --git a/t/t0000-basic.sh b/t/t0000-basic.sh
--- a/t/t0000-basic.sh
+++ b/t/t0000-basic.sh
@@ -166,7 +166,7 @@ cat >expected <<\EOF
EOF
test_expect_success \
'validate git-diff-files output for a know cache/work tree state.' \
- 'git-diff-files >current && cmp -s current expected'
+ 'git-diff-files >current && diff >/dev/null -b current expected'
test_expect_success \
'git-update-cache --refresh should succeed.' \
diff --git a/t/t0110-environment-names-old.sh b/t/t0110-environment-names-old.sh
diff --git a/t/t1000-read-tree-m-3way.sh b/t/t1000-read-tree-m-3way.sh
diff --git a/t/t2002-checkout-cache-u.sh b/t/t2002-checkout-cache-u.sh
--- a/t/t2002-checkout-cache-u.sh
+++ b/t/t2002-checkout-cache-u.sh
@@ -29,3 +29,5 @@ rm -f path0 &&
git-read-tree $t &&
git-checkout-cache -u -f -a &&
git-diff-files | diff - /dev/null'
+
+test_done
diff --git a/t/t4000-diff-format.sh b/t/t4000-diff-format.sh
diff --git a/t/t4001-diff-rename.sh b/t/t4001-diff-rename.sh
--- a/t/t4001-diff-rename.sh
+++ b/t/t4001-diff-rename.sh
@@ -58,3 +58,9 @@ rename new path1
Line 13
Line 14
EOF
+
+test_expect_success \
+ 'validate the output.' \
+ 'diff -I "rename similarity.*" >/dev/null current expected'
+
+test_done
------------------------------------------------
^ permalink raw reply
* Re: gitk-1.0 released
From: Frank Sorenson @ 2005-05-20 4:55 UTC (permalink / raw)
To: Benjamin Herrenschmidt; +Cc: Paul Mackerras, git
In-Reply-To: <1116544421.5153.46.camel@gaston>
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Benjamin Herrenschmidt wrote:
> Cool !
>
> Here's a feature request though: beeing able to type/paste a SHA1 in the
> SHA1 ID field to "jump" to that commit :)
Very nice. I really like gitk as well. In addition to pasting an sha1
in, how about pasting a tag?
Also, what about identifying tagged commits with a different color, a
star instead of just the round bullet, or some other identifier?
Frank
- --
Frank Sorenson - KD7TZK
Systems Manager, Computer Science Department
Brigham Young University
frank@tuxrocks.com
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.6 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org
iD8DBQFCjW2yaI0dwg4A47wRArsEAKCdkTBQEPD7yyb8ABiBg20nhdmKgACg2D2Y
W0ZxoOGTOspvrRczeEYN9mg=
=y2Z0
-----END PGP SIGNATURE-----
^ permalink raw reply
* Re: [PATCH] diff overhaul
From: Linus Torvalds @ 2005-05-20 5:30 UTC (permalink / raw)
To: Junio C Hamano; +Cc: git
In-Reply-To: <7vll6awta3.fsf@assigned-by-dhcp.cox.net>
On Thu, 19 May 2005, Junio C Hamano wrote:
>
> This also allowed diff-cache and diff-files to acquire -R
> (reverse) option to generate diff in reverse. Users of
> diff-tree can swap two trees easily so I did not add -R there.
Actually, diff-tree would want it too.
You can only swap the trees easily if you give two trees, not if you give
a commit.
Linus
^ permalink raw reply
* [PATCH] Fix git-fsck-cache segfault on invalid tag
From: Frank Sorenson @ 2005-05-20 7:00 UTC (permalink / raw)
To: Git Mailing List, Linus Torvalds
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
git-fsck-cache will segfault if a tag contains a non-existent sha1. This
patch fixes fsck-cache to report the invalid tag and not die.
- ---
commit a6a237ee3f3d2f5d76499b8f32f58057c9b4cd2d
tree ac5d65a040c22194ddcd0706dc5f0b8bb52aef65
parent 5cd4c7b7686d334e341b21d92449349feda3ef65
author Frank Sorenson <frank@tuxrocks.com> Fri, 20 May 2005 00:52:59 -0600
committer Frank Sorenson <frank@tuxrocks.com> Fri, 20 May 2005 00:52:59 -0600
fsck-cache.c | 4 ++++
1 files changed, 4 insertions(+)
Index: fsck-cache.c
===================================================================
- --- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/fsck-cache.c (mode:100644)
+++ ac5d65a040c22194ddcd0706dc5f0b8bb52aef65/fsck-cache.c (mode:100644)
@@ -315,6 +315,10 @@
return;
obj = lookup_object(sha1);
+ if (!obj) {
+ fprintf(stderr, "invalid tag %s - %s\n", path, hexname);
+ return;
+ }
obj->used = 1;
mark_reachable(obj, REACHABLE);
}
Frank
- --
Frank Sorenson - KD7TZK
Systems Manager, Computer Science Department
Brigham Young University
frank@tuxrocks.com
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.6 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org
iD8DBQFCjYsZaI0dwg4A47wRAn2PAJ9hyoev3stnaN0Qn2wWlBJEKiucQACgvT9Z
rVazYmUFj3nXvJDYaBoSRsM=
=KbSv
-----END PGP SIGNATURE-----
^ permalink raw reply
* Re: [PATCH] Fix git-fsck-cache segfault on invalid tag
From: Petr Baudis @ 2005-05-20 8:50 UTC (permalink / raw)
To: Frank Sorenson; +Cc: Git Mailing List, Linus Torvalds
In-Reply-To: <428D8B19.4070605@tuxrocks.com>
Dear diary, on Fri, May 20, 2005 at 09:00:41AM CEST, I got a letter
where Frank Sorenson <frank@tuxrocks.com> told me that...
> git-fsck-cache will segfault if a tag contains a non-existent sha1. This
> patch fixes fsck-cache to report the invalid tag and not die.
Oh. I've fixed this too but didn't even get to commit it yet. :-)
> Index: fsck-cache.c
> ===================================================================
> --- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/fsck-cache.c (mode:100644)
> +++ ac5d65a040c22194ddcd0706dc5f0b8bb52aef65/fsck-cache.c (mode:100644)
> @@ -315,6 +315,10 @@
> return;
>
> obj = lookup_object(sha1);
> + if (!obj) {
> + fprintf(stderr, "invalid tag %s - %s\n", path, hexname);
> + return;
> + }
> obj->used = 1;
> mark_reachable(obj, REACHABLE);
> }
My error message is
error("%s: invalid sha1 pointer %.40s", path, hexname);
I'd prefer that (at least use the error() call). The .40 is there since
it has a newline on its own.
--
Petr "Pasky" Baudis
Stuff: http://pasky.or.cz/
C++: an octopus made by nailing extra legs onto a dog. -- Steve Taylor
^ permalink raw reply
* [cogito] paged output for cg-diff
From: Michal Rokos @ 2005-05-20 9:05 UTC (permalink / raw)
To: git
Hello,
I'm a bit curious what is going on in development so I'm using cg-diff
often. Usually I pipe it to the less. So for me it would be very nice
when cg-diff behaves as cg-log that pipes output to pager.
So I changed cg-diff to do so.
New function PAGER() determines whether output is terminal and uses
PAGER in that case.
Do you like it?
Michal
Signed-off-by: Michal Rokos <michal@rokos.info>
Index: cg-Xlib
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-Xlib (mode:100755)
+++ uncommitted/cg-Xlib (mode:100755)
@@ -91,3 +91,12 @@
export BROKEN_MKTEMP=1
del=$($(which mktemp) -t 2>/dev/null) && { rm $del; export BROKEN_MKTEMP=; }
+
+PAGER () {
+ if [ -t 1 ]; then
+ ${PAGER:-less} ${PAGER_FLAGS:--R}
+ else
+ cat
+ fi
+}
+
Index: cg-diff
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-diff (mode:100755)
+++ uncommitted/cg-diff (mode:100755)
@@ -71,7 +71,7 @@
# FIXME: Update ret based on what did we match. And take "$@"
# to account after all.
ret=
- git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter"
+ git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter" | PAGER
[ "$filter" ] && rm $filter
@@ -85,7 +85,7 @@
[ "$id1" = "$id2" ] && die "trying to diff $id1 against itself"
-git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter"
+git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter" | PAGER
[ "$filter" ] && rm $filter
exit 0
Index: cg-log
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-log (mode:100755)
+++ uncommitted/cg-log (mode:100755)
@@ -181,4 +181,4 @@
done
echo
-done | ${PAGER:-less} ${PAGER_FLAGS:--R}
+done | PAGER
--
Michal Rokos
NextSoft s.r.o.
Vyskočilova 1/1410
140 21 Praha 4
tel: +420 267 224 311
fax: +420 267 224 307
mobil: +420 736 646 591
e-mail: michal.rokos@nextsoft.cz
^ permalink raw reply
* Re: gitk-1.0 released
From: Ingo Molnar @ 2005-05-20 11:22 UTC (permalink / raw)
To: Paul Mackerras; +Cc: git
In-Reply-To: <17037.5109.556362.904185@cargo.ozlabs.ibm.com>
* Paul Mackerras <paulus@samba.org> wrote:
> > (and the biggest missing feature of GIT right now is author +
> > last-commit annotated file viewing which could be integrated into gitk
> > a'ka BK's revtool: selecting a given line of the file would bring one to
> > that commit, etc.)
>
> Yes, indeed. I'll have to think about how to do it in a responsive
> fashion, since getting the necessary information involves reading all
> the commits and all the tree objects back to the beginning of time,
> AFAICS. [...]
i guess so. A possible solution seems to be to read every object
starting at the oldest one (assuming it's possible to get a list of
object IDs that are predecessors), and to split the oldest object up
into 'line' objects, attaching the (same) object ID to every line. Then
the algorithm would go forward in time and would process every diff from
that point on, and would add/remove line objects, attaching the new
object IDs as new lines get added. The resulting set of lines then
contain all the metadata needed (== object ID they originate from).
i dont think other SCMs can do this much faster: you need to go back to
the last (still relevant) version and have to process the deltas from
that point on. Delta-based formats would be somewhat faster and easier
to process, but probably not that much faster in terms of IO overhead.
Ingo
^ permalink raw reply
* Re: gitk-1.0 released
From: Ingo Molnar @ 2005-05-20 11:33 UTC (permalink / raw)
To: Paul Mackerras; +Cc: git
In-Reply-To: <17037.5109.556362.904185@cargo.ozlabs.ibm.com>
* Paul Mackerras <paulus@samba.org> wrote:
> > - first window appearance on an uncached repository can be pretty slow
> > due to disk seeks - so it might make sense to display something (an
> > hourglass?) sooner - when i first started it i thought it hung. On
> > already cached repositories the window comes up immediately, and the
> > list of commits is updated dynamically.
>
> The problem is that git-rev-tree HEAD doesn't output anything until it
> has read all the relevant commits, which can involve a lot of disk
> seeks. I put the "Reading commits..." message in to indicate that
> something was happening, but your hourglass cursor suggestion is a
> good one. It looks like git-rev-list might be better suited to what I
> want, actually.
it was quite a couple of seconds to get the empty windows with the
'Reading commits...' message. It was this first period of time (5-10
seconds?) which i mistook for a hang. Perhaps this is some Tk startup
slowness, not a genuine gitk issue?
> + if {$nparents($id) > 2} {
> + set xt [expr {$xt + ($nparents($id) - 2) * $linespc}]
> + }
thanks, this fix did the trick.
Ingo
^ permalink raw reply
* Re: [cogito] paged output for cg-diff
From: Junio C Hamano @ 2005-05-20 12:53 UTC (permalink / raw)
To: Michal Rokos; +Cc: git
In-Reply-To: <200505201105.08711.michal.rokos@nextsoft.cz>
>>>>> "MR" == Michal Rokos <michal.rokos@nextsoft.cz> writes:
MR> I'm a bit curious what is going on in development so I'm using cg-diff
MR> often. Usually I pipe it to the less. So for me it would be very nice
MR> when cg-diff behaves as cg-log that pipes output to pager.
I think that is a sensible thing to do. But doesn't "less"
already do this part without being told?
MR> +PAGER () {
MR> + if [ -t 1 ]; then
MR> + ${PAGER:-less} ${PAGER_FLAGS:--R}
MR> + else
MR> + cat
MR> + fi
MR> +}
^ permalink raw reply
* Re: [cogito] paged output for cg-diff
From: Michal Rokos @ 2005-05-20 13:17 UTC (permalink / raw)
To: git
Hello,
Junio is right, following is sufficent. Tested with 'more' too.
Michal
PS: I'm off the list, so please CC me.
Signed-off-by: Michal Rokos <michal@rokos.info>
Idea-from: Junio C Hamano <junkio@cox.net>
Index: cg-Xlib
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-Xlib (mode:100755)
+++ uncommitted/cg-Xlib (mode:100755)
@@ -91,3 +91,8 @@
export BROKEN_MKTEMP=1
del=$($(which mktemp) -t 2>/dev/null) && { rm $del; export BROKEN_MKTEMP=; }
+
+PAGER () {
+ ${PAGER:-less} ${PAGER_FLAGS:--R}
+}
+
Index: cg-diff
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-diff (mode:100755)
+++ uncommitted/cg-diff (mode:100755)
@@ -71,7 +71,7 @@
# FIXME: Update ret based on what did we match. And take "$@"
# to account after all.
ret=
- git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter"
+ git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter" | PAGER
[ "$filter" ] && rm $filter
@@ -85,7 +85,7 @@
[ "$id1" = "$id2" ] && die "trying to diff $id1 against itself"
-git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter"
+git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter" | PAGER
[ "$filter" ] && rm $filter
exit 0
Index: cg-log
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-log (mode:100755)
+++ uncommitted/cg-log (mode:100755)
@@ -181,4 +181,4 @@
done
echo
-done | ${PAGER:-less} ${PAGER_FLAGS:--R}
+done | PAGER
^ permalink raw reply
* [PATCH] Fix and clean up man page building
From: Jonas Fonseca @ 2005-05-20 13:35 UTC (permalink / raw)
To: Sebastian Kuzminsky; +Cc: git
In-Reply-To: <E1DYpbT-0003jv-JY@highlab.com>
Sebastian Kuzminsky <seb@highlab.com> wrote Thu, May 19, 2005:
> -%.1 : %.xml
> +%.1 %.7 : %.xml
> xmlto man $<
> + # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
> + [ "$@" = "git.7" ] || mv git.1 $@
>
> %.xml : %.txt
> asciidoc -b docbook -d manpage $<
This doesn't work for me since make stops when the test fails. Besides
it is a bit verbose. Following is a patch which will only check for
moving when building .7 files. It also cleans up the Makefile so it will
be easier to add the manpages for cogito.
Signed-off-by: Jonas Fonseca <fonseca@diku.dk>
--- f435f47dab3465a47fbd2114cf006e0e869f31a9/Documentation/Makefile (mode:100644)
+++ uncommitted/Documentation/Makefile (mode:100644)
@@ -1,6 +1,7 @@
-DOC_SRC=$(wildcard git*.txt)
-DOC_HTML=$(patsubst %.txt,%.html,$(DOC_SRC))
-DOC_MAN=$(patsubst %.txt,%.1,$(wildcard git-*.txt)) git.7
+MAN1_TXT=$(wildcard git-*.txt)
+MAN7_TXT=git.txt
+DOC_HTML=$(patsubst %.txt,%.html,$(MAN1_TXT) $(MAN7_TXT))
+DOC_MAN=$(patsubst %.txt,%.1,$(MAN1_TXT)) $(patsubst %.txt,%.7,$(MAN7_TXT))
all: $(DOC_HTML) $(DOC_MAN)
@@ -18,10 +19,12 @@
%.html : %.txt
asciidoc -b css-embedded -d manpage $<
+%.7 : %.1
+ # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
+ if [ -f "$<" ]; then mv $< $@; fi
+
%.1 %.7 : %.xml
xmlto man $<
- # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
- [ "$@" = "git.7" ] || mv git.1 $@
%.xml : %.txt
asciidoc -b docbook -d manpage $<
--
Jonas Fonseca
^ permalink raw reply
* Re: [cogito] paged output for cg-diff
From: Junio C Hamano @ 2005-05-20 13:50 UTC (permalink / raw)
To: Michal Rokos; +Cc: git
In-Reply-To: <200505201517.05995.michal@rokos.info>
>>>>> "MR" == Michal Rokos <michal@rokos.info> writes:
MR> Junio is right, following is sufficent. Tested with 'more' too.
MR> Idea-from: Junio C Hamano <junkio@cox.net>
I appreciate the credit, but that is probably not needed in this
case, since this is quite commonly used pattern. I've seen many
people do just this:
command | ${PAGER:-less}
And if you think about it, you would realize that the above is
good enough, and probably is a lot better than what you are
doing.
Your PAGER shell function gives "-R" indiscriminately when
$PAGER_FLAGS is not set (or set to empty, which is even worse
because you are not giving the user to override this _bad_
choice) without even checking if the $PAGER is something that
understands "-R" (namely, "less"). I do not think users with
their PAGER set to "more" or "cat" (I do the latter when I am
working in Emacs) would appreciate that behaviour.
On the other hand, if your user is a "less" user, and if the
user wants it to honor ANSI "color" escape sequences, it would
be more helpful to the user if you educate/encourage the user to
have "LESS=R" in the environment and make that in effect
everywhere less is used not just in Cogito. Giving that support
silently just in Cogito at the first thought may seem to be more
helpful but in reality it is not.
So I would suggest to use the above form without defining your
own PAGER shell function, and add a tip for "less" users to have
"LESS=R" in their environment somewhere in the documentation.
^ permalink raw reply
* Re: [PATCH] Fix git-fsck-cache segfault on invalid tag
From: Junio C Hamano @ 2005-05-20 13:58 UTC (permalink / raw)
To: Petr Baudis; +Cc: Frank Sorenson, Git Mailing List, Linus Torvalds
In-Reply-To: <20050520085047.GA27787@pasky.ji.cz>
>>>>> "PB" == Petr Baudis <pasky@ucw.cz> writes:
>> obj = lookup_object(sha1);
>> + if (!obj) {
>> + fprintf(stderr, "invalid tag %s - %s\n", path, hexname);
>> + return;
>> + }
>> ...
PB> My error message is
PB> error("%s: invalid sha1 pointer %.40s", path, hexname);
PB> I'd prefer that (at least use the error() call).
Ack.
I was about to say "doesn't lookup_object() give its own error
message before you say that, though?" because I remembered a
comment to that effect around ll 410 that gets the heads from
the command line argument, and then looked at lookup_object()
implementation to find that it does _not_ give error message.
So if you are going to do this, would you mind giving similar
error message to that command line heads stuff while you are at
it, please?
^ permalink raw reply
* Re: [PATCH] Fix and clean up man page building
From: Raja R Harinath @ 2005-05-20 14:08 UTC (permalink / raw)
To: git
In-Reply-To: <20050520133533.GA27395@diku.dk>
Hi,
Jonas Fonseca <fonseca@diku.dk> writes:
> +%.7 : %.1
> + # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
> + if [ -f "$<" ]; then mv $< $@; fi
> +
> %.1 %.7 : %.xml
> xmlto man $<
> - # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
> - [ "$@" = "git.7" ] || mv git.1 $@
>
> %.xml : %.txt
> asciidoc -b docbook -d manpage $<
That doesn't look right. I think you want
%.7: %.xml
xmlto man %<
%.1: %.xml
xmlto man $<
[ test -f $@ ] || mv git.1 $@
- Hari
^ permalink raw reply
* Re: [PATCH] Fix git-fsck-cache segfault on invalid tag
From: Frank Sorenson @ 2005-05-20 14:36 UTC (permalink / raw)
To: Petr Baudis; +Cc: Git Mailing List, Linus Torvalds
In-Reply-To: <20050520085047.GA27787@pasky.ji.cz>
-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1
Petr Baudis wrote:
> Dear diary, on Fri, May 20, 2005 at 09:00:41AM CEST, I got a letter
> where Frank Sorenson <frank@tuxrocks.com> told me that...
>
>>git-fsck-cache will segfault if a tag contains a non-existent sha1. This
>>patch fixes fsck-cache to report the invalid tag and not die.
>
>
> Oh. I've fixed this too but didn't even get to commit it yet. :-)
Okay. At least we fixed the same bug. It was a good exercise for me to
track it down anyway :)
> My error message is
>
> error("%s: invalid sha1 pointer %.40s", path, hexname);
>
> I'd prefer that (at least use the error() call). The .40 is there since
> it has a newline on its own.
Great. Your message looks fine. It looks like error() should work fine
as well.
Frank
- --
Frank Sorenson - KD7TZK
Systems Manager, Computer Science Department
Brigham Young University
frank@tuxrocks.com
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.6 (GNU/Linux)
Comment: Using GnuPG with Thunderbird - http://enigmail.mozdev.org
iD8DBQFCjfXgaI0dwg4A47wRAikrAKCvPmZBQK34sdnnY61/meuewu2jzQCfT7Qf
TDSNgfp3WBJOTvWG5uhwX4s=
=CUF2
-----END PGP SIGNATURE-----
^ permalink raw reply
* Re: [PATCH] Fix and clean up man page building
From: Jonas Fonseca @ 2005-05-20 14:52 UTC (permalink / raw)
To: Raja R Harinath; +Cc: git
In-Reply-To: <m37jhu56ta.fsf@harinath.blr.novell.com>
Raja R Harinath <rharinath@novell.com> wrote Fri, May 20, 2005:
> Hi,
>
> Jonas Fonseca <fonseca@diku.dk> writes:
>
> > +%.7 : %.1
> > + # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
> > + if [ -f "$<" ]; then mv $< $@; fi
> > +
> > %.1 %.7 : %.xml
> > xmlto man $<
> > - # FIXME: this next line works around an output filename bug in asciidoc 6.0.3
> > - [ "$@" = "git.7" ] || mv git.1 $@
> >
> > %.xml : %.txt
> > asciidoc -b docbook -d manpage $<
>
> That doesn't look right. I think you want
>
> %.7: %.xml
> xmlto man %<
>
> %.1: %.xml
> xmlto man $<
> [ test -f $@ ] || mv git.1 $@
[ Looks like you mixed up %.1 and %.7 ]
Yes, separating the rule for %.1 and %.7 might be clearer. But it would
be great if it would work for any man page in section 7 not just git.7.
Since I hope to add cogito.7 soon.
--
Jonas Fonseca
^ permalink raw reply
* Re: [cogito] paged output for cg-diff
From: Thomas Glanzmann @ 2005-05-20 14:55 UTC (permalink / raw)
To: git
In-Reply-To: <7v64xevz15.fsf@assigned-by-dhcp.cox.net>
Hello,
> I think that is a sensible thing to do. But doesn't "less"
> already do this part without being told?
yes, every pager does.
Thomas
^ permalink raw reply
* "git-diff-tree -R A B == git-diff-tree B A"?
From: Junio C Hamano @ 2005-05-20 14:56 UTC (permalink / raw)
To: torvalds; +Cc: git
I was preparing a set of tests for diff family because I wanted
to have something that catches screwups I am going to inflict
upon them during the coming couple of days. One of the tests
accidentally found out that the above is not true in the current
implementation. Just an excerpt of relevant lines [*1*]:
$ git-diff-tree -r $tree_B $tree_A
+100644 blob 7e426fb079479fd67f6d81f984e4ec649a44bc25 AN
+100644 blob 68a6d8b91da11045cf4aa3a5ab9f2a781c701249 DF/DF
-100644 blob 71420ab81e254145d26d6fc0cddee64c1acd4787 DF
-100644 blob 3c4d8de5fbad08572bab8e10eef8dbb264cf0231 DM
$ git-diff-tree -R $tree_A $tree_B
+100644 blob 7e426fb079479fd67f6d81f984e4ec649a44bc25 AN
-100644 blob 71420ab81e254145d26d6fc0cddee64c1acd4787 DF
+100644 blob 68a6d8b91da11045cf4aa3a5ab9f2a781c701249 DF/DF
-100644 blob 3c4d8de5fbad08572bab8e10eef8dbb264cf0231 DM
I personally don't care about the difference of the order these
are output, but it affects the stability of the test, and also
is inconsistent --- everybody else sorts the entries in the
cache order.
Although I do not see practical problems in this inconsistency,
I am asking you just in case if you care about it. If there is
a downstream consumer that relies on the ordering of the entries
this may cause problems (diff-helper is OK).
[Footnote]
*1* The trees are taken from t1000-read-tree-m-3way.sh test.
^ permalink raw reply
* [cogito PATCH] Add "-c" (colorize) option to cg-diff
From: Catalin Marinas @ 2005-05-20 14:58 UTC (permalink / raw)
To: git
[-- Attachment #1: Type: text/plain, Size: 134 bytes --]
An option I found quite useful in quilt. I just copied the
corresponding code from quilt (released under GPLv2) to cg-diff.
Catalin
[-- Attachment #2: patch-color-diff --]
[-- Type: text/plain, Size: 3131 bytes --]
Add "-c" (colorize) option to cg-diff
Signed-off-by: Catalin Marinas <catalin.marinas@arm.com>
Index: cg-diff
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-diff (mode:100755)
+++ uncommitted/cg-diff (mode:100755)
@@ -14,6 +14,8 @@
# -p instead of one ID denotes a parent commit to the specified ID
# (which must not be a tree, obviously).
#
+# -c colorizes the diff output
+#
# Outputs a diff converting the first tree to the second one.
. ${COGITO_LIB}cg-Xlib
@@ -22,7 +24,17 @@
id1=" "
id2=" "
parent=
+opt_color=
+setup_colors()
+{
+ local C=diff_hdr=32:diff_add=36:diff_mod=35:diff_rem=35:diff_hunk=33:diff_ctx=35:diff_cctx=33:patch_offs=33:patch_fuzz=35:patch_fail=31:clear=00
+ [ -n "$COGITO_COLORS" ] && C="$C:$COGITO_COLORS"
+
+ C=${C//=/=\'$'\e'[}
+ C=color_${C//:/m\'; color_}m\'
+ eval $C
+}
# FIXME: The commandline parsing is awful.
@@ -31,6 +43,12 @@
parent=1
fi
+if [ "$1" = "-c" ]; then
+ shift
+ opt_color=1
+ setup_colors
+fi
+
if [ "$1" = "-r" ]; then
shift
id1=$(echo "$1": | cut -d : -f 1)
@@ -44,6 +62,32 @@
shift
fi
+colorize() {
+ if [ "$opt_color" ]; then
+ /usr/bin/gawk '
+ { if (/^(Index:|\-\-\-|\+\+\+|\*\*\*) /)
+ print "'$color_diff_hdr'" $0 "'$color_clear'"
+ else if (/^\+/)
+ print "'$color_diff_add'" $0 "'$color_clear'"
+ else if (/^-/)
+ print "'$color_diff_rem'" $0 "'$color_clear'"
+ else if (/^!/)
+ print "'$color_diff_mod'" $0 "'$color_clear'"
+ else if (/^@@ \-[0-9]+(,[0-9]+)? \+[0-9]+(,[0-9]+)? @@/)
+ print gensub(/^(@@[^@]*@@)([ \t]*)(.*)/,
+ "'$color_diff_hunk'" "\\1" "'$color_clear'" \
+ "\\2" \
+ "'$color_diff_ctx'" "\\3" "'$color_clear'", "")
+ else if (/^\*\*\*\*\*\*\*\*\*\*\*\*\*\*\*/)
+ print "'$color_diff_cctx'" $0 "'$color_clear'"
+ else
+ print
+ }'
+ else
+ cat
+ fi
+}
+
if [ "$parent" ]; then
id2="$id1"
id1=$(parent-id "$id2" | head -n 1)
@@ -71,7 +115,7 @@
# FIXME: Update ret based on what did we match. And take "$@"
# to account after all.
ret=
- git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter"
+ git-diff-cache -r -z $tree | xargs -0 ${COGITO_LIB}cg-Xdiffdo "$tree" uncommitted "$filter" | colorize
[ "$filter" ] && rm $filter
@@ -85,7 +129,7 @@
[ "$id1" = "$id2" ] && die "trying to diff $id1 against itself"
-git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter"
+git-diff-tree -r -z $id1 $id2 | xargs -0 ${COGITO_LIB}cg-Xdiffdo $id1 $id2 "$filter" | colorize
[ "$filter" ] && rm $filter
exit 0
Index: cg-help
===================================================================
--- ca5fef50fb68a3afbb35e1a48ac622f7a964f021/cg-help (mode:100755)
+++ uncommitted/cg-help (mode:100755)
@@ -26,7 +26,7 @@
cg-cancel
cg-clone [-s] SOURCE_LOC [DESTDIR]
cg-commit [-m"Commit message"]... [-e | -E] [FILE]... < log message
- cg-diff [-p] [-r FROM_ID[:TO_ID]] [FILE]...
+ cg-diff [-p] [-c] [-r FROM_ID[:TO_ID]] [FILE]...
cg-export DEST [TREE_ID]
cg-help [COMMAND]
cg-init
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox