]> git.ipfire.org Git - thirdparty/git.git/commitdiff
regex: add regexec_buf() that can work on a non NUL-terminated string
authorJohannes Schindelin <johannes.schindelin@gmx.de>
Wed, 21 Sep 2016 18:24:04 +0000 (20:24 +0200)
committerJunio C Hamano <gitster@pobox.com>
Wed, 21 Sep 2016 20:56:15 +0000 (13:56 -0700)
We just introduced a test that demonstrates that our sloppy use of
regexec() on a mmap()ed area can result in incorrect results or even
hard crashes.

So what we need to fix this is a function that calls regexec() on a
length-delimited, rather than a NUL-terminated, string.

Happily, there is an extension to regexec() introduced by the NetBSD
project and present in all major regex implementation including
Linux', MacOSX' and the one Git includes in compat/regex/: by using
the (non-POSIX) REG_STARTEND flag, it is possible to tell the
regexec() function that it should only look at the offsets between
pmatch[0].rm_so and pmatch[0].rm_eo.

That is exactly what we need.

Since support for REG_STARTEND is so widespread by now, let's just
introduce a helper function that always uses it, and tell people
on a platform whose regex library does not support it to use the
one from our compat/regex/ directory.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
Makefile
git-compat-util.h

index e11e626d05213f4734815f03f8077ffae6793a51..c6dc42d067c1d2c46ad35c4fd01a41b05d75f243 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -296,7 +296,8 @@ all::
 # Define USE_NED_ALLOCATOR if you want to replace the platforms default
 # memory allocators with the nedmalloc allocator written by Niall Douglas.
 #
-# Define NO_REGEX if you have no or inferior regex support in your C library.
+# Define NO_REGEX if your C library lacks regex support with REG_STARTEND
+# feature.
 #
 # Define HAVE_DEV_TTY if your system can open /dev/tty to interact with the
 # user.
index 1f8b5f3b1f1ac17716681fee2d72b9c124a9b99c..7047d281e56353d79b384cce55d199691ab33842 100644 (file)
@@ -942,6 +942,19 @@ void git_qsort(void *base, size_t nmemb, size_t size,
 #define qsort git_qsort
 #endif
 
+#ifndef REG_STARTEND
+#error "Git requires REG_STARTEND support. Compile with NO_REGEX=NeedsStartEnd"
+#endif
+
+static inline int regexec_buf(const regex_t *preg, const char *buf, size_t size,
+                             size_t nmatch, regmatch_t pmatch[], int eflags)
+{
+       assert(nmatch > 0 && pmatch);
+       pmatch[0].rm_so = 0;
+       pmatch[0].rm_eo = size;
+       return regexec(preg, buf, nmatch, pmatch, eflags | REG_STARTEND);
+}
+
 #ifndef DIR_HAS_BSD_GROUP_SEMANTICS
 # define FORCE_DIR_SET_GID S_ISGID
 #else