diff --git a/configure.in b/configure.in index e46a8b110..a6f2fc2a7 100644 --- a/configure.in +++ b/configure.in @@ -9337,6 +9337,9 @@ ac_configure_args="$ac_configure_args --prefix=$dist" if test "$MOZ_MEMORY"; then ac_configure_args="$ac_configure_args --enable-jemalloc" fi +if test "$TENFOURFOX_VMX"; then + ac_configure_args="$ac_configure_args --enable-tenfourfox-vmx" +fi if test -n "$ZLIB_IN_MOZGLUE"; then MOZ_ZLIB_LIBS= fi @@ -9355,6 +9358,7 @@ export DIST export MOZ_LINKER export ZLIB_IN_MOZGLUE export MOZ_MEMORY +export TENFOURFOX_VMX if ! test -e js; then mkdir js diff --git a/js/src/jsstr.cpp b/js/src/jsstr.cpp index b299beb48..6ca0f75b9 100644 --- a/js/src/jsstr.cpp +++ b/js/src/jsstr.cpp @@ -51,6 +51,9 @@ #include "vm/StringObject-inl.h" #include "vm/TypeInference-inl.h" +#include "mozilla-config.h" +#include "plvmx.h" + using namespace js; using namespace js::gc; using namespace js::unicode; @@ -1155,10 +1158,12 @@ FirstCharMatcherUnrolled(const TextChar* text, uint32_t n, const PatChar pat) static const char* FirstCharMatcher8bit(const char* text, uint32_t n, const char pat) { -#if defined(__clang__) +#ifndef TENFOURFOX_VMX +#warning using non-VMX memchr return FirstCharMatcherUnrolled(text, n, pat); #else - return reinterpret_cast(memchr(text, pat, n)); +#warning using VMX memchr + return reinterpret_cast(vmx_memchr(text, pat, n)); #endif } diff --git a/nsprpub/config/autoconf.mk.in b/nsprpub/config/autoconf.mk.in index 8c9a43aa1..187b320e7 100644 --- a/nsprpub/config/autoconf.mk.in +++ b/nsprpub/config/autoconf.mk.in @@ -54,6 +54,7 @@ USE_N32 = @USE_N32@ USE_X32 = @USE_X32@ USE_64 = @USE_64@ ENABLE_STRIP = @ENABLE_STRIP@ +TENFOURFOX_VMX = @TENFOURFOX_VMX@ USE_PTHREADS = @USE_PTHREADS@ USE_BTHREADS = @USE_BTHREADS@ diff --git a/nsprpub/configure b/nsprpub/configure index 2e6ca1bd0..d10db68c1 100755 --- a/nsprpub/configure +++ b/nsprpub/configure @@ -667,6 +667,7 @@ DLL_SUFFIX LIB_SUFFIX OBJ_SUFFIX CPU_ARCH +TENFOURFOX_VMX PR_MD_ARCH_DIR PR_MD_ASFILES PR_MD_CSRCS @@ -801,6 +802,7 @@ enable_x32 enable_64bit enable_mdupdate enable_cplus +enable_tenfourfox_vmx with_arm_kuser with_macos_sdk enable_macos_target @@ -1465,6 +1467,7 @@ Optional Features: --enable-macos-target=VER Set the minimum MacOS version needed at runtime 10.2 for ppc, 10.4 for x86 + --enable-tenfourfox-vmx Enable VMX SIMD features for PowerPC --disable-os2-high-mem Disable high-memory support on OS/2 --enable-strip Enable stripping of shared libs and programs @@ -2495,6 +2498,7 @@ _HAVE_PTHREADS= USE_PTHREADS= USE_USER_PTHREADS= USE_NSPR_THREADS= +TENFOURFOX_VMX= USE_N32= USE_X32= USE_64= @@ -2904,6 +2908,16 @@ if test "${enable_n32+set}" = set; then : fi fi +# Check whether --enable-tenfourfox-vmx was given. +if test "${enable_tenfourfox_vmx+set}" = set; then : + enableval=$enable_tenfourfox_vmx; if test "$enableval" = "yes"; then + TENFOURFOX_VMX=1 + else if test "$enableval" = "no"; then + TENFOURFOX_VMX= + fi + fi +fi + # Check whether --enable-x32 was given. if test "${enable_x32+set}" = set; then : @@ -6524,6 +6538,10 @@ fi $as_echo "#define HAVE_SOCKLEN_T 1" >>confdefs.h + if test -n "$TENFOURFOX_VMX"; then + $as_echo "#define TENFOURFOX_VMX 1" >>confdefs.h + fi + AS='$(CC) -x assembler-with-cpp' CFLAGS="$CFLAGS -Wall -fno-common" case "${target_cpu}" in diff --git a/nsprpub/configure.in b/nsprpub/configure.in index f96407a4f..6a6a680a3 100644 --- a/nsprpub/configure.in +++ b/nsprpub/configure.in @@ -313,6 +313,15 @@ AC_ARG_ENABLE(optimize, MOZ_OPTIMIZE= fi ]) +AC_ARG_ENABLE(tenfourfox-vmx, +[ --enable-tenfourfox-vmx Turn on AltiVec-VMX specific options for TenFourFox ], +[ if test "$enableval" != "no"; then + AC_DEFINE(TENFOURFOX_VMX) + TENFOURFOX_VMX=1 + else + TENFOURFOX_VMX= + fi ]) + AC_ARG_ENABLE(debug, [ --enable-debug[=DBG] Enable debugging (using compiler flags DBG)], [ if test "$enableval" != "no"; then @@ -3049,6 +3058,7 @@ AC_SUBST(PR_MD_CSRCS) AC_SUBST(PR_MD_ASFILES) AC_SUBST(PR_MD_ARCH_DIR) AC_SUBST(CPU_ARCH) +AC_SUBST(TENFOURFOX_VMX) AC_SUBST(OBJ_SUFFIX) AC_SUBST(LIB_SUFFIX) diff --git a/nsprpub/lib/libc/src/Makefile.in b/nsprpub/lib/libc/src/Makefile.in index e8a6d9fd0..0c44e3cf9 100644 --- a/nsprpub/lib/libc/src/Makefile.in +++ b/nsprpub/lib/libc/src/Makefile.in @@ -39,6 +39,11 @@ LIBRARY_VERSION = $(MOD_MAJOR_VERSION) RELEASE_LIBS = $(TARGETS) +ifeq ($(TENFOURFOX_VMX),1) +CSRCS += plvmx.c +CFLAGS += -faltivec +endif + ifeq ($(OS_ARCH),WINNT) RES=$(OBJDIR)/plc.res RESNAME=plc.rc diff --git a/nsprpub/lib/libc/src/plvmx.c b/nsprpub/lib/libc/src/plvmx.c new file mode 100644 index 000000000..a2588585e --- /dev/null +++ b/nsprpub/lib/libc/src/plvmx.c @@ -0,0 +1,64 @@ +#include +#include "plvmx.h" + +void *vmx_memchr(const void *b, int c, size_t length) { + + +/* From: +https://github.com/ridiculousfish/HexFiend/blob/4d5bcee5715f5f288649f7471d1da5bd06376f46/framework/sources/HFFastMemchr.m + with some optimizations */ + + const unsigned char *haystack = (const unsigned char *)b; + unsigned char needle = (unsigned char)c; + + unsigned prefixLength = (unsigned)((16 - ((unsigned long)haystack) % 16) % 16); + unsigned suffixLength = (unsigned)(((unsigned long)(haystack + length)) % 16); + // It is possible for altivecLength to be < 0 for short strings. + int altivecLength = length - prefixLength - suffixLength; + + if (altivecLength < 16) { + while (length--) { + if (*haystack == needle) return (void *)haystack; + haystack++; + } + return NULL; + } + + size_t numVectors = altivecLength >> 4; + while (prefixLength--) { + if (*haystack == needle) return (void *)haystack; + haystack++; + } + + unsigned int mashedByte = (needle << 24 ) | (needle << 16) | (needle << 8) | needle; + const vector unsigned char searchVector = (vector unsigned int){mashedByte, mashedByte, mashedByte, mashedByte}; + while (numVectors--) { + if (vec_any_eq(*(const vector unsigned char*)haystack, searchVector)) goto foundResult; + haystack += 16; + } + + while (suffixLength--) { + if (*haystack == needle) return (void *)haystack; + haystack++; + } + + return NULL; + +foundResult: + ; + /* some byte has the result - look in groups of 4 to find which it is */ + unsigned numWords = 4; + unsigned int val; + while (numWords--) { + val = *(unsigned int*)haystack; + if (((val >> 24) & 0xFF) == needle) return (void *)haystack; + if (((val >> 16) & 0xFF) == needle) return (void *)(1 + haystack); + if (((val >> 8) & 0xFF) == needle) return (void *)(2 + haystack); + if ((val & 0xFF) == needle) return (void *)(3 + haystack); + haystack += 4; + } + + /* should never get here */ + fprintf(stderr, "failed vmx_memchr()\n"); + return NULL; +}