Browse Source

pcre2: Update to upstream version 10.39

Changelog: https://github.com/PhilipHazel/pcre2/blob/pcre2-10.39/ChangeLog
(cherry picked from commit 914b7f825d9b4bd2653cdd5a43e84f5843eedb20)
Rémi Verschelde 3 years ago
parent
commit
86ab8b2613
35 changed files with 2924 additions and 1626 deletions
  1. 2 2
      COPYRIGHT.txt
  2. 1 1
      thirdparty/README.md
  3. 4 4
      thirdparty/pcre2/AUTHORS
  4. 4 4
      thirdparty/pcre2/LICENCE
  5. 87 20
      thirdparty/pcre2/src/config.h
  6. 7 5
      thirdparty/pcre2/src/pcre2.h
  7. 9 4
      thirdparty/pcre2/src/pcre2_auto_possess.c
  8. 59 27
      thirdparty/pcre2/src/pcre2_compile.c
  9. 44 25
      thirdparty/pcre2/src/pcre2_dfa_match.c
  10. 2 1
      thirdparty/pcre2/src/pcre2_error.c
  11. 47 42
      thirdparty/pcre2/src/pcre2_jit_compile.c
  12. 777 42
      thirdparty/pcre2/src/pcre2_jit_simd_inc.h
  13. 49 28
      thirdparty/pcre2/src/pcre2_match.c
  14. 181 166
      thirdparty/pcre2/src/pcre2_tables.c
  15. 838 812
      thirdparty/pcre2/src/pcre2_ucd.c
  16. 7 1
      thirdparty/pcre2/src/pcre2_ucp.h
  17. 14 0
      thirdparty/pcre2/src/sljit/sljitConfigInternal.h
  18. 71 53
      thirdparty/pcre2/src/sljit/sljitExecAllocator.c
  19. 14 11
      thirdparty/pcre2/src/sljit/sljitLir.c
  20. 37 39
      thirdparty/pcre2/src/sljit/sljitLir.h
  21. 16 7
      thirdparty/pcre2/src/sljit/sljitNativeARM_32.c
  22. 15 6
      thirdparty/pcre2/src/sljit/sljitNativeARM_64.c
  23. 15 6
      thirdparty/pcre2/src/sljit/sljitNativeARM_T2_32.c
  24. 1 1
      thirdparty/pcre2/src/sljit/sljitNativeMIPS_32.c
  25. 1 1
      thirdparty/pcre2/src/sljit/sljitNativeMIPS_64.c
  26. 10 6
      thirdparty/pcre2/src/sljit/sljitNativeMIPS_common.c
  27. 16 10
      thirdparty/pcre2/src/sljit/sljitNativePPC_32.c
  28. 22 10
      thirdparty/pcre2/src/sljit/sljitNativePPC_64.c
  29. 66 27
      thirdparty/pcre2/src/sljit/sljitNativePPC_common.c
  30. 481 251
      thirdparty/pcre2/src/sljit/sljitNativeS390X.c
  31. 3 0
      thirdparty/pcre2/src/sljit/sljitNativeSPARC_32.c
  32. 11 7
      thirdparty/pcre2/src/sljit/sljitNativeSPARC_common.c
  33. 0 2
      thirdparty/pcre2/src/sljit/sljitNativeX86_common.c
  34. 7 3
      thirdparty/pcre2/src/sljit/sljitUtils.c
  35. 6 2
      thirdparty/pcre2/src/sljit/sljitWXExecAllocator.c

+ 2 - 2
COPYRIGHT.txt

@@ -346,8 +346,8 @@ License: BSD-3-clause
 
 Files: ./thirdparty/pcre2/
 Comment: PCRE2
-Copyright: 1997-2020, University of Cambridge
- 2009-2020, Zoltan Herczeg
+Copyright: 1997-2021, University of Cambridge
+ 2009-2021, Zoltan Herczeg
 License: BSD-3-clause
 
 Files: ./thirdparty/pvrtccompressor/

+ 1 - 1
thirdparty/README.md

@@ -442,7 +442,7 @@ Files extracted from upstream source:
 ## pcre2
 
 - Upstream: http://www.pcre.org
-- Version: 10.36 (r1288, 2020)
+- Version: 10.39 (35fee4193b852cb504892352bd0155de10809889, 2021)
 - License: BSD-3-Clause
 
 Files extracted from upstream source:

+ 4 - 4
thirdparty/pcre2/AUTHORS

@@ -5,10 +5,10 @@ Written by:       Philip Hazel
 Email local part: Philip.Hazel
 Email domain:     gmail.com
 
-University of Cambridge Computing Service,
+Retired from University of Cambridge Computing Service,
 Cambridge, England.
 
-Copyright (c) 1997-2020 University of Cambridge
+Copyright (c) 1997-2021 University of Cambridge
 All rights reserved
 
 
@@ -19,7 +19,7 @@ Written by:       Zoltan Herczeg
 Email local part: hzmester
 Emain domain:     freemail.hu
 
-Copyright(c) 2010-2020 Zoltan Herczeg
+Copyright(c) 2010-2021 Zoltan Herczeg
 All rights reserved.
 
 
@@ -30,7 +30,7 @@ Written by:       Zoltan Herczeg
 Email local part: hzmester
 Emain domain:     freemail.hu
 
-Copyright(c) 2009-2020 Zoltan Herczeg
+Copyright(c) 2009-2021 Zoltan Herczeg
 All rights reserved.
 
 ####

+ 4 - 4
thirdparty/pcre2/LICENCE

@@ -23,10 +23,10 @@ Written by:       Philip Hazel
 Email local part: Philip.Hazel
 Email domain:     gmail.com
 
-University of Cambridge Computing Service,
+Retired from University of Cambridge Computing Service,
 Cambridge, England.
 
-Copyright (c) 1997-2020 University of Cambridge
+Copyright (c) 1997-2021 University of Cambridge
 All rights reserved.
 
 
@@ -37,7 +37,7 @@ Written by:       Zoltan Herczeg
 Email local part: hzmester
 Email domain:     freemail.hu
 
-Copyright(c) 2010-2020 Zoltan Herczeg
+Copyright(c) 2010-2021 Zoltan Herczeg
 All rights reserved.
 
 
@@ -48,7 +48,7 @@ Written by:       Zoltan Herczeg
 Email local part: hzmester
 Email domain:     freemail.hu
 
-Copyright(c) 2009-2020 Zoltan Herczeg
+Copyright(c) 2009-2021 Zoltan Herczeg
 All rights reserved.
 
 

+ 87 - 20
thirdparty/pcre2/src/config.h

@@ -85,8 +85,8 @@ sure both macros are undefined; an emulation function will then be used. */
 /* Define to 1 if you have the `memmove' function. */
 /* #undef HAVE_MEMMOVE */
 
-/* Define to 1 if you have the <memory.h> header file. */
-/* #undef HAVE_MEMORY_H */
+/* Define to 1 if you have the <minix/config.h> header file. */
+/* #undef HAVE_MINIX_CONFIG_H */
 
 /* Define to 1 if you have the `mkostemp' function. */
 /* #undef HAVE_MKOSTEMP */
@@ -103,12 +103,18 @@ sure both macros are undefined; an emulation function will then be used. */
 /* Define to 1 if you have the <readline/readline.h> header file. */
 /* #undef HAVE_READLINE_READLINE_H */
 
+/* Define to 1 if you have the `realpath' function. */
+/* #undef HAVE_REALPATH */
+
 /* Define to 1 if you have the `secure_getenv' function. */
 /* #undef HAVE_SECURE_GETENV */
 
 /* Define to 1 if you have the <stdint.h> header file. */
 /* #undef HAVE_STDINT_H */
 
+/* Define to 1 if you have the <stdio.h> header file. */
+/* #undef HAVE_STDIO_H */
+
 /* Define to 1 if you have the <stdlib.h> header file. */
 /* #undef HAVE_STDLIB_H */
 
@@ -136,6 +142,9 @@ sure both macros are undefined; an emulation function will then be used. */
 /* Define to 1 if the compiler supports simple visibility declarations. */
 /* #undef HAVE_VISIBILITY */
 
+/* Define to 1 if you have the <wchar.h> header file. */
+/* #undef HAVE_WCHAR_H */
+
 /* Define to 1 if you have the <windows.h> header file. */
 /* #undef HAVE_WINDOWS_H */
 
@@ -224,7 +233,7 @@ sure both macros are undefined; an emulation function will then be used. */
 #define PACKAGE_NAME "PCRE2"
 
 /* Define to the full name and version of this package. */
-#define PACKAGE_STRING "PCRE2 10.36"
+#define PACKAGE_STRING "PCRE2 10.39"
 
 /* Define to the one symbol short name of this package. */
 #define PACKAGE_TARNAME "pcre2"
@@ -233,7 +242,7 @@ sure both macros are undefined; an emulation function will then be used. */
 #define PACKAGE_URL ""
 
 /* Define to the version of this package. */
-#define PACKAGE_VERSION "10.36"
+#define PACKAGE_VERSION "10.39"
 
 /* The value of PARENS_NEST_LIMIT specifies the maximum depth of nested
    parentheses (of any kind) in a pattern. This limits the amount of system
@@ -286,7 +295,9 @@ sure both macros are undefined; an emulation function will then be used. */
    unless SUPPORT_JIT is also defined. */
 /* #undef SLJIT_PROT_EXECUTABLE_ALLOCATOR */
 
-/* Define to 1 if you have the ANSI C header files. */
+/* Define to 1 if all of the C90 standard headers exist (not just the ones
+   required in a freestanding environment). This macro is provided for
+   backward compatibility; new code need not use it. */
 /* #undef STDC_HEADERS */
 
 /* Define to any value to enable support for Just-In-Time compiling. */
@@ -340,35 +351,91 @@ sure both macros are undefined; an emulation function will then be used. */
 #ifndef _ALL_SOURCE
 # define _ALL_SOURCE 1
 #endif
+/* Enable general extensions on macOS.  */
+#ifndef _DARWIN_C_SOURCE
+# define _DARWIN_C_SOURCE 1
+#endif
+/* Enable general extensions on Solaris.  */
+#ifndef __EXTENSIONS__
+# define __EXTENSIONS__ 1
+#endif
 /* Enable GNU extensions on systems that have them.  */
 #ifndef _GNU_SOURCE
 # define _GNU_SOURCE 1
 #endif
-/* Enable threading extensions on Solaris.  */
+/* Enable X/Open compliant socket functions that do not require linking
+   with -lxnet on HP-UX 11.11.  */
+#ifndef _HPUX_ALT_XOPEN_SOCKET_API
+# define _HPUX_ALT_XOPEN_SOCKET_API 1
+#endif
+/* Identify the host operating system as Minix.
+   This macro does not affect the system headers' behavior.
+   A future release of Autoconf may stop defining this macro.  */
+#ifndef _MINIX
+/* # undef _MINIX */
+#endif
+/* Enable general extensions on NetBSD.
+   Enable NetBSD compatibility extensions on Minix.  */
+#ifndef _NETBSD_SOURCE
+# define _NETBSD_SOURCE 1
+#endif
+/* Enable OpenBSD compatibility extensions on NetBSD.
+   Oddly enough, this does nothing on OpenBSD.  */
+#ifndef _OPENBSD_SOURCE
+# define _OPENBSD_SOURCE 1
+#endif
+/* Define to 1 if needed for POSIX-compatible behavior.  */
+#ifndef _POSIX_SOURCE
+/* # undef _POSIX_SOURCE */
+#endif
+/* Define to 2 if needed for POSIX-compatible behavior.  */
+#ifndef _POSIX_1_SOURCE
+/* # undef _POSIX_1_SOURCE */
+#endif
+/* Enable POSIX-compatible threading on Solaris.  */
 #ifndef _POSIX_PTHREAD_SEMANTICS
 # define _POSIX_PTHREAD_SEMANTICS 1
 #endif
+/* Enable extensions specified by ISO/IEC TS 18661-5:2014.  */
+#ifndef __STDC_WANT_IEC_60559_ATTRIBS_EXT__
+# define __STDC_WANT_IEC_60559_ATTRIBS_EXT__ 1
+#endif
+/* Enable extensions specified by ISO/IEC TS 18661-1:2014.  */
+#ifndef __STDC_WANT_IEC_60559_BFP_EXT__
+# define __STDC_WANT_IEC_60559_BFP_EXT__ 1
+#endif
+/* Enable extensions specified by ISO/IEC TS 18661-2:2015.  */
+#ifndef __STDC_WANT_IEC_60559_DFP_EXT__
+# define __STDC_WANT_IEC_60559_DFP_EXT__ 1
+#endif
+/* Enable extensions specified by ISO/IEC TS 18661-4:2015.  */
+#ifndef __STDC_WANT_IEC_60559_FUNCS_EXT__
+# define __STDC_WANT_IEC_60559_FUNCS_EXT__ 1
+#endif
+/* Enable extensions specified by ISO/IEC TS 18661-3:2015.  */
+#ifndef __STDC_WANT_IEC_60559_TYPES_EXT__
+# define __STDC_WANT_IEC_60559_TYPES_EXT__ 1
+#endif
+/* Enable extensions specified by ISO/IEC TR 24731-2:2010.  */
+#ifndef __STDC_WANT_LIB_EXT2__
+# define __STDC_WANT_LIB_EXT2__ 1
+#endif
+/* Enable extensions specified by ISO/IEC 24747:2009.  */
+#ifndef __STDC_WANT_MATH_SPEC_FUNCS__
+# define __STDC_WANT_MATH_SPEC_FUNCS__ 1
+#endif
 /* Enable extensions on HP NonStop.  */
 #ifndef _TANDEM_SOURCE
 # define _TANDEM_SOURCE 1
 #endif
-/* Enable general extensions on Solaris.  */
-#ifndef __EXTENSIONS__
-# define __EXTENSIONS__ 1
+/* Enable X/Open extensions.  Define to 500 only if necessary
+   to make mbstate_t available.  */
+#ifndef _XOPEN_SOURCE
+/* # undef _XOPEN_SOURCE */
 #endif
 
 /* Version number of package */
-#define VERSION "10.36"
-
-/* Define to 1 if on MINIX. */
-/* #undef _MINIX */
-
-/* Define to 2 if the system does not provide POSIX.1 features except with
-   this defined. */
-/* #undef _POSIX_1_SOURCE */
-
-/* Define to 1 if you need to in order for `stat' and other things to work. */
-/* #undef _POSIX_SOURCE */
+#define VERSION "10.39"
 
 /* Define to empty if `const' does not conform to ANSI C. */
 /* #undef const */

+ 7 - 5
thirdparty/pcre2/src/pcre2.h

@@ -5,7 +5,7 @@
 /* This is the public header file for the PCRE library, second API, to be
 #included by applications that call PCRE2 functions.
 
-           Copyright (c) 2016-2020 University of Cambridge
+           Copyright (c) 2016-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -42,9 +42,9 @@ POSSIBILITY OF SUCH DAMAGE.
 /* The current PCRE version information. */
 
 #define PCRE2_MAJOR           10
-#define PCRE2_MINOR           36
+#define PCRE2_MINOR           39
 #define PCRE2_PRERELEASE      
-#define PCRE2_DATE            2020-12-04
+#define PCRE2_DATE            2021-10-29
 
 /* When an application links to a PCRE DLL in Windows, the symbols that are
 imported have to be identified as such. When building PCRE2, the appropriate
@@ -84,8 +84,8 @@ set, we ensure here that it has no effect. */
 /* Have to include limits.h, stdlib.h, and inttypes.h to ensure that size_t and
 uint8_t, UCHAR_MAX, etc are defined. Some systems that do have inttypes.h do
 not have stdint.h, which is why we use inttypes.h, which according to the C
-standard is a superset of stdint.h. If none of these headers are available,
-the relevant values must be provided by some other means. */
+standard is a superset of stdint.h. If inttypes.h is not available the build
+will break and the relevant values must be provided by some other means. */
 
 #include <limits.h>
 #include <stdlib.h>
@@ -152,6 +152,7 @@ D   is inspected during pcre2_dfa_match() execution
 #define PCRE2_EXTRA_MATCH_LINE               0x00000008u  /* C */
 #define PCRE2_EXTRA_ESCAPED_CR_IS_LF         0x00000010u  /* C */
 #define PCRE2_EXTRA_ALT_BSUX                 0x00000020u  /* C */
+#define PCRE2_EXTRA_ALLOW_LOOKAROUND_BSK     0x00000040u  /* C */
 
 /* These are for pcre2_jit_compile(). */
 
@@ -311,6 +312,7 @@ pcre2_pattern_convert(). */
 #define PCRE2_ERROR_SCRIPT_RUN_NOT_AVAILABLE       196
 #define PCRE2_ERROR_TOO_MANY_CAPTURES              197
 #define PCRE2_ERROR_CONDITION_ATOMIC_ASSERTION_EXPECTED  198
+#define PCRE2_ERROR_BACKSLASH_K_IN_LOOKAROUND      199
 
 
 /* "Expected" matching error codes: no match and partial match. */

+ 9 - 4
thirdparty/pcre2/src/pcre2_auto_possess.c

@@ -7,7 +7,7 @@ and semantics are as close as possible to those of the Perl 5 language.
 
                        Written by Philip Hazel
      Original API code Copyright (c) 1997-2012 University of Cambridge
-          New API code Copyright (c) 2016-2020 University of Cambridge
+          New API code Copyright (c) 2016-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -490,6 +490,7 @@ switch(c)
   list[2] = (uint32_t)(end - code);
   return end;
   }
+
 return NULL;    /* Opcode not accepted */
 }
 
@@ -1186,12 +1187,16 @@ for (;;)
     c = *repeat_opcode;
     if (c >= OP_CRSTAR && c <= OP_CRMINRANGE)
       {
-      /* end must not be NULL. */
-      end = get_chr_property_list(code, utf, ucp, cb->fcc, list);
+      /* The return from get_chr_property_list() will never be NULL when
+      *code (aka c) is one of the three class opcodes. However, gcc with
+      -fanalyzer notes that a NULL return is possible, and grumbles. Hence we
+      put in a check. */
 
+      end = get_chr_property_list(code, utf, ucp, cb->fcc, list);
       list[1] = (c & 1) == 0;
 
-      if (compare_opcodes(end, utf, ucp, cb, list, end, &rec_limit))
+      if (end != NULL &&
+          compare_opcodes(end, utf, ucp, cb, list, end, &rec_limit))
         {
         switch (c)
           {

+ 59 - 27
thirdparty/pcre2/src/pcre2_compile.c

@@ -7,7 +7,7 @@ and semantics are as close as possible to those of the Perl 5 language.
 
                        Written by Philip Hazel
      Original API code Copyright (c) 1997-2012 University of Cambridge
-          New API code Copyright (c) 2016-2020 University of Cambridge
+          New API code Copyright (c) 2016-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -137,7 +137,7 @@ static BOOL
 
 static int
   check_lookbehinds(uint32_t *, uint32_t **, parsed_recurse_check *,
-    compile_block *);
+    compile_block *, int *);
 
 
 /*************************************************
@@ -782,12 +782,15 @@ are allowed. */
 #define PUBLIC_COMPILE_EXTRA_OPTIONS \
    (PUBLIC_LITERAL_COMPILE_EXTRA_OPTIONS| \
     PCRE2_EXTRA_ALLOW_SURROGATE_ESCAPES|PCRE2_EXTRA_BAD_ESCAPE_IS_LITERAL| \
-    PCRE2_EXTRA_ESCAPED_CR_IS_LF|PCRE2_EXTRA_ALT_BSUX)
+    PCRE2_EXTRA_ESCAPED_CR_IS_LF|PCRE2_EXTRA_ALT_BSUX| \
+    PCRE2_EXTRA_ALLOW_LOOKAROUND_BSK)
 
 /* Compile time error code numbers. They are given names so that they can more
 easily be tracked. When a new number is added, the tables called eint1 and
 eint2 in pcre2posix.c may need to be updated, and a new error text must be
-added to compile_error_texts in pcre2_error.c. */
+added to compile_error_texts in pcre2_error.c. Also, the error codes in
+pcre2.h.in must be updated - their values are exactly 100 greater than these
+values. */
 
 enum { ERR0 = COMPILE_ERROR_BASE,
        ERR1,  ERR2,  ERR3,  ERR4,  ERR5,  ERR6,  ERR7,  ERR8,  ERR9,  ERR10,
@@ -799,7 +802,7 @@ enum { ERR0 = COMPILE_ERROR_BASE,
        ERR61, ERR62, ERR63, ERR64, ERR65, ERR66, ERR67, ERR68, ERR69, ERR70,
        ERR71, ERR72, ERR73, ERR74, ERR75, ERR76, ERR77, ERR78, ERR79, ERR80,
        ERR81, ERR82, ERR83, ERR84, ERR85, ERR86, ERR87, ERR88, ERR89, ERR90,
-       ERR91, ERR92, ERR93, ERR94, ERR95, ERR96, ERR97, ERR98 };
+       ERR91, ERR92, ERR93, ERR94, ERR95, ERR96, ERR97, ERR98, ERR99 };
 
 /* This is a table of start-of-pattern options such as (*UTF) and settings such
 as (*LIMIT_MATCH=nnnn) and (*CRLF). For completeness and backward
@@ -1398,32 +1401,47 @@ static BOOL
 read_repeat_counts(PCRE2_SPTR *ptrptr, PCRE2_SPTR ptrend, uint32_t *minp,
   uint32_t *maxp, int *errorcodeptr)
 {
-PCRE2_SPTR p = *ptrptr;
+PCRE2_SPTR p;
 BOOL yield = FALSE;
+BOOL had_comma = FALSE;
 int32_t min = 0;
 int32_t max = REPEAT_UNLIMITED; /* This value is larger than MAX_REPEAT_COUNT */
 
-/* NB read_number() initializes the error code to zero. The only error is for a
-number that is too big. */
+/* Check the syntax */
+
+*errorcodeptr = 0;
+for (p = *ptrptr;; p++)
+  {
+  uint32_t c;
+  if (p >= ptrend) return FALSE;
+  c = *p;
+  if (IS_DIGIT(c)) continue;
+  if (c == CHAR_RIGHT_CURLY_BRACKET) break;
+  if (c == CHAR_COMMA)
+    {
+    if (had_comma) return FALSE;
+    had_comma = TRUE;
+    }
+  else return FALSE;
+  }
+
+/* The only error from read_number() is for a number that is too big. */
 
+p = *ptrptr;
 if (!read_number(&p, ptrend, -1, MAX_REPEAT_COUNT, ERR5, &min, errorcodeptr))
   goto EXIT;
 
-if (p >= ptrend) goto EXIT;
-
 if (*p == CHAR_RIGHT_CURLY_BRACKET)
   {
   p++;
   max = min;
   }
-
 else
   {
-  if (*p++ != CHAR_COMMA || p >= ptrend) goto EXIT;
-  if (*p != CHAR_RIGHT_CURLY_BRACKET)
+  if (*(++p) != CHAR_RIGHT_CURLY_BRACKET)
     {
     if (!read_number(&p, ptrend, -1, MAX_REPEAT_COUNT, ERR5, &max,
-        errorcodeptr) || p >= ptrend ||  *p != CHAR_RIGHT_CURLY_BRACKET)
+        errorcodeptr))
       goto EXIT;
     if (max < min)
       {
@@ -1438,11 +1456,10 @@ yield = TRUE;
 if (minp != NULL) *minp = (uint32_t)min;
 if (maxp != NULL) *maxp = (uint32_t)max;
 
-/* Update the pattern pointer on success, or after an error, but not when
-the result is "not a repeat quantifier". */
+/* Update the pattern pointer */
 
 EXIT:
-if (yield || *errorcodeptr != 0) *ptrptr = p;
+*ptrptr = p;
 return yield;
 }
 
@@ -1776,19 +1793,23 @@ else
       {
       oldptr = ptr;
       ptr--;   /* Back to the digit */
-      if (!read_number(&ptr, ptrend, -1, INT_MAX/10 - 1, ERR61, &s,
-          errorcodeptr))
-        break;
 
-      /* \1 to \9 are always back references. \8x and \9x are too; \1x to \7x
+      /* As we know we are at a digit, the only possible error from
+      read_number() is a number that is too large to be a group number. In this
+      case we fall through handle this as not a group reference. If we have
+      read a small enough number, check for a back reference.
+
+      \1 to \9 are always back references. \8x and \9x are too; \1x to \7x
       are octal escapes if there are not that many previous captures. */
 
-      if (s < 10 || oldptr[-1] >= CHAR_8 || s <= (int)cb->bracount)
+      if (read_number(&ptr, ptrend, -1, INT_MAX/10 - 1, 0, &s, errorcodeptr) &&
+          (s < 10 || oldptr[-1] >= CHAR_8 || s <= (int)cb->bracount))
         {
         if (s > (int)MAX_GROUP_NUMBER) *errorcodeptr = ERR61;
           else escape = -s;     /* Indicates a back reference */
         break;
         }
+
       ptr = oldptr;      /* Put the pointer back and fall through */
       }
 
@@ -7781,6 +7802,16 @@ for (;; pptr++)
       }
 #endif
 
