git-log --cherry-pick A...B
This is meant to be a saner replacement for "git-cherry". When used with "A...B", this filters out commits whose patch text has the same patch-id as a commit on the other side. It would probably most useful to use with --left-right. Signed-off-by: Junio C Hamano <junkio@cox.net>
This commit is contained in:
parent
5d23e133d2
commit
d7a17cad97
88
revision.c
88
revision.c
@ -8,6 +8,7 @@
|
|||||||
#include "revision.h"
|
#include "revision.h"
|
||||||
#include "grep.h"
|
#include "grep.h"
|
||||||
#include "reflog-walk.h"
|
#include "reflog-walk.h"
|
||||||
|
#include "patch-ids.h"
|
||||||
|
|
||||||
static char *path_name(struct name_path *path, const char *name)
|
static char *path_name(struct name_path *path, const char *name)
|
||||||
{
|
{
|
||||||
@ -422,6 +423,86 @@ static void add_parents_to_list(struct rev_info *revs, struct commit *commit, st
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void cherry_pick_list(struct commit_list *list)
|
||||||
|
{
|
||||||
|
struct commit_list *p;
|
||||||
|
int left_count = 0, right_count = 0;
|
||||||
|
int left_first;
|
||||||
|
struct patch_ids ids;
|
||||||
|
|
||||||
|
/* First count the commits on the left and on the right */
|
||||||
|
for (p = list; p; p = p->next) {
|
||||||
|
struct commit *commit = p->item;
|
||||||
|
unsigned flags = commit->object.flags;
|
||||||
|
if (flags & BOUNDARY)
|
||||||
|
;
|
||||||
|
else if (flags & SYMMETRIC_LEFT)
|
||||||
|
left_count++;
|
||||||
|
else
|
||||||
|
right_count++;
|
||||||
|
}
|
||||||
|
|
||||||
|
left_first = left_count < right_count;
|
||||||
|
init_patch_ids(&ids);
|
||||||
|
|
||||||
|
/* Compute patch-ids for one side */
|
||||||
|
for (p = list; p; p = p->next) {
|
||||||
|
struct commit *commit = p->item;
|
||||||
|
unsigned flags = commit->object.flags;
|
||||||
|
|
||||||
|
if (flags & BOUNDARY)
|
||||||
|
continue;
|
||||||
|
/*
|
||||||
|
* If we have fewer left, left_first is set and we omit
|
||||||
|
* commits on the right branch in this loop. If we have
|
||||||
|
* fewer right, we skip the left ones.
|
||||||
|
*/
|
||||||
|
if (left_first != !!(flags & SYMMETRIC_LEFT))
|
||||||
|
continue;
|
||||||
|
commit->util = add_commit_patch_id(commit, &ids);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check the other side */
|
||||||
|
for (p = list; p; p = p->next) {
|
||||||
|
struct commit *commit = p->item;
|
||||||
|
struct patch_id *id;
|
||||||
|
unsigned flags = commit->object.flags;
|
||||||
|
|
||||||
|
if (flags & BOUNDARY)
|
||||||
|
continue;
|
||||||
|
/*
|
||||||
|
* If we have fewer left, left_first is set and we omit
|
||||||
|
* commits on the left branch in this loop.
|
||||||
|
*/
|
||||||
|
if (left_first == !!(flags & SYMMETRIC_LEFT))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Have we seen the same patch id?
|
||||||
|
*/
|
||||||
|
id = has_commit_patch_id(commit, &ids);
|
||||||
|
if (!id)
|
||||||
|
continue;
|
||||||
|
id->seen = 1;
|
||||||
|
commit->object.flags |= SHOWN;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Now check the original side for seen ones */
|
||||||
|
for (p = list; p; p = p->next) {
|
||||||
|
struct commit *commit = p->item;
|
||||||
|
struct patch_id *ent;
|
||||||
|
|
||||||
|
ent = commit->util;
|
||||||
|
if (!ent)
|
||||||
|
continue;
|
||||||
|
if (ent->seen)
|
||||||
|
commit->object.flags |= SHOWN;
|
||||||
|
commit->util = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
free_patch_ids(&ids);
|
||||||
|
}
|
||||||
|
|
||||||
static void limit_list(struct rev_info *revs)
|
static void limit_list(struct rev_info *revs)
|
||||||
{
|
{
|
||||||
struct commit_list *list = revs->commits;
|
struct commit_list *list = revs->commits;
|
||||||
@ -449,6 +530,9 @@ static void limit_list(struct rev_info *revs)
|
|||||||
continue;
|
continue;
|
||||||
p = &commit_list_insert(commit, p)->next;
|
p = &commit_list_insert(commit, p)->next;
|
||||||
}
|
}
|
||||||
|
if (revs->cherry_pick)
|
||||||
|
cherry_pick_list(newlist);
|
||||||
|
|
||||||
revs->commits = newlist;
|
revs->commits = newlist;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -913,6 +997,10 @@ int setup_revisions(int argc, const char **argv, struct rev_info *revs, const ch
|
|||||||
revs->left_right = 1;
|
revs->left_right = 1;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
if (!strcmp(arg, "--cherry-pick")) {
|
||||||
|
revs->cherry_pick = 1;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
if (!strcmp(arg, "--objects")) {
|
if (!strcmp(arg, "--objects")) {
|
||||||
revs->tag_objects = 1;
|
revs->tag_objects = 1;
|
||||||
revs->tree_objects = 1;
|
revs->tree_objects = 1;
|
||||||
|
@ -47,6 +47,7 @@ struct rev_info {
|
|||||||
left_right:1,
|
left_right:1,
|
||||||
parents:1,
|
parents:1,
|
||||||
reverse:1,
|
reverse:1,
|
||||||
|
cherry_pick:1,
|
||||||
first_parent_only:1;
|
first_parent_only:1;
|
||||||
|
|
||||||
/* Diff flags */
|
/* Diff flags */
|
||||||
|
Loading…
Reference in New Issue
Block a user