diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 9f236af..02c7e07 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -8,7 +8,7 @@ jobs: strategy: matrix: - version: [ 18, 19, 20, 21, 22, 23 ] + version: [ 24 ] vector-length: [ 256, 512 ] steps: diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 1cdb32f..43ce479 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -17,11 +17,11 @@ jobs: - uses: gradle/actions/wrapper-validation@v3 - - name: Set up JDK 18 + - name: Set up JDK 24 uses: actions/setup-java@v4 with: distribution: temurin - java-version: 18 + java-version: 24 - name: Setup Gradle uses: gradle/actions/setup-gradle@v3 diff --git a/README.md b/README.md index 1802aa2..0fe809e 100644 --- a/README.md +++ b/README.md @@ -73,7 +73,7 @@ Please remember about specifying the desired version. Note that simdjson-java follows the [SemVer specification](https://semver.org/), which means, for example, that a major version of zero indicates initial development, so the library's API should not be considered stable. -We require Java 18 or better. +We require Java 24 or better. ## Benchmarks diff --git a/build.gradle b/build.gradle index 4bcf450..b9b4d2a 100644 --- a/build.gradle +++ b/build.gradle @@ -33,9 +33,9 @@ java { // It seems that specifying the minimum supported Java version while allowing the use of newer // ones isn't possible in Gradle. To test the library against multiple Java versions, the // workaround proposed in https://github.com/gradle/gradle/issues/16256 has been applied: - if (!JavaVersion.current().isCompatibleWith(JavaVersion.VERSION_18)) { + if (!JavaVersion.current().isCompatibleWith(JavaVersion.VERSION_24)) { toolchain { - languageVersion = JavaLanguageVersion.of(18) + languageVersion = JavaLanguageVersion.of(24) } } withJavadocJar() diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar index 9bbc975..1b33c55 100644 Binary files a/gradle/wrapper/gradle-wrapper.jar and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 37f853b..d4081da 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-8.13-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.3-bin.zip networkTimeout=10000 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME diff --git a/gradlew b/gradlew index faf9300..23d15a9 100755 --- a/gradlew +++ b/gradlew @@ -114,7 +114,7 @@ case "$( uname )" in #( NONSTOP* ) nonstop=true ;; esac -CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar +CLASSPATH="\\\"\\\"" # Determine the Java command to use to start the JVM. @@ -213,7 +213,7 @@ DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' set -- \ "-Dorg.gradle.appname=$APP_BASE_NAME" \ -classpath "$CLASSPATH" \ - org.gradle.wrapper.GradleWrapperMain \ + -jar "$APP_HOME/gradle/wrapper/gradle-wrapper.jar" \ "$@" # Stop when "xargs" is not available. diff --git a/gradlew.bat b/gradlew.bat index 9b42019..5eed7ee 100644 --- a/gradlew.bat +++ b/gradlew.bat @@ -70,11 +70,11 @@ goto fail :execute @rem Setup the command line -set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar +set CLASSPATH= @rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* :end @rem End local scope for the variables with windows NT shell diff --git a/src/main/java/org/simdjson/StructuralIndexer.java b/src/main/java/org/simdjson/StructuralIndexer.java index 3720fda..1850742 100644 --- a/src/main/java/org/simdjson/StructuralIndexer.java +++ b/src/main/java/org/simdjson/StructuralIndexer.java @@ -7,7 +7,7 @@ import static jdk.incubator.vector.ByteVector.SPECIES_256; import static jdk.incubator.vector.ByteVector.SPECIES_512; -import static jdk.incubator.vector.VectorOperators.UNSIGNED_LE; +import static jdk.incubator.vector.VectorOperators.ULE; class StructuralIndexer { @@ -88,8 +88,8 @@ private void index256(byte[] buffer, int length) { escaped = (EVEN_BITS_MASK ^ invertMask) & followsEscape; } - long unescaped0 = chunk0.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); - long unescaped1 = chunk1.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped0 = chunk0.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped1 = chunk1.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); long unescaped = unescaped0 | (unescaped1 << 32); long quote0 = chunk0.eq(QUOTE).toLong(); @@ -148,8 +148,8 @@ private void index256(byte[] buffer, int length) { escaped = (EVEN_BITS_MASK ^ invertMask) & followsEscape; } - long unescaped0 = chunk0.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); - long unescaped1 = chunk1.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped0 = chunk0.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped1 = chunk1.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); long unescaped = unescaped0 | (unescaped1 << 32); long quote0 = chunk0.eq(QUOTE).toLong(); @@ -228,7 +228,7 @@ private void index512(byte[] buffer, int length) { escaped = (EVEN_BITS_MASK ^ invertMask) & followsEscape; } - long unescaped = chunk.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped = chunk.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); long quote = chunk.eq(QUOTE).toLong() & ~escaped; long inString = prefixXor(quote) ^ prevInString; prevInString = inString >> 63; @@ -271,7 +271,7 @@ private void index512(byte[] buffer, int length) { escaped = (EVEN_BITS_MASK ^ invertMask) & followsEscape; } - long unescaped = chunk.compare(UNSIGNED_LE, LAST_CONTROL_CHARACTER).toLong(); + long unescaped = chunk.compare(ULE, LAST_CONTROL_CHARACTER).toLong(); long quote = chunk.eq(QUOTE).toLong() & ~escaped; long inString = prefixXor(quote) ^ prevInString; prevInString = inString >> 63; diff --git a/src/main/java/org/simdjson/Utf8Validator.java b/src/main/java/org/simdjson/Utf8Validator.java index 7645fd1..0d220b3 100644 --- a/src/main/java/org/simdjson/Utf8Validator.java +++ b/src/main/java/org/simdjson/Utf8Validator.java @@ -11,8 +11,8 @@ import static jdk.incubator.vector.VectorOperators.LSHL; import static jdk.incubator.vector.VectorOperators.LSHR; import static jdk.incubator.vector.VectorOperators.NE; -import static jdk.incubator.vector.VectorOperators.UNSIGNED_GE; -import static jdk.incubator.vector.VectorOperators.UNSIGNED_GT; +import static jdk.incubator.vector.VectorOperators.UGE; +import static jdk.incubator.vector.VectorOperators.UGT; import static jdk.incubator.vector.VectorShuffle.iota; import static org.simdjson.VectorUtils.BYTE_SPECIES; import static org.simdjson.VectorUtils.INT_SPECIES; @@ -65,7 +65,7 @@ static void validate(byte[] buffer, int length) { if (chunk.and(ALL_ASCII_MASK).compare(EQ, 0).allTrue()) { errors |= previousIncomplete; } else { - previousIncomplete = chunk.compare(UNSIGNED_GE, INCOMPLETE_CHECK).toLong(); + previousIncomplete = chunk.compare(UGE, INCOMPLETE_CHECK).toLong(); // Shift the input forward by four bytes to make space for the previous four bytes. // The previous three bytes are required for validation, pulling in the last integer // will give the previous four bytes. The switch to integer vectors is to allow for @@ -97,13 +97,13 @@ static void validate(byte[] buffer, int length) { .or(chunkWithPreviousFourBytes.lanewise(LSHR, TWO_BYTES_SIZE)) .reinterpretAsBytes(); // The minimum leading byte of 3-byte sequences is always greater than the maximum leading byte of 2-byte sequences. - VectorMask is3ByteLead = previousTwoBytes.compare(UNSIGNED_GT, MAX_2_LEADING_BYTE); + VectorMask is3ByteLead = previousTwoBytes.compare(UGT, MAX_2_LEADING_BYTE); ByteVector previousThreeBytes = chunkAsInts .lanewise(LSHL, THREE_BYTES_SIZE) .or(chunkWithPreviousFourBytes.lanewise(LSHR, Byte.SIZE)) .reinterpretAsBytes(); // The minimum leading byte of 4-byte sequences is always greater than the maximum leading byte of 3-byte sequences. - VectorMask is4ByteLead = previousThreeBytes.compare(UNSIGNED_GT, MAX_3_LEADING_BYTE); + VectorMask is4ByteLead = previousThreeBytes.compare(UGT, MAX_3_LEADING_BYTE); // The firstCheck vector contains 0x80 values on continuation byte indexes. // The leading bytes of 3 and 4-byte sequences should match up with these indexes and zero them out. ByteVector secondCheck = firstCheck.add((byte) 0x80, is3ByteLead.or(is4ByteLead)); @@ -117,7 +117,7 @@ static void validate(byte[] buffer, int length) { ByteVector chunk = ByteVector.fromArray(BYTE_SPECIES, buffer, offset, remainingBytes); if (!chunk.and(ALL_ASCII_MASK).compare(EQ, 0).allTrue()) { IntVector chunkAsInts = chunk.reinterpretAsInts(); - previousIncomplete = chunk.compare(UNSIGNED_GE, INCOMPLETE_CHECK).toLong(); + previousIncomplete = chunk.compare(UGE, INCOMPLETE_CHECK).toLong(); // Shift the input forward by four bytes to make space for the previous four bytes. // The previous three bytes are required for validation, pulling in the last integer // will give the previous four bytes. The switch to integer vectors is to allow for @@ -149,13 +149,13 @@ static void validate(byte[] buffer, int length) { .or(chunkWithPreviousFourBytes.lanewise(LSHR, TWO_BYTES_SIZE)) .reinterpretAsBytes(); // The minimum leading byte of 3-byte sequences is always greater than the maximum leading byte of 2-byte sequences. - VectorMask is3ByteLead = previousTwoBytes.compare(UNSIGNED_GT, MAX_2_LEADING_BYTE); + VectorMask is3ByteLead = previousTwoBytes.compare(UGT, MAX_2_LEADING_BYTE); ByteVector previousThreeBytes = chunkAsInts .lanewise(LSHL, THREE_BYTES_SIZE) .or(chunkWithPreviousFourBytes.lanewise(LSHR, Byte.SIZE)) .reinterpretAsBytes(); // The minimum leading byte of 4-byte sequences is always greater than the maximum leading byte of 3-byte sequences. - VectorMask is4ByteLead = previousThreeBytes.compare(UNSIGNED_GT, MAX_3_LEADING_BYTE); + VectorMask is4ByteLead = previousThreeBytes.compare(UGT, MAX_3_LEADING_BYTE); // The firstCheck vector contains 0x80 values on continuation byte indexes. // The leading bytes of 3 and 4-byte sequences should match up with these indexes and zero them out. ByteVector secondCheck = firstCheck.add((byte) 0x80, is3ByteLead.or(is4ByteLead));