From 34534152f5ad64d4d1fbc50ef475bc68cb7ac750 Mon Sep 17 00:00:00 2001 From: Kai Luo Date: Wed, 4 Jan 2023 18:00:09 +0800 Subject: [PATCH 1/5] [LSDA] Take ttype_index into account when taking action If cs_action != 0, we should check the ttype_index field in action record. If ttype_index == 0, a clean up action is taken. --- library/std/src/personality/dwarf/eh.rs | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/library/std/src/personality/dwarf/eh.rs b/library/std/src/personality/dwarf/eh.rs index a783e187004..e7bd700b8b8 100644 --- a/library/std/src/personality/dwarf/eh.rs +++ b/library/std/src/personality/dwarf/eh.rs @@ -84,7 +84,7 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result let cs_start = read_encoded_pointer(&mut reader, context, call_site_encoding)?; let cs_len = read_encoded_pointer(&mut reader, context, call_site_encoding)?; let cs_lpad = read_encoded_pointer(&mut reader, context, call_site_encoding)?; - let cs_action = reader.read_uleb128(); + let cs_action_entry = reader.read_uleb128(); // Callsite table is sorted by cs_start, so if we've passed the ip, we // may stop searching. if ip < func_start + cs_start { @@ -95,7 +95,15 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result return Ok(EHAction::None); } else { let lpad = lpad_base + cs_lpad; - return Ok(interpret_cs_action(cs_action, lpad)); + if cs_action_entry == 0 { + return Ok(interpret_cs_action(0, lpad)); + } else { + let action_record = + (action_table as *mut u8).offset(cs_action_entry as isize - 1); + let mut action_reader = DwarfReader::new(action_record); + let ttype_index = action_reader.read_sleb128(); + return Ok(interpret_cs_action(ttype_index as u64, lpad)); + } } } } From 04a697502fbb3a69fe5dbeb0b3babf6f1e67711f Mon Sep 17 00:00:00 2001 From: Kai Luo Date: Mon, 9 Jan 2023 23:02:53 +0800 Subject: [PATCH 2/5] Also check ttype_index when using SJLJ --- library/std/src/personality/dwarf/eh.rs | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/library/std/src/personality/dwarf/eh.rs b/library/std/src/personality/dwarf/eh.rs index e7bd700b8b8..1e71da95a30 100644 --- a/library/std/src/personality/dwarf/eh.rs +++ b/library/std/src/personality/dwarf/eh.rs @@ -121,13 +121,21 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result let mut idx = ip; loop { let cs_lpad = reader.read_uleb128(); - let cs_action = reader.read_uleb128(); + let cs_action_entry = reader.read_uleb128(); idx -= 1; if idx == 0 { // Can never have null landing pad for sjlj -- that would have // been indicated by a -1 call site index. let lpad = (cs_lpad + 1) as usize; - return Ok(interpret_cs_action(cs_action, lpad)); + if cs_action_entry == 0 { + return Ok(interpret_cs_action(0, lpad)); + } else { + let action_record = + (action_table as *mut u8).offset(cs_action_entry as isize - 1); + let mut action_reader = DwarfReader::new(action_record); + let ttype_index = action_reader.read_sleb128(); + return Ok(interpret_cs_action(ttype_index as u64, lpad)); + } } } } From 8333e5cf5e4a37852774993a5a2398c8a0891239 Mon Sep 17 00:00:00 2001 From: Kai Luo Date: Mon, 9 Jan 2023 23:09:18 +0800 Subject: [PATCH 3/5] Add comments --- library/std/src/personality/dwarf/eh.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/library/std/src/personality/dwarf/eh.rs b/library/std/src/personality/dwarf/eh.rs index 1e71da95a30..4a98c36f42c 100644 --- a/library/std/src/personality/dwarf/eh.rs +++ b/library/std/src/personality/dwarf/eh.rs @@ -102,6 +102,8 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result (action_table as *mut u8).offset(cs_action_entry as isize - 1); let mut action_reader = DwarfReader::new(action_record); let ttype_index = action_reader.read_sleb128(); + // Normally, if ttype_index < 0, meaning the catch type is exception specification. + // Since we only care about if ttype_index is zero, so casting ttype_index to u64 makes sense. return Ok(interpret_cs_action(ttype_index as u64, lpad)); } } From d4926eb8ab9c70ff25f38fc699f629e50b704770 Mon Sep 17 00:00:00 2001 From: Kai Luo Date: Mon, 9 Jan 2023 23:18:06 +0800 Subject: [PATCH 4/5] Move to intepret_cs_action --- library/std/src/personality/dwarf/eh.rs | 41 ++++++++++--------------- 1 file changed, 17 insertions(+), 24 deletions(-) diff --git a/library/std/src/personality/dwarf/eh.rs b/library/std/src/personality/dwarf/eh.rs index 4a98c36f42c..4d114d61674 100644 --- a/library/std/src/personality/dwarf/eh.rs +++ b/library/std/src/personality/dwarf/eh.rs @@ -95,17 +95,7 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result return Ok(EHAction::None); } else { let lpad = lpad_base + cs_lpad; - if cs_action_entry == 0 { - return Ok(interpret_cs_action(0, lpad)); - } else { - let action_record = - (action_table as *mut u8).offset(cs_action_entry as isize - 1); - let mut action_reader = DwarfReader::new(action_record); - let ttype_index = action_reader.read_sleb128(); - // Normally, if ttype_index < 0, meaning the catch type is exception specification. - // Since we only care about if ttype_index is zero, so casting ttype_index to u64 makes sense. - return Ok(interpret_cs_action(ttype_index as u64, lpad)); - } + return Ok(interpret_cs_action(action_table as *mut u8, cs_action_entry, lpad)); } } } @@ -129,28 +119,31 @@ pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result // Can never have null landing pad for sjlj -- that would have // been indicated by a -1 call site index. let lpad = (cs_lpad + 1) as usize; - if cs_action_entry == 0 { - return Ok(interpret_cs_action(0, lpad)); - } else { - let action_record = - (action_table as *mut u8).offset(cs_action_entry as isize - 1); - let mut action_reader = DwarfReader::new(action_record); - let ttype_index = action_reader.read_sleb128(); - return Ok(interpret_cs_action(ttype_index as u64, lpad)); - } + return Ok(interpret_cs_action(action_table as *mut u8, cs_action_entry, lpad)); } } } } -fn interpret_cs_action(cs_action: u64, lpad: usize) -> EHAction { - if cs_action == 0 { +unsafe fn interpret_cs_action( + action_table: *mut u8, + cs_action_entry: u64, + lpad: usize, +) -> EHAction { + if cs_action_entry == 0 { // If cs_action is 0 then this is a cleanup (Drop::drop). We run these // for both Rust panics and foreign exceptions. EHAction::Cleanup(lpad) } else { - // Stop unwinding Rust panics at catch_unwind. - EHAction::Catch(lpad) + let action_record = (action_table as *mut u8).offset(cs_action_entry as isize - 1); + let mut action_reader = DwarfReader::new(action_record); + let ttype_index = action_reader.read_sleb128(); + if ttype_index == 0 { + EHAction::Cleanup(lpad) + } else { + // Stop unwinding Rust panics at catch_unwind. + EHAction::Catch(lpad) + } } } From 93ef4b3991d19cddf011da8f0b5a7bf9a8672541 Mon Sep 17 00:00:00 2001 From: Kai Luo Date: Mon, 9 Jan 2023 23:26:06 +0800 Subject: [PATCH 5/5] Add comment --- library/std/src/personality/dwarf/eh.rs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/library/std/src/personality/dwarf/eh.rs b/library/std/src/personality/dwarf/eh.rs index 4d114d61674..87585a8fcd0 100644 --- a/library/std/src/personality/dwarf/eh.rs +++ b/library/std/src/personality/dwarf/eh.rs @@ -131,10 +131,12 @@ unsafe fn interpret_cs_action( lpad: usize, ) -> EHAction { if cs_action_entry == 0 { - // If cs_action is 0 then this is a cleanup (Drop::drop). We run these + // If cs_action_entry is 0 then this is a cleanup (Drop::drop). We run these // for both Rust panics and foreign exceptions. EHAction::Cleanup(lpad) } else { + // If lpad != 0 and cs_action_entry != 0, we have to check ttype_index. + // If ttype_index == 0 under the condition, we take cleanup action. let action_record = (action_table as *mut u8).offset(cs_action_entry as isize - 1); let mut action_reader = DwarfReader::new(action_record); let ttype_index = action_reader.read_sleb128();