master
Ales Katona 4 years ago
parent 7a7bbb2ac0
commit 43c7f19dde
Signed by: almindor
GPG Key ID: 2F773149BF38B48F

@ -85,18 +85,6 @@ impl Loadable {
// }
}
pub const fn section_names() -> &'static [&'static str] {
&[".text", ".rodata", ".data", ".bss"]
}
pub const fn section_count() -> usize {
Self::section_names().len()
}
pub const fn segment_count() -> usize {
3
}
pub fn segment_sections(&self) -> impl Iterator<Item = &SegmentSections> {
let text = once(&self.text);
let rodata = once(&self.rodata);

@ -1,10 +1,4 @@
use std::{
fs::File,
io::BufWriter,
io::{Write},
mem::size_of,
path::{PathBuf},
};
use std::{fs::File, io::BufWriter, io::Write, mem::size_of, path::PathBuf};
use elf_utilities::{
header::Ehdr64,
@ -19,6 +13,8 @@ use crate::{
use super::ElfObject;
const SECTION_NAMES: [&str; 5] = [".text", ".rodata", ".data", ".bss", ".shstrtab"];
pub struct ElfOutput {
destination: PathBuf,
writer: BufWriter<File>,
@ -36,6 +32,29 @@ impl ElfOutput {
Ok(result)
}
fn write_shstrtab(
&mut self,
shstrtab: (Vec<u8>, Vec<usize>),
mut offset: usize,
name_idx: usize,
) -> Result<usize, Error> {
const SHS: u16 = size_of::<Shdr64>() as u16;
// write .shstrtab header
let data_offset = (offset + usize::from(SHS)) as u64;
let strtab_header = make_section_header(
shstrtab.1[name_idx],
ShType::StrTab,
data_offset,
shstrtab.0.len() as u64,
);
offset += self.writer.write(&strtab_header.to_le_bytes())?;
// write .shstrtab data
offset += self.writer.write(&shstrtab.0)?;
Ok(offset)
}
}
impl Output<ElfObject> for ElfOutput {
@ -44,10 +63,10 @@ impl Output<ElfObject> for ElfOutput {
const PHS: u16 = size_of::<Phdr64>() as u16;
const SHS: u16 = size_of::<Shdr64>() as u16;
let strtab = make_strtab();
let shstrtab = make_shstrtab();
let mut ehdr = make_elf_header();
ehdr.e_shnum = Loadable::section_count() as u16 + 1; // +1 for .shstrtab
ehdr.e_phnum = Loadable::segment_count() as u16;
ehdr.e_shnum = SECTION_NAMES.len() as u16;
ehdr.e_phnum = 3u16; // .text, .rodata + .data, .bss
ehdr.e_shstrndx = ehdr.e_shnum - 1; // .shstrab is always last
ehdr.e_entry = loadable.start_offset()?;
ehdr.e_phentsize = PHS;
@ -77,7 +96,7 @@ impl Output<ElfObject> for ElfOutput {
// write section header table (text + rodata + data + bss)
for sections in loadable.segment_sections() {
let sh = make_section_header(
strtab.1[name_idx],
shstrtab.1[name_idx],
ShType::ProgBits,
0,
sections.data_size(),
@ -87,19 +106,7 @@ impl Output<ElfObject> for ElfOutput {
}
// .shstrtab as last section header written (+ the name data including)
{
// write .shstrtab header
let data_offset = (offset + usize::from(SHS)) as u64;
let strtab_header = make_section_header(
strtab.1[name_idx],
ShType::StrTab,
data_offset,
strtab.0.len() as u64,
);
offset += self.writer.write(&strtab_header.to_le_bytes())?;
// write .shstrtab data
offset += self.writer.write(&strtab.0)?;
}
offset = self.write_shstrtab(shstrtab, offset, name_idx)?;
// program data (segments)
offset += pad_to_next_page(&mut self.writer, offset)?;
@ -188,11 +195,8 @@ fn make_program_header(offset: usize, size: u64, which: SegmentType) -> Phdr64 {
}
// strtab as bytes + indexes to individual strings
fn make_strtab() -> (Vec<u8>, Vec<usize>) {
let mut section_names = Vec::from(Loadable::section_names());
section_names.push(".shstrtab");
let strtab_bytes = build_string_table(section_names, true);
fn make_shstrtab() -> (Vec<u8>, Vec<usize>) {
let strtab_bytes = build_string_table(Vec::from(SECTION_NAMES), true);
let mut indexes = Vec::new();
let mut on_string = false;

Loading…
Cancel
Save