embassy-rs / nrf-softdevice

Apache License 2.0
256 stars 76 forks source link

Error: The core is in locked up status as a result of an unrecoverable exception #261

Closed Gibbz closed 1 hour ago

Gibbz commented 2 weeks ago

Ive been trying to get the softdevice working. Now that I got past the priority issues, i'm having a new error. It flashes and builds fine. But when running it crashes.

ERROR probe_rs::architecture::arm::core::armv7m: The core is in locked up status as a result of an unrecoverable exception

It occurs on the line:

let sd = Softdevice::enable(&config); // <- this causes locked up crash!

My bluetooth modified example:

use defmt::{*};
use embassy_executor::Spawner;
use nrf_softdevice::ble::advertisement_builder::{Flag, LegacyAdvertisementBuilder, LegacyAdvertisementPayload, ServiceList, ServiceUuid16};
use nrf_softdevice::ble::peripheral;
use nrf_softdevice::{raw, Softdevice};
use core::mem;

const TASK_ID: &str = "BLUETOOTH";

#[embassy_executor::task]
pub async fn bluetooth (
    spawner: Spawner
) {
    info!("{}: start", TASK_ID);

    // softdevice config
    let config = nrf_softdevice::Config {
        clock: Some(raw::nrf_clock_lf_cfg_t {
            source: raw::NRF_CLOCK_LF_SRC_RC as u8,
            rc_ctiv: 16,
            rc_temp_ctiv: 2,
            accuracy: raw::NRF_CLOCK_LF_ACCURACY_500_PPM as u8,
        }),
        conn_gap: Some(raw::ble_gap_conn_cfg_t {
            conn_count: 6,
            event_length: 24,
        }),
        conn_gatt: Some(raw::ble_gatt_conn_cfg_t { att_mtu: 256 }),
        gatts_attr_tab_size: Some(raw::ble_gatts_cfg_attr_tab_size_t {
            attr_tab_size: raw::BLE_GATTS_ATTR_TAB_SIZE_DEFAULT,
        }),
        gap_role_count: Some(raw::ble_gap_cfg_role_count_t {
            adv_set_count: 1,
            periph_role_count: 3,
            central_role_count: 3,
            central_sec_count: 0,
            _bitfield_1: raw::ble_gap_cfg_role_count_t::new_bitfield_1(0),
        }),
        gap_device_name: Some(raw::ble_gap_cfg_device_name_t {
            p_value: b"HelloRust" as *const u8 as _,
            current_len: 9,
            max_len: 9,
            write_perm: unsafe { mem::zeroed() },
            _bitfield_1: raw::ble_gap_cfg_device_name_t::new_bitfield_1(raw::BLE_GATTS_VLOC_STACK as u8),
        }),
        ..Default::default()
    };

    // spawn softdevice task
    let sd = Softdevice::enable(&config); // <- this causes locked up crash!
    unwrap!(spawner.spawn(softdevice_task(sd)));

    // change config    
    let mut config = peripheral::Config::default();
    config.interval = 50;

    static ADV_DATA: LegacyAdvertisementPayload = LegacyAdvertisementBuilder::new()
        .flags(&[Flag::GeneralDiscovery, Flag::LE_Only])
        .services_16(ServiceList::Complete, &[ServiceUuid16::HEALTH_THERMOMETER]) // if there were a lot of these there may not be room for the full name
        .short_name("Hello")
        .build();

    // but we can put it in the scan data
    // so the full name is visible once connected
    static SCAN_DATA: LegacyAdvertisementPayload = LegacyAdvertisementBuilder::new().full_name("Hello, Rust!").build();

    let adv = peripheral::NonconnectableAdvertisement::ScannableUndirected {
        adv_data: &ADV_DATA,
        scan_data: &SCAN_DATA,
    };
    unwrap!(peripheral::advertise(sd, adv, &config).await);
}

#[embassy_executor::task]
async fn softdevice_task(sd: &'static Softdevice) -> ! {
    sd.run().await
}

My toml:

[package]
edition = "2021"
name = "bike-aid-nrf-rs"
version = "0.1.0"

[features] 
default = [
    "ble-l2cap",
    "ble-gatt-server",
    "ble-gatt-client",
    "ble-sec",
    "nrf52840",
]

ble-l2cap = ["nrf-softdevice/ble-l2cap"]
ble-gatt-server = ["nrf-softdevice/ble-gatt-server"]
ble-gatt-client = ["nrf-softdevice/ble-gatt-client"]
ble-sec = ["nrf-softdevice/ble-sec"]

nrf52840 = [
  "embassy-nrf/nrf52840",
  "nrf-softdevice/nrf52840",
  "nrf-softdevice/s140",
  "dep:nrf-softdevice-s140"
]

[dependencies]
# embassy
embassy-futures = { version = "0.1.0" }
embassy-sync = { version = "0.6.0", features = ["defmt"] }
embassy-executor = { version = "0.5.0", features = ["task-arena-size-32768", "arch-cortex-m", "executor-thread", "executor-interrupt", "defmt", "integrated-timers"] }
embassy-time = { version = "0.3.1", features = ["defmt", "defmt-timestamp-uptime"] }
embassy-nrf = { version = "0.1.0", features = ["defmt", "nrf52840", "time-driver-rtc1", "gpiote", "unstable-pac", "time", "nfc-pins-as-gpio", "reset-pin-as-gpio"] }
embassy-embedded-hal = { version = "0.1.0" }

# log
defmt = "0.3.8"
defmt-rtt = "0.4.1"

# arm
cortex-m = { version = "0.7.7", features = ["inline-asm"] }
cortex-m-rt = "0.7.3"

# misc
panic-probe = { version = "0.3.1", features = ["print-defmt"] }
serde = { version = "1.0.136", default-features = false }
embedded-hal = "1.0.0"

# maths
num-traits = { version = "0.2.19", default-features = false, features = ["libm"] }

# nrf softdevice bluetooth
nrf-softdevice-s140 = { version = "0.1.2", optional = true }
nrf-softdevice = { version = "0.1.0", features = ["nrf52840", "s140", "defmt", "ble-peripheral", "ble-central", "critical-section-impl"] }
embedded-storage = "0.3.1"
embedded-storage-async = "0.4.1"
futures = { version = "0.3.29", default-features = false }
fixed = "1.24.0"
heapless = "0.8.0"
atomic-pool = "1.0.1"
static_cell = "2.0.0"

# device driver
nb = "1.1.0"
mcp4725 = "0.4.2"
ads1x1x = "0.2.2"
mpu6050 = "0.1.6"

[profile.release]
debug = 2

[patch.crates-io]
# make sure to get the latest git rev from github, you can see the latest one here:
# https://github.com/embassy-rs/embassy/commits/main/
embassy-futures = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}
embassy-sync = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}
embassy-executor = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}
embassy-time = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}
embassy-nrf = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}
embassy-embedded-hal = { git = "https://github.com/embassy-rs/embassy", rev = "f91244bae6a4b277f8464c499e50c492a7671039"}

nrf-softdevice-s140 = { git = "https://github.com/embassy-rs/nrf-softdevice", rev = "d5f023ba0f30d9d6779931f8a20a3c81c45b90f2"}
nrf-softdevice = { git = "https://github.com/embassy-rs/nrf-softdevice", rev = "d5f023ba0f30d9d6779931f8a20a3c81c45b90f2"}
Dirbaio commented 2 weeks ago

have you flashed the softdevice accoridng to these instructions? https://github.com/embassy-rs/nrf-softdevice?tab=readme-ov-file#running-examples

note the erase before flashing it is important.

Gibbz commented 2 weeks ago

Yes ive flashed to 7.3.0. Im wondering if the issue is with the memory.x file. I have the one from the examples for 52840 7.1.0. But I have version 7.3.0

MEMORY
{
  /* NOTE 1 K = 1 KiBi = 1024 bytes */
  /* NRF52840 with Softdevice S140 7.0.1 */
  FLASH : ORIGIN = 0x00027000, LENGTH = 868K
  RAM : ORIGIN = 0x20020000, LENGTH = 128K
}
Dirbaio commented 1 week ago

that shouldn't be an issue, memory.x is the same for all 7.x softdevices.

Have you first erased the entire chip then flashed the softdevice? Just flashing can break if there was some firmware before.

Also, if you flash an unmodified example from this repo, does it work?

Gibbz commented 1 week ago

Okay. Ive tried a different firmware no change. When I tried an example it works fine. Any idea what could be missing? It must be some configuration issue.

Edit: I have copied the example file into my project, and it runs fine from there also! So it cant be the toml file or any other config. Ill try strip back the source code and see if I can find whats going on....

Gibbz commented 1 week ago

Okay, the issue is still with the interrupts. How can I fix this? Specifically the temp one.... Is this one of those devices that are off limits with the softdevice?

use crate::signals;
use embassy_nrf::{peripherals::TEMP, temp::Temp};
use embassy_time::Timer;
use embassy_nrf::{bind_interrupts, interrupt};
use embassy_nrf::interrupt::InterruptExt;
use embassy_nrf::temp;
use defmt::*;

const TASK_ID: &str = "TEMPERATURE";

#[embassy_executor::task]
pub async fn temperature (
    temp: TEMP
) {
    //return;
    info!("{}: start", TASK_ID);

    bind_interrupts!(struct Irqs {TEMP => temp::InterruptHandler;});
    interrupt::TEMP.set_priority(interrupt::Priority::P3);
    let mut t = Temp::new(temp, Irqs);
    let pub_temperature = signals::TEMPERATURE.publisher().unwrap();

    loop {
        let value: u16 = t.read().await.to_num::<u16>();
        //info!("{}", value);
        pub_temperature.publish_immediate(value); // in degrees C, no decimals
        Timer::after_secs(60).await;
    }
}