Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
openeuler
Kernel
提交
399f157a
K
Kernel
项目概览
openeuler
/
Kernel
大约 1 年 前同步成功
通知
5
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
K
Kernel
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
399f157a
编写于
2月 28, 2017
作者:
R
Russell King
浏览文件
操作
浏览文件
下载
差异文件
Merge branch 'devel-stable' into misc
上级
a09975bf
1a08e3d9
变更
51
隐藏空白更改
内联
并排
Showing
51 changed file
with
569 addition
and
337 deletion
+569
-337
Documentation/DocBook/Makefile
Documentation/DocBook/Makefile
+1
-1
Documentation/unaligned-memory-access.txt
Documentation/unaligned-memory-access.txt
+1
-1
Makefile
Makefile
+1
-1
arch/arm64/include/asm/asm-uaccess.h
arch/arm64/include/asm/asm-uaccess.h
+65
-0
arch/arm64/include/asm/uaccess.h
arch/arm64/include/asm/uaccess.h
+0
-64
arch/arm64/kernel/entry.S
arch/arm64/kernel/entry.S
+1
-1
arch/arm64/lib/clear_user.S
arch/arm64/lib/clear_user.S
+1
-1
arch/arm64/lib/copy_from_user.S
arch/arm64/lib/copy_from_user.S
+1
-1
arch/arm64/lib/copy_in_user.S
arch/arm64/lib/copy_in_user.S
+1
-1
arch/arm64/lib/copy_to_user.S
arch/arm64/lib/copy_to_user.S
+1
-1
arch/arm64/mm/cache.S
arch/arm64/mm/cache.S
+1
-1
arch/arm64/xen/hypercall.S
arch/arm64/xen/hypercall.S
+1
-1
arch/x86/Kconfig
arch/x86/Kconfig
+1
-0
arch/x86/include/asm/bitops.h
arch/x86/include/asm/bitops.h
+13
-0
arch/x86/kernel/cpu/mcheck/mce_amd.c
arch/x86/kernel/cpu/mcheck/mce_amd.c
+3
-0
crypto/testmgr.c
crypto/testmgr.c
+28
-2
drivers/crypto/marvell/cesa.h
drivers/crypto/marvell/cesa.h
+2
-1
drivers/crypto/marvell/hash.c
drivers/crypto/marvell/hash.c
+33
-1
drivers/crypto/marvell/tdma.c
drivers/crypto/marvell/tdma.c
+8
-1
drivers/firmware/psci.c
drivers/firmware/psci.c
+1
-1
drivers/net/ethernet/korina.c
drivers/net/ethernet/korina.c
+4
-4
drivers/net/ethernet/mellanox/mlx4/en_netdev.c
drivers/net/ethernet/mellanox/mlx4/en_netdev.c
+2
-1
drivers/net/ethernet/realtek/r8169.c
drivers/net/ethernet/realtek/r8169.c
+1
-0
drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
+3
-1
drivers/net/ipvlan/ipvlan.h
drivers/net/ipvlan/ipvlan.h
+5
-0
drivers/net/ipvlan/ipvlan_core.c
drivers/net/ipvlan/ipvlan_core.c
+38
-22
drivers/net/ipvlan/ipvlan_main.c
drivers/net/ipvlan/ipvlan_main.c
+6
-1
fs/dax.c
fs/dax.c
+154
-89
fs/ext2/inode.c
fs/ext2/inode.c
+1
-2
fs/ext4/file.c
fs/ext4/file.c
+10
-38
include/linux/dax.h
include/linux/dax.h
+3
-0
include/linux/filter.h
include/linux/filter.h
+0
-1
include/linux/mm.h
include/linux/mm.h
+4
-0
include/linux/page-flags.h
include/linux/page-flags.h
+1
-1
include/net/netns/ipv4.h
include/net/netns/ipv4.h
+1
-0
include/net/tcp.h
include/net/tcp.h
+0
-1
kernel/cpu.c
kernel/cpu.c
+8
-1
kernel/kexec_core.c
kernel/kexec_core.c
+1
-1
lib/Kconfig.debug
lib/Kconfig.debug
+4
-1
mm/cma.c
mm/cma.c
+5
-10
mm/filemap.c
mm/filemap.c
+31
-5
mm/kasan/kasan_init.c
mm/kasan/kasan_init.c
+8
-7
mm/truncate.c
mm/truncate.c
+61
-14
mm/usercopy.c
mm/usercopy.c
+2
-2
net/core/filter.c
net/core/filter.c
+0
-6
net/ipv4/sysctl_net_ipv4.c
net/ipv4/sysctl_net_ipv4.c
+7
-7
net/ipv4/tcp_ipv4.c
net/ipv4/tcp_ipv4.c
+2
-2
net/openvswitch/datapath.c
net/openvswitch/datapath.c
+0
-1
net/openvswitch/flow.c
net/openvswitch/flow.c
+27
-27
net/sched/cls_api.c
net/sched/cls_api.c
+3
-1
net/tipc/socket.c
net/tipc/socket.c
+13
-11
未找到文件。
Documentation/DocBook/Makefile
浏览文件 @
399f157a
...
...
@@ -12,7 +12,7 @@ DOCBOOKS := z8530book.xml \
kernel-api.xml filesystems.xml lsm.xml kgdb.xml
\
gadget.xml libata.xml mtdnand.xml librs.xml rapidio.xml
\
genericirq.xml s390-drivers.xml uio-howto.xml scsi.xml
\
80211.xml
sh.xml regulator.xml w1.xml
\
sh.xml regulator.xml w1.xml
\
writing_musb_glue_layer.xml iio.xml
ifeq
($(DOCBOOKS),)
...
...
Documentation/unaligned-memory-access.txt
浏览文件 @
399f157a
...
...
@@ -151,7 +151,7 @@ bool ether_addr_equal(const u8 *addr1, const u8 *addr2)
#else
const u16 *a = (const u16 *)addr1;
const u16 *b = (const u16 *)addr2;
return ((a[0] ^ b[0]) | (a[1] ^ b[1]) | (a[2] ^ b[2]))
!
= 0;
return ((a[0] ^ b[0]) | (a[1] ^ b[1]) | (a[2] ^ b[2]))
=
= 0;
#endif
}
...
...
Makefile
浏览文件 @
399f157a
VERSION
=
4
PATCHLEVEL
=
10
SUBLEVEL
=
0
EXTRAVERSION
=
-rc
1
EXTRAVERSION
=
-rc
2
NAME
=
Roaring Lionus
# *DOCUMENTATION*
...
...
arch/arm64/include/asm/asm-uaccess.h
0 → 100644
浏览文件 @
399f157a
#ifndef __ASM_ASM_UACCESS_H
#define __ASM_ASM_UACCESS_H
#include <asm/alternative.h>
#include <asm/kernel-pgtable.h>
#include <asm/sysreg.h>
#include <asm/assembler.h>
/*
* User access enabling/disabling macros.
*/
#ifdef CONFIG_ARM64_SW_TTBR0_PAN
.
macro
__uaccess_ttbr0_disable
,
tmp1
mrs
\
tmp1
,
ttbr1_el1
// swapper_pg_dir
add
\
tmp1
,
\
tmp1
,
#
SWAPPER_DIR_SIZE
// reserved_ttbr0 at the end of swapper_pg_dir
msr
ttbr0_el1
,
\
tmp1
// set reserved TTBR0_EL1
isb
.
endm
.
macro
__uaccess_ttbr0_enable
,
tmp1
get_thread_info
\
tmp1
ldr
\
tmp1
,
[
\
tmp1
,
#
TSK_TI_TTBR0
]
// load saved TTBR0_EL1
msr
ttbr0_el1
,
\
tmp1
// set the non-PAN TTBR0_EL1
isb
.
endm
.
macro
uaccess_ttbr0_disable
,
tmp1
alternative_if_not
ARM64_HAS_PAN
__uaccess_ttbr0_disable
\
tmp1
alternative_else_nop_endif
.
endm
.
macro
uaccess_ttbr0_enable
,
tmp1
,
tmp2
alternative_if_not
ARM64_HAS_PAN
save_and_disable_irq
\
tmp2
// avoid preemption
__uaccess_ttbr0_enable
\
tmp1
restore_irq
\
tmp2
alternative_else_nop_endif
.
endm
#else
.
macro
uaccess_ttbr0_disable
,
tmp1
.
endm
.
macro
uaccess_ttbr0_enable
,
tmp1
,
tmp2
.
endm
#endif
/*
* These macros are no-ops when UAO is present.
*/
.
macro
uaccess_disable_not_uao
,
tmp1
uaccess_ttbr0_disable
\
tmp1
alternative_if
ARM64_ALT_PAN_NOT_UAO
SET_PSTATE_PAN
(
1
)
alternative_else_nop_endif
.
endm
.
macro
uaccess_enable_not_uao
,
tmp1
,
tmp2
uaccess_ttbr0_enable
\
tmp1
,
\
tmp2
alternative_if
ARM64_ALT_PAN_NOT_UAO
SET_PSTATE_PAN
(
0
)
alternative_else_nop_endif
.
endm
#endif
arch/arm64/include/asm/uaccess.h
浏览文件 @
399f157a
...
...
@@ -22,8 +22,6 @@
#include <asm/kernel-pgtable.h>
#include <asm/sysreg.h>
#ifndef __ASSEMBLY__
/*
* User space memory access functions
*/
...
...
@@ -424,66 +422,4 @@ extern long strncpy_from_user(char *dest, const char __user *src, long count);
extern
__must_check
long
strlen_user
(
const
char
__user
*
str
);
extern
__must_check
long
strnlen_user
(
const
char
__user
*
str
,
long
n
);
#else
/* __ASSEMBLY__ */
#include <asm/assembler.h>
/*
* User access enabling/disabling macros.
*/
#ifdef CONFIG_ARM64_SW_TTBR0_PAN
.
macro
__uaccess_ttbr0_disable
,
tmp1
mrs
\
tmp1
,
ttbr1_el1
// swapper_pg_dir
add
\
tmp1
,
\
tmp1
,
#
SWAPPER_DIR_SIZE
// reserved_ttbr0 at the end of swapper_pg_dir
msr
ttbr0_el1
,
\
tmp1
// set reserved TTBR0_EL1
isb
.
endm
.
macro
__uaccess_ttbr0_enable
,
tmp1
get_thread_info
\
tmp1
ldr
\
tmp1
,
[
\
tmp1
,
#
TSK_TI_TTBR0
]
// load saved TTBR0_EL1
msr
ttbr0_el1
,
\
tmp1
// set the non-PAN TTBR0_EL1
isb
.
endm
.
macro
uaccess_ttbr0_disable
,
tmp1
alternative_if_not
ARM64_HAS_PAN
__uaccess_ttbr0_disable
\
tmp1
alternative_else_nop_endif
.
endm
.
macro
uaccess_ttbr0_enable
,
tmp1
,
tmp2
alternative_if_not
ARM64_HAS_PAN
save_and_disable_irq
\
tmp2
// avoid preemption
__uaccess_ttbr0_enable
\
tmp1
restore_irq
\
tmp2
alternative_else_nop_endif
.
endm
#else
.
macro
uaccess_ttbr0_disable
,
tmp1
.
endm
.
macro
uaccess_ttbr0_enable
,
tmp1
,
tmp2
.
endm
#endif
/*
* These macros are no-ops when UAO is present.
*/
.
macro
uaccess_disable_not_uao
,
tmp1
uaccess_ttbr0_disable
\
tmp1
alternative_if
ARM64_ALT_PAN_NOT_UAO
SET_PSTATE_PAN
(
1
)
alternative_else_nop_endif
.
endm
.
macro
uaccess_enable_not_uao
,
tmp1
,
tmp2
uaccess_ttbr0_enable
\
tmp1
,
\
tmp2
alternative_if
ARM64_ALT_PAN_NOT_UAO
SET_PSTATE_PAN
(
0
)
alternative_else_nop_endif
.
endm
#endif
/* __ASSEMBLY__ */
#endif
/* __ASM_UACCESS_H */
arch/arm64/kernel/entry.S
浏览文件 @
399f157a
...
...
@@ -31,7 +31,7 @@
#include <asm/memory.h>
#include <asm/ptrace.h>
#include <asm/thread_info.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
#include <asm/unistd.h>
/*
...
...
arch/arm64/lib/clear_user.S
浏览文件 @
399f157a
...
...
@@ -17,7 +17,7 @@
*/
#include <linux/linkage.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
.
text
...
...
arch/arm64/lib/copy_from_user.S
浏览文件 @
399f157a
...
...
@@ -17,7 +17,7 @@
#include <linux/linkage.h>
#include <asm/cache.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
/*
*
Copy
from
user
space
to
a
kernel
buffer
(
alignment
handled
by
the
hardware
)
...
...
arch/arm64/lib/copy_in_user.S
浏览文件 @
399f157a
...
...
@@ -19,7 +19,7 @@
#include <linux/linkage.h>
#include <asm/cache.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
/*
*
Copy
from
user
space
to
user
space
(
alignment
handled
by
the
hardware
)
...
...
arch/arm64/lib/copy_to_user.S
浏览文件 @
399f157a
...
...
@@ -17,7 +17,7 @@
#include <linux/linkage.h>
#include <asm/cache.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
/*
*
Copy
to
user
space
from
a
kernel
buffer
(
alignment
handled
by
the
hardware
)
...
...
arch/arm64/mm/cache.S
浏览文件 @
399f157a
...
...
@@ -23,7 +23,7 @@
#include <asm/assembler.h>
#include <asm/cpufeature.h>
#include <asm/alternative.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
/*
*
flush_icache_range
(
start
,
end
)
...
...
arch/arm64/xen/hypercall.S
浏览文件 @
399f157a
...
...
@@ -49,7 +49,7 @@
#include <linux/linkage.h>
#include <asm/assembler.h>
#include <
linux/
uaccess.h>
#include <
asm/asm-
uaccess.h>
#include <xen/interface/xen.h>
...
...
arch/x86/Kconfig
浏览文件 @
399f157a
...
...
@@ -46,6 +46,7 @@ config X86
select ARCH_CLOCKSOURCE_DATA
select ARCH_DISCARD_MEMBLOCK
select ARCH_HAS_ACPI_TABLE_UPGRADE if ACPI
select ARCH_HAS_DEBUG_VIRTUAL
select ARCH_HAS_DEVMEM_IS_ALLOWED
select ARCH_HAS_ELF_RANDOMIZE
select ARCH_HAS_FAST_MULTIPLIER
...
...
arch/x86/include/asm/bitops.h
浏览文件 @
399f157a
...
...
@@ -139,6 +139,19 @@ static __always_inline void __clear_bit(long nr, volatile unsigned long *addr)
asm
volatile
(
"btr %1,%0"
:
ADDR
:
"Ir"
(
nr
));
}
static
__always_inline
bool
clear_bit_unlock_is_negative_byte
(
long
nr
,
volatile
unsigned
long
*
addr
)
{
bool
negative
;
asm
volatile
(
LOCK_PREFIX
"andb %2,%1
\n\t
"
CC_SET
(
s
)
:
CC_OUT
(
s
)
(
negative
),
ADDR
:
"ir"
((
char
)
~
(
1
<<
nr
))
:
"memory"
);
return
negative
;
}
// Let everybody know we have it
#define clear_bit_unlock_is_negative_byte clear_bit_unlock_is_negative_byte
/*
* __clear_bit_unlock - Clears a bit in memory
* @nr: Bit to clear
...
...
arch/x86/kernel/cpu/mcheck/mce_amd.c
浏览文件 @
399f157a
...
...
@@ -1182,6 +1182,9 @@ static int threshold_create_bank(unsigned int cpu, unsigned int bank)
const
char
*
name
=
get_name
(
bank
,
NULL
);
int
err
=
0
;
if
(
!
dev
)
return
-
ENODEV
;
if
(
is_shared_bank
(
bank
))
{
nb
=
node_to_amd_nb
(
amd_get_nb_id
(
cpu
));
...
...
crypto/testmgr.c
浏览文件 @
399f157a
...
...
@@ -1461,16 +1461,25 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
for
(
i
=
0
;
i
<
ctcount
;
i
++
)
{
unsigned
int
dlen
=
COMP_BUF_SIZE
;
int
ilen
=
ctemplate
[
i
].
inlen
;
void
*
input_vec
;
input_vec
=
kmalloc
(
ilen
,
GFP_KERNEL
);
if
(
!
input_vec
)
{
ret
=
-
ENOMEM
;
goto
out
;
}
memcpy
(
input_vec
,
ctemplate
[
i
].
input
,
ilen
);
memset
(
output
,
0
,
dlen
);
init_completion
(
&
result
.
completion
);
sg_init_one
(
&
src
,
ctemplate
[
i
].
input
,
ilen
);
sg_init_one
(
&
src
,
input_vec
,
ilen
);
sg_init_one
(
&
dst
,
output
,
dlen
);
req
=
acomp_request_alloc
(
tfm
);
if
(
!
req
)
{
pr_err
(
"alg: acomp: request alloc failed for %s
\n
"
,
algo
);
kfree
(
input_vec
);
ret
=
-
ENOMEM
;
goto
out
;
}
...
...
@@ -1483,6 +1492,7 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
if
(
ret
)
{
pr_err
(
"alg: acomp: compression failed on test %d for %s: ret=%d
\n
"
,
i
+
1
,
algo
,
-
ret
);
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
...
...
@@ -1491,6 +1501,7 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
pr_err
(
"alg: acomp: Compression test %d failed for %s: output len = %d
\n
"
,
i
+
1
,
algo
,
req
->
dlen
);
ret
=
-
EINVAL
;
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
...
...
@@ -1500,26 +1511,37 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
i
+
1
,
algo
);
hexdump
(
output
,
req
->
dlen
);
ret
=
-
EINVAL
;
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
kfree
(
input_vec
);
acomp_request_free
(
req
);
}
for
(
i
=
0
;
i
<
dtcount
;
i
++
)
{
unsigned
int
dlen
=
COMP_BUF_SIZE
;
int
ilen
=
dtemplate
[
i
].
inlen
;
void
*
input_vec
;
input_vec
=
kmalloc
(
ilen
,
GFP_KERNEL
);
if
(
!
input_vec
)
{
ret
=
-
ENOMEM
;
goto
out
;
}
memcpy
(
input_vec
,
dtemplate
[
i
].
input
,
ilen
);
memset
(
output
,
0
,
dlen
);
init_completion
(
&
result
.
completion
);
sg_init_one
(
&
src
,
dtemplate
[
i
].
input
,
ilen
);
sg_init_one
(
&
src
,
input_vec
,
ilen
);
sg_init_one
(
&
dst
,
output
,
dlen
);
req
=
acomp_request_alloc
(
tfm
);
if
(
!
req
)
{
pr_err
(
"alg: acomp: request alloc failed for %s
\n
"
,
algo
);
kfree
(
input_vec
);
ret
=
-
ENOMEM
;
goto
out
;
}
...
...
@@ -1532,6 +1554,7 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
if
(
ret
)
{
pr_err
(
"alg: acomp: decompression failed on test %d for %s: ret=%d
\n
"
,
i
+
1
,
algo
,
-
ret
);
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
...
...
@@ -1540,6 +1563,7 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
pr_err
(
"alg: acomp: Decompression test %d failed for %s: output len = %d
\n
"
,
i
+
1
,
algo
,
req
->
dlen
);
ret
=
-
EINVAL
;
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
...
...
@@ -1549,10 +1573,12 @@ static int test_acomp(struct crypto_acomp *tfm, struct comp_testvec *ctemplate,
i
+
1
,
algo
);
hexdump
(
output
,
req
->
dlen
);
ret
=
-
EINVAL
;
kfree
(
input_vec
);
acomp_request_free
(
req
);
goto
out
;
}
kfree
(
input_vec
);
acomp_request_free
(
req
);
}
...
...
drivers/crypto/marvell/cesa.h
浏览文件 @
399f157a
...
...
@@ -273,7 +273,8 @@ struct mv_cesa_op_ctx {
#define CESA_TDMA_SRC_IN_SRAM BIT(30)
#define CESA_TDMA_END_OF_REQ BIT(29)
#define CESA_TDMA_BREAK_CHAIN BIT(28)
#define CESA_TDMA_TYPE_MSK GENMASK(27, 0)
#define CESA_TDMA_SET_STATE BIT(27)
#define CESA_TDMA_TYPE_MSK GENMASK(26, 0)
#define CESA_TDMA_DUMMY 0
#define CESA_TDMA_DATA 1
#define CESA_TDMA_OP 2
...
...
drivers/crypto/marvell/hash.c
浏览文件 @
399f157a
...
...
@@ -280,13 +280,32 @@ static void mv_cesa_ahash_std_prepare(struct ahash_request *req)
sreq
->
offset
=
0
;
}
static
void
mv_cesa_ahash_dma_step
(
struct
ahash_request
*
req
)
{
struct
mv_cesa_ahash_req
*
creq
=
ahash_request_ctx
(
req
);
struct
mv_cesa_req
*
base
=
&
creq
->
base
;
/* We must explicitly set the digest state. */
if
(
base
->
chain
.
first
->
flags
&
CESA_TDMA_SET_STATE
)
{
struct
mv_cesa_engine
*
engine
=
base
->
engine
;
int
i
;
/* Set the hash state in the IVDIG regs. */
for
(
i
=
0
;
i
<
ARRAY_SIZE
(
creq
->
state
);
i
++
)
writel_relaxed
(
creq
->
state
[
i
],
engine
->
regs
+
CESA_IVDIG
(
i
));
}
mv_cesa_dma_step
(
base
);
}
static
void
mv_cesa_ahash_step
(
struct
crypto_async_request
*
req
)
{
struct
ahash_request
*
ahashreq
=
ahash_request_cast
(
req
);
struct
mv_cesa_ahash_req
*
creq
=
ahash_request_ctx
(
ahashreq
);
if
(
mv_cesa_req_get_type
(
&
creq
->
base
)
==
CESA_DMA_REQ
)
mv_cesa_
dma_step
(
&
creq
->
base
);
mv_cesa_
ahash_dma_step
(
ahashreq
);
else
mv_cesa_ahash_std_step
(
ahashreq
);
}
...
...
@@ -584,12 +603,16 @@ static int mv_cesa_ahash_dma_req_init(struct ahash_request *req)
struct
mv_cesa_ahash_dma_iter
iter
;
struct
mv_cesa_op_ctx
*
op
=
NULL
;
unsigned
int
frag_len
;
bool
set_state
=
false
;
int
ret
;
u32
type
;
basereq
->
chain
.
first
=
NULL
;
basereq
->
chain
.
last
=
NULL
;
if
(
!
mv_cesa_mac_op_is_first_frag
(
&
creq
->
op_tmpl
))
set_state
=
true
;
if
(
creq
->
src_nents
)
{
ret
=
dma_map_sg
(
cesa_dev
->
dev
,
req
->
src
,
creq
->
src_nents
,
DMA_TO_DEVICE
);
...
...
@@ -683,6 +706,15 @@ static int mv_cesa_ahash_dma_req_init(struct ahash_request *req)
if
(
type
!=
CESA_TDMA_RESULT
)
basereq
->
chain
.
last
->
flags
|=
CESA_TDMA_BREAK_CHAIN
;
if
(
set_state
)
{
/*
* Put the CESA_TDMA_SET_STATE flag on the first tdma desc to
* let the step logic know that the IVDIG registers should be
* explicitly set before launching a TDMA chain.
*/
basereq
->
chain
.
first
->
flags
|=
CESA_TDMA_SET_STATE
;
}
return
0
;
err_free_tdma:
...
...
drivers/crypto/marvell/tdma.c
浏览文件 @
399f157a
...
...
@@ -109,7 +109,14 @@ void mv_cesa_tdma_chain(struct mv_cesa_engine *engine,
last
->
next
=
dreq
->
chain
.
first
;
engine
->
chain
.
last
=
dreq
->
chain
.
last
;
if
(
!
(
last
->
flags
&
CESA_TDMA_BREAK_CHAIN
))
/*
* Break the DMA chain if the CESA_TDMA_BREAK_CHAIN is set on
* the last element of the current chain, or if the request
* being queued needs the IV regs to be set before lauching
* the request.
*/
if
(
!
(
last
->
flags
&
CESA_TDMA_BREAK_CHAIN
)
&&
!
(
dreq
->
chain
.
first
->
flags
&
CESA_TDMA_SET_STATE
))
last
->
next_dma
=
dreq
->
chain
.
first
->
cur_dma
;
}
}
...
...
drivers/firmware/psci.c
浏览文件 @
399f157a
...
...
@@ -383,7 +383,7 @@ static int psci_suspend_finisher(unsigned long index)
u32
*
state
=
__this_cpu_read
(
psci_power_state
);
return
psci_ops
.
cpu_suspend
(
state
[
index
-
1
],
virt_to_phys
(
cpu_resume
));
__pa_symbol
(
cpu_resume
));
}
int
psci_cpu_suspend_enter
(
unsigned
long
index
)
...
...
drivers/net/ethernet/korina.c
浏览文件 @
399f157a
...
...
@@ -900,10 +900,10 @@ static void korina_restart_task(struct work_struct *work)
DMA_STAT_DONE
|
DMA_STAT_HALT
|
DMA_STAT_ERR
,
&
lp
->
rx_dma_regs
->
dmasm
);
korina_free_ring
(
dev
);
napi_disable
(
&
lp
->
napi
);
korina_free_ring
(
dev
);
if
(
korina_init
(
dev
)
<
0
)
{
printk
(
KERN_ERR
"%s: cannot restart device
\n
"
,
dev
->
name
);
return
;
...
...
@@ -1064,12 +1064,12 @@ static int korina_close(struct net_device *dev)
tmp
=
tmp
|
DMA_STAT_DONE
|
DMA_STAT_HALT
|
DMA_STAT_ERR
;
writel
(
tmp
,
&
lp
->
rx_dma_regs
->
dmasm
);
korina_free_ring
(
dev
);
napi_disable
(
&
lp
->
napi
);
cancel_work_sync
(
&
lp
->
restart_task
);
korina_free_ring
(
dev
);
free_irq
(
lp
->
rx_irq
,
dev
);
free_irq
(
lp
->
tx_irq
,
dev
);
free_irq
(
lp
->
ovr_irq
,
dev
);
...
...
drivers/net/ethernet/mellanox/mlx4/en_netdev.c
浏览文件 @
399f157a
...
...
@@ -1638,7 +1638,8 @@ int mlx4_en_start_port(struct net_device *dev)
/* Configure tx cq's and rings */
for
(
t
=
0
;
t
<
MLX4_EN_NUM_TX_TYPES
;
t
++
)
{
u8
num_tx_rings_p_up
=
t
==
TX
?
priv
->
num_tx_rings_p_up
:
1
;
u8
num_tx_rings_p_up
=
t
==
TX
?
priv
->
num_tx_rings_p_up
:
priv
->
tx_ring_num
[
t
];
for
(
i
=
0
;
i
<
priv
->
tx_ring_num
[
t
];
i
++
)
{
/* Configure cq */
...
...
drivers/net/ethernet/realtek/r8169.c
浏览文件 @
399f157a
...
...
@@ -326,6 +326,7 @@ enum cfg_version {
static
const
struct
pci_device_id
rtl8169_pci_tbl
[]
=
{
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8129
),
0
,
0
,
RTL_CFG_0
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8136
),
0
,
0
,
RTL_CFG_2
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8161
),
0
,
0
,
RTL_CFG_1
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8167
),
0
,
0
,
RTL_CFG_0
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8168
),
0
,
0
,
RTL_CFG_1
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8169
),
0
,
0
,
RTL_CFG_0
},
...
...
drivers/net/ethernet/stmicro/stmmac/stmmac_mdio.c
浏览文件 @
399f157a
...
...
@@ -116,7 +116,7 @@ static int stmmac_mdio_write(struct mii_bus *bus, int phyaddr, int phyreg,
unsigned
int
mii_address
=
priv
->
hw
->
mii
.
addr
;
unsigned
int
mii_data
=
priv
->
hw
->
mii
.
data
;
u32
value
=
MII_
WRITE
|
MII_
BUSY
;
u32
value
=
MII_BUSY
;
value
|=
(
phyaddr
<<
priv
->
hw
->
mii
.
addr_shift
)
&
priv
->
hw
->
mii
.
addr_mask
;
...
...
@@ -126,6 +126,8 @@ static int stmmac_mdio_write(struct mii_bus *bus, int phyaddr, int phyreg,
&
priv
->
hw
->
mii
.
clk_csr_mask
;
if
(
priv
->
plat
->
has_gmac4
)
value
|=
MII_GMAC4_WRITE
;
else
value
|=
MII_WRITE
;
/* Wait until any existing MII operation is complete */
if
(
stmmac_mdio_busy_wait
(
priv
->
ioaddr
,
mii_address
))
...
...
drivers/net/ipvlan/ipvlan.h
浏览文件 @
399f157a
...
...
@@ -99,6 +99,11 @@ struct ipvl_port {
int
count
;
};
struct
ipvl_skb_cb
{
bool
tx_pkt
;
};
#define IPVL_SKB_CB(_skb) ((struct ipvl_skb_cb *)&((_skb)->cb[0]))
static
inline
struct
ipvl_port
*
ipvlan_port_get_rcu
(
const
struct
net_device
*
d
)
{
return
rcu_dereference
(
d
->
rx_handler_data
);
...
...
drivers/net/ipvlan/ipvlan_core.c
浏览文件 @
399f157a
...
...
@@ -198,7 +198,7 @@ void ipvlan_process_multicast(struct work_struct *work)
unsigned
int
mac_hash
;
int
ret
;
u8
pkt_type
;
bool
hlocal
,
dlocal
;
bool
tx_pkt
;
__skb_queue_head_init
(
&
list
);
...
...
@@ -207,8 +207,11 @@ void ipvlan_process_multicast(struct work_struct *work)
spin_unlock_bh
(
&
port
->
backlog
.
lock
);
while
((
skb
=
__skb_dequeue
(
&
list
))
!=
NULL
)
{
struct
net_device
*
dev
=
skb
->
dev
;
bool
consumed
=
false
;
ethh
=
eth_hdr
(
skb
);
hlocal
=
ether_addr_equal
(
ethh
->
h_source
,
port
->
dev
->
dev_addr
)
;
tx_pkt
=
IPVL_SKB_CB
(
skb
)
->
tx_pkt
;
mac_hash
=
ipvlan_mac_hash
(
ethh
->
h_dest
);
if
(
ether_addr_equal
(
ethh
->
h_dest
,
port
->
dev
->
broadcast
))
...
...
@@ -216,41 +219,45 @@ void ipvlan_process_multicast(struct work_struct *work)
else
pkt_type
=
PACKET_MULTICAST
;
dlocal
=
false
;
rcu_read_lock
();
list_for_each_entry_rcu
(
ipvlan
,
&
port
->
ipvlans
,
pnode
)
{
if
(
hlocal
&&
(
ipvlan
->
dev
==
skb
->
dev
))
{
dlocal
=
true
;
if
(
tx_pkt
&&
(
ipvlan
->
dev
==
skb
->
dev
))
continue
;
}
if
(
!
test_bit
(
mac_hash
,
ipvlan
->
mac_filters
))
continue
;
if
(
!
(
ipvlan
->
dev
->
flags
&
IFF_UP
))
continue
;
ret
=
NET_RX_DROP
;
len
=
skb
->
len
+
ETH_HLEN
;
nskb
=
skb_clone
(
skb
,
GFP_ATOMIC
);
if
(
!
nskb
)
goto
acct
;
nskb
->
pkt_type
=
pkt_type
;
nskb
->
dev
=
ipvlan
->
dev
;
if
(
hlocal
)
ret
=
dev_forward_skb
(
ipvlan
->
dev
,
nskb
);
else
ret
=
netif_rx
(
nskb
);
acct:
local_bh_disable
();
if
(
nskb
)
{
consumed
=
true
;
nskb
->
pkt_type
=
pkt_type
;
nskb
->
dev
=
ipvlan
->
dev
;
if
(
tx_pkt
)
ret
=
dev_forward_skb
(
ipvlan
->
dev
,
nskb
);
else
ret
=
netif_rx
(
nskb
);
}
ipvlan_count_rx
(
ipvlan
,
len
,
ret
==
NET_RX_SUCCESS
,
true
);
local_bh_enable
();
}
rcu_read_unlock
();
if
(
dlocal
)
{
if
(
tx_pkt
)
{
/* If the packet originated here, send it out. */
skb
->
dev
=
port
->
dev
;
skb
->
pkt_type
=
pkt_type
;
dev_queue_xmit
(
skb
);
}
else
{
kfree_skb
(
skb
);
if
(
consumed
)
consume_skb
(
skb
);
else
kfree_skb
(
skb
);
}
if
(
dev
)
dev_put
(
dev
);
}
}
...
...
@@ -470,15 +477,24 @@ static int ipvlan_process_outbound(struct sk_buff *skb)
}
static
void
ipvlan_multicast_enqueue
(
struct
ipvl_port
*
port
,
struct
sk_buff
*
skb
)
struct
sk_buff
*
skb
,
bool
tx_pkt
)
{
if
(
skb
->
protocol
==
htons
(
ETH_P_PAUSE
))
{
kfree_skb
(
skb
);
return
;
}
/* Record that the deferred packet is from TX or RX path. By
* looking at mac-addresses on packet will lead to erronus decisions.
* (This would be true for a loopback-mode on master device or a
* hair-pin mode of the switch.)
*/
IPVL_SKB_CB
(
skb
)
->
tx_pkt
=
tx_pkt
;
spin_lock
(
&
port
->
backlog
.
lock
);
if
(
skb_queue_len
(
&
port
->
backlog
)
<
IPVLAN_QBACKLOG_LIMIT
)
{
if
(
skb
->
dev
)
dev_hold
(
skb
->
dev
);
__skb_queue_tail
(
&
port
->
backlog
,
skb
);
spin_unlock
(
&
port
->
backlog
.
lock
);
schedule_work
(
&
port
->
wq
);
...
...
@@ -537,7 +553,7 @@ static int ipvlan_xmit_mode_l2(struct sk_buff *skb, struct net_device *dev)
}
else
if
(
is_multicast_ether_addr
(
eth
->
h_dest
))
{
ipvlan_skb_crossing_ns
(
skb
,
NULL
);
ipvlan_multicast_enqueue
(
ipvlan
->
port
,
skb
);
ipvlan_multicast_enqueue
(
ipvlan
->
port
,
skb
,
true
);
return
NET_XMIT_SUCCESS
;
}
...
...
@@ -634,7 +650,7 @@ static rx_handler_result_t ipvlan_handle_mode_l2(struct sk_buff **pskb,
*/
if
(
nskb
)
{
ipvlan_skb_crossing_ns
(
nskb
,
NULL
);
ipvlan_multicast_enqueue
(
port
,
nskb
);
ipvlan_multicast_enqueue
(
port
,
nskb
,
false
);
}
}
}
else
{
...
...
drivers/net/ipvlan/ipvlan_main.c
浏览文件 @
399f157a
...
...
@@ -135,6 +135,7 @@ static int ipvlan_port_create(struct net_device *dev)
static
void
ipvlan_port_destroy
(
struct
net_device
*
dev
)
{
struct
ipvl_port
*
port
=
ipvlan_port_get_rtnl
(
dev
);
struct
sk_buff
*
skb
;
dev
->
priv_flags
&=
~
IFF_IPVLAN_MASTER
;
if
(
port
->
mode
==
IPVLAN_MODE_L3S
)
{
...
...
@@ -144,7 +145,11 @@ static void ipvlan_port_destroy(struct net_device *dev)
}
netdev_rx_handler_unregister
(
dev
);
cancel_work_sync
(
&
port
->
wq
);
__skb_queue_purge
(
&
port
->
backlog
);
while
((
skb
=
__skb_dequeue
(
&
port
->
backlog
))
!=
NULL
)
{
if
(
skb
->
dev
)
dev_put
(
skb
->
dev
);
kfree_skb
(
skb
);
}
kfree
(
port
);
}
...
...
fs/dax.c
浏览文件 @
399f157a
...
...
@@ -451,16 +451,37 @@ void dax_wake_mapping_entry_waiter(struct address_space *mapping,
__wake_up
(
wq
,
TASK_NORMAL
,
wake_all
?
0
:
1
,
&
key
);
}
static
int
__dax_invalidate_mapping_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
,
bool
trunc
)
{
int
ret
=
0
;
void
*
entry
;
struct
radix_tree_root
*
page_tree
=
&
mapping
->
page_tree
;
spin_lock_irq
(
&
mapping
->
tree_lock
);
entry
=
get_unlocked_mapping_entry
(
mapping
,
index
,
NULL
);
if
(
!
entry
||
!
radix_tree_exceptional_entry
(
entry
))
goto
out
;
if
(
!
trunc
&&
(
radix_tree_tag_get
(
page_tree
,
index
,
PAGECACHE_TAG_DIRTY
)
||
radix_tree_tag_get
(
page_tree
,
index
,
PAGECACHE_TAG_TOWRITE
)))
goto
out
;
radix_tree_delete
(
page_tree
,
index
);
mapping
->
nrexceptional
--
;
ret
=
1
;
out:
put_unlocked_mapping_entry
(
mapping
,
index
,
entry
);
spin_unlock_irq
(
&
mapping
->
tree_lock
);
return
ret
;
}
/*
* Delete exceptional DAX entry at @index from @mapping. Wait for radix tree
* entry to get unlocked before deleting it.
*/
int
dax_delete_mapping_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
)
{
void
*
entry
;
int
ret
=
__dax_invalidate_mapping_entry
(
mapping
,
index
,
true
)
;
spin_lock_irq
(
&
mapping
->
tree_lock
);
entry
=
get_unlocked_mapping_entry
(
mapping
,
index
,
NULL
);
/*
* This gets called from truncate / punch_hole path. As such, the caller
* must hold locks protecting against concurrent modifications of the
...
...
@@ -468,16 +489,46 @@ int dax_delete_mapping_entry(struct address_space *mapping, pgoff_t index)
* caller has seen exceptional entry for this index, we better find it
* at that index as well...
*/
if
(
WARN_ON_ONCE
(
!
entry
||
!
radix_tree_exceptional_entry
(
entry
)))
{
spin_unlock_irq
(
&
mapping
->
tree_lock
);
return
0
;
}
radix_tree_delete
(
&
mapping
->
page_tree
,
index
);
WARN_ON_ONCE
(
!
ret
);
return
ret
;
}
/*
* Invalidate exceptional DAX entry if easily possible. This handles DAX
* entries for invalidate_inode_pages() so we evict the entry only if we can
* do so without blocking.
*/
int
dax_invalidate_mapping_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
)
{
int
ret
=
0
;
void
*
entry
,
**
slot
;
struct
radix_tree_root
*
page_tree
=
&
mapping
->
page_tree
;
spin_lock_irq
(
&
mapping
->
tree_lock
);
entry
=
__radix_tree_lookup
(
page_tree
,
index
,
NULL
,
&
slot
);
if
(
!
entry
||
!
radix_tree_exceptional_entry
(
entry
)
||
slot_locked
(
mapping
,
slot
))
goto
out
;
if
(
radix_tree_tag_get
(
page_tree
,
index
,
PAGECACHE_TAG_DIRTY
)
||
radix_tree_tag_get
(
page_tree
,
index
,
PAGECACHE_TAG_TOWRITE
))
goto
out
;
radix_tree_delete
(
page_tree
,
index
);
mapping
->
nrexceptional
--
;
ret
=
1
;
out:
spin_unlock_irq
(
&
mapping
->
tree_lock
);
dax_wake_mapping_entry_waiter
(
mapping
,
index
,
entry
,
true
);
if
(
ret
)
dax_wake_mapping_entry_waiter
(
mapping
,
index
,
entry
,
true
);
return
ret
;
}
return
1
;
/*
* Invalidate exceptional DAX entry if it is clean.
*/
int
dax_invalidate_mapping_entry_sync
(
struct
address_space
*
mapping
,
pgoff_t
index
)
{
return
__dax_invalidate_mapping_entry
(
mapping
,
index
,
false
);
}
/*
...
...
@@ -488,15 +539,16 @@ int dax_delete_mapping_entry(struct address_space *mapping, pgoff_t index)
* otherwise it will simply fall out of the page cache under memory
* pressure without ever having been dirtied.
*/
static
int
dax_load_hole
(
struct
address_space
*
mapping
,
void
*
entry
,
static
int
dax_load_hole
(
struct
address_space
*
mapping
,
void
*
*
entry
,
struct
vm_fault
*
vmf
)
{
struct
page
*
page
;
int
ret
;
/* Hole page already exists? Return it... */
if
(
!
radix_tree_exceptional_entry
(
entry
))
{
vmf
->
page
=
entry
;
return
VM_FAULT_LOCKED
;
if
(
!
radix_tree_exceptional_entry
(
*
entry
))
{
page
=
*
entry
;
goto
out
;
}
/* This will replace locked radix tree entry with a hole page */
...
...
@@ -504,8 +556,17 @@ static int dax_load_hole(struct address_space *mapping, void *entry,
vmf
->
gfp_mask
|
__GFP_ZERO
);
if
(
!
page
)
return
VM_FAULT_OOM
;
out:
vmf
->
page
=
page
;
return
VM_FAULT_LOCKED
;
ret
=
finish_fault
(
vmf
);
vmf
->
page
=
NULL
;
*
entry
=
page
;
if
(
!
ret
)
{
/* Grab reference for PTE that is now referencing the page */
get_page
(
page
);
return
VM_FAULT_NOPAGE
;
}
return
ret
;
}
static
int
copy_user_dax
(
struct
block_device
*
bdev
,
sector_t
sector
,
size_t
size
,
...
...
@@ -934,6 +995,17 @@ dax_iomap_actor(struct inode *inode, loff_t pos, loff_t length, void *data,
if
(
WARN_ON_ONCE
(
iomap
->
type
!=
IOMAP_MAPPED
))
return
-
EIO
;
/*
* Write can allocate block for an area which has a hole page mapped
* into page tables. We have to tear down these mappings so that data
* written by write(2) is visible in mmap.
*/
if
((
iomap
->
flags
&
IOMAP_F_NEW
)
&&
inode
->
i_mapping
->
nrpages
)
{
invalidate_inode_pages2_range
(
inode
->
i_mapping
,
pos
>>
PAGE_SHIFT
,
(
end
-
1
)
>>
PAGE_SHIFT
);
}
while
(
pos
<
end
)
{
unsigned
offset
=
pos
&
(
PAGE_SIZE
-
1
);
struct
blk_dax_ctl
dax
=
{
0
};
...
...
@@ -992,23 +1064,6 @@ dax_iomap_rw(struct kiocb *iocb, struct iov_iter *iter,
if
(
iov_iter_rw
(
iter
)
==
WRITE
)
flags
|=
IOMAP_WRITE
;
/*
* Yes, even DAX files can have page cache attached to them: A zeroed
* page is inserted into the pagecache when we have to serve a write
* fault on a hole. It should never be dirtied and can simply be
* dropped from the pagecache once we get real data for the page.
*
* XXX: This is racy against mmap, and there's nothing we can do about
* it. We'll eventually need to shift this down even further so that
* we can check if we allocated blocks over a hole first.
*/
if
(
mapping
->
nrpages
)
{
ret
=
invalidate_inode_pages2_range
(
mapping
,
pos
>>
PAGE_SHIFT
,
(
pos
+
iov_iter_count
(
iter
)
-
1
)
>>
PAGE_SHIFT
);
WARN_ON_ONCE
(
ret
);
}
while
(
iov_iter_count
(
iter
))
{
ret
=
iomap_apply
(
inode
,
pos
,
iov_iter_count
(
iter
),
flags
,
ops
,
iter
,
dax_iomap_actor
);
...
...
@@ -1023,6 +1078,15 @@ dax_iomap_rw(struct kiocb *iocb, struct iov_iter *iter,
}
EXPORT_SYMBOL_GPL
(
dax_iomap_rw
);
static
int
dax_fault_return
(
int
error
)
{
if
(
error
==
0
)
return
VM_FAULT_NOPAGE
;
if
(
error
==
-
ENOMEM
)
return
VM_FAULT_OOM
;
return
VM_FAULT_SIGBUS
;
}
/**
* dax_iomap_fault - handle a page fault on a DAX file
* @vma: The virtual memory area where the fault occurred
...
...
@@ -1055,12 +1119,6 @@ int dax_iomap_fault(struct vm_area_struct *vma, struct vm_fault *vmf,
if
(
pos
>=
i_size_read
(
inode
))
return
VM_FAULT_SIGBUS
;
entry
=
grab_mapping_entry
(
mapping
,
vmf
->
pgoff
,
0
);
if
(
IS_ERR
(
entry
))
{
error
=
PTR_ERR
(
entry
);
goto
out
;
}
if
((
vmf
->
flags
&
FAULT_FLAG_WRITE
)
&&
!
vmf
->
cow_page
)
flags
|=
IOMAP_WRITE
;
...
...
@@ -1071,9 +1129,15 @@ int dax_iomap_fault(struct vm_area_struct *vma, struct vm_fault *vmf,
*/
error
=
ops
->
iomap_begin
(
inode
,
pos
,
PAGE_SIZE
,
flags
,
&
iomap
);
if
(
error
)
goto
unlock_entry
;
return
dax_fault_return
(
error
)
;
if
(
WARN_ON_ONCE
(
iomap
.
offset
+
iomap
.
length
<
pos
+
PAGE_SIZE
))
{
error
=
-
EIO
;
/* fs corruption? */
vmf_ret
=
dax_fault_return
(
-
EIO
);
/* fs corruption? */
goto
finish_iomap
;
}
entry
=
grab_mapping_entry
(
mapping
,
vmf
->
pgoff
,
0
);
if
(
IS_ERR
(
entry
))
{
vmf_ret
=
dax_fault_return
(
PTR_ERR
(
entry
));
goto
finish_iomap
;
}
...
...
@@ -1096,13 +1160,13 @@ int dax_iomap_fault(struct vm_area_struct *vma, struct vm_fault *vmf,
}
if
(
error
)
goto
finish_iomap
;
goto
error_unlock_entry
;
__SetPageUptodate
(
vmf
->
cow_page
);
vmf_ret
=
finish_fault
(
vmf
);
if
(
!
vmf_ret
)
vmf_ret
=
VM_FAULT_DONE_COW
;
goto
finish_iomap
;
goto
unlock_entry
;
}
switch
(
iomap
.
type
)
{
...
...
@@ -1114,12 +1178,15 @@ int dax_iomap_fault(struct vm_area_struct *vma, struct vm_fault *vmf,
}
error
=
dax_insert_mapping
(
mapping
,
iomap
.
bdev
,
sector
,
PAGE_SIZE
,
&
entry
,
vma
,
vmf
);
/* -EBUSY is fine, somebody else faulted on the same PTE */
if
(
error
==
-
EBUSY
)
error
=
0
;
break
;
case
IOMAP_UNWRITTEN
:
case
IOMAP_HOLE
:
if
(
!
(
vmf
->
flags
&
FAULT_FLAG_WRITE
))
{
vmf_ret
=
dax_load_hole
(
mapping
,
entry
,
vmf
);
break
;
vmf_ret
=
dax_load_hole
(
mapping
,
&
entry
,
vmf
);
goto
unlock_entry
;
}
/*FALLTHRU*/
default:
...
...
@@ -1128,31 +1195,25 @@ int dax_iomap_fault(struct vm_area_struct *vma, struct vm_fault *vmf,
break
;
}
error_unlock_entry:
vmf_ret
=
dax_fault_return
(
error
)
|
major
;
unlock_entry:
put_locked_mapping_entry
(
mapping
,
vmf
->
pgoff
,
entry
);
finish_iomap:
if
(
ops
->
iomap_end
)
{
if
(
error
||
(
vmf_ret
&
VM_FAULT_ERROR
))
{
/* keep previous error */
ops
->
iomap_end
(
inode
,
pos
,
PAGE_SIZE
,
0
,
flags
,
&
iomap
);
}
else
{
error
=
ops
->
iomap_end
(
inode
,
pos
,
PAGE_SIZE
,
PAGE_SIZE
,
flags
,
&
iomap
);
}
}
unlock_entry:
if
(
vmf_ret
!=
VM_FAULT_LOCKED
||
error
)
put_locked_mapping_entry
(
mapping
,
vmf
->
pgoff
,
entry
);
out:
if
(
error
==
-
ENOMEM
)
return
VM_FAULT_OOM
|
major
;
/* -EBUSY is fine, somebody else faulted on the same PTE */
if
(
error
<
0
&&
error
!=
-
EBUSY
)
return
VM_FAULT_SIGBUS
|
major
;
if
(
vmf_ret
)
{
WARN_ON_ONCE
(
error
);
/* -EBUSY from ops->iomap_end? */
return
vmf_ret
;
int
copied
=
PAGE_SIZE
;
if
(
vmf_ret
&
VM_FAULT_ERROR
)
copied
=
0
;
/*
* The fault is done by now and there's no way back (other
* thread may be already happily using PTE we have installed).
* Just ignore error from ->iomap_end since we cannot do much
* with it.
*/
ops
->
iomap_end
(
inode
,
pos
,
PAGE_SIZE
,
copied
,
flags
,
&
iomap
);
}
return
VM_FAULT_NOPAGE
|
major
;
return
vmf_ret
;
}
EXPORT_SYMBOL_GPL
(
dax_iomap_fault
);
...
...
@@ -1276,16 +1337,6 @@ int dax_iomap_pmd_fault(struct vm_area_struct *vma, unsigned long address,
if
((
pgoff
|
PG_PMD_COLOUR
)
>
max_pgoff
)
goto
fallback
;
/*
* grab_mapping_entry() will make sure we get a 2M empty entry, a DAX
* PMD or a HZP entry. If it can't (because a 4k page is already in
* the tree, for instance), it will return -EEXIST and we just fall
* back to 4k entries.
*/
entry
=
grab_mapping_entry
(
mapping
,
pgoff
,
RADIX_DAX_PMD
);
if
(
IS_ERR
(
entry
))
goto
fallback
;
/*
* Note that we don't use iomap_apply here. We aren't doing I/O, only
* setting up a mapping, so really we're using iomap_begin() as a way
...
...
@@ -1294,10 +1345,21 @@ int dax_iomap_pmd_fault(struct vm_area_struct *vma, unsigned long address,
pos
=
(
loff_t
)
pgoff
<<
PAGE_SHIFT
;
error
=
ops
->
iomap_begin
(
inode
,
pos
,
PMD_SIZE
,
iomap_flags
,
&
iomap
);
if
(
error
)
goto
unlock_entry
;
goto
fallback
;
if
(
iomap
.
offset
+
iomap
.
length
<
pos
+
PMD_SIZE
)
goto
finish_iomap
;
/*
* grab_mapping_entry() will make sure we get a 2M empty entry, a DAX
* PMD or a HZP entry. If it can't (because a 4k page is already in
* the tree, for instance), it will return -EEXIST and we just fall
* back to 4k entries.
*/
entry
=
grab_mapping_entry
(
mapping
,
pgoff
,
RADIX_DAX_PMD
);
if
(
IS_ERR
(
entry
))
goto
finish_iomap
;
vmf
.
pgoff
=
pgoff
;
vmf
.
flags
=
flags
;
vmf
.
gfp_mask
=
mapping_gfp_mask
(
mapping
)
|
__GFP_IO
;
...
...
@@ -1310,7 +1372,7 @@ int dax_iomap_pmd_fault(struct vm_area_struct *vma, unsigned long address,
case
IOMAP_UNWRITTEN
:
case
IOMAP_HOLE
:
if
(
WARN_ON_ONCE
(
write
))
goto
finish_iomap
;
goto
unlock_entry
;
result
=
dax_pmd_load_hole
(
vma
,
pmd
,
&
vmf
,
address
,
&
iomap
,
&
entry
);
break
;
...
...
@@ -1319,20 +1381,23 @@ int dax_iomap_pmd_fault(struct vm_area_struct *vma, unsigned long address,
break
;
}
unlock_entry:
put_locked_mapping_entry
(
mapping
,
pgoff
,
entry
);
finish_iomap:
if
(
ops
->
iomap_end
)
{
if
(
result
==
VM_FAULT_FALLBACK
)
{
ops
->
iomap_end
(
inode
,
pos
,
PMD_SIZE
,
0
,
iomap_flags
,
&
iomap
);
}
else
{
error
=
ops
->
iomap_end
(
inode
,
pos
,
PMD_SIZE
,
PMD_SIZE
,
iomap_flags
,
&
iomap
);
if
(
error
)
result
=
VM_FAULT_FALLBACK
;
}
int
copied
=
PMD_SIZE
;
if
(
result
==
VM_FAULT_FALLBACK
)
copied
=
0
;
/*
* The fault is done by now and there's no way back (other
* thread may be already happily using PMD we have installed).
* Just ignore error from ->iomap_end since we cannot do much
* with it.
*/
ops
->
iomap_end
(
inode
,
pos
,
PMD_SIZE
,
copied
,
iomap_flags
,
&
iomap
);
}
unlock_entry:
put_locked_mapping_entry
(
mapping
,
pgoff
,
entry
);
fallback:
if
(
result
==
VM_FAULT_FALLBACK
)
{
split_huge_pmd
(
vma
,
pmd
,
address
);
...
...
fs/ext2/inode.c
浏览文件 @
399f157a
...
...
@@ -751,9 +751,8 @@ static int ext2_get_blocks(struct inode *inode,
mutex_unlock
(
&
ei
->
truncate_mutex
);
goto
cleanup
;
}
}
else
{
*
new
=
true
;
}
*
new
=
true
;
ext2_splice_branch
(
inode
,
iblock
,
partial
,
indirect_blks
,
count
);
mutex_unlock
(
&
ei
->
truncate_mutex
);
...
...
fs/ext4/file.c
浏览文件 @
399f157a
...
...
@@ -258,7 +258,6 @@ ext4_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
static
int
ext4_dax_fault
(
struct
vm_area_struct
*
vma
,
struct
vm_fault
*
vmf
)
{
int
result
;
handle_t
*
handle
=
NULL
;
struct
inode
*
inode
=
file_inode
(
vma
->
vm_file
);
struct
super_block
*
sb
=
inode
->
i_sb
;
bool
write
=
vmf
->
flags
&
FAULT_FLAG_WRITE
;
...
...
@@ -266,24 +265,12 @@ static int ext4_dax_fault(struct vm_area_struct *vma, struct vm_fault *vmf)
if
(
write
)
{
sb_start_pagefault
(
sb
);
file_update_time
(
vma
->
vm_file
);
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
handle
=
ext4_journal_start_sb
(
sb
,
EXT4_HT_WRITE_PAGE
,
EXT4_DATA_TRANS_BLOCKS
(
sb
));
}
else
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
if
(
IS_ERR
(
handle
))
result
=
VM_FAULT_SIGBUS
;
else
result
=
dax_iomap_fault
(
vma
,
vmf
,
&
ext4_iomap_ops
);
if
(
write
)
{
if
(
!
IS_ERR
(
handle
))
ext4_journal_stop
(
handle
);
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
}
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
result
=
dax_iomap_fault
(
vma
,
vmf
,
&
ext4_iomap_ops
);
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
if
(
write
)
sb_end_pagefault
(
sb
);
}
else
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
return
result
;
}
...
...
@@ -292,7 +279,6 @@ static int ext4_dax_pmd_fault(struct vm_area_struct *vma, unsigned long addr,
pmd_t
*
pmd
,
unsigned
int
flags
)
{
int
result
;
handle_t
*
handle
=
NULL
;
struct
inode
*
inode
=
file_inode
(
vma
->
vm_file
);
struct
super_block
*
sb
=
inode
->
i_sb
;
bool
write
=
flags
&
FAULT_FLAG_WRITE
;
...
...
@@ -300,27 +286,13 @@ static int ext4_dax_pmd_fault(struct vm_area_struct *vma, unsigned long addr,
if
(
write
)
{
sb_start_pagefault
(
sb
);
file_update_time
(
vma
->
vm_file
);
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
handle
=
ext4_journal_start_sb
(
sb
,
EXT4_HT_WRITE_PAGE
,
ext4_chunk_trans_blocks
(
inode
,
PMD_SIZE
/
PAGE_SIZE
));
}
else
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
if
(
IS_ERR
(
handle
))
result
=
VM_FAULT_SIGBUS
;
else
{
result
=
dax_iomap_pmd_fault
(
vma
,
addr
,
pmd
,
flags
,
&
ext4_iomap_ops
);
}
if
(
write
)
{
if
(
!
IS_ERR
(
handle
))
ext4_journal_stop
(
handle
);
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
down_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
result
=
dax_iomap_pmd_fault
(
vma
,
addr
,
pmd
,
flags
,
&
ext4_iomap_ops
);
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
if
(
write
)
sb_end_pagefault
(
sb
);
}
else
up_read
(
&
EXT4_I
(
inode
)
->
i_mmap_sem
);
return
result
;
}
...
...
include/linux/dax.h
浏览文件 @
399f157a
...
...
@@ -41,6 +41,9 @@ ssize_t dax_iomap_rw(struct kiocb *iocb, struct iov_iter *iter,
int
dax_iomap_fault
(
struct
vm_area_struct
*
vma
,
struct
vm_fault
*
vmf
,
struct
iomap_ops
*
ops
);
int
dax_delete_mapping_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
);
int
dax_invalidate_mapping_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
);
int
dax_invalidate_mapping_entry_sync
(
struct
address_space
*
mapping
,
pgoff_t
index
);
void
dax_wake_mapping_entry_waiter
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
,
bool
wake_all
);
...
...
include/linux/filter.h
浏览文件 @
399f157a
...
...
@@ -610,7 +610,6 @@ bool bpf_helper_changes_pkt_data(void *func);
struct
bpf_prog
*
bpf_patch_insn_single
(
struct
bpf_prog
*
prog
,
u32
off
,
const
struct
bpf_insn
*
patch
,
u32
len
);
void
bpf_warn_invalid_xdp_action
(
u32
act
);
void
bpf_warn_invalid_xdp_buffer
(
void
);
#ifdef CONFIG_BPF_JIT
extern
int
bpf_jit_enable
;
...
...
include/linux/mm.h
浏览文件 @
399f157a
...
...
@@ -76,6 +76,10 @@ extern int mmap_rnd_compat_bits __read_mostly;
#define page_to_virt(x) __va(PFN_PHYS(page_to_pfn(x)))
#endif
#ifndef lm_alias
#define lm_alias(x) __va(__pa_symbol(x))
#endif
/*
* To prevent common memory management code establishing
* a zero page mapping on a read fault.
...
...
include/linux/page-flags.h
浏览文件 @
399f157a
...
...
@@ -73,13 +73,13 @@
*/
enum
pageflags
{
PG_locked
,
/* Page is locked. Don't touch. */
PG_waiters
,
/* Page has waiters, check its waitqueue */
PG_error
,
PG_referenced
,
PG_uptodate
,
PG_dirty
,
PG_lru
,
PG_active
,
PG_waiters
,
/* Page has waiters, check its waitqueue. Must be bit #7 and in the same byte as "PG_locked" */
PG_slab
,
PG_owner_priv_1
,
/* Owner use. If pagecache, fs may use*/
PG_arch_1
,
...
...
include/net/netns/ipv4.h
浏览文件 @
399f157a
...
...
@@ -110,6 +110,7 @@ struct netns_ipv4 {
int
sysctl_tcp_orphan_retries
;
int
sysctl_tcp_fin_timeout
;
unsigned
int
sysctl_tcp_notsent_lowat
;
int
sysctl_tcp_tw_reuse
;
int
sysctl_igmp_max_memberships
;
int
sysctl_igmp_max_msf
;
...
...
include/net/tcp.h
浏览文件 @
399f157a
...
...
@@ -252,7 +252,6 @@ extern int sysctl_tcp_wmem[3];
extern
int
sysctl_tcp_rmem
[
3
];
extern
int
sysctl_tcp_app_win
;
extern
int
sysctl_tcp_adv_win_scale
;
extern
int
sysctl_tcp_tw_reuse
;
extern
int
sysctl_tcp_frto
;
extern
int
sysctl_tcp_low_latency
;
extern
int
sysctl_tcp_nometrics_save
;
...
...
kernel/cpu.c
浏览文件 @
399f157a
...
...
@@ -1471,6 +1471,7 @@ int __cpuhp_setup_state(enum cpuhp_state state,
bool
multi_instance
)
{
int
cpu
,
ret
=
0
;
bool
dynstate
;
if
(
cpuhp_cb_check
(
state
)
||
!
name
)
return
-
EINVAL
;
...
...
@@ -1480,6 +1481,12 @@ int __cpuhp_setup_state(enum cpuhp_state state,
ret
=
cpuhp_store_callbacks
(
state
,
name
,
startup
,
teardown
,
multi_instance
);
dynstate
=
state
==
CPUHP_AP_ONLINE_DYN
;
if
(
ret
>
0
&&
dynstate
)
{
state
=
ret
;
ret
=
0
;
}
if
(
ret
||
!
invoke
||
!
startup
)
goto
out
;
...
...
@@ -1508,7 +1515,7 @@ int __cpuhp_setup_state(enum cpuhp_state state,
* If the requested state is CPUHP_AP_ONLINE_DYN, return the
* dynamically allocated state in case of success.
*/
if
(
!
ret
&&
state
==
CPUHP_AP_ONLINE_DYN
)
if
(
!
ret
&&
dynstate
)
return
state
;
return
ret
;
}
...
...
kernel/kexec_core.c
浏览文件 @
399f157a
...
...
@@ -1399,7 +1399,7 @@ void __weak arch_crash_save_vmcoreinfo(void)
phys_addr_t
__weak
paddr_vmcoreinfo_note
(
void
)
{
return
__pa
((
unsigned
long
)(
char
*
)
&
vmcoreinfo_note
);
return
__pa
_symbol
((
unsigned
long
)(
char
*
)
&
vmcoreinfo_note
);
}
static
int
__init
crash_save_vmcoreinfo_init
(
void
)
...
...
lib/Kconfig.debug
浏览文件 @
399f157a
...
...
@@ -622,9 +622,12 @@ config DEBUG_VM_PGFLAGS
If unsure, say N.
config ARCH_HAS_DEBUG_VIRTUAL
bool
config DEBUG_VIRTUAL
bool "Debug VM translations"
depends on DEBUG_KERNEL &&
X86
depends on DEBUG_KERNEL &&
ARCH_HAS_DEBUG_VIRTUAL
help
Enable some costly sanity checks in virtual to page code. This can
catch mistakes with virt_to_page() and friends.
...
...
mm/cma.c
浏览文件 @
399f157a
...
...
@@ -235,18 +235,13 @@ int __init cma_declare_contiguous(phys_addr_t base,
phys_addr_t
highmem_start
;
int
ret
=
0
;
#ifdef CONFIG_X86
/*
* high_memory isn't direct mapped memory so retrieving its physical
* address isn't appropriate. But it would be useful to check the
* physical address of the highmem boundary so it's justifiable to get
* the physical address from it. On x86 there is a validation check for
* this case, so the following workaround is needed to avoid it.
* We can't use __pa(high_memory) directly, since high_memory
* isn't a valid direct map VA, and DEBUG_VIRTUAL will (validly)
* complain. Find the boundary by adding one to the last valid
* address.
*/
highmem_start
=
__pa_nodebug
(
high_memory
);
#else
highmem_start
=
__pa
(
high_memory
);
#endif
highmem_start
=
__pa
(
high_memory
-
1
)
+
1
;
pr_debug
(
"%s(size %pa, base %pa, limit %pa alignment %pa)
\n
"
,
__func__
,
&
size
,
&
base
,
&
limit
,
&
alignment
);
...
...
mm/filemap.c
浏览文件 @
399f157a
...
...
@@ -912,6 +912,29 @@ void add_page_wait_queue(struct page *page, wait_queue_t *waiter)
}
EXPORT_SYMBOL_GPL
(
add_page_wait_queue
);
#ifndef clear_bit_unlock_is_negative_byte
/*
* PG_waiters is the high bit in the same byte as PG_lock.
*
* On x86 (and on many other architectures), we can clear PG_lock and
* test the sign bit at the same time. But if the architecture does
* not support that special operation, we just do this all by hand
* instead.
*
* The read of PG_waiters has to be after (or concurrently with) PG_locked
* being cleared, but a memory barrier should be unneccssary since it is
* in the same byte as PG_locked.
*/
static
inline
bool
clear_bit_unlock_is_negative_byte
(
long
nr
,
volatile
void
*
mem
)
{
clear_bit_unlock
(
nr
,
mem
);
/* smp_mb__after_atomic(); */
return
test_bit
(
PG_waiters
,
mem
);
}
#endif
/**
* unlock_page - unlock a locked page
* @page: the page
...
...
@@ -921,16 +944,19 @@ EXPORT_SYMBOL_GPL(add_page_wait_queue);
* mechanism between PageLocked pages and PageWriteback pages is shared.
* But that's OK - sleepers in wait_on_page_writeback() just go back to sleep.
*
* The mb is necessary to enforce ordering between the clear_bit and the read
* of the waitqueue (to avoid SMP races with a parallel wait_on_page_locked()).
* Note that this depends on PG_waiters being the sign bit in the byte
* that contains PG_locked - thus the BUILD_BUG_ON(). That allows us to
* clear the PG_locked bit and test PG_waiters at the same time fairly
* portably (architectures that do LL/SC can test any bit, while x86 can
* test the sign bit).
*/
void
unlock_page
(
struct
page
*
page
)
{
BUILD_BUG_ON
(
PG_waiters
!=
7
);
page
=
compound_head
(
page
);
VM_BUG_ON_PAGE
(
!
PageLocked
(
page
),
page
);
clear_bit_unlock
(
PG_locked
,
&
page
->
flags
);
smp_mb__after_atomic
();
wake_up_page
(
page
,
PG_locked
);
if
(
clear_bit_unlock_is_negative_byte
(
PG_locked
,
&
page
->
flags
))
wake_up_page_bit
(
page
,
PG_locked
);
}
EXPORT_SYMBOL
(
unlock_page
);
...
...
mm/kasan/kasan_init.c
浏览文件 @
399f157a
...
...
@@ -15,6 +15,7 @@
#include <linux/kasan.h>
#include <linux/kernel.h>
#include <linux/memblock.h>
#include <linux/mm.h>
#include <linux/pfn.h>
#include <asm/page.h>
...
...
@@ -49,7 +50,7 @@ static void __init zero_pte_populate(pmd_t *pmd, unsigned long addr,
pte_t
*
pte
=
pte_offset_kernel
(
pmd
,
addr
);
pte_t
zero_pte
;
zero_pte
=
pfn_pte
(
PFN_DOWN
(
__pa
(
kasan_zero_page
)),
PAGE_KERNEL
);
zero_pte
=
pfn_pte
(
PFN_DOWN
(
__pa
_symbol
(
kasan_zero_page
)),
PAGE_KERNEL
);
zero_pte
=
pte_wrprotect
(
zero_pte
);
while
(
addr
+
PAGE_SIZE
<=
end
)
{
...
...
@@ -69,7 +70,7 @@ static void __init zero_pmd_populate(pud_t *pud, unsigned long addr,
next
=
pmd_addr_end
(
addr
,
end
);
if
(
IS_ALIGNED
(
addr
,
PMD_SIZE
)
&&
end
-
addr
>=
PMD_SIZE
)
{
pmd_populate_kernel
(
&
init_mm
,
pmd
,
kasan_zero_pte
);
pmd_populate_kernel
(
&
init_mm
,
pmd
,
lm_alias
(
kasan_zero_pte
)
);
continue
;
}
...
...
@@ -92,9 +93,9 @@ static void __init zero_pud_populate(pgd_t *pgd, unsigned long addr,
if
(
IS_ALIGNED
(
addr
,
PUD_SIZE
)
&&
end
-
addr
>=
PUD_SIZE
)
{
pmd_t
*
pmd
;
pud_populate
(
&
init_mm
,
pud
,
kasan_zero_pmd
);
pud_populate
(
&
init_mm
,
pud
,
lm_alias
(
kasan_zero_pmd
)
);
pmd
=
pmd_offset
(
pud
,
addr
);
pmd_populate_kernel
(
&
init_mm
,
pmd
,
kasan_zero_pte
);
pmd_populate_kernel
(
&
init_mm
,
pmd
,
lm_alias
(
kasan_zero_pte
)
);
continue
;
}
...
...
@@ -135,11 +136,11 @@ void __init kasan_populate_zero_shadow(const void *shadow_start,
* puds,pmds, so pgd_populate(), pud_populate()
* is noops.
*/
pgd_populate
(
&
init_mm
,
pgd
,
kasan_zero_pud
);
pgd_populate
(
&
init_mm
,
pgd
,
lm_alias
(
kasan_zero_pud
)
);
pud
=
pud_offset
(
pgd
,
addr
);
pud_populate
(
&
init_mm
,
pud
,
kasan_zero_pmd
);
pud_populate
(
&
init_mm
,
pud
,
lm_alias
(
kasan_zero_pmd
)
);
pmd
=
pmd_offset
(
pud
,
addr
);
pmd_populate_kernel
(
&
init_mm
,
pmd
,
kasan_zero_pte
);
pmd_populate_kernel
(
&
init_mm
,
pmd
,
lm_alias
(
kasan_zero_pte
)
);
continue
;
}
...
...
mm/truncate.c
浏览文件 @
399f157a
...
...
@@ -24,20 +24,12 @@
#include <linux/rmap.h>
#include "internal.h"
static
void
clear_
exceptional_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
)
static
void
clear_
shadow_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
)
{
struct
radix_tree_node
*
node
;
void
**
slot
;
/* Handled by shmem itself */
if
(
shmem_mapping
(
mapping
))
return
;
if
(
dax_mapping
(
mapping
))
{
dax_delete_mapping_entry
(
mapping
,
index
);
return
;
}
spin_lock_irq
(
&
mapping
->
tree_lock
);
/*
* Regular page slots are stabilized by the page lock even
...
...
@@ -55,6 +47,56 @@ static void clear_exceptional_entry(struct address_space *mapping,
spin_unlock_irq
(
&
mapping
->
tree_lock
);
}
/*
* Unconditionally remove exceptional entry. Usually called from truncate path.
*/
static
void
truncate_exceptional_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
)
{
/* Handled by shmem itself */
if
(
shmem_mapping
(
mapping
))
return
;
if
(
dax_mapping
(
mapping
))
{
dax_delete_mapping_entry
(
mapping
,
index
);
return
;
}
clear_shadow_entry
(
mapping
,
index
,
entry
);
}
/*
* Invalidate exceptional entry if easily possible. This handles exceptional
* entries for invalidate_inode_pages() so for DAX it evicts only unlocked and
* clean entries.
*/
static
int
invalidate_exceptional_entry
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
)
{
/* Handled by shmem itself */
if
(
shmem_mapping
(
mapping
))
return
1
;
if
(
dax_mapping
(
mapping
))
return
dax_invalidate_mapping_entry
(
mapping
,
index
);
clear_shadow_entry
(
mapping
,
index
,
entry
);
return
1
;
}
/*
* Invalidate exceptional entry if clean. This handles exceptional entries for
* invalidate_inode_pages2() so for DAX it evicts only clean entries.
*/
static
int
invalidate_exceptional_entry2
(
struct
address_space
*
mapping
,
pgoff_t
index
,
void
*
entry
)
{
/* Handled by shmem itself */
if
(
shmem_mapping
(
mapping
))
return
1
;
if
(
dax_mapping
(
mapping
))
return
dax_invalidate_mapping_entry_sync
(
mapping
,
index
);
clear_shadow_entry
(
mapping
,
index
,
entry
);
return
1
;
}
/**
* do_invalidatepage - invalidate part or all of a page
* @page: the page which is affected
...
...
@@ -262,7 +304,8 @@ void truncate_inode_pages_range(struct address_space *mapping,
break
;
if
(
radix_tree_exceptional_entry
(
page
))
{
clear_exceptional_entry
(
mapping
,
index
,
page
);
truncate_exceptional_entry
(
mapping
,
index
,
page
);
continue
;
}
...
...
@@ -351,7 +394,8 @@ void truncate_inode_pages_range(struct address_space *mapping,
}
if
(
radix_tree_exceptional_entry
(
page
))
{
clear_exceptional_entry
(
mapping
,
index
,
page
);
truncate_exceptional_entry
(
mapping
,
index
,
page
);
continue
;
}
...
...
@@ -470,7 +514,8 @@ unsigned long invalidate_mapping_pages(struct address_space *mapping,
break
;
if
(
radix_tree_exceptional_entry
(
page
))
{
clear_exceptional_entry
(
mapping
,
index
,
page
);
invalidate_exceptional_entry
(
mapping
,
index
,
page
);
continue
;
}
...
...
@@ -592,7 +637,9 @@ int invalidate_inode_pages2_range(struct address_space *mapping,
break
;
if
(
radix_tree_exceptional_entry
(
page
))
{
clear_exceptional_entry
(
mapping
,
index
,
page
);
if
(
!
invalidate_exceptional_entry2
(
mapping
,
index
,
page
))
ret
=
-
EBUSY
;
continue
;
}
...
...
mm/usercopy.c
浏览文件 @
399f157a
...
...
@@ -108,13 +108,13 @@ static inline const char *check_kernel_text_object(const void *ptr,
* __pa() is not just the reverse of __va(). This can be detected
* and checked:
*/
textlow_linear
=
(
unsigned
long
)
__va
(
__pa
(
textlow
)
);
textlow_linear
=
(
unsigned
long
)
lm_alias
(
textlow
);
/* No different mapping: we're done. */
if
(
textlow_linear
==
textlow
)
return
NULL
;
/* Check the secondary mapping... */
texthigh_linear
=
(
unsigned
long
)
__va
(
__pa
(
texthigh
)
);
texthigh_linear
=
(
unsigned
long
)
lm_alias
(
texthigh
);
if
(
overlaps
(
ptr
,
n
,
textlow_linear
,
texthigh_linear
))
return
"<linear kernel text>"
;
...
...
net/core/filter.c
浏览文件 @
399f157a
...
...
@@ -2972,12 +2972,6 @@ void bpf_warn_invalid_xdp_action(u32 act)
}
EXPORT_SYMBOL_GPL
(
bpf_warn_invalid_xdp_action
);
void
bpf_warn_invalid_xdp_buffer
(
void
)
{
WARN_ONCE
(
1
,
"Illegal XDP buffer encountered, expect throughput degradation
\n
"
);
}
EXPORT_SYMBOL_GPL
(
bpf_warn_invalid_xdp_buffer
);
static
u32
sk_filter_convert_ctx_access
(
enum
bpf_access_type
type
,
int
dst_reg
,
int
src_reg
,
int
ctx_off
,
struct
bpf_insn
*
insn_buf
,
...
...
net/ipv4/sysctl_net_ipv4.c
浏览文件 @
399f157a
...
...
@@ -432,13 +432,6 @@ static struct ctl_table ipv4_table[] = {
.
extra1
=
&
tcp_adv_win_scale_min
,
.
extra2
=
&
tcp_adv_win_scale_max
,
},
{
.
procname
=
"tcp_tw_reuse"
,
.
data
=
&
sysctl_tcp_tw_reuse
,
.
maxlen
=
sizeof
(
int
),
.
mode
=
0644
,
.
proc_handler
=
proc_dointvec
},
{
.
procname
=
"tcp_frto"
,
.
data
=
&
sysctl_tcp_frto
,
...
...
@@ -960,6 +953,13 @@ static struct ctl_table ipv4_net_table[] = {
.
mode
=
0644
,
.
proc_handler
=
proc_dointvec
,
},
{
.
procname
=
"tcp_tw_reuse"
,
.
data
=
&
init_net
.
ipv4
.
sysctl_tcp_tw_reuse
,
.
maxlen
=
sizeof
(
int
),
.
mode
=
0644
,
.
proc_handler
=
proc_dointvec
},
#ifdef CONFIG_IP_ROUTE_MULTIPATH
{
.
procname
=
"fib_multipath_use_neigh"
,
...
...
net/ipv4/tcp_ipv4.c
浏览文件 @
399f157a
...
...
@@ -84,7 +84,6 @@
#include <crypto/hash.h>
#include <linux/scatterlist.h>
int
sysctl_tcp_tw_reuse
__read_mostly
;
int
sysctl_tcp_low_latency
__read_mostly
;
#ifdef CONFIG_TCP_MD5SIG
...
...
@@ -120,7 +119,7 @@ int tcp_twsk_unique(struct sock *sk, struct sock *sktw, void *twp)
and use initial timestamp retrieved from peer table.
*/
if
(
tcptw
->
tw_ts_recent_stamp
&&
(
!
twp
||
(
sysctl_tcp_tw_reuse
&&
(
!
twp
||
(
s
ock_net
(
sk
)
->
ipv4
.
s
ysctl_tcp_tw_reuse
&&
get_seconds
()
-
tcptw
->
tw_ts_recent_stamp
>
1
)))
{
tp
->
write_seq
=
tcptw
->
tw_snd_nxt
+
65535
+
2
;
if
(
tp
->
write_seq
==
0
)
...
...
@@ -2456,6 +2455,7 @@ static int __net_init tcp_sk_init(struct net *net)
net
->
ipv4
.
sysctl_tcp_orphan_retries
=
0
;
net
->
ipv4
.
sysctl_tcp_fin_timeout
=
TCP_FIN_TIMEOUT
;
net
->
ipv4
.
sysctl_tcp_notsent_lowat
=
UINT_MAX
;
net
->
ipv4
.
sysctl_tcp_tw_reuse
=
0
;
return
0
;
fail:
...
...
net/openvswitch/datapath.c
浏览文件 @
399f157a
...
...
@@ -606,7 +606,6 @@ static int ovs_packet_cmd_execute(struct sk_buff *skb, struct genl_info *info)
rcu_assign_pointer
(
flow
->
sf_acts
,
acts
);
packet
->
priority
=
flow
->
key
.
phy
.
priority
;
packet
->
mark
=
flow
->
key
.
phy
.
skb_mark
;
packet
->
protocol
=
flow
->
key
.
eth
.
type
;
rcu_read_lock
();
dp
=
get_dp_rcu
(
net
,
ovs_header
->
dp_ifindex
);
...
...
net/openvswitch/flow.c
浏览文件 @
399f157a
...
...
@@ -312,7 +312,8 @@ static bool icmp6hdr_ok(struct sk_buff *skb)
* Returns 0 if it encounters a non-vlan or incomplete packet.
* Returns 1 after successfully parsing vlan tag.
*/
static
int
parse_vlan_tag
(
struct
sk_buff
*
skb
,
struct
vlan_head
*
key_vh
)
static
int
parse_vlan_tag
(
struct
sk_buff
*
skb
,
struct
vlan_head
*
key_vh
,
bool
untag_vlan
)
{
struct
vlan_head
*
vh
=
(
struct
vlan_head
*
)
skb
->
data
;
...
...
@@ -330,7 +331,20 @@ static int parse_vlan_tag(struct sk_buff *skb, struct vlan_head *key_vh)
key_vh
->
tci
=
vh
->
tci
|
htons
(
VLAN_TAG_PRESENT
);
key_vh
->
tpid
=
vh
->
tpid
;
__skb_pull
(
skb
,
sizeof
(
struct
vlan_head
));
if
(
unlikely
(
untag_vlan
))
{
int
offset
=
skb
->
data
-
skb_mac_header
(
skb
);
u16
tci
;
int
err
;
__skb_push
(
skb
,
offset
);
err
=
__skb_vlan_pop
(
skb
,
&
tci
);
__skb_pull
(
skb
,
offset
);
if
(
err
)
return
err
;
__vlan_hwaccel_put_tag
(
skb
,
key_vh
->
tpid
,
tci
);
}
else
{
__skb_pull
(
skb
,
sizeof
(
struct
vlan_head
));
}
return
1
;
}
...
...
@@ -351,13 +365,13 @@ static int parse_vlan(struct sk_buff *skb, struct sw_flow_key *key)
key
->
eth
.
vlan
.
tpid
=
skb
->
vlan_proto
;
}
else
{
/* Parse outer vlan tag in the non-accelerated case. */
res
=
parse_vlan_tag
(
skb
,
&
key
->
eth
.
vlan
);
res
=
parse_vlan_tag
(
skb
,
&
key
->
eth
.
vlan
,
true
);
if
(
res
<=
0
)
return
res
;
}
/* Parse inner vlan tag. */
res
=
parse_vlan_tag
(
skb
,
&
key
->
eth
.
cvlan
);
res
=
parse_vlan_tag
(
skb
,
&
key
->
eth
.
cvlan
,
false
);
if
(
res
<=
0
)
return
res
;
...
...
@@ -800,29 +814,15 @@ int ovs_flow_key_extract_userspace(struct net *net, const struct nlattr *attr,
if
(
err
)
return
err
;
if
(
ovs_key_mac_proto
(
key
)
==
MAC_PROTO_NONE
)
{
/* key_extract assumes that skb->protocol is set-up for
* layer 3 packets which is the case for other callers,
* in particular packets recieved from the network stack.
* Here the correct value can be set from the metadata
* extracted above.
*/
skb
->
protocol
=
key
->
eth
.
type
;
}
else
{
struct
ethhdr
*
eth
;
skb_reset_mac_header
(
skb
);
eth
=
eth_hdr
(
skb
);
/* Normally, setting the skb 'protocol' field would be
* handled by a call to eth_type_trans(), but it assumes
* there's a sending device, which we may not have.
*/
if
(
eth_proto_is_802_3
(
eth
->
h_proto
))
skb
->
protocol
=
eth
->
h_proto
;
else
skb
->
protocol
=
htons
(
ETH_P_802_2
);
}
/* key_extract assumes that skb->protocol is set-up for
* layer 3 packets which is the case for other callers,
* in particular packets received from the network stack.
* Here the correct value can be set from the metadata
* extracted above.
* For L2 packet key eth type would be zero. skb protocol
* would be set to correct value later during key-extact.
*/
skb
->
protocol
=
key
->
eth
.
type
;
return
key_extract
(
skb
,
key
);
}
net/sched/cls_api.c
浏览文件 @
399f157a
...
...
@@ -148,13 +148,15 @@ static int tc_ctl_tfilter(struct sk_buff *skb, struct nlmsghdr *n)
unsigned
long
cl
;
unsigned
long
fh
;
int
err
;
int
tp_created
=
0
;
int
tp_created
;
if
((
n
->
nlmsg_type
!=
RTM_GETTFILTER
)
&&
!
netlink_ns_capable
(
skb
,
net
->
user_ns
,
CAP_NET_ADMIN
))
return
-
EPERM
;
replay:
tp_created
=
0
;
err
=
nlmsg_parse
(
n
,
sizeof
(
*
t
),
tca
,
TCA_MAX
,
NULL
);
if
(
err
<
0
)
return
err
;
...
...
net/tipc/socket.c
浏览文件 @
399f157a
...
...
@@ -441,15 +441,19 @@ static void __tipc_shutdown(struct socket *sock, int error)
while
((
skb
=
__skb_dequeue
(
&
sk
->
sk_receive_queue
))
!=
NULL
)
{
if
(
TIPC_SKB_CB
(
skb
)
->
bytes_read
)
{
kfree_skb
(
skb
);
}
else
{
if
(
!
tipc_sk_type_connectionless
(
sk
)
&&
sk
->
sk_state
!=
TIPC_DISCONNECTING
)
{
tipc_set_sk_state
(
sk
,
TIPC_DISCONNECTING
);
tipc_node_remove_conn
(
net
,
dnode
,
tsk
->
portid
);
}
tipc_sk_respond
(
sk
,
skb
,
error
);
continue
;
}
if
(
!
tipc_sk_type_connectionless
(
sk
)
&&
sk
->
sk_state
!=
TIPC_DISCONNECTING
)
{
tipc_set_sk_state
(
sk
,
TIPC_DISCONNECTING
);
tipc_node_remove_conn
(
net
,
dnode
,
tsk
->
portid
);
}
tipc_sk_respond
(
sk
,
skb
,
error
);
}
if
(
tipc_sk_type_connectionless
(
sk
))
return
;
if
(
sk
->
sk_state
!=
TIPC_DISCONNECTING
)
{
skb
=
tipc_msg_create
(
TIPC_CRITICAL_IMPORTANCE
,
TIPC_CONN_MSG
,
SHORT_H_SIZE
,
0
,
dnode
,
...
...
@@ -457,10 +461,8 @@ static void __tipc_shutdown(struct socket *sock, int error)
tsk
->
portid
,
error
);
if
(
skb
)
tipc_node_xmit_skb
(
net
,
skb
,
dnode
,
tsk
->
portid
);
if
(
!
tipc_sk_type_connectionless
(
sk
))
{
tipc_node_remove_conn
(
net
,
dnode
,
tsk
->
portid
);
tipc_set_sk_state
(
sk
,
TIPC_DISCONNECTING
);
}
tipc_node_remove_conn
(
net
,
dnode
,
tsk
->
portid
);
tipc_set_sk_state
(
sk
,
TIPC_DISCONNECTING
);
}
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录