Skip to content

Commit

Permalink
Merge pull request #1466 from peterhuene/fix-unwind-emit
Browse files Browse the repository at this point in the history
Refactor unwind generation in Cranelift.
  • Loading branch information
peterhuene authored Apr 16, 2020
2 parents 99adc1d + 4d7a283 commit 7d88384
Show file tree
Hide file tree
Showing 44 changed files with 2,690 additions and 3,151 deletions.
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

30 changes: 0 additions & 30 deletions cranelift/codegen/src/binemit/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -173,36 +173,6 @@ pub trait CodeSink {
}
}

/// Type of the frame unwind information.
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
pub enum FrameUnwindKind {
/// Windows fastcall unwinding (as in .pdata).
Fastcall,
/// FDE entry for libunwind (similar to .eh_frame format).
Libunwind,
}

/// Offset in frame unwind information buffer.
pub type FrameUnwindOffset = usize;

/// Sink for frame unwind information.
pub trait FrameUnwindSink {
/// Get the current position.
fn len(&self) -> FrameUnwindOffset;

/// Add bytes to the code section.
fn bytes(&mut self, _: &[u8]);

/// Reserves bytes in the buffer.
fn reserve(&mut self, _len: usize) {}

/// Add a relocation entry.
fn reloc(&mut self, _: Reloc, _: FrameUnwindOffset);

/// Specified offset to main structure.
fn set_entry_offset(&mut self, _: FrameUnwindOffset);
}

