[comp.windows.x] MVMS code patches for Sun server

peterson@SW.MCC.COM (James Peterson) (12/01/88)

The following patches modify the Sun X11R3 server to handle multiple
virtual monochrome screens.  These changes are controlled by the compile
option MVMS.  To use these changes, you will need to define MVMS for 
compilation.  This can be done in your Sun.macros (in util/imake.includes)
where ServerDefines is defined (lines 73 and 75 of Sun.macros) or in the
Imakefile in server (where STD_DEFINES is set at line 4).

diff -r -c server/include/misc.h nserver/include/misc.h
*** server/include/misc.h	Wed Nov 30 14:33:48 1988
--- nserver/include/misc.h	Wed Nov  9 08:11:34 1988
***************
*** 40,46 ****
  #endif
  #endif
  
! #define MAXSCREENS	3
  #define MAXCLIENTS	128
  #define MAXFORMATS	8
  #define MAXVISUALS_PER_SCREEN 50
--- 40,46 ----
  #endif
  #endif
  
! #define MAXSCREENS	10
  #define MAXCLIENTS	128
  #define MAXFORMATS	8
  #define MAXVISUALS_PER_SCREEN 50
diff -r -c server/include/scrnintstr.h nserver/include/scrnintstr.h
*** server/include/scrnintstr.h	Wed Nov 30 14:33:51 1988
--- nserver/include/scrnintstr.h	Wed Nov 30 11:30:06 1988
***************
*** 163,168 ****
--- 163,173 ----
      void (* WakeupHandler)();		/* data: pointer */
      pointer blockData;
      pointer wakeupData;
+ 
+ #ifdef MVMS
+     /* screen topology pointers */
+     ScreenPtr   UpScreen, DownScreen, LeftScreen, RightScreen;
+ #endif MVMS
  } ScreenRec;
  
  typedef struct _ScreenInfo {
diff -r -c server/dix/main.c nserver/dix/main.c
*** server/dix/main.c	Wed Nov 30 14:31:24 1988
--- nserver/dix/main.c	Wed Nov 30 11:31:26 1988
***************
*** 23,28 ****
--- 23,32 ----
  ******************************************************************/
  /* $XConsortium: main.c,v 1.143 88/09/19 12:13:43 jim Exp $ */
  
+ #ifdef MVMS
+ #include <stdio.h>
+ #endif MVMS
+ 
  #include "X.h"
  #include "Xproto.h"
  #include "input.h"
***************
*** 195,200 ****
--- 199,207 ----
  	InitOutput(&screenInfo, argc, argv);
  	if (screenInfo.numScreens < 1)
  	    FatalError("no screens found\n");
+ #ifdef MVMS
+ 	InitScreenTopology();
+ #endif MVMS
  	InitEvents();
  	InitExtensions(); 
  	InitInput(argc, argv);
***************
*** 384,409 ****
  
      int i = screenInfo.numScreens;
      int scanlinepad, format, depth, bitsPerPixel, j, k;
- #ifdef DEBUG
-     void	(**jNI) ();
- #endif /* DEBUG */
  
      if (screenInfo.numScreens == screenInfo.arraySize)
      {
! 	screenInfo.arraySize += 5;
  	screenInfo.screen = (ScreenPtr)xrealloc(
  	    screenInfo.screen, 
  	    screenInfo.arraySize * sizeof(ScreenRec));
      }
  
- #ifdef DEBUG
- 	    for (jNI = &screenInfo.screen[i].QueryBestSize; 
- 		 jNI < (void (**) ()) &screenInfo.screen[i].RegionExtents; 
- 		 jNI++)
- 		*jNI = NotImplemented;
- #endif /* DEBUG */
  
- 
      /*
       * This loop gets run once for every Screen that gets added,
       * but thats ok.  If the ddx layer initializes the formats
--- 392,410 ----
  
      int i = screenInfo.numScreens;
      int scanlinepad, format, depth, bitsPerPixel, j, k;
  
+     if (screenInfo.numScreens > MAXSCREENS-1)
+           FatalError("Too many screens -- increase MAXSCREENS and recompile");
+ 
      if (screenInfo.numScreens == screenInfo.arraySize)
      {
! 	screenInfo.arraySize += MAXSCREENS;
  	screenInfo.screen = (ScreenPtr)xrealloc(
  	    screenInfo.screen, 
  	    screenInfo.arraySize * sizeof(ScreenRec));
      }
  
  
      /*
       * This loop gets run once for every Screen that gets added,
       * but thats ok.  If the ddx layer initializes the formats
***************
*** 437,442 ****
--- 438,450 ----
      */ 
      screenInfo.screen[i].rgf = ~0;  /* there are no scratch GCs yet*/
      screenInfo.screen[i].myNum = i;
+ #ifdef MVMS
+     screenInfo.screen[i].UpScreen =    NULL; /* default topology */
+     screenInfo.screen[i].DownScreen =  NULL;
+     screenInfo.screen[i].LeftScreen =  NULL;
+     screenInfo.screen[i].RightScreen = NULL;
+ #endif MVMS
+ 
      if ((*pfnInit)(i, &screenInfo.screen[i], argc, argv))
      {
  	screenInfo.numScreens++;
***************
*** 449,452 ****
--- 457,541 ----
      return screenInfo.numScreens;
  }
  
+ #ifdef MVMS
+ /* ************************************************************ */
+ /*								*/
+ /*								*/
+ /* ************************************************************ */
  
+ extern char *getenv();
+ 
+ InitScreenTopology()
+ {
+   char *TFileName;
+   FILE *TFile;
+   char line[81];
+ 
+   /* get name of screen topology description file */
+   TFileName = getenv("XSCREENTOPOLOGY");
+ 
+   /* if no screen topology given, use default -- ... i-1 <-> i <-> i+1 ... */
+   if (TFileName == NULL || (TFile = fopen(TFileName, "r")) == NULL)
+     {
+       int i;
+       for (i = 0; i < screenInfo.numScreens; i++)
+ 	{
+ 	  screenInfo.screen[i].LeftScreen = &screenInfo.screen[i-1];
+ 	  screenInfo.screen[i].RightScreen = &screenInfo.screen[i+1];
+ 	}
+ 
+       /* redo the first and last (could have used modulo arithmetic above) */
+       screenInfo.screen[0].LeftScreen 
+ 	= &screenInfo.screen[screenInfo.numScreens-1];
+       screenInfo.screen[screenInfo.numScreens-1].RightScreen 
+ 	= &screenInfo.screen[0];
+       return;
+     }
+ 
+   while (fgets(line,81,TFile) != NULL)
+     {
+       char *s = line;
+       short index;
+       ScreenPtr pScreen, newScreen;
+ 
+       /* skip blanks */ while (*s == ' ' || *s == '\t') s++;
+       /* screen number */ index = atoi(s);
+       /* find colon */ while (*s != ':' && *s != '\0') s++;
+       /* skip past colon */ s++;
+       if (index < 0 || screenInfo.numScreens <= index) continue;
+       pScreen = &screenInfo.screen[index];
+       /* get toplogies */
+       while (*s != '\0')
+ 	{
+ 	  char link;
+ 	  short t;
+ 
+ 	  /* skip blanks */ while (*s == ' ' || *s == '\t') s++;
+ 	  /* check if end of line */ if (*s == '\0') continue;
+ 	  /* get the direction of the link */ link = *s++;
+ 	  /* get the screen in that direction */ index = atoi(s);
+ 	  /* skip the screen number */
+ 	  while ((*s != '\0') && (*s != ' ' && *s != '\t')) s++;
+ 	  if (index < 0 || screenInfo.numScreens <= index) continue;
+ 	  newScreen =  &screenInfo.screen[index];
+ 	  
+ 	  /* now set the topology pointer */
+ 	  switch(link)
+ 	    {
+ 	    case 'r': case 'R': pScreen->RightScreen = newScreen;
+ 	      break;
+ 	    case 'l': case 'L': pScreen->LeftScreen = newScreen;
+ 	      break;
+ 	    case 'a': case 'A':
+ 	    case 'u': case 'U': pScreen->UpScreen = newScreen;
+ 	      break;
+ 	    case 'b': case 'B':
+ 	    case 'd': case 'D': pScreen->DownScreen = newScreen;
+ 	      break;
+ 	    }
+ 	}
+ 
+     }
+   fclose(TFile);
+ }
+ #endif MVMS
diff -r -c server/ddx/sun/sunBW2.c nserver/ddx/sun/sunBW2.c
*** server/ddx/sun/sunBW2.c	Wed Nov 30 14:31:59 1988
--- nserver/ddx/sun/sunBW2.c	Wed Nov 30 10:50:16 1988
***************
*** 303,309 ****
--- 303,313 ----
   *-----------------------------------------------------------------------
   */
  
+ #ifndef MVMS
  Bool
+ #else MVMS
+ int
+ #endif MVMS
  sunBW2Probe(pScreenInfo, index, fbNum, argc, argv)
      ScreenInfo	  *pScreenInfo;	/* The screenInfo struct */
      int	    	  index;    	/* The index of pScreen in the ScreenInfo */
***************
*** 314,320 ****
--- 318,328 ----
      int         i, oldNumScreens;
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
***************
*** 327,333 ****
--- 335,345 ----
  	if ((fd = sunOpenFrameBuffer(FBTYPE_SUN2BW, &fbType, index, fbNum,
  				     argc, argv)) < 0) {
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  	isHiRes = (fbType.fb_width > 1152);
***************
*** 341,347 ****
--- 353,363 ----
  		Error("mapping BW2 (hires)");
  		sunFbData[fbNum].probeStatus = probedAndFailed;
  		(void) close(fd);
+ #ifndef MVMS
  		return FALSE;
+ #else MVMS
+ 		return(0);
+ #endif MVMS
  	    }
  	}
  	else {
***************
*** 353,359 ****
--- 369,379 ----
  		Error("mapping BW2");
  		sunFbData[fbNum].probeStatus = probedAndFailed;
  		(void) close(fd);
+ #ifndef MVMS
  		return FALSE;
+ #else MVMS
+ 		return(0);
+ #endif MVMS
  	    }
  	}
  #else
