Skip to content

Commit 1196de4

Browse files
committed
util: introduce git__strlcmp
Introduce a utility function that compares a NUL terminated string to a possibly not-NUL terminated string with length. This is similar to `strncmp` but with an added check to ensure that the lengths match (not just the `size` portion of the two strings).
1 parent e5a3277 commit 1196de4

File tree

2 files changed

+22
-0
lines changed

2 files changed

+22
-0
lines changed

src/util.h

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -168,6 +168,17 @@ extern int git__strncasecmp(const char *a, const char *b, size_t sz);
168168

169169
extern int git__strcasesort_cmp(const char *a, const char *b);
170170

171+
/*
172+
* Compare some NUL-terminated `a` to a possibly non-NUL terminated
173+
* `b` of length `b_len`; like `strncmp` but ensuring that
174+
* `strlen(a) == b_len` as well.
175+
*/
176+
GIT_INLINE(int) git__strlcmp(const char *a, const char *b, size_t b_len)
177+
{
178+
int cmp = strncmp(a, b, b_len);
179+
return cmp ? cmp : (int)a[b_len];
180+
}
181+
171182
typedef struct {
172183
git_atomic32 refcount;
173184
void *owner;

tests/core/string.c

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,3 +123,14 @@ void test_core_string__strcasecmp(void)
123123
cl_assert(git__strcasecmp("et", "e\342\202\254ghi=") < 0);
124124
cl_assert(git__strcasecmp("\303\215", "\303\255") < 0);
125125
}
126+
127+
void test_core_string__strlcmp(void)
128+
{
129+
const char foo[3] = { 'f', 'o', 'o' };
130+
131+
cl_assert(git__strlcmp("foo", "foo", 3) == 0);
132+
cl_assert(git__strlcmp("foo", foo, 3) == 0);
133+
cl_assert(git__strlcmp("foo", "foobar", 3) == 0);
134+
cl_assert(git__strlcmp("foobar", "foo", 3) > 0);
135+
cl_assert(git__strlcmp("foo", "foobar", 6) < 0);
136+
}

0 commit comments

Comments
 (0)