/// Report a bad encoding error.
#[cold]
pub fn bad_encoding(func: &Function, inst: Inst) -> ! {
Expand Down
20 changes: 8 additions & 12 deletions cranelift/codegen/src/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,8 @@
//! single ISA instance.
use crate::binemit::{
relax_branches, shrink_instructions, CodeInfo, FrameUnwindKind, FrameUnwindSink,
MemoryCodeSink, RelocSink, StackmapSink, TrapSink,
relax_branches, shrink_instructions, CodeInfo, MemoryCodeSink, RelocSink, StackmapSink,
TrapSink,
};
use crate::dce::do_dce;
use crate::dominator_tree::DominatorTree;
Expand Down Expand Up @@ -231,19 +231,15 @@ impl Context {
sink.info
}

/// Emit unwind information.
/// Creates unwind information for the function.
///
/// Requires that the function layout be calculated (see `relax_branches`).
///
/// Only some calling conventions (e.g. Windows fastcall) will have unwind information.
/// This is a no-op if the function has no unwind information.
pub fn emit_unwind_info(
/// Returns `None` if the function has no unwind information.
#[cfg(feature = "unwind")]
pub fn create_unwind_info(
&self,
isa: &dyn TargetIsa,
kind: FrameUnwindKind,
sink: &mut dyn FrameUnwindSink,
) -> CodegenResult<()> {
isa.emit_unwind_info(&self.func, kind, sink)
) -> CodegenResult<Option<crate::isa::unwind::UnwindInfo>> {
isa.create_unwind_info(&self.func)
}

/// Run the verifier on the function.
Expand Down
74 changes: 0 additions & 74 deletions cranelift/codegen/src/ir/framelayout.rs

This file was deleted.

23 changes: 8 additions & 15 deletions cranelift/codegen/src/ir/function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,14 @@ use crate::ir::{
Block, ExtFuncData, FuncRef, GlobalValue, GlobalValueData, Heap, HeapData, Inst, JumpTable,
JumpTableData, Opcode, SigRef, StackSlot, StackSlotData, Table, TableData,
};
use crate::ir::{BlockOffsets, FrameLayout, InstEncodings, SourceLocs, StackSlots, ValueLocations};
use crate::ir::{BlockOffsets, InstEncodings, SourceLocs, StackSlots, ValueLocations};
use crate::ir::{DataFlowGraph, ExternalName, Layout, Signature};
use crate::ir::{JumpTableOffsets, JumpTables};
use crate::isa::{CallConv, EncInfo, Encoding, Legalize, TargetIsa};
use crate::regalloc::{EntryRegDiversions, RegDiversions};
use crate::value_label::ValueLabelsRanges;
use crate::write::write_function;
use alloc::vec::Vec;
use core::fmt;

/// A function.
Expand Down Expand Up @@ -87,15 +88,13 @@ pub struct Function {

/// Instruction that marks the end (inclusive) of the function's prologue.
///
/// This is used for some calling conventions to track the end of unwind information.
/// This is used for some ABIs to generate unwind information.
pub prologue_end: Option<Inst>,

/// Frame layout for the instructions.
/// The instructions that mark the start (inclusive) of an epilogue in the function.
///
/// The stack unwinding requires to have information about which registers and where they
/// are saved in the frame. This information is created during the prologue and epilogue
/// passes.
pub frame_layout: Option<FrameLayout>,
/// This is used for some ABIs to generate unwind information.
pub epilogues_start: Vec<Inst>,
}

impl Function {
Expand All @@ -119,7 +118,7 @@ impl Function {
jt_offsets: SecondaryMap::new(),
srclocs: SecondaryMap::new(),
prologue_end: None,
frame_layout: None,
epilogues_start: Vec::new(),
}
}

Expand All @@ -140,7 +139,7 @@ impl Function {
self.jt_offsets.clear();
self.srclocs.clear();
self.prologue_end = None;
self.frame_layout = None;
self.epilogues_start.clear();
}

/// Create a new empty, anonymous function with a Fast calling convention.
Expand Down Expand Up @@ -258,12 +257,6 @@ impl Function {
/// Starts collection of debug information.
pub fn collect_debug_info(&mut self) {
self.dfg.collect_debug_info();
self.collect_frame_layout_info();
}

/// Starts collection of frame layout information.
pub fn collect_frame_layout_info(&mut self) {
self.frame_layout = Some(FrameLayout::new());
}

/// Changes the destination of a jump or branch instruction.
Expand Down
2 changes: 0 additions & 2 deletions cranelift/codegen/src/ir/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@ pub mod dfg;
pub mod entities;
mod extfunc;
mod extname;
mod framelayout;
pub mod function;
mod globalvalue;
mod heap;
Expand Down Expand Up @@ -40,7 +39,6 @@ pub use crate::ir::extfunc::{
AbiParam, ArgumentExtension, ArgumentPurpose, ExtFuncData, Signature,
};
pub use crate::ir::extname::ExternalName;
pub use crate::ir::framelayout::{FrameLayout, FrameLayoutChange, FrameLayoutChanges};
pub use crate::ir::function::{DisplayFunctionAnnotations, Function};
pub use crate::ir::globalvalue::GlobalValueData;
pub use crate::ir::heap::{HeapData, HeapStyle};
Expand Down
14 changes: 0 additions & 14 deletions cranelift/codegen/src/isa/fde.rs

This file was deleted.

32 changes: 20 additions & 12 deletions cranelift/codegen/src/isa/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,8 @@ pub use crate::isa::stack::{StackBase, StackBaseMask, StackRef};
use crate::binemit;
use crate::flowgraph;
use crate::ir;
use crate::isa::fde::RegisterMappingError;
#[cfg(feature = "unwind")]
use crate::isa::unwind::systemv::RegisterMappingError;
use crate::machinst::MachBackend;
use crate::regalloc;
use crate::result::CodegenResult;
Expand All @@ -77,15 +77,15 @@ mod riscv;
#[cfg(feature = "x86")]
mod x86;

#[cfg(feature = "unwind")]
pub mod fde;

#[cfg(feature = "arm32")]
mod arm32;

#[cfg(feature = "arm64")]
mod aarch64;

#[cfg(feature = "unwind")]
pub mod unwind;

mod call_conv;
mod constraints;
mod enc_tables;
Expand Down Expand Up @@ -394,17 +394,25 @@ pub trait TargetIsa: fmt::Display + Send + Sync {
/// IntCC condition for Unsigned Subtraction Overflow (Borrow/Carry).
fn unsigned_sub_overflow_condition(&self) -> ir::condcodes::IntCC;

/// Emit unwind information for the given function.
/// Creates unwind information for the function.
///
/// Only some calling conventions (e.g. Windows fastcall) will have unwind information.
fn emit_unwind_info(
/// Returns `None` if there is no unwind information for the function.
#[cfg(feature = "unwind")]
fn create_unwind_info(
&self,
_func: &ir::Function,
_kind: binemit::FrameUnwindKind,
_sink: &mut dyn binemit::FrameUnwindSink,
) -> CodegenResult<()> {
// No-op by default
Ok(())
) -> CodegenResult<Option<unwind::UnwindInfo>> {
// By default, an ISA has no unwind information
Ok(None)
}

/// Creates a new System V Common Information Entry for the ISA.
///
/// Returns `None` if the ISA does not support System V unwind information.
#[cfg(feature = "unwind")]
fn create_systemv_cie(&self) -> Option<gimli::write::CommonInformationEntry> {
// By default, an ISA cannot create a System V CIE
None
}

/// Get the new-style MachBackend, if this is an adapter around one.
Expand Down
16 changes: 16 additions & 0 deletions cranelift/codegen/src/isa/unwind.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
//! Represents information relating to function unwinding.
#[cfg(feature = "enable-serde")]
use serde::{Deserialize, Serialize};

pub mod systemv;
pub mod winx64;

/// Represents unwind information for a single function.
#[derive(Clone, Debug, PartialEq, Eq)]
#[cfg_attr(feature = "enable-serde", derive(Serialize, Deserialize))]
pub enum UnwindInfo {
/// Windows x64 ABI unwind information.
WindowsX64(winx64::UnwindInfo),
/// System V ABI unwind information.
SystemV(systemv::UnwindInfo),
}
Loading

0 comments on commit 7d88384

Please sign in to comment.