* [PATCH v3] staging: sm750fb: fix mono image source stride mismatch in lynxfb_ops_imageblit()
@ 2026-07-28 13:10 Muhammad Bilal
2026-07-28 15:45 ` Dan Carpenter
0 siblings, 1 reply; 2+ messages in thread
From: Muhammad Bilal @ 2026-07-28 13:10 UTC (permalink / raw)
To: sudipm.mukherjee, teddy.wang
Cc: gregkh, linux-fbdev, linux-staging, linux-kernel, Muhammad Bilal,
stable
sm750_hw_imageblit() advances its monochrome source pointer by
src_delta per scanline, and computes the correct rounded-up stride
internally as:
bytes_per_scan = (width + start_bit + 7) / 8;
Its only caller, lynxfb_ops_imageblit(), instead passed src_delta as
image->width >> 3. For widths not a multiple of 8 this under-counted
the stride, so the source pointer fell further behind the real
per-scanline layout on every line, corrupting the rendered image.
Rather than just fixing the caller's calculation, remove src_delta
as a parameter entirely and have sm750_hw_imageblit() advance by the
bytes_per_scan it already computes for itself. There has only ever
been one caller, and that caller was passing an out-of-sync
derivative of the same width/start_bit values sm750_hw_imageblit()
already has, so keeping stride as a separate parameter served no
purpose beyond letting the two calculations drift apart, which is
exactly what happened here.
Rounding up, rather than down, is the direction consistent with the
rest of the fbdev core: struct fb_image mono bitmap data (the same
image->data this driver receives) is walked elsewhere with byte
strides derived from a ceiling division of width by 8. The generic
mono bit iterator in drivers/video/fbdev/core/fb_imageblit.h advances
scanlines with "iter->data += BITS_TO_BYTES(iter->width)", and
BITS_TO_BYTES() (include/linux/bitops.h) is a ceiling division.
sm750_hw_imageblit()'s own "(width + start_bit + 7) / 8" is that same
ceiling division with an added start_bit offset, so the caller's
">> 3" (floor) was the one calculation out of step with how this data
layout is handled everywhere else.
Found by code review of sm750_hw_imageblit()'s internal stride
calculation against what its only caller was passing in, and
confirmed with a clean -Werror build. I do not have this hardware,
so this has not been exercised at runtime on real sm750 silicon.
Fixes: 81dee67e215b2 ("staging: sm750fb: add sm750 to staging")
Cc: stable@vger.kernel.org
Signed-off-by: Muhammad Bilal <meatuni001@gmail.com>
---
v3: Added the version notes below, which Dan pointed out were
missing from v2. Added Cc: stable@vger.kernel.org, flagged by
Greg's patch-bot since the Fixes: tag targets an old (2015)
commit. Added the rounding-direction justification Dan asked
about, citing fb_imageblit.h's BITS_TO_BYTES() as the existing
kernel-wide convention for this same struct fb_image layout.
Moved the "no hardware" disclosure from an email reply into the
commit message itself, per Dan's request.
v2: Added a Fixes tag. Moved the src_delta calculation into
sm750_hw_imageblit() itself and dropped it as a parameter, per
Dan Carpenter's review.
drivers/staging/sm750fb/sm750.c | 2 +-
drivers/staging/sm750fb/sm750.h | 2 +-
drivers/staging/sm750fb/sm750_accel.c | 6 ++----
drivers/staging/sm750fb/sm750_accel.h | 4 +---
4 files changed, 5 insertions(+), 9 deletions(-)
diff --git a/drivers/staging/sm750fb/sm750.c b/drivers/staging/sm750fb/sm750.c
index 89c811e..da0b497 100644
--- a/drivers/staging/sm750fb/sm750.c
+++ b/drivers/staging/sm750fb/sm750.c
@@ -261,7 +261,7 @@ static void lynxfb_ops_imageblit(struct fb_info *info,
spin_lock(&sm750_dev->slock);
sm750_dev->accel.de_imageblit(&sm750_dev->accel,
- image->data, image->width >> 3, 0,
+ image->data, 0,
base, pitch, bpp,
image->dx, image->dy,
image->width, image->height,
diff --git a/drivers/staging/sm750fb/sm750.h b/drivers/staging/sm750fb/sm750.h
index d2c522e..83229fe 100644
--- a/drivers/staging/sm750fb/sm750.h
+++ b/drivers/staging/sm750fb/sm750.h
@@ -73,7 +73,7 @@ struct lynx_accel {
u32 rop2);
int (*de_imageblit)(struct lynx_accel *accel, const char *p_srcbuf,
- u32 src_delta, u32 start_bit, u32 d_base, u32 d_pitch,
+ u32 start_bit, u32 d_base, u32 d_pitch,
u32 byte_per_pixel, u32 dx, u32 dy, u32 width,
u32 height, u32 f_color, u32 b_color, u32 rop2);
diff --git a/drivers/staging/sm750fb/sm750_accel.c b/drivers/staging/sm750fb/sm750_accel.c
index 0316ea6..bac9a20 100644
--- a/drivers/staging/sm750fb/sm750_accel.c
+++ b/drivers/staging/sm750fb/sm750_accel.c
@@ -288,8 +288,6 @@ static unsigned int de_get_transparency(struct lynx_accel *accel)
* sm750_hw_imageblit
* @accel: Acceleration device data
* @src_buf: pointer to start of source buffer in system memory
- * @src_delta: Pitch value (in bytes) of the source buffer, +ive means top down
- * and -ive mean button up
* @start_bit: Mono data can start at any bit in a byte, this value should be
* 0 to 7
* @dest_base: Address of destination: offset in frame buffer
@@ -304,7 +302,7 @@ static unsigned int de_get_transparency(struct lynx_accel *accel)
* @rop2: ROP value
*/
int sm750_hw_imageblit(struct lynx_accel *accel, const char *src_buf,
- u32 src_delta, u32 start_bit, u32 dest_base, u32 dest_pitch,
+ u32 start_bit, u32 dest_base, u32 dest_pitch,
u32 byte_per_pixel, u32 dx, u32 dy, u32 width,
u32 height, u32 fg_color, u32 bg_color, u32 rop2)
{
@@ -395,7 +393,7 @@ int sm750_hw_imageblit(struct lynx_accel *accel, const char *src_buf,
write_dp_port(accel, *(unsigned int *)remain);
}
- src_buf += src_delta;
+ src_buf += bytes_per_scan;
}
return 0;
diff --git a/drivers/staging/sm750fb/sm750_accel.h b/drivers/staging/sm750fb/sm750_accel.h
index d15a40c..4f609d6 100644
--- a/drivers/staging/sm750fb/sm750_accel.h
+++ b/drivers/staging/sm750fb/sm750_accel.h
@@ -220,8 +220,6 @@ int sm750_hw_copyarea(struct lynx_accel *accel,
/**
* sm750_hw_imageblit
* @pSrcbuf: pointer to start of source buffer in system memory
- * @srcDelta: Pitch value (in bytes) of the source buffer, +ive means top down
- *>----- and -ive mean button up
* @startBit: Mono data can start at any bit in a byte, this value should be
*>----- 0 to 7
* @dBase: Address of destination: offset in frame buffer
@@ -236,7 +234,7 @@ int sm750_hw_copyarea(struct lynx_accel *accel,
* @rop2: ROP value
*/
int sm750_hw_imageblit(struct lynx_accel *accel, const char *pSrcbuf,
- u32 srcDelta, u32 startBit, u32 dBase, u32 dPitch,
+ u32 startBit, u32 dBase, u32 dPitch,
u32 bytePerPixel, u32 dx, u32 dy, u32 width,
u32 height, u32 fColor, u32 bColor, u32 rop2);
--
2.55.0
^ permalink raw reply related [flat|nested] 2+ messages in thread* Re: [PATCH v3] staging: sm750fb: fix mono image source stride mismatch in lynxfb_ops_imageblit()
2026-07-28 13:10 [PATCH v3] staging: sm750fb: fix mono image source stride mismatch in lynxfb_ops_imageblit() Muhammad Bilal
@ 2026-07-28 15:45 ` Dan Carpenter
0 siblings, 0 replies; 2+ messages in thread
From: Dan Carpenter @ 2026-07-28 15:45 UTC (permalink / raw)
To: Muhammad Bilal
Cc: sudipm.mukherjee, teddy.wang, gregkh, linux-fbdev, linux-staging,
linux-kernel, stable
On Tue, Jul 28, 2026 at 06:10:50PM +0500, Muhammad Bilal wrote:
> sm750_hw_imageblit() advances its monochrome source pointer by
> src_delta per scanline, and computes the correct rounded-up stride
> internally as:
>
> bytes_per_scan = (width + start_bit + 7) / 8;
>
> Its only caller, lynxfb_ops_imageblit(), instead passed src_delta as
> image->width >> 3. For widths not a multiple of 8 this under-counted
> the stride, so the source pointer fell further behind the real
> per-scanline layout on every line, corrupting the rendered image.
>
> Rather than just fixing the caller's calculation, remove src_delta
> as a parameter entirely and have sm750_hw_imageblit() advance by the
> bytes_per_scan it already computes for itself. There has only ever
> been one caller, and that caller was passing an out-of-sync
> derivative of the same width/start_bit values sm750_hw_imageblit()
> already has, so keeping stride as a separate parameter served no
> purpose beyond letting the two calculations drift apart, which is
> exactly what happened here.
>
> Rounding up, rather than down, is the direction consistent with the
> rest of the fbdev core: struct fb_image mono bitmap data (the same
> image->data this driver receives) is walked elsewhere with byte
> strides derived from a ceiling division of width by 8. The generic
> mono bit iterator in drivers/video/fbdev/core/fb_imageblit.h advances
> scanlines with "iter->data += BITS_TO_BYTES(iter->width)", and
> BITS_TO_BYTES() (include/linux/bitops.h) is a ceiling division.
> sm750_hw_imageblit()'s own "(width + start_bit + 7) / 8" is that same
> ceiling division with an added start_bit offset, so the caller's
> ">> 3" (floor) was the one calculation out of step with how this data
> layout is handled everywhere else.
>
> Found by code review of sm750_hw_imageblit()'s internal stride
> calculation against what its only caller was passing in, and
> confirmed with a clean -Werror build. I do not have this hardware,
> so this has not been exercised at runtime on real sm750 silicon.
>
> Fixes: 81dee67e215b2 ("staging: sm750fb: add sm750 to staging")
> Cc: stable@vger.kernel.org
> Signed-off-by: Muhammad Bilal <meatuni001@gmail.com>
> ---
> v3: Added the version notes below, which Dan pointed out were
> missing from v2. Added Cc: stable@vger.kernel.org, flagged by
> Greg's patch-bot since the Fixes: tag targets an old (2015)
> commit. Added the rounding-direction justification Dan asked
> about, citing fb_imageblit.h's BITS_TO_BYTES() as the existing
> kernel-wide convention for this same struct fb_image layout.
> Moved the "no hardware" disclosure from an email reply into the
> commit message itself, per Dan's request.
Generally the no hardware disclosure would come here under the
--- cut off line. But I'm not going to nit pick about that, it's
fine.
I see also that the "Pitch value (in bytes)" comment supports rounding
up so this looks good to me.
Reviewed-by: Dan Carpenter <error27@gmail.com>
regards,
dan carpenter
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2026-07-28 15:45 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-07-28 13:10 [PATCH v3] staging: sm750fb: fix mono image source stride mismatch in lynxfb_ops_imageblit() Muhammad Bilal
2026-07-28 15:45 ` Dan Carpenter
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.