Add range checking around cache opts Add a git_cache_set_max_object_size method that does more checking around setting the max object size. Also add a git_cache_size to read the number of objects currently in the cache. This makes it easier to write tests.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100
diff --git a/src/cache.c b/src/cache.c
index f8cddea..263f736 100644
--- a/src/cache.c
+++ b/src/cache.c
@@ -19,17 +19,28 @@ GIT__USE_OIDMAP
bool git_cache__enabled = true;
-size_t git_cache__max_object_size[8] = {
- 0, /* GIT_OBJ__EXT1 */
+static size_t git_cache__max_object_size[8] = {
+ 0, /* GIT_OBJ__EXT1 */
4096, /* GIT_OBJ_COMMIT */
4096, /* GIT_OBJ_TREE */
- 0, /* GIT_OBJ_BLOB */
+ 0, /* GIT_OBJ_BLOB */
4096, /* GIT_OBJ_TAG */
- 0, /* GIT_OBJ__EXT2 */
- 0, /* GIT_OBJ_OFS_DELTA */
- 0 /* GIT_OBJ_REF_DELTA */
+ 0, /* GIT_OBJ__EXT2 */
+ 0, /* GIT_OBJ_OFS_DELTA */
+ 0 /* GIT_OBJ_REF_DELTA */
};
+int git_cache_set_max_object_size(git_otype type, size_t size)
+{
+ if (type < 0 || (size_t)type >= ARRAY_SIZE(git_cache__max_object_size)) {
+ giterr_set(GITERR_INVALID, "type out of range");
+ return -1;
+ }
+
+ git_cache__max_object_size[type] = size;
+ return 0;
+}
+
void git_cache_dump_stats(git_cache *cache)
{
git_cached_obj *object;
diff --git a/src/cache.h b/src/cache.h
index 8b2aa1f..13b630e 100644
--- a/src/cache.h
+++ b/src/cache.h
@@ -20,9 +20,6 @@ enum {
GIT_CACHE_STORE_PARSED = 2
};
-extern bool git_cache__enabled;
-extern size_t git_cache__max_object_size[8];
-
typedef struct {
git_oid oid;
int16_t type;
@@ -37,6 +34,10 @@ typedef struct {
size_t used_memory;
} git_cache;
+extern bool git_cache__enabled;
+
+int git_cache_set_max_object_size(git_otype type, size_t size);
+
int git_cache_init(git_cache *cache);
void git_cache_free(git_cache *cache);
@@ -47,6 +48,11 @@ git_odb_object *git_cache_get_raw(git_cache *cache, const git_oid *oid);
git_object *git_cache_get_parsed(git_cache *cache, const git_oid *oid);
void *git_cache_get_any(git_cache *cache, const git_oid *oid);
+GIT_INLINE(size_t) git_cache_size(git_cache *cache)
+{
+ return (size_t)kh_size(cache->map);
+}
+
GIT_INLINE(void) git_cached_obj_incref(void *_obj)
{
git_cached_obj *obj = _obj;
diff --git a/src/util.c b/src/util.c
index 0b5fbdc..1ed5d5d 100644
--- a/src/util.c
+++ b/src/util.c
@@ -95,14 +95,16 @@ int git_libgit2_opts(int key, ...)
error = git_futils_dirs_set(error, va_arg(ap, const char *));
break;
- case GIT_OPT_SET_CACHE_LIMIT: {
+ case GIT_OPT_SET_CACHE_LIMIT:
+ {
git_otype type = (git_otype)va_arg(ap, int);
- git_cache__max_object_size[type] = va_arg(ap, size_t);
+ size_t size = va_arg(ap, size_t);
+ error = git_cache_set_max_object_size(type, size);
break;
}
case GIT_OPT_ENABLE_CACHING:
- git_cache__enabled = va_arg(ap, int);
+ git_cache__enabled = (va_arg(ap, int) != 0);
break;
}