add debug info item to generated dex

This commit is contained in:
Jean-Marie Mineau 2023-12-12 11:46:04 +01:00
parent bd22b7990b
commit 5854ba5e66
Signed by: histausse
GPG key ID: B66AEEDA9B645AD2

View file

@ -78,6 +78,8 @@ pub struct DexWriter {
method_handles: Vec<MethodHandleItem>, method_handles: Vec<MethodHandleItem>,
/// The code_items sections. /// The code_items sections.
code_items: Vec<CodeItem>, code_items: Vec<CodeItem>,
/// The debug info items section.
debug_info_items: Vec<DebugInfoItem>,
/// The map_list /// The map_list
map_list: MapList, map_list: MapList,
} }
@ -136,6 +138,7 @@ impl Default for DexWriter {
annotation_set_items: vec![], annotation_set_items: vec![],
annotation_items: vec![], annotation_items: vec![],
annotation_set_lists: vec![], annotation_set_lists: vec![],
debug_info_items: vec![],
} }
} }
} }
@ -409,11 +412,21 @@ impl DexWriter {
} else { } else {
Some(handler_list) Some(handler_list)
}; };
let debug_info_off = if code.debug_info.is_empty() {
0
} else {
let debug_info_off = self.section_manager.get_size(Section::DebugInfoItem);
let item = DebugInfoItem::deserialize_from_slice(&code.debug_info)?;
self.section_manager
.add_elt(Section::DebugInfoItem, Some(item.size()));
self.debug_info_items.push(item);
debug_info_off + 1
};
let item = CodeItem { let item = CodeItem {
registers_size: code.registers_size, registers_size: code.registers_size,
ins_size: code.ins_size, ins_size: code.ins_size,
outs_size: code.outs_size, outs_size: code.outs_size,
debug_info_off: 0, // TODO: code.debug_info debug_info_off, // linked in link_debug_info()
insns: code.insns.clone(), insns: code.insns.clone(),
tries, tries,
handlers, handlers,
@ -1332,7 +1345,7 @@ impl DexWriter {
/// # Warning /// # Warning
/// ///
/// Linking can only occur once all sections are entirelly generated. /// Linking can only occur once all sections are entirelly generated.
fn link_class_data_occurences(&mut self) -> Result<()> { fn link_class_data_occurences(&mut self) {
debug!("Link the class_data_item entries in class_def_items"); debug!("Link the class_data_item entries in class_def_items");
for class_def in self.class_defs_list.iter_mut() { for class_def in self.class_defs_list.iter_mut() {
// prelink value is set to offset in the section + 1 (to distinguish with 0) // prelink value is set to offset in the section + 1 (to distinguish with 0)
@ -1341,7 +1354,6 @@ impl DexWriter {
self.section_manager.get_offset(Section::ClassDataItem) - 1; self.section_manager.get_offset(Section::ClassDataItem) - 1;
} }
} }
Ok(())
} }
/// Link the offsets of static_values_off in class_def_items. /// Link the offsets of static_values_off in class_def_items.
@ -1349,7 +1361,7 @@ impl DexWriter {
/// # Warning /// # Warning
/// ///
/// Linking can only occur once all sections are entirelly generated. /// Linking can only occur once all sections are entirelly generated.
fn link_static_values(&mut self) -> Result<()> { fn link_static_values(&mut self) {
debug!("Link the static_values entries in class_def_items"); debug!("Link the static_values entries in class_def_items");
for class_def in self.class_defs_list.iter_mut() { for class_def in self.class_defs_list.iter_mut() {
if class_def.static_values_off != 0 { if class_def.static_values_off != 0 {
@ -1357,7 +1369,6 @@ impl DexWriter {
self.section_manager.get_offset(Section::EncodedArrayItem) - 1; self.section_manager.get_offset(Section::EncodedArrayItem) - 1;
} }
} }
Ok(())
} }
/// Link the offsets of code item in class_data_items. /// Link the offsets of code item in class_data_items.
@ -1365,7 +1376,7 @@ impl DexWriter {
/// # Warning /// # Warning
/// ///
/// Linking can only occur once all sections are entirelly generated. /// Linking can only occur once all sections are entirelly generated.
fn link_code_item(&mut self) -> Result<()> { fn link_code_item(&mut self) {
debug!("Link the code_item entries in class_data_items"); debug!("Link the code_item entries in class_data_items");
for data in &mut self.class_data_list { for data in &mut self.class_data_list {
for method in &mut data.direct_methods { for method in &mut data.direct_methods {
@ -1379,7 +1390,20 @@ impl DexWriter {
} }
} }
} }
Ok(()) }
/// Link the offset of debug info item in code items.
///
/// # Warning
///
/// Linking can only occur once all sections are entirelly generated.
fn link_debug_info(&mut self) {
debug!("Link the debug_info_off entries in code_items");
for code in self.code_items.iter_mut() {
if code.debug_info_off != 0 {
code.debug_info_off += self.section_manager.get_offset(Section::DebugInfoItem);
}
}
} }
/// Link all annotations objects. /// Link all annotations objects.
@ -1387,7 +1411,7 @@ impl DexWriter {
/// # Warning /// # Warning
/// ///
/// Linking can only occur once all sections are entirelly generated. /// Linking can only occur once all sections are entirelly generated.
fn link_annotations(&mut self) -> Result<()> { fn link_annotations(&mut self) {
for annotation in self.annotations_directory_items.iter_mut() { for annotation in self.annotations_directory_items.iter_mut() {
if annotation.class_annotations_off != 0 { if annotation.class_annotations_off != 0 {
annotation.class_annotations_off += annotation.class_annotations_off +=
@ -1427,7 +1451,6 @@ impl DexWriter {
} }
} }
} }
Ok(())
} }
fn write_dex_file(&mut self, writer: &mut dyn Write) -> Result<()> { fn write_dex_file(&mut self, writer: &mut dyn Write) -> Result<()> {
@ -1450,10 +1473,11 @@ impl DexWriter {
self.link_header(); self.link_header();
self.link_type_list_occurences()?; self.link_type_list_occurences()?;
self.link_class_data_occurences()?; self.link_class_data_occurences();
self.link_static_values()?; self.link_static_values();
self.link_code_item()?; self.link_code_item();
self.link_annotations()?; self.link_debug_info();
self.link_annotations();
debug!("Serialize the dex file"); debug!("Serialize the dex file");
// TODO: compute checksum, hash, ect // TODO: compute checksum, hash, ect
@ -1529,7 +1553,10 @@ impl DexWriter {
for string in &self.string_data_list { for string in &self.string_data_list {
string.serialize(writer)?; string.serialize(writer)?;
} }
// TODO: DebugInfoItem, // DebugInfoItem section
for debug_info in &self.debug_info_items {
debug_info.serialize(writer)?;
}
// AnnotationItem section // AnnotationItem section
for annot in &self.annotation_items { for annot in &self.annotation_items {
annot.serialize(writer)?; annot.serialize(writer)?;