From: Benjamin Kaduk Date: Fri, 20 Feb 2015 17:05:42 +0000 (-0500) Subject: Import upstream patches to fix grave jessie bugs X-Git-Tag: debian/1.6.9-2+deb8u1~1 X-Git-Url: https://git.michaelhowe.org/gitweb/?a=commitdiff_plain;h=eaf56d9770853b2626c9f5453b45a9d1fef8f952;p=packages%2Fo%2Fopenafs.git Import upstream patches to fix grave jessie bugs The kernel security update for linux-images-3.16.0-4-$arch included a KPI change, causing the openafs modules to FTBFS. A data corruption bug was discovered when writing to large mmaped files. --- diff --git a/debian/changelog b/debian/changelog index ff8ba71ec..6cc5bfe81 100644 --- a/debian/changelog +++ b/debian/changelog @@ -1,3 +1,11 @@ +openafs (1.6.9-2+deb8u1) UNRELEASED; urgency=high + + * Import patches from upstream: + - Avoid using stale data version after writepage. (Closes: #778851.) + - Fix build when d_alias is in the d_u union. (Closes: #778196.) + + -- Benjamin Kaduk Fri, 20 Feb 2015 12:00:01 -0500 + openafs (1.6.9-2) unstable; urgency=medium [ Russ Allbery ] diff --git a/debian/patches/0003-Unix-CM-Avoid-using-stale-DV-in-afs_StoreAllSegments.patch b/debian/patches/0003-Unix-CM-Avoid-using-stale-DV-in-afs_StoreAllSegments.patch new file mode 100644 index 000000000..5f4c27c5d --- /dev/null +++ b/debian/patches/0003-Unix-CM-Avoid-using-stale-DV-in-afs_StoreAllSegments.patch @@ -0,0 +1,74 @@ +From: Marc Dionne +Date: Fri, 19 Dec 2014 10:11:53 -0500 +Subject: Unix CM: Avoid using stale DV in afs_StoreAllSegments + +It was reported in RT 131976 that on Linux some file +corruption was observed when doing mmap writes to +a file substantially larger than the cache size. + +osi_VM_StoreAllSegments drops locks and asks the OS to flush +any dirty pages in the file 's mapping. This will trigger +calls into our writepage op, and if the number of dirty +cache chunks is too high (as will happen for a file larger +than the cache size), afs_DoPartialWrite will recursively +call afs_StoreAllSegments and some chunks will be written +back to the server. After potentially doing this several +times, control will return to the original afs_StoreAllSegments. + +At that point the data version that was stored before +osi_VM_StoreAllSegments is no longer correct, leading to +possible data corruption. + +Triggering this bug requires writing a file larger than the +cache so that partial stores are done, and writing enough +data to exceed the system's maximum dirty ratio and cause +it to initiate writeback. + +To fix, just wait until after osi_VM_StoreAllSegments to +look at and store the data version + +FIXES 131976 + +Reviewed-on: http://gerrit.openafs.org/11644 +Tested-by: BuildBot +Reviewed-by: Jeffrey Altman +(cherry picked from commit b22c586bcdf785c489009ab96cbb572181cb9b09) + +Change-Id: I32a2f6f32d432fe4a2e21ebd4bb278a9d7e5499f +Reviewed-on: http://gerrit.openafs.org/11656 +Tested-by: BuildBot +Reviewed-by: Benjamin Kaduk +Reviewed-by: Stephan Wiesand +(cherry picked from commit 013e8db33fbec8b5db4ac5a1ec94a7f5b2afbc45) +--- + src/afs/afs_segments.c | 10 ++++++++-- + 1 file changed, 8 insertions(+), 2 deletions(-) + +diff --git a/src/afs/afs_segments.c b/src/afs/afs_segments.c +index f407b49..1ea3311 100644 +--- a/src/afs/afs_segments.c ++++ b/src/afs/afs_segments.c +@@ -174,8 +174,6 @@ afs_StoreAllSegments(struct vcache *avc, struct vrequest *areq, + + AFS_STATCNT(afs_StoreAllSegments); + +- hset(oldDV, avc->f.m.DataVersion); +- hset(newDV, avc->f.m.DataVersion); + hash = DVHash(&avc->f.fid); + foreign = (avc->f.states & CForeign); + dcList = (struct dcache **)osi_AllocLargeSpace(AFS_LRALLOCSIZ); +@@ -213,6 +211,14 @@ afs_StoreAllSegments(struct vcache *avc, struct vrequest *areq, + /*printf("Net down in afs_StoreSegments\n");*/ + return ENETDOWN; + } ++ ++ /* ++ * Can't do this earlier because osi_VM_StoreAllSegments drops locks ++ * and can indirectly do some stores that increase the DV. ++ */ ++ hset(oldDV, avc->f.m.DataVersion); ++ hset(newDV, avc->f.m.DataVersion); ++ + ConvertWToSLock(&avc->lock); + + /* diff --git a/debian/patches/0004-Linux-d_alias-becomes-d_u.d_alias.patch b/debian/patches/0004-Linux-d_alias-becomes-d_u.d_alias.patch new file mode 100644 index 000000000..cbf8769d6 --- /dev/null +++ b/debian/patches/0004-Linux-d_alias-becomes-d_u.d_alias.patch @@ -0,0 +1,89 @@ +From: Marc Dionne +Date: Thu, 18 Dec 2014 07:13:46 -0500 +Subject: Linux: d_alias becomes d_u.d_alias +MIME-Version: 1.0 +Content-Type: text/plain; charset="utf-8" +Content-Transfer-Encoding: 8bit + +The fields in struct dentry are re-arranged so that d_alias +shares space wth d_rcu inside the d_u union. Some references +need to change from d_alias to d_u.d_alias. + +The kernel change was introduced for 3.19 but was also backported +to the 3.18 stable series in 3.18.1, so this commit is required +for 3.19 and current 3.18 kernels. + +Reviewed-on: http://gerrit.openafs.org/11642 +Reviewed-by: Anders Kaseorg +Reviewed-by: Michael Laß +Reviewed-by: Daria Brashear +Tested-by: BuildBot +(cherry picked from commit d6f29679098aff171e69511823b340ccf28e5c31) + +Change-Id: Ifb6199aa7fa922e64540d9fad1d2d79facbb9761 +Reviewed-on: http://gerrit.openafs.org/11659 +Reviewed-by: Chas Williams - CONTRACTOR +Tested-by: BuildBot +Reviewed-by: Daria Brashear +Reviewed-by: Stephan Wiesand +(cherry picked from commit 860764da5ee2e48a2c3f7552fad1766e19eae47f) +--- + acinclude.m4 | 1 + + src/afs/LINUX/osi_compat.h | 4 ++++ + src/cf/linux-test4.m4 | 9 ++++++++- + 3 files changed, 13 insertions(+), 1 deletion(-) + +diff --git a/acinclude.m4 b/acinclude.m4 +index 13d70db..80a05b7 100644 +--- a/acinclude.m4 ++++ b/acinclude.m4 +@@ -828,6 +828,7 @@ case $AFS_SYSNAME in *_linux* | *_umlinux*) + [backing-dev.h]) + AC_CHECK_LINUX_STRUCT([cred], [session_keyring], [cred.h]) + AC_CHECK_LINUX_STRUCT([ctl_table], [ctl_name], [sysctl.h]) ++ AC_CHECK_LINUX_STRUCT([dentry], [d_u.d_alias], [dcache.h]) + AC_CHECK_LINUX_STRUCT([dentry_operations], [d_automount], [dcache.h]) + AC_CHECK_LINUX_STRUCT([inode], [i_alloc_sem], [fs.h]) + AC_CHECK_LINUX_STRUCT([inode], [i_blkbits], [fs.h]) +diff --git a/src/afs/LINUX/osi_compat.h b/src/afs/LINUX/osi_compat.h +index c500c61..15f7f69 100644 +--- a/src/afs/LINUX/osi_compat.h ++++ b/src/afs/LINUX/osi_compat.h +@@ -37,6 +37,10 @@ typedef struct vfs_path afs_linux_path_t; + typedef struct path afs_linux_path_t; + #endif + ++#if defined(STRUCT_DENTRY_HAS_D_U_D_ALIAS) ++# define d_alias d_u.d_alias ++#endif ++ + #ifndef HAVE_LINUX_DO_SYNC_READ + static inline int + do_sync_read(struct file *fp, char *buf, size_t count, loff_t *offp) { +diff --git a/src/cf/linux-test4.m4 b/src/cf/linux-test4.m4 +index b068af5..65237e2 100644 +--- a/src/cf/linux-test4.m4 ++++ b/src/cf/linux-test4.m4 +@@ -723,7 +723,11 @@ AC_DEFUN([LINUX_D_ALIAS_IS_HLIST], [ + [#include ], + [struct dentry *d = NULL; + struct hlist_node *hn = NULL; +- d->d_alias = *hn;], ++ #if defined(STRUCT_DENTRY_HAS_D_U_D_ALIAS) ++ d->d_u.d_alias = *hn; ++ #else ++ d->d_alias = *hn; ++ #endif], + [D_ALIAS_IS_HLIST], + [define if dentry->d_alias is an hlist], + []) +@@ -737,6 +741,9 @@ AC_DEFUN([LINUX_HLIST_ITERATOR_NO_NODE], [ + #include ], + [struct dentry *d = NULL, *cur; + struct inode *ip; ++ #if defined(STRUCT_DENTRY_HAS_D_U_D_ALIAS) ++ # define d_alias d_u.d_alias ++ #endif + hlist_for_each_entry(cur, &ip->i_dentry, d_alias) { } + ], + [HLIST_ITERATOR_NO_NODE], diff --git a/debian/patches/series b/debian/patches/series index aa8c90d9e..35f95c006 100644 --- a/debian/patches/series +++ b/debian/patches/series @@ -1,2 +1,4 @@ 0001-Linux-3.16-Switch-to-iter_file_splice_write.patch 0002-Linux-3.16-Convert-to-new-write_iter-read_iter-ops.patch +0003-Unix-CM-Avoid-using-stale-DV-in-afs_StoreAllSegments.patch +0004-Linux-d_alias-becomes-d_u.d_alias.patch