+    /* \K is forbidden in lookarounds since 10.38 because that's what Perl has
+    done. However, there's an option, in case anyone was relying on it. */
+
+    if (cb->assert_depth > 0 && meta_arg == ESC_K &&
+        (cb->cx->extra_options & PCRE2_EXTRA_ALLOW_LOOKAROUND_BSK) == 0)
+      {
+      *errorcodeptr = ERR99;
+      return 0;
+      }
+
     /* For the rest (including \X when Unicode is supported - if not it's
     faulted at parse time), the OP value is the escape value when PCRE2_UCP is
     not set; if it is set, these escapes do not show up here because they are
@@ -9130,7 +9161,7 @@ for (;; pptr++)
     case META_LOOKAHEAD:
     case META_LOOKAHEADNOT:
     case META_LOOKAHEAD_NA:
-    *errcodeptr = check_lookbehinds(pptr + 1, &pptr, recurses, cb);
+    *errcodeptr = check_lookbehinds(pptr + 1, &pptr, recurses, cb, lcptr);
     if (*errcodeptr != 0) return -1;
 
     /* Ignore any qualifiers that follow a lookahead assertion. */
@@ -9470,16 +9501,16 @@ Arguments
   retptr    if not NULL, return the ket pointer here
   recurses  chain of recurse_check to catch mutual recursion
   cb        points to the compile block
+  lcptr     points to loop counter
 
 Returns:    0 on success, or an errorcode (cb->erroroffset will be set)
 */
 
 static int
 check_lookbehinds(uint32_t *pptr, uint32_t **retptr,
-  parsed_recurse_check *recurses, compile_block *cb)
+  parsed_recurse_check *recurses, compile_block *cb, int *lcptr)
 {
 int errorcode = 0;
-int loopcount = 0;
 int nestlevel = 0;
 
 cb->erroroffset = PCRE2_UNSET;
@@ -9605,7 +9636,7 @@ for (; *pptr != META_END; pptr++)
     case META_LOOKBEHIND:
     case META_LOOKBEHINDNOT:
     case META_LOOKBEHIND_NA:
-    if (!set_lookbehind_lengths(&pptr, &errorcode, &loopcount, recurses, cb))
+    if (!set_lookbehind_lengths(&pptr, &errorcode, lcptr, recurses, cb))
       return errorcode;
     break;
     }
@@ -10060,7 +10091,8 @@ lengths. */
 
 if (has_lookbehind)
   {
-  errorcode = check_lookbehinds(cb.parsed_pattern, NULL, NULL, &cb);
+  int loopcount = 0;
+  errorcode = check_lookbehinds(cb.parsed_pattern, NULL, NULL, &cb, &loopcount);
   if (errorcode != 0) goto HAD_CB_ERROR;
   }
 

+ 44 - 25
thirdparty/pcre2/src/pcre2_dfa_match.c

@@ -7,7 +7,7 @@ and semantics are as close as possible to those of the Perl 5 language.
 
                        Written by Philip Hazel
      Original API code Copyright (c) 1997-2012 University of Cambridge
-          New API code Copyright (c) 2016-2020 University of Cambridge
+          New API code Copyright (c) 2016-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -3256,8 +3256,8 @@ BOOL has_first_cu = FALSE;
 BOOL has_req_cu = FALSE;
 
 #if PCRE2_CODE_UNIT_WIDTH == 8
-BOOL memchr_not_found_first_cu = FALSE;
-BOOL memchr_not_found_first_cu2 = FALSE;
+PCRE2_SPTR memchr_found_first_cu = NULL;
+PCRE2_SPTR memchr_found_first_cu2 = NULL;
 #endif
 
 PCRE2_UCHAR first_cu = 0;
@@ -3648,13 +3648,7 @@ for (;;)
         }
       }
 
-    /* Not anchored. Advance to a unique first code unit if there is one. In
-    8-bit mode, the use of memchr() gives a big speed up, even though we have
-    to call it twice in caseless mode, in order to find the earliest occurrence
-    of the character in either of its cases. If a call to memchr() that
-    searches the rest of the subject fails to find one case, remember that in
-    order not to keep on repeating the search. This can make a huge difference
-    when the strings are very long and only one case is present. */
+    /* Not anchored. Advance to a unique first code unit if there is one. */
 
     else
       {
@@ -3662,43 +3656,68 @@ for (;;)
         {
         if (first_cu != first_cu2)  /* Caseless */
           {
+          /* In 16-bit and 32_bit modes we have to do our own search, so can
+          look for both cases at once. */
+
 #if PCRE2_CODE_UNIT_WIDTH != 8
           PCRE2_UCHAR smc;
           while (start_match < end_subject &&
                 (smc = UCHAR21TEST(start_match)) != first_cu &&
-                  smc != first_cu2)
+                 smc != first_cu2)
             start_match++;
+#else
+          /* In 8-bit mode, the use of memchr() gives a big speed up, even
+          though we have to call it twice in order to find the earliest
+          occurrence of the code unit in either of its cases. Caching is used
+          to remember the positions of previously found code units. This can
+          make a huge difference when the strings are very long and only one
+          case is actually present. */
 
-#else  /* 8-bit code units */
           PCRE2_SPTR pp1 = NULL;
           PCRE2_SPTR pp2 = NULL;
-          PCRE2_SIZE cu2size = end_subject - start_match;
+          PCRE2_SIZE searchlength = end_subject - start_match;
 
-          if (!memchr_not_found_first_cu)
+          /* If we haven't got a previously found position for first_cu, or if
+          the current starting position is later, we need to do a search. If
+          the code unit is not found, set it to the end. */
+
+          if (memchr_found_first_cu == NULL ||
+              start_match > memchr_found_first_cu)
             {
-            pp1 = memchr(start_match, first_cu, end_subject - start_match);
-            if (pp1 == NULL) memchr_not_found_first_cu = TRUE;
-              else cu2size = pp1 - start_match;
+            pp1 = memchr(start_match, first_cu, searchlength);
+            memchr_found_first_cu = (pp1 == NULL)? end_subject : pp1;
             }
 
-          /* If pp1 is not NULL, we have arranged to search only as far as pp1,
-          to see if the other case is earlier, so we can set "not found" only
-          when both searches have returned NULL. */
+          /* If the start is before a previously found position, use the
+          previous position, or NULL if a previous search failed. */
+
+          else pp1 = (memchr_found_first_cu == end_subject)? NULL :
+            memchr_found_first_cu;
 
-          if (!memchr_not_found_first_cu2)
+          /* Do the same thing for the other case. */
+
+          if (memchr_found_first_cu2 == NULL ||
+              start_match > memchr_found_first_cu2)
             {
-            pp2 = memchr(start_match, first_cu2, cu2size);
-            memchr_not_found_first_cu2 = (pp2 == NULL && pp1 == NULL);
+            pp2 = memchr(start_match, first_cu2, searchlength);
+            memchr_found_first_cu2 = (pp2 == NULL)? end_subject : pp2;
             }
 
+          else pp2 = (memchr_found_first_cu2 == end_subject)? NULL :
+            memchr_found_first_cu2;
+
+          /* Set the start to the end of the subject if neither case was found.
+          Otherwise, use the earlier found point. */
+
           if (pp1 == NULL)
             start_match = (pp2 == NULL)? end_subject : pp2;
           else
             start_match = (pp2 == NULL || pp1 < pp2)? pp1 : pp2;
-#endif
+
+#endif  /* 8-bit handling */
           }
 
-        /* The caseful case */
+        /* The caseful case is much simpler. */
 
         else
           {

+ 2 - 1
thirdparty/pcre2/src/pcre2_error.c

@@ -7,7 +7,7 @@ and semantics are as close as possible to those of the Perl 5 language.
 
                        Written by Philip Hazel
      Original API code Copyright (c) 1997-2012 University of Cambridge
-          New API code Copyright (c) 2016-2019 University of Cambridge
+          New API code Copyright (c) 2016-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -186,6 +186,7 @@ static const unsigned char compile_error_texts[] =
   "script runs require Unicode support, which this version of PCRE2 does not have\0"
   "too many capturing groups (maximum 65535)\0"
   "atomic assertion expected after (?( or (?(?C)\0"
+  "\\K is not allowed in lookarounds (but see PCRE2_EXTRA_ALLOW_LOOKAROUND_BSK)\0"
   ;
 
 /* Match-time and UTF error texts are in the same format. */

+ 47 - 42
thirdparty/pcre2/src/pcre2_jit_compile.c

@@ -1226,7 +1226,7 @@ while (cc < ccend)
 return TRUE;
 }
 
-#define EARLY_FAIL_ENHANCE_MAX (1 + 1)
+#define EARLY_FAIL_ENHANCE_MAX (1 + 3)
 
 /*
 start:
@@ -1236,23 +1236,28 @@ start:
 
 return: current number of iterators enhanced with fast fail
 */
-static int detect_early_fail(compiler_common *common, PCRE2_SPTR cc, int *private_data_start, sljit_s32 depth, int start)
+static int detect_early_fail(compiler_common *common, PCRE2_SPTR cc, int *private_data_start,
+   sljit_s32 depth, int start, BOOL fast_forward_allowed)
 {
+PCRE2_SPTR begin = cc;
 PCRE2_SPTR next_alt;
 PCRE2_SPTR end;
 PCRE2_SPTR accelerated_start;
+BOOL prev_fast_forward_allowed;
 int result = 0;
 int count;
-BOOL fast_forward_allowed = TRUE;
 
 SLJIT_ASSERT(*cc == OP_ONCE || *cc == OP_BRA || *cc == OP_CBRA);
 SLJIT_ASSERT(*cc != OP_CBRA || common->optimized_cbracket[GET2(cc, 1 + LINK_SIZE)] != 0);
 SLJIT_ASSERT(start < EARLY_FAIL_ENHANCE_MAX);
 
+next_alt = cc + GET(cc, 1);
+if (*next_alt == OP_ALT)
+  fast_forward_allowed = FALSE;
+
 do
   {
   count = start;
-  next_alt = cc + GET(cc, 1);
   cc += 1 + LINK_SIZE + ((*cc == OP_CBRA) ? IMM2_SIZE : 0);
 
   while (TRUE)
@@ -1475,31 +1480,20 @@ do
       case OP_CBRA:
       end = cc + GET(cc, 1);
 
-      if (*end == OP_KET && PRIVATE_DATA(end) == 0)
-        {
-        if (*cc == OP_CBRA)
-          {
-          if (common->optimized_cbracket[GET2(cc, 1 + LINK_SIZE)] == 0)
-            break;
-          cc += IMM2_SIZE;
-          }
-
-        cc += 1 + LINK_SIZE;
-        continue;
-        }
-
+      prev_fast_forward_allowed = fast_forward_allowed;
       fast_forward_allowed = FALSE;
       if (depth >= 4)
         break;
 
       end = bracketend(cc) - (1 + LINK_SIZE);
-      if (*end != OP_KET || PRIVATE_DATA(end) != 0)
+      if (*end != OP_KET || (*cc == OP_CBRA && common->optimized_cbracket[GET2(cc, 1 + LINK_SIZE)] == 0))
         break;
 
-      if (*cc == OP_CBRA && common->optimized_cbracket[GET2(cc, 1 + LINK_SIZE)] == 0)
-        break;
+      count = detect_early_fail(common, cc, private_data_start, depth + 1, count, prev_fast_forward_allowed);
+
+      if (PRIVATE_DATA(cc) != 0)
+        common->private_data_ptrs[begin - common->start] = 1;
 
-      count = detect_early_fail(common, cc, private_data_start, depth + 1, count);
       if (count < EARLY_FAIL_ENHANCE_MAX)
         {
         cc = end + (1 + LINK_SIZE);
@@ -1521,7 +1515,7 @@ do
         {
         count++;
 
-        if (fast_forward_allowed && *next_alt == OP_KET)
+        if (fast_forward_allowed)
           {
           common->fast_forward_bc_ptr = accelerated_start;
           common->private_data_ptrs[(accelerated_start + 1) - common->start] = ((*private_data_start) << 3) | type_skip;
@@ -1555,6 +1549,8 @@ do
           return EARLY_FAIL_ENHANCE_MAX;
         }
 
+      /* Cannot be part of a repeat. */
+      common->private_data_ptrs[begin - common->start] = 1;
       count++;
 
       if (count < EARLY_FAIL_ENHANCE_MAX)
@@ -1569,8 +1565,8 @@ do
   else if (result < count)
     result = count;
 
-  fast_forward_allowed = FALSE;
   cc = next_alt;
+  next_alt = cc + GET(cc, 1);
   }
 while (*cc == OP_ALT);
 
@@ -1620,11 +1616,12 @@ sljit_sw length = end - begin;
 sljit_s32 min, max, i;
 
 /* Detect fixed iterations first. */
-if (end[-(1 + LINK_SIZE)] != OP_KET)
+if (end[-(1 + LINK_SIZE)] != OP_KET || PRIVATE_DATA(begin) != 0)
   return FALSE;
 
-/* Already detected repeat. */
-if (common->private_data_ptrs[end - common->start - LINK_SIZE] != 0)
+/* /(?:AB){4,6}/ is currently converted to /(?:AB){3}(?AB){1,3}/
+ * Skip the check of the second part. */
+if (PRIVATE_DATA(end - LINK_SIZE) == 0)
   return TRUE;
 
 next = end;
@@ -1763,6 +1760,7 @@ while (cc < ccend)
   if (private_data_ptr > SLJIT_MAX_LOCAL_SIZE)
     break;
 
+  /* When the bracket is prefixed by a zero iteration, skip the repeat check (at this point). */
   if (repeat_check && (*cc == OP_ONCE || *cc == OP_BRA || *cc == OP_CBRA || *cc == OP_COND))
     {
     if (detect_repeat(common, cc))
@@ -1813,6 +1811,7 @@ while (cc < ccend)
 
     case OP_COND:
     /* Might be a hidden SCOND. */
+    common->private_data_ptrs[cc - common->start] = 0;
     alternative = cc + GET(cc, 1);
     if (*alternative == OP_KETRMAX || *alternative == OP_KETRMIN)
       {
@@ -4203,9 +4202,6 @@ TMP2 is not used. Otherwise TMP2 must contain the start of the subject buffer,
 and it is destroyed. Does not modify STR_PTR for invalid character sequences. */
 DEFINE_COMPILER;
 
-SLJIT_UNUSED_ARG(backtracks);
-SLJIT_UNUSED_ARG(must_be_valid);
-
 #if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
 struct sljit_jump *jump;
 #endif
@@ -4279,6 +4275,10 @@ if (common->invalid_utf && !must_be_valid)
   }
 #endif /* PCRE2_CODE_UNIT_WIDTH == [8|16|32] */
 #endif /* SUPPORT_UNICODE */
+
+SLJIT_UNUSED_ARG(backtracks);
+SLJIT_UNUSED_ARG(must_be_valid);
+
 OP2(SLJIT_SUB, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, IN_UCHARS(1));
 }
 
@@ -8141,7 +8141,7 @@ switch(type)
     }
   else
     OP2(SLJIT_AND32 | SLJIT_SET_Z, SLJIT_UNUSED, 0, SLJIT_MEM1(ARGUMENTS), SLJIT_OFFSETOF(jit_arguments, options), SLJIT_IMM, PCRE2_NOTEOL);
-  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO32));
+  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO));
 
   if (!common->endonly)
     compile_simple_assertion_matchingpath(common, OP_EODN, cc, backtracks);
@@ -8161,7 +8161,7 @@ switch(type)
     }
   else
     OP2(SLJIT_AND32 | SLJIT_SET_Z, SLJIT_UNUSED, 0, SLJIT_MEM1(ARGUMENTS), SLJIT_OFFSETOF(jit_arguments, options), SLJIT_IMM, PCRE2_NOTEOL);
-  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO32));
+  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO));
   check_partial(common, FALSE);
   jump[0] = JUMP(SLJIT_JUMP);
   JUMPHERE(jump[1]);
@@ -8201,14 +8201,14 @@ switch(type)
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_MEM1(TMP2), SLJIT_OFFSETOF(jit_arguments, begin));
     add_jump(compiler, backtracks, CMP(SLJIT_GREATER, STR_PTR, 0, TMP1, 0));
     OP2(SLJIT_AND32 | SLJIT_SET_Z, SLJIT_UNUSED, 0, SLJIT_MEM1(TMP2), SLJIT_OFFSETOF(jit_arguments, options), SLJIT_IMM, PCRE2_NOTBOL);
-    add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO32));
+    add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO));
     }
   else
     {
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_MEM1(ARGUMENTS), SLJIT_OFFSETOF(jit_arguments, begin));
     add_jump(compiler, backtracks, CMP(SLJIT_GREATER, STR_PTR, 0, TMP1, 0));
     OP2(SLJIT_AND32 | SLJIT_SET_Z, SLJIT_UNUSED, 0, SLJIT_MEM1(ARGUMENTS), SLJIT_OFFSETOF(jit_arguments, options), SLJIT_IMM, PCRE2_NOTBOL);
-    add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO32));
+    add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO));
     }
   return cc;
 
@@ -8227,7 +8227,7 @@ switch(type)
     jump[1] = CMP(SLJIT_GREATER, STR_PTR, 0, TMP2, 0);
     OP2(SLJIT_AND32 | SLJIT_SET_Z, SLJIT_UNUSED, 0, SLJIT_MEM1(ARGUMENTS), SLJIT_OFFSETOF(jit_arguments, options), SLJIT_IMM, PCRE2_NOTBOL);
     }
-  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO32));
+  add_jump(compiler, backtracks, JUMP(SLJIT_NOT_ZERO));
   jump[0] = JUMP(SLJIT_JUMP);
   JUMPHERE(jump[1]);
 
@@ -9581,11 +9581,11 @@ free_stack(common, callout_arg_size);
 
 /* Check return value. */
 OP2(SLJIT_SUB32 | SLJIT_SET_Z | SLJIT_SET_SIG_GREATER, SLJIT_UNUSED, 0, SLJIT_RETURN_REG, 0, SLJIT_IMM, 0);
-add_jump(compiler, &backtrack->topbacktracks, JUMP(SLJIT_SIG_GREATER32));
+add_jump(compiler, &backtrack->topbacktracks, JUMP(SLJIT_SIG_GREATER));
 if (common->abort_label == NULL)
-  add_jump(compiler, &common->abort, JUMP(SLJIT_NOT_EQUAL32) /* SIG_LESS */);
+  add_jump(compiler, &common->abort, JUMP(SLJIT_NOT_EQUAL) /* SIG_LESS */);
 else
-  JUMPTO(SLJIT_NOT_EQUAL32 /* SIG_LESS */, common->abort_label);
+  JUMPTO(SLJIT_NOT_EQUAL /* SIG_LESS */, common->abort_label);
 return cc + callout_length;
 }
 
@@ -11232,7 +11232,7 @@ early_fail_type = (early_fail_ptr & 0x7);
 early_fail_ptr >>= 3;
 
 /* During recursion, these optimizations are disabled. */
-if (common->early_fail_start_ptr == 0)
+if (common->early_fail_start_ptr == 0 && common->fast_forward_bc_ptr == NULL)
   {
   early_fail_ptr = 0;
   early_fail_type = type_skip;
@@ -13661,9 +13661,11 @@ if (!common->private_data_ptrs)
 memset(common->private_data_ptrs, 0, total_length * sizeof(sljit_s32));
 
 private_data_size = common->cbra_ptr + (re->top_bracket + 1) * sizeof(sljit_sw);
-set_private_data_ptrs(common, &private_data_size, ccend);
+
 if ((re->overall_options & PCRE2_ANCHORED) == 0 && (re->overall_options & PCRE2_NO_START_OPTIMIZE) == 0 && !common->has_skip_in_assert_back)
-  detect_early_fail(common, common->start, &private_data_size, 0, 0);
+  detect_early_fail(common, common->start, &private_data_size, 0, 0, TRUE);
+
+set_private_data_ptrs(common, &private_data_size, ccend);
 
 SLJIT_ASSERT(common->early_fail_start_ptr <= common->early_fail_end_ptr);
 
@@ -14130,6 +14132,10 @@ PCRE2_EXP_DEFN int PCRE2_CALL_CONVENTION
 pcre2_jit_compile(pcre2_code *code, uint32_t options)
 {
 pcre2_real_code *re = (pcre2_real_code *)code;
+#ifdef SUPPORT_JIT
+executable_functions *functions;
+static int executable_allocator_is_working = 0;
+#endif
 
 if (code == NULL)
   return PCRE2_ERROR_NULL;
@@ -14164,8 +14170,7 @@ actions are needed:
 */
 
 #ifdef SUPPORT_JIT
-executable_functions *functions = (executable_functions *)re->executable_jit;
-static int executable_allocator_is_working = 0;
+functions = (executable_functions *)re->executable_jit;
 #endif
 
 if ((options & PCRE2_JIT_INVALID_UTF) != 0)

+ 777 - 42
thirdparty/pcre2/src/pcre2_jit_simd_inc.h

@@ -39,7 +39,29 @@ POSSIBILITY OF SUCH DAMAGE.
 -----------------------------------------------------------------------------
 */
 
-#if (defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) && !(defined SUPPORT_VALGRIND)
+#if !(defined SUPPORT_VALGRIND)
+
+#if ((defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86) \
+     || (defined SLJIT_CONFIG_S390X && SLJIT_CONFIG_S390X))
+
+typedef enum {
+  vector_compare_match1,
+  vector_compare_match1i,
+  vector_compare_match2,
+} vector_compare_type;
+
+static SLJIT_INLINE sljit_u32 max_fast_forward_char_pair_offset(void)
+{
+#if PCRE2_CODE_UNIT_WIDTH == 8
+return 15;
+#elif PCRE2_CODE_UNIT_WIDTH == 16
+return 7;
+#elif PCRE2_CODE_UNIT_WIDTH == 32
+return 3;
+#else
+#error "Unsupported unit width"
+#endif
+}
 
 #if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
 static struct sljit_jump *jump_if_utf_char_start(struct sljit_compiler *compiler, sljit_s32 reg)
@@ -56,6 +78,10 @@ return CMP(SLJIT_NOT_EQUAL, reg, 0, SLJIT_IMM, 0xdc00);
 }
 #endif
 
+#endif /* SLJIT_CONFIG_X86 || SLJIT_CONFIG_S390X */
+
+#if (defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86)
+
 static sljit_s32 character_to_int32(PCRE2_UCHAR chr)
 {
 sljit_u32 value = chr;
@@ -97,13 +123,7 @@ instruction[4] = (sljit_u8)offset;
 sljit_emit_op_custom(compiler, instruction, 5);
 }
 
-typedef enum {
-    sse2_compare_match1,
-    sse2_compare_match1i,
-    sse2_compare_match2,
-} sse2_compare_type;
-
-static void fast_forward_char_pair_sse2_compare(struct sljit_compiler *compiler, sse2_compare_type compare_type,
+static void fast_forward_char_pair_sse2_compare(struct sljit_compiler *compiler, vector_compare_type compare_type,
   int step, sljit_s32 dst_ind, sljit_s32 cmp1_ind, sljit_s32 cmp2_ind, sljit_s32 tmp_ind)
 {
 sljit_u8 instruction[4];
@@ -112,11 +132,11 @@ instruction[1] = 0x0f;
 
 SLJIT_ASSERT(step >= 0 && step <= 3);
 
-if (compare_type != sse2_compare_match2)
+if (compare_type != vector_compare_match2)
   {
   if (step == 0)
     {
-    if (compare_type == sse2_compare_match1i)
+    if (compare_type == vector_compare_match1i)
       {
       /* POR xmm1, xmm2/m128 */
       /* instruction[0] = 0x66; */
@@ -185,14 +205,14 @@ switch (step)
 static void fast_forward_char_simd(compiler_common *common, PCRE2_UCHAR char1, PCRE2_UCHAR char2, sljit_s32 offset)
 {
 DEFINE_COMPILER;
+sljit_u8 instruction[8];
 struct sljit_label *start;
 #if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
 struct sljit_label *restart;
 #endif
 struct sljit_jump *quit;
 struct sljit_jump *partial_quit[2];
-sse2_compare_type compare_type = sse2_compare_match1;
-sljit_u8 instruction[8];
+vector_compare_type compare_type = vector_compare_match1;
 sljit_s32 tmp1_reg_ind = sljit_get_register_index(TMP1);
 sljit_s32 str_ptr_reg_ind = sljit_get_register_index(STR_PTR);
 sljit_s32 data_ind = 0;
@@ -207,12 +227,12 @@ SLJIT_UNUSED_ARG(offset);
 if (char1 != char2)
   {
   bit = char1 ^ char2;
-  compare_type = sse2_compare_match1i;
+  compare_type = vector_compare_match1i;
 
   if (!is_powerof2(bit))
     {
     bit = 0;
-    compare_type = sse2_compare_match2;
+    compare_type = vector_compare_match2;
     }
   }
 
@@ -349,11 +369,11 @@ if (common->utf && offset > 0)
 static jump_list *fast_requested_char_simd(compiler_common *common, PCRE2_UCHAR char1, PCRE2_UCHAR char2)
 {
 DEFINE_COMPILER;
+sljit_u8 instruction[8];
 struct sljit_label *start;
 struct sljit_jump *quit;
 jump_list *not_found = NULL;
-sse2_compare_type compare_type = sse2_compare_match1;
-sljit_u8 instruction[8];
+vector_compare_type compare_type = vector_compare_match1;
 sljit_s32 tmp1_reg_ind = sljit_get_register_index(TMP1);
 sljit_s32 str_ptr_reg_ind = sljit_get_register_index(STR_PTR);
 sljit_s32 data_ind = 0;
@@ -366,12 +386,12 @@ int i;
 if (char1 != char2)
   {
   bit = char1 ^ char2;
-  compare_type = sse2_compare_match1i;
+  compare_type = vector_compare_match1i;
 
   if (!is_powerof2(bit))
     {
     bit = 0;
-    compare_type = sse2_compare_match2;
+    compare_type = vector_compare_match2;
     }
   }
 
@@ -476,27 +496,15 @@ return not_found;
 
 #ifndef _WIN64
 
-static SLJIT_INLINE sljit_u32 max_fast_forward_char_pair_offset(void)
-{
-#if PCRE2_CODE_UNIT_WIDTH == 8
-return 15;
-#elif PCRE2_CODE_UNIT_WIDTH == 16
-return 7;
-#elif PCRE2_CODE_UNIT_WIDTH == 32
-return 3;
-#else
-#error "Unsupported unit width"
-#endif
-}
-
 #define JIT_HAS_FAST_FORWARD_CHAR_PAIR_SIMD (sljit_has_cpu_feature(SLJIT_HAS_SSE2))
 
 static void fast_forward_char_pair_simd(compiler_common *common, sljit_s32 offs1,
   PCRE2_UCHAR char1a, PCRE2_UCHAR char1b, sljit_s32 offs2, PCRE2_UCHAR char2a, PCRE2_UCHAR char2b)
 {
 DEFINE_COMPILER;
-sse2_compare_type compare1_type = sse2_compare_match1;
-sse2_compare_type compare2_type = sse2_compare_match1;
+sljit_u8 instruction[8];
+vector_compare_type compare1_type = vector_compare_match1;
+vector_compare_type compare2_type = vector_compare_match1;
 sljit_u32 bit1 = 0;
 sljit_u32 bit2 = 0;
 sljit_u32 diff = IN_UCHARS(offs1 - offs2);
@@ -516,7 +524,6 @@ struct sljit_label *start;
 struct sljit_label *restart;
 #endif
 struct sljit_jump *jump[2];
-sljit_u8 instruction[8];
 int i;
 
 SLJIT_ASSERT(common->mode == PCRE2_JIT_COMPLETE && offs1 > offs2);
@@ -549,13 +556,13 @@ else
   bit1 = char1a ^ char1b;
   if (is_powerof2(bit1))
     {
-    compare1_type = sse2_compare_match1i;
+    compare1_type = vector_compare_match1i;
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_IMM, character_to_int32(char1a | bit1));
     OP1(SLJIT_MOV, TMP2, 0, SLJIT_IMM, character_to_int32(bit1));
     }
   else
     {
-    compare1_type = sse2_compare_match2;
+    compare1_type = vector_compare_match2;
     bit1 = 0;
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_IMM, character_to_int32(char1a));
     OP1(SLJIT_MOV, TMP2, 0, SLJIT_IMM, character_to_int32(char1b));
@@ -578,13 +585,13 @@ else
   bit2 = char2a ^ char2b;
   if (is_powerof2(bit2))
     {
-    compare2_type = sse2_compare_match1i;
+    compare2_type = vector_compare_match1i;
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_IMM, character_to_int32(char2a | bit2));
     OP1(SLJIT_MOV, TMP2, 0, SLJIT_IMM, character_to_int32(bit2));
     }
   else
     {
-    compare2_type = sse2_compare_match2;
+    compare2_type = vector_compare_match2;
     bit2 = 0;
     OP1(SLJIT_MOV, TMP1, 0, SLJIT_IMM, character_to_int32(char2a));
     OP1(SLJIT_MOV, TMP2, 0, SLJIT_IMM, character_to_int32(char2b));
@@ -731,9 +738,6 @@ OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, TMP1, 0);
 
 add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
 
-if (common->match_end_ptr != 0)
-  OP1(SLJIT_MOV, STR_END, 0, SLJIT_MEM1(SLJIT_SP), common->match_end_ptr);
-
 #if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
 if (common->utf)
   {
@@ -760,7 +764,7 @@ if (common->match_end_ptr != 0)
 
 #undef SSE2_COMPARE_TYPE_INDEX
 
-#endif /* SLJIT_CONFIG_X86 && !SUPPORT_VALGRIND */
+#endif /* SLJIT_CONFIG_X86 */
 
 #if (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64 && (defined __ARM_NEON || defined __ARM_NEON__))
 
@@ -1121,3 +1125,734 @@ JUMPHERE(partial_quit);
 }
 
 #endif /* SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64 */
+
+#if (defined SLJIT_CONFIG_S390X && SLJIT_CONFIG_S390X)
+
+#if PCRE2_CODE_UNIT_WIDTH == 8
+#define VECTOR_ELEMENT_SIZE 0
+#elif PCRE2_CODE_UNIT_WIDTH == 16
+#define VECTOR_ELEMENT_SIZE 1
+#elif PCRE2_CODE_UNIT_WIDTH == 32
+#define VECTOR_ELEMENT_SIZE 2
+#else
+#error "Unsupported unit width"
+#endif
+
+static void load_from_mem_vector(struct sljit_compiler *compiler, BOOL vlbb, sljit_s32 dst_vreg,
+  sljit_s32 base_reg, sljit_s32 index_reg)
+{
+sljit_u16 instruction[3];
+
+instruction[0] = (sljit_u16)(0xe700 | (dst_vreg << 4) | index_reg);
+instruction[1] = (sljit_u16)(base_reg << 12);
+instruction[2] = (sljit_u16)((0x8 << 8) | (vlbb ? 0x07 : 0x06));
+
+sljit_emit_op_custom(compiler, instruction, 6);
+}
+
+#if PCRE2_CODE_UNIT_WIDTH == 32
+
+static void replicate_imm_vector(struct sljit_compiler *compiler, int step, sljit_s32 dst_vreg,
+  PCRE2_UCHAR chr, sljit_s32 tmp_general_reg)
+{
+sljit_u16 instruction[3];
+
+SLJIT_ASSERT(step >= 0 && step <= 1);
+
+if (chr < 0x7fff)
+  {
+  if (step == 1)
+    return;
+
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (dst_vreg << 4));
+  instruction[1] = (sljit_u16)chr;
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  return;
+  }
+
+if (step == 0)
+  {
+  OP1(SLJIT_MOV, tmp_general_reg, 0, SLJIT_IMM, chr);
+
+  /* VLVG */
+  instruction[0] = (sljit_u16)(0xe700 | (dst_vreg << 4) | sljit_get_register_index(tmp_general_reg));
+  instruction[1] = 0;
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x22);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  return;
+  }
+
+/* VREP */
+instruction[0] = (sljit_u16)(0xe700 | (dst_vreg << 4) | dst_vreg);
+instruction[1] = 0;
+instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xc << 8) | 0x4d);
+sljit_emit_op_custom(compiler, instruction, 6);
+}
+
+#endif
+
+static void fast_forward_char_pair_sse2_compare(struct sljit_compiler *compiler, vector_compare_type compare_type,
+  int step, sljit_s32 dst_ind, sljit_s32 cmp1_ind, sljit_s32 cmp2_ind, sljit_s32 tmp_ind)
+{
+sljit_u16 instruction[3];
+
+SLJIT_ASSERT(step >= 0 && step <= 2);
+
+if (step == 1)
+  {
+  /* VCEQ */
+  instruction[0] = (sljit_u16)(0xe700 | (dst_ind << 4) | dst_ind);
+  instruction[1] = (sljit_u16)(cmp1_ind << 12);
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0xf8);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  return;
+  }
+
+if (compare_type != vector_compare_match2)
+  {
+  if (step == 0 && compare_type == vector_compare_match1i)
+    {
+    /* VO */
+    instruction[0] = (sljit_u16)(0xe700 | (dst_ind << 4) | dst_ind);
+    instruction[1] = (sljit_u16)(cmp2_ind << 12);
+    instruction[2] = (sljit_u16)((0xe << 8) | 0x6a);
+    sljit_emit_op_custom(compiler, instruction, 6);
+    }
+  return;
+  }
+
+switch (step)
+  {
+  case 0:
+  /* VCEQ */
+  instruction[0] = (sljit_u16)(0xe700 | (tmp_ind << 4) | dst_ind);
+  instruction[1] = (sljit_u16)(cmp2_ind << 12);
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0xf8);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  return;
+
+  case 2:
+  /* VO */
+  instruction[0] = (sljit_u16)(0xe700 | (dst_ind << 4) | dst_ind);
+  instruction[1] = (sljit_u16)(tmp_ind << 12);
+  instruction[2] = (sljit_u16)((0xe << 8) | 0x6a);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  return;
+  }
+}
+
+#define JIT_HAS_FAST_FORWARD_CHAR_SIMD 1
+
+static void fast_forward_char_simd(compiler_common *common, PCRE2_UCHAR char1, PCRE2_UCHAR char2, sljit_s32 offset)
+{
+DEFINE_COMPILER;
+sljit_u16 instruction[3];
+struct sljit_label *start;
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+struct sljit_label *restart;
+#endif
+struct sljit_jump *quit;
+struct sljit_jump *partial_quit[2];
+vector_compare_type compare_type = vector_compare_match1;
+sljit_s32 tmp1_reg_ind = sljit_get_register_index(TMP1);
+sljit_s32 str_ptr_reg_ind = sljit_get_register_index(STR_PTR);
+sljit_s32 data_ind = 0;
+sljit_s32 tmp_ind = 1;
+sljit_s32 cmp1_ind = 2;
+sljit_s32 cmp2_ind = 3;
+sljit_s32 zero_ind = 4;
+sljit_u32 bit = 0;
+int i;
+
+SLJIT_UNUSED_ARG(offset);
+
+if (char1 != char2)
+  {
+  bit = char1 ^ char2;
+  compare_type = vector_compare_match1i;
+
+  if (!is_powerof2(bit))
+    {
+    bit = 0;
+    compare_type = vector_compare_match2;
+    }
+  }
+
+partial_quit[0] = CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0);
+if (common->mode == PCRE2_JIT_COMPLETE)
+  add_jump(compiler, &common->failed_match, partial_quit[0]);
+
+/* First part (unaligned start) */
+
+OP2(SLJIT_ADD, TMP2, 0, STR_PTR, 0, SLJIT_IMM, 16);
+
+#if PCRE2_CODE_UNIT_WIDTH != 32
+
+/* VREPI */
+instruction[0] = (sljit_u16)(0xe700 | (cmp1_ind << 4));
+instruction[1] = (sljit_u16)(char1 | bit);
+instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+if (char1 != char2)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (cmp2_ind << 4));
+  instruction[1] = (sljit_u16)(bit != 0 ? bit : char2);
+  /* instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45); */
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+#else /* PCRE2_CODE_UNIT_WIDTH == 32 */
+
+for (int i = 0; i < 2; i++)
+  {
+  replicate_imm_vector(compiler, i, cmp1_ind, char1 | bit, TMP1);
+
+  if (char1 != char2)
+    replicate_imm_vector(compiler, i, cmp2_ind, bit != 0 ? bit : char2, TMP1);
+  }
+
+#endif /* PCRE2_CODE_UNIT_WIDTH != 32 */
+
+if (compare_type == vector_compare_match2)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (zero_ind << 4));
+  instruction[1] = 0;
+  instruction[2] = (sljit_u16)((0x8 << 8) | 0x45);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+restart = LABEL();
+#endif
+
+load_from_mem_vector(compiler, TRUE, data_ind, str_ptr_reg_ind, 0);
+OP2(SLJIT_AND, TMP2, 0, TMP2, 0, SLJIT_IMM, ~15);
+
+if (compare_type != vector_compare_match2)
+  {
+  if (compare_type == vector_compare_match1i)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, 0, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFEE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((cmp1_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0x80);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+else
+  {
+  for (i = 0; i < 3; i++)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, i, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFENE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp1_reg_ind << 4) | data_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, TMP1, 0);
+quit = CMP(SLJIT_LESS, STR_PTR, 0, TMP2, 0);
+
+OP2(SLJIT_SUB, STR_PTR, 0, TMP2, 0, SLJIT_IMM, 16);
+
+/* Second part (aligned) */
+start = LABEL();
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, 16);
+
+partial_quit[1] = CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0);
+if (common->mode == PCRE2_JIT_COMPLETE)
+  add_jump(compiler, &common->failed_match, partial_quit[1]);
+
+load_from_mem_vector(compiler, TRUE, data_ind, str_ptr_reg_ind, 0);
+
+if (compare_type != vector_compare_match2)
+  {
+  if (compare_type == vector_compare_match1i)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, 0, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFEE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((cmp1_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0x80);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+else
+  {
+  for (i = 0; i < 3; i++)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, i, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFENE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+sljit_set_current_flags(compiler, SLJIT_SET_OVERFLOW);
+JUMPTO(SLJIT_OVERFLOW, start);
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp1_reg_ind << 4) | data_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, TMP1, 0);
+
+JUMPHERE(quit);
+
+if (common->mode != PCRE2_JIT_COMPLETE)
+  {
+  JUMPHERE(partial_quit[0]);
+  JUMPHERE(partial_quit[1]);
+  OP2(SLJIT_SUB | SLJIT_SET_GREATER, SLJIT_UNUSED, 0, STR_PTR, 0, STR_END, 0);
+  CMOV(SLJIT_GREATER, STR_PTR, STR_END, 0);
+  }
+else
+  add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+if (common->utf && offset > 0)
+  {
+  SLJIT_ASSERT(common->mode == PCRE2_JIT_COMPLETE);
+
+  OP1(MOV_UCHAR, TMP1, 0, SLJIT_MEM1(STR_PTR), IN_UCHARS(-offset));
+
+  quit = jump_if_utf_char_start(compiler, TMP1);
+
+  OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, IN_UCHARS(1));
+  add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+
+  OP2(SLJIT_ADD, TMP2, 0, STR_PTR, 0, SLJIT_IMM, 16);
+  JUMPTO(SLJIT_JUMP, restart);
+
+  JUMPHERE(quit);
+  }
+#endif
+}
+
+#define JIT_HAS_FAST_REQUESTED_CHAR_SIMD 1
+
+static jump_list *fast_requested_char_simd(compiler_common *common, PCRE2_UCHAR char1, PCRE2_UCHAR char2)
+{
+DEFINE_COMPILER;
+sljit_u16 instruction[3];
+struct sljit_label *start;
+struct sljit_jump *quit;
+jump_list *not_found = NULL;
+vector_compare_type compare_type = vector_compare_match1;
+sljit_s32 tmp1_reg_ind = sljit_get_register_index(TMP1);
+sljit_s32 tmp3_reg_ind = sljit_get_register_index(TMP3);
+sljit_s32 data_ind = 0;
+sljit_s32 tmp_ind = 1;
+sljit_s32 cmp1_ind = 2;
+sljit_s32 cmp2_ind = 3;
+sljit_s32 zero_ind = 4;
+sljit_u32 bit = 0;
+int i;
+
+if (char1 != char2)
+  {
+  bit = char1 ^ char2;
+  compare_type = vector_compare_match1i;
+
+  if (!is_powerof2(bit))
+    {
+    bit = 0;
+    compare_type = vector_compare_match2;
+    }
+  }
+
+add_jump(compiler, &not_found, CMP(SLJIT_GREATER_EQUAL, TMP1, 0, STR_END, 0));
+
+/* First part (unaligned start) */
+
+OP2(SLJIT_ADD, TMP2, 0, TMP1, 0, SLJIT_IMM, 16);
+
+#if PCRE2_CODE_UNIT_WIDTH != 32
+
+/* VREPI */
+instruction[0] = (sljit_u16)(0xe700 | (cmp1_ind << 4));
+instruction[1] = (sljit_u16)(char1 | bit);
+instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+if (char1 != char2)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (cmp2_ind << 4));
+  instruction[1] = (sljit_u16)(bit != 0 ? bit : char2);
+  /* instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45); */
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+#else /* PCRE2_CODE_UNIT_WIDTH == 32 */
+
+for (int i = 0; i < 2; i++)
+  {
+  replicate_imm_vector(compiler, i, cmp1_ind, char1 | bit, TMP3);
+
+  if (char1 != char2)
+    replicate_imm_vector(compiler, i, cmp2_ind, bit != 0 ? bit : char2, TMP3);
+  }
+
+#endif /* PCRE2_CODE_UNIT_WIDTH != 32 */
+
+if (compare_type == vector_compare_match2)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (zero_ind << 4));
+  instruction[1] = 0;
+  instruction[2] = (sljit_u16)((0x8 << 8) | 0x45);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+load_from_mem_vector(compiler, TRUE, data_ind, tmp1_reg_ind, 0);
+OP2(SLJIT_AND, TMP2, 0, TMP2, 0, SLJIT_IMM, ~15);
+
+if (compare_type != vector_compare_match2)
+  {
+  if (compare_type == vector_compare_match1i)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, 0, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFEE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((cmp1_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0x80);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+else
+  {
+  for (i = 0; i < 3; i++)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, i, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFENE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp3_reg_ind << 4) | data_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, TMP1, 0, TMP1, 0, TMP3, 0);
+quit = CMP(SLJIT_LESS, TMP1, 0, TMP2, 0);
+
+OP2(SLJIT_SUB, TMP1, 0, TMP2, 0, SLJIT_IMM, 16);
+
+/* Second part (aligned) */
+start = LABEL();
+
+OP2(SLJIT_ADD, TMP1, 0, TMP1, 0, SLJIT_IMM, 16);
+
+add_jump(compiler, &not_found, CMP(SLJIT_GREATER_EQUAL, TMP1, 0, STR_END, 0));
+
+load_from_mem_vector(compiler, TRUE, data_ind, tmp1_reg_ind, 0);
+
+if (compare_type != vector_compare_match2)
+  {
+  if (compare_type == vector_compare_match1i)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, 0, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFEE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((cmp1_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0xe << 8) | 0x80);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+else
+  {
+  for (i = 0; i < 3; i++)
+    fast_forward_char_pair_sse2_compare(compiler, compare_type, i, data_ind, cmp1_ind, cmp2_ind, tmp_ind);
+
+  /* VFENE */
+  instruction[0] = (sljit_u16)(0xe700 | (data_ind << 4) | data_ind);
+  instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+  instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+sljit_set_current_flags(compiler, SLJIT_SET_OVERFLOW);
+JUMPTO(SLJIT_OVERFLOW, start);
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp3_reg_ind << 4) | data_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, TMP1, 0, TMP1, 0, TMP3, 0);
+
+JUMPHERE(quit);
+add_jump(compiler, &not_found, CMP(SLJIT_GREATER_EQUAL, TMP1, 0, STR_END, 0));
+
+return not_found;
+}
+
+#define JIT_HAS_FAST_FORWARD_CHAR_PAIR_SIMD 1
+
+static void fast_forward_char_pair_simd(compiler_common *common, sljit_s32 offs1,
+  PCRE2_UCHAR char1a, PCRE2_UCHAR char1b, sljit_s32 offs2, PCRE2_UCHAR char2a, PCRE2_UCHAR char2b)
+{
+DEFINE_COMPILER;
+sljit_u16 instruction[3];
+struct sljit_label *start;
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+struct sljit_label *restart;
+#endif
+struct sljit_jump *quit;
+struct sljit_jump *jump[2];
+vector_compare_type compare1_type = vector_compare_match1;
+vector_compare_type compare2_type = vector_compare_match1;
+sljit_u32 bit1 = 0;
+sljit_u32 bit2 = 0;
+sljit_s32 diff = IN_UCHARS(offs2 - offs1);
+sljit_s32 tmp1_reg_ind = sljit_get_register_index(TMP1);
+sljit_s32 tmp2_reg_ind = sljit_get_register_index(TMP2);
+sljit_s32 str_ptr_reg_ind = sljit_get_register_index(STR_PTR);
+sljit_s32 data1_ind = 0;
+sljit_s32 data2_ind = 1;
+sljit_s32 tmp1_ind = 2;
+sljit_s32 tmp2_ind = 3;
+sljit_s32 cmp1a_ind = 4;
+sljit_s32 cmp1b_ind = 5;
+sljit_s32 cmp2a_ind = 6;
+sljit_s32 cmp2b_ind = 7;
+sljit_s32 zero_ind = 8;
+int i;
+
+SLJIT_ASSERT(common->mode == PCRE2_JIT_COMPLETE && offs1 > offs2);
+SLJIT_ASSERT(-diff <= (sljit_s32)IN_UCHARS(max_fast_forward_char_pair_offset()));
+SLJIT_ASSERT(tmp1_reg_ind != 0 && tmp2_reg_ind != 0);
+
+if (char1a != char1b)
+  {
+  bit1 = char1a ^ char1b;
+  compare1_type = vector_compare_match1i;
+
+  if (!is_powerof2(bit1))
+    {
+    bit1 = 0;
+    compare1_type = vector_compare_match2;
+    }
+  }
+
+if (char2a != char2b)
+  {
+  bit2 = char2a ^ char2b;
+  compare2_type = vector_compare_match1i;
+
+  if (!is_powerof2(bit2))
+    {
+    bit2 = 0;
+    compare2_type = vector_compare_match2;
+    }
+  }
+
+/* Initialize. */
+if (common->match_end_ptr != 0)
+  {
+  OP1(SLJIT_MOV, TMP1, 0, SLJIT_MEM1(SLJIT_SP), common->match_end_ptr);
+  OP1(SLJIT_MOV, TMP3, 0, STR_END, 0);
+  OP2(SLJIT_ADD, TMP1, 0, TMP1, 0, SLJIT_IMM, IN_UCHARS(offs1 + 1));
+
+  OP2(SLJIT_SUB | SLJIT_SET_LESS, SLJIT_UNUSED, 0, TMP1, 0, STR_END, 0);
+  CMOV(SLJIT_LESS, STR_END, TMP1, 0);
+  }
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, IN_UCHARS(offs1));
+add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+OP2(SLJIT_AND, TMP2, 0, STR_PTR, 0, SLJIT_IMM, ~15);
+
+#if PCRE2_CODE_UNIT_WIDTH != 32
+
+OP2(SLJIT_SUB, TMP1, 0, STR_PTR, 0, SLJIT_IMM, -diff);
+
+/* VREPI */
+instruction[0] = (sljit_u16)(0xe700 | (cmp1a_ind << 4));
+instruction[1] = (sljit_u16)(char1a | bit1);
+instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+if (char1a != char1b)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (cmp1b_ind << 4));
+  instruction[1] = (sljit_u16)(bit1 != 0 ? bit1 : char1b);
+  /* instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45); */
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+/* VREPI */
+instruction[0] = (sljit_u16)(0xe700 | (cmp2a_ind << 4));
+instruction[1] = (sljit_u16)(char2a | bit2);
+/* instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45); */
+sljit_emit_op_custom(compiler, instruction, 6);
+
+if (char2a != char2b)
+  {
+  /* VREPI */
+  instruction[0] = (sljit_u16)(0xe700 | (cmp2b_ind << 4));
+  instruction[1] = (sljit_u16)(bit2 != 0 ? bit2 : char2b);
+  /* instruction[2] = (sljit_u16)((VECTOR_ELEMENT_SIZE << 12) | (0x8 << 8) | 0x45); */
+  sljit_emit_op_custom(compiler, instruction, 6);
+  }
+
+#else /* PCRE2_CODE_UNIT_WIDTH == 32 */
+
+for (int i = 0; i < 2; i++)
+  {
+  replicate_imm_vector(compiler, i, cmp1a_ind, char1a | bit1, TMP1);
+
+  if (char1a != char1b)
+    replicate_imm_vector(compiler, i, cmp1b_ind, bit1 != 0 ? bit1 : char1b, TMP1);
+
+  replicate_imm_vector(compiler, i, cmp2a_ind, char2a | bit2, TMP1);
+
+  if (char2a != char2b)
+    replicate_imm_vector(compiler, i, cmp2b_ind, bit2 != 0 ? bit2 : char2b, TMP1);
+  }
+
+OP2(SLJIT_SUB, TMP1, 0, STR_PTR, 0, SLJIT_IMM, -diff);
+
+#endif /* PCRE2_CODE_UNIT_WIDTH != 32 */
+
+/* VREPI */
+instruction[0] = (sljit_u16)(0xe700 | (zero_ind << 4));
+instruction[1] = 0;
+instruction[2] = (sljit_u16)((0x8 << 8) | 0x45);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+restart = LABEL();
+#endif
+
+jump[0] = CMP(SLJIT_LESS, TMP1, 0, TMP2, 0);
+load_from_mem_vector(compiler, TRUE, data2_ind, tmp1_reg_ind, 0);
+jump[1] = JUMP(SLJIT_JUMP);
+JUMPHERE(jump[0]);
+load_from_mem_vector(compiler, FALSE, data2_ind, tmp1_reg_ind, 0);
+JUMPHERE(jump[1]);
+
+load_from_mem_vector(compiler, TRUE, data1_ind, str_ptr_reg_ind, 0);
+OP2(SLJIT_ADD, TMP2, 0, TMP2, 0, SLJIT_IMM, 16);
+
+for (i = 0; i < 3; i++)
+  {
+  fast_forward_char_pair_sse2_compare(compiler, compare1_type, i, data1_ind, cmp1a_ind, cmp1b_ind, tmp1_ind);
+  fast_forward_char_pair_sse2_compare(compiler, compare2_type, i, data2_ind, cmp2a_ind, cmp2b_ind, tmp2_ind);
+  }
+
+/* VN */
+instruction[0] = (sljit_u16)(0xe700 | (data1_ind << 4) | data1_ind);
+instruction[1] = (sljit_u16)(data2_ind << 12);
+instruction[2] = (sljit_u16)((0xe << 8) | 0x68);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+/* VFENE */
+instruction[0] = (sljit_u16)(0xe700 | (data1_ind << 4) | data1_ind);
+instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp1_reg_ind << 4) | data1_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, TMP1, 0);
+quit = CMP(SLJIT_LESS, STR_PTR, 0, TMP2, 0);
+
+OP2(SLJIT_SUB, STR_PTR, 0, TMP2, 0, SLJIT_IMM, 16);
+OP1(SLJIT_MOV, TMP1, 0, SLJIT_IMM, diff);
+
+/* Main loop. */
+start = LABEL();
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, 16);
+add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+
+load_from_mem_vector(compiler, FALSE, data1_ind, str_ptr_reg_ind, 0);
+load_from_mem_vector(compiler, FALSE, data2_ind, str_ptr_reg_ind, tmp1_reg_ind);
+
+for (i = 0; i < 3; i++)
+  {
+  fast_forward_char_pair_sse2_compare(compiler, compare1_type, i, data1_ind, cmp1a_ind, cmp1b_ind, tmp1_ind);
+  fast_forward_char_pair_sse2_compare(compiler, compare2_type, i, data2_ind, cmp2a_ind, cmp2b_ind, tmp2_ind);
+  }
+
+/* VN */
+instruction[0] = (sljit_u16)(0xe700 | (data1_ind << 4) | data1_ind);
+instruction[1] = (sljit_u16)(data2_ind << 12);
+instruction[2] = (sljit_u16)((0xe << 8) | 0x68);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+/* VFENE */
+instruction[0] = (sljit_u16)(0xe700 | (data1_ind << 4) | data1_ind);
+instruction[1] = (sljit_u16)((zero_ind << 12) | (1 << 4));
+instruction[2] = (sljit_u16)((0xe << 8) | 0x81);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+sljit_set_current_flags(compiler, SLJIT_SET_OVERFLOW);
+JUMPTO(SLJIT_OVERFLOW, start);
+
+/* VLGVB */
+instruction[0] = (sljit_u16)(0xe700 | (tmp2_reg_ind << 4) | data1_ind);
+instruction[1] = 7;
+instruction[2] = (sljit_u16)((0x4 << 8) | 0x21);
+sljit_emit_op_custom(compiler, instruction, 6);
+
+OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, TMP2, 0);
+
+JUMPHERE(quit);
+
+add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+
+#if defined SUPPORT_UNICODE && PCRE2_CODE_UNIT_WIDTH != 32
+if (common->utf)
+  {
+  SLJIT_ASSERT(common->mode == PCRE2_JIT_COMPLETE);
+
+  OP1(MOV_UCHAR, TMP1, 0, SLJIT_MEM1(STR_PTR), IN_UCHARS(-offs1));
+
+  quit = jump_if_utf_char_start(compiler, TMP1);
+
+  OP2(SLJIT_ADD, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, IN_UCHARS(1));
+  add_jump(compiler, &common->failed_match, CMP(SLJIT_GREATER_EQUAL, STR_PTR, 0, STR_END, 0));
+
+  /* TMP1 contains diff. */
+  OP2(SLJIT_AND, TMP2, 0, STR_PTR, 0, SLJIT_IMM, ~15);
+  OP2(SLJIT_SUB, TMP1, 0, STR_PTR, 0, SLJIT_IMM, -diff);
+  JUMPTO(SLJIT_JUMP, restart);
+
+  JUMPHERE(quit);
+  }
+#endif
+
+OP2(SLJIT_SUB, STR_PTR, 0, STR_PTR, 0, SLJIT_IMM, IN_UCHARS(offs1));
+
+if (common->match_end_ptr != 0)
+  OP1(SLJIT_MOV, STR_END, 0, TMP3, 0);
+}
+
+#endif /* SLJIT_CONFIG_S390X */
+
+#endif /* !SUPPORT_VALGRIND */

+ 49 - 28
thirdparty/pcre2/src/pcre2_match.c

@@ -7,7 +7,7 @@ and semantics are as close as possible to those of the Perl 5 language.
 
                        Written by Philip Hazel
      Original API code Copyright (c) 1997-2012 University of Cambridge
-          New API code Copyright (c) 2015-2020 University of Cambridge
+          New API code Copyright (c) 2015-2021 University of Cambridge
 
 -----------------------------------------------------------------------------
 Redistribution and use in source and binary forms, with or without
@@ -818,10 +818,12 @@ fprintf(stderr, "++ op=%d\n", *Fecode);
 
       /* N is now the frame of the recursion; the previous frame is at the
       OP_RECURSE position. Go back there, copying the current subject position
-      and mark, and move on past the OP_RECURSE. */
+      and mark, and the start_match position (\K might have changed it), and
+      then move on past the OP_RECURSE. */
 
       P->eptr = Feptr;
       P->mark = Fmark;
+      P->start_match = Fstart_match;
       F = P;
       Fecode += 1 + LINK_SIZE;
       continue;
@@ -6115,8 +6117,8 @@ BOOL has_req_cu = FALSE;
 BOOL startline;
 
 #if PCRE2_CODE_UNIT_WIDTH == 8
-BOOL memchr_not_found_first_cu;
-BOOL memchr_not_found_first_cu2;
+PCRE2_SPTR memchr_found_first_cu;
+PCRE2_SPTR memchr_found_first_cu2;
 #endif
 
 PCRE2_UCHAR first_cu = 0;
@@ -6710,8 +6712,8 @@ start_partial = match_partial = NULL;
 mb->hitend = FALSE;
 
 #if PCRE2_CODE_UNIT_WIDTH == 8
-memchr_not_found_first_cu = FALSE;
-memchr_not_found_first_cu2 = FALSE;
+memchr_found_first_cu = NULL;
+memchr_found_first_cu2 = NULL;
 #endif
 
 for(;;)
@@ -6780,13 +6782,7 @@ for(;;)
         }
       }
 
