├── .github
├── ISSUE_TEMPLATE
│ ├── bug_report.md
│ └── feature_request.md
├── dependabot.yml
└── workflows
│ ├── ci-workflow.yml
│ └── pr-workflow.yml
├── .gitignore
├── CODE_OF_CONDUCT.md
├── CONTRIBUTING.md
├── LICENSE.md
├── README.md
├── benchmarks
├── README.md
├── charts
│ ├── array.r
│ ├── common.r
│ ├── fieldSerializer.r
│ ├── string.r
│ └── variableEncoding.r
├── lib
│ ├── byte-buddy-1.12.7.jar
│ ├── commons-cli-1.3.1.jar
│ ├── commons-math3-3.2.jar
│ ├── jmh-core-1.21.jar
│ ├── jmh-generator-annprocess-1.21.jar
│ └── jopt-simple-4.6.jar
├── pom.xml
├── run.sh
└── src
│ └── main
│ └── java
│ └── com
│ └── esotericsoftware
│ └── kryo
│ └── benchmarks
│ ├── BigDecimalBenchmark.java
│ ├── ConcurrencyBenchmark.java
│ ├── FieldSerializerBenchmark.java
│ ├── KryoBenchmarks.java
│ ├── MapBenchmark.java
│ ├── data
│ ├── Image.java
│ ├── Media.java
│ ├── MediaContent.java
│ └── Sample.java
│ └── io
│ ├── ArrayBenchmark.java
│ ├── InputOutputState.java
│ ├── StringBenchmark.java
│ └── VariableEncodingBenchmark.java
├── build
├── assembly-all.xml
├── commons-lang-2.6.jar
├── junit-platform-console-standalone-1.8.2.jar
└── settings-sonatype.xml
├── compat_reports
├── kryo-2.22.jar
├── kryo-2.23.0.jar
├── kryo
│ ├── 2.22_to_2.23.0
│ │ └── compat_report.html
│ ├── 2.23.0_to_2.24.0
│ │ └── compat_report.html
│ ├── 2.24.0_to_3.0.0
│ │ └── compat_report.html
│ ├── 3.0.0_to_3.0.1
│ │ └── compat_report.html
│ ├── 3.0.1_to_3.0.2
│ │ └── compat_report.html
│ ├── 3.0.2_to_3.0.3
│ │ └── compat_report.html
│ ├── 3.0.3_to_4.0.0
│ │ └── compat_report.html
│ ├── 4.0.0_to_4.0.1
│ │ └── compat_report.html
│ ├── 4.0.1_to_4.0.2
│ │ └── compat_report.html
│ ├── 4.0.2_to_4.0.3
│ │ └── compat_report.html
│ ├── 4.0.2_to_5.0.0-RC1
│ │ └── compat_report.html
│ ├── 5.0.0-RC1_to_5.0.0-RC2
│ │ └── compat_report.html
│ ├── 5.0.0-RC2_to_5.0.0-RC3
│ │ └── compat_report.html
│ ├── 5.0.0-RC4_to_5.0.0-RC5
│ │ └── compat_report.html
│ ├── 5.0.0-RC5_to_5.0.0-RC6
│ │ └── compat_report.html
│ ├── 5.0.0-RC6_to_5.0.0-RC7
│ │ └── compat_report.html
│ ├── 5.0.0-RC7_to_5.0.0-RC8
│ │ └── compat_report.html
│ ├── 5.0.0-RC8_to_5.0.0-RC9
│ │ └── compat_report.html
│ ├── 5.0.0-RC9_to_5.0.0
│ │ └── compat_report.html
│ ├── 5.0.0_to_5.0.1
│ │ └── compat_report.html
│ ├── 5.0.1_to_5.0.2
│ │ └── compat_report.html
│ ├── 5.0.2_to_5.0.3
│ │ └── compat_report.html
│ ├── 5.0.3_to_5.0.4
│ │ └── compat_report.html
│ ├── 5.0.4_to_5.1.0
│ │ └── compat_report.html
│ ├── 5.1.0_to_5.1.1
│ │ └── compat_report.html
│ ├── 5.1.1_to_5.2.0
│ │ └── compat_report.html
│ ├── 5.2.0_to_5.2.1
│ │ └── compat_report.html
│ ├── 5.2.1_to_5.3.0
│ │ └── compat_report.html
│ ├── 5.3.0_to_5.4.0
│ │ └── compat_report.html
│ ├── 5.4.0_to_5.5.0
│ │ └── compat_report.html
│ ├── 5.5.0_to_5.6.0
│ │ └── compat_report.html
│ ├── 5.6.0_to_5.6.1
│ │ └── compat_report.html
│ └── 5.6.1_to_5.6.2
│ │ └── compat_report.html
└── skip-classes.txt
├── eclipse
├── .classpath
├── .factorypath
├── .importorder
├── .project
├── .settings
│ ├── org.eclipse.jdt.apt.core.prefs
│ ├── org.eclipse.jdt.core.prefs
│ └── org.eclipse.jdt.ui.prefs
└── code-format.xml
├── lib
├── minlog-1.3.1.jar
├── objenesis-3.2.jar
└── reflectasm-1.11.9.jar
├── main-versioned
└── pom.xml
├── main
└── pom.xml
├── pom.xml
├── src
└── com
│ └── esotericsoftware
│ └── kryo
│ ├── ClassResolver.java
│ ├── DefaultSerializer.java
│ ├── Kryo.java
│ ├── KryoCopyable.java
│ ├── KryoException.java
│ ├── KryoSerializable.java
│ ├── ReferenceResolver.java
│ ├── Registration.java
│ ├── Serializer.java
│ ├── SerializerFactory.java
│ ├── io
│ ├── ByteBufferInput.java
│ ├── ByteBufferInputStream.java
│ ├── ByteBufferOutput.java
│ ├── ByteBufferOutputStream.java
│ ├── Input.java
│ ├── InputChunked.java
│ ├── KryoBufferOverflowException.java
│ ├── KryoBufferUnderflowException.java
│ ├── KryoDataInput.java
│ ├── KryoDataOutput.java
│ ├── KryoObjectInput.java
│ ├── KryoObjectOutput.java
│ ├── Output.java
│ └── OutputChunked.java
│ ├── serializers
│ ├── AsmField.java
│ ├── BeanSerializer.java
│ ├── BlowfishSerializer.java
│ ├── CachedFields.java
│ ├── ClosureSerializer.java
│ ├── CollectionSerializer.java
│ ├── CompatibleFieldSerializer.java
│ ├── DefaultArraySerializers.java
│ ├── DefaultSerializers.java
│ ├── DeflateSerializer.java
│ ├── EnumMapSerializer.java
│ ├── EnumNameSerializer.java
│ ├── ExternalizableSerializer.java
│ ├── FieldSerializer.java
│ ├── ImmutableCollectionsSerializers.java
│ ├── ImmutableSerializer.java
│ ├── JavaSerializer.java
│ ├── MapSerializer.java
│ ├── OptionalSerializers.java
│ ├── RecordSerializer.java
│ ├── ReflectField.java
│ ├── TaggedFieldSerializer.java
│ ├── TimeSerializers.java
│ ├── UnsafeField.java
│ └── VersionFieldSerializer.java
│ ├── unsafe
│ ├── UnsafeByteBufferInput.java
│ ├── UnsafeByteBufferOutput.java
│ ├── UnsafeInput.java
│ ├── UnsafeOutput.java
│ └── UnsafeUtil.java
│ └── util
│ ├── CuckooObjectMap.java
│ ├── DefaultClassResolver.java
│ ├── DefaultGenerics.java
│ ├── DefaultInstantiatorStrategy.java
│ ├── Generics.java
│ ├── GenericsUtil.java
│ ├── HashMapReferenceResolver.java
│ ├── IdentityMap.java
│ ├── IdentityObjectIntMap.java
│ ├── IntArray.java
│ ├── IntMap.java
│ ├── ListReferenceResolver.java
│ ├── MapReferenceResolver.java
│ ├── NoGenerics.java
│ ├── Null.java
│ ├── ObjectIntMap.java
│ ├── ObjectMap.java
│ ├── Pool.java
│ └── Util.java
├── test-jdk11
└── com
│ └── esotericsoftware
│ └── kryo
│ ├── TestDataJava11.java
│ └── serializers
│ └── ImmutableCollectionsSerializersTest.java
├── test-jdk17
└── com
│ └── esotericsoftware
│ └── kryo
│ ├── TestDataJava17.java
│ └── serializers
│ └── RecordSerializerTest.java
├── test-kotlin
└── com.esotericsoftware.kryo
│ └── SerializationTest.kt
└── test
├── com
└── esotericsoftware
│ └── kryo
│ ├── CopyTest.java
│ ├── DefaultInstantiatorStrategyTest.java
│ ├── DepthTest.java
│ ├── GarbageCollectionTest.java
│ ├── KryoAssert.java
│ ├── KryoTestCase.java
│ ├── ReferenceTest.java
│ ├── ReflectionAssert.java
│ ├── RegistrationTest.java
│ ├── SerializationBenchmarkTest.java
│ ├── SerializationCompatTest.java
│ ├── SerializationCompatTestData.java
│ ├── Unsafe.java
│ ├── WarnUnregisteredClassesTest.java
│ ├── io
│ ├── ByteBufferInputOutputTest.java
│ ├── ChunkedTest.java
│ ├── InputOutputTest.java
│ ├── UnsafeByteBufferInputOutputTest.java
│ └── UnsafeInputOutputTest.java
│ ├── serializers
│ ├── ArraySerializerTest.java
│ ├── BeanSerializerTest.java
│ ├── BlowfishSerializerTest.java
│ ├── ClosureSerializerTest.java
│ ├── CollectionSerializerTest.java
│ ├── CompatibleFieldSerializerTest.java
│ ├── DefaultSerializersTest.java
│ ├── DeflateSerializerTest.java
│ ├── EnumNameSerializerTest.java
│ ├── ExternalizableSerializerTest.java
│ ├── FieldSerializerGenericsTest.java
│ ├── FieldSerializerInheritanceTest.java
│ ├── FieldSerializerTest.java
│ ├── GenericsTest.java
│ ├── JavaSerializerTest.java
│ ├── MapSerializerTest.java
│ ├── OptionalSerializersTest.java
│ ├── ParallelSerializationTest.java
│ ├── SerializerPriorityTest.java
│ ├── TaggedFieldSerializerTest.java
│ ├── TimeSerializersTest.java
│ └── VersionedFieldSerializerTest.java
│ └── util
│ ├── GenericsUtilTest.java
│ ├── PoolTest.java
│ └── UtilTest.java
└── resources
├── TestData-bytebuffer.ser
├── TestData-standard.ser
├── TestDataJava11-bytebuffer.ser
├── TestDataJava11-standard.ser
├── TestDataJava17-bytebuffer.ser
├── TestDataJava17-standard.ser
├── TestDataJava8-bytebuffer.ser
└── TestDataJava8-standard.ser
/.github/ISSUE_TEMPLATE/bug_report.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Bug report
3 | about: Create a report to help us improve
4 | title: ''
5 | labels: bug, needs repro
6 | assignees: ''
7 |
8 | ---
9 |
10 | **Describe the bug**
11 | A clear and concise description of what the bug is.
12 |
13 | **To Reproduce**
14 | Provide a minimal reproducible example of the problem, ideally in the form of a runnable test-case.
15 |
16 | **Environment:**
17 | - OS: [e.g. Ubuntu]
18 | - JDK Version: [e.g. 11]
19 | - Kryo Version: [e.g. 5.1.0]
20 |
21 | **Additional context**
22 | Add any other context about the problem here.
23 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/feature_request.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Feature request
3 | about: Suggest an idea for this project
4 | title: ''
5 | labels: feature request
6 | assignees: ''
7 |
8 | ---
9 |
10 | **Is your feature request related to a problem? Please describe.**
11 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
12 |
13 | **Describe the solution you'd like**
14 | A clear and concise description of what you want to happen.
15 |
16 | **Describe alternatives you've considered**
17 | A clear and concise description of any alternative solutions or features you've considered.
18 |
19 | **Additional context**
20 | Add any other context or screenshots about the feature request here.
21 |
--------------------------------------------------------------------------------
/.github/dependabot.yml:
--------------------------------------------------------------------------------
1 | version: 2
2 | updates:
3 | - package-ecosystem: "maven"
4 | directory: "/"
5 | schedule:
6 | interval: "weekly"
7 |
--------------------------------------------------------------------------------
/.github/workflows/ci-workflow.yml:
--------------------------------------------------------------------------------
1 | name: CI
2 |
3 | on:
4 | push:
5 | branches:
6 | - master
7 |
8 | jobs:
9 | build:
10 | runs-on: ubuntu-latest
11 |
12 | env:
13 | PUBLISH_ARTIFACTS: true
14 |
15 | steps:
16 | - uses: actions/checkout@v4
17 | - uses: actions/setup-java@v4
18 | with:
19 | distribution: 'temurin'
20 | java-version: 11
21 | cache: 'maven'
22 |
23 | - name: Build with JDK 11
24 | run: mvn -B install --no-transfer-progress -DskipTests
25 |
26 | - uses: actions/setup-java@v4
27 | with:
28 | distribution: 'temurin'
29 | java-version: 8
30 | - name: Test with JDK 8
31 | run: mvn -v && mvn -B test
32 |
33 | - uses: actions/setup-java@v4
34 | with:
35 | distribution: 'temurin'
36 | java-version: 11
37 | - name: Test with JDK 11
38 | run: mvn -v && mvn -B test
39 |
40 | - uses: actions/setup-java@v4
41 | with:
42 | distribution: 'temurin'
43 | java-version: 17
44 | - name: Test with JDK 17
45 | run: mvn -v && mvn -B test
46 |
47 | - uses: actions/setup-java@v4
48 | with:
49 | distribution: 'temurin'
50 | java-version: 21
51 | - name: Test with JDK 21
52 | run: mvn -v && mvn -B test
53 |
54 | - uses: actions/setup-java@v4
55 | with:
56 | distribution: 'temurin'
57 | java-version: 24
58 | - name: Test with JDK 24
59 | run: mvn -v && mvn -B test
60 |
61 | - name: Set up settings.xml for Sonatype
62 | uses: actions/setup-java@v4
63 | with:
64 | distribution: 'temurin'
65 | java-version: 11
66 |
67 | - name: Publish SNAPSHOT version to Sonatype (we can skip tests, since we only deploy, if the build workflow succeeded)
68 | run: mvn -v && mvn -B -P requireSnapshot --no-transfer-progress -DskipTests deploy --settings build/settings-sonatype.xml
69 | if: env.PUBLISH_ARTIFACTS == 'true'
70 | env:
71 | SONATYPE_USERNAME: yJQKaLoU
72 | SONATYPE_PASSWORD: ${{ secrets.SONATYPE_PW_TOKEN }}
73 |
--------------------------------------------------------------------------------
/.github/workflows/pr-workflow.yml:
--------------------------------------------------------------------------------
1 | name: PR Build
2 |
3 | on: pull_request
4 |
5 | jobs:
6 | build:
7 | runs-on: ubuntu-latest
8 |
9 | steps:
10 | - uses: actions/checkout@v4
11 | - uses: actions/setup-java@v4
12 | with:
13 | distribution: 'temurin'
14 | java-version: 11
15 | cache: 'maven'
16 |
17 | - name: Build with JDK 11
18 | run: mvn -B install --no-transfer-progress -DskipTests
19 |
20 | - uses: actions/setup-java@v4
21 | with:
22 | distribution: 'temurin'
23 | java-version: 8
24 | - name: Test with JDK 8
25 | run: mvn -v && mvn -B test
26 |
27 | - uses: actions/setup-java@v4
28 | with:
29 | distribution: 'temurin'
30 | java-version: 11
31 | - name: Test with JDK 11
32 | run: mvn -v && mvn -B test
33 |
34 | - uses: actions/setup-java@v4
35 | with:
36 | distribution: 'temurin'
37 | java-version: 17
38 | - name: Test with JDK 17
39 | run: mvn -v && mvn -B test
40 |
41 | - uses: actions/setup-java@v4
42 | with:
43 | distribution: 'temurin'
44 | java-version: 21
45 | - name: Test with JDK 21
46 | run: mvn -v && mvn -B test
47 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Temporary Files
2 | *~
3 | .*.swp
4 | .DS_STORE
5 | *.iml
6 |
7 | benchmarks/charts/results
8 | jmh-result.csv
9 | .R*
10 |
11 | bin/
12 | target/
13 |
14 | # Mac specific files
15 | .DS_Store
16 |
17 | # Vim
18 | .*.sw[0-9a-zA-Z]
19 |
20 | # IntelliJ
21 | .idea/
22 | *.iml
23 | *.ipr
24 | *.iws
25 |
26 | # Eclipse
27 | .apt_generated/
28 | .Rproj.user
29 |
--------------------------------------------------------------------------------
/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | Project license(s): 3-Clause BSD License
2 |
3 | * You will only Submit Contributions where You have authored 100% of the content.
4 |
5 | * You will only Submit Contributions to which You have the necessary rights. This means that if You are employed You have received the necessary permissions from Your employer to make the Contributions.
6 |
7 | * Whatever content You Contribute will be under the copyright and license listed in LICENSE.md.
8 |
--------------------------------------------------------------------------------
/LICENSE.md:
--------------------------------------------------------------------------------
1 | Copyright (c) 2008-2025, Nathan Sweet
2 | All rights reserved.
3 |
4 | Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
5 |
6 | * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
7 | * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
8 | * Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
9 |
10 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
11 |
--------------------------------------------------------------------------------
/benchmarks/README.md:
--------------------------------------------------------------------------------
1 | # Kryo Benchmarks
2 |
3 | This subproject contains [JMH](http://openjdk.java.net/projects/code-tools/jmh/) benchmarks for Kryo. The [R/ggplot2 files](https://github.com/EsotericSoftware/kryo/tree/master/benchmarks/charts) are used to generate charts from the benchmark results.
4 |
5 | ## Usage
6 |
7 | ### With Maven
8 |
9 | To run benchmarks execute:
10 | ```
11 | mvn -f benchmarks/pom.xml compile exec:java -Dexec.args="[parameters]"
12 | ```
13 |
14 | Where `[parameters]` should be replaced with JMH parameters.
15 |
16 | ### Without Maven
17 |
18 | This assumes your IDE has compiled Kryo to the `bin` directory, including the benchmarks source and processing of the JMH annotations.
19 | ```
20 | java -cp "bin;lib/*;benchmarks/lib/*" com.esotericsoftware.kryo.benchmarks.KryoBenchmarks [parameters]
21 | ```
22 | Where `[parameters]` should be replaced with JMH parameters.
23 |
24 | ### Parameters
25 |
26 | If no JMH parameters are given, the benchmarks are run with settings only suitable for development (fork 0, short runs). A full list of JMH parameters can be found by running:
27 | ```
28 | java -cp "benchmarks/lib/*" org.openjdk.jmh.Main -h
29 | ```
30 | Or by digging through the [JMH source](http://hg.openjdk.java.net/code-tools/jmh/file/3769055ad883/jmh-core/src/main/java/org/openjdk/jmh/runner/options/CommandLineOptions.java).
31 |
32 | Running without parameters is equivalent to:
33 | ```
34 | -f 0 -wi 1 -i 1 -t 1 -w 1s -r 1s
35 | ```
36 |
37 | The standard parameters to obtain reasonable results are:
38 | ```
39 | -f 4 -wi 5 -i 3 -t 2 -w 2s -r 2s
40 | ```
41 |
42 | To run only specific benchmarks, specify the benchmark class name(s):
43 | ```
44 | -f 4 -wi 5 -i 3 -t 2 -w 2s -r 2s FieldSerializerBenchmark
45 | ```
46 |
47 | To run only a subset of a benchmark, specify the benchmark class name and the methods:
48 | ```
49 | -f 4 -wi 5 -i 3 -t 2 -w 2s -r 2s FieldSerializerBenchmark.field FieldSerializerBenchmark.tagged
50 | ```
51 |
--------------------------------------------------------------------------------
/benchmarks/charts/array.r:
--------------------------------------------------------------------------------
1 |
2 | source("../common.r")
3 |
4 | data = jmhCSV("array.csv")
5 |
6 | data = data[,grep("^(Benchmark|Score|Error|bufferType)$", colnames(data))] # keep only these columns
7 |
8 | g = jmhBarChart(data, "bufferType", "Buffer type", "Operation", "Seconds per 12M operations", "ArrayBenchmark")
9 |
10 | if (!rstudio) png("array.png", 1024, 445)
11 | grid.arrange(g)
12 |
--------------------------------------------------------------------------------
/benchmarks/charts/common.r:
--------------------------------------------------------------------------------
1 |
2 | options(scipen=999)
3 |
4 | rstudio = Sys.getenv("RSTUDIO_USER_IDENTITY") != ""
5 |
6 | loadLibrary = function (name) {
7 | if (!require(name, character.only=TRUE)) {
8 | install.packages(name)
9 | library(name, character.only=TRUE)
10 | }
11 | }
12 | loadLibrary("ggplot2")
13 | loadLibrary("gridExtra")
14 |
15 | jmhCSV = function (path) {
16 | data = read.csv(path, sep=",", header=T)
17 |
18 | # delete all before last dot in benchmark names
19 | data$Benchmark = sub("^.+\\.", "", data$Benchmark)
20 |
21 | # rename Error column
22 | colnames(data)[colnames(data) == "Score.Error..99.9.."] = "Error"
23 |
24 | # remove Param prefix
25 | colnames(data) = sub("Param..", "", colnames(data))
26 |
27 | data
28 | }
29 |
30 | jmhBarChart = function (data, fill, fillLabel, xLabel, yLabel, title=NULL) {
31 | g = ggplot(data, aes(x=Benchmark, y=Score, fill=data[,fill], ymin=Score - Error, ymax=Score + Error))
32 | g = g + geom_bar(stat="identity", position="dodge", color="black", width=0.9)
33 | g = g + geom_errorbar(width=.33, size=.5, position=position_dodge(0.9))
34 | g = g + labs(x=xLabel, y=yLabel, fill=fillLabel) + geom_hline(yintercept=0)
35 | if (!rstudio) {
36 | if (length(title) != 0) g = g + ggtitle(title)
37 | g = g + theme(text=element_text(size=16))
38 | }
39 | g
40 | }
41 |
--------------------------------------------------------------------------------
/benchmarks/charts/fieldSerializer.r:
--------------------------------------------------------------------------------
1 |
2 | source("../common.r")
3 | loadLibrary("gridExtra")
4 |
5 | data = jmhCSV("fieldSerializer.csv")
6 |
7 | data$references = sub("true", "refs", data$references)
8 | data$references = sub("false", "no refs", data$references)
9 |
10 | data$chunked = sub("true", ", chunked", data$chunked)
11 | data$chunked = sub("false", "", data$chunked)
12 |
13 | data$Type = paste(data$references, data$chunked, sep="")
14 |
15 | data = data[,grep("^(Benchmark|Type|Score|Error|objectType)$", colnames(data))] # keep only these columns
16 |
17 | g1 = jmhBarChart(subset(data, objectType == "sample"), "Type", "Serializer settings", "Sample", "Round trips per second")
18 | g2 = jmhBarChart(subset(data, objectType == "media"), "Type", "Serializer settings", "Media", "Round trips per second")
19 |
20 | if (!rstudio) {
21 | g1 = g1 + ggtitle("FieldSerializerBenchmark")
22 | png("fieldSerializer.png", 1024, 890)
23 | }
24 | grid.arrange(g1, g2)
25 |
--------------------------------------------------------------------------------
/benchmarks/charts/string.r:
--------------------------------------------------------------------------------
1 |
2 | source("../common.r")
3 |
4 | data = jmhCSV("string.csv")
5 |
6 | data = data[,grep("^(Benchmark|Score|Error|bufferType)$", colnames(data))] # keep only these columns
7 |
8 | g = jmhBarChart(data, "bufferType", "Buffer type", "Operation", "Seconds per 12M operations", "StringBenchmark")
9 |
10 | if (!rstudio) png("string.png", 1024, 445)
11 | grid.arrange(g)
12 |
--------------------------------------------------------------------------------
/benchmarks/charts/variableEncoding.r:
--------------------------------------------------------------------------------
1 |
2 | source("../common.r")
3 |
4 | data = jmhCSV("variableEncoding.csv")
5 |
6 | data = data[,grep("^(Benchmark|Score|Error|bufferType)$", colnames(data))] # keep only these columns
7 |
8 | g = jmhBarChart(data, "bufferType", "Buffer type", "Operation", "Seconds per 150M operations", "VariableEncodingBenchmark")
9 |
10 | if (!rstudio) png("variableEncoding.png", 1024, 445)
11 | grid.arrange(g)
12 |
--------------------------------------------------------------------------------
/benchmarks/lib/byte-buddy-1.12.7.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/byte-buddy-1.12.7.jar
--------------------------------------------------------------------------------
/benchmarks/lib/commons-cli-1.3.1.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/commons-cli-1.3.1.jar
--------------------------------------------------------------------------------
/benchmarks/lib/commons-math3-3.2.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/commons-math3-3.2.jar
--------------------------------------------------------------------------------
/benchmarks/lib/jmh-core-1.21.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/jmh-core-1.21.jar
--------------------------------------------------------------------------------
/benchmarks/lib/jmh-generator-annprocess-1.21.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/jmh-generator-annprocess-1.21.jar
--------------------------------------------------------------------------------
/benchmarks/lib/jopt-simple-4.6.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/benchmarks/lib/jopt-simple-4.6.jar
--------------------------------------------------------------------------------
/benchmarks/pom.xml:
--------------------------------------------------------------------------------
1 |
2 | 4.0.0
3 |
4 |
5 | com.esotericsoftware
6 | kryo-parent
7 | 5.6.3-SNAPSHOT
8 | ../pom.xml
9 |
10 |
11 | kryo-benchmarks
12 | jar
13 |
14 | Kryo Benchmarks
15 | JMH benchmarks for Kryo.
16 |
17 |
18 | ${basedir}/..
19 | 1.37
20 | 1.17.5
21 | benchmarks
22 | UTF-8
23 |
24 |
25 |
26 |
27 | com.esotericsoftware
28 | kryo
29 | ${project.version}
30 |
31 |
32 | org.openjdk.jmh
33 | jmh-core
34 | ${jmh.version}
35 |
36 |
37 | org.openjdk.jmh
38 | jmh-generator-annprocess
39 | ${jmh.version}
40 | provided
41 |
42 |
43 | net.bytebuddy
44 | byte-buddy
45 | ${byte-buddy.version}
46 |
47 |
48 |
49 |
50 | src/main/java
51 |
52 |
53 | maven-dependency-plugin
54 | 3.8.1
55 |
56 |
57 | build-classpath
58 |
59 | build-classpath
60 |
61 |
62 | runtime
63 | depClasspath
64 |
65 |
66 |
67 |
68 |
69 |
70 | org.codehaus.mojo
71 | exec-maven-plugin
72 | 3.5.0
73 |
74 |
75 | run-tests
76 |
77 | java
78 |
79 |
80 |
81 |
82 | com.esotericsoftware.kryo.benchmarks.KryoBenchmarks
83 |
84 |
85 | java.class.path
86 | ${project.build.outputDirectory}${path.separator}${depClasspath}
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
--------------------------------------------------------------------------------
/benchmarks/run.sh:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env bash
2 |
3 | args="-f 4 -wi 5 -i 3 -t 2 -w 2s -r 2s -rf csv -rff"
4 | jmh="$JAVA_HOME/bin/java -cp ../eclipse/bin;../eclipse/.apt_generated;../lib/*;lib/* com.esotericsoftware.kryo.benchmarks.KryoBenchmarks $args"
5 |
6 | set -ex
7 |
8 | mkdir -p charts/results
9 | $jmh charts/results/fieldSerializer.csv FieldSerializerBenchmark
10 | $jmh charts/results/array.csv ArrayBenchmark
11 | $jmh charts/results/string.csv StringBenchmark
12 | $jmh charts/results/variableEncoding.csv VariableEncodingBenchmark
13 |
14 | cd charts/results
15 | find ../*.r -type f -exec echo "{}:" \; -exec Rscript {} \;
16 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/BigDecimalBenchmark.java:
--------------------------------------------------------------------------------
1 | package com.esotericsoftware.kryo.benchmarks;
2 |
3 | import com.esotericsoftware.kryo.Serializer;
4 | import com.esotericsoftware.kryo.io.Input;
5 | import com.esotericsoftware.kryo.io.Output;
6 | import com.esotericsoftware.kryo.serializers.DefaultSerializers;
7 | import org.openjdk.jmh.annotations.Benchmark;
8 | import org.openjdk.jmh.annotations.Level;
9 | import org.openjdk.jmh.annotations.Param;
10 | import org.openjdk.jmh.annotations.Scope;
11 | import org.openjdk.jmh.annotations.Setup;
12 | import org.openjdk.jmh.annotations.State;
13 | import org.openjdk.jmh.annotations.TearDown;
14 | import org.openjdk.jmh.runner.Runner;
15 | import org.openjdk.jmh.runner.RunnerException;
16 | import org.openjdk.jmh.runner.options.Options;
17 | import org.openjdk.jmh.runner.options.OptionsBuilder;
18 |
19 | import java.math.BigDecimal;
20 |
21 | import static java.lang.Integer.parseInt;
22 | import static java.math.BigDecimal.ONE;
23 | import static java.math.BigDecimal.ZERO;
24 | import static java.util.concurrent.TimeUnit.MICROSECONDS;
25 | import static org.openjdk.jmh.runner.options.TimeValue.seconds;
26 |
27 | public class BigDecimalBenchmark {
28 |
29 | @State(Scope.Thread)
30 | public static class MyState {
31 | final Serializer serializer = new DefaultSerializers.BigDecimalSerializer();
32 |
33 | Output output;
34 | Input input;
35 |
36 | @Param({
37 | "null", "zero", "one", "0",
38 | "2", "10", "max_in_long", "20", // twenty is more than the number of digits in Long.MAX_VALUE
39 | "-2", "-10", "min_in_long", "-20" // twenty is more than the number of digits in Long.MIN_VALUE
40 | })
41 | String numOfDigits = "5";
42 | int scale = 2;
43 |
44 | BigDecimal decimal;
45 |
46 | @Setup(Level.Iteration)
47 | public void setUp() {
48 | decimal = newDecimal(numOfDigits, scale);
49 | output = new Output(2, -1);
50 | serializer.write(null, output, decimal);
51 | input = new Input(output.toBytes());
52 | output.reset();
53 | }
54 |
55 | private static BigDecimal newDecimal(String numOfDigits, int scale) {
56 | switch (numOfDigits) {
57 | case "null": return null;
58 | case "zero": return ZERO;
59 | case "one": return ONE;
60 | case "0": return BigDecimal.valueOf(0, scale);
61 | case "max_in_long": return BigDecimal.valueOf(Long.MAX_VALUE, scale);
62 | case "min_in_long": return BigDecimal.valueOf(Long.MIN_VALUE, scale);
63 | default:
64 | int digits = parseInt(numOfDigits.replace("-", ""));
65 | BigDecimal d = BigDecimal.valueOf(10, 1 - digits).subtract(ONE).scaleByPowerOfTen(-scale); // '9' repeated numOfDigit times
66 | return numOfDigits.charAt(0) != '-' ? d : d.negate();
67 | }
68 | }
69 |
70 | @TearDown(Level.Iteration)
71 | public void tearDown () {
72 | output.close();
73 | input.close();
74 | }
75 | }
76 |
77 | @Benchmark
78 | public byte[] write (MyState state) {
79 | state.output.reset();
80 | state.serializer.write(null, state.output, state.decimal);
81 | return state.output.getBuffer();
82 | }
83 |
84 | @Benchmark
85 | public BigDecimal read (MyState state) {
86 | state.input.reset();
87 | return state.serializer.read(null, state.input, BigDecimal.class);
88 | }
89 |
90 | public static void main (String[] args) throws RunnerException {
91 | final Options opt = new OptionsBuilder()
92 | .include(".*" + BigDecimalBenchmark.class.getSimpleName() + ".*")
93 | .timeUnit(MICROSECONDS)
94 | .warmupIterations(1)
95 | .warmupTime(seconds(1))
96 | .measurementIterations(4)
97 | .measurementTime(seconds(1))
98 | .forks(1)
99 | .build();
100 | new Runner(opt).run();
101 | }
102 | }
103 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/KryoBenchmarks.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks;
21 |
22 | import org.openjdk.jmh.Main;
23 |
24 | public class KryoBenchmarks {
25 | /** To run from command line: $ mvn clean install exec:java -Dexec.args="-f 4 -wi 5 -i 3 -t 2 -w 2s -r 2s"
26 | *
27 | * Fork 0 can be used for debugging/development, eg: -f 0 -wi 1 -i 1 -t 1 -w 1s -r 1s [benchmarkClassName] */
28 | static public void main (String[] args) throws Exception {
29 | if (args.length == 0) {
30 | String commandLine = "-f 0 -wi 1 -i 1 -t 1 -w 1s -r 1s " // For developement only (fork 0, short runs).
31 | // + "-bs 2500000 ArrayBenchmark" //
32 | // + "-rf csv FieldSerializerBenchmark.field FieldSerializerBenchmark.tagged" //
33 | // + "FieldSerializerBenchmark.tagged" //
34 | ;
35 | System.out.println(commandLine);
36 | args = commandLine.split(" ");
37 | }
38 | Main.main(args);
39 | }
40 | }
41 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/data/Image.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.data;
21 |
22 | import com.esotericsoftware.kryo.serializers.TaggedFieldSerializer.Tag;
23 |
24 | public class Image {
25 | @Tag(0) public String uri;
26 | @Tag(1) public String title; // Can be null.
27 | @Tag(2) public int width;
28 | @Tag(3) public int height;
29 | @Tag(4) public Size size;
30 | @Tag(5) public Media media; // Can be null.
31 |
32 | public Image () {
33 | }
34 |
35 | public Image (String uri, String title, int width, int height, Size size, Media media) {
36 | this.height = height;
37 | this.title = title;
38 | this.uri = uri;
39 | this.width = width;
40 | this.size = size;
41 | this.media = media;
42 | }
43 |
44 | public boolean equals (Object o) {
45 | if (this == o) return true;
46 | if (o == null || getClass() != o.getClass()) return false;
47 | Image other = (Image)o;
48 | if (height != other.height) return false;
49 | if (width != other.width) return false;
50 | if (size != other.size) return false;
51 | if (title != null ? !title.equals(other.title) : other.title != null) return false;
52 | if (uri != null ? !uri.equals(other.uri) : other.uri != null) return false;
53 | return true;
54 | }
55 |
56 | public int hashCode () {
57 | int result = uri != null ? uri.hashCode() : 0;
58 | result = 31 * result + (title != null ? title.hashCode() : 0);
59 | result = 31 * result + width;
60 | result = 31 * result + height;
61 | result = 31 * result + (size != null ? size.hashCode() : 0);
62 | return result;
63 | }
64 |
65 | public String toString () {
66 | StringBuilder sb = new StringBuilder();
67 | sb.append("[Image ");
68 | sb.append("uri=").append(uri);
69 | sb.append(", title=").append(title);
70 | sb.append(", width=").append(width);
71 | sb.append(", height=").append(height);
72 | sb.append(", size=").append(size);
73 | sb.append("]");
74 | return sb.toString();
75 | }
76 |
77 | static public enum Size {
78 | SMALL, LARGE
79 | }
80 | }
81 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/data/MediaContent.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.data;
21 |
22 | import com.esotericsoftware.kryo.benchmarks.data.Image.Size;
23 | import com.esotericsoftware.kryo.benchmarks.data.Media.Player;
24 | import com.esotericsoftware.kryo.serializers.TaggedFieldSerializer.Tag;
25 |
26 | import java.util.ArrayList;
27 | import java.util.List;
28 |
29 | public class MediaContent implements java.io.Serializable {
30 | @Tag(0) public Media media;
31 | @Tag(1) public List images;
32 |
33 | public MediaContent () {
34 | }
35 |
36 | public MediaContent (Media media, List images) {
37 | this.media = media;
38 | this.images = images;
39 | }
40 |
41 | public MediaContent populate (boolean circularReference) {
42 | media = new Media();
43 | media.uri = "http://javaone.com/keynote.ogg";
44 | media.width = 641;
45 | media.height = 481;
46 | media.format = "video/theora\u1234";
47 | media.duration = 18000001;
48 | media.size = 58982401;
49 | media.persons = new ArrayList();
50 | media.persons.add("Bill Gates, Jr.");
51 | media.persons.add("Steven Jobs");
52 | media.player = Player.FLASH;
53 | media.copyright = "Copyright (c) 2009, Scooby Dooby Doo";
54 | images = new ArrayList();
55 | Media media = circularReference ? this.media : null;
56 | images.add(new Image("http://javaone.com/keynote_huge.jpg", "Javaone Keynote\u1234", 32000, 24000, Size.LARGE, media));
57 | images.add(new Image("http://javaone.com/keynote_large.jpg", null, 1024, 768, Size.LARGE, media));
58 | images.add(new Image("http://javaone.com/keynote_small.jpg", null, 320, 240, Size.SMALL, media));
59 | return this;
60 | }
61 |
62 | public boolean equals (Object o) {
63 | if (this == o) return true;
64 | if (o == null || getClass() != o.getClass()) return false;
65 | MediaContent other = (MediaContent)o;
66 | if (images != null ? !images.equals(other.images) : other.images != null) return false;
67 | if (media != null ? !media.equals(other.media) : other.media != null) return false;
68 | return true;
69 | }
70 |
71 | public int hashCode () {
72 | int result = media != null ? media.hashCode() : 0;
73 | result = 31 * result + (images != null ? images.hashCode() : 0);
74 | return result;
75 | }
76 |
77 | public String toString () {
78 | StringBuilder sb = new StringBuilder();
79 | sb.append("[MediaContent: ");
80 | sb.append("media=").append(media);
81 | sb.append(", images=").append(images);
82 | sb.append("]");
83 | return sb.toString();
84 | }
85 | }
86 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/io/ArrayBenchmark.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.io;
21 |
22 | import org.openjdk.jmh.annotations.Benchmark;
23 | import org.openjdk.jmh.annotations.BenchmarkMode;
24 | import org.openjdk.jmh.annotations.Measurement;
25 | import org.openjdk.jmh.annotations.Mode;
26 | import org.openjdk.jmh.annotations.Scope;
27 | import org.openjdk.jmh.annotations.State;
28 |
29 | @BenchmarkMode(Mode.SingleShotTime)
30 | @Measurement(batchSize = 12000000)
31 | public class ArrayBenchmark {
32 | @Benchmark
33 | public void writeInts (WriteIntsState state) {
34 | state.reset();
35 | state.output.writeInts(state.ints, 0, state.ints.length);
36 | }
37 |
38 | @Benchmark
39 | public void readInts (ReadIntsState state) {
40 | state.reset();
41 | state.input.readInts(state.ints.length);
42 | }
43 |
44 | @Benchmark
45 | public void writeVarInts (WriteIntsState state) {
46 | state.reset();
47 | state.output.writeInts(state.ints, 0, state.ints.length, true);
48 | }
49 |
50 | @Benchmark
51 | public void readVarInts (ReadIntsState state) {
52 | state.reset();
53 | state.input.readInts(state.ints.length, true);
54 | }
55 |
56 | @Benchmark
57 | public void writeLongs (WriteLongsState state) {
58 | state.reset();
59 | state.output.writeLongs(state.longs, 0, state.longs.length);
60 | }
61 |
62 | @Benchmark
63 | public void readLongs (ReadLongsState state) {
64 | state.reset();
65 | state.input.readLongs(state.longs.length);
66 | }
67 |
68 | @Benchmark
69 | public void writeVarLongs (WriteLongsState state) {
70 | state.reset();
71 | state.output.writeLongs(state.longs, 0, state.longs.length, true);
72 | }
73 |
74 | @Benchmark
75 | public void readVarLongs (ReadLongsState state) {
76 | state.reset();
77 | state.input.readLongs(state.longs.length, true);
78 | }
79 |
80 | //
81 |
82 | @State(Scope.Thread)
83 | static public class WriteIntsState extends InputOutputState {
84 | public int[] ints = {0, 1, 2, 3, 4, 5, 63, 64, 65, 127, 128, 129, 4000, 5000, 6000, 16000, 32000, 256000, 1024000, -1, -2,
85 | -3, -4, Integer.MIN_VALUE, Integer.MAX_VALUE};
86 | }
87 |
88 | @State(Scope.Thread)
89 | static public class ReadIntsState extends WriteIntsState {
90 | public void setup () {
91 | super.setup();
92 | new ArrayBenchmark().writeInts(this);
93 | }
94 | }
95 |
96 | @State(Scope.Thread)
97 | static public class WriteLongsState extends InputOutputState {
98 | public long[] longs = {0, 1, 2, 3, 4, 5, 63, 64, 65, 127, 128, 129, 4000, 5000, 6000, 16000, 32000, 256000, 1024000, -1, -2,
99 | -3, -4, Integer.MIN_VALUE, Integer.MAX_VALUE, Long.MIN_VALUE, Long.MAX_VALUE, 9999999999l};
100 |
101 | public void setup () {
102 | super.setup();
103 | new ArrayBenchmark().writeLongs(this);
104 | }
105 | }
106 |
107 | @State(Scope.Thread)
108 | static public class ReadLongsState extends WriteLongsState {
109 | public void setup () {
110 | super.setup();
111 | new ArrayBenchmark().writeLongs(this);
112 | }
113 | }
114 | }
115 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/io/InputOutputState.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.io;
21 |
22 | import com.esotericsoftware.kryo.io.ByteBufferInput;
23 | import com.esotericsoftware.kryo.io.ByteBufferOutput;
24 | import com.esotericsoftware.kryo.io.Input;
25 | import com.esotericsoftware.kryo.io.Output;
26 | import com.esotericsoftware.kryo.unsafe.UnsafeByteBufferInput;
27 | import com.esotericsoftware.kryo.unsafe.UnsafeByteBufferOutput;
28 | import com.esotericsoftware.kryo.unsafe.UnsafeInput;
29 | import com.esotericsoftware.kryo.unsafe.UnsafeOutput;
30 |
31 | import org.openjdk.jmh.annotations.Level;
32 | import org.openjdk.jmh.annotations.Param;
33 | import org.openjdk.jmh.annotations.Scope;
34 | import org.openjdk.jmh.annotations.Setup;
35 | import org.openjdk.jmh.annotations.State;
36 |
37 | @State(Scope.Thread)
38 | public class InputOutputState {
39 | @Param() public InputOutputState.BufferType bufferType;
40 |
41 | Output output;
42 | Input input;
43 |
44 | @Setup(Level.Trial)
45 | public void setup () {
46 | switch (bufferType) {
47 | case array:
48 | output = new Output(1024 * 512);
49 | input = new Input(output.getBuffer());
50 | break;
51 | case unsafeArray:
52 | output = new UnsafeOutput(1024 * 512);
53 | input = new UnsafeInput(output.getBuffer());
54 | break;
55 | case byteBuffer:
56 | output = new ByteBufferOutput(1024 * 512);
57 | input = new ByteBufferInput(((ByteBufferOutput)output).getByteBuffer());
58 | break;
59 | case unsafeByteBuffer:
60 | output = new UnsafeByteBufferOutput(1024 * 512);
61 | input = new UnsafeByteBufferInput(((UnsafeByteBufferOutput)output).getByteBuffer());
62 | break;
63 | }
64 | }
65 |
66 | public void reset () {
67 | input.setPosition(0);
68 | output.setPosition(0);
69 | }
70 |
71 | static public enum BufferType {
72 | array, unsafeArray, byteBuffer, unsafeByteBuffer
73 | }
74 | }
75 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/io/StringBenchmark.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.io;
21 |
22 | import org.openjdk.jmh.annotations.Benchmark;
23 | import org.openjdk.jmh.annotations.BenchmarkMode;
24 | import org.openjdk.jmh.annotations.Measurement;
25 | import org.openjdk.jmh.annotations.Mode;
26 | import org.openjdk.jmh.annotations.Scope;
27 | import org.openjdk.jmh.annotations.State;
28 |
29 | @BenchmarkMode(Mode.SingleShotTime)
30 | @Measurement(batchSize = 12000000)
31 | public class StringBenchmark {
32 | @Benchmark
33 | public void writeString (InputOutputState state) {
34 | state.reset();
35 | state.output.writeString("abc0123456789"); // Short enough to be detected as ASCII.
36 | }
37 |
38 | @Benchmark
39 | public String readString (ReadString state) {
40 | state.reset();
41 | return state.input.readString();
42 | }
43 |
44 | @Benchmark
45 | public void writeStringLong (InputOutputState state) {
46 | state.reset();
47 | state.output.writeString(
48 | "abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789");
49 | }
50 |
51 | @Benchmark
52 | public String readStringLong (ReadStringLong state) {
53 | state.reset();
54 | return state.input.readString();
55 | }
56 |
57 | @Benchmark
58 | public void writeAsciiLong (InputOutputState state) {
59 | state.reset();
60 | state.output.writeAscii(
61 | "abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789abcdefghijklmnopqrstuvwxyz0123456789");
62 | }
63 |
64 | @Benchmark
65 | public String readAsciiLong (ReadAsciiLong state) {
66 | state.reset();
67 | return state.input.readString();
68 | }
69 |
70 | //
71 |
72 | @State(Scope.Thread)
73 | static public class ReadString extends InputOutputState {
74 | public void setup () {
75 | super.setup();
76 | new StringBenchmark().writeString(this);
77 | }
78 | }
79 |
80 | @State(Scope.Thread)
81 | static public class ReadStringLong extends InputOutputState {
82 | public void setup () {
83 | super.setup();
84 | new StringBenchmark().writeStringLong(this);
85 | }
86 | }
87 |
88 | @State(Scope.Thread)
89 | static public class ReadAsciiLong extends InputOutputState {
90 | public void setup () {
91 | super.setup();
92 | new StringBenchmark().writeAsciiLong(this);
93 | }
94 | }
95 | }
96 |
--------------------------------------------------------------------------------
/benchmarks/src/main/java/com/esotericsoftware/kryo/benchmarks/io/VariableEncodingBenchmark.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.benchmarks.io;
21 |
22 | import org.openjdk.jmh.annotations.Benchmark;
23 | import org.openjdk.jmh.annotations.BenchmarkMode;
24 | import org.openjdk.jmh.annotations.Measurement;
25 | import org.openjdk.jmh.annotations.Mode;
26 | import org.openjdk.jmh.annotations.Scope;
27 | import org.openjdk.jmh.annotations.State;
28 |
29 | @BenchmarkMode(Mode.SingleShotTime)
30 | @Measurement(batchSize = 150000000)
31 | public class VariableEncodingBenchmark {
32 | @Benchmark
33 | public void writeInt (InputOutputState state) {
34 | state.reset();
35 | state.output.writeInt(1234);
36 | }
37 |
38 | @Benchmark
39 | public void readInt (ReadInt state) {
40 | state.reset();
41 | state.input.readInt();
42 | }
43 |
44 | @Benchmark
45 | public void writeVarInt (InputOutputState state) {
46 | state.reset();
47 | state.output.writeVarInt(1234, true);
48 | }
49 |
50 | @Benchmark
51 | public int readVarInt (ReadVarInt state) {
52 | state.reset();
53 | return state.input.readVarInt(true);
54 | }
55 |
56 | @Benchmark
57 | public void writeLong (InputOutputState state) {
58 | state.reset();
59 | state.output.writeLong(12341234);
60 | }
61 |
62 | @Benchmark
63 | public long readLong (ReadLong state) {
64 | state.reset();
65 | return state.input.readLong();
66 | }
67 |
68 | @Benchmark
69 | public void writeVarLong (InputOutputState state) {
70 | state.reset();
71 | state.output.writeVarLong(12341234, true);
72 | }
73 |
74 | @Benchmark
75 | public long readVarLong (ReadLong state) {
76 | state.reset();
77 | return state.input.readVarLong(true);
78 | }
79 |
80 | //
81 |
82 | @State(Scope.Thread)
83 | static public class ReadInt extends InputOutputState {
84 | public ReadInt () {
85 | new VariableEncodingBenchmark().writeInt(this);
86 | }
87 | }
88 |
89 | @State(Scope.Thread)
90 | static public class ReadVarInt extends InputOutputState {
91 | public ReadVarInt () {
92 | new VariableEncodingBenchmark().readVarInt(this);
93 | }
94 | }
95 |
96 | @State(Scope.Thread)
97 | static public class ReadLong extends InputOutputState {
98 | public ReadLong () {
99 | new VariableEncodingBenchmark().writeLong(this);
100 | }
101 | }
102 |
103 | @State(Scope.Thread)
104 | static public class ReadVarLong extends InputOutputState {
105 | public ReadVarLong () {
106 | new VariableEncodingBenchmark().writeVarLong(this);
107 | }
108 | }
109 | }
110 |
--------------------------------------------------------------------------------
/build/assembly-all.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | all
4 |
5 | zip
6 |
7 |
8 |
9 | .
10 |
11 | README*
12 | LICENCE*
13 | CHANGES*
14 | lib/
15 | src/
16 |
17 |
18 |
19 | target
20 |
21 |
22 | *.jar
23 |
24 |
25 |
26 |
27 |
--------------------------------------------------------------------------------
/build/commons-lang-2.6.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/build/commons-lang-2.6.jar
--------------------------------------------------------------------------------
/build/junit-platform-console-standalone-1.8.2.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/build/junit-platform-console-standalone-1.8.2.jar
--------------------------------------------------------------------------------
/build/settings-sonatype.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | sonatype-nexus-snapshots
5 | ${env.SONATYPE_USERNAME}
6 | ${env.SONATYPE_PASSWORD}
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/compat_reports/kryo-2.22.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/compat_reports/kryo-2.22.jar
--------------------------------------------------------------------------------
/compat_reports/kryo-2.23.0.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/compat_reports/kryo-2.23.0.jar
--------------------------------------------------------------------------------
/compat_reports/skip-classes.txt:
--------------------------------------------------------------------------------
1 | com.esotericsoftware.kryo.Generics
2 |
--------------------------------------------------------------------------------
/eclipse/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
21 |
22 |
23 |
24 |
25 |
26 |
27 |
28 |
29 |
--------------------------------------------------------------------------------
/eclipse/.factorypath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
--------------------------------------------------------------------------------
/eclipse/.importorder:
--------------------------------------------------------------------------------
1 | # Organize Import Order
2 | # Import this file in Window -> Preferences -> Java -> Code Style -> Organize Imports -> Import...
3 | 0=\#
4 | 1=com.esotericsoftware
5 | 2=java
6 | 3=javax
7 | 4=org
8 | 5=
9 |
--------------------------------------------------------------------------------
/eclipse/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | kryo
4 |
5 |
6 |
7 |
8 |
9 | org.eclipse.jdt.core.javabuilder
10 |
11 |
12 |
13 |
14 |
15 | org.eclipse.jdt.core.javanature
16 |
17 |
18 |
19 | benchmarks
20 | 2
21 | PARENT-1-PROJECT_LOC/benchmarks
22 |
23 |
24 | build
25 | 2
26 | PARENT-1-PROJECT_LOC/build
27 |
28 |
29 | lib
30 | 2
31 | PARENT-1-PROJECT_LOC/lib
32 |
33 |
34 | src
35 | 2
36 | PARENT-1-PROJECT_LOC/src
37 |
38 |
39 | test
40 | 2
41 | PARENT-1-PROJECT_LOC/test
42 |
43 |
44 |
45 |
--------------------------------------------------------------------------------
/eclipse/.settings/org.eclipse.jdt.apt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.apt.aptEnabled=true
3 | org.eclipse.jdt.apt.genSrcDir=.apt_generated
4 | org.eclipse.jdt.apt.genTestSrcDir=.apt_generated_tests
5 | org.eclipse.jdt.apt.reconcileEnabled=true
6 |
--------------------------------------------------------------------------------
/eclipse/.settings/org.eclipse.jdt.ui.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | formatter_profile=_libgdx
3 | formatter_settings_version=12
4 |
--------------------------------------------------------------------------------
/lib/minlog-1.3.1.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/lib/minlog-1.3.1.jar
--------------------------------------------------------------------------------
/lib/objenesis-3.2.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/lib/objenesis-3.2.jar
--------------------------------------------------------------------------------
/lib/reflectasm-1.11.9.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/EsotericSoftware/kryo/23fbc2d531b9d7fe2408ad825fbc9f27b42f5936/lib/reflectasm-1.11.9.jar
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/ClassResolver.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | import com.esotericsoftware.kryo.io.Input;
23 | import com.esotericsoftware.kryo.io.Output;
24 |
25 | /** Handles class registration, writing class identifiers to bytes, and reading class identifiers from bytes.
26 | * @author Nathan Sweet */
27 | public interface ClassResolver {
28 | /** Sets the Kryo instance that this ClassResolver will be used for. This is called automatically by Kryo. */
29 | public void setKryo (Kryo kryo);
30 |
31 | /** Stores the specified registration.
32 | * @see Kryo#register(Registration) */
33 | public Registration register (Registration registration);
34 |
35 | /** Removes the registration for the specified ID.
36 | * @return May be null if the class ID was not registered. */
37 | public Registration unregister (int classID);
38 |
39 | /** Called when an unregistered type is encountered and {@link Kryo#setRegistrationRequired(boolean)} is false. */
40 | public Registration registerImplicit (Class type);
41 |
42 | /** Returns the registration for the specified class, or null if the class is not registered. */
43 | public Registration getRegistration (Class type);
44 |
45 | /** Returns the registration for the specified ID, or null if no class is registered with that ID. */
46 | public Registration getRegistration (int classID);
47 |
48 | /** Writes a class and returns its registration.
49 | * @param type May be null.
50 | * @return Will be null if type is null. */
51 | public Registration writeClass (Output output, Class type);
52 |
53 | /** Reads a class and returns its registration.
54 | * @return May be null. */
55 | public Registration readClass (Input input);
56 |
57 | /** Called by {@link Kryo#reset()}. */
58 | public void reset ();
59 | }
60 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/DefaultSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | import com.esotericsoftware.kryo.SerializerFactory.ReflectionSerializerFactory;
23 |
24 | import java.lang.annotation.ElementType;
25 | import java.lang.annotation.Retention;
26 | import java.lang.annotation.RetentionPolicy;
27 | import java.lang.annotation.Target;
28 |
29 | /** Sets the default serializer to use for the annotated class. The specified Serializer class must have a constructor taking a
30 | * Kryo instance and a class, a Kryo instance, a class, or no arguments.
31 | * @see Kryo#register(Class)
32 | * @author Nathan Sweet */
33 | @Retention(RetentionPolicy.RUNTIME)
34 | @Target(ElementType.TYPE)
35 | public @interface DefaultSerializer {
36 | /** The serializer class to serialize the annotated type, which will be created by the {@link #serializerFactory()}. Can be
37 | * omitted if the serializer factory knows what type of serializer to create. */
38 | Class extends Serializer> value() default Serializer.class;
39 |
40 | /** The factory used to create the serializer. */
41 | Class extends SerializerFactory> serializerFactory() default ReflectionSerializerFactory.class;
42 | }
43 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/KryoCopyable.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | /** Allows implementing classes to perform their own copying. Hand written copying can be more efficient in some cases.
23 | *
24 | * This method is used instead of the registered serializer's {@link Serializer#copy(Kryo, Object)} method.
25 | * @author Nathan Sweet */
26 | public interface KryoCopyable {
27 | /** Returns a copy that has the same values as this object. Before Kryo can be used to copy child objects,
28 | * {@link Kryo#reference(Object)} must be called with the copy to ensure it can be referenced by the child objects.
29 | * @see Serializer#copy(Kryo, Object) */
30 | public T copy (Kryo kryo);
31 | }
32 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/KryoException.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | /** General Kryo RuntimeException.
23 | * @author Nathan Sweet */
24 | public class KryoException extends RuntimeException {
25 | private StringBuffer trace;
26 |
27 | public KryoException () {
28 | super();
29 | }
30 |
31 | public KryoException (String message, Throwable cause) {
32 | super(message, cause);
33 | }
34 |
35 | public KryoException (String message) {
36 | super(message);
37 | }
38 |
39 | public KryoException (Throwable cause) {
40 | super(cause);
41 | }
42 |
43 | public String getMessage () {
44 | if (trace == null) return super.getMessage();
45 | StringBuffer buffer = new StringBuffer(512);
46 | buffer.append(super.getMessage());
47 | if (buffer.length() > 0) buffer.append('\n');
48 | buffer.append("Serialization trace:");
49 | buffer.append(trace);
50 | return buffer.toString();
51 | }
52 |
53 | /** Adds information to the exception message about where in the the object graph serialization failure occurred.
54 | * {@link Serializer Serializers} can catch {@link KryoException}, add trace information, and rethrow the exception. */
55 | public void addTrace (String info) {
56 | if (info == null) throw new IllegalArgumentException("info cannot be null.");
57 | if (trace == null) trace = new StringBuffer(512);
58 | trace.append('\n');
59 | trace.append(info);
60 | }
61 | }
62 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/KryoSerializable.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | import com.esotericsoftware.kryo.io.Input;
23 | import com.esotericsoftware.kryo.io.Output;
24 | import com.esotericsoftware.kryo.serializers.DefaultSerializers.KryoSerializableSerializer;
25 |
26 | /** Allows implementing classes to perform their own serialization. Hand written serialization can be more efficient in some
27 | * cases.
28 | *
29 | * The default serializer for KryoSerializable is {@link KryoSerializableSerializer}, which uses {@link Kryo#newInstance(Class)}
30 | * to construct the class.
31 | * @author Nathan Sweet */
32 | public interface KryoSerializable {
33 | public void write (Kryo kryo, Output output);
34 |
35 | public void read (Kryo kryo, Input input);
36 | }
37 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/ReferenceResolver.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | /** When references are enabled, this tracks objects that have already been read or written, provides an ID for objects that are
23 | * written, and looks up by ID objects that have been read.
24 | * @author Nathan Sweet */
25 | public interface ReferenceResolver {
26 | /** Sets the Kryo instance that this ClassResolver will be used for. This is called automatically by Kryo. */
27 | public void setKryo (Kryo kryo);
28 |
29 | /** Returns an ID for the object if it has been written previously, otherwise returns -1. */
30 | public int getWrittenId (Object object);
31 |
32 | /** Returns a new ID for an object that is being written for the first time.
33 | * @return The ID, which is stored more efficiently if it is positive and must not be -1 or -2. */
34 | public int addWrittenObject (Object object);
35 |
36 | /** Reserves the ID for the next object that will be read. This is called only the first time an object is encountered.
37 | * @param type The type of object that will be read.
38 | * @return The ID, which is stored more efficiently if it is positive and must not be -1 or -2. */
39 | public int nextReadId (Class type);
40 |
41 | /** Sets the ID for an object that has been read.
42 | * @param id The ID from {@link #nextReadId(Class)}. */
43 | public void setReadObject (int id, Object object);
44 |
45 | /** Returns the object for the specified ID. The ID and object are guaranteed to have been previously passed in a call to
46 | * {@link #setReadObject(int, Object)}. */
47 | public Object getReadObject (Class type, int id);
48 |
49 | /** Called by {@link Kryo#reset()}. */
50 | public void reset ();
51 |
52 | /** Returns true if references will be written for the specified type.
53 | * @param type Will never be a primitive type, but may be a primitive type wrapper. */
54 | public boolean useReferences (Class type);
55 | }
56 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/Registration.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo;
21 |
22 | import static com.esotericsoftware.kryo.util.Util.*;
23 | import static com.esotericsoftware.minlog.Log.*;
24 |
25 | import org.objenesis.instantiator.ObjectInstantiator;
26 |
27 | /** Describes the {@link Serializer} and class ID to use for a class.
28 | * @author Nathan Sweet */
29 | public class Registration {
30 | private final Class type;
31 | private final boolean typeNameAscii;
32 | private final int id;
33 | private Serializer serializer;
34 | private ObjectInstantiator instantiator;
35 |
36 | public Registration (Class type, Serializer serializer, int id) {
37 | if (type == null) throw new IllegalArgumentException("type cannot be null.");
38 | if (serializer == null) throw new IllegalArgumentException("serializer cannot be null.");
39 | this.type = type;
40 | this.serializer = serializer;
41 | this.id = id;
42 | typeNameAscii = isAscii(type.getName());
43 | }
44 |
45 | public Class getType () {
46 | return type;
47 | }
48 |
49 | public boolean isTypeNameAscii () {
50 | return typeNameAscii;
51 | }
52 |
53 | /** Returns the registered class ID.
54 | * @see Kryo#register(Class) */
55 | public int getId () {
56 | return id;
57 | }
58 |
59 | public Serializer getSerializer () {
60 | return serializer;
61 | }
62 |
63 | public void setSerializer (Serializer serializer) {
64 | if (serializer == null) throw new IllegalArgumentException("serializer cannot be null.");
65 | this.serializer = serializer;
66 | if (TRACE) trace("kryo", "Update registered serializer: " + type.getName() + " (" + serializer.getClass().getName() + ")");
67 | }
68 |
69 | /** @return May be null if not yet set. */
70 | public ObjectInstantiator getInstantiator () {
71 | return instantiator;
72 | }
73 |
74 | /** Sets the instantiator that will create a new instance of the type in {@link Kryo#newInstance(Class)}. */
75 | public void setInstantiator (ObjectInstantiator instantiator) {
76 | if (instantiator == null) throw new IllegalArgumentException("instantiator cannot be null.");
77 | this.instantiator = instantiator;
78 | }
79 |
80 | public String toString () {
81 | return "[" + id + ", " + className(type) + "]";
82 | }
83 | }
84 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/ByteBufferInputStream.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import java.io.IOException;
23 | import java.io.InputStream;
24 | import java.nio.Buffer;
25 | import java.nio.ByteBuffer;
26 |
27 | /** An InputStream whose source is a {@link ByteBuffer}.
28 | * @author Nathan Sweet */
29 | public class ByteBufferInputStream extends InputStream {
30 | private ByteBuffer byteBuffer;
31 |
32 | /** Creates an uninitialized stream that cannot be used until {@link #setByteBuffer(ByteBuffer)} is called. */
33 | public ByteBufferInputStream () {
34 | }
35 |
36 | /** Creates a stream with a new non-direct buffer of the specified size. The position and limit of the buffer is zero. */
37 | public ByteBufferInputStream (int bufferSize) {
38 | this(ByteBuffer.allocate(bufferSize));
39 | flipBuffer(byteBuffer);
40 | }
41 |
42 | public ByteBufferInputStream (ByteBuffer byteBuffer) {
43 | this.byteBuffer = byteBuffer;
44 | }
45 |
46 | public ByteBuffer getByteBuffer () {
47 | return byteBuffer;
48 | }
49 |
50 | public void setByteBuffer (ByteBuffer byteBuffer) {
51 | this.byteBuffer = byteBuffer;
52 | }
53 |
54 | public int read () throws IOException {
55 | if (!byteBuffer.hasRemaining()) return -1;
56 | return byteBuffer.get() & 0xFF;
57 | }
58 |
59 | public int read (byte[] bytes, int offset, int length) throws IOException {
60 | if (length == 0) return 0;
61 | int count = Math.min(byteBuffer.remaining(), length);
62 | if (count == 0) return -1;
63 | byteBuffer.get(bytes, offset, count);
64 | return count;
65 | }
66 |
67 | public int available () throws IOException {
68 | return byteBuffer.remaining();
69 | }
70 |
71 | private void flipBuffer (Buffer buffer) {
72 | buffer.flip();
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/ByteBufferOutputStream.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import java.io.IOException;
23 | import java.io.OutputStream;
24 | import java.nio.ByteBuffer;
25 |
26 | /** An OutputStream whose target is a {@link ByteBuffer}. If bytes would be written that would overflow the buffer,
27 | * {@link #flush()} is called. Subclasses can override flush to empty the buffer.
28 | * @author Nathan Sweet */
29 | public class ByteBufferOutputStream extends OutputStream {
30 | private ByteBuffer byteBuffer;
31 |
32 | /** Creates an uninitialized stream that cannot be used until {@link #setByteBuffer(ByteBuffer)} is called. */
33 | public ByteBufferOutputStream () {
34 | }
35 |
36 | /** Creates a stream with a new non-direct buffer of the specified size. */
37 | public ByteBufferOutputStream (int bufferSize) {
38 | this(ByteBuffer.allocate(bufferSize));
39 | }
40 |
41 | public ByteBufferOutputStream (ByteBuffer byteBuffer) {
42 | this.byteBuffer = byteBuffer;
43 | }
44 |
45 | public ByteBuffer getByteBuffer () {
46 | return byteBuffer;
47 | }
48 |
49 | public void setByteBuffer (ByteBuffer byteBuffer) {
50 | this.byteBuffer = byteBuffer;
51 | }
52 |
53 | public void write (int b) throws IOException {
54 | if (!byteBuffer.hasRemaining()) flush();
55 | byteBuffer.put((byte)b);
56 | }
57 |
58 | public void write (byte[] bytes, int offset, int length) throws IOException {
59 | if (byteBuffer.remaining() < length) flush();
60 | byteBuffer.put(bytes, offset, length);
61 | }
62 | }
63 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/InputChunked.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import static com.esotericsoftware.minlog.Log.*;
23 |
24 | import com.esotericsoftware.kryo.KryoException;
25 |
26 | import java.io.IOException;
27 | import java.io.InputStream;
28 |
29 | /** An {@link Input} that reads lengths and chunks of data from another OutputStream, allowing chunks to be skipped.
30 | * @author Nathan Sweet */
31 | public class InputChunked extends Input {
32 | private int chunkSize = -1;
33 |
34 | /** @see Input#Input() */
35 | public InputChunked () {
36 | super();
37 | }
38 |
39 | /** @see Input#Input(int) */
40 | public InputChunked (int bufferSize) {
41 | super(bufferSize);
42 | }
43 |
44 | /** @see Input#Input(InputStream) */
45 | public InputChunked (InputStream inputStream) {
46 | super(inputStream);
47 | }
48 |
49 | /** @see Input#Input(InputStream, int) */
50 | public InputChunked (InputStream inputStream, int bufferSize) {
51 | super(inputStream, bufferSize);
52 | }
53 |
54 | public void setInputStream (InputStream inputStream) {
55 | super.setInputStream(inputStream);
56 | chunkSize = -1;
57 | }
58 |
59 | public void setBuffer (byte[] bytes, int offset, int count) {
60 | super.setBuffer(bytes, offset, count);
61 | chunkSize = -1;
62 | }
63 |
64 | public void reset () {
65 | super.reset();
66 | chunkSize = -1;
67 | }
68 |
69 | protected int fill (byte[] buffer, int offset, int count) throws KryoException {
70 | if (chunkSize == -1) { // No current chunk, expect a new chunk.
71 | if (!readChunkSize()) return -1;
72 | } else if (chunkSize == 0) // End of chunk.
73 | return -1;
74 | int actual = super.fill(buffer, offset, Math.min(chunkSize, count));
75 | chunkSize -= actual;
76 | if (chunkSize == 0 && !readChunkSize()) return -1;
77 | return actual;
78 | }
79 |
80 | /** @return false if the end of the stream was reached. */
81 | private boolean readChunkSize () {
82 | try {
83 | InputStream inputStream = getInputStream();
84 | for (int offset = 0, result = 0; offset < 32; offset += 7) {
85 | int b = inputStream.read();
86 | if (b == -1) return false;
87 | result |= (b & 0x7F) << offset;
88 | if ((b & 0x80) == 0) {
89 | chunkSize = result;
90 | if (TRACE && chunkSize > 0) trace("kryo", "Read chunk: " + chunkSize);
91 | return true;
92 | }
93 | }
94 | } catch (IOException ex) {
95 | throw new KryoException("Unable to read chunk size.", ex);
96 | }
97 | throw new KryoException("Unable to read chunk size: malformed integer");
98 | }
99 |
100 | /** Advances the stream to the next chunk. InputChunked will appear to hit the end of the data until this method is called. */
101 | public void nextChunk () {
102 | position = limit; // Underflow resets the position to 0. Ensure we are at the end of the chunk.
103 | if (chunkSize == -1) readChunkSize(); // No current chunk, expect a new chunk.
104 | while (chunkSize > 0)
105 | skip(chunkSize);
106 | chunkSize = -1;
107 | if (TRACE) trace("kryo", "Next chunk.");
108 | }
109 | }
110 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoBufferOverflowException.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import com.esotericsoftware.kryo.KryoException;
23 |
24 | public class KryoBufferOverflowException extends KryoException {
25 |
26 | public KryoBufferOverflowException () {
27 | super();
28 | }
29 |
30 | public KryoBufferOverflowException (String message, Throwable cause) {
31 | super(message, cause);
32 | }
33 |
34 | public KryoBufferOverflowException (String message) {
35 | super(message);
36 | }
37 |
38 | public KryoBufferOverflowException (Throwable cause) {
39 | super(cause);
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoBufferUnderflowException.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import com.esotericsoftware.kryo.KryoException;
23 |
24 | public class KryoBufferUnderflowException extends KryoException {
25 |
26 | public KryoBufferUnderflowException () {
27 | super();
28 | }
29 |
30 | public KryoBufferUnderflowException (String message, Throwable cause) {
31 | super(message, cause);
32 | }
33 |
34 | public KryoBufferUnderflowException (String message) {
35 | super(message);
36 | }
37 |
38 | public KryoBufferUnderflowException (Throwable cause) {
39 | super(cause);
40 | }
41 | }
42 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoDataInput.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import com.esotericsoftware.kryo.KryoException;
23 |
24 | import java.io.DataInput;
25 | import java.io.EOFException;
26 | import java.io.IOException;
27 |
28 | /** A {@link DataInput} which reads from an {@link Input}. {@link #readLine()} is unsupported. Other methods behave slightly
29 | * differently, eg {@link #readUTF()} may return a null string.
30 | * @author Robert DiFalco */
31 | public class KryoDataInput implements DataInput, AutoCloseable {
32 | protected Input input;
33 |
34 | public KryoDataInput (Input input) {
35 | this.input = input;
36 | }
37 |
38 | public void setInput (Input input) {
39 | this.input = input;
40 | }
41 |
42 | public void readFully (byte[] b) throws IOException {
43 | readFully(b, 0, b.length);
44 | }
45 |
46 | public void readFully (byte[] b, int off, int len) throws IOException {
47 | try {
48 | input.readBytes(b, off, len);
49 | } catch (KryoException ex) {
50 | throw new EOFException(ex.getMessage());
51 | }
52 | }
53 |
54 | public int skipBytes (int n) throws IOException {
55 | return (int)input.skip((long)n);
56 | }
57 |
58 | public boolean readBoolean () throws IOException {
59 | return input.readBoolean();
60 | }
61 |
62 | public byte readByte () throws IOException {
63 | return input.readByte();
64 | }
65 |
66 | public int readUnsignedByte () throws IOException {
67 | return input.readByteUnsigned();
68 | }
69 |
70 | public short readShort () throws IOException {
71 | return input.readShort();
72 | }
73 |
74 | public int readUnsignedShort () throws IOException {
75 | return input.readShortUnsigned();
76 | }
77 |
78 | public char readChar () throws IOException {
79 | return input.readChar();
80 | }
81 |
82 | public int readInt () throws IOException {
83 | return input.readInt();
84 | }
85 |
86 | public long readLong () throws IOException {
87 | return input.readLong();
88 | }
89 |
90 | public float readFloat () throws IOException {
91 | return input.readFloat();
92 | }
93 |
94 | public double readDouble () throws IOException {
95 | return input.readDouble();
96 | }
97 |
98 | /** Not implemented.
99 | * @throws UnsupportedOperationException when called.
100 | * @deprecated this method is not supported in this implementation. */
101 | public String readLine () throws UnsupportedOperationException {
102 | throw new UnsupportedOperationException();
103 | }
104 |
105 | /** Reads the length and string of UTF8 characters, or null. This can read strings written by
106 | * {@link KryoDataOutput#writeUTF(String)}, {@link com.esotericsoftware.kryo.io.Output#writeString(String)}, and
107 | * {@link com.esotericsoftware.kryo.io.Output#writeAscii(String)}.
108 | * @return May be null. */
109 | public String readUTF () throws IOException {
110 | return input.readString();
111 | }
112 |
113 | public void close () throws Exception {
114 | input.close();
115 | }
116 | }
117 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoDataOutput.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import java.io.DataOutput;
23 | import java.io.IOException;
24 |
25 | /** A {@link DataOutput} which writes data to an {@link Output}.
26 | * @author Robert DiFalco */
27 | public class KryoDataOutput implements DataOutput, AutoCloseable {
28 | protected Output output;
29 |
30 | public KryoDataOutput (Output output) {
31 | this.output = output;
32 | }
33 |
34 | public void setOutput (Output output) {
35 | this.output = output;
36 | }
37 |
38 | public void write (int b) throws IOException {
39 | output.write(b);
40 | }
41 |
42 | public void write (byte[] b) throws IOException {
43 | output.write(b);
44 | }
45 |
46 | public void write (byte[] b, int off, int len) throws IOException {
47 | output.write(b, off, len);
48 | }
49 |
50 | public void writeBoolean (boolean v) throws IOException {
51 | output.writeBoolean(v);
52 | }
53 |
54 | public void writeByte (int v) throws IOException {
55 | output.writeByte(v);
56 | }
57 |
58 | public void writeShort (int v) throws IOException {
59 | output.writeShort(v);
60 | }
61 |
62 | public void writeChar (int v) throws IOException {
63 | output.writeChar((char)v);
64 | }
65 |
66 | public void writeInt (int v) throws IOException {
67 | output.writeInt(v);
68 | }
69 |
70 | public void writeLong (long v) throws IOException {
71 | output.writeLong(v);
72 | }
73 |
74 | public void writeFloat (float v) throws IOException {
75 | output.writeFloat(v);
76 | }
77 |
78 | public void writeDouble (double v) throws IOException {
79 | output.writeDouble(v);
80 | }
81 |
82 | public void writeBytes (String s) throws IOException {
83 | int len = s.length();
84 | for (int i = 0; i < len; i++) {
85 | output.write((byte)s.charAt(i));
86 | }
87 | }
88 |
89 | public void writeChars (String s) throws IOException {
90 | int len = s.length();
91 | for (int i = 0; i < len; i++) {
92 | int v = s.charAt(i);
93 | output.write(v & 0xFF);
94 | output.write((v >>> 8) & 0xFF);
95 | }
96 | }
97 |
98 | public void writeUTF (String s) throws IOException {
99 | output.writeString(s);
100 | }
101 |
102 | public void close () throws Exception {
103 | output.close();
104 | }
105 | }
106 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoObjectInput.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 |
24 | import java.io.IOException;
25 | import java.io.ObjectInput;
26 |
27 | /** An {@link ObjectInput} which reads data from an {@link Input}.
28 | *
29 | * Note this is not an implementation of {@link java.io.ObjectInputStream} which has special handling for Java serialization, such
30 | * as support for readResolve.
31 | * @author Robert DiFalco */
32 | public class KryoObjectInput extends KryoDataInput implements ObjectInput {
33 | private final Kryo kryo;
34 |
35 | public KryoObjectInput (Kryo kryo, Input input) {
36 | super(input);
37 | this.kryo = kryo;
38 | }
39 |
40 | public Object readObject () throws ClassNotFoundException, IOException {
41 | return kryo.readClassAndObject(input);
42 | }
43 |
44 | public int read () throws IOException {
45 | return input.read();
46 | }
47 |
48 | public int read (byte[] b) throws IOException {
49 | return input.read(b);
50 | }
51 |
52 | public int read (byte[] b, int off, int len) throws IOException {
53 | return input.read(b, off, len);
54 | }
55 |
56 | public long skip (long n) throws IOException {
57 | return input.skip(n);
58 | }
59 |
60 | public int available () throws IOException {
61 | return 0;
62 | }
63 |
64 | public void close () throws IOException {
65 | input.close();
66 | }
67 | }
68 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/KryoObjectOutput.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 |
24 | import java.io.IOException;
25 | import java.io.ObjectOutput;
26 |
27 | /** An {@link java.io.ObjectOutput} which writes data to an {@link Output}.
28 | *
29 | * Note this is not an implementation of {@link java.io.ObjectOutputStream} which has special handling for Java serialization and
30 | * serialization extras like writeReplace. By default it will simply delegate to the appropriate Kryo method. Also, using it will
31 | * currently add one extra byte for each time {@link #writeObject(Object)} is invoked since we need to allow unknown null objects.
32 | * @author Robert DiFalco */
33 | public class KryoObjectOutput extends KryoDataOutput implements ObjectOutput {
34 | private final Kryo kryo;
35 |
36 | public KryoObjectOutput (Kryo kryo, Output output) {
37 | super(output);
38 | this.kryo = kryo;
39 | }
40 |
41 | public void writeObject (Object object) throws IOException {
42 | kryo.writeClassAndObject(output, object);
43 | }
44 |
45 | public void flush () throws IOException {
46 | output.flush();
47 | }
48 |
49 | public void close () throws IOException {
50 | output.close();
51 | }
52 | }
53 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/io/OutputChunked.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.io;
21 |
22 | import static com.esotericsoftware.kryo.util.Util.*;
23 | import static com.esotericsoftware.minlog.Log.*;
24 |
25 | import com.esotericsoftware.kryo.KryoException;
26 |
27 | import java.io.IOException;
28 | import java.io.OutputStream;
29 |
30 | /** An {@link Output} that writes the length before each flush. The length allows the chunks to be skipped when reading.
31 | * @author Nathan Sweet */
32 | public class OutputChunked extends Output {
33 | /** @see Output#Output() */
34 | public OutputChunked () {
35 | super();
36 | }
37 |
38 | /** @see Output#Output(int) */
39 | public OutputChunked (int bufferSize) {
40 | super(bufferSize);
41 | }
42 |
43 | /** @see Output#Output(OutputStream) */
44 | public OutputChunked (OutputStream outputStream) {
45 | super(outputStream);
46 | }
47 |
48 | /** @see Output#Output(OutputStream, int) */
49 | public OutputChunked (OutputStream outputStream, int bufferSize) {
50 | super(outputStream, bufferSize);
51 | }
52 |
53 | public void flush () throws KryoException {
54 | if (position() > 0) {
55 | try {
56 | writeChunkSize();
57 | super.flush();
58 | } catch (IOException ex) {
59 | throw new KryoException(ex);
60 | }
61 | } else {
62 | super.flush();
63 | }
64 | }
65 |
66 | private void writeChunkSize () throws IOException {
67 | int size = position();
68 | if (TRACE) trace("kryo", "Write chunk: " + size + pos(size));
69 | OutputStream outputStream = getOutputStream();
70 | if ((size & ~0x7F) == 0) {
71 | outputStream.write(size);
72 | return;
73 | }
74 | outputStream.write((size & 0x7F) | 0x80);
75 | size >>>= 7;
76 | if ((size & ~0x7F) == 0) {
77 | outputStream.write(size);
78 | return;
79 | }
80 | outputStream.write((size & 0x7F) | 0x80);
81 | size >>>= 7;
82 | if ((size & ~0x7F) == 0) {
83 | outputStream.write(size);
84 | return;
85 | }
86 | outputStream.write((size & 0x7F) | 0x80);
87 | size >>>= 7;
88 | if ((size & ~0x7F) == 0) {
89 | outputStream.write(size);
90 | return;
91 | }
92 | outputStream.write((size & 0x7F) | 0x80);
93 | size >>>= 7;
94 | outputStream.write(size);
95 | }
96 |
97 | /** Marks the current written data as the end of a chunk. This chunk can then be skipped when reading. */
98 | public void endChunk () {
99 | flush();
100 | if (TRACE) trace("kryo", "End chunk.");
101 | try {
102 | getOutputStream().write(0); // Zero length chunk.
103 | } catch (IOException ex) {
104 | throw new KryoException(ex);
105 | }
106 | }
107 | }
108 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/BlowfishSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.KryoException;
24 | import com.esotericsoftware.kryo.Serializer;
25 | import com.esotericsoftware.kryo.io.Input;
26 | import com.esotericsoftware.kryo.io.Output;
27 |
28 | import java.io.IOException;
29 |
30 | import javax.crypto.Cipher;
31 | import javax.crypto.CipherInputStream;
32 | import javax.crypto.CipherOutputStream;
33 | import javax.crypto.spec.SecretKeySpec;
34 |
35 | /** Encrypts data using the blowfish cipher.
36 | * @author Nathan Sweet */
37 | public class BlowfishSerializer extends Serializer {
38 | private final Serializer serializer;
39 | private static SecretKeySpec keySpec;
40 |
41 | public BlowfishSerializer (Serializer serializer, byte[] key) {
42 | this.serializer = serializer;
43 | keySpec = new SecretKeySpec(key, "Blowfish");
44 | }
45 |
46 | public void write (Kryo kryo, Output output, Object object) {
47 | Cipher cipher = getCipher(Cipher.ENCRYPT_MODE);
48 | CipherOutputStream cipherStream = new CipherOutputStream(output, cipher);
49 | Output cipherOutput = new Output(cipherStream, 256) {
50 | public void close () throws KryoException {
51 | // Don't allow the CipherOutputStream to close the output.
52 | }
53 | };
54 | serializer.write(kryo, cipherOutput, object);
55 | cipherOutput.flush();
56 | try {
57 | cipherStream.close();
58 | } catch (IOException ex) {
59 | throw new KryoException(ex);
60 | }
61 | }
62 |
63 | public Object read (Kryo kryo, Input input, Class type) {
64 | Cipher cipher = getCipher(Cipher.DECRYPT_MODE);
65 | CipherInputStream cipherInput = new CipherInputStream(input, cipher);
66 | return serializer.read(kryo, new Input(cipherInput, 256), type);
67 | }
68 |
69 | public Object copy (Kryo kryo, Object original) {
70 | return serializer.copy(kryo, original);
71 | }
72 |
73 | private static Cipher getCipher (int mode) {
74 | try {
75 | Cipher cipher = Cipher.getInstance("Blowfish");
76 | cipher.init(mode, keySpec);
77 | return cipher;
78 | } catch (Exception ex) {
79 | throw new KryoException(ex);
80 | }
81 | }
82 | }
83 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/DeflateSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.KryoException;
24 | import com.esotericsoftware.kryo.Serializer;
25 | import com.esotericsoftware.kryo.io.Input;
26 | import com.esotericsoftware.kryo.io.InputChunked;
27 | import com.esotericsoftware.kryo.io.Output;
28 | import com.esotericsoftware.kryo.io.OutputChunked;
29 |
30 | import java.io.IOException;
31 | import java.util.zip.Deflater;
32 | import java.util.zip.DeflaterOutputStream;
33 | import java.util.zip.Inflater;
34 | import java.util.zip.InflaterInputStream;
35 |
36 | public class DeflateSerializer extends Serializer {
37 | private final Serializer serializer;
38 | private boolean noHeaders = true;
39 | private int compressionLevel = 4;
40 |
41 | public DeflateSerializer (Serializer serializer) {
42 | this.serializer = serializer;
43 | }
44 |
45 | public void write (Kryo kryo, Output output, Object object) {
46 | OutputChunked outputChunked = new OutputChunked(output, 256);
47 | Deflater deflater = new Deflater(compressionLevel, noHeaders);
48 | try {
49 | DeflaterOutputStream deflaterStream = new DeflaterOutputStream(outputChunked, deflater);
50 | Output deflaterOutput = new Output(deflaterStream, 256);
51 | serializer.write(kryo, deflaterOutput, object);
52 | deflaterOutput.flush();
53 | deflaterStream.finish();
54 | } catch (IOException ex) {
55 | throw new KryoException(ex);
56 | } finally {
57 | deflater.end();
58 | }
59 | outputChunked.endChunk();
60 | }
61 |
62 | public Object read (Kryo kryo, Input input, Class type) {
63 | // The inflater would read from input beyond the compressed bytes if chunked enoding wasn't used.
64 | Inflater inflater = new Inflater(noHeaders);
65 | try {
66 | InflaterInputStream inflaterStream = new InflaterInputStream(new InputChunked(input, 256), inflater);
67 | return serializer.read(kryo, new Input(inflaterStream, 256), type);
68 | } finally {
69 | inflater.end();
70 | }
71 | }
72 |
73 | public void setNoHeaders (boolean noHeaders) {
74 | this.noHeaders = noHeaders;
75 | }
76 |
77 | /** Default is 4.
78 | * @see Deflater#setLevel(int) */
79 | public void setCompressionLevel (int compressionLevel) {
80 | this.compressionLevel = compressionLevel;
81 | }
82 |
83 | public Object copy (Kryo kryo, Object original) {
84 | return serializer.copy(kryo, original);
85 | }
86 | }
87 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/EnumMapSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.io.Input;
24 |
25 | import java.util.EnumMap;
26 |
27 | /** @author Nathan Sweet */
28 | public class EnumMapSerializer extends MapSerializer {
29 | private final Class extends Enum> enumType;
30 |
31 | public EnumMapSerializer (Class extends Enum> enumType) {
32 | this.enumType = enumType;
33 | }
34 |
35 | protected EnumMap create (Kryo kryo, Input input, Class extends EnumMap> type, int size) {
36 | return new EnumMap(enumType);
37 | }
38 |
39 | protected EnumMap createCopy (Kryo kryo, EnumMap original) {
40 | return new EnumMap(original);
41 | }
42 | }
43 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/EnumNameSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.KryoException;
24 | import com.esotericsoftware.kryo.io.Input;
25 | import com.esotericsoftware.kryo.io.Output;
26 |
27 | /** Serializes enums using the enum's name. This prevents invalidating previously serialized byts when the enum order changes.
28 | * @author KwonNam Son */
29 | public class EnumNameSerializer extends ImmutableSerializer {
30 | private final Class extends Enum> enumType;
31 |
32 | public EnumNameSerializer (Class extends Enum> enumType) {
33 | this.enumType = enumType;
34 | }
35 |
36 | public void write (Kryo kryo, Output output, Enum object) {
37 | output.writeString(object.name());
38 | }
39 |
40 | public Enum read (Kryo kryo, Input input, Class type) {
41 | String name = input.readString();
42 | try {
43 | return Enum.valueOf(enumType, name);
44 | } catch (IllegalArgumentException ex) {
45 | throw new KryoException("Enum value not found with name: " + name, ex);
46 | }
47 | }
48 | }
49 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/ImmutableSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Serializer;
23 |
24 | /** A serializer which has {@link #setImmutable(boolean)} set to true. This convenience class exists only to reduce the typing
25 | * needed to define a serializer which is immutable.
26 | * @author Nathan Sweet */
27 | public abstract class ImmutableSerializer extends Serializer {
28 | {
29 | setImmutable(true);
30 | }
31 | }
32 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/serializers/JavaSerializer.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.serializers;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.KryoException;
24 | import com.esotericsoftware.kryo.KryoSerializable;
25 | import com.esotericsoftware.kryo.Serializer;
26 | import com.esotericsoftware.kryo.io.Input;
27 | import com.esotericsoftware.kryo.io.Output;
28 | import com.esotericsoftware.kryo.util.ObjectMap;
29 |
30 | import java.io.IOException;
31 | import java.io.InputStream;
32 | import java.io.ObjectInputStream;
33 | import java.io.ObjectOutputStream;
34 | import java.io.ObjectStreamClass;
35 |
36 | /** Serializes objects using Java's built in serialization mechanism. Note that this is very inefficient and should be avoided if
37 | * possible.
38 | * @see Serializer
39 | * @see FieldSerializer
40 | * @see KryoSerializable
41 | * @author Nathan Sweet */
42 | public class JavaSerializer extends Serializer {
43 | public void write (Kryo kryo, Output output, Object object) {
44 | try {
45 | ObjectMap graphContext = kryo.getGraphContext();
46 | ObjectOutputStream objectStream = (ObjectOutputStream)graphContext.get(this);
47 | if (objectStream == null) {
48 | objectStream = new ObjectOutputStream(output);
49 | graphContext.put(this, objectStream);
50 | }
51 | objectStream.writeObject(object);
52 | objectStream.flush();
53 | } catch (Exception ex) {
54 | throw new KryoException("Error during Java serialization.", ex);
55 | }
56 | }
57 |
58 | public Object read (Kryo kryo, Input input, Class type) {
59 | try {
60 | ObjectMap graphContext = kryo.getGraphContext();
61 | ObjectInputStream objectStream = (ObjectInputStream)graphContext.get(this);
62 | if (objectStream == null) {
63 | objectStream = new ObjectInputStreamWithKryoClassLoader(input, kryo);
64 | graphContext.put(this, objectStream);
65 | }
66 | return objectStream.readObject();
67 | } catch (Exception ex) {
68 | throw new KryoException("Error during Java deserialization.", ex);
69 | }
70 | }
71 |
72 | /** {@link ObjectInputStream} uses the last user-defined {@link ClassLoader}, which may not be the correct one. This is a known
73 | * Java issue and is often solved by using a specific class loader. See:
74 | * https://github.com/apache/spark/blob/v1.6.3/streaming/src/main/scala/org/apache/spark/streaming/Checkpoint.scala#L154
75 | * https://issues.apache.org/jira/browse/GROOVY-1627 */
76 | private static class ObjectInputStreamWithKryoClassLoader extends ObjectInputStream {
77 | private final Kryo kryo;
78 |
79 | ObjectInputStreamWithKryoClassLoader (InputStream in, Kryo kryo) throws IOException {
80 | super(in);
81 | this.kryo = kryo;
82 | }
83 |
84 | protected Class resolveClass (ObjectStreamClass type) {
85 | try {
86 | return Class.forName(type.getName(), false, kryo.getClassLoader());
87 | } catch (ClassNotFoundException ignored) {}
88 | try {
89 | return super.resolveClass(type);
90 | } catch (ClassNotFoundException ex) {
91 | throw new KryoException("Class not found: " + type.getName(), ex);
92 | } catch (IOException ex) {
93 | throw new KryoException("Could not load class: " + type.getName(), ex);
94 | }
95 | }
96 | }
97 | }
98 |
--------------------------------------------------------------------------------
/src/com/esotericsoftware/kryo/util/HashMapReferenceResolver.java:
--------------------------------------------------------------------------------
1 | /* Copyright (c) 2008-2025, Nathan Sweet
2 | * All rights reserved.
3 | *
4 | * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following
5 | * conditions are met:
6 | *
7 | * - Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
8 | * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following
9 | * disclaimer in the documentation and/or other materials provided with the distribution.
10 | * - Neither the name of Esoteric Software nor the names of its contributors may be used to endorse or promote products derived
11 | * from this software without specific prior written permission.
12 | *
13 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
14 | * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
15 | * SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
16 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
17 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
18 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */
19 |
20 | package com.esotericsoftware.kryo.util;
21 |
22 | import com.esotericsoftware.kryo.Kryo;
23 | import com.esotericsoftware.kryo.ReferenceResolver;
24 |
25 | import java.util.ArrayList;
26 | import java.util.IdentityHashMap;
27 |
28 | /** Uses an {@link IdentityHashMap} to track objects that have already been written. This can handle a graph with any number of
29 | * objects, but is slightly slower than {@link MapReferenceResolver} because IdentityHashMap allocates on put and slower slower
30 | * than {@link ListReferenceResolver} for graphs with few objects.
31 | * @author Nathan Sweet */
32 | public class HashMapReferenceResolver implements ReferenceResolver {
33 | protected Kryo kryo;
34 | protected final IdentityHashMap