Skip to content

Commit 064c098

Browse files
AlisonSchofielddavejiang
authored andcommitted
cxl/region: Use do_div() for 64-bit modulo operation
div64_u64_rem() was the wrong choice for doing a modulo operation and it was used incorrectly, causing a kernel oops by passing NULL as the remainder parameter. Replace it with the do_div() helper that does the intended math (gran_offset = offset % gran) and is architecture safe. This bug appeared during testing of unaligned address translations. The visibility to userspace would be limited to folks doing poison injection or clear by HPA on unaligned regions. Fixes: 78b50b598462 ("cxl/region: Translate HPA to DPA and memdev in unaligned regions") Signed-off-by: Alison Schofield <alison.schofield@intel.com> Link: https://patch.msgid.link/20260117044732.567831-1-alison.schofield@intel.com Signed-off-by: Dave Jiang <dave.jiang@intel.com>
1 parent b51792f commit 064c098

1 file changed

Lines changed: 2 additions & 1 deletion

File tree

drivers/cxl/core/region.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3324,6 +3324,7 @@ static int unaligned_region_offset_to_dpa_result(struct cxl_region *cxlr,
33243324
u64 interleave_width, interleave_index;
33253325
u64 gran, gran_offset, dpa_offset;
33263326
u64 hpa = p->res->start + offset;
3327+
u64 tmp = offset;
33273328

33283329
/*
33293330
* Unaligned addresses are not algebraically invertible. Calculate
@@ -3333,7 +3334,7 @@ static int unaligned_region_offset_to_dpa_result(struct cxl_region *cxlr,
33333334
gran = cxld->interleave_granularity;
33343335
interleave_width = gran * cxld->interleave_ways;
33353336
interleave_index = div64_u64(offset, interleave_width);
3336-
gran_offset = div64_u64_rem(offset, gran, NULL);
3337+
gran_offset = do_div(tmp, gran);
33373338

33383339
dpa_offset = interleave_index * gran + gran_offset;
33393340

0 commit comments

Comments
 (0)