-    /* Not anchored. Advance to a unique first code unit if there is one. In
-    8-bit mode, the use of memchr() gives a big speed up, even though we have
-    to call it twice in caseless mode, in order to find the earliest occurrence
-    of the character in either of its cases. If a call to memchr() that
-    searches the rest of the subject fails to find one case, remember that in
-    order not to keep on repeating the search. This can make a huge difference
-    when the strings are very long and only one case is present. */
+    /* Not anchored. Advance to a unique first code unit if there is one. */
 
     else
       {
@@ -6794,43 +6790,68 @@ for(;;)
         {
         if (first_cu != first_cu2)  /* Caseless */
           {
+          /* In 16-bit and 32_bit modes we have to do our own search, so can
+          look for both cases at once. */
+
 #if PCRE2_CODE_UNIT_WIDTH != 8
           PCRE2_UCHAR smc;
           while (start_match < end_subject &&
                 (smc = UCHAR21TEST(start_match)) != first_cu &&
-                  smc != first_cu2)
+                 smc != first_cu2)
             start_match++;
+#else
+          /* In 8-bit mode, the use of memchr() gives a big speed up, even
+          though we have to call it twice in order to find the earliest
+          occurrence of the code unit in either of its cases. Caching is used
+          to remember the positions of previously found code units. This can
+          make a huge difference when the strings are very long and only one
+          case is actually present. */
 
-#else  /* 8-bit code units */
           PCRE2_SPTR pp1 = NULL;
           PCRE2_SPTR pp2 = NULL;
-          PCRE2_SIZE cu2size = end_subject - start_match;
+          PCRE2_SIZE searchlength = end_subject - start_match;
 
-          if (!memchr_not_found_first_cu)
+          /* If we haven't got a previously found position for first_cu, or if
+          the current starting position is later, we need to do a search. If
+          the code unit is not found, set it to the end. */
+
+          if (memchr_found_first_cu == NULL ||
+              start_match > memchr_found_first_cu)
             {
-            pp1 = memchr(start_match, first_cu, end_subject - start_match);
-            if (pp1 == NULL) memchr_not_found_first_cu = TRUE;
-              else cu2size = pp1 - start_match;
+            pp1 = memchr(start_match, first_cu, searchlength);
+            memchr_found_first_cu = (pp1 == NULL)? end_subject : pp1;
             }
 
-          /* If pp1 is not NULL, we have arranged to search only as far as pp1,
-          to see if the other case is earlier, so we can set "not found" only
-          when both searches have returned NULL. */
+          /* If the start is before a previously found position, use the
+          previous position, or NULL if a previous search failed. */
+
+          else pp1 = (memchr_found_first_cu == end_subject)? NULL :
+            memchr_found_first_cu;
 
-          if (!memchr_not_found_first_cu2)
+          /* Do the same thing for the other case. */
+
+          if (memchr_found_first_cu2 == NULL ||
+              start_match > memchr_found_first_cu2)
             {
-            pp2 = memchr(start_match, first_cu2, cu2size);
-            memchr_not_found_first_cu2 = (pp2 == NULL && pp1 == NULL);
+            pp2 = memchr(start_match, first_cu2, searchlength);
+            memchr_found_first_cu2 = (pp2 == NULL)? end_subject : pp2;
             }
 
+          else pp2 = (memchr_found_first_cu2 == end_subject)? NULL :
+            memchr_found_first_cu2;
+
+          /* Set the start to the end of the subject if neither case was found.
+          Otherwise, use the earlier found point. */
+
           if (pp1 == NULL)
             start_match = (pp2 == NULL)? end_subject : pp2;
           else
             start_match = (pp2 == NULL || pp1 < pp2)? pp1 : pp2;
-#endif
+
+#endif  /* 8-bit handling */
           }
 
-        /* The caseful case */
+        /* The caseful case is much simpler. */
 
         else
           {

+ 181 - 166
thirdparty/pcre2/src/pcre2_tables.c

@@ -273,6 +273,7 @@ strings to make sure that UTF-8 support works on EBCDIC platforms. */
 #define STRING_Cs0 STR_C STR_s "\0"
 #define STRING_Cuneiform0 STR_C STR_u STR_n STR_e STR_i STR_f STR_o STR_r STR_m "\0"
 #define STRING_Cypriot0 STR_C STR_y STR_p STR_r STR_i STR_o STR_t "\0"
+#define STRING_Cypro_Minoan0 STR_C STR_y STR_p STR_r STR_o STR_UNDERSCORE STR_M STR_i STR_n STR_o STR_a STR_n "\0"
 #define STRING_Cyrillic0 STR_C STR_y STR_r STR_i STR_l STR_l STR_i STR_c "\0"
 #define STRING_Deseret0 STR_D STR_e STR_s STR_e STR_r STR_e STR_t "\0"
 #define STRING_Devanagari0 STR_D STR_e STR_v STR_a STR_n STR_a STR_g STR_a STR_r STR_i "\0"
@@ -371,6 +372,7 @@ strings to make sure that UTF-8 support works on EBCDIC platforms. */
 #define STRING_Old_Sogdian0 STR_O STR_l STR_d STR_UNDERSCORE STR_S STR_o STR_g STR_d STR_i STR_a STR_n "\0"
 #define STRING_Old_South_Arabian0 STR_O STR_l STR_d STR_UNDERSCORE STR_S STR_o STR_u STR_t STR_h STR_UNDERSCORE STR_A STR_r STR_a STR_b STR_i STR_a STR_n "\0"
 #define STRING_Old_Turkic0 STR_O STR_l STR_d STR_UNDERSCORE STR_T STR_u STR_r STR_k STR_i STR_c "\0"
+#define STRING_Old_Uyghur0 STR_O STR_l STR_d STR_UNDERSCORE STR_U STR_y STR_g STR_h STR_u STR_r "\0"
 #define STRING_Oriya0 STR_O STR_r STR_i STR_y STR_a "\0"
 #define STRING_Osage0 STR_O STR_s STR_a STR_g STR_e "\0"
 #define STRING_Osmanya0 STR_O STR_s STR_m STR_a STR_n STR_y STR_a "\0"
@@ -415,6 +417,7 @@ strings to make sure that UTF-8 support works on EBCDIC platforms. */
 #define STRING_Tai_Viet0 STR_T STR_a STR_i STR_UNDERSCORE STR_V STR_i STR_e STR_t "\0"
 #define STRING_Takri0 STR_T STR_a STR_k STR_r STR_i "\0"
 #define STRING_Tamil0 STR_T STR_a STR_m STR_i STR_l "\0"
+#define STRING_Tangsa0 STR_T STR_a STR_n STR_g STR_s STR_a "\0"
 #define STRING_Tangut0 STR_T STR_a STR_n STR_g STR_u STR_t "\0"
 #define STRING_Telugu0 STR_T STR_e STR_l STR_u STR_g STR_u "\0"
 #define STRING_Thaana0 STR_T STR_h STR_a STR_a STR_n STR_a "\0"
@@ -422,9 +425,11 @@ strings to make sure that UTF-8 support works on EBCDIC platforms. */
 #define STRING_Tibetan0 STR_T STR_i STR_b STR_e STR_t STR_a STR_n "\0"
 #define STRING_Tifinagh0 STR_T STR_i STR_f STR_i STR_n STR_a STR_g STR_h "\0"
 #define STRING_Tirhuta0 STR_T STR_i STR_r STR_h STR_u STR_t STR_a "\0"
+#define STRING_Toto0 STR_T STR_o STR_t STR_o "\0"
 #define STRING_Ugaritic0 STR_U STR_g STR_a STR_r STR_i STR_t STR_i STR_c "\0"
 #define STRING_Unknown0 STR_U STR_n STR_k STR_n STR_o STR_w STR_n "\0"
 #define STRING_Vai0 STR_V STR_a STR_i "\0"
+#define STRING_Vithkuqi0 STR_V STR_i STR_t STR_h STR_k STR_u STR_q STR_i "\0"
 #define STRING_Wancho0 STR_W STR_a STR_n STR_c STR_h STR_o "\0"
 #define STRING_Warang_Citi0 STR_W STR_a STR_r STR_a STR_n STR_g STR_UNDERSCORE STR_C STR_i STR_t STR_i "\0"
 #define STRING_Xan0 STR_X STR_a STR_n "\0"
@@ -476,6 +481,7 @@ const char PRIV(utt_names)[] =
   STRING_Cs0
   STRING_Cuneiform0
   STRING_Cypriot0
+  STRING_Cypro_Minoan0
   STRING_Cyrillic0
   STRING_Deseret0
   STRING_Devanagari0
@@ -574,6 +580,7 @@ const char PRIV(utt_names)[] =
   STRING_Old_Sogdian0
   STRING_Old_South_Arabian0
   STRING_Old_Turkic0
+  STRING_Old_Uyghur0
   STRING_Oriya0
   STRING_Osage0
   STRING_Osmanya0
@@ -618,6 +625,7 @@ const char PRIV(utt_names)[] =
   STRING_Tai_Viet0
   STRING_Takri0
   STRING_Tamil0
+  STRING_Tangsa0
   STRING_Tangut0
   STRING_Telugu0
   STRING_Thaana0
@@ -625,9 +633,11 @@ const char PRIV(utt_names)[] =
   STRING_Tibetan0
   STRING_Tifinagh0
   STRING_Tirhuta0
+  STRING_Toto0
   STRING_Ugaritic0
   STRING_Unknown0
   STRING_Vai0
+  STRING_Vithkuqi0
   STRING_Wancho0
   STRING_Warang_Citi0
   STRING_Xan0
@@ -679,172 +689,177 @@ const ucp_type_table PRIV(utt)[] = {
   { 255, PT_PC, ucp_Cs },
   { 258, PT_SC, ucp_Cuneiform },
   { 268, PT_SC, ucp_Cypriot },
-  { 276, PT_SC, ucp_Cyrillic },
-  { 285, PT_SC, ucp_Deseret },
-  { 293, PT_SC, ucp_Devanagari },
-  { 304, PT_SC, ucp_Dives_Akuru },
-  { 316, PT_SC, ucp_Dogra },
-  { 322, PT_SC, ucp_Duployan },
-  { 331, PT_SC, ucp_Egyptian_Hieroglyphs },
-  { 352, PT_SC, ucp_Elbasan },
-  { 360, PT_SC, ucp_Elymaic },
-  { 368, PT_SC, ucp_Ethiopic },
-  { 377, PT_SC, ucp_Georgian },
-  { 386, PT_SC, ucp_Glagolitic },
-  { 397, PT_SC, ucp_Gothic },
-  { 404, PT_SC, ucp_Grantha },
-  { 412, PT_SC, ucp_Greek },
-  { 418, PT_SC, ucp_Gujarati },
-  { 427, PT_SC, ucp_Gunjala_Gondi },
-  { 441, PT_SC, ucp_Gurmukhi },
-  { 450, PT_SC, ucp_Han },
-  { 454, PT_SC, ucp_Hangul },
-  { 461, PT_SC, ucp_Hanifi_Rohingya },
-  { 477, PT_SC, ucp_Hanunoo },
-  { 485, PT_SC, ucp_Hatran },
-  { 492, PT_SC, ucp_Hebrew },
-  { 499, PT_SC, ucp_Hiragana },
-  { 508, PT_SC, ucp_Imperial_Aramaic },
-  { 525, PT_SC, ucp_Inherited },
-  { 535, PT_SC, ucp_Inscriptional_Pahlavi },
-  { 557, PT_SC, ucp_Inscriptional_Parthian },
-  { 580, PT_SC, ucp_Javanese },
-  { 589, PT_SC, ucp_Kaithi },
-  { 596, PT_SC, ucp_Kannada },
-  { 604, PT_SC, ucp_Katakana },
-  { 613, PT_SC, ucp_Kayah_Li },
-  { 622, PT_SC, ucp_Kharoshthi },
-  { 633, PT_SC, ucp_Khitan_Small_Script },
-  { 653, PT_SC, ucp_Khmer },
-  { 659, PT_SC, ucp_Khojki },
-  { 666, PT_SC, ucp_Khudawadi },
-  { 676, PT_GC, ucp_L },
-  { 678, PT_LAMP, 0 },
-  { 681, PT_SC, ucp_Lao },
-  { 685, PT_SC, ucp_Latin },
-  { 691, PT_SC, ucp_Lepcha },
-  { 698, PT_SC, ucp_Limbu },
-  { 704, PT_SC, ucp_Linear_A },
-  { 713, PT_SC, ucp_Linear_B },
-  { 722, PT_SC, ucp_Lisu },
-  { 727, PT_PC, ucp_Ll },
-  { 730, PT_PC, ucp_Lm },
-  { 733, PT_PC, ucp_Lo },
-  { 736, PT_PC, ucp_Lt },
-  { 739, PT_PC, ucp_Lu },
-  { 742, PT_SC, ucp_Lycian },
-  { 749, PT_SC, ucp_Lydian },
-  { 756, PT_GC, ucp_M },
-  { 758, PT_SC, ucp_Mahajani },
-  { 767, PT_SC, ucp_Makasar },
-  { 775, PT_SC, ucp_Malayalam },
-  { 785, PT_SC, ucp_Mandaic },
-  { 793, PT_SC, ucp_Manichaean },
-  { 804, PT_SC, ucp_Marchen },
-  { 812, PT_SC, ucp_Masaram_Gondi },
-  { 826, PT_PC, ucp_Mc },
-  { 829, PT_PC, ucp_Me },
-  { 832, PT_SC, ucp_Medefaidrin },
-  { 844, PT_SC, ucp_Meetei_Mayek },
-  { 857, PT_SC, ucp_Mende_Kikakui },
-  { 871, PT_SC, ucp_Meroitic_Cursive },
-  { 888, PT_SC, ucp_Meroitic_Hieroglyphs },
-  { 909, PT_SC, ucp_Miao },
-  { 914, PT_PC, ucp_Mn },
-  { 917, PT_SC, ucp_Modi },
-  { 922, PT_SC, ucp_Mongolian },
-  { 932, PT_SC, ucp_Mro },
-  { 936, PT_SC, ucp_Multani },
-  { 944, PT_SC, ucp_Myanmar },
-  { 952, PT_GC, ucp_N },
-  { 954, PT_SC, ucp_Nabataean },
-  { 964, PT_SC, ucp_Nandinagari },
-  { 976, PT_PC, ucp_Nd },
-  { 979, PT_SC, ucp_New_Tai_Lue },
-  { 991, PT_SC, ucp_Newa },
-  { 996, PT_SC, ucp_Nko },
-  { 1000, PT_PC, ucp_Nl },
-  { 1003, PT_PC, ucp_No },
-  { 1006, PT_SC, ucp_Nushu },
-  { 1012, PT_SC, ucp_Nyiakeng_Puachue_Hmong },
-  { 1035, PT_SC, ucp_Ogham },
-  { 1041, PT_SC, ucp_Ol_Chiki },
-  { 1050, PT_SC, ucp_Old_Hungarian },
-  { 1064, PT_SC, ucp_Old_Italic },
-  { 1075, PT_SC, ucp_Old_North_Arabian },
-  { 1093, PT_SC, ucp_Old_Permic },
-  { 1104, PT_SC, ucp_Old_Persian },
-  { 1116, PT_SC, ucp_Old_Sogdian },
-  { 1128, PT_SC, ucp_Old_South_Arabian },
-  { 1146, PT_SC, ucp_Old_Turkic },
-  { 1157, PT_SC, ucp_Oriya },
-  { 1163, PT_SC, ucp_Osage },
-  { 1169, PT_SC, ucp_Osmanya },
-  { 1177, PT_GC, ucp_P },
-  { 1179, PT_SC, ucp_Pahawh_Hmong },
-  { 1192, PT_SC, ucp_Palmyrene },
-  { 1202, PT_SC, ucp_Pau_Cin_Hau },
-  { 1214, PT_PC, ucp_Pc },
-  { 1217, PT_PC, ucp_Pd },
-  { 1220, PT_PC, ucp_Pe },
-  { 1223, PT_PC, ucp_Pf },
-  { 1226, PT_SC, ucp_Phags_Pa },
-  { 1235, PT_SC, ucp_Phoenician },
-  { 1246, PT_PC, ucp_Pi },
-  { 1249, PT_PC, ucp_Po },
-  { 1252, PT_PC, ucp_Ps },
-  { 1255, PT_SC, ucp_Psalter_Pahlavi },
-  { 1271, PT_SC, ucp_Rejang },
-  { 1278, PT_SC, ucp_Runic },
-  { 1284, PT_GC, ucp_S },
-  { 1286, PT_SC, ucp_Samaritan },
-  { 1296, PT_SC, ucp_Saurashtra },
-  { 1307, PT_PC, ucp_Sc },
-  { 1310, PT_SC, ucp_Sharada },
-  { 1318, PT_SC, ucp_Shavian },
-  { 1326, PT_SC, ucp_Siddham },
-  { 1334, PT_SC, ucp_SignWriting },
-  { 1346, PT_SC, ucp_Sinhala },
-  { 1354, PT_PC, ucp_Sk },
-  { 1357, PT_PC, ucp_Sm },
-  { 1360, PT_PC, ucp_So },
-  { 1363, PT_SC, ucp_Sogdian },
-  { 1371, PT_SC, ucp_Sora_Sompeng },
-  { 1384, PT_SC, ucp_Soyombo },
-  { 1392, PT_SC, ucp_Sundanese },
-  { 1402, PT_SC, ucp_Syloti_Nagri },
-  { 1415, PT_SC, ucp_Syriac },
-  { 1422, PT_SC, ucp_Tagalog },
-  { 1430, PT_SC, ucp_Tagbanwa },
-  { 1439, PT_SC, ucp_Tai_Le },
-  { 1446, PT_SC, ucp_Tai_Tham },
-  { 1455, PT_SC, ucp_Tai_Viet },
-  { 1464, PT_SC, ucp_Takri },
-  { 1470, PT_SC, ucp_Tamil },
-  { 1476, PT_SC, ucp_Tangut },
-  { 1483, PT_SC, ucp_Telugu },
-  { 1490, PT_SC, ucp_Thaana },
-  { 1497, PT_SC, ucp_Thai },
-  { 1502, PT_SC, ucp_Tibetan },
-  { 1510, PT_SC, ucp_Tifinagh },
-  { 1519, PT_SC, ucp_Tirhuta },
-  { 1527, PT_SC, ucp_Ugaritic },
-  { 1536, PT_SC, ucp_Unknown },
-  { 1544, PT_SC, ucp_Vai },
-  { 1548, PT_SC, ucp_Wancho },
-  { 1555, PT_SC, ucp_Warang_Citi },
-  { 1567, PT_ALNUM, 0 },
-  { 1571, PT_PXSPACE, 0 },
-  { 1575, PT_SPACE, 0 },
-  { 1579, PT_UCNC, 0 },
-  { 1583, PT_WORD, 0 },
-  { 1587, PT_SC, ucp_Yezidi },
-  { 1594, PT_SC, ucp_Yi },
-  { 1597, PT_GC, ucp_Z },
-  { 1599, PT_SC, ucp_Zanabazar_Square },
-  { 1616, PT_PC, ucp_Zl },
-  { 1619, PT_PC, ucp_Zp },
-  { 1622, PT_PC, ucp_Zs }
+  { 276, PT_SC, ucp_Cypro_Minoan },
+  { 289, PT_SC, ucp_Cyrillic },
+  { 298, PT_SC, ucp_Deseret },
+  { 306, PT_SC, ucp_Devanagari },
+  { 317, PT_SC, ucp_Dives_Akuru },
+  { 329, PT_SC, ucp_Dogra },
+  { 335, PT_SC, ucp_Duployan },
+  { 344, PT_SC, ucp_Egyptian_Hieroglyphs },
+  { 365, PT_SC, ucp_Elbasan },
+  { 373, PT_SC, ucp_Elymaic },
+  { 381, PT_SC, ucp_Ethiopic },
+  { 390, PT_SC, ucp_Georgian },
+  { 399, PT_SC, ucp_Glagolitic },
+  { 410, PT_SC, ucp_Gothic },
+  { 417, PT_SC, ucp_Grantha },
+  { 425, PT_SC, ucp_Greek },
+  { 431, PT_SC, ucp_Gujarati },
+  { 440, PT_SC, ucp_Gunjala_Gondi },
+  { 454, PT_SC, ucp_Gurmukhi },
+  { 463, PT_SC, ucp_Han },
+  { 467, PT_SC, ucp_Hangul },
+  { 474, PT_SC, ucp_Hanifi_Rohingya },
+  { 490, PT_SC, ucp_Hanunoo },
+  { 498, PT_SC, ucp_Hatran },
+  { 505, PT_SC, ucp_Hebrew },
+  { 512, PT_SC, ucp_Hiragana },
+  { 521, PT_SC, ucp_Imperial_Aramaic },
+  { 538, PT_SC, ucp_Inherited },
+  { 548, PT_SC, ucp_Inscriptional_Pahlavi },
+  { 570, PT_SC, ucp_Inscriptional_Parthian },
+  { 593, PT_SC, ucp_Javanese },
+  { 602, PT_SC, ucp_Kaithi },
+  { 609, PT_SC, ucp_Kannada },
+  { 617, PT_SC, ucp_Katakana },
+  { 626, PT_SC, ucp_Kayah_Li },
+  { 635, PT_SC, ucp_Kharoshthi },
+  { 646, PT_SC, ucp_Khitan_Small_Script },
+  { 666, PT_SC, ucp_Khmer },
+  { 672, PT_SC, ucp_Khojki },
+  { 679, PT_SC, ucp_Khudawadi },
+  { 689, PT_GC, ucp_L },
+  { 691, PT_LAMP, 0 },
+  { 694, PT_SC, ucp_Lao },
+  { 698, PT_SC, ucp_Latin },
+  { 704, PT_SC, ucp_Lepcha },
+  { 711, PT_SC, ucp_Limbu },
+  { 717, PT_SC, ucp_Linear_A },
+  { 726, PT_SC, ucp_Linear_B },
+  { 735, PT_SC, ucp_Lisu },
+  { 740, PT_PC, ucp_Ll },
+  { 743, PT_PC, ucp_Lm },
+  { 746, PT_PC, ucp_Lo },
+  { 749, PT_PC, ucp_Lt },
+  { 752, PT_PC, ucp_Lu },
+  { 755, PT_SC, ucp_Lycian },
+  { 762, PT_SC, ucp_Lydian },
+  { 769, PT_GC, ucp_M },
+  { 771, PT_SC, ucp_Mahajani },
+  { 780, PT_SC, ucp_Makasar },
+  { 788, PT_SC, ucp_Malayalam },
+  { 798, PT_SC, ucp_Mandaic },
+  { 806, PT_SC, ucp_Manichaean },
+  { 817, PT_SC, ucp_Marchen },
+  { 825, PT_SC, ucp_Masaram_Gondi },
+  { 839, PT_PC, ucp_Mc },
+  { 842, PT_PC, ucp_Me },
+  { 845, PT_SC, ucp_Medefaidrin },
+  { 857, PT_SC, ucp_Meetei_Mayek },
+  { 870, PT_SC, ucp_Mende_Kikakui },
+  { 884, PT_SC, ucp_Meroitic_Cursive },
+  { 901, PT_SC, ucp_Meroitic_Hieroglyphs },
+  { 922, PT_SC, ucp_Miao },
+  { 927, PT_PC, ucp_Mn },
+  { 930, PT_SC, ucp_Modi },
+  { 935, PT_SC, ucp_Mongolian },
+  { 945, PT_SC, ucp_Mro },
+  { 949, PT_SC, ucp_Multani },
+  { 957, PT_SC, ucp_Myanmar },
+  { 965, PT_GC, ucp_N },
+  { 967, PT_SC, ucp_Nabataean },
+  { 977, PT_SC, ucp_Nandinagari },
+  { 989, PT_PC, ucp_Nd },
+  { 992, PT_SC, ucp_New_Tai_Lue },
+  { 1004, PT_SC, ucp_Newa },
+  { 1009, PT_SC, ucp_Nko },
+  { 1013, PT_PC, ucp_Nl },
+  { 1016, PT_PC, ucp_No },
+  { 1019, PT_SC, ucp_Nushu },
+  { 1025, PT_SC, ucp_Nyiakeng_Puachue_Hmong },
+  { 1048, PT_SC, ucp_Ogham },
+  { 1054, PT_SC, ucp_Ol_Chiki },
+  { 1063, PT_SC, ucp_Old_Hungarian },
+  { 1077, PT_SC, ucp_Old_Italic },
+  { 1088, PT_SC, ucp_Old_North_Arabian },
+  { 1106, PT_SC, ucp_Old_Permic },
+  { 1117, PT_SC, ucp_Old_Persian },
+  { 1129, PT_SC, ucp_Old_Sogdian },
+  { 1141, PT_SC, ucp_Old_South_Arabian },
+  { 1159, PT_SC, ucp_Old_Turkic },
+  { 1170, PT_SC, ucp_Old_Uyghur },
+  { 1181, PT_SC, ucp_Oriya },
+  { 1187, PT_SC, ucp_Osage },
+  { 1193, PT_SC, ucp_Osmanya },
+  { 1201, PT_GC, ucp_P },
+  { 1203, PT_SC, ucp_Pahawh_Hmong },
+  { 1216, PT_SC, ucp_Palmyrene },
+  { 1226, PT_SC, ucp_Pau_Cin_Hau },
+  { 1238, PT_PC, ucp_Pc },
+  { 1241, PT_PC, ucp_Pd },
+  { 1244, PT_PC, ucp_Pe },
+  { 1247, PT_PC, ucp_Pf },
+  { 1250, PT_SC, ucp_Phags_Pa },
+  { 1259, PT_SC, ucp_Phoenician },
+  { 1270, PT_PC, ucp_Pi },
+  { 1273, PT_PC, ucp_Po },
+  { 1276, PT_PC, ucp_Ps },
+  { 1279, PT_SC, ucp_Psalter_Pahlavi },
+  { 1295, PT_SC, ucp_Rejang },
+  { 1302, PT_SC, ucp_Runic },
+  { 1308, PT_GC, ucp_S },
+  { 1310, PT_SC, ucp_Samaritan },
+  { 1320, PT_SC, ucp_Saurashtra },
+  { 1331, PT_PC, ucp_Sc },
+  { 1334, PT_SC, ucp_Sharada },
+  { 1342, PT_SC, ucp_Shavian },
+  { 1350, PT_SC, ucp_Siddham },
+  { 1358, PT_SC, ucp_SignWriting },
+  { 1370, PT_SC, ucp_Sinhala },
+  { 1378, PT_PC, ucp_Sk },
+  { 1381, PT_PC, ucp_Sm },
+  { 1384, PT_PC, ucp_So },
+  { 1387, PT_SC, ucp_Sogdian },
+  { 1395, PT_SC, ucp_Sora_Sompeng },
+  { 1408, PT_SC, ucp_Soyombo },
+  { 1416, PT_SC, ucp_Sundanese },
+  { 1426, PT_SC, ucp_Syloti_Nagri },
+  { 1439, PT_SC, ucp_Syriac },
+  { 1446, PT_SC, ucp_Tagalog },
+  { 1454, PT_SC, ucp_Tagbanwa },
+  { 1463, PT_SC, ucp_Tai_Le },
+  { 1470, PT_SC, ucp_Tai_Tham },
+  { 1479, PT_SC, ucp_Tai_Viet },
+  { 1488, PT_SC, ucp_Takri },
+  { 1494, PT_SC, ucp_Tamil },
+  { 1500, PT_SC, ucp_Tangsa },
+  { 1507, PT_SC, ucp_Tangut },
+  { 1514, PT_SC, ucp_Telugu },
+  { 1521, PT_SC, ucp_Thaana },
+  { 1528, PT_SC, ucp_Thai },
+  { 1533, PT_SC, ucp_Tibetan },
+  { 1541, PT_SC, ucp_Tifinagh },
+  { 1550, PT_SC, ucp_Tirhuta },
+  { 1558, PT_SC, ucp_Toto },
+  { 1563, PT_SC, ucp_Ugaritic },
+  { 1572, PT_SC, ucp_Unknown },
+  { 1580, PT_SC, ucp_Vai },
+  { 1584, PT_SC, ucp_Vithkuqi },
+  { 1593, PT_SC, ucp_Wancho },
+  { 1600, PT_SC, ucp_Warang_Citi },
+  { 1612, PT_ALNUM, 0 },
+  { 1616, PT_PXSPACE, 0 },
+  { 1620, PT_SPACE, 0 },
+  { 1624, PT_UCNC, 0 },
+  { 1628, PT_WORD, 0 },
+  { 1632, PT_SC, ucp_Yezidi },
+  { 1639, PT_SC, ucp_Yi },
+  { 1642, PT_GC, ucp_Z },
+  { 1644, PT_SC, ucp_Zanabazar_Square },
+  { 1661, PT_PC, ucp_Zl },
+  { 1664, PT_PC, ucp_Zp },
+  { 1667, PT_PC, ucp_Zs }
 };
 
 const size_t PRIV(utt_size) = sizeof(PRIV(utt)) / sizeof(ucp_type_table);

File diff suppressed because it is too large
+ 838 - 812
thirdparty/pcre2/src/pcre2_ucd.c


+ 7 - 1
thirdparty/pcre2/src/pcre2_ucp.h

@@ -291,7 +291,13 @@ enum {
   ucp_Chorasmian,
   ucp_Dives_Akuru,
   ucp_Khitan_Small_Script,
-  ucp_Yezidi
+  ucp_Yezidi,
+  /* New for Unicode 14.0.0 */
+  ucp_Cypro_Minoan,
+  ucp_Old_Uyghur,
+  ucp_Tangsa,
+  ucp_Toto,
+  ucp_Vithkuqi
 };
 
 #endif  /* PCRE2_UCP_H_IDEMPOTENT_GUARD */

+ 14 - 0
thirdparty/pcre2/src/sljit/sljitConfigInternal.h

@@ -158,6 +158,8 @@ extern "C" {
 #define SLJIT_CONFIG_MIPS_64 1
 #elif defined(__sparc__) || defined(__sparc)
 #define SLJIT_CONFIG_SPARC_32 1
+#elif defined(__s390x__)
+#define SLJIT_CONFIG_S390X 1
 #else
 /* Unsupported architecture */
 #define SLJIT_CONFIG_UNSUPPORTED 1
@@ -759,6 +761,18 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_sw sljit_exec_offset(void* ptr);
 #define SLJIT_NUMBER_OF_SCRATCH_FLOAT_REGISTERS \
 	(SLJIT_NUMBER_OF_FLOAT_REGISTERS - SLJIT_NUMBER_OF_SAVED_FLOAT_REGISTERS)
 
+/********************************/
+/* CPU status flags management. */
+/********************************/
+
+#if (defined SLJIT_CONFIG_ARM_32 && SLJIT_CONFIG_ARM_32) \
+	|| (defined SLJIT_CONFIG_ARM_64 && SLJIT_CONFIG_ARM_64) \
+	|| (defined SLJIT_CONFIG_MIPS && SLJIT_CONFIG_MIPS) \
+	|| (defined SLJIT_CONFIG_SPARC && SLJIT_CONFIG_SPARC) \
+	|| (defined SLJIT_CONFIG_S390X && SLJIT_CONFIG_S390X)
+#define SLJIT_HAS_STATUS_FLAGS_STATE 1
+#endif
+
 /*************************************/
 /* Debug and verbose related macros. */
 /*************************************/

+ 71 - 53
thirdparty/pcre2/src/sljit/sljitExecAllocator.c

@@ -79,6 +79,7 @@
 */
 
 #ifdef _WIN32
+#define SLJIT_UPDATE_WX_FLAGS(from, to, enable_exec)
 
 static SLJIT_INLINE void* alloc_chunk(sljit_uw size)
 {
@@ -91,96 +92,108 @@ static SLJIT_INLINE void free_chunk(void *chunk, sljit_uw size)
 	VirtualFree(chunk, 0, MEM_RELEASE);
 }
 
-#else
-
-#ifdef __APPLE__
-#ifdef MAP_ANON
-/* Configures TARGET_OS_OSX when appropriate */
-#include <TargetConditionals.h>
-
-#if TARGET_OS_OSX && defined(MAP_JIT)
-#include <sys/utsname.h>
-#endif /* TARGET_OS_OSX && MAP_JIT */
-
-#ifdef MAP_JIT
+#else /* POSIX */
 
+#if defined(__APPLE__) && defined(MAP_JIT)
 /*
    On macOS systems, returns MAP_JIT if it is defined _and_ we're running on a
-   version where it's OK to have more than one JIT block.
+   version where it's OK to have more than one JIT block or where MAP_JIT is
+   required.
    On non-macOS systems, returns MAP_JIT if it is defined.
 */
+#include <TargetConditionals.h>
+#if TARGET_OS_OSX
+#if defined SLJIT_CONFIG_X86 && SLJIT_CONFIG_X86
+#ifdef MAP_ANON
+#include <sys/utsname.h>
+#include <stdlib.h>
+
+#define SLJIT_MAP_JIT	(get_map_jit_flag())
+
 static SLJIT_INLINE int get_map_jit_flag()
 {
-#if TARGET_OS_OSX
-	sljit_sw page_size = get_page_alignment() + 1;
+	sljit_sw page_size;
 	void *ptr;
+	struct utsname name;
 	static int map_jit_flag = -1;
 
-	/*
-	  The following code is thread safe because multiple initialization
-	  sets map_jit_flag to the same value and the code has no side-effects.
-	  Changing the kernel version witout system restart is (very) unlikely.
-	*/
-	if (map_jit_flag == -1) {
-		struct utsname name;
-
+	if (map_jit_flag < 0) {
 		map_jit_flag = 0;
 		uname(&name);
 
-		/* Kernel version for 10.14.0 (Mojave) */
+		/* Kernel version for 10.14.0 (Mojave) or later */
 		if (atoi(name.release) >= 18) {
+			page_size = get_page_alignment() + 1;
 			/* Only use MAP_JIT if a hardened runtime is used */
+			ptr = mmap(NULL, page_size, PROT_WRITE | PROT_EXEC,
+					MAP_PRIVATE | MAP_ANON, -1, 0);
 
-			ptr = mmap(NULL, page_size, PROT_WRITE | PROT_EXEC, MAP_PRIVATE | MAP_ANON, -1, 0);
-
-			if (ptr == MAP_FAILED) {
-				map_jit_flag = MAP_JIT;
-			} else {
+			if (ptr != MAP_FAILED)
 				munmap(ptr, page_size);
-			}
+			else
+				map_jit_flag = MAP_JIT;
 		}
 	}
-
 	return map_jit_flag;
-#else /* !TARGET_OS_OSX */
-	return MAP_JIT;
-#endif /* TARGET_OS_OSX */
 }
-
-#endif /* MAP_JIT */
 #endif /* MAP_ANON */
-#endif /* __APPLE__ */
+#else /* !SLJIT_CONFIG_X86 */
+#if !(defined SLJIT_CONFIG_ARM && SLJIT_CONFIG_ARM)
+#error Unsupported architecture
+#endif /* SLJIT_CONFIG_ARM */
+#include <pthread.h>
+
+#define SLJIT_MAP_JIT	(MAP_JIT)
+#define SLJIT_UPDATE_WX_FLAGS(from, to, enable_exec) \
+                        apple_update_wx_flags(enable_exec)
+
+static SLJIT_INLINE void apple_update_wx_flags(sljit_s32 enable_exec)
+{
+	pthread_jit_write_protect_np(enable_exec);
+}
+#endif /* SLJIT_CONFIG_X86 */
+#else /* !TARGET_OS_OSX */
+#define SLJIT_MAP_JIT	(MAP_JIT)
+#endif /* TARGET_OS_OSX */
+#endif /* __APPLE__ && MAP_JIT */
+#ifndef SLJIT_UPDATE_WX_FLAGS
+#define SLJIT_UPDATE_WX_FLAGS(from, to, enable_exec)
+#endif /* !SLJIT_UPDATE_WX_FLAGS */
+#ifndef SLJIT_MAP_JIT
+#define SLJIT_MAP_JIT	(0)
+#endif /* !SLJIT_MAP_JIT */
 
 static SLJIT_INLINE void* alloc_chunk(sljit_uw size)
 {
 	void *retval;
-	const int prot = PROT_READ | PROT_WRITE | PROT_EXEC;
-
-#ifdef MAP_ANON
+	int prot = PROT_READ | PROT_WRITE | PROT_EXEC;
+	int flags = MAP_PRIVATE;
+	int fd = -1;
 
-	int flags = MAP_PRIVATE | MAP_ANON;
-
-#ifdef MAP_JIT
-	flags |= get_map_jit_flag();
+#ifdef PROT_MAX
+	prot |= PROT_MAX(prot);
 #endif
 
-	retval = mmap(NULL, size, prot, flags, -1, 0);
+#ifdef MAP_ANON
+	flags |= MAP_ANON | SLJIT_MAP_JIT;
 #else /* !MAP_ANON */
 	if (SLJIT_UNLIKELY((dev_zero < 0) && open_dev_zero()))
 		return NULL;
 
-	retval = mmap(NULL, size, prot, MAP_PRIVATE, dev_zero, 0);
+	fd = dev_zero;
 #endif /* MAP_ANON */
 
+	retval = mmap(NULL, size, prot, flags, fd, 0);
 	if (retval == MAP_FAILED)
-		retval = NULL;
-	else {
-		if (mprotect(retval, size, prot) < 0) {
-			munmap(retval, size);
-			retval = NULL;
-		}
+		return NULL;
+
+	if (mprotect(retval, size, PROT_READ | PROT_WRITE | PROT_EXEC) < 0) {
+		munmap(retval, size);
+		return NULL;
 	}
 
+	SLJIT_UPDATE_WX_FLAGS(retval, (uint8_t *)retval + size, 0);
+
 	return retval;
 }
 
@@ -189,7 +202,7 @@ static SLJIT_INLINE void free_chunk(void *chunk, sljit_uw size)
 	munmap(chunk, size);
 }
 
-#endif
+#endif /* windows */
 
 /* --------------------------------------------------------------------- */
 /*  Common functions                                                     */
@@ -261,6 +274,7 @@ SLJIT_API_FUNC_ATTRIBUTE void* sljit_malloc_exec(sljit_uw size)
 	while (free_block) {
 		if (free_block->size >= size) {
 			chunk_size = free_block->size;
+			SLJIT_UPDATE_WX_FLAGS(NULL, NULL, 0);
 			if (chunk_size > size + 64) {
 				/* We just cut a block from the end of the free block. */
 				chunk_size -= size;
@@ -326,6 +340,7 @@ SLJIT_API_FUNC_ATTRIBUTE void sljit_free_exec(void* ptr)
 	allocated_size -= header->size;
 
 	/* Connecting free blocks together if possible. */
+	SLJIT_UPDATE_WX_FLAGS(NULL, NULL, 0);
 
 	/* If header->prev_size == 0, free_block will equal to header.
 	   In this case, free_block->header.size will be > 0. */
@@ -358,6 +373,7 @@ SLJIT_API_FUNC_ATTRIBUTE void sljit_free_exec(void* ptr)
 		}
 	}
 
+	SLJIT_UPDATE_WX_FLAGS(NULL, NULL, 1);
 	SLJIT_ALLOCATOR_UNLOCK();
 }
 
@@ -367,6 +383,7 @@ SLJIT_API_FUNC_ATTRIBUTE void sljit_free_unused_memory_exec(void)
 	struct free_block* next_free_block;
 
 	SLJIT_ALLOCATOR_LOCK();
+	SLJIT_UPDATE_WX_FLAGS(NULL, NULL, 0);
 
 	free_block = free_blocks;
 	while (free_block) {
@@ -381,5 +398,6 @@ SLJIT_API_FUNC_ATTRIBUTE void sljit_free_unused_memory_exec(void)
 	}
 
 	SLJIT_ASSERT((total_size && free_blocks) || (!total_size && !free_blocks));
+	SLJIT_UPDATE_WX_FLAGS(NULL, NULL, 1);
 	SLJIT_ALLOCATOR_UNLOCK();
 }

+ 14 - 11
thirdparty/pcre2/src/sljit/sljitLir.c

@@ -532,13 +532,21 @@ SLJIT_API_FUNC_ATTRIBUTE void sljit_set_put_label(struct sljit_put_label *put_la
 		put_label->label = label;
 }
 
+#define SLJIT_CURRENT_FLAGS_ALL \
+	(SLJIT_CURRENT_FLAGS_I32_OP | SLJIT_CURRENT_FLAGS_ADD_SUB | SLJIT_CURRENT_FLAGS_COMPARE)
+
 SLJIT_API_FUNC_ATTRIBUTE void sljit_set_current_flags(struct sljit_compiler *compiler, sljit_s32 current_flags)
 {
 	SLJIT_UNUSED_ARG(compiler);
 	SLJIT_UNUSED_ARG(current_flags);
 
+#if (defined SLJIT_HAS_STATUS_FLAGS_STATE && SLJIT_HAS_STATUS_FLAGS_STATE)
+	compiler->status_flags_state = current_flags;
+#endif
+
 #if (defined SLJIT_ARGUMENT_CHECKS && SLJIT_ARGUMENT_CHECKS)
-	if ((current_flags & ~(VARIABLE_FLAG_MASK | SLJIT_I32_OP | SLJIT_SET_Z)) == 0) {
+	compiler->last_flags = 0;
+	if ((current_flags & ~(VARIABLE_FLAG_MASK | SLJIT_SET_Z | SLJIT_CURRENT_FLAGS_ALL)) == 0) {
 		compiler->last_flags = GET_FLAG_TYPE(current_flags) | (current_flags & (SLJIT_I32_OP | SLJIT_SET_Z));
 	}
 #endif
@@ -968,7 +976,7 @@ static const char* fop2_names[] = {
 };
 
 #define JUMP_POSTFIX(type) \
-	((type & 0xff) <= SLJIT_MUL_NOT_OVERFLOW ? ((type & SLJIT_I32_OP) ? "32" : "") \
+	((type & 0xff) <= SLJIT_NOT_OVERFLOW ? ((type & SLJIT_I32_OP) ? "32" : "") \
 	: ((type & 0xff) <= SLJIT_ORDERED_F64 ? ((type & SLJIT_F32_OP) ? ".f32" : ".f64") : ""))
 
 static char* jump_names[] = {
@@ -978,7 +986,6 @@ static char* jump_names[] = {
 	(char*)"sig_less", (char*)"sig_greater_equal",
 	(char*)"sig_greater", (char*)"sig_less_equal",
 	(char*)"overflow", (char*)"not_overflow",
-	(char*)"mul_overflow", (char*)"mul_not_overflow",
 	(char*)"carry", (char*)"",
 	(char*)"equal", (char*)"not_equal",
 	(char*)"less", (char*)"greater_equal",
@@ -1278,7 +1285,7 @@ static SLJIT_INLINE CHECK_RETURN_TYPE check_sljit_emit_op2(struct sljit_compiler
 	case SLJIT_MUL:
 		CHECK_ARGUMENT(!(op & SLJIT_SET_Z));
 		CHECK_ARGUMENT(!(op & VARIABLE_FLAG_MASK)
-			|| GET_FLAG_TYPE(op) == SLJIT_MUL_OVERFLOW);
+			|| GET_FLAG_TYPE(op) == SLJIT_OVERFLOW);
 		break;
 	case SLJIT_ADD:
 		CHECK_ARGUMENT(!(op & VARIABLE_FLAG_MASK)
@@ -1601,9 +1608,7 @@ static SLJIT_INLINE CHECK_RETURN_TYPE check_sljit_emit_jump(struct sljit_compile
 			CHECK_ARGUMENT(compiler->last_flags & SLJIT_SET_Z);
 		else
 			CHECK_ARGUMENT((type & 0xff) == (compiler->last_flags & 0xff)
-				|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW)
-				|| ((type & 0xff) == SLJIT_MUL_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_MUL_OVERFLOW));
-		CHECK_ARGUMENT((type & SLJIT_I32_OP) == (compiler->last_flags & SLJIT_I32_OP));
+				|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW));
 	}
 #endif
 #if (defined SLJIT_VERBOSE && SLJIT_VERBOSE)
@@ -1818,8 +1823,7 @@ static SLJIT_INLINE CHECK_RETURN_TYPE check_sljit_emit_op_flags(struct sljit_com
 		CHECK_ARGUMENT(compiler->last_flags & SLJIT_SET_Z);
 	else
 		CHECK_ARGUMENT((type & 0xff) == (compiler->last_flags & 0xff)
-			|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW)
-			|| ((type & 0xff) == SLJIT_MUL_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_MUL_OVERFLOW));
+			|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW));
 
 	FUNCTION_CHECK_DST(dst, dstw, 0);
 
@@ -1858,8 +1862,7 @@ static SLJIT_INLINE CHECK_RETURN_TYPE check_sljit_emit_cmov(struct sljit_compile
 		CHECK_ARGUMENT(compiler->last_flags & SLJIT_SET_Z);
 	else
 		CHECK_ARGUMENT((type & 0xff) == (compiler->last_flags & 0xff)
-			|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW)
-			|| ((type & 0xff) == SLJIT_MUL_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_MUL_OVERFLOW));
+			|| ((type & 0xff) == SLJIT_NOT_OVERFLOW && (compiler->last_flags & 0xff) == SLJIT_OVERFLOW));
 #endif
 #if (defined SLJIT_VERBOSE && SLJIT_VERBOSE)
 	if (SLJIT_UNLIKELY(!!compiler->verbose)) {

+ 37 - 39
thirdparty/pcre2/src/sljit/sljitLir.h

@@ -412,6 +412,10 @@ struct sljit_compiler {
 	/* Executable size for statistical purposes. */
 	sljit_uw executable_size;
 
+#if (defined SLJIT_HAS_STATUS_FLAGS_STATE && SLJIT_HAS_STATUS_FLAGS_STATE)
+	sljit_s32 status_flags_state;
+#endif
+
 #if (defined SLJIT_CONFIG_X86_32 && SLJIT_CONFIG_X86_32)
 	sljit_s32 args;
 	sljit_s32 locals_offset;
@@ -460,7 +464,7 @@ struct sljit_compiler {
 
 #if (defined SLJIT_CONFIG_S390X && SLJIT_CONFIG_S390X)
 	/* Need to allocate register save area to make calls. */
-	sljit_s32 have_save_area;
+	sljit_s32 mode;
 #endif
 
 #if (defined SLJIT_VERBOSE && SLJIT_VERBOSE)
@@ -996,7 +1000,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op1(struct sljit_compiler *compile
 #define SLJIT_SUBC			(SLJIT_OP2_BASE + 3)
 #define SLJIT_SUBC32			(SLJIT_SUBC | SLJIT_I32_OP)
 /* Note: integer mul
-   Flags: MUL_OVERFLOW */
+   Flags: OVERFLOW */
 #define SLJIT_MUL			(SLJIT_OP2_BASE + 4)
 #define SLJIT_MUL32			(SLJIT_MUL | SLJIT_I32_OP)
 /* Flags: Z */
@@ -1141,89 +1145,69 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_label* sljit_emit_label(struct sljit_compi
 
 /* Integer comparison types. */
 #define SLJIT_EQUAL			0
-#define SLJIT_EQUAL32			(SLJIT_EQUAL | SLJIT_I32_OP)
-#define SLJIT_ZERO			0
-#define SLJIT_ZERO32			(SLJIT_ZERO | SLJIT_I32_OP)
+#define SLJIT_ZERO			SLJIT_EQUAL
 #define SLJIT_NOT_EQUAL			1
-#define SLJIT_NOT_EQUAL32		(SLJIT_NOT_EQUAL | SLJIT_I32_OP)
-#define SLJIT_NOT_ZERO			1
-#define SLJIT_NOT_ZERO32		(SLJIT_NOT_ZERO | SLJIT_I32_OP)
+#define SLJIT_NOT_ZERO			SLJIT_NOT_EQUAL
 
 #define SLJIT_LESS			2
-#define SLJIT_LESS32			(SLJIT_LESS | SLJIT_I32_OP)
 #define SLJIT_SET_LESS			SLJIT_SET(SLJIT_LESS)
 #define SLJIT_GREATER_EQUAL		3
-#define SLJIT_GREATER_EQUAL32		(SLJIT_GREATER_EQUAL | SLJIT_I32_OP)
 #define SLJIT_SET_GREATER_EQUAL		SLJIT_SET(SLJIT_GREATER_EQUAL)
 #define SLJIT_GREATER			4
-#define SLJIT_GREATER32			(SLJIT_GREATER | SLJIT_I32_OP)
 #define SLJIT_SET_GREATER		SLJIT_SET(SLJIT_GREATER)
 #define SLJIT_LESS_EQUAL		5
-#define SLJIT_LESS_EQUAL32		(SLJIT_LESS_EQUAL | SLJIT_I32_OP)
 #define SLJIT_SET_LESS_EQUAL		SLJIT_SET(SLJIT_LESS_EQUAL)
 #define SLJIT_SIG_LESS			6
-#define SLJIT_SIG_LESS32		(SLJIT_SIG_LESS | SLJIT_I32_OP)
 #define SLJIT_SET_SIG_LESS		SLJIT_SET(SLJIT_SIG_LESS)
 #define SLJIT_SIG_GREATER_EQUAL		7
-#define SLJIT_SIG_GREATER_EQUAL32	(SLJIT_SIG_GREATER_EQUAL | SLJIT_I32_OP)
 #define SLJIT_SET_SIG_GREATER_EQUAL	SLJIT_SET(SLJIT_SIG_GREATER_EQUAL)
 #define SLJIT_SIG_GREATER		8
-#define SLJIT_SIG_GREATER32		(SLJIT_SIG_GREATER | SLJIT_I32_OP)
 #define SLJIT_SET_SIG_GREATER		SLJIT_SET(SLJIT_SIG_GREATER)
 #define SLJIT_SIG_LESS_EQUAL		9
-#define SLJIT_SIG_LESS_EQUAL32		(SLJIT_SIG_LESS_EQUAL | SLJIT_I32_OP)
 #define SLJIT_SET_SIG_LESS_EQUAL	SLJIT_SET(SLJIT_SIG_LESS_EQUAL)
 
 #define SLJIT_OVERFLOW			10
-#define SLJIT_OVERFLOW32		(SLJIT_OVERFLOW | SLJIT_I32_OP)
 #define SLJIT_SET_OVERFLOW		SLJIT_SET(SLJIT_OVERFLOW)
 #define SLJIT_NOT_OVERFLOW		11
-#define SLJIT_NOT_OVERFLOW32		(SLJIT_NOT_OVERFLOW | SLJIT_I32_OP)
-
-#define SLJIT_MUL_OVERFLOW		12
-#define SLJIT_MUL_OVERFLOW32		(SLJIT_MUL_OVERFLOW | SLJIT_I32_OP)
-#define SLJIT_SET_MUL_OVERFLOW		SLJIT_SET(SLJIT_MUL_OVERFLOW)
-#define SLJIT_MUL_NOT_OVERFLOW		13
-#define SLJIT_MUL_NOT_OVERFLOW32	(SLJIT_MUL_NOT_OVERFLOW | SLJIT_I32_OP)
 
 /* There is no SLJIT_CARRY or SLJIT_NOT_CARRY. */
-#define SLJIT_SET_CARRY			SLJIT_SET(14)
+#define SLJIT_SET_CARRY			SLJIT_SET(12)
 
 /* Floating point comparison types. */
-#define SLJIT_EQUAL_F64			16
+#define SLJIT_EQUAL_F64			14
 #define SLJIT_EQUAL_F32			(SLJIT_EQUAL_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_EQUAL_F		SLJIT_SET(SLJIT_EQUAL_F64)
-#define SLJIT_NOT_EQUAL_F64		17
+#define SLJIT_NOT_EQUAL_F64		15
 #define SLJIT_NOT_EQUAL_F32		(SLJIT_NOT_EQUAL_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_NOT_EQUAL_F		SLJIT_SET(SLJIT_NOT_EQUAL_F64)
-#define SLJIT_LESS_F64			18
+#define SLJIT_LESS_F64			16
 #define SLJIT_LESS_F32			(SLJIT_LESS_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_LESS_F		SLJIT_SET(SLJIT_LESS_F64)
-#define SLJIT_GREATER_EQUAL_F64		19
+#define SLJIT_GREATER_EQUAL_F64		17
 #define SLJIT_GREATER_EQUAL_F32		(SLJIT_GREATER_EQUAL_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_GREATER_EQUAL_F	SLJIT_SET(SLJIT_GREATER_EQUAL_F64)
-#define SLJIT_GREATER_F64		20
+#define SLJIT_GREATER_F64		18
 #define SLJIT_GREATER_F32		(SLJIT_GREATER_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_GREATER_F		SLJIT_SET(SLJIT_GREATER_F64)
-#define SLJIT_LESS_EQUAL_F64		21
+#define SLJIT_LESS_EQUAL_F64		19
 #define SLJIT_LESS_EQUAL_F32		(SLJIT_LESS_EQUAL_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_LESS_EQUAL_F		SLJIT_SET(SLJIT_LESS_EQUAL_F64)
-#define SLJIT_UNORDERED_F64		22
+#define SLJIT_UNORDERED_F64		20
 #define SLJIT_UNORDERED_F32		(SLJIT_UNORDERED_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_UNORDERED_F		SLJIT_SET(SLJIT_UNORDERED_F64)
-#define SLJIT_ORDERED_F64		23
+#define SLJIT_ORDERED_F64		21
 #define SLJIT_ORDERED_F32		(SLJIT_ORDERED_F64 | SLJIT_F32_OP)
 #define SLJIT_SET_ORDERED_F		SLJIT_SET(SLJIT_ORDERED_F64)
 
 /* Unconditional jump types. */
-#define SLJIT_JUMP			24
+#define SLJIT_JUMP			22
 	/* Fast calling method. See sljit_emit_fast_enter / SLJIT_FAST_RETURN. */
-#define SLJIT_FAST_CALL			25
+#define SLJIT_FAST_CALL			23
 	/* Called function must be declared with the SLJIT_FUNC attribute. */
-#define SLJIT_CALL			26
+#define SLJIT_CALL			24
 	/* Called function must be declared with cdecl attribute.
 	   This is the default attribute for C functions. */
-#define SLJIT_CALL_CDECL		27
+#define SLJIT_CALL_CDECL		25
 
 /* The target can be changed during runtime (see: sljit_set_jump_addr). */
 #define SLJIT_REWRITABLE_JUMP		0x1000
@@ -1534,8 +1518,22 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_get_float_register_index(sljit_s32 reg)
 SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_custom(struct sljit_compiler *compiler,
 	void *instruction, sljit_s32 size);
 
-/* Define the currently available CPU status flags. It is usually used after an
-   sljit_emit_op_custom call to define which flags are set. */
+/* Flags were set by a 32 bit operation. */
+#define SLJIT_CURRENT_FLAGS_I32_OP		SLJIT_I32_OP
+
+/* Flags were set by an ADD, ADDC, SUB, SUBC, or NEG operation. */
+#define SLJIT_CURRENT_FLAGS_ADD_SUB		0x01
+
+/* Flags were set by a SUB with unused destination.
+   Must be combined with SLJIT_CURRENT_FLAGS_ADD_SUB. */
+#define SLJIT_CURRENT_FLAGS_COMPARE		0x02
+
+/* Define the currently available CPU status flags. It is usually used after
+   an sljit_emit_label or sljit_emit_op_custom operations to define which CPU
+   status flags are available.
+
+   The current_flags must be a valid combination of SLJIT_SET_* and
+   SLJIT_CURRENT_FLAGS_* constants. */
 
 SLJIT_API_FUNC_ATTRIBUTE void sljit_set_current_flags(struct sljit_compiler *compiler,
 	sljit_s32 current_flags);

+ 16 - 7
thirdparty/pcre2/src/sljit/sljitNativeARM_32.c

@@ -1197,6 +1197,8 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 
 	case SLJIT_ADD:
 		SLJIT_ASSERT(!(flags & INV_IMM));
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
+
 		if ((flags & (UNUSED_RETURN | SET_FLAGS)) == (UNUSED_RETURN | SET_FLAGS) && !(flags & ARGS_SWAPPED))
 			return push_inst(compiler, CMN | SET_FLAGS | RN(src1) | ((src2 & SRC2_IMM) ? src2 : RM(src2)));
 		return push_inst(compiler, ADD | (flags & SET_FLAGS) | RD(dst) | RN(src1) | ((src2 & SRC2_IMM) ? src2 : RM(src2)));
@@ -1207,6 +1209,8 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 
 	case SLJIT_SUB:
 		SLJIT_ASSERT(!(flags & INV_IMM));
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
+
 		if ((flags & (UNUSED_RETURN | SET_FLAGS)) == (UNUSED_RETURN | SET_FLAGS) && !(flags & ARGS_SWAPPED))
 			return push_inst(compiler, CMP | SET_FLAGS | RN(src1) | ((src2 & SRC2_IMM) ? src2 : RM(src2)));
 		return push_inst(compiler, (!(flags & ARGS_SWAPPED) ? SUB : RSB) | (flags & SET_FLAGS)
@@ -1220,6 +1224,7 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 	case SLJIT_MUL:
 		SLJIT_ASSERT(!(flags & INV_IMM));
 		SLJIT_ASSERT(!(src2 & SRC2_IMM));
+		compiler->status_flags_state = 0;
 
 		if (!HAS_FLAGS(op))
 			return push_inst(compiler, MUL | (reg_map[dst] << 16) | (reg_map[src2] << 8) | reg_map[src1]);
@@ -2153,16 +2158,14 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_fast_enter(struct sljit_compiler *
 /*  Conditional instructions                                             */
 /* --------------------------------------------------------------------- */
 
-static sljit_uw get_cc(sljit_s32 type)
+static sljit_uw get_cc(struct sljit_compiler *compiler, sljit_s32 type)
 {
 	switch (type) {
 	case SLJIT_EQUAL:
-	case SLJIT_MUL_NOT_OVERFLOW:
 	case SLJIT_EQUAL_F64:
 		return 0x00000000;
 
 	case SLJIT_NOT_EQUAL:
-	case SLJIT_MUL_OVERFLOW:
 	case SLJIT_NOT_EQUAL_F64:
 		return 0x10000000;
 
@@ -2195,10 +2198,16 @@ static sljit_uw get_cc(sljit_s32 type)
 		return 0xd0000000;
 
 	case SLJIT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x10000000;
+
 	case SLJIT_UNORDERED_F64:
 		return 0x60000000;
 
 	case SLJIT_NOT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x00000000;
+
 	case SLJIT_ORDERED_F64:
 		return 0x70000000;
 
@@ -2242,7 +2251,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 	if (type >= SLJIT_FAST_CALL)
 		PTR_FAIL_IF(prepare_blx(compiler));
 	PTR_FAIL_IF(push_inst_with_unique_literal(compiler, ((EMIT_DATA_TRANSFER(WORD_SIZE | LOAD_DATA, 1,
-		type <= SLJIT_JUMP ? TMP_PC : TMP_REG1, TMP_PC, 0)) & ~COND_MASK) | get_cc(type), 0));
+		type <= SLJIT_JUMP ? TMP_PC : TMP_REG1, TMP_PC, 0)) & ~COND_MASK) | get_cc(compiler, type), 0));
 
 	if (jump->flags & SLJIT_REWRITABLE_JUMP) {
 		jump->addr = compiler->size;
@@ -2260,7 +2269,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 	if (type >= SLJIT_FAST_CALL)
 		jump->flags |= IS_BL;
 	PTR_FAIL_IF(emit_imm(compiler, TMP_REG1, 0));
-	PTR_FAIL_IF(push_inst(compiler, (((type <= SLJIT_JUMP ? BX : BLX) | RM(TMP_REG1)) & ~COND_MASK) | get_cc(type)));
+	PTR_FAIL_IF(push_inst(compiler, (((type <= SLJIT_JUMP ? BX : BLX) | RM(TMP_REG1)) & ~COND_MASK) | get_cc(compiler, type)));
 	jump->addr = compiler->size;
 #endif
 	return jump;
@@ -2589,7 +2598,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 	ADJUST_LOCAL_OFFSET(dst, dstw);
 
 	op = GET_OPCODE(op);
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 	dst_reg = FAST_IS_REG(dst) ? dst : TMP_REG1;
 
 	if (op < SLJIT_ADD) {
@@ -2629,7 +2638,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_cmov(struct sljit_compiler *compil
 
 	dst_reg &= ~SLJIT_I32_OP;
 
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 
 	if (SLJIT_UNLIKELY(src & SLJIT_IMM)) {
 		tmp = get_imm(srcw);

+ 15 - 6
thirdparty/pcre2/src/sljit/sljitNativeARM_64.c

@@ -644,6 +644,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 			imm = -imm;
 			/* Fall through. */
 		case SLJIT_ADD:
+			compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 			if (imm == 0) {
 				CHECK_FLAGS(1 << 29);
 				return push_inst(compiler, ((op == SLJIT_ADD ? ADDI : SUBI) ^ inv_bits) | RD(dst) | RN(reg));
@@ -781,6 +782,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 		break; /* Set flags. */
 	case SLJIT_NEG:
 		SLJIT_ASSERT(arg1 == TMP_REG1);
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		if (flags & SET_FLAGS)
 			inv_bits |= 1 << 29;
 		return push_inst(compiler, (SUB ^ inv_bits) | RD(dst) | RN(TMP_ZERO) | RM(arg2));
@@ -789,17 +791,20 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 		return push_inst(compiler, (CLZ ^ inv_bits) | RD(dst) | RN(arg2));
 	case SLJIT_ADD:
 		CHECK_FLAGS(1 << 29);
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return push_inst(compiler, (ADD ^ inv_bits) | RD(dst) | RN(arg1) | RM(arg2));
 	case SLJIT_ADDC:
 		CHECK_FLAGS(1 << 29);
 		return push_inst(compiler, (ADC ^ inv_bits) | RD(dst) | RN(arg1) | RM(arg2));
 	case SLJIT_SUB:
 		CHECK_FLAGS(1 << 29);
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return push_inst(compiler, (SUB ^ inv_bits) | RD(dst) | RN(arg1) | RM(arg2));
 	case SLJIT_SUBC:
 		CHECK_FLAGS(1 << 29);
 		return push_inst(compiler, (SBC ^ inv_bits) | RD(dst) | RN(arg1) | RM(arg2));
 	case SLJIT_MUL:
+		compiler->status_flags_state = 0;
 		if (!(flags & SET_FLAGS))
 			return push_inst(compiler, (MADD ^ inv_bits) | RD(dst) | RN(arg1) | RM(arg2) | RT2(TMP_ZERO));
 		if (flags & INT_OP) {
@@ -1600,16 +1605,14 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_fast_enter(struct sljit_compiler *
 /*  Conditional instructions                                             */
 /* --------------------------------------------------------------------- */
 
-static sljit_uw get_cc(sljit_s32 type)
+static sljit_uw get_cc(struct sljit_compiler *compiler, sljit_s32 type)
 {
 	switch (type) {
 	case SLJIT_EQUAL:
-	case SLJIT_MUL_NOT_OVERFLOW:
 	case SLJIT_EQUAL_F64:
 		return 0x1;
 
 	case SLJIT_NOT_EQUAL:
-	case SLJIT_MUL_OVERFLOW:
 	case SLJIT_NOT_EQUAL_F64:
 		return 0x0;
 
@@ -1642,10 +1645,16 @@ static sljit_uw get_cc(sljit_s32 type)
 		return 0xc;
 
 	case SLJIT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x0;
+
 	case SLJIT_UNORDERED_F64:
 		return 0x7;
 
 	case SLJIT_NOT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x1;
+
 	case SLJIT_ORDERED_F64:
 		return 0x6;
 
@@ -1685,7 +1694,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 
 	if (type < SLJIT_JUMP) {
 		jump->flags |= IS_COND;
-		PTR_FAIL_IF(push_inst(compiler, B_CC | (6 << 5) | get_cc(type)));
+		PTR_FAIL_IF(push_inst(compiler, B_CC | (6 << 5) | get_cc(compiler, type)));
 	}
 	else if (type >= SLJIT_FAST_CALL)
 		jump->flags |= IS_BL;
@@ -1799,7 +1808,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 	CHECK(check_sljit_emit_op_flags(compiler, op, dst, dstw, type));
 	ADJUST_LOCAL_OFFSET(dst, dstw);
 
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 	dst_r = FAST_IS_REG(dst) ? dst : TMP_REG1;
 
 	if (GET_OPCODE(op) < SLJIT_ADD) {
@@ -1854,7 +1863,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_cmov(struct sljit_compiler *compil
 		srcw = 0;
 	}
 
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 	dst_reg &= ~SLJIT_I32_OP;
 
 	return push_inst(compiler, (CSEL ^ inv_bits) | (cc << 12) | RD(dst_reg) | RN(dst_reg) | RM(src));

+ 15 - 6
thirdparty/pcre2/src/sljit/sljitNativeARM_T2_32.c

@@ -610,6 +610,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 			   Although some clever things could be done here, "NOT IMM" does not worth the efforts. */
 			break;
 		case SLJIT_ADD:
+			compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 			nimm = -(sljit_sw)imm;
 			if (IS_2_LO_REGS(reg, dst)) {
 				if (imm <= 0x7)
@@ -643,6 +644,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 			break;
 		case SLJIT_SUB:
 			/* SUB operation can be replaced by ADD because of the negative carry flag. */
+			compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 			if (flags & ARG1_IMM) {
 				if (imm == 0 && IS_2_LO_REGS(reg, dst))
 					return push_inst16(compiler, RSBSI | RD3(dst) | RN3(reg));
@@ -801,6 +803,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 		FAIL_IF(push_inst32(compiler, CLZ | RN4(arg2) | RD4(dst) | RM4(arg2)));
 		return SLJIT_SUCCESS;
 	case SLJIT_ADD:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		if (IS_3_LO_REGS(dst, arg1, arg2))
 			return push_inst16(compiler, ADDS | RD3(dst) | RN3(arg1) | RM3(arg2));
 		if (dst == arg1 && !(flags & SET_FLAGS))
@@ -811,6 +814,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 			return push_inst16(compiler, ADCS | RD3(dst) | RN3(arg2));
 		return push_inst32(compiler, ADC_W | (flags & SET_FLAGS) | RD4(dst) | RN4(arg1) | RM4(arg2));
 	case SLJIT_SUB:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		if (flags & UNUSED_RETURN) {
 			if (IS_2_LO_REGS(arg1, arg2))
 				return push_inst16(compiler, CMP | RD3(arg1) | RN3(arg2));
@@ -824,6 +828,7 @@ static sljit_s32 emit_op_imm(struct sljit_compiler *compiler, sljit_s32 flags, s
 			return push_inst16(compiler, SBCS | RD3(dst) | RN3(arg2));
 		return push_inst32(compiler, SBC_W | (flags & SET_FLAGS) | RD4(dst) | RN4(arg1) | RM4(arg2));
 	case SLJIT_MUL:
+		compiler->status_flags_state = 0;
 		if (!(flags & SET_FLAGS))
 			return push_inst32(compiler, MUL | RD4(dst) | RN4(arg1) | RM4(arg2));
 		SLJIT_ASSERT(dst != TMP_REG2);
@@ -1760,16 +1765,14 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_fast_enter(struct sljit_compiler *
 /*  Conditional instructions                                             */
 /* --------------------------------------------------------------------- */
 
-static sljit_uw get_cc(sljit_s32 type)
+static sljit_uw get_cc(struct sljit_compiler *compiler, sljit_s32 type)
 {
 	switch (type) {
 	case SLJIT_EQUAL:
-	case SLJIT_MUL_NOT_OVERFLOW:
 	case SLJIT_EQUAL_F64:
 		return 0x0;
 
 	case SLJIT_NOT_EQUAL:
-	case SLJIT_MUL_OVERFLOW:
 	case SLJIT_NOT_EQUAL_F64:
 		return 0x1;
 
@@ -1802,10 +1805,16 @@ static sljit_uw get_cc(sljit_s32 type)
 		return 0xd;
 
 	case SLJIT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x1;
+
 	case SLJIT_UNORDERED_F64:
 		return 0x6;
 
 	case SLJIT_NOT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return 0x0;
+
 	case SLJIT_ORDERED_F64:
 		return 0x7;
 
@@ -1847,7 +1856,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 	PTR_FAIL_IF(emit_imm32_const(compiler, TMP_REG1, 0));
 	if (type < SLJIT_JUMP) {
 		jump->flags |= IS_COND;
-		cc = get_cc(type);
+		cc = get_cc(compiler, type);
 		jump->flags |= cc << 8;
 		PTR_FAIL_IF(push_inst16(compiler, IT | (cc << 4) | 0x8));
 	}
@@ -2177,7 +2186,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 	ADJUST_LOCAL_OFFSET(dst, dstw);
 
 	op = GET_OPCODE(op);
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 	dst_r = FAST_IS_REG(dst) ? dst : TMP_REG1;
 
 	if (op < SLJIT_ADD) {
@@ -2229,7 +2238,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_cmov(struct sljit_compiler *compil
 
 	dst_reg &= ~SLJIT_I32_OP;
 
-	cc = get_cc(type & 0xff);
+	cc = get_cc(compiler, type & 0xff);
 
 	if (!(src & SLJIT_IMM)) {
 		FAIL_IF(push_inst16(compiler, IT | (cc << 4) | 0x8));

+ 1 - 1
thirdparty/pcre2/src/sljit/sljitNativeMIPS_32.c

@@ -367,7 +367,7 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 	case SLJIT_MUL:
 		SLJIT_ASSERT(!(flags & SRC2_IMM));
 
-		if (GET_FLAG_TYPE(op) != SLJIT_MUL_OVERFLOW) {
+		if (GET_FLAG_TYPE(op) != SLJIT_OVERFLOW) {
 #if (defined SLJIT_MIPS_REV && SLJIT_MIPS_REV >= 1)
 			return push_inst(compiler, MUL | S(src1) | T(src2) | D(dst), DR(dst));
 #else /* SLJIT_MIPS_REV < 1 */

+ 1 - 1
thirdparty/pcre2/src/sljit/sljitNativeMIPS_64.c

@@ -458,7 +458,7 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 	case SLJIT_MUL:
 		SLJIT_ASSERT(!(flags & SRC2_IMM));
 
-		if (GET_FLAG_TYPE(op) != SLJIT_MUL_OVERFLOW) {
+		if (GET_FLAG_TYPE(op) != SLJIT_OVERFLOW) {
 #if (defined SLJIT_MIPS_REV && SLJIT_MIPS_REV >= 6)
 			return push_inst(compiler, SELECT_OP(DMUL, MUL) | S(src1) | T(src2) | D(dst), DR(dst));
 #elif (defined SLJIT_MIPS_REV && SLJIT_MIPS_REV >= 1)

+ 10 - 6
thirdparty/pcre2/src/sljit/sljitNativeMIPS_common.c

@@ -1377,6 +1377,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op1(struct sljit_compiler *compile
 		return emit_op(compiler, op, flags, dst, dstw, TMP_REG1, 0, src, srcw);
 
 	case SLJIT_NEG:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return emit_op(compiler, SLJIT_SUB | GET_ALL_FLAGS(op), flags | IMM_OP, dst, dstw, SLJIT_IMM, 0, src, srcw);
 
 	case SLJIT_CLZ:
@@ -1424,13 +1425,16 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 	switch (GET_OPCODE(op)) {
 	case SLJIT_ADD:
 	case SLJIT_ADDC:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return emit_op(compiler, op, flags | CUMULATIVE_OP | IMM_OP, dst, dstw, src1, src1w, src2, src2w);
 
 	case SLJIT_SUB:
 	case SLJIT_SUBC:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return emit_op(compiler, op, flags | IMM_OP, dst, dstw, src1, src1w, src2, src2w);
 
 	case SLJIT_MUL:
+		compiler->status_flags_state = 0;
 		return emit_op(compiler, op, flags | CUMULATIVE_OP, dst, dstw, src1, src1w, src2, src2w);
 
 	case SLJIT_AND:
@@ -1860,7 +1864,6 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 	case SLJIT_SIG_LESS:
 	case SLJIT_SIG_GREATER:
 	case SLJIT_OVERFLOW:
-	case SLJIT_MUL_OVERFLOW:
 		BR_Z(OTHER_FLAG);
 		break;
 	case SLJIT_GREATER_EQUAL:
@@ -1868,7 +1871,6 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 	case SLJIT_SIG_GREATER_EQUAL:
 	case SLJIT_SIG_LESS_EQUAL:
 	case SLJIT_NOT_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
 		BR_NZ(OTHER_FLAG);
 		break;
 	case SLJIT_NOT_EQUAL_F64:
@@ -2127,8 +2129,12 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 		FAIL_IF(push_inst(compiler, SLTIU | SA(EQUAL_FLAG) | TA(dst_ar) | IMM(1), dst_ar));
 		src_ar = dst_ar;
 		break;
-	case SLJIT_MUL_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
+	case SLJIT_OVERFLOW:
+	case SLJIT_NOT_OVERFLOW:
+		if (compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB) {
+			src_ar = OTHER_FLAG;
+			break;
+		}
 		FAIL_IF(push_inst(compiler, SLTIU | SA(OTHER_FLAG) | TA(dst_ar) | IMM(1), dst_ar));
 		src_ar = dst_ar;
 		type ^= 0x1; /* Flip type bit for the XORI below. */
@@ -2219,7 +2225,6 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_cmov(struct sljit_compiler *compil
 	case SLJIT_SIG_LESS:
 	case SLJIT_SIG_GREATER:
 	case SLJIT_OVERFLOW:
-	case SLJIT_MUL_OVERFLOW:
 		ins = MOVN | TA(OTHER_FLAG);
 		break;
 	case SLJIT_GREATER_EQUAL:
@@ -2227,7 +2232,6 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_cmov(struct sljit_compiler *compil
 	case SLJIT_SIG_GREATER_EQUAL:
 	case SLJIT_SIG_LESS_EQUAL:
 	case SLJIT_NOT_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
 		ins = MOVZ | TA(OTHER_FLAG);
 		break;
 	case SLJIT_EQUAL_F64:

+ 16 - 10
thirdparty/pcre2/src/sljit/sljitNativePPC_32.c

@@ -119,9 +119,10 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 			SLJIT_ASSERT(src2 == TMP_REG2);
 			return push_inst(compiler, ADDIC | D(dst) | A(src1) | compiler->imm);
 		}
+		SLJIT_ASSERT(!(flags & ALT_FORM4));
 		if (!(flags & ALT_SET_FLAGS))
 			return push_inst(compiler, ADD | D(dst) | A(src1) | B(src2));
-		if (flags & ALT_FORM4)
+		if (flags & ALT_FORM5)
 			return push_inst(compiler, ADDC | RC(ALT_SET_FLAGS) | D(dst) | A(src1) | B(src2));
 		return push_inst(compiler, ADD | RC(flags) | D(dst) | A(src1) | B(src2));
 
@@ -143,24 +144,29 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 		}
 
 		if (flags & ALT_FORM2) {
+			if (flags & ALT_FORM3) {
+				FAIL_IF(push_inst(compiler, CMPI | CRD(0) | A(src1) | compiler->imm));
+				if (!(flags & ALT_FORM4))
+					return SLJIT_SUCCESS;
+				return push_inst(compiler, ADDI | D(dst) | A(src1) | (-compiler->imm & 0xffff));
+			}
+			FAIL_IF(push_inst(compiler, CMP | CRD(0) | A(src1) | B(src2)));
+			if (!(flags & ALT_FORM4))
+				return SLJIT_SUCCESS;
+			return push_inst(compiler, SUBF | D(dst) | A(src2) | B(src1));
+		}
+
+		if (flags & ALT_FORM3) {
 			/* Setting XER SO is not enough, CR SO is also needed. */
 			return push_inst(compiler, SUBF | OE(ALT_SET_FLAGS) | RC(ALT_SET_FLAGS) | D(dst) | A(src2) | B(src1));
 		}
 
-		if (flags & ALT_FORM3) {
+		if (flags & ALT_FORM4) {
 			/* Flags does not set: BIN_IMM_EXTS unnecessary. */
 			SLJIT_ASSERT(src2 == TMP_REG2);
 			return push_inst(compiler, SUBFIC | D(dst) | A(src1) | compiler->imm);
 		}
 
-		if (flags & ALT_FORM4) {
-			if (flags & ALT_FORM5) {
-				SLJIT_ASSERT(src2 == TMP_REG2);
-				return push_inst(compiler, CMPI | CRD(0) | A(src1) | compiler->imm);
-			}
-			return push_inst(compiler, CMP | CRD(0) | A(src1) | B(src2));
-		}
-
 		if (!(flags & ALT_SET_FLAGS))
 			return push_inst(compiler, SUBF | D(dst) | A(src2) | B(src1));
 		if (flags & ALT_FORM5)

+ 22 - 10
thirdparty/pcre2/src/sljit/sljitNativePPC_64.c

@@ -252,10 +252,17 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 			BIN_IMM_EXTS();
 			return push_inst(compiler, ADDIC | D(dst) | A(src1) | compiler->imm);
 		}
+		if (flags & ALT_FORM4) {
+			if (flags & ALT_FORM5)
+				FAIL_IF(push_inst(compiler, ADDI | D(dst) | A(src1) | compiler->imm));
+			else
+				FAIL_IF(push_inst(compiler, ADD | D(dst) | A(src1) | B(src2)));
+			return push_inst(compiler, CMPI | A(dst) | 0);
+		}
 		if (!(flags & ALT_SET_FLAGS))
 			return push_inst(compiler, ADD | D(dst) | A(src1) | B(src2));
 		BIN_EXTS();
-		if (flags & ALT_FORM4)
+		if (flags & ALT_FORM5)
 			return push_inst(compiler, ADDC | RC(ALT_SET_FLAGS) | D(dst) | A(src1) | B(src2));
 		return push_inst(compiler, ADD | RC(flags) | D(dst) | A(src1) | B(src2));
 
@@ -278,6 +285,19 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 		}
 
 		if (flags & ALT_FORM2) {
+			if (flags & ALT_FORM3) {
+				FAIL_IF(push_inst(compiler, CMPI | CRD(0 | ((flags & ALT_SIGN_EXT) ? 0 : 1)) | A(src1) | compiler->imm));
+				if (!(flags & ALT_FORM4))
+					return SLJIT_SUCCESS;
+				return push_inst(compiler, ADDI | D(dst) | A(src1) | (-compiler->imm & 0xffff));
+			}
+			FAIL_IF(push_inst(compiler, CMP | CRD(0 | ((flags & ALT_SIGN_EXT) ? 0 : 1)) | A(src1) | B(src2)));
+			if (!(flags & ALT_FORM4))
+				return SLJIT_SUCCESS;
+			return push_inst(compiler, SUBF | D(dst) | A(src2) | B(src1));
+		}
+
+		if (flags & ALT_FORM3) {
 			if (flags & ALT_SIGN_EXT) {
 				FAIL_IF(push_inst(compiler, RLDI(TMP_REG1, src1, 32, 31, 1)));
 				src1 = TMP_REG1;
@@ -291,20 +311,12 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 			return SLJIT_SUCCESS;
 		}
 
-		if (flags & ALT_FORM3) {
+		if (flags & ALT_FORM4) {
 			/* Flags does not set: BIN_IMM_EXTS unnecessary. */
 			SLJIT_ASSERT(src2 == TMP_REG2);
 			return push_inst(compiler, SUBFIC | D(dst) | A(src1) | compiler->imm);
 		}
 
-		if (flags & ALT_FORM4) {
-			if (flags & ALT_FORM5) {
-				SLJIT_ASSERT(src2 == TMP_REG2);
-				return push_inst(compiler, CMPI | CRD(0 | ((flags & ALT_SIGN_EXT) ? 0 : 1)) | A(src1) | compiler->imm);
-			}
-			return push_inst(compiler, CMP | CRD(0 | ((flags & ALT_SIGN_EXT) ? 0 : 1)) | A(src1) | B(src2));
-		}
-
 		if (!(flags & ALT_SET_FLAGS))
 			return push_inst(compiler, SUBF | D(dst) | A(src2) | B(src1));
 		BIN_EXTS();

+ 66 - 27
thirdparty/pcre2/src/sljit/sljitNativePPC_common.c

@@ -1324,6 +1324,25 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op1(struct sljit_compiler *compile
 	((src) & SLJIT_IMM)
 #endif
 
+#if (defined SLJIT_CONFIG_PPC_64 && SLJIT_CONFIG_PPC_64)
+#define TEST_ADD_FORM1(op) \
+	(GET_FLAG_TYPE(op) == SLJIT_OVERFLOW \
+		|| (op & (SLJIT_I32_OP | SLJIT_SET_Z | VARIABLE_FLAG_MASK)) == (SLJIT_I32_OP | SLJIT_SET_Z | SLJIT_SET_CARRY))
+#define TEST_SUB_FORM2(op) \
+	((GET_FLAG_TYPE(op) >= SLJIT_SIG_LESS && GET_FLAG_TYPE(op) <= SLJIT_SIG_LESS_EQUAL) \
+		|| (op & (SLJIT_I32_OP | SLJIT_SET_Z | VARIABLE_FLAG_MASK)) == (SLJIT_I32_OP | SLJIT_SET_Z))
+#define TEST_SUB_FORM3(op) \
+	(GET_FLAG_TYPE(op) == SLJIT_OVERFLOW \
+		|| (op & (SLJIT_I32_OP | SLJIT_SET_Z)) == (SLJIT_I32_OP | SLJIT_SET_Z))
+#else
+#define TEST_ADD_FORM1(op) \
+	(GET_FLAG_TYPE(op) == SLJIT_OVERFLOW)
+#define TEST_SUB_FORM2(op) \
+	(GET_FLAG_TYPE(op) >= SLJIT_SIG_LESS && GET_FLAG_TYPE(op) <= SLJIT_SIG_LESS_EQUAL)
+#define TEST_SUB_FORM3(op) \
+	(GET_FLAG_TYPE(op) == SLJIT_OVERFLOW)
+#endif
+
 SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compiler, sljit_s32 op,
 	sljit_s32 dst, sljit_sw dstw,
 	sljit_s32 src1, sljit_sw src1w,
@@ -1362,7 +1381,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 
 	switch (GET_OPCODE(op)) {
 	case SLJIT_ADD:
-		if (GET_FLAG_TYPE(op) == SLJIT_OVERFLOW)
+		if (TEST_ADD_FORM1(op))
 			return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM1, dst, dstw, src1, src1w, src2, src2w);
 
 		if (!HAS_FLAGS(op) && ((src1 | src2) & SLJIT_IMM)) {
@@ -1392,6 +1411,20 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 				return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM2 | ALT_FORM4, dst, dstw, src2, src2w, TMP_REG2, 0);
 			}
 		}
+
+#if (defined SLJIT_CONFIG_PPC_64 && SLJIT_CONFIG_PPC_64)
+		if ((op & (SLJIT_I32_OP | SLJIT_SET_Z)) == (SLJIT_I32_OP | SLJIT_SET_Z)) {
+			if (TEST_SL_IMM(src2, src2w)) {
+				compiler->imm = src2w & 0xffff;
+				return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM4 | ALT_FORM5, dst, dstw, src1, src1w, TMP_REG2, 0);
+			}
+			if (TEST_SL_IMM(src1, src1w)) {
+				compiler->imm = src1w & 0xffff;
+				return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM4 | ALT_FORM5, dst, dstw, src2, src2w, TMP_REG2, 0);
+			}
+			return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM4, dst, dstw, src1, src1w, src2, src2w);
+		}
+#endif
 		if (HAS_FLAGS(op)) {
 			if (TEST_SL_IMM(src2, src2w)) {
 				compiler->imm = src2w & 0xffff;
@@ -1402,7 +1435,7 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 				return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM3, dst, dstw, src2, src2w, TMP_REG2, 0);
 			}
 		}
-		return emit_op(compiler, SLJIT_ADD, flags | ((GET_FLAG_TYPE(op) == GET_FLAG_TYPE(SLJIT_SET_CARRY)) ? ALT_FORM4 : 0), dst, dstw, src1, src1w, src2, src2w);
+		return emit_op(compiler, SLJIT_ADD, flags | ((GET_FLAG_TYPE(op) == GET_FLAG_TYPE(SLJIT_SET_CARRY)) ? ALT_FORM5 : 0), dst, dstw, src1, src1w, src2, src2w);
 
 	case SLJIT_ADDC:
 		return emit_op(compiler, SLJIT_ADDC, flags, dst, dstw, src1, src1w, src2, src2w);
@@ -1424,18 +1457,36 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM1 | ALT_FORM3, dst, dstw, src1, src1w, src2, src2w);
 		}
 
-		if (GET_FLAG_TYPE(op) == SLJIT_OVERFLOW)
+		if (dst == SLJIT_UNUSED && GET_FLAG_TYPE(op) <= SLJIT_SIG_LESS_EQUAL) {
+			if (TEST_SL_IMM(src2, src2w)) {
+				compiler->imm = src2w & 0xffff;
+				return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM2 | ALT_FORM3, dst, dstw, src1, src1w, TMP_REG2, 0);
+			}
 			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM2, dst, dstw, src1, src1w, src2, src2w);
+		}
 
-		if (!HAS_FLAGS(op) && ((src1 | src2) & SLJIT_IMM)) {
-			if (TEST_SL_IMM(src2, -src2w)) {
-				compiler->imm = (-src2w) & 0xffff;
-				return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM2, dst, dstw, src1, src1w, TMP_REG2, 0);
-			}
-			if (TEST_SL_IMM(src1, src1w)) {
-				compiler->imm = src1w & 0xffff;
-				return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM3, dst, dstw, src2, src2w, TMP_REG2, 0);
+		if (TEST_SUB_FORM2(op)) {
+			if ((src2 & SLJIT_IMM) && src2w >= -SIMM_MAX && src2w <= SIMM_MAX) {
+				compiler->imm = src2w & 0xffff;
+				return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM2 | ALT_FORM3 | ALT_FORM4, dst, dstw, src1, src1w, TMP_REG2, 0);
 			}
+			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM2 | ALT_FORM4, dst, dstw, src1, src1w, src2, src2w);
+		}
+
+		if (TEST_SUB_FORM3(op))
+			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM3, dst, dstw, src1, src1w, src2, src2w);
+
+		if (TEST_SL_IMM(src2, -src2w)) {
+			compiler->imm = (-src2w) & 0xffff;
+			return emit_op(compiler, SLJIT_ADD, flags | (!HAS_FLAGS(op) ? ALT_FORM2 : ALT_FORM3), dst, dstw, src1, src1w, TMP_REG2, 0);
+		}
+
+		if (TEST_SL_IMM(src1, src1w) && !(op & SLJIT_SET_Z)) {
+			compiler->imm = src1w & 0xffff;
+			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM4, dst, dstw, src2, src2w, TMP_REG2, 0);
+		}
+
+		if (!HAS_FLAGS(op)) {
 			if (TEST_SH_IMM(src2, -src2w)) {
 				compiler->imm = ((-src2w) >> 16) & 0xffff;
 				return emit_op(compiler, SLJIT_ADD, flags |  ALT_FORM2 | ALT_FORM3, dst, dstw, src1, src1w, TMP_REG2, 0);
@@ -1447,18 +1498,6 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 			}
 		}
 
-		if (dst == SLJIT_UNUSED && GET_FLAG_TYPE(op) != GET_FLAG_TYPE(SLJIT_SET_CARRY)) {
-			if (TEST_SL_IMM(src2, src2w)) {
-				compiler->imm = src2w & 0xffff;
-				return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM4 | ALT_FORM5, dst, dstw, src1, src1w, TMP_REG2, 0);
-			}
-			return emit_op(compiler, SLJIT_SUB, flags | ALT_FORM4, dst, dstw, src1, src1w, src2, src2w);
-		}
-
-		if (TEST_SL_IMM(src2, -src2w)) {
-			compiler->imm = (-src2w) & 0xffff;
-			return emit_op(compiler, SLJIT_ADD, flags | ALT_FORM3, dst, dstw, src1, src1w, TMP_REG2, 0);
-		}
 		/* We know ALT_SIGN_EXT is set if it is an SLJIT_I32_OP on 64 bit systems. */
 		return emit_op(compiler, SLJIT_SUB, flags | ((GET_FLAG_TYPE(op) == GET_FLAG_TYPE(SLJIT_SET_CARRY)) ? ALT_FORM5 : 0), dst, dstw, src1, src1w, src2, src2w);
 
@@ -1536,6 +1575,10 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op2(struct sljit_compiler *compile
 	return SLJIT_SUCCESS;
 }
 
+#undef TEST_ADD_FORM1
+#undef TEST_SUB_FORM2
+#undef TEST_SUB_FORM3
+
 SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_src(struct sljit_compiler *compiler, sljit_s32 op,
 	sljit_s32 src, sljit_sw srcw)
 {
@@ -1941,11 +1984,9 @@ static sljit_ins get_bo_bi_flags(sljit_s32 type)
 		return (4 << 21) | ((4 + 1) << 16);
 
 	case SLJIT_OVERFLOW:
-	case SLJIT_MUL_OVERFLOW:
 		return (12 << 21) | (3 << 16);
 
 	case SLJIT_NOT_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
 		return (4 << 21) | (3 << 16);
 
 	case SLJIT_EQUAL_F64:
@@ -2143,12 +2184,10 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 		break;
 
 	case SLJIT_OVERFLOW:
-	case SLJIT_MUL_OVERFLOW:
 		cr_bit = 3;
 		break;
 
 	case SLJIT_NOT_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
 		cr_bit = 3;
 		invert = 1;
 		break;

File diff suppressed because it is too large
+ 481 - 251
thirdparty/pcre2/src/sljit/sljitNativeS390X.c


+ 3 - 0
thirdparty/pcre2/src/sljit/sljitNativeSPARC_32.c

@@ -93,18 +93,21 @@ static SLJIT_INLINE sljit_s32 emit_single_op(struct sljit_compiler *compiler, sl
 		return push_inst(compiler, ADD | D(dst) | S1(dst) | IMM(1), UNMOVABLE_INS);
 
 	case SLJIT_ADD:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return push_inst(compiler, ADD | (flags & SET_FLAGS) | D(dst) | S1(src1) | ARG2(flags, src2), DR(dst) | (flags & SET_FLAGS));
 
 	case SLJIT_ADDC:
 		return push_inst(compiler, ADDC | (flags & SET_FLAGS) | D(dst) | S1(src1) | ARG2(flags, src2), DR(dst) | (flags & SET_FLAGS));
 
 	case SLJIT_SUB:
+		compiler->status_flags_state = SLJIT_CURRENT_FLAGS_ADD_SUB;
 		return push_inst(compiler, SUB | (flags & SET_FLAGS) | D(dst) | S1(src1) | ARG2(flags, src2), DR(dst) | (flags & SET_FLAGS));
 
 	case SLJIT_SUBC:
 		return push_inst(compiler, SUBC | (flags & SET_FLAGS) | D(dst) | S1(src1) | ARG2(flags, src2), DR(dst) | (flags & SET_FLAGS));
 
 	case SLJIT_MUL:
+		compiler->status_flags_state = 0;
 		FAIL_IF(push_inst(compiler, SMUL | D(dst) | S1(src1) | ARG2(flags, src2), DR(dst)));
 		if (!(flags & SET_FLAGS))
 			return SLJIT_SUCCESS;

+ 11 - 7
thirdparty/pcre2/src/sljit/sljitNativeSPARC_common.c

@@ -1275,16 +1275,14 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_label* sljit_emit_label(struct sljit_compi
 	return label;
 }
 
-static sljit_ins get_cc(sljit_s32 type)
+static sljit_ins get_cc(struct sljit_compiler *compiler, sljit_s32 type)
 {
 	switch (type) {
 	case SLJIT_EQUAL:
-	case SLJIT_MUL_NOT_OVERFLOW:
 	case SLJIT_NOT_EQUAL_F64: /* Unordered. */
 		return DA(0x1);
 
 	case SLJIT_NOT_EQUAL:
-	case SLJIT_MUL_OVERFLOW:
 	case SLJIT_EQUAL_F64:
 		return DA(0x9);
 
@@ -1317,10 +1315,16 @@ static sljit_ins get_cc(sljit_s32 type)
 		return DA(0x2);
 
 	case SLJIT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return DA(0x9);
+
 	case SLJIT_UNORDERED_F64:
 		return DA(0x7);
 
 	case SLJIT_NOT_OVERFLOW:
+		if (!(compiler->status_flags_state & SLJIT_CURRENT_FLAGS_ADD_SUB))
+			return DA(0x1);
+
 	case SLJIT_ORDERED_F64:
 		return DA(0xf);
 
@@ -1347,7 +1351,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 		if (((compiler->delay_slot & DST_INS_MASK) != UNMOVABLE_INS) && !(compiler->delay_slot & ICC_IS_SET))
 			jump->flags |= IS_MOVABLE;
 #if (defined SLJIT_CONFIG_SPARC_32 && SLJIT_CONFIG_SPARC_32)
-		PTR_FAIL_IF(push_inst(compiler, BICC | get_cc(type ^ 1) | 5, UNMOVABLE_INS));
+		PTR_FAIL_IF(push_inst(compiler, BICC | get_cc(compiler, type ^ 1) | 5, UNMOVABLE_INS));
 #else
 #error "Implementation required"
 #endif
@@ -1357,7 +1361,7 @@ SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_jump(struct sljit_compile
 		if (((compiler->delay_slot & DST_INS_MASK) != UNMOVABLE_INS) && !(compiler->delay_slot & FCC_IS_SET))
 			jump->flags |= IS_MOVABLE;
 #if (defined SLJIT_CONFIG_SPARC_32 && SLJIT_CONFIG_SPARC_32)
-		PTR_FAIL_IF(push_inst(compiler, FBFCC | get_cc(type ^ 1) | 5, UNMOVABLE_INS));
+		PTR_FAIL_IF(push_inst(compiler, FBFCC | get_cc(compiler, type ^ 1) | 5, UNMOVABLE_INS));
 #else
 #error "Implementation required"
 #endif
@@ -1474,9 +1478,9 @@ SLJIT_API_FUNC_ATTRIBUTE sljit_s32 sljit_emit_op_flags(struct sljit_compiler *co
 
 	type &= 0xff;
 	if (type < SLJIT_EQUAL_F64)
-		FAIL_IF(push_inst(compiler, BICC | get_cc(type) | 3, UNMOVABLE_INS));
+		FAIL_IF(push_inst(compiler, BICC | get_cc(compiler, type) | 3, UNMOVABLE_INS));
 	else
-		FAIL_IF(push_inst(compiler, FBFCC | get_cc(type) | 3, UNMOVABLE_INS));
+		FAIL_IF(push_inst(compiler, FBFCC | get_cc(compiler, type) | 3, UNMOVABLE_INS));
 
 	FAIL_IF(push_inst(compiler, OR | D(reg) | S1(0) | IMM(1), UNMOVABLE_INS));
 	FAIL_IF(push_inst(compiler, OR | D(reg) | S1(0) | IMM(0), UNMOVABLE_INS));

+ 0 - 2
thirdparty/pcre2/src/sljit/sljitNativeX86_common.c

@@ -411,11 +411,9 @@ static sljit_u8 get_jump_code(sljit_s32 type)
 		return 0x8e /* jle */;
 
 	case SLJIT_OVERFLOW:
-	case SLJIT_MUL_OVERFLOW:
 		return 0x80 /* jo */;
 
 	case SLJIT_NOT_OVERFLOW:
-	case SLJIT_MUL_NOT_OVERFLOW:
 		return 0x81 /* jno */;
 
 	case SLJIT_UNORDERED_F64:

+ 7 - 3
thirdparty/pcre2/src/sljit/sljitUtils.c

@@ -48,7 +48,7 @@ static HANDLE allocator_lock;
 static SLJIT_INLINE void allocator_grab_lock(void)
 {
 	HANDLE lock;
-	if (SLJIT_UNLIKELY(!allocator_lock)) {
+	if (SLJIT_UNLIKELY(!InterlockedCompareExchangePointer(&allocator_lock, NULL, NULL))) {
 		lock = CreateMutex(NULL, FALSE, NULL);
 		if (InterlockedCompareExchangePointer(&allocator_lock, lock, NULL))
 			CloseHandle(lock);
@@ -146,9 +146,13 @@ static SLJIT_INLINE sljit_sw get_page_alignment(void) {
 #include <unistd.h>
 
 static SLJIT_INLINE sljit_sw get_page_alignment(void) {
-	static sljit_sw sljit_page_align;
-	if (!sljit_page_align) {
+	static sljit_sw sljit_page_align = -1;
+	if (sljit_page_align < 0) {
+#ifdef _SC_PAGESIZE
 		sljit_page_align = sysconf(_SC_PAGESIZE);
+#else
+		sljit_page_align = getpagesize();
+#endif
 		/* Should never happen. */
 		if (sljit_page_align < 0)
 			sljit_page_align = 4096;

+ 6 - 2
thirdparty/pcre2/src/sljit/sljitWXExecAllocator.c

@@ -121,14 +121,18 @@ SLJIT_API_FUNC_ATTRIBUTE void* sljit_malloc_exec(sljit_uw size)
 	static pthread_mutex_t se_lock = PTHREAD_MUTEX_INITIALIZER;
 #endif
 	static int se_protected = !SLJIT_PROT_WX;
+	int prot = PROT_READ | PROT_WRITE | SLJIT_PROT_WX;
 	sljit_uw* ptr;
 
 	if (SLJIT_UNLIKELY(se_protected < 0))
 		return NULL;
 
+#ifdef PROT_MAX
+	prot |= PROT_MAX(PROT_READ | PROT_WRITE | PROT_EXEC);
+#endif
+
 	size += sizeof(sljit_uw);
-	ptr = (sljit_uw*)mmap(NULL, size, PROT_READ | PROT_WRITE | SLJIT_PROT_WX,
-				MAP_PRIVATE | MAP_ANON, -1, 0);
+	ptr = (sljit_uw*)mmap(NULL, size, prot, MAP_PRIVATE | MAP_ANON, -1, 0);
 
 	if (ptr == MAP_FAILED)
 		return NULL;

Some files were not shown because too many files changed in this diff