From: Benjamin Kaduk Date: Thu, 30 Jul 2015 06:53:21 +0000 (-0400) Subject: Import upstream patches from the 1.6.13 security release X-Git-Tag: debian/1.6.9-2+deb8u6~7 X-Git-Url: https://git.michaelhowe.org/gitweb/?a=commitdiff_plain;h=3734e9c5e699b76573b3be347ab556bee7866da4;p=packages%2Fo%2Fopenafs.git Import upstream patches from the 1.6.13 security release --- diff --git a/debian/changelog b/debian/changelog index 96d69bcc2..81b4d65f4 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,3 +1,19 @@ +openafs (1.6.9-2+deb8u3) jessie-security; urgency=high + + * Apply upstream security deltas from the 1.6.13 release: + - 14a4e5bf OPENAFS-SA-2015-001: vos leaks stack data onto the wire + when creating vldb entries + - eea46650 OPENAFS-SA-2015-002: bos commands can be spoofed, including + some which alter server state + - d4cd5780 OPENAFS-SA-2015-003: pioctls leak kernel memory contents + - 06a5b0bd OPENAFS-SA-2015-004: kernel pioctl support for OSD command + parsing can trigger a panic + - 63087b33 OPENAFS-SA-2015-006: Buffer overflow in OpenAFS vlserver + * The patch for OPENAFS-SA-2015-005 is not applied, since that + vulnerability is limited to the Solaris kernel module + + -- Benjamin Kaduk Thu, 30 Jul 2015 02:47:21 -0400 + openafs (1.6.9-2+deb8u2) testing; urgency=high * The build fix in 1.6.9-2+deb8u1 was incomplete; import more patches diff --git a/debian/patches/0007-vos-Clear-nvldbentry-before-sending-on-the-wire.patch b/debian/patches/0007-vos-Clear-nvldbentry-before-sending-on-the-wire.patch new file mode 100644 index 000000000..56cb45f72 --- /dev/null +++ b/debian/patches/0007-vos-Clear-nvldbentry-before-sending-on-the-wire.patch @@ -0,0 +1,70 @@ +From: Daria Brashear +Date: Wed, 8 Jul 2015 13:51:47 -0400 +Subject: vos: Clear nvldbentry before sending on the wire + +Don't leak stack data onto the wire. Clear nvldbentry before use. + +FIXES 131907 (CVE-2015-3282) + +(cherry picked from commit 415a2aad4c1e9ab5d034b62989e4c16a37b5dcc7) + +Change-Id: Ic245a2b5ef5cc54a2a5fdfb5d458b6892c4bcf34 +(cherry picked from commit 14a4e5bf9ec05946f67123531d6c64a612919e8c) +--- + src/volser/vos.c | 2 ++ + src/volser/vsprocs.c | 8 ++++++++ + 2 files changed, 10 insertions(+) + +diff --git a/src/volser/vos.c b/src/volser/vos.c +index 0376025..77007e9 100644 +--- a/src/volser/vos.c ++++ b/src/volser/vos.c +@@ -5522,6 +5522,8 @@ ConvertRO(struct cmd_syndesc *as, void *arock) + 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", +diff --git a/src/volser/vsprocs.c b/src/volser/vsprocs.c +index 0124bfb..3142119 100644 +--- a/src/volser/vsprocs.c ++++ b/src/volser/vsprocs.c +@@ -743,6 +743,8 @@ UV_CreateVolume3(afs_uint32 aserver, afs_int32 apart, char *aname, + aconn = (struct rx_connection *)0; + error = 0; + ++ memset(&storeEntry, 0, sizeof(struct nvldbentry)); ++ + init_volintInfo(&tstatus); + tstatus.maxquota = aquota; + +@@ -873,6 +875,8 @@ UV_AddVLDBEntry(afs_uint32 aserver, afs_int32 apart, char *aname, + 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 @@ UV_DeleteVolume(afs_uint32 aserver, afs_int32 apart, afs_uint32 avolid) + 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 @@ MapNetworkToHost(struct nvldbentry *old, struct nvldbentry *new) + { + int i, count; + ++ memset(new, 0, sizeof(struct nvldbentry)); ++ + /*copy all the fields */ + strcpy(new->name, old->name); + /* new->volumeType = old->volumeType;*/ diff --git a/debian/patches/0008-bos-Use-crypt-for-commands-where-spoofing-could-be-a.patch b/debian/patches/0008-bos-Use-crypt-for-commands-where-spoofing-could-be-a.patch new file mode 100644 index 000000000..a8b8650df --- /dev/null +++ b/debian/patches/0008-bos-Use-crypt-for-commands-where-spoofing-could-be-a.patch @@ -0,0 +1,220 @@ +From: Daria Brashear +Date: Wed, 8 Jul 2015 14:11:33 -0400 +Subject: bos: 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) + +(cherry picked from commit 62926630a82b8635d1cb1514b852f9f7a2609311) + +Change-Id: Ib9e2514c4d14a77eead69677da1dabf86e526ebc +(cherry picked from commit eea466507af6320c35e3e8dc751da60a52b15a23) +--- + src/bozo/bos.c | 44 ++++++++++++++++++++++---------------------- + 1 file changed, 22 insertions(+), 22 deletions(-) + +diff --git a/src/bozo/bos.c b/src/bozo/bos.c +index 15bf343..d919c7f 100644 +--- a/src/bozo/bos.c ++++ b/src/bozo/bos.c +@@ -243,7 +243,7 @@ SetAuth(struct cmd_syndesc *as, void *arock) + 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 */ +@@ -308,7 +308,7 @@ Prune(struct cmd_syndesc *as, void *arock) + 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; +@@ -330,7 +330,7 @@ Exec(struct cmd_syndesc *as, void *arock) + 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)); +@@ -396,7 +396,7 @@ UnInstall(struct cmd_syndesc *as, void *arock) + 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; +@@ -455,7 +455,7 @@ Install(struct cmd_syndesc *as, void *arock) + 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; +@@ -507,7 +507,7 @@ Shutdown(struct cmd_syndesc *as, void *arock) + 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) +@@ -614,7 +614,7 @@ SetRestartCmd(struct cmd_syndesc *as, void *arock) + struct rx_connection *tconn; + + count = 0; +- tconn = GetConn(as, 0); ++ tconn = GetConn(as, 1); + if (as->parms[2].items) { + count++; + type = 1; +@@ -651,7 +651,7 @@ Startup(struct cmd_syndesc *as, void *arock) + 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) +@@ -674,7 +674,7 @@ Restart(struct cmd_syndesc *as, void *arock) + 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) { +@@ -718,7 +718,7 @@ SetCellName(struct cmd_syndesc *as, void *arock) + 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)); +@@ -733,7 +733,7 @@ AddHost(struct cmd_syndesc *as, void *arock) + 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) { +@@ -759,7 +759,7 @@ RemoveHost(struct cmd_syndesc *as, void *arock) + 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) +@@ -883,7 +883,7 @@ RemoveKey(struct cmd_syndesc *as, void *arock) + 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); +@@ -944,7 +944,7 @@ AddSUser(struct cmd_syndesc *as, void *arock) + 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) { +@@ -964,7 +964,7 @@ RemoveSUser(struct cmd_syndesc *as, void *arock) + 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) { +@@ -1063,7 +1063,7 @@ CreateServer(struct cmd_syndesc *as, void *arock) + 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++) { +@@ -1093,7 +1093,7 @@ DeleteServer(struct cmd_syndesc *as, void *arock) + 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) { +@@ -1115,7 +1115,7 @@ StartServer(struct cmd_syndesc *as, void *arock) + 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) +@@ -1133,7 +1133,7 @@ StopServer(struct cmd_syndesc *as, void *arock) + 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) +@@ -1398,7 +1398,7 @@ GetLogCmd(struct cmd_syndesc *as, void *arock) + 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) { +@@ -1476,7 +1476,7 @@ SalvageCmd(struct cmd_syndesc *as, void *arock) + 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]; + +@@ -1891,7 +1891,7 @@ SetRestrict(struct cmd_syndesc *as, void *arock) + 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 --git a/debian/patches/0009-afs-Clear-pioctl-data-interchange-buffer-before-use.patch b/debian/patches/0009-afs-Clear-pioctl-data-interchange-buffer-before-use.patch new file mode 100644 index 000000000..dfc7da016 --- /dev/null +++ b/debian/patches/0009-afs-Clear-pioctl-data-interchange-buffer-before-use.patch @@ -0,0 +1,33 @@ +From: Daria Brashear +Date: Wed, 8 Jul 2015 14:16:41 -0400 +Subject: afs: 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) + +(cherry picked from commit 592a99d6e693bc640e2bdfc2e7e5243fcedc8f93) + +Change-Id: I90fef404978bd7aae3eb88836bcd4f95587fd45c +(cherry picked from commit d4cd57807660a6fd3b47bc83de14a78fa8292a5f) +--- + src/afs/afs_pioctl.c | 5 +++++ + 1 file changed, 5 insertions(+) + +diff --git a/src/afs/afs_pioctl.c b/src/afs/afs_pioctl.c +index e0a744d..8a76a3d 100644 +--- a/src/afs/afs_pioctl.c ++++ b/src/afs/afs_pioctl.c +@@ -62,6 +62,11 @@ afs_pd_alloc(struct afs_pdata *apd, size_t size) + 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 --git a/debian/patches/0010-afs-Use-correct-output-buffer-for-FSCmd-pioctl.patch b/debian/patches/0010-afs-Use-correct-output-buffer-for-FSCmd-pioctl.patch new file mode 100644 index 000000000..5e86b09ab --- /dev/null +++ b/debian/patches/0010-afs-Use-correct-output-buffer-for-FSCmd-pioctl.patch @@ -0,0 +1,32 @@ +From: Andrew Deason +Date: Wed, 8 Jul 2015 14:20:13 -0400 +Subject: afs: 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) + +(cherry picked from commit ef671f497e9161ec2759446d594789495d3346f1) + +Change-Id: I1ee1fa7dff1d2594cfe9fab5ae0b7fc9245803de +(cherry picked from commit 06a5b0bd91f3ec6efad8b21831b4d1ec1a0f5003) +--- + src/afs/afs_pioctl.c | 3 +-- + 1 file changed, 1 insertion(+), 2 deletions(-) + +diff --git a/src/afs/afs_pioctl.c b/src/afs/afs_pioctl.c +index 8a76a3d..61f48a8 100644 +--- a/src/afs/afs_pioctl.c ++++ b/src/afs/afs_pioctl.c +@@ -5023,8 +5023,7 @@ DECL_PIOCTL(PFsCmd) + 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 --git a/debian/patches/0011-vlserver-Disable-regex-volume-name-processing-in-Lis.patch b/debian/patches/0011-vlserver-Disable-regex-volume-name-processing-in-Lis.patch new file mode 100644 index 000000000..744b04aa3 --- /dev/null +++ b/debian/patches/0011-vlserver-Disable-regex-volume-name-processing-in-Lis.patch @@ -0,0 +1,137 @@ +From: Andrew Deason +Date: Wed, 8 Jul 2015 14:37:16 -0400 +Subject: vlserver: Disable regex volume name processing in ListAttributesN2 + +For the interim and until it is needed, this is most prudently +simply disabled. + +FIXES 131890 + +(cherry picked from commit 22481ab3705522ac1988b7de038c4dbc1e5009a9) + +Change-Id: I612ea4a1c85fdb895acc6a71801e659869e849c2 +(cherry picked from commit 63087b338e3d0fbbb26ee183a039052bf07aaaec) +--- + src/vlserver/vlprocs.c | 74 ++++++-------------------------------------------- + 1 file changed, 8 insertions(+), 66 deletions(-) + +diff --git a/src/vlserver/vlprocs.c b/src/vlserver/vlprocs.c +index 169bbdd..7f666db 100644 +--- a/src/vlserver/vlprocs.c ++++ b/src/vlserver/vlprocs.c +@@ -1428,11 +1428,10 @@ SVL_ListAttributesN2(struct rx_call *rxcall, + 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,8 +1480,7 @@ SVL_ListAttributesN2(struct rx_call *rxcall, + } + + /* 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 */ +@@ -1496,21 +1494,9 @@ SVL_ListAttributesN2(struct rx_call *rxcall, + 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 +1526,12 @@ SVL_ListAttributesN2(struct rx_call *rxcall, + 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 +1543,7 @@ SVL_ListAttributesN2(struct rx_call *rxcall, + */ + 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 --git a/debian/patches/series b/debian/patches/series index 31d16251c..a908daebd 100644 --- a/debian/patches/series +++ b/debian/patches/series @@ -4,3 +4,8 @@ 0004-Linux-d_alias-becomes-d_u.d_alias.patch 0005-libafs-api-to-create-and-free-vrequests.patch 0006-Linux-Move-code-to-reset-the-root-to-afs-LINUX.patch +0007-vos-Clear-nvldbentry-before-sending-on-the-wire.patch +0008-bos-Use-crypt-for-commands-where-spoofing-could-be-a.patch +0009-afs-Clear-pioctl-data-interchange-buffer-before-use.patch +0010-afs-Use-correct-output-buffer-for-FSCmd-pioctl.patch +0011-vlserver-Disable-regex-volume-name-processing-in-Lis.patch