summaryrefslogtreecommitdiff
path: root/src/tree.c
diff options
context:
space:
mode:
authorVicent Marti <tanoku@gmail.com>2010-10-08 13:52:17 +0300
committerVicent Marti <tanoku@gmail.com>2010-10-08 13:52:17 +0300
commite4def81aab5df3ce1bd8622f3c89224d5910a97b (patch)
tree70f358a8d5eea6ed395b58f92c088f2855597d9f /src/tree.c
parent0ba7a0318652e5e89101e9ee72cb1356c21cef56 (diff)
downloadlibgit2-e4def81aab5df3ce1bd8622f3c89224d5910a97b.tar.gz
Fix issue 3 (memory corruption resize_tree_array)
The tree array wasn't being initialized when instantiating a tree object in memory instead of loading it from disk. New unit tests added to check for the problem. Signed-off-by: Vicent Marti <tanoku@gmail.com>
Diffstat (limited to 'src/tree.c')
-rw-r--r--src/tree.c25
1 files changed, 19 insertions, 6 deletions
diff --git a/src/tree.c b/src/tree.c
index b809290b2..28bc035d2 100644
--- a/src/tree.c
+++ b/src/tree.c
@@ -29,17 +29,24 @@
#include "tree.h"
#include "git/repository.h"
-static void resize_tree_array(git_tree *tree)
+static int resize_tree_array(git_tree *tree)
{
git_tree_entry **new_entries;
- tree->array_size = tree->array_size * 2;
+ tree->array_size *= 2;
+ if (tree->array_size == 0)
+ tree->array_size = 8;
new_entries = git__malloc(tree->array_size * sizeof(git_tree_entry *));
+ if (new_entries == NULL)
+ return GIT_ENOMEM;
+
memcpy(new_entries, tree->entries, tree->entry_count * sizeof(git_tree_entry *));
free(tree->entries);
tree->entries = new_entries;
+
+ return GIT_SUCCESS;
}
int entry_cmp(const void *key, const void *array_member)
@@ -166,17 +173,18 @@ size_t git_tree_entrycount(git_tree *tree)
return tree->entry_count;
}
-void git_tree_add_entry(git_tree *tree, const git_oid *id, const char *filename, int attributes)
+int git_tree_add_entry(git_tree *tree, const git_oid *id, const char *filename, int attributes)
{
git_tree_entry *entry;
assert(tree && id && filename);
if (tree->entry_count >= tree->array_size)
- resize_tree_array(tree);
+ if (resize_tree_array(tree) < 0)
+ return GIT_ENOMEM;
if ((entry = git__malloc(sizeof(git_tree_entry))) == NULL)
- return;
+ return GIT_ENOMEM;
memset(entry, 0x0, sizeof(git_tree_entry));
@@ -189,6 +197,7 @@ void git_tree_add_entry(git_tree *tree, const git_oid *id, const char *filename,
entry_resort(tree);
tree->object.modified = 1;
+ return GIT_SUCCESS;
}
int git_tree_remove_entry_byindex(git_tree *tree, int idx)
@@ -277,11 +286,15 @@ int git_tree__parse(git_tree *tree)
tree->array_size = (tree->object.source.raw.len / avg_entry_size) + 1;
tree->entries = git__malloc(tree->array_size * sizeof(git_tree_entry *));
+ if (tree->entries == NULL)
+ return GIT_ENOMEM;
+
while (buffer < buffer_end) {
git_tree_entry *entry;
if (tree->entry_count >= tree->array_size)
- resize_tree_array(tree);
+ if (resize_tree_array(tree) < 0)
+ return GIT_ENOMEM;
entry = git__malloc(sizeof(git_tree_entry));
if (entry == NULL) {