diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 57092a752f5..9962dcb0740 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -23,7 +23,7 @@ on: env: CARGO_TERM_COLOR: always GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} - MSRV: "1.79.0" + MSRV: "1.83.0" RUSTDOCFLAGS: -Dwarnings DEFMT_LOG: trace diff --git a/esp-hal-embassy/CHANGELOG.md b/esp-hal-embassy/CHANGELOG.md index 7a766bb6135..9482b188b1e 100644 --- a/esp-hal-embassy/CHANGELOG.md +++ b/esp-hal-embassy/CHANGELOG.md @@ -7,10 +7,13 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] + ### Added ### Changed +- Bump MSRV to 1.83 (#2615) + ### Fixed ### Removed diff --git a/esp-hal-embassy/Cargo.toml b/esp-hal-embassy/Cargo.toml index 9d6885b2b6f..651c47f6222 100644 --- a/esp-hal-embassy/Cargo.toml +++ b/esp-hal-embassy/Cargo.toml @@ -2,7 +2,7 @@ name = "esp-hal-embassy" version = "0.5.0" edition = "2021" -rust-version = "1.79.0" +rust-version = "1.83.0" description = "Embassy support for esp-hal" repository = "https://github.com/esp-rs/esp-hal" license = "MIT OR Apache-2.0" diff --git a/esp-hal-embassy/README.md b/esp-hal-embassy/README.md index 411cc69ce03..998c6fe3d63 100644 --- a/esp-hal-embassy/README.md +++ b/esp-hal-embassy/README.md @@ -2,7 +2,7 @@ [![Crates.io](https://img.shields.io/crates/v/esp-hal-embassy?labelColor=1C2C2E&color=C96329&logo=Rust&style=flat-square)](https://crates.io/crates/esp-hal-embassy) [![docs.rs](https://img.shields.io/docsrs/esp-hal-embassy?labelColor=1C2C2E&color=C96329&logo=rust&style=flat-square)](https://docs.rs/esp-hal-embassy) -![MSRV](https://img.shields.io/badge/MSRV-1.76-blue?labelColor=1C2C2E&style=flat-square) +![MSRV](https://img.shields.io/badge/MSRV-1.83-blue?labelColor=1C2C2E&style=flat-square) ![Crates.io](https://img.shields.io/crates/l/esp-hal-embassy?labelColor=1C2C2E&style=flat-square) [![Matrix](https://img.shields.io/matrix/esp-rs:matrix.org?label=join%20matrix&labelColor=1C2C2E&color=BEC5C9&logo=matrix&style=flat-square)](https://matrix.to/#/#esp-rs:matrix.org) @@ -18,7 +18,7 @@ Note that this crate currently requires you to enable the `unstable` feature on ## Minimum Supported Rust Version (MSRV) -This crate is guaranteed to compile on stable Rust 1.79 and up. It _might_ +This crate is guaranteed to compile on stable Rust 1.83 and up. It _might_ compile with older versions but that may change in any new patch release. ## License diff --git a/esp-hal-procmacros/Cargo.toml b/esp-hal-procmacros/Cargo.toml index bb4e9592f4b..3b2eec93acb 100644 --- a/esp-hal-procmacros/Cargo.toml +++ b/esp-hal-procmacros/Cargo.toml @@ -2,7 +2,7 @@ name = "esp-hal-procmacros" version = "0.15.0" edition = "2021" -rust-version = "1.76.0" +rust-version = "1.83.0" description = "Procedural macros for esp-hal" repository = "https://github.com/esp-rs/esp-hal" license = "MIT OR Apache-2.0" diff --git a/esp-hal/CHANGELOG.md b/esp-hal/CHANGELOG.md index 68f4672270d..f75a2bcb610 100644 --- a/esp-hal/CHANGELOG.md +++ b/esp-hal/CHANGELOG.md @@ -7,6 +7,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] + ### Added - ESP32-S3: Added SDMMC signals (#2556) @@ -35,6 +36,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Changed +- Bump MSRV to 1.83 (#2615) - In addition to taking by value, peripheral drivers can now mutably borrow DMA channel objects. (#2526) - DMA channel objects are no longer wrapped in `Channel`. The `Channel` drivers are now managed by DMA enabled peripheral drivers. (#2526) - The `Dpi` driver and `DpiTransfer` now have a `Mode` type parameter. The driver's asyncness is determined by the asyncness of the `Lcd` used to create it. (#2526) @@ -200,8 +202,6 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [0.21.0] -- Bump MSRV to 1.79.0 (#1971) - ### Added - Introduce traits for the DMA buffer objects (#1976, #2213) diff --git a/esp-hal/Cargo.toml b/esp-hal/Cargo.toml index d28f9c221a6..8142ec59bc9 100644 --- a/esp-hal/Cargo.toml +++ b/esp-hal/Cargo.toml @@ -2,7 +2,7 @@ name = "esp-hal" version = "0.22.0" edition = "2021" -rust-version = "1.79.0" +rust-version = "1.83.0" description = "Bare-metal HAL for Espressif devices" documentation = "https://docs.esp-rs.org/esp-hal/" repository = "https://github.com/esp-rs/esp-hal" diff --git a/esp-hal/README.md b/esp-hal/README.md index 9b887d93261..5a5eaf844af 100644 --- a/esp-hal/README.md +++ b/esp-hal/README.md @@ -2,7 +2,7 @@ [![Crates.io](https://img.shields.io/crates/v/esp-hal?labelColor=1C2C2E&color=C96329&logo=Rust&style=flat-square)](https://crates.io/crates/esp-hal) [![docs.rs](https://img.shields.io/docsrs/esp-hal?labelColor=1C2C2E&color=C96329&logo=rust&style=flat-square)](https://docs.esp-rs.org/esp-hal) -![MSRV](https://img.shields.io/badge/MSRV-1.76-blue?labelColor=1C2C2E&style=flat-square) +![MSRV](https://img.shields.io/badge/MSRV-1.83-blue?labelColor=1C2C2E&style=flat-square) ![Crates.io](https://img.shields.io/crates/l/esp-hal?labelColor=1C2C2E&style=flat-square) [![Matrix](https://img.shields.io/matrix/esp-rs:matrix.org?label=join%20matrix&labelColor=1C2C2E&color=BEC5C9&logo=matrix&style=flat-square)](https://matrix.to/#/#esp-rs:matrix.org) @@ -48,7 +48,7 @@ For help getting started with this HAL, please refer to [The Rust on ESP Book] a ## Minimum Supported Rust Version (MSRV) -This crate is guaranteed to compile on stable Rust 1.79 and up. It _might_ +This crate is guaranteed to compile on stable Rust 1.83 and up. It _might_ compile with older versions but that may change in any new patch release. ## License diff --git a/esp-hal/src/analog/adc/esp32.rs b/esp-hal/src/analog/adc/esp32.rs index d5d99358f10..afdb563adf1 100644 --- a/esp-hal/src/analog/adc/esp32.rs +++ b/esp-hal/src/analog/adc/esp32.rs @@ -327,7 +327,7 @@ where } } -impl<'d, ADC1> Adc<'d, ADC1> { +impl Adc<'_, ADC1> { /// Enable the Hall sensor pub fn enable_hall_sensor() { unsafe { &*RTC_IO::ptr() } diff --git a/esp-hal/src/assist_debug.rs b/esp-hal/src/assist_debug.rs index 437aaaef223..0063b4f1eae 100644 --- a/esp-hal/src/assist_debug.rs +++ b/esp-hal/src/assist_debug.rs @@ -391,7 +391,7 @@ impl DebugAssist<'_> { } #[cfg(all(assist_debug_region_monitor, multi_core))] -impl<'d> DebugAssist<'d> { +impl DebugAssist<'_> { /// Enable region monitoring of read/write performed by the secondary CPU in /// a certain memory region0. Whenever the bus reads or writes in the /// specified memory region, an interrupt will be triggered. diff --git a/esp-hal/src/dma/mod.rs b/esp-hal/src/dma/mod.rs index 6c542da5a60..9b697b11478 100644 --- a/esp-hal/src/dma/mod.rs +++ b/esp-hal/src/dma/mod.rs @@ -1892,7 +1892,7 @@ where } } -impl<'a, M, CH> ChannelRx<'a, M, CH> +impl ChannelRx<'_, M, CH> where M: Mode, CH: DmaRxChannel, @@ -2186,7 +2186,7 @@ where } } -impl<'a, M, CH> ChannelTx<'a, M, CH> +impl ChannelTx<'_, M, CH> where M: Mode, CH: DmaTxChannel, diff --git a/esp-hal/src/dma/pdma/mod.rs b/esp-hal/src/dma/pdma/mod.rs index 12d744f1469..7461cab5e4f 100644 --- a/esp-hal/src/dma/pdma/mod.rs +++ b/esp-hal/src/dma/pdma/mod.rs @@ -194,7 +194,7 @@ pub(super) fn init_dma(_cs: CriticalSection<'_>) { } } -impl<'d, CH, M> Channel<'d, M, CH> +impl Channel<'_, M, CH> where CH: DmaChannel, M: Mode, diff --git a/esp-hal/src/gpio/mod.rs b/esp-hal/src/gpio/mod.rs index 1c96a76ad91..9d76487849d 100644 --- a/esp-hal/src/gpio/mod.rs +++ b/esp-hal/src/gpio/mod.rs @@ -2459,7 +2459,7 @@ mod asynch { pin: Flex<'d, P>, } - impl<'d, P: InputPin> PinFuture<'d, P> { + impl PinFuture<'_, P> { fn pin_mask(&self) -> u32 { let bank = self.pin.gpio_bank(private::Internal); 1 << (self.pin.number() - bank.offset()) diff --git a/esp-hal/src/i2s/parallel.rs b/esp-hal/src/i2s/parallel.rs index 1bb0d8cc7a2..030fcf38e78 100644 --- a/esp-hal/src/i2s/parallel.rs +++ b/esp-hal/src/i2s/parallel.rs @@ -401,7 +401,7 @@ where } } -impl<'d, I, BUF, DM> Deref for I2sParallelTransfer<'d, BUF, DM, I> +impl Deref for I2sParallelTransfer<'_, BUF, DM, I> where I: Instance, BUF: DmaTxBuffer, @@ -414,7 +414,7 @@ where } } -impl<'d, I, BUF, DM> DerefMut for I2sParallelTransfer<'d, BUF, DM, I> +impl DerefMut for I2sParallelTransfer<'_, BUF, DM, I> where I: Instance, BUF: DmaTxBuffer, @@ -425,7 +425,7 @@ where } } -impl<'d, I, BUF, DM> Drop for I2sParallelTransfer<'d, BUF, DM, I> +impl Drop for I2sParallelTransfer<'_, BUF, DM, I> where I: Instance, BUF: DmaTxBuffer, diff --git a/esp-hal/src/lcd_cam/cam.rs b/esp-hal/src/lcd_cam/cam.rs index abe7d8c7673..27b1dfa141e 100644 --- a/esp-hal/src/lcd_cam/cam.rs +++ b/esp-hal/src/lcd_cam/cam.rs @@ -432,7 +432,7 @@ impl<'d, BUF: DmaRxBuffer> CameraTransfer<'d, BUF> { } } -impl<'d, BUF: DmaRxBuffer> Deref for CameraTransfer<'d, BUF> { +impl Deref for CameraTransfer<'_, BUF> { type Target = BUF::View; fn deref(&self) -> &Self::Target { @@ -440,13 +440,13 @@ impl<'d, BUF: DmaRxBuffer> Deref for CameraTransfer<'d, BUF> { } } -impl<'d, BUF: DmaRxBuffer> DerefMut for CameraTransfer<'d, BUF> { +impl DerefMut for CameraTransfer<'_, BUF> { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.buffer_view } } -impl<'d, BUF: DmaRxBuffer> Drop for CameraTransfer<'d, BUF> { +impl Drop for CameraTransfer<'_, BUF> { fn drop(&mut self) { self.stop_peripherals(); diff --git a/esp-hal/src/lcd_cam/lcd/dpi.rs b/esp-hal/src/lcd_cam/lcd/dpi.rs index 368ae1c8aed..7c43a54dccc 100644 --- a/esp-hal/src/lcd_cam/lcd/dpi.rs +++ b/esp-hal/src/lcd_cam/lcd/dpi.rs @@ -661,7 +661,7 @@ impl<'d, BUF: DmaTxBuffer, DM: Mode> DpiTransfer<'d, BUF, DM> { } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> Deref for DpiTransfer<'d, BUF, DM> { +impl Deref for DpiTransfer<'_, BUF, DM> { type Target = BUF::View; fn deref(&self) -> &Self::Target { @@ -669,13 +669,13 @@ impl<'d, BUF: DmaTxBuffer, DM: Mode> Deref for DpiTransfer<'d, BUF, DM> { } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> DerefMut for DpiTransfer<'d, BUF, DM> { +impl DerefMut for DpiTransfer<'_, BUF, DM> { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.buffer_view } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> Drop for DpiTransfer<'d, BUF, DM> { +impl Drop for DpiTransfer<'_, BUF, DM> { fn drop(&mut self) { self.stop_peripherals(); diff --git a/esp-hal/src/lcd_cam/lcd/i8080.rs b/esp-hal/src/lcd_cam/lcd/i8080.rs index 7cea535d765..2f351ca3993 100644 --- a/esp-hal/src/lcd_cam/lcd/i8080.rs +++ b/esp-hal/src/lcd_cam/lcd/i8080.rs @@ -396,7 +396,7 @@ where } } -impl<'d, DM: Mode> core::fmt::Debug for I8080<'d, DM> { +impl core::fmt::Debug for I8080<'_, DM> { fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result { f.debug_struct("I8080").finish() } @@ -470,7 +470,7 @@ impl<'d, BUF: DmaTxBuffer, DM: Mode> I8080Transfer<'d, BUF, DM> { } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> Deref for I8080Transfer<'d, BUF, DM> { +impl Deref for I8080Transfer<'_, BUF, DM> { type Target = BUF::View; fn deref(&self) -> &Self::Target { @@ -478,7 +478,7 @@ impl<'d, BUF: DmaTxBuffer, DM: Mode> Deref for I8080Transfer<'d, BUF, DM> { } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> DerefMut for I8080Transfer<'d, BUF, DM> { +impl DerefMut for I8080Transfer<'_, BUF, DM> { fn deref_mut(&mut self) -> &mut Self::Target { &mut self.buf_view } @@ -523,7 +523,7 @@ impl<'d, BUF: DmaTxBuffer> I8080Transfer<'d, BUF, crate::Async> { } } -impl<'d, BUF: DmaTxBuffer, DM: Mode> Drop for I8080Transfer<'d, BUF, DM> { +impl Drop for I8080Transfer<'_, BUF, DM> { fn drop(&mut self) { self.stop_peripherals(); @@ -645,7 +645,7 @@ impl<'d> TxEightBits<'d> { } } -impl<'d> TxPins for TxEightBits<'d> { +impl TxPins for TxEightBits<'_> { fn configure(&mut self) { const SIGNALS: [OutputSignal; 8] = [ OutputSignal::LCD_DATA_0, @@ -706,7 +706,7 @@ impl<'d> TxSixteenBits<'d> { } } -impl<'d> TxPins for TxSixteenBits<'d> { +impl TxPins for TxSixteenBits<'_> { fn configure(&mut self) { const SIGNALS: [OutputSignal; 16] = [ OutputSignal::LCD_DATA_0, diff --git a/esp-hal/src/ledc/timer.rs b/esp-hal/src/ledc/timer.rs index 30bf8082652..1534feffc20 100644 --- a/esp-hal/src/ledc/timer.rs +++ b/esp-hal/src/ledc/timer.rs @@ -369,7 +369,7 @@ impl TimerHW for Timer<'_, LowSpeed> { #[cfg(esp32)] /// Timer HW implementation for HighSpeed timers -impl<'a> TimerHW for Timer<'a, HighSpeed> { +impl TimerHW for Timer<'_, HighSpeed> { /// Get the current source timer frequency from the HW fn freq_hw(&self) -> Option { self.clock_source.map(|source| match source { diff --git a/esp-hal/src/otg_fs.rs b/esp-hal/src/otg_fs.rs index bdcf56d5365..3823e23ed15 100644 --- a/esp-hal/src/otg_fs.rs +++ b/esp-hal/src/otg_fs.rs @@ -109,9 +109,9 @@ impl<'d> Usb<'d> { } } -unsafe impl<'d> Sync for Usb<'d> {} +unsafe impl Sync for Usb<'_> {} -unsafe impl<'d> UsbPeripheral for Usb<'d> { +unsafe impl UsbPeripheral for Usb<'_> { const REGISTERS: *const () = peripherals::USB0::ptr() as *const (); const HIGH_SPEED: bool = false; @@ -250,7 +250,7 @@ pub mod asynch { _usb: Usb<'d>, } - impl<'d> Bus<'d> { + impl Bus<'_> { fn init(&mut self) { Usb::_enable(); @@ -328,7 +328,7 @@ pub mod asynch { } } - impl<'d> Drop for Bus<'d> { + impl Drop for Bus<'_> { fn drop(&mut self) { Bus::disable(self); } diff --git a/esp-hal/src/rsa/esp32.rs b/esp-hal/src/rsa/esp32.rs index c5b9938d824..56b6ea3a547 100644 --- a/esp-hal/src/rsa/esp32.rs +++ b/esp-hal/src/rsa/esp32.rs @@ -10,7 +10,7 @@ use crate::rsa::{ RsaMultiplication, }; -impl<'d, DM: crate::Mode> Rsa<'d, DM> { +impl Rsa<'_, DM> { /// After the RSA Accelerator is released from reset, the memory blocks /// needs to be initialized, only after that peripheral should be used. /// This function would return without an error if the memory is initialized @@ -79,7 +79,7 @@ pub mod operand_sizes { ); } -impl<'a, 'd, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularMultiplication<'a, 'd, T, DM> +impl<'d, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularMultiplication<'_, 'd, T, DM> where T: RsaMode, { @@ -98,7 +98,7 @@ where } } -impl<'a, 'd, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularExponentiation<'a, 'd, T, DM> +impl<'d, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularExponentiation<'_, 'd, T, DM> where T: RsaMode, { @@ -108,7 +108,7 @@ where } } -impl<'a, 'd, T: RsaMode + Multi, DM: crate::Mode, const N: usize> RsaMultiplication<'a, 'd, T, DM> +impl<'d, T: RsaMode + Multi, DM: crate::Mode, const N: usize> RsaMultiplication<'_, 'd, T, DM> where T: RsaMode, { diff --git a/esp-hal/src/rsa/esp32sX.rs b/esp-hal/src/rsa/esp32sX.rs index 588da50d318..7af4ff4b601 100644 --- a/esp-hal/src/rsa/esp32sX.rs +++ b/esp-hal/src/rsa/esp32sX.rs @@ -10,7 +10,7 @@ use crate::rsa::{ RsaMultiplication, }; -impl<'d, DM: crate::Mode> Rsa<'d, DM> { +impl Rsa<'_, DM> { /// After the RSA accelerator is released from reset, the memory blocks /// needs to be initialized, only after that peripheral should be used. /// This function would return without an error if the memory is @@ -248,7 +248,7 @@ pub mod operand_sizes { ); } -impl<'a, 'd, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularExponentiation<'a, 'd, T, DM> +impl<'d, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularExponentiation<'_, 'd, T, DM> where T: RsaMode, { @@ -268,7 +268,7 @@ where } } -impl<'a, 'd, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularMultiplication<'a, 'd, T, DM> +impl<'d, T: RsaMode, DM: crate::Mode, const N: usize> RsaModularMultiplication<'_, 'd, T, DM> where T: RsaMode, { @@ -281,7 +281,7 @@ where } } -impl<'a, 'd, T: RsaMode + Multi, DM: crate::Mode, const N: usize> RsaMultiplication<'a, 'd, T, DM> +impl<'d, T: RsaMode + Multi, DM: crate::Mode, const N: usize> RsaMultiplication<'_, 'd, T, DM> where T: RsaMode, { diff --git a/esp-hal/src/rtc_cntl/sleep/esp32s3.rs b/esp-hal/src/rtc_cntl/sleep/esp32s3.rs index 3fbb349a264..44e8bd63899 100644 --- a/esp-hal/src/rtc_cntl/sleep/esp32s3.rs +++ b/esp-hal/src/rtc_cntl/sleep/esp32s3.rs @@ -234,7 +234,7 @@ impl Drop for Ext1WakeupSource<'_, '_> { } } -impl<'a, 'b> RtcioWakeupSource<'a, 'b> { +impl RtcioWakeupSource<'_, '_> { fn apply_pin(&self, pin: &mut dyn RtcPin, level: WakeupLevel) { let rtcio = unsafe { &*crate::peripherals::RTC_IO::PTR }; diff --git a/esp-hal/src/soc/esp32/cpu_control.rs b/esp-hal/src/soc/esp32/cpu_control.rs index d0a0a143202..3d557ed163a 100644 --- a/esp-hal/src/soc/esp32/cpu_control.rs +++ b/esp-hal/src/soc/esp32/cpu_control.rs @@ -127,7 +127,7 @@ pub struct AppCoreGuard<'a> { phantom: PhantomData<&'a ()>, } -impl<'a> Drop for AppCoreGuard<'a> { +impl Drop for AppCoreGuard<'_> { fn drop(&mut self) { unsafe { internal_park_core(Cpu::AppCpu); @@ -323,6 +323,7 @@ impl<'d> CpuControl<'d> { where F: FnOnce(), { + #[allow(static_mut_refs)] // FIXME match START_CORE1_FUNCTION.take() { Some(entry) => { let entry = unsafe { ManuallyDrop::take(&mut *entry.cast::>()) }; diff --git a/esp-hal/src/soc/esp32s3/cpu_control.rs b/esp-hal/src/soc/esp32s3/cpu_control.rs index 9e086bed5e2..f2494bf44f0 100644 --- a/esp-hal/src/soc/esp32s3/cpu_control.rs +++ b/esp-hal/src/soc/esp32s3/cpu_control.rs @@ -127,7 +127,7 @@ pub struct AppCoreGuard<'a> { phantom: PhantomData<&'a ()>, } -impl<'a> Drop for AppCoreGuard<'a> { +impl Drop for AppCoreGuard<'_> { fn drop(&mut self) { unsafe { internal_park_core(Cpu::AppCpu); @@ -259,6 +259,7 @@ impl<'d> CpuControl<'d> { where F: FnOnce(), { + #[allow(static_mut_refs)] // FIXME match START_CORE1_FUNCTION.take() { Some(entry) => { let entry = unsafe { ManuallyDrop::take(&mut *entry.cast::>()) }; diff --git a/esp-hal/src/soc/mod.rs b/esp-hal/src/soc/mod.rs index e5a41924589..562510e902d 100644 --- a/esp-hal/src/soc/mod.rs +++ b/esp-hal/src/soc/mod.rs @@ -30,6 +30,7 @@ static mut MAPPED_PSRAM: MappedPsram = MappedPsram { memory_range: 0..0 }; pub(crate) fn psram_range() -> Range { cfg_if::cfg_if! { if #[cfg(any(feature = "quad-psram", feature = "octal-psram"))] { + #[allow(static_mut_refs)] unsafe { MAPPED_PSRAM.memory_range.clone() } } else { 0..0 diff --git a/esp-hal/src/spi/slave.rs b/esp-hal/src/spi/slave.rs index 62a97e4c4ba..db7c7314d6c 100644 --- a/esp-hal/src/spi/slave.rs +++ b/esp-hal/src/spi/slave.rs @@ -315,7 +315,7 @@ pub mod dma { } } - impl<'d, M, T> SpiDma<'d, M, T> + impl SpiDma<'_, M, T> where M: Mode, T: InstanceDma, diff --git a/esp-hal/src/timer/mod.rs b/esp-hal/src/timer/mod.rs index 562f510bc63..481bcd3d382 100644 --- a/esp-hal/src/timer/mod.rs +++ b/esp-hal/src/timer/mod.rs @@ -155,7 +155,7 @@ where } } -impl<'d, T> OneShotTimer<'d, Async, T> +impl OneShotTimer<'_, Async, T> where T: Timer, { @@ -197,7 +197,7 @@ where } } -impl<'d, M, T> OneShotTimer<'d, M, T> +impl OneShotTimer<'_, M, T> where M: Mode, T: Timer, @@ -329,7 +329,7 @@ where } } -impl<'d, M, T> PeriodicTimer<'d, M, T> +impl PeriodicTimer<'_, M, T> where M: Mode, T: Timer, diff --git a/esp-hal/src/touch.rs b/esp-hal/src/touch.rs index be26e24c52e..35825953206 100644 --- a/esp-hal/src/touch.rs +++ b/esp-hal/src/touch.rs @@ -90,7 +90,7 @@ pub struct Touch<'d, TOUCHMODE: TouchMode, MODE: Mode> { _touch_mode: PhantomData, _mode: PhantomData, } -impl<'d, TOUCHMODE: TouchMode, MODE: Mode> Touch<'d, TOUCHMODE, MODE> { +impl Touch<'_, TOUCHMODE, MODE> { /// Common initialization of the touch peripheral. fn initialize_common(config: Option) { let rtccntl = unsafe { &*RTC_CNTL::ptr() }; diff --git a/esp-ieee802154/CHANGELOG.md b/esp-ieee802154/CHANGELOG.md index 747b0e8b3b3..658aec3ae2d 100644 --- a/esp-ieee802154/CHANGELOG.md +++ b/esp-ieee802154/CHANGELOG.md @@ -7,10 +7,13 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] + ### Added ### Changed +- Bump MSRV to 1.83 (#2615) + ### Fixed ### Removed diff --git a/esp-ieee802154/Cargo.toml b/esp-ieee802154/Cargo.toml index b1a6bcd1207..231167b3710 100644 --- a/esp-ieee802154/Cargo.toml +++ b/esp-ieee802154/Cargo.toml @@ -2,7 +2,7 @@ name = "esp-ieee802154" version = "0.4.0" edition = "2021" -rust-version = "1.76.0" +rust-version = "1.83.0" description = "Low-level IEEE 802.15.4 driver for the ESP32-C6 and ESP32-H2" repository = "https://github.com/esp-rs/esp-hal" license = "MIT OR Apache-2.0" diff --git a/esp-ieee802154/README.md b/esp-ieee802154/README.md index e7a60084679..fbf7e41c2e5 100644 --- a/esp-ieee802154/README.md +++ b/esp-ieee802154/README.md @@ -2,7 +2,7 @@ [![Crates.io](https://img.shields.io/crates/v/esp-ieee802154?labelColor=1C2C2E&color=C96329&logo=Rust&style=flat-square)](https://crates.io/crates/esp-ieee802154) [![docs.rs](https://img.shields.io/docsrs/esp-ieee802154?labelColor=1C2C2E&color=C96329&logo=rust&style=flat-square)](https://docs.rs/esp-ieee802154) -![MSRV](https://img.shields.io/badge/MSRV-1.76-blue?labelColor=1C2C2E&style=flat-square) +![MSRV](https://img.shields.io/badge/MSRV-1.83-blue?labelColor=1C2C2E&style=flat-square) ![Crates.io](https://img.shields.io/crates/l/esp-ieee802154?labelColor=1C2C2E&style=flat-square) [![Matrix](https://img.shields.io/matrix/esp-rs:matrix.org?label=join%20matrix&labelColor=1C2C2E&color=BEC5C9&logo=matrix&style=flat-square)](https://matrix.to/#/#esp-rs:matrix.org) @@ -16,7 +16,7 @@ Implements the PHY/MAC layers of the IEEE802.15.4 protocol stack, and supports s ## Minimum Supported Rust Version (MSRV) -This crate is guaranteed to compile on stable Rust 1.76 and up. It _might_ +This crate is guaranteed to compile on stable Rust 1.83 and up. It _might_ compile with older versions but that may change in any new patch release. ## License diff --git a/esp-println/src/lib.rs b/esp-println/src/lib.rs index efa71327678..c71ebfd73be 100644 --- a/esp-println/src/lib.rs +++ b/esp-println/src/lib.rs @@ -478,7 +478,7 @@ type LockInner<'a> = critical_section::CriticalSection<'a>; #[derive(Clone, Copy)] struct LockToken<'a>(LockInner<'a>); -impl<'a> LockToken<'a> { +impl LockToken<'_> { #[allow(unused)] unsafe fn conjure() -> Self { #[cfg(feature = "critical-section")] diff --git a/esp-wifi/CHANGELOG.md b/esp-wifi/CHANGELOG.md index 5f9b7ef3457..4a9324bf8d7 100644 --- a/esp-wifi/CHANGELOG.md +++ b/esp-wifi/CHANGELOG.md @@ -7,11 +7,15 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] + ### Added ### Changed +- Bump MSRV to 1.83 (#2615) + ### Fixed + - Fixed triggering a debug-assertion during scan (#2612) ### Removed diff --git a/esp-wifi/Cargo.toml b/esp-wifi/Cargo.toml index 00193a6ca21..0925bf50377 100644 --- a/esp-wifi/Cargo.toml +++ b/esp-wifi/Cargo.toml @@ -2,7 +2,7 @@ name = "esp-wifi" version = "0.11.0" edition = "2021" -rust-version = "1.79.0" +rust-version = "1.83.0" authors = ["The ESP-RS team"] description = "A WiFi, Bluetooth and ESP-NOW driver for use with Espressif chips and bare-metal Rust" documentation = "https://docs.esp-rs.org/esp-hal/" diff --git a/esp-wifi/README.md b/esp-wifi/README.md index 9eabc3c6179..b6c3b7c8e9e 100644 --- a/esp-wifi/README.md +++ b/esp-wifi/README.md @@ -2,7 +2,7 @@ [![Crates.io](https://img.shields.io/crates/v/esp-wifi?labelColor=1C2C2E&color=C96329&logo=Rust&style=flat-square)](https://crates.io/crates/esp-wifi) [![docs.rs](https://img.shields.io/docsrs/esp-wifi?labelColor=1C2C2E&color=C96329&logo=rust&style=flat-square)](https://docs.esp-rs.org/esp-hal) -![MSRV](https://img.shields.io/badge/MSRV-1.76-blue?labelColor=1C2C2E&style=flat-square) +![MSRV](https://img.shields.io/badge/MSRV-1.83-blue?labelColor=1C2C2E&style=flat-square) ![Crates.io](https://img.shields.io/crates/l/esp-wifi?labelColor=1C2C2E&style=flat-square) [![Matrix](https://img.shields.io/matrix/esp-rs:matrix.org?label=join%20matrix&labelColor=1C2C2E&color=BEC5C9&logo=matrix&style=flat-square)](https://matrix.to/#/#esp-rs:matrix.org) @@ -24,7 +24,10 @@ If a cell contains an em dash (—) this means that the particular feature i | ESP32-S2 | ✓ | — | — | ✓ | | ESP32-S3 | ✓ | ✓ | ✓ | ✓ | -Minimum supported Rust compiler version: 1.79.0 +## Minimum Supported Rust Version (MSRV) + +This crate is guaranteed to compile on stable Rust 1.83 and up. It _might_ +compile with older versions but that may change in any new patch release. ## Missing / To be done diff --git a/xtask/src/main.rs b/xtask/src/main.rs index 775bb86829c..49dac201dfe 100644 --- a/xtask/src/main.rs +++ b/xtask/src/main.rs @@ -790,7 +790,7 @@ fn lint_package(chip: &Chip, path: &Path, args: &[&str], fix: bool) -> Result<() // build in release to reuse example artifacts let cargo_args = builder.arg("--release"); let cargo_args = if fix { - cargo_args.arg("--fix").arg("--lib") + cargo_args.arg("--fix").arg("--lib").arg("--allow-dirty") } else { cargo_args.arg("--").arg("-D").arg("warnings") }; diff --git a/xtensa-lx-rt/src/exception/asm.rs b/xtensa-lx-rt/src/exception/asm.rs index 4155d5f7e34..cfd24bf0228 100644 --- a/xtensa-lx-rt/src/exception/asm.rs +++ b/xtensa-lx-rt/src/exception/asm.rs @@ -1,6 +1,6 @@ -use core::arch::{asm, global_asm}; +use core::arch::global_asm; -use crate::cfg_asm; +use crate::cfg_global_asm; // We could cfg symbols away and reduce frame size depending on features enabled // i.e the frame size is a fixed size based on all the features right now @@ -89,188 +89,7 @@ global_asm!( .set PS_EXCM, 0x00000010 .set PS_UM, 0x00000020 .set PS_WOE, 0x00040000 - " -); -/// Save processor state to stack. -/// -/// *Must only be called with call0.* -/// *For spill all window registers to work WOE must be enabled on entry -/// -/// Saves all registers except PC, PS, A0, A1 -/// -/// Inputs: -/// A0 is the return address -/// A1 is the stack pointers -/// Exceptions are disabled (PS.EXCM = 1) -/// -/// Output: -/// A0 is the return address -/// A1 is the stack pointer -/// A3, A9 are used as scratch registers -/// EPC1 is changed -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn save_context() { - cfg_asm!( - { - " - s32i a2, sp, +XT_STK_A2 - s32i a3, sp, +XT_STK_A3 - s32i a4, sp, +XT_STK_A4 - s32i a5, sp, +XT_STK_A5 - s32i a6, sp, +XT_STK_A6 - s32i a7, sp, +XT_STK_A7 - s32i a8, sp, +XT_STK_A8 - s32i a9, sp, +XT_STK_A9 - s32i a10, sp, +XT_STK_A10 - s32i a11, sp, +XT_STK_A11 - s32i a12, sp, +XT_STK_A12 - s32i a13, sp, +XT_STK_A13 - s32i a14, sp, +XT_STK_A14 - s32i a15, sp, +XT_STK_A15 - - rsr a3, SAR - s32i a3, sp, +XT_STK_SAR - ", - #[cfg(all(XCHAL_HAVE_CP, not(feature = "float-save-restore")))] - " - /* Disable coprocessor, any use of floats in ISRs will cause an exception unless float-save-restore feature is enabled */ - rsr a3, CPENABLE - s32i a3, sp, +XT_STK_F64R_LO_CPENABLE - movi a3, 0 - wsr a3, CPENABLE - rsync - ", - #[cfg(XCHAL_HAVE_LOOPS)] - " - // Loop Option - rsr a3, LBEG - s32i a3, sp, +XT_STK_LBEG - rsr a3, LEND - s32i a3, sp, +XT_STK_LEND - rsr a3, LCOUNT - s32i a3, sp, +XT_STK_LCOUNT - ", - #[cfg(XCHAL_HAVE_THREADPTR)] - " - // Thread Pointer Option - rur a3, threadptr - s32i a3, sp, +XT_STK_THREADPTR - ", - #[cfg(XCHAL_HAVE_S32C1I)] - " - // Conditional Store Option - rsr a3, scompare1 - s32i a3, sp, +XT_STK_SCOMPARE1 - ", - #[cfg(XCHAL_HAVE_BOOLEANS)] - " - // Boolean Option - rsr a3, br - s32i a3, sp, +XT_STK_BR - ", - #[cfg(XCHAL_HAVE_MAC16)] - " - // MAC16 Option - rsr a3, acclo - s32i a3, sp, +XT_STK_ACCLO - rsr a3, acchi - s32i a3, sp, +XT_STK_ACCHI - rsr a3, m0 - s32i a3, sp, +XT_STK_M0 - rsr a3, m1 - s32i a3, sp, +XT_STK_M1 - rsr a3, m2 - s32i a3, sp, +XT_STK_M2 - rsr a3, m3 - s32i a3, sp, +XT_STK_M3 - ", - #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_DFP_ACCEL))] - " - // Double Precision Accelerator Option - rur a3, f64r_lo - s32i a3, sp, +XT_STK_F64R_LO_CPENABLE - rur a3, f64r_hi - s32i a3, sp, +XT_STK_F64R_HI - rur a3, f64s - s32i a3, sp, +XT_STK_F64S - ", - #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_FP))] - " - // Coprocessor Option - rur a3, fcr - s32i a3, sp, +XT_STK_FCR - rur a3, fsr - s32i a3, sp, +XT_STK_FSR - ssi f0, sp, +XT_STK_F0 - ssi f1, sp, +XT_STK_F1 - ssi f2, sp, +XT_STK_F2 - ssi f3, sp, +XT_STK_F3 - ssi f4, sp, +XT_STK_F4 - ssi f5, sp, +XT_STK_F5 - ssi f6, sp, +XT_STK_F6 - ssi f7, sp, +XT_STK_F7 - ssi f8, sp, +XT_STK_F8 - ssi f9, sp, +XT_STK_F9 - ssi f10, sp, +XT_STK_F10 - ssi f11, sp, +XT_STK_F11 - ssi f12, sp, +XT_STK_F12 - ssi f13, sp, +XT_STK_F13 - ssi f14, sp, +XT_STK_F14 - ssi f15, sp, +XT_STK_F15 - ", - #[cfg(XCHAL_HAVE_WINDOWED)] - " - s32i a0, sp, +XT_STK_TMP // keep return address on the stack - - // SPILL_REGISTERS macro requires window overflow exceptions to be enabled, - // i.e. PS.EXCM cleared and PS.WOE set. - // Since we are going to clear PS.EXCM, we also need to increase INTLEVEL - // at least to XCHAL_EXCM_LEVEL. This matches that value of effective INTLEVEL - // at entry (CINTLEVEL=max(PS.INTLEVEL, XCHAL_EXCM_LEVEL) when PS.EXCM is set. - // Since WindowOverflow exceptions will trigger inside SPILL_REGISTERS, - // need to save/restore EPC1 as well. - // Note: even though a4-a15 are saved into the exception frame, we should not - // clobber them until after SPILL_REGISTERS. This is because these registers - // may contain live windows belonging to previous frames in the call stack. - // These frames will be spilled by SPILL_REGISTERS, and if the register was - // used as a temporary by this code, the temporary value would get stored - // onto the stack, instead of the real value. - // - - rsr a2, PS // to be restored after SPILL_REGISTERS - movi a0, PS_INTLEVEL_MASK - and a3, a2, a0 // get the current INTLEVEL - bgeui a3, +PS_INTLEVEL_EXCM, 1f // calculate max(INTLEVEL, XCHAL_EXCM_LEVEL) - 3 = XCHAL_EXCM_LEVEL - movi a3, PS_INTLEVEL_EXCM - 1: - movi a0, PS_WOE // clear EXCM, enable window overflow, set new INTLEVEL - or a3, a3, a0 - wsr a3, ps - rsr a0, EPC1 - - addmi sp, sp, +XT_STK_FRMSZ // go back to spill register region - SPILL_REGISTERS - addmi sp, sp, -XT_STK_FRMSZ // return the current stack pointer - - wsr a2, PS // restore to the value at entry - rsync - wsr a0, EPC1 - - l32i a0, sp, +XT_STK_TMP - ", - " - ret - ", - }, - options(noreturn) - ); -} - -global_asm!( - r#" // Spills all active windowed registers (i.e. registers not visible as // A0-A15) to their ABI-defined spill regions on the stack. // It will spill registers to their reserved locations in previous frames. @@ -314,11 +133,7 @@ global_asm!( and a12, a12, a12 rotw 4 .endm - "# -); -global_asm!( - r#" .macro SAVE_CONTEXT level:req mov a0, a1 // save a1/sp addmi sp, sp, -XT_STK_FRMSZ // only allow multiple of 256 @@ -326,7 +141,7 @@ global_asm!( s32i a0, sp, +XT_STK_A1 // save interruptee's A1/SP s32e a0, sp, -12 // for debug backtrace - .ifc \level,1 + .ifc \\level,1 rsr a0, PS s32i a0, sp, +XT_STK_PS // save interruptee's PS @@ -335,156 +150,36 @@ global_asm!( rsr a0, EXCVADDR s32i a0, sp, +XT_STK_EXCVADDR .else - rsr a0, EPS\level + rsr a0, EPS\\level s32i a0, sp, +XT_STK_PS // save interruptee's PS .endif - rsr a0, EPC\level + rsr a0, EPC\\level s32i a0, sp, +XT_STK_PC // save interruptee's PC s32e a0, sp, -16 // for debug backtrace - rsr a0, EXCSAVE\level + rsr a0, EXCSAVE\\level s32i a0, sp, +XT_STK_A0 // save interruptee's A0 call0 save_context .endm - "# -); - -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn restore_context() { - cfg_asm!( - { - " - l32i a3, sp, +XT_STK_SAR - wsr a3, SAR - ", - #[cfg(XCHAL_HAVE_LOOPS)] - " - // Loop Option - l32i a3, sp, +XT_STK_LBEG - wsr a3, LBEG - l32i a3, sp, +XT_STK_LEND - wsr a3, LEND - l32i a3, sp, +XT_STK_LCOUNT - wsr a3, LCOUNT - ", - #[cfg(XCHAL_HAVE_THREADPTR)] - " - // Thread Pointer Option - l32i a3, sp, +XT_STK_THREADPTR - wur a3, threadptr - ", - #[cfg(XCHAL_HAVE_S32C1I)] - " - // Conditional Store Option - l32i a3, sp, +XT_STK_SCOMPARE1 - wsr a3, scompare1 - ", - #[cfg(XCHAL_HAVE_BOOLEANS)] - " - // Boolean Option - l32i a3, sp, +XT_STK_BR - wsr a3, br - ", - #[cfg(XCHAL_HAVE_MAC16)] - " - // MAC16 Option - l32i a3, sp, +XT_STK_ACCLO - wsr a3, acclo - l32i a3, sp, +XT_STK_ACCHI - wsr a3, acchi - l32i a3, sp, +XT_STK_M0 - wsr a3, m0 - l32i a3, sp, +XT_STK_M1 - wsr a3, m1 - l32i a3, sp, +XT_STK_M2 - wsr a3, m2 - l32i a3, sp, +XT_STK_M3 - wsr a3, m3 - ", - #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_DFP_ACCEL))] - " - // Double Precision Accelerator Option - l32i a3, sp, +XT_STK_F64R_LO_CPENABLE - wur a3, f64r_lo - l32i a3, sp, +XT_STK_F64R_HI - wur a3, f64r_hi - l32i a3, sp, +XT_STK_F64S - wur a3, f64s - ", - #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_FP))] - " - // Coprocessor Option - l32i a3, sp, +XT_STK_FCR - wur a3, fcr - l32i a3, sp, +XT_STK_FSR - wur a3, fsr - lsi f0, sp, +XT_STK_F0 - lsi f1, sp, +XT_STK_F1 - lsi f2, sp, +XT_STK_F2 - lsi f3, sp, +XT_STK_F3 - lsi f4, sp, +XT_STK_F4 - lsi f5, sp, +XT_STK_F5 - lsi f6, sp, +XT_STK_F6 - lsi f7, sp, +XT_STK_F7 - lsi f8, sp, +XT_STK_F8 - lsi f9, sp, +XT_STK_F9 - lsi f10, sp, +XT_STK_F10 - lsi f11, sp, +XT_STK_F11 - lsi f12, sp, +XT_STK_F12 - lsi f13, sp, +XT_STK_F13 - lsi f14, sp, +XT_STK_F14 - lsi f15, sp, +XT_STK_F15 - ", - #[cfg(all(XCHAL_HAVE_CP, not(feature = "float-save-restore")))] - " - /* Restore coprocessor state after ISR */ - l32i a3, sp, +XT_STK_F64R_LO_CPENABLE - wsr a3, CPENABLE - rsync - ", - " - // general registers - l32i a2, sp, +XT_STK_A2 - l32i a3, sp, +XT_STK_A3 - l32i a4, sp, +XT_STK_A4 - l32i a5, sp, +XT_STK_A5 - l32i a6, sp, +XT_STK_A6 - l32i a7, sp, +XT_STK_A7 - l32i a8, sp, +XT_STK_A8 - l32i a9, sp, +XT_STK_A9 - l32i a10, sp, +XT_STK_A10 - l32i a11, sp, +XT_STK_A11 - l32i a12, sp, +XT_STK_A12 - l32i a13, sp, +XT_STK_A13 - l32i a14, sp, +XT_STK_A14 - l32i a15, sp, +XT_STK_A15 - ret - ", - }, options(noreturn)); -} -global_asm!( - r#" .macro RESTORE_CONTEXT level:req // Restore context and return call0 restore_context - .ifc \level,1 + .ifc \\level,1 l32i a0, sp, +XT_STK_PS // retrieve interruptee's PS wsr a0, PS l32i a0, sp, +XT_STK_PC // retrieve interruptee's PC - wsr a0, EPC\level + wsr a0, EPC\\level .else l32i a0, sp, +XT_STK_PS // retrieve interruptee's PS - wsr a0, EPS\level + wsr a0, EPS\\level l32i a0, sp, +XT_STK_PC // retrieve interruptee's PC - wsr a0, EPC\level + wsr a0, EPC\\level .endif l32i a0, sp, +XT_STK_A0 // retrieve interruptee's A0 @@ -492,199 +187,723 @@ global_asm!( rsync // ensure PS and EPC written .endm - "# -); -/// Handle Other Exceptions or Level 1 interrupt by storing full context and -/// then calling regular function -/// -/// # Input: -/// * A0 stored in EXCSAVE1 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_exception() { - asm!( - " - SAVE_CONTEXT 1 - - movi a0, (PS_INTLEVEL_EXCM | PS_WOE) - wsr a0, PS - rsync + .macro HANDLE_INTERRUPT_LEVEL level + SAVE_CONTEXT \\level - l32i a6, sp, +XT_STK_EXCCAUSE // put cause in a6 = a2 in callee - beqi a6, 4, .Level1Interrupt + movi a0, (\\level | PS_WOE) + wsr a0, PS + rsync - mov a7, sp // put address of save frame in a7=a3 in callee - call4 __exception // call handler <= actual call! + movi a6, \\level // put interrupt level in a6 = a2 in callee + mov a7, sp // put address of save frame in a7=a3 in callee + call4 __level_\\level\\()_interrupt // call handler <= actual call! - j .RestoreContext + RESTORE_CONTEXT \\level + rfi \\level - .Level1Interrupt: - movi a0, (1 | PS_WOE) // set PS.INTLEVEL accordingly - wsr a0, PS - rsync + .endm + " +); + +cfg_global_asm!( + " + // Save processor state to stack. + // + // *Must only be called with call0.* + // *For spill all window registers to work WOE must be enabled on entry + // + // Saves all registers except PC, PS, A0, A1 + // + // Inputs: + // A0 is the return address + // A1 is the stack pointers + // Exceptions are disabled (PS.EXCM = 1) + // + // Output: + // A0 is the return address + // A1 is the stack pointer + // A3, A9 are used as scratch registers + // EPC1 is changed + .section .rwtext,\"ax\",@progbits + .global save_context + .p2align 2 + .type save_context,@function +save_context: +.Lsave_context_start: + s32i a2, sp, +XT_STK_A2 + s32i a3, sp, +XT_STK_A3 + s32i a4, sp, +XT_STK_A4 + s32i a5, sp, +XT_STK_A5 + s32i a6, sp, +XT_STK_A6 + s32i a7, sp, +XT_STK_A7 + s32i a8, sp, +XT_STK_A8 + s32i a9, sp, +XT_STK_A9 + s32i a10, sp, +XT_STK_A10 + s32i a11, sp, +XT_STK_A11 + s32i a12, sp, +XT_STK_A12 + s32i a13, sp, +XT_STK_A13 + s32i a14, sp, +XT_STK_A14 + s32i a15, sp, +XT_STK_A15 + + rsr a3, SAR + s32i a3, sp, +XT_STK_SAR + ", + #[cfg(all(XCHAL_HAVE_CP, not(feature = "float-save-restore")))] + " + /* Disable coprocessor, any use of floats in ISRs will cause an exception unless float-save-restore feature is enabled */ + rsr a3, CPENABLE + s32i a3, sp, +XT_STK_F64R_LO_CPENABLE + movi a3, 0 + wsr a3, CPENABLE + rsync + ", + #[cfg(XCHAL_HAVE_LOOPS)] + " + // Loop Option + rsr a3, LBEG + s32i a3, sp, +XT_STK_LBEG + rsr a3, LEND + s32i a3, sp, +XT_STK_LEND + rsr a3, LCOUNT + s32i a3, sp, +XT_STK_LCOUNT + ", + #[cfg(XCHAL_HAVE_THREADPTR)] + " + // Thread Pointer Option + rur a3, threadptr + s32i a3, sp, +XT_STK_THREADPTR + ", + #[cfg(XCHAL_HAVE_S32C1I)] + " + // Conditional Store Option + rsr a3, scompare1 + s32i a3, sp, +XT_STK_SCOMPARE1 + ", + #[cfg(XCHAL_HAVE_BOOLEANS)] + " + // Boolean Option + rsr a3, br + s32i a3, sp, +XT_STK_BR + ", + #[cfg(XCHAL_HAVE_MAC16)] + " + // MAC16 Option + rsr a3, acclo + s32i a3, sp, +XT_STK_ACCLO + rsr a3, acchi + s32i a3, sp, +XT_STK_ACCHI + rsr a3, m0 + s32i a3, sp, +XT_STK_M0 + rsr a3, m1 + s32i a3, sp, +XT_STK_M1 + rsr a3, m2 + s32i a3, sp, +XT_STK_M2 + rsr a3, m3 + s32i a3, sp, +XT_STK_M3 + ", + #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_DFP_ACCEL))] + " + // Double Precision Accelerator Option + rur a3, f64r_lo + s32i a3, sp, +XT_STK_F64R_LO_CPENABLE + rur a3, f64r_hi + s32i a3, sp, +XT_STK_F64R_HI + rur a3, f64s + s32i a3, sp, +XT_STK_F64S + ", + #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_FP))] + " + // Coprocessor Option + rur a3, fcr + s32i a3, sp, +XT_STK_FCR + rur a3, fsr + s32i a3, sp, +XT_STK_FSR + ssi f0, sp, +XT_STK_F0 + ssi f1, sp, +XT_STK_F1 + ssi f2, sp, +XT_STK_F2 + ssi f3, sp, +XT_STK_F3 + ssi f4, sp, +XT_STK_F4 + ssi f5, sp, +XT_STK_F5 + ssi f6, sp, +XT_STK_F6 + ssi f7, sp, +XT_STK_F7 + ssi f8, sp, +XT_STK_F8 + ssi f9, sp, +XT_STK_F9 + ssi f10, sp, +XT_STK_F10 + ssi f11, sp, +XT_STK_F11 + ssi f12, sp, +XT_STK_F12 + ssi f13, sp, +XT_STK_F13 + ssi f14, sp, +XT_STK_F14 + ssi f15, sp, +XT_STK_F15 + ", + #[cfg(XCHAL_HAVE_WINDOWED)] + " + s32i a0, sp, +XT_STK_TMP // keep return address on the stack + + // SPILL_REGISTERS macro requires window overflow exceptions to be enabled, + // i.e. PS.EXCM cleared and PS.WOE set. + // Since we are going to clear PS.EXCM, we also need to increase INTLEVEL + // at least to XCHAL_EXCM_LEVEL. This matches that value of effective INTLEVEL + // at entry (CINTLEVEL=max(PS.INTLEVEL, XCHAL_EXCM_LEVEL) when PS.EXCM is set. + // Since WindowOverflow exceptions will trigger inside SPILL_REGISTERS, + // need to save/restore EPC1 as well. + // Note: even though a4-a15 are saved into the exception frame, we should not + // clobber them until after SPILL_REGISTERS. This is because these registers + // may contain live windows belonging to previous frames in the call stack. + // These frames will be spilled by SPILL_REGISTERS, and if the register was + // used as a temporary by this code, the temporary value would get stored + // onto the stack, instead of the real value. + // - movi a6, 1 // put interrupt level in a6 = a2 in callee - mov a7, sp // put address of save frame in a7=a3 in callee - call4 __level_1_interrupt // call handler <= actual call! - - .RestoreContext: - RESTORE_CONTEXT 1 - - rfe // PS.EXCM is cleared - ", - options(noreturn) - ) -} - -/// Handle Double Exceptions by storing full context and then calling regular -/// function Double exceptions are not a normal occurrence. They indicate a bug -/// of some kind. -/// -/// # Input: -/// * A0 stored in EXCSAVE1 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_double_exception() { - asm!( - " - mov a0, a1 // save a1/sp - addmi sp, sp, -XT_STK_FRMSZ // only allow multiple of 256 - - s32i a0, sp, +XT_STK_A1 // save interruptee's A1/SP - s32e a0, sp, -12 // for debug backtrace - - rsr a0, PS - s32i a0, sp, +XT_STK_PS // save interruptee's PS - - rsr a0, EXCCAUSE - s32i a0, sp, +XT_STK_EXCCAUSE - rsr a0, EXCVADDR - s32i a0, sp, +XT_STK_EXCVADDR - - rsr a0, DEPC - s32i a0, sp, +XT_STK_PC // save interruptee's PC - s32e a0, sp, -16 // for debug backtrace - - rsr a0, EXCSAVE7 // ok to reuse EXCSAVE7 for double exception as long as - // double exception is not in first couple of instructions - // of level 7 handler - s32i a0, sp, +XT_STK_A0 // save interruptee's A0 - - call0 save_context - - l32i a6, sp, +XT_STK_EXCCAUSE // put cause in a6 = a2 in callee - mov a7, sp // put address of save frame in a7=a3 in callee - call4 __exception // call handler <= actual call! - - // Restore context and return - call0 restore_context - - l32i a0, sp, +XT_STK_PS // retrieve interruptee's PS - wsr a0, PS - l32i a0, sp, +XT_STK_PC // retrieve interruptee's PC - wsr a0, EPC1 - - l32i a0, sp, +XT_STK_A0 // retrieve interruptee's A0 - l32i sp, sp, +XT_STK_A1 // remove exception frame - rsync // ensure PS and EPC written - - rfde - ", - options(noreturn) - ) -} + rsr a2, PS // to be restored after SPILL_REGISTERS + movi a0, PS_INTLEVEL_MASK + and a3, a2, a0 // get the current INTLEVEL + bgeui a3, +PS_INTLEVEL_EXCM, 1f // calculate max(INTLEVEL, XCHAL_EXCM_LEVEL) - 3 = XCHAL_EXCM_LEVEL + movi a3, PS_INTLEVEL_EXCM + 1: + movi a0, PS_WOE // clear EXCM, enable window overflow, set new INTLEVEL + or a3, a3, a0 + wsr a3, ps + rsr a0, EPC1 + + addmi sp, sp, +XT_STK_FRMSZ // go back to spill register region + SPILL_REGISTERS + addmi sp, sp, -XT_STK_FRMSZ // return the current stack pointer + + wsr a2, PS // restore to the value at entry + rsync + wsr a0, EPC1 + + l32i a0, sp, +XT_STK_TMP + ", + " + ret +.Lsave_context_end: + .size .Lsave_context_start, .Lsave_context_end + + .section .rwtext,\"ax\",@progbits + .global restore_context + .p2align 2 + .type restore_context,@function +restore_context: +.Lrestore_context_start: + l32i a3, sp, +XT_STK_SAR + wsr a3, SAR + ", + #[cfg(XCHAL_HAVE_LOOPS)] + " + // Loop Option + l32i a3, sp, +XT_STK_LBEG + wsr a3, LBEG + l32i a3, sp, +XT_STK_LEND + wsr a3, LEND + l32i a3, sp, +XT_STK_LCOUNT + wsr a3, LCOUNT + ", + #[cfg(XCHAL_HAVE_THREADPTR)] + " + // Thread Pointer Option + l32i a3, sp, +XT_STK_THREADPTR + wur a3, threadptr + ", + #[cfg(XCHAL_HAVE_S32C1I)] + " + // Conditional Store Option + l32i a3, sp, +XT_STK_SCOMPARE1 + wsr a3, scompare1 + ", + #[cfg(XCHAL_HAVE_BOOLEANS)] + " + // Boolean Option + l32i a3, sp, +XT_STK_BR + wsr a3, br + ", + #[cfg(XCHAL_HAVE_MAC16)] + " + // MAC16 Option + l32i a3, sp, +XT_STK_ACCLO + wsr a3, acclo + l32i a3, sp, +XT_STK_ACCHI + wsr a3, acchi + l32i a3, sp, +XT_STK_M0 + wsr a3, m0 + l32i a3, sp, +XT_STK_M1 + wsr a3, m1 + l32i a3, sp, +XT_STK_M2 + wsr a3, m2 + l32i a3, sp, +XT_STK_M3 + wsr a3, m3 + ", + #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_DFP_ACCEL))] + " + // Double Precision Accelerator Option + l32i a3, sp, +XT_STK_F64R_LO_CPENABLE + wur a3, f64r_lo + l32i a3, sp, +XT_STK_F64R_HI + wur a3, f64r_hi + l32i a3, sp, +XT_STK_F64S + wur a3, f64s + ", + #[cfg(all(feature = "float-save-restore", XCHAL_HAVE_FP))] + " + // Coprocessor Option + l32i a3, sp, +XT_STK_FCR + wur a3, fcr + l32i a3, sp, +XT_STK_FSR + wur a3, fsr + lsi f0, sp, +XT_STK_F0 + lsi f1, sp, +XT_STK_F1 + lsi f2, sp, +XT_STK_F2 + lsi f3, sp, +XT_STK_F3 + lsi f4, sp, +XT_STK_F4 + lsi f5, sp, +XT_STK_F5 + lsi f6, sp, +XT_STK_F6 + lsi f7, sp, +XT_STK_F7 + lsi f8, sp, +XT_STK_F8 + lsi f9, sp, +XT_STK_F9 + lsi f10, sp, +XT_STK_F10 + lsi f11, sp, +XT_STK_F11 + lsi f12, sp, +XT_STK_F12 + lsi f13, sp, +XT_STK_F13 + lsi f14, sp, +XT_STK_F14 + lsi f15, sp, +XT_STK_F15 + ", + #[cfg(all(XCHAL_HAVE_CP, not(feature = "float-save-restore")))] + " + /* Restore coprocessor state after ISR */ + l32i a3, sp, +XT_STK_F64R_LO_CPENABLE + wsr a3, CPENABLE + rsync + ", + " + // general registers + l32i a2, sp, +XT_STK_A2 + l32i a3, sp, +XT_STK_A3 + l32i a4, sp, +XT_STK_A4 + l32i a5, sp, +XT_STK_A5 + l32i a6, sp, +XT_STK_A6 + l32i a7, sp, +XT_STK_A7 + l32i a8, sp, +XT_STK_A8 + l32i a9, sp, +XT_STK_A9 + l32i a10, sp, +XT_STK_A10 + l32i a11, sp, +XT_STK_A11 + l32i a12, sp, +XT_STK_A12 + l32i a13, sp, +XT_STK_A13 + l32i a14, sp, +XT_STK_A14 + l32i a15, sp, +XT_STK_A15 + ret +.Lrestore_context_end: + .size .Lrestore_context_start, .Lrestore_context_end + ", +); global_asm!( - r#" - .macro HANDLE_INTERRUPT_LEVEL level - SAVE_CONTEXT \level + " + // Handle Other Exceptions or Level 1 interrupt by storing full context and + // then calling regular function + // + // # Input: + // * A0 stored in EXCSAVE1 + + .section .rwtext,\"ax\",@progbits + .global __default_naked_exception + .p2align 2 + .type __default_naked_exception,@function +__default_naked_exception: +.Ldefault_naked_exception_start: + SAVE_CONTEXT 1 + + movi a0, (PS_INTLEVEL_EXCM | PS_WOE) + wsr a0, PS + rsync + + l32i a6, sp, +XT_STK_EXCCAUSE // put cause in a6 = a2 in callee + beqi a6, 4, .Level1Interrupt + + mov a7, sp // put address of save frame in a7=a3 in callee + call4 __exception // call handler <= actual call! - movi a0, (\level | PS_WOE) + j .RestoreContext + +.Level1Interrupt: + movi a0, (1 | PS_WOE) // set PS.INTLEVEL accordingly wsr a0, PS rsync - movi a6, \level // put interrupt level in a6 = a2 in callee - mov a7, sp // put address of save frame in a7=a3 in callee - call4 __level_\level\()_interrupt // call handler <= actual call! + movi a6, 1 // put interrupt level in a6 = a2 in callee + mov a7, sp // put address of save frame in a7=a3 in callee + call4 __level_1_interrupt // call handler <= actual call! - RESTORE_CONTEXT \level - rfi \level +.RestoreContext: + RESTORE_CONTEXT 1 - .endm -"# + rfe // PS.EXCM is cleared +.Ldefault_naked_exception_end: + .size .Ldefault_naked_exception_start, .Ldefault_naked_exception_end + + // Handle Double Exceptions by storing full context and then calling regular + // function Double exceptions are not a normal occurrence. They indicate a bug + // of some kind. + // + // # Input: + // * A0 stored in EXCSAVE1 + .section .rwtext,\"ax\",@progbits + .global __default_naked_double_exception + .p2align 2 + .type __default_naked_double_exception,@function +__default_naked_double_exception: +.Ldefault_double_naked_exception_start: + mov a0, a1 // save a1/sp + addmi sp, sp, -XT_STK_FRMSZ // only allow multiple of 256 + + s32i a0, sp, +XT_STK_A1 // save interruptee's A1/SP + s32e a0, sp, -12 // for debug backtrace + + rsr a0, PS + s32i a0, sp, +XT_STK_PS // save interruptee's PS + + rsr a0, EXCCAUSE + s32i a0, sp, +XT_STK_EXCCAUSE + rsr a0, EXCVADDR + s32i a0, sp, +XT_STK_EXCVADDR + + rsr a0, DEPC + s32i a0, sp, +XT_STK_PC // save interruptee's PC + s32e a0, sp, -16 // for debug backtrace + + rsr a0, EXCSAVE7 // ok to reuse EXCSAVE7 for double exception as long as + // double exception is not in first couple of instructions + // of level 7 handler + s32i a0, sp, +XT_STK_A0 // save interruptee's A0 + + call0 save_context + + l32i a6, sp, +XT_STK_EXCCAUSE // put cause in a6 = a2 in callee + mov a7, sp // put address of save frame in a7=a3 in callee + call4 __exception // call handler <= actual call! + + // Restore context and return + call0 restore_context + + l32i a0, sp, +XT_STK_PS // retrieve interruptee's PS + wsr a0, PS + l32i a0, sp, +XT_STK_PC // retrieve interruptee's PC + wsr a0, EPC1 + + l32i a0, sp, +XT_STK_A0 // retrieve interruptee's A0 + l32i sp, sp, +XT_STK_A1 // remove exception frame + rsync // ensure PS and EPC written + + rfde +.Ldefault_double_naked_exception_end: + .size .Ldefault_double_naked_exception_start, .Ldefault_double_naked_exception_end + + // Handle Level 2 Interrupt by storing full context and then calling regular + // function + // + // # Input: + // * A0 stored in EXCSAVE2 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_2_interrupt + .p2align 2 + .type __default_naked_level_2_interrupt,@function +__default_naked_level_2_interrupt: +.Ldefault_naked_level_2_interrupt_start: + HANDLE_INTERRUPT_LEVEL 2 +.Ldefault_naked_level_2_interrupt_end: + .size .Ldefault_naked_level_2_interrupt_start, .Ldefault_naked_level_2_interrupt_end + + // Handle Level 3 Interrupt by storing full context and then calling regular + // function + // + // # Input: + // * A0 stored in EXCSAVE3 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_3_interrupt + .p2align 2 + .type __default_naked_level_3_interrupt,@function +__default_naked_level_3_interrupt: +.Ldefault_naked_level_3_interrupt_start: + HANDLE_INTERRUPT_LEVEL 3 +.Ldefault_naked_level_3_interrupt_end: + .size .Ldefault_naked_level_3_interrupt_start, .Ldefault_naked_level_3_interrupt_end + + // Handle Level 4 Interrupt by storing full context and then calling regular + // function + // + // # Input: + // * A0 stored in EXCSAVE4 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_4_interrupt + .p2align 2 + .type __default_naked_level_4_interrupt,@function +__default_naked_level_4_interrupt: +.Ldefault_naked_level_4_interrupt_start: + HANDLE_INTERRUPT_LEVEL 4 +.Ldefault_naked_level_4_interrupt_end: + .size .Ldefault_naked_level_4_interrupt_start, .Ldefault_naked_level_4_interrupt_end + + // Handle Level 5 Interrupt by storing full context and then calling regular + // function + // + // # Input: + // * A0 stored in EXCSAVE5 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_5_interrupt + .p2align 2 + .type __default_naked_level_5_interrupt,@function +__default_naked_level_5_interrupt: +.Ldefault_naked_level_5_interrupt_start: + HANDLE_INTERRUPT_LEVEL 5 +.Ldefault_naked_level_5_interrupt_end: + .size .Ldefault_naked_level_5_interrupt_start, .Ldefault_naked_level_5_interrupt_end + + // Handle Level 6 (=Debug) Interrupt by storing full context and then calling + // regular function + // + // # Input: + // * A0 stored in EXCSAVE6 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_6_interrupt + .p2align 2 + .type __default_naked_level_6_interrupt,@function +__default_naked_level_6_interrupt: +.Ldefault_naked_level_6_interrupt_start: + HANDLE_INTERRUPT_LEVEL 6 +.Ldefault_naked_level_6_interrupt_end: + .size .Ldefault_naked_level_6_interrupt_start, .Ldefault_naked_level_6_interrupt_end + + // Handle Level 7 (=NMI) Interrupt by storing full context and then calling + // regular function + // + // # Input: + // * A0 stored in EXCSAVE7 + .section .rwtext,\"ax\",@progbits + .global __default_naked_level_7_interrupt + .p2align 2 + .type __default_naked_level_7_interrupt,@function +__default_naked_level_7_interrupt: +.Ldefault_naked_level_7_interrupt_start: + HANDLE_INTERRUPT_LEVEL 7 +.Ldefault_naked_level_7_interrupt_end: + .size .Ldefault_naked_level_7_interrupt_start, .Ldefault_naked_level_7_interrupt_end +" ); -/// Handle Level 2 Interrupt by storing full context and then calling regular -/// function -/// -/// # Input: -/// * A0 stored in EXCSAVE2 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_2_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 2", options(noreturn)); -} - -/// Handle Level 3 Interrupt by storing full context and then calling regular -/// function -/// -/// # Input: -/// * A0 stored in EXCSAVE3 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_3_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 3", options(noreturn)); -} - -/// Handle Level 4 Interrupt by storing full context and then calling regular -/// function -/// -/// # Input: -/// * A0 stored in EXCSAVE4 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_4_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 4", options(noreturn)); -} - -/// Handle Level 5 Interrupt by storing full context and then calling regular -/// function -/// -/// # Input: -/// * A0 stored in EXCSAVE5 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_5_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 5", options(noreturn)); -} - -/// Handle Level 6 (=Debug) Interrupt by storing full context and then calling -/// regular function -/// -/// # Input: -/// * A0 stored in EXCSAVE6 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_6_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 6", options(noreturn)); -} - -/// Handle Level 7 (=NMI) Interrupt by storing full context and then calling -/// regular function -/// -/// # Input: -/// * A0 stored in EXCSAVE7 -#[naked] -#[no_mangle] -#[link_section = ".rwtext"] -unsafe extern "C" fn __default_naked_level_7_interrupt() { - asm!("HANDLE_INTERRUPT_LEVEL 7", options(noreturn)); -} +// Raw vector handlers +// +// The interrupt handlers all use special return instructions. +// rust still generates a ret.w instruction, which will never be reached. +// generation of the ret.w can be prevented by using +// core::intrinsics::unreachable, but then a break 15,1 will be generated (which +// takes 3 bytes instead of 2) or a 'loop {}', but then a jump to own address +// will be generated which is also 3 bytes. No way found yet to prevent this +// generation altogether. +global_asm!( + " + .section .WindowOverflow8.text,\"ax\",@progbits + .global _WindowOverflow8 + .p2align 2 + .type _WindowOverflow8,@function +_WindowOverflow8: + s32e a0, a9, -16 + l32e a0, a1, -12 + + s32e a1, a9, -12 + s32e a2, a9, -8 + s32e a3, a9, -4 + s32e a4, a0, -32 + s32e a5, a0, -28 + s32e a6, a0, -24 + s32e a7, a0, -20 + rfwo + + .section .WindowUnderflow8.text,\"ax\",@progbits + .global _WindowUnderflow8 + .p2align 2 + .type _WindowUnderflow8,@function +_WindowUnderflow8: + l32e a0, a9, -16 + l32e a1, a9, -12 + l32e a2, a9, -8 + l32e a7, a1, -12 + + l32e a3, a9, -4 + l32e a4, a7, -32 + l32e a5, a7, -28 + l32e a6, a7, -24 + l32e a7, a7, -20 + rfwu + + .section .WindowOverflow12.text,\"ax\",@progbits + .global _WindowOverflow12 + .p2align 2 + .type _WindowOverflow12,@function +_WindowOverflow12: + s32e a0, a13, -16 + l32e a0, a1, -12 + + s32e a1, a13, -12 + s32e a2, a13, -8 + s32e a3, a13, -4 + s32e a4, a0, -48 + s32e a5, a0, -44 + s32e a6, a0, -40 + s32e a7, a0, -36 + s32e a8, a0, -32 + s32e a9, a0, -28 + s32e a10, a0, -24 + s32e a11, a0, -20 + rfwo + + .section .WindowUnderflow12.text,\"ax\",@progbits + .global _WindowUnderflow12 + .p2align 2 + .type _WindowUnderflow12,@function +_WindowUnderflow12: + l32e a0, a13, -16 + l32e a1, a13, -12 + l32e a2, a13, -8 + l32e a11, a1, -12 + + l32e a3, a13, -4 + l32e a4, a11, -48 + l32e a5, a11, -44 + l32e a6, a11, -40 + l32e a7, a11, -36 + l32e a8, a11, -32 + l32e a9, a11, -28 + l32e a10, a11, -24 + l32e a11, a11, -20 + rfwu + + .section .WindowOverflow4.text,\"ax\",@progbits + .global _WindowOverflow4 + .p2align 2 + .type _WindowOverflow4,@function +_WindowOverflow4: + s32e a0, a5, -16 + s32e a1, a5, -12 + s32e a2, a5, -8 + s32e a3, a5, -4 + rfwo + + .section .WindowUnderflow4.text,\"ax\",@progbits + .global _WindowUnderflow4 + .p2align 2 + .type _WindowUnderflow4,@function +_WindowUnderflow4: + l32e a0, a5, -16 + l32e a1, a5, -12 + l32e a2, a5, -8 + l32e a3, a5, -4 + rfwu + + // inline the _AllocAException saves on the ret.w for WindowUnderflow4 + // this makes that it just fits, which is needed for the bbci instructions + + .align 4 + _AllocAException: + rsr a0, WINDOWBASE // grab WINDOWBASE before rotw changes it + rotw -1 // WINDOWBASE goes to a4, new a0-a3 are scratch + rsr a2, PS + extui a3, a2, 8, 4 // XCHAL_PS_OWB_SHIFT, XCHAL_PS_OWB_BITS + xor a3, a3, a4 // bits changed from old to current windowbase + rsr a4, EXCSAVE1 // restore original a0 (now in a4) + slli a3, a3, 8 // XCHAL_PS_OWB_SHIFT + xor a2, a2, a3 // flip changed bits in old window base + wsr a2, PS // update PS.OWB to new window base + rsync + + bbci a4, 31, _WindowUnderflow4 + rotw -1 // original a0 goes to a8 + bbci a8, 30, _WindowUnderflow8 + rotw -1 + j _WindowUnderflow12 + + .section .KernelExceptionVector.text,\"ax\",@progbits + .global _KernelExceptionVector + .p2align 2 + .type _KernelExceptionVector,@function +_KernelExceptionVector: + wsr a0, EXCSAVE1 // preserve a0 + rsr a0, EXCCAUSE // get exception cause + + beqi a0, 5, .AllocAException + + call0 __naked_kernel_exception + + .section .UserExceptionVector.text,\"ax\",@progbits + .global _UserExceptionVector + .p2align 2 + .type _UserExceptionVector,@function +_UserExceptionVector: + wsr a0, EXCSAVE1 // preserve a0 + rsr a0, EXCCAUSE // get exception cause + + beqi a0, 5, .AllocAException + + call0 __naked_user_exception + +.AllocAException: + call0 _AllocAException + + .section .DoubleExceptionVector.text,\"ax\",@progbits + .global _DoubleExceptionVector + .p2align 2 + .type _DoubleExceptionVector,@function +_DoubleExceptionVector: + wsr a0, EXCSAVE1 // preserve a0 (EXCSAVE1 can be reused as long as there + // is no double exception in the first exception until + // EXCSAVE1 is stored to the stack.) + call0 __naked_double_exception // used as long jump + + .section .Level2InterruptVector.text,\"ax\",@progbits + .global _Level2InterruptVector + .p2align 2 + .type _Level2InterruptVector,@function +_Level2InterruptVector: + wsr a0, EXCSAVE2 // preserve a0 + call0 __naked_level_2_interrupt // used as long jump + + .section .Level3InterruptVector.text,\"ax\",@progbits + .global _Level3InterruptVector + .p2align 2 + .type _Level3InterruptVector,@function +_Level3InterruptVector: + wsr a0, EXCSAVE3 // preserve a0 + call0 __naked_level_3_interrupt // used as long jump + + .section .Level4InterruptVector.text,\"ax\",@progbits + .global _Level4InterruptVector + .p2align 2 + .type _Level4InterruptVector,@function +_Level4InterruptVector: + wsr a0, EXCSAVE4 // preserve a0 + call0 __naked_level_4_interrupt // used as long jump + + .section .Level5InterruptVector.text,\"ax\",@progbits + .global _Level5InterruptVector + .p2align 2 + .type _Level5InterruptVector,@function +_Level5InterruptVector: + wsr a0, EXCSAVE5 // preserve a0 + call0 __naked_level_5_interrupt // used as long jump + + .section .DebugExceptionVector.text,\"ax\",@progbits + .global _Level6InterruptVector + .p2align 2 + .type _Level6InterruptVector,@function +_Level6InterruptVector: + wsr a0, EXCSAVE6 // preserve a0 + call0 __naked_level_6_interrupt // used as long jump + + .section .NMIExceptionVector.text,\"ax\",@progbits + .global _Level7InterruptVector + .p2align 2 + .type _Level7InterruptVector,@function +_Level7InterruptVector: + wsr a0, EXCSAVE7 // preserve a0 + call0 __naked_level_7_interrupt // used as long jump + " +); diff --git a/xtensa-lx-rt/src/exception/context.rs b/xtensa-lx-rt/src/exception/context.rs index 2e7e96925a0..b5a0b279733 100644 --- a/xtensa-lx-rt/src/exception/context.rs +++ b/xtensa-lx-rt/src/exception/context.rs @@ -1,5 +1,3 @@ -use core::arch::asm; - use super::ExceptionCause; /// State of the CPU saved when entering exception or interrupt @@ -161,293 +159,3 @@ extern "C" fn __default_interrupt(level: u32, save_frame: &Context) { extern "C" fn __default_double_exception(cause: ExceptionCause, save_frame: &Context) { panic!("Double Exception: {:?}, {:08x?}", cause, save_frame) } - -// Raw vector handlers -// -// The interrupt handlers all use special return instructions. -// rust still generates a ret.w instruction, which will never be reached. -// generation of the ret.w can be prevented by using -// core::intrinsics::unreachable, but then a break 15,1 will be generated (which -// takes 3 bytes instead of 2) or a 'loop {}', but then a jump to own address -// will be generated which is also 3 bytes. No way found yet to prevent this -// generation altogether. - -#[naked] -#[no_mangle] -#[link_section = ".KernelExceptionVector.text"] -unsafe extern "C" fn _KernelExceptionVector() { - asm!( - " - wsr a0, EXCSAVE1 // preserve a0 - rsr a0, EXCCAUSE // get exception cause - - beqi a0, 5, .AllocAException - - call0 __naked_kernel_exception - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".UserExceptionVector.text"] -unsafe extern "C" fn _UserExceptionVector() { - asm!( - " - wsr a0, EXCSAVE1 // preserve a0 - rsr a0, EXCCAUSE // get exception cause - - beqi a0, 5, .AllocAException - - call0 __naked_user_exception - - .AllocAException: - call0 _AllocAException - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".DoubleExceptionVector.text"] -unsafe extern "C" fn _DoubleExceptionVector() { - asm!( - " - wsr a0, EXCSAVE1 // preserve a0 (EXCSAVE1 can be reused as long as there - // is no double exception in the first exception until - // EXCSAVE1 is stored to the stack.) - call0 __naked_double_exception // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".Level2InterruptVector.text"] -unsafe extern "C" fn _Level2InterruptVector() { - asm!( - " - wsr a0, EXCSAVE2 // preserve a0 - call0 __naked_level_2_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".Level3InterruptVector.text"] -unsafe extern "C" fn _Level3InterruptVector() { - asm!( - " - wsr a0, EXCSAVE3 // preserve a0 - call0 __naked_level_3_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".Level4InterruptVector.text"] -unsafe extern "C" fn _Level4InterruptVector() { - asm!( - " - wsr a0, EXCSAVE4 // preserve a0 - call0 __naked_level_4_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".Level5InterruptVector.text"] -unsafe extern "C" fn _Level5InterruptVector() { - asm!( - " - wsr a0, EXCSAVE5 // preserve a0 - call0 __naked_level_5_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".DebugExceptionVector.text"] -unsafe extern "C" fn _Level6InterruptVector() { - asm!( - " - wsr a0, EXCSAVE6 // preserve a0 - call0 __naked_level_6_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".NMIExceptionVector.text"] -unsafe extern "C" fn _Level7InterruptVector() { - asm!( - " - wsr a0, EXCSAVE7 // preserve a0 - call0 __naked_level_7_interrupt // used as long jump - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowOverflow4.text"] -unsafe extern "C" fn _WindowOverflow4() { - asm!( - " - s32e a0, a5, -16 - s32e a1, a5, -12 - s32e a2, a5, -8 - s32e a3, a5, -4 - rfwo - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowUnderflow4.text"] -unsafe extern "C" fn _WindowUnderflow4() { - asm!( - " - l32e a0, a5, -16 - l32e a1, a5, -12 - l32e a2, a5, -8 - l32e a3, a5, -4 - rfwu - - // inline the _AllocAException saves on the ret.w for WindowUnderflow4 - // this makes that it just fits, which is needed for the bbci instructions - - .align 4 - _AllocAException: - rsr a0, WINDOWBASE // grab WINDOWBASE before rotw changes it - rotw -1 // WINDOWBASE goes to a4, new a0-a3 are scratch - rsr a2, PS - extui a3, a2, 8, 4 // XCHAL_PS_OWB_SHIFT, XCHAL_PS_OWB_BITS - xor a3, a3, a4 // bits changed from old to current windowbase - rsr a4, EXCSAVE1 // restore original a0 (now in a4) - slli a3, a3, 8 // XCHAL_PS_OWB_SHIFT - xor a2, a2, a3 // flip changed bits in old window base - wsr a2, PS // update PS.OWB to new window base - rsync - - bbci a4, 31, _WindowUnderflow4 - rotw -1 // original a0 goes to a8 - bbci a8, 30, _WindowUnderflow8 - rotw -1 - j _WindowUnderflow12 - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowOverflow8.text"] -unsafe extern "C" fn _WindowOverflow8() { - asm!( - " - s32e a0, a9, -16 - l32e a0, a1, -12 - - s32e a1, a9, -12 - s32e a2, a9, -8 - s32e a3, a9, -4 - s32e a4, a0, -32 - s32e a5, a0, -28 - s32e a6, a0, -24 - s32e a7, a0, -20 - rfwo - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowUnderflow8.text"] -unsafe extern "C" fn _WindowUnderflow8() { - asm!( - " - l32e a0, a9, -16 - l32e a1, a9, -12 - l32e a2, a9, -8 - l32e a7, a1, -12 - - l32e a3, a9, -4 - l32e a4, a7, -32 - l32e a5, a7, -28 - l32e a6, a7, -24 - l32e a7, a7, -20 - rfwu - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowOverflow12.text"] -unsafe extern "C" fn _WindowOverflow12() { - asm!( - " - s32e a0, a13, -16 - l32e a0, a1, -12 - - s32e a1, a13, -12 - s32e a2, a13, -8 - s32e a3, a13, -4 - s32e a4, a0, -48 - s32e a5, a0, -44 - s32e a6, a0, -40 - s32e a7, a0, -36 - s32e a8, a0, -32 - s32e a9, a0, -28 - s32e a10, a0, -24 - s32e a11, a0, -20 - rfwo - ", - options(noreturn) - ); -} - -#[naked] -#[no_mangle] -#[link_section = ".WindowUnderflow12.text"] -unsafe extern "C" fn _WindowUnderflow12() { - asm!( - " - l32e a0, a13, -16 - l32e a1, a13, -12 - l32e a2, a13, -8 - l32e a11, a1, -12 - - l32e a3, a13, -4 - l32e a4, a11, -48 - l32e a5, a11, -44 - l32e a6, a11, -40 - l32e a7, a11, -36 - l32e a8, a11, -32 - l32e a9, a11, -28 - l32e a10, a11, -24 - l32e a11, a11, -20 - rfwu - ", - options(noreturn) - ); -} diff --git a/xtensa-lx-rt/src/lib.rs b/xtensa-lx-rt/src/lib.rs index a3ee0e054a1..0f4e183f211 100644 --- a/xtensa-lx-rt/src/lib.rs +++ b/xtensa-lx-rt/src/lib.rs @@ -170,3 +170,23 @@ macro_rules! cfg_asm { cfg_asm!(@inner, [], [$($opts)*], $($asms)*) }; } + +#[doc(hidden)] +#[macro_export] +macro_rules! cfg_global_asm { + {@inner, [$($x:tt)*], } => { + global_asm!{$($x)*} + }; + (@inner, [$($x:tt)*], #[cfg($meta:meta)] $asm:literal, $($rest:tt)*) => { + #[cfg($meta)] + cfg_global_asm!{@inner, [$($x)* $asm,], $($rest)*} + #[cfg(not($meta))] + cfg_global_asm!{@inner, [$($x)*], $($rest)*} + }; + {@inner, [$($x:tt)*], $asm:literal, $($rest:tt)*} => { + cfg_global_asm!{@inner, [$($x)* $asm,], $($rest)*} + }; + {$($asms:tt)*} => { + cfg_global_asm!{@inner, [], $($asms)*} + }; +}