diff --git a/src/write/elf/writer.rs b/src/write/elf/writer.rs index 5895f56e..756910a0 100644 --- a/src/write/elf/writer.rs +++ b/src/write/elf/writer.rs @@ -658,7 +658,7 @@ impl<'a> Writer<'a> { /// /// This range is used for a section named `.strtab`. /// - /// This function does nothing if no strings were defined. + /// This function does nothing if a string table is not required. /// This must be called after [`Self::add_string`]. pub fn reserve_strtab(&mut self) { debug_assert_eq!(self.strtab_offset, 0); @@ -684,6 +684,9 @@ impl<'a> Writer<'a> { /// Reserve the section index for the string table. /// + /// You should check [`Self::strtab_needed`] before calling this + /// unless you have other means of knowing if this section is needed. + /// /// This must be called before [`Self::reserve_section_headers`]. pub fn reserve_strtab_section_index(&mut self) -> SectionIndex { self.reserve_strtab_section_index_with_name(&b".strtab"[..]) @@ -691,6 +694,9 @@ impl<'a> Writer<'a> { /// Reserve the section index for the string table. /// + /// You should check [`Self::strtab_needed`] before calling this + /// unless you have other means of knowing if this section is needed. + /// /// This must be called before [`Self::reserve_section_headers`]. pub fn reserve_strtab_section_index_with_name(&mut self, name: &'a [u8]) -> SectionIndex { debug_assert_eq!(self.strtab_index, SectionIndex(0)); @@ -732,6 +738,8 @@ impl<'a> Writer<'a> { debug_assert_eq!(self.symtab_offset, 0); debug_assert_eq!(self.symtab_num, 0); self.symtab_num = 1; + // The symtab must link to a strtab. + self.need_strtab = true; SymbolIndex(0) } @@ -752,6 +760,8 @@ impl<'a> Writer<'a> { debug_assert_eq!(self.symtab_shndx_offset, 0); if self.symtab_num == 0 { self.symtab_num = 1; + // The symtab must link to a strtab. + self.need_strtab = true; } let index = self.symtab_num; self.symtab_num += 1; @@ -1052,6 +1062,9 @@ impl<'a> Writer<'a> { /// Reserve the section index for the dynamic string table. /// + /// You should check [`Self::dynstr_needed`] before calling this + /// unless you have other means of knowing if this section is needed. + /// /// This must be called before [`Self::reserve_section_headers`]. pub fn reserve_dynstr_section_index(&mut self) -> SectionIndex { self.reserve_dynstr_section_index_with_name(&b".dynstr"[..]) @@ -1059,6 +1072,9 @@ impl<'a> Writer<'a> { /// Reserve the section index for the dynamic string table. /// + /// You should check [`Self::dynstr_needed`] before calling this + /// unless you have other means of knowing if this section is needed. + /// /// This must be called before [`Self::reserve_section_headers`]. pub fn reserve_dynstr_section_index_with_name(&mut self, name: &'a [u8]) -> SectionIndex { debug_assert_eq!(self.dynstr_index, SectionIndex(0)); diff --git a/tests/round_trip/elf.rs b/tests/round_trip/elf.rs index dfc566c5..23047b5e 100644 --- a/tests/round_trip/elf.rs +++ b/tests/round_trip/elf.rs @@ -42,6 +42,21 @@ fn symtab_shndx() { } } +#[test] +fn empty_symtab() { + let object = + write::Object::new(BinaryFormat::Elf, Architecture::X86_64, Endianness::Little); + let bytes = object.write().unwrap(); + + let object = read::File::parse(&*bytes).unwrap(); + assert_eq!(object.format(), BinaryFormat::Elf); + assert_eq!(object.architecture(), Architecture::X86_64); + let symtab = object.section_by_name(".symtab").unwrap(); + assert_eq!(symtab.size(), 24); + let strtab = object.section_by_name(".strtab").unwrap(); + assert_eq!(strtab.size(), 1); +} + #[test] fn aligned_sections() { let mut object =