Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 12 additions & 4 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -90,14 +90,22 @@ UnityDataTool find-refs database.db -n "ObjectName" -t "Texture2D"

### Component Hierarchy
```
UnityDataTool (CLI executable)
UnityDataTool (CLI executable) — wires the feature libraries into commands
├── Analyzer → SQLite database generation
├── TextDumper → Human-readable text output
├── ReferenceFinder → Object reference chain tracing
└── UnityFileSystem → C# wrapper for native library
└── UnityFileSystemApi (native .dll/.dylib/.so)
├── ReferenceFinder → Object reference chain tracing (queries the Analyzer database)
├── Archive → inspect / extract Unity Archives (the `archive` command)
├── SerializedFile → inspect SerializedFile header/metadata/objects (the `serialized-file` command)
└── (base libraries, used by the feature libraries above)
├── UnityBinaryFormat → C# parsers & helpers for Archives / SerializedFiles
├── UnityDataModels → schemas for JSON build-report formats
└── UnityFileSystem → C# wrapper for native library
└── UnityFileSystemApi (native .dll/.dylib/.so)
```

The feature libraries each build on UnityBinaryFormat and UnityFileSystem. See the
"Repository content" section of `README.md` for a diagram of the dependencies.

### Key Architectural Patterns

**Native Interop**: UnityFileSystem wraps UnityFileSystemApi (native library from Unity Editor) via P/Invoke in `DllWrapper.cs`. The native library reads Unity Archive and SerializedFile formats.
Expand Down
28 changes: 28 additions & 0 deletions Archive/Archive.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Library</OutputType>
<TargetFramework>net9.0</TargetFramework>
<ApplicationIcon />
<StartupObject />
<LangVersion>latest</LangVersion>
</PropertyGroup>

<PropertyGroup Condition=" '$(Configuration)' == 'Debug' ">
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>

<PropertyGroup Condition=" '$(Configuration)' == 'Release' ">
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="System.IO.Packaging" Version="7.0.0" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\UnityBinaryFormat\UnityBinaryFormat.csproj" />
<ProjectReference Include="..\UnityFileSystem\UnityFileSystem.csproj" />
</ItemGroup>

</Project>
20 changes: 13 additions & 7 deletions UnityDataTool/Archive.cs → Archive/ArchiveTool.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,17 @@
using UnityDataTools.BinaryFormat;
using UnityDataTools.FileSystem;

namespace UnityDataTools.UnityDataTool;
namespace UnityDataTools.Archive;

