summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorBo Gan <ganboing@gmail.com>2026-06-08 23:00:24 -0700
committerAnup Patel <anup@brainfault.org>2026-06-17 11:43:38 +0530
commita8be5e9478be08f09a720f7013ec30d6e2bd9fcc (patch)
treeec25b77714dc1492dbdb87a92ebadd183c6a5167 /include
parent914aeddaf16d91d39112056c5dd2b013b757a424 (diff)
downloadopensbi-a8be5e9478be08f09a720f7013ec30d6e2bd9fcc.tar.gz
opensbi-a8be5e9478be08f09a720f7013ec30d6e2bd9fcc.zip
lib: sbi: Rework misaligned vector load/store
Fix the following issues with misaligned vector load/store: a. Stack overflow: the mask[VLEN_MAX / 8] variable consumes 8K stack space, given VLEN_MAX=65536, overflowing the default-sized stack. There's no need to fetch the whole mask in one go, instead, make it on-demand. Use a 128-byte mask as local buffer to hold the sliding window of mask. For rvv load, this is allowed -- from the spec: "The destination vector register group for a masked vector instruction cannot overlap the source mask register (v0), unless the destination vector register is being written with a mask value (e.g., compares) or the scalar result of a reduction" We don't need to worry about the mask getting overwritten. b. Maintain the value of vstart upon abort (uptrap) to avoid duplicate work. After fault resolution, the instruction can restart from the faulting vstart. For Fault-Only-First loads, reset vstart to 0, as previously done so, to conform to spec. c. Explicitly set VS dirty in VSSTATUS with SET_VS_DIRTY() if faulting from V=1, and if any vector register, including vstart/vl/vtype, gets changed in the handler. It can add 1 unnecessary op to set VS dirty in M/SSTATUS (not VSSTATUS), where the HW already did, but for code simplicity, do it anyway. The overhead should be negligible. Signed-off-by: Bo Gan <ganboing@gmail.com> Tested-by: Anirudh Srinivasan <asrinivasan@oss.tenstorrent.com> Reviewed-by: Anup Patel <anup@brainfault.org> Link: https://lore.kernel.org/r/20260609060024.706-5-ganboing@gmail.com Signed-off-by: Anup Patel <anup@brainfault.org>
Diffstat (limited to 'include')
-rw-r--r--include/sbi/sbi_vector.h6
1 files changed, 6 insertions, 0 deletions
diff --git a/include/sbi/sbi_vector.h b/include/sbi/sbi_vector.h
index f00184f0..c14f3174 100644
--- a/include/sbi/sbi_vector.h
+++ b/include/sbi/sbi_vector.h
@@ -20,6 +20,12 @@ struct sbi_vector_context {
uint8_t vregs[];
};
+#define SET_VS_DIRTY(regs) do { \
+ if (sbi_regs_from_virt(regs)) \
+ csr_set(CSR_VSSTATUS, MSTATUS_VS); \
+ regs->mstatus |= MSTATUS_VS; \
+} while(0)
+
#ifdef OPENSBI_CC_SUPPORT_VECTOR
void sbi_vector_save(struct sbi_vector_context *dst);
void sbi_vector_restore(const struct sbi_vector_context *src);