Unverified Commit 26f2f4f0 by Enkelmann Committed by GitHub

add generic parameter objects for entry points (#227)

parent fac0ec9d
......@@ -161,7 +161,16 @@ impl<'a> PointerInference<'a> {
));
}
for (sub_tid, start_node_index) in entry_sub_to_entry_node_map.into_iter() {
let mut fn_entry_state = State::new(&project.stack_pointer_register, sub_tid.clone());
let mut fn_entry_state = if let Some(cconv) = project.get_standard_calling_convention()
{
State::new_with_generic_parameter_objects(
&project.stack_pointer_register,
sub_tid.clone(),
&cconv.integer_parameter_register,
)
} else {
State::new(&project.stack_pointer_register, sub_tid.clone())
};
if project.cpu_architecture.contains("MIPS") {
let _ = fn_entry_state
.set_mips_link_register(&sub_tid, project.stack_pointer_register.size);
......@@ -298,7 +307,16 @@ impl<'a> PointerInference<'a> {
[&self.computation.get_graph()[entry].get_block().tid]
.tid
.clone();
let mut fn_entry_state = State::new(&project.stack_pointer_register, sub_tid.clone());
let mut fn_entry_state = if let Some(cconv) = project.get_standard_calling_convention()
{
State::new_with_generic_parameter_objects(
&project.stack_pointer_register,
sub_tid.clone(),
&cconv.integer_parameter_register,
)
} else {
State::new(&project.stack_pointer_register, sub_tid.clone())
};
if project.cpu_architecture.contains("MIPS") {
let _ = fn_entry_state
.set_mips_link_register(&sub_tid, project.stack_pointer_register.size);
......
......@@ -64,6 +64,46 @@ impl State {
}
}
/// Create a new state that contains one memory object corresponding to the stack
/// and one memory object for each provided parameter register.
///
/// This function can be used to approximate states of entry points
/// where the number and types of its parameters is unknown.
/// Note that this may also cause analysis errors,
/// e.g. if two parameters point to the same memory object instead of different ones.
pub fn new_with_generic_parameter_objects(
stack_register: &Variable,
function_tid: Tid,
params: &[String],
) -> State {
let mut state = State::new(stack_register, function_tid.clone());
for param_name in params {
let param = Variable {
name: param_name.clone(),
size: stack_register.size,
is_temp: false,
};
let param_id = AbstractIdentifier::new(
function_tid.clone(),
AbstractLocation::from_var(&param).unwrap(),
);
state.memory.add_abstract_object(
param_id.clone(),
Bitvector::zero(stack_register.size.into()).into(),
super::object::ObjectType::Heap,
stack_register.size,
);
state.set_register(
&param,
DataDomain::from_target(
param_id,
Bitvector::zero(stack_register.size.into()).into(),
),
)
}
state
}
/// Set the MIPS link register `t9` to the address of the callee TID.
///
/// According to the System V ABI for MIPS the caller has to save the callee address in register `t9`
......
......@@ -1117,3 +1117,16 @@ fn test_check_def_for_null_dereferences() {
state.set_register(&var_rax, address);
assert_eq!(state.check_def_for_null_dereferences(&def).ok(), Some(true));
}
#[test]
fn test_new_with_generic_parameter_objects() {
let param_names = vec!["param1".to_string(), "param2".to_string()];
let state = State::new_with_generic_parameter_objects(
&register("RSP"),
Tid::new("func_tid"),
&param_names,
);
assert_eq!(state.memory.get_num_objects(), 3);
assert!(state.get_register_by_name("param1").is_some());
assert!(state.get_register_by_name("param2").is_some());
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment