Skip to content

ejfkdev/java-serialization-rs

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

java-serialization-rs

English | 中文

CI Crates.io Documentation License: MIT Rust MSRV unsafe forbidden Lines of Code

A Java object serialization stream parser written in Rust, based on the Java Object Serialization Specification.

Features

  • Full support for Java serialization protocol (magic 0xACED, version 5)
  • All type codes: TC_OBJECT, TC_ARRAY, TC_CLASSDESC, TC_ENUM, TC_PROXYCLASSDESC, TC_STRING, TC_LONGSTRING, etc.
  • Block data and annotation parsing
  • Handle reference resolution (back-references via TC_REFERENCE)
  • Automatic JDK 8u20 exploit payload adaptation (missing TC_ENDBLOCKDATA retry)
  • Optional serde support for JSON/other format output
  • Tested against 35 ysoserial gadget chain payloads

Quick Start

Add to your Cargo.toml:

[dependencies]
java-serialization = "0.1"

Parse a serialization stream:

use java_serialization::parse_serialization_stream;

let data = std::fs::read("payload.ser")?;
let (_, stream) = parse_serialization_stream(&data)?;
for obj in stream.objects() {
    println!("{:?}", obj);
}

Serde Support

Enable the serde feature to serialize parsed structures to JSON or other formats:

[dependencies]
java-serialization = { version = "0.1", features = ["serde"] }
use java_serialization::parse_serialization_stream;

let data = std::fs::read("payload.ser")?;
let (_, stream) = parse_serialization_stream(&data)?;
let json = serde_json::to_string_pretty(&stream)?;
println!("{}", json);

JDK 8u20 Preprocessing

JDK 8u20 exploit payloads omit a TC_ENDBLOCKDATA byte after a TC_REFERENCE to handle 0x7e0009, causing standard parsers to fail. parse_serialization_stream automatically retries with preprocessing on failure. You can also apply it manually:

use java_serialization::{parse_serialization_stream, preprocess_jdk8u20};

let data = std::fs::read("JDK8u20.ser")?;
let preprocessed = preprocess_jdk8u20(&data);
let (_, stream) = parse_serialization_stream(&preprocessed)?;

API Overview

Type Description
SerializationStream Top-level parsed stream with version and contents
StreamObject Enum of all object types (NewObject, NewArray, NewString, NewEnum, etc.)
ClassDesc Class descriptor (normal or proxy)
FieldValue Primitive or object field value
BlockData Block data (short or long)

Testing

cargo test              # run all tests
cargo test --all-features  # include serde feature
cargo clippy --all-features -- -D warnings  # lint

The test suite validates against 35 ysoserial-generated .ser files covering gadget chains including CommonsCollections, Spring, Groovy, Clojure, Hibernate, and more.

Security Disclaimer

This project is a parser only — it does not execute or instantiate any Java objects. The .ser files in the testcases/ directory are included solely for testing parser correctness against known Java deserialization payload formats.

These files are generated by ysoserial and are intended for authorized security research, vulnerability assessment, and educational purposes only. Do not use them against systems you do not own or have explicit permission to test.

License

MIT

About

Java object serialization stream parser written in Rust

Topics

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors

Languages