Implement name overrides #181
13 changed files with 524 additions and 503 deletions
|
@ -324,11 +324,11 @@ async fn build_bundles(state: Arc<ActionState>) -> Result<Vec<Bundle>> {
|
||||||
|
|
||||||
let mut bundles = Vec::new();
|
let mut bundles = Vec::new();
|
||||||
|
|
||||||
let mut add_lua_asset = |name, data: &str| {
|
let mut add_lua_asset = |name: &str, data: &str| {
|
||||||
let span = tracing::info_span!("Compiling Lua", name, data_len = data.len());
|
let span = tracing::info_span!("Compiling Lua", name, data_len = data.len());
|
||||||
let _enter = span.enter();
|
let _enter = span.enter();
|
||||||
|
|
||||||
let file = lua::compile(name, data).wrap_err("Failed to compile Lua")?;
|
let file = lua::compile(name.to_string(), data).wrap_err("Failed to compile Lua")?;
|
||||||
|
|
||||||
mod_bundle.add_file(file);
|
mod_bundle.add_file(file);
|
||||||
|
|
||||||
|
@ -517,8 +517,8 @@ async fn patch_boot_bundle(
|
||||||
.wrap_err("Failed to render template `mod_main.lua`")?;
|
.wrap_err("Failed to render template `mod_main.lua`")?;
|
||||||
|
|
||||||
tracing::trace!("Main script rendered:\n===========\n{}\n=============", lua);
|
tracing::trace!("Main script rendered:\n===========\n{}\n=============", lua);
|
||||||
let file =
|
let file = lua::compile(MOD_BOOT_SCRIPT.to_string(), lua)
|
||||||
lua::compile(MOD_BOOT_SCRIPT, lua).wrap_err("Failed to compile mod main Lua file")?;
|
.wrap_err("Failed to compile mod main Lua file")?;
|
||||||
|
|
||||||
boot_bundle.add_file(file);
|
boot_bundle.add_file(file);
|
||||||
}
|
}
|
||||||
|
|
|
@ -297,6 +297,7 @@ fn extract_mod_config<R: Read + Seek>(archive: &mut ZipArchive<R>) -> Result<(Mo
|
||||||
packages: Vec::new(),
|
packages: Vec::new(),
|
||||||
resources,
|
resources,
|
||||||
depends: Vec::new(),
|
depends: Vec::new(),
|
||||||
|
name_overrides: Default::default(),
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok((cfg, root))
|
Ok((cfg, root))
|
||||||
|
|
|
@ -103,38 +103,41 @@ async fn find_project_config(dir: Option<PathBuf>) -> Result<ModConfig> {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tracing::instrument(skip_all)]
|
#[tracing::instrument(skip_all)]
|
||||||
async fn compile_package_files<P>(pkg: &Package, root: P) -> Result<Vec<BundleFile>>
|
async fn compile_package_files(pkg: &Package, cfg: &ModConfig) -> Result<Vec<BundleFile>> {
|
||||||
where
|
let root = Arc::new(&cfg.dir);
|
||||||
P: AsRef<Path> + std::fmt::Debug,
|
let name_overrides = &cfg.name_overrides;
|
||||||
{
|
|
||||||
let root = Arc::new(root.as_ref());
|
|
||||||
|
|
||||||
let tasks = pkg
|
let tasks = pkg
|
||||||
.iter()
|
.iter()
|
||||||
.flat_map(|(file_type, paths)| {
|
.flat_map(|(file_type, names)| {
|
||||||
paths.iter().map(|path| {
|
names.iter().map(|name| {
|
||||||
(
|
(
|
||||||
*file_type,
|
*file_type,
|
||||||
path,
|
name,
|
||||||
// Cloning the `Arc` here solves the issue that in the next `.map`, I need to
|
// Cloning the `Arc` here solves the issue that in the next `.map`, I need to
|
||||||
// `move` the closure parameters, but can't `move` `root` before it was cloned.
|
// `move` the closure parameters, but can't `move` `root` before it was cloned.
|
||||||
root.clone(),
|
root.clone(),
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
.map(|(file_type, path, root)| async move {
|
.map(|(file_type, name, root)| async move {
|
||||||
let sjson = fs::read_to_string(&path).await?;
|
let path = PathBuf::from(name);
|
||||||
|
let sjson = fs::read_to_string(&path)
|
||||||
|
.await
|
||||||
|
.wrap_err_with(|| format!("Failed to read file '{}'", path.display()))?;
|
||||||
|
|
||||||
let mut path = path.clone();
|
let name = path.with_extension("").to_slash_lossy().to_string();
|
||||||
path.set_extension("");
|
let name = if let Some(new_name) = name_overrides.get(&name) {
|
||||||
|
let new_name = match u64::from_str_radix(new_name, 16) {
|
||||||
BundleFile::from_sjson(
|
Ok(hash) => IdString64::from(hash),
|
||||||
path.to_slash_lossy().to_string(),
|
Err(_) => IdString64::from(new_name.clone()),
|
||||||
file_type,
|
};
|
||||||
sjson,
|
tracing::info!("Overriding '{}' -> '{}'", name, new_name.display());
|
||||||
root.as_ref(),
|
new_name
|
||||||
)
|
} else {
|
||||||
.await
|
IdString64::from(name.clone())
|
||||||
|
};
|
||||||
|
BundleFile::from_sjson(name, file_type, sjson, root.as_ref()).await
|
||||||
});
|
});
|
||||||
|
|
||||||
let results = futures::stream::iter(tasks)
|
let results = futures::stream::iter(tasks)
|
||||||
|
@ -146,12 +149,11 @@ where
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tracing::instrument]
|
#[tracing::instrument]
|
||||||
async fn build_package<P1, P2>(package: P1, root: P2) -> Result<Bundle>
|
async fn build_package(
|
||||||
where
|
cfg: &ModConfig,
|
||||||
P1: AsRef<Path> + std::fmt::Debug,
|
package: impl AsRef<Path> + std::fmt::Debug,
|
||||||
P2: AsRef<Path> + std::fmt::Debug,
|
) -> Result<Bundle> {
|
||||||
{
|
let root = &cfg.dir;
|
||||||
let root = root.as_ref();
|
|
||||||
let package = package.as_ref();
|
let package = package.as_ref();
|
||||||
|
|
||||||
let mut path = root.join(package);
|
let mut path = root.join(package);
|
||||||
|
@ -165,7 +167,7 @@ where
|
||||||
.await
|
.await
|
||||||
.wrap_err_with(|| format!("Invalid package file {}", &pkg_name))?;
|
.wrap_err_with(|| format!("Invalid package file {}", &pkg_name))?;
|
||||||
|
|
||||||
let files = compile_package_files(&pkg, root).await?;
|
let files = compile_package_files(&pkg, cfg).await?;
|
||||||
let mut bundle = Bundle::new(pkg_name);
|
let mut bundle = Bundle::new(pkg_name);
|
||||||
for file in files {
|
for file in files {
|
||||||
bundle.add_file(file);
|
bundle.add_file(file);
|
||||||
|
@ -254,14 +256,14 @@ pub(crate) async fn read_project_config(dir: Option<PathBuf>) -> Result<ModConfi
|
||||||
Ok(cfg)
|
Ok(cfg)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) async fn build<P1, P2>(
|
#[tracing::instrument]
|
||||||
|
pub(crate) async fn build<P>(
|
||||||
cfg: &ModConfig,
|
cfg: &ModConfig,
|
||||||
out_path: P1,
|
out_path: impl AsRef<Path> + std::fmt::Debug,
|
||||||
game_dir: Arc<Option<P2>>,
|
game_dir: Arc<Option<P>>,
|
||||||
) -> Result<()>
|
) -> Result<()>
|
||||||
where
|
where
|
||||||
P1: AsRef<Path>,
|
P: AsRef<Path> + std::fmt::Debug,
|
||||||
P2: AsRef<Path>,
|
|
||||||
{
|
{
|
||||||
let out_path = out_path.as_ref();
|
let out_path = out_path.as_ref();
|
||||||
|
|
||||||
|
@ -286,7 +288,7 @@ where
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
let bundle = build_package(path, &cfg.dir).await.wrap_err_with(|| {
|
let bundle = build_package(&cfg, path).await.wrap_err_with(|| {
|
||||||
format!(
|
format!(
|
||||||
"Failed to build package '{}' at '{}'",
|
"Failed to build package '{}' at '{}'",
|
||||||
path.display(),
|
path.display(),
|
||||||
|
|
|
@ -351,6 +351,7 @@ pub(crate) async fn run(_ctx: sdk::Context, matches: &ArgMatches) -> Result<()>
|
||||||
},
|
},
|
||||||
depends: vec![ModDependency::ID(String::from("DMF"))],
|
depends: vec![ModDependency::ID(String::from("DMF"))],
|
||||||
bundled: true,
|
bundled: true,
|
||||||
|
name_overrides: HashMap::new(),
|
||||||
};
|
};
|
||||||
|
|
||||||
tracing::debug!(?dtmt_cfg);
|
tracing::debug!(?dtmt_cfg);
|
||||||
|
|
|
@ -77,17 +77,14 @@ pub(crate) fn command_definition() -> Command {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn compile<P1, P2, P3>(
|
#[tracing::instrument]
|
||||||
|
async fn compile(
|
||||||
cfg: &ModConfig,
|
cfg: &ModConfig,
|
||||||
out_path: P1,
|
out_path: impl AsRef<Path> + std::fmt::Debug,
|
||||||
archive_path: P2,
|
archive_path: impl AsRef<Path> + std::fmt::Debug,
|
||||||
game_dir: Arc<Option<P3>>,
|
game_dir: Arc<Option<impl AsRef<Path> + std::fmt::Debug>>,
|
||||||
) -> Result<()>
|
) -> Result<()> {
|
||||||
where
|
let out_path = out_path.as_ref();
|
||||||
P1: AsRef<Path> + std::marker::Copy,
|
|
||||||
P2: AsRef<Path>,
|
|
||||||
P3: AsRef<Path>,
|
|
||||||
{
|
|
||||||
build(cfg, out_path, game_dir)
|
build(cfg, out_path, game_dir)
|
||||||
.await
|
.await
|
||||||
.wrap_err("Failed to build bundles")?;
|
.wrap_err("Failed to build bundles")?;
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
use std::collections::HashMap;
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
|
|
||||||
use color_eyre::eyre::{OptionExt as _, WrapErr as _};
|
use color_eyre::eyre::{OptionExt as _, WrapErr as _};
|
||||||
|
@ -67,6 +68,8 @@ pub struct ModConfig {
|
||||||
pub depends: Vec<ModDependency>,
|
pub depends: Vec<ModDependency>,
|
||||||
#[serde(default = "default_true", skip_serializing_if = "is_true")]
|
#[serde(default = "default_true", skip_serializing_if = "is_true")]
|
||||||
pub bundled: bool,
|
pub bundled: bool,
|
||||||
|
#[serde(default)]
|
||||||
|
pub name_overrides: HashMap<String, String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub const STEAMAPP_ID: u32 = 1361210;
|
pub const STEAMAPP_ID: u32 = 1361210;
|
||||||
|
|
|
@ -13,7 +13,7 @@ use crate::binary::ToBinary;
|
||||||
use crate::murmur::Murmur64;
|
use crate::murmur::Murmur64;
|
||||||
use crate::Bundle;
|
use crate::Bundle;
|
||||||
|
|
||||||
use super::file::BundleFileType;
|
use super::filetype::BundleFileType;
|
||||||
|
|
||||||
const DATABASE_VERSION: u32 = 0x6;
|
const DATABASE_VERSION: u32 = 0x6;
|
||||||
const FILE_VERSION: u32 = 0x4;
|
const FILE_VERSION: u32 = 0x4;
|
||||||
|
|
|
@ -5,407 +5,12 @@ use bitflags::bitflags;
|
||||||
use color_eyre::eyre::Context;
|
use color_eyre::eyre::Context;
|
||||||
use color_eyre::{eyre, Result};
|
use color_eyre::{eyre, Result};
|
||||||
use futures::future::join_all;
|
use futures::future::join_all;
|
||||||
use serde::Serialize;
|
|
||||||
|
|
||||||
use crate::binary::sync::*;
|
use crate::binary::sync::*;
|
||||||
use crate::filetype::*;
|
use crate::filetype::*;
|
||||||
use crate::murmur::{HashGroup, IdString64, Murmur64};
|
use crate::murmur::{HashGroup, IdString64, Murmur64};
|
||||||
|
|
||||||
#[derive(Debug, Hash, PartialEq, Eq, Copy, Clone)]
|
use super::filetype::BundleFileType;
|
||||||
pub enum BundleFileType {
|
|
||||||
Animation,
|
|
||||||
AnimationCurves,
|
|
||||||
Apb,
|
|
||||||
BakedLighting,
|
|
||||||
Bik,
|
|
||||||
BlendSet,
|
|
||||||
Bones,
|
|
||||||
Chroma,
|
|
||||||
CommonPackage,
|
|
||||||
Config,
|
|
||||||
Crypto,
|
|
||||||
Data,
|
|
||||||
Entity,
|
|
||||||
Flow,
|
|
||||||
Font,
|
|
||||||
Ies,
|
|
||||||
Ini,
|
|
||||||
Input,
|
|
||||||
Ivf,
|
|
||||||
Keys,
|
|
||||||
Level,
|
|
||||||
Lua,
|
|
||||||
Material,
|
|
||||||
Mod,
|
|
||||||
MouseCursor,
|
|
||||||
NavData,
|
|
||||||
NetworkConfig,
|
|
||||||
OddleNet,
|
|
||||||
Package,
|
|
||||||
Particles,
|
|
||||||
PhysicsProperties,
|
|
||||||
RenderConfig,
|
|
||||||
RtPipeline,
|
|
||||||
Scene,
|
|
||||||
Shader,
|
|
||||||
ShaderLibrary,
|
|
||||||
ShaderLibraryGroup,
|
|
||||||
ShadingEnvionmentMapping,
|
|
||||||
ShadingEnvironment,
|
|
||||||
Slug,
|
|
||||||
SlugAlbum,
|
|
||||||
SoundEnvironment,
|
|
||||||
SpuJob,
|
|
||||||
StateMachine,
|
|
||||||
StaticPVS,
|
|
||||||
Strings,
|
|
||||||
SurfaceProperties,
|
|
||||||
Texture,
|
|
||||||
TimpaniBank,
|
|
||||||
TimpaniMaster,
|
|
||||||
Tome,
|
|
||||||
Ugg,
|
|
||||||
Unit,
|
|
||||||
Upb,
|
|
||||||
VectorField,
|
|
||||||
Wav,
|
|
||||||
WwiseBank,
|
|
||||||
WwiseDep,
|
|
||||||
WwiseEvent,
|
|
||||||
WwiseMetadata,
|
|
||||||
WwiseStream,
|
|
||||||
Xml,
|
|
||||||
|
|
||||||
Unknown(Murmur64),
|
|
||||||
}
|
|
||||||
|
|
||||||
impl BundleFileType {
|
|
||||||
pub fn ext_name(&self) -> String {
|
|
||||||
match self {
|
|
||||||
BundleFileType::AnimationCurves => String::from("animation_curves"),
|
|
||||||
BundleFileType::Animation => String::from("animation"),
|
|
||||||
BundleFileType::Apb => String::from("apb"),
|
|
||||||
BundleFileType::BakedLighting => String::from("baked_lighting"),
|
|
||||||
BundleFileType::Bik => String::from("bik"),
|
|
||||||
BundleFileType::BlendSet => String::from("blend_set"),
|
|
||||||
BundleFileType::Bones => String::from("bones"),
|
|
||||||
BundleFileType::Chroma => String::from("chroma"),
|
|
||||||
BundleFileType::CommonPackage => String::from("common_package"),
|
|
||||||
BundleFileType::Config => String::from("config"),
|
|
||||||
BundleFileType::Crypto => String::from("crypto"),
|
|
||||||
BundleFileType::Data => String::from("data"),
|
|
||||||
BundleFileType::Entity => String::from("entity"),
|
|
||||||
BundleFileType::Flow => String::from("flow"),
|
|
||||||
BundleFileType::Font => String::from("font"),
|
|
||||||
BundleFileType::Ies => String::from("ies"),
|
|
||||||
BundleFileType::Ini => String::from("ini"),
|
|
||||||
BundleFileType::Input => String::from("input"),
|
|
||||||
BundleFileType::Ivf => String::from("ivf"),
|
|
||||||
BundleFileType::Keys => String::from("keys"),
|
|
||||||
BundleFileType::Level => String::from("level"),
|
|
||||||
BundleFileType::Lua => String::from("lua"),
|
|
||||||
BundleFileType::Material => String::from("material"),
|
|
||||||
BundleFileType::Mod => String::from("mod"),
|
|
||||||
BundleFileType::MouseCursor => String::from("mouse_cursor"),
|
|
||||||
BundleFileType::NavData => String::from("nav_data"),
|
|
||||||
BundleFileType::NetworkConfig => String::from("network_config"),
|
|
||||||
BundleFileType::OddleNet => String::from("oodle_net"),
|
|
||||||
BundleFileType::Package => String::from("package"),
|
|
||||||
BundleFileType::Particles => String::from("particles"),
|
|
||||||
BundleFileType::PhysicsProperties => String::from("physics_properties"),
|
|
||||||
BundleFileType::RenderConfig => String::from("render_config"),
|
|
||||||
BundleFileType::RtPipeline => String::from("rt_pipeline"),
|
|
||||||
BundleFileType::Scene => String::from("scene"),
|
|
||||||
BundleFileType::ShaderLibraryGroup => String::from("shader_library_group"),
|
|
||||||
BundleFileType::ShaderLibrary => String::from("shader_library"),
|
|
||||||
BundleFileType::Shader => String::from("shader"),
|
|
||||||
BundleFileType::ShadingEnvionmentMapping => String::from("shading_environment_mapping"),
|
|
||||||
BundleFileType::ShadingEnvironment => String::from("shading_environment"),
|
|
||||||
BundleFileType::SlugAlbum => String::from("slug_album"),
|
|
||||||
BundleFileType::Slug => String::from("slug"),
|
|
||||||
BundleFileType::SoundEnvironment => String::from("sound_environment"),
|
|
||||||
BundleFileType::SpuJob => String::from("spu_job"),
|
|
||||||
BundleFileType::StateMachine => String::from("state_machine"),
|
|
||||||
BundleFileType::StaticPVS => String::from("static_pvs"),
|
|
||||||
BundleFileType::Strings => String::from("strings"),
|
|
||||||
BundleFileType::SurfaceProperties => String::from("surface_properties"),
|
|
||||||
BundleFileType::Texture => String::from("texture"),
|
|
||||||
BundleFileType::TimpaniBank => String::from("timpani_bank"),
|
|
||||||
BundleFileType::TimpaniMaster => String::from("timpani_master"),
|
|
||||||
BundleFileType::Tome => String::from("tome"),
|
|
||||||
BundleFileType::Ugg => String::from("ugg"),
|
|
||||||
BundleFileType::Unit => String::from("unit"),
|
|
||||||
BundleFileType::Upb => String::from("upb"),
|
|
||||||
BundleFileType::VectorField => String::from("vector_field"),
|
|
||||||
BundleFileType::Wav => String::from("wav"),
|
|
||||||
BundleFileType::WwiseBank => String::from("wwise_bank"),
|
|
||||||
BundleFileType::WwiseDep => String::from("wwise_dep"),
|
|
||||||
BundleFileType::WwiseEvent => String::from("wwise_event"),
|
|
||||||
BundleFileType::WwiseMetadata => String::from("wwise_metadata"),
|
|
||||||
BundleFileType::WwiseStream => String::from("wwise_stream"),
|
|
||||||
BundleFileType::Xml => String::from("xml"),
|
|
||||||
|
|
||||||
BundleFileType::Unknown(s) => format!("{s:016X}"),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn decompiled_ext_name(&self) -> String {
|
|
||||||
match self {
|
|
||||||
BundleFileType::Texture => String::from("dds"),
|
|
||||||
BundleFileType::WwiseBank => String::from("bnk"),
|
|
||||||
BundleFileType::WwiseStream => String::from("ogg"),
|
|
||||||
_ => self.ext_name(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn hash(&self) -> Murmur64 {
|
|
||||||
Murmur64::from(*self)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl std::str::FromStr for BundleFileType {
|
|
||||||
type Err = color_eyre::Report;
|
|
||||||
|
|
||||||
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
|
||||||
let val = match s {
|
|
||||||
"animation_curves" => BundleFileType::AnimationCurves,
|
|
||||||
"animation" => BundleFileType::Animation,
|
|
||||||
"apb" => BundleFileType::Apb,
|
|
||||||
"baked_lighting" => BundleFileType::BakedLighting,
|
|
||||||
"bik" => BundleFileType::Bik,
|
|
||||||
"blend_set" => BundleFileType::BlendSet,
|
|
||||||
"bones" => BundleFileType::Bones,
|
|
||||||
"chroma" => BundleFileType::Chroma,
|
|
||||||
"common_package" => BundleFileType::CommonPackage,
|
|
||||||
"config" => BundleFileType::Config,
|
|
||||||
"crypto" => BundleFileType::Crypto,
|
|
||||||
"data" => BundleFileType::Data,
|
|
||||||
"entity" => BundleFileType::Entity,
|
|
||||||
"flow" => BundleFileType::Flow,
|
|
||||||
"font" => BundleFileType::Font,
|
|
||||||
"ies" => BundleFileType::Ies,
|
|
||||||
"ini" => BundleFileType::Ini,
|
|
||||||
"input" => BundleFileType::Input,
|
|
||||||
"ivf" => BundleFileType::Ivf,
|
|
||||||
"keys" => BundleFileType::Keys,
|
|
||||||
"level" => BundleFileType::Level,
|
|
||||||
"lua" => BundleFileType::Lua,
|
|
||||||
"material" => BundleFileType::Material,
|
|
||||||
"mod" => BundleFileType::Mod,
|
|
||||||
"mouse_cursor" => BundleFileType::MouseCursor,
|
|
||||||
"nav_data" => BundleFileType::NavData,
|
|
||||||
"network_config" => BundleFileType::NetworkConfig,
|
|
||||||
"oodle_net" => BundleFileType::OddleNet,
|
|
||||||
"package" => BundleFileType::Package,
|
|
||||||
"particles" => BundleFileType::Particles,
|
|
||||||
"physics_properties" => BundleFileType::PhysicsProperties,
|
|
||||||
"render_config" => BundleFileType::RenderConfig,
|
|
||||||
"rt_pipeline" => BundleFileType::RtPipeline,
|
|
||||||
"scene" => BundleFileType::Scene,
|
|
||||||
"shader_library_group" => BundleFileType::ShaderLibraryGroup,
|
|
||||||
"shader_library" => BundleFileType::ShaderLibrary,
|
|
||||||
"shader" => BundleFileType::Shader,
|
|
||||||
"shading_environment_mapping" => BundleFileType::ShadingEnvionmentMapping,
|
|
||||||
"shading_environment" => BundleFileType::ShadingEnvironment,
|
|
||||||
"slug_album" => BundleFileType::SlugAlbum,
|
|
||||||
"slug" => BundleFileType::Slug,
|
|
||||||
"sound_environment" => BundleFileType::SoundEnvironment,
|
|
||||||
"spu_job" => BundleFileType::SpuJob,
|
|
||||||
"state_machine" => BundleFileType::StateMachine,
|
|
||||||
"static_pvs" => BundleFileType::StaticPVS,
|
|
||||||
"strings" => BundleFileType::Strings,
|
|
||||||
"surface_properties" => BundleFileType::SurfaceProperties,
|
|
||||||
"texture" => BundleFileType::Texture,
|
|
||||||
"timpani_bank" => BundleFileType::TimpaniBank,
|
|
||||||
"timpani_master" => BundleFileType::TimpaniMaster,
|
|
||||||
"tome" => BundleFileType::Tome,
|
|
||||||
"ugg" => BundleFileType::Ugg,
|
|
||||||
"unit" => BundleFileType::Unit,
|
|
||||||
"upb" => BundleFileType::Upb,
|
|
||||||
"vector_field" => BundleFileType::VectorField,
|
|
||||||
"wav" => BundleFileType::Wav,
|
|
||||||
"wwise_bank" => BundleFileType::WwiseBank,
|
|
||||||
"wwise_dep" => BundleFileType::WwiseDep,
|
|
||||||
"wwise_event" => BundleFileType::WwiseEvent,
|
|
||||||
"wwise_metadata" => BundleFileType::WwiseMetadata,
|
|
||||||
"wwise_stream" => BundleFileType::WwiseStream,
|
|
||||||
"xml" => BundleFileType::Xml,
|
|
||||||
s => eyre::bail!("Unknown type string '{}'", s),
|
|
||||||
};
|
|
||||||
|
|
||||||
Ok(val)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Serialize for BundleFileType {
|
|
||||||
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
|
||||||
where
|
|
||||||
S: serde::Serializer,
|
|
||||||
{
|
|
||||||
let value = self.ext_name();
|
|
||||||
value.serialize(serializer)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl From<Murmur64> for BundleFileType {
|
|
||||||
fn from(value: Murmur64) -> Self {
|
|
||||||
Self::from(Into::<u64>::into(value))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl From<u64> for BundleFileType {
|
|
||||||
fn from(hash: u64) -> BundleFileType {
|
|
||||||
match hash {
|
|
||||||
0x931e336d7646cc26 => BundleFileType::Animation,
|
|
||||||
0xdcfb9e18fff13984 => BundleFileType::AnimationCurves,
|
|
||||||
0x3eed05ba83af5090 => BundleFileType::Apb,
|
|
||||||
0x7ffdb779b04e4ed1 => BundleFileType::BakedLighting,
|
|
||||||
0xaa5965f03029fa18 => BundleFileType::Bik,
|
|
||||||
0xe301e8af94e3b5a3 => BundleFileType::BlendSet,
|
|
||||||
0x18dead01056b72e9 => BundleFileType::Bones,
|
|
||||||
0xb7893adf7567506a => BundleFileType::Chroma,
|
|
||||||
0xfe9754bd19814a47 => BundleFileType::CommonPackage,
|
|
||||||
0x82645835e6b73232 => BundleFileType::Config,
|
|
||||||
0x69108ded1e3e634b => BundleFileType::Crypto,
|
|
||||||
0x8fd0d44d20650b68 => BundleFileType::Data,
|
|
||||||
0x9831ca893b0d087d => BundleFileType::Entity,
|
|
||||||
0x92d3ee038eeb610d => BundleFileType::Flow,
|
|
||||||
0x9efe0a916aae7880 => BundleFileType::Font,
|
|
||||||
0x8f7d5a2c0f967655 => BundleFileType::Ies,
|
|
||||||
0xd526a27da14f1dc5 => BundleFileType::Ini,
|
|
||||||
0x2bbcabe5074ade9e => BundleFileType::Input,
|
|
||||||
0xfa4a8e091a91201e => BundleFileType::Ivf,
|
|
||||||
0xa62f9297dc969e85 => BundleFileType::Keys,
|
|
||||||
0x2a690fd348fe9ac5 => BundleFileType::Level,
|
|
||||||
0xa14e8dfa2cd117e2 => BundleFileType::Lua,
|
|
||||||
0xeac0b497876adedf => BundleFileType::Material,
|
|
||||||
0x3fcdd69156a46417 => BundleFileType::Mod,
|
|
||||||
0xb277b11fe4a61d37 => BundleFileType::MouseCursor,
|
|
||||||
0x169de9566953d264 => BundleFileType::NavData,
|
|
||||||
0x3b1fa9e8f6bac374 => BundleFileType::NetworkConfig,
|
|
||||||
0xb0f2c12eb107f4d8 => BundleFileType::OddleNet,
|
|
||||||
0xad9c6d9ed1e5e77a => BundleFileType::Package,
|
|
||||||
0xa8193123526fad64 => BundleFileType::Particles,
|
|
||||||
0xbf21403a3ab0bbb1 => BundleFileType::PhysicsProperties,
|
|
||||||
0x27862fe24795319c => BundleFileType::RenderConfig,
|
|
||||||
0x9ca183c2d0e76dee => BundleFileType::RtPipeline,
|
|
||||||
0x9d0a795bfe818d19 => BundleFileType::Scene,
|
|
||||||
0xcce8d5b5f5ae333f => BundleFileType::Shader,
|
|
||||||
0xe5ee32a477239a93 => BundleFileType::ShaderLibrary,
|
|
||||||
0x9e5c3cc74575aeb5 => BundleFileType::ShaderLibraryGroup,
|
|
||||||
0x250e0a11ac8e26f8 => BundleFileType::ShadingEnvionmentMapping,
|
|
||||||
0xfe73c7dcff8a7ca5 => BundleFileType::ShadingEnvironment,
|
|
||||||
0xa27b4d04a9ba6f9e => BundleFileType::Slug,
|
|
||||||
0xe9fc9ea7042e5ec0 => BundleFileType::SlugAlbum,
|
|
||||||
0xd8b27864a97ffdd7 => BundleFileType::SoundEnvironment,
|
|
||||||
0xf97af9983c05b950 => BundleFileType::SpuJob,
|
|
||||||
0xa486d4045106165c => BundleFileType::StateMachine,
|
|
||||||
0xe3f0baa17d620321 => BundleFileType::StaticPVS,
|
|
||||||
0x0d972bab10b40fd3 => BundleFileType::Strings,
|
|
||||||
0xad2d3fa30d9ab394 => BundleFileType::SurfaceProperties,
|
|
||||||
0xcd4238c6a0c69e32 => BundleFileType::Texture,
|
|
||||||
0x99736be1fff739a4 => BundleFileType::TimpaniBank,
|
|
||||||
0x00a3e6c59a2b9c6c => BundleFileType::TimpaniMaster,
|
|
||||||
0x19c792357c99f49b => BundleFileType::Tome,
|
|
||||||
0x712d6e3dd1024c9c => BundleFileType::Ugg,
|
|
||||||
0xe0a48d0be9a7453f => BundleFileType::Unit,
|
|
||||||
0xa99510c6e86dd3c2 => BundleFileType::Upb,
|
|
||||||
0xf7505933166d6755 => BundleFileType::VectorField,
|
|
||||||
0x786f65c00a816b19 => BundleFileType::Wav,
|
|
||||||
0x535a7bd3e650d799 => BundleFileType::WwiseBank,
|
|
||||||
0xaf32095c82f2b070 => BundleFileType::WwiseDep,
|
|
||||||
0xaabdd317b58dfc8a => BundleFileType::WwiseEvent,
|
|
||||||
0xd50a8b7e1c82b110 => BundleFileType::WwiseMetadata,
|
|
||||||
0x504b55235d21440e => BundleFileType::WwiseStream,
|
|
||||||
0x76015845a6003765 => BundleFileType::Xml,
|
|
||||||
|
|
||||||
_ => BundleFileType::Unknown(Murmur64::from(hash)),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl From<BundleFileType> for u64 {
|
|
||||||
fn from(t: BundleFileType) -> u64 {
|
|
||||||
match t {
|
|
||||||
BundleFileType::Animation => 0x931e336d7646cc26,
|
|
||||||
BundleFileType::AnimationCurves => 0xdcfb9e18fff13984,
|
|
||||||
BundleFileType::Apb => 0x3eed05ba83af5090,
|
|
||||||
BundleFileType::BakedLighting => 0x7ffdb779b04e4ed1,
|
|
||||||
BundleFileType::Bik => 0xaa5965f03029fa18,
|
|
||||||
BundleFileType::BlendSet => 0xe301e8af94e3b5a3,
|
|
||||||
BundleFileType::Bones => 0x18dead01056b72e9,
|
|
||||||
BundleFileType::Chroma => 0xb7893adf7567506a,
|
|
||||||
BundleFileType::CommonPackage => 0xfe9754bd19814a47,
|
|
||||||
BundleFileType::Config => 0x82645835e6b73232,
|
|
||||||
BundleFileType::Crypto => 0x69108ded1e3e634b,
|
|
||||||
BundleFileType::Data => 0x8fd0d44d20650b68,
|
|
||||||
BundleFileType::Entity => 0x9831ca893b0d087d,
|
|
||||||
BundleFileType::Flow => 0x92d3ee038eeb610d,
|
|
||||||
BundleFileType::Font => 0x9efe0a916aae7880,
|
|
||||||
BundleFileType::Ies => 0x8f7d5a2c0f967655,
|
|
||||||
BundleFileType::Ini => 0xd526a27da14f1dc5,
|
|
||||||
BundleFileType::Input => 0x2bbcabe5074ade9e,
|
|
||||||
BundleFileType::Ivf => 0xfa4a8e091a91201e,
|
|
||||||
BundleFileType::Keys => 0xa62f9297dc969e85,
|
|
||||||
BundleFileType::Level => 0x2a690fd348fe9ac5,
|
|
||||||
BundleFileType::Lua => 0xa14e8dfa2cd117e2,
|
|
||||||
BundleFileType::Material => 0xeac0b497876adedf,
|
|
||||||
BundleFileType::Mod => 0x3fcdd69156a46417,
|
|
||||||
BundleFileType::MouseCursor => 0xb277b11fe4a61d37,
|
|
||||||
BundleFileType::NavData => 0x169de9566953d264,
|
|
||||||
BundleFileType::NetworkConfig => 0x3b1fa9e8f6bac374,
|
|
||||||
BundleFileType::OddleNet => 0xb0f2c12eb107f4d8,
|
|
||||||
BundleFileType::Package => 0xad9c6d9ed1e5e77a,
|
|
||||||
BundleFileType::Particles => 0xa8193123526fad64,
|
|
||||||
BundleFileType::PhysicsProperties => 0xbf21403a3ab0bbb1,
|
|
||||||
BundleFileType::RenderConfig => 0x27862fe24795319c,
|
|
||||||
BundleFileType::RtPipeline => 0x9ca183c2d0e76dee,
|
|
||||||
BundleFileType::Scene => 0x9d0a795bfe818d19,
|
|
||||||
BundleFileType::Shader => 0xcce8d5b5f5ae333f,
|
|
||||||
BundleFileType::ShaderLibrary => 0xe5ee32a477239a93,
|
|
||||||
BundleFileType::ShaderLibraryGroup => 0x9e5c3cc74575aeb5,
|
|
||||||
BundleFileType::ShadingEnvionmentMapping => 0x250e0a11ac8e26f8,
|
|
||||||
BundleFileType::ShadingEnvironment => 0xfe73c7dcff8a7ca5,
|
|
||||||
BundleFileType::Slug => 0xa27b4d04a9ba6f9e,
|
|
||||||
BundleFileType::SlugAlbum => 0xe9fc9ea7042e5ec0,
|
|
||||||
BundleFileType::SoundEnvironment => 0xd8b27864a97ffdd7,
|
|
||||||
BundleFileType::SpuJob => 0xf97af9983c05b950,
|
|
||||||
BundleFileType::StateMachine => 0xa486d4045106165c,
|
|
||||||
BundleFileType::StaticPVS => 0xe3f0baa17d620321,
|
|
||||||
BundleFileType::Strings => 0x0d972bab10b40fd3,
|
|
||||||
BundleFileType::SurfaceProperties => 0xad2d3fa30d9ab394,
|
|
||||||
BundleFileType::Texture => 0xcd4238c6a0c69e32,
|
|
||||||
BundleFileType::TimpaniBank => 0x99736be1fff739a4,
|
|
||||||
BundleFileType::TimpaniMaster => 0x00a3e6c59a2b9c6c,
|
|
||||||
BundleFileType::Tome => 0x19c792357c99f49b,
|
|
||||||
BundleFileType::Ugg => 0x712d6e3dd1024c9c,
|
|
||||||
BundleFileType::Unit => 0xe0a48d0be9a7453f,
|
|
||||||
BundleFileType::Upb => 0xa99510c6e86dd3c2,
|
|
||||||
BundleFileType::VectorField => 0xf7505933166d6755,
|
|
||||||
BundleFileType::Wav => 0x786f65c00a816b19,
|
|
||||||
BundleFileType::WwiseBank => 0x535a7bd3e650d799,
|
|
||||||
BundleFileType::WwiseDep => 0xaf32095c82f2b070,
|
|
||||||
BundleFileType::WwiseEvent => 0xaabdd317b58dfc8a,
|
|
||||||
BundleFileType::WwiseMetadata => 0xd50a8b7e1c82b110,
|
|
||||||
BundleFileType::WwiseStream => 0x504b55235d21440e,
|
|
||||||
BundleFileType::Xml => 0x76015845a6003765,
|
|
||||||
|
|
||||||
BundleFileType::Unknown(hash) => hash.into(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
impl From<BundleFileType> for Murmur64 {
|
|
||||||
fn from(t: BundleFileType) -> Murmur64 {
|
|
||||||
let hash: u64 = t.into();
|
|
||||||
Murmur64::from(hash)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl std::fmt::Display for BundleFileType {
|
|
||||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
|
||||||
write!(f, "{}", self.ext_name())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
struct BundleFileHeader {
|
struct BundleFileHeader {
|
||||||
|
@ -515,7 +120,7 @@ pub struct BundleFile {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl BundleFile {
|
impl BundleFile {
|
||||||
pub fn new(name: String, file_type: BundleFileType) -> Self {
|
pub fn new(name: impl Into<IdString64>, file_type: BundleFileType) -> Self {
|
||||||
Self {
|
Self {
|
||||||
file_type,
|
file_type,
|
||||||
name: name.into(),
|
name: name.into(),
|
||||||
|
@ -647,20 +252,15 @@ impl BundleFile {
|
||||||
Ok(w.into_inner())
|
Ok(w.into_inner())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tracing::instrument(name = "File::from_sjson", skip(sjson))]
|
#[tracing::instrument("File::from_sjson", skip(sjson, name), fields(name = %name.display()))]
|
||||||
pub async fn from_sjson<P, S>(
|
pub async fn from_sjson(
|
||||||
name: String,
|
name: IdString64,
|
||||||
file_type: BundleFileType,
|
file_type: BundleFileType,
|
||||||
sjson: S,
|
sjson: impl AsRef<str>,
|
||||||
root: P,
|
root: impl AsRef<Path> + std::fmt::Debug,
|
||||||
) -> Result<Self>
|
) -> Result<Self> {
|
||||||
where
|
|
||||||
P: AsRef<Path> + std::fmt::Debug,
|
|
||||||
S: AsRef<str>,
|
|
||||||
{
|
|
||||||
match file_type {
|
match file_type {
|
||||||
BundleFileType::Lua => lua::compile(name.clone(), sjson)
|
BundleFileType::Lua => lua::compile(name, sjson).wrap_err("Failed to compile Lua file"),
|
||||||
.wrap_err_with(|| format!("Failed to compile Lua file '{}'", name)),
|
|
||||||
BundleFileType::Unknown(_) => {
|
BundleFileType::Unknown(_) => {
|
||||||
eyre::bail!("Unknown file type. Cannot compile from SJSON");
|
eyre::bail!("Unknown file type. Cannot compile from SJSON");
|
||||||
}
|
}
|
||||||
|
@ -699,10 +299,7 @@ impl BundleFile {
|
||||||
s
|
s
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn matches_name<S>(&self, name: S) -> bool
|
pub fn matches_name(&self, name: impl Into<IdString64>) -> bool {
|
||||||
where
|
|
||||||
S: Into<IdString64>,
|
|
||||||
{
|
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
if self.name == name {
|
if self.name == name {
|
||||||
return true;
|
return true;
|
||||||
|
|
400
lib/sdk/src/bundle/filetype.rs
Normal file
400
lib/sdk/src/bundle/filetype.rs
Normal file
|
@ -0,0 +1,400 @@
|
||||||
|
use color_eyre::{eyre, Result};
|
||||||
|
use serde::Serialize;
|
||||||
|
|
||||||
|
use crate::murmur::Murmur64;
|
||||||
|
|
||||||
|
#[derive(Debug, Hash, PartialEq, Eq, Copy, Clone)]
|
||||||
|
pub enum BundleFileType {
|
||||||
|
Animation,
|
||||||
|
AnimationCurves,
|
||||||
|
Apb,
|
||||||
|
BakedLighting,
|
||||||
|
Bik,
|
||||||
|
BlendSet,
|
||||||
|
Bones,
|
||||||
|
Chroma,
|
||||||
|
CommonPackage,
|
||||||
|
Config,
|
||||||
|
Crypto,
|
||||||
|
Data,
|
||||||
|
Entity,
|
||||||
|
Flow,
|
||||||
|
Font,
|
||||||
|
Ies,
|
||||||
|
Ini,
|
||||||
|
Input,
|
||||||
|
Ivf,
|
||||||
|
Keys,
|
||||||
|
Level,
|
||||||
|
Lua,
|
||||||
|
Material,
|
||||||
|
Mod,
|
||||||
|
MouseCursor,
|
||||||
|
NavData,
|
||||||
|
NetworkConfig,
|
||||||
|
OddleNet,
|
||||||
|
Package,
|
||||||
|
Particles,
|
||||||
|
PhysicsProperties,
|
||||||
|
RenderConfig,
|
||||||
|
RtPipeline,
|
||||||
|
Scene,
|
||||||
|
Shader,
|
||||||
|
ShaderLibrary,
|
||||||
|
ShaderLibraryGroup,
|
||||||
|
ShadingEnvionmentMapping,
|
||||||
|
ShadingEnvironment,
|
||||||
|
Slug,
|
||||||
|
SlugAlbum,
|
||||||
|
SoundEnvironment,
|
||||||
|
SpuJob,
|
||||||
|
StateMachine,
|
||||||
|
StaticPVS,
|
||||||
|
Strings,
|
||||||
|
SurfaceProperties,
|
||||||
|
Texture,
|
||||||
|
TimpaniBank,
|
||||||
|
TimpaniMaster,
|
||||||
|
Tome,
|
||||||
|
Ugg,
|
||||||
|
Unit,
|
||||||
|
Upb,
|
||||||
|
VectorField,
|
||||||
|
Wav,
|
||||||
|
WwiseBank,
|
||||||
|
WwiseDep,
|
||||||
|
WwiseEvent,
|
||||||
|
WwiseMetadata,
|
||||||
|
WwiseStream,
|
||||||
|
Xml,
|
||||||
|
|
||||||
|
Unknown(Murmur64),
|
||||||
|
}
|
||||||
|
|
||||||
|
impl BundleFileType {
|
||||||
|
pub fn ext_name(&self) -> String {
|
||||||
|
match self {
|
||||||
|
BundleFileType::AnimationCurves => String::from("animation_curves"),
|
||||||
|
BundleFileType::Animation => String::from("animation"),
|
||||||
|
BundleFileType::Apb => String::from("apb"),
|
||||||
|
BundleFileType::BakedLighting => String::from("baked_lighting"),
|
||||||
|
BundleFileType::Bik => String::from("bik"),
|
||||||
|
BundleFileType::BlendSet => String::from("blend_set"),
|
||||||
|
BundleFileType::Bones => String::from("bones"),
|
||||||
|
BundleFileType::Chroma => String::from("chroma"),
|
||||||
|
BundleFileType::CommonPackage => String::from("common_package"),
|
||||||
|
BundleFileType::Config => String::from("config"),
|
||||||
|
BundleFileType::Crypto => String::from("crypto"),
|
||||||
|
BundleFileType::Data => String::from("data"),
|
||||||
|
BundleFileType::Entity => String::from("entity"),
|
||||||
|
BundleFileType::Flow => String::from("flow"),
|
||||||
|
BundleFileType::Font => String::from("font"),
|
||||||
|
BundleFileType::Ies => String::from("ies"),
|
||||||
|
BundleFileType::Ini => String::from("ini"),
|
||||||
|
BundleFileType::Input => String::from("input"),
|
||||||
|
BundleFileType::Ivf => String::from("ivf"),
|
||||||
|
BundleFileType::Keys => String::from("keys"),
|
||||||
|
BundleFileType::Level => String::from("level"),
|
||||||
|
BundleFileType::Lua => String::from("lua"),
|
||||||
|
BundleFileType::Material => String::from("material"),
|
||||||
|
BundleFileType::Mod => String::from("mod"),
|
||||||
|
BundleFileType::MouseCursor => String::from("mouse_cursor"),
|
||||||
|
BundleFileType::NavData => String::from("nav_data"),
|
||||||
|
BundleFileType::NetworkConfig => String::from("network_config"),
|
||||||
|
BundleFileType::OddleNet => String::from("oodle_net"),
|
||||||
|
BundleFileType::Package => String::from("package"),
|
||||||
|
BundleFileType::Particles => String::from("particles"),
|
||||||
|
BundleFileType::PhysicsProperties => String::from("physics_properties"),
|
||||||
|
BundleFileType::RenderConfig => String::from("render_config"),
|
||||||
|
BundleFileType::RtPipeline => String::from("rt_pipeline"),
|
||||||
|
BundleFileType::Scene => String::from("scene"),
|
||||||
|
BundleFileType::ShaderLibraryGroup => String::from("shader_library_group"),
|
||||||
|
BundleFileType::ShaderLibrary => String::from("shader_library"),
|
||||||
|
BundleFileType::Shader => String::from("shader"),
|
||||||
|
BundleFileType::ShadingEnvionmentMapping => String::from("shading_environment_mapping"),
|
||||||
|
BundleFileType::ShadingEnvironment => String::from("shading_environment"),
|
||||||
|
BundleFileType::SlugAlbum => String::from("slug_album"),
|
||||||
|
BundleFileType::Slug => String::from("slug"),
|
||||||
|
BundleFileType::SoundEnvironment => String::from("sound_environment"),
|
||||||
|
BundleFileType::SpuJob => String::from("spu_job"),
|
||||||
|
BundleFileType::StateMachine => String::from("state_machine"),
|
||||||
|
BundleFileType::StaticPVS => String::from("static_pvs"),
|
||||||
|
BundleFileType::Strings => String::from("strings"),
|
||||||
|
BundleFileType::SurfaceProperties => String::from("surface_properties"),
|
||||||
|
BundleFileType::Texture => String::from("texture"),
|
||||||
|
BundleFileType::TimpaniBank => String::from("timpani_bank"),
|
||||||
|
BundleFileType::TimpaniMaster => String::from("timpani_master"),
|
||||||
|
BundleFileType::Tome => String::from("tome"),
|
||||||
|
BundleFileType::Ugg => String::from("ugg"),
|
||||||
|
BundleFileType::Unit => String::from("unit"),
|
||||||
|
BundleFileType::Upb => String::from("upb"),
|
||||||
|
BundleFileType::VectorField => String::from("vector_field"),
|
||||||
|
BundleFileType::Wav => String::from("wav"),
|
||||||
|
BundleFileType::WwiseBank => String::from("wwise_bank"),
|
||||||
|
BundleFileType::WwiseDep => String::from("wwise_dep"),
|
||||||
|
BundleFileType::WwiseEvent => String::from("wwise_event"),
|
||||||
|
BundleFileType::WwiseMetadata => String::from("wwise_metadata"),
|
||||||
|
BundleFileType::WwiseStream => String::from("wwise_stream"),
|
||||||
|
BundleFileType::Xml => String::from("xml"),
|
||||||
|
|
||||||
|
BundleFileType::Unknown(s) => format!("{s:016X}"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn decompiled_ext_name(&self) -> String {
|
||||||
|
match self {
|
||||||
|
BundleFileType::Texture => String::from("dds"),
|
||||||
|
BundleFileType::WwiseBank => String::from("bnk"),
|
||||||
|
BundleFileType::WwiseStream => String::from("ogg"),
|
||||||
|
_ => self.ext_name(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn hash(&self) -> Murmur64 {
|
||||||
|
Murmur64::from(*self)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl std::str::FromStr for BundleFileType {
|
||||||
|
type Err = color_eyre::Report;
|
||||||
|
|
||||||
|
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||||
|
let val = match s {
|
||||||
|
"animation_curves" => BundleFileType::AnimationCurves,
|
||||||
|
"animation" => BundleFileType::Animation,
|
||||||
|
"apb" => BundleFileType::Apb,
|
||||||
|
"baked_lighting" => BundleFileType::BakedLighting,
|
||||||
|
"bik" => BundleFileType::Bik,
|
||||||
|
"blend_set" => BundleFileType::BlendSet,
|
||||||
|
"bones" => BundleFileType::Bones,
|
||||||
|
"chroma" => BundleFileType::Chroma,
|
||||||
|
"common_package" => BundleFileType::CommonPackage,
|
||||||
|
"config" => BundleFileType::Config,
|
||||||
|
"crypto" => BundleFileType::Crypto,
|
||||||
|
"data" => BundleFileType::Data,
|
||||||
|
"entity" => BundleFileType::Entity,
|
||||||
|
"flow" => BundleFileType::Flow,
|
||||||
|
"font" => BundleFileType::Font,
|
||||||
|
"ies" => BundleFileType::Ies,
|
||||||
|
"ini" => BundleFileType::Ini,
|
||||||
|
"input" => BundleFileType::Input,
|
||||||
|
"ivf" => BundleFileType::Ivf,
|
||||||
|
"keys" => BundleFileType::Keys,
|
||||||
|
"level" => BundleFileType::Level,
|
||||||
|
"lua" => BundleFileType::Lua,
|
||||||
|
"material" => BundleFileType::Material,
|
||||||
|
"mod" => BundleFileType::Mod,
|
||||||
|
"mouse_cursor" => BundleFileType::MouseCursor,
|
||||||
|
"nav_data" => BundleFileType::NavData,
|
||||||
|
"network_config" => BundleFileType::NetworkConfig,
|
||||||
|
"oodle_net" => BundleFileType::OddleNet,
|
||||||
|
"package" => BundleFileType::Package,
|
||||||
|
"particles" => BundleFileType::Particles,
|
||||||
|
"physics_properties" => BundleFileType::PhysicsProperties,
|
||||||
|
"render_config" => BundleFileType::RenderConfig,
|
||||||
|
"rt_pipeline" => BundleFileType::RtPipeline,
|
||||||
|
"scene" => BundleFileType::Scene,
|
||||||
|
"shader_library_group" => BundleFileType::ShaderLibraryGroup,
|
||||||
|
"shader_library" => BundleFileType::ShaderLibrary,
|
||||||
|
"shader" => BundleFileType::Shader,
|
||||||
|
"shading_environment_mapping" => BundleFileType::ShadingEnvionmentMapping,
|
||||||
|
"shading_environment" => BundleFileType::ShadingEnvironment,
|
||||||
|
"slug_album" => BundleFileType::SlugAlbum,
|
||||||
|
"slug" => BundleFileType::Slug,
|
||||||
|
"sound_environment" => BundleFileType::SoundEnvironment,
|
||||||
|
"spu_job" => BundleFileType::SpuJob,
|
||||||
|
"state_machine" => BundleFileType::StateMachine,
|
||||||
|
"static_pvs" => BundleFileType::StaticPVS,
|
||||||
|
"strings" => BundleFileType::Strings,
|
||||||
|
"surface_properties" => BundleFileType::SurfaceProperties,
|
||||||
|
"texture" => BundleFileType::Texture,
|
||||||
|
"timpani_bank" => BundleFileType::TimpaniBank,
|
||||||
|
"timpani_master" => BundleFileType::TimpaniMaster,
|
||||||
|
"tome" => BundleFileType::Tome,
|
||||||
|
"ugg" => BundleFileType::Ugg,
|
||||||
|
"unit" => BundleFileType::Unit,
|
||||||
|
"upb" => BundleFileType::Upb,
|
||||||
|
"vector_field" => BundleFileType::VectorField,
|
||||||
|
"wav" => BundleFileType::Wav,
|
||||||
|
"wwise_bank" => BundleFileType::WwiseBank,
|
||||||
|
"wwise_dep" => BundleFileType::WwiseDep,
|
||||||
|
"wwise_event" => BundleFileType::WwiseEvent,
|
||||||
|
"wwise_metadata" => BundleFileType::WwiseMetadata,
|
||||||
|
"wwise_stream" => BundleFileType::WwiseStream,
|
||||||
|
"xml" => BundleFileType::Xml,
|
||||||
|
s => eyre::bail!("Unknown type string '{}'", s),
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(val)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Serialize for BundleFileType {
|
||||||
|
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
|
||||||
|
where
|
||||||
|
S: serde::Serializer,
|
||||||
|
{
|
||||||
|
let value = self.ext_name();
|
||||||
|
value.serialize(serializer)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<Murmur64> for BundleFileType {
|
||||||
|
fn from(value: Murmur64) -> Self {
|
||||||
|
Self::from(Into::<u64>::into(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<u64> for BundleFileType {
|
||||||
|
fn from(hash: u64) -> BundleFileType {
|
||||||
|
match hash {
|
||||||
|
0x931e336d7646cc26 => BundleFileType::Animation,
|
||||||
|
0xdcfb9e18fff13984 => BundleFileType::AnimationCurves,
|
||||||
|
0x3eed05ba83af5090 => BundleFileType::Apb,
|
||||||
|
0x7ffdb779b04e4ed1 => BundleFileType::BakedLighting,
|
||||||
|
0xaa5965f03029fa18 => BundleFileType::Bik,
|
||||||
|
0xe301e8af94e3b5a3 => BundleFileType::BlendSet,
|
||||||
|
0x18dead01056b72e9 => BundleFileType::Bones,
|
||||||
|
0xb7893adf7567506a => BundleFileType::Chroma,
|
||||||
|
0xfe9754bd19814a47 => BundleFileType::CommonPackage,
|
||||||
|
0x82645835e6b73232 => BundleFileType::Config,
|
||||||
|
0x69108ded1e3e634b => BundleFileType::Crypto,
|
||||||
|
0x8fd0d44d20650b68 => BundleFileType::Data,
|
||||||
|
0x9831ca893b0d087d => BundleFileType::Entity,
|
||||||
|
0x92d3ee038eeb610d => BundleFileType::Flow,
|
||||||
|
0x9efe0a916aae7880 => BundleFileType::Font,
|
||||||
|
0x8f7d5a2c0f967655 => BundleFileType::Ies,
|
||||||
|
0xd526a27da14f1dc5 => BundleFileType::Ini,
|
||||||
|
0x2bbcabe5074ade9e => BundleFileType::Input,
|
||||||
|
0xfa4a8e091a91201e => BundleFileType::Ivf,
|
||||||
|
0xa62f9297dc969e85 => BundleFileType::Keys,
|
||||||
|
0x2a690fd348fe9ac5 => BundleFileType::Level,
|
||||||
|
0xa14e8dfa2cd117e2 => BundleFileType::Lua,
|
||||||
|
0xeac0b497876adedf => BundleFileType::Material,
|
||||||
|
0x3fcdd69156a46417 => BundleFileType::Mod,
|
||||||
|
0xb277b11fe4a61d37 => BundleFileType::MouseCursor,
|
||||||
|
0x169de9566953d264 => BundleFileType::NavData,
|
||||||
|
0x3b1fa9e8f6bac374 => BundleFileType::NetworkConfig,
|
||||||
|
0xb0f2c12eb107f4d8 => BundleFileType::OddleNet,
|
||||||
|
0xad9c6d9ed1e5e77a => BundleFileType::Package,
|
||||||
|
0xa8193123526fad64 => BundleFileType::Particles,
|
||||||
|
0xbf21403a3ab0bbb1 => BundleFileType::PhysicsProperties,
|
||||||
|
0x27862fe24795319c => BundleFileType::RenderConfig,
|
||||||
|
0x9ca183c2d0e76dee => BundleFileType::RtPipeline,
|
||||||
|
0x9d0a795bfe818d19 => BundleFileType::Scene,
|
||||||
|
0xcce8d5b5f5ae333f => BundleFileType::Shader,
|
||||||
|
0xe5ee32a477239a93 => BundleFileType::ShaderLibrary,
|
||||||
|
0x9e5c3cc74575aeb5 => BundleFileType::ShaderLibraryGroup,
|
||||||
|
0x250e0a11ac8e26f8 => BundleFileType::ShadingEnvionmentMapping,
|
||||||
|
0xfe73c7dcff8a7ca5 => BundleFileType::ShadingEnvironment,
|
||||||
|
0xa27b4d04a9ba6f9e => BundleFileType::Slug,
|
||||||
|
0xe9fc9ea7042e5ec0 => BundleFileType::SlugAlbum,
|
||||||
|
0xd8b27864a97ffdd7 => BundleFileType::SoundEnvironment,
|
||||||
|
0xf97af9983c05b950 => BundleFileType::SpuJob,
|
||||||
|
0xa486d4045106165c => BundleFileType::StateMachine,
|
||||||
|
0xe3f0baa17d620321 => BundleFileType::StaticPVS,
|
||||||
|
0x0d972bab10b40fd3 => BundleFileType::Strings,
|
||||||
|
0xad2d3fa30d9ab394 => BundleFileType::SurfaceProperties,
|
||||||
|
0xcd4238c6a0c69e32 => BundleFileType::Texture,
|
||||||
|
0x99736be1fff739a4 => BundleFileType::TimpaniBank,
|
||||||
|
0x00a3e6c59a2b9c6c => BundleFileType::TimpaniMaster,
|
||||||
|
0x19c792357c99f49b => BundleFileType::Tome,
|
||||||
|
0x712d6e3dd1024c9c => BundleFileType::Ugg,
|
||||||
|
0xe0a48d0be9a7453f => BundleFileType::Unit,
|
||||||
|
0xa99510c6e86dd3c2 => BundleFileType::Upb,
|
||||||
|
0xf7505933166d6755 => BundleFileType::VectorField,
|
||||||
|
0x786f65c00a816b19 => BundleFileType::Wav,
|
||||||
|
0x535a7bd3e650d799 => BundleFileType::WwiseBank,
|
||||||
|
0xaf32095c82f2b070 => BundleFileType::WwiseDep,
|
||||||
|
0xaabdd317b58dfc8a => BundleFileType::WwiseEvent,
|
||||||
|
0xd50a8b7e1c82b110 => BundleFileType::WwiseMetadata,
|
||||||
|
0x504b55235d21440e => BundleFileType::WwiseStream,
|
||||||
|
0x76015845a6003765 => BundleFileType::Xml,
|
||||||
|
|
||||||
|
_ => BundleFileType::Unknown(Murmur64::from(hash)),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<BundleFileType> for u64 {
|
||||||
|
fn from(t: BundleFileType) -> u64 {
|
||||||
|
match t {
|
||||||
|
BundleFileType::Animation => 0x931e336d7646cc26,
|
||||||
|
BundleFileType::AnimationCurves => 0xdcfb9e18fff13984,
|
||||||
|
BundleFileType::Apb => 0x3eed05ba83af5090,
|
||||||
|
BundleFileType::BakedLighting => 0x7ffdb779b04e4ed1,
|
||||||
|
BundleFileType::Bik => 0xaa5965f03029fa18,
|
||||||
|
BundleFileType::BlendSet => 0xe301e8af94e3b5a3,
|
||||||
|
BundleFileType::Bones => 0x18dead01056b72e9,
|
||||||
|
BundleFileType::Chroma => 0xb7893adf7567506a,
|
||||||
|
BundleFileType::CommonPackage => 0xfe9754bd19814a47,
|
||||||
|
BundleFileType::Config => 0x82645835e6b73232,
|
||||||
|
BundleFileType::Crypto => 0x69108ded1e3e634b,
|
||||||
|
BundleFileType::Data => 0x8fd0d44d20650b68,
|
||||||
|
BundleFileType::Entity => 0x9831ca893b0d087d,
|
||||||
|
BundleFileType::Flow => 0x92d3ee038eeb610d,
|
||||||
|
BundleFileType::Font => 0x9efe0a916aae7880,
|
||||||
|
BundleFileType::Ies => 0x8f7d5a2c0f967655,
|
||||||
|
BundleFileType::Ini => 0xd526a27da14f1dc5,
|
||||||
|
BundleFileType::Input => 0x2bbcabe5074ade9e,
|
||||||
|
BundleFileType::Ivf => 0xfa4a8e091a91201e,
|
||||||
|
BundleFileType::Keys => 0xa62f9297dc969e85,
|
||||||
|
BundleFileType::Level => 0x2a690fd348fe9ac5,
|
||||||
|
BundleFileType::Lua => 0xa14e8dfa2cd117e2,
|
||||||
|
BundleFileType::Material => 0xeac0b497876adedf,
|
||||||
|
BundleFileType::Mod => 0x3fcdd69156a46417,
|
||||||
|
BundleFileType::MouseCursor => 0xb277b11fe4a61d37,
|
||||||
|
BundleFileType::NavData => 0x169de9566953d264,
|
||||||
|
BundleFileType::NetworkConfig => 0x3b1fa9e8f6bac374,
|
||||||
|
BundleFileType::OddleNet => 0xb0f2c12eb107f4d8,
|
||||||
|
BundleFileType::Package => 0xad9c6d9ed1e5e77a,
|
||||||
|
BundleFileType::Particles => 0xa8193123526fad64,
|
||||||
|
BundleFileType::PhysicsProperties => 0xbf21403a3ab0bbb1,
|
||||||
|
BundleFileType::RenderConfig => 0x27862fe24795319c,
|
||||||
|
BundleFileType::RtPipeline => 0x9ca183c2d0e76dee,
|
||||||
|
BundleFileType::Scene => 0x9d0a795bfe818d19,
|
||||||
|
BundleFileType::Shader => 0xcce8d5b5f5ae333f,
|
||||||
|
BundleFileType::ShaderLibrary => 0xe5ee32a477239a93,
|
||||||
|
BundleFileType::ShaderLibraryGroup => 0x9e5c3cc74575aeb5,
|
||||||
|
BundleFileType::ShadingEnvionmentMapping => 0x250e0a11ac8e26f8,
|
||||||
|
BundleFileType::ShadingEnvironment => 0xfe73c7dcff8a7ca5,
|
||||||
|
BundleFileType::Slug => 0xa27b4d04a9ba6f9e,
|
||||||
|
BundleFileType::SlugAlbum => 0xe9fc9ea7042e5ec0,
|
||||||
|
BundleFileType::SoundEnvironment => 0xd8b27864a97ffdd7,
|
||||||
|
BundleFileType::SpuJob => 0xf97af9983c05b950,
|
||||||
|
BundleFileType::StateMachine => 0xa486d4045106165c,
|
||||||
|
BundleFileType::StaticPVS => 0xe3f0baa17d620321,
|
||||||
|
BundleFileType::Strings => 0x0d972bab10b40fd3,
|
||||||
|
BundleFileType::SurfaceProperties => 0xad2d3fa30d9ab394,
|
||||||
|
BundleFileType::Texture => 0xcd4238c6a0c69e32,
|
||||||
|
BundleFileType::TimpaniBank => 0x99736be1fff739a4,
|
||||||
|
BundleFileType::TimpaniMaster => 0x00a3e6c59a2b9c6c,
|
||||||
|
BundleFileType::Tome => 0x19c792357c99f49b,
|
||||||
|
BundleFileType::Ugg => 0x712d6e3dd1024c9c,
|
||||||
|
BundleFileType::Unit => 0xe0a48d0be9a7453f,
|
||||||
|
BundleFileType::Upb => 0xa99510c6e86dd3c2,
|
||||||
|
BundleFileType::VectorField => 0xf7505933166d6755,
|
||||||
|
BundleFileType::Wav => 0x786f65c00a816b19,
|
||||||
|
BundleFileType::WwiseBank => 0x535a7bd3e650d799,
|
||||||
|
BundleFileType::WwiseDep => 0xaf32095c82f2b070,
|
||||||
|
BundleFileType::WwiseEvent => 0xaabdd317b58dfc8a,
|
||||||
|
BundleFileType::WwiseMetadata => 0xd50a8b7e1c82b110,
|
||||||
|
BundleFileType::WwiseStream => 0x504b55235d21440e,
|
||||||
|
BundleFileType::Xml => 0x76015845a6003765,
|
||||||
|
|
||||||
|
BundleFileType::Unknown(hash) => hash.into(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
impl From<BundleFileType> for Murmur64 {
|
||||||
|
fn from(t: BundleFileType) -> Murmur64 {
|
||||||
|
let hash: u64 = t.into();
|
||||||
|
Murmur64::from(hash)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl std::fmt::Display for BundleFileType {
|
||||||
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
|
write!(f, "{}", self.ext_name())
|
||||||
|
}
|
||||||
|
}
|
|
@ -12,8 +12,10 @@ use crate::murmur::{HashGroup, IdString64, Murmur64};
|
||||||
|
|
||||||
pub(crate) mod database;
|
pub(crate) mod database;
|
||||||
pub(crate) mod file;
|
pub(crate) mod file;
|
||||||
|
pub(crate) mod filetype;
|
||||||
|
|
||||||
pub use file::{BundleFile, BundleFileType, BundleFileVariant};
|
pub use file::{BundleFile, BundleFileVariant};
|
||||||
|
pub use filetype::BundleFileType;
|
||||||
|
|
||||||
#[derive(Clone, Copy, Debug, PartialEq, PartialOrd)]
|
#[derive(Clone, Copy, Debug, PartialEq, PartialOrd)]
|
||||||
enum BundleFormat {
|
enum BundleFormat {
|
||||||
|
|
|
@ -15,6 +15,7 @@ use tokio::fs;
|
||||||
use crate::binary::sync::ReadExt;
|
use crate::binary::sync::ReadExt;
|
||||||
use crate::binary::sync::WriteExt;
|
use crate::binary::sync::WriteExt;
|
||||||
use crate::bundle::file::{BundleFileVariant, UserFile};
|
use crate::bundle::file::{BundleFileVariant, UserFile};
|
||||||
|
use crate::murmur::IdString64;
|
||||||
use crate::{BundleFile, BundleFileType};
|
use crate::{BundleFile, BundleFileType};
|
||||||
|
|
||||||
const BITSQUID_LUAJIT_HEADER: u32 = 0x8253461B;
|
const BITSQUID_LUAJIT_HEADER: u32 = 0x8253461B;
|
||||||
|
@ -117,17 +118,13 @@ where
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tracing::instrument(skip_all)]
|
#[tracing::instrument(skip_all)]
|
||||||
pub fn compile<S, C>(name: S, code: C) -> Result<BundleFile>
|
pub fn compile(name: impl Into<IdString64>, code: impl AsRef<str>) -> Result<BundleFile> {
|
||||||
where
|
|
||||||
S: Into<String>,
|
|
||||||
C: AsRef<str>,
|
|
||||||
{
|
|
||||||
let name = name.into();
|
let name = name.into();
|
||||||
let code = code.as_ref();
|
let code = code.as_ref();
|
||||||
|
|
||||||
tracing::trace!(
|
tracing::trace!(
|
||||||
"Compiling '{}', {} bytes of code",
|
"Compiling '{}', {} bytes of code",
|
||||||
name,
|
name.display(),
|
||||||
code.as_bytes().len()
|
code.as_bytes().len()
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -135,8 +132,8 @@ where
|
||||||
let state = lua::luaL_newstate();
|
let state = lua::luaL_newstate();
|
||||||
lua::luaL_openlibs(state);
|
lua::luaL_openlibs(state);
|
||||||
|
|
||||||
let name = CString::new(format!("@{name}").into_bytes())
|
let name = CString::new(format!("@{}", name.display()).into_bytes())
|
||||||
.wrap_err_with(|| format!("Cannot convert name into CString: {}", name))?;
|
.wrap_err_with(|| format!("Cannot convert name into CString: {}", name.display()))?;
|
||||||
match lua::luaL_loadbuffer(
|
match lua::luaL_loadbuffer(
|
||||||
state,
|
state,
|
||||||
code.as_ptr() as _,
|
code.as_ptr() as _,
|
||||||
|
|
|
@ -7,12 +7,12 @@ use std::str::FromStr;
|
||||||
use async_recursion::async_recursion;
|
use async_recursion::async_recursion;
|
||||||
use color_eyre::eyre::{self, Context};
|
use color_eyre::eyre::{self, Context};
|
||||||
use color_eyre::Result;
|
use color_eyre::Result;
|
||||||
use path_slash::PathBufExt;
|
|
||||||
use tokio::fs;
|
use tokio::fs;
|
||||||
|
|
||||||
use crate::binary::sync::{ReadExt, WriteExt};
|
use crate::binary::sync::{ReadExt, WriteExt};
|
||||||
use crate::bundle::file::{BundleFileType, UserFile};
|
use crate::bundle::file::UserFile;
|
||||||
use crate::murmur::{HashGroup, Murmur64};
|
use crate::bundle::filetype::BundleFileType;
|
||||||
|
use crate::murmur::{HashGroup, IdString64, Murmur64};
|
||||||
|
|
||||||
#[tracing::instrument]
|
#[tracing::instrument]
|
||||||
#[async_recursion]
|
#[async_recursion]
|
||||||
|
@ -90,12 +90,12 @@ where
|
||||||
Ok(paths)
|
Ok(paths)
|
||||||
}
|
}
|
||||||
|
|
||||||
type PackageType = HashMap<BundleFileType, HashSet<PathBuf>>;
|
type PackageType = HashMap<BundleFileType, HashSet<String>>;
|
||||||
type PackageDefinition = HashMap<String, HashSet<String>>;
|
type PackageDefinition = HashMap<String, HashSet<String>>;
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
pub struct Package {
|
pub struct Package {
|
||||||
_name: String,
|
_name: IdString64,
|
||||||
_root: PathBuf,
|
_root: PathBuf,
|
||||||
inner: PackageType,
|
inner: PackageType,
|
||||||
flags: u8,
|
flags: u8,
|
||||||
|
@ -116,9 +116,9 @@ impl DerefMut for Package {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Package {
|
impl Package {
|
||||||
pub fn new(name: String, root: PathBuf) -> Self {
|
pub fn new(name: impl Into<IdString64>, root: PathBuf) -> Self {
|
||||||
Self {
|
Self {
|
||||||
_name: name,
|
_name: name.into(),
|
||||||
_root: root,
|
_root: root,
|
||||||
inner: Default::default(),
|
inner: Default::default(),
|
||||||
flags: 1,
|
flags: 1,
|
||||||
|
@ -129,17 +129,22 @@ impl Package {
|
||||||
self.values().fold(0, |total, files| total + files.len())
|
self.values().fold(0, |total, files| total + files.len())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn add_file<P: Into<PathBuf>>(&mut self, file_type: BundleFileType, name: P) {
|
pub fn add_file(&mut self, file_type: BundleFileType, name: impl Into<String>) {
|
||||||
self.inner.entry(file_type).or_default().insert(name.into());
|
self.inner.entry(file_type).or_default().insert(name.into());
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tracing::instrument("Package::from_sjson", skip(sjson), fields(sjson_len = sjson.as_ref().len()))]
|
#[tracing::instrument("Package::from_sjson", skip(sjson), fields(sjson_len = sjson.as_ref().len()))]
|
||||||
pub async fn from_sjson<P, S>(sjson: S, name: String, root: P) -> Result<Self>
|
pub async fn from_sjson<P, S>(
|
||||||
|
sjson: S,
|
||||||
|
name: impl Into<IdString64> + std::fmt::Debug,
|
||||||
|
root: P,
|
||||||
|
) -> Result<Self>
|
||||||
where
|
where
|
||||||
P: AsRef<Path> + std::fmt::Debug,
|
P: AsRef<Path> + std::fmt::Debug,
|
||||||
S: AsRef<str>,
|
S: AsRef<str>,
|
||||||
{
|
{
|
||||||
let root = root.as_ref();
|
let root = root.as_ref();
|
||||||
|
let name = name.into();
|
||||||
let definition: PackageDefinition = serde_sjson::from_str(sjson.as_ref())?;
|
let definition: PackageDefinition = serde_sjson::from_str(sjson.as_ref())?;
|
||||||
let mut inner: PackageType = Default::default();
|
let mut inner: PackageType = Default::default();
|
||||||
|
|
||||||
|
@ -173,7 +178,11 @@ impl Package {
|
||||||
continue;
|
continue;
|
||||||
};
|
};
|
||||||
|
|
||||||
inner.entry(t).or_default().insert(path);
|
tracing::debug!("Adding file {}", path.display());
|
||||||
|
inner
|
||||||
|
.entry(t)
|
||||||
|
.or_default()
|
||||||
|
.insert(path.display().to_string());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -192,11 +201,9 @@ impl Package {
|
||||||
pub fn to_sjson(&self) -> Result<String> {
|
pub fn to_sjson(&self) -> Result<String> {
|
||||||
let mut map: PackageDefinition = Default::default();
|
let mut map: PackageDefinition = Default::default();
|
||||||
|
|
||||||
for (t, paths) in self.iter() {
|
for (t, names) in self.iter() {
|
||||||
for path in paths.iter() {
|
for name in names.iter() {
|
||||||
map.entry(t.ext_name())
|
map.entry(t.ext_name()).or_default().insert(name.clone());
|
||||||
.or_default()
|
|
||||||
.insert(path.display().to_string());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -222,11 +229,11 @@ impl Package {
|
||||||
for _ in 0..file_count {
|
for _ in 0..file_count {
|
||||||
let t = BundleFileType::from(r.read_u64()?);
|
let t = BundleFileType::from(r.read_u64()?);
|
||||||
let hash = Murmur64::from(r.read_u64()?);
|
let hash = Murmur64::from(r.read_u64()?);
|
||||||
let path = ctx.lookup_hash(hash, HashGroup::Filename);
|
let name = ctx.lookup_hash(hash, HashGroup::Filename);
|
||||||
inner
|
inner
|
||||||
.entry(t)
|
.entry(t)
|
||||||
.or_default()
|
.or_default()
|
||||||
.insert(PathBuf::from(path.display().to_string()));
|
.insert(name.display().to_string());
|
||||||
}
|
}
|
||||||
|
|
||||||
let flags = r.read_u8()?;
|
let flags = r.read_u8()?;
|
||||||
|
@ -239,7 +246,7 @@ impl Package {
|
||||||
|
|
||||||
let pkg = Self {
|
let pkg = Self {
|
||||||
inner,
|
inner,
|
||||||
_name: name,
|
_name: name.into(),
|
||||||
_root: PathBuf::new(),
|
_root: PathBuf::new(),
|
||||||
flags,
|
flags,
|
||||||
};
|
};
|
||||||
|
@ -255,12 +262,10 @@ impl Package {
|
||||||
w.write_u32(0x2b)?;
|
w.write_u32(0x2b)?;
|
||||||
w.write_u32(self.values().flatten().count() as u32)?;
|
w.write_u32(self.values().flatten().count() as u32)?;
|
||||||
|
|
||||||
for (t, paths) in self.iter() {
|
for (t, names) in self.iter() {
|
||||||
for path in paths.iter() {
|
for name in names.iter() {
|
||||||
w.write_u64(t.hash().into())?;
|
w.write_u64(t.hash().into())?;
|
||||||
|
w.write_u64(Murmur64::hash(name.as_bytes()).into())?;
|
||||||
let hash = Murmur64::hash(path.to_slash_lossy().as_bytes());
|
|
||||||
w.write_u64(hash.into())?;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -280,17 +285,11 @@ where
|
||||||
Ok(vec![UserFile::new(s.into_bytes())])
|
Ok(vec![UserFile::new(s.into_bytes())])
|
||||||
}
|
}
|
||||||
|
|
||||||
// #[tracing::instrument(skip_all)]
|
|
||||||
// pub fn compile(_ctx: &crate::Context, data: String) -> Result<Vec<u8>> {
|
|
||||||
// let pkg = Package::from_sjson(data)?;
|
|
||||||
// pkg.to_binary()
|
|
||||||
// }
|
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod test {
|
mod test {
|
||||||
use std::path::PathBuf;
|
use std::path::PathBuf;
|
||||||
|
|
||||||
use crate::BundleFileType;
|
use crate::bundle::filetype::BundleFileType;
|
||||||
|
|
||||||
use super::resolve_wildcard;
|
use super::resolve_wildcard;
|
||||||
use super::Package;
|
use super::Package;
|
||||||
|
|
|
@ -1,3 +1,7 @@
|
||||||
|
use std::path::Path;
|
||||||
|
|
||||||
|
use path_slash::PathExt;
|
||||||
|
|
||||||
use self::util::{parse_hex32, parse_hex64};
|
use self::util::{parse_hex32, parse_hex64};
|
||||||
|
|
||||||
use super::*;
|
use super::*;
|
||||||
|
@ -263,11 +267,23 @@ impl IdString64 {
|
||||||
IdString64::String(_) => false,
|
IdString64::String(_) => false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Would love to have this as a proper `impl From`, but
|
||||||
|
// rustc will complain that it overlaps with the `impl From<Into<String>>`.
|
||||||
|
pub fn from_path(p: impl AsRef<Path>) -> Self {
|
||||||
|
Self::String(p.as_ref().to_slash_lossy().to_string())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<S: Into<String>> From<S> for IdString64 {
|
impl From<String> for IdString64 {
|
||||||
fn from(value: S) -> Self {
|
fn from(value: String) -> Self {
|
||||||
Self::String(value.into())
|
Self::String(value)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl From<u64> for IdString64 {
|
||||||
|
fn from(value: u64) -> Self {
|
||||||
|
Self::Hash(value.into())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -283,6 +299,12 @@ impl From<IdString64> for Murmur64 {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Default for IdString64 {
|
||||||
|
fn default() -> Self {
|
||||||
|
Self::Hash(0.into())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
impl PartialEq for IdString64 {
|
impl PartialEq for IdString64 {
|
||||||
fn eq(&self, other: &Self) -> bool {
|
fn eq(&self, other: &Self) -> bool {
|
||||||
self.to_murmur64() == other.to_murmur64()
|
self.to_murmur64() == other.to_murmur64()
|
||||||
|
|
Loading…
Add table
Reference in a new issue