From: Luo Meng luomeng12@huawei.com
hulk inclusion category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I5KK4D CVE: NA
--------------------------------
This reverts commit f4f117026d586db38c025cd95b6094ff8de326df.
7f3945b4aab5 (NFS: Use of mapping_set_error() results in spurious errors) delete mappint->flags because of 67dd23f9e6fb (nfs: ensure correct writeback errors are returned on close()). However 67dd23f9e6fb has been reverted, use mappint->flags to return error.
Signed-off-by: Luo Meng luomeng12@huawei.com Reviewed-by: Zhang Xiaoxu zhangxiaoxu5@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- fs/nfs/write.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-)
diff --git a/fs/nfs/write.c b/fs/nfs/write.c index 5d07799513a6..e8f6ce88b1fb 100644 --- a/fs/nfs/write.c +++ b/fs/nfs/write.c @@ -310,10 +310,7 @@ static void nfs_mapping_set_error(struct page *page, int error) struct address_space *mapping = page_file_mapping(page);
SetPageError(page); - filemap_set_wb_err(mapping, error); - if (mapping->host) - errseq_set(&mapping->host->i_sb->s_wb_err, - error == -ENOSPC ? -ENOSPC : -EIO); + mapping_set_error(mapping, error); nfs_set_pageerror(mapping); }
From: Luo Meng luomeng12@huawei.com
mainline inclusion from mainline-v5.19 commit 3534e5a5ed2997ca1b00f44a0378a075bd05e8a3 category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I5GRX6
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?i...
--------------------------------
Fault inject on pool metadata device reports: BUG: KASAN: use-after-free in dm_pool_register_metadata_threshold+0x40/0x80 Read of size 8 at addr ffff8881b9d50068 by task dmsetup/950
CPU: 7 PID: 950 Comm: dmsetup Tainted: G W 5.19.0-rc6 #1 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.14.0-1.fc33 04/01/2014 Call Trace: <TASK> dump_stack_lvl+0x34/0x44 print_address_description.constprop.0.cold+0xeb/0x3f4 kasan_report.cold+0xe6/0x147 dm_pool_register_metadata_threshold+0x40/0x80 pool_ctr+0xa0a/0x1150 dm_table_add_target+0x2c8/0x640 table_load+0x1fd/0x430 ctl_ioctl+0x2c4/0x5a0 dm_ctl_ioctl+0xa/0x10 __x64_sys_ioctl+0xb3/0xd0 do_syscall_64+0x35/0x80 entry_SYSCALL_64_after_hwframe+0x46/0xb0
This can be easily reproduced using: echo offline > /sys/block/sda/device/state dd if=/dev/zero of=/dev/mapper/thin bs=4k count=10 dmsetup load pool --table "0 20971520 thin-pool /dev/sda /dev/sdb 128 0 0"
If a metadata commit fails, the transaction will be aborted and the metadata space maps will be destroyed. If a DM table reload then happens for this failed thin-pool, a use-after-free will occur in dm_sm_register_threshold_callback (called from dm_pool_register_metadata_threshold).
Fix this by in dm_pool_register_metadata_threshold() by returning the -EINVAL error if the thin-pool is in fail mode. Also fail pool_ctr() with a new error message: "Error registering metadata threshold".
Fixes: ac8c3f3df65e4 ("dm thin: generate event when metadata threshold passed") Cc: stable@vger.kernel.org Reported-by: Hulk Robot hulkci@huawei.com Signed-off-by: Luo Meng luomeng12@huawei.com Signed-off-by: Mike Snitzer snitzer@kernel.org Signed-off-by: Luo Meng luomeng12@huawei.com Reviewed-by: Zhang Xiaoxu zhangxiaoxu5@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- drivers/md/dm-thin-metadata.c | 7 +++++-- drivers/md/dm-thin.c | 4 +++- 2 files changed, 8 insertions(+), 3 deletions(-)
diff --git a/drivers/md/dm-thin-metadata.c b/drivers/md/dm-thin-metadata.c index 6ebb2127f3e2..842d79e5ea3a 100644 --- a/drivers/md/dm-thin-metadata.c +++ b/drivers/md/dm-thin-metadata.c @@ -2058,10 +2058,13 @@ int dm_pool_register_metadata_threshold(struct dm_pool_metadata *pmd, dm_sm_threshold_fn fn, void *context) { - int r; + int r = -EINVAL;
pmd_write_lock_in_core(pmd); - r = dm_sm_register_threshold_callback(pmd->metadata_sm, threshold, fn, context); + if (!pmd->fail_io) { + r = dm_sm_register_threshold_callback(pmd->metadata_sm, + threshold, fn, context); + } pmd_write_unlock(pmd);
return r; diff --git a/drivers/md/dm-thin.c b/drivers/md/dm-thin.c index fff4c50df74d..a196d7cb51bd 100644 --- a/drivers/md/dm-thin.c +++ b/drivers/md/dm-thin.c @@ -3401,8 +3401,10 @@ static int pool_ctr(struct dm_target *ti, unsigned argc, char **argv) calc_metadata_threshold(pt), metadata_low_callback, pool); - if (r) + if (r) { + ti->error = "Error registering metadata threshold"; goto out_flags_changed; + }
dm_pool_register_pre_commit_callback(pool->pmd, metadata_pre_commit_callback, pool);
From: ZhaoLong Wang wangzhaolong1@huawei.com
hulk inclusion category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I5MFXJ CVE: NA
-----------------------------------------
The readahead feature of the hulk-5.10 ebpf enhancement involves interface changes and needs to be compatible with the ebpf tool of version 4.19. This patch changes the _ctl_mode to _mode of fs_file_read_ctx structure.
Signed-off-by: ZhaoLong Wang wangzhaolong1@huawei.com Reviewed-by: zhihao Cheng chengzhihao1@huawei.com Reviewed-by: Hou Tao houtao1@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- fs/read_write.c | 8 ++++---- include/linux/fs.h | 10 +++++----- .../selftests/bpf/progs/file_read_pattern_prog.c | 16 ++++++++-------- 3 files changed, 17 insertions(+), 17 deletions(-)
diff --git a/fs/read_write.c b/fs/read_write.c index d175b5e8d3d3..c8df4ce598e1 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -1688,7 +1688,7 @@ static void fs_file_read_ctx_init(struct fs_file_read_ctx *ctx, { memset(ctx, 0, sizeof(*ctx)); ctx->name = file_dentry(filp)->d_name.name; - ctx->f_ctl_mode = filp->f_ctl_mode; + ctx->f_mode = filp->f_mode; ctx->key = (unsigned long)filp; ctx->i_size = file_inode(filp)->i_size; ctx->prev_index = filp->f_ra.prev_pos >> PAGE_SHIFT; @@ -1706,11 +1706,11 @@ void fs_file_read_update_args_by_trace(struct kiocb *iocb) fs_file_read_ctx_init(&ctx, filp, iocb->ki_pos); trace_fs_file_read(&ctx, FS_FILE_READ_VERSION);
- if (!ctx.set_f_ctl_mode && !ctx.clr_f_ctl_mode) + if (!ctx.set_f_mode && !ctx.clr_f_mode) return;
- filp->f_ctl_mode |= ctx.set_f_ctl_mode & FS_FILE_READ_MODE_MASK; - filp->f_ctl_mode &= ~(ctx.clr_f_ctl_mode & FS_FILE_READ_MODE_MASK); + filp->f_ctl_mode |= ctx.set_f_mode & FS_FILE_READ_MODE_MASK; + filp->f_ctl_mode &= ~(ctx.clr_f_mode & FS_FILE_READ_MODE_MASK); } EXPORT_SYMBOL_GPL(fs_file_read_update_args_by_trace); #endif diff --git a/include/linux/fs.h b/include/linux/fs.h index 5c71b826c89c..b95ff48204ba 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -185,10 +185,10 @@ typedef int (dio_iodone_t)(struct kiocb *iocb, loff_t offset, #define FMODE_BUF_RASYNC ((__force fmode_t)0x40000000)
/* File mode control flag, expect random access pattern */ -#define FMODE_CTL_RANDOM ((__force fmode_t)0x1) +#define FMODE_CTL_RANDOM ((__force fmode_t)0x1000)
/* File mode control flag, will try to read head of the file into pagecache */ -#define FMODE_CTL_WILLNEED ((__force fmode_t)0x2) +#define FMODE_CTL_WILLNEED ((__force fmode_t)0x400000)
/* * Attribute flags. These should be or-ed together to figure out what @@ -3561,12 +3561,12 @@ static inline int inode_drain_writes(struct inode *inode)
struct fs_file_read_ctx { const unsigned char *name; - unsigned int f_ctl_mode; + unsigned int f_mode; unsigned int rsvd; /* clear from f_ctl_mode */ - unsigned int clr_f_ctl_mode; + unsigned int clr_f_mode; /* set into f_ctl_mode */ - unsigned int set_f_ctl_mode; + unsigned int set_f_mode; unsigned long key; /* file size */ long long i_size; diff --git a/tools/testing/selftests/bpf/progs/file_read_pattern_prog.c b/tools/testing/selftests/bpf/progs/file_read_pattern_prog.c index cd2dcd7c64bb..1d9f199d8370 100644 --- a/tools/testing/selftests/bpf/progs/file_read_pattern_prog.c +++ b/tools/testing/selftests/bpf/progs/file_read_pattern_prog.c @@ -11,17 +11,17 @@ #endif
/* Need to keep consistent with definitions in include/linux/fs.h */ -#define FMODE_CTL_RANDOM 0x1 -#define FMODE_CTL_WILLNEED 0x2 +#define FMODE_CTL_RANDOM 0x1000 +#define FMODE_CTL_WILLNEED 0x400000
struct fs_file_read_ctx { const unsigned char *name; - unsigned int f_ctl_mode; + unsigned int f_mode; unsigned int rsvd; /* clear from f_ctl_mode */ - unsigned int clr_f_ctl_mode; + unsigned int clr_f_mode; /* set into f_ctl_mode */ - unsigned int set_f_ctl_mode; + unsigned int set_f_mode; unsigned long key; /* file size */ long long i_size; @@ -80,7 +80,7 @@ int fs_file_read(struct fs_file_read_args *args) return 0;
if (rd_ctx->i_size <= (4 << 20)) { - rd_ctx->set_f_ctl_mode = FMODE_CTL_WILLNEED; + rd_ctx->set_f_mode = FMODE_CTL_WILLNEED; return 0; }
@@ -112,9 +112,9 @@ int fs_file_read(struct fs_file_read_args *args) if (now - hist->last_nsec >= 500000000ULL || hist->tot_nr >= 10) { if (hist->tot_nr >= 10) { if (hist->seq_nr <= hist->tot_nr * 3 / 10) - rd_ctx->set_f_ctl_mode = FMODE_CTL_RANDOM; + rd_ctx->set_f_mode = FMODE_CTL_RANDOM; else if (hist->seq_nr >= hist->tot_nr * 7 / 10) - rd_ctx->clr_f_ctl_mode = FMODE_CTL_RANDOM; + rd_ctx->clr_f_mode = FMODE_CTL_RANDOM; }
hist->last_nsec = now;
From: Oliver Upton oupton@google.com
mainline inclusion from mainline-v5.14 commit fe5161d2c39b8c2801f0e786631460c6e8a1cae4 category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I4VZJT CVE: NA
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?i...
--------------------------------
Most other architectures that implement KVM record a statistic indicating the number of times a vCPU has exited due to a pending signal. Add support for that stat to arm64.
Reviewed-by: Jing Zhang jingzhangos@google.com Signed-off-by: Oliver Upton oupton@google.com Signed-off-by: Marc Zyngier maz@kernel.org Link: https://lore.kernel.org/r/20210802192809.1851010-2-oupton@google.com
Signed-off-by: Zhang Qiao zhangqiao22@huawei.com Reviewed-by: Keqian Zhu zhukeqian1@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- arch/arm64/include/asm/kvm_host.h | 1 + arch/arm64/kvm/arm.c | 1 + arch/arm64/kvm/guest.c | 2 ++ 3 files changed, 4 insertions(+)
diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h index 7e8deca33a02..1a80df133d9d 100644 --- a/arch/arm64/include/asm/kvm_host.h +++ b/arch/arm64/include/asm/kvm_host.h @@ -477,6 +477,7 @@ struct kvm_vcpu_stat { u64 wfi_exit_stat; u64 mmio_exit_user; u64 mmio_exit_kernel; + u64 signal_exits; u64 exits; u64 fp_asimd_exit_stat; u64 irq_exit_stat; diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c index d7745ff2eb59..b50d9daf3685 100644 --- a/arch/arm64/kvm/arm.c +++ b/arch/arm64/kvm/arm.c @@ -794,6 +794,7 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu) if (signal_pending(current)) { ret = -EINTR; run->exit_reason = KVM_EXIT_INTR; + ++vcpu->stat.signal_exits; }
/* diff --git a/arch/arm64/kvm/guest.c b/arch/arm64/kvm/guest.c index 9f678decc8e5..009b8a727692 100644 --- a/arch/arm64/kvm/guest.c +++ b/arch/arm64/kvm/guest.c @@ -39,6 +39,7 @@ struct kvm_stats_debugfs_item debugfs_entries[] = { VCPU_STAT("wfi_exit_stat", wfi_exit_stat), VCPU_STAT("mmio_exit_user", mmio_exit_user), VCPU_STAT("mmio_exit_kernel", mmio_exit_kernel), + VCPU_STAT("signal_exits", signal_exits), VCPU_STAT("exits", exits), VCPU_STAT("halt_poll_success_ns", halt_poll_success_ns), VCPU_STAT("halt_poll_fail_ns", halt_poll_fail_ns), @@ -54,6 +55,7 @@ struct dfx_kvm_stats_debugfs_item dfx_debugfs_entries[] = { DFX_STAT("wfi_exit_stat", wfi_exit_stat), DFX_STAT("mmio_exit_user", mmio_exit_user), DFX_STAT("mmio_exit_kernel", mmio_exit_kernel), + DFX_STAT("signal_exits", signal_exits), DFX_STAT("exits", exits), DFX_STAT("fp_asimd_exit_stat", fp_asimd_exit_stat), DFX_STAT("irq_exit_stat", irq_exit_stat),
From: Oliver Upton oupton@google.com
mainline inclusion from mainline-v5.14 commit e1c6b9e1669e44fb7f9688e34e460b759e3b9187 category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I4VZJT CVE: NA
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?i...
--------------------------------
Some architectures (e.g. arm64) have yet to adopt the generic entry infrastructure. Despite that, it would be nice to use some common plumbing for guest entry/exit handling. For example, KVM/arm64 currently does not handle TIF_NOTIFY_PENDING correctly.
Allow use of only the generic KVM entry code by tightening up the include list. No functional change intended.
Signed-off-by: Oliver Upton oupton@google.com Signed-off-by: Marc Zyngier maz@kernel.org Link: https://lore.kernel.org/r/20210802192809.1851010-3-oupton@google.com Signed-off-by: Zhang Qiao zhangqiao22@huawei.com Reviewed-by: Keqian Zhu zhukeqian1@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- include/linux/entry-kvm.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/include/linux/entry-kvm.h b/include/linux/entry-kvm.h index 0cef17afb41a..f49472ebd8a4 100644 --- a/include/linux/entry-kvm.h +++ b/include/linux/entry-kvm.h @@ -2,7 +2,11 @@ #ifndef __LINUX_ENTRYKVM_H #define __LINUX_ENTRYKVM_H
-#include <linux/entry-common.h> +#include <linux/static_call_types.h> +#include <linux/tracehook.h> +#include <linux/syscalls.h> +#include <linux/seccomp.h> +#include <linux/sched.h>
/* Transfer to guest mode work */ #ifdef CONFIG_KVM_XFER_TO_GUEST_WORK
From: Oliver Upton oupton@google.com
mainline inclusion from mainline-v5.14 commit 6caa5812e2d126a0aa8a17816c1ba6f0a0c2b309 category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I4VZJT CVE: NA
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?i...
--------------------------------
Clean up handling of checks for pending work by switching to the generic infrastructure to do so.
We pick up handling for TIF_NOTIFY_RESUME from this switch, meaning that task work will be correctly handled.
Signed-off-by: Oliver Upton oupton@google.com Signed-off-by: Marc Zyngier maz@kernel.org Link: https://lore.kernel.org/r/20210802192809.1851010-4-oupton@google.com Signed-off-by: Zhang Qiao zhangqiao22@huawei.com Reviewed-by: Keqian Zhu zhukeqian1@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- arch/arm64/kvm/Kconfig | 1 + arch/arm64/kvm/arm.c | 72 ++++++++++++++++++++++++++---------------- 2 files changed, 45 insertions(+), 28 deletions(-)
diff --git a/arch/arm64/kvm/Kconfig b/arch/arm64/kvm/Kconfig index 043756db8f6e..bc6b692128c9 100644 --- a/arch/arm64/kvm/Kconfig +++ b/arch/arm64/kvm/Kconfig @@ -28,6 +28,7 @@ menuconfig KVM select HAVE_KVM_ARCH_TLB_FLUSH_ALL select KVM_MMIO select KVM_GENERIC_DIRTYLOG_READ_PROTECT + select KVM_XFER_TO_GUEST_WORK select SRCU select KVM_VFIO select HAVE_KVM_EVENTFD diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c index b50d9daf3685..384cc56a6549 100644 --- a/arch/arm64/kvm/arm.c +++ b/arch/arm64/kvm/arm.c @@ -6,6 +6,7 @@
#include <linux/bug.h> #include <linux/cpu_pm.h> +#include <linux/entry-kvm.h> #include <linux/errno.h> #include <linux/err.h> #include <linux/kvm_host.h> @@ -727,6 +728,45 @@ static void update_vcpu_stat_time(struct kvm_vcpu_stat *vcpu_stat) vcpu_stat->gtime = current->gtime; }
+/** + * kvm_vcpu_exit_request - returns true if the VCPU should *not* enter the guest + * @vcpu: The VCPU pointer + * @ret: Pointer to write optional return code + * + * Returns: true if the VCPU needs to return to a preemptible + interruptible + * and skip guest entry. + * + * This function disambiguates between two different types of exits: exits to a + * preemptible + interruptible kernel context and exits to userspace. For an + * exit to userspace, this function will write the return code to ret and return + * true. For an exit to preemptible + interruptible kernel context (i.e. check + * for pending work and re-enter), return true without writing to ret. + */ +static bool kvm_vcpu_exit_request(struct kvm_vcpu *vcpu, int *ret) +{ + struct kvm_run *run = vcpu->run; + + /* + * If we're using a userspace irqchip, then check if we need + * to tell a userspace irqchip about timer or PMU level + * changes and if so, exit to userspace (the actual level + * state gets updated in kvm_timer_update_run and + * kvm_pmu_update_run below). + */ + if (static_branch_unlikely(&userspace_irqchip_in_use)) { + if (kvm_timer_should_notify_user(vcpu) || + kvm_pmu_should_notify_user(vcpu)) { + *ret = -EINTR; + run->exit_reason = KVM_EXIT_INTR; + return true; + } + } + + return kvm_request_pending(vcpu) || + need_new_vmid_gen(&vcpu->arch.hw_mmu->vmid) || + xfer_to_guest_mode_work_pending(); +} + /** * kvm_arch_vcpu_ioctl_run - the main VCPU run function to execute guest code * @vcpu: The VCPU pointer @@ -768,7 +808,9 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu) /* * Check conditions before entering the guest */ - cond_resched(); + ret = xfer_to_guest_mode_handle_work(vcpu); + if (!ret) + ret = 1;
update_vmid(&vcpu->arch.hw_mmu->vmid);
@@ -787,31 +829,6 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu)
kvm_vgic_flush_hwstate(vcpu);
- /* - * Exit if we have a signal pending so that we can deliver the - * signal to user space. - */ - if (signal_pending(current)) { - ret = -EINTR; - run->exit_reason = KVM_EXIT_INTR; - ++vcpu->stat.signal_exits; - } - - /* - * If we're using a userspace irqchip, then check if we need - * to tell a userspace irqchip about timer or PMU level - * changes and if so, exit to userspace (the actual level - * state gets updated in kvm_timer_update_run and - * kvm_pmu_update_run below). - */ - if (static_branch_unlikely(&userspace_irqchip_in_use)) { - if (kvm_timer_should_notify_user(vcpu) || - kvm_pmu_should_notify_user(vcpu)) { - ret = -EINTR; - run->exit_reason = KVM_EXIT_INTR; - } - } - /* * Ensure we set mode to IN_GUEST_MODE after we disable * interrupts and before the final VCPU requests check. @@ -820,8 +837,7 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu) */ smp_store_mb(vcpu->mode, IN_GUEST_MODE);
- if (ret <= 0 || need_new_vmid_gen(&vcpu->arch.hw_mmu->vmid) || - kvm_request_pending(vcpu)) { + if (ret <= 0 || kvm_vcpu_exit_request(vcpu, &ret)) { vcpu->mode = OUTSIDE_GUEST_MODE; isb(); /* Ensure work in x_flush_hwstate is committed */ kvm_pmu_sync_hwstate(vcpu);
From: Eric Dumazet edumazet@google.com
stable inclusion from stable-v5.10.137 commit d0412d8f693e6f00b6cda80cc3ae1fbc7c14d392 category: bugfix bugzilla: https://gitee.com/openeuler/kernel/issues/I5NYY0?from=project-issue CVE: NA
Reference: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?id=...
--------------------------------
[ Upstream commit 7c80b038d23e1f4c7fcc311f43f83b8c60e7fb80 ]
If sk->sk_forward_alloc is 150000, and we need to schedule 150001 bytes, we want to allocate 1 byte more (rounded up to one page), instead of 150001 :/
Fixes: 1da177e4c3f4 ("Linux-2.6.12-rc2") Signed-off-by: Eric Dumazet edumazet@google.com Reviewed-by: Shakeel Butt shakeelb@google.com Acked-by: Soheil Hassas Yeganeh soheil@google.com Signed-off-by: Jakub Kicinski kuba@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org Signed-off-by: Ziyang Xuan william.xuanziyang@huawei.com Reviewed-by: Yue Haibing yuehaibing@huawei.com Reviewed-by: Wei Yongjun weiyongjun1@huawei.com Signed-off-by: Zheng Zengkai zhengzengkai@huawei.com --- include/net/sock.h | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
diff --git a/include/net/sock.h b/include/net/sock.h index bd34faf53b1f..10668d5e38e9 100644 --- a/include/net/sock.h +++ b/include/net/sock.h @@ -1491,19 +1491,23 @@ static inline bool sk_has_account(struct sock *sk)
static inline bool sk_wmem_schedule(struct sock *sk, int size) { + int delta; + if (!sk_has_account(sk)) return true; - return size <= sk->sk_forward_alloc || - __sk_mem_schedule(sk, size, SK_MEM_SEND); + delta = size - sk->sk_forward_alloc; + return delta <= 0 || __sk_mem_schedule(sk, delta, SK_MEM_SEND); }
static inline bool sk_rmem_schedule(struct sock *sk, struct sk_buff *skb, int size) { + int delta; + if (!sk_has_account(sk)) return true; - return size <= sk->sk_forward_alloc || - __sk_mem_schedule(sk, size, SK_MEM_RECV) || + delta = size - sk->sk_forward_alloc; + return delta <= 0 || __sk_mem_schedule(sk, delta, SK_MEM_RECV) || skb_pfmemalloc(skb); }