summaryrefslogtreecommitdiff
path: root/x11
diff options
context:
space:
mode:
authorJean-Marc Zucconi <jmz@FreeBSD.org>2001-08-23 23:43:09 +0000
committerJean-Marc Zucconi <jmz@FreeBSD.org>2001-08-23 23:43:09 +0000
commite6e8cc0c83320a14e7a74373e3079b80c368d488 (patch)
treef328a022e7e5971592ead0a964b4d01e172e2d0b /x11
parentFix a race condition in mouse device. (diff)
Fix a local DoS against xfs.
Submitted by: kris Obtained from: XFree86 CVS repository
Notes
Notes: svn path=/head/; revision=46756
Diffstat (limited to 'x11')
-rw-r--r--x11/XFree86-4/Makefile2
-rw-r--r--x11/XFree86-4/files/patch-xfs292
2 files changed, 293 insertions, 1 deletions
diff --git a/x11/XFree86-4/Makefile b/x11/XFree86-4/Makefile
index 2dcafe7b144a..d68fbfd83677 100644
--- a/x11/XFree86-4/Makefile
+++ b/x11/XFree86-4/Makefile
@@ -7,7 +7,7 @@
PORTNAME= XFree86
PORTVERSION= 4.1.0
-PORTREVISION= 5
+PORTREVISION= 6
CATEGORIES= x11
MASTER_SITES= ${MASTER_SITE_XFREE}
MASTER_SITE_SUBDIR= 4.1.0
diff --git a/x11/XFree86-4/files/patch-xfs b/x11/XFree86-4/files/patch-xfs
new file mode 100644
index 000000000000..8ac159dd7603
--- /dev/null
+++ b/x11/XFree86-4/files/patch-xfs
@@ -0,0 +1,292 @@
+--- programs/xfs/difs/dispatch.c 2001/04/01 14:00:20 3.9
++++ programs/xfs/difs/dispatch.c 2001/06/21 01:15:44
+@@ -141,8 +141,10 @@
+ op = MAJOROP;
+ if (op >= NUM_PROC_VECTORS)
+ result = ProcBadRequest (client);
+- else
++ else if (*client->requestVector[op] != NULL)
+ result = (*client->requestVector[op]) (client);
++ else
++ result = FSBadRequest;
+ }
+ if (result != FSSuccess) {
+ if (client->noClientException != FSSuccess)
+@@ -202,8 +204,12 @@
+ return (client->noClientException = -2);
+ if (((*(char *) &whichbyte) && (prefix->byteOrder == 'B')) ||
+ (!(*(char *) &whichbyte) && (prefix->byteOrder == 'l'))) {
++ int status;
++
+ client->swapped = TRUE;
+- SwapConnClientPrefix(prefix);
++ status = SwapConnClientPrefix(client, prefix);
++ if (status != FSSuccess)
++ return (status);
+ }
+ client->major_version = prefix->major_version;
+ client->minor_version = prefix->minor_version;
+@@ -257,7 +263,16 @@
+ client_auth[i].name = (char *) ad;
+ ad += client_auth[i].namelen;
+ client_auth[i].data = (char *) ad;
++
+ ad += client_auth[i].datalen;
++
++ if (ad - (char *)auth_data > stuff->length -
++ (i < (int)prefix->num_auths) ? 8 : 0) {
++ int lengthword = stuff->length;
++
++ SendErrToClient(client, FSBadLength, (pointer)&lengthword);
++ return (FSBadLength);
++ }
+ }
+ num_alts = ListAlternateServers(&altservers);
+ for (i = 0, altlen = 0; i < num_alts; i++) {
+@@ -585,6 +600,13 @@
+ ad += acp[i].namelen;
+ acp[i].data = (char *) ad;
+ ad += acp[i].datalen;
++ if (ad - (char *)stuff + SIZEOF(fsCreateACReq) > stuff->length -
++ (i < (int)stuff->num_auths ? 8 : 0)) {
++ int lengthword = stuff->length;
++
++ SendErrToClient(client, FSBadLength, (pointer)&lengthword);
++ return (FSBadLength);
++ }
+ }
+
+ /* XXX needs work for AuthContinue */
+@@ -702,6 +724,13 @@
+ REQUEST(fsSetResolutionReq);
+ REQUEST_AT_LEAST_SIZE(fsSetResolutionReq);
+
++ if (stuff->length - SIZEOF(fsResolution) != stuff->num_resolutions *
++ sizeof(fsResolution)) {
++ int lengthword = stuff->length;
++
++ SendErrToClient(client, FSBadAlloc, &lengthword);
++ return FSBadLength;
++ }
+ new_res = (fsResolution *)
+ fsalloc(SIZEOF(fsResolution) * stuff->num_resolutions);
+ if (!new_res) {
+@@ -725,6 +754,13 @@
+ REQUEST(fsReq);
+ REQUEST_AT_LEAST_SIZE(fsReq);
+
++ if (stuff->length - SIZEOF(fsResolution) != client->num_resolutions *
++ sizeof(fsResolution)) {
++ int lengthword = stuff->length;
++
++ SendErrToClient(client, FSBadAlloc, &lengthword);
++ return FSBadLength;
++ }
+ reply.type = FS_Reply;
+ reply.num_resolutions = client->num_resolutions;
+ reply.sequenceNumber = client->sequence;
+--- programs/xfs/difs/fonts.c 2001/04/01 14:00:20 3.9
++++ programs/xfs/difs/fonts.c 2001/06/21 01:15:45
+@@ -709,8 +709,12 @@
+ }
+ }
+ if (validpaths < npaths) {
+- fplist = (FontPathElementPtr *)
++ FontPathElementPtr *ftmp = (FontPathElementPtr *)
+ fsrealloc(fplist, sizeof(FontPathElementPtr) * validpaths);
++
++ if (!ftmp)
++ goto bail;
++ fplist = ftmp;
+ npaths = validpaths;
+ }
+ if (validpaths == 0) {
+--- programs/xfs/difs/main.c 2001/04/01 14:00:20 3.7
++++ programs/xfs/difs/main.c 2001/06/21 01:15:45
+@@ -171,11 +171,14 @@
+ exit(0);
+ }
+
+-void
++int
+ NotImplemented(void)
+ {
+ NoopDDA(); /* dummy to get difsutils.o to link */
+- FatalError("Not implemented\n");
++ /* Getting here can become the next xfs exploit... so don't exit */
++ ErrorF("Not implemented\n");
++
++ return (FSBadImplementation);
+ }
+
+ static Bool
+--- programs/xfs/difs/swapreq.c 2001/01/17 23:45:29 1.5
++++ programs/xfs/difs/swapreq.c 2001/06/21 01:15:46
+@@ -135,8 +135,8 @@
+ return ((*ProcVector[stuff->reqType]) (client));
+ }
+
+-static void
+-swap_auth(pointer data, int num)
++static int
++swap_auth(ClientPtr client, pointer data, int num, int length)
+ {
+ unsigned char *p;
+ unsigned char t;
+@@ -158,16 +158,29 @@
+ p += 2;
+ p += (namelen + 3) & ~3;
+ p += (datalen + 3) & ~3;
++ if (p - (unsigned char *)data > length - (i < num ? 8 : 0)) {
++ int lengthword = length;
++
++ SendErrToClient(client, FSBadLength, (pointer)&lengthword);
++ return (FSBadLength);
++ }
+ }
++
++ return (FSSuccess);
+ }
+
+ int
+ SProcCreateAC(ClientPtr client)
+ {
++ int status;
++
+ REQUEST(fsCreateACReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->acid = lswapl(stuff->acid);
+- swap_auth((pointer) &stuff[1], stuff->num_auths);
++ status = swap_auth(client, (pointer) &stuff[1],
++ stuff->num_auths, stuff->length);
++ if (status != FSSuccess)
++ return (status);
+ return ((*ProcVector[stuff->reqType]) (client));
+ }
+
+@@ -177,6 +190,8 @@
+ REQUEST(fsSetResolutionReq);
+ stuff->length = lswaps(stuff->length);
+ stuff->num_resolutions = lswaps(stuff->num_resolutions);
++ if ((int)stuff->length - (&stuff[1] - &stuff[0]) < stuff->num_resolutions)
++ return (FSBadLength);
+ SwapShorts((short *) &stuff[1], stuff->num_resolutions);
+
+ return ((*ProcVector[stuff->reqType]) (client));
+@@ -255,11 +270,14 @@
+ return ((*ProcVector[stuff->reqType]) (client));
+ }
+
+-void
+-SwapConnClientPrefix(fsConnClientPrefix *pCCP)
++int
++SwapConnClientPrefix(ClientPtr client, fsConnClientPrefix *pCCP)
+ {
++ REQUEST(fsFakeReq);
++
+ 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);
++ return (swap_auth(client, (pointer) &pCCP[1],
++ pCCP->num_auths, stuff->length));
+ }
+--- programs/xfs/include/difs.h 1999/08/21 13:48:50 1.2
++++ programs/xfs/include/difs.h 2001/06/21 01:15:46
+@@ -83,6 +83,6 @@
+ #endif
+
+ /* difs/main.c */
+-extern void NotImplemented(void);
++extern int NotImplemented(void);
+
+ #endif
+--- programs/xfs/include/osstruct.h 2001/01/16 22:52:04 1.1.1.4
++++ programs/xfs/include/osstruct.h 2001/06/21 01:15:46
+@@ -49,16 +49,16 @@
+ #include "os.h"
+
+ typedef struct _alt_server {
+- char subset;
+- short namelen;
+- char *name;
++ char subset;
++ unsigned short namelen;
++ char *name;
+ } AlternateServerRec;
+
+ typedef struct _auth {
+- short namelen;
+- short datalen;
+- char *name;
+- char *data;
++ unsigned short namelen;
++ unsigned short datalen;
++ char *name;
++ char *data;
+ } AuthRec;
+
+ #endif /* _OSSTRUCT_H_ */
+--- programs/xfs/include/swapreq.h 1998/10/25 07:12:32 1.1
++++ programs/xfs/include/swapreq.h 2001/06/21 01:15:47
+@@ -48,7 +48,7 @@
+ extern int SProcResourceRequest(ClientPtr client);
+ extern int SProcSetResolution(ClientPtr client);
+ extern int SProcSimpleRequest(ClientPtr client);
+-extern void SwapConnClientPrefix(fsConnClientPrefix *pCCP);
++extern int SwapConnClientPrefix(ClientPtr client, fsConnClientPrefix *pCCP);
+ extern void SwapLongs(long *list, unsigned long count);
+ extern void SwapShorts(short *list, unsigned long count);
+
+cvs server: Diffing xc/programs/xfs/os
+--- programs/xfs/os/io.c 2001/01/17 23:45:32 3.12
++++ programs/xfs/os/io.c 2001/06/21 01:15:47
+@@ -127,14 +127,24 @@
+ int
+ ReadRequest(ClientPtr client)
+ {
+- OsCommPtr oc = (OsCommPtr) client->osPrivate;
+- ConnectionInputPtr oci = oc->input;
++ OsCommPtr oc;
++ ConnectionInputPtr oci;
+ fsReq *request;
+- int fd = oc->fd;
+- int result,
++ int fd,
++ result,
+ gotnow,
+ needed = 0;
+
++ if (client == NULL)
++ return -1;
++ oc = (OsCommPtr) client->osPrivate;
++ if (oc == NULL)
++ return -1;
++ oci = oc->input;
++ fd = oc->fd;
++ if (oci == NULL || fd < 0)
++ return -1;
++
+ if (AvailableInput) {
+ if (AvailableInput != oc) {
+ ConnectionInputPtr aci = AvailableInput->input;
+@@ -207,6 +217,8 @@
+ oci->bufcnt = gotnow;
+ }
+ /* fill 'er up */
++ if (oc->trans_conn == NULL)
++ return -1;
+ result = _FontTransRead(oc->trans_conn, oci->buffer + oci->bufcnt,
+ oci->size - oci->bufcnt);
+ if (result <= 0) {
+@@ -230,7 +242,7 @@
+ (oci->bufcnt < BUFSIZE) && (needed < BUFSIZE)) {
+ char *ibuf;
+
+- ibuf = (char *) fsrealloc(oci, BUFSIZE);
++ ibuf = (char *) fsrealloc(oci->buffer, BUFSIZE);
+ if (ibuf) {
+ oci->size = BUFSIZE;
+ oci->buffer = ibuf;
+
+