-
Notifications
You must be signed in to change notification settings - Fork 338
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
target/riscv: simplify reset for rtos harts #821
Conversation
018ab71
to
9cecda8
Compare
Prior to the change, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for adding more error checking, too.
What hardware have you tested this with? I'm especially thinking of multi-hart systems. The tests against spike don't really cover this code, and it's a bit of a house of cards.
This seems to work fine on HiFive Unleashed. |
4b26eac
to
3e9a08d
Compare
We also tested on HiFive Unleashed as well as on Syntacore SCR7 SMP (on which the bug was discovered in the first place) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@en-sc Thank you for the changes. I have checked the code visually and it looks all right. I have only few minor review findings.
src/target/riscv/riscv-013.c
Outdated
|
||
uint32_t dmstatus; | ||
int dmi_busy_delay = info->dmi_busy_delay; | ||
const int dmi_busy_delay = info->dmi_busy_delay; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For readability, could we please call this this orig_dmi_busy_delay
?
const int dmi_busy_delay = info->dmi_busy_delay; | |
const int orig_dmi_busy_delay = info->dmi_busy_delay; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addressed.
src/target/riscv/riscv-013.c
Outdated
"Increase the timeout with riscv set_reset_timeout_sec.", | ||
riscv_reset_timeout_sec, dmstatus, | ||
get_field(dmstatus, DM_DMSTATUS_ALLUNAVAIL) ? "true" : "false", | ||
get_field(dmstatus, DM_DMSTATUS_ALLUNAVAIL) ? "true" : "false"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There seems to be a copy-paste typo:
get_field(dmstatus, DM_DMSTATUS_ALLUNAVAIL) ? "true" : "false"); | |
get_field(dmstatus, DM_DMSTATUS_ALLHAVERESET) ? "true" : "false"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addressed.
src/target/riscv/riscv-013.c
Outdated
uint32_t control = 0, control_haltreq; | ||
control = set_field(control, DM_DMCONTROL_DMACTIVE, 1); | ||
control_haltreq = set_field(control, DM_DMCONTROL_HALTREQ, target->reset_halt ? 1 : 0); | ||
dmi_write(target, DM_DMCONTROL, | ||
result = dmi_write(target, DM_DMCONTROL, | ||
set_dmcontrol_hartsel(control_haltreq, info->index)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For readability, I'd recommend to simplify this part and set always all the fields of dmcontrol:
uint32_t control = 0;
control = set_field(control, DM_DMCONTROL_DMACTIVE, 1);
control = set_field(control, DM_DMCONTROL_HALTREQ, target->reset_halt ? 1 : 0);
control = set_dmcontrol_hartsel(control, info->index);
result = dmi_write(target, DMI_DMCONTROL, control);
Also I'd recommend to use just one variable in this function (control
).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addressed.
src/target/riscv/riscv-013.c
Outdated
/* Ack reset and clear DM_DMCONTROL_HALTREQ if previously set */ | ||
return dmi_write(target, DM_DMCONTROL, | ||
set_dmcontrol_hartsel(control, info->index) | | ||
DM_DMCONTROL_ACKHAVERESET); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same as at the top of the function, I'd recommend to set all the fields here to make it very easy to read:
control = 0;
control = set_field(control, DM_DMCONTROL_DMACTIVE, 1);
control = set_field(control, DM_DMCONTROL_ACKHAVERESET, 1);
result = dmi_write(target, DMI_DMCONTROL, control);
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Addressed.
src/target/riscv/riscv-013.c
Outdated
@@ -4459,8 +4424,10 @@ riscv_insn_t riscv013_read_debug_buffer(struct target *target, unsigned index) | |||
int riscv013_invalidate_cached_debug_buffer(struct target *target) | |||
{ | |||
dm013_info_t *dm = get_dm(target); | |||
if (!dm) | |||
if (!dm) { | |||
LOG_TARGET_ERROR(target, "No DM is specified for the target"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Have you please come across a scenario when this error message would pop up?
Since there is no progbuf_cache to invalidate if the target does not have a debug module specified, I'd recommend to demote this to a debug message only.
In another words, if there is no DM assigned, the operation in such case should not be considered as failed - it is simply not applicable.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you for the suggestion! I've added the message just in case. Have not observed it yet. I've demoted the message as you recommended.
3e9a08d
to
e76c3d3
Compare
@timsifive, @JanMatCodasip, can you please clarify something for me: |
Since the deletion of `-rtos hwthread`, there is no need to treat harts with `-rtos` specified differently on reset. Signed-off-by: Evgeniy Naydanov <[email protected]> Change-Id: I88a9129936b5172bb7479dfa1255e29ff460c054
e76c3d3
to
1c16824
Compare
|
It is not required for the target. The reset took effect just as well without writing ackhavereset. It would be better for OpenOCD to confirm that havereset is set for every hart, and then to ack it so that the bit is clear and OpenOCD will notice if a spontaneous reset occurs. |
@timsifive @en-sc @JanMatCodasip This commit causes certain cores to fail to boot on riscv smp multicore systems. Here's how I configured it.
|
Few questions:
|
The "fail to boot" is mean this ctest failed, and OpenOCD has no error messages.
|
If openocd has no error messages than likely this may be an application bug (timings of the operations were changed).
|
The targets are running, you can see this in the last poll in the log. Here is the snippet regarding
So I agree with @aap-sc and would like suggest to double-check the software you are running. Please, note that the decoding of debug register's fields does note contain the last field (riscv/riscv-debug-spec#908 is a fix for that). |
Since the deletion of
-rtos hwthread
, there is no need to treat harts with-rtos
specified differently on reset.Change-Id: I88a9129936b5172bb7479dfa1255e29ff460c054