***************
*** 367,373 ****
--- 387,397 ----
  	    ErrorF("Could not allocate room for frame buffer.\n");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  	if (mmap((isHiRes ? (pointer) BW2HRfb : (pointer) BW2fb),
  		 (isHiRes ? sizeof(BW2HRRec) : sizeof(BW2Rec)),
***************
*** 376,382 ****
--- 400,410 ----
  	    ErrorF("Mapping bw2");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  #endif	_MAP_NEW
  
***************
*** 390,396 ****
--- 418,428 ----
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    /* do we need to free BW2fb or BW2HRfb? */
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  	if ((sunFbData[fbNum].scratch_pr = mem_create(
***************
*** 400,406 ****
--- 432,442 ----
  	    /* do we need to free BW2fb or BW2HRfb? */
  	    pr_destroy(sunFbData[fbNum].pr);
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  #endif ZOIDS
  	sunFbs[index].fb = (isHiRes ? (pointer) BW2HRfb : (pointer) BW2fb);
***************
*** 417,422 ****
--- 453,462 ----
      oldNumScreens = pScreenInfo->numScreens;
      i = AddScreen(sunBW2Init, argc, argv);
      pScreenInfo->screen[index].CloseScreen = sunBW2CloseScreen;
+ #ifndef MVMS
      return (i > oldNumScreens);
+ #else MVMS
+     return (i - oldNumScreens);
+ #endif MVMS
  }
  
diff -r -c server/ddx/sun/sunCG2C.c nserver/ddx/sun/sunCG2C.c
*** server/ddx/sun/sunCG2C.c	Wed Nov 30 14:31:58 1988
--- nserver/ddx/sun/sunCG2C.c	Wed Nov 30 11:43:54 1988
***************
*** 451,457 ****
--- 451,461 ----
   *
   *-----------------------------------------------------------------------
   */
+ #ifndef MVMS
  Bool
+ #else MVMS
+ int
+ #endif MVMS
  sunCG2CProbe (pScreenInfo, index, fbNum, argc, argv)
      ScreenInfo	  *pScreenInfo;	/* The screenInfo struct */
      int	    	  index;    	/* The index of pScreen in the ScreenInfo */
***************
*** 466,478 ****
       * display.
       */
      for (i = 0; i < argc; i++) {
  	if (strcmp (argv[i], "-mono") == 0) {
  	    return sunCG2MProbe (pScreenInfo, index, fbNum, argc, argv);
  	}
      }
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
  	return FALSE;
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
--- 470,492 ----
       * display.
       */
      for (i = 0; i < argc; i++) {
+ #ifndef MVMS
  	if (strcmp (argv[i], "-mono") == 0) {
  	    return sunCG2MProbe (pScreenInfo, index, fbNum, argc, argv);
+ #else MVMS
+ 	if (strncmp (argv[i], "-mono", 5) == 0) {
+ 	    return(sunCG2MProbe (pScreenInfo, index, fbNum,
+ 				 argc, argv, argv[i]));
+ #endif MVMS
  	}
      }
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
***************
*** 483,489 ****
--- 497,507 ----
  	if ((fd = sunOpenFrameBuffer(FBTYPE_SUN2COLOR, &fbType,
  				     index, fbNum, argc, argv)) < 0) {
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  #ifdef	_MAP_NEW
***************
*** 515,521 ****
--- 533,543 ----
  	if (CG2Cfb.image == (union byteplane *) NULL) {
  	    ErrorF ("Could not allocate room for frame buffer.\n");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  	
  	if (mmap (CG2C_IMAGE(CG2Cfb), CG2C_IMAGELEN, PROT_READ | PROT_WRITE,
***************
*** 542,548 ****
--- 564,574 ----
  bad:
  	sunFbData[fbNum].probeStatus = probedAndFailed;
  	(void) close (fd);
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
  
  ok:
  	/*
***************
*** 560,564 ****
--- 586,594 ----
      oldNumScreens = pScreenInfo->numScreens;
      i = AddScreen(sunCG2CInit, argc, argv);
      pScreenInfo->screen[index].CloseScreen = sunCG2CCloseScreen;
+ #ifndef MVMS
      return (i > oldNumScreens);
+ #else MVMS
+     return (i - oldNumScreens);
+ #endif MVMS
  }
diff -r -c server/ddx/sun/sunCG2M.c nserver/ddx/sun/sunCG2M.c
*** server/ddx/sun/sunCG2M.c	Wed Nov 30 14:31:55 1988
--- nserver/ddx/sun/sunCG2M.c	Wed Nov 30 11:45:39 1988
***************
*** 35,40 ****
--- 35,46 ----
  extern caddr_t mmap();
  #endif  _MAP_NEW
  
+ #ifdef MVMS
+ /* forward reference */
+ void sunCG2MSwitch ();
+ extern char *getenv();
+ #endif MVMS
+ 
  /*-
   * The cg2 frame buffer is divided into several pieces.
   *	1) a stack of 8 monochrome bitplanes
***************
*** 69,76 ****
--- 75,92 ----
      } u_ppmask;
  };
  
+ #ifdef MVMS
+ struct cg2m_colormap 
+ {  	/* Shouldn't these be u_char's??? */
+   u_short	    	redmap[256];	/* Red-component map */
+   u_short	    	greenmap[256];	/* Green-component map */
+   u_short	    	bluemap[256];	/* Blue-component map */
+ };
+ #endif MVMS
+ 
  struct cg2m_cmap {
      union {
+ #ifndef MVMS
  	struct {  	/* Shouldn't these be u_char's??? */
  	    u_short	    	redmap[256];	/* Red-component map */
  	    u_short	    	greenmap[256];	/* Green-component map */
***************
*** 77,82 ****
--- 93,102 ----
  	    u_short	    	bluemap[256];	/* Blue-component map */
  	}   	  	    cmap;
  	char	  	    pad[8192];
+ #else MVMS
+          struct cg2m_colormap cmap;
+ 	 char	  	      pad[8192];
+ #endif MVMS
      } u_cmap;
  };
  
***************
*** 85,96 ****
--- 105,127 ----
  				    /* monochrome frame buffer. */
      struct cg2m_reg *u_csr;		/* the status register */
      struct cg2m_ppmask *u_ppmask;	/* the plane mask register */
+ #ifndef MVMS
      struct cg2m_cmap *u_cmap;		/* the colormap */
+ #else MVMS
+     struct cg2m_cmap *u_cmap;		/* the real colormap */
+ 
+     unsigned short   p_ppmask;		/* the private plane mask register */
+     struct cg2m_colormap p_cmap;	/* the private colormap */
+ #endif MVMS
  } CG2M, CG2MRec, *CG2MPtr;
  
  #define CG2M_IMAGE(fb)	    ((caddr_t)((fb).image))
  #define CG2M_IMAGEOFF	    ((off_t)0x00000000)
+ #ifndef MVMS
  #define CG2M_IMAGELEN	    (sizeof(union bitplane))
+ #else MVMS
+ #define CG2M_IMAGELEN	    (sizeof(union bitplane)*NumberOfMonos)
+ #endif MVMS
  #define CG2M_REG(fb)	    ((caddr_t)((fb).u_csr))
  #define CG2M_REGOFF	    ((off_t)0x00308000)
  #define CG2M_REGLEN	    (2*8192)
***************
*** 308,326 ****
--- 339,378 ----
   *
   *-----------------------------------------------------------------------
   */
+ 
+ #ifdef MVMS
+ #define MAXMONOSCREENS 8
+ static int NumberOfMonos;
+ #endif MVMS
+ 
+ #ifndef MVMS
  Bool
  sunCG2MProbe (pScreenInfo, index, fbNum, argc, argv)
+ #else MVMS
+ int
+ sunCG2MProbe (pScreenInfo, index, fbNum, argc, argv, MonoMode)
+ #endif MVMS
      ScreenInfo	  *pScreenInfo;	/* The screenInfo struct */
      int	    	  index;    	/* The index of pScreen in the ScreenInfo */
      int	    	  fbNum;    	/* Index into the sunFbData array */
      int	    	  argc;	    	/* The number of the Server's arguments. */
      char    	  **argv;   	/* The arguments themselves. Don't change! */
+ #ifdef MVMS
+     char          *MonoMode;
+ #endif MVMS
  {
      int 	  i;
      int		oldNumScreens;
+ #ifdef MVMS
+     int 	  j;
+ #endif MVMS
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
***************
*** 331,356 ****
--- 383,430 ----
  	if ((fd = sunOpenFrameBuffer(FBTYPE_SUN2COLOR, &fbType, index, fbNum, 
  		    argc, argv)) < 0) {
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
+ #ifdef MVMS
+ 	NumberOfMonos = atoi(&(MonoMode[5]));
+ 	if (NumberOfMonos <= 0) NumberOfMonos = 1;
+ 	if (NumberOfMonos >  MAXMONOSCREENS) NumberOfMonos = MAXMONOSCREENS;
+ #endif MVMS
+ 
  #ifdef	_MAP_NEW
          if ((int)(CG2Mfb.image = (union bitplane *) mmap ((caddr_t) 0,
  		  CG2M_IMAGELEN, PROT_READ | PROT_WRITE,
                    MAP_SHARED | _MAP_NEW, fd, CG2M_IMAGEOFF)) == -1) {
+ #ifndef MVMS
                        Error ("Mapping cg2m.image");
+ #else MVMS
+                       Error ("Mapping new cg2m.image");
+ #endif MVMS
                        goto bad;
          }
          if ((int)(CG2Mfb.u_csr = (struct cg2m_reg *) mmap ((caddr_t) 0,
  		  CG2M_REGLEN, PROT_READ | PROT_WRITE,
                    MAP_SHARED | _MAP_NEW, fd, CG2M_REGOFF)) == -1) {
+ #ifndef MVMS
                        Error ("Mapping cg2m.reg");
+ #else MVMS
+                       Error ("Mapping new cg2m.reg");
+ #endif MVMS
                        goto bad;
          }
          if ((int)(CG2Mfb.u_ppmask = (struct cg2m_ppmask *) mmap ((caddr_t) 0,
  		  CG2M_MASKLEN, PROT_READ | PROT_WRITE,
                    MAP_SHARED | _MAP_NEW, fd, CG2M_MASKOFF)) == -1) {
+ #ifndef MVMS
                        Error ("Mapping cg2m.reg");
+ #else MVMS
+                       Error ("Mapping new cg2m.mask");
+ #endif MVMS
                        goto bad;
          }
          if ((int)(CG2Mfb.u_cmap = (struct cg2m_cmap *) mmap ((caddr_t) 0,
***************
*** 358,379 ****
                    MAP_SHARED | _MAP_NEW, fd, CG2M_CMAPOFF)) != -1) {
                        goto ok;
          }
          Error ("Mapping cg2m.cmap");
  #else
  	CG2Mfb.image = (union bitplane *)valloc (CG2M_IMAGELEN + CG2M_REGLEN +
! 				CG2M_MASKLEN + CG2M_CMAPLEN);
! 	CG2Mfb.u_csr = (struct cg2m_reg *) ((char *)CG2Mfb.image +
! 				CG2M_IMAGELEN);
! 	CG2Mfb.u_ppmask = (struct cg2m_ppmask *) ((char *)CG2Mfb.u_csr +
! 				CG2M_REGLEN);
! 	CG2Mfb.u_cmap = (struct cg2m_cmap *) ((char *)CG2Mfb.u_ppmask +
! 				CG2M_MASKLEN);
! 	if (CG2Mfb.image == (union bitplane *) NULL) {
  	    ErrorF ("Could not allocate room for frame buffer.\n");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    return FALSE;
! 	}
  	
  	if (mmap (CG2M_IMAGE(CG2Mfb), CG2M_IMAGELEN, PROT_READ | PROT_WRITE,
  		  MAP_SHARED, fd, CG2M_IMAGEOFF) < 0) {
  		      Error ("Mapping cg2m.image");
--- 432,464 ----
                    MAP_SHARED | _MAP_NEW, fd, CG2M_CMAPOFF)) != -1) {
                        goto ok;
          }
+ #ifndef MVMS
          Error ("Mapping cg2m.cmap");
+ #else MVMS
+         Error ("Mapping new cg2m.cmap");
+ #endif MVMS
  #else
  	CG2Mfb.image = (union bitplane *)valloc (CG2M_IMAGELEN + CG2M_REGLEN +
! 						 CG2M_MASKLEN + CG2M_CMAPLEN);
! 	if (CG2Mfb.image == (union bitplane *) NULL) 
! 	  {
  	    ErrorF ("Could not allocate room for frame buffer.\n");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
! #else MVMS
! 	    return(0);
! #endif MVMS
! 	  }
  	
+ 	CG2Mfb.u_csr = (struct cg2m_reg *) ((char *)CG2Mfb.image +
+ 					    CG2M_IMAGELEN);
+ 	CG2Mfb.u_ppmask = (struct cg2m_ppmask *) ((char *)CG2Mfb.u_csr +
+ 						  CG2M_REGLEN);
+ 	CG2Mfb.u_cmap = (struct cg2m_cmap *) ((char *)CG2Mfb.u_ppmask +
+ 					      CG2M_MASKLEN);
+ 	
+ 	
  	if (mmap (CG2M_IMAGE(CG2Mfb), CG2M_IMAGELEN, PROT_READ | PROT_WRITE,
  		  MAP_SHARED, fd, CG2M_IMAGEOFF) < 0) {
  		      Error ("Mapping cg2m.image");
***************
*** 395,410 ****
--- 480,506 ----
  	}
  	Error ("Mapping cg2m.cmap");
  #endif	_MAP_NEW
+ 
  bad:
  	sunFbData[fbNum].probeStatus = probedAndFailed;
  	(void) close (fd);
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
  
  ok:
  	/*
+ #ifndef MVMS
  	 * Enable only the first plane and make all even pixels be white,
  	 * while all odd pixels are black.
+ #else MVMS
+ 	 * Enable only the first n planes and make a colormap for each plane.
+ #endif MVMS
  	 */
+ 
+ #ifndef MVMS
  	CG2Mfb.u_ppmask->u_ppmask.ppmask = 1;
  	CG2Mfb.u_csr->u_csr.csr.update_cmap = 0;
  	for ( i=0; i<256; i+=2 ) {
***************
*** 421,433 ****
--- 517,717 ----
  	sunFbs[index].info = fbType;
  	sunFbs[index].fb = (pointer) &CG2Mfb;
  	sunFbs[index].EnterLeave = NoopDDA;
+ #else MVMS
+ 	for (j = 0; j < NumberOfMonos; j++)
+ 	  {
+ 	    CG2MRec *CG2MfbCopy;
+ 	    
+ 	    /* first copy the CG2M record to get the various fields */
+ 	    CG2MfbCopy = (CG2MRec *)Xalloc(sizeof(CG2MRec));
+ 	    bcopy(&CG2Mfb,CG2MfbCopy,sizeof(CG2MRec));
+ 
+ 	    /* modify where the image goes -- in the j-th bitplane */
+ 	    CG2MfbCopy->image += j;
+ 	    
+ 	    /* set up the color map for the j-th bitplane */
+ 	    MakeMonoColorMap(CG2MfbCopy, j);
+ 	    
+ 	    sunFbs[index+j].fd = fd;
+ 	    sunFbs[index+j].info = fbType;
+ 	    sunFbs[index+j].fb = (pointer) CG2MfbCopy;
+ 	    sunFbs[index+j].EnterLeave = sunCG2MSwitch;
+ 	  }
+ #endif MVMS
  	sunFbData[fbNum].probeStatus = probedAndSucceeded;
      }
  
      oldNumScreens = pScreenInfo->numScreens;
+ #ifndef MVMS
      i = AddScreen(sunCG2MInit, argc, argv);
      pScreenInfo->screen[index].CloseScreen = sunCG2MCloseScreen;
      return (i > oldNumScreens);
+ #else MVMS
+     for (j = 0; j < NumberOfMonos; j++)
+       {
+ 	i = AddScreen(sunCG2MInit, argc, argv);
+ 	pScreenInfo->screen[i-1].CloseScreen = sunCG2MCloseScreen;
+       }
+     return (i - oldNumScreens);
+ #endif MVMS
  }
  
+ #ifdef MVMS
+ /* ************************************************************ */
+ /*								*/
+ /*								*/
+ /* ************************************************************ */
  
+ MakeMonoColorMap(CG2Mfb, j)
+ CG2MRec *CG2Mfb;
+ short j;
+ {
+     struct cg2m_colormap *p;
+     register int i;
+     unsigned short r,g,b;
+     int span, start;
+     
+     if (j == 0) InitMonoScreenColors();
+ 
+     CG2Mfb->p_ppmask = 1 << j;
+ 
+     p = &(CG2Mfb->p_cmap);
+     /* first set the background color (white) */
+     r = g = b = 255;
+     GetBackColor(j,&r,&g,&b);
+     for (i=0; i < 256; i++) 
+ 	{
+ 		p->redmap[i] = r;
+ 		p->greenmap[i] = g;
+ 		p->bluemap[i] = b;
+ 	}
+ 
+     /* now set the foreground color (black) */
+     r = g = b = 0;
+     GetForeColor(j,&r,&g,&b);
+     span = 1 << j;
+     start = span;
+     while (start < 256)
+         { 
+ 		for (i=0; i < span; i++) 
+ 		   {
+ 			p->redmap[start] = r;
+ 			p->greenmap[start] = g;
+ 			p->bluemap[start] = b;
+ 			start += 1;
+ 		   }
+ 		start += span;
+ 	}
+ 
+ }
+ 
+ #define MAXCOLORNAMELENGTH 20
+ 
+ char *DefaultBack[MAXMONOSCREENS] = {"white", "white", "white", "thistle", 
+ 			  "wheat", "lightblue", "yellow", "black" };
+ 
+ char *DefaultFore[MAXMONOSCREENS] = {"black", "navy", "indianred", "violet", 
+ 			  "darkgreen", "salmon", "brown", "white" };
+ InitMonoScreenColors()
+ {
+   char *MSCFileName;
+   FILE *MSCFile;
+   int c;
+   char *back, *fore;
+   int index;
+   short n;
+ 
+   MSCFileName = getenv("XSCREENCOLORS");
+   if (MSCFileName == NULL || *MSCFileName == '\0') return;
+   MSCFile = fopen(MSCFileName, "r");
+   if (MSCFile == NULL) return;
+ 
+   /* now we have a file which should hold the screen color names, read them */
+   while ((c = getc(MSCFile)) != EOF)
+     {
+       if (c != '#')
+ 	{
+ 	  ungetc(c,MSCFile);
+ 	  back = (char *)Xalloc(MAXCOLORNAMELENGTH);
+ 	  fore = (char *)Xalloc(MAXCOLORNAMELENGTH);
+ 	  n = fscanf(MSCFile, "%d %19s %19s", &index, back, fore);
+ 	  if (n == 3 && 0 <= index && index < MAXMONOSCREENS)
+ 	    {
+ 	      DefaultBack[index] = back;
+ 	      DefaultFore[index] = fore;
+ 	    }
+ 	}
+       while ((c = getc(MSCFile)) != '\n' && c != EOF)
+ 	  /* skip to end of line */;
+     }
+   fclose(MSCFile);
+ }
+ 
+   
+ GetBackColor(j,r,g,b)
+ int j;
+ unsigned short *r, *g, *b;
+ {
+   OsLookupColor(0,DefaultBack[j], strlen(DefaultBack[j]), r, g, b);
+   *r =  (*r >> 8) & 0xFF;
+   *g =  (*g >> 8) & 0xFF;
+   *b =  (*b >> 8) & 0xFF;
+ }
+  
+ GetForeColor(j,r,g,b)
+ int j;
+ unsigned short *r, *g, *b;
+ {
+   OsLookupColor(0,DefaultFore[j], strlen(DefaultFore[j]), r, g, b);
+   *r =  (*r >> 8) & 0xFF;
+   *g =  (*g >> 8) & 0xFF;
+   *b =  (*b >> 8) & 0xFF;
+ }
+ 
+ 
+ 
+ /*-
+  *--------------------------------------------------------------
+  * sunCG2MSwitch --
+  *      Enable or disable specific mono planes on a color device
+  *
+  * Results:
+  *      Color plane enabled for select =0, disabled otherwise.
+  *
+  *--------------------------------------------------------------
+  */
+ 
+ 
+ static void
+ sunCG2MSwitch (pScreen, select)
+     ScreenPtr  pScreen;
+     u_char     select;
+ {
+   CG2MRec *hardware;
+   short i;
+ 
+   /* we will be called once to leave the current screen
+      and once to enter the new screen.  We do nothing to leave, only
+      to enter.  Enter is select==0; Leave is select==1.
+   */
+   if (select != 0) return;
+   hardware = (CG2MPtr)sunFbs[pScreen->myNum].fb;
+ 
+   /* set the plane mask register for this screen */
+   /* set it for all screens, we will only modify the one we need */
+   hardware->u_ppmask->u_ppmask.ppmask = 0xFF;
+ 
+   /* allow hardware color map to change */;
+   hardware->u_csr->u_csr.csr.update_cmap = 0;
+ 
+   for ( i=0; i<256; i++) 
+     {
+       hardware->u_cmap->u_cmap.cmap.redmap[i]  = hardware->p_cmap.redmap[i];
+       hardware->u_cmap->u_cmap.cmap.greenmap[i]= hardware->p_cmap.greenmap[i];
+       hardware->u_cmap->u_cmap.cmap.bluemap[i] = hardware->p_cmap.bluemap[i];
+     }
+ 
+   /* copy TTL cmap to ECL cmap */;
+   hardware->u_csr->u_csr.csr.update_cmap = 1;
+ }
+ #endif MVMS
diff -r -c server/ddx/sun/sunCG3C.c nserver/ddx/sun/sunCG3C.c
*** server/ddx/sun/sunCG3C.c	Wed Nov 30 14:32:00 1988
--- nserver/ddx/sun/sunCG3C.c	Wed Nov 30 10:33:16 1988
***************
*** 496,502 ****
--- 496,506 ----
   *
   *-----------------------------------------------------------------------
   */
+ #ifndef MVMS
  Bool
+ #else MVMS
+ int
+ #endif MVMS
  sunCG3CProbe (pScreenInfo, index, fbNum, argc, argv)
      ScreenInfo	  *pScreenInfo;	/* The screenInfo struct */
      int	    	  index;    	/* The index of pScreen in the ScreenInfo */
***************
*** 509,515 ****
--- 513,523 ----
      int         i, oldNumScreens;
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
***************
*** 519,525 ****
--- 527,537 ----
  	if ((fd = sunOpenFrameBuffer(FBTYPE_SUN3COLOR, &fbType, index, fbNum,
  				     argc, argv)) < 0) {
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  #ifdef	_MAP_NEW
***************
*** 531,537 ****
--- 543,553 ----
  	        Error("Mapping cg3c");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
  	        (void) close(fd);
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	    }
  	}
  	else if (fbType.fb_width == CG3B_WIDTH) {
***************
*** 542,548 ****
--- 558,568 ----
  	        Error("Mapping cg3c");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
  	        (void) close(fd);
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	    }
  	}
  	else {
***************
*** 549,555 ****
--- 569,579 ----
  	        Error("Mapping cg3c");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
  	        (void) close(fd);
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	}
  #else	_MAP_NEW
  	if (fbType.fb_width == CG3A_WIDTH) {
***************
*** 558,564 ****
--- 582,592 ----
  	    if (CG3ACfb == (CG3ACPtr) NULL) {
  	        ErrorF("Could not allocate room for frame buffer.\n");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	    }
  
  	    if (mmap((caddr_t) CG3ACfb, CG3AC_MONOLEN + 
***************
*** 568,574 ****
--- 596,606 ----
  	    	Error("Mapping cg3c");
  	    	sunFbData[fbNum].probeStatus = probedAndFailed;
  	    	(void) close(fd);
+ #ifndef MVMS
  	    	return FALSE;
+ #else MVMS
+ 	    	return(0);
+ #endif MVMS
  	    }
  	}
  	else if (fbType.fb_width == CG3B_WIDTH) {
***************
*** 577,583 ****
--- 609,619 ----
  	    if (CG3BCfb == (CG3BCPtr) NULL) {
  	        ErrorF("Could not allocate room for frame buffer.\n");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	    }
  
  	    if (mmap((caddr_t) CG3BCfb, CG3BC_MONOLEN + 
***************
*** 587,593 ****
--- 623,633 ----
  	    	Error("Mapping cg3c");
  	    	sunFbData[fbNum].probeStatus = probedAndFailed;
  	    	(void) close(fd);
+ #ifndef MVMS
  	    	return FALSE;
+ #else MVMS
+ 	    	return(0);
+ #endif MVMS
  	    }
  	}
  	else {
***************
*** 594,600 ****
--- 634,644 ----
  	        Error("Mapping cg3c");
  	        sunFbData[fbNum].probeStatus = probedAndFailed;
  	        (void) close(fd);
+ #ifndef MVMS
  	        return FALSE;
+ #else MVMS
+ 	        return(0);
+ #endif MVMS
  	}
  #endif	_MAP_NEW
  
***************
*** 617,625 ****
--- 661,677 ----
      i = AddScreen(sunCG3CInit, argc, argv);
      pScreenInfo->screen[index].CloseScreen = sunCG3CCloseScreen;
  
+ #ifndef MVMS
      return (i > oldNumScreens);
+ #else MVMS
+     return (i - oldNumScreens);
+ #endif MVMS
  
  #else /* non 386 */
+ #ifndef MVMS
      return FALSE;
+ #else MVMS
+     return(0);
+ #endif MVMS
  #endif
  }
diff -r -c server/ddx/sun/sunCG4C.c nserver/ddx/sun/sunCG4C.c
*** server/ddx/sun/sunCG4C.c	Wed Nov 30 14:31:59 1988
--- nserver/ddx/sun/sunCG4C.c	Wed Nov 30 10:33:16 1988
***************
*** 435,441 ****
--- 435,445 ----
   *
   *-----------------------------------------------------------------------
   */
+ #ifndef MVMS
  Bool
+ #else MVMS
+ int
+ #endif MVMS
  sunCG4CProbe (pScreenInfo, index, fbNum, argc, argv)
      ScreenInfo	  *pScreenInfo;	/* The screenInfo struct */
      int	    	  index;    	/* The index of pScreen in the ScreenInfo */
***************
*** 446,452 ****
--- 450,460 ----
      int         i, oldNumScreens;
  
      if (sunFbData[fbNum].probeStatus == probedAndFailed) {
+ #ifndef MVMS
  	return FALSE;
+ #else MVMS
+ 	return(0);
+ #endif MVMS
      }
  
      if (sunFbData[fbNum].probeStatus == neverProbed) {
***************
*** 456,462 ****
--- 464,474 ----
  	if ((fd = sunOpenFrameBuffer(FBTYPE_SUN4COLOR, &fbType, index, fbNum,
  				     argc, argv)) < 0) {
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  #ifdef	_MAP_NEW
***************
*** 467,473 ****
--- 479,489 ----
  	    Error("Mapping cg4c");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  #else	_MAP_NEW
  	CG4Cfb = (CG4CPtr) valloc(CG4C_MONOLEN + CG4C_ENBLEN + CG4C_IMAGELEN);
***************
*** 474,480 ****
--- 490,500 ----
  	if (CG4Cfb == (CG4CPtr) NULL) {
  	    ErrorF("Could not allocate room for frame buffer.\n");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  
  	if (mmap((caddr_t) CG4Cfb, CG4C_MONOLEN + CG4C_ENBLEN + CG4C_IMAGELEN,
***************
*** 483,489 ****
--- 503,513 ----
  	    Error("Mapping cg4c");
  	    sunFbData[fbNum].probeStatus = probedAndFailed;
  	    (void) close(fd);
+ #ifndef MVMS
  	    return FALSE;
+ #else MVMS
+ 	    return(0);
+ #endif MVMS
  	}
  #endif	_MAP_NEW
  
***************
*** 505,509 ****
--- 529,537 ----
      /* Now set the enable plane for color */
      if (index == 0) sunCG4CSwitch (&(pScreenInfo->screen[0]), 0);
  
+ #ifndef MVMS
      return (i > oldNumScreens);
+ #else MVMS
+     return (i - oldNumScreens);
+ #endif MVMS
  }
diff -r -c server/ddx/sun/sunInit.c nserver/ddx/sun/sunInit.c
*** server/ddx/sun/sunInit.c	Wed Nov 30 14:31:56 1988
--- nserver/ddx/sun/sunInit.c	Wed Nov 30 11:17:50 1988
***************
*** 55,64 ****
--- 55,71 ----
  
  extern int sunMouseProc();
  extern void sunKbdProc();
+ #ifndef MVMS
  extern Bool sunBW2Probe();
  extern Bool sunCG2CProbe();
  extern Bool sunCG3CProbe();
  extern Bool sunCG4CProbe();
+ #else MVMS
+ extern int sunBW2Probe();
+ extern int sunCG2CProbe();
+ extern int sunCG3CProbe();
+ extern int sunCG4CProbe();
+ #endif MVMS
  extern void ProcessInputEvents();
  
  extern void SetInputCheck();
***************
*** 124,130 ****
  #define NUMSCREENS (sizeof(sunFbData)/sizeof(sunFbData[0]))
  #define NUMDEVICES 2
  
! fbFd	sunFbs[NUMSCREENS];  /* Space for descriptors of open frame buffers */
  
  static PixmapFormatRec	formats[] = {
      1, 1, BITMAP_SCANLINE_PAD,	/* 1-bit deep */
--- 131,137 ----
  #define NUMSCREENS (sizeof(sunFbData)/sizeof(sunFbData[0]))
  #define NUMDEVICES 2
  
! fbFd	sunFbs[MAXSCREENS];  /* Space for descriptors of open frame buffers */
  
  static PixmapFormatRec	formats[] = {
      1, 1, BITMAP_SCANLINE_PAD,	/* 1-bit deep */
***************
*** 178,187 ****
      int     	  argc;
      char    	  **argv;
  {
!     int     	  i, index, ac = argc;
      char	  **av = argv;
      int		  nonBlockConsole = 1;
      static int	  setup_on_exit = 0;
  
      while (ac--) {
  	if (!strcmp(*av,"-debug")) {
--- 185,198 ----
      int     	  argc;
      char    	  **argv;
  {
!     int           i;
!     int     	  ac = argc;
      char	  **av = argv;
      int		  nonBlockConsole = 1;
      static int	  setup_on_exit = 0;
+ #ifndef MVMS
+     int           index;
+ #endif MVMS
  
      while (ac--) {
  	if (!strcmp(*av,"-debug")) {
***************
*** 222,227 ****
--- 233,239 ----
  
      autoRepeatHandlersInstalled = FALSE;
  
+ #ifndef MVMS
      for (i = 0, index = 0; i < NUMSCREENS; i++) {
  	if ((* sunFbData[i].probeProc) (pScreenInfo, index, i, argc, argv)) {
  	    /* This display exists OK */
***************
*** 235,245 ****
--- 247,281 ----
  	FatalError("Can't find any displays\n");
  
      pScreenInfo->numScreens = index;
+ #else MVMS
+     sunInitScreens(pScreenInfo, argc, argv);
+ #endif MVMS
  
      sunInitCursor();
      signal(SIGWINCH, SIG_IGN);
  }
  
+ #ifdef MVMS
+ sunInitScreens(pScreenInfo, argc, argv)
+     ScreenInfo 	  *pScreenInfo;
+     int     	  argc;
+     char    	  **argv;
+ {
+     int   i, index;
+     int NumberOfScreens;
+ 
+      for (i = 0, index = 0; i < NUMSCREENS; i++) {
+        NumberOfScreens =
+ 	 (* sunFbData[i].probeProc) (pScreenInfo, index, i, argc, argv);
+        index += NumberOfScreens;
+     }
+     if (index == 0)
+ 	FatalError("Can't find any displays\n");
+ 
+     pScreenInfo->numScreens = index;
+ }
+ #endif MVMS
+ 
  /*-
   *-----------------------------------------------------------------------
   * InitInput --
***************
*** 436,461 ****
      char *result;
      static char returnstring[100];
  
      while (n--) {
! 	while (*dList && *dList != ':') {
! 	    dList++;
! 	}
      }
-     if (*dList) {
- 	register char *cp = dList;
  
! 	while (*cp && *cp != ':') {
! 	    cp++;
! 	}
! 	result = returnstring;
! 	strncpy (result, dList, cp - dList);
! 	result[cp - dList] = '\0';
      } else {
! 	result = (char *)0;
      }
      return (result);
  }
  
  /*-
   *-----------------------------------------------------------------------
   * sunOpenFrameBuffer --
--- 472,530 ----
      char *result;
      static char returnstring[100];
  
+     /* skip to the nth colon or end of the string; n is 0-origin */
      while (n--) {
!         /* find the next colon */
!         while (*dList != '\0' && *dList != ':') {
!             dList++;
!         }
!         if (*dList != '\0') dList++ /* skip colon */;
      }
  
!     /* if there was no nth colon -- return NULL */
!     if (*dList == '\0') {
!         result = (char *)NULL;
      } else {
!         register char *cp = dList;
! 	short length;
! 
! 	/* we found the nth colon -- now find the next colon (or end of string)
! 	   and copy the delimited string to our buffer for return */
!         while (*cp != '\0' && *cp != ':') {
! 	    cp++;
!         }
!         result = returnstring;
! 	length = cp - dList;
! 	/* check that we do not exceed the length of our static returnstring */
! 	if (length > sizeof(returnstring)-1) length = sizeof(returnstring)-1;
! 	strncpy (result, dList, length);
! 	result[length] = '\0';
      }
+ 
      return (result);
  }
  
+ 
+ static char *
+ CheckDeviceList(dList, fbNum)
+ char *dList;
+ int  fbNum;
+ {
+   short index;
+   char *name;
+ 
+   for (index = 0; (name = nthdev(dList,index)) != NULL; index++)
+     {
+       if ((strcmp(name, sunFbData[fbNum].devName) == 0)
+           && (access (name, R_OK | W_OK) == 0))
+         {
+           return(name);
+         }
+     }
+   return(NULL);
+ }
+ 
+ 
  /*-
   *-----------------------------------------------------------------------
   * sunOpenFrameBuffer --
***************
*** 519,530 ****
       * If one was and the device is both readable and writeable,
       * set 'name' to it, else set it to NULL.
       */
!     if (devsw == (char *)NULL ||
! 	(name = nthdev (devsw, index)) == (char *)NULL ||
! 	(access (name, R_OK | W_OK) != 0) ||
! 	(strcmp(name, sunFbData[fbNum].devName) != 0)) {
! 	    name = (char *)NULL;
!     }
  	    
      /*
       * If we still don't have a device for this screen, check the
--- 588,597 ----
       * If one was and the device is both readable and writeable,
       * set 'name' to it, else set it to NULL.
       */
!     if (devsw != (char *)NULL)
!       {
! 	name = CheckDeviceList (devsw, fbNum);
!       }
  	    
      /*
       * If we still don't have a device for this screen, check the
***************
*** 533,544 ****
       * properly accessible, then reset the name to NULL to force the
       * checking of the sunFbData array.
       */
!     if (devsw == (char *)NULL && name == (char *)NULL &&
! 	xdevice != (char *)NULL &&
! 	(name = nthdev(xdevice, index)) != (char *)NULL &&
! 	(access (name, R_OK | W_OK) != 0)) {
! 	    name = (char *)NULL;
!     }
  
      /*
       * Take the device given in the frame buffer description
--- 600,611 ----
       * properly accessible, then reset the name to NULL to force the
       * checking of the sunFbData array.
       */
!     if (devsw == (char *)NULL 
! 	&& name == (char *)NULL 
! 	&& xdevice != (char *)NULL)
!       {
! 	name = CheckDeviceList (xdevice, fbNum);
!       }
  
      /*
       * Take the device given in the frame buffer description
***************
*** 545,554 ****
       * and see if it exists and is accessible. If it does/is,
       * we will use it, as long as no other device was given.
       */
!     if (devsw == (char *)NULL && name == (char *)NULL &&
! 	access(sunFbData[fbNum].devName, (R_OK | W_OK)) == 0) {
! 	    name = sunFbData[fbNum].devName;
!     }
  
      /*
       * If we still have nothing and have yet to use "/dev/fb" for
--- 612,624 ----
       * and see if it exists and is accessible. If it does/is,
       * we will use it, as long as no other device was given.
       */
!     if (devsw == (char *)NULL 
! 	&& xdevice == (char *)NULL 
! 	&& name == (char *)NULL 
! 	&& access(sunFbData[fbNum].devName, (R_OK | W_OK)) == 0) 
!       {
! 	name = sunFbData[fbNum].devName;
!       }
  
      /*
       * If we still have nothing and have yet to use "/dev/fb" for
diff -r -c server/ddx/sun/sunIo.c nserver/ddx/sun/sunIo.c
*** server/ddx/sun/sunIo.c	Wed Nov 30 14:31:56 1988
--- nserver/ddx/sun/sunIo.c	Wed Nov 30 10:33:18 1988
***************
*** 350,355 ****
--- 350,369 ----
  	if (++i >= argc) UseMsg ();
  	return 2;
      }
+ #ifndef MVMS
+     if (strcmp (argv[i], "-mono") == 0) {	/* -mono */
+ #else MVMS
+     if (strncmp (argv[i], "-mono", 5) == 0) {	/* -mono */
+ #endif MVMS
+         return 1;
+     }
+ #ifdef MVMS
+     if (strcmp (argv[i], "-skey") == 0) {	/* -skey [lrf] */
+ 	if (++i >= argc) UseMsg ();
+ 	SetSunScreenKeys(argv[i]);
+ 	return 2;
+     }
+ #endif MVMS
      return 0;
  }
  
***************
*** 357,360 ****
--- 371,378 ----
  ddxUseMsg()
  {
      ErrorF("-dev filename          name of device to open\n");
+ #ifdef MVMS
+     ErrorF("-mono3                 number of mono screens\n");
+     ErrorF("-key [f|l|r]           function key set to use for screens\n");
+ #endif MVMS
  }
diff -r -c server/ddx/sun/sunKbd.c nserver/ddx/sun/sunKbd.c
*** server/ddx/sun/sunKbd.c	Wed Nov 30 14:31:56 1988
--- nserver/ddx/sun/sunKbd.c	Wed Nov 30 10:33:18 1988
***************
*** 386,391 ****
--- 386,421 ----
      }
  }
  
+ #ifdef MVMS
+ /* array to translate Screen Selection Keys (F1, F2, ..., F9) to 
+    screens 0 to 8; since the array is automatically initialized to zero,
+    we keep the screen indexes offset by one (i.e., 1 means screen 0, ... */
+ 
+ static short ScreenKeySelection[128];
+ 
+ /* these arrays define the id's that we get if the user types the function
+    key.  Order is important, so F1 is a 5, F2 is a 6, etc. */
+ 
+ #define ArraySize(x)  (sizeof(x)/sizeof(x[0]))
+ short FKeys[] = {5,6,8,10,12,14,16,17,18};
+ short LKeys[] = {1,3, 25,26, 49,51, 72,73, 95,97};
+ short RKeys[] = {21,22,23, 45,46,47, 68,69,70, 91,92,93, 112,113,114};
+ 
+ SetSunScreenKeys(s)
+ char *s;
+ {
+   char c = *s;
+   short i;
+ 
+   if (c == 'f' || c == 'F')
+     for (i=0; i < ArraySize(FKeys); i++) ScreenKeySelection[FKeys[i]] = i+1;
+   else if (c == 'r' || c == 'R')
+     for (i=0; i < ArraySize(RKeys); i++) ScreenKeySelection[RKeys[i]] = i+1;
+   else if (c == 'l' || c == 'L')
+     for (i=0; i < ArraySize(LKeys); i++) ScreenKeySelection[LKeys[i]] = i+1;
+ }
+ #endif MVMS
+ 
  /*-
   *-----------------------------------------------------------------------
   * sunKbdGetEvents --
***************
*** 476,481 ****
--- 507,532 ----
      CARD16		keyModifiers;
  
      ptrPriv = (PtrPrivPtr) LookupPointerDevice()->devicePrivate;
+ 
+ #ifdef MVMS
+     /* check if the input event is a Screen Selection key */
+     if (screenInfo.numScreens > 1 && fe->id < 128)
+       {
+ 	/* it could be a screen selection */
+ 	short index = ScreenKeySelection[fe->id]-1;
+ 	/* check if we have that many screens */
+ 	if (0 <= index && index < screenInfo.numScreens)
+ 	  {
+ 	    /* key on down stroke of Screen Selection key */
+ 	    if (fe->value == 1)
+ 	      {
+ 		NewCurrentScreen (&(screenInfo.screen[index]),
+ 				  ptrPriv->x, ptrPriv->y);
+ 	      }
+ 	    return;
+ 	  }
+       }
+ #endif MVMS
  
      if (autoRepeatKeyDown && fe->id == AUTOREPEAT_EVENTID) {
  	pPriv = (KbPrivPtr) pKeyboard->devicePrivate;
diff -r -c server/ddx/sun/sunMouse.c nserver/ddx/sun/sunMouse.c
*** server/ddx/sun/sunMouse.c	Wed Nov 30 14:31:57 1988
--- nserver/ddx/sun/sunMouse.c	Wed Nov 30 10:33:19 1988
***************
*** 135,137 ****
--- 135,141 ----
  	    sysMousePriv.pScreen = &screenInfo.screen[0];
  	    sysMousePriv.x = sysMousePriv.pScreen->width / 2;
  	    sysMousePriv.y = sysMousePriv.pScreen->height / 2;
+ #ifdef MVMS
+ 	    NewCurrentScreen (sysMousePriv.pScreen,
+ 			      sysMousePriv.x, sysMousePriv.y);
+ #endif MVMS
***************
*** 325,335 ****
--- 329,344 ----
      DevicePtr	  pMouse;   	/* Mouse from which the event came */
      Firm_event	  *fe;	    	/* Event to process */
  {
+ #ifndef MVMS
      int      index;		/* screen index */
+ #endif MVMS
      xEvent		xE;
      register PtrPrivPtr	pPriv;	/* Private data for pointer */
      register SunMsPrivPtr pSunPriv; /* Private data for mouse */
      register int  	bmask;	/* Temporary button mask */
+ #ifdef MVMS
+     ScreenPtr           newScreen; /* pointer to new screen, if mouse moves */
+ #endif MVMS
  
      pPriv = (PtrPrivPtr)pMouse->devicePrivate;
      pSunPriv = (SunMsPrivPtr) pPriv->devPrivate;
***************
*** 380,391 ****
--- 389,407 ----
  	     * simply removing the cursor or just shifting it a bit.
  	     * If it is removed, DIX will restore it before we goes to sleep...
  	     *
+ #ifndef MVMS
  	     * What should be done if it goes off the screen? Move to another
  	     * screen? For now, we just force the pointer to stay on the
  	     * screen...
+ #else MVMS
+ 	     * If the mouse attempts to move off the screen, we look for 
+ 	     * a screen to the left or right and update the screen and
+ 	     * position accordingly.
+ #endif MVMS
  	     */
  	    pPriv->x += MouseAccelerate (pMouse, fe->value);
  
+ #ifndef MVMS
              /*
               * Active Zaphod implementation:
               *    increment or decrement the current screen
***************
*** 410,426 ****
--- 426,485 ----
                  }
                  else {
                      pPriv->x -= pPriv->pScreen->width;
+ #else MVMS
+ 	    newScreen = pPriv->pScreen;
+ 	    while (pPriv->x > newScreen->width)
+ 	      {
+ 		/* Mouse has moved off the right edge. Check if we should
+ 		   move to another screen.  If not, stop at right edge */
+ 		if (PointerConfinedToScreen() 
+ 		    || newScreen->RightScreen == NULL)
+ 		  pPriv->x =  newScreen->width;
+ 		else  {
+ 		  /* reset x to be on new screen (may have different height) */
+ 		  pPriv->x = (pPriv->x - newScreen->width);
+ 		  pPriv->y = (pPriv->y * newScreen->RightScreen->height)
+ 		                       / newScreen->height;
+ 		  newScreen = newScreen->RightScreen;
+ 		  }
+ 	      }
+ 	    while (pPriv->x < 0)
+ 	      {
+ 		/* Mouse has moved off the left edge. Check if we should
+ 		   move to another screen.  If not, stop at left edge */
+ 		if (PointerConfinedToScreen() 
+ 		    || newScreen->LeftScreen == NULL)
+ 		  pPriv->x =  0;
+ 		else  {
+ 		  /* reset x to be on new screen (may have different height) */
+ 		  pPriv->y = (pPriv->y * newScreen->LeftScreen->height)
+ 		                       / newScreen->height;
+ 		  newScreen = newScreen->LeftScreen;
+ 		  pPriv->x = (pPriv->x + newScreen->width);
+ 		  }
+ 	      }
+ #endif MVMS
  
+ #ifndef MVMS
                      if (pPriv->pScreen->myNum != screenInfo.numScreens -1)
                          (pPriv->pScreen)++;
                      else
                           pPriv->pScreen = &screenInfo.screen[0];
                  }
+ #else MVMS
+             if (newScreen != pPriv->pScreen)
+ 	      {
+ 		sunMouseChangeScreens(pPriv->pScreen, newScreen);
+ 		pPriv->pScreen = newScreen;
+ 	      }
+ #endif MVMS
  
+ #ifndef MVMS
                  index = pPriv->pScreen->myNum;
                  /* enable color plane if new current screen */
                  (*sunFbs[index].EnterLeave) (pPriv->pScreen, 0);
              }
+ #endif MVMS
  
  	    if (!sunConstrainXY (&pPriv->x, &pPriv->y)) {
  		return;
***************
*** 443,459 ****
  	     * here instead of add...
  	     */
  	    pPriv->y -= MouseAccelerate (pMouse, fe->value);
  	    if (!sunConstrainXY (&pPriv->x, &pPriv->y)) {
  		return;
  	    }
  #ifdef SUN_ALL_MOTION
  	    xE.u.u.type = MotionNotify;
  	    sunMoveCursor (pPriv->pScreen, pPriv->x, pPriv->y);
  	    break;
  #else
  	    ((SunMsPrivPtr)pPriv->devPrivate)->mouseMoved = TRUE;
  	    return;
  #endif SUN_ALL_MOTION
  	default:
  	    FatalError ("sunMouseProcessEvent: unrecognized id\n");
  	    break;
--- 503,567 ----
  	     * here instead of add...
  	     */
  	    pPriv->y -= MouseAccelerate (pMouse, fe->value);
+ 
+ #ifdef MVMS
+ 	    newScreen = pPriv->pScreen;
+ 	    while (pPriv->y > newScreen->height)
+ 	      {
+ 		/* Mouse has moved off the bottom edge. Check if we should
+ 		   move to another screen.  If not, stop at bottom edge */
+ 		if (PointerConfinedToScreen() 
+ 		    || newScreen->DownScreen == NULL)
+ 		  pPriv->y =  newScreen->height;
+ 		else  {
+ 		  /* reset y to be on new screen (may have different width) */
+ 		  pPriv->y = (pPriv->y - newScreen->height);
+ 		  pPriv->x = (pPriv->x * newScreen->DownScreen->width)
+ 		                       / newScreen->width;
+ 		  newScreen = newScreen->DownScreen;
+ 		  }
+ 	      }
+ 	    while (pPriv->y < 0)
+ 	      {
+ 		/* Mouse has moved off the top edge. Check if we should
+ 		   move to another screen.  If not, stop at top edge */
+ 		if (PointerConfinedToScreen() 
+ 		    || newScreen->UpScreen == NULL)
+ 		  pPriv->y =  0;
+ 		else  {
+ 		  /* reset y to be on new screen (may have different width) */
+ 		  pPriv->x = (pPriv->x * newScreen->UpScreen->width)
+ 		                       / newScreen->width;
+ 		  newScreen = newScreen->UpScreen;
+ 		  pPriv->y = (pPriv->y + newScreen->width);
+ 		  }
+ 	      }
+ 
+             if (newScreen != pPriv->pScreen)
+ 	      {
+ 		sunMouseChangeScreens(pPriv->pScreen, newScreen);
+ 		pPriv->pScreen = newScreen;
+ 	      }
+ #endif MVMS
+ 
  	    if (!sunConstrainXY (&pPriv->x, &pPriv->y)) {
  		return;
  	    }
+ 
+ #ifdef MVMS
+             NewCurrentScreen (pPriv->pScreen, pPriv->x, pPriv->y);
+ #endif MVMS
+ 
  #ifdef SUN_ALL_MOTION
  	    xE.u.u.type = MotionNotify;
  	    sunMoveCursor (pPriv->pScreen, pPriv->x, pPriv->y);
  	    break;
  #else
  	    ((SunMsPrivPtr)pPriv->devPrivate)->mouseMoved = TRUE;
  	    return;
  #endif SUN_ALL_MOTION
+ 
+ 
  	default:
  	    FatalError ("sunMouseProcessEvent: unrecognized id\n");
  	    break;
***************
*** 464,469 ****
--- 572,590 ----
  
      (* pMouse->processInputProc) (&xE, pMouse);
  }
+ 
+ #ifdef MVMS
+ sunMouseChangeScreens(oldScreen, newScreen)
+ ScreenPtr oldScreen, newScreen;
+ {
+   sunRemoveCursor();
+   /* disable color plane if it's current */
+   (*sunFbs[oldScreen->myNum].EnterLeave) (oldScreen, 1);
+   /* enable color plane if new current screen */
+   (*sunFbs[newScreen->myNum].EnterLeave) (newScreen, 0);
+ }
+ #endif MVMS
+ 
  
  /*-
   *-----------------------------------------------------------------------