Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
G
git2
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
lvzhengyang
git2
Commits
d9ecaf8c
Commit
d9ecaf8c
authored
Apr 07, 2013
by
Vicent Marti
Browse files
Options
Browse Files
Download
Plain Diff
Merge remote-tracking branch 'gnprice/revwalk' into development
parents
22744837
2e233285
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
363 additions
and
15 deletions
+363
-15
examples/.gitignore
+1
-0
examples/rev-list.c
+116
-0
examples/test/test-rev-list.sh
+95
-0
include/git2/revparse.h
+13
-0
include/git2/revwalk.h
+16
-1
src/revparse.c
+25
-0
src/revwalk.c
+25
-0
tests-clar/refs/revparse.c
+43
-0
tests-clar/revwalk/basic.c
+29
-14
No files found.
examples/.gitignore
View file @
d9ecaf8c
general
showindex
diff
rev-list
*.dSYM
examples/rev-list.c
0 → 100644
View file @
d9ecaf8c
#include <stdio.h>
#include <string.h>
#include <git2.h>
static
void
check_error
(
int
error_code
,
const
char
*
action
)
{
if
(
!
error_code
)
return
;
const
git_error
*
error
=
giterr_last
();
fprintf
(
stderr
,
"Error %d %s: %s
\n
"
,
-
error_code
,
action
,
(
error
&&
error
->
message
)
?
error
->
message
:
"???"
);
exit
(
1
);
}
static
int
push_commit
(
git_revwalk
*
walk
,
git_object
*
obj
,
int
hide
)
{
if
(
hide
)
return
git_revwalk_hide
(
walk
,
git_object_id
(
obj
));
else
return
git_revwalk_push
(
walk
,
git_object_id
(
obj
));
}
static
int
push_spec
(
git_repository
*
repo
,
git_revwalk
*
walk
,
const
char
*
spec
,
int
hide
)
{
int
error
;
git_object
*
obj
;
if
((
error
=
git_revparse_single
(
&
obj
,
repo
,
spec
)))
return
error
;
return
push_commit
(
walk
,
obj
,
hide
);
}
static
int
push_range
(
git_repository
*
repo
,
git_revwalk
*
walk
,
const
char
*
range
,
int
hide
)
{
git_object
*
left
,
*
right
;
int
threedots
;
int
error
=
0
;
if
((
error
=
git_revparse_rangelike
(
&
left
,
&
right
,
&
threedots
,
repo
,
range
)))
return
error
;
if
(
threedots
)
{
/* TODO: support "<commit>...<commit>" */
return
GIT_EINVALIDSPEC
;
}
if
((
error
=
push_commit
(
walk
,
left
,
!
hide
)))
goto
out
;
error
=
push_commit
(
walk
,
right
,
hide
);
out:
git_object_free
(
left
);
git_object_free
(
right
);
return
error
;
}
static
int
revwalk_parseopts
(
git_repository
*
repo
,
git_revwalk
*
walk
,
int
nopts
,
const
char
*
const
*
opts
)
{
int
hide
,
i
,
error
;
unsigned
int
sorting
=
GIT_SORT_NONE
;
hide
=
0
;
for
(
i
=
0
;
i
<
nopts
;
i
++
)
{
if
(
!
strcmp
(
opts
[
i
],
"--topo-order"
))
{
sorting
=
GIT_SORT_TOPOLOGICAL
|
(
sorting
&
GIT_SORT_REVERSE
);
git_revwalk_sorting
(
walk
,
sorting
);
}
else
if
(
!
strcmp
(
opts
[
i
],
"--date-order"
))
{
sorting
=
GIT_SORT_TIME
|
(
sorting
&
GIT_SORT_REVERSE
);
git_revwalk_sorting
(
walk
,
sorting
);
}
else
if
(
!
strcmp
(
opts
[
i
],
"--reverse"
))
{
sorting
=
(
sorting
&
~
GIT_SORT_REVERSE
)
|
((
sorting
&
GIT_SORT_REVERSE
)
?
0
:
GIT_SORT_REVERSE
);
git_revwalk_sorting
(
walk
,
sorting
);
}
else
if
(
!
strcmp
(
opts
[
i
],
"--not"
))
{
hide
=
!
hide
;
}
else
if
(
opts
[
i
][
0
]
==
'^'
)
{
if
((
error
=
push_spec
(
repo
,
walk
,
opts
[
i
]
+
1
,
!
hide
)))
return
error
;
}
else
if
(
strstr
(
opts
[
i
],
".."
))
{
if
((
error
=
push_range
(
repo
,
walk
,
opts
[
i
],
hide
)))
return
error
;
}
else
{
if
((
error
=
push_spec
(
repo
,
walk
,
opts
[
i
],
hide
)))
return
error
;
}
}
return
0
;
}
int
main
(
int
argc
,
char
**
argv
)
{
int
error
;
git_repository
*
repo
;
git_revwalk
*
walk
;
git_oid
oid
;
char
buf
[
41
];
error
=
git_repository_open_ext
(
&
repo
,
"."
,
0
,
NULL
);
check_error
(
error
,
"opening repository"
);
error
=
git_revwalk_new
(
&
walk
,
repo
);
check_error
(
error
,
"allocating revwalk"
);
error
=
revwalk_parseopts
(
repo
,
walk
,
argc
-
1
,
argv
+
1
);
check_error
(
error
,
"parsing options"
);
while
(
!
git_revwalk_next
(
&
oid
,
walk
))
{
git_oid_fmt
(
buf
,
&
oid
);
buf
[
40
]
=
'\0'
;
printf
(
"%s
\n
"
,
buf
);
}
return
0
;
}
examples/test/test-rev-list.sh
0 → 100755
View file @
d9ecaf8c
#!/bin/bash
THIS_FILE
=
"
$(
readlink
-f
"
$0
"
)
"
ROOT
=
"
$(
dirname
"
$(
dirname
"
$(
dirname
"
$THIS_FILE
"
)
"
)
"
)
"
PROGRAM
=
"
$ROOT
"
/examples/rev-list
LIBDIR
=
"
$ROOT
"
/build
REPO
=
"
$ROOT
"
/tests-clar/resources/testrepo.git
cd
"
$REPO
"
run
()
{
LD_LIBRARY_PATH
=
"
$LIBDIR
"
"
$PROGRAM
"
"
$@
"
}
diff
-u
- <
(
run
--date-order
a4a7dce
)
<<
EOF
a4a7dce85cf63874e984719f4fdd239f5145052f
c47800c7266a2be04c571c04d5a6614691ea99bd
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
5b5b025afb0b4c913b4c338a42934a3863bf3644
8496071c1b46c854b31185ea97743be6a8774479
EOF
out
=
"
$(
run
--topo-order
a4a7dce
)
"
diff
-q
- <
(
echo
-n
"
$out
"
)
<<
EOF
>/dev/null ||
a4a7dce85cf63874e984719f4fdd239f5145052f
c47800c7266a2be04c571c04d5a6614691ea99bd
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
5b5b025afb0b4c913b4c338a42934a3863bf3644
8496071c1b46c854b31185ea97743be6a8774479
EOF
diff
-u
- <
(
echo
"
$out
"
)
<<
EOF
a4a7dce85cf63874e984719f4fdd239f5145052f
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
c47800c7266a2be04c571c04d5a6614691ea99bd
5b5b025afb0b4c913b4c338a42934a3863bf3644
8496071c1b46c854b31185ea97743be6a8774479
EOF
diff
-u
- <
(
run
--date-order
--reverse
a4a7dce
)
<<
EOF
8496071c1b46c854b31185ea97743be6a8774479
5b5b025afb0b4c913b4c338a42934a3863bf3644
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
9fd738e8f7967c078dceed8190330fc8648ee56a
c47800c7266a2be04c571c04d5a6614691ea99bd
a4a7dce85cf63874e984719f4fdd239f5145052f
EOF
out
=
$(
run
--topo-order
--reverse
a4a7dce
)
diff
-q
- <
(
echo
-n
"
$out
"
)
<<
EOF
>/dev/null ||
8496071c1b46c854b31185ea97743be6a8774479
5b5b025afb0b4c913b4c338a42934a3863bf3644
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
9fd738e8f7967c078dceed8190330fc8648ee56a
c47800c7266a2be04c571c04d5a6614691ea99bd
a4a7dce85cf63874e984719f4fdd239f5145052f
EOF
diff
-u
- <
(
echo
"
$out
"
)
<<
EOF
8496071c1b46c854b31185ea97743be6a8774479
5b5b025afb0b4c913b4c338a42934a3863bf3644
c47800c7266a2be04c571c04d5a6614691ea99bd
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
9fd738e8f7967c078dceed8190330fc8648ee56a
a4a7dce85cf63874e984719f4fdd239f5145052f
EOF
out
=
"
$(
run
--date-order
--topo-order
--reverse
--reverse
a4a7dce
)
"
diff
-q
- <
(
echo
-n
"
$out
"
)
<<
EOF
>/dev/null ||
a4a7dce85cf63874e984719f4fdd239f5145052f
c47800c7266a2be04c571c04d5a6614691ea99bd
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
5b5b025afb0b4c913b4c338a42934a3863bf3644
8496071c1b46c854b31185ea97743be6a8774479
EOF
diff
-u
- <
(
echo
"
$out
"
)
<<
EOF
a4a7dce85cf63874e984719f4fdd239f5145052f
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
c47800c7266a2be04c571c04d5a6614691ea99bd
5b5b025afb0b4c913b4c338a42934a3863bf3644
8496071c1b46c854b31185ea97743be6a8774479
EOF
diff
-u
- <
(
run ^9fd738e~2 9fd738e
)
<<
EOF
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
EOF
diff
-u
- <
(
run
--not
9fd738e..9fd738e~2
)
<<
EOF
9fd738e8f7967c078dceed8190330fc8648ee56a
4a202b346bb0fb0db7eff3cffeb3c70babbd2045
EOF
include/git2/revparse.h
View file @
d9ecaf8c
...
...
@@ -32,6 +32,19 @@ GIT_BEGIN_DECL
*/
GIT_EXTERN
(
int
)
git_revparse_single
(
git_object
**
out
,
git_repository
*
repo
,
const
char
*
spec
);
/**
* Parse a string with the form of a revision range, as accepted by
* `git rev-list`, `git diff`, and others.
*
* @param left (output) the left-hand commit
* @param right (output) the right-hand commit
* @param threedots (output) 0 if the endpoints are separated by two dots, 1 if by three
* @param repo the repository to find the commits in
* @param rangelike the rangelike string to be parsed
* @return 0 on success, or any error `git_revparse_single` can return
*/
GIT_EXTERN
(
int
)
git_revparse_rangelike
(
git_object
**
left
,
git_object
**
right
,
int
*
threedots
,
git_repository
*
repo
,
const
char
*
rangelike
);
/** @} */
GIT_END_DECL
#endif
include/git2/revwalk.h
View file @
d9ecaf8c
...
...
@@ -92,7 +92,7 @@ GIT_EXTERN(void) git_revwalk_reset(git_revwalk *walker);
*
* The given commit will be used as one of the roots
* when starting the revision walk. At least one commit
* must be pushed
the repository
before a walk can
* must be pushed
onto the walker
before a walk can
* be started.
*
* @param walk the walker being used for the traversal.
...
...
@@ -217,6 +217,21 @@ GIT_EXTERN(int) git_revwalk_next(git_oid *out, git_revwalk *walk);
GIT_EXTERN
(
void
)
git_revwalk_sorting
(
git_revwalk
*
walk
,
unsigned
int
sort_mode
);
/**
* Push and hide the respective endpoints of the given range.
*
* The range should be of the form
* <commit>..<commit>
* where each <commit> is in the form accepted by 'git_revparse_single'.
* The left-hand commit will be hidden and the right-hand commit pushed.
*
* @param walk the walker being used for the traversal
* @param range the range
* @return 0 or an error code
*
*/
GIT_EXTERN
(
int
)
git_revwalk_push_range
(
git_revwalk
*
walk
,
const
char
*
range
);
/**
* Free a revision walker previously allocated.
*
* @param walk traversal handle to close. If NULL nothing occurs.
...
...
src/revparse.c
View file @
d9ecaf8c
...
...
@@ -867,3 +867,28 @@ cleanup:
git_buf_free
(
&
buf
);
return
error
;
}
int
git_revparse_rangelike
(
git_object
**
left
,
git_object
**
right
,
int
*
threedots
,
git_repository
*
repo
,
const
char
*
rangelike
)
{
int
error
=
0
;
const
char
*
p
,
*
q
;
char
*
revspec
;
p
=
strstr
(
rangelike
,
".."
);
if
(
!
p
)
{
giterr_set
(
GITERR_INVALID
,
"Malformed range (or rangelike syntax): %s"
,
rangelike
);
return
GIT_EINVALIDSPEC
;
}
else
if
(
p
[
2
]
==
'.'
)
{
*
threedots
=
1
;
q
=
p
+
3
;
}
else
{
*
threedots
=
0
;
q
=
p
+
2
;
}
revspec
=
git__substrdup
(
rangelike
,
p
-
rangelike
);
error
=
(
git_revparse_single
(
left
,
repo
,
revspec
)
||
git_revparse_single
(
right
,
repo
,
q
));
git__free
(
revspec
);
return
error
;
}
src/revwalk.c
View file @
d9ecaf8c
...
...
@@ -11,6 +11,7 @@
#include "pool.h"
#include "revwalk.h"
#include "git2/revparse.h"
#include "merge.h"
#include <regex.h>
...
...
@@ -228,6 +229,30 @@ int git_revwalk_push_ref(git_revwalk *walk, const char *refname)
return
push_ref
(
walk
,
refname
,
0
);
}
int
git_revwalk_push_range
(
git_revwalk
*
walk
,
const
char
*
range
)
{
git_object
*
left
,
*
right
;
int
threedots
;
int
error
=
0
;
if
((
error
=
git_revparse_rangelike
(
&
left
,
&
right
,
&
threedots
,
walk
->
repo
,
range
)))
return
error
;
if
(
threedots
)
{
/* TODO: support "<commit>...<commit>" */
giterr_set
(
GITERR_INVALID
,
"Symmetric differences not implemented in revwalk"
);
return
GIT_EINVALIDSPEC
;
}
if
((
error
=
push_commit
(
walk
,
git_object_id
(
left
),
1
)))
goto
out
;
error
=
push_commit
(
walk
,
git_object_id
(
right
),
0
);
out:
git_object_free
(
left
);
git_object_free
(
right
);
return
error
;
}
int
git_revwalk_hide_ref
(
git_revwalk
*
walk
,
const
char
*
refname
)
{
assert
(
walk
&&
refname
);
...
...
tests-clar/refs/revparse.c
View file @
d9ecaf8c
...
...
@@ -32,6 +32,33 @@ static void test_object(const char *spec, const char *expected_oid)
test_object_inrepo
(
spec
,
expected_oid
,
g_repo
);
}
static
void
test_rangelike
(
const
char
*
rangelike
,
const
char
*
expected_left
,
const
char
*
expected_right
,
int
expected_threedots
)
{
char
objstr
[
64
]
=
{
0
};
git_object
*
left
,
*
right
;
int
threedots
;
int
error
;
error
=
git_revparse_rangelike
(
&
left
,
&
right
,
&
threedots
,
g_repo
,
rangelike
);
if
(
expected_left
!=
NULL
)
{
cl_assert_equal_i
(
0
,
error
);
cl_assert_equal_i
(
threedots
,
expected_threedots
);
git_oid_fmt
(
objstr
,
git_object_id
(
left
));
cl_assert_equal_s
(
objstr
,
expected_left
);
git_oid_fmt
(
objstr
,
git_object_id
(
right
));
cl_assert_equal_s
(
objstr
,
expected_right
);
}
else
cl_assert
(
error
!=
0
);
git_object_free
(
left
);
git_object_free
(
right
);
}
void
test_refs_revparse__initialize
(
void
)
{
cl_git_pass
(
git_repository_open
(
&
g_repo
,
cl_fixture
(
"testrepo.git"
)));
...
...
@@ -596,3 +623,19 @@ void test_refs_revparse__try_to_retrieve_branch_before_abbrev_sha(void)
git_object_free
(
target
);
cl_git_sandbox_cleanup
();
}
void
test_refs_revparse__range
(
void
)
{
test_rangelike
(
"be3563a^1..be3563a"
,
"9fd738e8f7967c078dceed8190330fc8648ee56a"
,
"be3563ae3f795b2b4353bcce3a527ad0a4f7f644"
,
0
);
test_rangelike
(
"be3563a^1...be3563a"
,
"9fd738e8f7967c078dceed8190330fc8648ee56a"
,
"be3563ae3f795b2b4353bcce3a527ad0a4f7f644"
,
1
);
test_rangelike
(
"be3563a^1.be3563a"
,
NULL
,
NULL
,
0
);
}
tests-clar/revwalk/basic.c
View file @
d9ecaf8c
#include "clar_libgit2.h"
/*
$ git log --oneline --graph --decorate
* a4a7dce (HEAD, br2) Merge branch 'master' into br2
* a4a7dce [0] Merge branch 'master' into br2
|\
| * 9fd738e
(master)
a fourth commit
| * 4a202b3 a third commit
* | c47800c branch commit one
| * 9fd738e
[1]
a fourth commit
| * 4a202b3
[2]
a third commit
* | c47800c
[3]
branch commit one
|/
* 5b5b025 another commit
* 8496071 testing
* 5b5b025
[5]
another commit
* 8496071
[4]
testing
*/
static
const
char
*
commit_head
=
"a4a7dce85cf63874e984719f4fdd239f5145052f"
;
...
...
@@ -39,6 +38,10 @@ static const int commit_sorting_time_reverse[][6] = {
{
4
,
5
,
2
,
1
,
3
,
0
}
};
static
const
int
commit_sorting_segment
[][
6
]
=
{
{
1
,
2
,
-
1
,
-
1
,
-
1
,
-
1
}
};
#define commit_count 6
static
const
int
result_bytes
=
24
;
...
...
@@ -57,22 +60,17 @@ static int get_commit_index(git_oid *raw_oid)
return
-
1
;
}
static
int
test_walk
(
git_revwalk
*
walk
,
const
git_oid
*
root
,
int
flags
,
const
int
possible_results
[][
6
],
int
results_count
)
static
int
test_walk
_only
(
git_revwalk
*
walk
,
const
int
possible_results
[][
commit_count
],
int
results_count
)
{
git_oid
oid
;
int
i
;
int
result_array
[
commit_count
];
git_revwalk_sorting
(
walk
,
flags
);
git_revwalk_push
(
walk
,
root
);
for
(
i
=
0
;
i
<
commit_count
;
++
i
)
result_array
[
i
]
=
-
1
;
i
=
0
;
while
(
git_revwalk_next
(
&
oid
,
walk
)
==
0
)
{
result_array
[
i
++
]
=
get_commit_index
(
&
oid
);
/*{
...
...
@@ -91,6 +89,15 @@ static int test_walk(git_revwalk *walk, const git_oid *root,
return
GIT_ERROR
;
}
static
int
test_walk
(
git_revwalk
*
walk
,
const
git_oid
*
root
,
int
flags
,
const
int
possible_results
[][
6
],
int
results_count
)
{
git_revwalk_sorting
(
walk
,
flags
);
git_revwalk_push
(
walk
,
root
);
return
test_walk_only
(
walk
,
possible_results
,
results_count
);
}
static
git_repository
*
_repo
;
static
git_revwalk
*
_walk
;
...
...
@@ -189,3 +196,11 @@ void test_revwalk_basic__disallow_non_commit(void)
cl_git_pass
(
git_oid_fromstr
(
&
oid
,
"521d87c1ec3aef9824daf6d96cc0ae3710766d91"
));
cl_git_fail
(
git_revwalk_push
(
_walk
,
&
oid
));
}
void
test_revwalk_basic__push_range
(
void
)
{
git_revwalk_reset
(
_walk
);
git_revwalk_sorting
(
_walk
,
0
);
cl_git_pass
(
git_revwalk_push_range
(
_walk
,
"9fd738e~2..9fd738e"
));
cl_git_pass
(
test_walk_only
(
_walk
,
commit_sorting_segment
,
1
));
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment