Skip to content
This repository has been archived by the owner on Jan 30, 2024. It is now read-only.

Implement --no-reset mode for live attach to a running device #414

Open
wants to merge 7 commits into
base: main
Choose a base branch
from

Conversation

whitequark
Copy link

Fixes #354. Includes some related cleanups.

In my testing this works quite well, including backtraces. The one thing I haven't tested is really flooding defmt with messages, but it probably works fine.

Copy link
Member

@Urhengulas Urhengulas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks great. I added a few suggestions and questions.

PS. you are allowed to disagree with the suggestions.

src/backtrace/unwind.rs Outdated Show resolved Hide resolved
src/backtrace/unwind.rs Outdated Show resolved Hide resolved
src/cli.rs Outdated Show resolved Hide resolved
src/cli.rs Outdated Show resolved Hide resolved
src/main.rs Outdated Show resolved Hide resolved
src/main.rs Outdated Show resolved Hide resolved
src/main.rs Outdated Show resolved Hide resolved
src/main.rs Outdated Show resolved Hide resolved
src/main.rs Outdated Show resolved Hide resolved
@@ -130,7 +130,7 @@ impl Outcome {
Outcome::StackOverflow => log::error!("the program has overflowed its stack"),
Outcome::HardFault => log::error!("the program panicked"),
Outcome::Ok => log::info!("device halted without error"),
Outcome::CtrlC => log::info!("device halted by user"),
Outcome::CtrlC => log::info!("interrupted by user"),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Outcome::CtrlC => log::info!("interrupted by user"),
Outcome::CtrlC => log::info!("device interrupted by user"),

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I changed it to the current message because it's the probe that was interrupted, not the device -- the device keeps running if you do --no-reset.

Copy link
Member

@Urhengulas Urhengulas Jun 23, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe we can actually have two different messages then?

Suggested change
Outcome::CtrlC => log::info!("interrupted by user"),
Outcome::CtrlC if opts.no_reset == true => log::info!("interrupted by user; program keeps running"),
Outcome::CtrlC if opts.no_reset == false => log::info!("device halted by by user"),

I am not sure if opts is in scope here.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's not, but we can just add it as an argument:

fn log(&self, no_reset: bool)

pub initial_stack_pointer: u32,
// entry 1: Reset vector
pub reset: u32,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There was some discussion if we can extract the reset vector from the elf or not and how to make this as stable as possible. Please see #383 (comment). Do you think we can always™️ extract the reset vector the way you implemented it?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From the linked discussion:

It could be that the Flash memory at 0x2000_0000 is aliased at address 0x0000_0000 but I have not checked.

I think that's a typo: the Flash memory is (on STM32s for example; in principe it could be anywhere the instruction fetches are legal) at 0x0800_0000 and the SRAM is (always) at 0x2000_0000.

However, that aside, I looked it up in the ARMv7-M ARM and it seems that I misremembered some details and a much more reliable way would be to read the IVT address from the VTOR register on attach and then use that. I can implement that later.

Screenshot_20230622_171704

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can implement that later.

That would be nice. Maybe in a follow up PR.

In any case I we will need to test the current PR with the rp pico, because that one seems to behave a bit differently than many other microcontrollers because of the bootloader.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can do the testing. Just need to set it up.

src/main.rs Outdated
}

// run program and print logs until there is an exception
start_program(core, elf)?;
attach_to_program(core, elf)?;
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Gotta update it here too:

Suggested change
attach_to_program(core, elf)?;
attack_the_program(core, elf)?;

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh no 😆 I am sorry. This was meant to be a joke 🙈 Please change it back to attach_to_program 🤣

@Urhengulas
Copy link
Member

@whitequark What is the status? 😄

@whitequark
Copy link
Author

@Urhengulas I've been taking care of my health. ETA is this weekend.

@Urhengulas
Copy link
Member

@Urhengulas I've been taking care of my health

That is very good! 🍀
Sorry, I did not want to pressure you

@Urhengulas
Copy link
Member

@whitequark friendly ping 🛎️

@whitequark
Copy link
Author

I'm doing way better! I think I'll do this Saturday.

@Urhengulas
Copy link
Member

I'm doing way better! I think I'll do this Saturday.

That's great to hear!

@whitequark
Copy link
Author

Sorry, I don't think I'll find time to work on this any time soon as I've not had a chance to use probe-rs in months. Feel free to do with the PR whatever you like.

Copy link
Author

@whitequark whitequark left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like some of my responses never went through.

log::debug!("detaching from program");

if let Some(rtt_buffer_address) = elf.rtt_buffer_address() {
set_rtt_blocking_mode(core, rtt_buffer_address, false)?;
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh yeah this is true.

set_rtt_blocking_mode(core, rtt_buffer_address, false)?;
}

core.clear_hw_breakpoint(cortexm::clear_thumb_bit(elf.vector_table.hard_fault).into())?;
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's some code I moved around--I didn't introduce it. For some reason (I didn't investigate closely) probe-run sets a breakpoint on HardFault. Probably to display a nicer error if you hit one?


match (core.available_breakpoint_units()?, elf.rtt_buffer_address()) {
(0, Some(_)) => bail!("RTT not supported on device without HW breakpoints"),
(0, None) => log::warn!("device doesn't support HW breakpoints; HardFault will NOT make `probe-run` exit with an error code"),
(_, Some(rtt_buffer_address)) => set_rtt_to_blocking(core, elf.main_fn_address(), rtt_buffer_address)?,
(_, Some(rtt_buffer_address)) =>
set_rtt_blocking_mode(core, rtt_buffer_address, true)?,
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like #[pre_init] specifies any access to memory as UB, so it's not really "life before main".

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Support for viewing defmt RTT logs without resetting device
2 participants