mirror of https://github.com/encounter/objdiff.git
cli diff: Resolve object and project if not specified
This commit is contained in:
parent
5cfd04fd4f
commit
82f8c9fb65
|
@ -20,7 +20,7 @@ use crossterm::{
|
||||||
};
|
};
|
||||||
use event::KeyModifiers;
|
use event::KeyModifiers;
|
||||||
use objdiff_core::{
|
use objdiff_core::{
|
||||||
config::ProjectConfig,
|
config::{ProjectConfig, ProjectObject},
|
||||||
diff,
|
diff,
|
||||||
diff::display::{display_diff, DiffText, HighlightKind},
|
diff::display::{display_diff, DiffText, HighlightKind},
|
||||||
obj,
|
obj,
|
||||||
|
@ -54,29 +54,63 @@ pub fn run(args: Args) -> Result<()> {
|
||||||
let (target_path, base_path, project_config) =
|
let (target_path, base_path, project_config) =
|
||||||
match (&args.target, &args.base, &args.project, &args.unit) {
|
match (&args.target, &args.base, &args.project, &args.unit) {
|
||||||
(Some(t), Some(b), _, _) => (Some(t.clone()), Some(b.clone()), None),
|
(Some(t), Some(b), _, _) => (Some(t.clone()), Some(b.clone()), None),
|
||||||
(_, _, Some(p), Some(u)) => {
|
(_, _, p, u) => {
|
||||||
|
let project = match p {
|
||||||
|
Some(project) => project.clone(),
|
||||||
|
_ => std::env::current_dir().context("Failed to get the current directory")?,
|
||||||
|
};
|
||||||
let Some((project_config, project_config_info)) =
|
let Some((project_config, project_config_info)) =
|
||||||
objdiff_core::config::try_project_config(p)
|
objdiff_core::config::try_project_config(&project)
|
||||||
else {
|
else {
|
||||||
bail!("Project config not found in {}", p.display())
|
bail!("Project config not found in {}", &project.display())
|
||||||
};
|
};
|
||||||
let mut project_config = project_config.with_context(|| {
|
let mut project_config = project_config.with_context(|| {
|
||||||
format!("Reading project config {}", project_config_info.path.display())
|
format!("Reading project config {}", project_config_info.path.display())
|
||||||
})?;
|
})?;
|
||||||
let Some(object) = project_config.objects.iter_mut().find(|obj| obj.name() == u)
|
let object = {
|
||||||
else {
|
let resolve_paths = |o: &mut ProjectObject| {
|
||||||
bail!("Unit not found: {}", u)
|
o.resolve_paths(
|
||||||
|
&project,
|
||||||
|
project_config.target_dir.as_deref(),
|
||||||
|
project_config.base_dir.as_deref(),
|
||||||
|
)
|
||||||
|
};
|
||||||
|
if let Some(u) = u {
|
||||||
|
let Some(object) =
|
||||||
|
project_config.objects.iter_mut().find(|obj| obj.name() == u)
|
||||||
|
else {
|
||||||
|
bail!("Unit not found: {}", u)
|
||||||
|
};
|
||||||
|
resolve_paths(object);
|
||||||
|
object
|
||||||
|
} else {
|
||||||
|
let mut idx = None;
|
||||||
|
let mut count = 0usize;
|
||||||
|
for (i, obj) in project_config.objects.iter_mut().enumerate() {
|
||||||
|
resolve_paths(obj);
|
||||||
|
if load_obj(&obj.target_path)?
|
||||||
|
.and_then(|o| find_function(&o, &args.symbol))
|
||||||
|
.is_some()
|
||||||
|
{
|
||||||
|
idx = Some(i);
|
||||||
|
count += 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
match (count, idx) {
|
||||||
|
(0, None) => bail!("Symbol not found: {}", &args.symbol),
|
||||||
|
(1, Some(i)) => &mut project_config.objects[i],
|
||||||
|
(2.., Some(_)) => bail!(
|
||||||
|
"Multiple instances of {} were found, try specifying a unit",
|
||||||
|
&args.symbol
|
||||||
|
),
|
||||||
|
_ => unreachable!(),
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
object.resolve_paths(
|
|
||||||
p,
|
|
||||||
project_config.target_dir.as_deref(),
|
|
||||||
project_config.base_dir.as_deref(),
|
|
||||||
);
|
|
||||||
let target_path = object.target_path.clone();
|
let target_path = object.target_path.clone();
|
||||||
let base_path = object.base_path.clone();
|
let base_path = object.base_path.clone();
|
||||||
(target_path, base_path, Some(project_config))
|
(target_path, base_path, Some(project_config))
|
||||||
}
|
}
|
||||||
_ => bail!("Either target and base or project and unit must be specified"),
|
|
||||||
};
|
};
|
||||||
let mut state = FunctionDiffUi {
|
let mut state = FunctionDiffUi {
|
||||||
clear: true,
|
clear: true,
|
||||||
|
@ -137,6 +171,12 @@ pub fn run(args: Args) -> Result<()> {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn load_obj(path: &Option<PathBuf>) -> Result<Option<ObjInfo>> {
|
||||||
|
path.as_deref()
|
||||||
|
.map(|p| obj::elf::read(p).with_context(|| format!("Loading {}", p.display())))
|
||||||
|
.transpose()
|
||||||
|
}
|
||||||
|
|
||||||
fn find_function(obj: &ObjInfo, name: &str) -> Option<ObjSymbol> {
|
fn find_function(obj: &ObjInfo, name: &str) -> Option<ObjSymbol> {
|
||||||
for section in &obj.sections {
|
for section in &obj.sections {
|
||||||
if section.kind != ObjSectionKind::Code {
|
if section.kind != ObjSectionKind::Code {
|
||||||
|
@ -489,16 +529,8 @@ impl FunctionDiffUi {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn reload(&mut self) -> Result<()> {
|
fn reload(&mut self) -> Result<()> {
|
||||||
let mut target = self
|
let mut target = load_obj(&self.target_path)?;
|
||||||
.target_path
|
let mut base = load_obj(&self.base_path)?;
|
||||||
.as_deref()
|
|
||||||
.map(|p| obj::elf::read(p).with_context(|| format!("Loading {}", p.display())))
|
|
||||||
.transpose()?;
|
|
||||||
let mut base = self
|
|
||||||
.base_path
|
|
||||||
.as_deref()
|
|
||||||
.map(|p| obj::elf::read(p).with_context(|| format!("Loading {}", p.display())))
|
|
||||||
.transpose()?;
|
|
||||||
let config = diff::DiffObjConfig::default();
|
let config = diff::DiffObjConfig::default();
|
||||||
diff::diff_objs(&config, target.as_mut(), base.as_mut())?;
|
diff::diff_objs(&config, target.as_mut(), base.as_mut())?;
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue