From: Greg Kroah-Hartman Date: Sat, 26 Sep 2015 17:18:17 +0000 (-0700) Subject: 4.2-stable patches X-Git-Tag: v4.1.9~26 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=0383c2471f5a0693b282750cd8e1c76ad1ff21ae;p=thirdparty%2Fkernel%2Fstable-queue.git 4.2-stable patches added patches: fs-don-t-dump-core-if-the-corefile-would-become-world-readable.patch fs-if-a-coredump-already-exists-unlink-and-recreate-with-o_excl.patch mmc-core-fix-race-condition-in-mmc_wait_data_done.patch mmc-sdhci-also-get-preset-value-and-driver-type-for-mmc_ddr52.patch mmc-sdhci-fix-dma-memory-leak-in-sdhci_pre_req.patch mmc-sdhci-of-esdhc-add-workaround-for-pre-divider-initial-value.patch mmc-sdhci-pci-set-the-clear-transfer-mode-register-quirk-for-o2micro.patch parisc-filter-out-spurious-interrupts-in-pa-risc-irq-handler.patch parisc-use-double-word-condition-in-64bit-cas-operation.patch pci-parisc-enable-64-bit-bus-addresses-on-pa-risc.patch rtc-abx80x-fix-rtc-write-bit.patch rtc-s3c-fix-disabled-clocks-for-alarm.patch rtc-s5m-fix-to-update-ctrl-register.patch vmscan-fix-increasing-nr_isolated-incurred-by-putback-unevictable-pages.patch workqueue-make-flush_workqueue-available-again-to-non-gpl-modules.patch --- diff --git a/queue-4.2/fs-don-t-dump-core-if-the-corefile-would-become-world-readable.patch b/queue-4.2/fs-don-t-dump-core-if-the-corefile-would-become-world-readable.patch new file mode 100644 index 00000000000..1df39875c4b --- /dev/null +++ b/queue-4.2/fs-don-t-dump-core-if-the-corefile-would-become-world-readable.patch @@ -0,0 +1,51 @@ +From 40f705a736eac10e7dca7ab5dd5ed675a6df031d Mon Sep 17 00:00:00 2001 +From: Jann Horn +Date: Wed, 9 Sep 2015 15:38:30 -0700 +Subject: fs: Don't dump core if the corefile would become world-readable. + +From: Jann Horn + +commit 40f705a736eac10e7dca7ab5dd5ed675a6df031d upstream. + +On a filesystem like vfat, all files are created with the same owner +and mode independent of who created the file. When a vfat filesystem +is mounted with root as owner of all files and read access for everyone, +root's processes left world-readable coredumps on it (but other +users' processes only left empty corefiles when given write access +because of the uid mismatch). + +Given that the old behavior was inconsistent and insecure, I don't see +a problem with changing it. Now, all processes refuse to dump core unless +the resulting corefile will only be readable by their owner. + +Signed-off-by: Jann Horn +Acked-by: Kees Cook +Cc: Al Viro +Signed-off-by: Andrew Morton +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman + +--- + fs/coredump.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +--- a/fs/coredump.c ++++ b/fs/coredump.c +@@ -685,11 +685,15 @@ void do_coredump(const siginfo_t *siginf + if (!S_ISREG(inode->i_mode)) + goto close_fail; + /* +- * Dont allow local users get cute and trick others to coredump +- * into their pre-created files. ++ * Don't dump core if the filesystem changed owner or mode ++ * of the file during file creation. This is an issue when ++ * a process dumps core while its cwd is e.g. on a vfat ++ * filesystem. + */ + if (!uid_eq(inode->i_uid, current_fsuid())) + goto close_fail; ++ if ((inode->i_mode & 0677) != 0600) ++ goto close_fail; + if (!(cprm.file->f_mode & FMODE_CAN_WRITE)) + goto close_fail; + if (do_truncate(cprm.file->f_path.dentry, 0, 0, cprm.file)) diff --git a/queue-4.2/fs-if-a-coredump-already-exists-unlink-and-recreate-with-o_excl.patch b/queue-4.2/fs-if-a-coredump-already-exists-unlink-and-recreate-with-o_excl.patch new file mode 100644 index 00000000000..88ce408d613 --- /dev/null +++ b/queue-4.2/fs-if-a-coredump-already-exists-unlink-and-recreate-with-o_excl.patch @@ -0,0 +1,146 @@ +From fbb1816942c04429e85dbf4c1a080accc534299e Mon Sep 17 00:00:00 2001 +From: Jann Horn +Date: Wed, 9 Sep 2015 15:38:28 -0700 +Subject: fs: if a coredump already exists, unlink and recreate with O_EXCL + +From: Jann Horn + +commit fbb1816942c04429e85dbf4c1a080accc534299e upstream. + +It was possible for an attacking user to trick root (or another user) into +writing his coredumps into an attacker-readable, pre-existing file using +rename() or link(), causing the disclosure of secret data from the victim +process' virtual memory. Depending on the configuration, it was also +possible to trick root into overwriting system files with coredumps. Fix +that issue by never writing coredumps into existing files. + +Requirements for the attack: + - The attack only applies if the victim's process has a nonzero + RLIMIT_CORE and is dumpable. + - The attacker can trick the victim into coredumping into an + attacker-writable directory D, either because the core_pattern is + relative and the victim's cwd is attacker-writable or because an + absolute core_pattern pointing to a world-writable directory is used. + - The attacker has one of these: + A: on a system with protected_hardlinks=0: + execute access to a folder containing a victim-owned, + attacker-readable file on the same partition as D, and the + victim-owned file will be deleted before the main part of the attack + takes place. (In practice, there are lots of files that fulfill + this condition, e.g. entries in Debian's /var/lib/dpkg/info/.) + This does not apply to most Linux systems because most distros set + protected_hardlinks=1. + B: on a system with protected_hardlinks=1: + execute access to a folder containing a victim-owned, + attacker-readable and attacker-writable file on the same partition + as D, and the victim-owned file will be deleted before the main part + of the attack takes place. + (This seems to be uncommon.) + C: on any system, independent of protected_hardlinks: + write access to a non-sticky folder containing a victim-owned, + attacker-readable file on the same partition as D + (This seems to be uncommon.) + +The basic idea is that the attacker moves the victim-owned file to where +he expects the victim process to dump its core. The victim process dumps +its core into the existing file, and the attacker reads the coredump from +it. + +If the attacker can't move the file because he does not have write access +to the containing directory, he can instead link the file to a directory +he controls, then wait for the original link to the file to be deleted +(because the kernel checks that the link count of the corefile is 1). + +A less reliable variant that requires D to be non-sticky works with link() +and does not require deletion of the original link: link() the file into +D, but then unlink() it directly before the kernel performs the link count +check. + +On systems with protected_hardlinks=0, this variant allows an attacker to +not only gain information from coredumps, but also clobber existing, +victim-writable files with coredumps. (This could theoretically lead to a +privilege escalation.) + +Signed-off-by: Jann Horn +Cc: Kees Cook +Cc: Al Viro +Signed-off-by: Andrew Morton +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman + +--- + fs/coredump.c | 38 ++++++++++++++++++++++++++++++++------ + 1 file changed, 32 insertions(+), 6 deletions(-) + +--- a/fs/coredump.c ++++ b/fs/coredump.c +@@ -513,10 +513,10 @@ void do_coredump(const siginfo_t *siginf + const struct cred *old_cred; + struct cred *cred; + int retval = 0; +- int flag = 0; + int ispipe; + struct files_struct *displaced; +- bool need_nonrelative = false; ++ /* require nonrelative corefile path and be extra careful */ ++ bool need_suid_safe = false; + bool core_dumped = false; + static atomic_t core_dump_count = ATOMIC_INIT(0); + struct coredump_params cprm = { +@@ -550,9 +550,8 @@ void do_coredump(const siginfo_t *siginf + */ + if (__get_dumpable(cprm.mm_flags) == SUID_DUMP_ROOT) { + /* Setuid core dump mode */ +- flag = O_EXCL; /* Stop rewrite attacks */ + cred->fsuid = GLOBAL_ROOT_UID; /* Dump root private */ +- need_nonrelative = true; ++ need_suid_safe = true; + } + + retval = coredump_wait(siginfo->si_signo, &core_state); +@@ -633,7 +632,7 @@ void do_coredump(const siginfo_t *siginf + if (cprm.limit < binfmt->min_coredump) + goto fail_unlock; + +- if (need_nonrelative && cn.corename[0] != '/') { ++ if (need_suid_safe && cn.corename[0] != '/') { + printk(KERN_WARNING "Pid %d(%s) can only dump core "\ + "to fully qualified path!\n", + task_tgid_vnr(current), current->comm); +@@ -641,8 +640,35 @@ void do_coredump(const siginfo_t *siginf + goto fail_unlock; + } + ++ /* ++ * Unlink the file if it exists unless this is a SUID ++ * binary - in that case, we're running around with root ++ * privs and don't want to unlink another user's coredump. ++ */ ++ if (!need_suid_safe) { ++ mm_segment_t old_fs; ++ ++ old_fs = get_fs(); ++ set_fs(KERNEL_DS); ++ /* ++ * If it doesn't exist, that's fine. If there's some ++ * other problem, we'll catch it at the filp_open(). ++ */ ++ (void) sys_unlink((const char __user *)cn.corename); ++ set_fs(old_fs); ++ } ++ ++ /* ++ * There is a race between unlinking and creating the ++ * file, but if that causes an EEXIST here, that's ++ * fine - another process raced with us while creating ++ * the corefile, and the other process won. To userspace, ++ * what matters is that at least one of the two processes ++ * writes its coredump successfully, not which one. ++ */ + cprm.file = filp_open(cn.corename, +- O_CREAT | 2 | O_NOFOLLOW | O_LARGEFILE | flag, ++ O_CREAT | 2 | O_NOFOLLOW | ++ O_LARGEFILE | O_EXCL, + 0600); + if (IS_ERR(cprm.file)) + goto fail_unlock; diff --git a/queue-4.2/mmc-core-fix-race-condition-in-mmc_wait_data_done.patch b/queue-4.2/mmc-core-fix-race-condition-in-mmc_wait_data_done.patch new file mode 100644 index 00000000000..ed5f8f91bd0 --- /dev/null +++ b/queue-4.2/mmc-core-fix-race-condition-in-mmc_wait_data_done.patch @@ -0,0 +1,105 @@ +From 71f8a4b81d040b3d094424197ca2f1bf811b1245 Mon Sep 17 00:00:00 2001 +From: Jialing Fu +Date: Fri, 28 Aug 2015 11:13:09 +0800 +Subject: mmc: core: fix race condition in mmc_wait_data_done + +From: Jialing Fu + +commit 71f8a4b81d040b3d094424197ca2f1bf811b1245 upstream. + +The following panic is captured in ker3.14, but the issue still exists +in latest kernel. +--------------------------------------------------------------------- +[ 20.738217] c0 3136 (Compiler) Unable to handle kernel NULL pointer dereference +at virtual address 00000578 +...... +[ 20.738499] c0 3136 (Compiler) PC is at _raw_spin_lock_irqsave+0x24/0x60 +[ 20.738527] c0 3136 (Compiler) LR is at _raw_spin_lock_irqsave+0x20/0x60 +[ 20.740134] c0 3136 (Compiler) Call trace: +[ 20.740165] c0 3136 (Compiler) [] _raw_spin_lock_irqsave+0x24/0x60 +[ 20.740200] c0 3136 (Compiler) [] __wake_up+0x1c/0x54 +[ 20.740230] c0 3136 (Compiler) [] mmc_wait_data_done+0x28/0x34 +[ 20.740262] c0 3136 (Compiler) [] mmc_request_done+0xa4/0x220 +[ 20.740314] c0 3136 (Compiler) [] sdhci_tasklet_finish+0xac/0x264 +[ 20.740352] c0 3136 (Compiler) [] tasklet_action+0xa0/0x158 +[ 20.740382] c0 3136 (Compiler) [] __do_softirq+0x10c/0x2e4 +[ 20.740411] c0 3136 (Compiler) [] irq_exit+0x8c/0xc0 +[ 20.740439] c0 3136 (Compiler) [] handle_IRQ+0x48/0xac +[ 20.740469] c0 3136 (Compiler) [] gic_handle_irq+0x38/0x7c +---------------------------------------------------------------------- +Because in SMP, "mrq" has race condition between below two paths: +path1: CPU0: + static void mmc_wait_data_done(struct mmc_request *mrq) + { + mrq->host->context_info.is_done_rcv = true; + // + // If CPU0 has just finished "is_done_rcv = true" in path1, and at + // this moment, IRQ or ICache line missing happens in CPU0. + // What happens in CPU1 (path2)? + // + // If the mmcqd thread in CPU1(path2) hasn't entered to sleep mode: + // path2 would have chance to break from wait_event_interruptible + // in mmc_wait_for_data_req_done and continue to run for next + // mmc_request (mmc_blk_rw_rq_prep). + // + // Within mmc_blk_rq_prep, mrq is cleared to 0. + // If below line still gets host from "mrq" as the result of + // compiler, the panic happens as we traced. + wake_up_interruptible(&mrq->host->context_info.wait); + } + +path2: CPU1: + static int mmc_wait_for_data_req_done(... + { + ... + while (1) { + wait_event_interruptible(context_info->wait, + (context_info->is_done_rcv || + context_info->is_new_req)); + static void mmc_blk_rw_rq_prep(... + { + ... + memset(brq, 0, sizeof(struct mmc_blk_request)); + +This issue happens very coincidentally; however adding mdelay(1) in +mmc_wait_data_done as below could duplicate it easily. + + static void mmc_wait_data_done(struct mmc_request *mrq) + { + mrq->host->context_info.is_done_rcv = true; ++ mdelay(1); + wake_up_interruptible(&mrq->host->context_info.wait); + } + +At runtime, IRQ or ICache line missing may just happen at the same place +of the mdelay(1). + +This patch gets the mmc_context_info at the beginning of function, it can +avoid this race condition. + +Signed-off-by: Jialing Fu +Tested-by: Shawn Lin +Fixes: 2220eedfd7ae ("mmc: fix async request mechanism ....") +Signed-off-by: Shawn Lin +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/core/core.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/drivers/mmc/core/core.c ++++ b/drivers/mmc/core/core.c +@@ -358,8 +358,10 @@ EXPORT_SYMBOL(mmc_start_bkops); + */ + static void mmc_wait_data_done(struct mmc_request *mrq) + { +- mrq->host->context_info.is_done_rcv = true; +- wake_up_interruptible(&mrq->host->context_info.wait); ++ struct mmc_context_info *context_info = &mrq->host->context_info; ++ ++ context_info->is_done_rcv = true; ++ wake_up_interruptible(&context_info->wait); + } + + static void mmc_wait_done(struct mmc_request *mrq) diff --git a/queue-4.2/mmc-sdhci-also-get-preset-value-and-driver-type-for-mmc_ddr52.patch b/queue-4.2/mmc-sdhci-also-get-preset-value-and-driver-type-for-mmc_ddr52.patch new file mode 100644 index 00000000000..a916cd74b22 --- /dev/null +++ b/queue-4.2/mmc-sdhci-also-get-preset-value-and-driver-type-for-mmc_ddr52.patch @@ -0,0 +1,57 @@ +From 0dafa60eb2506617e6968b97cc5a44914a7fb1a6 Mon Sep 17 00:00:00 2001 +From: Jisheng Zhang +Date: Tue, 18 Aug 2015 16:21:39 +0800 +Subject: mmc: sdhci: also get preset value and driver type for MMC_DDR52 + +From: Jisheng Zhang + +commit 0dafa60eb2506617e6968b97cc5a44914a7fb1a6 upstream. + +commit bb8175a8aa42 ("mmc: sdhci: clarify DDR timing mode between +SD-UHS and eMMC") added MMC_DDR52 as eMMC's DDR mode to be +distinguished from SD-UHS, but it missed setting driver type for +MMC_DDR52 timing mode. + +So sometimes we get the following error on Marvell BG2Q DMP board: + +[ 1.559598] mmcblk0: error -84 transferring data, sector 0, nr 8, cmd +response 0x900, card status 0xb00 +[ 1.569314] mmcblk0: retrying using single block read +[ 1.575676] mmcblk0: error -84 transferring data, sector 2, nr 6, cmd +response 0x900, card status 0x0 +[ 1.585202] blk_update_request: I/O error, dev mmcblk0, sector 2 +[ 1.591818] mmcblk0: error -84 transferring data, sector 3, nr 5, cmd +response 0x900, card status 0x0 +[ 1.601341] blk_update_request: I/O error, dev mmcblk0, sector 3 + +This patches fixes this by adding the missing driver type setting. + +Fixes: bb8175a8aa42 ("mmc: sdhci: clarify DDR timing mode ...") +Signed-off-by: Jisheng Zhang +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/host/sdhci.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +--- a/drivers/mmc/host/sdhci.c ++++ b/drivers/mmc/host/sdhci.c +@@ -1132,6 +1132,7 @@ static u16 sdhci_get_preset_value(struct + preset = sdhci_readw(host, SDHCI_PRESET_FOR_SDR104); + break; + case MMC_TIMING_UHS_DDR50: ++ case MMC_TIMING_MMC_DDR52: + preset = sdhci_readw(host, SDHCI_PRESET_FOR_DDR50); + break; + case MMC_TIMING_MMC_HS400: +@@ -1559,7 +1560,8 @@ static void sdhci_do_set_ios(struct sdhc + (ios->timing == MMC_TIMING_UHS_SDR25) || + (ios->timing == MMC_TIMING_UHS_SDR50) || + (ios->timing == MMC_TIMING_UHS_SDR104) || +- (ios->timing == MMC_TIMING_UHS_DDR50))) { ++ (ios->timing == MMC_TIMING_UHS_DDR50) || ++ (ios->timing == MMC_TIMING_MMC_DDR52))) { + u16 preset; + + sdhci_enable_preset_value(host, true); diff --git a/queue-4.2/mmc-sdhci-fix-dma-memory-leak-in-sdhci_pre_req.patch b/queue-4.2/mmc-sdhci-fix-dma-memory-leak-in-sdhci_pre_req.patch new file mode 100644 index 00000000000..94d56cea6e7 --- /dev/null +++ b/queue-4.2/mmc-sdhci-fix-dma-memory-leak-in-sdhci_pre_req.patch @@ -0,0 +1,206 @@ +From d31911b9374a76560d2c8ea4aa6ce5781621e81d Mon Sep 17 00:00:00 2001 +From: Haibo Chen +Date: Tue, 25 Aug 2015 10:02:11 +0800 +Subject: mmc: sdhci: fix dma memory leak in sdhci_pre_req() + +From: Haibo Chen + +commit d31911b9374a76560d2c8ea4aa6ce5781621e81d upstream. + +Currently one mrq->data maybe execute dma_map_sg() twice +when mmc subsystem prepare over one new request, and the +following log show up: + sdhci[sdhci_pre_dma_transfer] invalid cookie: 24, next-cookie 25 + +In this condition, mrq->date map a dma-memory(1) in sdhci_pre_req +for the first time, and map another dma-memory(2) in sdhci_prepare_data +for the second time. But driver only unmap the dma-memory(2), and +dma-memory(1) never unmapped, which cause the dma memory leak issue. + +This patch use another method to map the dma memory for the mrq->data +which can fix this dma memory leak issue. + +Fixes: 348487cb28e6 ("mmc: sdhci: use pipeline mmc requests to improve performance") +Reported-and-tested-by: Jiri Slaby +Signed-off-by: Haibo Chen +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/host/sdhci.c | 67 +++++++++++++++++------------------------------ + drivers/mmc/host/sdhci.h | 8 ++--- + 2 files changed, 29 insertions(+), 46 deletions(-) + +--- a/drivers/mmc/host/sdhci.c ++++ b/drivers/mmc/host/sdhci.c +@@ -54,8 +54,7 @@ static void sdhci_finish_command(struct + static int sdhci_execute_tuning(struct mmc_host *mmc, u32 opcode); + static void sdhci_enable_preset_value(struct sdhci_host *host, bool enable); + static int sdhci_pre_dma_transfer(struct sdhci_host *host, +- struct mmc_data *data, +- struct sdhci_host_next *next); ++ struct mmc_data *data); + static int sdhci_do_get_cd(struct sdhci_host *host); + + #ifdef CONFIG_PM +@@ -496,7 +495,7 @@ static int sdhci_adma_table_pre(struct s + goto fail; + BUG_ON(host->align_addr & host->align_mask); + +- host->sg_count = sdhci_pre_dma_transfer(host, data, NULL); ++ host->sg_count = sdhci_pre_dma_transfer(host, data); + if (host->sg_count < 0) + goto unmap_align; + +@@ -635,9 +634,11 @@ static void sdhci_adma_table_post(struct + } + } + +- if (!data->host_cookie) ++ if (data->host_cookie == COOKIE_MAPPED) { + dma_unmap_sg(mmc_dev(host->mmc), data->sg, + data->sg_len, direction); ++ data->host_cookie = COOKIE_UNMAPPED; ++ } + } + + static u8 sdhci_calc_timeout(struct sdhci_host *host, struct mmc_command *cmd) +@@ -833,7 +834,7 @@ static void sdhci_prepare_data(struct sd + } else { + int sg_cnt; + +- sg_cnt = sdhci_pre_dma_transfer(host, data, NULL); ++ sg_cnt = sdhci_pre_dma_transfer(host, data); + if (sg_cnt <= 0) { + /* + * This only happens when someone fed +@@ -949,11 +950,13 @@ static void sdhci_finish_data(struct sdh + if (host->flags & SDHCI_USE_ADMA) + sdhci_adma_table_post(host, data); + else { +- if (!data->host_cookie) ++ if (data->host_cookie == COOKIE_MAPPED) { + dma_unmap_sg(mmc_dev(host->mmc), + data->sg, data->sg_len, + (data->flags & MMC_DATA_READ) ? + DMA_FROM_DEVICE : DMA_TO_DEVICE); ++ data->host_cookie = COOKIE_UNMAPPED; ++ } + } + } + +@@ -2099,49 +2102,36 @@ static void sdhci_post_req(struct mmc_ho + struct mmc_data *data = mrq->data; + + if (host->flags & SDHCI_REQ_USE_DMA) { +- if (data->host_cookie) ++ if (data->host_cookie == COOKIE_GIVEN || ++ data->host_cookie == COOKIE_MAPPED) + dma_unmap_sg(mmc_dev(host->mmc), data->sg, data->sg_len, + data->flags & MMC_DATA_WRITE ? + DMA_TO_DEVICE : DMA_FROM_DEVICE); +- mrq->data->host_cookie = 0; ++ data->host_cookie = COOKIE_UNMAPPED; + } + } + + static int sdhci_pre_dma_transfer(struct sdhci_host *host, +- struct mmc_data *data, +- struct sdhci_host_next *next) ++ struct mmc_data *data) + { + int sg_count; + +- if (!next && data->host_cookie && +- data->host_cookie != host->next_data.cookie) { +- pr_debug(DRIVER_NAME "[%s] invalid cookie: %d, next-cookie %d\n", +- __func__, data->host_cookie, host->next_data.cookie); +- data->host_cookie = 0; ++ if (data->host_cookie == COOKIE_MAPPED) { ++ data->host_cookie = COOKIE_GIVEN; ++ return data->sg_count; + } + +- /* Check if next job is already prepared */ +- if (next || +- (!next && data->host_cookie != host->next_data.cookie)) { +- sg_count = dma_map_sg(mmc_dev(host->mmc), data->sg, +- data->sg_len, +- data->flags & MMC_DATA_WRITE ? +- DMA_TO_DEVICE : DMA_FROM_DEVICE); +- +- } else { +- sg_count = host->next_data.sg_count; +- host->next_data.sg_count = 0; +- } ++ WARN_ON(data->host_cookie == COOKIE_GIVEN); + ++ sg_count = dma_map_sg(mmc_dev(host->mmc), data->sg, data->sg_len, ++ data->flags & MMC_DATA_WRITE ? ++ DMA_TO_DEVICE : DMA_FROM_DEVICE); + + if (sg_count == 0) +- return -EINVAL; ++ return -ENOSPC; + +- if (next) { +- next->sg_count = sg_count; +- data->host_cookie = ++next->cookie < 0 ? 1 : next->cookie; +- } else +- host->sg_count = sg_count; ++ data->sg_count = sg_count; ++ data->host_cookie = COOKIE_MAPPED; + + return sg_count; + } +@@ -2151,16 +2141,10 @@ static void sdhci_pre_req(struct mmc_hos + { + struct sdhci_host *host = mmc_priv(mmc); + +- if (mrq->data->host_cookie) { +- mrq->data->host_cookie = 0; +- return; +- } ++ mrq->data->host_cookie = COOKIE_UNMAPPED; + + if (host->flags & SDHCI_REQ_USE_DMA) +- if (sdhci_pre_dma_transfer(host, +- mrq->data, +- &host->next_data) < 0) +- mrq->data->host_cookie = 0; ++ sdhci_pre_dma_transfer(host, mrq->data); + } + + static void sdhci_card_event(struct mmc_host *mmc) +@@ -3032,7 +3016,6 @@ int sdhci_add_host(struct sdhci_host *ho + host->max_clk = host->ops->get_max_clock(host); + } + +- host->next_data.cookie = 1; + /* + * In case of Host Controller v3.00, find out whether clock + * multiplier is supported. +--- a/drivers/mmc/host/sdhci.h ++++ b/drivers/mmc/host/sdhci.h +@@ -309,9 +309,10 @@ struct sdhci_adma2_64_desc { + */ + #define SDHCI_MAX_SEGS 128 + +-struct sdhci_host_next { +- unsigned int sg_count; +- s32 cookie; ++enum sdhci_cookie { ++ COOKIE_UNMAPPED, ++ COOKIE_MAPPED, ++ COOKIE_GIVEN, + }; + + struct sdhci_host { +@@ -503,7 +504,6 @@ struct sdhci_host { + unsigned int tuning_mode; /* Re-tuning mode supported by host */ + #define SDHCI_TUNING_MODE_1 0 + +- struct sdhci_host_next next_data; + unsigned long private[0] ____cacheline_aligned; + }; + diff --git a/queue-4.2/mmc-sdhci-of-esdhc-add-workaround-for-pre-divider-initial-value.patch b/queue-4.2/mmc-sdhci-of-esdhc-add-workaround-for-pre-divider-initial-value.patch new file mode 100644 index 00000000000..afa933b3ea5 --- /dev/null +++ b/queue-4.2/mmc-sdhci-of-esdhc-add-workaround-for-pre-divider-initial-value.patch @@ -0,0 +1,37 @@ +From 77bd2f6f6c65b4ad259394d416855ed561f21e8f Mon Sep 17 00:00:00 2001 +From: Yangbo Lu +Date: Tue, 11 Aug 2015 10:53:34 +0800 +Subject: mmc: sdhci-of-esdhc: add workaround for pre divider initial value + +From: Yangbo Lu + +commit 77bd2f6f6c65b4ad259394d416855ed561f21e8f upstream. + +For eSDHC(version < 2.3), the pre divider only could divide base clock +by 2 at least. Add workaround for this to avoid unexpected issue. + +Signed-off-by: Yangbo Lu +Acked-by: Joakim Tjernlund +Fixes: bd455029d01c ("mmc: sdhci-of-esdhc: Pre divider starts at 1") +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/host/sdhci-of-esdhc.c | 6 ++++++ + 1 file changed, 6 insertions(+) + +--- a/drivers/mmc/host/sdhci-of-esdhc.c ++++ b/drivers/mmc/host/sdhci-of-esdhc.c +@@ -208,6 +208,12 @@ static void esdhc_of_set_clock(struct sd + if (clock == 0) + return; + ++ /* Workaround to start pre_div at 2 for VNN < VENDOR_V_23 */ ++ temp = esdhc_readw(host, SDHCI_HOST_VERSION); ++ temp = (temp & SDHCI_VENDOR_VER_MASK) >> SDHCI_VENDOR_VER_SHIFT; ++ if (temp < VENDOR_V_23) ++ pre_div = 2; ++ + /* Workaround to reduce the clock frequency for p1010 esdhc */ + if (of_find_compatible_node(NULL, NULL, "fsl,p1010-esdhc")) { + if (clock > 20000000) diff --git a/queue-4.2/mmc-sdhci-pci-set-the-clear-transfer-mode-register-quirk-for-o2micro.patch b/queue-4.2/mmc-sdhci-pci-set-the-clear-transfer-mode-register-quirk-for-o2micro.patch new file mode 100644 index 00000000000..2e3654b64c6 --- /dev/null +++ b/queue-4.2/mmc-sdhci-pci-set-the-clear-transfer-mode-register-quirk-for-o2micro.patch @@ -0,0 +1,32 @@ +From 143b648ddf1583905fa15d32be27a31442fc7933 Mon Sep 17 00:00:00 2001 +From: Adam Lee +Date: Mon, 3 Aug 2015 14:33:28 +0800 +Subject: mmc: sdhci-pci: set the clear transfer mode register quirk for O2Micro + +From: Adam Lee + +commit 143b648ddf1583905fa15d32be27a31442fc7933 upstream. + +This patch fixes MMC not working issue on O2Micro/BayHub Host, which +requires transfer mode register to be cleared when sending no DMA +command. + +Signed-off-by: Peter Guo +Signed-off-by: Adam Lee +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/host/sdhci-pci.c | 1 + + 1 file changed, 1 insertion(+) + +--- a/drivers/mmc/host/sdhci-pci.c ++++ b/drivers/mmc/host/sdhci-pci.c +@@ -618,6 +618,7 @@ static int jmicron_resume(struct sdhci_p + static const struct sdhci_pci_fixes sdhci_o2 = { + .probe = sdhci_pci_o2_probe, + .quirks = SDHCI_QUIRK_NO_ENDATTR_IN_NOPDESC, ++ .quirks2 = SDHCI_QUIRK2_CLEAR_TRANSFERMODE_REG_BEFORE_CMD, + .probe_slot = sdhci_pci_o2_probe_slot, + .resume = sdhci_pci_o2_resume, + }; diff --git a/queue-4.2/parisc-filter-out-spurious-interrupts-in-pa-risc-irq-handler.patch b/queue-4.2/parisc-filter-out-spurious-interrupts-in-pa-risc-irq-handler.patch new file mode 100644 index 00000000000..a862517fa20 --- /dev/null +++ b/queue-4.2/parisc-filter-out-spurious-interrupts-in-pa-risc-irq-handler.patch @@ -0,0 +1,78 @@ +From b1b4e435e4ef7de77f07bf2a42c8380b960c2d44 Mon Sep 17 00:00:00 2001 +From: Helge Deller +Date: Thu, 3 Sep 2015 22:45:21 +0200 +Subject: parisc: Filter out spurious interrupts in PA-RISC irq handler + +From: Helge Deller + +commit b1b4e435e4ef7de77f07bf2a42c8380b960c2d44 upstream. + +When detecting a serial port on newer PA-RISC machines (with iosapic) we have a +long way to go to find the right IRQ line, registering it, then registering the +serial port and the irq handler for the serial port. During this phase spurious +interrupts for the serial port may happen which then crashes the kernel because +the action handler might not have been set up yet. + +So, basically it's a race condition between the serial port hardware and the +CPU which sets up the necessary fields in the irq sructs. The main reason for +this race is, that we unmask the serial port irqs too early without having set +up everything properly before (which isn't easily possible because we need the +IRQ number to register the serial ports). + +This patch is a work-around for this problem. It adds checks to the CPU irq +handler to verify if the IRQ action field has been initialized already. If not, +we just skip this interrupt (which isn't critical for a serial port at bootup). +The real fix would probably involve rewriting all PA-RISC specific IRQ code +(for CPU, IOSAPIC, GSC and EISA) to use IRQ domains with proper parenting of +the irq chips and proper irq enabling along this line. + +This bug has been in the PA-RISC port since the beginning, but the crashes +happened very rarely with currently used hardware. But on the latest machine +which I bought (a C8000 workstation), which uses the fastest CPUs (4 x PA8900, +1GHz) and which has the largest possible L1 cache size (64MB each), the kernel +crashed at every boot because of this race. So, without this patch the machine +would currently be unuseable. + +For the record, here is the flow logic: +1. serial_init_chip() in 8250_gsc.c calls iosapic_serial_irq(). +2. iosapic_serial_irq() calls txn_alloc_irq() to find the irq. +3. iosapic_serial_irq() calls cpu_claim_irq() to register the CPU irq +4. cpu_claim_irq() unmasks the CPU irq (which it shouldn't!) +5. serial_init_chip() then registers the 8250 port. +Problems: +- In step 4 the CPU irq shouldn't have been registered yet, but after step 5 +- If serial irq happens between 4 and 5 have finished, the kernel will crash + +Signed-off-by: Helge Deller +Signed-off-by: Greg Kroah-Hartman + +--- + arch/parisc/kernel/irq.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +--- a/arch/parisc/kernel/irq.c ++++ b/arch/parisc/kernel/irq.c +@@ -507,8 +507,8 @@ void do_cpu_irq_mask(struct pt_regs *reg + struct pt_regs *old_regs; + unsigned long eirr_val; + int irq, cpu = smp_processor_id(); +-#ifdef CONFIG_SMP + struct irq_desc *desc; ++#ifdef CONFIG_SMP + cpumask_t dest; + #endif + +@@ -521,8 +521,12 @@ void do_cpu_irq_mask(struct pt_regs *reg + goto set_out; + irq = eirr_to_irq(eirr_val); + +-#ifdef CONFIG_SMP ++ /* Filter out spurious interrupts, mostly from serial port at bootup */ + desc = irq_to_desc(irq); ++ if (unlikely(!desc->action)) ++ goto set_out; ++ ++#ifdef CONFIG_SMP + cpumask_copy(&dest, desc->irq_data.affinity); + if (irqd_is_per_cpu(&desc->irq_data) && + !cpumask_test_cpu(smp_processor_id(), &dest)) { diff --git a/queue-4.2/parisc-use-double-word-condition-in-64bit-cas-operation.patch b/queue-4.2/parisc-use-double-word-condition-in-64bit-cas-operation.patch new file mode 100644 index 00000000000..4697e5f0701 --- /dev/null +++ b/queue-4.2/parisc-use-double-word-condition-in-64bit-cas-operation.patch @@ -0,0 +1,34 @@ +From 1b59ddfcf1678de38a1f8ca9fb8ea5eebeff1843 Mon Sep 17 00:00:00 2001 +From: John David Anglin +Date: Mon, 7 Sep 2015 20:13:28 -0400 +Subject: parisc: Use double word condition in 64bit CAS operation + +From: John David Anglin + +commit 1b59ddfcf1678de38a1f8ca9fb8ea5eebeff1843 upstream. + +The attached change fixes the condition used in the "sub" instruction. +A double word comparison is needed. This fixes the 64-bit LWS CAS +operation on 64-bit kernels. + +I can now enable 64-bit atomic support in GCC. + +Signed-off-by: John David Anglin +Signed-off-by: Helge Deller +Signed-off-by: Greg Kroah-Hartman + +--- + arch/parisc/kernel/syscall.S | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/arch/parisc/kernel/syscall.S ++++ b/arch/parisc/kernel/syscall.S +@@ -821,7 +821,7 @@ cas2_action: + /* 64bit CAS */ + #ifdef CONFIG_64BIT + 19: ldd,ma 0(%sr3,%r26), %r29 +- sub,= %r29, %r25, %r0 ++ sub,*= %r29, %r25, %r0 + b,n cas2_end + 20: std,ma %r24, 0(%sr3,%r26) + copy %r0, %r28 diff --git a/queue-4.2/pci-parisc-enable-64-bit-bus-addresses-on-pa-risc.patch b/queue-4.2/pci-parisc-enable-64-bit-bus-addresses-on-pa-risc.patch new file mode 100644 index 00000000000..6cb21f9da7f --- /dev/null +++ b/queue-4.2/pci-parisc-enable-64-bit-bus-addresses-on-pa-risc.patch @@ -0,0 +1,58 @@ +From e02a653e15d8d32e9e768fd99a3271aafe5c5d77 Mon Sep 17 00:00:00 2001 +From: Helge Deller +Date: Wed, 2 Sep 2015 18:17:29 +0200 +Subject: PCI,parisc: Enable 64-bit bus addresses on PA-RISC + +From: Helge Deller + +commit e02a653e15d8d32e9e768fd99a3271aafe5c5d77 upstream. + +Commit 3a9ad0b ("PCI: Add pci_bus_addr_t") unconditionally introduced usage of +64-bit PCI bus addresses on all 64-bit platforms which broke PA-RISC. + +It turned out that due to enabling the 64-bit addresses, the PCI logic decided +to use the GMMIO instead of the LMMIO region. This commit simply disables +registering the GMMIO and thus we fall back to use the LMMIO region as before. + +Reverts commit 45ea2a5fed6dacb9bb0558d8b21eacc1c45d5bb4 +("PCI: Don't use 64-bit bus addresses on PA-RISC") + +To: linux-parisc@vger.kernel.org +Cc: linux-pci@vger.kernel.org +Cc: Bjorn Helgaas +Cc: Meelis Roos +Signed-off-by: Helge Deller +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/parisc/lba_pci.c | 7 +++++-- + drivers/pci/Kconfig | 2 +- + 2 files changed, 6 insertions(+), 3 deletions(-) + +--- a/drivers/parisc/lba_pci.c ++++ b/drivers/parisc/lba_pci.c +@@ -1556,8 +1556,11 @@ lba_driver_probe(struct parisc_device *d + if (lba_dev->hba.lmmio_space.flags) + pci_add_resource_offset(&resources, &lba_dev->hba.lmmio_space, + lba_dev->hba.lmmio_space_offset); +- if (lba_dev->hba.gmmio_space.flags) +- pci_add_resource(&resources, &lba_dev->hba.gmmio_space); ++ if (lba_dev->hba.gmmio_space.flags) { ++ /* pci_add_resource(&resources, &lba_dev->hba.gmmio_space); */ ++ pr_warn("LBA: Not registering GMMIO space %pR\n", ++ &lba_dev->hba.gmmio_space); ++ } + + pci_add_resource(&resources, &lba_dev->hba.bus_num); + +--- a/drivers/pci/Kconfig ++++ b/drivers/pci/Kconfig +@@ -2,7 +2,7 @@ + # PCI configuration + # + config PCI_BUS_ADDR_T_64BIT +- def_bool y if (ARCH_DMA_ADDR_T_64BIT || (64BIT && !PARISC)) ++ def_bool y if (ARCH_DMA_ADDR_T_64BIT || 64BIT) + depends on PCI + + config PCI_MSI diff --git a/queue-4.2/rtc-abx80x-fix-rtc-write-bit.patch b/queue-4.2/rtc-abx80x-fix-rtc-write-bit.patch new file mode 100644 index 00000000000..16cb8de5346 --- /dev/null +++ b/queue-4.2/rtc-abx80x-fix-rtc-write-bit.patch @@ -0,0 +1,30 @@ +From 5f1b2f77646fc0ef2f36fc554f5722a1381d0892 Mon Sep 17 00:00:00 2001 +From: Mitja Spes +Date: Wed, 2 Sep 2015 10:02:29 +0200 +Subject: rtc: abx80x: fix RTC write bit + +From: Mitja Spes + +commit 5f1b2f77646fc0ef2f36fc554f5722a1381d0892 upstream. + +Fix RTC write bit as per application manual + +Signed-off-by: Mitja Spes +Signed-off-by: Alexandre Belloni +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/rtc/rtc-abx80x.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/rtc/rtc-abx80x.c ++++ b/drivers/rtc/rtc-abx80x.c +@@ -28,7 +28,7 @@ + #define ABX8XX_REG_WD 0x07 + + #define ABX8XX_REG_CTRL1 0x10 +-#define ABX8XX_CTRL_WRITE BIT(1) ++#define ABX8XX_CTRL_WRITE BIT(0) + #define ABX8XX_CTRL_12_24 BIT(6) + + #define ABX8XX_REG_CFG_KEY 0x1f diff --git a/queue-4.2/rtc-s3c-fix-disabled-clocks-for-alarm.patch b/queue-4.2/rtc-s3c-fix-disabled-clocks-for-alarm.patch new file mode 100644 index 00000000000..c839e58de7b --- /dev/null +++ b/queue-4.2/rtc-s3c-fix-disabled-clocks-for-alarm.patch @@ -0,0 +1,81 @@ +From 1fb1c35f56bb6ab4a65920c648154b0f78f634a5 Mon Sep 17 00:00:00 2001 +From: Joonyoung Shim +Date: Wed, 12 Aug 2015 19:21:46 +0900 +Subject: rtc: s3c: fix disabled clocks for alarm + +From: Joonyoung Shim + +commit 1fb1c35f56bb6ab4a65920c648154b0f78f634a5 upstream. + +The clock enable/disable codes for alarm have been removed from +commit 24e1455493da ("drivers/rtc/rtc-s3c.c: delete duplicate clock +control") and the clocks are disabled even if alarm is set, so alarm +interrupt can't happen. + +The s3c_rtc_setaie function can be called several times with 'enabled' +argument having same value, so it needs to check whether clocks are +enabled or not. + +Signed-off-by: Joonyoung Shim +Reviewed-by: Krzysztof Kozlowski +Signed-off-by: Alexandre Belloni +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/rtc/rtc-s3c.c | 24 ++++++++++++++++++------ + 1 file changed, 18 insertions(+), 6 deletions(-) + +--- a/drivers/rtc/rtc-s3c.c ++++ b/drivers/rtc/rtc-s3c.c +@@ -39,6 +39,7 @@ struct s3c_rtc { + void __iomem *base; + struct clk *rtc_clk; + struct clk *rtc_src_clk; ++ bool clk_disabled; + + struct s3c_rtc_data *data; + +@@ -71,9 +72,12 @@ static void s3c_rtc_enable_clk(struct s3 + unsigned long irq_flags; + + spin_lock_irqsave(&info->alarm_clk_lock, irq_flags); +- clk_enable(info->rtc_clk); +- if (info->data->needs_src_clk) +- clk_enable(info->rtc_src_clk); ++ if (info->clk_disabled) { ++ clk_enable(info->rtc_clk); ++ if (info->data->needs_src_clk) ++ clk_enable(info->rtc_src_clk); ++ info->clk_disabled = false; ++ } + spin_unlock_irqrestore(&info->alarm_clk_lock, irq_flags); + } + +@@ -82,9 +86,12 @@ static void s3c_rtc_disable_clk(struct s + unsigned long irq_flags; + + spin_lock_irqsave(&info->alarm_clk_lock, irq_flags); +- if (info->data->needs_src_clk) +- clk_disable(info->rtc_src_clk); +- clk_disable(info->rtc_clk); ++ if (!info->clk_disabled) { ++ if (info->data->needs_src_clk) ++ clk_disable(info->rtc_src_clk); ++ clk_disable(info->rtc_clk); ++ info->clk_disabled = true; ++ } + spin_unlock_irqrestore(&info->alarm_clk_lock, irq_flags); + } + +@@ -128,6 +135,11 @@ static int s3c_rtc_setaie(struct device + + s3c_rtc_disable_clk(info); + ++ if (enabled) ++ s3c_rtc_enable_clk(info); ++ else ++ s3c_rtc_disable_clk(info); ++ + return 0; + } + diff --git a/queue-4.2/rtc-s5m-fix-to-update-ctrl-register.patch b/queue-4.2/rtc-s5m-fix-to-update-ctrl-register.patch new file mode 100644 index 00000000000..d6226203fea --- /dev/null +++ b/queue-4.2/rtc-s5m-fix-to-update-ctrl-register.patch @@ -0,0 +1,56 @@ +From ff02c0444b83201ff76cc49deccac8cf2bffc7bc Mon Sep 17 00:00:00 2001 +From: Joonyoung Shim +Date: Fri, 21 Aug 2015 18:43:41 +0900 +Subject: rtc: s5m: fix to update ctrl register + +From: Joonyoung Shim + +commit ff02c0444b83201ff76cc49deccac8cf2bffc7bc upstream. + +According to datasheet, the S2MPS13X and S2MPS14X should update write +buffer via setting WUDR bit to high after ctrl register is written. + +If not, ALARM interrupt of rtc-s5m doesn't happen first time when i use +tools/testing/selftests/timers/rtctest.c test program and hour format is +used to 12 hour mode in Odroid-XU3 board. + +One more issue is the RTC doesn't keep time on Odroid-XU3 board when i +turn on board after power off even if RTC battery is connected. It can +be solved as setting WUDR & RUDR bits to high at the same time after +RTC_CTRL register is written. It's same with condition of only writing +ALARM registers, so this is for only S2MPS14 and we should set WUDR & +A_UDR bits to high on S2MPS13. + +I can't find any reasonable description about this like fix from +datasheet, but can find similar codes from rtc driver source of +hardkernel kernel and vendor kernel. + +Signed-off-by: Joonyoung Shim +Reviewed-by: Krzysztof Kozlowski +Tested-by: Krzysztof Kozlowski +Signed-off-by: Alexandre Belloni +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/rtc/rtc-s5m.c | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +--- a/drivers/rtc/rtc-s5m.c ++++ b/drivers/rtc/rtc-s5m.c +@@ -635,6 +635,16 @@ static int s5m8767_rtc_init_reg(struct s + case S2MPS13X: + data[0] = (0 << BCD_EN_SHIFT) | (1 << MODEL24_SHIFT); + ret = regmap_write(info->regmap, info->regs->ctrl, data[0]); ++ if (ret < 0) ++ break; ++ ++ /* ++ * Should set WUDR & (RUDR or AUDR) bits to high after writing ++ * RTC_CTRL register like writing Alarm registers. We can't find ++ * the description from datasheet but vendor code does that ++ * really. ++ */ ++ ret = s5m8767_rtc_set_alarm_reg(info); + break; + + default: diff --git a/queue-4.2/series b/queue-4.2/series index 4499e3e3d65..efca88f13ed 100644 --- a/queue-4.2/series +++ b/queue-4.2/series @@ -93,3 +93,18 @@ sunrpc-fix-a-thinko-in-xs_connect.patch sunrpc-xs_reset_transport-must-mark-the-connection-as-disconnected.patch sunrpc-ensure-that-we-wait-for-connections-to-complete-before-retrying.patch sunrpc-lock-the-transport-layer-on-shutdown.patch +rtc-s3c-fix-disabled-clocks-for-alarm.patch +rtc-s5m-fix-to-update-ctrl-register.patch +rtc-abx80x-fix-rtc-write-bit.patch +pci-parisc-enable-64-bit-bus-addresses-on-pa-risc.patch +parisc-use-double-word-condition-in-64bit-cas-operation.patch +parisc-filter-out-spurious-interrupts-in-pa-risc-irq-handler.patch +workqueue-make-flush_workqueue-available-again-to-non-gpl-modules.patch +vmscan-fix-increasing-nr_isolated-incurred-by-putback-unevictable-pages.patch +fs-if-a-coredump-already-exists-unlink-and-recreate-with-o_excl.patch +fs-don-t-dump-core-if-the-corefile-would-become-world-readable.patch +mmc-sdhci-pci-set-the-clear-transfer-mode-register-quirk-for-o2micro.patch +mmc-sdhci-of-esdhc-add-workaround-for-pre-divider-initial-value.patch +mmc-sdhci-also-get-preset-value-and-driver-type-for-mmc_ddr52.patch +mmc-sdhci-fix-dma-memory-leak-in-sdhci_pre_req.patch +mmc-core-fix-race-condition-in-mmc_wait_data_done.patch diff --git a/queue-4.2/vmscan-fix-increasing-nr_isolated-incurred-by-putback-unevictable-pages.patch b/queue-4.2/vmscan-fix-increasing-nr_isolated-incurred-by-putback-unevictable-pages.patch new file mode 100644 index 00000000000..d0aa77bd171 --- /dev/null +++ b/queue-4.2/vmscan-fix-increasing-nr_isolated-incurred-by-putback-unevictable-pages.patch @@ -0,0 +1,54 @@ +From c54839a722a02818677bcabe57e957f0ce4f841d Mon Sep 17 00:00:00 2001 +From: Jaewon Kim +Date: Tue, 8 Sep 2015 15:02:21 -0700 +Subject: vmscan: fix increasing nr_isolated incurred by putback unevictable pages + +From: Jaewon Kim + +commit c54839a722a02818677bcabe57e957f0ce4f841d upstream. + +reclaim_clean_pages_from_list() assumes that shrink_page_list() returns +number of pages removed from the candidate list. But shrink_page_list() +puts back mlocked pages without passing it to caller and without +counting as nr_reclaimed. This increases nr_isolated. + +To fix this, this patch changes shrink_page_list() to pass unevictable +pages back to caller. Caller will take care those pages. + +Minchan said: + +It fixes two issues. + +1. With unevictable page, cma_alloc will be successful. + +Exactly speaking, cma_alloc of current kernel will fail due to +unevictable pages. + +2. fix leaking of NR_ISOLATED counter of vmstat + +With it, too_many_isolated works. Otherwise, it could make hang until +the process get SIGKILL. + +Signed-off-by: Jaewon Kim +Acked-by: Minchan Kim +Cc: Mel Gorman +Acked-by: Vlastimil Babka +Signed-off-by: Andrew Morton +Signed-off-by: Linus Torvalds +Signed-off-by: Greg Kroah-Hartman + +--- + mm/vmscan.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/mm/vmscan.c ++++ b/mm/vmscan.c +@@ -1190,7 +1190,7 @@ cull_mlocked: + if (PageSwapCache(page)) + try_to_free_swap(page); + unlock_page(page); +- putback_lru_page(page); ++ list_add(&page->lru, &ret_pages); + continue; + + activate_locked: diff --git a/queue-4.2/workqueue-make-flush_workqueue-available-again-to-non-gpl-modules.patch b/queue-4.2/workqueue-make-flush_workqueue-available-again-to-non-gpl-modules.patch new file mode 100644 index 00000000000..1c872ae8242 --- /dev/null +++ b/queue-4.2/workqueue-make-flush_workqueue-available-again-to-non-gpl-modules.patch @@ -0,0 +1,38 @@ +From 1dadafa86a779884f14a6e7a3ddde1a57b0a0a65 Mon Sep 17 00:00:00 2001 +From: Tim Gardner +Date: Tue, 4 Aug 2015 11:26:04 -0600 +Subject: workqueue: Make flush_workqueue() available again to non GPL modules + +From: Tim Gardner + +commit 1dadafa86a779884f14a6e7a3ddde1a57b0a0a65 upstream. + +Commit 37b1ef31a568fc02e53587620226e5f3c66454c8 ("workqueue: move +flush_scheduled_work() to workqueue.h") moved the exported non GPL +flush_scheduled_work() from a function to an inline wrapper. +Unfortunately, it directly calls flush_workqueue() which is a GPL function. +This has the effect of changing the licensing requirement for this function +and makes it unavailable to non GPL modules. + +See commit ad7b1f841f8a54c6d61ff181451f55b68175e15a ("workqueue: Make +schedule_work() available again to non GPL modules") for precedent. + +Signed-off-by: Tim Gardner +Signed-off-by: Tejun Heo +Signed-off-by: Greg Kroah-Hartman + +--- + kernel/workqueue.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/kernel/workqueue.c ++++ b/kernel/workqueue.c +@@ -2614,7 +2614,7 @@ void flush_workqueue(struct workqueue_st + out_unlock: + mutex_unlock(&wq->mutex); + } +-EXPORT_SYMBOL_GPL(flush_workqueue); ++EXPORT_SYMBOL(flush_workqueue); + + /** + * drain_workqueue - drain a workqueue