Bug Summary

File:multiVis.c
Location:line 570, column 26
Description:Dereference of null pointer

Annotated Source Code

1/** ------------------------------------------------------------------------
2 This file contains functions to create a list of regions which
3 tile a specified window. Each region contains all visible
4 portions of the window which are drawn with the same visual.
5 If the window consists of subwindows of two different visual types,
6 there will be two regions in the list. The list can be traversed
7 to correctly pull an image of the window using XGetImage or the
8 Image Library.
9
10Copyright 1994 Hewlett-Packard Co.
11Copyright 1996, 1998 The Open Group
12
13Permission to use, copy, modify, distribute, and sell this software and its
14documentation for any purpose is hereby granted without fee, provided that
15the above copyright notice appear in all copies and that both that
16copyright notice and this permission notice appear in supporting
17documentation.
18
19The above copyright notice and this permission notice shall be included
20in all copies or substantial portions of the Software.
21
22THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
23OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
25IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR
26OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
27ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
28OTHER DEALINGS IN THE SOFTWARE.
29
30Except as contained in this notice, the name of The Open Group shall
31not be used in advertising or otherwise to promote the sale, use or
32other dealings in this Software without prior written authorization
33from The Open Group.
34
35 ------------------------------------------------------------------------ **/
36
37#include <stdlib.h>
38#include <X11/Xlib.h>
39#include <X11/Xutil.h>
40#include <X11/X.h>
41#include <stdio.h>
42#include "list.h"
43#include "wsutils.h"
44#include "multiVis.h"
45/* These structures are copied from X11/region.h. For some reason
46 * they're invisible from the outside.
47 */
48typedef struct {
49 short x1, x2, y1, y2;
50} myBox, myBOX, myBoxRec, *myBoxPtr;
51
52typedef struct my_XRegion {
53 long size;
54 long numRects;
55 myBOX *rects;
56 myBOX extents;
57} myREGION;
58
59/* Items in long list of windows that have some part in the grabbed area */
60typedef struct {
61 Window win;
62 Visual *vis;
63 Colormap cmap;
64 int x_rootrel, y_rootrel; /* root relative location of window */
65 int x_vis, y_vis; /* rt rel x,y of vis part, not parent clipped */
66 int width, height; /* width and height of visible part */
67 int border_width; /* border width of the window */
68 Window parent; /* id of parent (for debugging) */
69} image_win_type;
70
71/* Items in short list of regions that tile the grabbed area. May have
72 multiple windows in the region.
73*/
74typedef struct {
75 Window win; /* lowest window of this visual */
76 Visual *vis;
77 Colormap cmap;
78 int x_rootrel, y_rootrel; /* root relative location of bottom window */
79 int x_vis, y_vis; /* rt rel x,y of vis part, not parent clipped */
80 int width, height; /* w & h of visible rect of bottom window */
81 int border; /* border width of the window */
82 Region visible_region;
83} image_region_type;
84
85/** ------------------------------------------------------------------------
86 Returns TRUE if the two structs pointed to have the same "vis" &
87 "cmap" fields and s2 lies completely within s1. s1 and s2 can
88 point to structs of image_win_type or image_region_type.
89 ------------------------------------------------------------------------ **/
90#define SAME_REGIONS( s1, s2)((s1)->vis == (s2)->vis && (s1)->cmap == (s2
)->cmap && (s1)->x_vis <= (s2)->x_vis &&
(s1)->y_vis <= (s2)->y_vis && (s1)->x_vis
+ (s1)->width >= (s2)->x_vis + (s2)->width &&
(s1)->y_vis + (s1)->height >= (s2)->y_vis + (s2)
->height)
\
91 ((s1)->vis == (s2)->vis && (s1)->cmap == (s2)->cmap && \
92 (s1)->x_vis <= (s2)->x_vis && \
93 (s1)->y_vis <= (s2)->y_vis && \
94 (s1)->x_vis + (s1)->width >= (s2)->x_vis + (s2)->width && \
95 (s1)->y_vis + (s1)->height >= (s2)->y_vis + (s2)->height)
96
97#ifndef MIN
98#define MIN( a, b)((a) < (b) ? a : b) ((a) < (b) ? a : b)
99#define MAX( a, b)((a) > (b) ? a : b) ((a) > (b) ? a : b)
100#endif
101
102#define RED_SHIFT16 16
103#define GREEN_SHIFT8 8
104#define BLUE_SHIFT0 0
105
106/*
107extern list_ptr new_list();
108extern list_ptr dup_list_head();
109extern void * first_in_list();
110extern void * next_in_list();
111extern int add_to_list();
112extern void zero_list();
113extern void delete_list();
114extern void delete_list_destroying();
115extern unsigned int list_length();
116*/
117
118/* Prototype Declarations for Static Functions */
119static int QueryColorMap(
120 Display *, Colormap , Visual *,
121 XColor **, int *, int *, int *
122 );
123static void TransferImage(
124 Display *, XImage *,int, int , image_region_type*,
125 XImage *,int ,int
126 );
127static XImage * ReadRegionsInList(
128 Display *, Visual *, int ,int ,int ,
129 int , XRectangle, list_ptr
130 );
131
132static list_ptr make_region_list(
133 Display*, Window, XRectangle*,
134 int*, int, XVisualInfo**, int *
135 );
136
137static void destroy_region_list(
138 list_ptr
139 ) ;
140static void subtr_rect_from_image_region(
141 image_region_type *, int , int , int , int
142 );
143static void add_rect_to_image_region(
144 image_region_type *,
145 int , int , int , int
146 );
147static int src_in_region_list(
148 image_win_type *, list_ptr
149 );
150static void add_window_to_list(
151 list_ptr, Window, int, int ,
152 int , int , int , int, int,
153 Visual*, Colormap, Window
154 );
155static int src_in_image(
156 image_win_type *, int , XVisualInfo**
157 );
158static int src_in_overlay(
159 image_region_type *, int, OverlayInfo *, int*, int*
160 );
161static void make_src_list(
162 Display *, list_ptr, XRectangle *, Window,
163 int, int, XWindowAttributes *, XRectangle *
164);
165static void destroy_image_region(
166 image_region_type *
167);
168
169/* End of Prototype Declarations */
170
171void initFakeVisual(Visual *Vis)
172{
173 Vis->ext_data=NULL((void*)0);
174 Vis->class = DirectColor5 ;
175 Vis->red_mask = 0x00FF0000;
176 Vis->green_mask = 0x0000FF00 ;
177 Vis->blue_mask = 0x000000FF ;
178 Vis->map_entries = 256 ;
179 Vis->bits_per_rgb = 8 ;
180}
181
182static int
183QueryColorMap(Display *disp, Colormap src_cmap, Visual *src_vis,
184 XColor **src_colors, int *rShift, int *gShift, int *bShift)
185{
186 int ncolors,i ;
187 unsigned long redMask, greenMask, blueMask;
188 int redShift, greenShift, blueShift;
189 XColor *colors ;
190
191 ncolors = src_vis->map_entries ;
192 *src_colors = colors = (XColor *)malloc(ncolors * sizeof(XColor) ) ;
193
194 if(src_vis->class != TrueColor4 && src_vis->class != DirectColor5)
195 {
196 for(i=0 ; i < ncolors ; i++)
197 {
198 colors[i].pixel = i ;
199 colors[i].pad = 0;
200 colors[i].flags = DoRed(1<<0)|DoGreen(1<<1)|DoBlue(1<<2);
201 }
202 }
203 else /** src is decomposed rgb ***/
204 {
205 /* Get the X colormap */
206 redMask = src_vis->red_mask;
207 greenMask = src_vis->green_mask;
208 blueMask = src_vis->blue_mask;
209 redShift = 0; while (!(redMask&0x1)) {
210 redShift++;
211 redMask = redMask>>1;
212 }
213 greenShift = 0; while (!(greenMask&0x1)) {
214 greenShift++;
215 greenMask = greenMask>>1;
216 }
217 blueShift = 0; while (!(blueMask&0x1)) {
218 blueShift++;
219 blueMask = blueMask>>1;
220 }
221 *rShift = redShift ;
222 *gShift = greenShift ;
223 *bShift = blueShift ;
224 for (i=0; i<ncolors; i++) {
225 if( i <= redMask)colors[i].pixel = (i<<redShift) ;
226 if( i <= greenMask)colors[i].pixel |= (i<<greenShift) ;
227 if( i <= blueMask)colors[i].pixel |= (i<<blueShift) ;
228 /***** example :for gecko's 3-3-2 map, blue index should be <= 3.
229 colors[i].pixel = (i<<redShift)|(i<<greenShift)|(i<<blueShift);
230 *****/
231 colors[i].pad = 0;
232 colors[i].flags = DoRed(1<<0)|DoGreen(1<<1)|DoBlue(1<<2);
233 }
234 }
235
236
237 XQueryColors(disp, src_cmap, colors, ncolors);
238 return ncolors ;
239}
240
241int
242GetMultiVisualRegions(Display *disp,
243 /* root win on which grab was done */
244 Window srcRootWinid,
245 /* root rel UL corner of bounding box of grab */
246 int x, int y,
247 /* size of bounding box of grab */
248 unsigned int width, unsigned int height,
249 int *transparentOverlays, int *numVisuals,
250 XVisualInfo **pVisuals, int *numOverlayVisuals,
251 OverlayInfo **pOverlayVisuals,
252 int *numImageVisuals, XVisualInfo ***pImageVisuals,
253 /* list of regions to read from */
254 list_ptr *vis_regions,
255 list_ptr *vis_image_regions, int *allImage)
256{
257 int hasNonDefault;
258 XRectangle bbox; /* bounding box of grabbed area */
259
260
261 bbox.x = x; /* init X rect for bounding box */
262 bbox.y = y;
263 bbox.width = width;
264 bbox.height = height;
265
266 GetXVisualInfo(disp,DefaultScreen(disp)(((_XPrivDisplay)disp)->default_screen),
267 transparentOverlays,
268 numVisuals, pVisuals,
269 numOverlayVisuals, pOverlayVisuals,
270 numImageVisuals, pImageVisuals);
271
272 *vis_regions = *vis_image_regions = NULL((void*)0) ;
273 if ((*vis_regions = make_region_list( disp, srcRootWinid, &bbox,
274 &hasNonDefault, *numImageVisuals,
275 *pImageVisuals, allImage)) == NULL((void*)0))
276 return 0 ;
277
278 if (*transparentOverlays)
279 {
280 *allImage = 1; /* until proven otherwise,
281 this flags that it to be an image only list */
282 *vis_image_regions =
283 make_region_list( disp, srcRootWinid, &bbox, &hasNonDefault,
284 *numImageVisuals, *pImageVisuals, allImage);
285 }
286
287 /* if there is a second region in any of the two lists return 1 **/
288 if ( ( *vis_regions && (*vis_regions)->next && (*vis_regions)->next->next ) ||
289 ( *vis_image_regions && (*vis_image_regions)->next &&
290 (*vis_image_regions)->next->next ) ) return 1 ;
291 else return 0 ;
292
293}
294
295static void TransferImage(Display *disp, XImage *reg_image,
296 int srcw, int srch,
297 image_region_type *reg, XImage *target_image,
298 int dst_x, int dst_y)
299{
300 int i,j,old_pixel,new_pixel,red_ind,green_ind,blue_ind ;
301 XColor *colors;
302 int rShift,gShift,bShift;
303
304 (void) QueryColorMap(disp,reg->cmap,reg->vis,&colors,
305 &rShift,&gShift,&bShift) ;
306
307 switch (reg->vis->class) {
308 case TrueColor4 :
309 for(i=0 ; i < srch ; i++)
310 {
311 for(j=0 ; j < srcw ; j++)
312 {
313 old_pixel = XGetPixel(reg_image,j,i)((*((reg_image)->f.get_pixel))((reg_image), (j), (i))) ;
314
315 if( reg->vis->map_entries == 16) {
316
317 red_ind = (old_pixel & reg->vis->red_mask) >> rShift ;
318 green_ind = (old_pixel & reg->vis->green_mask) >> gShift ;
319 blue_ind = (old_pixel & reg->vis->blue_mask) >> bShift ;
320
321 new_pixel = (
322 ((colors[red_ind].red >> 8) << RED_SHIFT16)
323 |((colors[green_ind].green >> 8) << GREEN_SHIFT8)
324 |((colors[blue_ind].blue >> 8) << BLUE_SHIFT0)
325 );
326 }
327 else
328 new_pixel = old_pixel;
329
330 XPutPixel(target_image,dst_x+j, dst_y+i,new_pixel)((*((target_image)->f.put_pixel))((target_image), (dst_x+j
), (dst_y+i), (new_pixel)))
;
331
332 }
333 }
334 break;
335 case DirectColor5 :
336 for(i=0 ; i < srch ; i++)
337 {
338
339 for(j=0 ; j < srcw ; j++)
340 {
341 old_pixel = XGetPixel(reg_image,j,i)((*((reg_image)->f.get_pixel))((reg_image), (j), (i))) ;
342 red_ind = (old_pixel & reg->vis->red_mask) >> rShift ;
343 green_ind = (old_pixel & reg->vis->green_mask) >> gShift ;
344 blue_ind = (old_pixel & reg->vis->blue_mask) >> bShift ;
345
346 new_pixel = (
347 ((colors[red_ind].red >> 8) << RED_SHIFT16)
348 |((colors[green_ind].green >> 8) << GREEN_SHIFT8)
349 |((colors[blue_ind].blue >> 8) << BLUE_SHIFT0)
350 );
351 XPutPixel(target_image,dst_x+j, dst_y+i,new_pixel)((*((target_image)->f.put_pixel))((target_image), (dst_x+j
), (dst_y+i), (new_pixel)))
;
352
353 }
354 }
355 break;
356 default :
357 for(i=0 ; i < srch ; i++)
358 {
359 for(j=0 ; j < srcw ; j++)
360 {
361 old_pixel = XGetPixel(reg_image,j,i)((*((reg_image)->f.get_pixel))((reg_image), (j), (i))) ;
362
363 new_pixel = (
364 ((colors[old_pixel].red >> 8) << RED_SHIFT16)
365 |((colors[old_pixel].green >> 8) << GREEN_SHIFT8)
366 |((colors[old_pixel].blue >> 8) << BLUE_SHIFT0)
367 );
368 XPutPixel(target_image,dst_x+j, dst_y+i,new_pixel)((*((target_image)->f.put_pixel))((target_image), (dst_x+j
), (dst_y+i), (new_pixel)))
;
369
370 }
371 }
372 break;
373 }
374}
375
376static XImage *
377ReadRegionsInList(Display *disp, Visual *fakeVis, int depth, int format,
378 int width,int height,
379 XRectangle bbox, /* bounding box of grabbed area */
380 list_ptr regions) /* list of regions to read from */
381{
382 image_region_type *reg;
383 int dst_x, dst_y; /* where in pixmap to write (UL) */
384 int diff;
385
386 XImage *reg_image,*ximage ;
387 int srcRect_x,srcRect_y,srcRect_width,srcRect_height ;
388 int bytes_per_line;
389 int bitmap_unit;
390
391 bitmap_unit = sizeof (long);
392
393 ximage = XCreateImage(disp,fakeVis,depth,format,0,NULL((void*)0),width,height,
394 8,0) ;
395 bytes_per_line = ximage->bytes_per_line;
396
397 if (format == ZPixmap2)
398 ximage->data = malloc(height*bytes_per_line);
399 else
400 ximage->data = malloc(height*bytes_per_line*depth);
401
402 ximage->bits_per_pixel = depth; /** Valid only if format is ZPixmap ***/
403
404 for (reg = (image_region_type *) first_in_list( regions); reg;
405 reg = (image_region_type *) next_in_list( regions))
406 {
407 int rect;
408 struct my_XRegion *vis_reg;
409 vis_reg = (struct my_XRegion *)(reg->visible_region);
410 for (rect = 0;
411 rect < vis_reg->numRects;
412 rect++)
413 {
414 /** ------------------------------------------------------------------------
415 Intersect bbox with visible part of region giving src rect & output
416 location. Width is the min right side minus the max left side.
417 Similar for height. Offset src rect so x,y are relative to
418 origin of win, not the root-relative visible rect of win.
419 ------------------------------------------------------------------------ **/
420 srcRect_width = MIN( vis_reg->rects[rect].x2, bbox.width + bbox.x)((vis_reg->rects[rect].x2) < (bbox.width + bbox.x) ? vis_reg
->rects[rect].x2 : bbox.width + bbox.x)
-
421 MAX( vis_reg->rects[rect].x1, bbox.x)((vis_reg->rects[rect].x1) > (bbox.x) ? vis_reg->rects
[rect].x1 : bbox.x)
;
422 srcRect_height = MIN( vis_reg->rects[rect].y2, bbox.height + bbox.y)((vis_reg->rects[rect].y2) < (bbox.height + bbox.y) ? vis_reg
->rects[rect].y2 : bbox.height + bbox.y)
-
423 MAX( vis_reg->rects[rect].y1, bbox.y)((vis_reg->rects[rect].y1) > (bbox.y) ? vis_reg->rects
[rect].y1 : bbox.y)
;
424 diff = bbox.x - vis_reg->rects[rect].x1;
425 srcRect_x = MAX( 0, diff)((0) > (diff) ? 0 : diff) + (vis_reg->rects[rect].x1 - reg->x_rootrel - reg->border);
426 dst_x = MAX( 0, -diff)((0) > (-diff) ? 0 : -diff) ;
427 diff = bbox.y - vis_reg->rects[rect].y1;
428 srcRect_y = MAX( 0, diff)((0) > (diff) ? 0 : diff) + (vis_reg->rects[rect].y1 - reg->y_rootrel - reg->border);
429 dst_y = MAX( 0, -diff)((0) > (-diff) ? 0 : -diff) ;
430 reg_image = XGetImage(disp,reg->win,srcRect_x,srcRect_y,
431 srcRect_width,srcRect_height,AllPlanes((unsigned long)~0L),format) ;
432 TransferImage(disp,reg_image,srcRect_width,
433 srcRect_height,reg,ximage,dst_x,dst_y) ;
434 }
435 }
436 return ximage ;
437}
438
439
440/** ------------------------------------------------------------------------
441 ------------------------------------------------------------------------ **/
442
443XImage *ReadAreaToImage(Display *disp,
444 /* root win on which grab was done */
445 Window srcRootWinid,
446 /* root rel UL corner of bounding box of grab */
447 int x, int y,
448 /* size of bounding box of grab */
449 unsigned int width, unsigned int height,
450 int numVisuals, XVisualInfo *pVisuals,
451 int numOverlayVisuals, OverlayInfo *pOverlayVisuals,
452 int numImageVisuals, XVisualInfo **pImageVisuals,
453 /* list of regions to read from */
454 list_ptr vis_regions,
455 /* list of regions to read from */
456 list_ptr vis_image_regions,
457 int format, int allImage)
458{
459 image_region_type *reg;
460 XRectangle bbox; /* bounding box of grabbed area */
461 int depth ;
462 XImage *ximage, *ximage_ipm = NULL((void*)0);
463 Visual fakeVis ;
464 int x1, y1;
465 XImage *image;
466#if 0
467 unsigned char *pmData , *ipmData ;
468#endif
469 int transparentColor, transparentType;
470 int srcRect_x,srcRect_y,srcRect_width,srcRect_height ;
471 int diff ;
472 int dst_x, dst_y; /* where in pixmap to write (UL) */
473 int pixel;
474
475 bbox.x = x; /* init X rect for bounding box */
476 bbox.y = y;
477 bbox.width = width;
478 bbox.height = height;
479
480
481 initFakeVisual(&fakeVis) ;
482
483 depth = 24 ;
484 ximage = ReadRegionsInList(disp,&fakeVis,depth,format,width,height,
485 bbox,vis_regions) ;
486#if 0
487 pmData = (unsigned char *)ximage -> data ;
488#endif
489
490/* if transparency possible do it again, but this time for image planes only */
491 if (vis_image_regions && (vis_image_regions->next) && !allImage)
1
Taking false branch
492 {
493 ximage_ipm = ReadRegionsInList(disp,&fakeVis,depth,format,width,height,
494 bbox,vis_image_regions) ;
495#if 0
496 ipmData = (unsigned char *)ximage_ipm -> data ;
497#endif
498 }
499/* Now tranverse the overlay visual windows and test for transparency index. */
500/* If you find one, subsitute the value from the matching image plane pixmap. */
501
502 for (reg = (image_region_type *) first_in_list( vis_regions); reg;
2
Loop condition is true. Entering loop body
4
Loop condition is true. Entering loop body
6
Loop condition is true. Entering loop body
8
Loop condition is true. Entering loop body
503 reg = (image_region_type *) next_in_list( vis_regions))
504 {
505
506 if (src_in_overlay( reg, numOverlayVisuals, pOverlayVisuals,
3
Taking false branch
5
Taking false branch
7
Taking false branch
9
Taking true branch
507 &transparentColor, &transparentType))
508 {
509 int test = 0 ;
510 srcRect_width = MIN( reg->width + reg->x_vis, bbox.width + bbox.x)((reg->width + reg->x_vis) < (bbox.width + bbox.x) ?
reg->width + reg->x_vis : bbox.width + bbox.x)
511 - MAX( reg->x_vis, bbox.x)((reg->x_vis) > (bbox.x) ? reg->x_vis : bbox.x);
512 srcRect_height = MIN( reg->height + reg->y_vis, bbox.height((reg->height + reg->y_vis) < (bbox.height + bbox.y)
? reg->height + reg->y_vis : bbox.height + bbox.y)
513 + bbox.y)((reg->height + reg->y_vis) < (bbox.height + bbox.y)
? reg->height + reg->y_vis : bbox.height + bbox.y)
- MAX( reg->y_vis, bbox.y)((reg->y_vis) > (bbox.y) ? reg->y_vis : bbox.y);
514 diff = bbox.x - reg->x_vis;
515 srcRect_x = MAX( 0, diff)((0) > (diff) ? 0 : diff) + (reg->x_vis - reg->x_rootrel - reg->border);
10
Within the expansion of the macro 'MAX':
a
Assuming 'diff' is < 0
516 dst_x = MAX( 0, -diff)((0) > (-diff) ? 0 : -diff) ;
517 diff = bbox.y - reg->y_vis;
518 srcRect_y = MAX( 0, diff)((0) > (diff) ? 0 : diff) + (reg->y_vis - reg->y_rootrel - reg->border);
11
Within the expansion of the macro 'MAX':
a
Assuming 'diff' is < 0
519 dst_y = MAX( 0, -diff)((0) > (-diff) ? 0 : -diff) ;
520 /* let's test some pixels for transparency */
521 image = XGetImage(disp, reg->win, srcRect_x, srcRect_y,
522 srcRect_width, srcRect_height, 0xffffffff, ZPixmap2);
523
524 /* let's assume byte per pixel for overlay image for now */
525 if ((image->depth == 8) && (transparentType == TransparentPixel1))
12
Taking false branch
526 {
527 unsigned char *pixel_ptr;
528 unsigned char *start_of_line = (unsigned char *) image->data;
529
530 for (y1 = 0; y1 < srcRect_height; y1++) {
531 pixel_ptr = start_of_line;
532 for (x1 = 0; x1 < srcRect_width; x1++)
533 {
534 if (*pixel_ptr++ == transparentColor)
535 {
536#if 0
537 *pmData++ = *ipmData++;
538 *pmData++ = *ipmData++;
539 *pmData++ = *ipmData++;
540#endif
541 pixel = XGetPixel(ximage_ipm,dst_x+x1,dst_y+y1)((*((ximage_ipm)->f.get_pixel))((ximage_ipm), (dst_x+x1), (
dst_y+y1)))
;
542 XPutPixel(ximage,dst_x+x1, dst_y+y1,pixel)((*((ximage)->f.put_pixel))((ximage), (dst_x+x1), (dst_y+y1
), (pixel)))
;
543
544 if(!test){
545 test = 1 ;
546 }
547 }
548#if 0
549 else {
550 pmData +=3;
551 ipmData +=3;
552 }
553#endif
554 }
555 start_of_line += image->bytes_per_line;
556 }
557 } else {
558 if (transparentType == TransparentPixel1) {
13
Assuming 'transparentType' is equal to 1
14
Taking true branch
559 for (y1 = 0; y1 < srcRect_height; y1++) {
15
Assuming 'y1' is < 'srcRect_height'
16
Loop condition is true. Entering loop body
560 for (x1 = 0; x1 < srcRect_width; x1++)
17
Assuming 'x1' is < 'srcRect_width'
18
Loop condition is true. Entering loop body
561 {
562 int pixel_value = XGetPixel(image, x1, y1)((*((image)->f.get_pixel))((image), (x1), (y1)));
563 if (pixel_value == transparentColor)
19
Taking true branch
564 {
565#if 0
566 *pmData++ = *ipmData++;
567 *pmData++ = *ipmData++;
568 *pmData++ = *ipmData++;
569#endif
570 pixel = XGetPixel(ximage_ipm,dst_x+x1,dst_y+y1)((*((ximage_ipm)->f.get_pixel))((ximage_ipm), (dst_x+x1), (
dst_y+y1)))
;
20
Within the expansion of the macro 'XGetPixel':
a
Dereference of null pointer
571 XPutPixel(ximage,dst_x+x1, dst_y+y1,pixel)((*((ximage)->f.put_pixel))((ximage), (dst_x+x1), (dst_y+y1
), (pixel)))
;
572 if(!test){
573 test = 1 ;
574 }
575 }
576#if 0
577 else {
578 pmData +=3;
579 ipmData +=3;
580 }
581#endif
582 }
583 }
584 } else {
585 for (y1 = 0; y1 < srcRect_height; y1++) {
586 for (x1 = 0; x1 < srcRect_width; x1++)
587 {
588 int pixel_value = XGetPixel(image, x1, y1)((*((image)->f.get_pixel))((image), (x1), (y1)));
589 if (pixel_value & transparentColor)
590 {
591#if 0
592 *pmData++ = *ipmData++;
593 *pmData++ = *ipmData++;
594 *pmData++ = *ipmData++;
595#endif
596 pixel = XGetPixel(ximage_ipm,dst_x+x1,dst_y+y1)((*((ximage_ipm)->f.get_pixel))((ximage_ipm), (dst_x+x1), (
dst_y+y1)))
;
597 XPutPixel(ximage,dst_x+x1, dst_y+y1,pixel)((*((ximage)->f.put_pixel))((ximage), (dst_x+x1), (dst_y+y1
), (pixel)))
;
598 if(!test){
599 test = 1 ;
600 }
601 }
602#if 0
603 else {
604 pmData +=3;
605 ipmData +=3;
606 }
607#endif
608 }
609 }
610 }
611 }
612 XDestroyImage (image)((*((image)->f.destroy_image))((image)));
613 } /* end of src_in_overlay */
614 } /** end transparency **/
615 destroy_region_list( vis_regions);
616 if (vis_image_regions) destroy_region_list( vis_image_regions );
617 FreeXVisualInfo(pVisuals, pOverlayVisuals, pImageVisuals);
618 XSync(disp, 0);
619
620 return ximage;
621}
622
623/** ------------------------------------------------------------------------
624 Creates a list of the subwindows of a given window which have a
625 different visual than their parents. The function is recursive.
626 This list is used in make_region_list(), which coalesces the
627 windows with the same visual into a region.
628 image_wins must point to an existing list struct that's already
629 been zeroed (zero_list()).
630 ------------------------------------------------------------------------ **/
631static void make_src_list(Display *disp, list_ptr image_wins,
632 /* bnding box of area we want */
633 XRectangle *bbox,
634 Window curr,
635 /* pos of curr WRT root */
636 int x_rootrel, int y_rootrel,
637 XWindowAttributes *curr_attrs,
638 /* visible part of curr, not obscurred by ancestors */
639 XRectangle *pclip)
640{
641 XWindowAttributes child_attrs;
642 Window root, parent, *child; /* variables for XQueryTree() */
643 Window *save_child_list; /* variables for XQueryTree() */
644 unsigned int nchild; /* variables for XQueryTree() */
645 XRectangle child_clip; /* vis part of child */
646 int curr_clipX, curr_clipY, curr_clipRt, curr_clipBt;
647
648 /* check that win is mapped & not outside bounding box */
649 if (curr_attrs->map_state == IsViewable2 &&
650 curr_attrs->class == InputOutput1 &&
651 !( pclip->x >= (int) (bbox->x + bbox->width) ||
652 pclip->y >= (int) (bbox->y + bbox->height) ||
653 (int) (pclip->x + pclip->width) <= bbox->x ||
654 (int) (pclip->y + pclip->height) <= bbox->y)) {
655
656 XQueryTree( disp, curr, &root, &parent, &child, &nchild );
657 save_child_list = child; /* so we can free list when we're done */
658 add_window_to_list( image_wins, curr, x_rootrel, y_rootrel,
659 pclip->x, pclip->y,
660 pclip->width, pclip->height,
661 curr_attrs->border_width,curr_attrs->visual,
662 curr_attrs->colormap, parent);
663
664
665/** ------------------------------------------------------------------------
666 set RR coords of right (Rt), left (X), bottom (Bt) and top (Y)
667 of rect we clip all children by. This is our own clip rect (pclip)
668 inflicted on us by our parent plus our own borders. Within the
669 child loop, we figure the clip rect for each child by adding in
670 it's rectangle (not taking into account the child's borders).
671 ------------------------------------------------------------------------ **/
672 curr_clipX = MAX( pclip->x, x_rootrel + (int) curr_attrs->border_width)((pclip->x) > (x_rootrel + (int) curr_attrs->border_width
) ? pclip->x : x_rootrel + (int) curr_attrs->border_width
)
;
673 curr_clipY = MAX( pclip->y, y_rootrel + (int) curr_attrs->border_width)((pclip->y) > (y_rootrel + (int) curr_attrs->border_width
) ? pclip->y : y_rootrel + (int) curr_attrs->border_width
)
;
674 curr_clipRt = MIN( pclip->x + (int) pclip->width,((pclip->x + (int) pclip->width) < (x_rootrel + (int
) curr_attrs->width + 2 * (int) curr_attrs->border_width
) ? pclip->x + (int) pclip->width : x_rootrel + (int) curr_attrs
->width + 2 * (int) curr_attrs->border_width)
675 x_rootrel + (int) curr_attrs->width +((pclip->x + (int) pclip->width) < (x_rootrel + (int
) curr_attrs->width + 2 * (int) curr_attrs->border_width
) ? pclip->x + (int) pclip->width : x_rootrel + (int) curr_attrs
->width + 2 * (int) curr_attrs->border_width)
676 2 * (int) curr_attrs->border_width)((pclip->x + (int) pclip->width) < (x_rootrel + (int
) curr_attrs->width + 2 * (int) curr_attrs->border_width
) ? pclip->x + (int) pclip->width : x_rootrel + (int) curr_attrs
->width + 2 * (int) curr_attrs->border_width)
;
677 curr_clipBt = MIN( pclip->y + (int) pclip->height,((pclip->y + (int) pclip->height) < (y_rootrel + (int
) curr_attrs->height + 2 * (int) curr_attrs->border_width
) ? pclip->y + (int) pclip->height : y_rootrel + (int) curr_attrs
->height + 2 * (int) curr_attrs->border_width)
678 y_rootrel + (int) curr_attrs->height +((pclip->y + (int) pclip->height) < (y_rootrel + (int
) curr_attrs->height + 2 * (int) curr_attrs->border_width
) ? pclip->y + (int) pclip->height : y_rootrel + (int) curr_attrs
->height + 2 * (int) curr_attrs->border_width)
679 2 * (int) curr_attrs->border_width)((pclip->y + (int) pclip->height) < (y_rootrel + (int
) curr_attrs->height + 2 * (int) curr_attrs->border_width
) ? pclip->y + (int) pclip->height : y_rootrel + (int) curr_attrs
->height + 2 * (int) curr_attrs->border_width)
;
680
681 while (nchild--) {
682 int new_width, new_height;
683 int child_xrr, child_yrr; /* root relative x & y of child */
684
685 XGetWindowAttributes( disp, *child, &child_attrs);
686
687 /* intersect parent & child clip rects */
688 child_xrr = x_rootrel + child_attrs.x + curr_attrs->border_width;
689 child_clip.x = MAX( curr_clipX, child_xrr)((curr_clipX) > (child_xrr) ? curr_clipX : child_xrr);
690 new_width = MIN( curr_clipRt, child_xrr + (int) child_attrs.width((curr_clipRt) < (child_xrr + (int) child_attrs.width + 2 *
child_attrs.border_width) ? curr_clipRt : child_xrr + (int) child_attrs
.width + 2 * child_attrs.border_width)
691 + 2 * child_attrs.border_width)((curr_clipRt) < (child_xrr + (int) child_attrs.width + 2 *
child_attrs.border_width) ? curr_clipRt : child_xrr + (int) child_attrs
.width + 2 * child_attrs.border_width)
692 - child_clip.x;
693 if (new_width >= 0) {
694 child_clip.width = new_width;
695
696 child_yrr = y_rootrel + child_attrs.y +
697 curr_attrs->border_width;
698 child_clip.y = MAX( curr_clipY, child_yrr)((curr_clipY) > (child_yrr) ? curr_clipY : child_yrr);
699 new_height = MIN( curr_clipBt,((curr_clipBt) < (child_yrr + (int) child_attrs.height + 2
* child_attrs.border_width) ? curr_clipBt : child_yrr + (int
) child_attrs.height + 2 * child_attrs.border_width)
700 child_yrr + (int) child_attrs.height +((curr_clipBt) < (child_yrr + (int) child_attrs.height + 2
* child_attrs.border_width) ? curr_clipBt : child_yrr + (int
) child_attrs.height + 2 * child_attrs.border_width)
701 2 * child_attrs.border_width)((curr_clipBt) < (child_yrr + (int) child_attrs.height + 2
* child_attrs.border_width) ? curr_clipBt : child_yrr + (int
) child_attrs.height + 2 * child_attrs.border_width)
702 - child_clip.y;
703 if (new_height >= 0) {
704 child_clip.height = new_height;
705 make_src_list( disp, image_wins, bbox, *child,
706 child_xrr, child_yrr,
707 &child_attrs, &child_clip);
708 }
709 }
710 child++;
711 }
712 XFree( save_child_list);
713 }
714}
715
716
717/** ------------------------------------------------------------------------
718 This function creates a list of regions which tile a specified
719 window. Each region contains all visible portions of the window
720 which are drawn with the same visual. For example, if the
721 window consists of subwindows of two different visual types,
722 there will be two regions in the list.
723 Returns a pointer to the list.
724 ------------------------------------------------------------------------ **/
725static list_ptr make_region_list(Display *disp, Window win, XRectangle *bbox,
726 int *hasNonDefault, int numImageVisuals,
727 XVisualInfo **pImageVisuals, int *allImage)
728{
729 XWindowAttributes win_attrs;
730 list image_wins;
731 list_ptr image_regions;
732 list_ptr srcs_left;
733 image_region_type *new_reg;
734 image_win_type *base_src, *src;
735 Region bbox_region = XCreateRegion();
736 XRectangle clip;
737 int image_only;
738
739 int count=0 ;
740
741 *hasNonDefault = False0;
742 XUnionRectWithRegion( bbox, bbox_region, bbox_region);
743 XGetWindowAttributes( disp, win, &win_attrs);
744
745 zero_list( &image_wins);
746 clip.x = 0;
747 clip.y = 0;
748 clip.width = win_attrs.width;
749 clip.height = win_attrs.height;
750 make_src_list( disp, &image_wins, bbox, win,
751 0 /* x_rootrel */, 0 /* y_rootrel */, &win_attrs, &clip);
752
753 image_regions = new_list();
754 image_only = (*allImage) ? True1:False0;
755
756 for (base_src = (image_win_type *) first_in_list( &image_wins); base_src;
757 base_src = (image_win_type *) next_in_list( &image_wins))
758 {
759 /* test for image visual */
760 if (!image_only || src_in_image(base_src, numImageVisuals, pImageVisuals))
761 {
762 /* find a window whose visual hasn't been put in list yet */
763 if (!src_in_region_list( base_src, image_regions))
764 {
765 if (! (new_reg = (image_region_type *)
766 malloc( sizeof( image_region_type)))) {
767 return (list_ptr) NULL((void*)0);
768 }
769 count++;
770
771 new_reg->visible_region = XCreateRegion();
772 new_reg->win = base_src->win;
773 new_reg->vis = base_src->vis;
774 new_reg->cmap = base_src->cmap;
775 new_reg->x_rootrel = base_src->x_rootrel;
776 new_reg->y_rootrel = base_src->y_rootrel;
777 new_reg->x_vis = base_src->x_vis;
778 new_reg->y_vis = base_src->y_vis;
779 new_reg->width = base_src->width;
780 new_reg->height = base_src->height;
781 new_reg->border = base_src->border_width;
782
783 srcs_left = (list_ptr) dup_list_head( &image_wins, START_AT_CURR1);
784 for (src = (image_win_type *) first_in_list( srcs_left); src;
785 src = (image_win_type *) next_in_list( srcs_left)) {
786 if (SAME_REGIONS( base_src, src)((base_src)->vis == (src)->vis && (base_src)->
cmap == (src)->cmap && (base_src)->x_vis <= (
src)->x_vis && (base_src)->y_vis <= (src)->
y_vis && (base_src)->x_vis + (base_src)->width >=
(src)->x_vis + (src)->width && (base_src)->
y_vis + (base_src)->height >= (src)->y_vis + (src)->
height)
) {
787 add_rect_to_image_region( new_reg, src->x_vis, src->y_vis,
788 src->width, src->height);
789 }
790 else {
791 if (!image_only || src_in_image(src, numImageVisuals, pImageVisuals))
792 {
793 subtr_rect_from_image_region( new_reg, src->x_vis,
794 src->y_vis, src->width, src->height);
795 }
796 }
797 }
798 XIntersectRegion( bbox_region, new_reg->visible_region,
799 new_reg->visible_region);
800 if (! XEmptyRegion( new_reg->visible_region)) {
801 add_to_list( image_regions, new_reg);
802 if (new_reg->vis != DefaultVisualOfScreen( win_attrs.screen)((win_attrs.screen)->root_visual) ||
803 new_reg->cmap != DefaultColormapOfScreen(((win_attrs.screen)->cmap)
804 win_attrs.screen)((win_attrs.screen)->cmap)) {
805 *hasNonDefault = True1;
806 }
807 }
808 else {
809 XDestroyRegion( new_reg->visible_region);
810 free( (void *) new_reg);
811 }
812 }
813 } else *allImage = 0;
814 }
815 delete_list( &image_wins, True1);
816 XDestroyRegion( bbox_region);
817 return image_regions;
818}
819/** ------------------------------------------------------------------------
820 Destructor called from destroy_region_list().
821 ------------------------------------------------------------------------ **/
822static void destroy_image_region(image_region_type *image_region)
823{
824 XDestroyRegion( image_region->visible_region);
825 free( (void *) image_region);
826}
827
828/** ------------------------------------------------------------------------
829 Destroys the region list, destroying all the regions contained in it.
830 ------------------------------------------------------------------------ **/
831static void destroy_region_list(list_ptr rlist)
832{
833 delete_list_destroying( rlist, (DESTRUCT_FUNC_PTR)destroy_image_region);
834}
835
836
837/** ------------------------------------------------------------------------
838 Subtracts the specified rectangle from the region in image_region.
839 First converts the rectangle to a region of its own, since X
840 only provides a way to subtract one region from another, not a
841 rectangle from a region.
842 ------------------------------------------------------------------------ **/
843static void subtr_rect_from_image_region(image_region_type *image_region,
844 int x, int y, int width, int height)
845{
846 XRectangle rect;
847 Region rect_region;
848
849 rect_region = XCreateRegion();
850 rect.x = x;
851 rect.y = y;
852 rect.width = width;
853 rect.height = height;
854 XUnionRectWithRegion( &rect, rect_region, rect_region);
855 XSubtractRegion( image_region->visible_region, rect_region,
856 image_region->visible_region);
857 XDestroyRegion( rect_region);
858}
859
860
861/** ------------------------------------------------------------------------
862 Adds the specified rectangle to the region in image_region.
863 ------------------------------------------------------------------------ **/
864static void add_rect_to_image_region(image_region_type *image_region,
865 int x, int y, int width, int height)
866{
867 XRectangle rect;
868
869 rect.x = x;
870 rect.y = y;
871 rect.width = width;
872 rect.height = height;
873 XUnionRectWithRegion( &rect, image_region->visible_region,
874 image_region->visible_region);
875}
876
877
878/** ------------------------------------------------------------------------
879 Returns TRUE if the given src's visual is already represented in
880 the image_regions list, FALSE otherwise.
881 ------------------------------------------------------------------------ **/
882static int src_in_region_list(image_win_type *src, list_ptr image_regions)
883{
884 image_region_type *ir;
885
886 for (ir = (image_region_type *) first_in_list( image_regions); ir;
887 ir = (image_region_type *) next_in_list( image_regions)) {
888 if (SAME_REGIONS( ir, src)((ir)->vis == (src)->vis && (ir)->cmap == (src
)->cmap && (ir)->x_vis <= (src)->x_vis &&
(ir)->y_vis <= (src)->y_vis && (ir)->x_vis
+ (ir)->width >= (src)->x_vis + (src)->width &&
(ir)->y_vis + (ir)->height >= (src)->y_vis + (src
)->height)
) {
889
890 return 1;
891 }
892 }
893
894 return 0;
895}
896
897
898/** ------------------------------------------------------------------------
899 Makes a new entry in image_wins with the given fields filled in.
900 ------------------------------------------------------------------------ **/
901static void add_window_to_list(list_ptr image_wins, Window w,
902 int xrr, int yrr, int x_vis, int y_vis,
903 int width, int height, int border_width,
904 Visual *vis, Colormap cmap, Window parent)
905{
906 image_win_type *new_src;
907
908 if ((new_src = (image_win_type *) malloc( sizeof( image_win_type))) == NULL((void*)0))
909
910 return;
911
912 new_src->win = w;
913 new_src->x_rootrel = xrr;
914 new_src->y_rootrel = yrr;
915 new_src->x_vis = x_vis;
916 new_src->y_vis = y_vis;
917 new_src->width = width;
918 new_src->height = height;
919 new_src->border_width = border_width;
920 new_src->vis = vis;
921 new_src->cmap = cmap;
922 new_src->parent = parent;
923 add_to_list( image_wins, new_src);
924}
925
926/** ------------------------------------------------------------------------
927 Returns TRUE if the given src's visual is in the image planes,
928 FALSE otherwise.
929 ------------------------------------------------------------------------ **/
930static int src_in_image(image_win_type *src, int numImageVisuals,
931 XVisualInfo **pImageVisuals)
932{
933 int i;
934
935 for (i = 0 ; i < numImageVisuals ; i++)
936 {
937 if (pImageVisuals[i]->visual == src->vis)
938 return 1;
939 }
940 return 0;
941}
942
943
944/** ------------------------------------------------------------------------
945 Returns TRUE if the given src's visual is in the overlay planes
946 and transparency is possible, FALSE otherwise.
947 ------------------------------------------------------------------------ **/
948static int src_in_overlay(image_region_type *src, int numOverlayVisuals,
949 OverlayInfo *pOverlayVisuals,
950 int *transparentColor, int *transparentType)
951{
952 int i;
953
954 for (i = 0 ; i < numOverlayVisuals ; i++)
955 {
956 if (((pOverlayVisuals[i].pOverlayVisualInfo)->visual == src->vis)
957 && (pOverlayVisuals[i].transparentType != None0L))
958 {
959 *transparentColor = pOverlayVisuals[i].value;
960 *transparentType = pOverlayVisuals[i].transparentType;
961 return 1;
962 }
963
964 else {
965 }
966
967 }
968 return 0;
969}
970
971
972/********************** from wsutils.c ******************************/
973
974/******************************************************************************
975 *
976 * This file contains a set of example utility procedures; procedures that can
977 * help a "window-smart" Starbase or PHIGS program determine information about
978 * a device, and create image and overlay plane windows. To use these
979 * utilities, #include "wsutils.h" and compile this file and link the results
980 * with your program.
981 *
982 ******************************************************************************/
983
984
985
986#define STATIC_GRAY0x01 0x01
987#define GRAY_SCALE0x02 0x02
988#define PSEUDO_COLOR0x04 0x04
989#define TRUE_COLOR0x10 0x10
990#define DIRECT_COLOR0x11 0x11
991
992
993static int weCreateServerOverlayVisualsProperty = False0;
994
995
996/******************************************************************************
997 *
998 * GetXVisualInfo()
999 *
1000 * This routine takes an X11 Display, screen number, and returns whether the
1001 * screen supports transparent overlays and three arrays:
1002 *
1003 * 1) All of the XVisualInfo struct's for the screen.
1004 * 2) All of the OverlayInfo struct's for the screen.
1005 * 3) An array of pointers to the screen's image plane XVisualInfo
1006 * structs.
1007 *
1008 * The code below obtains the array of all the screen's visuals, and obtains
1009 * the array of all the screen's overlay visual information. It then processes
1010 * the array of the screen's visuals, determining whether the visual is an
1011 * overlay or image visual.
1012 *
1013 * If the routine sucessfully obtained the visual information, it returns zero.
1014 * If the routine didn't obtain the visual information, it returns non-zero.
1015 *
1016 ******************************************************************************/
1017
1018int GetXVisualInfo(/* Which X server (aka "display"). */
1019 Display *display,
1020 /* Which screen of the "display". */
1021 int screen,
1022 /* Non-zero if there's at least one overlay visual and
1023 * if at least one of those supports a transparent pixel. */
1024 int *transparentOverlays,
1025 /* Number of XVisualInfo struct's pointed to by pVisuals. */
1026 int *numVisuals,
1027 /* All of the device's visuals. */
1028 XVisualInfo **pVisuals,
1029 /* Number of OverlayInfo's pointed to by pOverlayVisuals.
1030 * If this number is zero, the device does not have
1031 * overlay planes. */
1032 int *numOverlayVisuals,
1033 /* The device's overlay plane visual information. */
1034 OverlayInfo **pOverlayVisuals,
1035 /* Number of XVisualInfo's pointed to by pImageVisuals. */
1036 int *numImageVisuals,
1037 /* The device's image visuals. */
1038 XVisualInfo ***pImageVisuals)
1039{
1040 XVisualInfo getVisInfo; /* Paramters of XGetVisualInfo */
1041 int mask;
1042 XVisualInfo *pVis, **pIVis; /* Faster, local copies */
1043 OverlayInfo *pOVis;
1044 OverlayVisualPropertyRec *pOOldVis;
1045 int nVisuals, nOVisuals;
1046 Atom overlayVisualsAtom; /* Parameters for XGetWindowProperty */
1047 Atom actualType;
1048 unsigned long numLongs, bytesAfter;
1049 int actualFormat;
1050 int nImageVisualsAlloced; /* Values to process the XVisualInfo */
1051 int imageVisual; /* array */
1052
1053
1054 /* First, get the list of visuals for this screen. */
1055 getVisInfo.screen = screen;
1056 mask = VisualScreenMask0x2;
1057
1058 *pVisuals = XGetVisualInfo(display, mask, &getVisInfo, numVisuals);
1059 if ((nVisuals = *numVisuals) <= 0)
1060 {
1061 /* Return that the information wasn't sucessfully obtained: */
1062 return(1);
1063 }
1064 pVis = *pVisuals;
1065
1066
1067 /* Now, get the overlay visual information for this screen. To obtain
1068 * this information, get the SERVER_OVERLAY_VISUALS property.
1069 */
1070 overlayVisualsAtom = XInternAtom(display, "SERVER_OVERLAY_VISUALS", True1);
1071 if (overlayVisualsAtom != None0L)
1072 {
1073 /* Since the Atom exists, we can request the property's contents. The
1074 * do-while loop makes sure we get the entire list from the X server.
1075 */
1076 bytesAfter = 0;
1077 numLongs = sizeof(OverlayVisualPropertyRec) / sizeof(long);
1078 do
1079 {
1080 numLongs += bytesAfter * sizeof(long);
1081 XGetWindowProperty(display, RootWindow(display, screen)((&((_XPrivDisplay)display)->screens[screen])->root
)
,
1082 overlayVisualsAtom, 0, numLongs, False0,
1083 overlayVisualsAtom, &actualType, &actualFormat,
1084 &numLongs, &bytesAfter, (unsigned char**) pOverlayVisuals);
1085 } while (bytesAfter > 0);
1086
1087
1088 /* Calculate the number of overlay visuals in the list. */
1089 *numOverlayVisuals = numLongs / (sizeof(OverlayVisualPropertyRec) / sizeof(long));
1090 }
1091 else
1092 {
1093 /* This screen doesn't have overlay planes. */
1094 *numOverlayVisuals = 0;
1095 *pOverlayVisuals = NULL((void*)0);
1096 *transparentOverlays = 0;
1097 }
1098
1099
1100 /* Process the pVisuals array. */
1101 *numImageVisuals = 0;
1102 nImageVisualsAlloced = 1;
1103 pIVis = *pImageVisuals = (XVisualInfo **) malloc(sizeof(XVisualInfo *));
1104 while (--nVisuals >= 0)
1105 {
1106 nOVisuals = *numOverlayVisuals;
1107 pOVis = *pOverlayVisuals;
1108 imageVisual = True1;
1109 while (--nOVisuals >= 0)
1110 {
1111 pOOldVis = (OverlayVisualPropertyRec *) pOVis;
1112 if (pVis->visualid == pOOldVis->visualID)
1113 {
1114 imageVisual = False0;
1115 pOVis->pOverlayVisualInfo = pVis;
1116 if (pOVis->transparentType == TransparentPixel1)
1117 *transparentOverlays = 1;
1118 }
1119 pOVis++;
1120 }
1121 if (imageVisual)
1122 {
1123 if ((*numImageVisuals += 1) > nImageVisualsAlloced)
1124 {
1125 nImageVisualsAlloced++;
1126 *pImageVisuals = (XVisualInfo **)
1127 realloc(*pImageVisuals, (nImageVisualsAlloced * sizeof(XVisualInfo *)));
1128 pIVis = *pImageVisuals + (*numImageVisuals - 1);
1129 }
1130 *pIVis++ = pVis;
1131 }
1132 pVis++;
1133 }
1134
1135
1136 /* Return that the information was sucessfully obtained: */
1137 return(0);
1138
1139} /* GetXVisualInfo() */
1140
1141
1142/******************************************************************************
1143 *
1144 * FreeXVisualInfo()
1145 *
1146 * This routine frees the data that was allocated by GetXVisualInfo().
1147 *
1148 ******************************************************************************/
1149
1150void FreeXVisualInfo(XVisualInfo *pVisuals, OverlayInfo *pOverlayVisuals,
1151 XVisualInfo **pImageVisuals)
1152{
1153 XFree(pVisuals);
1154 if (weCreateServerOverlayVisualsProperty)
1155 free(pOverlayVisuals);
1156 else
1157 XFree(pOverlayVisuals);
1158 free(pImageVisuals);
1159
1160} /* FreeXVisualInfo() */