summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaisuke Matsuda <matsuda@preferred.jp>2026-07-23 08:19:12 +0000
committerXu Yilun <yilun.xu@linux.intel.com>2026-08-04 17:35:41 +0800
commit9da70a43b5fea60d758137f7f0ccfe19356cb5bb (patch)
tree910432f3a0ef4b096ffa11b9bbd8e2ecc085c5b6
parent2c972f03ccdda4fe9df4833056c5b4bfd953a61c (diff)
downloadlinux-9da70a43b5fea60d758137f7f0ccfe19356cb5bb.tar.gz
linux-9da70a43b5fea60d758137f7f0ccfe19356cb5bb.zip
fpga: altera-cvp: Avoid out-of-bounds read in trailing byte write
The trailing byte path in altera_cvp_send_block() dereferences a u32 pointer even when only 1-3 bytes remain in the input buffer. If the buffer ends at a page or scatterlist boundary, this can read past the valid image data and fault. Copy the remaining bytes into a zero-initialized u32 before writing the final word so only valid bytes are read from the input buffer. Fixes: 34d1dc17ce97 ("fpga manager: Add Altera CvP driver") Cc: stable@vger.kernel.org Signed-off-by: Daisuke Matsuda <matsuda@preferred.jp> Reviewed-by: Xu Yilun <yilun.xu@intel.com> Link: https://lore.kernel.org/r/20260723081912.74082-1-dskmtsd@gmail.com Signed-off-by: Xu Yilun <yilun.xu@linux.intel.com>
-rw-r--r--drivers/fpga/altera-cvp.c10
1 files changed, 6 insertions, 4 deletions
diff --git a/drivers/fpga/altera-cvp.c b/drivers/fpga/altera-cvp.c
index 44badfd11e1b..070c025ee215 100644
--- a/drivers/fpga/altera-cvp.c
+++ b/drivers/fpga/altera-cvp.c
@@ -16,6 +16,7 @@
#include <linux/module.h>
#include <linux/pci.h>
#include <linux/sizes.h>
+#include <linux/string.h>
#define CVP_BAR 0 /* BAR used for data transfer in memory mode */
#define CVP_DUMMY_WR 244 /* dummy writes to clear CvP state machine */
@@ -261,7 +262,7 @@ static int altera_cvp_v2_wait_for_credit(struct fpga_manager *mgr,
static int altera_cvp_send_block(struct altera_cvp_conf *conf,
const u32 *data, size_t len)
{
- u32 mask, words = len / sizeof(u32);
+ u32 words = len / sizeof(u32);
int i, remainder;
for (i = 0; i < words; i++)
@@ -270,9 +271,10 @@ static int altera_cvp_send_block(struct altera_cvp_conf *conf,
/* write up to 3 trailing bytes, if any */
remainder = len % sizeof(u32);
if (remainder) {
- mask = BIT(remainder * 8) - 1;
- if (mask)
- conf->write_data(conf, *data & mask);
+ u32 word = 0;
+
+ memcpy(&word, data, remainder);
+ conf->write_data(conf, word);
}
return 0;