Extract shorthand registration into its own function

This commit is contained in:
Agus Zubiaga 2024-06-05 22:16:32 -03:00
parent f92bf4852f
commit 3ff0c986e8
No known key found for this signature in database

View File

@ -2250,161 +2250,83 @@ fn update<'a>(
Ok(state) Ok(state)
} }
Header(header) => { Header(header) => {
use HeaderType::*;
log!("loaded header for {:?}", header.module_id); log!("loaded header for {:?}", header.module_id);
let home = header.module_id; let home = header.module_id;
let mut work = MutSet::default(); let mut work = MutSet::default();
// Register the package's path under its shorthand // Only lock shorthands if this header has packages
// (e.g. for { pf: "blah" }, register that "pf" should resolve to "blah") if !header.packages.is_empty() {
{ let mut shorthands = state.arc_shorthands.lock();
let mut shorthands = (*state.arc_shorthands).lock();
for (shorthand, package_name) in header.packages.iter() { register_package_shorthands(&mut shorthands, &header, src_dir, &state.cache_dir)?;
let package_str = package_name.as_str(); }
let shorthand_path = if package_str.starts_with("https://") {
#[cfg(not(target_family = "wasm"))]
{
let url = package_str;
match PackageMetadata::try_from(url) {
Ok(url_metadata) => {
// This was a valid URL
let root_module_dir = state
.cache_dir
.join(url_metadata.cache_subdir)
.join(url_metadata.content_hash);
let root_module = root_module_dir.join(
url_metadata.root_module_filename.unwrap_or("main.roc"),
);
ShorthandPath::FromHttpsUrl { use HeaderType::*;
root_module_dir,
root_module,
}
}
Err(url_err) => {
let buf = to_https_problem_report_string(
url,
Problem::InvalidUrl(url_err),
header.module_path,
);
return Err(LoadingProblem::FormattedReport(buf));
}
}
}
#[cfg(target_family = "wasm")] match header.header_type {
{ App { to_platform, .. } => {
panic!( state.platform_path = PlatformPath::Valid(to_platform);
"Specifying packages via URLs is currently unsupported in wasm." }
); Package {
} config_shorthand,
exposes_ids,
..
} => {
if header.is_root_module {
state.exposed_modules = exposes_ids;
}
work.extend(state.dependencies.notify_package(config_shorthand));
}
Platform {
config_shorthand,
provides,
exposes_ids,
..
} => {
work.extend(state.dependencies.notify_package(config_shorthand));
let is_prebuilt = if header.is_root_module {
debug_assert!(matches!(state.platform_path, PlatformPath::NotSpecified));
state.platform_path = PlatformPath::RootIsPlatformModule;
// If the root module is this platform, then the platform is the very
// thing we're rebuilding!
false
} else { } else {
// This wasn't a URL, so it must be a filesystem path. // platforms from HTTPS URLs are always prebuilt
let root_module: PathBuf = src_dir.join(package_str); matches!(
let root_module_dir = root_module.parent().unwrap_or_else(|| { state.arc_shorthands.lock().get(config_shorthand),
if root_module.is_file() { Some(ShorthandPath::FromHttpsUrl { .. })
// Files must have parents! )
internal_error!("Somehow I got a file path to a real file on the filesystem that has no parent!");
} else {
// TODO make this a nice report
todo!(
"platform module {:?} was not a file.",
package_str
)
}
}).into();
ShorthandPath::RelativeToSrc {
root_module_dir,
root_module,
}
}; };
log!( // If we're building an app module, and this was the platform
"New package shorthand: {:?} => {:?}", // specified in its header's `to` field, record it as our platform.
shorthand, if state.opt_platform_shorthand == Some(config_shorthand) {
shorthand_path debug_assert!(state.platform_data.is_none());
);
shorthands.insert(shorthand, shorthand_path); state.platform_data = Some(PlatformData {
module_id: header.module_id,
provides,
is_prebuilt,
});
}
if header.is_root_module {
state.exposed_modules = exposes_ids;
}
} }
Builtin { .. } | Module { .. } => {
match header.header_type { if header.is_root_module {
App { to_platform, .. } => { debug_assert!(matches!(state.platform_path, PlatformPath::NotSpecified));
state.platform_path = PlatformPath::Valid(to_platform); state.platform_path = PlatformPath::RootIsModule;
} }
Package { }
config_shorthand, Hosted { .. } => {
exposes_ids, if header.is_root_module {
.. debug_assert!(matches!(state.platform_path, PlatformPath::NotSpecified));
} => { state.platform_path = PlatformPath::RootIsHosted;
if header.is_root_module {
state.exposed_modules = exposes_ids;
}
work.extend(state.dependencies.notify_package(config_shorthand));
}
Platform {
config_shorthand,
provides,
exposes_ids,
..
} => {
work.extend(state.dependencies.notify_package(config_shorthand));
let is_prebuilt = if header.is_root_module {
debug_assert!(matches!(
state.platform_path,
PlatformPath::NotSpecified
));
state.platform_path = PlatformPath::RootIsPlatformModule;
// If the root module is this platform, then the platform is the very
// thing we're rebuilding!
false
} else {
// platforms from HTTPS URLs are always prebuilt
matches!(
shorthands.get(config_shorthand),
Some(ShorthandPath::FromHttpsUrl { .. })
)
};
// If we're building an app module, and this was the platform
// specified in its header's `to` field, record it as our platform.
if state.opt_platform_shorthand == Some(config_shorthand) {
debug_assert!(state.platform_data.is_none());
state.platform_data = Some(PlatformData {
module_id: header.module_id,
provides,
is_prebuilt,
});
}
if header.is_root_module {
state.exposed_modules = exposes_ids;
}
}
Builtin { .. } | Module { .. } => {
if header.is_root_module {
debug_assert!(matches!(
state.platform_path,
PlatformPath::NotSpecified
));
state.platform_path = PlatformPath::RootIsModule;
}
}
Hosted { .. } => {
if header.is_root_module {
debug_assert!(matches!(
state.platform_path,
PlatformPath::NotSpecified
));
state.platform_path = PlatformPath::RootIsHosted;
}
} }
} }
} }
@ -3125,6 +3047,81 @@ fn update<'a>(
} }
} }
fn register_package_shorthands<'a>(
shorthands: &mut MutMap<&'a str, ShorthandPath>,
header: &ModuleHeader<'a>,
src_dir: &Path,
cache_dir: &Path,
) -> Result<(), LoadingProblem<'a>> {
for (shorthand, package_name) in header.packages.iter() {
let package_str = package_name.as_str();
let shorthand_path = if package_str.starts_with("https://") {
#[cfg(not(target_family = "wasm"))]
{
let url = package_str;
match PackageMetadata::try_from(url) {
Ok(url_metadata) => {
// This was a valid URL
let root_module_dir = cache_dir
.join(url_metadata.cache_subdir)
.join(url_metadata.content_hash);
let root_module = root_module_dir
.join(url_metadata.root_module_filename.unwrap_or("main.roc"));
ShorthandPath::FromHttpsUrl {
root_module_dir,
root_module,
}
}
Err(url_err) => {
let buf = to_https_problem_report_string(
url,
Problem::InvalidUrl(url_err),
header.module_path.clone(),
);
return Err(LoadingProblem::FormattedReport(buf));
}
}
}
#[cfg(target_family = "wasm")]
{
panic!("Specifying packages via URLs is currently unsupported in wasm.");
}
} else {
// This wasn't a URL, so it must be a filesystem path.
let root_module: PathBuf = src_dir.join(package_str);
let root_module_dir = root_module.parent().unwrap_or_else(|| {
if root_module.is_file() {
// Files must have parents!
internal_error!("Somehow I got a file path to a real file on the filesystem that has no parent!");
} else {
// TODO make this a nice report
todo!(
"platform module {:?} was not a file.",
package_str
)
}
}).into();
ShorthandPath::RelativeToSrc {
root_module_dir,
root_module,
}
};
log!(
"New package shorthand: {:?} => {:?}",
shorthand,
shorthand_path
);
shorthands.insert(shorthand, shorthand_path);
}
Ok(())
}
#[cfg(debug_assertions)] #[cfg(debug_assertions)]
fn log_layout_stats(module_id: ModuleId, layout_cache: &LayoutCache) { fn log_layout_stats(module_id: ModuleId, layout_cache: &LayoutCache) {
let (cache_stats, raw_function_cache_stats) = layout_cache.statistics(); let (cache_stats, raw_function_cache_stats) = layout_cache.statistics();