From: "Antonino A. Daplas" - Add support for fonts bigger thatn 16x32 by dynamically allocating buffer based on font dimensions instead of statically allocating at 64 bytes. - use softcursor if cursor size exceeds 32x32. - fix rivafb_cursor if cursor width is not divisible by 2 Signed-off-by: Antonino Daplas Signed-off-by: Andrew Morton --- 25-akpm/drivers/video/riva/fbdev.c | 72 ++++++++++++++++++++++--------------- 1 files changed, 43 insertions(+), 29 deletions(-) diff -puN drivers/video/riva/fbdev.c~fbdev-support-for-bigger-than-16x32-fonts-in-rivafb-cursor drivers/video/riva/fbdev.c --- 25/drivers/video/riva/fbdev.c~fbdev-support-for-bigger-than-16x32-fonts-in-rivafb-cursor 2004-11-10 18:36:11.996574592 -0800 +++ 25-akpm/drivers/video/riva/fbdev.c 2004-11-10 18:36:12.001573832 -0800 @@ -444,6 +444,8 @@ static void rivafb_load_cursor_image(str bg = le16_to_cpu(bg); fg = le16_to_cpu(fg); + w = (w + 1) & ~1; + for (i = 0; i < h; i++) { b = *data++; reverse_order(&b); @@ -1577,6 +1579,10 @@ static int rivafb_cursor(struct fb_info u16 fg, bg; int i, set = cursor->set; + if (cursor->image.width > MAX_CURS || + cursor->image.height > MAX_CURS) + return soft_cursor(info, cursor); + par->riva.ShowHideCursor(&par->riva, 0); if (par->cursor_reset) { @@ -1606,38 +1612,46 @@ static int rivafb_cursor(struct fb_info u32 d_pitch = MAX_CURS/8; u8 *dat = (u8 *) cursor->image.data; u8 *msk = (u8 *) cursor->mask; - u8 src[64]; - - switch (cursor->rop) { - case ROP_XOR: - for (i = 0; i < s_pitch * cursor->image.height; - i++) - src[i] = dat[i] ^ msk[i]; - break; - case ROP_COPY: - default: - for (i = 0; i < s_pitch * cursor->image.height; - i++) - src[i] = dat[i] & msk[i]; - break; - } + u8 *src; - fb_sysmove_buf_aligned(info, &info->pixmap, data, d_pitch, src, - s_pitch, cursor->image.height); + src = kmalloc(s_pitch * cursor->image.height, GFP_ATOMIC); - bg = ((info->cmap.red[bg_idx] & 0xf8) << 7) | - ((info->cmap.green[bg_idx] & 0xf8) << 2) | - ((info->cmap.blue[bg_idx] & 0xf8) >> 3) | 1 << 15; - - fg = ((info->cmap.red[fg_idx] & 0xf8) << 7) | - ((info->cmap.green[fg_idx] & 0xf8) << 2) | - ((info->cmap.blue[fg_idx] & 0xf8) >> 3) | 1 << 15; - - par->riva.LockUnlock(&par->riva, 0); + if (src) { + switch (cursor->rop) { + case ROP_XOR: + for (i = 0; i < s_pitch * cursor->image.height; + i++) + src[i] = dat[i] ^ msk[i]; + break; + case ROP_COPY: + default: + for (i = 0; i < s_pitch * cursor->image.height; + i++) + src[i] = dat[i] & msk[i]; + break; + } - rivafb_load_cursor_image(par, data, bg, fg, - cursor->image.width, - cursor->image.height); + fb_sysmove_buf_aligned(info, &info->pixmap, data, + d_pitch, src, s_pitch, + cursor->image.height); + + bg = ((info->cmap.red[bg_idx] & 0xf8) << 7) | + ((info->cmap.green[bg_idx] & 0xf8) << 2) | + ((info->cmap.blue[bg_idx] & 0xf8) >> 3) | + 1 << 15; + + fg = ((info->cmap.red[fg_idx] & 0xf8) << 7) | + ((info->cmap.green[fg_idx] & 0xf8) << 2) | + ((info->cmap.blue[fg_idx] & 0xf8) >> 3) | + 1 << 15; + + par->riva.LockUnlock(&par->riva, 0); + + rivafb_load_cursor_image(par, data, bg, fg, + cursor->image.width, + cursor->image.height); + kfree(src); + } } if (cursor->enable) _