--- ./regexec.c.orig	2018-03-12 10:06:19.475661653 +0000
+++ ./regexec.c	2018-03-12 10:06:36.322612919 +0000
@@ -1226,13 +1226,15 @@ Perl_re_intuit_start(pTHX_ REGEXP * cons
                               ? (utf8_target ? trie_utf8 : trie_plain) \
                               : (utf8_target ? trie_utf8_fold : trie_latin_utf8_fold))
 
-#define REXEC_TRIE_READ_CHAR(trie_type, trie, widecharmap, uc, uscan, len, uvc, charid, foldlen, foldbuf, uniflags) \
+/* 'uscan' is set to foldbuf, and incremented, so below the end of uscan is
+ * 'foldbuf+sizeof(foldbuf)' */
+#define REXEC_TRIE_READ_CHAR(trie_type, trie, widecharmap, uc, uc_end, uscan, len, uvc, charid, foldlen, foldbuf, uniflags) \
 STMT_START {                               \
     STRLEN skiplen;                                                                 \
     switch (trie_type) {                                                            \
     case trie_utf8_fold:                                                            \
         if ( foldlen>0 ) {                                                          \
-            uvc = utf8n_to_uvuni( (const U8*) uscan, UTF8_MAXLEN, &len, uniflags ); \
+            uvc = utf8n_to_uvuni( (const U8*) uscan, foldlen, &len, uniflags ); \
             foldlen -= len;                                                         \
             uscan += len;                                                           \
             len=0;                                                                  \
@@ -1246,7 +1248,7 @@ STMT_START {
         break;                                                                      \
     case trie_latin_utf8_fold:                                                      \
         if ( foldlen>0 ) {                                                          \
-            uvc = utf8n_to_uvuni( (const U8*) uscan, UTF8_MAXLEN, &len, uniflags ); \
+            uvc = utf8n_to_uvuni( (const U8*) uscan, foldlen, &len, uniflags ); \
             foldlen -= len;                                                         \
             uscan += len;                                                           \
             len=0;                                                                  \
@@ -1259,7 +1261,7 @@ STMT_START {
         }                                                                           \
         break;                                                                      \
     case trie_utf8:                                                                 \
-        uvc = utf8n_to_uvuni( (const U8*) uc, UTF8_MAXLEN, &len, uniflags );        \
+        uvc = utf8n_to_uvuni( (const U8*) uc, uc_end - uc, &len, uniflags );        \
         break;                                                                      \
     case trie_plain:                                                                \
         uvc = (UV)*uc;                                                              \
@@ -1927,7 +1929,7 @@ S_find_byclass(pTHX_ regexp * prog, cons
                     points[pointpos++ % maxlen]= uc;
                     if (foldlen || uc < (U8*)strend) {
                         REXEC_TRIE_READ_CHAR(trie_type, trie,
-                                         widecharmap, uc,
+                                         widecharmap, uc, (U8*)strend,
                                          uscan, len, uvc, charid, foldlen,
                                          foldbuf, uniflags);
                         DEBUG_TRIE_EXECUTE_r({
@@ -3875,7 +3877,7 @@ S_regmatch(pTHX_ regmatch_info *reginfo,
 		    /* read a char and goto next state */
 		    if ( base && (foldlen || uc < (U8*)PL_regeol)) {
 			I32 offset;
-			REXEC_TRIE_READ_CHAR(trie_type, trie, widecharmap, uc,
+			REXEC_TRIE_READ_CHAR(trie_type, trie, widecharmap, uc, (U8*)PL_regeol,
 					     uscan, len, uvc, charid, foldlen,
 					     foldbuf, uniflags);
 			charcount++;
@@ -4009,7 +4011,7 @@ S_regmatch(pTHX_ regmatch_info *reginfo,
 			while (foldlen) {
 			    if (!--chars)
 				break;
-			    uvc = utf8n_to_uvuni(uscan, UTF8_MAXLEN, &len,
+			    uvc = utf8n_to_uvuni(uscan, foldlen, &len,
 					    uniflags);
 			    uscan += len;
 			    foldlen -= len;
