Re: [AD] bug in getpixel

[ Thread Index | Date Index | More lists.liballeg.org/allegro-developers Archives ]


On 2005-11-14, Vincent Penecherc'h <Vincent.Penecherch@xxxxxxxxxx> wrote:
> How's that for an attention grabbing subject ? :)
> 
> In 24 bit modes, when the last pixel of a memory BITMAP
> is right on the end of a page, the assembler getpixel will
> trigger a page fault by reading an unaligned int for the
> three bytes of the pixel (in the last page) and a random
> byte (in the next page) which will then get masked out,
> but the damage is done.
> 
> I've tried changing the code to either read 3 bytes and
> or the results, or read aligned and shift for odd addresses,
> but both are slower than the unaligned reads, so I've
> just added 1 to the allocated memory for 24 bit BITMAPs.

I don't understand the rationale behind adding just one byte. Say
I wanted a bitmap of 3x1 pixels, which will malloc 3 * 1 * 3 =
9 bytes. Adding one makes it 10, but wouldn't alignment rules
require 12? How about 64bit machines? I guess we haven't asm for
them, but surely that will be a problem too (some day)?

Besides, you could comment it better:

Index: src/graphics.c
===================================================================
RCS file: /cvsroot/alleg/allegro/src/graphics.c,v
retrieving revision 1.66
diff -u -p -r1.66 graphics.c
--- src/graphics.c      12 Nov 2005 16:59:33 -0000      1.66
+++ src/graphics.c      26 Nov 2005 21:35:38 -0000
@@ -1042,7 +1042,7 @@ BITMAP *create_bitmap_ex(int color_depth
 {
    GFX_VTABLE *vtable;
    BITMAP *bitmap;
-   int i;
+   int padding = 0;
    ASSERT(width >= 0);
    ASSERT(height > 0);
    ASSERT(system_driver);
@@ -1058,7 +1058,11 @@ BITMAP *create_bitmap_ex(int color_depth
    if (!bitmap)
       return NULL;
 
-   bitmap->dat = malloc(width * height * BYTES_PER_PIXEL(color_depth));
+   /* This avoids a crash for assembler code accessing the last pixel. */
+   if (color_depth == 24)
+      padding = 1;
+
+   bitmap->dat = malloc(width * height * BYTES_PER_PIXEL(color_depth) + padding);
    if (!bitmap->dat) {
       free(bitmap);
       return NULL;





Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/