public static class Archive
public static class ArchiveTool
{
public static int HandleExtract(FileInfo filename, DirectoryInfo outputFolder, string filter = null)
public enum OutputFormat
{
Text,
Json
}

public static int ExtractContent(FileInfo filename, DirectoryInfo outputFolder, string filter = null)
{
try
{
Expand Down Expand Up @@ -39,7 +45,7 @@ err is NotSupportedException
return 0;
}

public static int HandleList(FileInfo filename, OutputFormat format)
public static int ListContent(FileInfo filename, OutputFormat format)
{
try
{
Expand Down Expand Up @@ -70,7 +76,7 @@ err is NotSupportedException
return 0;
}

public static int HandleHeader(FileInfo filename, OutputFormat format)
public static int PrintHeader(FileInfo filename, OutputFormat format)
{
var path = filename.ToString();

Expand All @@ -94,7 +100,7 @@ public static int HandleHeader(FileInfo filename, OutputFormat format)
return 0;
}

public static int HandleBlocks(FileInfo filename, OutputFormat format)
public static int ListBlocks(FileInfo filename, OutputFormat format)
{
var path = filename.ToString();

Expand Down Expand Up @@ -124,7 +130,7 @@ public static int HandleBlocks(FileInfo filename, OutputFormat format)
return 0;
}

public static int HandleInfo(FileInfo filename, OutputFormat format)
public static int PrintSummary(FileInfo filename, OutputFormat format)
{
var path = filename.ToString();

Expand Down
3 changes: 3 additions & 0 deletions Archive/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Archive

See [Documentation/command-archive.md](../Documentation/command-archive.md)
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
using System.Text;
using System.Text.Json;

namespace UnityDataTools.UnityDataTool;
namespace UnityDataTools.Archive;

public static class WebBundleHelper
{
Expand Down Expand Up @@ -50,14 +50,14 @@ public static void Extract(FileInfo filename, DirectoryInfo outputFolder, string
Console.WriteLine($"Extracted {extracted} out of {total} files.");
}

public static void List(FileInfo filename, OutputFormat format)
public static void List(FileInfo filename, ArchiveTool.OutputFormat format)
{
using var fileStream = File.Open(filename.ToString(), FileMode.Open);
using var stream = GetStream(filename, fileStream);
using var reader = new BinaryReader(stream, Encoding.UTF8);
var fileDescriptions = ParseWebBundleHeader(reader);

if (format == OutputFormat.Json)
if (format == ArchiveTool.OutputFormat.Json)
{
var jsonArray = new object[fileDescriptions.Count];
for (int i = 0; i < fileDescriptions.Count; i++)
Expand Down
97 changes: 79 additions & 18 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,19 +37,84 @@ New to Unity's data files or to UnityDataTool? These topics are a good place to

## Repository content

The repository contains the following items:
* [UnityDataTool](Documentation/unitydatatool.md): a command-line tool providing access to the Analyzer, TextDumper and other class libraries.
* [Analyzer](Documentation/analyzer.md): a class library that can be used to extract key information
from Unity data files and output it into a SQLite database.
* [TextDumper](Documentation/textdumper.md): a class library that can be used to dump SerializedFiles into
a human-readable format (similar to binary2text).
* [ReferenceFinder](Documentation/referencefinder.md): a class library that can be used to find
reference chains from objects to other objects using a database created by the Analyzer
* UnityFileSystem: source code and binaries of a .NET class library exposing the functionalities or the
UnityFileSystemApi native library.
* UnityFileSystem.Tests: test suite for the UnityFileSystem library.
* UnityProjects: Unity projects used to generate some of the test data.
* TestCommon: a helper library used by the test projects.
The solution is organised in three layers. At the base are the libraries that read Unity's binary
formats. On top of those sit the feature libraries that turn that raw data into something useful
(a database, a text dump, a reference graph). And at the top is the command-line tool that exposes
all of that functionality to users.

```mermaid
flowchart TD
CLI["<b>UnityDataTool</b><br/>command-line tool"]

Analyzer["<b>Analyzer</b><br/>SQLite database"]
TextDumper["<b>TextDumper</b><br/>human-readable dump"]
ReferenceFinder["<b>ReferenceFinder</b><br/>reference chains"]
Archive["<b>Archive</b><br/>inspect / extract archives"]
SerializedFile["<b>SerializedFile</b><br/>inspect SerializedFiles"]

UnityFileSystem["<b>UnityFileSystem</b><br/>C# wrapper +<br/>UnityFileSystemApi (native)"]
UnityBinaryFormat["<b>UnityBinaryFormat</b><br/>C# parsers &amp; helpers<br/>for Archives / SerializedFiles"]
UnityDataModels["<b>UnityDataModels</b><br/>schemas for build reporting file formats"]

CLI --> Analyzer
CLI --> TextDumper
CLI --> ReferenceFinder
CLI --> Archive
CLI --> SerializedFile

Analyzer --> UnityFileSystem
Analyzer --> UnityBinaryFormat
Analyzer --> UnityDataModels
TextDumper --> UnityFileSystem
TextDumper --> UnityBinaryFormat
Archive --> UnityFileSystem
Archive --> UnityBinaryFormat
SerializedFile --> UnityFileSystem
SerializedFile --> UnityBinaryFormat
UnityBinaryFormat --> UnityFileSystem

ReferenceFinder -. "reads the SQLite database" .-> Analyzer
```

**Command-line tool**
* [UnityDataTool](Documentation/unitydatatool.md): the command-line tool. It wires the feature
libraries together and exposes them as commands (`analyze`, `dump`, `find-refs`, `archive`,
`serialized-file`, and more), so most users only ever interact with this executable.

**Feature libraries**
* [Analyzer](Documentation/analyzer.md): extracts key information from Unity data files into a SQLite
database for detailed analysis. It also parses Addressables build reports.
* [TextDumper](Documentation/textdumper.md): dumps SerializedFiles into a human-readable format
(similar to Unity's binary2text).
* [ReferenceFinder](Documentation/referencefinder.md): finds reference chains from one object to
another by querying a database produced by the Analyzer (a data dependency rather than a code one).
* [Archive](Documentation/command-archive.md): inspects and extracts the contents of Unity Archives
(AssetBundles and web platform `.data` files) — the `archive` command.
* [SerializedFile](Documentation/command-serialized-file.md): inspects the header, metadata, object
list, and external references of a SerializedFile — the `serialized-file` command.

**Base libraries**
* UnityFileSystem: a .NET class library, with source and binaries, that wraps the native
`UnityFileSystemApi` to mount Unity Archives and read SerializedFiles.
* UnityBinaryFormat: C# parsers and helpers for reading data out of Unity Archives and SerializedFiles.
* UnityDataModels: shared C# models for the reading JSON format files produced by the build (Addressables BuildLayout.json, Content Directory ContentLayout.json).

## Purpose of UnityFileSystemApi

UnityFileSystemApi is compiled from the Unity source code and exposes the core functionality to open and read the Unity Archive and Serialized File formats as a flexible, performant library. It exposes the ability to navigate the TypeTrees inside a SerializedFile so objects can be read generically, without hardcoded type knowledge.

It enables custom tools for binary2text-like output and efficient SQLite database generation.

### Tests and test data

The automated tests are not shown in the diagram above. Each library has its own test project, and the
shared test data doubles as convenient sample content for ad hoc use of the tool.

* TestCommon: a helper library whose `Data/` folder holds small reference files extracted from real
Unity builds (Player, AssetBundles, content directory etc). These back the automated tests and are also handy for trying out the tool by hand.
* Analyzer.Tests, UnityDataTool.Tests, UnityFileSystem.Tests: the per-library test suites.
* UnityProjects: two Unity projects (`Baseline` and `LeadingEdge`) used to regenerate some of the test
data as Unity evolves.

## Downloads

Expand All @@ -63,7 +128,7 @@ Refer to the [commit history](https://github.com/Unity-Technologies/UnityDataToo

## Getting UnityFileSystemApi

UnityDataTool uses the native `UnityFileSystemApi` library to read Unity Archives and SerializedFiles. **Normally you don't need to do anything with this library.** The repository already includes a recent Windows, Mac, and Linux copy in the [`UnityFileSystem/`](https://github.com/Unity-Technologies/UnityDataTools/tree/main/UnityFileSystem) directory, and using that bundled copy is the recommended way to run the tool.
UnityDataTool uses the pre-compiled `UnityFileSystemApi` library to read Unity Archives and SerializedFiles. **Normally you don't need to do anything with this library.** The repository already includes a recent Windows, Mac, and Linux copy in the [`UnityFileSystem/`](https://github.com/Unity-Technologies/UnityDataTools/tree/main/UnityFileSystem) directory, and using that bundled copy is the recommended way to run the tool.

The library is backward compatible but not forward compatible: a given version can read content from the same or older Unity versions, but may be unable to read content produced by a newer Unity Editor than the library itself. The bundled copy is updated periodically as Unity evolves, so in practice it can read content from just about any Unity version.

Expand All @@ -84,10 +149,6 @@ On Windows, the executable is written to `UnityDataTool\bin\Release\net9.0`. Add

See the [command-line tool documentation](./Documentation/unitydatatool.md) for usage instructions.

## Purpose of UnityFileSystemApi

UnityFileSystemApi exposes the core functionality of WebExtract and binary2text to open and read the Unity Archive and Serialized File formats, exposed as a flexible, performant library. It enables custom tools for binary2text-like output and efficient SQLite database generation.

## Origins

This tool is the evolution of the [AssetBundle Analyzer](https://github.com/faelenor/asset-bundle-analyzer)
Expand Down
3 changes: 3 additions & 0 deletions SerializedFile/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# SerializedFile

See [Documentation/command-serialized-file.md](../Documentation/command-serialized-file.md)
24 changes: 24 additions & 0 deletions SerializedFile/SerializedFile.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Library</OutputType>
<TargetFramework>net9.0</TargetFramework>
<ApplicationIcon />
<StartupObject />
<LangVersion>latest</LangVersion>
</PropertyGroup>

<PropertyGroup Condition=" '$(Configuration)' == 'Debug' ">
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>

<PropertyGroup Condition=" '$(Configuration)' == 'Release' ">
<PlatformTarget>AnyCPU</PlatformTarget>
</PropertyGroup>

<ItemGroup>
<ProjectReference Include="..\UnityBinaryFormat\UnityBinaryFormat.csproj" />
<ProjectReference Include="..\UnityFileSystem\UnityFileSystem.csproj" />
</ItemGroup>

</Project>
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,17 @@
using UnityDataTools.BinaryFormat;
using UnityDataTools.FileSystem;

namespace UnityDataTools.UnityDataTool;
namespace UnityDataTools.SerializedFile;

public static class SerializedFileCommands
public static class SerializedFileTool
{
public static int HandleExternalRefs(FileInfo filename, OutputFormat format)
public enum OutputFormat
{
Text,
Json
}

public static int ListExternalRefs(FileInfo filename, OutputFormat format)
{
// External references are read directly from the parsed metadata rather than via UnityFileSystemApi.
//
Expand Down Expand Up @@ -44,10 +50,10 @@ public static int HandleExternalRefs(FileInfo filename, OutputFormat format)
return 0;
}

public static int HandleObjectList(FileInfo filename, OutputFormat format)
public static int ListObjects(FileInfo filename, OutputFormat format)
{
// The object list is read directly from the parsed metadata rather than via UnityFileSystemApi.
// (See comment in HandleExternalRefs() for the reasons for doing it that way)
// (See comment in ListExternalRefs() for the reasons for doing it that way)
if (!ValidateSerializedFile(filename.FullName, out var fileInfo))
return 1;

Expand All @@ -72,7 +78,7 @@ public static int HandleObjectList(FileInfo filename, OutputFormat format)
return 0;
}

public static int HandleHeader(FileInfo filename, OutputFormat format)
public static int PrintHeader(FileInfo filename, OutputFormat format)
{
if (!ValidateSerializedFile(filename.FullName, out var fileInfo))
return 1;
Expand All @@ -85,7 +91,7 @@ public static int HandleHeader(FileInfo filename, OutputFormat format)
return 0;
}

public static int HandleMetadata(FileInfo filename, OutputFormat format)
public static int PrintMetadata(FileInfo filename, OutputFormat format)
{
if (!ValidateSerializedFile(filename.FullName, out var fileInfo))
return 1;
Expand Down
1 change: 1 addition & 0 deletions UnityDataTool.Tests/WebBundleSupportTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
using System.Linq;
using System.Threading.Tasks;
using NUnit.Framework;
using UnityDataTools.Archive;
using UnityDataTools.FileSystem;

namespace UnityDataTools.UnityDataTool.Tests;
Expand Down
Loading
Loading