1 dawes 3.15 /* $Xorg: InitOutput.c,v 1.3 2000/08/17 19:48:38 cpqbld Exp $ */
|
2 dawes 1.1 /*
3
|
4 dawes 3.9 Copyright 1993, 1998 The Open Group
|
5 dawes 1.1
|
6 dawes 3.9 All Rights Reserved.
|
7 dawes 1.1
8 The above copyright notice and this permission notice shall be included
9 in all copies or substantial portions of the Software.
10
11 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
12 OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
13 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
14 dawes 3.9 IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR
|
15 dawes 1.1 OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
16 ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
17 OTHER DEALINGS IN THE SOFTWARE.
18
|
19 dawes 3.9 Except as contained in this notice, the name of The Open Group shall
|
20 dawes 1.1 not be used in advertising or otherwise to promote the sale, use or
21 other dealings in this Software without prior written authorization
|
22 dawes 3.9 from The Open Group.
|
23 dawes 1.1
24 */
|
25 herrb 3.16 /* $XFree86: xc/programs/Xserver/hw/vfb/InitOutput.c,v 3.15 2001/01/17 22:36:54 dawes Exp $ */
|
26 dawes 1.1
|
27 dawes 3.12 #if defined(WIN32) && !defined(__CYGWIN__)
|
28 dawes 3.4 #include <X11/Xwinsock.h>
29 #endif
|
30 dawes 1.1 #include <stdio.h>
31 #include "X11/X.h"
32 #define NEED_EVENTS
33 #include "X11/Xproto.h"
34 #include "X11/Xos.h"
35 #include "scrnintstr.h"
36 #include "servermd.h"
37 #define PSZ 8
|
38 eich 3.14 #include "fb.h"
|
39 dawes 1.1 #include "mibstore.h"
40 #include "colormapst.h"
41 #include "gcstruct.h"
42 #include "input.h"
43 #include "mipointer.h"
44 #include <sys/types.h>
45 #ifdef HAS_MMAP
46 #include <sys/mman.h>
47 #ifndef MAP_FILE
48 #define MAP_FILE 0
49 #endif
50 #endif /* HAS_MMAP */
51 #include <sys/stat.h>
52 #include <errno.h>
|
53 dawes 3.4 #ifndef WIN32
|
54 dawes 1.1 #include <sys/param.h>
|
55 dawes 3.4 #endif
|
56 dawes 1.1 #include <X11/XWDFile.h>
57 #ifdef HAS_SHM
|
58 dawes 3.12 #ifndef __CYGWIN__
|
59 dawes 1.1 #include <sys/ipc.h>
|
60 dawes 3.12 #else
61 #include <sys/cygipc.h>
62 #endif
|
63 dawes 1.1 #include <sys/shm.h>
64 #endif /* HAS_SHM */
65 #include "dix.h"
|
66 dawes 3.0 #include "miline.h"
|
67 dawes 1.1
|
68 dawes 3.12 #ifdef __CYGWIN__
69 /*
70 * NT UX defines/includes
71 */
72 #include <sys/mman.h>
73
74 #define HAS_MMAP 1
75
76 extern char *get_surf( unsigned long size );
77 extern char *get_framebuf( unsigned long size );
78 extern int enable_ntux_xf( );
79 #endif /* __CYGWIN__ */
80
|
81 dawes 1.1 extern char *display;
82
83 #define VFB_DEFAULT_WIDTH 1280
84 #define VFB_DEFAULT_HEIGHT 1024
85 #define VFB_DEFAULT_DEPTH 8
86 #define VFB_DEFAULT_WHITEPIXEL 0
87 #define VFB_DEFAULT_BLACKPIXEL 1
|
88 dawes 3.0 #define VFB_DEFAULT_LINEBIAS 0
|
89 dawes 1.1 #define XWD_WINDOW_NAME_LEN 60
90
91 typedef struct
92 {
93 int scrnum;
94 int width;
95 int paddedWidth;
96 int height;
97 int depth;
98 int bitsPerPixel;
99 int sizeInBytes;
100 int ncolors;
101 char *pfbMemory;
102 XWDColor *pXWDCmap;
103 XWDFileHeader *pXWDHeader;
104 Pixel blackPixel;
105 Pixel whitePixel;
|
106 dawes 3.0 unsigned int lineBias;
|
107 dawes 1.1
108 #ifdef HAS_MMAP
109 int mmap_fd;
110 char mmap_file[MAXPATHLEN];
111 #endif
112
113 #ifdef HAS_SHM
114 int shmid;
115 #endif
116 } vfbScreenInfo, *vfbScreenInfoPtr;
117
118 static int vfbNumScreens;
119 static vfbScreenInfo vfbScreens[MAXSCREENS];
120 static Bool vfbPixmapDepths[33];
121 static char *pfbdir = NULL;
122 typedef enum { NORMAL_MEMORY_FB, SHARED_MEMORY_FB, MMAPPED_FILE_FB } fbMemType;
123 static fbMemType fbmemtype = NORMAL_MEMORY_FB;
124 static char needswap = 0;
125 static int lastScreen = -1;
126
|
127 dawes 3.12 #ifdef __CYGWIN__
128 static int b_video_memory = 0;
129 #endif
130
|
131 dawes 1.1 #define swapcopy16(_dst, _src) \
132 if (needswap) { CARD16 _s = _src; cpswaps(_s, _dst); } \
133 else _dst = _src;
134
135 #define swapcopy32(_dst, _src) \
136 if (needswap) { CARD32 _s = _src; cpswapl(_s, _dst); } \
137 else _dst = _src;
138
139
140 static void
141 vfbInitializePixmapDepths()
142 {
143 int i;
144 vfbPixmapDepths[1] = TRUE; /* always need bitmaps */
145 for (i = 2; i <= 32; i++)
146 vfbPixmapDepths[i] = FALSE;
147 }
148
149 static void
150 vfbInitializeDefaultScreens()
151 {
152 dawes 1.1 int i;
153
154 for (i = 0; i < MAXSCREENS; i++)
155 {
156 vfbScreens[i].scrnum = i;
157 vfbScreens[i].width = VFB_DEFAULT_WIDTH;
158 vfbScreens[i].height = VFB_DEFAULT_HEIGHT;
159 vfbScreens[i].depth = VFB_DEFAULT_DEPTH;
160 vfbScreens[i].blackPixel = VFB_DEFAULT_BLACKPIXEL;
161 vfbScreens[i].whitePixel = VFB_DEFAULT_WHITEPIXEL;
|
162 dawes 3.0 vfbScreens[i].lineBias = VFB_DEFAULT_LINEBIAS;
|
163 dawes 1.1 vfbScreens[i].pfbMemory = NULL;
164 }
165 vfbNumScreens = 1;
166 }
167
168 static int
169 vfbBitsPerPixel(depth)
170 int depth;
171 {
172 if (depth == 1) return 1;
173 else if (depth <= 8) return 8;
174 else if (depth <= 16) return 16;
175 else return 32;
176 }
177
178 void
179 ddxGiveUp()
180 {
181 int i;
182
183 /* clean up the framebuffers */
184 dawes 1.1
185 switch (fbmemtype)
186 {
187 #ifdef HAS_MMAP
188 case MMAPPED_FILE_FB:
189 for (i = 0; i < vfbNumScreens; i++)
190 {
191 if (-1 == unlink(vfbScreens[i].mmap_file))
192 {
193 perror("unlink");
194 ErrorF("unlink %s failed, errno %d",
195 vfbScreens[i].mmap_file, errno);
196 }
197 }
198 break;
199 #endif /* HAS_MMAP */
200
201 #ifdef HAS_SHM
202 case SHARED_MEMORY_FB:
203 for (i = 0; i < vfbNumScreens; i++)
204 {
205 dawes 1.1 if (-1 == shmdt((char *)vfbScreens[i].pXWDHeader))
206 {
207 perror("shmdt");
208 ErrorF("shmdt failed, errno %d", errno);
209 }
210 }
211 break;
212 #endif /* HAS_SHM */
213
214 case NORMAL_MEMORY_FB:
215 for (i = 0; i < vfbNumScreens; i++)
216 {
|
217 dawes 3.12 #ifdef __CYGWIN__
218 if (!b_video_memory)
219 #endif
|
220 dawes 1.1 Xfree(vfbScreens[i].pXWDHeader);
221 }
222 break;
223 }
224 }
225
226 void
227 AbortDDX()
228 {
229 ddxGiveUp();
230 }
|
231 herrb 3.16
232 #ifdef __DARWIN__
233 void
234 DarwinHandleGUI(int argc, char *argv[])
235 {
236 }
237 #endif
|
238 dawes 1.1
239 void
240 OsVendorInit()
241 {
242 }
243
244 void
|
245 dawes 3.2 OsVendorFatalError()
246 {
247 }
248
249 void
|
250 dawes 1.1 ddxUseMsg()
251 {
252 ErrorF("-screen scrn WxHxD set screen's width, height, depth\n");
253 ErrorF("-pixdepths list-of-int support given pixmap depths\n");
|
254 dawes 3.0 ErrorF("-linebias n adjust thin line pixelization\n");
|
255 dawes 3.4 ErrorF("-blackpixel n pixel value for black\n");
256 ErrorF("-whitepixel n pixel value for white\n");
|
257 dawes 1.1
258 #ifdef HAS_MMAP
259 ErrorF("-fbdir directory put framebuffers in mmap'ed files in directory\n");
260 #endif
261
262 #ifdef HAS_SHM
263 ErrorF("-shmem put framebuffers in shared memory\n");
264 #endif
265 }
266
267 int
268 ddxProcessArgument (argc, argv, i)
269 int argc;
270 char *argv[];
271 int i;
272 {
273 static Bool firstTime = TRUE;
274
275 if (firstTime)
276 {
277 vfbInitializeDefaultScreens();
278 dawes 1.1 vfbInitializePixmapDepths();
279 firstTime = FALSE;
280 }
281
282 if (strcmp (argv[i], "-screen") == 0) /* -screen n WxHxD */
283 {
284 int screenNum;
285 if (i + 2 >= argc) UseMsg();
286 screenNum = atoi(argv[i+1]);
287 if (screenNum < 0 || screenNum >= MAXSCREENS)
288 {
289 ErrorF("Invalid screen number %d\n", screenNum);
290 UseMsg();
291 }
292 if (3 != sscanf(argv[i+2], "%dx%dx%d",
293 &vfbScreens[screenNum].width,
294 &vfbScreens[screenNum].height,
295 &vfbScreens[screenNum].depth))
296 {
297 ErrorF("Invalid screen configuration %s\n", argv[i+2]);
298 UseMsg();
299 dawes 1.1 }
300
301 if (screenNum >= vfbNumScreens)
302 vfbNumScreens = screenNum + 1;
303 lastScreen = screenNum;
304 return 3;
305 }
306
307 if (strcmp (argv[i], "-pixdepths") == 0) /* -pixdepths list-of-depth */
308 {
309 int depth, ret = 1;
310
311 if (++i >= argc) UseMsg();
312 while ((i < argc) && (depth = atoi(argv[i++])) != 0)
313 {
314 if (depth < 0 || depth > 32)
315 {
316 ErrorF("Invalid pixmap depth %d\n", depth);
317 UseMsg();
318 }
319 vfbPixmapDepths[depth] = TRUE;
320 dawes 1.1 ret++;
321 }
322 return ret;
323 }
324
325 if (strcmp (argv[i], "-blackpixel") == 0) /* -blackpixel n */
326 {
327 Pixel pix;
328 if (++i >= argc) UseMsg();
329 pix = atoi(argv[i]);
330 if (-1 == lastScreen)
331 {
332 int i;
333 for (i = 0; i < MAXSCREENS; i++)
334 {
335 vfbScreens[i].blackPixel = pix;
336 }
337 }
338 else
339 {
340 vfbScreens[lastScreen].blackPixel = pix;
341 dawes 1.1 }
342 return 2;
343 }
344
345 if (strcmp (argv[i], "-whitepixel") == 0) /* -whitepixel n */
346 {
347 Pixel pix;
348 if (++i >= argc) UseMsg();
349 pix = atoi(argv[i]);
350 if (-1 == lastScreen)
351 {
352 int i;
353 for (i = 0; i < MAXSCREENS; i++)
354 {
355 vfbScreens[i].whitePixel = pix;
356 }
357 }
358 else
359 {
360 vfbScreens[lastScreen].whitePixel = pix;
361 }
362 dawes 1.1 return 2;
363 }
364
|
365 dawes 3.0 if (strcmp (argv[i], "-linebias") == 0) /* -linebias n */
366 {
367 unsigned int linebias;
368 if (++i >= argc) UseMsg();
369 linebias = atoi(argv[i]);
370 if (-1 == lastScreen)
371 {
372 int i;
373 for (i = 0; i < MAXSCREENS; i++)
374 {
375 vfbScreens[i].lineBias = linebias;
376 }
377 }
378 else
379 {
380 vfbScreens[lastScreen].lineBias = linebias;
381 }
382 return 2;
383 }
|
384 dawes 1.1
385 #ifdef HAS_MMAP
386 if (strcmp (argv[i], "-fbdir") == 0) /* -fbdir directory */
387 {
388 if (++i >= argc) UseMsg();
389 pfbdir = argv[i];
390 fbmemtype = MMAPPED_FILE_FB;
391 return 2;
392 }
393 #endif /* HAS_MMAP */
394
395 #ifdef HAS_SHM
396 if (strcmp (argv[i], "-shmem") == 0) /* -shmem */
397 {
398 fbmemtype = SHARED_MEMORY_FB;
399 return 1;
400 }
401 #endif
402
403 return 0;
404 }
405 dawes 1.1
406 #ifdef DDXTIME /* from ServerOSDefines */
407 CARD32
408 GetTimeInMillis()
409 {
410 struct timeval tp;
411
412 X_GETTIMEOFDAY(&tp);
413 return(tp.tv_sec * 1000) + (tp.tv_usec / 1000);
414 }
415 #endif
416
417
418 static Bool
419 vfbMultiDepthCreateGC(pGC)
420 GCPtr pGC;
421 {
422 switch (vfbBitsPerPixel(pGC->depth))
423 {
424 case 1: return mfbCreateGC (pGC);
|
425 eich 3.14 case 8:
426 case 16:
427 case 32: return fbCreateGC (pGC);
|
428 dawes 1.1 default: return FALSE;
429 }
430 }
431
432 static void
433 vfbMultiDepthGetSpans(pDrawable, wMax, ppt, pwidth, nspans, pdstStart)
434 DrawablePtr pDrawable; /* drawable from which to get bits */
435 int wMax; /* largest value of all *pwidths */
436 register DDXPointPtr ppt; /* points to start copying from */
437 int *pwidth; /* list of number of bits to copy */
438 int nspans; /* number of scanlines to copy */
439 char *pdstStart; /* where to put the bits */
440 {
441 switch (pDrawable->bitsPerPixel) {
442 case 1:
443 mfbGetSpans(pDrawable, wMax, ppt, pwidth, nspans, pdstStart);
444 break;
445 case 8:
446 case 16:
447 case 32:
|
448 eich 3.14 fbGetSpans(pDrawable, wMax, ppt, pwidth, nspans, pdstStart);
|
449 dawes 1.1 break;
450 }
451 return;
452 }
453
454 static void
455 vfbMultiDepthGetImage(pDrawable, sx, sy, w, h, format, planeMask, pdstLine)
456 DrawablePtr pDrawable;
457 int sx, sy, w, h;
458 unsigned int format;
459 unsigned long planeMask;
460 char *pdstLine;
461 {
462 switch (pDrawable->bitsPerPixel)
463 {
464 case 1:
465 mfbGetImage(pDrawable, sx, sy, w, h, format, planeMask, pdstLine);
466 break;
467 case 8:
468 case 16:
469 case 32:
|
470 eich 3.14 fbGetImage(pDrawable, sx, sy, w, h, format, planeMask, pdstLine);
|
471 dawes 1.1 break;
472 }
473 }
474
475 static ColormapPtr InstalledMaps[MAXSCREENS];
476
477 static int
478 vfbListInstalledColormaps(pScreen, pmaps)
479 ScreenPtr pScreen;
480 Colormap *pmaps;
481 {
482 /* By the time we are processing requests, we can guarantee that there
483 * is always a colormap installed */
484 *pmaps = InstalledMaps[pScreen->myNum]->mid;
485 return (1);
486 }
487
488
489 static void
490 vfbInstallColormap(pmap)
491 ColormapPtr pmap;
492 dawes 1.1 {
493 int index = pmap->pScreen->myNum;
494 ColormapPtr oldpmap = InstalledMaps[index];
495
496 if (pmap != oldpmap)
497 {
498 int entries;
499 XWDFileHeader *pXWDHeader;
500 XWDColor *pXWDCmap;
501 VisualPtr pVisual;
502 Pixel * ppix;
503 xrgb * prgb;
504 xColorItem *defs;
505 int i;
506
507 if(oldpmap != (ColormapPtr)None)
508 WalkTree(pmap->pScreen, TellLostMap, (char *)&oldpmap->mid);
509 /* Install pmap */
510 InstalledMaps[index] = pmap;
511 WalkTree(pmap->pScreen, TellGainedMap, (char *)&pmap->mid);
512
513 dawes 1.1 entries = pmap->pVisual->ColormapEntries;
514 pXWDHeader = vfbScreens[pmap->pScreen->myNum].pXWDHeader;
515 pXWDCmap = vfbScreens[pmap->pScreen->myNum].pXWDCmap;
516 pVisual = pmap->pVisual;
517
518 swapcopy32(pXWDHeader->visual_class, pVisual->class);
519 swapcopy32(pXWDHeader->red_mask, pVisual->redMask);
520 swapcopy32(pXWDHeader->green_mask, pVisual->greenMask);
521 swapcopy32(pXWDHeader->blue_mask, pVisual->blueMask);
522 swapcopy32(pXWDHeader->bits_per_rgb, pVisual->bitsPerRGBValue);
523 swapcopy32(pXWDHeader->colormap_entries, pVisual->ColormapEntries);
524
525 ppix = (Pixel *)ALLOCATE_LOCAL(entries * sizeof(Pixel));
526 prgb = (xrgb *)ALLOCATE_LOCAL(entries * sizeof(xrgb));
527 defs = (xColorItem *)ALLOCATE_LOCAL(entries * sizeof(xColorItem));
528
529 for (i = 0; i < entries; i++) ppix[i] = i;
530 /* XXX truecolor */
531 QueryColors(pmap, entries, ppix, prgb);
532
533 for (i = 0; i < entries; i++) { /* convert xrgbs to xColorItems */
534 dawes 1.1 defs[i].pixel = ppix[i] & 0xff; /* change pixel to index */
535 defs[i].red = prgb[i].red;
536 defs[i].green = prgb[i].green;
537 defs[i].blue = prgb[i].blue;
538 defs[i].flags = DoRed|DoGreen|DoBlue;
539 }
540 (*pmap->pScreen->StoreColors)(pmap, entries, defs);
541
542 DEALLOCATE_LOCAL(ppix);
543 DEALLOCATE_LOCAL(prgb);
544 DEALLOCATE_LOCAL(defs);
545 }
546 }
547
548 static void
549 vfbUninstallColormap(pmap)
550 ColormapPtr pmap;
551 {
552 ColormapPtr curpmap = InstalledMaps[pmap->pScreen->myNum];
553
554 if(pmap == curpmap)
555 dawes 1.1 {
556 if (pmap->mid != pmap->pScreen->defColormap)
557 {
558 curpmap = (ColormapPtr) LookupIDByType(pmap->pScreen->defColormap,
559 RT_COLORMAP);
560 (*pmap->pScreen->InstallColormap)(curpmap);
561 }
562 }
563 }
564
565 static void
566 vfbStoreColors(pmap, ndef, pdefs)
567 ColormapPtr pmap;
568 int ndef;
569 xColorItem *pdefs;
570 {
571 XWDColor *pXWDCmap;
572 int i;
573
574 if (pmap != InstalledMaps[pmap->pScreen->myNum]) return;
575
576 dawes 1.1 pXWDCmap = vfbScreens[pmap->pScreen->myNum].pXWDCmap;
577
578 if ((pmap->pVisual->class | DynamicClass) == DirectColor)
579 return;
580
581 for (i = 0; i < ndef; i++)
582 {
583 if (pdefs[i].flags & DoRed)
584 swapcopy16(pXWDCmap[pdefs[i].pixel].red, pdefs[i].red);
585 if (pdefs[i].flags & DoGreen)
586 swapcopy16(pXWDCmap[pdefs[i].pixel].green, pdefs[i].green);
587 if (pdefs[i].flags & DoBlue)
588 swapcopy16(pXWDCmap[pdefs[i].pixel].blue, pdefs[i].blue);
589 }
590 }
591
592 static Bool
593 vfbSaveScreen(pScreen, on)
594 ScreenPtr pScreen;
595 int on;
596 {
597 dawes 1.1 return TRUE;
598 }
599
600 #ifdef HAS_MMAP
601
602 /* this flushes any changes to the screens out to the mmapped file */
603 static void
604 vfbBlockHandler(blockData, pTimeout, pReadmask)
605 pointer blockData;
606 OSTimePtr pTimeout;
607 pointer pReadmask;
608 {
609 int i;
610
611 for (i = 0; i < vfbNumScreens; i++)
612 {
|
613 dawes 3.0 #ifdef MS_ASYNC
|
614 dawes 1.1 if (-1 == msync((caddr_t)vfbScreens[i].pXWDHeader,
615 (size_t)vfbScreens[i].sizeInBytes, MS_ASYNC))
|
616 dawes 3.0 #else
|
617 dawes 3.1 /* silly NetBSD and who else? */
|
618 dawes 3.0 if (-1 == msync((caddr_t)vfbScreens[i].pXWDHeader,
619 (size_t)vfbScreens[i].sizeInBytes))
620 #endif
|
621 dawes 1.1 {
622 perror("msync");
623 ErrorF("msync failed, errno %d", errno);
624 }
625 }
626 }
627
628
629 static void
630 vfbWakeupHandler(blockData, result, pReadmask)
631 pointer blockData;
632 int result;
633 pointer pReadmask;
634 {
635 }
636
637
638 static void
639 vfbAllocateMmappedFramebuffer(pvfb)
640 vfbScreenInfoPtr pvfb;
641 {
642 dawes 1.1 #define DUMMY_BUFFER_SIZE 65536
643 char dummyBuffer[DUMMY_BUFFER_SIZE];
644 int currentFileSize, writeThisTime;
645
646 sprintf(pvfb->mmap_file, "%s/Xvfb_screen%d", pfbdir, pvfb->scrnum);
647 if (-1 == (pvfb->mmap_fd = open(pvfb->mmap_file, O_CREAT|O_RDWR, 0666)))
648 {
649 perror("open");
650 ErrorF("open %s failed, errno %d", pvfb->mmap_file, errno);
651 return;
652 }
653
654 /* Extend the file to be the proper size */
655
656 bzero(dummyBuffer, DUMMY_BUFFER_SIZE);
657 for (currentFileSize = 0;
658 currentFileSize < pvfb->sizeInBytes;
659 currentFileSize += writeThisTime)
660 {
661 writeThisTime = min(DUMMY_BUFFER_SIZE,
662 pvfb->sizeInBytes - currentFileSize);
663 dawes 1.1 if (-1 == write(pvfb->mmap_fd, dummyBuffer, writeThisTime))
664 {
665 perror("write");
666 ErrorF("write %s failed, errno %d", pvfb->mmap_file, errno);
667 return;
668 }
669 }
670
671 /* try to mmap the file */
672
673 pvfb->pXWDHeader = (XWDFileHeader *)mmap((caddr_t)NULL, pvfb->sizeInBytes,
674 PROT_READ|PROT_WRITE,
675 MAP_FILE|MAP_SHARED,
676 pvfb->mmap_fd, 0);
|
677 tsi 3.13 if (-1 == (long)pvfb->pXWDHeader)
|
678 dawes 1.1 {
679 perror("mmap");
680 ErrorF("mmap %s failed, errno %d", pvfb->mmap_file, errno);
681 pvfb->pXWDHeader = NULL;
682 return;
683 }
684
685 if (!RegisterBlockAndWakeupHandlers(vfbBlockHandler, vfbWakeupHandler,
686 NULL))
687 {
688 pvfb->pXWDHeader = NULL;
689 }
690 }
691 #endif /* HAS_MMAP */
692
693
694 #ifdef HAS_SHM
695 static void
696 vfbAllocateSharedMemoryFramebuffer(pvfb)
697 vfbScreenInfoPtr pvfb;
698 {
699 dawes 1.1 /* create the shared memory segment */
700
701 pvfb->shmid = shmget(IPC_PRIVATE, pvfb->sizeInBytes, IPC_CREAT|0777);
702 if (pvfb->shmid < 0)
703 {
704 perror("shmget");
705 ErrorF("shmget %d bytes failed, errno %d", pvfb->sizeInBytes, errno);
706 return;
707 }
708
709 /* try to attach it */
710
711 pvfb->pXWDHeader = (XWDFileHeader *)shmat(pvfb->shmid, 0, 0);
|
712 tsi 3.13 if (-1 == (long)pvfb->pXWDHeader)
|
713 dawes 1.1 {
714 perror("shmat");
715 ErrorF("shmat failed, errno %d", errno);
716 pvfb->pXWDHeader = NULL;
717 return;
718 }
719
720 ErrorF("screen %d shmid %d\n", pvfb->scrnum, pvfb->shmid);
721 }
722 #endif /* HAS_SHM */
723
724 static char *
725 vfbAllocateFramebufferMemory(pvfb)
726 vfbScreenInfoPtr pvfb;
727 {
728 if (pvfb->pfbMemory) return pvfb->pfbMemory; /* already done */
729
730 if (pvfb->bitsPerPixel == 1)
731 pvfb->sizeInBytes = (pvfb->paddedWidth * pvfb->height);
732 else
733 pvfb->sizeInBytes = pvfb->paddedWidth * pvfb->height *
734 dawes 1.1 (pvfb->bitsPerPixel/8);
735
736 /* Calculate how many entries in colormap. This is rather bogus, because
737 * the visuals haven't even been set up yet, but we need to know because we
738 * have to allocate space in the file for the colormap. The number 10
739 * below comes from the MAX_PSEUDO_DEPTH define in cfbcmap.c.
740 */
741
742 if (pvfb->depth <= 10)
743 { /* single index colormaps */
744 pvfb->ncolors = 1 << pvfb->depth;
745 }
746 else
747 { /* decomposed colormaps */
748 int nplanes_per_color_component = pvfb->depth / 3;
749 if (pvfb->depth % 3) nplanes_per_color_component++;
750 pvfb->ncolors = 1 << nplanes_per_color_component;
751 }
752
753 /* add extra bytes for XWDFileHeader, window name, and colormap */
754
755 dawes 1.1 pvfb->sizeInBytes += SIZEOF(XWDheader) + XWD_WINDOW_NAME_LEN +
756 pvfb->ncolors * SIZEOF(XWDColor);
757
758 pvfb->pXWDHeader = NULL;
759 switch (fbmemtype)
760 {
761 #ifdef HAS_MMAP
762 case MMAPPED_FILE_FB: vfbAllocateMmappedFramebuffer(pvfb); break;
763 #endif
764
765 #ifdef HAS_SHM
766 case SHARED_MEMORY_FB: vfbAllocateSharedMemoryFramebuffer(pvfb); break;
767 #endif
768
769 case NORMAL_MEMORY_FB:
770 pvfb->pXWDHeader = (XWDFileHeader *)Xalloc(pvfb->sizeInBytes);
771 break;
772 }
773
774 if (pvfb->pXWDHeader)
775 {
776 dawes 1.1 pvfb->pXWDCmap = (XWDColor *)((char *)pvfb->pXWDHeader
777 + SIZEOF(XWDheader) + XWD_WINDOW_NAME_LEN);
|
778 dawes 3.12 #ifndef __CYGWIN__
|
779 dawes 1.1 pvfb->pfbMemory = (char *)(pvfb->pXWDCmap + pvfb->ncolors);
|
780 dawes 3.12 #else
781 pvfb->pfbMemory =
782 (char *)get_framebuf((unsigned long)
783 pvfb->paddedWidth * pvfb->height);
784 if (pvfb->pfbMemory)
785 b_video_memory = 1;
786 else
787 pvfb->pfbMemory = (char *)(pvfb->pXWDCmap + pvfb->ncolors);
788 #endif
|
789 dawes 1.1 return pvfb->pfbMemory;
790 }
791 else
792 return NULL;
793 }
794
795
796 static void
797 vfbWriteXWDFileHeader(pScreen)
798 ScreenPtr pScreen;
799 {
800 vfbScreenInfoPtr pvfb = &vfbScreens[pScreen->myNum];
801 XWDFileHeader *pXWDHeader = pvfb->pXWDHeader;
802 char hostname[XWD_WINDOW_NAME_LEN];
803 VisualPtr pVisual;
804 unsigned long swaptest = 1;
805 int i;
806
807 needswap = *(char *) &swaptest;
808
809 pXWDHeader->header_size = (char *)pvfb->pXWDCmap - (char *)pvfb->pXWDHeader;
810 dawes 1.1 pXWDHeader->file_version = XWD_FILE_VERSION;
811
812 pXWDHeader->pixmap_format = ZPixmap;
813 pXWDHeader->pixmap_depth = pvfb->depth;
814 pXWDHeader->pixmap_height = pXWDHeader->window_height = pvfb->height;
815 pXWDHeader->xoffset = 0;
816 pXWDHeader->byte_order = IMAGE_BYTE_ORDER;
|
817 dawes 3.0 pXWDHeader->bitmap_bit_order = BITMAP_BIT_ORDER;
818 #ifndef INTERNAL_VS_EXTERNAL_PADDING
819 pXWDHeader->pixmap_width = pXWDHeader->window_width = pvfb->width;
|
820 dawes 1.1 pXWDHeader->bitmap_unit = BITMAP_SCANLINE_UNIT;
821 pXWDHeader->bitmap_pad = BITMAP_SCANLINE_PAD;
|
822 dawes 3.0 #else
823 pXWDHeader->pixmap_width = pXWDHeader->window_width = pvfb->paddedWidth;
824 pXWDHeader->bitmap_unit = BITMAP_SCANLINE_UNIT_PROTO;
825 pXWDHeader->bitmap_pad = BITMAP_SCANLINE_PAD_PROTO;
826 #endif
|
827 dawes 1.1 pXWDHeader->bits_per_pixel = pvfb->bitsPerPixel;
828 pXWDHeader->bytes_per_line = pvfb->paddedWidth;
829 pXWDHeader->ncolors = pvfb->ncolors;
830
831 /* visual related fields are written when colormap is installed */
832
833 pXWDHeader->window_x = pXWDHeader->window_y = 0;
834 pXWDHeader->window_bdrwidth = 0;
835
836 /* write xwd "window" name: Xvfb hostname:server.screen */
837
838 if (-1 == gethostname(hostname, sizeof(hostname)))
839 hostname[0] = 0;
840 else
841 hostname[XWD_WINDOW_NAME_LEN-1] = 0;
842 sprintf((char *)(pXWDHeader+1), "Xvfb %s:%s.%d", hostname, display,
843 pScreen->myNum);
844
845 /* write colormap pixel slot values */
846
847 for (i = 0; i < pvfb->ncolors; i++)
848 dawes 1.1 {
849 pvfb->pXWDCmap[i].pixel = i;
850 }
851
852 /* byte swap to most significant byte first */
853
854 if (needswap)
855 {
856 SwapLongs((CARD32 *)pXWDHeader, SIZEOF(XWDheader)/4);
857 for (i = 0; i < pvfb->ncolors; i++)
858 {
859 register char n;
860 swapl(&pvfb->pXWDCmap[i].pixel, n);
861 }
862 }
863 }
864
865
866 static Bool
867 vfbCursorOffScreen (ppScreen, x, y)
868 ScreenPtr *ppScreen;
869 dawes 1.1 int *x, *y;
870 {
871 return FALSE;
872 }
873
874 static void
875 vfbCrossScreen (pScreen, entering)
876 ScreenPtr pScreen;
877 Bool entering;
878 {
879 }
880
881 static miPointerScreenFuncRec vfbPointerCursorFuncs =
882 {
883 vfbCursorOffScreen,
884 vfbCrossScreen,
885 miPointerWarpCursor
886 };
887
888 static Bool
889 vfbScreenInit(index, pScreen, argc, argv)
890 dawes 1.1 int index;
891 ScreenPtr pScreen;
892 int argc;
893 char ** argv;
894 {
895 vfbScreenInfoPtr pvfb = &vfbScreens[index];
896 int dpix = 100, dpiy = 100;
897 int ret;
898 char *pbits;
899
900 pvfb->paddedWidth = PixmapBytePad(pvfb->width, pvfb->depth);
901 pvfb->bitsPerPixel = vfbBitsPerPixel(pvfb->depth);
902 pbits = vfbAllocateFramebufferMemory(pvfb);
903 if (!pbits) return FALSE;
904
|
905 eich 3.14 /* miSetPixmapDepths ();*/
906
|
907 dawes 1.1 switch (pvfb->bitsPerPixel)
908 {
909 case 1:
910 ret = mfbScreenInit(pScreen, pbits, pvfb->width, pvfb->height,
911 dpix, dpiy, pvfb->paddedWidth * 8);
912 break;
913 case 8:
914 case 16:
915 case 32:
|
916 eich 3.14 ret = fbScreenInit(pScreen, pbits, pvfb->width, pvfb->height,
917 dpix, dpiy, pvfb->paddedWidth,pvfb->bitsPerPixel);
918 #ifdef RENDER
919 if (ret)
920 fbPictureInit (pScreen, 0, 0);
921 #endif
|
922 dawes 1.1 break;
923 default:
924 return FALSE;
925 }
926
927 if (!ret) return FALSE;
928
|
929 hohndel 3.8 miInitializeBackingStore(pScreen);
930
931 /*
932 * Circumvent the backing store that was just initialised. This amounts
933 * to a truely bizarre way of initialising SaveDoomedAreas and friends.
934 */
|
935 dawes 1.1 pScreen->CreateGC = vfbMultiDepthCreateGC;
936 pScreen->GetImage = vfbMultiDepthGetImage;
937 pScreen->GetSpans = vfbMultiDepthGetSpans;
938
939 pScreen->InstallColormap = vfbInstallColormap;
940 pScreen->UninstallColormap = vfbUninstallColormap;
941 pScreen->ListInstalledColormaps = vfbListInstalledColormaps;
942
943 pScreen->SaveScreen = vfbSaveScreen;
944 pScreen->StoreColors = vfbStoreColors;
945
946 miDCInitialize(pScreen, &vfbPointerCursorFuncs);
947
948 vfbWriteXWDFileHeader(pScreen);
949
950 pScreen->blackPixel = pvfb->blackPixel;
951 pScreen->whitePixel = pvfb->whitePixel;
952
953 if (pvfb->bitsPerPixel == 1)
954 {
955 ret = mfbCreateDefColormap(pScreen);
956 dawes 1.1 }
957 else
958 {
|
959 eich 3.14 ret = fbCreateDefColormap(pScreen);
|
960 dawes 1.1 }
|
961 dawes 3.0
962 miSetZeroLineBias(pScreen, pvfb->lineBias);
|
963 dawes 1.1
964 return ret;
965
966 } /* end vfbScreenInit */
967
968
969 void
970 InitOutput(screenInfo, argc, argv)
971 ScreenInfo *screenInfo;
972 int argc;
973 char **argv;
974 {
975 int i;
976 int NumFormats = 0;
977 FILE *pf = stderr;
|
978 dawes 3.12
979
980 #ifdef __CYGWIN__
981 enable_ntux_xf();
982 #endif
|
983 dawes 1.1
984 /* initialize pixmap formats */
985
986 /* must have a pixmap depth to match every screen depth */
987 for (i = 0; i < vfbNumScreens; i++)
988 {
989 vfbPixmapDepths[vfbScreens[i].depth] = TRUE;
990 }
991
992 for (i = 1; i <= 32; i++)
993 {
994 if (vfbPixmapDepths[i])
995 {
996 if (NumFormats >= MAXFORMATS)
997 FatalError ("MAXFORMATS is too small for this server\n");
998 screenInfo->formats[NumFormats].depth = i;
999 screenInfo->formats[NumFormats].bitsPerPixel = vfbBitsPerPixel(i);
1000 screenInfo->formats[NumFormats].scanlinePad = BITMAP_SCANLINE_PAD;
1001 NumFormats++;
1002 }
1003 }
1004 dawes 1.1
1005 screenInfo->imageByteOrder = IMAGE_BYTE_ORDER;
1006 screenInfo->bitmapScanlineUnit = BITMAP_SCANLINE_UNIT;
1007 screenInfo->bitmapScanlinePad = BITMAP_SCANLINE_PAD;
1008 screenInfo->bitmapBitOrder = BITMAP_BIT_ORDER;
1009 screenInfo->numPixmapFormats = NumFormats;
1010
1011 /* initialize screens */
1012
1013 for (i = 0; i < vfbNumScreens; i++)
1014 {
1015 if (-1 == AddScreen(vfbScreenInit, argc, argv))
1016 {
1017 FatalError("Couldn't add screen %d", i);
1018 }
1019 }
1020
1021 } /* end InitOutput */
1022
1023 /* this is just to get the server to link on AIX */
1024 #ifdef AIXV3
1025 dawes 1.1 int SelectWaitTime = 10000; /* usec */
1026 #endif
|
1027 dawes 3.6
|