summaryrefslogtreecommitdiff
path: root/plugins/bntl_utils/src/command/validate.rs
diff options
context:
space:
mode:
authorMason Reed <mason@vector35.com>2026-02-19 11:19:16 -0800
committerMason Reed <35282038+emesare@users.noreply.github.com>2026-02-23 00:09:44 -0800
commit69a9f9e48d6bc76e91eec2a18cd8fee73a496b93 (patch)
tree05753a93eccb3d1c2614b3365f620a2bf17e704b /plugins/bntl_utils/src/command/validate.rs
parent65c217ae27e6b0abe26d5baea40f2bab695a3651 (diff)
[BNTL] Misc improvements
Diffstat (limited to 'plugins/bntl_utils/src/command/validate.rs')
-rw-r--r--plugins/bntl_utils/src/command/validate.rs113
1 files changed, 58 insertions, 55 deletions
diff --git a/plugins/bntl_utils/src/command/validate.rs b/plugins/bntl_utils/src/command/validate.rs
index 8f0095ae..a0507974 100644
--- a/plugins/bntl_utils/src/command/validate.rs
+++ b/plugins/bntl_utils/src/command/validate.rs
@@ -1,76 +1,79 @@
+use crate::command::{InputDirectoryField, OutputDirectoryField};
use crate::helper::path_to_type_libraries;
use crate::validate::TypeLibValidater;
use binaryninja::binary_view::{BinaryView, BinaryViewExt};
use binaryninja::command::Command;
-use binaryninja::interaction::get_open_filename_input;
+use binaryninja::interaction::Form;
use binaryninja::platform::Platform;
-use binaryninja::types::TypeLibrary;
pub struct Validate;
-impl Command for Validate {
- fn action(&self, _view: &BinaryView) {
- let Some(input_path) =
- get_open_filename_input("Select a type library to validate", "*.bntl")
- else {
- return;
- };
-
- let type_lib = match TypeLibrary::load_from_file(&input_path) {
- Some(type_lib) => type_lib,
- None => {
- tracing::error!("Failed to load type library from {}", input_path.display());
- return;
- }
- };
-
- // Type libraries should always have at least one platform associated with them.
- if type_lib.platform_names().is_empty() {
- tracing::error!("Type library {} has no platforms!", input_path.display());
+impl Validate {
+ pub fn execute() {
+ let mut form = Form::new("Validate Type Libraries");
+ form.add_field(InputDirectoryField::field());
+ form.add_field(OutputDirectoryField::field());
+ if !form.prompt() {
return;
}
+ let output_dir = OutputDirectoryField::from_form(&form).unwrap();
+ let input_path = InputDirectoryField::from_form(&form).unwrap();
- // TODO: Currently we collect input path dependencies from the platform and the parent directory.
- let dependencies = path_to_type_libraries(input_path.parent().unwrap());
-
- let validator = TypeLibValidater::new().with_type_libraries(dependencies);
- // Validate for every platform so that we can find issues in lesser used platforms.
- for platform_name in &type_lib.platform_names() {
- let Some(platform) = Platform::by_name(platform_name) else {
- tracing::error!("Failed to find platform with name {}", platform_name);
- continue;
- };
- let results = validator
- .clone()
- .with_platform(&platform)
- .validate(&type_lib);
- if results.issues.is_empty() {
- tracing::info!(
- "No issues found for type library {} on platform {}",
- type_lib.name(),
- platform_name
- );
+ let type_libraries = path_to_type_libraries(&input_path);
+ // TODO: Run this in parallel.
+ for type_lib in &type_libraries {
+ // Type libraries should always have at least one platform associated with them.
+ if type_lib.platform_names().is_empty() {
+ tracing::error!("Type library {} has no platforms!", input_path.display());
continue;
}
- let rendered = match results.render_report() {
- Ok(rendered) => rendered,
- Err(err) => {
- tracing::error!("Failed to render validation report: {}", err);
+
+ // TODO: Currently we collect input path dependencies from the platform and the parent directory.
+ let validator = TypeLibValidater::new().with_type_libraries(type_libraries.clone());
+ // Validate for every platform so that we can find issues in lesser used platforms.
+ for platform_name in &type_lib.platform_names() {
+ let Some(platform) = Platform::by_name(platform_name) else {
+ tracing::error!("Failed to find platform with name {}", platform_name);
+ continue;
+ };
+ let results = validator
+ .clone()
+ .with_platform(&platform)
+ .validate(&type_lib);
+ if results.issues.is_empty() {
+ tracing::info!(
+ "No issues found for type library {} on platform {}",
+ type_lib.name(),
+ platform_name
+ );
continue;
}
- };
- let out_path = input_path.with_extension(format!("{}.html", platform_name));
- let out_name = format!("{} ({})", type_lib.name(), platform_name);
- _view.show_html_report(&out_name, &rendered, "");
- if let Err(e) = std::fs::write(out_path, rendered) {
- tracing::error!(
- "Failed to write validation report to {}: {}",
- input_path.display(),
- e
- );
+ let rendered = match results.render_report() {
+ Ok(rendered) => rendered,
+ Err(err) => {
+ tracing::error!("Failed to render validation report: {}", err);
+ continue;
+ }
+ };
+ let out_path = output_dir.with_extension(format!("{}.html", platform_name));
+ if let Err(e) = std::fs::write(out_path, rendered) {
+ tracing::error!(
+ "Failed to write validation report to {}: {}",
+ output_dir.display(),
+ e
+ );
+ }
}
}
}
+}
+
+impl Command for Validate {
+ fn action(&self, _view: &BinaryView) {
+ std::thread::spawn(move || {
+ Validate::execute();
+ });
+ }
fn valid(&self, _view: &BinaryView) -> bool {
true