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
29e1789b
Commit
29e1789b
authored
Apr 04, 2011
by
Vicent Marti
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Fix the git_tree_write implementation
parent
47d8ec56
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
74 additions
and
60 deletions
+74
-60
include/git2/tree.h
+16
-10
src/tree.c
+58
-50
No files found.
include/git2/tree.h
View file @
29e1789b
...
...
@@ -134,21 +134,27 @@ GIT_EXTERN(const git_oid *) git_tree_entry_id(git_tree_entry *entry);
* @param object pointer to the converted object
* @param repo repository where to lookup the pointed object
* @param entry a tree entry
* @return
a reference to the pointed object in the repository
* @return
0 on success; error code otherwise
*/
GIT_EXTERN
(
int
)
git_tree_entry_2object
(
git_object
**
object_out
,
git_repository
*
repo
,
git_tree_entry
*
entry
);
/**
* Create tree by scanning the index file.
*
* @param object identity for the tree
* @param repository where to lookup for object db
* @param base directory path
* @param path length for base
* @param index entry offset to start scan
* @return number of items added to the tree
* Write a tree to the ODB from the index file
*
* This method will scan the index and write a representation
* of its current state back to disk; it recursively creates
* tree objects for each of the subtrees stored in the index,
* but only returns the OID of the root tree. This is the OID
* that can be used e.g. to create a commit.
*
* The index instance cannot be bare, and needs to be associated
* to an existing repository.
*
* @param oid Pointer where to store the written tree
* @param index Index to write
* @return 0 on success; error code otherwise
*/
GIT_EXTERN
(
int
)
git_tree_create
(
git_oid
*
oid
,
git_repository
*
repo
,
const
char
*
base
,
int
baselen
,
int
entry_no
);
GIT_EXTERN
(
int
)
git_tree_create
_fromindex
(
git_oid
*
oid
,
git_index
*
index
);
/** @} */
GIT_END_DECL
...
...
src/tree.c
View file @
29e1789b
...
...
@@ -137,7 +137,7 @@ static int tree_parse_buffer(git_tree *tree, const char *buffer, const char *buf
while
(
buffer
<
buffer_end
)
{
git_tree_entry
*
entry
;
entry
=
git__
malloc
(
sizeof
(
git_tree_entry
));
entry
=
git__
calloc
(
1
,
sizeof
(
git_tree_entry
));
if
(
entry
==
NULL
)
{
error
=
GIT_ENOMEM
;
break
;
...
...
@@ -178,90 +178,98 @@ int git_tree__parse(git_tree *tree, git_odb_object *obj)
return
tree_parse_buffer
(
tree
,
(
char
*
)
obj
->
raw
.
data
,
(
char
*
)
obj
->
raw
.
data
+
obj
->
raw
.
len
);
}
int
git_tree_create
(
git_oid
*
oid
,
git_repository
*
repo
,
const
char
*
base
,
int
baselen
,
int
entry_no
)
static
int
write_entry
(
char
*
buffer
,
int
mode
,
const
char
*
path
,
size_t
path_len
,
const
git_oid
*
oid
)
{
unsigned
long
size
,
offset
;
char
*
buffer
;
int
nr
,
maxentries
;
git_index
*
index
;
git_odb_stream
*
stream
;
int
error
;
git_index_open_inrepo
(
&
index
,
repo
);
maxentries
=
git_index_entrycount
(
index
);
int
written
;
written
=
sprintf
(
buffer
,
"%o %.*s%c"
,
mode
,
(
int
)
path_len
,
path
,
0
);
memcpy
(
buffer
+
written
,
&
oid
->
id
,
GIT_OID_RAWSZ
);
return
written
+
GIT_OID_RAWSZ
;
}
/* FIXME: A matching error code could not be found. Hence used a close error code GIT_EBAREINDEX */
if
(
maxentries
<=
0
)
{
return
GIT_EBAREINDEX
;
}
static
int
write_index
(
git_oid
*
oid
,
git_index
*
index
,
const
char
*
base
,
int
baselen
,
int
entry_no
,
int
maxentries
)
{
size_t
size
,
offset
;
char
*
buffer
;
int
nr
,
error
;
/* Guess at some random initial size */
size
=
8192
;
size
=
maxentries
*
40
;
buffer
=
git__malloc
(
size
);
if
(
buffer
==
NULL
)
return
GIT_ENOMEM
;
offset
=
0
;
nr
=
entry_no
;
do
{
for
(
nr
=
entry_no
;
nr
<
maxentries
;
++
nr
)
{
git_index_entry
*
entry
=
git_index_get
(
index
,
nr
);
const
char
*
pathname
=
entry
->
path
,
*
filename
,
*
dirname
;
int
pathlen
=
strlen
(
pathname
),
entrylen
;
git_oid
*
entry_oid
;
unsigned
int
mode
;
unsigned
char
*
sha1
;
unsigned
int
write_mode
;
git_oid
subtree_oid
;
git_oid
*
write_oid
;
/* Did we hit the end of the directory? Return how many we wrote */
if
(
baselen
>=
pathlen
||
memcmp
(
base
,
pathname
,
baselen
))
if
(
baselen
>=
pathlen
||
memcmp
(
base
,
pathname
,
baselen
)
!=
0
)
break
;
entry_oid
=
&
entry
->
oid
;
mode
=
entry
->
mode
;
sha1
=
entry_oid
->
id
;
/* Do we have _further_ subdirectories? */
filename
=
pathname
+
baselen
;
dirname
=
strchr
(
filename
,
'/'
);
write_oid
=
&
entry
->
oid
;
write_mode
=
entry
->
mode
;
if
(
dirname
)
{
int
subdir_written
;
subdir_written
=
git_tree_create
(
oid
,
repo
,
pathname
,
dirname
-
pathname
+
1
,
nr
);
if
(
subdir_written
==
GIT_ENOMEM
)
return
GIT_ENOMEM
;
#if 0
if (entry->mode != S_IFDIR) {
free(buffer);
return GIT_EOBJCORRUPTED;
}
#endif
subdir_written
=
write_index
(
&
subtree_oid
,
index
,
pathname
,
dirname
-
pathname
+
1
,
nr
,
maxentries
);
if
(
subdir_written
<
GIT_SUCCESS
)
{
free
(
buffer
);
return
subdir_written
;
}
nr
+=
subdir_written
;
nr
=
subdir_written
-
1
;
/* Now we need to write out the directory entry into this tree.. */
mode
=
S_IFDIR
;
pathlen
=
dirname
-
pathname
;
/* ..but the directory entry doesn't count towards the total count */
nr
--
;
sha1
=
oid
->
id
;
write_oid
=
&
subtree_oid
;
write_mode
=
S_IFDIR
;
}
entrylen
=
pathlen
-
baselen
;
if
(
offset
+
entrylen
+
100
>
size
)
{
size
=
alloc_nr
(
offset
+
entrylen
+
100
);
if
(
offset
+
entrylen
+
32
>
size
)
{
size
=
alloc_nr
(
offset
+
entrylen
+
32
);
buffer
=
git__realloc
(
buffer
,
size
);
if
(
buffer
==
NULL
)
return
GIT_ENOMEM
;
}
offset
+=
sprintf
(
buffer
+
offset
,
"%o %.*s"
,
mode
,
entrylen
,
filename
);
buffer
[
offset
++
]
=
0
;
memcpy
(
buffer
+
offset
,
sha1
,
GIT_OID_RAWSZ
);
offset
+=
GIT_OID_RAWSZ
;
nr
++
;
}
while
(
nr
<
maxentries
);
if
((
error
=
git_odb_open_wstream
(
&
stream
,
repo
->
db
,
offset
,
GIT_OBJ_TREE
))
<
GIT_SUCCESS
)
return
error
;
stream
->
write
(
stream
,
buffer
,
offset
);
error
=
stream
->
finalize_write
(
oid
,
stream
);
stream
->
free
(
stream
);
offset
+=
write_entry
(
buffer
+
offset
,
write_mode
,
filename
,
entrylen
,
write_oid
);
}
error
=
git_odb_write
(
oid
,
index
->
repository
->
db
,
buffer
,
offset
,
GIT_OBJ_TREE
);
free
(
buffer
);
return
(
error
==
GIT_SUCCESS
)
?
nr
:
error
;
}
int
git_tree_create_fromindex
(
git_oid
*
oid
,
git_index
*
index
)
{
int
error
;
if
(
index
->
repository
==
NULL
)
return
GIT_EBAREINDEX
;
return
nr
;
error
=
write_index
(
oid
,
index
,
""
,
0
,
0
,
git_index_entrycount
(
index
));
return
(
error
<
GIT_SUCCESS
)
?
error
:
GIT_SUCCESS
;
}
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