kek@DINORAH.WUSTL.EDU (04/05/89)
(Bob Scheifler replied to RUSTY) >The Sun ddx simply allocates read-only entries out of the default colormap >(and I don't think it ever frees them). Yanking an arbitrary number of colors >away from the user is unfriendly. Always allocating out of the default map >is incorrect for windows that use other colormaps. There is no guarantee that >the allocation will succeed (the server is technically permitted to fail in >this operation, but it isn't very desirable to do so). Config: Apollo DM 3000, XR3 fixes 1-8, std make World using TCP only. We have noticed many time how frail the cursor is on sample server for apollo. The X looses its white outline immediately and occasionally picks up what looks like fuzz after some unknown number of operations. Even more aggravating is that the cursor does some kind of XORing of the pixels over which it passes. This is most obviously seen if we mouse over to the colorchart client which is a 16x16 grid of all of the (256) pixel values to give visual confirmation to the way we think the colormap is being used. Here, it is seen that the X cursor always takes on the odd value which is equal to or one greater than the pixels it is overwriting. The effect is pretty spectacular when it appears that the cursor passes _over_ some structures but _under_ others depending whether numeric value of that color is even or odd (today). Real frustration comes when you try to move the cursor in a region which is large compared to the cursor and whose pixel value is odd. Here the cursor has no contrast (without its outline) and so, is not seen. It really makes pointing difficult. has anyone else seen/fixed this? BTW The beta server from Apollo does _not_ exhibit this difficulty but we haven't switched over to that until we have ironed out window manager issues (dm vs uwm).
bowbeer@apollo.COM (Joe Bowbeer) (04/15/89)
Ken, This is a copy of the bug report I'm sending to xbugs. The patch and code included should solve your problems. I'm giving this wide distribution because I think it's a particularly irritating problem and affects a lot of folks. VERSION: X11 release 3 CLIENT MACHINE: Apollo CLIENT OPERATING SYSTEM: sr10.1 (and to a lesser extent on sr9.7) DISPLAY: all color displays SYNOPSIS: intermittent problems drawing into pixmaps DESCRIPTION: Sometimes pixmaps are rendered currectly. This visual effects are incorrect cursor patterns, incorrect tiles, etc. FIX: There are actually two problems here having to do with the the pixmap implementation. One problem is that the current bitmap cache (LastGPRBitmap) is not updated after calling gpr_$deallocate_bitmap. If the current bitmap is the one being deallocated and then another bitmap is created and used, its id will most likely be identical to the old bitmap, but because of the cache alias the gpr_$set_bitmap call will be elided. This problem is fixed by updating the bitmap cache after calling gpr_$deallocate_bitmap. See server/ddx/apollo/apclr_curs.c patch below. The second problem is caused by a subtle bug in sr10.1 gprlib. While a patch is available this month (call 1-800-2APOLLO), the rewritten pixmap routines (below) avoid this bug and are also faster and more space efficient to boot. Note that the new apcDestroyPixmap routine also contains the deallocate fix. -------------------------------------------------------------------------------- [ Patch for server/ddx/apollo/apclr_curs.c ] $ diff -c -b apclr_curs.c.orig apclr_curs.c *** apclr_curs.c.orig Wed Jan 18 17:20:31 1989 --- apclr_curs.c Thu Apr 13 23:52:32 1989 *************** *** 261,266 **** --- 261,268 ---- return (TRUE); } + extern gpr_$bitmap_desc_t LastGPRBitmap; /* peek inside apc_$set_bitmap */ + /* * apClrUnrealizeCursor -- DDX interface (screen) * Given a cursor record and the cursor-private record for a *************** *** 275,280 **** --- 277,284 ---- status_$t st; gpr_$deallocate_bitmap( pPrivC->pRealizedData, st ); + if ((gpr_$bitmap_desc_t)pPrivC->pRealizedData == LastGPRBitmap) + gpr_$inq_bitmap( LastGPRBitmap, st ); /* update cache */ return (TRUE); } -------------------------------------------------------------------------------- [ Rewritten server/ddx/apollo/apc/apcpixmap.c ] /****************************************************************** Copyright 1989 by Apollo Computer Inc., Chelmsford, Massachusetts. All Rights Reserved Permission to use, duplicate, change, and distribute this software and its documentation for any purpose and without fee is granted, provided that the above copyright notice appear in such copy and that this copyright notice appear in all supporting documentation, and that the names of Apollo Computer Inc. or MIT not be used in advertising or publicity pertaining to distribution of the software without written prior permission. ******************************************************************/ #include "apc.h" #include "Xmd.h" #include "servermd.h" #include "pixmapstr.h" PixmapPtr apcCreatePixmap (pScreen, width, height, depth, format) ScreenPtr pScreen; int width; int height; int depth; int format; { apDisplayDataPtr pDisp = &apDisplayData[pScreen->myNum]; PixmapPtr pPixmap; apcPrivPMPtr pPriv; unsigned int linebytes, planebytes, totalbytes; gpr_$offset_t size; gpr_$bmf_group_header_t group_header; gpr_$bitmap_desc_t bitmap; status_$t status; if ( !(pPixmap = (PixmapPtr)Xalloc(sizeof(PixmapRec))) ) return (PixmapPtr)NULL; pPixmap->drawable.type = DRAWABLE_PIXMAP; pPixmap->drawable.pScreen = pScreen; pPixmap->drawable.depth = depth; pPixmap->drawable.serialNumber = NEXT_SERIAL_NUMBER; pPixmap->width = width; pPixmap->height = height; pPixmap->devKind = PixmapBytePad(width, depth); pPixmap->refcnt = 1; if ( !(pPriv = (apcPrivPMPtr)Xalloc(sizeof(apcPrivPM)))) { Xfree(pPixmap); return (PixmapPtr)NULL; } pPixmap->devPrivate = (pointer)pPriv; /* * We wish to allocate the pixmap memory ourselves with Xalloc instead of letting * GPR do it. We do not need GPR to zero the pixmap, nor to allocate the pixmap in * memory backed by separate filesystem objects ("blocks" of GPR bitmaps). (This * is only to support frame mode, and makes allocation more expensive in time and * space.) We also suspect GPR's complex 2-D allocator results in severe * fragmentation of the collection of these objects under some X usage patterns. * * Here we compute the group header information needed to call gpr_$make_bitmap_from_array, * and actually allocate the memory with Xalloc. We create a planewise GPR bitmap. * We round bytes_per_line up to a multiple of 4; bytes_per_sect is just bytes_per_line * times height, in order to lay out the planes with no extra intervening space * (some of the spans code depends on this). */ linebytes = ((width + 0x1F) & (~0x1F)) >> 3; planebytes = linebytes * height; totalbytes = planebytes * depth; if ( !(pPriv->bitmap_ptr = (int *)Xalloc(totalbytes)) ) { Xfree(pPriv); Xfree(pPixmap); return (PixmapPtr)NULL; } bzero((char *)pPriv->bitmap_ptr, totalbytes); size.x_size = width; size.y_size = height; group_header.n_sects = depth; group_header.pixel_size = 1; group_header.allocated_size = 1; group_header.bytes_per_line = linebytes; group_header.bytes_per_sect = planebytes; group_header.storage_offset = (char *)pPriv->bitmap_ptr; gpr_$make_bitmap_from_array(size, pDisp->attribute_block, 1, group_header, bitmap, status); pPriv->bitmap_desc = bitmap; pPriv->width = linebytes >> 1; pPriv->size = size; return pPixmap; } extern gpr_$bitmap_desc_t LastGPRBitmap; /* peek inside apc_$set_bitmap */ Bool apcDestroyPixmap(pPixmap) PixmapPtr pPixmap; { status_$t status; gpr_$bitmap_desc_t bitmap; apcPrivPMPtr pPriv; /* BOGOSITY ALERT */ if ((unsigned)pPixmap < 42) return TRUE; if(--pPixmap->refcnt) return TRUE; bitmap = ((apcPrivPMPtr)(pPixmap->devPrivate))->bitmap_desc; gpr_$deallocate_bitmap(bitmap, status); if (bitmap == LastGPRBitmap) gpr_$inq_bitmap(LastGPRBitmap, status); /* update cache */ pPriv = (apcPrivPMPtr)pPixmap->devPrivate; Xfree(pPriv->bitmap_ptr); Xfree(pPriv); Xfree(pPixmap); return TRUE; } --------------------------------------------------------------------------------