summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKaleb Keithley <kaleb@freedesktop.org>2003-11-14 15:54:53 +0000
committerKaleb Keithley <kaleb@freedesktop.org>2003-11-14 15:54:53 +0000
commitdb757f1d2a5a951ec26aa4ed64134d8113089fd0 (patch)
treeef126a8a6974ad41b7f9a2a46f2c2b3449cdcde7
R6.6 is the Xorg base-lineXORG-MAIN
-rw-r--r--config.cpp10
-rw-r--r--difs/atom.c205
-rw-r--r--difs/cache.c388
-rw-r--r--difs/charinfo.c631
-rw-r--r--difs/difsutils.c673
-rw-r--r--difs/dispatch.c1109
-rw-r--r--difs/events.c134
-rw-r--r--difs/extensions.c306
-rw-r--r--difs/fontinfo.c435
-rw-r--r--difs/fonts.c1552
-rw-r--r--difs/globals.c67
-rw-r--r--difs/initfonts.c80
-rw-r--r--difs/main.c200
-rw-r--r--difs/resource.c569
-rw-r--r--difs/swaprep.c472
-rw-r--r--difs/swapreq.c286
-rw-r--r--difs/tables.c190
-rw-r--r--include/access.h66
-rw-r--r--include/accstr.h64
-rw-r--r--include/assert.h59
-rw-r--r--include/auth.h58
-rw-r--r--include/authstr.h61
-rw-r--r--include/cache.h73
-rw-r--r--include/cachestr.h77
-rw-r--r--include/client.h117
-rw-r--r--include/clientstr.h89
-rw-r--r--include/closestr.h143
-rw-r--r--include/closure.h59
-rw-r--r--include/difsfn.h63
-rw-r--r--include/difsfnst.h74
-rw-r--r--include/extentst.h88
-rw-r--r--include/globals.h78
-rw-r--r--include/misc.h195
-rw-r--r--include/os.h96
-rw-r--r--include/osstruct.h68
-rw-r--r--include/servermd.h62
-rw-r--r--include/site.h67
-rw-r--r--os/access.c138
-rw-r--r--os/config.c610
-rw-r--r--os/config.h69
-rw-r--r--os/configstr.h59
-rw-r--r--os/connection.c579
-rw-r--r--os/error.c217
-rw-r--r--os/io.c688
-rw-r--r--os/osdep.h123
-rw-r--r--os/osglue.c384
-rw-r--r--os/osinit.c62
-rw-r--r--os/utils.c443
-rw-r--r--os/waitfor.c230
-rw-r--r--xfs.man205
50 files changed, 12771 insertions, 0 deletions
diff --git a/config.cpp b/config.cpp
new file mode 100644
index 0000000..73f049f
--- /dev/null
+++ b/config.cpp
@@ -0,0 +1,10 @@
+XCOMM font server configuration file
+XCOMM $Xorg: config.cpp,v 1.3 2000/08/17 19:54:19 cpqbld Exp $
+
+clone-self = on
+use-syslog = off
+catalogue = DEFAULTFONTPATH
+error-file = FSERRORS
+XCOMM in decipoints
+default-point-size = 120
+default-resolutions = 75,75,100,100
diff --git a/difs/atom.c b/difs/atom.c
new file mode 100644
index 0000000..40ead2b
--- /dev/null
+++ b/difs/atom.c
@@ -0,0 +1,205 @@
+/* $Xorg: atom.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * font server atom manipulations
+ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)atom.c 4.1 5/2/91
+ *
+ */
+
+#include "misc.h"
+#include "resource.h"
+
+#define InitialTableSize 100
+#define FSA_LAST_PREDEFINED 0 /* only None is predefined */
+
+typedef struct _Node {
+ struct _Node *left,
+ *right;
+ Atom a;
+ unsigned int fingerPrint;
+ char *string;
+} NodeRec, *NodePtr;
+
+static Atom lastAtom = None;
+static NodePtr atomRoot = (NodePtr) NULL;
+static unsigned long tableLength;
+static NodePtr *nodeTable;
+
+Atom
+MakeAtom(string, len, makeit)
+ char *string;
+ unsigned len;
+ Bool makeit;
+{
+ register NodePtr *np;
+ unsigned i;
+ int comp;
+ register unsigned int fp = 0;
+
+ np = &atomRoot;
+ for (i = 0; i < (len + 1) / 2; i++) {
+ fp = fp * 27 + string[i];
+ fp = fp * 27 + string[len - 1 - i];
+ }
+ while (*np != (NodePtr) NULL) {
+ if (fp < (*np)->fingerPrint)
+ np = &((*np)->left);
+ else if (fp > (*np)->fingerPrint)
+ np = &((*np)->right);
+ else { /* now start testing the strings */
+ comp = strncmp(string, (*np)->string, (int) len);
+ if ((comp < 0) || ((comp == 0) && (len < strlen((*np)->string))))
+ np = &((*np)->left);
+ else if (comp > 0)
+ np = &((*np)->right);
+ else
+ return (*np)->a;
+ }
+ }
+ if (makeit) {
+ register NodePtr nd;
+
+ nd = (NodePtr) fsalloc(sizeof(NodeRec));
+ if (!nd)
+ return BAD_RESOURCE;
+ if (lastAtom < FSA_LAST_PREDEFINED) {
+ nd->string = string;
+ } else {
+ nd->string = (char *) fsalloc(len + 1);
+ if (!nd->string) {
+ fsfree(nd);
+ return BAD_RESOURCE;
+ }
+ strncpy(nd->string, string, (int) len);
+ nd->string[len] = 0;
+ }
+ if ((lastAtom + 1) >= tableLength) {
+ NodePtr *table;
+
+ table = (NodePtr *) fsrealloc(nodeTable,
+ tableLength * (2 * sizeof(NodePtr)));
+ if (!table) {
+ if (nd->string != string)
+ fsfree(nd->string);
+ fsfree(nd);
+ return BAD_RESOURCE;
+ }
+ tableLength <<= 1;
+ nodeTable = table;
+ }
+ *np = nd;
+ nd->left = nd->right = (NodePtr) NULL;
+ nd->fingerPrint = fp;
+ nd->a = (++lastAtom);
+ *(nodeTable + lastAtom) = nd;
+ return nd->a;
+ } else
+ return None;
+}
+
+ValidAtom(atom)
+ Atom atom;
+{
+ return (atom != None) && (atom <= lastAtom);
+}
+
+char *
+NameForAtom(atom)
+ Atom atom;
+{
+ NodePtr node;
+
+ if (atom > lastAtom)
+ return 0;
+ if ((node = nodeTable[atom]) == (NodePtr) NULL)
+ return 0;
+ return node->string;
+}
+
+static void
+atom_error()
+{
+ FatalError("initializing atoms\n");
+}
+
+static void
+free_atom(patom)
+ NodePtr patom;
+{
+ if (patom->left)
+ free_atom(patom->left);
+ if (patom->right)
+ free_atom(patom->right);
+ if (patom->a > FSA_LAST_PREDEFINED)
+ fsfree(patom->string);
+ fsfree(patom);
+}
+
+static void
+free_all_atoms()
+{
+ if (atomRoot == (NodePtr) NULL)
+ return;
+ free_atom(atomRoot);
+ atomRoot = (NodePtr) NULL;
+ fsfree(nodeTable);
+ nodeTable = (NodePtr *) NULL;
+ lastAtom = None;
+}
+
+void
+InitAtoms()
+{
+ free_all_atoms();
+ tableLength = InitialTableSize;
+ nodeTable = (NodePtr *) fsalloc(InitialTableSize * sizeof(NodePtr));
+ if (!nodeTable)
+ atom_error();
+ nodeTable[None] = (NodePtr) NULL;
+ lastAtom = FSA_LAST_PREDEFINED;
+}
diff --git a/difs/cache.c b/difs/cache.c
new file mode 100644
index 0000000..e8b6280
--- /dev/null
+++ b/difs/cache.c
@@ -0,0 +1,388 @@
+/* $Xorg: cache.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)cache.c 4.2 91/05/02
+ *
+ */
+#include "cachestr.h"
+#include "misc.h"
+
+#define INITBUCKETS 64
+#define INITHASHSIZE 6
+#define MAXHASHSIZE 11
+
+
+#define ENTRYOFFSET 22
+#define CACHE_ENTRY_MASK 0x3FFFFF
+#define CACHE_ENTRY_BITS(id) ((id) & 0x1fc00000)
+#define CACHE_ID(id) ((int)(CACHE_ENTRY_BITS(id) >> ENTRYOFFSET))
+
+#define NullCacheEntry ((CacheEntryPtr) 0)
+
+#define MAX_NUM_CACHES 32
+/* XXX make this dynamic? */
+static CachePtr caches[MAX_NUM_CACHES];
+static int num_caches = 1;
+
+/*-
+ * Notes on cache implementation
+ *
+ * This is basically the X11 resource code, with some modifications
+ * to handle aging.
+ *
+ * Its currently optimized for lookup & store. Flushing old stuff
+ * is a lot slower than it should probably be, but there's tradeoffs
+ * in tuning.
+ */
+
+Cache
+CacheInit(maxsize)
+ unsigned long maxsize;
+{
+ Cache id = (Cache) num_caches;
+ CachePtr cache;
+
+ cache = (CachePtr) fsalloc(sizeof(CacheRec));
+ if (!cache)
+ return (Cache) 0;
+ cache->entries = (CacheEntryPtr *)
+ fsalloc(INITBUCKETS * sizeof(CacheEntryPtr));
+ bzero((char *) cache->entries, (INITBUCKETS * sizeof(CacheEntryPtr)));
+ if (!cache->entries) {
+ fsfree(cache);
+ return (Cache) 0;
+ }
+ caches[id] = cache;
+ cache->elements = 0;
+ cache->buckets = INITBUCKETS;
+ cache->hashsize = INITHASHSIZE;
+ cache->maxsize = maxsize;
+ cache->cursize = 0;
+ cache->nextid = id << ENTRYOFFSET;
+ cache->id = id;
+ num_caches++;
+ return id;
+}
+
+static int
+hash(cid)
+ CacheID cid;
+{
+ CachePtr cache = caches[CACHE_ID(cid)];
+
+ switch (cache->hashsize) {
+#ifdef DEBUG /* only need this if INITHASHSIZE < 6 */
+ case 2:
+ return ((int) (0x03 & (cid ^ (cid >> 2) ^ (cid >> 8))));
+ case 3:
+ return ((int) (0x07 & (cid ^ (cid >> 3) ^ (cid >> 9))));
+ case 4:
+ return ((int) (0x0F & (cid ^ (cid >> 4) ^ (cid >> 10))));
+ case 5:
+ return ((int) (0x01F & (cid ^ (cid >> 5) ^ (cid >> 11))));
+#endif
+ case 6:
+ return ((int) (0x03F & (cid ^ (cid >> 6) ^ (cid >> 12))));
+ case 7:
+ return ((int) (0x07F & (cid ^ (cid >> 7) ^ (cid >> 13))));
+ case 8:
+ return ((int) (0x0FF & (cid ^ (cid >> 8) ^ (cid >> 16))));
+ case 9:
+ return ((int) (0x1FF & (cid ^ (cid >> 9))));
+ case 10:
+ return ((int) (0x3FF & (cid ^ (cid >> 10))));
+ case 11:
+ return ((int) (0x7FF & (cid ^ (cid >> 11))));
+ }
+ return -1;
+}
+
+static void
+rebuild_cache(cache)
+ CachePtr cache;
+{
+ int j;
+ CacheEntryPtr cp,
+ next,
+ **tails,
+ *entries,
+ **tptr,
+ *cptr;
+
+ assert(cache);
+ j = 2 * cache->buckets;
+ tails = (CacheEntryPtr **) ALLOCATE_LOCAL(j * sizeof(CacheEntryPtr *));
+ if (!tails)
+ return;
+ entries = (CacheEntryPtr *) fsalloc(j * sizeof(CacheEntryPtr));
+ if (entries) {
+ DEALLOCATE_LOCAL(tails);
+ return;
+ }
+ for (cptr = entries, tptr = tails; --j >= 0; cptr++, tptr++) {
+ *cptr = NullCacheEntry;
+ *tptr = cptr;
+ }
+ cache->hashsize++;
+ for (j = cache->buckets, cptr = cache->entries; --j >= 0; cptr++) {
+ for (cp = *cptr; cp; cp = next) {
+ next = cp->next;
+ cp->next = NullCacheEntry;
+ tptr = &tails[hash(cp->id)];
+ **tptr = cp;
+ *tptr = &cp->next;
+ }
+ }
+ DEALLOCATE_LOCAL(tails);
+ cache->buckets *= 2;
+ fsfree(cache->entries);
+ cache->entries = entries;
+}
+
+/*
+ * throws out all existing entries
+ */
+void
+CacheReset()
+{
+ CacheEntryPtr cp;
+ CachePtr cache;
+ int i,
+ j;
+
+ for (j = 0; j < num_caches; j++) {
+ cache = caches[j];
+ if (!cache)
+ continue;
+ for (i = 0; i < cache->buckets; i++) {
+ for (cp = cache->entries[i]; cp; cp = cp->next) {
+ cache->elements--;
+ cache->cursize -= cp->size;
+ (*cp->free_func) (cp->id, cp->data, CacheWasReset);
+ fsfree(cp);
+ }
+ cache->entries[i] = (CacheEntryPtr) 0;
+ }
+ assert(cache->cursize == 0);
+ }
+}
+
+static void
+flush_cache(cache, needed)
+ CachePtr cache;
+ unsigned long needed;
+{
+/* XXX -- try to set oldprev properly inside search loop */
+ CacheEntryPtr cp,
+ oldest,
+ *oldprev;
+ int oldbucket,
+ i;
+
+ while ((cache->cursize + needed) > cache->maxsize) {
+ oldest = (CacheEntryPtr) 0;
+ /* find oldest */
+ for (i = 0; i < cache->buckets; i++) {
+ cp = cache->entries[i];
+ if (!cp)
+ continue;
+ if (!oldest) {
+ oldbucket = i;
+ oldest = cp;
+ }
+ while (cp) {
+ if (cp->timestamp < oldest->timestamp) {
+ oldest = cp;
+ oldbucket = i;
+ }
+ cp = cp->next;
+ }
+ }
+ /* fixup list */
+ oldprev = &cache->entries[oldbucket];
+ cp = *oldprev;
+ for (; cp = *oldprev; oldprev = &cp->next) {
+ if (cp == oldest) {
+ *oldprev = oldest->next;
+ break;
+ }
+ }
+ /* clobber it */
+ cache->elements--;
+ cache->cursize -= oldest->size;
+ (*oldest->free_func) (oldest->id, oldest->data, CacheEntryOld);
+ fsfree(oldest);
+ }
+}
+
+void
+CacheResize(cid, newsize)
+ Cache cid;
+{
+ CachePtr cache = caches[cid];
+
+ if (!cache)
+ return;
+
+ if (newsize < cache->maxsize) {
+ /* have to toss some stuff */
+ flush_cache(cache, cache->maxsize - newsize);
+ }
+ cache->maxsize = newsize;
+}
+
+CacheID
+CacheStoreMemory(cid, data, size, free_func)
+ Cache cid;
+ pointer data;
+ unsigned long size;
+ CacheFree free_func;
+{
+ CacheID id;
+ CacheEntryPtr cp,
+ *head;
+ CachePtr cache = caches[cid];
+
+ if (size > cache->maxsize) /* beyond cache limits */
+ return (CacheID) 0;
+
+ if ((cache->elements >= 4 * cache->buckets) &&
+ (cache->hashsize < MAXHASHSIZE)) {
+ rebuild_cache(cache);
+ }
+ id = cache->nextid++;
+
+ if ((cache->cursize + size) > cache->maxsize) {
+ flush_cache(cache, size);
+ }
+ head = &cache->entries[hash(id)];
+ cp = (CacheEntryPtr) fsalloc(sizeof(CacheEntryRec));
+ if (!cp) {
+ return (CacheID) 0;
+ }
+ cp->next = *head;
+ cp->id = id;
+ cp->timestamp = GetTimeInMillis();
+ cp->free_func = free_func;
+ cp->size = size;
+ cp->data = data;
+ cache->cursize += size;
+ cache->elements++;
+ *head = cp;
+
+ return id;
+}
+
+pointer
+CacheFetchMemory(cid, update)
+ CacheID cid;
+ Bool update;
+{
+ CachePtr cache = caches[CACHE_ID(cid)];
+ CacheEntryPtr cp,
+ *head;
+
+ head = &cache->entries[hash(cid)];
+ for (cp = *head; cp; cp = cp->next) {
+ if (cp->id == cid) {
+ if (update) {
+ cp->timestamp = GetTimeInMillis();
+ if (cp != *head) { /* put it in the front */
+ cp->next = *head;
+ *head = cp;
+ }
+ }
+ return cp->data;
+ }
+ }
+ return (pointer) 0;
+}
+
+int
+CacheFreeMemory(cid, notify)
+ CacheID cid;
+ Bool notify;
+{
+ CachePtr cache = caches[CACHE_ID(cid)];
+ CacheEntryPtr cp,
+ *prev,
+ *head;
+ int *elptr;
+ int elements;
+ Bool found = FALSE;
+
+ head = &cache->entries[hash(cid)];
+ elptr = &cache->elements;
+ prev = head;
+ while ((cp = *prev) != NullCacheEntry) {
+ if (cp->id == cid) {
+ *prev = cp->next;
+ elements = --*elptr;
+ if (notify) {
+ (*(cp->free_func)) (cid, cp->data, CacheEntryFreed);
+ }
+ cache->cursize -= cp->size;
+ fsfree(cp);
+ if (*elptr != elements)
+ prev = head;
+ found = TRUE;
+ } else {
+ prev = &cp->next;
+ }
+ }
+ if (!found)
+ FatalError("Freeing cache entry %d which isn't there\n", cid);
+}
+
+/* ARGSUSED */
+void
+CacheSimpleFree(cid, data, reason)
+ CacheID cid;
+ pointer data;
+ int reason;
+{
+ fsfree(data);
+}
diff --git a/difs/charinfo.c b/difs/charinfo.c
new file mode 100644
index 0000000..f664311
--- /dev/null
+++ b/difs/charinfo.c
@@ -0,0 +1,631 @@
+/* $Xorg: charinfo.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+/*
+ * Defines GetExtents() and GetBitmaps(), which are
+ * called from routines in fontinfo.c.
+ * This file was once on the other side of
+ * the font library interface as util/fsfuncs.c.
+ */
+
+#include <X11/Xos.h>
+#include "misc.h"
+#include "fontstruct.h"
+#include "clientstr.h"
+#define FSMD_H
+#include "FSproto.h"
+
+extern void TwoByteSwap();
+extern void FourByteSwap();
+
+#define GLWIDTHBYTESPADDED(bits,nbytes) \
+ ((nbytes) == 1 ? (((bits)+7)>>3) /* pad to 1 byte */ \
+ :(nbytes) == 2 ? ((((bits)+15)>>3)&~1) /* pad to 2 bytes */ \
+ :(nbytes) == 4 ? ((((bits)+31)>>3)&~3) /* pad to 4 bytes */ \
+ :(nbytes) == 8 ? ((((bits)+63)>>3)&~7) /* pad to 8 bytes */ \
+ : 0)
+
+#define GLYPH_SIZE(ch, nbytes) \
+ GLWIDTHBYTESPADDED((ch)->metrics.rightSideBearing - \
+ (ch)->metrics.leftSideBearing, (nbytes))
+
+#define n2dChars(pfi) (((pfi)->lastRow - (pfi)->firstRow + 1) * \
+ ((pfi)->lastCol - (pfi)->firstCol + 1))
+
+static CharInfoRec junkDefault;
+
+static int
+getCharInfos (pfont, num_ranges, range, ink_metrics, nump, retp)
+ FontPtr pfont;
+ int num_ranges;
+ fsRange *range;
+ Bool ink_metrics;
+ int *nump; /* return */
+ CharInfoPtr **retp; /* return */
+{
+ CharInfoPtr *xchars, *xci;
+ int nchars;
+ FontInfoPtr pinfo = &pfont->info;
+ unsigned int r, c;
+ unsigned char ch[2];
+ int firstCol = pinfo->firstCol;
+ int firstRow = pinfo->firstRow;
+ int lastRow = pinfo->lastRow;
+ int lastCol = pinfo->lastCol;
+ int minCol, maxCol;
+ int num_cols = lastCol - firstCol + 1;
+ fsRange local_range, *rp;
+ int i;
+ FontEncoding encoding;
+ int err;
+ unsigned long glyphCount;
+ unsigned short defaultCh;
+ CharInfoPtr defaultPtr;
+ int (*metrics_func) ();
+
+ /*
+ * compute nchars
+ */
+ if (num_ranges == 0) {
+ if (lastRow)
+ nchars = n2dChars(pinfo);
+ else
+ nchars = lastCol - firstCol + 1;
+ local_range.min_char_low = firstCol;
+ local_range.min_char_high = firstRow;
+ local_range.max_char_low = lastCol;
+ local_range.max_char_high = lastRow;
+ range = &local_range;
+ num_ranges = 1;
+ } else {
+ nchars = 0;
+ for (i = 0, rp = range; i < num_ranges; i++, rp++) {
+ if (rp->min_char_high > rp->max_char_high ||
+ rp->min_char_low > rp->max_char_low)
+ return BadCharRange;
+ nchars += (rp->max_char_high - rp->min_char_high + 1) *
+ (rp->max_char_low - rp->min_char_low + 1);
+ }
+ }
+
+ xchars = (CharInfoPtr *) fsalloc (sizeof (CharInfoPtr) * nchars);
+ if (!xchars)
+ return AllocError;
+
+ if (ink_metrics)
+ metrics_func = pfont->get_metrics;
+ else
+ metrics_func = pfont->get_glyphs;
+
+ xci = xchars;
+ encoding = Linear16Bit;
+ if (lastRow)
+ encoding = TwoD16Bit;
+ defaultCh = pinfo->defaultCh;
+ ch[0] = defaultCh >> 8;
+ ch[1] = defaultCh & 0xff;
+ /* get the default character */
+ (*metrics_func) (pfont, 1, ch, encoding,
+ &glyphCount, &defaultPtr);
+ if (glyphCount != 1)
+ defaultPtr = 0;
+
+ /* for each range, get each character individually, undoing the
+ default character substitution so we get zero metrics for
+ non-existent characters. */
+ for (i = 0, rp = range; i < num_ranges; i++, rp++) {
+ for (r = rp->min_char_high; r <= rp->max_char_high; r++)
+ {
+ for (c = rp->min_char_low; c <= rp->max_char_low; c++) {
+ ch[0] = r;
+ ch[1] = c;
+ err = (*metrics_func) (pfont, 1, ch, encoding,
+ &glyphCount, xci);
+ if (err != Successful)
+ {
+ fsfree (xchars);
+ return err;
+ }
+ if (glyphCount != 1 ||
+ *xci == defaultPtr && defaultCh != ((r<<8)+c))
+ *xci = &junkDefault;
+ xci++;
+ }
+ }
+ }
+ *retp = xchars;
+ *nump = nchars;
+ return Successful;
+}
+
+int
+GetExtents(client, pfont, flags, num_ranges, range, num_extents, data)
+ ClientPtr client;
+ FontPtr pfont;
+ Mask flags;
+ unsigned long num_ranges;
+ fsRange *range;
+ unsigned long *num_extents; /* return */
+ fsXCharInfo **data; /* return */
+{
+ unsigned long size;
+ fsXCharInfo *ci;
+ fsXCharInfo cilocal;
+ char *pci;
+ CharInfoPtr *xchars, *xchars_cur;
+ CharInfoPtr xci;
+ int nchars;
+ int err;
+
+ if (flags & LoadAll)
+ num_ranges = 0;
+ err = getCharInfos (pfont, num_ranges, range,
+ client->major_version > 1 ? TRUE : FALSE,
+ &nchars, &xchars);
+ if (err != Successful)
+ return err;
+
+ size = SIZEOF(fsXCharInfo) * nchars;
+ pci = (char *) fsalloc(size);
+ if (!pci) {
+ fsfree (xchars);
+ return AllocError;
+ }
+
+ ci = (fsXCharInfo *) pci;
+ *num_extents = nchars;
+
+ /* pack the data */
+ xchars_cur = xchars;
+ while (nchars--) {
+ xci = *xchars_cur++;
+ cilocal.ascent = xci->metrics.ascent;
+ cilocal.descent = xci->metrics.descent;
+ cilocal.left = xci->metrics.leftSideBearing;
+ cilocal.right = xci->metrics.rightSideBearing;
+ cilocal.width = xci->metrics.characterWidth;
+ cilocal.attributes = xci->metrics.attributes;
+ memcpy(pci, &cilocal, SIZEOF(fsXCharInfo));
+ pci += SIZEOF(fsXCharInfo);
+ }
+
+ fsfree (xchars);
+
+ *data = ci;
+
+ return Successful;
+}
+
+static int
+packGlyphs (client, pfont, format, flags, num_ranges, range, tsize, num_glyphs,
+ offsets, data, freeData)
+ ClientPtr client;
+ FontPtr pfont;
+ int format;
+ Mask flags;
+ unsigned long num_ranges;
+ fsRange *range;
+ int *tsize;
+ unsigned long *num_glyphs;
+ fsOffset32 **offsets;
+ pointer *data;
+ int *freeData;
+{
+ int i;
+ fsOffset32 *lengths, *l;
+ unsigned long size = 0;
+ pointer gdata,
+ gd;
+ int bitorder, byteorder, scanlinepad, scanlineunit, mappad;
+ int height, dstbpr, charsize;
+ int dst_off, src_off;
+ Bool contiguous, reformat;
+ long nchars;
+ int src_glyph_pad = pfont->glyph;
+ int src_bit_order = pfont->bit;
+ int src_byte_order = pfont->byte;
+ int err;
+ int max_ascent, max_descent;
+ int min_left, max_right;
+ int srcbpr;
+ int lshift = 0, rshift = 0, dst_left_bytes = 0, src_left_bytes = 0;
+ unsigned char *srcp;
+ unsigned char *dstp;
+ unsigned char bits1, bits2;
+ int width;
+ int src_extra;
+ int dst_extra;
+ int r, w;
+ CharInfoPtr *bitChars, *bitCharsFree, bitc;
+ CharInfoPtr *inkChars, *inkCharsFree = 0, inkc;
+ FontInfoPtr pinfo = &pfont->info;
+ xCharInfo *bitm, *inkm;
+
+ err = CheckFSFormat(format, (fsBitmapFormatMask) ~ 0,
+ &bitorder, &byteorder, &scanlineunit, &scanlinepad, &mappad);
+
+ if (err != Successful)
+ return err;
+
+ if (flags & LoadAll)
+ num_ranges = 0;
+
+ err = getCharInfos (pfont, num_ranges, range, FALSE, &nchars, &bitCharsFree);
+
+ if (err != Successful)
+ return err;
+
+ /* compute dstbpr for padded out fonts */
+ reformat = bitorder != src_bit_order || byteorder != src_byte_order;
+
+ /* we need the ink metrics when shrink-wrapping a TE font (sigh),
+ * but only for protocol version > 1 */
+ if (mappad != BitmapFormatImageRectMax &&
+ pinfo->inkMetrics &&
+ client->major_version > 1)
+ {
+ err = getCharInfos (pfont, num_ranges, range, TRUE, &nchars, &inkCharsFree);
+ if (err != Successful)
+ {
+ fsfree (bitCharsFree);
+ return err;
+ }
+ reformat = TRUE;
+ }
+
+ /* get space for glyph offsets */
+ lengths = (fsOffset32 *) fsalloc(SIZEOF(fsOffset32) * nchars);
+ if (!lengths) {
+ fsfree (bitCharsFree);
+ fsfree (inkCharsFree);
+ return AllocError;
+ }
+
+ switch (mappad)
+ {
+ case BitmapFormatImageRectMax:
+ max_ascent = FONT_MAX_ASCENT(pinfo);
+ max_descent = FONT_MAX_DESCENT(pinfo);
+ height = max_ascent + max_descent;
+ /* do font ascent and font descent match bitmap bounds ? */
+ if (height != pinfo->minbounds.ascent + pinfo->minbounds.descent)
+ reformat = TRUE;
+ /* fall through */
+ case BitmapFormatImageRectMaxWidth:
+ min_left = FONT_MIN_LEFT(pinfo);
+ max_right = FONT_MAX_RIGHT(pinfo);
+ if (min_left != pinfo->maxbounds.leftSideBearing)
+ reformat = TRUE;
+ if (max_right != pinfo->maxbounds.rightSideBearing)
+ reformat = TRUE;
+ dstbpr = GLWIDTHBYTESPADDED(max_right - min_left, scanlinepad);
+ break;
+ case BitmapFormatImageRectMin:
+ break;
+ }
+ if (mappad == BitmapFormatImageRectMax)
+ charsize = dstbpr * height;
+ size = 0;
+ gdata = 0;
+ contiguous = TRUE;
+ l = lengths;
+ inkChars = inkCharsFree;
+ bitChars = bitCharsFree;
+ for (i = 0; i < nchars; i++)
+ {
+ inkc = bitc = *bitChars++;
+ /* when ink metrics != bitmap metrics, use ink metrics */
+ if (inkChars)
+ inkc = *inkChars++;
+ l->position = size;
+ /*
+ * Do not repad characters with no bits except for those
+ * with non-zero width.
+ */
+ if (bitc && (bitc->bits || bitc->metrics.characterWidth)) {
+ if (!gdata)
+ gdata = (pointer) bitc->bits;
+ if ((char *) gdata + size != bitc->bits)
+ contiguous = FALSE;
+ if (mappad == BitmapFormatImageRectMin)
+ dstbpr = GLYPH_SIZE(inkc, scanlinepad);
+ if (dstbpr != GLYPH_SIZE(bitc, src_glyph_pad)) reformat = TRUE;
+ if (mappad != BitmapFormatImageRectMax)
+ {
+ height = inkc->metrics.ascent + inkc->metrics.descent;
+ charsize = height * dstbpr;
+ }
+ l->length = charsize;
+ size += charsize;
+ }
+ else
+ l->length = 0;
+ l++;
+ }
+ if (contiguous && !reformat)
+ {
+ *num_glyphs = nchars;
+ *freeData = FALSE;
+ *data = gdata;
+ *tsize = size;
+ *offsets = lengths;
+ fsfree (bitCharsFree);
+ fsfree (inkCharsFree);
+ return Successful;
+ }
+ if (size)
+ {
+ gdata = (pointer) fsalloc(size);
+ if (!gdata) {
+ fsfree (bitCharsFree);
+ fsfree (inkCharsFree);
+ fsfree (lengths);
+ return AllocError;
+ }
+ bzero ((char *) gdata, size);
+ }
+ else
+ gdata = NULL;
+
+ *freeData = TRUE;
+ l = lengths;
+ gd = gdata;
+
+ /* finally do the work */
+ bitChars = bitCharsFree;
+ inkChars = inkCharsFree;
+ for (i = 0; i < nchars; i++, l++)
+ {
+ inkc = bitc = *bitChars++;
+ if (inkChars)
+ inkc = *inkChars++;
+
+ /* ignore missing chars */
+ if (l->length == 0)
+ continue;
+
+ bitm = &bitc->metrics;
+ inkm = &inkc->metrics;
+
+ /* start address for the destination of bits for this char */
+
+ dstp = gd;
+
+ if (mappad == BitmapFormatImageRectMax)
+ height = max_ascent + max_descent;
+ else
+ height = inkm->ascent + inkm->descent;
+
+ /* adjust destination and calculate shift offsets */
+ switch (mappad) {
+ case BitmapFormatImageRectMax:
+ /* leave the first padded rows blank */
+ if (max_ascent > inkm->ascent)
+ {
+ height -= (max_ascent - inkm->ascent);
+ dstp += dstbpr * (max_ascent - inkm->ascent);
+ }
+ if (max_descent > inkm->descent)
+ {
+ height -= (max_descent - inkm->descent);
+ }
+ /* fall thru */
+ case BitmapFormatImageRectMaxWidth:
+ dst_off = inkm->leftSideBearing - min_left;
+ if (dst_off < 0) dst_off = 0;
+ break;
+ case BitmapFormatImageRectMin:
+ dst_off = 0;
+ dstbpr = GLYPH_SIZE(inkc, scanlinepad);
+ break;
+ }
+
+ srcbpr = GLYPH_SIZE (bitc, src_glyph_pad);
+ srcp = (unsigned char *) bitc->bits;
+
+ /* adjust source */
+ src_off = 0;
+ if (inkm != bitm)
+ {
+ srcp += (bitm->ascent - inkm->ascent) * srcbpr;
+ src_off = inkm->leftSideBearing - bitm->leftSideBearing;
+ }
+
+ dst_left_bytes = dst_off >> 3;
+ dst_off &= 7;
+ src_left_bytes = src_off >> 3;
+ src_off &= 7;
+
+ /* minimum of source/dest bytes per row */
+ width = srcbpr - src_left_bytes;
+ if (width > dstbpr - dst_left_bytes)
+ width = dstbpr - dst_left_bytes;
+ /* extra bytes in source and dest for padding */
+ src_extra = srcbpr - width - src_left_bytes;
+ dst_extra = dstbpr - width - dst_left_bytes;
+
+#define MSBBitLeft(b,c) ((b) << (c))
+#define MSBBitRight(b,c) ((b) >> (c))
+#define LSBBitLeft(b,c) ((b) >> (c))
+#define LSBBitRight(b,c) ((b) << (c))
+
+ if (dst_off == src_off)
+ {
+ if (srcbpr == dstbpr && src_left_bytes == dst_left_bytes)
+ {
+ r = height * srcbpr;
+ memmove( dstp, srcp, r);
+ dstp += r;
+ }
+ else
+ {
+ for (r = height; r; r--)
+ {
+ dstp += dst_left_bytes;
+ srcp += src_left_bytes;
+ for (w = width; w; w--)
+ *dstp++ = *srcp++;
+ dstp += dst_extra;
+ srcp += src_extra;
+ }
+ }
+ }
+ else
+ {
+ if (dst_off > src_off)
+ {
+ rshift = dst_off - src_off;
+ lshift = 8 - rshift;
+ }
+ else
+ {
+ lshift = src_off - dst_off;
+ rshift = 8 - lshift;
+ /* run the loop one fewer time if necessary */
+ if (src_extra <= dst_extra)
+ {
+ dst_extra++;
+ width--;
+ }
+ else
+ src_extra--;
+ }
+
+ for (r = inkm->ascent + inkm->descent; r; r--)
+ {
+ dstp += dst_left_bytes;
+ srcp += src_left_bytes;
+ bits2 = 0;
+ /* fetch first part of source when necessary */
+ if (dst_off < src_off)
+ bits2 = *srcp++;
+ /*
+ * XXX I bet this does not work when
+ * src_bit_order != src_byte_order && scanlineunit > 1
+ */
+ for (w = width; w; w--)
+ {
+ bits1 = *srcp++;
+ if (src_bit_order == MSBFirst)
+ {
+ *dstp++ = MSBBitRight(bits1, rshift) |
+ MSBBitLeft (bits2, lshift);
+ }
+ else
+ {
+ *dstp++ = LSBBitRight(bits1, rshift) |
+ LSBBitLeft (bits2, lshift);
+ }
+ bits2 = bits1;
+ }
+ /* get the last few bits if we have a place to store them */
+ if (dst_extra > 0)
+ {
+ if (src_bit_order == MSBFirst)
+ *dstp = MSBBitLeft (bits2, lshift);
+ else
+ *dstp = LSBBitLeft (bits2, lshift);
+ }
+ dstp += dst_extra;
+ srcp += src_extra;
+ }
+ }
+ /* skip the amount we just filled in */
+ gd += l->length;
+ }
+
+
+ /* now do the bit, byte, word swapping */
+ if (bitorder != src_bit_order)
+ BitOrderInvert(gdata, size);
+ if (byteorder != src_byte_order)
+ {
+ if (scanlineunit == 2)
+ TwoByteSwap(gdata, size);
+ else if (scanlineunit == 4)
+ FourByteSwap(gdata, size);
+ }
+ fsfree (bitCharsFree);
+ fsfree (inkCharsFree);
+ *num_glyphs = nchars;
+ *data = gdata;
+ *tsize = size;
+ *offsets = lengths;
+
+ return Successful;
+}
+
+/* ARGSUSED */
+int
+GetBitmaps(client, pfont, format, flags, num_ranges, range,
+ size, num_glyphs, offsets, data, freeData)
+ ClientPtr client;
+ FontPtr pfont;
+ fsBitmapFormat format;
+ Mask flags;
+ unsigned long num_ranges;
+ fsRange *range;
+ int *size;
+ unsigned long *num_glyphs;
+ fsOffset32 **offsets;
+ pointer *data;
+ int *freeData;
+{
+ int err;
+
+ assert(pfont);
+
+ *size = 0;
+ *data = (pointer) 0;
+
+ err = LoadGlyphRanges(client, pfont, TRUE, num_ranges * 2, 0, range);
+
+ if (err != Successful)
+ return err;
+
+ return packGlyphs (client, pfont, format, flags,
+ num_ranges, range, size, num_glyphs,
+ offsets, data, freeData);
+}
diff --git a/difs/difsutils.c b/difs/difsutils.c
new file mode 100644
index 0000000..cbe1b2a
--- /dev/null
+++ b/difs/difsutils.c
@@ -0,0 +1,673 @@
+/* $Xorg: difsutils.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * misc utility routines
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#define XK_LATIN1
+#include <stdio.h>
+#include <ctype.h>
+#include "misc.h"
+#include "globals.h"
+#include "clientstr.h"
+#include "accstr.h"
+#include "fontstruct.h"
+#include <X11/keysymdef.h>
+
+#include "authstr.h"
+#include "auth.h"
+#include "client.h"
+
+extern ClientPtr currentClient;
+static FontResolutionPtr default_resolutions;
+static int num_resolutions;
+static int default_point_size = 120;
+
+AuthContextPtr
+GetClientAuthorization()
+{
+ return currentClient->auth;
+}
+
+void
+SetDefaultPointSize(ps)
+ int ps;
+{
+ int i;
+
+ default_point_size = ps;
+ for (i = 0; i < num_resolutions; i++)
+ default_resolutions[i].point_size = ps;
+}
+
+int
+SetDefaultResolutions(str)
+ char *str;
+{
+ int num,
+ numr = 0,
+ n;
+ char *s;
+ FontResolutionPtr new,
+ nr;
+ int state;
+
+ s = str;
+ while (*s) { /* count commas */
+ if (*s == ',')
+ numr++;
+ s++;
+ }
+
+ if ((numr % 2) != 1) { /* must be multiple of 2 + 1 */
+ return FSBadResolution;
+ }
+ numr = (numr + 1) / 2;
+ nr = new = (FontResolutionPtr) fsalloc(sizeof(FontResolutionRec)
+ * numr);
+ if (!new)
+ return FSBadAlloc;
+ s = str;
+ num = 0;
+ state = 0;
+ while (*s) {
+ if (*s == ',') {
+ if (state == 0) {
+ nr->x_resolution = num;
+ state++;
+ } else {
+ state = 0;
+ nr->y_resolution = num;
+ nr->point_size = default_point_size;
+ nr++;
+ }
+ num = 0;
+ s++;
+ continue;
+ }
+ if (!isdigit(*s)) {
+ fsfree((char *) new);
+ return FSBadResolution;
+ }
+ n = *s - '0';
+ num = num * 10 + n;
+ s++;
+ }
+
+ /* do the last one */
+ assert(state == 1);
+ nr->y_resolution = num;
+ nr->point_size = default_point_size;
+
+ if (default_resolutions) {
+ fsfree((char *) default_resolutions);
+ }
+ default_resolutions = new;
+ num_resolutions = numr;
+ return FSSuccess;
+}
+
+FontResolutionPtr
+GetClientResolutions(num)
+ int *num;
+{
+ /* return the client's if it has them, otherwise the default values */
+ if (currentClient->num_resolutions) {
+ *num = currentClient->num_resolutions;
+ return (FontResolutionPtr) currentClient->resolutions;
+ } else {
+ *num = num_resolutions;
+ return default_resolutions;
+ }
+}
+
+int
+GetDefaultPointSize()
+{
+ FontResolutionPtr res;
+ int num;
+
+ res = GetClientResolutions(&num);
+ if (res)
+ return res->point_size;
+ else
+ return default_point_size;
+}
+
+Bool
+XpClientIsBitmapClient(client)
+ ClientPtr client;
+{
+ return TRUE;
+}
+
+Bool
+XpClientIsPrintClient(client, fpe)
+ ClientPtr client;
+ FontPathElementPtr fpe;
+{
+ return FALSE;
+}
+
+void
+CopyISOLatin1Lowered(dest, source, length)
+ register unsigned char *dest,
+ *source;
+ int length;
+{
+ register int i;
+
+ for (i = 0; i < length; i++, source++, dest++) {
+ if ((*source >= XK_A) && (*source <= XK_Z))
+ *dest = *source + (XK_a - XK_A);
+ else if ((*source >= XK_Agrave) && (*source <= XK_Odiaeresis))
+ *dest = *source + (XK_agrave - XK_Agrave);
+ else if ((*source >= XK_Ooblique) && (*source <= XK_Thorn))
+ *dest = *source + (XK_oslash - XK_Ooblique);
+ else
+ *dest = *source;
+ }
+ *dest = '\0';
+}
+
+int
+strncmpnocase(first, second, n)
+ char *first,
+ *second;
+ int n;
+{
+ register unsigned char *ap,
+ *bp;
+
+ for (ap = (unsigned char *) first,
+ bp = (unsigned char *) second;
+ /* SUPPRESS 112 */
+ n > 0 && *ap && *bp; n--, ap++, bp++) {
+ register unsigned char a,
+ b;
+
+ /* SUPPRESS 112 */
+ if ((a = *ap) != (b = *bp)) {
+ /* try lowercasing and try again */
+
+ if ((a >= XK_A) && (a <= XK_Z))
+ a += (XK_a - XK_A);
+ else if ((a >= XK_Agrave) && (a <= XK_Odiaeresis))
+ a += (XK_agrave - XK_Agrave);
+ else if ((a >= XK_Ooblique) && (a <= XK_Thorn))
+ a += (XK_oslash - XK_Ooblique);
+
+ if ((b >= XK_A) && (b <= XK_Z))
+ b += (XK_a - XK_A);
+ else if ((b >= XK_Agrave) && (b <= XK_Odiaeresis))
+ b += (XK_agrave - XK_Agrave);
+ else if ((b >= XK_Ooblique) && (b <= XK_Thorn))
+ b += (XK_oslash - XK_Ooblique);
+
+ if (a != b)
+ break;
+ }
+ }
+ /* SUPPRESS 112 */
+ return (n ? (((int) *ap) - ((int) *bp)) : 0);
+}
+
+void
+NoopDDA()
+{
+}
+
+/* host list manipulation */
+int
+AddHost(list, addr)
+ HostList *list;
+ HostAddress *addr;
+{
+ HostAddress *new;
+
+ new = (HostAddress *) fsalloc(sizeof(HostAddress));
+ if (!new)
+ return FSBadAlloc;
+ new->address = (pointer) fsalloc(addr->addr_len);
+ if (!new->address) {
+ fsfree((char *) addr);
+ return FSBadAlloc;
+ }
+ new->type = addr->type;
+ new->addr_len = addr->addr_len;
+ memmove( (char *) new->address, (char *) addr->address, new->addr_len);
+
+ new->next = *list;
+ *list = new;
+ return FSSuccess;
+}
+
+int
+RemoveHost(list, addr)
+ HostList *list;
+ HostAddress *addr;
+{
+ HostAddress *t,
+ *last;
+
+ last = (HostAddress *) 0;
+ t = *list;
+ while (t) {
+ if (t->type == addr->type &&
+ t->addr_len == addr->addr_len &&
+ memcmp((char *) t->address, (char *) addr->address,
+ min(t->addr_len, addr->addr_len)) == 0) {
+ if (last) {
+ last->next = t->next;
+ } else {
+ *list = t->next;
+ }
+ fsfree((char *) t->address);
+ fsfree((char *) t);
+ return FSSuccess;
+ }
+ last = t;
+ t = t->next;
+ }
+ return FSBadName; /* bad host name */
+}
+
+Bool
+ValidHost(list, addr)
+ HostList list;
+ HostAddress *addr;
+{
+ HostAddress *t;
+
+ t = list;
+ while (t) {
+ if (t->type == addr->type &&
+ t->addr_len == addr->addr_len &&
+ memcmp((char *) t->address, (char *) addr->address,
+ min(t->addr_len, addr->addr_len)) == 0) {
+ return TRUE;
+ }
+ }
+ return FALSE;
+}
+
+/* block & wakeup handlers */
+
+typedef struct _BlockHandler {
+ void (*BlockHandler) ();
+ void (*WakeupHandler) ();
+ pointer blockData;
+ Bool deleted;
+} BlockHandlerRec, *BlockHandlerPtr;
+
+static BlockHandlerPtr handlers;
+static int numHandlers;
+static int sizeHandlers;
+static Bool inHandler;
+static Bool handlerDeleted;
+
+/* called from the OS layer */
+BlockHandler(pTimeout, pReadmask)
+ pointer pTimeout; /* DIX doesn't want to know how OS represents
+ * time */
+ pointer pReadmask; /* nor how it represents the set of
+ * descriptors */
+{
+ register int i,
+ j;
+
+ ++inHandler;
+ for (i = 0; i < numHandlers; i++)
+ (*handlers[i].BlockHandler) (handlers[i].blockData,
+ pTimeout, pReadmask);
+ if (handlerDeleted) {
+ for (i = 0; i < numHandlers;)
+ if (handlers[i].deleted) {
+ for (j = i; j < numHandlers - 1; j++)
+ handlers[j] = handlers[j + 1];
+ numHandlers--;
+ } else
+ i++;
+ }
+ --inHandler;
+}
+
+
+WakeupHandler(result, pReadmask)
+ int result; /* result from the wait */
+ pointer pReadmask; /* the resulting descriptor mask */
+{
+ register int i,
+ j;
+
+ ++inHandler;
+ for (i = numHandlers - 1; i >= 0; i--)
+ (*handlers[i].WakeupHandler) (handlers[i].blockData,
+ result, pReadmask);
+ if (handlerDeleted) {
+ for (i = 0; i < numHandlers;)
+ if (handlers[i].deleted) {
+ for (j = i; j < numHandlers - 1; j++)
+ handlers[j] = handlers[j + 1];
+ numHandlers--;
+ } else
+ i++;
+ }
+ --inHandler;
+}
+
+/* Reentrant with BlockHandler and WakeupHandler, except wakeup won't
+ * get called until next time
+ */
+
+Bool
+RegisterBlockAndWakeupHandlers(blockHandler, wakeupHandler, blockData)
+ void (*blockHandler) ();
+ void (*wakeupHandler) ();
+ pointer blockData;
+{
+ BlockHandlerPtr new;
+
+ if (numHandlers >= sizeHandlers) {
+ new = (BlockHandlerPtr) fsrealloc(handlers, (numHandlers + 1) *
+ sizeof(BlockHandlerRec));
+ if (!new)
+ return FALSE;
+ handlers = new;
+ sizeHandlers = numHandlers + 1;
+ }
+ handlers[numHandlers].BlockHandler = blockHandler;
+ handlers[numHandlers].WakeupHandler = wakeupHandler;
+ handlers[numHandlers].blockData = blockData;
+ numHandlers = numHandlers + 1;
+ return TRUE;
+}
+
+void
+RemoveBlockAndWakeupHandlers(blockHandler, wakeupHandler, blockData)
+ void (*blockHandler) ();
+ void (*wakeupHandler) ();
+ pointer blockData;
+{
+ int i;
+
+ for (i = 0; i < numHandlers; i++)
+ if (handlers[i].BlockHandler == blockHandler &&
+ handlers[i].WakeupHandler == wakeupHandler &&
+ handlers[i].blockData == blockData) {
+ if (inHandler) {
+ handlerDeleted = TRUE;
+ handlers[i].deleted = TRUE;
+ } else {
+ for (; i < numHandlers - 1; i++)
+ handlers[i] = handlers[i + 1];
+ numHandlers--;
+ }
+ break;
+ }
+}
+
+InitBlockAndWakeupHandlers()
+{
+ fsfree(handlers);
+ handlers = (BlockHandlerPtr) 0;
+ numHandlers = 0;
+ sizeHandlers = 0;
+}
+
+/*
+ * A general work queue. Perform some task before the server
+ * sleeps for input.
+ */
+
+WorkQueuePtr workQueue;
+static WorkQueuePtr *workQueueLast = &workQueue;
+
+/* ARGSUSED */
+void
+ProcessWorkQueue()
+{
+ WorkQueuePtr q,
+ n,
+ p;
+
+ p = NULL;
+ /*
+ * Scan the work queue once, calling each function. Those which return
+ * TRUE are removed from the queue, otherwise they will be called again.
+ * This must be reentrant with QueueWorkProc, hence the crufty usage of
+ * variables.
+ */
+ for (q = workQueue; q; q = n) {
+ if ((*q->function) (q->client, q->closure)) {
+ /* remove q from the list */
+ n = q->next; /* don't fetch until after func called */
+ if (p)
+ p->next = n;
+ else
+ workQueue = n;
+ fsfree(q);
+ } else {
+ n = q->next; /* don't fetch until after func called */
+ p = q;
+ }
+ }
+ if (p)
+ workQueueLast = &p->next;
+ else {
+ workQueueLast = &workQueue;
+ }
+}
+
+Bool
+QueueWorkProc(function, client, data)
+ Bool (*function) ();
+ ClientPtr client;
+ pointer data;
+{
+ WorkQueuePtr q;
+
+ q = (WorkQueuePtr) fsalloc(sizeof *q);
+ if (!q)
+ return FALSE;
+ q->function = function;
+ q->client = client;
+ q->closure = data;
+ q->next = NULL;
+ *workQueueLast = q;
+ workQueueLast = &q->next;
+ return TRUE;
+}
+
+/*
+ * Manage a queue of sleeping clients, awakening them
+ * when requested, by using the OS functions IgnoreClient
+ * and AttendClient. Note that this *ignores* the troubles
+ * with request data interleaving itself with events, but
+ * we'll leave that until a later time.
+ */
+
+typedef struct _SleepQueue {
+ struct _SleepQueue *next;
+ ClientPtr client;
+ Bool (*function) ();
+ pointer closure;
+} SleepQueueRec, *SleepQueuePtr;
+
+static SleepQueuePtr sleepQueue = NULL;
+
+Bool
+ClientSleep(client, function, data)
+ ClientPtr client;
+ Bool (*function) ();
+ pointer data;
+{
+ SleepQueuePtr q;
+
+ q = (SleepQueuePtr) fsalloc(sizeof *q);
+ if (!q)
+ return FALSE;
+
+ IgnoreClient(client);
+ q->next = sleepQueue;
+ q->client = client;
+ q->function = function;
+ q->closure = data;
+ sleepQueue = q;
+ return TRUE;
+}
+
+Bool
+ClientSignal(client)
+ ClientPtr client;
+{
+ SleepQueuePtr q;
+
+ for (q = sleepQueue; q; q = q->next)
+ if (q->client == client) {
+ return QueueWorkProc(q->function, q->client, q->closure);
+ }
+ return FALSE;
+}
+
+ClientWakeup(client)
+ ClientPtr client;
+{
+ SleepQueuePtr q,
+ *prev;
+
+ prev = &sleepQueue;
+ while ((q = *prev) != (SleepQueuePtr) 0) {
+ if (q->client == client) {
+ *prev = q->next;
+ fsfree(q);
+ if (client->clientGone == CLIENT_GONE)
+ CloseDownClient(client);
+ else
+ AttendClient(client);
+ break;
+ }
+ prev = &q->next;
+ }
+}
+
+Bool
+ClientIsAsleep(client)
+ ClientPtr client;
+{
+ SleepQueuePtr q;
+
+ for (q = sleepQueue; q; q = q->next)
+ if (q->client == client)
+ return TRUE;
+ return FALSE;
+}
+
+unsigned long *
+Xalloc(m)
+ unsigned long m;
+{
+ return fsalloc(m);
+}
+
+unsigned long *
+Xrealloc(n, m)
+ unsigned long *n,
+ m;
+{
+ return fsrealloc(n, m);
+}
+
+void
+Xfree(n)
+ unsigned long *n;
+{
+ fsfree(n);
+}
+
+int
+set_font_authorizations(authorizations, authlen, client)
+char **authorizations;
+int *authlen;
+ClientPtr client;
+{
+#define AUTH1_NAME "hp-hostname-1"
+#define AUTH2_NAME "hp-printername-1"
+ static char result[1024];
+ char *p;
+ AuthContextPtr acp = client->auth;
+ int len1, len2;
+
+ if (acp != NULL && acp->authname != NULL && acp->authdata != NULL &&
+ (!strcmp(AUTH1_NAME, acp->authname) ||
+ !strcmp(AUTH2_NAME, acp->authname)) &&
+ (len1 = strlen(acp->authname) + 1) +
+ (len2 = strlen(acp->authdata) + 1) + 2 * sizeof(short) <= 1024)
+ {
+ p = result;
+ *p++ = len1 >> 8;
+ *p++ = len1 &0xff;
+ *p++ = len2 >> 8;
+ *p++ = len2 & 0xff;
+ memmove( p, acp->authname, len1);
+ p += len1;
+ memmove( p, acp->authdata, len2);
+ p += len2;
+ *authlen = p - result;
+ *authorizations = result;
+ return 1;
+ }
+
+ *authlen = 0;
+ return 0;
+}
+
+int
+client_auth_generation(client)
+ClientPtr client;
+{
+ return client->auth_generation;
+}
diff --git a/difs/dispatch.c b/difs/dispatch.c
new file mode 100644
index 0000000..ae0a563
--- /dev/null
+++ b/difs/dispatch.c
@@ -0,0 +1,1109 @@
+/* $Xorg: dispatch.c,v 1.6 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * protocol dispatcher
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FS.h"
+#include "FSproto.h"
+#include "clientstr.h"
+#include "authstr.h"
+#include "misc.h"
+#include "osstruct.h"
+#include "extentst.h"
+#include "globals.h"
+#include "resource.h"
+#include "difsfnst.h"
+#include "fontstruct.h"
+#include "site.h"
+#include "events.h"
+#include "cache.h"
+
+static void kill_all_clients();
+
+char dispatchException = 0;
+char isItTimeToYield;
+
+ClientPtr currentClient;
+
+static int nClients = 0;
+static int nextFreeClientID;
+
+extern char *ConnectionInfo;
+extern int ConnInfoLen;
+
+extern char *configfilename;
+
+extern Bool drone_server;
+
+extern void NotImplemented();
+
+extern int (*InitialVector[3]) ();
+extern int (*ProcVector[NUM_PROC_VECTORS]) ();
+extern int (*SwappedProcVector[NUM_PROC_VECTORS]) ();
+extern void (*EventSwapVector[NUM_EVENT_VECTORS]) ();
+extern void (*ReplySwapVector[NUM_PROC_VECTORS]) ();
+
+extern void Swap32Write(), Swap16Write(), CopySwap16Write();
+
+#define MAJOROP ((fsReq *)client->requestBuffer)->reqType
+
+#define ALL_FORMAT_BITS (BitmapFormatByteOrderMask | \
+ BitmapFormatBitOrderMask | \
+ BitmapFormatScanlineUnitMask | \
+ BitmapFormatScanlinePadMask | \
+ BitmapFormatImageRectMask)
+
+#define ALL_FORMAT_MASK_BITS (BitmapFormatMaskByte | \
+ BitmapFormatMaskBit | \
+ BitmapFormatMaskImageRectangle | \
+ BitmapFormatMaskScanLinePad | \
+ BitmapFormatMaskScanLineUnit)
+
+Dispatch()
+{
+ int nready,
+ result;
+ int *clientReady;
+ ClientPtr client;
+ int op;
+
+ nextFreeClientID = MINCLIENT;
+ nClients = 0;
+
+ clientReady = (int *) ALLOCATE_LOCAL(sizeof(int) * MaxClients);
+ if (!clientReady)
+ return;
+
+ while (1) {
+ /* wait for something */
+ nready = WaitForSomething(clientReady);
+
+ while (!dispatchException && (--nready >= 0)) {
+ client = currentClient = clients[clientReady[nready]];
+
+ /* Client can be NULL if CloseDownClient() is called during
+ this dispatchException loop. */
+ if (client == (ClientPtr)NULL) continue;
+
+ isItTimeToYield = FALSE;
+
+ while (!isItTimeToYield) {
+ result = ReadRequest(client);
+ if (result <= 0) {
+ if (result < 0)
+ CloseDownClient(client);
+ break;
+ }
+ client->sequence++;
+
+ if (result > (MAX_REQUEST_SIZE << 2))
+ result = FSBadLength;
+ else
+ {
+ op = MAJOROP;
+ if (op >= NUM_PROC_VECTORS)
+ result = ProcBadRequest (client);
+ else
+ result = (*client->requestVector[op]) (client);
+ }
+ if (result != FSSuccess) {
+ if (client->noClientException != FSSuccess)
+ CloseDownClient(client);
+ break;
+ }
+ }
+ FlushAllOutput ();
+ }
+ /* reset if server is a drone and has run out of clients */
+ if (drone_server && nClients == 0) {
+ dispatchException |= DE_RESET;
+ }
+ if (dispatchException) {
+ /* re-read the config file */
+ if (dispatchException & DE_RECONFIG) {
+ NoticeF("Re-reading config file\n");
+ if (ReadConfigFile(configfilename) != FSSuccess)
+ ErrorF("couldn't parse config file\n");
+ SetConfigValues();
+ dispatchException &= ~DE_RECONFIG;
+ }
+ /* flush all the caches */
+ if (dispatchException & DE_FLUSH) {
+ NoticeF("flushing all caches\n");
+ CacheReset();
+ dispatchException &= ~DE_FLUSH;
+ }
+ /* reset */
+ if (dispatchException & DE_RESET) {
+ NoticeF("resetting\n");
+ break;
+ }
+ /* die *now* */
+ if (dispatchException & DE_TERMINATE) {
+ NoticeF("terminating\n");
+ kill_all_clients();
+ exit(0);
+ break;
+ }
+ }
+ }
+ kill_all_clients();
+ dispatchException = 0;
+}
+
+int
+ProcInitialConnection(client)
+ ClientPtr client;
+{
+ REQUEST(fsFakeReq);
+ fsConnClientPrefix *prefix;
+ int whichbyte = 1;
+
+ nClients++;
+ prefix = (fsConnClientPrefix *) stuff+1;
+ if ((prefix->byteOrder != 'l') && (prefix->byteOrder != 'B'))
+ return (client->noClientException = -2);
+ if (((*(char *) &whichbyte) && (prefix->byteOrder == 'B')) ||
+ (!(*(char *) &whichbyte) && (prefix->byteOrder == 'l'))) {
+ client->swapped = TRUE;
+ SwapConnClientPrefix(prefix);
+ }
+ client->major_version = prefix->major_version;
+ client->minor_version = prefix->minor_version;
+ stuff->reqType = 2;
+ stuff->length += prefix->auth_len;
+ if (client->swapped) {
+ stuff->length = lswaps(stuff->length);
+ }
+ ResetCurrentRequest(client);
+ return client->noClientException;
+}
+
+int
+ProcEstablishConnection(client)
+ ClientPtr client;
+{
+ fsConnClientPrefix *prefix;
+ fsConnSetup csp;
+ int ret;
+ pointer auth_data,
+ ad;
+ char *server_auth_data;
+ AuthPtr client_auth;
+ int i,
+ num_alts,
+ altlen,
+ auth_accept,
+ auth_index,
+ auth_len;
+ AlternateServerPtr altservers;
+
+ REQUEST(fsFakeReq);
+
+ prefix = (fsConnClientPrefix *) stuff+1;
+ auth_data = (pointer) prefix + sz_fsConnClientPrefix;
+ client_auth = (AuthPtr) ALLOCATE_LOCAL(prefix->num_auths * sizeof(AuthRec));
+ if (!client_auth) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+/* XXXX -- this needs work for multiple auth replies */
+
+ /* build up a list of the stuff */
+ for (i = 0, ad = auth_data; i < (int)prefix->num_auths; i++) {
+ /* copy carefully in case wire data is not aligned */
+ client_auth[i].namelen = (((unsigned char *)ad)[0] << 8) +
+ ((unsigned char *)ad)[1];
+ ad += 2;
+ client_auth[i].datalen = (((unsigned char *)ad)[0] << 8) +
+ ((unsigned char *)ad)[1];
+ ad += 2;
+ client_auth[i].name = (char *) ad;
+ ad += client_auth[i].namelen;
+ client_auth[i].data = (char *) ad;
+ ad += client_auth[i].datalen;
+ }
+ num_alts = ListAlternateServers(&altservers);
+ for (i = 0, altlen = 0; i < num_alts; i++) {
+ /* subset + len + namelen + pad */
+ altlen += (2 + altservers[i].namelen + 3) >> 2;
+ }
+
+ auth_index = prefix->num_auths;
+ client->auth_generation = 0;
+ ret = CheckClientAuthorization(client, client_auth,
+ &auth_accept, &auth_index, &auth_len, &server_auth_data);
+ if (auth_index > 0)
+ {
+ AuthContextPtr authp;
+ authp = (AuthContextPtr) fsalloc(sizeof(AuthContextRec));
+ if (!authp) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ authp->authname = 0;
+ authp->authdata = 0;
+ authp->authname =
+ (char *) fsalloc(client_auth[auth_index - 1].namelen + 1);
+ authp->authdata =
+ (char *) fsalloc(client_auth[auth_index - 1].datalen + 1);
+ if (!authp->authname || !authp->authdata) {
+ fsfree((char *) authp->authname);
+ fsfree((char *) authp->authdata);
+ fsfree((char *) authp);
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ memmove( authp->authname, client_auth[auth_index - 1].name,
+ client_auth[auth_index - 1].namelen);
+ memmove( authp->authdata, client_auth[auth_index - 1].data,
+ client_auth[auth_index - 1].datalen);
+ /* Save it with a zero resource id... subsequent
+ SetAuthorizations of None will find it. And it will be freed
+ by FreeClientResources when the connection closes. */
+ if (!AddResource(client->index, 0, RT_AUTHCONT,(pointer) authp))
+ {
+ fsfree((char *) authp->authname);
+ fsfree((char *) authp->authdata);
+ fsfree((char *) authp);
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ client->auth = client->default_auth = authp;
+ }
+ else
+ client->auth = client->default_auth = (AuthContextPtr)0;
+
+ DEALLOCATE_LOCAL(client_auth);
+
+ if (ret != FSSuccess) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ csp.status = auth_accept;
+ if (client->major_version == 1)
+ /* we implement backwards compatibility for version 1.0 */
+ csp.major_version = client->major_version;
+ else
+ csp.major_version = FS_PROTOCOL;
+ csp.minor_version = FS_PROTOCOL_MINOR;
+ csp.num_alternates = num_alts;
+ csp.alternate_len = altlen;
+ csp.auth_len = auth_len >> 2;
+ csp.auth_index = auth_index;
+ if (client->swapped) {
+ WriteSConnSetup(client, &csp);
+ } else {
+ (void) WriteToClient(client, SIZEOF(fsConnSetup), (char *) &csp);
+ }
+
+ /* send the alternates info */
+ for (i = 0; i < num_alts; i++) {
+ char tmp[258];
+
+ /* WriteToClient pads, so we have to fake some things */
+ tmp[0] = altservers[i].subset;
+ tmp[1] = altservers[i].namelen;
+ memmove( (char *) &tmp[2], altservers[i].name, altservers[i].namelen);
+ (void) WriteToClient(client, altservers[i].namelen + 2, tmp);
+ }
+
+ if (auth_len)
+ (void) WriteToClient(client, auth_len, (char *) server_auth_data);
+
+ if (auth_accept != AuthSuccess) {
+ nClients--;
+ return (client->noClientException = -2);
+ }
+ client->requestVector = client->swapped ? SwappedProcVector : ProcVector;
+ client->sequence = 0;
+ if (client->swapped)
+ (void) WriteSConnectionInfo(client, ConnInfoLen, ConnectionInfo);
+ else
+ (void) WriteToClient(client, ConnInfoLen, ConnectionInfo);
+
+#ifdef DEBUG
+ fprintf(stderr, "Establishing new connection\n");
+#endif
+
+ return client->noClientException;
+}
+
+/*
+ * NOTE -- the incoming data may be mangled
+ */
+
+void
+SendErrToClient(client, error, data)
+ ClientPtr client;
+ int error;
+ pointer data; /* resource id, format, resolution, etc */
+{
+ fsError rep;
+ int extralen = 0;
+
+ switch (error) {
+ case FSBadFormat:
+ extralen = SIZEOF(fsBitmapFormat);
+ break;
+ case FSBadFont:
+ case FSBadAccessContext:
+ case FSBadIDChoice:
+ case FSBadEventMask:
+ if (data) {
+ if (client->swapped)
+ SwapLongs((long *) data, 1);
+ extralen = 4;
+ }
+ break;
+ case FSBadRange:
+ extralen = SIZEOF(fsRange);
+ break;
+ case FSBadResolution:
+ if (data) {
+ if (client->swapped)
+ SwapShorts((short *) data, 1);
+ /* note sneaky hack */
+ rep.pad = *(CARD16 *) data;
+ data += 2;
+ extralen = 4;
+ }
+ break;
+ case FSBadLength:
+ if (data) {
+ if (client->swapped)
+ SwapLongs((long *) data, 1);
+ extralen = 4;
+ }
+ break;
+ default:
+ /* nothing else to send */
+ break;
+ }
+
+ rep.type = FS_Error;
+ rep.sequenceNumber = client->sequence;
+ rep.request = error;
+ rep.major_opcode = ((fsReq *) client->requestBuffer)->reqType;
+ rep.minor_opcode = MinorOpcodeOfRequest(client),
+ rep.timestamp = GetTimeInMillis();
+ rep.length = (SIZEOF(fsError) + extralen) >> 2;
+
+ WriteErrorToClient(client, &rep);
+
+ if (extralen)
+ WriteToClient(client, extralen, (char *) data);
+}
+
+/* ARGSUSED */
+int
+ProcBadRequest(client)
+ ClientPtr client;
+{
+ SendErrToClient(client, FSBadRequest, NULL);
+ return FSBadRequest;
+}
+
+int
+ProcNoop(client)
+ ClientPtr client;
+{
+ REQUEST(fsReq);
+ REQUEST_AT_LEAST_SIZE(fsReq);
+
+ return client->noClientException;
+}
+
+int
+ProcListCatalogues(client)
+ ClientPtr client;
+{
+ int len,
+ num;
+ char *catalogues;
+ fsListCataloguesReply rep;
+
+ REQUEST(fsListCataloguesReq);
+ REQUEST_AT_LEAST_SIZE(fsListCataloguesReq);
+
+ num = ListCatalogues((char *)stuff + SIZEOF(fsListCataloguesReq),
+ stuff->nbytes, stuff->maxNames,
+ &catalogues, &len);
+ rep.type = FS_Reply;
+ rep.num_replies = 0;
+ rep.num_catalogues = num;
+ rep.sequenceNumber = client->sequence;
+ rep.length = (SIZEOF(fsListCataloguesReply) + len + 3) >> 2;
+
+ WriteReplyToClient(client, SIZEOF(fsListCataloguesReply), &rep);
+ (void) WriteToClient(client, len, (char *) catalogues);
+ fsfree((char *) catalogues);
+ return client->noClientException;
+}
+
+int
+ProcSetCatalogues(client)
+ ClientPtr client;
+{
+ char *new_cat;
+ int err,
+ len;
+ int num;
+
+ REQUEST(fsSetCataloguesReq);
+ REQUEST_AT_LEAST_SIZE(fsSetCataloguesReq);
+
+ if (stuff->num_catalogues == 0) {
+ /* use the default */
+ num = ListCatalogues("*", 1, 10000, &new_cat, &len);
+ } else {
+ num = stuff->num_catalogues;
+ err = ValidateCatalogues(&num, (char *)stuff + SIZEOF(fsSetCataloguesReq));
+ if (err == FSSuccess) {
+ len = (stuff->length << 2) - SIZEOF(fsSetCataloguesReq);
+ new_cat = (char *) fsalloc(len);
+ if (!new_cat)
+ return FSBadAlloc;
+ memmove( new_cat, (char *)stuff + SIZEOF(fsSetCataloguesReq), len);
+ } else {
+ SendErrToClient(client, err, (pointer) &num);
+ return err;
+ }
+ }
+ if (client->catalogues)
+ fsfree((char *) client->catalogues);
+ client->catalogues = new_cat;
+ client->num_catalogues = num;
+ return client->noClientException;
+}
+
+int
+ProcGetCatalogues(client)
+ ClientPtr client;
+{
+ int len,
+ i,
+ size;
+ char *cp;
+ fsGetCataloguesReply rep;
+
+ REQUEST(fsGetCataloguesReq);
+ REQUEST_AT_LEAST_SIZE(fsGetCataloguesReq);
+
+ for (i = 0, len = 0, cp = client->catalogues;
+ i < client->num_catalogues; i++) {
+ size = *cp++;
+ len += size + 1; /* str length + size byte */
+ cp += size;
+ }
+
+ rep.type = FS_Reply;
+ rep.num_catalogues = client->num_catalogues;
+ rep.sequenceNumber = client->sequence;
+ rep.length = (SIZEOF(fsGetCataloguesReply) + len + 3) >> 2;
+
+ WriteReplyToClient(client, SIZEOF(fsGetCataloguesReply), &rep);
+ (void) WriteToClient(client, len, client->catalogues);
+
+ return client->noClientException;
+}
+
+int
+ProcCreateAC(client)
+ ClientPtr client;
+{
+ fsCreateACReply rep;
+ AuthPtr acp;
+ AuthContextPtr authp;
+ int accept,
+ i,
+ err,
+ index,
+ size;
+ pointer ad;
+ char *auth_data;
+
+ REQUEST(fsCreateACReq);
+ REQUEST_AT_LEAST_SIZE(fsCreateACReq);
+
+ authp = (AuthContextPtr) LookupIDByType(client->index, stuff->acid,
+ RT_AUTHCONT);
+ if (authp) {
+ int aligned_acid = stuff->acid;
+ SendErrToClient(client, FSBadIDChoice, (pointer) &aligned_acid);
+ return FSBadIDChoice;
+ }
+ acp = 0;
+ if (stuff->num_auths)
+ {
+ acp = (AuthPtr) ALLOCATE_LOCAL(stuff->num_auths * sizeof(AuthRec));
+ if (!acp) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ }
+ /* build up a list of the stuff */
+ for (i = 0, ad = (pointer)stuff + SIZEOF(fsCreateACReq); i < (int)stuff->num_auths; i++) {
+ /* copy carefully in case data is not aligned */
+ acp[i].namelen = (((unsigned char *)ad)[0] << 8) +
+ ((unsigned char *)ad)[1];
+ ad += 2;
+ acp[i].datalen = (((unsigned char *)ad)[0] << 8) +
+ ((unsigned char *)ad)[1];
+ ad += 2;
+ acp[i].name = (char *) ad;
+ ad += acp[i].namelen;
+ acp[i].data = (char *) ad;
+ ad += acp[i].datalen;
+ }
+
+/* XXX needs work for AuthContinue */
+ index = stuff->num_auths;
+ err = CheckClientAuthorization(client, acp, &accept, &index, &size,
+ &auth_data);
+
+ if (err != FSSuccess) {
+ SendErrToClient(client, err, (pointer) 0);
+ if (acp)
+ DEALLOCATE_LOCAL(acp);
+ return err;
+ }
+ authp = (AuthContextPtr) fsalloc(sizeof(AuthContextRec));
+ if (!authp) {
+ goto alloc_failure;
+ }
+ authp->authname = 0;
+ authp->authdata = 0;
+ if (index > 0)
+ {
+ authp->authname = (char *) fsalloc(acp[index - 1].namelen + 1);
+ authp->authdata = (char *) fsalloc(acp[index - 1].datalen + 1);
+ if (!authp->authname || !authp->authdata) {
+ fsfree((char *) authp->authname);
+ fsfree((char *) authp->authdata);
+ fsfree((char *) authp);
+ goto alloc_failure;
+ }
+ memmove( authp->authname, acp[index - 1].name, acp[index - 1].namelen);
+ memmove( authp->authdata, acp[index - 1].data, acp[index - 1].datalen);
+ }
+ else
+ size = 0;
+ authp->acid = stuff->acid;
+ if (!AddResource(client->index, stuff->acid, RT_AUTHCONT,(pointer) authp))
+ {
+alloc_failure:
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ if (acp)
+ DEALLOCATE_LOCAL(acp);
+ return FSBadAlloc;
+ }
+ DEALLOCATE_LOCAL(acp);
+ rep.type = FS_Reply;
+ rep.status = accept;
+ rep.auth_index = index;
+ rep.sequenceNumber = client->sequence;
+ rep.length = (SIZEOF(fsCreateACReply) + size) >> 2;
+
+ WriteReplyToClient(client, SIZEOF(fsCreateACReply), &rep);
+ if (size)
+ (void) WriteToClient(client, size, auth_data);
+
+ return client->noClientException;
+}
+
+/* ARGSUSED */
+int
+DeleteAuthCont (value, id)
+ pointer value;
+ FSID id;
+{
+ AuthContextPtr authp = (AuthContextPtr) value;
+
+ if (authp->authname)
+ fsfree (authp->authname);
+ if (authp->authdata)
+ fsfree (authp->authdata);
+ fsfree (authp);
+ return 1;
+}
+
+int
+ProcFreeAC(client)
+ ClientPtr client;
+{
+ AuthContextPtr authp;
+
+ REQUEST(fsFreeACReq);
+ REQUEST_AT_LEAST_SIZE(fsFreeACReq);
+ authp = (AuthContextPtr) LookupIDByType(client->index, stuff->id,
+ RT_AUTHCONT);
+ if (!authp) {
+ int aligned_id = stuff->id;
+ SendErrToClient(client, FSBadIDChoice, (pointer) &aligned_id);
+ return FSBadIDChoice;
+ }
+ if (client->auth == authp)
+ client->auth = client->default_auth;
+ FreeResource(client->index, stuff->id, RT_NONE);
+ return client->noClientException;
+}
+
+int
+ProcSetAuthorization(client)
+ ClientPtr client;
+{
+ AuthContextPtr acp;
+
+ REQUEST(fsSetAuthorizationReq);
+ REQUEST_AT_LEAST_SIZE(fsSetAuthorizationReq);
+ acp = (AuthContextPtr) LookupIDByType(client->index, stuff->id,
+ RT_AUTHCONT);
+ if (!acp) {
+ int aligned_id = stuff->id;
+ SendErrToClient(client, FSBadIDChoice, (pointer) &aligned_id);
+ return FSBadIDChoice;
+ }
+ client->auth = acp; /* XXX does this need a refcount? */
+ return client->noClientException;
+}
+
+int
+ProcSetResolution(client)
+ ClientPtr client;
+{
+ fsResolution *new_res;
+
+ REQUEST(fsSetResolutionReq);
+ REQUEST_AT_LEAST_SIZE(fsSetResolutionReq);
+
+ new_res = (fsResolution *)
+ fsalloc(SIZEOF(fsResolution) * stuff->num_resolutions);
+ if (!new_res) {
+ SendErrToClient(client, FSBadAlloc, NULL);
+ return FSBadAlloc;
+ }
+ fsfree((char *) client->resolutions);
+ memmove( (char *) new_res, (char *)stuff + SIZEOF(fsSetResolutionReq),
+ (stuff->num_resolutions * SIZEOF(fsResolution)));
+ client->resolutions = new_res;
+ client->num_resolutions = stuff->num_resolutions;
+
+ return client->noClientException;
+}
+
+int
+ProcGetResolution(client)
+ ClientPtr client;
+{
+ fsGetResolutionReply reply;
+
+ REQUEST(fsReq);
+ REQUEST_AT_LEAST_SIZE(fsReq);
+
+ reply.type = FS_Reply;
+ reply.num_resolutions = client->num_resolutions;
+ reply.sequenceNumber = client->sequence;
+ reply.length = (SIZEOF(fsGetResolutionReply) +
+ client->num_resolutions * SIZEOF(fsResolution)) >> 2;
+
+ WriteReplyToClient(client, SIZEOF(fsGetResolutionReply), &reply);
+ if (client->swapped)
+ client->pSwapReplyFunc = CopySwap16Write;
+
+ WriteSwappedDataToClient(client,
+ (client->num_resolutions * SIZEOF(fsResolution)), client->resolutions);
+
+ return client->noClientException;
+}
+
+int
+ProcListFonts(client)
+ ClientPtr client;
+{
+ REQUEST(fsListFontsReq);
+ REQUEST_FIXED_SIZE(fsListFontsReq, stuff->nbytes);
+
+ return ListFonts(client, stuff->nbytes,
+ (unsigned char *)stuff + SIZEOF(fsListFontsReq),
+ stuff->maxNames);
+}
+
+int
+ProcListFontsWithXInfo(client)
+ ClientPtr client;
+{
+ REQUEST(fsListFontsWithXInfoReq);
+ REQUEST_FIXED_SIZE(fsListFontsWithXInfoReq, stuff->nbytes);
+
+ return StartListFontsWithInfo(client, stuff->nbytes,
+ (unsigned char *)stuff + SIZEOF(fsListFontsWithXInfoReq), stuff->maxNames);
+}
+
+int
+ProcOpenBitmapFont(client)
+ ClientPtr client;
+{
+ FontPtr pfont;
+ int nbytes,
+ err;
+ unsigned char *fname;
+
+ REQUEST(fsOpenBitmapFontReq);
+ fname = (unsigned char *)stuff + SIZEOF(fsOpenBitmapFontReq);
+ nbytes = *fname++;
+
+ REQUEST_FIXED_SIZE(fsOpenBitmapFontReq, (nbytes + 1));
+
+ pfont = (FontPtr) LookupIDByType(client->index, stuff->fid, RT_FONT);
+ if (pfont) {
+ int aligned_fid = stuff->fid;
+ SendErrToClient(client, FSBadIDChoice, (pointer) &aligned_fid);
+ return FSBadIDChoice;
+ }
+ if (stuff->format_hint != 0 &&
+ stuff->format_hint & ~ALL_FORMAT_BITS) {
+ int aligned_format_hint = stuff->format_hint;
+ SendErrToClient(client, FSBadFormat, (pointer) &aligned_format_hint);
+ return FSBadFormat;
+ }
+ if (stuff->format_mask & ~ALL_FORMAT_MASK_BITS) {
+ int aligned_format_mask = stuff->format_mask;
+ SendErrToClient(client, FSBadFormat, (pointer) &aligned_format_mask);
+ return FSBadFormat;
+ }
+ err = OpenFont(client, stuff->fid, stuff->format_hint, stuff->format_mask,
+ nbytes, (char *) fname);
+
+ if (err == FSSuccess) {
+ return client->noClientException;
+ } else {
+ return err;
+ }
+}
+int
+ProcQueryXInfo(client)
+ ClientPtr client;
+{
+ ClientFontPtr cfp;
+ int err,
+ lendata;
+ fsQueryXInfoReply reply;
+ fsPropInfo *prop_info;
+
+ REQUEST(fsQueryXInfoReq);
+
+ REQUEST_AT_LEAST_SIZE(fsQueryXInfoReq);
+
+ cfp = (ClientFontPtr) LookupIDByType(client->index, stuff->id, RT_FONT);
+ if (!cfp) {
+ int aligned_id = stuff->id;
+ SendErrToClient(client, FSBadFont, (pointer) &aligned_id);
+ return FSBadFont;
+ }
+ reply.type = FS_Reply;
+ reply.sequenceNumber = client->sequence;
+
+ /* get the header */
+ fsPack_XFontInfoHeader(&cfp->font->info, &reply, client->major_version);
+ err = convert_props(&cfp->font->info, &prop_info);
+
+ switch (err)
+ {
+ case Successful:
+ break;
+ case AllocError:
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return err;
+ default:
+ ErrorF("ProcQueryXInfo: unexpected return val %d from convert_props\n",
+ err);
+ SendErrToClient(client, FSBadImplementation, (pointer) 0);
+ return err;
+ }
+ lendata = SIZEOF(fsPropInfo) +
+ prop_info->num_offsets * SIZEOF(fsPropOffset) +
+ prop_info->data_len;
+
+ reply.length = (SIZEOF(fsQueryXInfoReply) + lendata + 3) >> 2;
+ WriteReplyToClient(client, SIZEOF(fsQueryXInfoReply), &reply);
+
+ if (client->swapped)
+ SwapPropInfo(prop_info);
+ (void) WriteToClient(client, lendata, (char *) prop_info);
+
+ fsfree((char *) prop_info);
+ return client->noClientException;
+}
+
+int
+ProcQueryXExtents(client)
+ ClientPtr client;
+{
+ ClientFontPtr cfp;
+ int err;
+ int item_size;
+
+ REQUEST(fsQueryXExtents8Req);
+
+ REQUEST_AT_LEAST_SIZE(fsQueryXExtents8Req);
+
+ cfp = (ClientFontPtr) LookupIDByType(client->index, stuff->fid, RT_FONT);
+ if (!cfp) {
+ int aligned_fid = stuff->fid;
+ SendErrToClient(client, FSBadFont, (pointer) &aligned_fid);
+ return FSBadFont;
+ }
+ item_size = (stuff->reqType == FS_QueryXExtents8) ? 1 : 2;
+
+ /* get the extents */
+ err = QueryExtents(client, cfp, item_size,
+ stuff->num_ranges, stuff->range,
+ (pointer)stuff + SIZEOF(fsQueryXExtents8Req));
+
+ if (err != FSSuccess) {
+ return err;
+ } else
+ return client->noClientException;
+}
+
+int
+ProcQueryXBitmaps(client)
+ ClientPtr client;
+{
+ ClientFontPtr cfp;
+ int err;
+ int item_size;
+
+ REQUEST(fsQueryXBitmaps8Req);
+
+ REQUEST_AT_LEAST_SIZE(fsQueryXBitmaps8Req);
+
+ cfp = (ClientFontPtr) LookupIDByType(client->index, stuff->fid, RT_FONT);
+ if (!cfp) {
+ int aligned_fid = stuff->fid;
+ SendErrToClient(client, FSBadFont, (pointer) &aligned_fid);
+ return FSBadFont;
+ }
+ if (stuff->format & ~ALL_FORMAT_BITS) {
+ int aligned_format = stuff->format;
+ SendErrToClient(client, FSBadFormat, (pointer) &aligned_format);
+ return FSBadFormat;
+ }
+ assert((stuff->reqType == FS_QueryXBitmaps8) || (stuff->reqType == FS_QueryXBitmaps16));
+ item_size = (stuff->reqType == FS_QueryXBitmaps8) ? 1 : 2;
+
+ /* get the glyphs */
+ err = QueryBitmaps(client, cfp, item_size, stuff->format,
+ stuff->num_ranges, stuff->range,
+ (pointer)stuff + SIZEOF(fsQueryXBitmaps8Req));
+
+ if (err != FSSuccess) {
+ return err;
+ } else {
+ return client->noClientException;
+ }
+}
+
+int
+ProcCloseFont(client)
+ ClientPtr client;
+{
+ ClientFontPtr cfp;
+
+ REQUEST(fsResourceReq);
+
+ REQUEST_SIZE_MATCH(fsResourceReq);
+ cfp = (ClientFontPtr) LookupIDByType(client->index, stuff->id, RT_FONT);
+ if (cfp) {
+ FreeResource(client->index, stuff->id, RT_NONE);
+ return client->noClientException;
+ } else {
+ int aligned_id = stuff->id;
+ SendErrToClient(client, FSBadFont, (pointer) &aligned_id);
+ return FSBadFont;
+ }
+}
+
+void
+CloseDownClient(client)
+ ClientPtr client;
+{
+ if (client->clientGone != CLIENT_GONE) {
+ DeleteClientFontStuff(client);
+ client->clientGone = CLIENT_GONE;
+ CloseDownConnection(client);
+ --nClients;
+ }
+
+ if (ClientIsAsleep(client))
+ ClientSignal(client);
+ else
+ {
+ FreeClientResources(client);
+ if (client->index < nextFreeClientID)
+ nextFreeClientID = client->index;
+ clients[client->index] = NullClient;
+#ifdef DebugConnectionTranslation
+ CheckFileNumbers();
+#endif /* DebugConnectionTranslation */
+
+#ifdef NOTYET
+ /* reset server when last client goes away */
+ if (client->requestVector != InitialVector && nClients == 0)
+ dispatchException |= DE_RESET;
+#endif
+
+ if (currentClient == client)
+ currentClient = serverClient;
+ fsfree(client);
+
+#ifdef DEBUG
+ fprintf(stderr, "Shut down client\n");
+#endif
+
+ while (!clients[currentMaxClients - 1])
+ currentMaxClients--;
+ }
+}
+
+static void
+kill_all_clients()
+{
+ int i;
+
+ for (i = MINCLIENT; i < currentMaxClients; i++) {
+ if (clients[i])
+ CloseDownClient(clients[i]);
+ }
+}
+
+void
+InitProcVectors()
+{
+ int i;
+
+ for (i = 0; i < NUM_PROC_VECTORS; i++) {
+ if (!ProcVector[i]) {
+ ProcVector[i] = SwappedProcVector[i] = ProcBadRequest;
+ ReplySwapVector[i] = NotImplemented;
+ }
+ }
+ for (i = FSLASTEvent; i < NUM_EVENT_VECTORS; i++) {
+ EventSwapVector[i] = NotImplemented;
+ }
+}
+
+InitClient(client, i, ospriv)
+ ClientPtr client;
+ int i;
+ pointer ospriv;
+{
+ client->index = i;
+ client->sequence = 0;
+ client->last_request_time = GetTimeInMillis();
+ client->clientGone = CLIENT_ALIVE;
+ client->noClientException = FSSuccess;
+ client->requestVector = InitialVector;
+ client->osPrivate = ospriv;
+ client->swapped = FALSE;
+
+ client->auth = (AuthContextPtr) 0;
+ client->catalogues = NULL;
+ client->num_catalogues = 0;
+ client->num_resolutions = 0;
+ client->resolutions = (fsResolution *) 0;
+ client->eventmask = (Mask) 0;
+}
+
+ClientPtr
+NextAvailableClient(ospriv)
+ pointer ospriv;
+{
+ int i;
+ ClientPtr client;
+ fsFakeReq data;
+ extern long MaxClients;
+
+ i = nextFreeClientID;
+ if (i == MaxClients)
+ return NullClient;
+
+ clients[i] = client = (ClientPtr) fsalloc(sizeof(ClientRec));
+ if (!client)
+ return NullClient;
+
+ InitClient(client, i, ospriv);
+
+ if (!InitClientResources(client)) {
+ fsfree(client);
+ return NullClient;
+ }
+ data.reqType = 1;
+ data.length = (sizeof(fsFakeReq) + SIZEOF(fsConnClientPrefix)) >> 2;
+ if (!InsertFakeRequest(client, (char *) &data, sizeof(fsFakeReq))) {
+ FreeClientResources(client);
+ fsfree(client);
+ return NullClient;
+ }
+ if (i == currentMaxClients)
+ currentMaxClients++;
+ while ((nextFreeClientID < MAXCLIENTS) && clients[nextFreeClientID])
+ nextFreeClientID++;
+
+ /* if we've maxed out, try to clone */
+ if (nextFreeClientID == MaxClients) {
+ CloneMyself();
+ }
+ return client;
+}
+
+MarkClientException(client)
+ ClientPtr client;
+{
+ client->noClientException = -2;
+}
diff --git a/difs/events.c b/difs/events.c
new file mode 100644
index 0000000..cd75ad4
--- /dev/null
+++ b/difs/events.c
@@ -0,0 +1,134 @@
+/* $Xorg: events.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * event handling stuff
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "clientstr.h"
+#include "FSproto.h"
+#include "globals.h"
+#include "events.h"
+
+extern void (*EventSwapVector[NUM_EVENT_VECTORS]) ();
+
+static Mask lastEventMask = FontChangeNotifyMask;
+
+#define AllEventMasks (lastEventMask | (lastEventMask - 1))
+
+void
+WriteErrorToClient(client, error)
+ ClientPtr client;
+ fsError *error;
+{
+ if (client->swapped) {
+ fsError errorTo;
+
+ SErrorEvent(error, &errorTo);
+ (void) WriteToClient(client, SIZEOF(fsError), (char *) &errorTo);
+ } else {
+ (void) WriteToClient(client, SIZEOF(fsError),
+ (char *) error);
+ }
+}
+
+int
+ProcSetEventMask(client)
+ ClientPtr client;
+{
+ REQUEST(fsSetEventMaskReq);
+ REQUEST_AT_LEAST_SIZE(fsSetEventMaskReq);
+
+ if (stuff->event_mask & ~AllEventMasks) {
+ SendErrToClient(client, FSBadEventMask, (pointer) stuff->event_mask);
+ return FSBadEventMask;
+ }
+ client->eventmask = stuff->event_mask;
+ return client->noClientException;
+}
+
+int
+ProcGetEventMask(client)
+ ClientPtr client;
+{
+ fsGetEventMaskReply rep;
+
+ REQUEST(fsGetEventMaskReq);
+ REQUEST_AT_LEAST_SIZE(fsGetEventMaskReq);
+
+ rep.type = FS_Reply;
+ rep.sequenceNumber = client->sequence;
+ rep.length = SIZEOF(fsGetEventMaskReply) >> 2;
+ rep.event_mask = client->eventmask;
+
+ return client->noClientException;
+}
+
+void
+SendKeepAliveEvent(client)
+ ClientPtr client;
+{
+ fsKeepAliveEvent ev;
+
+ ev.type = FS_Event;
+ ev.event_code = KeepAlive;
+ ev.sequenceNumber = client->sequence;
+ ev.length = SIZEOF(fsKeepAliveEvent) >> 2;
+ ev.timestamp = GetTimeInMillis();
+
+#ifdef DEBUG
+ fprintf(stderr, "client #%d is getting a KeepAlive\n", client->index);
+#endif
+
+ if (client->swapped) {
+ /* SErrorEvent requires two fsError pointers */
+ fsError evTo;
+
+ SErrorEvent((fsError *) & ev, (fsError *) &evTo);
+ (void) WriteToClient(client, SIZEOF(fsKeepAliveEvent), (char *) &evTo);
+ } else {
+ (void) WriteToClient(client, SIZEOF(fsKeepAliveEvent), (char *) &ev);
+ }
+}
diff --git a/difs/extensions.c b/difs/extensions.c
new file mode 100644
index 0000000..5c1f8b0
--- /dev/null
+++ b/difs/extensions.c
@@ -0,0 +1,306 @@
+/* $Xorg: extensions.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * font server extensions
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FSproto.h"
+#include "misc.h"
+#include "clientstr.h"
+#include "extentst.h"
+
+#define EXTENSION_BASE 128
+#define EXTENSION_EVENT_BASE 64
+#define LAST_EVENT 128
+#define LAST_ERROR 255
+
+static ExtensionEntry **extensions = (ExtensionEntry **) NULL;
+extern int (*ProcVector[]) ();
+extern int (*SwappedProcVector[]) ();
+extern void (*ReplySwapVector[]) ();
+
+int lastEvent = EXTENSION_EVENT_BASE;
+static int lastError = FirstExtensionError;
+static int NumExtensions = 0;
+
+
+ExtensionEntry *
+AddExtension(name, num_events, num_errors, main_proc, smain_proc,
+ closedown_proc, minorop_proc)
+ char *name;
+ int num_events;
+ int num_errors;
+ int (*main_proc) ();
+ int (*smain_proc) ();
+ void (*closedown_proc) ();
+ unsigned short (*minorop_proc) ();
+{
+ int i;
+ ExtensionEntry *ext,
+ **newexts;
+
+ if (!main_proc || !smain_proc || !closedown_proc || !minorop_proc)
+ return ((ExtensionEntry *) 0);
+ if ((lastEvent + num_events > LAST_EVENT) ||
+ (unsigned) (lastError + num_errors > LAST_ERROR))
+ return ((ExtensionEntry *) 0);
+ ext = (ExtensionEntry *) fsalloc(sizeof(ExtensionEntry));
+ if (!ext)
+ return ((ExtensionEntry *) 0);
+ ext->name = (char *) fsalloc(strlen(name) + 1);
+ ext->num_aliases = 0;
+ ext->aliases = (char **) NULL;
+ if (!ext->name) {
+ fsfree(ext);
+ return ((ExtensionEntry *) 0);
+ }
+ strcpy(ext->name, name);
+ i = NumExtensions;
+ newexts = (ExtensionEntry **) fsrealloc(extensions,
+ (i + 1) * sizeof(ExtensionEntry *));
+ if (!newexts) {
+ fsfree(ext->name);
+ fsfree(ext);
+ return ((ExtensionEntry *) 0);
+ }
+ NumExtensions++;
+ extensions = newexts;
+ extensions[i] = ext;
+ ext->index = i;
+ ext->base = i + EXTENSION_BASE;
+ ext->CloseDown = closedown_proc;
+ ext->MinorOpcode = minorop_proc;
+ ProcVector[i + EXTENSION_BASE] = main_proc;
+ SwappedProcVector[i + EXTENSION_BASE] = smain_proc;
+ if (num_events) {
+ ext->eventBase = lastEvent;
+ ext->eventLast = lastEvent + num_events;
+ lastEvent += num_events;
+ } else {
+ ext->eventBase = 0;
+ ext->eventLast = 0;
+ }
+ if (num_errors) {
+ ext->errorBase = lastError;
+ ext->errorLast = lastError + num_errors;
+ lastError += num_errors;
+ } else {
+ ext->errorBase = 0;
+ ext->errorLast = 0;
+ }
+ return ext;
+}
+
+Bool
+AddExtensionAlias(alias, ext)
+ char *alias;
+ ExtensionEntry *ext;
+{
+ char *name;
+ char **aliases;
+
+ aliases = (char **) fsrealloc(ext->aliases,
+ (ext->num_aliases + 1) * sizeof(char *));
+ if (!aliases)
+ return FALSE;
+ ext->aliases = aliases;
+ name = (char *) fsalloc(strlen(alias) + 1);
+ if (!name)
+ return FALSE;
+ strcpy(name, alias);
+ ext->aliases[ext->num_aliases++] = name;
+ return TRUE;
+}
+
+unsigned short
+StandardMinorOpcode(client)
+ ClientPtr client;
+{
+ return ((fsReq *) client->requestBuffer)->data;
+}
+
+unsigned short
+MinorOpcodeOfRequest(client)
+ ClientPtr client;
+{
+ unsigned char major;
+
+ major = ((fsReq *) client->requestBuffer)->reqType;
+ if (major < EXTENSION_BASE)
+ return 0;
+ major -= EXTENSION_BASE;
+ if (major >= NumExtensions)
+ return 0;
+ return (*extensions[major]->MinorOpcode) (client);
+}
+
+CloseDownExtensions()
+{
+ int i,
+ j;
+
+ for (i = NumExtensions - 1; i >= 0; i--) {
+ (*extensions[i]->CloseDown) (extensions[i]);
+ NumExtensions = i;
+ fsfree(extensions[i]->name);
+ for (j = extensions[i]->num_aliases; --j >= 0;)
+ fsfree(extensions[i]->aliases[j]);
+ fsfree(extensions[i]->aliases);
+ fsfree(extensions[i]);
+ }
+ fsfree(extensions);
+ extensions = (ExtensionEntry **) NULL;
+ lastEvent = EXTENSION_EVENT_BASE;
+ lastError = FirstExtensionError;
+}
+
+void
+InitExtensions()
+{
+}
+
+int
+ProcQueryExtension(client)
+ ClientPtr client;
+{
+ fsQueryExtensionReply reply;
+ int i,
+ j;
+
+ REQUEST(fsQueryExtensionReq);
+
+ REQUEST_AT_LEAST_SIZE(fsQueryExtensionReq);
+
+ reply.type = FS_Reply;
+ reply.length = SIZEOF(fsQueryExtensionReply) >> 2;
+ reply.major_opcode = 0;
+ reply.sequenceNumber = client->sequence;
+
+ if (!NumExtensions) {
+ reply.present = fsFalse;
+ } else {
+ for (i = 0; i < NumExtensions; i++) {
+ if ((strlen(extensions[i]->name) == stuff->nbytes) &&
+ !strncmp((char *) &stuff[1], extensions[i]->name,
+ (int) stuff->nbytes))
+ break;
+ for (j = extensions[i]->num_aliases; --j >= 0;) {
+ if ((strlen(extensions[i]->aliases[j]) == stuff->nbytes) &&
+ !strncmp((char *) &stuff[1], extensions[i]->aliases[j],
+ (int) stuff->nbytes))
+ break;
+ }
+ if (j >= 0)
+ break;
+ }
+ if (i == NumExtensions) {
+ reply.present = fsFalse;
+ } else {
+ reply.present = fsTrue;
+ reply.major_opcode = extensions[i]->base;
+ reply.first_event = extensions[i]->eventBase;
+ reply.first_error = extensions[i]->errorBase;
+ }
+
+ }
+ WriteReplyToClient(client, SIZEOF(fsQueryExtensionReply), &reply);
+ return client->noClientException;
+}
+
+int
+ProcListExtensions(client)
+ ClientPtr client;
+{
+ fsListExtensionsReply reply;
+ char *bufptr,
+ *buffer;
+ int total_length = 0;
+
+ REQUEST(fsListExtensionsReq);
+ REQUEST_SIZE_MATCH(fsListExtensionsReq);
+
+ reply.type = FS_Reply;
+ reply.nExtensions = NumExtensions;
+ reply.length = SIZEOF(fsListExtensionsReply) >> 2;
+ reply.sequenceNumber = client->sequence;
+ buffer = NULL;
+
+ if (NumExtensions) {
+ int i,
+ j;
+
+ for (i = 0; i < NumExtensions; i++) {
+ total_length += strlen(extensions[i]->name) + 1;
+ reply.nExtensions += extensions[i]->num_aliases;
+ for (j = extensions[i]->num_aliases; --j >= 0;)
+ total_length += strlen(extensions[i]->aliases[j]) + 1;
+ }
+ reply.length += (total_length + 3) >> 2;
+ buffer = bufptr = (char *) ALLOCATE_LOCAL(total_length);
+ if (!buffer) {
+ SendErrToClient(client, FSBadAlloc, NULL);
+ return FSBadAlloc;
+ }
+ for (i = 0; i < NumExtensions; i++) {
+ int len;
+
+ *bufptr++ = len = strlen(extensions[i]->name);
+ memmove( bufptr, extensions[i]->name, len);
+ bufptr += len;
+ for (j = extensions[i]->num_aliases; --j >= 0;) {
+ *bufptr++ = len = strlen(extensions[i]->aliases[j]);
+ memmove( bufptr, extensions[i]->aliases[j], len);
+ bufptr += len;
+ }
+ }
+ }
+ WriteReplyToClient(client, SIZEOF(fsListExtensionsReply), &reply);
+ if (total_length) {
+ WriteToClient(client, total_length, buffer);
+ DEALLOCATE_LOCAL(buffer);
+ }
+ return client->noClientException;
+}
diff --git a/difs/fontinfo.c b/difs/fontinfo.c
new file mode 100644
index 0000000..50ee743
--- /dev/null
+++ b/difs/fontinfo.c
@@ -0,0 +1,435 @@
+/* $Xorg: fontinfo.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * font data query
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FS.h"
+#include "FSproto.h"
+#include <stdio.h>
+#include <X11/Xos.h>
+#include "clientstr.h"
+#include "difsfnst.h"
+#include "fontstruct.h"
+#include "closestr.h"
+#include "globals.h"
+
+extern void (*ReplySwapVector[NUM_PROC_VECTORS]) ();
+
+void
+CopyCharInfo(ci, dst)
+ CharInfoPtr ci;
+ fsXCharInfo *dst;
+{
+ xCharInfo *src = &ci->metrics;
+
+ dst->ascent = src->ascent;
+ dst->descent = src->descent;
+ dst->left = src->leftSideBearing;
+ dst->right = src->rightSideBearing;
+ dst->width = src->characterWidth;
+ dst->attributes = src->attributes;
+}
+
+
+int
+convert_props(pinfo, props)
+ FontInfoPtr pinfo;
+ fsPropInfo **props;
+{
+ int i;
+ int data_len, cur_off;
+ char *str;
+ pointer ptr, off_ptr, string_base;
+ fsPropOffset local_offset;
+
+ /*
+ * compute the size of the property data
+ */
+ data_len = 0;
+ for (i = 0; i < pinfo->nprops; i++)
+ {
+ data_len += strlen(NameForAtom(pinfo->props[i].name));
+ if (pinfo->isStringProp[i])
+ data_len += strlen(NameForAtom(pinfo->props[i].value));
+ }
+
+ /*
+ * allocate the single chunk that the difs layer requires
+ */
+ ptr = (pointer) fsalloc(SIZEOF(fsPropInfo)
+ + SIZEOF(fsPropOffset) * pinfo->nprops
+ + data_len);
+ if (!ptr)
+ return AllocError;
+ string_base = ptr + SIZEOF(fsPropInfo) + SIZEOF(fsPropOffset) * pinfo->nprops;
+
+ /*
+ * copy in the header
+ */
+ ((fsPropInfo *)ptr)->num_offsets = pinfo->nprops;
+ ((fsPropInfo *)ptr)->data_len = data_len;
+
+ /*
+ * compute the offsets and copy the string data
+ */
+ off_ptr = ptr + SIZEOF(fsPropInfo);
+ cur_off = 0;
+ for (i = 0; i < pinfo->nprops; i++)
+ {
+ local_offset.name.position = cur_off;
+ str = NameForAtom(pinfo->props[i].name);
+ local_offset.name.length = strlen(str);
+ memmove( string_base+cur_off, str, local_offset.name.length);
+ cur_off += local_offset.name.length;
+ if (pinfo->isStringProp[i])
+ {
+ local_offset.value.position = cur_off;
+ str = NameForAtom(pinfo->props[i].value);
+ local_offset.value.length = strlen(str);
+ memmove( string_base+cur_off, str, local_offset.value.length);
+ cur_off += local_offset.value.length;
+ local_offset.type = PropTypeString;
+ } else {
+ local_offset.value.position = pinfo->props[i].value;
+ local_offset.value.length = 0; /* protocol says must be zero */
+ local_offset.type = PropTypeSigned;
+ }
+ memmove( off_ptr, &local_offset, SIZEOF(fsPropOffset));
+ off_ptr += SIZEOF(fsPropOffset);
+ }
+
+ assert(off_ptr == string_base);
+ assert(cur_off == data_len);
+
+ *props = (fsPropInfo *) ptr;
+ return Successful;
+}
+
+
+/*
+ * does the real work of turning a list of range (or chars) into
+ * a list of ranges
+ */
+static fsRange *
+build_range(type, src, item_size, num, all, pfi)
+ Bool type;
+ pointer src;
+ int item_size;
+ int *num;
+ Bool *all;
+ FontInfoPtr pfi;
+{
+ fsRange *new = (fsRange *) 0,
+ *np;
+ unsigned long src_num;
+ int i;
+
+ if (type) { /* range flag is set, deal with data as a list
+ * of char2bs */
+ char *rp = (char *) src;
+
+ src_num = *num;
+ if (src_num == 0) {
+ *all = TRUE;
+ return new;
+ }
+
+ np = new = (fsRange *) fsalloc(sizeof(fsRange) * (src_num + 1) / 2);
+ if (!np)
+ return np;
+ /* Build a new range */
+ for (i = 1; i < src_num; i += 2)
+ {
+ np->min_char_high = (item_size == 1) ? 0 : *rp++;
+ np->min_char_low = *rp++;
+ np->max_char_high = (item_size == 1) ? 0 : *rp++;
+ np->max_char_low = *rp++;
+ np++;
+ }
+
+ /* If src_num is odd, we need to determine the final range
+ by examining the fontinfo */
+ if (i == src_num)
+ {
+ np->min_char_high = (item_size == 1) ? 0 : *rp++;
+ np->min_char_low = *rp++;
+ np->max_char_high = pfi->lastRow;
+ np->max_char_low = pfi->lastCol;
+ np++;
+ }
+ *num = np - new;
+ return new;
+ } else { /* deal with data as a list of characters */
+ pointer pp = src;
+
+ src_num = *num;
+ np = new = (fsRange *) fsalloc(SIZEOF(fsRange) * src_num);
+ if (!np)
+ return np;
+
+ /* Build a range, with coalescence, from the list of chars */
+
+ for (i = 0; i < src_num; i++) {
+ if (item_size == 1) {
+ np->min_char_low = *pp;
+ np->min_char_high = 0;
+ } else {
+ np->min_char_low = ((fsChar2b *) pp)->low;
+ np->min_char_high = ((fsChar2b *) pp)->high;
+ }
+ np->max_char_high = np->min_char_high;
+ np->max_char_low = np->min_char_low;
+ /* Can we coalesce? */
+ if (np > new &&
+ np->max_char_high == np[-1].max_char_high &&
+ np->max_char_low == np[-1].max_char_low + 1)
+ np[-1].max_char_low++; /* Yes */
+ else
+ np++; /* No */
+ pp += item_size;
+ }
+ *num = np - new;
+ return new;
+ }
+}
+
+/*
+ * provide backward compatibility with version 1, which had
+ * the bytes of char2b backwards
+ */
+static void
+swap_char2b (values, number)
+ fsChar2b *values;
+ int number;
+{
+ fsChar2b temp;
+ int i;
+
+ for (i = 0; i < number; i++) {
+ temp.low = ((fsChar2b_version1 *)values)->low;
+ temp.high = ((fsChar2b_version1 *)values)->high;
+ *values++ = temp;
+ }
+}
+
+
+static Bool
+do_query_extents(client, c)
+ ClientPtr client;
+ QEclosurePtr c;
+{
+ int err;
+ unsigned long lendata,
+ num_extents;
+ fsXCharInfo *extents;
+ fsQueryXExtents8Reply reply;
+
+ err = GetExtents (c->client, c->pfont,
+ c->flags, c->nranges, c->range, &num_extents, &extents);
+ if (err == Suspended) {
+ if (!c->slept) {
+ c->pfont->unload_glyphs = 0; /* Not a safe call for this font */
+ c->slept = TRUE;
+ ClientSleep(client, do_query_extents, (pointer) c);
+ }
+ return TRUE;
+ }
+ if (err != Successful) {
+ SendErrToClient(c->client, FontToFSError(err), (pointer) 0);
+ goto finish;
+ }
+ reply.type = FS_Reply;
+ reply.sequenceNumber = c->client->sequence;
+ reply.num_extents = num_extents;
+ lendata = SIZEOF(fsXCharInfo) * num_extents;
+ reply.length = (SIZEOF(fsQueryXExtents8Reply) + lendata) >> 2;
+ if (client->swapped)
+ SwapExtents(extents, num_extents);
+ WriteReplyToClient(c->client, SIZEOF(fsQueryXExtents8Reply), &reply);
+ (void) WriteToClient(c->client, lendata, (char *) extents);
+ fsfree((char *) extents);
+finish:
+ if (c->slept)
+ ClientWakeup(c->client);
+ if (c->pfont->unload_glyphs) /* For rasterizers that want to save memory */
+ (*c->pfont->unload_glyphs)(c->pfont);
+ fsfree(c->range);
+ fsfree(c);
+ return TRUE;
+}
+
+int
+QueryExtents(client, cfp, item_size, nranges, range_flag, range_data)
+ ClientPtr client;
+ ClientFontPtr cfp;
+ int item_size;
+ int nranges;
+ Bool range_flag;
+ pointer range_data;
+{
+ QEclosurePtr c;
+ fsRange *fixed_range;
+ Bool all_glyphs = FALSE;
+
+ if (item_size == 2 && client->major_version == 1)
+ swap_char2b (range_data, nranges);
+
+ fixed_range = build_range(range_flag, range_data, item_size,
+ &nranges, &all_glyphs, &cfp->font->info);
+
+ if (!fixed_range && !all_glyphs) {
+ SendErrToClient(client, FSBadRange, 0);
+ return FSBadRange;
+ }
+ c = (QEclosurePtr) fsalloc(sizeof(QEclosureRec));
+ if (!c)
+ return FSBadAlloc;
+ c->client = client;
+ c->slept = FALSE;
+ c->pfont = cfp->font;
+ c->flags = (all_glyphs) ? LoadAll : 0;
+ c->flags |= (item_size == 1) ? EightBitFont : SixteenBitFont;
+ c->nranges = nranges;
+ c->range = fixed_range;
+
+ (void) do_query_extents(client, c);
+ return FSSuccess;
+}
+
+static Bool
+do_query_bitmaps(client, c)
+ ClientPtr client;
+ QBclosurePtr c;
+{
+ int err;
+ unsigned long num_glyphs, data_size;
+ fsOffset32 *offsets;
+ pointer glyph_data;
+ fsQueryXBitmaps8Reply reply;
+ int freedata;
+
+ err = GetBitmaps (c->client, c->pfont, c->format,
+ c->flags, c->nranges, c->range,
+ &data_size, &num_glyphs, &offsets, &glyph_data, &freedata);
+
+ if (err == Suspended) {
+ if (!c->slept) {
+ c->pfont->unload_glyphs = 0; /* Not a safe call for this font */
+ c->slept = TRUE;
+ ClientSleep(client, do_query_bitmaps, (pointer) c);
+ }
+ return TRUE;
+ }
+ if (err != Successful) {
+ SendErrToClient(c->client, FontToFSError(err), (pointer) 0);
+ goto finish;
+ }
+ reply.type = FS_Reply;
+ reply.sequenceNumber = c->client->sequence;
+ reply.replies_hint = 0;
+ reply.num_chars = num_glyphs;
+ reply.nbytes = data_size;
+ reply.length = (SIZEOF(fsQueryXBitmaps8Reply) + data_size +
+ (SIZEOF(fsOffset32) * num_glyphs) + 3) >> 2;
+
+ WriteReplyToClient(c->client, SIZEOF(fsQueryXBitmaps8Reply), &reply);
+ if (client->swapped)
+ SwapLongs((long *)offsets, num_glyphs * 2);
+ (void) WriteToClient(c->client, (num_glyphs * SIZEOF(fsOffset32)),
+ (char *) offsets);
+ (void) WriteToClient(c->client, data_size, (char *) glyph_data);
+ fsfree((char *) offsets);
+ if (freedata)
+ fsfree((char *) glyph_data);
+finish:
+ if (c->slept)
+ ClientWakeup(c->client);
+ if (c->pfont->unload_glyphs) /* For rasterizers that want to save memory */
+ (*c->pfont->unload_glyphs)(c->pfont);
+ fsfree(c->range);
+ fsfree(c);
+ return TRUE;
+}
+
+int
+QueryBitmaps(client, cfp, item_size, format, nranges, range_flag, range_data)
+ ClientPtr client;
+ ClientFontPtr cfp;
+ int item_size;
+ fsBitmapFormat format;
+ int nranges;
+ Bool range_flag;
+ pointer range_data;
+{
+ QBclosurePtr c;
+ fsRange *fixed_range;
+ Bool all_glyphs = FALSE;
+
+ if (item_size == 2 && client->major_version == 1)
+ swap_char2b (range_data, nranges);
+
+ fixed_range = build_range(range_flag, range_data, item_size,
+ &nranges, &all_glyphs, &cfp->font->info);
+
+ if (!fixed_range && !all_glyphs) {
+ SendErrToClient(client, FSBadRange, 0);
+ return FSBadRange;
+ }
+ c = (QBclosurePtr) fsalloc(sizeof(QBclosureRec));
+ if (!c)
+ return FSBadAlloc;
+ c->client = client;
+ c->slept = FALSE;
+ c->pfont = cfp->font;
+ c->flags = (all_glyphs) ? LoadAll : 0;
+ c->nranges = nranges;
+ c->range = fixed_range;
+ c->format = format;
+
+ (void) do_query_bitmaps(client, c);
+ return FSSuccess;
+}
diff --git a/difs/fonts.c b/difs/fonts.c
new file mode 100644
index 0000000..a3f6a9f
--- /dev/null
+++ b/difs/fonts.c
@@ -0,0 +1,1552 @@
+/* $Xorg: fonts.c,v 1.5 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * font control
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FS.h"
+#include "FSproto.h"
+#include <stdio.h>
+#include <X11/Xos.h>
+#include "clientstr.h"
+#include "resource.h"
+#include "difsfnst.h"
+#include "fontstruct.h"
+#include "closestr.h"
+#include "globals.h"
+
+extern void (*ReplySwapVector[NUM_PROC_VECTORS]) ();
+extern FSID FakeClientID();
+
+static FontPathElementPtr *font_path_elements = (FontPathElementPtr *) 0;
+static int num_fpes = 0;
+static FPEFunctions *fpe_functions = (FPEFunctions *) 0;
+static int num_fpe_types = 0;
+
+static int num_slept_fpes = 0;
+static int size_slept_fpes = 0;
+static FontPathElementPtr *slept_fpes = (FontPathElementPtr *) 0;
+
+extern FontPatternCachePtr fontPatternCache;
+
+#define NUM_IDS_PER_CLIENT 5
+
+int
+FontToFSError(err)
+ int err;
+{
+ switch (err) {
+ case Successful:
+ return FSSuccess;
+ case AllocError:
+ return FSBadAlloc;
+ case BadFontName:
+ case BadFontPath:
+ return FSBadName;
+ case BadFontFormat:
+ return FSBadFormat;
+ case BadCharRange:
+ return FSBadRange;
+ default:
+ return err;
+ }
+}
+
+/* XXX -- these two funcs may want to be broken into macros */
+void
+UseFPE(fpe)
+ FontPathElementPtr fpe;
+{
+ fpe->refcount++;
+}
+
+void
+FreeFPE(fpe)
+ FontPathElementPtr fpe;
+{
+ fpe->refcount--;
+ if (fpe->refcount == 0) {
+ (*fpe_functions[fpe->type].free_fpe) (fpe);
+ fsfree(fpe->name);
+ fsfree(fpe);
+ }
+}
+
+/*
+ * note that the font wakeup queue is not refcounted. this is because
+ * an fpe needs to be added when it's inited, and removed when it's finally
+ * freed, in order to handle any data that isn't requested, like FS events.
+ *
+ * since the only thing that should call these routines is the renderer's
+ * init_fpe() and free_fpe(), there shouldn't be any problem in using
+ * freed data.
+ */
+void
+QueueFontWakeup(fpe)
+ FontPathElementPtr fpe;
+{
+ int i;
+ FontPathElementPtr *new;
+
+ for (i = 0; i < num_slept_fpes; i++) {
+ if (slept_fpes[i] == fpe) {
+
+#ifdef DEBUG
+ fprintf(stderr, "re-queueing fpe wakeup\n");
+#endif
+
+ return;
+ }
+ }
+ if (num_slept_fpes == size_slept_fpes) {
+ new = (FontPathElementPtr *)
+ fsrealloc(slept_fpes,
+ sizeof(FontPathElementPtr) * (size_slept_fpes + 4));
+ if (!new)
+ return;
+ slept_fpes = new;
+ size_slept_fpes += 4;
+ }
+ slept_fpes[num_slept_fpes] = fpe;
+ num_slept_fpes++;
+}
+
+void
+RemoveFontWakeup(fpe)
+ FontPathElementPtr fpe;
+{
+ int i,
+ j;
+
+ for (i = 0; i < num_slept_fpes; i++) {
+ if (slept_fpes[i] == fpe) {
+ for (j = i; j < num_slept_fpes; j++) {
+ slept_fpes[j] = slept_fpes[j + 1];
+ }
+ num_slept_fpes--;
+ return;
+ }
+ }
+}
+
+/* ARGSUSED */
+void
+FontWakeup(data, count, LastSelectMask)
+ pointer data;
+ int count;
+ unsigned long *LastSelectMask;
+{
+ int i;
+ FontPathElementPtr fpe;
+
+ if (count < 0)
+ return; /* ignore -1 return from select XXX */
+ /* wake up any fpe's that may be waiting for information */
+ for (i = 0; i < num_slept_fpes; i++) {
+ fpe = slept_fpes[i];
+ (void) (*fpe_functions[fpe->type].wakeup_fpe) (fpe, LastSelectMask);
+ }
+}
+
+static Bool
+add_id_to_list(ids, fid)
+ FontIDListPtr ids;
+ Font fid;
+{
+ Font *newlist;
+
+ /*
+ * assumes the list is packed tightly
+ */
+ if (ids->num == ids->size) {
+ /* increase size of array */
+ newlist = (Font *) fsrealloc(ids->client_list,
+ sizeof(Font) * (ids->size + NUM_IDS_PER_CLIENT));
+ if (!newlist)
+ return FALSE;
+ ids->client_list = newlist;
+ ids->size += NUM_IDS_PER_CLIENT;
+ }
+ ids->client_list[ids->num++] = fid;
+ return TRUE;
+}
+
+static void
+remove_id_from_list(ids, fid)
+ FontIDListPtr ids;
+ Font fid;
+{
+ int i;
+
+ for (i = 0; i < ids->num; i++) {
+ if (ids->client_list[i] == fid) {
+ /* a memmove() might be better here */
+ while (i < ids->num) {
+ ids->client_list[i] = ids->client_list[i + 1];
+ i++;
+ }
+ ids->num--;
+ return;
+ }
+ }
+ assert(0);
+}
+
+static FontIDListPtr
+make_clients_id_list()
+{
+ FontIDListPtr ids;
+ Font *fids;
+
+ ids = (FontIDListPtr) fsalloc(sizeof(FontIDListRec));
+ fids = (Font *) fsalloc(sizeof(Font) * NUM_IDS_PER_CLIENT);
+ if (!ids || !fids) {
+ fsfree(ids);
+ fsfree(fids);
+ return (FontIDListPtr) 0;
+ }
+ bzero((char *) fids, sizeof(Font) * NUM_IDS_PER_CLIENT);
+ ids->client_list = fids;
+ ids->size = NUM_IDS_PER_CLIENT;
+ ids->num = 0;
+ return ids;
+}
+
+static void
+free_svrPrivate(svrPrivate)
+ pointer svrPrivate;
+{
+ int i;
+ FontIDListPtr *idlist, ids;
+
+ idlist = (FontIDListPtr *) svrPrivate;
+ if (idlist) {
+ for (i = 0; i < MAXCLIENTS; i++) {
+ ids = idlist[i];
+ if (ids) {
+ fsfree((char *) ids->client_list);
+ fsfree((char *) ids);
+ }
+ }
+ fsfree((char *) idlist);
+ }
+}
+
+static Bool
+do_open_font(client, c)
+ ClientPtr client;
+ OFclosurePtr c;
+{
+ FontPtr pfont = NullFont;
+ FontPathElementPtr fpe;
+ int err;
+ int i;
+ char *alias,
+ *newname;
+ int newlen;
+ ClientFontPtr cfp;
+ fsOpenBitmapFontReply rep;
+ Font orig;
+ FontIDListPtr *idlist,
+ ids;
+ int aliascount = 20;
+
+ if (client->clientGone == CLIENT_GONE) {
+ if (c->current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current_fpe];
+ (*fpe_functions[fpe->type].client_died) ((pointer) client, fpe);
+ }
+ err = Successful;
+ goto dropout;
+ }
+ while (c->current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current_fpe];
+ err = (*fpe_functions[fpe->type].open_font)
+ ((pointer) c->client, fpe, c->flags,
+ c->fontname, c->fnamelen, c->format, c->format_mask,
+ c->fontid, &pfont, &alias,
+ c->non_cachable_font && c->non_cachable_font->fpe == fpe ?
+ c->non_cachable_font :
+ (FontPtr)0);
+
+ if (err == FontNameAlias && alias) {
+ newlen = strlen(alias);
+ newname = (char *) fsrealloc(c->fontname, newlen);
+ if (!newname) {
+ err = AllocError;
+ break;
+ }
+ memmove( newname, alias, newlen);
+ c->fontname = newname;
+ c->fnamelen = newlen;
+ c->current_fpe = 0;
+ if (--aliascount <= 0) break;
+ continue;
+ }
+ if (err == BadFontName) {
+ c->current_fpe++;
+ continue;
+ }
+ if (err == Suspended) {
+ if (!c->slept) {
+ c->slept = TRUE;
+ ClientSleep(client, do_open_font, (pointer) c);
+ }
+ return TRUE;
+ }
+ break;
+ }
+ if (err != Successful) {
+ goto dropout;
+ }
+ if (!pfont) {
+ err = BadFontName;
+ goto dropout;
+ }
+ cfp = (ClientFontPtr) fsalloc(sizeof(ClientFontRec));
+ if (!cfp) {
+ err = AllocError;
+ goto dropout;
+ }
+ cfp->font = pfont;
+ cfp->clientindex = c->client->index;
+
+ if (fontPatternCache && pfont != c->non_cachable_font)
+ CacheFontPattern(fontPatternCache, c->orig_name, c->orig_len, pfont);
+
+ /* either pull out the other id or make the array */
+ if (pfont->refcnt != 0) {
+ idlist = (FontIDListPtr *) pfont->svrPrivate;
+ ids = idlist[c->client->index];
+ if (!ids) {
+ ids = make_clients_id_list();
+ if (!ids) {
+ err = AllocError;
+ fsfree(cfp);
+ goto dropout;
+ }
+ idlist[c->client->index] = ids;
+ }
+ orig = (ids->num > 0) ? ids->client_list[0] : (Font)0;
+ } else {
+ idlist = (FontIDListPtr *) fsalloc(sizeof(FontIDListPtr) * MAXCLIENTS);
+ if (!idlist) {
+ err = AllocError;
+ fsfree(cfp);
+ goto dropout;
+ }
+ ids = make_clients_id_list();
+ if (!ids) {
+ err = AllocError;
+ fsfree(idlist);
+ fsfree(cfp);
+ goto dropout;
+ }
+ bzero((char *) idlist, (sizeof(FontIDListPtr) * MAXCLIENTS));
+ idlist[c->client->index] = ids;
+ orig = (Font) 0;
+ pfont->svrPrivate = (pointer) idlist;
+ }
+ if (!AddResource(c->client->index, c->fontid, RT_FONT, (pointer) cfp)) {
+ fsfree(cfp);
+ free_svrPrivate(pfont->svrPrivate);
+ pfont->svrPrivate = (pointer) 0;
+ err = AllocError;
+ goto dropout;
+ }
+ add_id_to_list(ids, c->fontid);
+ /* send the reply */
+ rep.type = FS_Reply;
+ rep.otherid = orig;
+ if (orig)
+ rep.otherid_valid = TRUE;
+ else
+ rep.otherid_valid = FALSE;
+ rep.cachable = pfont->info.cachable;
+ rep.sequenceNumber = client->sequence;
+ rep.length = SIZEOF(fsOpenBitmapFontReply) >> 2;
+ WriteReplyToClient(client,
+ SIZEOF(fsOpenBitmapFontReply), &rep);
+ if (pfont->refcnt == 0) {
+ if (!pfont->fpe)
+ pfont->fpe = fpe;
+ UseFPE(pfont->fpe);
+ }
+ pfont->refcnt++;
+dropout:
+ if (err != Successful) {
+ SendErrToClient(c->client, FontToFSError(err), (pointer) &(c->fontid));
+ }
+ if (c->slept)
+ ClientWakeup(c->client);
+ for (i = 0; i < c->num_fpes; i++) {
+ FreeFPE(c->fpe_list[i]);
+ }
+ fsfree(c->fpe_list);
+ fsfree(c->fontname);
+ fsfree(c);
+ return TRUE;
+}
+
+int
+OpenFont(client, fid, format, format_mask, namelen, name)
+ ClientPtr client;
+ Font fid;
+ fsBitmapFormat format;
+ fsBitmapFormatMask format_mask;
+ int namelen;
+ char *name;
+{
+ FontPtr pfont = (FontPtr)0;
+ fsOpenBitmapFontReply rep;
+ OFclosurePtr c;
+ FontIDListPtr *idlist,
+ ids;
+ int i;
+
+ if (namelen == 0 || namelen > XLFDMAXFONTNAMELEN) {
+ SendErrToClient(client, FSBadName, (pointer) 0);
+ return FSBadName;
+ }
+ /*
+ ** Check name cache. If we find a cached version of this font that
+ ** is cachable, immediately satisfy the request with it. If we find
+ ** a cached version of this font that is non-cachable, we do not
+ ** satisfy the request with it. Instead, we pass the FontPtr to the
+ ** FPE's open_font code (the fontfile FPE in turn passes the
+ ** information to the rasterizer; the fserve FPE ignores it).
+ **
+ ** Presumably, the font is marked non-cachable because the FPE has
+ ** put some licensing restrictions on it. If the FPE, using
+ ** whatever logic it relies on, determines that it is willing to
+ ** share this existing font with the client, then it has the option
+ ** to return the FontPtr we passed it as the newly-opened font.
+ ** This allows the FPE to exercise its licensing logic without
+ ** having to create another instance of a font that already exists.
+ */
+
+ if (fontPatternCache &&
+ (pfont = FindCachedFontPattern(fontPatternCache, name, namelen)) &&
+ pfont->info.cachable) {
+ ClientFontPtr cfp;
+
+ idlist = (FontIDListPtr *) pfont->svrPrivate;
+ ids = idlist[client->index];
+ if (!ids) {
+ ids = make_clients_id_list();
+ if (!ids) {
+ goto lowmem;
+ }
+ idlist[client->index] = ids;
+ }
+ cfp = (ClientFontPtr) fsalloc(sizeof(ClientFontRec));
+ if (!cfp) {
+ lowmem:
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return FSBadAlloc;
+ }
+ cfp->font = pfont;
+ cfp->clientindex = client->index;
+ if (!AddResource(client->index, fid, RT_FONT, (pointer) cfp)) {
+ goto lowmem;
+ }
+ if (!add_id_to_list(ids, fid)) {
+ goto lowmem;
+ }
+ pfont->refcnt++;
+ rep.type = FS_Reply;
+ if (ids->num > 1)
+ {
+ rep.otherid = ids->client_list[0];
+ rep.otherid_valid = TRUE;
+ }
+ else
+ {
+ rep.otherid = 0;
+ rep.otherid_valid = FALSE;
+ }
+ rep.cachable = TRUE; /* XXX */
+ rep.sequenceNumber = client->sequence;
+ rep.length = SIZEOF(fsOpenBitmapFontReply) >> 2;
+ WriteReplyToClient(client,
+ SIZEOF(fsOpenBitmapFontReply), &rep);
+ return FSSuccess;
+ }
+ c = (OFclosurePtr) fsalloc(sizeof(OFclosureRec));
+ if (!c)
+ goto lowmem;
+ c->fontname = (char *) fsalloc(namelen);
+ if (!c->fontname) {
+ fsfree(c);
+ goto lowmem;
+ }
+ /*
+ * copy the current FPE list, so that if it gets changed by another client
+ * while we're blocking, the request still appears atomic
+ */
+ c->fpe_list = (FontPathElementPtr *)
+ fsalloc(sizeof(FontPathElementPtr) * num_fpes);
+ if (!c->fpe_list) {
+ fsfree(c->fontname);
+ fsfree(c);
+ goto lowmem;
+ }
+ memmove( c->fontname, name, namelen);
+ for (i = 0; i < num_fpes; i++) {
+ c->fpe_list[i] = font_path_elements[i];
+ UseFPE(c->fpe_list[i]);
+ }
+ c->client = client;
+ c->fontid = fid;
+ c->current_fpe = 0;
+ c->num_fpes = num_fpes;
+ c->fnamelen = namelen;
+ c->orig_name = name;
+ c->orig_len = namelen;
+ c->slept = FALSE;
+ c->flags = (FontLoadInfo | FontLoadProps);
+ c->format = format;
+ c->format_mask = format_mask;
+ c->non_cachable_font = pfont;
+
+ (void) do_open_font(client, c);
+ return FSSuccess;
+}
+
+static int
+close_font(pfont)
+ FontPtr pfont;
+{
+ FontPathElementPtr fpe;
+
+ assert(pfont);
+ if (--pfont->refcnt == 0) {
+ if (fontPatternCache)
+ RemoveCachedFontPattern(fontPatternCache, pfont);
+ fpe = pfont->fpe;
+ free_svrPrivate(pfont->svrPrivate);
+ (*fpe_functions[fpe->type].close_font) (fpe, pfont);
+ FreeFPE(fpe);
+ }
+ return FSSuccess;
+}
+
+int
+CloseClientFont(cfp, fid)
+ ClientFontPtr cfp;
+ FSID fid;
+{
+ FontIDListPtr *idlist;
+ FontIDListPtr ids;
+ int ret;
+
+ assert(cfp);
+ /* clear otherid id */
+ idlist = (FontIDListPtr *) cfp->font->svrPrivate;
+ ids = idlist[cfp->clientindex];
+ remove_id_from_list(ids, fid);
+ ret = close_font(cfp->font);
+ fsfree((char *) cfp);
+ return ret;
+}
+
+/*
+ * search all the knwon FPE prefixes looking for one to match the given
+ * FPE name
+ */
+static int
+determine_fpe_type(name)
+ char *name;
+{
+ int i;
+ for (i = 0; i < num_fpe_types; i++) {
+ if ((*fpe_functions[i].name_check) (name))
+ return i;
+ }
+ return -1;
+}
+
+static void
+free_font_path(list, n)
+ FontPathElementPtr *list;
+ int n;
+{
+ int i;
+
+ for (i = 0; i < n; i++) {
+ FreeFPE(list[i]);
+ }
+ fsfree((char *) list);
+}
+
+static FontPathElementPtr
+find_existing_fpe(list, num, name, len)
+ FontPathElementPtr *list;
+ int num;
+ char *name;
+ int len;
+{
+ FontPathElementPtr fpe;
+ int i;
+
+ for (i = 0; i < num; i++) {
+ fpe = list[i];
+ if (fpe->name_length == len && memcmp(name, fpe->name, len) == 0)
+ return fpe;
+ }
+ return (FontPathElementPtr) 0;
+}
+
+/*
+ * does the work of setting up the fpe list
+ *
+ * paths should be a counted string
+ */
+static int
+set_font_path_elements(npaths, paths, bad)
+ int npaths;
+ char *paths;
+ int *bad;
+{
+ int i,
+ err;
+ int len;
+ int type;
+ char *cp = paths;
+ FontPathElementPtr fpe,
+ *fplist;
+
+ fplist = (FontPathElementPtr *)
+ fsalloc(sizeof(FontPathElementPtr) * npaths);
+ if (!fplist) {
+ *bad = 0;
+ return FSBadAlloc;
+ }
+ for (i = 0; i < num_fpe_types; i++) {
+ if (fpe_functions[i].set_path_hook)
+ (*fpe_functions[i].set_path_hook) ();
+ }
+ for (i = 0; i < npaths; i++) {
+ len = *cp++;
+ if (len) {
+ char *name;
+ /* if it's already in our active list, just reset it */
+ /*
+ * note that this can miss FPE's in limbo -- may be worth catching
+ * them, though it'd muck up refcounting
+ */
+ fpe = find_existing_fpe(font_path_elements, num_fpes, cp, len);
+ if (fpe) {
+ err = (*fpe_functions[fpe->type].reset_fpe) (fpe);
+ if (err == Successful) {
+ UseFPE(fpe);/* since it'll be decref'd later when freed
+ * from the old list */
+ fplist[i] = fpe;
+ cp += len;
+ continue;
+ }
+ /* can't do it, so act like it's a new one */
+ }
+ name = (char *) fsalloc(len + 1);
+ if (!name) {
+ err = FSBadAlloc;
+ goto bail;
+ }
+ strncpy(name, (char *) cp, len);
+ name[len] = '\0';
+ type = determine_fpe_type(name);
+ if (type == -1)
+ {
+ fsfree(name);
+ err = FSBadName;
+ goto bail;
+ }
+ /* must be new -- make it */
+ fpe = (FontPathElementPtr) fsalloc(sizeof(FontPathElementRec));
+ if (!fpe) {
+ fsfree(name);
+ err = FSBadAlloc;
+ goto bail;
+ }
+ fpe->type = type;
+ fpe->name = name;
+ fpe->refcount = 1;
+ fplist[i] = fpe;
+
+ cp += len;
+ fpe->name_length = len;
+ err = (*fpe_functions[fpe->type].init_fpe) (fpe);
+ if (err != Successful) {
+ fsfree(fpe->name);
+ fsfree(fpe);
+ err = FontToFSError(err);
+ goto bail;
+ }
+ }
+ }
+ free_font_path(font_path_elements, num_fpes);
+ font_path_elements = fplist;
+ num_fpes = npaths;
+ if (fontPatternCache)
+ EmptyFontPatternCache(fontPatternCache);
+ return FSSuccess;
+bail:
+ *bad = i;
+ while (--i >= 0)
+ FreeFPE(fplist[i]);
+ fsfree(fplist);
+ return err;
+}
+
+/*
+ * expects comma seperated string
+ */
+int
+SetFontCatalogue(str, badpath)
+ char *str;
+ int *badpath;
+{
+ int len,
+ npaths;
+ char *paths,
+ *end,
+ *p;
+ int err;
+
+ len = strlen(str) + 1;
+ paths = p = (char *) ALLOCATE_LOCAL(len);
+ npaths = 0;
+
+ while (*str) {
+ end = index(str, ',');
+ if (!end) {
+ end = str + strlen(str);
+ }
+ *p++ = len = end - str;
+ memmove( p, str, len);
+ npaths++;
+ str += len; /* skip entry */
+ if (*str == ',')
+ str++; /* skip any comma */
+ p += len;
+ }
+
+ err = set_font_path_elements(npaths, paths, badpath);
+
+ DEALLOCATE_LOCAL(paths);
+
+ return err;
+}
+
+Bool
+do_list_fonts_and_aliases(client, c)
+ ClientPtr client;
+ LFclosurePtr c;
+{
+ FontPathElementPtr fpe;
+ int err = Successful;
+ FontNamesPtr names = NULL;
+ char *name, *resolved;
+ int namelen, resolvedlen;
+ int nnames;
+ int stringLens;
+ int i;
+ fsListFontsReply reply;
+ char *bufptr;
+ char *bufferStart;
+ int aliascount = 0;
+
+ if (client->clientGone == CLIENT_GONE) {
+ if (c->current.current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current.current_fpe];
+ (*fpe_functions[fpe->type].client_died) ((pointer) client, fpe);
+ }
+ err = Successful;
+ goto bail;
+ }
+
+ if (!c->current.patlen)
+ goto finish;
+
+ while (c->current.current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current.current_fpe];
+ err = Successful;
+
+ if (!fpe_functions[fpe->type].start_list_fonts_and_aliases)
+ {
+ /* This FPE doesn't support/require list_fonts_and_aliases */
+
+ err = (*fpe_functions[fpe->type].list_fonts)
+ ((pointer) c->client, fpe, c->current.pattern,
+ c->current.patlen, c->current.max_names - c->names->nnames,
+ c->names);
+
+ if (err == Suspended) {
+ if (!c->slept) {
+ c->slept = TRUE;
+ ClientSleep(client, do_list_fonts_and_aliases, (pointer) c);
+ }
+ return TRUE;
+ }
+
+ err = BadFontName;
+ }
+ else
+ {
+ /* Start of list_fonts_and_aliases functionality. Modeled
+ after list_fonts_with_info in that it resolves aliases,
+ except that the information collected from FPEs is just
+ names, not font info. Each list_next_font_or_alias()
+ returns either a name into name/namelen or an alias into
+ name/namelen and its target name into resolved/resolvedlen.
+ The code at this level then resolves the alias by polling
+ the FPEs. */
+
+ if (!c->current.list_started) {
+ err = (*fpe_functions[fpe->type].start_list_fonts_and_aliases)
+ ((pointer) c->client, fpe, c->current.pattern,
+ c->current.patlen, c->current.max_names - c->names->nnames,
+ &c->current.private);
+ if (err == Suspended) {
+ if (!c->slept) {
+ ClientSleep(client, do_list_fonts_and_aliases,
+ (pointer) c);
+ c->slept = TRUE;
+ }
+ return TRUE;
+ }
+ if (err == Successful)
+ c->current.list_started = TRUE;
+ }
+ if (err == Successful) {
+ name = 0;
+ err = (*fpe_functions[fpe->type].list_next_font_or_alias)
+ ((pointer) c->client, fpe, &name, &namelen, &resolved,
+ &resolvedlen, c->current.private);
+ if (err == Suspended) {
+ if (!c->slept) {
+ ClientSleep(client, do_list_fonts_and_aliases,
+ (pointer) c);
+ c->slept = TRUE;
+ }
+ return TRUE;
+ }
+ }
+
+ if (err == Successful)
+ {
+ if (c->haveSaved)
+ {
+ if (c->savedName)
+ (void)AddFontNamesName(c->names, c->savedName,
+ c->savedNameLen);
+ }
+ else
+ (void)AddFontNamesName(c->names, name, namelen);
+ }
+
+ /*
+ * When we get an alias back, save our state and reset back to
+ * the start of the FPE looking for the specified name. As
+ * soon as a real font is found for the alias, pop back to the
+ * old state
+ */
+ else if (err == FontNameAlias) {
+ char tmp_pattern[XLFDMAXFONTNAMELEN];
+ /*
+ * when an alias recurses, we need to give
+ * the last FPE a chance to clean up; so we call
+ * it again, and assume that the error returned
+ * is BadFontName, indicating the alias resolution
+ * is complete.
+ */
+ memmove(tmp_pattern, resolved, resolvedlen);
+ if (c->haveSaved)
+ {
+ char *tmpname;
+ int tmpnamelen;
+
+ tmpname = 0;
+ (void) (*fpe_functions[fpe->type].list_next_font_or_alias)
+ ((pointer) c->client, fpe, &tmpname, &tmpnamelen,
+ &tmpname, &tmpnamelen, c->current.private);
+ if (--aliascount <= 0)
+ {
+ err = BadFontName;
+ goto ContBadFontName;
+ }
+ }
+ else
+ {
+ c->saved = c->current;
+ c->haveSaved = TRUE;
+ if (c->savedName)
+ fsfree(c->savedName);
+ c->savedName = (char *)fsalloc(namelen + 1);
+ if (c->savedName)
+ memmove(c->savedName, name, namelen + 1);
+ c->savedNameLen = namelen;
+ aliascount = 20;
+ }
+ memmove(c->current.pattern, tmp_pattern, resolvedlen);
+ c->current.patlen = resolvedlen;
+ c->current.max_names = c->names->nnames + 1;
+ c->current.current_fpe = -1;
+ c->current.private = 0;
+ err = BadFontName;
+ }
+ }
+ /*
+ * At the end of this FPE, step to the next. If we've finished
+ * processing an alias, pop state back. If we've collected enough
+ * font names, quit.
+ */
+ if (err == BadFontName) {
+ ContBadFontName: ;
+ c->current.list_started = FALSE;
+ c->current.current_fpe++;
+ err = Successful;
+ if (c->haveSaved)
+ {
+ /* If we're searching for an alias, limit the search to
+ FPE's of the same type as the one the alias came
+ from. This is unnecessarily restrictive, but if we
+ have both fontfile and fs FPE's, this restriction can
+ drastically reduce network traffic to the fs -- else
+ we could poll the fs for *every* local alias found;
+ on a typical system enabling FILE_NAMES_ALIASES, this
+ is significant. */
+
+ while (c->current.current_fpe < c->num_fpes &&
+ c->fpe_list[c->current.current_fpe]->type !=
+ c->fpe_list[c->saved.current_fpe]->type)
+ c->current.current_fpe++;
+
+ if (c->names->nnames == c->current.max_names ||
+ c->current.current_fpe == c->num_fpes) {
+ c->haveSaved = FALSE;
+ c->current = c->saved;
+ /* Give the saved namelist a chance to clean itself up */
+ continue;
+ }
+ }
+ if (c->names->nnames == c->current.max_names)
+ break;
+ }
+ }
+
+ /*
+ * send the reply
+ */
+ if (err != Successful) {
+ SendErrToClient(client, FontToFSError(err), (pointer) 0);
+ goto bail;
+ }
+
+finish:
+
+ names = c->names;
+ nnames = names->nnames;
+ client = c->client;
+ stringLens = 0;
+ for (i = 0; i < nnames; i++)
+ stringLens += (names->length[i] <= 255) ? names->length[i] : 0;
+
+ reply.type = FS_Reply;
+ reply.length = (SIZEOF(fsListFontsReply) + stringLens + nnames + 3) >> 2;
+ reply.following = 0;
+ reply.nFonts = nnames;
+ reply.sequenceNumber = client->sequence;
+
+ bufptr = bufferStart = (char *) ALLOCATE_LOCAL(reply.length << 2);
+
+ if (!bufptr && reply.length) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ goto bail;
+ }
+ /*
+ * since WriteToClient long word aligns things, copy to temp buffer and
+ * write all at once
+ */
+ for (i = 0; i < nnames; i++) {
+ if (names->length[i] > 255)
+ reply.nFonts--;
+ else
+ {
+ *bufptr++ = names->length[i];
+ memmove( bufptr, names->names[i], names->length[i]);
+ bufptr += names->length[i];
+ }
+ }
+ nnames = reply.nFonts;
+ reply.length = (SIZEOF(fsListFontsReply) + stringLens + nnames + 3) >> 2;
+ WriteReplyToClient(client, SIZEOF(fsListFontsReply), &reply);
+ (void) WriteToClient(client, stringLens + nnames, bufferStart);
+ DEALLOCATE_LOCAL(bufferStart);
+
+bail:
+ if (c->slept)
+ ClientWakeup(client);
+ for (i = 0; i < c->num_fpes; i++)
+ FreeFPE(c->fpe_list[i]);
+ fsfree(c->fpe_list);
+ if (c->savedName) fsfree(c->savedName);
+ FreeFontNames(names);
+ fsfree(c);
+ return TRUE;
+}
+
+int
+ListFonts(client, length, pattern, maxNames)
+ ClientPtr client;
+ int length;
+ unsigned char *pattern;
+ int maxNames;
+{
+ int i;
+ LFclosurePtr c;
+
+ /*
+ * The right error to return here would be BadName, however the
+ * specification does not allow for a Name error on this request.
+ * Perhaps a better solution would be to return a nil list, i.e.
+ * a list containing zero fontnames.
+ */
+ if (length > XLFDMAXFONTNAMELEN) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return TRUE;
+ }
+
+ if (!(c = (LFclosurePtr) fsalloc(sizeof *c)))
+ goto badAlloc;
+ c->fpe_list = (FontPathElementPtr *)
+ fsalloc(sizeof(FontPathElementPtr) * num_fpes);
+ if (!c->fpe_list) {
+ fsfree(c);
+ goto badAlloc;
+ }
+ c->names = MakeFontNamesRecord(maxNames < 100 ? maxNames : 100);
+ if (!c->names)
+ {
+ fsfree(c->fpe_list);
+ fsfree(c);
+ goto badAlloc;
+ }
+ memmove( c->current.pattern, pattern, length);
+ for (i = 0; i < num_fpes; i++) {
+ c->fpe_list[i] = font_path_elements[i];
+ UseFPE(c->fpe_list[i]);
+ }
+ c->client = client;
+ c->num_fpes = num_fpes;
+ c->current.patlen = length;
+ c->current.current_fpe = 0;
+ c->current.max_names = maxNames;
+ c->current.list_started = FALSE;
+ c->current.private = 0;
+ c->haveSaved = FALSE;
+ c->slept = FALSE;
+ c->savedName = 0;
+ do_list_fonts_and_aliases(client, c);
+ return TRUE;
+badAlloc:
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return TRUE;
+}
+
+static int padlength[4] = {0, 3, 2, 1};
+static char padding[3];
+
+Bool
+do_list_fonts_with_info(client, c)
+ ClientPtr client;
+ LFWXIclosurePtr c;
+{
+ FontPathElementPtr fpe;
+ int err = Successful;
+ char *name;
+ int namelen;
+ int numFonts;
+ FontInfoRec fontInfo,
+ *pFontInfo;
+ fsListFontsWithXInfoReply *reply;
+ int length;
+ fsPropInfo *prop_info;
+ int lenpropdata;
+ int i;
+ int aliascount = 0;
+
+ if (client->clientGone == CLIENT_GONE) {
+ if (c->current.current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current.current_fpe];
+ (*fpe_functions[fpe->type].client_died) ((pointer) client, fpe);
+ }
+ err = Successful;
+ goto bail;
+ }
+ while (c->current.current_fpe < c->num_fpes) {
+ fpe = c->fpe_list[c->current.current_fpe];
+ err = Successful;
+ if (!c->current.list_started) {
+ err = (*fpe_functions[fpe->type].start_list_fonts_with_info)
+ ((pointer) c->client, fpe, c->current.pattern,
+ c->current.patlen, c->current.max_names,
+ &c->current.private);
+ if (err == Suspended) {
+ if (!c->slept) {
+ ClientSleep(client, do_list_fonts_with_info,
+ (pointer) c);
+ c->slept = TRUE;
+ }
+ return TRUE;
+ }
+ if (err == Successful)
+ c->current.list_started = TRUE;
+ }
+ if (err == Successful) {
+ name = 0;
+ pFontInfo = &fontInfo;
+ err = (*fpe_functions[fpe->type].list_next_font_with_info)
+ ((pointer) c->client, fpe, &name, &namelen,
+ &pFontInfo, &numFonts, c->current.private);
+ if (err == Suspended) {
+ if (!c->slept) {
+ ClientSleep(client, do_list_fonts_with_info,
+ (pointer) c);
+ c->slept = TRUE;
+ }
+ return TRUE;
+ }
+ }
+ /*
+ * When we get an alias back, save our state and reset back to the
+ * start of the FPE looking for the specified name. As soon as a real
+ * font is found for the alias, pop back to the old state
+ */
+ if (err == FontNameAlias) {
+ /*
+ * when an alias recurses, we need to give
+ * the last FPE a chance to clean up; so we call
+ * it again, and assume that the error returned
+ * is BadFontName, indicating the alias resolution
+ * is complete.
+ */
+ if (c->haveSaved)
+ {
+ char *tmpname;
+ int tmpnamelen;
+ FontInfoPtr tmpFontInfo;
+
+ tmpname = 0;
+ tmpFontInfo = &fontInfo;
+ (void) (*fpe_functions[fpe->type].list_next_font_with_info)
+ ((pointer) client, fpe, &tmpname, &tmpnamelen,
+ &tmpFontInfo, &numFonts, c->current.private);
+ if (--aliascount <= 0)
+ {
+ err = BadFontName;
+ goto ContBadFontName;
+ }
+ }
+ else
+ {
+ c->saved = c->current;
+ c->haveSaved = TRUE;
+ c->savedNumFonts = numFonts;
+ c->savedName = (char *) pFontInfo;
+ aliascount = 20;
+ }
+ memmove(c->current.pattern, name, namelen);
+ c->current.patlen = namelen;
+ c->current.max_names = 1;
+ c->current.current_fpe = 0;
+ c->current.private = 0;
+ c->current.list_started = FALSE;
+ }
+ /*
+ * At the end of this FPE, step to the next. If we've finished
+ * processing an alias, pop state back. If we've sent enough font
+ * names, quit.
+ */
+ else if (err == BadFontName) {
+ ContBadFontName: ;
+ c->current.list_started = FALSE;
+ c->current.current_fpe++;
+ err = Successful;
+ if (c->haveSaved) {
+ if (c->current.max_names == 0 ||
+ c->current.current_fpe == c->num_fpes) {
+ c->haveSaved = FALSE;
+ c->saved.max_names -= (1 - c->current.max_names);
+ c->current = c->saved;
+ }
+ }
+ else if (c->current.max_names == 0)
+ break;
+ } else if (err == Successful) {
+/* XXX why is it xFontProp ? */
+ length = sizeof(*reply) + pFontInfo->nprops * sizeof(xFontProp);
+ reply = c->reply;
+ if (c->length < length) {
+ reply = (fsListFontsWithXInfoReply *) fsrealloc(c->reply, length);
+ if (!reply) {
+ err = AllocError;
+ break;
+ }
+ c->reply = reply;
+ c->length = length;
+ }
+ if (c->haveSaved) {
+ numFonts = c->savedNumFonts;
+ name = c->savedName;
+ namelen = strlen(name);
+ }
+ fsPack_XFontInfoHeader(pFontInfo, reply, client->major_version);
+ err = convert_props(pFontInfo, &prop_info);
+ if (err != Successful)
+ break;
+ lenpropdata = SIZEOF(fsPropInfo) +
+ prop_info->num_offsets * SIZEOF(fsPropOffset) +
+ prop_info->data_len;
+
+ reply->type = FS_Reply;
+ reply->length =
+ (SIZEOF(fsListFontsWithXInfoReply) +
+ lenpropdata + namelen + 3) >> 2;
+ reply->sequenceNumber = client->sequence;
+ reply->nameLength = namelen;
+ reply->nReplies = numFonts;
+ WriteReplyToClient(client, SIZEOF(fsListFontsWithXInfoReply), reply);
+ if (client->swapped)
+ SwapPropInfo(prop_info);
+ if (client->major_version > 1)
+ {
+ (void)WriteToClientUnpadded(client, lenpropdata, (char *) prop_info);
+ (void)WriteToClientUnpadded(client, namelen, name);
+ (void)WriteToClientUnpadded(client,
+ padlength[(lenpropdata+namelen)&3],
+ padding);
+ } else {
+ (void) WriteToClient(client, namelen, name);
+ (void) WriteToClient(client, lenpropdata, (char *) prop_info);
+ }
+ if (pFontInfo == &fontInfo) {
+ fsfree(fontInfo.props);
+ fsfree(fontInfo.isStringProp);
+ }
+ fsfree(prop_info);
+
+ --c->current.max_names;
+ if (c->current.max_names < 0)
+ abort();
+ }
+ }
+
+ /*
+ * send the final reply
+ */
+ if (err == Successful) {
+ fsGenericReply *final_reply;
+
+ final_reply = (fsGenericReply *)c->reply;
+ if (client->major_version > 1)
+ length = SIZEOF(fsGenericReply);
+ else
+ length = SIZEOF(fsListFontsWithXInfoReply);
+ if (c->length < length) {
+ final_reply = (fsGenericReply *) fsrealloc(c->reply, length);
+ if (final_reply) {
+ c->reply = (fsListFontsWithXInfoReply *)final_reply;
+ c->length = length;
+ } else
+ err = AllocError;
+ }
+ if (err == Successful) {
+ final_reply->type = FS_Reply;
+ final_reply->data1 = 0; /* notes that this is final */
+ final_reply->sequenceNumber = client->sequence;
+ final_reply->length = length >> 2;
+ WriteReplyToClient(client, length, final_reply);
+ }
+ }
+ if (err != Successful)
+ SendErrToClient(client, FontToFSError(err), (pointer) 0);
+bail:
+ if (c->slept)
+ ClientWakeup(client);
+ for (i = 0; i < c->num_fpes; i++)
+ FreeFPE(c->fpe_list[i]);
+ fsfree(c->fpe_list);
+ fsfree(c->reply);
+ fsfree(c);
+ return TRUE;
+}
+
+int
+StartListFontsWithInfo(client, length, pattern, maxNames)
+ ClientPtr client;
+ int length;
+ unsigned char *pattern;
+ int maxNames;
+{
+ int i;
+ LFWXIclosurePtr c;
+
+ /*
+ * The right error to return here would be BadName, however the
+ * specification does not allow for a Name error on this request.
+ * Perhaps a better solution would be to return a nil list, i.e.
+ * a list containing zero fontnames.
+ */
+ if (length > XLFDMAXFONTNAMELEN) {
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return TRUE;
+ }
+
+ if (!(c = (LFWXIclosurePtr) fsalloc(sizeof *c)))
+ goto badAlloc;
+ c->fpe_list = (FontPathElementPtr *)
+ fsalloc(sizeof(FontPathElementPtr) * num_fpes);
+ if (!c->fpe_list) {
+ fsfree(c);
+ goto badAlloc;
+ }
+ memmove( c->current.pattern, pattern, length);
+ for (i = 0; i < num_fpes; i++) {
+ c->fpe_list[i] = font_path_elements[i];
+ UseFPE(c->fpe_list[i]);
+ }
+ c->client = client;
+ c->num_fpes = num_fpes;
+ c->reply = 0;
+ c->length = 0;
+ c->current.patlen = length;
+ c->current.current_fpe = 0;
+ c->current.max_names = maxNames;
+ c->current.list_started = FALSE;
+ c->current.private = 0;
+ c->savedNumFonts = 0;
+ c->haveSaved = FALSE;
+ c->slept = FALSE;
+ do_list_fonts_with_info(client, c);
+ return TRUE;
+badAlloc:
+ SendErrToClient(client, FSBadAlloc, (pointer) 0);
+ return TRUE;
+}
+
+int
+LoadGlyphRanges(client, pfont, range_flag, num_ranges, item_size, data)
+ ClientPtr client;
+ FontPtr pfont;
+ Bool range_flag;
+ int num_ranges;
+ int item_size;
+ fsChar2b *data;
+{
+ /* either returns Successful, Suspended, or some nasty error */
+ if (fpe_functions[pfont->fpe->type].load_glyphs)
+ return (*fpe_functions[pfont->fpe->type].load_glyphs)(
+ (pointer)client, pfont, range_flag, num_ranges, item_size,
+ (unsigned char *)data);
+ else
+ return Successful;
+}
+
+int
+RegisterFPEFunctions(name_func, init_func, free_func, reset_func,
+ open_func, close_func, list_func, start_lfwi_func, next_lfwi_func,
+ wakeup_func, client_died, load_glyphs,
+ start_list_alias_func, next_list_alias_func,
+ set_path_func)
+ Bool (*name_func) ();
+ int (*init_func) ();
+ int (*free_func) ();
+ int (*reset_func) ();
+ int (*open_func) ();
+ int (*close_func) ();
+ int (*list_func) ();
+ int (*start_lfwi_func) ();
+ int (*next_lfwi_func) ();
+ int (*wakeup_func) ();
+ int (*client_died) ();
+ int (*load_glyphs) ();
+ int (*start_list_alias_func) ();
+ int (*next_list_alias_func) ();
+ void (*set_path_func) ();
+{
+ FPEFunctions *new;
+
+ /* grow the list */
+ new = (FPEFunctions *) fsrealloc(fpe_functions,
+ (num_fpe_types + 1) * sizeof(FPEFunctions));
+ if (!new)
+ return -1;
+ fpe_functions = new;
+
+ fpe_functions[num_fpe_types].name_check = name_func;
+ fpe_functions[num_fpe_types].open_font = open_func;
+ fpe_functions[num_fpe_types].close_font = close_func;
+ fpe_functions[num_fpe_types].wakeup_fpe = wakeup_func;
+ fpe_functions[num_fpe_types].list_fonts = list_func;
+ fpe_functions[num_fpe_types].start_list_fonts_with_info =
+ start_lfwi_func;
+ fpe_functions[num_fpe_types].list_next_font_with_info =
+ next_lfwi_func;
+ fpe_functions[num_fpe_types].init_fpe = init_func;
+ fpe_functions[num_fpe_types].free_fpe = free_func;
+ fpe_functions[num_fpe_types].reset_fpe = reset_func;
+
+ fpe_functions[num_fpe_types].client_died = client_died;
+ fpe_functions[num_fpe_types].load_glyphs = load_glyphs;
+ fpe_functions[num_fpe_types].start_list_fonts_and_aliases =
+ start_list_alias_func;
+ fpe_functions[num_fpe_types].list_next_font_or_alias =
+ next_list_alias_func;
+ fpe_functions[num_fpe_types].set_path_hook = set_path_func;
+
+ return num_fpe_types++;
+}
+
+void
+FreeFonts()
+{
+}
+
+/* convenience functions for FS interface */
+
+FontPtr
+find_old_font(id)
+ FSID id;
+{
+ return (FontPtr) LookupIDByType(SERVER_CLIENT, id, RT_NONE);
+}
+
+Font
+GetNewFontClientID()
+{
+ return (Font) FakeClientID(SERVER_CLIENT);
+}
+
+int
+StoreFontClientFont(pfont, id)
+ FontPtr pfont;
+ Font id;
+{
+ return AddResource(SERVER_CLIENT, id, RT_NONE, (pointer) pfont);
+}
+
+void
+DeleteFontClientID(id)
+ Font id;
+{
+ FreeResource(SERVER_CLIENT, id, RT_NONE);
+}
+
+static int fs_handlers_installed = 0;
+static unsigned int last_server_gen;
+
+int
+init_fs_handlers(fpe, block_handler)
+ FontPathElementPtr fpe;
+ void (*block_handler) ();
+{
+ /* if server has reset, make sure the b&w handlers are reinstalled */
+ if (last_server_gen < serverGeneration) {
+ last_server_gen = serverGeneration;
+ fs_handlers_installed = 0;
+ }
+ if (fs_handlers_installed == 0) {
+
+#ifdef DEBUG
+ fprintf(stderr, "adding FS b & w handlers\n");
+#endif
+
+ if (!RegisterBlockAndWakeupHandlers(block_handler,
+ FontWakeup, (pointer) 0))
+ return AllocError;
+ fs_handlers_installed++;
+ }
+ QueueFontWakeup(fpe);
+ return Successful;
+}
+
+void
+remove_fs_handlers(fpe, block_handler, all)
+ FontPathElementPtr fpe;
+ void (*block_handler) ();
+ Bool all;
+{
+ if (all) {
+ /* remove the handlers if no one else is using them */
+ if (--fs_handlers_installed == 0) {
+
+#ifdef DEBUG
+ fprintf(stderr, "removing FS b & w handlers\n");
+#endif
+
+ RemoveBlockAndWakeupHandlers(block_handler, FontWakeup,
+ (pointer) 0);
+ }
+ }
+ RemoveFontWakeup(fpe);
+}
+
+void
+DeleteClientFontStuff(client)
+ ClientPtr client;
+{
+ int i;
+ FontPathElementPtr fpe;
+
+ for (i = 0; i < num_fpes; i++)
+ {
+ fpe = font_path_elements[i];
+
+ if (fpe_functions[fpe->type].client_died)
+ (*fpe_functions[fpe->type].client_died) ((pointer) client, fpe);
+ }
+}
diff --git a/difs/globals.c b/difs/globals.c
new file mode 100644
index 0000000..aac2517
--- /dev/null
+++ b/difs/globals.c
@@ -0,0 +1,67 @@
+/* $Xorg: globals.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * various font server globals
+ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)globals.c 4.3 5/3/91
+ *
+ */
+#include "FSproto.h"
+#include "clientstr.h"
+#include "misc.h"
+#include "site.h"
+
+ClientPtr *clients;
+ClientPtr serverClient;
+int currentMaxClients;
+char *server;
+int serverGeneration = 0;
+int argcGlobal;
+char **argvGlobal;
+
+long TimeOutValue = DEFAULT_TIMEOUT * MILLI_PER_SECOND;
+long ReapClientTime = CLIENT_TIMEOUT * MILLI_PER_SECOND;
diff --git a/difs/initfonts.c b/difs/initfonts.c
new file mode 100644
index 0000000..ea6c95a
--- /dev/null
+++ b/difs/initfonts.c
@@ -0,0 +1,80 @@
+/* $Xorg: initfonts.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * %W% %E%
+ *
+ */
+
+#include "font.h"
+
+FontPatternCachePtr fontPatternCache;
+
+void
+InitFonts()
+{
+ if (fontPatternCache)
+ FreeFontPatternCache(fontPatternCache);
+ fontPatternCache = MakeFontPatternCache();
+
+ ResetFontPrivateIndex();
+
+#ifdef FONT_PCF
+ FontFileRegisterFpeFunctions();
+#ifdef LOWMEMFTPT
+
+#ifndef CRAY
+ SpeedoRegisterFontFileFunctions ();
+ Type1RegisterFontFileFunctions();
+#endif
+
+#endif /* ifdef LOWMEMFTPT */
+
+#endif
+
+#ifdef FONT_FS
+ fs_register_fpe_functions();
+#endif
+}
diff --git a/difs/main.c b/difs/main.c
new file mode 100644
index 0000000..dc43512
--- /dev/null
+++ b/difs/main.c
@@ -0,0 +1,200 @@
+/* $Xorg: main.c,v 1.5 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+ * Font server main routine
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FS.h"
+#include "FSproto.h"
+#include "clientstr.h"
+#include "resource.h"
+#include "misc.h"
+#include "globals.h"
+#include "servermd.h"
+#include "cache.h"
+#include "site.h"
+
+char *ConnectionInfo;
+int ConnInfoLen;
+
+Cache serverCache;
+
+#ifndef DEFAULT_CONFIG_FILE
+#define DEFAULT_CONFIG_FILE "/usr/lib/X11/fs/config"
+#endif
+
+#define SERVER_CACHE_SIZE 10000 /* for random server cacheables */
+
+extern void InitProcVectors();
+extern void InitFonts();
+extern void InitAtoms();
+extern void InitExtensions();
+extern void ProcessCmdLine();
+static Bool create_connection_block();
+
+extern ClientPtr currentClient;
+char *configfilename;
+extern Bool drone_server;
+
+extern OldListenRec *OldListen;
+extern int OldListenCount;
+
+
+main(argc, argv)
+ int argc;
+ char **argv;
+{
+ int i;
+
+ argcGlobal = argc;
+ argvGlobal = argv;
+
+ configfilename = DEFAULT_CONFIG_FILE;
+
+ /* init stuff */
+ ProcessCmdLine(argc, argv);
+ InitErrors();
+ /*
+ * do this first thing, to get any options that only take effect at
+ * startup time. it is erad again each time the server resets
+ */
+ if (ReadConfigFile(configfilename) != FSSuccess) {
+ ErrorF("fatal: couldn't read config file\n");
+ exit(1);
+ }
+
+ while (1) {
+ serverGeneration++;
+ OsInit();
+ if (serverGeneration == 1) {
+ /* do first time init */
+ serverCache = CacheInit(SERVER_CACHE_SIZE);
+ CreateSockets(OldListenCount, OldListen);
+ InitProcVectors();
+ clients = (ClientPtr *) fsalloc(MAXCLIENTS * sizeof(ClientPtr));
+ if (!clients)
+ FatalError("couldn't create client array\n");
+ for (i = MINCLIENT; i < MAXCLIENTS; i++)
+ clients[i] = NullClient;
+ /* make serverClient */
+ serverClient = (ClientPtr) fsalloc(sizeof(ClientRec));
+ if (!serverClient)
+ FatalError("couldn't create server client\n");
+ }
+ ResetSockets();
+
+ /* init per-cycle stuff */
+ InitClient(serverClient, SERVER_CLIENT, (pointer) 0);
+
+ clients[SERVER_CLIENT] = serverClient;
+ currentMaxClients = MINCLIENT;
+ currentClient = serverClient;
+
+ if (!InitClientResources(serverClient))
+ FatalError("couldn't init server resources\n");
+
+ InitExtensions();
+ InitAtoms();
+ InitFonts();
+ SetConfigValues();
+ if (!create_connection_block())
+ FatalError("couldn't create connection block\n");
+
+#ifdef DEBUG
+ fprintf(stderr, "Entering Dispatch loop\n");
+#endif
+
+ Dispatch();
+
+#ifdef DEBUG
+ fprintf(stderr, "Leaving Dispatch loop\n");
+#endif
+
+ /* clean up per-cycle stuff */
+ CacheReset();
+ CloseDownExtensions();
+ if ((dispatchException & DE_TERMINATE) || drone_server)
+ break;
+ fsfree(ConnectionInfo);
+ /* note that we're parsing it again, for each time the server resets */
+ if (ReadConfigFile(configfilename) != FSSuccess)
+ FatalError("couldn't read config file\n");
+ }
+
+ CloseSockets();
+ CloseErrors();
+ exit(0);
+}
+
+void
+NotImplemented()
+{
+ NoopDDA(); /* dummy to get difsutils.o to link */
+ FatalError("Not implemented\n");
+}
+
+static Bool
+create_connection_block()
+{
+ fsConnSetupAccept setup;
+ char *pBuf;
+
+ setup.release_number = VENDOR_RELEASE;
+ setup.vendor_len = strlen(VENDOR_STRING);
+ setup.max_request_len = MAX_REQUEST_SIZE;
+ setup.length = (SIZEOF(fsConnSetupAccept) + setup.vendor_len + 3) >> 2;
+
+ ConnInfoLen = SIZEOF(fsConnSetupAccept) + ((setup.vendor_len + 3) & ~3);
+ ConnectionInfo = (char *) fsalloc(ConnInfoLen);
+ if (!ConnectionInfo)
+ return FALSE;
+
+ memmove( ConnectionInfo, (char *) &setup, SIZEOF(fsConnSetupAccept));
+ pBuf = ConnectionInfo + SIZEOF(fsConnSetupAccept);
+ memmove( pBuf, VENDOR_STRING, (int) setup.vendor_len);
+
+ return TRUE;
+}
diff --git a/difs/resource.c b/difs/resource.c
new file mode 100644
index 0000000..037b97f
--- /dev/null
+++ b/difs/resource.c
@@ -0,0 +1,569 @@
+/* $Xorg: resource.c,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * %W% %G%
+ *
+ */
+/*
+ * a resource is a 32 bit quantity. the upper 12 bits are client id.
+ * client provides a 19 bit resource id. this is "hashed" by me by
+ * taking the 10 lower bits and xor'ing with the mid 10 bits.
+ *
+ * It is sometimes necessary for the server to create an ID that looks
+ * like it belongs to a client. This ID, however, must not be one
+ * the client actually can create, or we have the potential for conflict.
+ * The 20th bit of the ID is resevered for the server's use for this
+ * purpose. By setting CLIENT_ID(id) to the client, the SERVER_BIT to
+ * 1, and an otherwise unused ID in the low 19 bits, we can create a
+ * resource "owned" by the client.
+ *
+ * The following IDs are currently reserved for siccing on the client:
+ * 1 - allocated color to be freed when the client dies
+ */
+
+#include "FS.h"
+#include "misc.h"
+#include "os.h"
+#include "resource.h"
+#include "clientstr.h"
+#include "globals.h"
+
+static void rebuild_table();
+
+#define INITBUCKETS 64
+#define INITHASHSIZE 6
+#define MAXHASHSIZE 11
+
+typedef struct _Resource {
+ struct _Resource *next;
+ FSID id;
+ RESTYPE type;
+ pointer value;
+} ResourceRec, *ResourcePtr;
+
+#define NullResource ((ResourcePtr)NULL)
+
+typedef struct _ClientResource {
+ ResourcePtr *resources;
+ int elements;
+ int buckets;
+ int hashsize; /* log(2)(buckets) */
+ FSID fakeID;
+ FSID endFakeID;
+ FSID expectID;
+} ClientResourceRec;
+
+static RESTYPE lastResourceType;
+static RESTYPE lastResourceClass;
+static RESTYPE TypeMask;
+
+typedef int (*DeleteType) ();
+
+static DeleteType *DeleteFuncs = (DeleteType *) NULL;
+
+#ifdef NOTYET
+RESTYPE
+CreateNewResourceType(deleteFunc)
+ DeleteType deleteFunc;
+{
+ RESTYPE next = lastResourceType + 1;
+ DeleteType *funcs;
+
+ if (next & lastResourceClass)
+ return 0;
+ funcs = (DeleteType *) fsrealloc(DeleteFuncs,
+ (next + 1) * sizeof(DeleteType));
+ if (!funcs)
+ return 0;
+ lastResourceType = next;
+ DeleteFuncs = funcs;
+ DeleteFuncs[next] = deleteFunc;
+ return next;
+}
+
+RESTYPE
+CreateNewResourceClass()
+{
+ RESTYPE next = lastResourceClass >> 1;
+
+ if (next & lastResourceType)
+ return 0;
+ lastResourceClass = next;
+ TypeMask = next - 1;
+ return next;
+}
+
+#endif /* NOTYET */
+
+ClientResourceRec clientTable[MAXCLIENTS];
+
+/*****************
+ * InitClientResources
+ * When a new client is created, call this to allocate space
+ * in resource table
+ *****************/
+
+int
+NoneDeleteFunc ()
+{
+}
+
+Bool
+InitClientResources(client)
+ ClientPtr client;
+{
+ register int i,
+ j;
+
+ if (client == serverClient) {
+ extern int CloseClientFont();
+ extern int DeleteAuthCont ();
+
+ lastResourceType = RT_LASTPREDEF;
+ lastResourceClass = RC_LASTPREDEF;
+ TypeMask = RC_LASTPREDEF - 1;
+ if (DeleteFuncs)
+ fsfree(DeleteFuncs);
+ DeleteFuncs = (DeleteType *) fsalloc((lastResourceType + 1) *
+ sizeof(DeleteType));
+ if (!DeleteFuncs)
+ return FALSE;
+ DeleteFuncs[RT_NONE & TypeMask] = NoneDeleteFunc;
+ DeleteFuncs[RT_FONT & TypeMask] = CloseClientFont;
+ DeleteFuncs[RT_AUTHCONT & TypeMask] = DeleteAuthCont;
+ }
+ clientTable[i = client->index].resources =
+ (ResourcePtr *) fsalloc(INITBUCKETS * sizeof(ResourcePtr));
+ if (!clientTable[i].resources)
+ return FALSE;
+ clientTable[i].buckets = INITBUCKETS;
+ clientTable[i].elements = 0;
+ clientTable[i].hashsize = INITHASHSIZE;
+ clientTable[i].fakeID = SERVER_BIT;
+ clientTable[i].endFakeID = (clientTable[i].fakeID | RESOURCE_ID_MASK) + 1;
+ for (j = 0; j < INITBUCKETS; j++) {
+ clientTable[i].resources[j] = NullResource;
+ }
+ return TRUE;
+}
+
+static int
+hash(client, id)
+ int client;
+ register FSID id;
+{
+ id &= RESOURCE_ID_MASK;
+ switch (clientTable[client].hashsize) {
+ case 6:
+ return ((int) (0x03F & (id ^ (id >> 6) ^ (id >> 12))));
+ case 7:
+ return ((int) (0x07F & (id ^ (id >> 7) ^ (id >> 13))));
+ case 8:
+ return ((int) (0x0FF & (id ^ (id >> 8) ^ (id >> 16))));
+ case 9:
+ return ((int) (0x1FF & (id ^ (id >> 9))));
+ case 10:
+ return ((int) (0x3FF & (id ^ (id >> 10))));
+ case 11:
+ return ((int) (0x7FF & (id ^ (id >> 11))));
+ }
+ return -1;
+}
+
+
+static Font
+AvailableID(client, id, maxid, goodid)
+ register int client;
+ register FSID id, maxid, goodid;
+{
+ register ResourcePtr res;
+
+ if ((goodid >= id) && (goodid <= maxid))
+ return goodid;
+ for (; id <= maxid; id++)
+ {
+ res = clientTable[client].resources[hash(client, id)];
+ while (res && (res->id != id))
+ res = res->next;
+ if (!res)
+ return id;
+ }
+ return 0;
+}
+
+/*
+ * Return the next usable fake client ID.
+ *
+ * Normally this is just the next one in line, but if we've used the last
+ * in the range, we need to find a new range of safe IDs to avoid
+ * over-running another client.
+ */
+
+FSID
+FakeClientID(client)
+ int client;
+{
+ register FSID id, maxid;
+ register ResourcePtr *resp;
+ register ResourcePtr res;
+ register int i;
+ FSID goodid;
+
+ id = clientTable[client].fakeID++;
+ if (id != clientTable[client].endFakeID)
+ return id;
+ id = ((Mask)client << CLIENTOFFSET) | SERVER_BIT;
+ maxid = id | RESOURCE_ID_MASK;
+ goodid = 0;
+ for (resp = clientTable[client].resources, i = clientTable[client].buckets;
+ --i >= 0;)
+ {
+ for (res = *resp++; res; res = res->next)
+ {
+ if ((res->id < id) || (res->id > maxid))
+ continue;
+ if (((res->id - id) >= (maxid - res->id)) ?
+ (goodid = AvailableID(client, id, res->id - 1, goodid)) :
+ !(goodid = AvailableID(client, res->id + 1, maxid, goodid)))
+ maxid = res->id - 1;
+ else
+ id = res->id + 1;
+ }
+ }
+ if (id > maxid) {
+ if (!client)
+ FatalError("FakeClientID: server internal ids exhausted\n");
+ MarkClientException(clients[client]);
+ id = ((Mask)client << CLIENTOFFSET) | (SERVER_BIT * 3);
+ maxid = id | RESOURCE_ID_MASK;
+ }
+ clientTable[client].fakeID = id + 1;
+ clientTable[client].endFakeID = maxid + 1;
+ return id;
+}
+
+Bool
+AddResource(cid, id, type, value)
+ int cid;
+ FSID id;
+ RESTYPE type;
+ pointer value;
+{
+ register ClientResourceRec *rrec;
+ register ResourcePtr res,
+ *head;
+
+ rrec = &clientTable[cid];
+ if (!rrec->buckets) {
+ ErrorF("AddResource(%x, %x, %x), client=%d \n",
+ id, type, value, cid);
+ FatalError("client not in use\n");
+ }
+ if ((rrec->elements >= 4 * rrec->buckets) &&
+ (rrec->hashsize < MAXHASHSIZE))
+ rebuild_table(cid);
+ head = &rrec->resources[hash(cid, id)];
+ res = (ResourcePtr) fsalloc(sizeof(ResourceRec));
+ if (!res) {
+ (*DeleteFuncs[type & TypeMask]) (value, id);
+ return FALSE;
+ }
+ res->next = *head;
+ res->id = id;
+ res->type = type;
+ res->value = value;
+ *head = res;
+ rrec->elements++;
+ if (!(id & SERVER_BIT) && (id >= rrec->expectID))
+ rrec->expectID = id + 1;
+ return TRUE;
+}
+
+static void
+rebuild_table(client)
+ int client;
+{
+ register int j;
+ register ResourcePtr res,
+ next;
+ ResourcePtr **tails,
+ *resources;
+ register ResourcePtr **tptr,
+ *rptr;
+
+ /*
+ * For now, preserve insertion order, since some ddx layers depend on
+ * resources being free in the opposite order they are added.
+ */
+
+ j = 2 * clientTable[client].buckets;
+ tails = (ResourcePtr **) ALLOCATE_LOCAL(j * sizeof(ResourcePtr *));
+ if (!tails)
+ return;
+ resources = (ResourcePtr *) fsalloc(j * sizeof(ResourcePtr));
+ if (!resources) {
+ DEALLOCATE_LOCAL(tails);
+ return;
+ }
+ for (rptr = resources, tptr = tails; --j >= 0; rptr++, tptr++) {
+ *rptr = NullResource;
+ *tptr = rptr;
+ }
+ clientTable[client].hashsize++;
+ for (j = clientTable[client].buckets,
+ rptr = clientTable[client].resources;
+ --j >= 0;
+ rptr++) {
+ for (res = *rptr; res; res = next) {
+ next = res->next;
+ res->next = NullResource;
+ tptr = &tails[hash(client, res->id)];
+ **tptr = res;
+ *tptr = &res->next;
+ }
+ }
+ DEALLOCATE_LOCAL(tails);
+ clientTable[client].buckets *= 2;
+ fsfree(clientTable[client].resources);
+ clientTable[client].resources = resources;
+}
+
+void
+FreeResource(cid, id, skipDeleteFuncType)
+ int cid;
+ FSID id;
+ RESTYPE skipDeleteFuncType;
+{
+ register ResourcePtr res;
+ register ResourcePtr *prev,
+ *head;
+ register int *eltptr;
+ int elements;
+ Bool gotOne = FALSE;
+
+ if (clientTable[cid].buckets) {
+ head = &clientTable[cid].resources[hash(cid, id)];
+ eltptr = &clientTable[cid].elements;
+
+ prev = head;
+ while ((res = *prev) != (ResourcePtr) 0) {
+ if (res->id == id) {
+ RESTYPE rtype = res->type;
+
+ *prev = res->next;
+ elements = --*eltptr;
+ if (rtype != skipDeleteFuncType)
+ (*DeleteFuncs[rtype & TypeMask]) (res->value, res->id);
+ fsfree(res);
+ if (*eltptr != elements)
+ prev = head;/* prev may no longer be valid */
+ gotOne = TRUE;
+ } else
+ prev = &res->next;
+ }
+ }
+ if (!gotOne)
+ FatalError("Freeing resource id=%X which isn't there\n", id);
+}
+
+#ifdef NOTYET
+void
+FreeResourceByType(cid, id, type, skipFree)
+ int cid;
+ FSID id;
+ RESTYPE type;
+ Bool skipFree;
+{
+ register ResourcePtr res;
+ register ResourcePtr *prev,
+ *head;
+
+ if (clientTable[cid].buckets) {
+ head = &clientTable[cid].resources[hash(cid, id)];
+
+ prev = head;
+ while (res = *prev) {
+ if (res->id == id && res->type == type) {
+ *prev = res->next;
+ if (!skipFree)
+ (*DeleteFuncs[type & TypeMask]) (res->value, res->id);
+ fsfree(res);
+ break;
+ } else
+ prev = &res->next;
+ }
+ }
+}
+
+/*
+ * Change the value associated with a resource id. Caller
+ * is responsible for "doing the right thing" with the old
+ * data
+ */
+
+Bool
+ChangeResourceValue(cid, id, rtype, value)
+ int cid;
+ FSID id;
+ RESTYPE rtype;
+ pointer value;
+{
+ register ResourcePtr res;
+
+ if (clientTable[cid].buckets) {
+ res = clientTable[cid].resources[hash(cid, id)];
+
+ for (; res; res = res->next)
+ if ((res->id == id) && (res->type == rtype)) {
+ res->value = value;
+ return TRUE;
+ }
+ }
+ return FALSE;
+}
+
+#endif /* NOTYET */
+
+void
+FreeClientResources(client)
+ ClientPtr client;
+{
+ register ResourcePtr *resources;
+ register ResourcePtr this;
+ int j;
+
+ /*
+ * This routine shouldn't be called with a null client, but just in case
+ * ...
+ */
+
+ if (!client)
+ return;
+
+ resources = clientTable[client->index].resources;
+ for (j = 0; j < clientTable[client->index].buckets; j++) {
+ /*
+ * It may seem silly to update the head of this resource list as we
+ * delete the members, since the entire list will be deleted any way,
+ * but there are some resource deletion functions "FreeClientPixels"
+ * for one which do a LookupID on another resource id (a Colormap id
+ * in this case), so the resource list must be kept valid up to the
+ * point that it is deleted, so every time we delete a resource, we
+ * must update the head, just like in free_resource. I hope that this
+ * doesn't slow down mass deletion appreciably. PRH
+ */
+
+ ResourcePtr *head;
+
+ head = &resources[j];
+
+ for (this = *head; this; this = *head) {
+ RESTYPE rtype = this->type;
+
+ *head = this->next;
+ (*DeleteFuncs[rtype & TypeMask]) (this->value, this->id);
+ fsfree(this);
+ }
+ }
+ fsfree(clientTable[client->index].resources);
+ clientTable[client->index].buckets = 0;
+}
+
+FreeAllResources()
+{
+ int i;
+
+ for (i = 0; i < currentMaxClients; i++) {
+ if (clientTable[i].buckets)
+ FreeClientResources(clients[i]);
+ }
+}
+
+/*
+ * lookup_id_by_type returns the object with the given id and type, else NULL.
+ */
+pointer
+LookupIDByType(cid, id, rtype)
+ int cid;
+ FSID id;
+ RESTYPE rtype;
+{
+ register ResourcePtr res;
+
+ if (clientTable[cid].buckets) {
+ res = clientTable[cid].resources[hash(cid, id)];
+
+ for (; res; res = res->next)
+ if ((res->id == id) && (res->type == rtype))
+ return res->value;
+ }
+ return (pointer) NULL;
+}
+
+#ifdef NOTYET
+/*
+ * lookup_ID_by_class returns the object with the given id and any one of the
+ * given classes, else NULL.
+ */
+pointer
+LookupIDByClass(id, classes)
+ FSID id;
+ RESTYPE classes;
+{
+ int cid;
+ register ResourcePtr res;
+
+ if (((cid = CLIENT_ID(id)) < MAXCLIENTS) && clientTable[cid].buckets) {
+ res = clientTable[cid].resources[hash(cid, id)];
+
+ for (; res; res = res->next)
+ if ((res->id == id) && (res->type & classes))
+ return res->value;
+ }
+ return (pointer) NULL;
+}
+
+#endif /* NOTYET */
diff --git a/difs/swaprep.c b/difs/swaprep.c
new file mode 100644
index 0000000..b5ed328
--- /dev/null
+++ b/difs/swaprep.c
@@ -0,0 +1,472 @@
+/* $Xorg: swaprep.c,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+ * font server reply swapping
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "FSproto.h"
+#include "clientstr.h"
+#include "misc.h"
+
+static void SwapConnSetupAccept();
+
+void
+Swap32Write(client, size, pbuf)
+ ClientPtr client;
+ int size;
+ long *pbuf;
+{
+ int n,
+ i;
+
+ size >>= 2;
+ for (i = 0; i < size; i++) {
+ swapl(&pbuf[i], n);
+ }
+ (void) WriteToClient(client, size << 2, (char *) pbuf);
+}
+
+void
+Swap16Write(client, size, pbuf)
+ ClientPtr client;
+ int size;
+ short *pbuf;
+{
+ int n,
+ i;
+
+ size >>= 1;
+ for (i = 0; i < size; i++) {
+ swaps(&pbuf[i], n);
+ }
+ (void) WriteToClient(client, size << 1, (char *) pbuf);
+}
+
+CopySwap32Write(client, size, pbuf)
+ ClientPtr client;
+ int size;
+ long *pbuf;
+{
+ int bufsize = size;
+ long *pbufT;
+ long *from,
+ *to,
+ *fromLast,
+ *toLast;
+ long tmpbuf[1];
+
+ while (!(pbufT = (long *) ALLOCATE_LOCAL(bufsize))) {
+ bufsize >>= 1;
+ if (bufsize == 4) {
+ pbufT = tmpbuf;
+ break;
+ }
+ }
+ /* convert lengths from # of bytes to # of longs */
+ size >>= 2;
+ bufsize >>= 2;
+
+ from = pbuf;
+ fromLast = from + size;
+ while (from < fromLast) {
+ int nbytes;
+
+ to = pbufT;
+ toLast = to + min(bufsize, fromLast - from);
+ nbytes = (toLast - to) << 2;
+ while (to < toLast) {
+ /*
+ * can't write "cpswapl(*from++, *to++)" because cpswapl is a
+ * macro that evaulates its args more than once
+ */
+ cpswapl(*from, *to);
+ from++;
+ to++;
+ }
+ (void) WriteToClient(client, nbytes, (char *) pbufT);
+ }
+
+ if (pbufT != tmpbuf)
+ DEALLOCATE_LOCAL((char *) pbufT);
+}
+
+void
+CopySwap16Write(client, size, pbuf)
+ ClientPtr client;
+ int size;
+ short *pbuf;
+{
+ int bufsize = size;
+ short *pbufT;
+ register short *from,
+ *to,
+ *fromLast,
+ *toLast;
+ short tmpbuf[2];
+
+ /* Allocate as big a buffer as we can... */
+ while (!(pbufT = (short *) ALLOCATE_LOCAL(bufsize))) {
+ bufsize >>= 1;
+ if (bufsize == 4) {
+ pbufT = tmpbuf;
+ break;
+ }
+ }
+
+ /* convert lengths from # of bytes to # of shorts */
+ size >>= 1;
+ bufsize >>= 1;
+
+ from = pbuf;
+ fromLast = from + size;
+ while (from < fromLast) {
+ int nbytes;
+
+ to = pbufT;
+ toLast = to + min(bufsize, fromLast - from);
+ nbytes = (toLast - to) << 1;
+ while (to < toLast) {
+ /*
+ * can't write "cpswaps(*from++, *to++)" because cpswaps is a
+ * macro that evaulates its args more than once
+ */
+ cpswaps(*from, *to);
+ from++;
+ to++;
+ }
+ (void) WriteToClient(client, nbytes, (char *) pbufT);
+ }
+
+ if (pbufT != tmpbuf)
+ DEALLOCATE_LOCAL((char *) pbufT);
+}
+
+void
+SGenericReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsGenericReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SListExtensionsReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsListExtensionsReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SQueryExtensionReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsQueryExtensionReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->major_version = lswaps(pRep->major_version);
+ pRep->minor_version = lswaps(pRep->minor_version);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SListCataloguesReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsListCataloguesReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->num_replies = lswapl(pRep->num_replies);
+ pRep->num_catalogues = lswapl(pRep->num_catalogues);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SCreateACReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsCreateACReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->status = lswaps(pRep->status);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SGetEventMaskReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsGetEventMaskReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->event_mask = lswapl(pRep->event_mask);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SGetResolutionReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsGetResolutionReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SListFontsReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsListFontsReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->following = lswapl(pRep->following);
+ pRep->nFonts = lswapl(pRep->nFonts);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+#define SwapXFontInfoHeader(reply) \
+ reply->font_header_flags = lswapl(reply->font_header_flags); \
+ \
+ reply->font_header_min_bounds_left = lswaps(reply->font_header_min_bounds_left); \
+ reply->font_header_min_bounds_right = lswaps(reply->font_header_min_bounds_right); \
+ reply->font_header_min_bounds_width = lswaps(reply->font_header_min_bounds_width); \
+ reply->font_header_min_bounds_ascent = lswaps(reply->font_header_min_bounds_ascent); \
+ reply->font_header_min_bounds_descent = lswaps(reply->font_header_min_bounds_descent); \
+ reply->font_header_min_bounds_attributes = lswaps(reply->font_header_min_bounds_attributes); \
+ \
+ reply->font_header_max_bounds_left = lswaps(reply->font_header_max_bounds_left); \
+ reply->font_header_max_bounds_right = lswaps(reply->font_header_max_bounds_right); \
+ reply->font_header_max_bounds_width = lswaps(reply->font_header_max_bounds_width); \
+ reply->font_header_max_bounds_ascent = lswaps(reply->font_header_max_bounds_ascent); \
+ reply->font_header_max_bounds_descent = lswaps(reply->font_header_max_bounds_descent); \
+ reply->font_header_max_bounds_attributes = lswaps(reply->font_header_max_bounds_attributes); \
+ \
+ reply->font_header_font_ascent = lswaps(reply->font_header_font_ascent); \
+ reply->font_header_font_descent = lswaps(reply->font_header_font_descent)
+
+void
+SListFontsWithXInfoReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsListFontsWithXInfoReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ if (size > SIZEOF(fsGenericReply)) { /* not last in series? */
+ pRep->nReplies = lswapl(pRep->nReplies);
+ SwapXFontInfoHeader(pRep);
+ }
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SOpenBitmapFontReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsOpenBitmapFontReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->otherid = lswapl(pRep->otherid);
+
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SQueryXInfoReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsQueryXInfoReply *pRep;
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ SwapXFontInfoHeader(pRep);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SQueryXExtentsReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsQueryXExtents8Reply *pRep; /* QueryXExtents16Reply is the same */
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->num_extents = lswapl(pRep->num_extents);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SQueryXBitmapsReply(client, size, pRep)
+ ClientPtr client;
+ int size;
+ fsQueryXBitmaps8Reply *pRep; /* QueryXBitmaps16Reply is the same */
+{
+ pRep->sequenceNumber = lswaps(pRep->sequenceNumber);
+ pRep->length = lswapl(pRep->length);
+ pRep->replies_hint = lswapl(pRep->replies_hint);
+ pRep->num_chars = lswapl(pRep->num_chars);
+ pRep->nbytes = lswapl(pRep->nbytes);
+ (void) WriteToClient(client, size, (char *) pRep);
+}
+
+void
+SErrorEvent(error, perror)
+ fsError *error,
+ *perror;
+{
+ *perror = *error;
+ perror->sequenceNumber = lswaps(perror->sequenceNumber);
+ perror->length = lswapl(perror->length);
+ perror->timestamp = lswapl(perror->timestamp);
+}
+
+void
+WriteSConnectionInfo(client, size, pInfo)
+ ClientPtr client;
+ unsigned long size;
+ char *pInfo;
+{
+ char *pInfoT,
+ *pInfoTBase;
+ fsConnSetupAccept *pConnSetup = (fsConnSetupAccept *) pInfo;
+ int i;
+
+ pInfoT = pInfoTBase = (char *) ALLOCATE_LOCAL(size);
+ if (!pInfoT) {
+ client->noClientException = -2;
+ return;
+ }
+ SwapConnSetupAccept(pConnSetup, (fsConnSetupAccept *) pInfoT);
+ pInfoT += SIZEOF(fsConnSetup);
+ pInfo += SIZEOF(fsConnSetup);
+
+ i = (pConnSetup->vendor_len + 3) & ~3;
+ memmove( pInfoT, pInfo, i);
+
+ (void) WriteToClient(client, (int) size, (char *) pInfoTBase);
+ DEALLOCATE_LOCAL(pInfoTBase);
+}
+
+static void
+SwapConnSetupAccept(pConnSetup, pConnSetupT)
+ fsConnSetupAccept *pConnSetup,
+ *pConnSetupT;
+{
+ pConnSetupT->length = lswapl(pConnSetup->length);
+ pConnSetupT->max_request_len = lswaps(pConnSetup->max_request_len);
+ pConnSetupT->vendor_len = lswaps(pConnSetup->vendor_len);
+ pConnSetupT->release_number = lswapl(pConnSetup->release_number);
+}
+
+void
+WriteSConnSetup(client, pcsp)
+ ClientPtr client;
+ fsConnSetup *pcsp;
+{
+ fsConnSetup cspT;
+
+ cspT.status = lswaps(pcsp->status);
+ cspT.major_version = lswaps(pcsp->major_version);
+ cspT.minor_version = lswaps(pcsp->minor_version);
+ cspT.num_alternates = pcsp->num_alternates;
+ cspT.auth_index = pcsp->auth_index;
+ cspT.alternate_len = lswaps(pcsp->alternate_len);
+ cspT.auth_len = lswaps(pcsp->auth_len);
+ (void) WriteToClient(client, SIZEOF(fsConnSetup), (char *) &cspT);
+}
+
+static void
+SwapPropOffset(po)
+ char *po;
+{
+ int i, n;
+
+ for (i=0; i<4; i++)
+ {
+ swapl(po, n);
+ po += 4;
+ }
+}
+
+void
+SwapPropInfo(pi)
+ fsPropInfo *pi;
+{
+ int i;
+ char *po;
+
+ po = (char *) pi + SIZEOF(fsPropInfo);
+ for (i = 0; i < pi->num_offsets; i++)
+ {
+ SwapPropOffset(po);
+ po += SIZEOF(fsPropOffset);
+ }
+
+ pi->num_offsets = lswapl(pi->num_offsets);
+ pi->data_len = lswapl(pi->data_len);
+}
+
+void
+SwapExtents(extents, num)
+ fsXCharInfo *extents;
+ int num;
+{
+ SwapShorts((short *)extents, num * (SIZEOF(fsXCharInfo) / 2));
+}
diff --git a/difs/swapreq.c b/difs/swapreq.c
new file mode 100644
index 0000000..9767bec
--- /dev/null
+++ b/difs/swapreq.c
@@ -0,0 +1,286 @@
+/* $Xorg: swapreq.c,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+ * swapped requests
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "misc.h"
+#include "FSproto.h"
+#include "clientstr.h"
+#include "globals.h"
+
+extern int (*ProcVector[NUM_PROC_VECTORS]) ();
+
+void
+SwapLongs(list, count)
+ long *list;
+ unsigned long count;
+{
+ int n;
+ register char *longs = (char *)list;
+
+ while (count >= 8) {
+ swapl(longs + 0, n);
+ swapl(longs + 4, n);
+ swapl(longs + 8, n);
+ swapl(longs + 12, n);
+ swapl(longs + 16, n);
+ swapl(longs + 20, n);
+ swapl(longs + 24, n);
+ swapl(longs + 28, n);
+ longs += 32;
+ count -= 8;
+ }
+ if (count != 0) {
+ do {
+ swapl(longs, n);
+ longs += 4;
+ } while (--count != 0);
+ }
+}
+
+/* Byte swap a list of shorts */
+
+void
+SwapShorts(list, count)
+ short *list;
+ register unsigned long count;
+{
+ register char *shorts = (char *)list;
+ register int n;
+
+ while (count >= 16) {
+ swaps(shorts + 0, n);
+ swaps(shorts + 2, n);
+ swaps(shorts + 4, n);
+ swaps(shorts + 6, n);
+ swaps(shorts + 8, n);
+ swaps(shorts + 10, n);
+ swaps(shorts + 12, n);
+ swaps(shorts + 14, n);
+ swaps(shorts + 16, n);
+ swaps(shorts + 18, n);
+ swaps(shorts + 20, n);
+ swaps(shorts + 22, n);
+ swaps(shorts + 24, n);
+ swaps(shorts + 26, n);
+ swaps(shorts + 28, n);
+ swaps(shorts + 30, n);
+ shorts += 32;
+ count -= 16;
+ }
+ if (count != 0) {
+ do {
+ swaps(shorts, n);
+ shorts += 2;
+ } while (--count != 0);
+ }
+}
+
+/*
+ * used for all requests that have nothing but 'length' swapped
+ */
+int
+SProcSimpleRequest(client)
+ ClientPtr client;
+{
+ REQUEST(fsReq);
+ stuff->length = lswaps(stuff->length);
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+/*
+ * used for all requests that have nothing but 'length' & a resource id swapped
+ */
+int
+SProcResourceRequest(client)
+ ClientPtr client;
+{
+ REQUEST(fsResourceReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->id = lswapl(stuff->id);
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+static void
+swap_auth(data, num)
+ pointer data;
+ int num;
+{
+ pointer p;
+ unsigned char t;
+ CARD16 namelen,
+ datalen;
+ int i;
+
+ p = data;
+ for (i = 0; i < num; i++) {
+ namelen = *(CARD16 *) p;
+ t = p[0];
+ p[0] = p[1];
+ p[1] = t;
+ p += 2;
+ datalen = *(CARD16 *) p;
+ t = p[0];
+ p[0] = p[1];
+ p[1] = t;
+ p += 2;
+ p += (namelen + 3) & ~3;
+ p += (datalen + 3) & ~3;
+ }
+}
+
+int
+SProcCreateAC(client)
+ ClientPtr client;
+{
+ REQUEST(fsCreateACReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->acid = lswapl(stuff->acid);
+ swap_auth((pointer) &stuff[1], stuff->num_auths);
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+int
+SProcSetResolution(client)
+ ClientPtr client;
+{
+ REQUEST(fsSetResolutionReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->num_resolutions = lswaps(stuff->num_resolutions);
+ SwapShorts((short *) &stuff[1], stuff->num_resolutions);
+
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+
+int
+SProcQueryExtension(client)
+ ClientPtr client;
+{
+ REQUEST(fsQueryExtensionReq);
+ stuff->length = lswaps(stuff->length);
+ return ((*ProcVector[FS_QueryExtension]) (client));
+}
+
+int
+SProcListCatalogues(client)
+ ClientPtr client;
+{
+ REQUEST(fsListCataloguesReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->maxNames = lswapl(stuff->maxNames);
+ stuff->nbytes = lswaps(stuff->nbytes);
+ return ((*ProcVector[FS_ListCatalogues]) (client));
+}
+
+int
+SProcListFonts(client)
+ ClientPtr client;
+{
+ REQUEST(fsListFontsReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->maxNames = lswapl(stuff->maxNames);
+ stuff->nbytes = lswaps(stuff->nbytes);
+ return ((*ProcVector[FS_ListFonts]) (client));
+}
+
+int
+SProcListFontsWithXInfo(client)
+ ClientPtr client;
+{
+ REQUEST(fsListFontsWithXInfoReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->maxNames = lswapl(stuff->maxNames);
+ stuff->nbytes = lswaps(stuff->nbytes);
+ return ((*ProcVector[FS_ListFontsWithXInfo]) (client));
+}
+
+int
+SProcOpenBitmapFont(client)
+ ClientPtr client;
+{
+ REQUEST(fsOpenBitmapFontReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->fid = lswapl(stuff->fid);
+ stuff->format_hint = lswapl(stuff->format_hint);
+ stuff->format_mask = lswapl(stuff->format_mask);
+ return ((*ProcVector[FS_OpenBitmapFont]) (client));
+}
+
+int
+SProcQueryXExtents(client)
+ ClientPtr client;
+{
+ REQUEST(fsQueryXExtents8Req); /* 8 and 16 are the same here */
+ stuff->length = lswaps(stuff->length);
+ stuff->fid = lswapl(stuff->fid);
+ stuff->num_ranges = lswapl(stuff->num_ranges);
+
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+int
+SProcQueryXBitmaps(client)
+ ClientPtr client;
+{
+ REQUEST(fsQueryXBitmaps8Req); /* 8 and 16 are the same here */
+ stuff->length = lswaps(stuff->length);
+ stuff->fid = lswapl(stuff->fid);
+ stuff->format = lswapl(stuff->format);
+ stuff->num_ranges = lswapl(stuff->num_ranges);
+
+ return ((*ProcVector[stuff->reqType]) (client));
+}
+
+SwapConnClientPrefix(pCCP)
+ fsConnClientPrefix *pCCP;
+{
+ pCCP->major_version = lswaps(pCCP->major_version);
+ pCCP->minor_version = lswaps(pCCP->minor_version);
+ pCCP->auth_len = lswaps(pCCP->auth_len);
+ swap_auth((pointer) &pCCP[1], pCCP->num_auths);
+}
diff --git a/difs/tables.c b/difs/tables.c
new file mode 100644
index 0000000..29ba6b7
--- /dev/null
+++ b/difs/tables.c
@@ -0,0 +1,190 @@
+/* $Xorg: tables.c,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+ * all the dispatch, error, event and reply vectors
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include "globals.h"
+
+extern int ProcInitialConnection(), ProcEstablishConnection();
+
+extern int ProcSetAuthorization(),
+ ProcSetResolution(), ProcGetResolution(), ProcNoop(),
+ ProcListExtensions(), ProcQueryExtension(),
+ ProcListFonts(), ProcListFontsWithXInfo(),
+ ProcOpenBitmapFont(), ProcQueryXInfo(), ProcQueryXExtents(),
+ ProcQueryXBitmaps(), ProcCloseFont(),
+ ProcListCatalogues(), ProcSetCatalogues(), ProcGetCatalogues(),
+ ProcSetEventMask(), ProcGetEventMask(),
+ ProcCreateAC(), ProcFreeAC();
+
+extern int SProcSimpleRequest(), SProcResourceRequest(),
+ SProcListCatalogues(),
+ SProcSetResolution(),
+ SProcQueryExtension(),
+ SProcListFonts(), SProcListFontsWithXInfo(),
+ SProcOpenBitmapFont(), SProcQueryXExtents(),
+ SProcQueryXBitmaps(),
+ SProcCreateAC();
+
+extern void SErrorEvent();
+
+extern void NotImplemented(), SGenericReply(),
+ SListExtensionsReply(),
+ SListCataloguesReply(),
+ SQueryExtensionReply(),
+ SListFontsReply(), SListFontsWithXInfoReply(),
+ SOpenBitmapFontReply(),
+ SQueryXInfoReply(), SQueryXExtentsReply(),
+ SQueryXBitmapsReply(),
+ SGetEventMaskReply(), SCreateACReply(), SGetResolutionReply(),
+ SOpenBitmapFontReply();
+
+
+int (*InitialVector[3]) () =
+{
+ 0,
+ ProcInitialConnection,
+ ProcEstablishConnection
+};
+
+int (*ProcVector[NUM_PROC_VECTORS]) () =
+{
+ ProcNoop, /* 0 */
+ ProcListExtensions,
+ ProcQueryExtension,
+ ProcListCatalogues,
+ ProcSetCatalogues,
+ ProcGetCatalogues, /* 5 */
+ ProcSetEventMask,
+ ProcGetEventMask,
+ ProcCreateAC,
+ ProcFreeAC,
+ ProcSetAuthorization, /* 10 */
+ ProcSetResolution,
+ ProcGetResolution,
+ ProcListFonts,
+ ProcListFontsWithXInfo,
+ ProcOpenBitmapFont, /* 15 */
+ ProcQueryXInfo,
+ ProcQueryXExtents,
+ ProcQueryXExtents,
+ ProcQueryXBitmaps,
+ ProcQueryXBitmaps, /* 20 */
+ ProcCloseFont,
+ 0,
+ 0,
+ 0
+};
+
+int (*SwappedProcVector[NUM_PROC_VECTORS]) () =
+{
+ SProcSimpleRequest, /* 0 */
+ SProcSimpleRequest,
+ SProcQueryExtension,
+ SProcListCatalogues,
+ SProcSimpleRequest, /* SetCatalogues */
+ SProcSimpleRequest, /* 5 */
+ SProcResourceRequest, /* SetEventMask */
+ SProcSimpleRequest,
+ SProcCreateAC,
+ SProcResourceRequest,
+ SProcResourceRequest, /* 10 */
+ SProcSetResolution,
+ SProcSimpleRequest,
+ SProcListFonts,
+ SProcListFontsWithXInfo,
+ SProcOpenBitmapFont, /* 15 */
+ SProcResourceRequest,
+ SProcQueryXExtents,
+ SProcQueryXExtents,
+ SProcQueryXBitmaps,
+ SProcQueryXBitmaps, /* 20 */
+ SProcResourceRequest,
+ 0,
+ 0,
+ 0
+};
+
+void (*EventSwapVector[NUM_EVENT_VECTORS]) () =
+{
+ SErrorEvent,
+ NotImplemented,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0,
+ 0
+};
+
+void (*ReplySwapVector[NUM_PROC_VECTORS]) () =
+{
+ NotImplemented, /* NoOp */
+ SListExtensionsReply,
+ SQueryExtensionReply, /* SQueryExtensionReply */
+ SListCataloguesReply,
+ NotImplemented, /* SetCatalogues */
+ SGenericReply, /* GetCatalogues */
+ NotImplemented, /* SetEventMask */
+ SGetEventMaskReply,
+ SCreateACReply,
+ NotImplemented, /* FreeAC */
+ NotImplemented, /* SetAuthorization - 10 */
+ NotImplemented, /* SetResolution */
+ SGetResolutionReply,
+ SListFontsReply,
+ SListFontsWithXInfoReply,
+ SOpenBitmapFontReply, /* 15 */
+ SQueryXInfoReply,
+ SQueryXExtentsReply,
+ SQueryXExtentsReply,
+ SQueryXBitmapsReply,
+ SQueryXBitmapsReply, /* 20 */
+ NotImplemented, /* Close */
+ NotImplemented,
+ NotImplemented
+};
diff --git a/include/access.h b/include/access.h
new file mode 100644
index 0000000..21957c3
--- /dev/null
+++ b/include/access.h
@@ -0,0 +1,66 @@
+/* $Xorg: access.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)access.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _ACCESS_H_
+#define _ACCESS_H_
+
+typedef struct _hostaddress *HostList;
+
+#define HOST_AF_INET 1
+#define HOST_AF_DECnet 2
+
+extern int AddHost();
+extern int RemoveHost();
+extern int ValidHost();
+extern int GetHostAddress();
+extern int CheckClientAuthorization();
+extern void AccessSetConnectionLimit();
+
+#endif /* _ACCESS_H_ */
diff --git a/include/accstr.h b/include/accstr.h
new file mode 100644
index 0000000..55ce4f3
--- /dev/null
+++ b/include/accstr.h
@@ -0,0 +1,64 @@
+/* $Xorg: accstr.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)accstr.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _ACCSTR_H_
+#define _ACCSTR_H_
+#include "misc.h"
+#include "access.h"
+
+typedef struct _hostaddress {
+ int type;
+ pointer address;
+ int addr_len;
+ struct _hostaddress *next;
+} HostAddress;
+
+#endif /* _ACCSTR_H_ */
diff --git a/include/assert.h b/include/assert.h
new file mode 100644
index 0000000..aa95a69
--- /dev/null
+++ b/include/assert.h
@@ -0,0 +1,59 @@
+/* $Xorg: assert.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)assert.h 4.1 91/05/02
+ *
+ */
+#ifdef DEBUG
+#include <stdio.h>
+#ifdef SABER
+#define assert(ex) {if (!(ex)){(void)fprintf(stderr,"Assertion \"ex\" failed: file \"%s\", line %d\n", __FILE__, __LINE__);saber_stop();}}
+#else
+#define assert(ex) {if (!(ex)){(void)fprintf(stderr,"Assertion \"ex\" failed: file \"%s\", line %d\n", __FILE__, __LINE__);abort();}}
+#endif
+#else
+#define assert(ex)
+#endif
diff --git a/include/auth.h b/include/auth.h
new file mode 100644
index 0000000..79fbbfb
--- /dev/null
+++ b/include/auth.h
@@ -0,0 +1,58 @@
+/* $Xorg: auth.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)auth.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _AUTH_H_
+#define _AUTH_H_
+
+typedef struct _authcontext *AuthContextPtr;
+
+extern AuthContextPtr GetClientAuthorization();
+
+#endif /* _AUTH_H_ */
diff --git a/include/authstr.h b/include/authstr.h
new file mode 100644
index 0000000..de01f42
--- /dev/null
+++ b/include/authstr.h
@@ -0,0 +1,61 @@
+/* $Xorg: authstr.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)authstr.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _AUTHSTR_H_
+#define _AUTHSTR_H_
+#include "auth.h"
+
+typedef struct _authcontext {
+ char *authname;
+ char *authdata;
+ FSID acid;
+} AuthContextRec;
+
+#endif /* _AUTHSTR_H_ */
diff --git a/include/cache.h b/include/cache.h
new file mode 100644
index 0000000..e752055
--- /dev/null
+++ b/include/cache.h
@@ -0,0 +1,73 @@
+/* $Xorg: cache.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)cache.h 4.1 91/05/02
+ *
+ */
+#ifndef _CACHE_H_
+#define _CACHE_H_
+#include "misc.h"
+
+#define CacheWasReset 1
+#define CacheEntryFreed 2
+#define CacheEntryOld 3
+
+typedef unsigned long CacheID;
+typedef unsigned long Cache;
+typedef void (*CacheFree) ();
+
+typedef struct _cache *CachePtr;
+
+extern CacheID CacheStoreMemory();
+extern int CacheFreeMemory();
+extern void CacheSimpleFree();
+extern Cache CacheInit();
+extern void CacheReset();
+extern void CacheResize();
+extern pointer CacheFetchMemory();
+extern void CacheStats();
+
+#endif /* _CACHE_H_ */
diff --git a/include/cachestr.h b/include/cachestr.h
new file mode 100644
index 0000000..19bdd5a
--- /dev/null
+++ b/include/cachestr.h
@@ -0,0 +1,77 @@
+/* $Xorg: cachestr.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)cachestr.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _CACHSTR_H_
+#define _CACHSTR_H_
+#include "cache.h"
+
+typedef struct _cache_entry {
+ pointer data;
+ unsigned long timestamp;
+ CacheID id;
+ unsigned long size;
+ CacheFree free_func;
+ struct _cache_entry *next;
+} CacheEntryRec, *CacheEntryPtr;
+
+typedef struct _cache {
+ Cache id;
+ CacheEntryPtr *entries;
+ int elements;
+ int buckets;
+ int hashsize;
+ CacheID nextid;
+ unsigned long maxsize;
+ unsigned long cursize;
+} CacheRec;
+
+#define NullCacheEntryPtr ((CacheEntryPtr) 0)
+
+#endif /* _CACHSTR_H_ */
diff --git a/include/client.h b/include/client.h
new file mode 100644
index 0000000..e09f513
--- /dev/null
+++ b/include/client.h
@@ -0,0 +1,117 @@
+/* $Xorg: client.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#ifndef _CLIENT_H_
+#define _CLIENT_H_
+
+typedef struct _Client *ClientPtr;
+
+extern ClientPtr *clients;
+extern ClientPtr serverClient;
+
+#define NullClient ((ClientPtr) NULL)
+
+#define SERVER_CLIENT 0
+#define MINCLIENT 1
+
+#define CLIENT_ALIVE 0
+#define CLIENT_GONE 1
+#define CLIENT_AGED 2
+#define CLIENT_TIMED_OUT 4
+
+extern int currentMaxClients;
+
+#define REQUEST(type) \
+ type *stuff = (type *)client->requestBuffer
+
+#define REQUEST_FIXED_SIZE(fs_req, n) \
+ if (((SIZEOF(fs_req) >> 2) > stuff->length) || \
+ (((SIZEOF(fs_req) + (n) + 3) >> 2) != stuff->length)) { \
+ int lengthword = stuff->length; \
+ SendErrToClient(client, FSBadLength, (pointer)&lengthword); \
+ return (FSBadLength); \
+ }
+
+#define REQUEST_SIZE_MATCH(fs_req) \
+ if ((SIZEOF(fs_req) >> 2) != stuff->length) { \
+ int lengthword = stuff->length; \
+ SendErrToClient(client, FSBadLength, (pointer)&lengthword); \
+ return (FSBadLength); \
+ }
+
+#define REQUEST_AT_LEAST_SIZE(fs_req) \
+ if ((SIZEOF(fs_req) >> 2) > stuff->length) { \
+ int lengthword = stuff->length; \
+ SendErrToClient(client, FSBadLength, (pointer)&lengthword); \
+ return (FSBadLength); \
+ }
+
+#define WriteReplyToClient(client, size, reply) \
+ if ((client)->swapped) \
+ (*ReplySwapVector[((fsReq *)(client)->requestBuffer)->reqType]) \
+ (client, (int)(size), reply); \
+ else (void)WriteToClient(client, (int)(size), (char *)(reply));
+
+#define WriteSwappedDataToClient(client, size, pbuf) \
+ if ((client)->swapped) \
+ (*(client)->pSwapReplyFunc)(client, (int)(size), pbuf); \
+ else (void) WriteToClient(client, (int)(size), (char *)(pbuf));
+
+
+extern void SendErrToClient();
+
+extern void SwapFontHeader();
+extern void SwapExtents();
+extern void SwapPropInfo();
+extern void SwapCharInfo();
+extern void WriteSConnSetup();
+extern void WriteSConnectionInfo();
+extern void SErrorEvent();
+
+typedef struct _WorkQueue *WorkQueuePtr;
+extern void ProcessWorkQueue();
+
+#endif /* _CLIENT_H_ */
diff --git a/include/clientstr.h b/include/clientstr.h
new file mode 100644
index 0000000..c52c746
--- /dev/null
+++ b/include/clientstr.h
@@ -0,0 +1,89 @@
+/* $Xorg: clientstr.h,v 1.4 2001/02/09 02:05:43 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef _CLIENTSTR_H_
+#define _CLIENTSTR_H_
+
+#include "FS.h"
+#include "client.h"
+#include "auth.h"
+#include "misc.h"
+
+typedef struct _Client {
+ int index;
+ pointer osPrivate;
+ int noClientException;
+ int (**requestVector) ();
+ pointer requestBuffer;
+ int clientGone;
+ int sequence;
+ Bool swapped;
+ long last_request_time;
+ void (*pSwapReplyFunc) ();
+ AuthContextPtr auth;
+ int auth_generation;
+ AuthContextPtr default_auth;
+ char *catalogues;
+ int num_catalogues;
+ Mask eventmask;
+ fsResolution *resolutions;
+ int num_resolutions;
+ int major_version; /* client-major-protocol-version */
+ int minor_version;
+} ClientRec;
+
+typedef struct _WorkQueue {
+ struct _WorkQueue *next;
+ Bool (*function) ();
+ ClientPtr client;
+ pointer closure;
+} WorkQueueRec;
+
+
+extern void CloseDownClient();
+
+#endif /* _CLIENTSTR_H_ */
diff --git a/include/closestr.h b/include/closestr.h
new file mode 100644
index 0000000..925af84
--- /dev/null
+++ b/include/closestr.h
@@ -0,0 +1,143 @@
+/* $Xorg: closestr.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * $NCDId: @(#)closestr.h,v 4.1 1991/05/02 04:15:46 lemke Exp $
+ *
+ */
+
+#ifndef CLOSESTR_H
+#define CLOSESTR_H
+
+#include "FSproto.h"
+#include "closure.h"
+#include "misc.h"
+#include "font.h"
+
+/* closure structures */
+
+/* OpenFont */
+
+typedef struct _OFclosure {
+ ClientPtr client;
+ short current_fpe;
+ short num_fpes;
+ FontPathElementPtr *fpe_list;
+ Mask flags;
+ fsBitmapFormat format;
+ fsBitmapFormatMask format_mask;
+ Bool slept;
+ FSID fontid;
+ char *fontname;
+ int fnamelen;
+ char *orig_name;
+ int orig_len;
+ FontPtr non_cachable_font;
+} OFclosureRec;
+
+/* QueryExtents */
+
+typedef struct _QEclosure {
+ ClientPtr client;
+ int nranges;
+ fsRange *range;
+ FontPtr pfont;
+ Mask flags;
+ Bool slept;
+} QEclosureRec;
+
+/* QueryBitmaps */
+
+typedef struct _QBclosure {
+ ClientPtr client;
+ int nranges;
+ fsRange *range;
+ FontPtr pfont;
+ fsBitmapFormat format;
+ Mask flags;
+ Bool slept;
+} QBclosureRec;
+
+/* ListFontsWithInfo */
+
+#define XLFDMAXFONTNAMELEN 256
+typedef struct _LFWIstate {
+ char pattern[XLFDMAXFONTNAMELEN]; /* max len of font name */
+ int patlen;
+ int current_fpe;
+ int max_names;
+ Bool list_started;
+ pointer private;
+} LFWIstateRec, *LFWIstatePtr;
+
+
+typedef struct _LFWXIclosure {
+ ClientPtr client;
+ int num_fpes;
+ FontPathElementPtr *fpe_list;
+ fsListFontsWithXInfoReply *reply;
+ int length;
+ LFWIstateRec current;
+ LFWIstateRec saved;
+ int savedNumFonts;
+ Bool haveSaved;
+ Bool slept;
+ char *savedName;
+} LFWXIclosureRec;
+
+typedef struct _LFclosure {
+ ClientPtr client;
+ int num_fpes;
+ FontPathElementPtr *fpe_list;
+ FontNamesPtr names;
+ LFWIstateRec current;
+ LFWIstateRec saved;
+ Bool haveSaved;
+ Bool slept;
+ char *savedName;
+ int savedNameLen;
+} LFclosureRec;
+
+#endif /* CLOSESTR_H */
diff --git a/include/closure.h b/include/closure.h
new file mode 100644
index 0000000..ea8e260
--- /dev/null
+++ b/include/closure.h
@@ -0,0 +1,59 @@
+/* $Xorg: closure.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)closure.h 4.1 91/05/02
+ *
+ */
+#ifndef CLOSURE_H
+#define CLOSURE_H 1
+
+typedef struct _LFclosure *LFclosurePtr;
+typedef struct _LFWXIclosure *LFWXIclosurePtr;
+typedef struct _OFclosure *OFclosurePtr;
+typedef struct _QEclosure *QEclosurePtr;
+typedef struct _QBclosure *QBclosurePtr;
+
+#endif /* CLOSURE_H */
diff --git a/include/difsfn.h b/include/difsfn.h
new file mode 100644
index 0000000..c795eea
--- /dev/null
+++ b/include/difsfn.h
@@ -0,0 +1,63 @@
+/* $Xorg: difsfn.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef _DIFSFONT_H_
+#define _DIFSFONT_H_
+#include "misc.h"
+#include "font.h"
+
+typedef struct _ClientFont *ClientFontPtr;
+typedef struct _FontIDList *FontIDListPtr;
+typedef struct _font_name_cache FontNameCachePtr;
+
+#define NullClientFont ((ClientFontPtr)0)
+
+extern FontPtr FindCachedFontName();
+extern int CacheFontName();
+extern void RemoveBlockAndWakeupHandlers();
+
+#endif /* _DIFSFONT_H_ */
diff --git a/include/difsfnst.h b/include/difsfnst.h
new file mode 100644
index 0000000..5141051
--- /dev/null
+++ b/include/difsfnst.h
@@ -0,0 +1,74 @@
+/* $Xorg: difsfnst.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+
+#ifndef _DIFSFONTST_H_
+#define _DIFSFONTST_H_
+
+#include "difsfn.h"
+#include "font.h"
+#include "misc.h"
+
+/* has per-client info about the font */
+typedef struct _ClientFont {
+ FontPtr font;
+ int clientindex;
+} ClientFontRec;
+
+typedef struct _font_name_cache {
+ char *name;
+ int namelen;
+ FontPtr font;
+} FontNameCacheRec;
+
+/* one of these per client, with as many IDs as are needed */
+typedef struct _FontIDList {
+ Font *client_list;
+ int num;
+ int size;
+} FontIDListRec;
+
+#endif /* _DIFSFONTST_H_ */
diff --git a/include/extentst.h b/include/extentst.h
new file mode 100644
index 0000000..2d0f0ed
--- /dev/null
+++ b/include/extentst.h
@@ -0,0 +1,88 @@
+/* $Xorg: extentst.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)extentst.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _EXTENTST_H_
+#define _EXTENTST_H_
+
+typedef struct _ExtensionEntry {
+ int index;
+ void (*CloseDown) ();
+ char *name;
+ int base;
+ int eventBase;
+ int eventLast;
+ int errorBase;
+ int errorLast;
+ int num_aliases;
+ char **aliases;
+ pointer extPrivate;
+ unsigned short (*MinorOpcode) ();
+} ExtensionEntry;
+
+extern void (*EventSwapVector[]) ();
+
+typedef void (*ExtensionLookupProc) ();
+
+typedef struct _ProcEntry {
+ char *name;
+ ExtensionLookupProc proc;
+} ProcEntryRec, *ProcEntryPtr;
+
+extern void InitExtensions();
+extern int ProcQueryExtension();
+extern int ProcListExtensions();
+extern ExtensionEntry *AddExtension();
+extern Bool AddExtensionAlias();
+extern ExtensionLookupProc LookupProc();
+extern Bool RegisterProc();
+extern unsigned short MinorOpcodeOfRequest();
+extern unsigned short StandardMinorOpcode();
+
+#endif /* _EXTENTST_H_ */
diff --git a/include/globals.h b/include/globals.h
new file mode 100644
index 0000000..9b4d083
--- /dev/null
+++ b/include/globals.h
@@ -0,0 +1,78 @@
+/* $Xorg: globals.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)globals.h 4.2 91/05/03
+ *
+ */
+
+#ifndef _GLOBALS_H_
+#define _GLOBALS_H_
+
+#include "FSproto.h" /* for fsResolution */
+
+extern long TimeOutValue;
+extern long ReapClientTime;
+
+extern int currentMaxClients;
+extern long MaxClients;
+extern int serverGeneration;
+
+extern char isItTimeToYield;
+extern char dispatchException;
+
+extern int argcGlobal;
+extern char **argvGlobal;
+
+/* bit values for dispatchException */
+#define DE_RESET 0x1
+#define DE_TERMINATE 0x2
+#define DE_RECONFIG 0x4
+#define DE_FLUSH 0x8
+
+/* size of vector tables */
+#define NUM_PROC_VECTORS 25
+#define NUM_EVENT_VECTORS 8
+#endif /* _GLOBALS_H_ */
diff --git a/include/misc.h b/include/misc.h
new file mode 100644
index 0000000..b4038aa
--- /dev/null
+++ b/include/misc.h
@@ -0,0 +1,195 @@
+/* $Xorg: misc.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#ifndef _MISC_H_
+#define _MISC_H_
+
+#include <X11/Xosdefs.h>
+#include <X11/Xfuncs.h>
+
+#include "assert.h" /* so its everywhere */
+
+#ifndef NULL
+
+#ifndef X_NOT_STDC_ENV
+#include <stddef.h>
+#else
+#define NULL 0
+#endif
+
+#endif
+
+#define MAXCLIENTS 128
+
+typedef unsigned char *pointer;
+typedef int Bool;
+typedef unsigned long Atom;
+
+#define MILLI_PER_SECOND (1000)
+#define MILLI_PER_MINUTE (1000 * 60)
+
+#ifndef TRUE
+#define TRUE 1
+#define FALSE 0
+#endif
+
+#define min(a, b) (((a) < (b)) ? (a) : (b))
+#define max(a, b) (((a) > (b)) ? (a) : (b))
+#define abs(a) ((a) > 0 ? (a) : -(a))
+
+#include "os.h"
+
+#define lowbit(x) ((x) & (~(x) + 1))
+
+/* byte swapping helpers */
+
+/* byte swap a long literal */
+#define lswapl(x) ((((x) & 0xff) << 24) |\
+ (((x) & 0xff00) << 8) |\
+ (((x) & 0xff0000) >> 8) |\
+ (((x) >> 24) & 0xff))
+
+/* byte swap a short literal */
+#define lswaps(x) ((((x) & 0xff) << 8) | (((x) >> 8) & 0xff))
+
+
+/* byte swap a long */
+#define swapl(x, n) n = ((char *) (x))[0];\
+ ((char *) (x))[0] = ((char *) (x))[3];\
+ ((char *) (x))[3] = n;\
+ n = ((char *) (x))[1];\
+ ((char *) (x))[1] = ((char *) (x))[2];\
+ ((char *) (x))[2] = n;
+
+/* byte swap a short */
+#define swaps(x, n) n = ((char *) (x))[0];\
+ ((char *) (x))[0] = ((char *) (x))[1];\
+ ((char *) (x))[1] = n
+
+/* copy long from src to dst byteswapping on the way */
+#define cpswapl(src, dst) \
+ ((char *)&(dst))[0] = ((char *) &(src))[3];\
+ ((char *)&(dst))[1] = ((char *) &(src))[2];\
+ ((char *)&(dst))[2] = ((char *) &(src))[1];\
+ ((char *)&(dst))[3] = ((char *) &(src))[0];
+
+/* copy short from src to dst byteswapping on the way */
+#define cpswaps(src, dst)\
+ ((char *) &(dst))[0] = ((char *) &(src))[1];\
+ ((char *) &(dst))[1] = ((char *) &(src))[0];
+
+
+extern void SwapLongs();
+extern void SwapShorts();
+
+extern void CopyIsoLatin1Lowered();
+extern void NoopDDA();
+extern char *NameForAtom();
+extern void BitOrderInvert();
+extern void TwoByteInvert();
+extern void FourByteInvert();
+
+extern long GetTimeInMillis();
+
+
+#if (defined(__STDC__) && !defined(UNIXCPP)) || defined(ANSICPP)
+#define fsCat(x,y) x##_##y
+#else
+#define fsCat(x,y) x/**/_/**/y
+#endif
+
+/* copy a xCharInfo into a XCharInfo */
+
+#define fsPack_XCharInfo(structure, packet) \
+ fsCat(packet,left) = (structure)->leftSideBearing; \
+ fsCat(packet,right) = (structure)->rightSideBearing; \
+ fsCat(packet,width) = (structure)->characterWidth; \
+ fsCat(packet,ascent) = (structure)->ascent; \
+ fsCat(packet,descent) = (structure)->descent; \
+ fsCat(packet,attributes) = (structure)->attributes
+
+
+/* copy a FontInfoRec into a XFontInfoHeader */
+
+#define fsPack_XFontInfoHeader(structure, packet, clientversion) \
+ (packet)->font_header_flags = ((structure)->allExist) ? FontInfoAllCharsExist : 0; \
+ (packet)->font_header_draw_direction = ((structure)->drawDirection == LeftToRight) \
+ ? LeftToRightDrawDirection : RightToLeftDrawDirection; \
+ \
+ if ((structure)->inkInside) \
+ (packet)->font_header_flags |= FontInfoInkInside; \
+ \
+ if (clientversion > 1) { \
+ (packet)->font_hdr_char_range_min_char_high = (structure)->firstRow; \
+ (packet)->font_hdr_char_range_min_char_low = (structure)->firstCol; \
+ (packet)->font_hdr_char_range_max_char_high = (structure)->lastRow; \
+ (packet)->font_hdr_char_range_max_char_low = (structure)->lastCol; \
+ (packet)->font_header_default_char_high = (structure)->defaultCh >> 8; \
+ (packet)->font_header_default_char_low = (structure)->defaultCh & 0xff; \
+ } else { \
+ (packet)->font_hdr_char_range_min_char_high = (structure)->firstCol; \
+ (packet)->font_hdr_char_range_min_char_low = (structure)->firstRow; \
+ (packet)->font_hdr_char_range_max_char_high = (structure)->lastCol; \
+ (packet)->font_hdr_char_range_max_char_low = (structure)->lastRow; \
+ (packet)->font_header_default_char_high = (structure)->defaultCh & 0xff; \
+ (packet)->font_header_default_char_low = (structure)->defaultCh >> 8; \
+ } \
+ \
+ fsPack_XCharInfo(&(structure)->ink_minbounds, (packet)->font_header_min_bounds); \
+ fsPack_XCharInfo(&(structure)->ink_maxbounds, (packet)->font_header_max_bounds); \
+ \
+ (packet)->font_header_font_ascent = (structure)->fontAscent; \
+ (packet)->font_header_font_descent = (structure)->fontDescent
+
+
+typedef struct { /* when cloning, need old transport info */
+ int trans_id;
+ int fd;
+ int portnum;
+} OldListenRec;
+
+
+#endif /* _MISC_H_ */
diff --git a/include/os.h b/include/os.h
new file mode 100644
index 0000000..c5ff552
--- /dev/null
+++ b/include/os.h
@@ -0,0 +1,96 @@
+/* $Xorg: os.h,v 1.5 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * $NCDId: @(#)os.h,v 4.2 1991/05/10 07:59:16 lemke Exp $
+ *
+ */
+
+#ifndef _OS_H_
+#define _OS_H_
+
+#include "FSproto.h"
+#include "misc.h"
+#define ALLOCATE_LOCAL_FALLBACK(_size) FSalloc((unsigned long)_size)
+#define DEALLOCATE_LOCAL_FALLBACK(_ptr) FSfree((pointer)_ptr)
+#include "X11/Xalloca.h"
+
+#define MAX_REQUEST_SIZE 16384
+
+extern unsigned long *FSalloc();
+extern unsigned long *FSrealloc();
+extern void FSfree();
+
+#define fsalloc(size) FSalloc((unsigned long)size)
+#define fsrealloc(ptr, size) FSrealloc((pointer)ptr, (unsigned long)size)
+#define fsfree(ptr) FSfree((pointer)ptr)
+
+int ReadRequest();
+
+Bool CloseDownConnection();
+void CreateSockets();
+void CloseSockets();
+void FlushAllOuput();
+long GetTimeInMIllis();
+void Error();
+void InitErrors();
+void CloseErrors();
+void NoticeF();
+void ErrorF();
+void FatalError();
+void SetConfigValues();
+
+typedef pointer FID;
+typedef struct _FontPathRec *FontPathPtr;
+
+FontPathPtr expand_font_name_pattern();
+
+typedef struct _alt_server *AlternateServerPtr;
+typedef struct _auth *AuthPtr;
+
+extern int ListCatalogues();
+extern int ListAlternateServers();
+
+#endif /* _OS_H_ */
diff --git a/include/osstruct.h b/include/osstruct.h
new file mode 100644
index 0000000..cea8603
--- /dev/null
+++ b/include/osstruct.h
@@ -0,0 +1,68 @@
+/* $Xorg: osstruct.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)osstruct.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _OSSTRUCT_H_
+#define _OSSTRUCT_H_
+#include "os.h"
+
+typedef struct _alt_server {
+ char subset;
+ short namelen;
+ char *name;
+} AlternateServerRec;
+
+typedef struct _auth {
+ short namelen;
+ short datalen;
+ char *name;
+ char *data;
+} AuthRec;
+
+#endif /* _OSSTRUCT_H_ */
diff --git a/include/servermd.h b/include/servermd.h
new file mode 100644
index 0000000..7233bd9
--- /dev/null
+++ b/include/servermd.h
@@ -0,0 +1,62 @@
+/* $Xorg: servermd.h,v 1.6 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ */
+#ifndef _SERVERMD_H_
+#define _SERVERMD_H_
+
+#ifndef VENDOR_RELEASE
+#define VENDOR_RELEASE 6600
+#endif
+
+#ifndef VENDOR_STRING
+#define VENDOR_STRING "The X.Org Group"
+#endif
+
+#ifndef DEFAULT_FS_PORT
+#define DEFAULT_FS_PORT 7100
+#endif
+
+#endif /* _SERVERMD_H_ */
diff --git a/include/site.h b/include/site.h
new file mode 100644
index 0000000..41ebc15
--- /dev/null
+++ b/include/site.h
@@ -0,0 +1,67 @@
+/* $Xorg: site.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)site.h 4.3 91/05/06
+ *
+ */
+
+#ifndef _SITE_H_
+#define _SITE_H_
+/*
+ * site dependent definitions
+ */
+
+/* after twice this amount of time (in seconds) with no input from the
+ * client, it'll be toasted
+ */
+#define CLIENT_TIMEOUT 600
+
+
+#define DEFAULT_TIMEOUT 60
+
+#define DEFAULT_CLIENT_LIMIT 20
+
+#endif /* _SITE_H_ */
diff --git a/os/access.c b/os/access.c
new file mode 100644
index 0000000..43c035b
--- /dev/null
+++ b/os/access.c
@@ -0,0 +1,138 @@
+/* $Xorg: access.c,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include <X11/Xos.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <netdb.h>
+#include <netinet/in.h>
+#include "clientstr.h"
+#include "misc.h"
+#include "site.h"
+#include "accstr.h"
+#include "osdep.h"
+#include "osstruct.h"
+
+long MaxClients = DEFAULT_CLIENT_LIMIT;
+
+void
+AccessSetConnectionLimit(num)
+ int num;
+{
+ num++; /* take serverClient into account */
+ if (num > MAXSOCKS) {
+ ErrorF("Client limit of %d too high; using default of %d\n",
+ num, DEFAULT_CLIENT_LIMIT);
+ return;
+ }
+ MaxClients = num;
+}
+
+/*
+ * XXX
+ *
+ * needs massive amounts of OS-dependent work (big surprise)
+ */
+int
+GetHostAddress(addr)
+ HostAddress *addr;
+{
+ char hname[64];
+ struct hostent *hp;
+
+ addr->addr_len = sizeof(struct in_addr);
+ addr->address = (pointer) fsalloc(addr->addr_len);
+ if (!addr->address)
+ return FSBadAlloc;
+ addr->type = HOST_AF_INET;
+ gethostname(hname, sizeof(hname));
+ hp = gethostbyname(hname);
+ if (hp) {
+ memmove( (char *) addr->address, (char *) hp->h_addr, addr->addr_len);
+ } else {
+ fsfree((char *) addr->address);
+ return FSBadName;
+ }
+ return FSSuccess;
+}
+
+/* ARGSUSED */
+int
+CheckClientAuthorization(client, client_auth, accept, index, size, auth_data)
+ ClientPtr client;
+ AuthPtr client_auth;
+ int *accept;
+ int *index;
+ int *size;
+ char **auth_data;
+{
+ OsCommPtr oc;
+ int i;
+
+ /* now that it's connected, zero the connect time
+ so it doesn't get killed */
+ oc = (OsCommPtr)client->osPrivate;
+ oc->conn_time = 0;
+
+ *size = 0;
+ *accept = AuthSuccess;
+
+ client->auth_generation++;
+
+#define AUTH1_NAME "hp-hostname-1"
+#define AUTH2_NAME "hp-printername-1"
+ for (i = 0; i < *index; i++)
+ if (client_auth[i].namelen == sizeof(AUTH1_NAME) &&
+ !strcmp(client_auth[i].name, AUTH1_NAME) ||
+ client_auth[i].namelen == sizeof(AUTH2_NAME) &&
+ !strcmp(client_auth[i].name, AUTH2_NAME)) break;
+ if (i == *index)
+ i = 0;
+ else
+ i++;
+ *index = i;
+ return FSSuccess;
+}
diff --git a/os/config.c b/os/config.c
new file mode 100644
index 0000000..5648e5b
--- /dev/null
+++ b/os/config.c
@@ -0,0 +1,610 @@
+/* $Xorg: config.c,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * $NCDId: @(#)config.c,v 4.6 1991/07/09 14:08:09 lemke Exp $
+ *
+ */
+
+#include <stdio.h>
+#include <ctype.h>
+#include <X11/Xos.h>
+#include "misc.h"
+#include "configstr.h"
+#include "osdep.h"
+#include "globals.h"
+#include "access.h"
+
+static char *font_catalogue = NULL;
+
+static char *config_set_int(),
+ *config_set_bool(),
+ *config_set_catalogue(),
+ *config_set_glyph_caching_mode(),
+ *config_set_list(),
+ *config_set_file(),
+ *config_set_resolutions(),
+ *config_set_snf_format();
+
+/* these need to be in lower case and alphabetical order so a
+ * binary search lookup can be used
+ */
+static ConfigOptionRec config_options[] = {
+ {"alternate-servers", config_set_list},
+ {"catalogue", config_set_catalogue},
+ {"client-limit", config_set_int},
+ {"clone-self", config_set_bool},
+ {"default-point-size", config_set_int},
+ {"default-resolutions", config_set_resolutions},
+ {"deferglyphs", config_set_glyph_caching_mode},
+ {"error-file", config_set_file},
+ {"port", config_set_int},
+ {"server-number", config_set_int},
+ {"snf-format", config_set_snf_format},
+ {"trusted-clients", config_set_list},
+ {"use-syslog", config_set_bool},
+ {(char *) 0, 0},
+};
+
+char *ConfigErrors[] = {
+ "",
+ "CONFIG: insufficient memory to load configuration file \"%s\"\n",
+ "CONFIG: can't open configuration file \"%s\"\n",
+ "CONFIG: error reading configuration file \"%s\"\n",
+ "CONFIG: bad value \"%s\" for parameter \"%s\"\n",
+ "CONFIG: unknown parameter \"%s\"\n",
+ "CONFIG: missing '=' after parameter \"%s\"\n",
+ "CONFIG: value out of range for parameter \"%s\"\n",
+ "CONFIG: syntax error near parameter \"%s\"\n",
+ "CONFIG: missing value for parameter \"%s\"\n",
+ "CONFIG: extra value for parameter \"%s\"\n",
+};
+
+#define iseol(c) ((c) == '\n' || (c) == '\r' || (c) == '\f')
+#define skip_whitespace(c) while(isspace(*(c)) || *(c) == ',') (c)++;
+#define skip_val(c) while(!isspace(*(c)) && *(c) != ',' && *(c) != '\0')\
+ (c) ++;
+#define skip_list_val(c) while(!isspace(*(c)) && *(c) != '\0')\
+ (c) ++;
+#define blank_comment(c) while (!iseol(*(c)) && *(c) != '\0') \
+ *(c)++= ' ';
+
+static char *
+next_assign(c)
+ char *c;
+{
+ int nesting = 0;
+
+ while (*c != '\0') {
+ if (*c == '(')
+ nesting++;
+ else if (*c == ')')
+ nesting--;
+ else if (*c == '=' && nesting == 0)
+ return c;
+ c++;
+ }
+ return (char *) 0;
+}
+
+static void
+strip_comments(data)
+ char *data;
+{
+ char *c;
+
+ c = data;
+ while ((c = strchr(c, '#')) != NULL) {
+ if (c == data || *(c - 1) != '\\') {
+ blank_comment(c);
+ } else {
+ c++;
+ }
+ }
+}
+
+static ConfigOptionPtr
+match_param_name(name)
+ char *name;
+{
+ int pos,
+ rc,
+ low,
+ high;
+
+ low = 0;
+ high = sizeof(config_options) / sizeof(ConfigOptionRec) - 2;
+ pos = high >> 1;
+
+ while (low <= high) {
+ rc = strcmp(name, config_options[pos].parm_name);
+ if (rc == 0) {
+ return &config_options[pos];
+ } else if (rc < 0) {
+ high = pos - 1;
+ } else {
+ low = pos + 1;
+ }
+ pos = ((high + low) >> 1);
+ }
+ return 0;
+}
+
+static int
+parse_config(data)
+ char *data;
+{
+ char *c,
+ *val,
+ *next_eq,
+ *consumed,
+ *p;
+ char param_name[64];
+ Bool equals_missing;
+ ConfigOptionPtr param;
+
+ c = data;
+ skip_whitespace(c);
+
+ while (*c != '\0') {
+ equals_missing = FALSE;
+
+ /* get parm name in lower case */
+ p = c;
+ while (isalnum(*c) || *c == '-') {
+ if (isupper(*c))
+ *c = tolower(*c);
+ c++;
+ }
+ memmove( param_name, p, min(sizeof(param_name), (int) (c - p)));
+ param_name[(int) (c - p)] = '\0';
+
+ /* check for junk */
+ if (!isspace(*c) && *c != '=') {
+ ErrorF(ConfigErrors[CONFIG_ERR_SYNTAX], param_name);
+ /* eat garbage */
+ while (!isspace(*c) && *c != '=' && *c != '\0')
+ c++;
+ }
+ skip_whitespace(c);
+ if (*c != '=') {
+ ErrorF(ConfigErrors[CONFIG_ERR_NOEQUALS], param_name);
+ equals_missing = TRUE;
+ } else {
+ c++;
+ }
+
+ skip_whitespace(c);
+
+ /* find next assignment to guess where the value ends */
+ if ((next_eq = next_assign(c)) != NULL) {
+ /* back up over whitespace */
+ for (val = next_eq - 1; val >= c &&
+ (isspace(*val) || *val == ',');
+ val--);
+
+ /* back over parm name */
+ for (; val >= c && (isalnum(*val) || *val == '-'); val--);
+
+ if (val <= c) {
+ /* no value, ignore */
+ ErrorF(ConfigErrors[CONFIG_ERR_NOVALUE], param_name);
+ continue;
+ }
+ *val = '\0';
+ } else if (*c == '\0') {
+ /* no value, ignore */
+ ErrorF(ConfigErrors[CONFIG_ERR_NOVALUE], param_name);
+ continue;
+ }
+ /* match parm name */
+ if (equals_missing) {
+ equals_missing = FALSE;
+ } else if ((param = match_param_name(param_name)) == NULL) {
+ ErrorF(ConfigErrors[CONFIG_ERR_UNKNOWN], param_name);
+ } else {
+ consumed = (param->set_func) (param, c);
+
+ skip_whitespace(consumed);
+ if (*consumed != '\0') {
+ ErrorF(ConfigErrors[CONFIG_ERR_EXTRAVALUE],
+ param_name);
+ }
+ }
+
+ if (next_eq != NULL)
+ c = val + 1;
+ else /* last setting */
+ break;
+ }
+ return FSSuccess;
+}
+
+/*
+ * handles anything that should be set once the file is parsed
+ */
+void
+SetConfigValues()
+{
+ int err,
+ num;
+
+ err = SetFontCatalogue(font_catalogue, &num);
+ if (err != FSSuccess) {
+ FatalError("Element #%d (starting at 0) of font path is bad or has a bad font:\n\"%s\"\n",
+ num, font_catalogue);
+ }
+ InitErrors();
+ fsfree((char *) font_catalogue);
+ font_catalogue = NULL;
+}
+
+int
+ReadConfigFile(filename)
+ char *filename;
+{
+ FILE *fp;
+ int ret;
+ int len;
+ char *data;
+
+ data = (char *) fsalloc(CONFIG_MAX_FILESIZE);
+ if (!data) {
+ ErrorF(ConfigErrors[CONFIG_ERR_MEMORY], filename);
+ return FSBadAlloc;
+ }
+ if ((fp = fopen(filename, "r")) == NULL) {
+ fsfree(data);
+ ErrorF(ConfigErrors[CONFIG_ERR_OPEN], filename);
+ return FSBadName;
+ }
+ ret = fread(data, sizeof(char), CONFIG_MAX_FILESIZE, fp);
+ if (ret <= 0) {
+ fsfree(data);
+ (void) fclose(fp);
+ ErrorF(ConfigErrors[CONFIG_ERR_READ], filename);
+ return FSBadName;
+ }
+ len = ftell(fp);
+ len = min(len, CONFIG_MAX_FILESIZE);
+ data[len] = '\0'; /* NULL terminate the data */
+
+ (void) fclose(fp);
+
+ strip_comments(data);
+ ret = parse_config(data);
+
+ fsfree(data);
+
+ return ret;
+}
+
+struct nameVal {
+ char *name;
+ int val;
+};
+
+static char *
+config_parse_nameVal (c, ret, pval, name_val)
+ char *c;
+ int *ret;
+ int *pval;
+ struct nameVal *name_val;
+{
+ char *start,
+ t;
+ int i,
+ len;
+
+ start = c;
+ skip_val(c);
+ t = *c;
+ *c = '\0';
+ len = c - start;
+
+ for (i = 0; name_val[i].name; i++) {
+ if (!strncmpnocase(start, name_val[i].name, len)) {
+ *pval = name_val[i].val;
+ *ret = 0;
+ *c = t;
+ return c;
+ }
+ }
+ ErrorF(ConfigErrors[CONFIG_ERR_VALUE], start);
+ *c = t;
+ *ret = -1;
+ return c;
+}
+
+static char *
+config_parse_bool (c, ret, pval)
+ char *c;
+ int *ret;
+ Bool *pval;
+{
+ static struct nameVal bool_val[] = {
+ "yes", TRUE,
+ "on", TRUE,
+ "1", TRUE,
+ "true", TRUE,
+ "no", FALSE,
+ "off", FALSE,
+ "0", FALSE,
+ "false", FALSE,
+ (char *) 0, 0,
+ };
+ return config_parse_nameVal (c, ret, pval, bool_val);
+}
+
+static char *
+config_parse_int(c, ret, pval)
+ char *c;
+ int *ret;
+ int *pval;
+{
+ char *start,
+ t;
+
+ start = c;
+ while (*c != '\0' && !isspace(*c) && *c != ',') {
+ if (!isdigit(*c)) { /* error */
+ skip_val(c);
+ t = *c;
+ *c = '\0';
+ ErrorF(ConfigErrors[CONFIG_ERR_VALUE], start);
+ *ret = -1;
+ *c = t;
+ return c;
+ }
+ c++;
+ }
+ t = *c;
+ *c = '\0';
+ *ret = 0;
+ *pval = atoi(start);
+ *c = t;
+ return c;
+}
+
+
+/* config option sets */
+/* these have to know how to do the real work and tweak the proper things */
+static char *
+config_set_int(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ int ival,
+ ret;
+ extern int ListenPort;
+ extern void SetDefaultPointSize();
+
+ val = config_parse_int(val, &ret, &ival);
+ if (ret == -1)
+ return val;
+
+ /* now do individual attribute checks */
+ if (!strcmp(parm->parm_name, "port")) {
+ ListenPort = ival;
+ } else if (!strcmp(parm->parm_name, "client-limit")) {
+ AccessSetConnectionLimit(ival);
+ } else if (!strcmp(parm->parm_name, "default-point-size")) {
+ SetDefaultPointSize(ival);
+ }
+ return val;
+}
+
+static char *
+config_set_bool(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ int
+ ret;
+ Bool bval;
+ extern int ClientLimit;
+ extern Bool UseSyslog,
+ CloneSelf;
+
+ val = config_parse_bool(val, &ret, &bval);
+ if (ret == -1)
+ return val;
+
+ /* now do individual attribute checks */
+ if (!strcmp(parm->parm_name, "use-syslog")) {
+ UseSyslog = bval;
+ } else if (!strcmp(parm->parm_name, "clone-self")) {
+ CloneSelf = bval;
+ }
+ return val;
+}
+
+static char *
+config_set_file(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ extern char ErrorFile[];
+ char *start = val,
+ t;
+
+ skip_val(val);
+ t = *val;
+ *val = '\0';
+ if (!strcmp(parm->parm_name, "error-file")) {
+ memmove( ErrorFile, start, val - start + 1);
+ }
+ *val = t;
+ return val;
+}
+
+static char *
+config_set_catalogue(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ char *b;
+
+ if (!strcmp(parm->parm_name, "catalogue")) {
+ /* stash it for later */
+ fsfree((char *) font_catalogue); /* dump any previous one */
+ b = font_catalogue = (char *) fsalloc(strlen(val) + 1);
+ if (!font_catalogue)
+ FatalError("Insufficent memory for font catalogue\n");
+ while (*val) { /* remove all the gunk */
+ if (!isspace(*val)) {
+ *b++ = *val;
+ }
+ val++;
+ }
+ *b = '\0';
+ }
+ return val;
+}
+
+static char *
+config_set_list(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ char *start = val,
+ t;
+
+ skip_list_val(val);
+ t = *val;
+ *val = '\0';
+ if (!strcmp(parm->parm_name, "alternate-servers")) {
+ SetAlternateServers(start);
+ }
+ *val = t;
+ return val;
+}
+
+static char *
+config_set_glyph_caching_mode(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ char *start = val,
+ t;
+
+ skip_list_val(val);
+ t = *val;
+ *val = '\0';
+ if (!strcmp(parm->parm_name, "deferglyphs")) {
+ ParseGlyphCachingMode(start);
+ }
+ *val = t;
+ return val;
+}
+
+static char *
+config_set_resolutions(parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ char *start = val,
+ t;
+ int err;
+
+ skip_list_val(val);
+ t = *val;
+ *val = '\0';
+ if (!strcmp(parm->parm_name, "default-resolutions")) {
+ err = SetDefaultResolutions(start);
+ if (err != FSSuccess) {
+ FatalError("Bogus resolution list \"%s\"\n", start);
+ }
+ }
+ *val = t;
+ return val;
+}
+
+
+static char *
+config_parse_endian(c, ret, pval)
+ char *c;
+ int *ret;
+ int *pval;
+{
+ static struct nameVal endian_val[] = {
+ "lsb", LSBFirst,
+ "little", LSBFirst,
+ "lsbfirst", LSBFirst,
+ "msb", MSBFirst,
+ "big", MSBFirst,
+ "msbfirst", MSBFirst,
+ (char *) 0, 0,
+ };
+ return config_parse_nameVal (c, ret, pval, endian_val);
+}
+
+/* ARGSUSED */
+static char *
+config_set_snf_format (parm, val)
+ ConfigOptionPtr parm;
+ char *val;
+{
+ int bit, byte, glyph, scan;
+ int ret;
+
+ val = config_parse_endian (val, &ret, &bit);
+ if (ret == -1)
+ return val;
+ skip_whitespace (val);
+ val = config_parse_endian (val, &ret, &byte);
+ if (ret == -1)
+ return val;
+ skip_whitespace (val);
+ val = config_parse_int (val, &ret, &glyph);
+ if (ret == -1)
+ return val;
+ skip_whitespace (val);
+ val = config_parse_int (val, &ret, &scan);
+ if (ret == -1)
+ return val;
+ SnfSetFormat (bit, byte, glyph, scan);
+ return val;
+}
diff --git a/os/config.h b/os/config.h
new file mode 100644
index 0000000..ba6db45
--- /dev/null
+++ b/os/config.h
@@ -0,0 +1,69 @@
+/* $Xorg: config.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)config.h 4.1 91/05/02
+ *
+ */
+
+#ifndef _CONFIG_H_
+#define _CONFIG_H_
+
+/* max size in bytes of config file */
+#define CONFIG_MAX_FILESIZE 32767
+
+/* error codes */
+/* these should be in the same order as the error strings in config.c */
+#define CONFIG_ERR_MEMORY 1
+#define CONFIG_ERR_OPEN 2
+#define CONFIG_ERR_READ 3
+#define CONFIG_ERR_VALUE 4
+#define CONFIG_ERR_UNKNOWN 5
+#define CONFIG_ERR_NOEQUALS 6
+#define CONFIG_ERR_RANGE 7
+#define CONFIG_ERR_SYNTAX 8
+#define CONFIG_ERR_NOVALUE 9
+#define CONFIG_ERR_EXTRAVALUE 10
+#endif /* _CONFIG_H_ */
diff --git a/os/configstr.h b/os/configstr.h
new file mode 100644
index 0000000..1c8184f
--- /dev/null
+++ b/os/configstr.h
@@ -0,0 +1,59 @@
+/* $Xorg: configstr.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, DIGITAL OR MIT BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)configstr.h 4.1 91/05/02
+ *
+ */
+#ifndef _CONFIGSTR_H_
+#define _CONFIGSTR_H_
+#include "config.h"
+
+typedef struct _config_options {
+ char *parm_name;
+ char *(*set_func) ();
+} ConfigOptionRec, *ConfigOptionPtr;
+
+#endif /* _CONFIGSTR_H_ */
diff --git a/os/connection.c b/os/connection.c
new file mode 100644
index 0000000..0e3af59
--- /dev/null
+++ b/os/connection.c
@@ -0,0 +1,579 @@
+/* $Xorg: connection.c,v 1.5 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+ * handles connections
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+/*
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include <X11/Xtrans.h>
+#include "misc.h"
+#include <stdio.h>
+#include <errno.h>
+#include <sys/param.h>
+#include <sys/socket.h>
+#include <sys/uio.h>
+#include <signal.h>
+
+#include "FS.h"
+#include "FSproto.h"
+#include "clientstr.h"
+#include "X11/Xpoll.h"
+#include "osdep.h"
+#include "globals.h"
+#include "osstruct.h"
+#include "servermd.h"
+
+#ifdef X_NOT_STDC_ENV
+extern int errno;
+#endif
+
+
+int ListenPort = DEFAULT_FS_PORT; /* port to listen on */
+int lastfdesc;
+
+fd_set WellKnownConnections;
+fd_set AllSockets;
+fd_set AllClients;
+fd_set LastSelectMask;
+fd_set ClientsWithInput;
+fd_set ClientsWriteBlocked;
+fd_set OutputPending;
+extern long MaxClients;
+long OutputBufferSize = BUFSIZE;
+
+Bool NewOutputPending;
+Bool AnyClientsWriteBlocked;
+
+int ConnectionTranslation[MAXSOCKS];
+
+XtransConnInfo *ListenTransConns = NULL;
+int *ListenTransFds = NULL;
+int ListenTransCount;
+
+extern ClientPtr NextAvailableClient();
+
+#ifdef SIGNALRETURNSINT
+#define SIGVAL int
+#else
+#define SIGVAL void
+#endif
+
+extern SIGVAL AutoResetServer();
+extern SIGVAL GiveUp();
+extern SIGVAL ServerReconfig();
+extern SIGVAL ServerCacheFlush();
+extern SIGVAL CleanupChild();
+
+extern void FreeOsBuffers();
+
+static void error_conn_max();
+static void close_fd();
+
+
+static XtransConnInfo
+lookup_trans_conn (fd)
+
+int fd;
+
+{
+ if (ListenTransFds)
+ {
+ int i;
+ for (i = 0; i < ListenTransCount; i++)
+ if (ListenTransFds[i] == fd)
+ return ListenTransConns[i];
+ }
+
+ return (NULL);
+}
+
+StopListening()
+{
+ int i;
+
+ for (i = 0; i < ListenTransCount; i++)
+ {
+ FD_CLR (ListenTransFds[i], &AllSockets);
+ _FontTransCloseForCloning (ListenTransConns[i]);
+ }
+
+ free ((char *) ListenTransFds);
+ free ((char *) ListenTransConns);
+
+ ListenTransFds = NULL;
+ ListenTransConns = NULL;
+}
+
+/*
+ * creates the sockets for listening to clients
+ *
+ * only called when server first started
+ */
+void
+CreateSockets(old_listen_count, old_listen)
+
+int old_listen_count;
+OldListenRec *old_listen;
+
+{
+ int request,
+ i;
+
+ FD_ZERO(&AllSockets);
+ FD_ZERO(&AllClients);
+ FD_ZERO(&LastSelectMask);
+ FD_ZERO(&ClientsWithInput);
+ FD_ZERO(&WellKnownConnections);
+
+ for (i = 0; i < MAXSOCKS; i++)
+ ConnectionTranslation[i] = 0;
+
+#ifdef XNO_SYSCONF /* should only be on FreeBSD 1.x and NetBSD 0.x */
+#undef _SC_OPEN_MAX
+#endif
+#ifdef _SC_OPEN_MAX
+ lastfdesc = sysconf(_SC_OPEN_MAX) - 1;
+#else
+#ifdef hpux
+ lastfdesc = _NFILE - 1;
+#else
+ lastfdesc = getdtablesize() - 1;
+#endif
+#endif
+
+ if (lastfdesc > MAXSOCKS) {
+ lastfdesc = MAXSOCKS;
+ }
+
+ if (old_listen_count > 0) {
+
+ /*
+ * The font server cloned itself. Re-use previously opened
+ * transports for listening.
+ */
+
+ ListenTransConns = (XtransConnInfo *) malloc (
+ old_listen_count * sizeof (XtransConnInfo));
+
+ ListenTransFds = (int *) malloc (old_listen_count * sizeof (int));
+
+ ListenTransCount = 0;
+
+ for (i = 0; i < old_listen_count; i++)
+ {
+ char portnum[10];
+
+ if (old_listen[i].portnum != ListenPort)
+ continue; /* this should never happen */
+ else
+ sprintf (portnum, "%d", old_listen[i].portnum);
+
+ if ((ListenTransConns[ListenTransCount] =
+ _FontTransReopenCOTSServer (old_listen[i].trans_id,
+ old_listen[i].fd, portnum)) != NULL)
+ {
+ ListenTransFds[ListenTransCount] = old_listen[i].fd;
+ FD_SET (old_listen[i].fd, &WellKnownConnections);
+
+ NoticeF("Reusing existing file descriptor %d\n",
+ old_listen[i].fd);
+
+ ListenTransCount++;
+ }
+ }
+ } else {
+ char port[20];
+ int partial;
+
+ sprintf (port, "%d", ListenPort);
+
+ if ((_FontTransMakeAllCOTSServerListeners (port, &partial,
+ &ListenTransCount, &ListenTransConns) >= 0) &&
+ (ListenTransCount >= 1))
+ {
+ ListenTransFds = (int *) malloc (ListenTransCount * sizeof (int));
+
+ for (i = 0; i < ListenTransCount; i++)
+ {
+ int fd = _FontTransGetConnectionNumber (ListenTransConns[i]);
+
+ ListenTransFds[i] = fd;
+ FD_SET (fd, &WellKnownConnections);
+ }
+ }
+ }
+
+ if (! XFD_ANYSET(&WellKnownConnections))
+ FatalError("Cannot establish any listening sockets\n");
+
+
+ /* set up all the signal handlers */
+ signal(SIGPIPE, SIG_IGN);
+ signal(SIGHUP, AutoResetServer);
+ signal(SIGINT, GiveUp);
+ signal(SIGTERM, GiveUp);
+ signal(SIGUSR1, ServerReconfig);
+ signal(SIGUSR2, ServerCacheFlush);
+ signal(SIGCHLD, CleanupChild);
+
+ XFD_COPYSET (&WellKnownConnections, &AllSockets);
+}
+
+/*
+ * called when server cycles
+ */
+ResetSockets()
+{
+}
+
+void
+CloseSockets(void)
+{
+ int i;
+
+ for (i = 0; i < ListenTransCount; i++)
+ _FontTransClose (ListenTransConns[i]);
+}
+
+/*
+ * accepts new connections
+ */
+void
+MakeNewConnections()
+{
+ fd_mask readyconnections;
+ int curconn;
+ int newconn;
+ long connect_time;
+ int i;
+ ClientPtr client;
+ OsCommPtr oc;
+ fd_set tmask;
+
+ XFD_ANDSET (&tmask, &LastSelectMask, &WellKnownConnections);
+ readyconnections = tmask.fds_bits[0];
+ if (!readyconnections)
+ return;
+ connect_time = GetTimeInMillis();
+
+ /* kill off stragglers */
+ for (i = MINCLIENT; i < currentMaxClients; i++) {
+ if ((client = clients[i]) != NullClient) {
+ oc = (OsCommPtr) client->osPrivate;
+ if (oc && (oc->conn_time != 0) &&
+ (connect_time - oc->conn_time) >= TimeOutValue ||
+ client->noClientException != FSSuccess &&
+ client->clientGone != CLIENT_GONE)
+ CloseDownClient(client);
+ }
+ }
+
+ while (readyconnections) {
+ XtransConnInfo trans_conn, new_trans_conn;
+ int status;
+
+ curconn = ffs(readyconnections) - 1;
+ readyconnections &= ~(1 << curconn);
+
+ if ((trans_conn = lookup_trans_conn (curconn)) == NULL)
+ continue;
+
+ if ((new_trans_conn = _FontTransAccept (trans_conn, &status)) == NULL)
+ continue;
+
+ newconn = _FontTransGetConnectionNumber (new_trans_conn);
+
+ _FontTransSetOption(new_trans_conn, TRANS_NONBLOCKING, 1);
+
+ oc = (OsCommPtr) fsalloc(sizeof(OsCommRec));
+ if (!oc) {
+ fsfree(oc);
+ error_conn_max(new_trans_conn);
+ _FontTransClose(new_trans_conn);
+ continue;
+ }
+ FD_SET(newconn, &AllClients);
+ FD_SET(newconn, &AllSockets);
+ oc->fd = newconn;
+ oc->trans_conn = new_trans_conn;
+ oc->input = (ConnectionInputPtr) NULL;
+ oc->output = (ConnectionOutputPtr) NULL;
+ oc->conn_time = connect_time;
+
+ if ((newconn < lastfdesc) &&
+ (client = NextAvailableClient((pointer) oc))) {
+ ConnectionTranslation[newconn] = client->index;
+ } else {
+ error_conn_max(new_trans_conn);
+ close_fd(oc);
+ }
+ }
+}
+
+#define NOROOM "Maximum number of clients reached"
+
+static void
+error_conn_max(trans_conn)
+
+XtransConnInfo trans_conn;
+
+{
+ int fd = _FontTransGetConnectionNumber (trans_conn);
+ fsConnSetup conn;
+ char pad[3];
+ char byteOrder = 0;
+ int whichbyte = 1;
+ struct timeval waittime;
+ fd_set mask;
+
+
+ waittime.tv_usec = BOTIMEOUT / MILLI_PER_SECOND;
+ waittime.tv_usec = (BOTIMEOUT % MILLI_PER_SECOND) *
+ (1000000 / MILLI_PER_SECOND);
+ FD_ZERO(&mask);
+ FD_SET(fd, &mask);
+ (void) Select(fd + 1, &mask, NULL, NULL, &waittime);
+ /* try to read the byteorder of the connection */
+ (void) _FontTransRead(trans_conn, &byteOrder, 1);
+ if ((byteOrder == 'l') || (byteOrder == 'B')) {
+ int num_alts;
+ AlternateServerPtr altservers,
+ as;
+ int i,
+ altlen = 0;
+
+ num_alts = ListAlternateServers(&altservers);
+ conn.status = AuthDenied;
+ conn.major_version = FS_PROTOCOL;
+ conn.minor_version = FS_PROTOCOL_MINOR;
+ conn.num_alternates = num_alts;
+ for (i = 0, as = altservers; i < num_alts; i++, as++) {
+ altlen += (2 + as->namelen + 3) >> 2;
+ }
+ conn.alternate_len = altlen;
+ /* blow off the auth info */
+ conn.auth_index = 0;
+ conn.auth_len = 0;
+
+ if (((*(char *) &whichbyte) && (byteOrder == 'B')) ||
+ (!(*(char *) &whichbyte) && (byteOrder == 'l'))) {
+ conn.status = lswaps(conn.status);
+ conn.major_version = lswaps(conn.major_version);
+ conn.minor_version = lswaps(conn.minor_version);
+ conn.alternate_len = lswaps(conn.alternate_len);
+ }
+ (void) _FontTransWrite(trans_conn,
+ (char *) &conn, SIZEOF(fsConnSetup));
+ /* dump alternates */
+ for (i = 0, as = altservers; i < num_alts; i++, as++) {
+ (void) _FontTransWrite(trans_conn,
+ (char *) as, 2); /* XXX */
+ (void) _FontTransWrite(trans_conn,
+ (char *) as->name, as->namelen);
+ altlen = 2 + as->namelen;
+ /* pad it */
+ if (altlen & 3)
+ (void) _FontTransWrite(trans_conn,
+ (char *) pad, ((4 - (altlen & 3)) & 3));
+ }
+ }
+}
+
+static void
+close_fd(oc)
+ OsCommPtr oc;
+{
+ int fd = oc->fd;
+
+ if (oc->trans_conn)
+ _FontTransClose(oc->trans_conn);
+ FreeOsBuffers(oc);
+ FD_CLR(fd, &AllSockets);
+ FD_CLR(fd, &AllClients);
+ FD_CLR(fd, &ClientsWithInput);
+ FD_CLR(fd, &ClientsWriteBlocked);
+ if (!XFD_ANYSET(&ClientsWriteBlocked))
+ AnyClientsWriteBlocked = FALSE;
+ FD_CLR(fd, &OutputPending);
+ fsfree(oc);
+}
+
+CheckConnections()
+{
+ fd_set mask;
+ fd_set tmask;
+ int curclient;
+ int i;
+ struct timeval notime;
+ int r;
+
+ notime.tv_sec = 0;
+ notime.tv_usec = 0;
+
+ XFD_COPYSET(&AllClients, &mask);
+ for (i = 0; i < howmany(XFD_SETSIZE, NFDBITS); i++) {
+ while (mask.fds_bits[i]) {
+ curclient = ffs(mask.fds_bits[i]) - 1 + (i << 5);
+ FD_ZERO(&tmask);
+ FD_SET(curclient, &tmask);
+ r = Select(curclient + 1, &tmask, NULL, NULL, &notime);
+ if (r < 0)
+ CloseDownClient(clients[ConnectionTranslation[curclient]]);
+ FD_CLR(curclient, &mask);
+ }
+ }
+}
+
+CloseDownConnection(client)
+ ClientPtr client;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+
+ if (oc->output && oc->output->count)
+ FlushClient(client, oc, (char *) NULL, 0, 0);
+ ConnectionTranslation[oc->fd] = 0;
+ close_fd(oc);
+ client->osPrivate = (pointer) NULL;
+}
+
+
+/****************
+ * IgnoreClient
+ * Removes one client from input masks.
+ * Must have cooresponding call to AttendClient.
+ ****************/
+
+static fd_set IgnoredClientsWithInput;
+
+IgnoreClient(client)
+ ClientPtr client;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ int connection = oc->fd;
+
+ if (FD_ISSET(connection, &ClientsWithInput))
+ FD_SET(connection, &IgnoredClientsWithInput);
+ else
+ FD_CLR(connection, &IgnoredClientsWithInput);
+ FD_CLR(connection, &ClientsWithInput);
+ FD_CLR(connection, &AllSockets);
+ FD_CLR(connection, &AllClients);
+ FD_CLR(connection, &LastSelectMask);
+ isItTimeToYield = TRUE;
+}
+
+/****************
+ * AttendClient
+ * Adds one client back into the input masks.
+ ****************/
+
+AttendClient(client)
+ ClientPtr client;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ int connection = oc->fd;
+
+ FD_SET(connection, &AllClients);
+ FD_SET(connection, &AllSockets);
+ FD_SET(connection, &LastSelectMask);
+ if (FD_ISSET(connection, &IgnoredClientsWithInput))
+ FD_SET(connection, &ClientsWithInput);
+}
+
+/*
+ * figure out which clients need to be toasted
+ */
+ReapAnyOldClients()
+{
+ int i;
+ long cur_time = GetTimeInMillis();
+ ClientPtr client;
+ extern void SendKeepAliveEvent();
+
+#ifdef DEBUG
+ fprintf(stderr, "Looking for clients to reap\n");
+#endif
+
+ for (i = MINCLIENT; i < currentMaxClients; i++) {
+ client = clients[i];
+ if (client) {
+ if ((cur_time - client->last_request_time) >= ReapClientTime) {
+ if (client->clientGone == CLIENT_AGED) {
+ client->clientGone = CLIENT_TIMED_OUT;
+
+#ifdef DEBUG
+ fprintf(stderr, "reaping client #%d\n", i);
+#endif
+
+ CloseDownClient(client);
+ } else {
+ client->clientGone = CLIENT_AGED;
+ SendKeepAliveEvent(client);
+ }
+ }
+ }
+ }
+}
diff --git a/os/error.c b/os/error.c
new file mode 100644
index 0000000..e1b02e7
--- /dev/null
+++ b/os/error.c
@@ -0,0 +1,217 @@
+/* $Xorg: error.c,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+ * error message handling
+ */
+/*
+Copyright 1994, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include <stdio.h>
+#include <X11/Xos.h>
+#ifndef X_NOT_POSIX
+#ifdef _POSIX_SOURCE
+#include <limits.h>
+#else
+#define _POSIX_SOURCE
+#include <limits.h>
+#undef _POSIX_SOURCE
+#endif
+#endif
+#ifndef PATH_MAX
+#include <sys/param.h>
+#ifndef PATH_MAX
+#ifdef MAXPATHLEN
+#define PATH_MAX MAXPATHLEN
+#else
+#define PATH_MAX 1024
+#endif
+#endif
+#endif
+
+#ifdef USE_SYSLOG
+#include <syslog.h>
+#endif
+
+#include "misc.h"
+
+extern char *progname;
+
+Bool UseSyslog;
+char ErrorFile[PATH_MAX];
+
+static void
+abort_server()
+{
+ fflush(stderr);
+
+#ifdef SABER
+ saber_stop();
+#else
+ abort();
+#endif
+}
+
+void
+InitErrors()
+{
+ int i;
+
+#ifdef USE_SYSLOG
+ if (UseSyslog && !log_open) {
+ openlog("Font Server", LOG_PID, LOG_LOCAL0);
+ log_open = TRUE;
+ return;
+ }
+#endif
+
+ if (ErrorFile[0]) {
+ i = creat(ErrorFile, 0666);
+ if (i != -1) {
+ dup2(i, 2);
+ close(i);
+ } else {
+ ErrorF("Can't open error file \"%s\"\n", ErrorFile);
+ }
+ }
+}
+
+void
+CloseErrors()
+{
+#ifdef USE_SYSLOG
+ if (UseSyslog) {
+ closelog();
+ log_open = FALSE;
+ return;
+ }
+#endif
+}
+
+void
+Error(str)
+ char *str;
+{
+ /* XXX this should also go to syslog() */
+ perror(str);
+}
+
+/*
+ * used for informational messages
+ */
+/* VARARGS1 */
+void
+NoticeF(f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9) /* limit of 10 args */
+ char *f;
+ char *s0,
+ *s1,
+ *s2,
+ *s3,
+ *s4,
+ *s5,
+ *s6,
+ *s7,
+ *s8,
+ *s9;
+{
+
+#ifdef USE_SYSLOG
+ if (UseSyslog) {
+ syslog(LOG_NOTICE, f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9);
+ return;
+ }
+#endif
+
+ /* XXX should Notices just be ignored if not using syslog? */
+ fprintf(stderr, "%s notice: ", progname);
+ fprintf(stderr, f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9);
+}
+
+/*
+ * used for non-fatal error messages
+ */
+/* VARARGS1 */
+void
+ErrorF(f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9) /* limit of 10 args */
+ char *f;
+ char *s0,
+ *s1,
+ *s2,
+ *s3,
+ *s4,
+ *s5,
+ *s6,
+ *s7,
+ *s8,
+ *s9;
+{
+
+#ifdef USE_SYSLOG
+ if (UseSyslog) {
+ syslog(LOG_ERR, f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9);
+ return;
+ }
+#endif
+
+ fprintf(stderr, "%s error: ", progname);
+ fprintf(stderr, f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9);
+}
+
+/* VARARGS1 */
+void
+FatalError(f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9) /* limit of 10 args */
+ char *f;
+ char *s0,
+ *s1,
+ *s2,
+ *s3,
+ *s4,
+ *s5,
+ *s6,
+ *s7,
+ *s8,
+ *s9;
+{
+ ErrorF("Fatal font server error:\n");
+ ErrorF(f, s0, s1, s2, s3, s4, s5, s6, s7, s8, s9);
+ abort_server();
+ /* NOTREACHED */
+}
diff --git a/os/io.c b/os/io.c
new file mode 100644
index 0000000..abf4b4d
--- /dev/null
+++ b/os/io.c
@@ -0,0 +1,688 @@
+/* $Xorg: io.c,v 1.5 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+ * i/o functions
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include <X11/Xtrans.h>
+#include <stdio.h>
+#include <errno.h>
+#include <sys/types.h>
+#include <sys/param.h>
+#include <sys/uio.h>
+
+#include "FSproto.h"
+#include "clientstr.h"
+#include "X11/Xpoll.h"
+#include "osdep.h"
+#include "globals.h"
+
+#ifdef X_NOT_STDC_ENV
+extern int errno;
+#endif
+
+
+/* check for both EAGAIN and EWOULDBLOCK, because some supposedly POSIX
+ * systems are broken and return EWOULDBLOCK when they should return EAGAIN
+ */
+
+#if defined(EAGAIN) && defined(EWOULDBLOCK)
+#define ETEST(err) (err == EAGAIN || err == EWOULDBLOCK)
+#else
+
+#ifdef EAGAIN
+#define ETEST(err) (err == EAGAIN)
+#else
+#define ETEST(err) (err == EWOULDBLOCK)
+#endif
+
+#endif
+
+
+extern fd_set ClientsWithInput;
+extern fd_set ClientsWriteBlocked;
+extern fd_set OutputPending;
+
+extern long OutputBufferSize;
+
+extern int ConnectionTranslation[];
+
+extern Bool AnyClientsWriteBlocked;
+extern Bool NewOutputPending;
+
+static int timesThisConnection = 0;
+static ConnectionInputPtr FreeInputs = (ConnectionInputPtr) NULL;
+static ConnectionOutputPtr FreeOutputs = (ConnectionOutputPtr) NULL;
+static OsCommPtr AvailableInput = (OsCommPtr) NULL;
+
+static ConnectionInputPtr AllocateInputBuffer();
+static ConnectionOutputPtr AllocateOutputBuffer();
+
+
+#define MAX_TIMES_PER 10
+
+#define yield_control() \
+ { isItTimeToYield = TRUE; \
+ timesThisConnection = 0; }
+
+#define yield_control_no_input() \
+ { yield_control(); \
+ FD_CLR(fd, &ClientsWithInput); }
+
+#define yield_control_death() \
+ { timesThisConnection = 0; }
+
+#define request_length(req, client) \
+ ((int)((client)->swapped ? lswaps((req)->length) : (req)->length) << 2)
+
+int
+ReadRequest(client)
+ ClientPtr client;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ ConnectionInputPtr oci = oc->input;
+ fsReq *request;
+ int fd = oc->fd;
+ int result,
+ gotnow,
+ needed = 0;
+
+ if (AvailableInput) {
+ if (AvailableInput != oc) {
+ ConnectionInputPtr aci = AvailableInput->input;
+
+ if (aci->size > BUFWATERMARK) {
+ fsfree(aci->buffer);
+ fsfree(aci);
+ } else {
+ aci->next = FreeInputs;
+ FreeInputs = aci;
+ }
+ AvailableInput->input = (ConnectionInputPtr) NULL;
+ }
+ AvailableInput = (OsCommPtr) NULL;
+ }
+ if (!oci) {
+ if ((oci = FreeInputs ) != (ConnectionInputPtr) 0) {
+ FreeInputs = oci->next;
+ } else if (!(oci = AllocateInputBuffer())) {
+ yield_control_death();
+ return -1;
+ }
+ oc->input = oci;
+ }
+ oci->bufptr += oci->lenLastReq;
+
+ gotnow = oci->bufcnt + oci->buffer - oci->bufptr;
+
+#ifdef WORD64
+ /* need 8-byte alignment */
+ if ((oci->bufptr - oci->buffer) & 7 && gotnow > 0)
+ {
+ memmove( oci->buffer, oci->bufptr, gotnow);
+ oci->bufptr = oci->buffer;
+ oci->bufcnt = gotnow;
+ }
+#endif
+
+ request = (fsReq *) oci->bufptr;
+
+ /* not enough for a request */
+ if ((gotnow < SIZEOF(fsReq)) ||
+ (gotnow < (needed = request_length(request, client)))) {
+ oci->lenLastReq = 0;
+ if ((gotnow < SIZEOF(fsReq)) || needed == 0)
+ needed = SIZEOF(fsReq);
+ else if (needed > MAXBUFSIZE) {
+ yield_control_death();
+ return -1;
+ }
+ /* see if we need to shift up a partial request so the rest can fit */
+ if ((gotnow == 0) ||
+ ((oci->bufptr - oci->buffer + needed) > oci->size))
+ {
+ if ((gotnow > 0) && (oci->bufptr != oci->buffer))
+ memmove( oci->buffer, oci->bufptr, gotnow);
+ /* grow buffer if necessary */
+ if (needed > oci->size) {
+ char *ibuf;
+
+ ibuf = (char *) fsrealloc(oci->buffer, needed);
+ if (!ibuf) {
+ yield_control_death();
+ return -1;
+ }
+ oci->size = needed;
+ oci->buffer = ibuf;
+ }
+ oci->bufptr = oci->buffer;
+ oci->bufcnt = gotnow;
+ }
+ /* fill 'er up */
+ result = _FontTransRead(oc->trans_conn, oci->buffer + oci->bufcnt,
+ oci->size - oci->bufcnt);
+ if (result <= 0) {
+ if ((result < 0) && ETEST(errno)) {
+ yield_control_no_input();
+ return 0;
+ } else {
+ yield_control_death();
+ return -1;
+ }
+ }
+ oci->bufcnt += result;
+ gotnow += result;
+
+ /* free up space after huge requests */
+ if ((oci->size > BUFWATERMARK) &&
+ (oci->bufcnt < BUFSIZE) && (needed < BUFSIZE)) {
+ char *ibuf;
+
+ ibuf = (char *) fsrealloc(oci, BUFSIZE);
+ if (ibuf) {
+ oci->size = BUFSIZE;
+ oci->buffer = ibuf;
+ oci->bufptr = ibuf + oci->bufcnt - gotnow;
+ }
+ }
+ request = (fsReq *) oci->bufptr;
+ if ((gotnow < SIZEOF(fsReq)) ||
+ (gotnow < (needed = request_length(request, client)))) {
+ yield_control_no_input();
+ return 0;
+ }
+ }
+ if (needed == 0)
+ needed = SIZEOF(fsReq);
+ oci->lenLastReq = needed;
+ /*
+ * Check to see if client has at least one whole request in the buffer. If
+ * there is only a partial request, treat like buffer is empty so that
+ * select() will be called again and other clients can get into the queue.
+ */
+
+ if (gotnow >= needed + SIZEOF(fsReq)) {
+ request = (fsReq *) (oci->bufptr + needed);
+ if (gotnow >= needed + request_length(request, client))
+ FD_SET(fd, &ClientsWithInput);
+ else
+ yield_control_no_input();
+ } else {
+ if (gotnow == needed)
+ AvailableInput = oc;
+ yield_control_no_input();
+ }
+
+ if (++timesThisConnection >= MAX_TIMES_PER)
+ yield_control();
+
+ client->requestBuffer = (pointer) oci->bufptr;
+ return needed;
+}
+
+Bool
+InsertFakeRequest(client, data, count)
+ ClientPtr client;
+ char *data;
+ int count;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ ConnectionInputPtr oci = oc->input;
+ int fd = oc->fd;
+ fsReq *request;
+ int gotnow,
+ moveup;
+
+ if (AvailableInput) {
+ if (AvailableInput != oc) {
+ register ConnectionInputPtr aci = AvailableInput->input;
+
+ if (aci->size > BUFWATERMARK) {
+ fsfree(aci->buffer);
+ fsfree(aci);
+ } else {
+ aci->next = FreeInputs;
+ FreeInputs = aci;
+ }
+ AvailableInput->input = (ConnectionInputPtr) NULL;
+ }
+ AvailableInput = (OsCommPtr) NULL;
+ }
+ if (!oci) {
+ if ((oci = FreeInputs) != (ConnectionInputPtr) 0)
+ FreeInputs = oci->next;
+ else if (!(oci = AllocateInputBuffer()))
+ return FALSE;
+ oc->input = oci;
+
+ }
+ oci->bufptr += oci->lenLastReq;
+ oci->lenLastReq = 0;
+ gotnow = oci->bufcnt + oci->buffer - oci->bufptr;
+ if ((gotnow + count) > oci->size) {
+ char *ibuf;
+
+ ibuf = (char *) fsrealloc(oci->buffer, gotnow + count);
+ if (!ibuf)
+ return FALSE;
+ oci->size = gotnow + count;
+ oci->buffer = ibuf;
+ oci->bufptr = ibuf + oci->bufcnt - gotnow;
+ }
+ moveup = count - (oci->bufptr - oci->buffer);
+ if (moveup > 0) {
+ if (gotnow > 0)
+ memmove( oci->bufptr + moveup, oci->bufptr, gotnow);
+ oci->bufptr += moveup;
+ oci->bufcnt += moveup;
+ }
+ memmove( oci->bufptr - count, data, count);
+ oci->bufptr -= count;
+ request = (fsReq *) oci->bufptr;
+ gotnow += count;
+ if ((gotnow >= SIZEOF(fsReq)) &&
+ (gotnow >= request_length(request, client)))
+ FD_SET(fd, &ClientsWithInput);
+ else
+ yield_control_no_input();
+ return TRUE;
+}
+
+ResetCurrentRequest(client)
+ ClientPtr client;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ ConnectionInputPtr oci = oc->input;
+ int fd = oc->fd;
+ fsReq *request;
+ int gotnow;
+
+ if (AvailableInput == oc)
+ AvailableInput = (OsCommPtr) NULL;
+ oci->lenLastReq = 0;
+ request = (fsReq *) oci->bufptr;
+ gotnow = oci->bufcnt + oci->buffer - oci->bufptr;
+ if ((gotnow >= SIZEOF(fsReq)) &&
+ (gotnow >= request_length(request, client))) {
+ FD_SET(fd, &ClientsWithInput);
+ yield_control();
+ } else {
+ yield_control_no_input();
+ }
+}
+
+int
+FlushClient(client, oc, extraBuf, extraCount, padsize)
+ ClientPtr client;
+ OsCommPtr oc;
+ char *extraBuf;
+ int extraCount;
+ int padsize;
+{
+ ConnectionOutputPtr oco = oc->output;
+ int fd = oc->fd;
+ struct iovec iov[3];
+ char padBuffer[3];
+ long written;
+ long notWritten;
+ long todo;
+
+ if (!oco)
+ return 0;
+ written = 0;
+ notWritten = oco->count + extraCount + padsize;
+ todo = notWritten;
+ while (notWritten) {
+ long before = written;
+ long remain = todo;
+ int i = 0;
+ long len;
+
+ /*-
+ * You could be very general here and have "in" and "out" iovecs and
+ * write a loop without using a macro, but what the heck. This
+ * translates to:
+ *
+ * how much of this piece is new?
+ * if more new then we are trying this time, clamp
+ * if nothing new
+ * then bump down amount already written, for next piece
+ * else put new stuff in iovec, will need all of next piece
+ *
+ * Note that todo had better be at least 1 or else we'll end up
+ * writing 0 iovecs.
+ */
+
+#define InsertIOV(pointer, length) \
+ len = (length) - before; \
+ if (len > remain) \
+ len = remain; \
+ if (len <= 0) { \
+ before = (-len); \
+ } else { \
+ iov[i].iov_len = len; \
+ iov[i].iov_base = (pointer) + before; \
+ i++; \
+ remain -= len; \
+ before = 0; \
+ }
+
+ InsertIOV((char *) oco->buf, oco->count);
+ InsertIOV(extraBuf, extraCount);
+ InsertIOV(padBuffer, padsize);
+
+ errno = 0;
+ if (oc->trans_conn && (len = _FontTransWritev(oc->trans_conn, iov, i)) >= 0) {
+ written += len;
+ notWritten -= len;
+ todo = notWritten;
+ } else if (ETEST(errno)
+#ifdef SUNSYSV /* check for another brain-damaged OS bug */
+ || (errno == 0)
+#endif
+#ifdef EMSGSIZE /* check for another brain-damaged OS bug */
+ || ((errno == EMSGSIZE) && (todo == 1))
+#endif
+ )
+ {
+ FD_SET(fd, &ClientsWriteBlocked);
+ AnyClientsWriteBlocked = TRUE;
+
+ if (written < oco->count) {
+ if (written > 0) {
+ oco->count -= written;
+ memmove( (char *) oco->buf, (char *) oco->buf + written,
+ oco->count);
+ written = 0;
+ }
+ } else {
+ written -= oco->count;
+ oco->count = 0;
+ }
+
+ /* grow buffer if necessary */
+ if (notWritten > oco->size) {
+ unsigned char *obuf;
+
+ obuf = (unsigned char *) fsrealloc(oco->buf,
+ notWritten + OutputBufferSize);
+ if (!obuf) {
+ _FontTransClose(oc->trans_conn);
+ oc->trans_conn = NULL;
+ MarkClientException(client);
+ oco->count = 0;
+ return -1;
+ }
+ oco->size = notWritten + OutputBufferSize;
+ oco->buf = obuf;
+ }
+ if ((len = extraCount - written) > 0) {
+ memmove( (char *) oco->buf + oco->count,
+ extraBuf + written, len);
+ }
+ oco->count = notWritten;
+ return extraCount;
+ }
+#ifdef EMSGSIZE /* check for another brain-damaged OS bug */
+ else if (errno == EMSGSIZE)
+ {
+ todo >>= 1;
+ }
+#endif
+ else
+ {
+ if (oc->trans_conn)
+ _FontTransClose(oc->trans_conn);
+ oc->trans_conn = NULL;
+ MarkClientException(client);
+ oco->count = 0;
+ return -1;
+ }
+ }
+
+ /* everything was flushed */
+ oco->count = 0;
+
+ /* clear the write block if it was set */
+ if (AnyClientsWriteBlocked) {
+ FD_CLR(fd, &ClientsWriteBlocked);
+ if (!XFD_ANYSET(&ClientsWriteBlocked))
+ AnyClientsWriteBlocked = FALSE;
+ }
+ if (oco->size > BUFWATERMARK) {
+ fsfree(oco->buf);
+ fsfree(oco);
+ } else {
+ oco->next = FreeOutputs;
+ FreeOutputs = oco;
+ }
+ oc->output = (ConnectionOutputPtr) NULL;
+
+ return extraCount;
+}
+
+void
+FlushAllOutput()
+{
+ int index, base;
+ fd_mask mask;
+ OsCommPtr oc;
+ ClientPtr client;
+
+ if (!NewOutputPending)
+ return;
+
+ NewOutputPending = FALSE;
+
+ for (base = 0; base < howmany(XFD_SETSIZE, NFDBITS); base++) {
+ mask = OutputPending.fds_bits[base];
+ OutputPending.fds_bits[base] = 0;
+ while (mask) {
+ index = ffs(mask) - 1;
+ mask &= ~lowbit(mask);
+ if ((index = ConnectionTranslation[(base << 5) + index]) == 0)
+ continue;
+ client = clients[index];
+ if (client->clientGone == CLIENT_GONE)
+ continue;
+ oc = (OsCommPtr) client->osPrivate;
+ if (FD_ISSET(oc->fd, &ClientsWithInput)) {
+ FD_SET(oc->fd, &OutputPending);
+ NewOutputPending = TRUE;
+ } else {
+ (void) FlushClient(client, oc, (char *) NULL, 0, 0);
+ }
+ }
+ }
+}
+
+/*
+ * returns number of bytes written
+ */
+static int
+write_to_client_internal(client, count, buf, padBytes)
+ ClientPtr client;
+ int count;
+ char *buf;
+ int padBytes;
+{
+ OsCommPtr oc = (OsCommPtr) client->osPrivate;
+ ConnectionOutputPtr oco = oc->output;
+
+ if (!count)
+ return 0;
+
+ if (!oco) {
+ if ((oco = FreeOutputs) != (ConnectionOutputPtr) 0) {
+ FreeOutputs = oco->next;
+ } else if (!(oco = AllocateOutputBuffer())) {
+ _FontTransClose(oc->trans_conn);
+ oc->trans_conn = NULL;
+ MarkClientException(client);
+ return -1;
+ }
+ oc->output = oco;
+ }
+ if (oco->count + count + padBytes > oco->size) {
+ FD_CLR(oc->fd, &OutputPending);
+ NewOutputPending = FALSE;
+ return FlushClient(client, oc, buf, count, padBytes);
+ }
+ NewOutputPending = TRUE;
+ FD_SET(oc->fd, &OutputPending);
+ memmove( (char *) oco->buf + oco->count, buf, count);
+ oco->count += count + padBytes;
+
+ return count;
+}
+
+WriteToClientUnpadded(client, count, buf)
+ ClientPtr client;
+ int count;
+ char *buf;
+{
+ write_to_client_internal(client, count, buf, 0);
+}
+
+static int padlength[4] = {0, 3, 2, 1};
+
+WriteToClient(client, count, buf)
+ ClientPtr client;
+ int count;
+ char *buf;
+{
+ write_to_client_internal(client, count, buf, padlength[count & 3]);
+}
+
+static ConnectionInputPtr
+AllocateInputBuffer()
+{
+ register ConnectionInputPtr oci;
+
+ oci = (ConnectionInputPtr) fsalloc(sizeof(ConnectionInput));
+ if (!oci)
+ return (ConnectionInputPtr) NULL;
+ oci->buffer = (char *) fsalloc(BUFSIZE);
+ if (!oci->buffer) {
+ fsfree(oci);
+ return (ConnectionInputPtr) NULL;
+ }
+ oci->next = 0;
+ oci->size = BUFSIZE;
+ oci->bufptr = oci->buffer;
+ oci->bufcnt = 0;
+ oci->lenLastReq = 0;
+ return oci;
+}
+static ConnectionOutputPtr
+AllocateOutputBuffer()
+{
+ register ConnectionOutputPtr oco;
+
+ oco = (ConnectionOutputPtr) fsalloc(sizeof(ConnectionOutput));
+ if (!oco)
+ return (ConnectionOutputPtr) NULL;
+ oco->buf = (unsigned char *) fsalloc(BUFSIZE);
+ if (!oco->buf) {
+ fsfree(oco);
+ return (ConnectionOutputPtr) NULL;
+ }
+ oco->size = BUFSIZE;
+ oco->count = 0;
+ return oco;
+}
+
+
+void
+FreeOsBuffers(oc)
+ OsCommPtr oc;
+{
+ register ConnectionInputPtr oci;
+ register ConnectionOutputPtr oco;
+
+ if (AvailableInput == oc)
+ AvailableInput = (OsCommPtr) NULL;
+ if ((oci = oc->input) != (ConnectionInputPtr) 0) {
+ if (FreeInputs) {
+ fsfree(oci->buffer);
+ fsfree(oci);
+ } else {
+ FreeInputs = oci;
+ oci->next = (ConnectionInputPtr) NULL;
+ oci->bufptr = oci->buffer;
+ oci->bufcnt = 0;
+ oci->lenLastReq = 0;
+ }
+ }
+ if ((oco = oc->output) != (ConnectionOutputPtr) 0) {
+ if (FreeOutputs) {
+ fsfree(oco->buf);
+ fsfree(oco);
+ } else {
+ FreeOutputs = oco;
+ oco->next = (ConnectionOutputPtr) NULL;
+ oco->count = 0;
+ }
+ }
+}
+
+void
+ResetOsBuffers()
+{
+ register ConnectionInputPtr oci;
+ register ConnectionOutputPtr oco;
+
+ while ((oci = FreeInputs) != (ConnectionInputPtr) 0) {
+ FreeInputs = oci->next;
+ fsfree(oci->buffer);
+ fsfree(oci);
+ }
+ while ((oco = FreeOutputs) != (ConnectionOutputPtr) 0) {
+ FreeOutputs = oco->next;
+ fsfree(oco->buf);
+ fsfree(oco);
+ }
+}
diff --git a/os/osdep.h b/os/osdep.h
new file mode 100644
index 0000000..c588edb
--- /dev/null
+++ b/os/osdep.h
@@ -0,0 +1,123 @@
+/* $Xorg: osdep.h,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)osdep.h 4.1 5/2/91
+ *
+ */
+
+#ifndef _OSDEP_H_
+#define _OSDEP_H_
+
+#define BOTIMEOUT 200 /* in milliseconds */
+#define BUFSIZE 4096
+#define BUFWATERMARK 8192
+#define MAXBUFSIZE (1 << 18)
+
+#ifndef sgi /* SGI defines OPEN_MAX in a useless way */
+#ifndef X_NOT_POSIX
+#ifdef _POSIX_SOURCE
+#include <limits.h>
+#else
+#define _POSIX_SOURCE
+#include <limits.h>
+#undef _POSIX_SOURCE
+#endif
+#endif
+#endif
+
+#ifndef OPEN_MAX
+#ifdef SVR4
+#define OPEN_MAX 128
+#else
+#include <sys/param.h>
+#ifndef OPEN_MAX
+#if defined(NOFILE) && !defined(NOFILES_MAX)
+#define OPEN_MAX NOFILE
+#else
+#define OPEN_MAX NOFILES_MAX
+#endif
+#endif
+#endif
+#endif
+
+#if OPEN_MAX <= 128 /* 128 is value of MAXCLIENTS */
+#define MAXSOCKS (OPEN_MAX - 1)
+#else
+#define MAXSOCKS 128
+#endif
+
+#ifndef NULL
+#define NULL 0
+#endif
+
+typedef struct _connectionInput {
+ struct _connectionInput *next;
+ char *buffer; /* contains current client input */
+ char *bufptr; /* pointer to current start of data */
+ int bufcnt; /* count of bytes in buffer */
+ int lenLastReq;
+ int size;
+} ConnectionInput, *ConnectionInputPtr;
+
+typedef struct _connectionOutput {
+ struct _connectionOutput *next;
+ int size;
+ unsigned char *buf;
+ int count;
+} ConnectionOutput, *ConnectionOutputPtr;
+
+typedef struct _osComm {
+ int fd;
+ ConnectionInputPtr input;
+ ConnectionOutputPtr output;
+ long conn_time; /* timestamp if not established, else 0 */
+ struct _XtransConnInfo *trans_conn; /* transport connection object */
+} OsCommRec, *OsCommPtr;
+
+extern Bool CloneSelf;
+extern Bool UseSyslog;
+
+#endif /* _OSDEP_H_ */
diff --git a/os/osglue.c b/os/osglue.c
new file mode 100644
index 0000000..d0dd8cc
--- /dev/null
+++ b/os/osglue.c
@@ -0,0 +1,384 @@
+/* $Xorg: osglue.c,v 1.4 2001/02/09 02:05:44 xorgcvs Exp $ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * $NCDId: @(#)osglue.c,v 4.6 1991/07/09 14:07:30 lemke Exp $
+ *
+ */
+
+/*
+ * this is miscellaneous OS specific stuff.
+ *
+ * Catalogue support, alternate servers, and cloneing
+ */
+
+#include <X11/Xtrans.h>
+#include "osstruct.h"
+#include <stdio.h>
+#define XK_LATIN1
+#include <X11/keysymdef.h>
+
+Bool drone_server = FALSE;
+extern Bool CloneSelf;
+extern char *progname;
+extern char *configfilename;
+
+static int num_alts;
+static AlternateServerPtr alt_servers = (AlternateServerPtr) 0;
+
+extern XtransConnInfo *ListenTransConns;
+extern int *ListenTransFds;
+extern int ListenTransCount;
+
+/*
+ * XXX
+ *
+ * Catalogue support is absolutely minimal. Some guts are here, but
+ * we don't actually do anything with them so the only one exported is
+ * 'all'. Be warned that other parts of the server may incorrectly
+ * assume the catalogue list is global, and will therefore need fixing.
+ *
+ */
+
+static char *catalogue_name = "all";
+
+static Bool /* stolen from R4 Match() */
+pattern_match(pat, plen, string)
+ char *pat;
+ int plen;
+ char *string;
+{
+ register int i,
+ l;
+ int j,
+ m,
+ res;
+ register char cp,
+ cs;
+ int head,
+ tail;
+
+ head = 0;
+ tail = plen;
+
+ res = -1;
+ for (i = 0; i < head; i++) {
+ cp = pat[i];
+ if (cp == XK_question) {
+ if (!string[i])
+ return res;
+ res = 0;
+ } else if (cp != string[i])
+ return res;
+ }
+ if (head == plen)
+ return (string[head] ? res : 1);
+ l = head;
+ while (++i < tail) {
+ /* we just skipped an asterisk */
+ j = i;
+ m = l;
+ while ((cp = pat[i]) != XK_asterisk) {
+ if (!(cs = string[l]))
+ return 0;
+ if ((cp != cs) && (cp != XK_question)) {
+ m++;
+ cp = pat[j];
+ if (cp == XK_asterisk) {
+ if (!string[m])
+ return 0;
+ } else {
+ while ((cs = string[m]) != cp) {
+ if (!cs)
+ return 0;
+ m++;
+ }
+ }
+ l = m;
+ i = j;
+ }
+ l++;
+ i++;
+ }
+ }
+ m = strlen(&string[l]);
+ j = plen - tail;
+ if (m < j)
+ return 0;
+ l = (l + m) - j;
+ while (cp = pat[i]) {
+ if ((cp != string[l]) && (cp != XK_question))
+ return 0;
+ l++;
+ i++;
+ }
+ return 1;
+}
+
+int
+ListCatalogues(pattern, patlen, maxnames, catalogues, len)
+ char *pattern;
+ int patlen;
+ int maxnames;
+ char **catalogues;
+ int *len;
+{
+ int count = 0;
+ char *catlist = NULL;
+ int size = 0;
+
+ if (maxnames) {
+ if (pattern_match(pattern, patlen, catalogue_name)) {
+ size = strlen(catalogue_name);
+ catlist = (char *) fsalloc(size + 1);
+ if (!catlist)
+ goto bail;
+ *catlist = size;
+ memmove( &catlist[1], catalogue_name, size);
+ size++; /* for length */
+ count++;
+ }
+ }
+bail:
+ *len = size;
+ *catalogues = catlist;
+ return count;
+}
+
+/*
+ * check if catalogue list is valid
+ */
+
+int
+ValidateCatalogues(num, cats)
+ int *num;
+ char *cats;
+{
+ char *c = cats;
+ int i,
+ len;
+
+ for (i = 0; i < *num; i++) {
+ len = *c++;
+ if (strncmp(c, catalogue_name, len)) {
+ *num = i; /* return bad entry index */
+ return FSBadName;
+ }
+ c += len;
+ }
+ return FSSuccess;
+}
+
+int
+SetAlternateServers(list)
+ char *list;
+{
+ char *t,
+ *st;
+ AlternateServerPtr alts,
+ a;
+ int num,
+ i;
+
+ t = list;
+ num = 1;
+ while (*t) {
+ if (*t == ',')
+ num++;
+ t++;
+ }
+
+ a = alts = (AlternateServerPtr) fsalloc(sizeof(AlternateServerRec) * num);
+ if (!alts)
+ return FSBadAlloc;
+
+ st = t = list;
+ a->namelen = 0;
+ while (*t) {
+ if (*t == ',') {
+ a->name = (char *) fsalloc(a->namelen);
+ if (!a->name) {
+ /* XXX -- leak */
+ return FSBadAlloc;
+ }
+ memmove( a->name, st, a->namelen);
+ a->subset = FALSE; /* XXX */
+ a++;
+ t++;
+ st = t;
+ a->namelen = 0;
+ } else {
+ a->namelen++;
+ t++;
+ }
+ }
+ a->name = (char *) fsalloc(a->namelen);
+ if (!a->name) {
+ /* XXX -- leak */
+ return FSBadAlloc;
+ }
+ memmove( a->name, st, a->namelen);
+ a->subset = FALSE; /* XXX */
+
+ for (i = 0; i < num_alts; i++) {
+ fsfree((char *) alt_servers[i].name);
+ }
+ fsfree((char *) alt_servers);
+ num_alts = num;
+ alt_servers = alts;
+ return FSSuccess;
+}
+
+int
+ListAlternateServers(svrs)
+ AlternateServerPtr *svrs;
+{
+ *svrs = alt_servers;
+ return num_alts;
+}
+
+/*
+ * here's some fun stuff. in order to cleanly handle becoming overloaded,
+ * this allows us to clone ourselves. the parent keeps the Listen
+ * socket open, and sends it to itself. the child stops listening,
+ * and becomes a drone, hanging out till it loses all its clients.
+ */
+int
+CloneMyself()
+{
+ int child;
+ char old_listen_arg[256];
+ char *arg_ptr = old_listen_arg;
+ int i, j;
+ int lastfdesc;
+ char portnum[20];
+ extern int ListenPort;
+
+ assert(!drone_server); /* a drone shouldn't hit this */
+
+ if (!CloneSelf)
+ return -1;
+
+ old_listen_arg[0] = '\0';
+
+#ifdef XNO_SYSCONF /* should only be on FreeBSD 1.x and NetBSD 0.x */
+#undef _SC_OPEN_MAX
+#endif
+#ifdef _SC_OPEN_MAX
+ lastfdesc = sysconf(_SC_OPEN_MAX) - 1;
+#else
+#ifdef hpux
+ lastfdesc = _NFILE - 1;
+#else
+ lastfdesc = getdtablesize() - 1;
+#endif
+#endif
+
+ NoticeF("attempting clone...\n");
+ child = fork();
+ if (child == -1) {
+ /* failed to fork */
+ ErrorF("Clone failed to fork()\n");
+ return -1;
+ }
+ /*
+ * Note: they still share the same process group, and killing the parent
+ * will take out all the kids as well. this is considered a feature (at
+ * least until i'm convinced otherwise)
+ */
+ if (child == 0) {
+ StopListening();
+ NoticeF("Clone: child becoming drone\n");
+ drone_server = TRUE;
+ return 1;
+ } else { /* parent */
+ NoticeF("Clone: parent revitalizing as %s\n", progname);
+ CloseErrors();
+ /* XXX should we close stdio as well? */
+ for (i = 3; i < lastfdesc; i++)
+ {
+ for (j = 0; j < ListenTransCount; j++)
+ if (ListenTransFds[j] == i)
+ break;
+
+ if (j >= ListenTransCount)
+ (void) close(i);
+ }
+
+ for (i = 0; i < ListenTransCount; i++)
+ {
+ int trans_id, fd;
+ char *port;
+
+ if (!_FontTransGetReopenInfo (ListenTransConns[i],
+ &trans_id, &fd, &port))
+ continue;
+
+ sprintf (arg_ptr, "%d/%d/%s", trans_id, fd, port);
+ arg_ptr += strlen (arg_ptr);
+ free (port);
+
+ if (i < ListenTransCount - 1)
+ {
+ strcat (arg_ptr, ",");
+ arg_ptr++;
+ }
+ }
+
+ sprintf (portnum, "%d", ListenPort);
+ if (*old_listen_arg != '\0')
+ execlp(progname, progname,
+ "-ls", old_listen_arg,
+ "-cf", configfilename,
+ "-port", portnum,
+ NULL);
+
+ InitErrors(); /* reopen errors, since we don't want to lose
+ * this */
+ Error("Clone failed");
+ FatalError("Failed to clone self\n");
+ }
+ /* NOTREACHED */
+}
diff --git a/os/osinit.c b/os/osinit.c
new file mode 100644
index 0000000..995bf8c
--- /dev/null
+++ b/os/osinit.c
@@ -0,0 +1,62 @@
+/* $Xorg: osinit.c,v 1.4 2001/02/09 02:05:45 xorgcvs Exp $ */
+/*
+ * os init code
+ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * @(#)osinit.c 4.3 5/7/91
+ *
+ */
+
+#include "os.h"
+
+extern long LastReapTime;
+
+OsInit()
+{
+ LastReapTime = GetTimeInMillis();
+ OsInitAllocator ();
+}
diff --git a/os/utils.c b/os/utils.c
new file mode 100644
index 0000000..30c9f4f
--- /dev/null
+++ b/os/utils.c
@@ -0,0 +1,443 @@
+/* $Xorg: utils.c,v 1.4 2001/02/09 02:05:45 xorgcvs Exp $ */
+/*
+ * misc os utilities
+ */
+/*
+
+Copyright 1990, 1991, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and
+ * its documentation for any purpose is hereby granted without fee, provided
+ * that the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices, or Digital
+ * not be used in advertising or publicity pertaining to distribution
+ * of the software without specific, written prior permission.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES,
+ * OR DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
+ * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
+ * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
+ * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
+ * THIS SOFTWARE.
+ */
+
+#include <stdio.h>
+#include <X11/Xos.h>
+#include "misc.h"
+#include "globals.h"
+#include <signal.h>
+#ifdef MEMBUG
+#include <util/memleak/memleak.h>
+#endif
+
+#ifndef X_NOT_POSIX
+#ifdef _POSIX_SOURCE
+#include <limits.h>
+#else
+#define _POSIX_SOURCE
+#include <limits.h>
+#undef _POSIX_SOURCE
+#endif
+#endif /* X_NOT_POSIX */
+#ifndef PATH_MAX
+#include <sys/param.h>
+#ifndef PATH_MAX
+#ifdef MAXPATHLEN
+#define PATH_MAX MAXPATHLEN
+#else
+#define PATH_MAX 1024
+#endif
+#endif
+#endif /* PATH_MAX */
+
+#ifdef SIGNALRETURNSINT
+#define SIGVAL int
+#else
+#define SIGVAL void
+#endif
+
+#if defined(X_NOT_POSIX) && (defined(SYSV) || defined(SVR4))
+#define SIGNALS_RESET_WHEN_CAUGHT
+#endif
+
+extern char *configfilename;
+char *progname;
+Bool CloneSelf;
+extern int ListenPort;
+
+OldListenRec *OldListen = NULL;
+int OldListenCount = 0;
+
+/* ARGSUSED */
+SIGVAL
+AutoResetServer(n)
+ int n;
+{
+
+#ifdef DEBUG
+ fprintf(stderr, "got a reset signal\n");
+#endif
+
+ dispatchException |= DE_RESET;
+ isItTimeToYield = TRUE;
+
+#ifdef SIGNALS_RESET_WHEN_CAUGHT
+ signal(SIGHUP, AutoResetServer);
+#endif
+}
+
+SIGVAL
+GiveUp()
+{
+
+#ifdef DEBUG
+ fprintf(stderr, "got a TERM signal\n");
+#endif
+
+ dispatchException |= DE_TERMINATE;
+ isItTimeToYield = TRUE;
+}
+
+/* ARGSUSED */
+SIGVAL
+ServerReconfig(n)
+ int n;
+{
+
+#ifdef DEBUG
+ fprintf(stderr, "got a re-config signal\n");
+#endif
+
+ dispatchException |= DE_RECONFIG;
+ isItTimeToYield = TRUE;
+
+#ifdef SIGNALS_RESET_WHEN_CAUGHT
+ signal(SIGUSR1, ServerReconfig);
+#endif
+}
+
+/* ARGSUSED */
+SIGVAL
+ServerCacheFlush(n)
+ int n;
+{
+
+#ifdef DEBUG
+ fprintf(stderr, "got a flush signal\n");
+#endif
+
+ dispatchException |= DE_FLUSH;
+ isItTimeToYield = TRUE;
+
+#ifdef SIGNALS_RESET_WHEN_CAUGHT
+ signal(SIGUSR2, ServerCacheFlush);
+#endif
+}
+
+/* ARGSUSED */
+SIGVAL
+CleanupChild(n)
+ int n;
+{
+
+#ifdef DEBUG
+ fprintf(stderr, "got a child signal\n");
+#endif
+
+ wait(NULL);
+
+#ifdef SIGNALS_RESET_WHEN_CAUGHT
+ signal(SIGCHLD, CleanupChild);
+#endif
+}
+
+long
+GetTimeInMillis()
+{
+ struct timeval tp;
+
+ X_GETTIMEOFDAY(&tp);
+ return ((tp.tv_sec * 1000) + (tp.tv_usec / 1000));
+}
+
+static void
+usage()
+{
+ fprintf(stderr, "usage: %s [-config config_file] [-port tcp_port]\n",
+ progname);
+ exit(1);
+}
+
+OsInitAllocator ()
+{
+#ifdef MEMBUG
+ CheckMemory ();
+#endif
+}
+
+
+/*
+ * The '-ls' option is used for cloning the font server.
+ *
+ * We expect a single string of the form...
+ *
+ * transport_id/fd/portnum[,transport_id/fd/portnum]...
+ *
+ * [] denotes optional and ... denotes repitition.
+ *
+ * The string must be _exactly_ in the above format. Since this is
+ * an internal option used by the font server, it's ok to be strict
+ * about the format of the string.
+ */
+
+void
+ProcessLSoption (str)
+
+char *str;
+
+{
+ char *ptr = str;
+ char *slash, *next;
+ char number[20];
+ int count = 0;
+ int len, i;
+
+ while (*ptr != '\0')
+ {
+ if (*ptr == ',')
+ count++;
+ ptr++;
+ }
+
+ OldListenCount = count + 1;
+ OldListen = (OldListenRec *) malloc (
+ OldListenCount * sizeof (OldListenRec));
+
+ ptr = str;
+
+ for (i = 0; i < OldListenCount; i++)
+ {
+ slash = (char *) strchr (ptr, '/');
+ len = slash - ptr;
+ strncpy (number, ptr, len);
+ number[len] = '\0';
+ OldListen[i].trans_id = atoi (number);
+
+ ptr = slash + 1;
+
+ slash = (char *) strchr (ptr, '/');
+ len = slash - ptr;
+ strncpy (number, ptr, len);
+ number[len] = '\0';
+ OldListen[i].fd = atoi (number);
+
+ ptr = slash + 1;
+
+ if (i == OldListenCount - 1)
+ OldListen[i].portnum = atoi (ptr);
+ else
+ {
+ char *comma = (char *) strchr (ptr, ',');
+
+ len = comma - ptr;
+ strncpy (number, ptr, len);
+ number[len] = '\0';
+ OldListen[i].portnum = atoi (number);
+
+ ptr = comma + 1;
+ }
+ }
+}
+
+
+
+/* ARGSUSED */
+void
+ProcessCmdLine(argc, argv)
+ int argc;
+ char **argv;
+{
+ int i;
+
+ progname = argv[0];
+ for (i = 1; i < argc; i++) {
+ if (!strcmp(argv[i], "-port")) {
+ if (argv[i + 1])
+ ListenPort = atoi(argv[++i]);
+ else
+ usage();
+ } else if (!strcmp(argv[i], "-ls")) {
+ if (argv[i + 1])
+ ProcessLSoption (argv[++i]);
+ else
+ usage();
+ } else if (!strcmp(argv[i], "-cf") || !strcmp(argv[i], "-config")) {
+ if (argv[i + 1])
+ configfilename = argv[++i];
+ else
+ usage();
+ }
+#ifdef MEMBUG
+ else if ( strcmp( argv[i], "-alloc") == 0)
+ {
+ extern unsigned long MemoryFail;
+ if(++i < argc)
+ MemoryFail = atoi(argv[i]);
+ else
+ usage ();
+ }
+#endif
+ else
+ usage();
+ }
+}
+
+
+#ifndef SPECIAL_MALLOC
+
+unsigned long Must_have_memory;
+
+#ifdef MEMBUG
+#define MEM_FAIL_SCALE 100000
+unsigned long MemoryFail;
+
+#endif
+
+/* FSalloc -- FS's internal memory allocator. Why does it return unsigned
+ * int * instead of the more common char *? Well, if you read K&R you'll
+ * see they say that alloc must return a pointer "suitable for conversion"
+ * to whatever type you really want. In a full-blown generic allocator
+ * there's no way to solve the alignment problems without potentially
+ * wasting lots of space. But we have a more limited problem. We know
+ * we're only ever returning pointers to structures which will have to
+ * be long word aligned. So we are making a stronger guarantee. It might
+ * have made sense to make FSalloc return char * to conform with people's
+ * expectations of malloc, but this makes lint happier.
+ */
+
+unsigned long *
+FSalloc (amount)
+ unsigned long amount;
+{
+ register pointer ptr;
+
+ if ((long)amount < 0)
+ return (unsigned long *)NULL;
+ if (amount == 0)
+ amount++;
+ /* aligned extra on long word boundary */
+ amount = (amount + 3) & ~3;
+#ifdef MEMBUG
+ if (!Must_have_memory && MemoryFail &&
+ ((random() % MEM_FAIL_SCALE) < MemoryFail))
+ return (unsigned long *)NULL;
+ if (ptr = (pointer)fmalloc(amount))
+ return (unsigned long *) ptr;
+#else
+ if (ptr = (pointer)malloc(amount))
+ return (unsigned long *)ptr;
+#endif
+ if (Must_have_memory)
+ FatalError("Out of memory\n");
+ return (unsigned long *)NULL;
+}
+
+/*****************
+ * FScalloc
+ *****************/
+
+unsigned long *
+FScalloc (amount)
+ unsigned long amount;
+{
+ unsigned long *ret;
+
+ ret = FSalloc (amount);
+ if (ret)
+ bzero ((char *) ret, (int) amount);
+ return ret;
+}
+
+/*****************
+ * FSrealloc
+ *****************/
+
+unsigned long *
+FSrealloc (ptr, amount)
+ register pointer ptr;
+ unsigned long amount;
+{
+ char *realloc();
+
+#ifdef MEMBUG
+ if (!Must_have_memory && MemoryFail &&
+ ((random() % MEM_FAIL_SCALE) < MemoryFail))
+ return (unsigned long *)NULL;
+ ptr = (pointer)frealloc((char *) ptr, amount);
+ if (ptr)
+ return (unsigned long *) ptr;
+#else
+ if ((long)amount <= 0)
+ {
+ if (ptr && !amount)
+ free(ptr);
+ return (unsigned long *)NULL;
+ }
+ amount = (amount + 3) & ~3;
+ if (ptr)
+ ptr = (pointer)realloc((char *)ptr, amount);
+ else
+ ptr = (pointer)malloc(amount);
+ if (ptr)
+ return (unsigned long *)ptr;
+#endif
+ if (Must_have_memory)
+ FatalError("Out of memory\n");
+ return (unsigned long *)NULL;
+}
+
+/*****************
+ * FSfree
+ * calls free
+ *****************/
+
+void
+FSfree(ptr)
+ register pointer ptr;
+{
+#ifdef MEMBUG
+ if (ptr)
+ ffree((char *)ptr);
+#else
+ if (ptr)
+ free((char *)ptr);
+#endif
+}
+
+#endif /* SPECIAL_MALLOC */
diff --git a/os/waitfor.c b/os/waitfor.c
new file mode 100644
index 0000000..9b69621
--- /dev/null
+++ b/os/waitfor.c
@@ -0,0 +1,230 @@
+/* $Xorg: waitfor.c,v 1.4 2001/02/09 02:05:45 xorgcvs Exp $ */
+/*
+ * waits for input
+ */
+/*
+Copyright 1987, 1998 The Open Group
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from The Open Group.
+ * Copyright 1990, 1991 Network Computing Devices;
+ * Portions Copyright 1987 by Digital Equipment Corporation
+ *
+ * Permission to use, copy, modify, distribute, and sell this software and its
+ * documentation for any purpose is hereby granted without fee, provided that
+ * the above copyright notice appear in all copies and that both that
+ * copyright notice and this permission notice appear in supporting
+ * documentation, and that the names of Network Computing Devices,
+ * or Digital not be used in advertising or
+ * publicity pertaining to distribution of the software without specific,
+ * written prior permission. Network Computing Devices, or Digital
+ * make no representations about the
+ * suitability of this software for any purpose. It is provided "as is"
+ * without express or implied warranty.
+ *
+ * NETWORK COMPUTING DEVICES, AND DIGITAL DISCLAIM ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS, IN NO EVENT SHALL NETWORK COMPUTING DEVICES, OR DIGITAL BE
+ * LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
+ * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
+ * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
+ *
+ * $NCDId: @(#)waitfor.c,v 4.5 1991/06/24 11:59:20 lemke Exp $
+ *
+ */
+
+#include <X11/Xos.h> /* strings, time, etc */
+
+#include <stdio.h>
+#include <errno.h>
+#include <sys/param.h>
+
+#include "clientstr.h"
+#include "globals.h"
+#include "X11/Xpoll.h"
+#include "osdep.h"
+
+extern WorkQueuePtr workQueue;
+
+#ifdef X_NOT_STDC_ENV
+extern int errno;
+#endif
+
+
+extern void MakeNewConnections();
+extern void FlushAllOutput();
+
+extern fd_set WellKnownConnections;
+extern fd_set LastSelectMask;
+extern fd_set WriteMask;
+extern fd_set ClientsWithInput;
+extern fd_set ClientsWriteBlocked;
+extern fd_set AllSockets;
+extern fd_set AllClients;
+extern fd_set OutputPending;
+
+extern Bool AnyClientsWriteBlocked;
+extern Bool NewOutputPending;
+
+extern int ConnectionTranslation[];
+
+long LastReapTime;
+
+/*
+ * wait_for_something
+ *
+ * server suspends until
+ * - data from clients
+ * - new client connects
+ * - room to write data to clients
+ */
+
+WaitForSomething(pClientsReady)
+ int *pClientsReady;
+{
+ struct timeval *wt,
+ waittime;
+ fd_set clientsReadable;
+ fd_set clientsWriteable;
+ long curclient;
+ int selecterr;
+ long current_time = 0;
+ long timeout;
+ int nready,
+ i;
+
+ while (1) {
+ /* handle the work Q */
+ if (workQueue)
+ ProcessWorkQueue();
+
+ if (XFD_ANYSET(&ClientsWithInput)) {
+ XFD_COPYSET(&ClientsWithInput, &clientsReadable);
+ break;
+ }
+ /*
+ * deal with KeepAlive timeouts. if this seems to costly, SIGALRM
+ * could be used, but its more dangerous since some it could catch us
+ * at an inopportune moment (like inside un-reentrant malloc()).
+ */
+ current_time = GetTimeInMillis();
+ timeout = current_time - LastReapTime;
+ if (timeout > ReapClientTime) {
+ ReapAnyOldClients();
+ LastReapTime = current_time;
+ timeout = ReapClientTime;
+ }
+ timeout = ReapClientTime - timeout;
+ waittime.tv_sec = timeout / MILLI_PER_SECOND;
+ waittime.tv_usec = (timeout % MILLI_PER_SECOND) *
+ (1000000 / MILLI_PER_SECOND);
+ wt = &waittime;
+
+ XFD_COPYSET(&AllSockets, &LastSelectMask);
+
+ BlockHandler((pointer) &wt, (pointer) &LastSelectMask);
+ if (NewOutputPending)
+ FlushAllOutput();
+
+ if (AnyClientsWriteBlocked) {
+ XFD_COPYSET(&ClientsWriteBlocked, &clientsWriteable);
+ i = Select(MAXSOCKS, &LastSelectMask, &clientsWriteable, NULL, wt);
+ } else {
+ i = Select(MAXSOCKS, &LastSelectMask, NULL, NULL, wt);
+ }
+ selecterr = errno;
+
+ WakeupHandler(i, (pointer) &LastSelectMask);
+ if (i <= 0) { /* error or timeout */
+ FD_ZERO(&clientsWriteable);
+ if (i < 0) {
+ if (selecterr == EBADF) { /* somebody disconnected */
+ CheckConnections();
+ } else if (selecterr != EINTR) {
+ ErrorF("WaitForSomething: select(): errno %d\n", selecterr);
+ } else {
+ /*
+ * must have been broken by a signal. go deal with any
+ * exception flags
+ */
+ return 0;
+ }
+ } else { /* must have timed out */
+ ReapAnyOldClients();
+ LastReapTime = GetTimeInMillis();
+ }
+ } else {
+ if (AnyClientsWriteBlocked && XFD_ANYSET(&clientsWriteable)) {
+ NewOutputPending = TRUE;
+ XFD_ORSET(&OutputPending, &clientsWriteable, &OutputPending);
+ XFD_UNSET(&ClientsWriteBlocked, &clientsWriteable);
+ if (!XFD_ANYSET(&ClientsWriteBlocked))
+ AnyClientsWriteBlocked = FALSE;
+ }
+ XFD_ANDSET(&clientsReadable, &LastSelectMask, &AllClients);
+ if (LastSelectMask.fds_bits[0] & WellKnownConnections.fds_bits[0])
+ MakeNewConnections();
+ if (XFD_ANYSET(&clientsReadable))
+ break;
+
+ }
+ }
+ nready = 0;
+
+ if (XFD_ANYSET(&clientsReadable)) {
+ ClientPtr client;
+ int conn;
+
+ if (current_time) /* may not have been set */
+ current_time = GetTimeInMillis();
+ for (i = 0; i < howmany(XFD_SETSIZE, NFDBITS); i++) {
+ while (clientsReadable.fds_bits[i]) {
+ curclient = ffs(clientsReadable.fds_bits[i]) - 1;
+ conn = ConnectionTranslation[curclient + (i << 5)];
+ FD_CLR (curclient, &clientsReadable);
+ client = clients[conn];
+ if (!client)
+ continue;
+ pClientsReady[nready++] = conn;
+ client->last_request_time = current_time;
+ client->clientGone = CLIENT_ALIVE;
+ }
+ }
+ }
+ return nready;
+}
+
+#if 0
+/*
+ * This is not always a macro
+ */
+ANYSET(src)
+ long *src;
+{
+ int i;
+
+ for (i = 0; i < howmany(XFD_SETSIZE, NFDBITS); i++)
+ if (src[i])
+ return (1);
+ return (0);
+}
+
+#endif
diff --git a/xfs.man b/xfs.man
new file mode 100644
index 0000000..62737c5
--- /dev/null
+++ b/xfs.man
@@ -0,0 +1,205 @@
+.\" Copyright 1991, 1998 The Open Group
+.\"
+.\" Permission to use, copy, modify, distribute, and sell this software and its
+.\" documentation for any purpose is hereby granted without fee, provided that
+.\" the above copyright notice appear in all copies and that both that
+.\" copyright notice and this permission notice appear in supporting
+.\" documentation.
+.\"
+.\" The above copyright notice and this permission notice shall be included in
+.\" all copies or substantial portions of the Software.
+.\"
+.\" THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+.\" IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+.\" FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+.\" THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+.\" WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
+.\" OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+.\" SOFTWARE.
+.\"
+.\" Except as contained in this notice, the name of The Open Group shall not
+.\" be used in advertising or otherwise to promote the sale, use or other
+.\" dealing in this Software without prior written authorization from the
+.\" The Open Group.
+.\" Copyright 1991 Network Computing Devices
+.\"
+.\" Permission to use, copy, modify, distribute, and sell this software and
+.\" its documentation for any purpose is hereby granted without fee, provided
+.\" that the above copyright notice appear in all copies and that both that
+.\" copyright notice and this permission notice appear in supporting
+.\" documentation, and that the name of Network Computing Devices
+.\" not be used in advertising or
+.\" publicity pertaining to distribution of the software without specific,
+.\" written prior permission. Network Computing Devices make
+.\" no representations about the
+.\" suitability of this software for any purpose. It is provided "as is"
+.\" without express or implied warranty.
+.\" $Xorg: xfs.man,v 1.4 2001/02/09 02:05:42 xorgcvs Exp $
+.TH XFS 1 "Release 6.4" "X Version 11"
+.SH NAME
+xfs \- X font server
+.SH SYNOPSIS
+.B "xfs"
+[\-config \fIconfiguration_file\fP]
+[\-port \fItcp_port\fP]
+.SH DESCRIPTION
+.PP
+.I Xfs
+is the X Window System font server. It supplies fonts to X Window
+System display servers.
+.SH "STARTING THE SERVER"
+The server is usually run by a system administrator, and started via
+boot files like \fI/etc/rc.local\fR. Users may also wish to start
+private font servers for specific sets of fonts.
+.SH "OPTIONS"
+.TP 8
+.B \-config configuration_file
+Specifies the configuration file the font server will use.
+.TP 8
+.B \-ls listen-socket
+Specifies a file descriptor which is already set up to be used as the
+listen socket. This option is only intended to be used by the font server
+itself when automatically spawning another copy of itself to handle
+additional connections.
+.TP 8
+.B \-port tcp_port
+Specifies the TCP port number on which the server will listen for connections.
+The default port number is 7100.
+.SH "SIGNALS"
+.TP 8
+.I SIGTERM
+This causes the font server to exit cleanly.
+.TP 8
+.I SIGUSR1
+This signal is used to cause the server to re-read its configuration file.
+.TP 8
+.I SIGUSR2
+This signal is used to cause the server to flush any cached data it
+may have.
+.TP 8
+.I SIGHUP
+This signal is used to cause the server to reset, closing all active
+connections and re-reading the configuration file.
+.SH "CONFIGURATION"
+The configuration language is a list of keyword and value pairs.
+Each keyword is followed by an '=' and then the desired value.
+.PP
+Recognized keywords include:
+.sp
+.\" .IP "cache-size (cardinal)"
+.\" Size in bytes of the font server cache.
+.IP "catalogue (list of string)"
+Ordered list of font path element names.
+Use of the keyword "catalogue" is very misleading at present,
+the current implementation only supports a single catalogue ("all"),
+containing all of the specified fonts.
+.IP "alternate-servers (list of string)"
+List of alternate servers for this font server.
+.IP "client-limit (cardinal)"
+Number of clients this font server will support
+before refusing service. This is useful for tuning
+the load on each individual font server.
+.IP "clone-self (boolean)"
+Whether this font server should attempt to clone itself
+when it reachs the client-limit.
+.IP "default-point-size (cardinal)"
+The default pointsize (in decipoints) for fonts that
+don't specify. The default is 120.
+.IP "default-resolutions (list of resolutions)"
+Resolutions the server supports by default.
+This information may be used as a hint for
+pre-rendering, and substituted for scaled fonts
+which do not specify a resolution.
+A resolution is a comma-separated pair of x and y resolutions in
+pixels per inch.
+Multiple resolutions are separated by commas.
+.IP "error-file (string)"
+Filename of the error file. All warnings and errors
+will be logged here.
+.IP "port (cardinal)"
+TCP port on which the server will listen for connections.
+.IP "use-syslog (boolean)"
+Whether syslog(3) (on supported systems) is to be used
+for errors.
+.IP "deferglyphs (string)"
+Set the mode for delayed fetching and caching of glyphs. Value is
+"none", meaning deferred glyphs is disabled, "all", meaning it is
+enabled for all fonts, and "16", meaning it is enabled only for
+16-bits fonts.
+.\" .IP "trusted-clients (list of string)"
+.\" Those clients the fontserver will talk to. Others
+.\" will be refused for the initial connection. An empty
+.\" list means the server will talk to any client.
+.SH "EXAMPLE"
+.nf
+#
+# sample font server configuration file
+#
+
+# allow a max of 10 clients to connect to this font server
+client-limit = 10
+
+# when a font server reaches its limit, start up a new one
+clone-self = on
+
+# alternate font servers for clients to use
+alternate-servers = hansen:7101,hansen:7102
+
+# where to look for fonts
+# the first is a set of Speedo outlines, the second is a set of
+# misc bitmaps and the last is a set of 100dpi bitmaps
+#
+catalogue = /usr/X11R6/lib/X11/fonts/speedo,
+ /usr/X11R6/lib/X11/fonts/misc,
+ /usr/X11R6/lib/X11/fonts/100dpi/
+
+# in 12 points, decipoints
+default-point-size = 120
+
+# 100 x 100 and 75 x 75
+default-resolutions = 100,100,75,75
+use-syslog = off
+.fi
+.sp
+.SH "FONT SERVER NAMES"
+One of the following forms can be used to name a font server that
+accepts TCP connections:
+.sp
+.nf
+ tcp/\fIhostname\fP:\fIport\fP
+ tcp/\fIhostname\fP:\fIport\fP/\fIcataloguelist\fP
+.fi
+.PP
+The \fIhostname\fP specifies the name (or decimal numeric address)
+of the machine on which the font server is running. The \fIport\fP
+is the decimal TCP port on which the font server is listening for connections.
+The \fIcataloguelist\fP specifies a list of catalogue names,
+with '+' as a separator.
+.PP
+Examples: \fItcp/fs.x.org:7100\fP, \fItcp/18.30.0.212:7101/all\fP.
+.PP
+One of the following forms can be used to name a font server that
+accepts DECnet connections:
+.sp
+.nf
+ decnet/\fInodename\fP::font$\fIobjname\fP
+ decnet/\fInodename\fP::font$\fIobjname\fP/\fIcataloguelist\fP
+.fi
+.PP
+The \fInodename\fP specifies the name (or decimal numeric address)
+of the machine on which the font server is running.
+The \fIobjname\fP is a normal, case-insensitive DECnet object name.
+The \fIcataloguelist\fP specifies a list of catalogue names,
+with '+' as a separator.
+.PP
+Examples: \fIDECnet/SRVNOD::FONT$DEFAULT\fP, \fIdecnet/44.70::font$special/symbols\fP.
+.SH "SEE ALSO"
+X(1), \fIThe X Font Service Protocol\fP,
+.br
+\fIFont server implementation overview\fP
+.SH BUGS
+Multiple catalogues should be supported.
+.SH AUTHORS
+Dave Lemke, Network Computing Devices, Inc
+.br
+Keith Packard, Massachusetts Institute of Technology