diff -Nru openafs-1.6.7/debian/changelog openafs-1.6.7/debian/changelog --- openafs-1.6.7/debian/changelog 2015-03-04 17:16:16.000000000 +0100 +++ openafs-1.6.7/debian/changelog 2015-11-10 08:04:44.000000000 +0100 @@ -1,3 +1,17 @@ +openafs (1.6.7-1ubuntu2) trusty; urgency=low + + * SECURITY UPDATES: + - CVE-2015-3282: Clear nvldbentry before sending on the wire + - CVE-2015-3283: Use crypt for commands where spoofing could be a risk + - CVE-2015-3284: Clear pioctl data interchange buffer before use + - CVE-2015-3285: Use correct output buffer for FSCmd pioctl + - CVE-2015-6587: Disable regex volume name processing in ListAttributesN2 + - CVE-2015-7762: Apply OPENAFS-SA-2015-007 "Tattletale" patch + - CVE-2015-7763: Apply OPENAFS-SA-2015-007 "Tattletale" patch + - OPENAFS-SA-2015-007.patch: Rx ACK packets leak plaintext of previous packets + + -- Klas Mattsson Tue, 10 Nov 2015 08:03:52 +0100 + openafs (1.6.7-1ubuntu1) trusty; urgency=medium [Sergio Gelato ] diff -Nru openafs-1.6.7/debian/patches/CVE-2015-3282.patch openafs-1.6.7/debian/patches/CVE-2015-3282.patch --- openafs-1.6.7/debian/patches/CVE-2015-3282.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/CVE-2015-3282.patch 2015-11-10 07:59:15.000000000 +0100 @@ -0,0 +1,57 @@ +Clear nvldbentry before sending on the wire +Don't leak stack data onto the wire. Clear nvldbentry before use. +FIXES 131907 (CVE-2015-3282) + +Index: openafs-1.6.7/src/volser/vos.c +=================================================================== +--- openafs-1.6.7.orig/src/volser/vos.c 2014-04-03 16:00:15.000000000 +0200 ++++ openafs-1.6.7/src/volser/vos.c 2015-11-10 06:53:41.653367519 +0100 +@@ -5522,6 +5522,8 @@ + struct rx_connection *aconn; + int c, dc; + ++ memset(&storeEntry, 0, sizeof(struct nvldbentry)); ++ + server = GetServer(as->parms[0].items->data); + if (!server) { + fprintf(STDERR, "vos: host '%s' not found in host table\n", +Index: openafs-1.6.7/src/volser/vsprocs.c +=================================================================== +--- openafs-1.6.7.orig/src/volser/vsprocs.c 2014-04-03 16:00:15.000000000 +0200 ++++ openafs-1.6.7/src/volser/vsprocs.c 2015-11-10 06:53:51.757471208 +0100 +@@ -743,6 +743,8 @@ + aconn = (struct rx_connection *)0; + error = 0; + ++ memset(&storeEntry, 0, sizeof(struct nvldbentry)); ++ + init_volintInfo(&tstatus); + tstatus.maxquota = aquota; + +@@ -873,6 +875,8 @@ + afs_int32 vcode; + struct nvldbentry entry, storeEntry; /*the new vldb entry */ + ++ memset(&storeEntry, 0, sizeof(struct nvldbentry)); ++ + aconn = (struct rx_connection *)0; + error = 0; + +@@ -931,6 +935,8 @@ + afs_int32 avoltype = -1, vtype; + int notondisk = 0, notinvldb = 0; + ++ memset(&storeEntry, 0, sizeof(struct nvldbentry)); ++ + /* Find and read bhe VLDB entry for this volume */ + code = ubik_VL_SetLock(cstruct, 0, avolid, avoltype, VLOP_DELETE); + if (code) { +@@ -7491,6 +7497,8 @@ + { + int i, count; + ++ memset(new, 0, sizeof(struct nvldbentry)); ++ + /*copy all the fields */ + strcpy(new->name, old->name); + /* new->volumeType = old->volumeType;*/ diff -Nru openafs-1.6.7/debian/patches/CVE-2015-3283.patch openafs-1.6.7/debian/patches/CVE-2015-3283.patch --- openafs-1.6.7/debian/patches/CVE-2015-3283.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/CVE-2015-3283.patch 2015-11-10 08:00:02.000000000 +0100 @@ -0,0 +1,207 @@ +Use crypt for commands where spoofing could be a risk +bos defaults to not requiring crypt in a lot of cases, instead using clear. +As the simplest way to secure the channel is to enable crypt, do so. +FIXES 131782 (CVE-2015-3283) + +Index: openafs-1.6.7/src/bozo/bos.c +=================================================================== +--- openafs-1.6.7.orig/src/bozo/bos.c 2014-04-03 16:00:15.000000000 +0200 ++++ openafs-1.6.7/src/bozo/bos.c 2015-11-10 07:05:22.472810641 +0100 +@@ -240,7 +240,7 @@ + afs_int32 flag; + char *tp; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + tp = as->parms[1].items->data; + if (strcmp(tp, "on") == 0) + flag = 0; /* auth req.: noauthflag is false */ +@@ -305,7 +305,7 @@ + struct rx_connection *tconn; + afs_int32 flags; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + flags = 0; + if (as->parms[1].items) + flags |= BOZO_PRUNEBAK; +@@ -327,7 +327,7 @@ + struct rx_connection *tconn; + afs_int32 code; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + code = BOZO_Exec(tconn, as->parms[1].items->data); + if (code) + printf("bos: failed to execute command (%s)\n", em(code)); +@@ -393,7 +393,7 @@ + struct cmd_item *ti; + struct rx_connection *tconn; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (!as->parms[1].items) { + printf("bos: no files to uninstall\n"); + return 1; +@@ -452,7 +452,7 @@ + struct rx_call *tcall; + char destDir[256]; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (!as->parms[1].items) { + printf("bos: no files to install\n"); + return 1; +@@ -504,7 +504,7 @@ + afs_int32 code; + struct cmd_item *ti; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (as->parms[1].items == 0) { + code = BOZO_ShutdownAll(tconn); + if (code) +@@ -611,7 +611,7 @@ + struct rx_connection *tconn; + + count = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (as->parms[2].items) { + count++; + type = 1; +@@ -648,7 +648,7 @@ + afs_int32 code; + struct cmd_item *ti; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (as->parms[1].items == 0) { + code = BOZO_StartupAll(tconn); + if (code) +@@ -671,7 +671,7 @@ + afs_int32 code; + struct cmd_item *ti; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (as->parms[2].items) { + /* this is really a rebozo command */ + if (as->parms[1].items) { +@@ -715,7 +715,7 @@ + struct rx_connection *tconn; + afs_int32 code; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + code = BOZO_SetCellName(tconn, as->parms[1].items->data); + if (code) + printf("bos: failed to set cell (%s)\n", em(code)); +@@ -730,7 +730,7 @@ + struct cmd_item *ti; + char name[MAXHOSTCHARS]; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + if (as->parms[2].items) { + if (strlen(ti->data) > MAXHOSTCHARS - 3) { +@@ -756,7 +756,7 @@ + afs_int32 code; + struct cmd_item *ti; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_DeleteCellHost(tconn, ti->data); + if (code) +@@ -873,7 +873,7 @@ + afs_int32 temp; + struct cmd_item *ti; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + temp = atoi(ti->data); + code = BOZO_DeleteKey(tconn, temp); +@@ -934,7 +934,7 @@ + struct cmd_item *ti; + + failed = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_AddSUser(tconn, ti->data); + if (code) { +@@ -954,7 +954,7 @@ + int failed; + + failed = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_DeleteSUser(tconn, ti->data); + if (code) { +@@ -1053,7 +1053,7 @@ + int i; + char *type, *name, *notifier = NONOTIFIER; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (i = 0; i < 6; i++) + parms[i] = ""; + for (i = 0, ti = as->parms[3].items; (ti && i < 6); ti = ti->next, i++) { +@@ -1083,7 +1083,7 @@ + struct cmd_item *ti; + + code = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_DeleteBnode(tconn, ti->data); + if (code) { +@@ -1105,7 +1105,7 @@ + struct cmd_item *ti; + + code = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_SetStatus(tconn, ti->data, BSTAT_NORMAL); + if (code) +@@ -1123,7 +1123,7 @@ + struct cmd_item *ti; + + code = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + for (ti = as->parms[1].items; ti; ti = ti->next) { + code = BOZO_SetStatus(tconn, ti->data, BSTAT_SHUTDOWN); + if (code) +@@ -1388,7 +1388,7 @@ + int error; + + printf("Fetching log file '%s'...\n", as->parms[1].items->data); +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + tcall = rx_NewCall(tconn); + code = StartBOZO_GetLog(tcall, as->parms[1].items->data); + if (code) { +@@ -1466,7 +1466,7 @@ + memset(&mrafsParm, 0, sizeof(mrafsParm)); + + /* parm 0 is machine name, 1 is partition, 2 is volume, 3 is -all flag */ +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + + tp = &tname[0]; + +@@ -1881,7 +1881,7 @@ + struct rx_connection *tconn; + afs_int32 code, val; + +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + util_GetInt32(as->parms[1].items->data, &val); + code = BOZO_SetRestrictedMode(tconn, val); + if (code) diff -Nru openafs-1.6.7/debian/patches/CVE-2015-3284.patch openafs-1.6.7/debian/patches/CVE-2015-3284.patch --- openafs-1.6.7/debian/patches/CVE-2015-3284.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/CVE-2015-3284.patch 2015-11-10 08:00:39.000000000 +0100 @@ -0,0 +1,23 @@ +Clear pioctl data interchange buffer before use +Avoid leaking data in pioctl interchange buffers; clear the memory +when one is allocated. +FIXES 131892 (CVE-2015-3284) + + +Index: openafs-1.6.7/src/afs/afs_pioctl.c +=================================================================== +--- openafs-1.6.7.orig/src/afs/afs_pioctl.c 2015-11-10 07:30:34.396856586 +0100 ++++ openafs-1.6.7/src/afs/afs_pioctl.c 2015-11-10 07:53:07.895123866 +0100 +@@ -62,6 +62,12 @@ + if (apd->ptr == NULL) + return ENOMEM; + ++ if (size > AFS_LRALLOCSIZ) ++ memset(apd->ptr, 0, size + 1); ++ else ++ memset(apd->ptr, 0, AFS_LRALLOCSIZ); ++ ++ + apd->remaining = size; + + return 0; diff -Nru openafs-1.6.7/debian/patches/CVE-2015-3285.patch openafs-1.6.7/debian/patches/CVE-2015-3285.patch --- openafs-1.6.7/debian/patches/CVE-2015-3285.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/CVE-2015-3285.patch 2015-11-10 08:01:18.000000000 +0100 @@ -0,0 +1,19 @@ +Use correct output buffer for FSCmd pioctl +MRAFS added the FsCmd pioctl for passing messages to the fileserver; +a bug causes it to write into the wrong memory and potentially panic clients. +FIXES 131896 (CVE-2015-3285) + +Index: openafs-1.6.7/src/afs/afs_pioctl.c +=================================================================== +--- openafs-1.6.7.orig/src/afs/afs_pioctl.c 2014-04-03 16:00:15.000000000 +0200 ++++ openafs-1.6.7/src/afs/afs_pioctl.c 2015-11-10 07:30:34.396856586 +0100 +@@ -5018,8 +5018,7 @@ + if (tc) { + RX_AFS_GUNLOCK(); + code = +- RXAFS_FsCmd(rxconn, Fid, Inputs, +- (struct FsCmdOutputs *)aout); ++ RXAFS_FsCmd(rxconn, Fid, Inputs, Outputs); + RX_AFS_GLOCK(); + } else + code = -1; diff -Nru openafs-1.6.7/debian/patches/CVE-2015-6587.patch openafs-1.6.7/debian/patches/CVE-2015-6587.patch --- openafs-1.6.7/debian/patches/CVE-2015-6587.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/CVE-2015-6587.patch 2015-11-10 08:02:27.000000000 +0100 @@ -0,0 +1,125 @@ +Disable regex volume name processing in ListAttributesN2 +For the interim and until it is needed, this is most prudently simply disabled. +FIXES CVE-2015-6587 + +Index: openafs-1.6.7/src/vlserver/vlprocs.c +=================================================================== +--- openafs-1.6.7.orig/src/vlserver/vlprocs.c 2015-11-10 07:45:47.562493587 +0100 ++++ openafs-1.6.7/src/vlserver/vlprocs.c 2015-11-10 07:46:04.726670947 +0100 +@@ -1428,11 +1428,10 @@ + afs_int32 blockindex = 0, count = 0, k, match; + afs_int32 matchindex = 0; + int serverindex = -1; /* no server found */ +- int findserver = 0, findpartition = 0, findflag = 0, findname = 0; ++ int findserver = 0, findpartition = 0, findflag = 0; + int pollcount = 0; + int namematchRWBK, namematchRO, thismatch; + int matchtype = 0; +- char volumename[VL_MAXNAMELEN+2]; /* regex anchors */ + char rxstr[AFS_RXINFO_LEN]; + #ifdef HAVE_POSIX_REGEX + regex_t re; +@@ -1481,9 +1480,7 @@ + } + + /* Search each entry in the database and return all entries +- * that match the request. It checks volumename (with +- * wildcarding), entry flags, server, and partition. +- */ ++ * that match the request. It checks entry flags, server, and partition.*/ + else { + /* Get the server index for matching server address */ + if (attributes->Mask & VLLIST_SERVER) { +@@ -1496,21 +1493,9 @@ + findpartition = ((attributes->Mask & VLLIST_PARTITION) ? 1 : 0); + findflag = ((attributes->Mask & VLLIST_FLAG) ? 1 : 0); + if (name && (strcmp(name, ".*") != 0) && (strcmp(name, "") != 0)) { +- sprintf(volumename, "^%s$", name); +-#ifdef HAVE_POSIX_REGEX +- if (regcomp(&re, volumename, REG_NOSUB) != 0) { +- errorcode = VL_BADNAME; +- goto done; +- } +- need_regfree = 1; +-#else +- t = (char *)re_comp(volumename); +- if (t) { +- errorcode = VL_BADNAME; +- goto done; +- } +-#endif +- findname = 1; ++ /* regex-matching code has been disabled for security reasons. */ ++ errorcode = VL_BADNAME; ++ goto done; + } + + /* Read each entry and see if it is the one we want */ +@@ -1540,38 +1525,12 @@ + if (tentry.serverFlags[k] & VLSF_RWVOL) { + /* Does the name match the RW name */ + if (tentry.flags & VLF_RWEXISTS) { +- if (findname) { +- sprintf(volumename, "%s", tentry.name); +-#ifdef HAVE_POSIX_REGEX +- if (regexec(&re, volumename, 0, NULL, 0) == 0) { +- thismatch = VLSF_RWVOL; +- } +-#else +- if (re_exec(volumename)) { +- thismatch = VLSF_RWVOL; +- } +-#endif +- } else { +- thismatch = VLSF_RWVOL; +- } ++ thismatch = VLSF_RWVOL; + } + + /* Does the name match the BK name */ + if (!thismatch && (tentry.flags & VLF_BACKEXISTS)) { +- if (findname) { +- sprintf(volumename, "%s.backup", tentry.name); +-#ifdef HAVE_POSIX_REGEX +- if (regexec(&re, volumename, 0, NULL, 0) == 0) { +- thismatch = VLSF_BACKVOL; +- } +-#else +- if (re_exec(volumename)) { +- thismatch = VLSF_BACKVOL; +- } +-#endif +- } else { +- thismatch = VLSF_BACKVOL; +- } ++ thismatch = VLSF_BACKVOL; + } + + namematchRWBK = (thismatch ? 1 : 2); +@@ -1583,25 +1542,7 @@ + */ + else { + if (tentry.flags & VLF_ROEXISTS) { +- if (findname) { +- if (namematchRO) { +- thismatch = +- ((namematchRO == 1) ? VLSF_ROVOL : 0); +- } else { +- sprintf(volumename, "%s.readonly", +- tentry.name); +-#ifdef HAVE_POSIX_REGEX +- if (regexec(&re, volumename, 0, NULL, 0) == 0) { +- thismatch = VLSF_ROVOL; +- } +-#else +- if (re_exec(volumename)) +- thismatch = VLSF_ROVOL; +-#endif +- } +- } else { +- thismatch = VLSF_ROVOL; +- } ++ thismatch = VLSF_ROVOL; + } + namematchRO = (thismatch ? 1 : 2); + } diff -Nru openafs-1.6.7/debian/patches/OPENAFS-SA-2015-007.patch openafs-1.6.7/debian/patches/OPENAFS-SA-2015-007.patch --- openafs-1.6.7/debian/patches/OPENAFS-SA-2015-007.patch 1970-01-01 01:00:00.000000000 +0100 +++ openafs-1.6.7/debian/patches/OPENAFS-SA-2015-007.patch 2015-11-10 07:57:48.000000000 +0100 @@ -0,0 +1,70 @@ +Description: "Tattletale" - Rx ACK packets leak plaintext of previous packets +Origin: https://www.openafs.org/pages/security/OPENAFS-SA-2015-007.1.6.patch + +Index: openafs-1.6.7/src/rx/rx.c +=================================================================== +--- openafs-1.6.7.orig/src/rx/rx.c 2014-04-03 16:00:15.000000000 +0200 ++++ openafs-1.6.7/src/rx/rx.c 2015-11-10 07:56:38.629332917 +0100 +@@ -5508,6 +5508,9 @@ + int reason; Reason an acknowledge was prompted + */ + ++#define RX_ZEROS 1024 ++static char rx_zeros[RX_ZEROS]; ++ + struct rx_packet * + rxi_SendAck(struct rx_call *call, + struct rx_packet *optionalPacket, int serial, int reason, +@@ -5663,6 +5666,11 @@ + ap->nAcks = offset; + p->length = rx_AckDataSize(offset) + 4 * sizeof(afs_int32); + ++ /* Must zero the 3 octets that rx_AckDataSize skips at the end of the ++ * ACK list. ++ */ ++ rx_packetwrite(p, rx_AckDataSize(offset) - 3, 3, rx_zeros); ++ + /* these are new for AFS 3.3 */ + templ = rxi_AdjustMaxMTU(call->conn->peer->ifMTU, rx_maxReceiveSize); + templ = htonl(templ); +@@ -5681,6 +5689,8 @@ + rx_packetwrite(p, rx_AckDataSize(offset) + 3 * sizeof(afs_int32), + sizeof(afs_int32), &templ); + ++ p->length = rx_AckDataSize(offset) + 4 * sizeof(afs_int32); ++ + p->header.serviceId = call->conn->serviceId; + p->header.cid = (call->conn->cid | call->channel); + p->header.callNumber = *call->callNumber; +@@ -5694,19 +5704,20 @@ + #ifdef ADAPT_WINDOW + clock_GetTime(&call->pingRequestTime); + #endif +- if (padbytes) { +- p->length = padbytes + +- rx_AckDataSize(call->rwind) + 4 * sizeof(afs_int32); +- +- while (padbytes--) +- /* not fast but we can potentially use this if truncated +- * fragments are delivered to figure out the mtu. +- */ +- rx_packetwrite(p, rx_AckDataSize(offset) + 4 * +- sizeof(afs_int32), sizeof(afs_int32), +- &padbytes); ++ } ++ ++ while (padbytes > 0) { ++ if (padbytes > RX_ZEROS) { ++ rx_packetwrite(p, p->length, RX_ZEROS, rx_zeros); ++ p->length += RX_ZEROS; ++ padbytes -= RX_ZEROS; ++ } else { ++ rx_packetwrite(p, p->length, padbytes, rx_zeros); ++ p->length += padbytes; ++ padbytes = 0; + } + } ++ + if (call->conn->type == RX_CLIENT_CONNECTION) + p->header.flags |= RX_CLIENT_INITIATED; + diff -Nru openafs-1.6.7/debian/patches/series openafs-1.6.7/debian/patches/series --- openafs-1.6.7/debian/patches/series 2015-03-04 17:15:33.000000000 +0100 +++ openafs-1.6.7/debian/patches/series 2015-11-10 07:54:17.000000000 +0100 @@ -1 +1,7 @@ lp1423151_fix_dmks_build.patch +CVE-2015-3282.patch +CVE-2015-3283.patch +CVE-2015-3285.patch +CVE-2015-6587.patch +CVE-2015-3284.patch +OPENAFS-SA-2015-007.patch