aboutsummaryrefslogtreecommitdiff
path: root/cortex-m-rt/macros/src/lib.rs
diff options
context:
space:
mode:
authorGravatar Dion Dokter <dion@tweedegolf.com> 2023-05-19 10:49:46 +0200
committerGravatar Dion Dokter <dion@tweedegolf.com> 2023-05-19 10:51:17 +0200
commit70c3d0a2a1b3aeb97f5835dc481a767ecea909a4 (patch)
tree8bc5be381516c51aba1d59bf252f8c4e4f28ebf2 /cortex-m-rt/macros/src/lib.rs
parent82fa94d2cd2829cc37111d247e913cecdad561ac (diff)
downloadcortex-m-70c3d0a2a1b3aeb97f5835dc481a767ecea909a4.tar.gz
cortex-m-70c3d0a2a1b3aeb97f5835dc481a767ecea909a4.tar.zst
cortex-m-70c3d0a2a1b3aeb97f5835dc481a767ecea909a4.zip
Hardfault trampoline is now optional
Diffstat (limited to 'cortex-m-rt/macros/src/lib.rs')
-rw-r--r--cortex-m-rt/macros/src/lib.rs35
1 files changed, 34 insertions, 1 deletions
diff --git a/cortex-m-rt/macros/src/lib.rs b/cortex-m-rt/macros/src/lib.rs
index 27ee2f1..b529ef2 100644
--- a/cortex-m-rt/macros/src/lib.rs
+++ b/cortex-m-rt/macros/src/lib.rs
@@ -232,7 +232,7 @@ pub fn exception(args: TokenStream, input: TokenStream) -> TokenStream {
#f
)
}
- Exception::HardFault => {
+ Exception::HardFault if cfg!(feature = "hardfault-trampoline") => {
let valid_signature = f.sig.constness.is_none()
&& f.vis == Visibility::Inherited
&& f.sig.abi.is_none()
@@ -283,6 +283,39 @@ pub fn exception(args: TokenStream, input: TokenStream) -> TokenStream {
#f
)
}
+ Exception::HardFault => {
+ let valid_signature = f.sig.constness.is_none()
+ && f.vis == Visibility::Inherited
+ && f.sig.abi.is_none()
+ && f.sig.inputs.len() == 0
+ && f.sig.generics.params.is_empty()
+ && f.sig.generics.where_clause.is_none()
+ && f.sig.variadic.is_none()
+ && match f.sig.output {
+ ReturnType::Default => false,
+ ReturnType::Type(_, ref ty) => matches!(**ty, Type::Never(_)),
+ };
+
+ if !valid_signature {
+ return parse::Error::new(
+ fspan,
+ "`HardFault` handler must have signature `unsafe fn() -> !`",
+ )
+ .to_compile_error()
+ .into();
+ }
+
+ f.sig.ident = Ident::new(&format!("__cortex_m_rt_{}", f.sig.ident), Span::call_site());
+
+ quote!(
+ #[export_name = "HardFault"]
+ // Only emit link_section when building for embedded targets,
+ // because some hosted platforms (used to check the build)
+ // cannot handle the long link section names.
+ #[cfg_attr(target_os = "none", link_section = ".HardFault.user")]
+ #f
+ )
+ }
Exception::NonMaskableInt | Exception::Other => {
let valid_signature = f.sig.constness.is_none()
&& f.vis == Visibility::Inherited