mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-25 13:14:07 +08:00
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net
Conflicts: drivers/net/ieee802154/fakehard.c A bug fix went into 'net' for ieee802154/fakehard.c, which is removed in 'net-next'. Add build fix into the merge from Stephen Rothwell in openvswitch, the logging macros take a new initial 'log' argument, a new call was added in 'net' so when we merge that in here we have to explicitly add the new 'log' arg to it else the build fails. Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
commit
1459143386
@ -3,8 +3,10 @@
|
||||
Required properties:
|
||||
- compatible : should contain one of the following:
|
||||
- "renesas,sata-r8a7779" for R-Car H1
|
||||
- "renesas,sata-r8a7790" for R-Car H2
|
||||
- "renesas,sata-r8a7791" for R-Car M2
|
||||
- "renesas,sata-r8a7790-es1" for R-Car H2 ES1
|
||||
- "renesas,sata-r8a7790" for R-Car H2 other than ES1
|
||||
- "renesas,sata-r8a7791" for R-Car M2-W
|
||||
- "renesas,sata-r8a7793" for R-Car M2-N
|
||||
- reg : address and length of the SATA registers;
|
||||
- interrupts : must consist of one interrupt specifier.
|
||||
|
||||
|
@ -30,10 +30,6 @@ should only be used when a device has multiple interrupt parents.
|
||||
Example:
|
||||
interrupts-extended = <&intc1 5 1>, <&intc2 1 0>;
|
||||
|
||||
A device node may contain either "interrupts" or "interrupts-extended", but not
|
||||
both. If both properties are present, then the operating system should log an
|
||||
error and use only the data in "interrupts".
|
||||
|
||||
2) Interrupt controller nodes
|
||||
-----------------------------
|
||||
|
||||
|
@ -7,3 +7,14 @@ And for the interrupt mapping part:
|
||||
|
||||
Open Firmware Recommended Practice: Interrupt Mapping
|
||||
http://www.openfirmware.org/1275/practice/imap/imap0_9d.pdf
|
||||
|
||||
Additionally to the properties specified in the above standards a host bridge
|
||||
driver implementation may support the following properties:
|
||||
|
||||
- linux,pci-domain:
|
||||
If present this property assigns a fixed PCI domain number to a host bridge,
|
||||
otherwise an unstable (across boots) unique number will be assigned.
|
||||
It is required to either not set this property at all or set it for all
|
||||
host bridges in the system, otherwise potentially conflicting domain numbers
|
||||
may be assigned to root buses behind different host bridges. The domain
|
||||
number for each host bridge in the system must be unique.
|
||||
|
@ -9,7 +9,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
TZ1090-PDC's pin configuration nodes act as a container for an abitrary number
|
||||
TZ1090-PDC's pin configuration nodes act as a container for an arbitrary number
|
||||
of subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -9,7 +9,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
TZ1090's pin configuration nodes act as a container for an abitrary number of
|
||||
TZ1090's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -9,7 +9,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Lantiq's pin configuration nodes act as a container for an abitrary number of
|
||||
Lantiq's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those group(s), and two pin configuration parameters:
|
||||
|
@ -9,7 +9,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Lantiq's pin configuration nodes act as a container for an abitrary number of
|
||||
Lantiq's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those group(s), and two pin configuration parameters:
|
||||
|
@ -9,7 +9,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Tegra's pin configuration nodes act as a container for an abitrary number of
|
||||
Tegra's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -13,7 +13,7 @@ Optional properties:
|
||||
Please refer to pinctrl-bindings.txt in this directory for details of the common
|
||||
pinctrl bindings used by client devices.
|
||||
|
||||
SiRFprimaII's pinmux nodes act as a container for an abitrary number of subnodes.
|
||||
SiRFprimaII's pinmux nodes act as a container for an arbitrary number of subnodes.
|
||||
Each of these subnodes represents some desired configuration for a group of pins.
|
||||
|
||||
Required subnode-properties:
|
||||
|
@ -32,7 +32,7 @@ Required properties:
|
||||
Please refer to pinctrl-bindings.txt in this directory for details of the common
|
||||
pinctrl bindings used by client devices.
|
||||
|
||||
SPEAr's pinmux nodes act as a container for an abitrary number of subnodes. Each
|
||||
SPEAr's pinmux nodes act as a container for an arbitrary number of subnodes. Each
|
||||
of these subnodes represents muxing for a pin, a group, or a list of pins or
|
||||
groups.
|
||||
|
||||
|
@ -18,7 +18,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Qualcomm's pin configuration nodes act as a container for an abitrary number of
|
||||
Qualcomm's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -47,7 +47,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
The pin configuration nodes act as a container for an abitrary number of
|
||||
The pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -18,7 +18,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Qualcomm's pin configuration nodes act as a container for an abitrary number of
|
||||
Qualcomm's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -47,7 +47,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
The pin configuration nodes act as a container for an abitrary number of
|
||||
The pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -18,7 +18,7 @@ Please refer to pinctrl-bindings.txt in this directory for details of the
|
||||
common pinctrl bindings used by client devices, including the meaning of the
|
||||
phrase "pin configuration node".
|
||||
|
||||
Qualcomm's pin configuration nodes act as a container for an abitrary number of
|
||||
Qualcomm's pin configuration nodes act as a container for an arbitrary number of
|
||||
subnodes. Each of these subnodes represents some desired configuration for a
|
||||
pin, a group, or a list of pins or groups. This configuration can include the
|
||||
mux function to select on those pin(s)/group(s), and various pin configuration
|
||||
|
@ -34,6 +34,7 @@ chipidea Chipidea, Inc
|
||||
chrp Common Hardware Reference Platform
|
||||
chunghwa Chunghwa Picture Tubes Ltd.
|
||||
cirrus Cirrus Logic, Inc.
|
||||
cnm Chips&Media, Inc.
|
||||
cortina Cortina Systems, Inc.
|
||||
crystalfontz Crystalfontz America, Inc.
|
||||
dallas Maxim Integrated Products (formerly Dallas Semiconductor)
|
||||
@ -92,6 +93,7 @@ maxim Maxim Integrated Products
|
||||
mediatek MediaTek Inc.
|
||||
micrel Micrel Inc.
|
||||
microchip Microchip Technology Inc.
|
||||
micron Micron Technology Inc.
|
||||
mitsubishi Mitsubishi Electric Corporation
|
||||
mosaixtech Mosaix Technologies, Inc.
|
||||
moxa Moxa
|
||||
@ -127,6 +129,7 @@ renesas Renesas Electronics Corporation
|
||||
ricoh Ricoh Co. Ltd.
|
||||
rockchip Fuzhou Rockchip Electronics Co., Ltd
|
||||
samsung Samsung Semiconductor
|
||||
sandisk Sandisk Corporation
|
||||
sbs Smart Battery System
|
||||
schindler Schindler
|
||||
seagate Seagate Technology PLC
|
||||
@ -138,7 +141,7 @@ silergy Silergy Corp.
|
||||
sirf SiRF Technology, Inc.
|
||||
sitronix Sitronix Technology Corporation
|
||||
smsc Standard Microsystems Corporation
|
||||
snps Synopsys, Inc.
|
||||
snps Synopsys, Inc.
|
||||
solidrun SolidRun
|
||||
sony Sony Corporation
|
||||
spansion Spansion Inc.
|
||||
|
@ -38,22 +38,38 @@ Contents
|
||||
7.2.1 Status packet
|
||||
7.2.2 Head packet
|
||||
7.2.3 Motion packet
|
||||
8. Trackpoint (for Hardware version 3 and 4)
|
||||
8.1 Registers
|
||||
8.2 Native relative mode 6 byte packet format
|
||||
8.2.1 Status Packet
|
||||
|
||||
|
||||
|
||||
1. Introduction
|
||||
~~~~~~~~~~~~
|
||||
|
||||
Currently the Linux Elantech touchpad driver is aware of two different
|
||||
hardware versions unimaginatively called version 1 and version 2. Version 1
|
||||
is found in "older" laptops and uses 4 bytes per packet. Version 2 seems to
|
||||
be introduced with the EeePC and uses 6 bytes per packet, and provides
|
||||
additional features such as position of two fingers, and width of the touch.
|
||||
Currently the Linux Elantech touchpad driver is aware of four different
|
||||
hardware versions unimaginatively called version 1,version 2, version 3
|
||||
and version 4. Version 1 is found in "older" laptops and uses 4 bytes per
|
||||
packet. Version 2 seems to be introduced with the EeePC and uses 6 bytes
|
||||
per packet, and provides additional features such as position of two fingers,
|
||||
and width of the touch. Hardware version 3 uses 6 bytes per packet (and
|
||||
for 2 fingers the concatenation of two 6 bytes packets) and allows tracking
|
||||
of up to 3 fingers. Hardware version 4 uses 6 bytes per packet, and can
|
||||
combine a status packet with multiple head or motion packets. Hardware version
|
||||
4 allows tracking up to 5 fingers.
|
||||
|
||||
Some Hardware version 3 and version 4 also have a trackpoint which uses a
|
||||
separate packet format. It is also 6 bytes per packet.
|
||||
|
||||
The driver tries to support both hardware versions and should be compatible
|
||||
with the Xorg Synaptics touchpad driver and its graphical configuration
|
||||
utilities.
|
||||
|
||||
Note that a mouse button is also associated with either the touchpad or the
|
||||
trackpoint when a trackpoint is available. Disabling the Touchpad in xorg
|
||||
(TouchPadOff=0) will also disable the buttons associated with the touchpad.
|
||||
|
||||
Additionally the operation of the touchpad can be altered by adjusting the
|
||||
contents of some of its internal registers. These registers are represented
|
||||
by the driver as sysfs entries under /sys/bus/serio/drivers/psmouse/serio?
|
||||
@ -78,7 +94,7 @@ completeness sake.
|
||||
2. Extra knobs
|
||||
~~~~~~~~~~~
|
||||
|
||||
Currently the Linux Elantech touchpad driver provides two extra knobs under
|
||||
Currently the Linux Elantech touchpad driver provides three extra knobs under
|
||||
/sys/bus/serio/drivers/psmouse/serio? for the user.
|
||||
|
||||
* debug
|
||||
@ -112,6 +128,20 @@ Currently the Linux Elantech touchpad driver provides two extra knobs under
|
||||
data consistency checking can be done. For now checking is disabled by
|
||||
default. Currently even turning it on will do nothing.
|
||||
|
||||
* crc_enabled
|
||||
|
||||
Sets crc_enabled to 0/1. The name "crc_enabled" is the official name of
|
||||
this integrity check, even though it is not an actual cyclic redundancy
|
||||
check.
|
||||
|
||||
Depending on the state of crc_enabled, certain basic data integrity
|
||||
verification is done by the driver on hardware version 3 and 4. The
|
||||
driver will reject any packet that appears corrupted. Using this knob,
|
||||
The state of crc_enabled can be altered with this knob.
|
||||
|
||||
Reading the crc_enabled value will show the active value. Echoing
|
||||
"0" or "1" to this file will set the state to "0" or "1".
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
3. Differentiating hardware versions
|
||||
@ -746,3 +776,42 @@ byte 5:
|
||||
|
||||
byte 0 ~ 2 for one finger
|
||||
byte 3 ~ 5 for another
|
||||
|
||||
|
||||
8. Trackpoint (for Hardware version 3 and 4)
|
||||
=========================================
|
||||
8.1 Registers
|
||||
~~~~~~~~~
|
||||
No special registers have been identified.
|
||||
|
||||
8.2 Native relative mode 6 byte packet format
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
8.2.1 Status Packet
|
||||
~~~~~~~~~~~~~
|
||||
|
||||
byte 0:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
0 0 sx sy 0 M R L
|
||||
byte 1:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
~sx 0 0 0 0 0 0 0
|
||||
byte 2:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
~sy 0 0 0 0 0 0 0
|
||||
byte 3:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
0 0 ~sy ~sx 0 1 1 0
|
||||
byte 4:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
x7 x6 x5 x4 x3 x2 x1 x0
|
||||
byte 5:
|
||||
bit 7 6 5 4 3 2 1 0
|
||||
y7 y6 y5 y4 y3 y2 y1 y0
|
||||
|
||||
|
||||
x and y are written in two's complement spread
|
||||
over 9 bits with sx/sy the relative top bit and
|
||||
x7..x0 and y7..y0 the lower bits.
|
||||
~sx is the inverse of sx, ~sy is the inverse of sy.
|
||||
The sign of y is opposite to what the input driver
|
||||
expects for a relative movement
|
||||
|
34
MAINTAINERS
34
MAINTAINERS
@ -2752,6 +2752,13 @@ W: http://www.chelsio.com
|
||||
S: Supported
|
||||
F: drivers/net/ethernet/chelsio/cxgb3/
|
||||
|
||||
CXGB3 ISCSI DRIVER (CXGB3I)
|
||||
M: Karen Xie <kxie@chelsio.com>
|
||||
L: linux-scsi@vger.kernel.org
|
||||
W: http://www.chelsio.com
|
||||
S: Supported
|
||||
F: drivers/scsi/cxgbi/cxgb3i
|
||||
|
||||
CXGB3 IWARP RNIC DRIVER (IW_CXGB3)
|
||||
M: Steve Wise <swise@chelsio.com>
|
||||
L: linux-rdma@vger.kernel.org
|
||||
@ -2766,6 +2773,13 @@ W: http://www.chelsio.com
|
||||
S: Supported
|
||||
F: drivers/net/ethernet/chelsio/cxgb4/
|
||||
|
||||
CXGB4 ISCSI DRIVER (CXGB4I)
|
||||
M: Karen Xie <kxie@chelsio.com>
|
||||
L: linux-scsi@vger.kernel.org
|
||||
W: http://www.chelsio.com
|
||||
S: Supported
|
||||
F: drivers/scsi/cxgbi/cxgb4i
|
||||
|
||||
CXGB4 IWARP RNIC DRIVER (IW_CXGB4)
|
||||
M: Steve Wise <swise@chelsio.com>
|
||||
L: linux-rdma@vger.kernel.org
|
||||
@ -6617,6 +6631,23 @@ T: git git://git.kernel.org/pub/scm/linux/kernel/git/tmlind/linux-omap.git
|
||||
S: Maintained
|
||||
F: arch/arm/*omap*/
|
||||
F: drivers/i2c/busses/i2c-omap.c
|
||||
F: drivers/irqchip/irq-omap-intc.c
|
||||
F: drivers/mfd/*omap*.c
|
||||
F: drivers/mfd/menelaus.c
|
||||
F: drivers/mfd/palmas.c
|
||||
F: drivers/mfd/tps65217.c
|
||||
F: drivers/mfd/tps65218.c
|
||||
F: drivers/mfd/tps65910.c
|
||||
F: drivers/mfd/twl-core.[ch]
|
||||
F: drivers/mfd/twl4030*.c
|
||||
F: drivers/mfd/twl6030*.c
|
||||
F: drivers/mfd/twl6040*.c
|
||||
F: drivers/regulator/palmas-regulator*.c
|
||||
F: drivers/regulator/pbias-regulator.c
|
||||
F: drivers/regulator/tps65217-regulator.c
|
||||
F: drivers/regulator/tps65218-regulator.c
|
||||
F: drivers/regulator/tps65910-regulator.c
|
||||
F: drivers/regulator/twl-regulator.c
|
||||
F: include/linux/i2c-omap.h
|
||||
|
||||
OMAP DEVICE TREE SUPPORT
|
||||
@ -6627,6 +6658,9 @@ L: devicetree@vger.kernel.org
|
||||
S: Maintained
|
||||
F: arch/arm/boot/dts/*omap*
|
||||
F: arch/arm/boot/dts/*am3*
|
||||
F: arch/arm/boot/dts/*am4*
|
||||
F: arch/arm/boot/dts/*am5*
|
||||
F: arch/arm/boot/dts/*dra7*
|
||||
|
||||
OMAP CLOCK FRAMEWORK SUPPORT
|
||||
M: Paul Walmsley <paul@pwsan.com>
|
||||
|
7
Makefile
7
Makefile
@ -1,7 +1,7 @@
|
||||
VERSION = 3
|
||||
PATCHLEVEL = 18
|
||||
SUBLEVEL = 0
|
||||
EXTRAVERSION = -rc4
|
||||
EXTRAVERSION = -rc5
|
||||
NAME = Diseased Newt
|
||||
|
||||
# *DOCUMENTATION*
|
||||
@ -297,7 +297,7 @@ CONFIG_SHELL := $(shell if [ -x "$$BASH" ]; then echo $$BASH; \
|
||||
|
||||
HOSTCC = gcc
|
||||
HOSTCXX = g++
|
||||
HOSTCFLAGS = -Wall -Wmissing-prototypes -Wstrict-prototypes -O2 -fomit-frame-pointer
|
||||
HOSTCFLAGS = -Wall -Wmissing-prototypes -Wstrict-prototypes -O2 -fomit-frame-pointer -std=gnu89
|
||||
HOSTCXXFLAGS = -O2
|
||||
|
||||
ifeq ($(shell $(HOSTCC) -v 2>&1 | grep -c "clang version"), 1)
|
||||
@ -401,7 +401,8 @@ KBUILD_CPPFLAGS := -D__KERNEL__
|
||||
KBUILD_CFLAGS := -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs \
|
||||
-fno-strict-aliasing -fno-common \
|
||||
-Werror-implicit-function-declaration \
|
||||
-Wno-format-security
|
||||
-Wno-format-security \
|
||||
-std=gnu89
|
||||
|
||||
KBUILD_AFLAGS_KERNEL :=
|
||||
KBUILD_CFLAGS_KERNEL :=
|
||||
|
@ -397,8 +397,7 @@ dtb_check_done:
|
||||
add sp, sp, r6
|
||||
#endif
|
||||
|
||||
tst r4, #1
|
||||
bleq cache_clean_flush
|
||||
bl cache_clean_flush
|
||||
|
||||
adr r0, BSYM(restart)
|
||||
add r0, r0, r6
|
||||
@ -1047,6 +1046,8 @@ cache_clean_flush:
|
||||
b call_cache_fn
|
||||
|
||||
__armv4_mpu_cache_flush:
|
||||
tst r4, #1
|
||||
movne pc, lr
|
||||
mov r2, #1
|
||||
mov r3, #0
|
||||
mcr p15, 0, ip, c7, c6, 0 @ invalidate D cache
|
||||
@ -1064,6 +1065,8 @@ __armv4_mpu_cache_flush:
|
||||
mov pc, lr
|
||||
|
||||
__fa526_cache_flush:
|
||||
tst r4, #1
|
||||
movne pc, lr
|
||||
mov r1, #0
|
||||
mcr p15, 0, r1, c7, c14, 0 @ clean and invalidate D cache
|
||||
mcr p15, 0, r1, c7, c5, 0 @ flush I cache
|
||||
@ -1072,13 +1075,16 @@ __fa526_cache_flush:
|
||||
|
||||
__armv6_mmu_cache_flush:
|
||||
mov r1, #0
|
||||
mcr p15, 0, r1, c7, c14, 0 @ clean+invalidate D
|
||||
tst r4, #1
|
||||
mcreq p15, 0, r1, c7, c14, 0 @ clean+invalidate D
|
||||
mcr p15, 0, r1, c7, c5, 0 @ invalidate I+BTB
|
||||
mcr p15, 0, r1, c7, c15, 0 @ clean+invalidate unified
|
||||
mcreq p15, 0, r1, c7, c15, 0 @ clean+invalidate unified
|
||||
mcr p15, 0, r1, c7, c10, 4 @ drain WB
|
||||
mov pc, lr
|
||||
|
||||
__armv7_mmu_cache_flush:
|
||||
tst r4, #1
|
||||
bne iflush
|
||||
mrc p15, 0, r10, c0, c1, 5 @ read ID_MMFR1
|
||||
tst r10, #0xf << 16 @ hierarchical cache (ARMv7)
|
||||
mov r10, #0
|
||||
@ -1139,6 +1145,8 @@ iflush:
|
||||
mov pc, lr
|
||||
|
||||
__armv5tej_mmu_cache_flush:
|
||||
tst r4, #1
|
||||
movne pc, lr
|
||||
1: mrc p15, 0, r15, c7, c14, 3 @ test,clean,invalidate D cache
|
||||
bne 1b
|
||||
mcr p15, 0, r0, c7, c5, 0 @ flush I cache
|
||||
@ -1146,6 +1154,8 @@ __armv5tej_mmu_cache_flush:
|
||||
mov pc, lr
|
||||
|
||||
__armv4_mmu_cache_flush:
|
||||
tst r4, #1
|
||||
movne pc, lr
|
||||
mov r2, #64*1024 @ default: 32K dcache size (*2)
|
||||
mov r11, #32 @ default: 32 byte line size
|
||||
mrc p15, 0, r3, c0, c0, 1 @ read cache type
|
||||
@ -1179,6 +1189,8 @@ no_cache_id:
|
||||
|
||||
__armv3_mmu_cache_flush:
|
||||
__armv3_mpu_cache_flush:
|
||||
tst r4, #1
|
||||
movne pc, lr
|
||||
mov r1, #0
|
||||
mcr p15, 0, r1, c7, c0, 0 @ invalidate whole cache v3
|
||||
mov pc, lr
|
||||
|
@ -489,7 +489,7 @@
|
||||
reg = <0x00060000 0x00020000>;
|
||||
};
|
||||
partition@4 {
|
||||
label = "NAND.u-boot-spl";
|
||||
label = "NAND.u-boot-spl-os";
|
||||
reg = <0x00080000 0x00040000>;
|
||||
};
|
||||
partition@5 {
|
||||
|
@ -291,8 +291,8 @@
|
||||
dcdc3: regulator-dcdc3 {
|
||||
compatible = "ti,tps65218-dcdc3";
|
||||
regulator-name = "vdcdc3";
|
||||
regulator-min-microvolt = <1350000>;
|
||||
regulator-max-microvolt = <1350000>;
|
||||
regulator-min-microvolt = <1500000>;
|
||||
regulator-max-microvolt = <1500000>;
|
||||
regulator-boot-on;
|
||||
regulator-always-on;
|
||||
};
|
||||
|
@ -363,8 +363,8 @@
|
||||
dcdc3: regulator-dcdc3 {
|
||||
compatible = "ti,tps65218-dcdc3";
|
||||
regulator-name = "vdds_ddr";
|
||||
regulator-min-microvolt = <1350000>;
|
||||
regulator-max-microvolt = <1350000>;
|
||||
regulator-min-microvolt = <1500000>;
|
||||
regulator-max-microvolt = <1500000>;
|
||||
regulator-boot-on;
|
||||
regulator-always-on;
|
||||
};
|
||||
|
@ -358,8 +358,8 @@
|
||||
dcdc3: regulator-dcdc3 {
|
||||
compatible = "ti,tps65218-dcdc3";
|
||||
regulator-name = "vdcdc3";
|
||||
regulator-min-microvolt = <1350000>;
|
||||
regulator-max-microvolt = <1350000>;
|
||||
regulator-min-microvolt = <1500000>;
|
||||
regulator-max-microvolt = <1500000>;
|
||||
regulator-boot-on;
|
||||
regulator-always-on;
|
||||
};
|
||||
|
@ -12,5 +12,5 @@
|
||||
#include "sama5d3_uart.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad31", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d31", "atmel,sama5d3", "atmel,sama5";
|
||||
};
|
||||
|
@ -10,5 +10,5 @@
|
||||
#include "sama5d3_gmac.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad33", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d33", "atmel,sama5d3", "atmel,sama5";
|
||||
};
|
||||
|
@ -12,5 +12,5 @@
|
||||
#include "sama5d3_mci2.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad34", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d34", "atmel,sama5d3", "atmel,sama5";
|
||||
};
|
||||
|
@ -14,5 +14,5 @@
|
||||
#include "sama5d3_tcb1.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad35", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d35", "atmel,sama5d3", "atmel,sama5";
|
||||
};
|
||||
|
@ -16,5 +16,5 @@
|
||||
#include "sama5d3_uart.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad36", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d36", "atmel,sama5d3", "atmel,sama5";
|
||||
};
|
||||
|
@ -8,7 +8,7 @@
|
||||
*/
|
||||
|
||||
/ {
|
||||
compatible = "atmel,samad3xcm", "atmel,sama5d3", "atmel,sama5";
|
||||
compatible = "atmel,sama5d3xcm", "atmel,sama5d3", "atmel,sama5";
|
||||
|
||||
chosen {
|
||||
bootargs = "console=ttyS0,115200 rootfstype=ubifs ubi.mtd=5 root=ubi0:rootfs";
|
||||
|
@ -188,7 +188,7 @@ static void __init thermal_quirk(void)
|
||||
|
||||
static void __init mvebu_dt_init(void)
|
||||
{
|
||||
if (of_machine_is_compatible("plathome,openblocks-ax3-4"))
|
||||
if (of_machine_is_compatible("marvell,armadaxp"))
|
||||
i2c_quirk();
|
||||
if (of_machine_is_compatible("marvell,a375-db")) {
|
||||
external_abort_quirk();
|
||||
|
@ -798,6 +798,7 @@ config NEED_KUSER_HELPERS
|
||||
|
||||
config KUSER_HELPERS
|
||||
bool "Enable kuser helpers in vector page" if !NEED_KUSER_HELPERS
|
||||
depends on MMU
|
||||
default y
|
||||
help
|
||||
Warning: disabling this option may break user programs.
|
||||
|
@ -497,6 +497,34 @@ static void orion_gpio_dbg_show(struct seq_file *s, struct gpio_chip *chip)
|
||||
#define orion_gpio_dbg_show NULL
|
||||
#endif
|
||||
|
||||
static void orion_gpio_unmask_irq(struct irq_data *d)
|
||||
{
|
||||
struct irq_chip_generic *gc = irq_data_get_irq_chip_data(d);
|
||||
struct irq_chip_type *ct = irq_data_get_chip_type(d);
|
||||
u32 reg_val;
|
||||
u32 mask = d->mask;
|
||||
|
||||
irq_gc_lock(gc);
|
||||
reg_val = irq_reg_readl(gc->reg_base + ct->regs.mask);
|
||||
reg_val |= mask;
|
||||
irq_reg_writel(reg_val, gc->reg_base + ct->regs.mask);
|
||||
irq_gc_unlock(gc);
|
||||
}
|
||||
|
||||
static void orion_gpio_mask_irq(struct irq_data *d)
|
||||
{
|
||||
struct irq_chip_generic *gc = irq_data_get_irq_chip_data(d);
|
||||
struct irq_chip_type *ct = irq_data_get_chip_type(d);
|
||||
u32 mask = d->mask;
|
||||
u32 reg_val;
|
||||
|
||||
irq_gc_lock(gc);
|
||||
reg_val = irq_reg_readl(gc->reg_base + ct->regs.mask);
|
||||
reg_val &= ~mask;
|
||||
irq_reg_writel(reg_val, gc->reg_base + ct->regs.mask);
|
||||
irq_gc_unlock(gc);
|
||||
}
|
||||
|
||||
void __init orion_gpio_init(struct device_node *np,
|
||||
int gpio_base, int ngpio,
|
||||
void __iomem *base, int mask_offset,
|
||||
@ -565,8 +593,8 @@ void __init orion_gpio_init(struct device_node *np,
|
||||
ct = gc->chip_types;
|
||||
ct->regs.mask = ochip->mask_offset + GPIO_LEVEL_MASK_OFF;
|
||||
ct->type = IRQ_TYPE_LEVEL_HIGH | IRQ_TYPE_LEVEL_LOW;
|
||||
ct->chip.irq_mask = irq_gc_mask_clr_bit;
|
||||
ct->chip.irq_unmask = irq_gc_mask_set_bit;
|
||||
ct->chip.irq_mask = orion_gpio_mask_irq;
|
||||
ct->chip.irq_unmask = orion_gpio_unmask_irq;
|
||||
ct->chip.irq_set_type = gpio_irq_set_type;
|
||||
ct->chip.name = ochip->chip.label;
|
||||
|
||||
@ -575,8 +603,8 @@ void __init orion_gpio_init(struct device_node *np,
|
||||
ct->regs.ack = GPIO_EDGE_CAUSE_OFF;
|
||||
ct->type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING;
|
||||
ct->chip.irq_ack = irq_gc_ack_clr_bit;
|
||||
ct->chip.irq_mask = irq_gc_mask_clr_bit;
|
||||
ct->chip.irq_unmask = irq_gc_mask_set_bit;
|
||||
ct->chip.irq_mask = orion_gpio_mask_irq;
|
||||
ct->chip.irq_unmask = orion_gpio_unmask_irq;
|
||||
ct->chip.irq_set_type = gpio_irq_set_type;
|
||||
ct->handler = handle_edge_irq;
|
||||
ct->chip.name = ochip->chip.label;
|
||||
|
@ -142,7 +142,7 @@ static inline void *phys_to_virt(phys_addr_t x)
|
||||
* virt_to_page(k) convert a _valid_ virtual address to struct page *
|
||||
* virt_addr_valid(k) indicates whether a virtual address is valid
|
||||
*/
|
||||
#define ARCH_PFN_OFFSET PHYS_PFN_OFFSET
|
||||
#define ARCH_PFN_OFFSET ((unsigned long)PHYS_PFN_OFFSET)
|
||||
|
||||
#define virt_to_page(kaddr) pfn_to_page(__pa(kaddr) >> PAGE_SHIFT)
|
||||
#define virt_addr_valid(kaddr) pfn_valid(__pa(kaddr) >> PAGE_SHIFT)
|
||||
|
@ -54,18 +54,17 @@ ENTRY(efi_stub_entry)
|
||||
b.eq efi_load_fail
|
||||
|
||||
/*
|
||||
* efi_entry() will have relocated the kernel image if necessary
|
||||
* and we return here with device tree address in x0 and the kernel
|
||||
* entry point stored at *image_addr. Save those values in registers
|
||||
* which are callee preserved.
|
||||
* efi_entry() will have copied the kernel image if necessary and we
|
||||
* return here with device tree address in x0 and the kernel entry
|
||||
* point stored at *image_addr. Save those values in registers which
|
||||
* are callee preserved.
|
||||
*/
|
||||
mov x20, x0 // DTB address
|
||||
ldr x0, [sp, #16] // relocated _text address
|
||||
mov x21, x0
|
||||
|
||||
/*
|
||||
* Flush dcache covering current runtime addresses
|
||||
* of kernel text/data. Then flush all of icache.
|
||||
* Calculate size of the kernel Image (same for original and copy).
|
||||
*/
|
||||
adrp x1, _text
|
||||
add x1, x1, #:lo12:_text
|
||||
@ -73,9 +72,24 @@ ENTRY(efi_stub_entry)
|
||||
add x2, x2, #:lo12:_edata
|
||||
sub x1, x2, x1
|
||||
|
||||
/*
|
||||
* Flush the copied Image to the PoC, and ensure it is not shadowed by
|
||||
* stale icache entries from before relocation.
|
||||
*/
|
||||
bl __flush_dcache_area
|
||||
ic ialluis
|
||||
|
||||
/*
|
||||
* Ensure that the rest of this function (in the original Image) is
|
||||
* visible when the caches are disabled. The I-cache can't have stale
|
||||
* entries for the VA range of the current image, so no maintenance is
|
||||
* necessary.
|
||||
*/
|
||||
adr x0, efi_stub_entry
|
||||
adr x1, efi_stub_entry_end
|
||||
sub x1, x1, x0
|
||||
bl __flush_dcache_area
|
||||
|
||||
/* Turn off Dcache and MMU */
|
||||
mrs x0, CurrentEL
|
||||
cmp x0, #CurrentEL_EL2
|
||||
@ -105,4 +119,5 @@ efi_load_fail:
|
||||
ldp x29, x30, [sp], #32
|
||||
ret
|
||||
|
||||
efi_stub_entry_end:
|
||||
ENDPROC(efi_stub_entry)
|
||||
|
@ -163,9 +163,10 @@ static int __kprobes aarch64_insn_patch_text_cb(void *arg)
|
||||
* which ends with "dsb; isb" pair guaranteeing global
|
||||
* visibility.
|
||||
*/
|
||||
atomic_set(&pp->cpu_count, -1);
|
||||
/* Notify other processors with an additional increment. */
|
||||
atomic_inc(&pp->cpu_count);
|
||||
} else {
|
||||
while (atomic_read(&pp->cpu_count) != -1)
|
||||
while (atomic_read(&pp->cpu_count) <= num_online_cpus())
|
||||
cpu_relax();
|
||||
isb();
|
||||
}
|
||||
|
@ -46,7 +46,7 @@ USER(9f, strh wzr, [x0], #2 )
|
||||
sub x1, x1, #2
|
||||
4: adds x1, x1, #1
|
||||
b.mi 5f
|
||||
strb wzr, [x0]
|
||||
USER(9f, strb wzr, [x0] )
|
||||
5: mov x0, #0
|
||||
ret
|
||||
ENDPROC(__clear_user)
|
||||
|
@ -202,7 +202,7 @@ static void __init alloc_init_pmd(pud_t *pud, unsigned long addr,
|
||||
}
|
||||
|
||||
static void __init alloc_init_pud(pgd_t *pgd, unsigned long addr,
|
||||
unsigned long end, unsigned long phys,
|
||||
unsigned long end, phys_addr_t phys,
|
||||
int map_io)
|
||||
{
|
||||
pud_t *pud;
|
||||
|
@ -20,9 +20,15 @@
|
||||
#define WORD_INSN ".word"
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_CPU_MICROMIPS
|
||||
#define NOP_INSN "nop32"
|
||||
#else
|
||||
#define NOP_INSN "nop"
|
||||
#endif
|
||||
|
||||
static __always_inline bool arch_static_branch(struct static_key *key)
|
||||
{
|
||||
asm_volatile_goto("1:\tnop\n\t"
|
||||
asm_volatile_goto("1:\t" NOP_INSN "\n\t"
|
||||
"nop\n\t"
|
||||
".pushsection __jump_table, \"aw\"\n\t"
|
||||
WORD_INSN " 1b, %l[l_yes], %0\n\t"
|
||||
|
@ -41,10 +41,8 @@
|
||||
#define cpu_has_mcheck 0
|
||||
#define cpu_has_mdmx 0
|
||||
#define cpu_has_mips16 0
|
||||
#define cpu_has_mips32r1 0
|
||||
#define cpu_has_mips32r2 0
|
||||
#define cpu_has_mips3d 0
|
||||
#define cpu_has_mips64r1 0
|
||||
#define cpu_has_mips64r2 0
|
||||
#define cpu_has_mipsmt 0
|
||||
#define cpu_has_prefetch 0
|
||||
|
@ -301,7 +301,8 @@ do { \
|
||||
__get_kernel_common((x), size, __gu_ptr); \
|
||||
else \
|
||||
__get_user_common((x), size, __gu_ptr); \
|
||||
} \
|
||||
} else \
|
||||
(x) = 0; \
|
||||
\
|
||||
__gu_err; \
|
||||
})
|
||||
@ -316,6 +317,7 @@ do { \
|
||||
" .insn \n" \
|
||||
" .section .fixup,\"ax\" \n" \
|
||||
"3: li %0, %4 \n" \
|
||||
" move %1, $0 \n" \
|
||||
" j 2b \n" \
|
||||
" .previous \n" \
|
||||
" .section __ex_table,\"a\" \n" \
|
||||
@ -630,6 +632,7 @@ do { \
|
||||
" .insn \n" \
|
||||
" .section .fixup,\"ax\" \n" \
|
||||
"3: li %0, %4 \n" \
|
||||
" move %1, $0 \n" \
|
||||
" j 2b \n" \
|
||||
" .previous \n" \
|
||||
" .section __ex_table,\"a\" \n" \
|
||||
@ -773,10 +776,11 @@ extern void __put_user_unaligned_unknown(void);
|
||||
"jal\t" #destination "\n\t"
|
||||
#endif
|
||||
|
||||
#ifndef CONFIG_CPU_DADDI_WORKAROUNDS
|
||||
#define DADDI_SCRATCH "$0"
|
||||
#else
|
||||
#if defined(CONFIG_CPU_DADDI_WORKAROUNDS) || (defined(CONFIG_EVA) && \
|
||||
defined(CONFIG_CPU_HAS_PREFETCH))
|
||||
#define DADDI_SCRATCH "$3"
|
||||
#else
|
||||
#define DADDI_SCRATCH "$0"
|
||||
#endif
|
||||
|
||||
extern size_t __copy_user(void *__to, const void *__from, size_t __n);
|
||||
|
@ -757,31 +757,34 @@ static inline void cpu_probe_legacy(struct cpuinfo_mips *c, unsigned int cpu)
|
||||
c->cputype = CPU_LOONGSON2;
|
||||
__cpu_name[cpu] = "ICT Loongson-2";
|
||||
set_elf_platform(cpu, "loongson2e");
|
||||
set_isa(c, MIPS_CPU_ISA_III);
|
||||
break;
|
||||
case PRID_REV_LOONGSON2F:
|
||||
c->cputype = CPU_LOONGSON2;
|
||||
__cpu_name[cpu] = "ICT Loongson-2";
|
||||
set_elf_platform(cpu, "loongson2f");
|
||||
set_isa(c, MIPS_CPU_ISA_III);
|
||||
break;
|
||||
case PRID_REV_LOONGSON3A:
|
||||
c->cputype = CPU_LOONGSON3;
|
||||
c->writecombine = _CACHE_UNCACHED_ACCELERATED;
|
||||
__cpu_name[cpu] = "ICT Loongson-3";
|
||||
set_elf_platform(cpu, "loongson3a");
|
||||
set_isa(c, MIPS_CPU_ISA_M64R1);
|
||||
break;
|
||||
case PRID_REV_LOONGSON3B_R1:
|
||||
case PRID_REV_LOONGSON3B_R2:
|
||||
c->cputype = CPU_LOONGSON3;
|
||||
__cpu_name[cpu] = "ICT Loongson-3";
|
||||
set_elf_platform(cpu, "loongson3b");
|
||||
set_isa(c, MIPS_CPU_ISA_M64R1);
|
||||
break;
|
||||
}
|
||||
|
||||
set_isa(c, MIPS_CPU_ISA_III);
|
||||
c->options = R4K_OPTS |
|
||||
MIPS_CPU_FPU | MIPS_CPU_LLSC |
|
||||
MIPS_CPU_32FPR;
|
||||
c->tlbsize = 64;
|
||||
c->writecombine = _CACHE_UNCACHED_ACCELERATED;
|
||||
break;
|
||||
case PRID_IMP_LOONGSON_32: /* Loongson-1 */
|
||||
decode_configs(c);
|
||||
|
@ -18,31 +18,53 @@
|
||||
|
||||
#ifdef HAVE_JUMP_LABEL
|
||||
|
||||
#define J_RANGE_MASK ((1ul << 28) - 1)
|
||||
/*
|
||||
* Define parameters for the standard MIPS and the microMIPS jump
|
||||
* instruction encoding respectively:
|
||||
*
|
||||
* - the ISA bit of the target, either 0 or 1 respectively,
|
||||
*
|
||||
* - the amount the jump target address is shifted right to fit in the
|
||||
* immediate field of the machine instruction, either 2 or 1,
|
||||
*
|
||||
* - the mask determining the size of the jump region relative to the
|
||||
* delay-slot instruction, either 256MB or 128MB,
|
||||
*
|
||||
* - the jump target alignment, either 4 or 2 bytes.
|
||||
*/
|
||||
#define J_ISA_BIT IS_ENABLED(CONFIG_CPU_MICROMIPS)
|
||||
#define J_RANGE_SHIFT (2 - J_ISA_BIT)
|
||||
#define J_RANGE_MASK ((1ul << (26 + J_RANGE_SHIFT)) - 1)
|
||||
#define J_ALIGN_MASK ((1ul << J_RANGE_SHIFT) - 1)
|
||||
|
||||
void arch_jump_label_transform(struct jump_entry *e,
|
||||
enum jump_label_type type)
|
||||
{
|
||||
union mips_instruction *insn_p;
|
||||
union mips_instruction insn;
|
||||
union mips_instruction *insn_p =
|
||||
(union mips_instruction *)(unsigned long)e->code;
|
||||
|
||||
/* Jump only works within a 256MB aligned region. */
|
||||
BUG_ON((e->target & ~J_RANGE_MASK) != (e->code & ~J_RANGE_MASK));
|
||||
insn_p = (union mips_instruction *)msk_isa16_mode(e->code);
|
||||
|
||||
/* Target must have 4 byte alignment. */
|
||||
BUG_ON((e->target & 3) != 0);
|
||||
/* Jump only works within an aligned region its delay slot is in. */
|
||||
BUG_ON((e->target & ~J_RANGE_MASK) != ((e->code + 4) & ~J_RANGE_MASK));
|
||||
|
||||
/* Target must have the right alignment and ISA must be preserved. */
|
||||
BUG_ON((e->target & J_ALIGN_MASK) != J_ISA_BIT);
|
||||
|
||||
if (type == JUMP_LABEL_ENABLE) {
|
||||
insn.j_format.opcode = j_op;
|
||||
insn.j_format.target = (e->target & J_RANGE_MASK) >> 2;
|
||||
insn.j_format.opcode = J_ISA_BIT ? mm_j32_op : j_op;
|
||||
insn.j_format.target = e->target >> J_RANGE_SHIFT;
|
||||
} else {
|
||||
insn.word = 0; /* nop */
|
||||
}
|
||||
|
||||
get_online_cpus();
|
||||
mutex_lock(&text_mutex);
|
||||
*insn_p = insn;
|
||||
if (IS_ENABLED(CONFIG_CPU_MICROMIPS)) {
|
||||
insn_p->halfword[0] = insn.word >> 16;
|
||||
insn_p->halfword[1] = insn.word;
|
||||
} else
|
||||
*insn_p = insn;
|
||||
|
||||
flush_icache_range((unsigned long)insn_p,
|
||||
(unsigned long)insn_p + sizeof(*insn_p));
|
||||
|
@ -503,6 +503,7 @@
|
||||
STOREB(t0, NBYTES-2(dst), .Ls_exc_p1\@)
|
||||
.Ldone\@:
|
||||
jr ra
|
||||
nop
|
||||
.if __memcpy == 1
|
||||
END(memcpy)
|
||||
.set __memcpy, 0
|
||||
|
@ -33,6 +33,7 @@
|
||||
|
||||
static struct node_data prealloc__node_data[MAX_NUMNODES];
|
||||
unsigned char __node_distances[MAX_NUMNODES][MAX_NUMNODES];
|
||||
EXPORT_SYMBOL(__node_distances);
|
||||
struct node_data *__node_data[MAX_NUMNODES];
|
||||
EXPORT_SYMBOL(__node_data);
|
||||
|
||||
|
@ -299,6 +299,7 @@ void __update_tlb(struct vm_area_struct * vma, unsigned long address, pte_t pte)
|
||||
|
||||
local_irq_save(flags);
|
||||
|
||||
htw_stop();
|
||||
pid = read_c0_entryhi() & ASID_MASK;
|
||||
address &= (PAGE_MASK << 1);
|
||||
write_c0_entryhi(address | pid);
|
||||
@ -346,6 +347,7 @@ void __update_tlb(struct vm_area_struct * vma, unsigned long address, pte_t pte)
|
||||
tlb_write_indexed();
|
||||
}
|
||||
tlbw_use_hazard();
|
||||
htw_start();
|
||||
flush_itlb_vm(vma);
|
||||
local_irq_restore(flags);
|
||||
}
|
||||
@ -422,6 +424,7 @@ __init int add_temporary_entry(unsigned long entrylo0, unsigned long entrylo1,
|
||||
|
||||
local_irq_save(flags);
|
||||
/* Save old context and create impossible VPN2 value */
|
||||
htw_stop();
|
||||
old_ctx = read_c0_entryhi();
|
||||
old_pagemask = read_c0_pagemask();
|
||||
wired = read_c0_wired();
|
||||
@ -443,6 +446,7 @@ __init int add_temporary_entry(unsigned long entrylo0, unsigned long entrylo1,
|
||||
|
||||
write_c0_entryhi(old_ctx);
|
||||
write_c0_pagemask(old_pagemask);
|
||||
htw_start();
|
||||
out:
|
||||
local_irq_restore(flags);
|
||||
return ret;
|
||||
|
@ -92,7 +92,7 @@ static inline int unwind_user_frame(struct stackframe *old_frame,
|
||||
/* This marks the end of the previous function,
|
||||
which means we overran. */
|
||||
break;
|
||||
stack_size = (unsigned) stack_adjustment;
|
||||
stack_size = (unsigned long) stack_adjustment;
|
||||
} else if (is_ra_save_ins(&ip)) {
|
||||
int ra_slot = ip.i_format.simmediate;
|
||||
if (ra_slot < 0)
|
||||
|
@ -107,6 +107,7 @@ static void router_recurse(klrou_t *router_a, klrou_t *router_b, int depth)
|
||||
}
|
||||
|
||||
unsigned char __node_distances[MAX_COMPACT_NODES][MAX_COMPACT_NODES];
|
||||
EXPORT_SYMBOL(__node_distances);
|
||||
|
||||
static int __init compute_node_distance(nasid_t nasid_a, nasid_t nasid_b)
|
||||
{
|
||||
|
@ -9,6 +9,8 @@
|
||||
#include <asm/errno.h>
|
||||
#include <asm-generic/uaccess-unaligned.h>
|
||||
|
||||
#include <linux/bug.h>
|
||||
|
||||
#define VERIFY_READ 0
|
||||
#define VERIFY_WRITE 1
|
||||
|
||||
@ -28,11 +30,6 @@
|
||||
* that put_user is the same as __put_user, etc.
|
||||
*/
|
||||
|
||||
extern int __get_kernel_bad(void);
|
||||
extern int __get_user_bad(void);
|
||||
extern int __put_kernel_bad(void);
|
||||
extern int __put_user_bad(void);
|
||||
|
||||
static inline long access_ok(int type, const void __user * addr,
|
||||
unsigned long size)
|
||||
{
|
||||
@ -43,8 +40,8 @@ static inline long access_ok(int type, const void __user * addr,
|
||||
#define get_user __get_user
|
||||
|
||||
#if !defined(CONFIG_64BIT)
|
||||
#define LDD_KERNEL(ptr) __get_kernel_bad();
|
||||
#define LDD_USER(ptr) __get_user_bad();
|
||||
#define LDD_KERNEL(ptr) BUILD_BUG()
|
||||
#define LDD_USER(ptr) BUILD_BUG()
|
||||
#define STD_KERNEL(x, ptr) __put_kernel_asm64(x,ptr)
|
||||
#define STD_USER(x, ptr) __put_user_asm64(x,ptr)
|
||||
#define ASM_WORD_INSN ".word\t"
|
||||
@ -94,7 +91,7 @@ struct exception_data {
|
||||
case 2: __get_kernel_asm("ldh",ptr); break; \
|
||||
case 4: __get_kernel_asm("ldw",ptr); break; \
|
||||
case 8: LDD_KERNEL(ptr); break; \
|
||||
default: __get_kernel_bad(); break; \
|
||||
default: BUILD_BUG(); break; \
|
||||
} \
|
||||
} \
|
||||
else { \
|
||||
@ -103,7 +100,7 @@ struct exception_data {
|
||||
case 2: __get_user_asm("ldh",ptr); break; \
|
||||
case 4: __get_user_asm("ldw",ptr); break; \
|
||||
case 8: LDD_USER(ptr); break; \
|
||||
default: __get_user_bad(); break; \
|
||||
default: BUILD_BUG(); break; \
|
||||
} \
|
||||
} \
|
||||
\
|
||||
@ -136,7 +133,7 @@ struct exception_data {
|
||||
case 2: __put_kernel_asm("sth",__x,ptr); break; \
|
||||
case 4: __put_kernel_asm("stw",__x,ptr); break; \
|
||||
case 8: STD_KERNEL(__x,ptr); break; \
|
||||
default: __put_kernel_bad(); break; \
|
||||
default: BUILD_BUG(); break; \
|
||||
} \
|
||||
} \
|
||||
else { \
|
||||
@ -145,7 +142,7 @@ struct exception_data {
|
||||
case 2: __put_user_asm("sth",__x,ptr); break; \
|
||||
case 4: __put_user_asm("stw",__x,ptr); break; \
|
||||
case 8: STD_USER(__x,ptr); break; \
|
||||
default: __put_user_bad(); break; \
|
||||
default: BUILD_BUG(); break; \
|
||||
} \
|
||||
} \
|
||||
\
|
||||
|
@ -1,13 +1,7 @@
|
||||
#ifndef __ASM_PARISC_BITSPERLONG_H
|
||||
#define __ASM_PARISC_BITSPERLONG_H
|
||||
|
||||
/*
|
||||
* using CONFIG_* outside of __KERNEL__ is wrong,
|
||||
* __LP64__ was also removed from headers, so what
|
||||
* is the right approach on parisc?
|
||||
* -arnd
|
||||
*/
|
||||
#if (defined(__KERNEL__) && defined(CONFIG_64BIT)) || defined (__LP64__)
|
||||
#if defined(__LP64__)
|
||||
#define __BITS_PER_LONG 64
|
||||
#define SHIFT_PER_LONG 6
|
||||
#else
|
||||
|
@ -1,6 +1,8 @@
|
||||
#ifndef _PARISC_MSGBUF_H
|
||||
#define _PARISC_MSGBUF_H
|
||||
|
||||
#include <asm/bitsperlong.h>
|
||||
|
||||
/*
|
||||
* The msqid64_ds structure for parisc architecture, copied from sparc.
|
||||
* Note extra padding because this structure is passed back and forth
|
||||
@ -13,15 +15,15 @@
|
||||
|
||||
struct msqid64_ds {
|
||||
struct ipc64_perm msg_perm;
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad1;
|
||||
#endif
|
||||
__kernel_time_t msg_stime; /* last msgsnd time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad2;
|
||||
#endif
|
||||
__kernel_time_t msg_rtime; /* last msgrcv time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad3;
|
||||
#endif
|
||||
__kernel_time_t msg_ctime; /* last change time */
|
||||
|
@ -1,6 +1,8 @@
|
||||
#ifndef _PARISC_SEMBUF_H
|
||||
#define _PARISC_SEMBUF_H
|
||||
|
||||
#include <asm/bitsperlong.h>
|
||||
|
||||
/*
|
||||
* The semid64_ds structure for parisc architecture.
|
||||
* Note extra padding because this structure is passed back and forth
|
||||
@ -13,11 +15,11 @@
|
||||
|
||||
struct semid64_ds {
|
||||
struct ipc64_perm sem_perm; /* permissions .. see ipc.h */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad1;
|
||||
#endif
|
||||
__kernel_time_t sem_otime; /* last semop time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad2;
|
||||
#endif
|
||||
__kernel_time_t sem_ctime; /* last change time */
|
||||
|
@ -1,6 +1,8 @@
|
||||
#ifndef _PARISC_SHMBUF_H
|
||||
#define _PARISC_SHMBUF_H
|
||||
|
||||
#include <asm/bitsperlong.h>
|
||||
|
||||
/*
|
||||
* The shmid64_ds structure for parisc architecture.
|
||||
* Note extra padding because this structure is passed back and forth
|
||||
@ -13,19 +15,19 @@
|
||||
|
||||
struct shmid64_ds {
|
||||
struct ipc64_perm shm_perm; /* operation perms */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad1;
|
||||
#endif
|
||||
__kernel_time_t shm_atime; /* last attach time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad2;
|
||||
#endif
|
||||
__kernel_time_t shm_dtime; /* last detach time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad3;
|
||||
#endif
|
||||
__kernel_time_t shm_ctime; /* last change time */
|
||||
#ifndef CONFIG_64BIT
|
||||
#if __BITS_PER_LONG != 64
|
||||
unsigned int __pad4;
|
||||
#endif
|
||||
size_t shm_segsz; /* size of segment (bytes) */
|
||||
@ -36,23 +38,16 @@ struct shmid64_ds {
|
||||
unsigned int __unused2;
|
||||
};
|
||||
|
||||
#ifdef CONFIG_64BIT
|
||||
/* The 'unsigned int' (formerly 'unsigned long') data types below will
|
||||
* ensure that a 32-bit app calling shmctl(*,IPC_INFO,*) will work on
|
||||
* a wide kernel, but if some of these values are meant to contain pointers
|
||||
* they may need to be 'long long' instead. -PB XXX FIXME
|
||||
*/
|
||||
#endif
|
||||
struct shminfo64 {
|
||||
unsigned int shmmax;
|
||||
unsigned int shmmin;
|
||||
unsigned int shmmni;
|
||||
unsigned int shmseg;
|
||||
unsigned int shmall;
|
||||
unsigned int __unused1;
|
||||
unsigned int __unused2;
|
||||
unsigned int __unused3;
|
||||
unsigned int __unused4;
|
||||
unsigned long shmmax;
|
||||
unsigned long shmmin;
|
||||
unsigned long shmmni;
|
||||
unsigned long shmseg;
|
||||
unsigned long shmall;
|
||||
unsigned long __unused1;
|
||||
unsigned long __unused2;
|
||||
unsigned long __unused3;
|
||||
unsigned long __unused4;
|
||||
};
|
||||
|
||||
#endif /* _PARISC_SHMBUF_H */
|
||||
|
@ -85,7 +85,7 @@
|
||||
struct siginfo;
|
||||
|
||||
/* Type of a signal handler. */
|
||||
#ifdef CONFIG_64BIT
|
||||
#if defined(__LP64__)
|
||||
/* function pointers on 64-bit parisc are pointers to little structs and the
|
||||
* compiler doesn't support code which changes or tests the address of
|
||||
* the function in the little struct. This is really ugly -PB
|
||||
|
@ -833,8 +833,9 @@
|
||||
#define __NR_seccomp (__NR_Linux + 338)
|
||||
#define __NR_getrandom (__NR_Linux + 339)
|
||||
#define __NR_memfd_create (__NR_Linux + 340)
|
||||
#define __NR_bpf (__NR_Linux + 341)
|
||||
|
||||
#define __NR_Linux_syscalls (__NR_memfd_create + 1)
|
||||
#define __NR_Linux_syscalls (__NR_bpf + 1)
|
||||
|
||||
|
||||
#define __IGNORE_select /* newselect */
|
||||
|
@ -286,11 +286,11 @@
|
||||
ENTRY_COMP(msgsnd)
|
||||
ENTRY_COMP(msgrcv)
|
||||
ENTRY_SAME(msgget) /* 190 */
|
||||
ENTRY_SAME(msgctl)
|
||||
ENTRY_SAME(shmat)
|
||||
ENTRY_COMP(msgctl)
|
||||
ENTRY_COMP(shmat)
|
||||
ENTRY_SAME(shmdt)
|
||||
ENTRY_SAME(shmget)
|
||||
ENTRY_SAME(shmctl) /* 195 */
|
||||
ENTRY_COMP(shmctl) /* 195 */
|
||||
ENTRY_SAME(ni_syscall) /* streams1 */
|
||||
ENTRY_SAME(ni_syscall) /* streams2 */
|
||||
ENTRY_SAME(lstat64)
|
||||
@ -323,7 +323,7 @@
|
||||
ENTRY_SAME(epoll_ctl) /* 225 */
|
||||
ENTRY_SAME(epoll_wait)
|
||||
ENTRY_SAME(remap_file_pages)
|
||||
ENTRY_SAME(semtimedop)
|
||||
ENTRY_COMP(semtimedop)
|
||||
ENTRY_COMP(mq_open)
|
||||
ENTRY_SAME(mq_unlink) /* 230 */
|
||||
ENTRY_COMP(mq_timedsend)
|
||||
@ -436,6 +436,7 @@
|
||||
ENTRY_SAME(seccomp)
|
||||
ENTRY_SAME(getrandom)
|
||||
ENTRY_SAME(memfd_create) /* 340 */
|
||||
ENTRY_SAME(bpf)
|
||||
|
||||
/* Nothing yet */
|
||||
|
||||
|
@ -361,7 +361,7 @@ static int fsl_msi_setup_hwirq(struct fsl_msi *msi, struct platform_device *dev,
|
||||
cascade_data->virq = virt_msir;
|
||||
msi->cascade_array[irq_index] = cascade_data;
|
||||
|
||||
ret = request_irq(virt_msir, fsl_msi_cascade, 0,
|
||||
ret = request_irq(virt_msir, fsl_msi_cascade, IRQF_NO_THREAD,
|
||||
"fsl-msi-cascade", cascade_data);
|
||||
if (ret) {
|
||||
dev_err(&dev->dev, "failed to request_irq(%d), ret = %d\n",
|
||||
|
@ -22,7 +22,7 @@
|
||||
|
||||
int atomic_add_return(int, atomic_t *);
|
||||
int atomic_cmpxchg(atomic_t *, int, int);
|
||||
#define atomic_xchg(v, new) (xchg(&((v)->counter), new))
|
||||
int atomic_xchg(atomic_t *, int);
|
||||
int __atomic_add_unless(atomic_t *, int, int);
|
||||
void atomic_set(atomic_t *, int);
|
||||
|
||||
|
@ -11,22 +11,14 @@
|
||||
#ifndef __ARCH_SPARC_CMPXCHG__
|
||||
#define __ARCH_SPARC_CMPXCHG__
|
||||
|
||||
static inline unsigned long xchg_u32(__volatile__ unsigned long *m, unsigned long val)
|
||||
{
|
||||
__asm__ __volatile__("swap [%2], %0"
|
||||
: "=&r" (val)
|
||||
: "0" (val), "r" (m)
|
||||
: "memory");
|
||||
return val;
|
||||
}
|
||||
|
||||
unsigned long __xchg_u32(volatile u32 *m, u32 new);
|
||||
void __xchg_called_with_bad_pointer(void);
|
||||
|
||||
static inline unsigned long __xchg(unsigned long x, __volatile__ void * ptr, int size)
|
||||
{
|
||||
switch (size) {
|
||||
case 4:
|
||||
return xchg_u32(ptr, x);
|
||||
return __xchg_u32(ptr, x);
|
||||
}
|
||||
__xchg_called_with_bad_pointer();
|
||||
return x;
|
||||
|
@ -9,9 +9,9 @@ static inline __u16 __arch_swab16p(const __u16 *addr)
|
||||
{
|
||||
__u16 ret;
|
||||
|
||||
__asm__ __volatile__ ("lduha [%1] %2, %0"
|
||||
__asm__ __volatile__ ("lduha [%2] %3, %0"
|
||||
: "=r" (ret)
|
||||
: "r" (addr), "i" (ASI_PL));
|
||||
: "m" (*addr), "r" (addr), "i" (ASI_PL));
|
||||
return ret;
|
||||
}
|
||||
#define __arch_swab16p __arch_swab16p
|
||||
@ -20,9 +20,9 @@ static inline __u32 __arch_swab32p(const __u32 *addr)
|
||||
{
|
||||
__u32 ret;
|
||||
|
||||
__asm__ __volatile__ ("lduwa [%1] %2, %0"
|
||||
__asm__ __volatile__ ("lduwa [%2] %3, %0"
|
||||
: "=r" (ret)
|
||||
: "r" (addr), "i" (ASI_PL));
|
||||
: "m" (*addr), "r" (addr), "i" (ASI_PL));
|
||||
return ret;
|
||||
}
|
||||
#define __arch_swab32p __arch_swab32p
|
||||
@ -31,9 +31,9 @@ static inline __u64 __arch_swab64p(const __u64 *addr)
|
||||
{
|
||||
__u64 ret;
|
||||
|
||||
__asm__ __volatile__ ("ldxa [%1] %2, %0"
|
||||
__asm__ __volatile__ ("ldxa [%2] %3, %0"
|
||||
: "=r" (ret)
|
||||
: "r" (addr), "i" (ASI_PL));
|
||||
: "m" (*addr), "r" (addr), "i" (ASI_PL));
|
||||
return ret;
|
||||
}
|
||||
#define __arch_swab64p __arch_swab64p
|
||||
|
@ -581,7 +581,7 @@ static irqreturn_t schizo_pcierr_intr_other(struct pci_pbm_info *pbm)
|
||||
{
|
||||
unsigned long csr_reg, csr, csr_error_bits;
|
||||
irqreturn_t ret = IRQ_NONE;
|
||||
u16 stat;
|
||||
u32 stat;
|
||||
|
||||
csr_reg = pbm->pbm_regs + SCHIZO_PCI_CTRL;
|
||||
csr = upa_readq(csr_reg);
|
||||
@ -617,7 +617,7 @@ static irqreturn_t schizo_pcierr_intr_other(struct pci_pbm_info *pbm)
|
||||
pbm->name);
|
||||
ret = IRQ_HANDLED;
|
||||
}
|
||||
pci_read_config_word(pbm->pci_bus->self, PCI_STATUS, &stat);
|
||||
pbm->pci_ops->read(pbm->pci_bus, 0, PCI_STATUS, 2, &stat);
|
||||
if (stat & (PCI_STATUS_PARITY |
|
||||
PCI_STATUS_SIG_TARGET_ABORT |
|
||||
PCI_STATUS_REC_TARGET_ABORT |
|
||||
@ -625,7 +625,7 @@ static irqreturn_t schizo_pcierr_intr_other(struct pci_pbm_info *pbm)
|
||||
PCI_STATUS_SIG_SYSTEM_ERROR)) {
|
||||
printk("%s: PCI bus error, PCI_STATUS[%04x]\n",
|
||||
pbm->name, stat);
|
||||
pci_write_config_word(pbm->pci_bus->self, PCI_STATUS, 0xffff);
|
||||
pbm->pci_ops->write(pbm->pci_bus, 0, PCI_STATUS, 2, 0xffff);
|
||||
ret = IRQ_HANDLED;
|
||||
}
|
||||
return ret;
|
||||
|
@ -816,13 +816,17 @@ void arch_send_call_function_single_ipi(int cpu)
|
||||
void __irq_entry smp_call_function_client(int irq, struct pt_regs *regs)
|
||||
{
|
||||
clear_softint(1 << irq);
|
||||
irq_enter();
|
||||
generic_smp_call_function_interrupt();
|
||||
irq_exit();
|
||||
}
|
||||
|
||||
void __irq_entry smp_call_function_single_client(int irq, struct pt_regs *regs)
|
||||
{
|
||||
clear_softint(1 << irq);
|
||||
irq_enter();
|
||||
generic_smp_call_function_single_interrupt();
|
||||
irq_exit();
|
||||
}
|
||||
|
||||
static void tsb_sync(void *info)
|
||||
|
@ -45,6 +45,19 @@ ATOMIC_OP(add, +=)
|
||||
|
||||
#undef ATOMIC_OP
|
||||
|
||||
int atomic_xchg(atomic_t *v, int new)
|
||||
{
|
||||
int ret;
|
||||
unsigned long flags;
|
||||
|
||||
spin_lock_irqsave(ATOMIC_HASH(v), flags);
|
||||
ret = v->counter;
|
||||
v->counter = new;
|
||||
spin_unlock_irqrestore(ATOMIC_HASH(v), flags);
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL(atomic_xchg);
|
||||
|
||||
int atomic_cmpxchg(atomic_t *v, int old, int new)
|
||||
{
|
||||
int ret;
|
||||
@ -137,3 +150,17 @@ unsigned long __cmpxchg_u32(volatile u32 *ptr, u32 old, u32 new)
|
||||
return (unsigned long)prev;
|
||||
}
|
||||
EXPORT_SYMBOL(__cmpxchg_u32);
|
||||
|
||||
unsigned long __xchg_u32(volatile u32 *ptr, u32 new)
|
||||
{
|
||||
unsigned long flags;
|
||||
u32 prev;
|
||||
|
||||
spin_lock_irqsave(ATOMIC_HASH(ptr), flags);
|
||||
prev = *ptr;
|
||||
*ptr = new;
|
||||
spin_unlock_irqrestore(ATOMIC_HASH(ptr), flags);
|
||||
|
||||
return (unsigned long)prev;
|
||||
}
|
||||
EXPORT_SYMBOL(__xchg_u32);
|
||||
|
@ -144,7 +144,7 @@ config INSTRUCTION_DECODER
|
||||
|
||||
config PERF_EVENTS_INTEL_UNCORE
|
||||
def_bool y
|
||||
depends on PERF_EVENTS && SUP_SUP_INTEL && PCI
|
||||
depends on PERF_EVENTS && CPU_SUP_INTEL && PCI
|
||||
|
||||
config OUTPUT_FORMAT
|
||||
string
|
||||
|
@ -76,8 +76,10 @@ suffix-$(CONFIG_KERNEL_XZ) := xz
|
||||
suffix-$(CONFIG_KERNEL_LZO) := lzo
|
||||
suffix-$(CONFIG_KERNEL_LZ4) := lz4
|
||||
|
||||
RUN_SIZE = $(shell objdump -h vmlinux | \
|
||||
perl $(srctree)/arch/x86/tools/calc_run_size.pl)
|
||||
quiet_cmd_mkpiggy = MKPIGGY $@
|
||||
cmd_mkpiggy = $(obj)/mkpiggy $< > $@ || ( rm -f $@ ; false )
|
||||
cmd_mkpiggy = $(obj)/mkpiggy $< $(RUN_SIZE) > $@ || ( rm -f $@ ; false )
|
||||
|
||||
targets += piggy.S
|
||||
$(obj)/piggy.S: $(obj)/vmlinux.bin.$(suffix-y) $(obj)/mkpiggy FORCE
|
||||
|
@ -207,7 +207,8 @@ relocated:
|
||||
* Do the decompression, and jump to the new kernel..
|
||||
*/
|
||||
/* push arguments for decompress_kernel: */
|
||||
pushl $z_output_len /* decompressed length */
|
||||
pushl $z_run_size /* size of kernel with .bss and .brk */
|
||||
pushl $z_output_len /* decompressed length, end of relocs */
|
||||
leal z_extract_offset_negative(%ebx), %ebp
|
||||
pushl %ebp /* output address */
|
||||
pushl $z_input_len /* input_len */
|
||||
@ -217,7 +218,7 @@ relocated:
|
||||
pushl %eax /* heap area */
|
||||
pushl %esi /* real mode pointer */
|
||||
call decompress_kernel /* returns kernel location in %eax */
|
||||
addl $24, %esp
|
||||
addl $28, %esp
|
||||
|
||||
/*
|
||||
* Jump to the decompressed kernel.
|
||||
|
@ -402,13 +402,16 @@ relocated:
|
||||
* Do the decompression, and jump to the new kernel..
|
||||
*/
|
||||
pushq %rsi /* Save the real mode argument */
|
||||
movq $z_run_size, %r9 /* size of kernel with .bss and .brk */
|
||||
pushq %r9
|
||||
movq %rsi, %rdi /* real mode address */
|
||||
leaq boot_heap(%rip), %rsi /* malloc area for uncompression */
|
||||
leaq input_data(%rip), %rdx /* input_data */
|
||||
movl $z_input_len, %ecx /* input_len */
|
||||
movq %rbp, %r8 /* output target address */
|
||||
movq $z_output_len, %r9 /* decompressed length */
|
||||
movq $z_output_len, %r9 /* decompressed length, end of relocs */
|
||||
call decompress_kernel /* returns kernel location in %rax */
|
||||
popq %r9
|
||||
popq %rsi
|
||||
|
||||
/*
|
||||
|
@ -358,7 +358,8 @@ asmlinkage __visible void *decompress_kernel(void *rmode, memptr heap,
|
||||
unsigned char *input_data,
|
||||
unsigned long input_len,
|
||||
unsigned char *output,
|
||||
unsigned long output_len)
|
||||
unsigned long output_len,
|
||||
unsigned long run_size)
|
||||
{
|
||||
real_mode = rmode;
|
||||
|
||||
@ -381,8 +382,14 @@ asmlinkage __visible void *decompress_kernel(void *rmode, memptr heap,
|
||||
free_mem_ptr = heap; /* Heap */
|
||||
free_mem_end_ptr = heap + BOOT_HEAP_SIZE;
|
||||
|
||||
output = choose_kernel_location(input_data, input_len,
|
||||
output, output_len);
|
||||
/*
|
||||
* The memory hole needed for the kernel is the larger of either
|
||||
* the entire decompressed kernel plus relocation table, or the
|
||||
* entire decompressed kernel plus .bss and .brk sections.
|
||||
*/
|
||||
output = choose_kernel_location(input_data, input_len, output,
|
||||
output_len > run_size ? output_len
|
||||
: run_size);
|
||||
|
||||
/* Validate memory location choices. */
|
||||
if ((unsigned long)output & (MIN_KERNEL_ALIGN - 1))
|
||||
|
@ -36,11 +36,13 @@ int main(int argc, char *argv[])
|
||||
uint32_t olen;
|
||||
long ilen;
|
||||
unsigned long offs;
|
||||
unsigned long run_size;
|
||||
FILE *f = NULL;
|
||||
int retval = 1;
|
||||
|
||||
if (argc < 2) {
|
||||
fprintf(stderr, "Usage: %s compressed_file\n", argv[0]);
|
||||
if (argc < 3) {
|
||||
fprintf(stderr, "Usage: %s compressed_file run_size\n",
|
||||
argv[0]);
|
||||
goto bail;
|
||||
}
|
||||
|
||||
@ -74,6 +76,7 @@ int main(int argc, char *argv[])
|
||||
offs += olen >> 12; /* Add 8 bytes for each 32K block */
|
||||
offs += 64*1024 + 128; /* Add 64K + 128 bytes slack */
|
||||
offs = (offs+4095) & ~4095; /* Round to a 4K boundary */
|
||||
run_size = atoi(argv[2]);
|
||||
|
||||
printf(".section \".rodata..compressed\",\"a\",@progbits\n");
|
||||
printf(".globl z_input_len\n");
|
||||
@ -85,6 +88,8 @@ int main(int argc, char *argv[])
|
||||
/* z_extract_offset_negative allows simplification of head_32.S */
|
||||
printf(".globl z_extract_offset_negative\n");
|
||||
printf("z_extract_offset_negative = -0x%lx\n", offs);
|
||||
printf(".globl z_run_size\n");
|
||||
printf("z_run_size = %lu\n", run_size);
|
||||
|
||||
printf(".globl input_data, input_data_end\n");
|
||||
printf("input_data:\n");
|
||||
|
@ -150,6 +150,7 @@ static inline void arch_send_call_function_ipi_mask(const struct cpumask *mask)
|
||||
}
|
||||
|
||||
void cpu_disable_common(void);
|
||||
void cpu_die_common(unsigned int cpu);
|
||||
void native_smp_prepare_boot_cpu(void);
|
||||
void native_smp_prepare_cpus(unsigned int max_cpus);
|
||||
void native_smp_cpus_done(unsigned int max_cpus);
|
||||
|
@ -146,6 +146,8 @@ EXPORT_PER_CPU_SYMBOL_GPL(gdt_page);
|
||||
|
||||
static int __init x86_xsave_setup(char *s)
|
||||
{
|
||||
if (strlen(s))
|
||||
return 0;
|
||||
setup_clear_cpu_cap(X86_FEATURE_XSAVE);
|
||||
setup_clear_cpu_cap(X86_FEATURE_XSAVEOPT);
|
||||
setup_clear_cpu_cap(X86_FEATURE_XSAVES);
|
||||
|
@ -108,12 +108,13 @@ static size_t compute_container_size(u8 *data, u32 total_size)
|
||||
* load_microcode_amd() to save equivalent cpu table and microcode patches in
|
||||
* kernel heap memory.
|
||||
*/
|
||||
static void apply_ucode_in_initrd(void *ucode, size_t size)
|
||||
static void apply_ucode_in_initrd(void *ucode, size_t size, bool save_patch)
|
||||
{
|
||||
struct equiv_cpu_entry *eq;
|
||||
size_t *cont_sz;
|
||||
u32 *header;
|
||||
u8 *data, **cont;
|
||||
u8 (*patch)[PATCH_MAX_SIZE];
|
||||
u16 eq_id = 0;
|
||||
int offset, left;
|
||||
u32 rev, eax, ebx, ecx, edx;
|
||||
@ -123,10 +124,12 @@ static void apply_ucode_in_initrd(void *ucode, size_t size)
|
||||
new_rev = (u32 *)__pa_nodebug(&ucode_new_rev);
|
||||
cont_sz = (size_t *)__pa_nodebug(&container_size);
|
||||
cont = (u8 **)__pa_nodebug(&container);
|
||||
patch = (u8 (*)[PATCH_MAX_SIZE])__pa_nodebug(&amd_ucode_patch);
|
||||
#else
|
||||
new_rev = &ucode_new_rev;
|
||||
cont_sz = &container_size;
|
||||
cont = &container;
|
||||
patch = &amd_ucode_patch;
|
||||
#endif
|
||||
|
||||
data = ucode;
|
||||
@ -213,9 +216,9 @@ static void apply_ucode_in_initrd(void *ucode, size_t size)
|
||||
rev = mc->hdr.patch_id;
|
||||
*new_rev = rev;
|
||||
|
||||
/* save ucode patch */
|
||||
memcpy(amd_ucode_patch, mc,
|
||||
min_t(u32, header[1], PATCH_MAX_SIZE));
|
||||
if (save_patch)
|
||||
memcpy(patch, mc,
|
||||
min_t(u32, header[1], PATCH_MAX_SIZE));
|
||||
}
|
||||
}
|
||||
|
||||
@ -246,7 +249,7 @@ void __init load_ucode_amd_bsp(void)
|
||||
*data = cp.data;
|
||||
*size = cp.size;
|
||||
|
||||
apply_ucode_in_initrd(cp.data, cp.size);
|
||||
apply_ucode_in_initrd(cp.data, cp.size, true);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_X86_32
|
||||
@ -263,7 +266,7 @@ void load_ucode_amd_ap(void)
|
||||
size_t *usize;
|
||||
void **ucode;
|
||||
|
||||
mc = (struct microcode_amd *)__pa(amd_ucode_patch);
|
||||
mc = (struct microcode_amd *)__pa_nodebug(amd_ucode_patch);
|
||||
if (mc->hdr.patch_id && mc->hdr.processor_rev_id) {
|
||||
__apply_microcode_amd(mc);
|
||||
return;
|
||||
@ -275,7 +278,7 @@ void load_ucode_amd_ap(void)
|
||||
if (!*ucode || !*usize)
|
||||
return;
|
||||
|
||||
apply_ucode_in_initrd(*ucode, *usize);
|
||||
apply_ucode_in_initrd(*ucode, *usize, false);
|
||||
}
|
||||
|
||||
static void __init collect_cpu_sig_on_bsp(void *arg)
|
||||
@ -339,7 +342,7 @@ void load_ucode_amd_ap(void)
|
||||
* AP has a different equivalence ID than BSP, looks like
|
||||
* mixed-steppings silicon so go through the ucode blob anew.
|
||||
*/
|
||||
apply_ucode_in_initrd(ucode_cpio.data, ucode_cpio.size);
|
||||
apply_ucode_in_initrd(ucode_cpio.data, ucode_cpio.size, false);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
@ -347,7 +350,9 @@ void load_ucode_amd_ap(void)
|
||||
int __init save_microcode_in_initrd_amd(void)
|
||||
{
|
||||
unsigned long cont;
|
||||
int retval = 0;
|
||||
enum ucode_state ret;
|
||||
u8 *cont_va;
|
||||
u32 eax;
|
||||
|
||||
if (!container)
|
||||
@ -355,13 +360,15 @@ int __init save_microcode_in_initrd_amd(void)
|
||||
|
||||
#ifdef CONFIG_X86_32
|
||||
get_bsp_sig();
|
||||
cont = (unsigned long)container;
|
||||
cont = (unsigned long)container;
|
||||
cont_va = __va(container);
|
||||
#else
|
||||
/*
|
||||
* We need the physical address of the container for both bitness since
|
||||
* boot_params.hdr.ramdisk_image is a physical address.
|
||||
*/
|
||||
cont = __pa(container);
|
||||
cont = __pa(container);
|
||||
cont_va = container;
|
||||
#endif
|
||||
|
||||
/*
|
||||
@ -372,6 +379,8 @@ int __init save_microcode_in_initrd_amd(void)
|
||||
if (relocated_ramdisk)
|
||||
container = (u8 *)(__va(relocated_ramdisk) +
|
||||
(cont - boot_params.hdr.ramdisk_image));
|
||||
else
|
||||
container = cont_va;
|
||||
|
||||
if (ucode_new_rev)
|
||||
pr_info("microcode: updated early to new patch_level=0x%08x\n",
|
||||
@ -382,7 +391,7 @@ int __init save_microcode_in_initrd_amd(void)
|
||||
|
||||
ret = load_microcode_amd(eax, container, container_size);
|
||||
if (ret != UCODE_OK)
|
||||
return -EINVAL;
|
||||
retval = -EINVAL;
|
||||
|
||||
/*
|
||||
* This will be freed any msec now, stash patches for the current
|
||||
@ -391,5 +400,5 @@ int __init save_microcode_in_initrd_amd(void)
|
||||
container = NULL;
|
||||
container_size = 0;
|
||||
|
||||
return 0;
|
||||
return retval;
|
||||
}
|
||||
|
@ -465,6 +465,14 @@ static void mc_bp_resume(void)
|
||||
|
||||
if (uci->valid && uci->mc)
|
||||
microcode_ops->apply_microcode(cpu);
|
||||
else if (!uci->mc)
|
||||
/*
|
||||
* We might resume and not have applied late microcode but still
|
||||
* have a newer patch stashed from the early loader. We don't
|
||||
* have it in uci->mc so we have to load it the same way we're
|
||||
* applying patches early on the APs.
|
||||
*/
|
||||
load_ucode_ap();
|
||||
}
|
||||
|
||||
static struct syscore_ops mc_syscore_ops = {
|
||||
|
@ -124,7 +124,7 @@ void __init load_ucode_bsp(void)
|
||||
static bool check_loader_disabled_ap(void)
|
||||
{
|
||||
#ifdef CONFIG_X86_32
|
||||
return __pa_nodebug(dis_ucode_ldr);
|
||||
return *((bool *)__pa_nodebug(&dis_ucode_ldr));
|
||||
#else
|
||||
return dis_ucode_ldr;
|
||||
#endif
|
||||
|
@ -486,14 +486,17 @@ static struct attribute_group snbep_uncore_qpi_format_group = {
|
||||
.attrs = snbep_uncore_qpi_formats_attr,
|
||||
};
|
||||
|
||||
#define SNBEP_UNCORE_MSR_OPS_COMMON_INIT() \
|
||||
.init_box = snbep_uncore_msr_init_box, \
|
||||
#define __SNBEP_UNCORE_MSR_OPS_COMMON_INIT() \
|
||||
.disable_box = snbep_uncore_msr_disable_box, \
|
||||
.enable_box = snbep_uncore_msr_enable_box, \
|
||||
.disable_event = snbep_uncore_msr_disable_event, \
|
||||
.enable_event = snbep_uncore_msr_enable_event, \
|
||||
.read_counter = uncore_msr_read_counter
|
||||
|
||||
#define SNBEP_UNCORE_MSR_OPS_COMMON_INIT() \
|
||||
__SNBEP_UNCORE_MSR_OPS_COMMON_INIT(), \
|
||||
.init_box = snbep_uncore_msr_init_box \
|
||||
|
||||
static struct intel_uncore_ops snbep_uncore_msr_ops = {
|
||||
SNBEP_UNCORE_MSR_OPS_COMMON_INIT(),
|
||||
};
|
||||
@ -1919,6 +1922,30 @@ static struct intel_uncore_type hswep_uncore_cbox = {
|
||||
.format_group = &hswep_uncore_cbox_format_group,
|
||||
};
|
||||
|
||||
/*
|
||||
* Write SBOX Initialization register bit by bit to avoid spurious #GPs
|
||||
*/
|
||||
static void hswep_uncore_sbox_msr_init_box(struct intel_uncore_box *box)
|
||||
{
|
||||
unsigned msr = uncore_msr_box_ctl(box);
|
||||
|
||||
if (msr) {
|
||||
u64 init = SNBEP_PMON_BOX_CTL_INT;
|
||||
u64 flags = 0;
|
||||
int i;
|
||||
|
||||
for_each_set_bit(i, (unsigned long *)&init, 64) {
|
||||
flags |= (1ULL << i);
|
||||
wrmsrl(msr, flags);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static struct intel_uncore_ops hswep_uncore_sbox_msr_ops = {
|
||||
__SNBEP_UNCORE_MSR_OPS_COMMON_INIT(),
|
||||
.init_box = hswep_uncore_sbox_msr_init_box
|
||||
};
|
||||
|
||||
static struct attribute *hswep_uncore_sbox_formats_attr[] = {
|
||||
&format_attr_event.attr,
|
||||
&format_attr_umask.attr,
|
||||
@ -1944,7 +1971,7 @@ static struct intel_uncore_type hswep_uncore_sbox = {
|
||||
.event_mask = HSWEP_S_MSR_PMON_RAW_EVENT_MASK,
|
||||
.box_ctl = HSWEP_S0_MSR_PMON_BOX_CTL,
|
||||
.msr_offset = HSWEP_SBOX_MSR_OFFSET,
|
||||
.ops = &snbep_uncore_msr_ops,
|
||||
.ops = &hswep_uncore_sbox_msr_ops,
|
||||
.format_group = &hswep_uncore_sbox_format_group,
|
||||
};
|
||||
|
||||
@ -2025,13 +2052,27 @@ static struct intel_uncore_type hswep_uncore_imc = {
|
||||
SNBEP_UNCORE_PCI_COMMON_INIT(),
|
||||
};
|
||||
|
||||
static unsigned hswep_uncore_irp_ctrs[] = {0xa0, 0xa8, 0xb0, 0xb8};
|
||||
|
||||
static u64 hswep_uncore_irp_read_counter(struct intel_uncore_box *box, struct perf_event *event)
|
||||
{
|
||||
struct pci_dev *pdev = box->pci_dev;
|
||||
struct hw_perf_event *hwc = &event->hw;
|
||||
u64 count = 0;
|
||||
|
||||
pci_read_config_dword(pdev, hswep_uncore_irp_ctrs[hwc->idx], (u32 *)&count);
|
||||
pci_read_config_dword(pdev, hswep_uncore_irp_ctrs[hwc->idx] + 4, (u32 *)&count + 1);
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
static struct intel_uncore_ops hswep_uncore_irp_ops = {
|
||||
.init_box = snbep_uncore_pci_init_box,
|
||||
.disable_box = snbep_uncore_pci_disable_box,
|
||||
.enable_box = snbep_uncore_pci_enable_box,
|
||||
.disable_event = ivbep_uncore_irp_disable_event,
|
||||
.enable_event = ivbep_uncore_irp_enable_event,
|
||||
.read_counter = ivbep_uncore_irp_read_counter,
|
||||
.read_counter = hswep_uncore_irp_read_counter,
|
||||
};
|
||||
|
||||
static struct intel_uncore_type hswep_uncore_irp = {
|
||||
|
@ -1484,7 +1484,7 @@ unsigned long syscall_trace_enter_phase1(struct pt_regs *regs, u32 arch)
|
||||
*/
|
||||
if (work & _TIF_NOHZ) {
|
||||
user_exit();
|
||||
work &= ~TIF_NOHZ;
|
||||
work &= ~_TIF_NOHZ;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SECCOMP
|
||||
|
@ -1303,10 +1303,14 @@ static void __ref remove_cpu_from_maps(int cpu)
|
||||
numa_remove_cpu(cpu);
|
||||
}
|
||||
|
||||
static DEFINE_PER_CPU(struct completion, die_complete);
|
||||
|
||||
void cpu_disable_common(void)
|
||||
{
|
||||
int cpu = smp_processor_id();
|
||||
|
||||
init_completion(&per_cpu(die_complete, smp_processor_id()));
|
||||
|
||||
remove_siblinginfo(cpu);
|
||||
|
||||
/* It's now safe to remove this processor from the online map */
|
||||
@ -1316,8 +1320,6 @@ void cpu_disable_common(void)
|
||||
fixup_irqs();
|
||||
}
|
||||
|
||||
static DEFINE_PER_CPU(struct completion, die_complete);
|
||||
|
||||
int native_cpu_disable(void)
|
||||
{
|
||||
int ret;
|
||||
@ -1327,16 +1329,21 @@ int native_cpu_disable(void)
|
||||
return ret;
|
||||
|
||||
clear_local_APIC();
|
||||
init_completion(&per_cpu(die_complete, smp_processor_id()));
|
||||
cpu_disable_common();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void cpu_die_common(unsigned int cpu)
|
||||
{
|
||||
wait_for_completion_timeout(&per_cpu(die_complete, cpu), HZ);
|
||||
}
|
||||
|
||||
void native_cpu_die(unsigned int cpu)
|
||||
{
|
||||
/* We don't do anything here: idle task is faking death itself. */
|
||||
wait_for_completion_timeout(&per_cpu(die_complete, cpu), HZ);
|
||||
|
||||
cpu_die_common(cpu);
|
||||
|
||||
/* They ack this in play_dead() by setting CPU_DEAD */
|
||||
if (per_cpu(cpu_state, cpu) == CPU_DEAD) {
|
||||
|
@ -41,9 +41,8 @@ csum_partial_copy_from_user(const void __user *src, void *dst,
|
||||
while (((unsigned long)src & 6) && len >= 2) {
|
||||
__u16 val16;
|
||||
|
||||
*errp = __get_user(val16, (const __u16 __user *)src);
|
||||
if (*errp)
|
||||
return isum;
|
||||
if (__get_user(val16, (const __u16 __user *)src))
|
||||
goto out_err;
|
||||
|
||||
*(__u16 *)dst = val16;
|
||||
isum = (__force __wsum)add32_with_carry(
|
||||
|
@ -1123,7 +1123,7 @@ void mark_rodata_ro(void)
|
||||
unsigned long end = (unsigned long) &__end_rodata_hpage_align;
|
||||
unsigned long text_end = PFN_ALIGN(&__stop___ex_table);
|
||||
unsigned long rodata_end = PFN_ALIGN(&__end_rodata);
|
||||
unsigned long all_end = PFN_ALIGN(&_end);
|
||||
unsigned long all_end;
|
||||
|
||||
printk(KERN_INFO "Write protecting the kernel read-only data: %luk\n",
|
||||
(end - start) >> 10);
|
||||
@ -1134,7 +1134,16 @@ void mark_rodata_ro(void)
|
||||
/*
|
||||
* The rodata/data/bss/brk section (but not the kernel text!)
|
||||
* should also be not-executable.
|
||||
*
|
||||
* We align all_end to PMD_SIZE because the existing mapping
|
||||
* is a full PMD. If we would align _brk_end to PAGE_SIZE we
|
||||
* split the PMD and the reminder between _brk_end and the end
|
||||
* of the PMD will remain mapped executable.
|
||||
*
|
||||
* Any PMD which was setup after the one which covers _brk_end
|
||||
* has been zapped already via cleanup_highmem().
|
||||
*/
|
||||
all_end = roundup((unsigned long)_brk_end, PMD_SIZE);
|
||||
set_memory_nx(rodata_start, (all_end - rodata_start) >> PAGE_SHIFT);
|
||||
|
||||
rodata_test();
|
||||
|
39
arch/x86/tools/calc_run_size.pl
Normal file
39
arch/x86/tools/calc_run_size.pl
Normal file
@ -0,0 +1,39 @@
|
||||
#!/usr/bin/perl
|
||||
#
|
||||
# Calculate the amount of space needed to run the kernel, including room for
|
||||
# the .bss and .brk sections.
|
||||
#
|
||||
# Usage:
|
||||
# objdump -h a.out | perl calc_run_size.pl
|
||||
use strict;
|
||||
|
||||
my $mem_size = 0;
|
||||
my $file_offset = 0;
|
||||
|
||||
my $sections=" *[0-9]+ \.(?:bss|brk) +";
|
||||
while (<>) {
|
||||
if (/^$sections([0-9a-f]+) +(?:[0-9a-f]+ +){2}([0-9a-f]+)/) {
|
||||
my $size = hex($1);
|
||||
my $offset = hex($2);
|
||||
$mem_size += $size;
|
||||
if ($file_offset == 0) {
|
||||
$file_offset = $offset;
|
||||
} elsif ($file_offset != $offset) {
|
||||
# BFD linker shows the same file offset in ELF.
|
||||
# Gold linker shows them as consecutive.
|
||||
next if ($file_offset + $mem_size == $offset + $size);
|
||||
|
||||
printf STDERR "file_offset: 0x%lx\n", $file_offset;
|
||||
printf STDERR "mem_size: 0x%lx\n", $mem_size;
|
||||
printf STDERR "offset: 0x%lx\n", $offset;
|
||||
printf STDERR "size: 0x%lx\n", $size;
|
||||
|
||||
die ".bss and .brk are non-contiguous\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ($file_offset == 0) {
|
||||
die "Never found .bss or .brk file offset\n";
|
||||
}
|
||||
printf("%d\n", $mem_size + $file_offset);
|
@ -510,6 +510,9 @@ static void xen_cpu_die(unsigned int cpu)
|
||||
current->state = TASK_UNINTERRUPTIBLE;
|
||||
schedule_timeout(HZ/10);
|
||||
}
|
||||
|
||||
cpu_die_common(cpu);
|
||||
|
||||
xen_smp_intr_free(cpu);
|
||||
xen_uninit_lock_cpu(cpu);
|
||||
xen_teardown_timer(cpu);
|
||||
|
@ -97,19 +97,22 @@ void blk_recalc_rq_segments(struct request *rq)
|
||||
|
||||
void blk_recount_segments(struct request_queue *q, struct bio *bio)
|
||||
{
|
||||
bool no_sg_merge = !!test_bit(QUEUE_FLAG_NO_SG_MERGE,
|
||||
&q->queue_flags);
|
||||
bool merge_not_need = bio->bi_vcnt < queue_max_segments(q);
|
||||
unsigned short seg_cnt;
|
||||
|
||||
if (no_sg_merge && !bio_flagged(bio, BIO_CLONED) &&
|
||||
merge_not_need)
|
||||
bio->bi_phys_segments = bio->bi_vcnt;
|
||||
/* estimate segment number by bi_vcnt for non-cloned bio */
|
||||
if (bio_flagged(bio, BIO_CLONED))
|
||||
seg_cnt = bio_segments(bio);
|
||||
else
|
||||
seg_cnt = bio->bi_vcnt;
|
||||
|
||||
if (test_bit(QUEUE_FLAG_NO_SG_MERGE, &q->queue_flags) &&
|
||||
(seg_cnt < queue_max_segments(q)))
|
||||
bio->bi_phys_segments = seg_cnt;
|
||||
else {
|
||||
struct bio *nxt = bio->bi_next;
|
||||
|
||||
bio->bi_next = NULL;
|
||||
bio->bi_phys_segments = __blk_recalc_rq_segments(q, bio,
|
||||
no_sg_merge && merge_not_need);
|
||||
bio->bi_phys_segments = __blk_recalc_rq_segments(q, bio, false);
|
||||
bio->bi_next = nxt;
|
||||
}
|
||||
|
||||
|
@ -107,11 +107,7 @@ static void blk_mq_usage_counter_release(struct percpu_ref *ref)
|
||||
wake_up_all(&q->mq_freeze_wq);
|
||||
}
|
||||
|
||||
/*
|
||||
* Guarantee no request is in use, so we can change any data structure of
|
||||
* the queue afterward.
|
||||
*/
|
||||
void blk_mq_freeze_queue(struct request_queue *q)
|
||||
static void blk_mq_freeze_queue_start(struct request_queue *q)
|
||||
{
|
||||
bool freeze;
|
||||
|
||||
@ -123,9 +119,23 @@ void blk_mq_freeze_queue(struct request_queue *q)
|
||||
percpu_ref_kill(&q->mq_usage_counter);
|
||||
blk_mq_run_queues(q, false);
|
||||
}
|
||||
}
|
||||
|
||||
static void blk_mq_freeze_queue_wait(struct request_queue *q)
|
||||
{
|
||||
wait_event(q->mq_freeze_wq, percpu_ref_is_zero(&q->mq_usage_counter));
|
||||
}
|
||||
|
||||
/*
|
||||
* Guarantee no request is in use, so we can change any data structure of
|
||||
* the queue afterward.
|
||||
*/
|
||||
void blk_mq_freeze_queue(struct request_queue *q)
|
||||
{
|
||||
blk_mq_freeze_queue_start(q);
|
||||
blk_mq_freeze_queue_wait(q);
|
||||
}
|
||||
|
||||
static void blk_mq_unfreeze_queue(struct request_queue *q)
|
||||
{
|
||||
bool wake;
|
||||
@ -1921,7 +1931,7 @@ void blk_mq_free_queue(struct request_queue *q)
|
||||
/* Basically redo blk_mq_init_queue with queue frozen */
|
||||
static void blk_mq_queue_reinit(struct request_queue *q)
|
||||
{
|
||||
blk_mq_freeze_queue(q);
|
||||
WARN_ON_ONCE(!q->mq_freeze_depth);
|
||||
|
||||
blk_mq_sysfs_unregister(q);
|
||||
|
||||
@ -1936,8 +1946,6 @@ static void blk_mq_queue_reinit(struct request_queue *q)
|
||||
blk_mq_map_swqueue(q);
|
||||
|
||||
blk_mq_sysfs_register(q);
|
||||
|
||||
blk_mq_unfreeze_queue(q);
|
||||
}
|
||||
|
||||
static int blk_mq_queue_reinit_notify(struct notifier_block *nb,
|
||||
@ -1956,8 +1964,25 @@ static int blk_mq_queue_reinit_notify(struct notifier_block *nb,
|
||||
return NOTIFY_OK;
|
||||
|
||||
mutex_lock(&all_q_mutex);
|
||||
|
||||
/*
|
||||
* We need to freeze and reinit all existing queues. Freezing
|
||||
* involves synchronous wait for an RCU grace period and doing it
|
||||
* one by one may take a long time. Start freezing all queues in
|
||||
* one swoop and then wait for the completions so that freezing can
|
||||
* take place in parallel.
|
||||
*/
|
||||
list_for_each_entry(q, &all_q_list, all_q_node)
|
||||
blk_mq_freeze_queue_start(q);
|
||||
list_for_each_entry(q, &all_q_list, all_q_node)
|
||||
blk_mq_freeze_queue_wait(q);
|
||||
|
||||
list_for_each_entry(q, &all_q_list, all_q_node)
|
||||
blk_mq_queue_reinit(q);
|
||||
|
||||
list_for_each_entry(q, &all_q_list, all_q_node)
|
||||
blk_mq_unfreeze_queue(q);
|
||||
|
||||
mutex_unlock(&all_q_mutex);
|
||||
return NOTIFY_OK;
|
||||
}
|
||||
|
@ -157,14 +157,16 @@ out:
|
||||
|
||||
int ioprio_best(unsigned short aprio, unsigned short bprio)
|
||||
{
|
||||
unsigned short aclass = IOPRIO_PRIO_CLASS(aprio);
|
||||
unsigned short bclass = IOPRIO_PRIO_CLASS(bprio);
|
||||
unsigned short aclass;
|
||||
unsigned short bclass;
|
||||
|
||||
if (aclass == IOPRIO_CLASS_NONE)
|
||||
aclass = IOPRIO_CLASS_BE;
|
||||
if (bclass == IOPRIO_CLASS_NONE)
|
||||
bclass = IOPRIO_CLASS_BE;
|
||||
if (!ioprio_valid(aprio))
|
||||
aprio = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_BE, IOPRIO_NORM);
|
||||
if (!ioprio_valid(bprio))
|
||||
bprio = IOPRIO_PRIO_VALUE(IOPRIO_CLASS_BE, IOPRIO_NORM);
|
||||
|
||||
aclass = IOPRIO_PRIO_CLASS(aprio);
|
||||
bclass = IOPRIO_PRIO_CLASS(bprio);
|
||||
if (aclass == bclass)
|
||||
return min(aprio, bprio);
|
||||
if (aclass > bclass)
|
||||
|
@ -458,7 +458,7 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
|
||||
rq = blk_get_request(q, in_len ? WRITE : READ, __GFP_WAIT);
|
||||
if (IS_ERR(rq)) {
|
||||
err = PTR_ERR(rq);
|
||||
goto error;
|
||||
goto error_free_buffer;
|
||||
}
|
||||
blk_rq_set_block_pc(rq);
|
||||
|
||||
@ -531,9 +531,11 @@ int sg_scsi_ioctl(struct request_queue *q, struct gendisk *disk, fmode_t mode,
|
||||
}
|
||||
|
||||
error:
|
||||
blk_put_request(rq);
|
||||
|
||||
error_free_buffer:
|
||||
kfree(buffer);
|
||||
if (rq)
|
||||
blk_put_request(rq);
|
||||
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(sg_scsi_ioctl);
|
||||
|
@ -290,6 +290,14 @@ static struct dmi_system_id acpi_osi_dmi_table[] __initdata = {
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "Vostro 3446"),
|
||||
},
|
||||
},
|
||||
{
|
||||
.callback = dmi_disable_osi_win8,
|
||||
.ident = "Dell Vostro 3546",
|
||||
.matches = {
|
||||
DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."),
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "Vostro 3546"),
|
||||
},
|
||||
},
|
||||
|
||||
/*
|
||||
* BIOS invocation of _OSI(Linux) is almost always a BIOS bug.
|
||||
|
@ -878,7 +878,7 @@ int acpi_dev_suspend_late(struct device *dev)
|
||||
return 0;
|
||||
|
||||
target_state = acpi_target_system_state();
|
||||
wakeup = device_may_wakeup(dev);
|
||||
wakeup = device_may_wakeup(dev) && acpi_device_can_wakeup(adev);
|
||||
error = acpi_device_wakeup(adev, target_state, wakeup);
|
||||
if (wakeup && error)
|
||||
return error;
|
||||
|
@ -60,6 +60,7 @@ enum board_ids {
|
||||
/* board IDs by feature in alphabetical order */
|
||||
board_ahci,
|
||||
board_ahci_ign_iferr,
|
||||
board_ahci_nomsi,
|
||||
board_ahci_noncq,
|
||||
board_ahci_nosntf,
|
||||
board_ahci_yes_fbs,
|
||||
@ -121,6 +122,13 @@ static const struct ata_port_info ahci_port_info[] = {
|
||||
.udma_mask = ATA_UDMA6,
|
||||
.port_ops = &ahci_ops,
|
||||
},
|
||||
[board_ahci_nomsi] = {
|
||||
AHCI_HFLAGS (AHCI_HFLAG_NO_MSI),
|
||||
.flags = AHCI_FLAG_COMMON,
|
||||
.pio_mask = ATA_PIO4,
|
||||
.udma_mask = ATA_UDMA6,
|
||||
.port_ops = &ahci_ops,
|
||||
},
|
||||
[board_ahci_noncq] = {
|
||||
AHCI_HFLAGS (AHCI_HFLAG_NO_NCQ),
|
||||
.flags = AHCI_FLAG_COMMON,
|
||||
@ -313,6 +321,11 @@ static const struct pci_device_id ahci_pci_tbl[] = {
|
||||
{ PCI_VDEVICE(INTEL, 0x8c87), board_ahci }, /* 9 Series RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0x8c8e), board_ahci }, /* 9 Series RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0x8c8f), board_ahci }, /* 9 Series RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0xa103), board_ahci }, /* Sunrise Point-H AHCI */
|
||||
{ PCI_VDEVICE(INTEL, 0xa103), board_ahci }, /* Sunrise Point-H RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0xa105), board_ahci }, /* Sunrise Point-H RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0xa107), board_ahci }, /* Sunrise Point-H RAID */
|
||||
{ PCI_VDEVICE(INTEL, 0xa10f), board_ahci }, /* Sunrise Point-H RAID */
|
||||
|
||||
/* JMicron 360/1/3/5/6, match class to avoid IDE function */
|
||||
{ PCI_VENDOR_ID_JMICRON, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID,
|
||||
@ -475,10 +488,10 @@ static const struct pci_device_id ahci_pci_tbl[] = {
|
||||
{ PCI_VDEVICE(ASMEDIA, 0x0612), board_ahci }, /* ASM1062 */
|
||||
|
||||
/*
|
||||
* Samsung SSDs found on some macbooks. NCQ times out.
|
||||
* https://bugzilla.kernel.org/show_bug.cgi?id=60731
|
||||
* Samsung SSDs found on some macbooks. NCQ times out if MSI is
|
||||
* enabled. https://bugzilla.kernel.org/show_bug.cgi?id=60731
|
||||
*/
|
||||
{ PCI_VDEVICE(SAMSUNG, 0x1600), board_ahci_noncq },
|
||||
{ PCI_VDEVICE(SAMSUNG, 0x1600), board_ahci_nomsi },
|
||||
|
||||
/* Enmotus */
|
||||
{ PCI_DEVICE(0x1c44, 0x8000), board_ahci },
|
||||
@ -514,12 +527,9 @@ MODULE_PARM_DESC(marvell_enable, "Marvell SATA via AHCI (1 = enabled)");
|
||||
static void ahci_pci_save_initial_config(struct pci_dev *pdev,
|
||||
struct ahci_host_priv *hpriv)
|
||||
{
|
||||
unsigned int force_port_map = 0;
|
||||
unsigned int mask_port_map = 0;
|
||||
|
||||
if (pdev->vendor == PCI_VENDOR_ID_JMICRON && pdev->device == 0x2361) {
|
||||
dev_info(&pdev->dev, "JMB361 has only one port\n");
|
||||
force_port_map = 1;
|
||||
hpriv->force_port_map = 1;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -529,9 +539,9 @@ static void ahci_pci_save_initial_config(struct pci_dev *pdev,
|
||||
*/
|
||||
if (hpriv->flags & AHCI_HFLAG_MV_PATA) {
|
||||
if (pdev->device == 0x6121)
|
||||
mask_port_map = 0x3;
|
||||
hpriv->mask_port_map = 0x3;
|
||||
else
|
||||
mask_port_map = 0xf;
|
||||
hpriv->mask_port_map = 0xf;
|
||||
dev_info(&pdev->dev,
|
||||
"Disabling your PATA port. Use the boot option 'ahci.marvell_enable=0' to avoid this.\n");
|
||||
}
|
||||
|
@ -1778,16 +1778,15 @@ static void ahci_handle_port_interrupt(struct ata_port *ap,
|
||||
}
|
||||
}
|
||||
|
||||
static void ahci_update_intr_status(struct ata_port *ap)
|
||||
static void ahci_port_intr(struct ata_port *ap)
|
||||
{
|
||||
void __iomem *port_mmio = ahci_port_base(ap);
|
||||
struct ahci_port_priv *pp = ap->private_data;
|
||||
u32 status;
|
||||
|
||||
status = readl(port_mmio + PORT_IRQ_STAT);
|
||||
writel(status, port_mmio + PORT_IRQ_STAT);
|
||||
|
||||
atomic_or(status, &pp->intr_status);
|
||||
ahci_handle_port_interrupt(ap, port_mmio, status);
|
||||
}
|
||||
|
||||
static irqreturn_t ahci_port_thread_fn(int irq, void *dev_instance)
|
||||
@ -1808,34 +1807,6 @@ static irqreturn_t ahci_port_thread_fn(int irq, void *dev_instance)
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
irqreturn_t ahci_thread_fn(int irq, void *dev_instance)
|
||||
{
|
||||
struct ata_host *host = dev_instance;
|
||||
struct ahci_host_priv *hpriv = host->private_data;
|
||||
u32 irq_masked = hpriv->port_map;
|
||||
unsigned int i;
|
||||
|
||||
for (i = 0; i < host->n_ports; i++) {
|
||||
struct ata_port *ap;
|
||||
|
||||
if (!(irq_masked & (1 << i)))
|
||||
continue;
|
||||
|
||||
ap = host->ports[i];
|
||||
if (ap) {
|
||||
ahci_port_thread_fn(irq, ap);
|
||||
VPRINTK("port %u\n", i);
|
||||
} else {
|
||||
VPRINTK("port %u (no irq)\n", i);
|
||||
if (ata_ratelimit())
|
||||
dev_warn(host->dev,
|
||||
"interrupt on disabled port %u\n", i);
|
||||
}
|
||||
}
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
static irqreturn_t ahci_multi_irqs_intr(int irq, void *dev_instance)
|
||||
{
|
||||
struct ata_port *ap = dev_instance;
|
||||
@ -1875,6 +1846,8 @@ static irqreturn_t ahci_single_irq_intr(int irq, void *dev_instance)
|
||||
|
||||
irq_masked = irq_stat & hpriv->port_map;
|
||||
|
||||
spin_lock(&host->lock);
|
||||
|
||||
for (i = 0; i < host->n_ports; i++) {
|
||||
struct ata_port *ap;
|
||||
|
||||
@ -1883,7 +1856,7 @@ static irqreturn_t ahci_single_irq_intr(int irq, void *dev_instance)
|
||||
|
||||
ap = host->ports[i];
|
||||
if (ap) {
|
||||
ahci_update_intr_status(ap);
|
||||
ahci_port_intr(ap);
|
||||
VPRINTK("port %u\n", i);
|
||||
} else {
|
||||
VPRINTK("port %u (no irq)\n", i);
|
||||
@ -1906,9 +1879,11 @@ static irqreturn_t ahci_single_irq_intr(int irq, void *dev_instance)
|
||||
*/
|
||||
writel(irq_stat, mmio + HOST_IRQ_STAT);
|
||||
|
||||
spin_unlock(&host->lock);
|
||||
|
||||
VPRINTK("EXIT\n");
|
||||
|
||||
return handled ? IRQ_WAKE_THREAD : IRQ_NONE;
|
||||
return IRQ_RETVAL(handled);
|
||||
}
|
||||
|
||||
unsigned int ahci_qc_issue(struct ata_queued_cmd *qc)
|
||||
@ -2320,8 +2295,13 @@ static int ahci_port_start(struct ata_port *ap)
|
||||
*/
|
||||
pp->intr_mask = DEF_PORT_IRQ;
|
||||
|
||||
spin_lock_init(&pp->lock);
|
||||
ap->lock = &pp->lock;
|
||||
/*
|
||||
* Switch to per-port locking in case each port has its own MSI vector.
|
||||
*/
|
||||
if ((hpriv->flags & AHCI_HFLAG_MULTI_MSI)) {
|
||||
spin_lock_init(&pp->lock);
|
||||
ap->lock = &pp->lock;
|
||||
}
|
||||
|
||||
ap->private_data = pp;
|
||||
|
||||
@ -2482,31 +2462,6 @@ out_free_irqs:
|
||||
return rc;
|
||||
}
|
||||
|
||||
static int ahci_host_activate_single_irq(struct ata_host *host, int irq,
|
||||
struct scsi_host_template *sht)
|
||||
{
|
||||
int i, rc;
|
||||
|
||||
rc = ata_host_start(host);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
rc = devm_request_threaded_irq(host->dev, irq, ahci_single_irq_intr,
|
||||
ahci_thread_fn, IRQF_SHARED,
|
||||
dev_driver_string(host->dev), host);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
for (i = 0; i < host->n_ports; i++)
|
||||
ata_port_desc(host->ports[i], "irq %d", irq);
|
||||
|
||||
rc = ata_host_register(host, sht);
|
||||
if (rc)
|
||||
devm_free_irq(host->dev, irq, host);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
/**
|
||||
* ahci_host_activate - start AHCI host, request IRQs and register it
|
||||
* @host: target ATA host
|
||||
@ -2532,7 +2487,8 @@ int ahci_host_activate(struct ata_host *host, int irq,
|
||||
if (hpriv->flags & AHCI_HFLAG_MULTI_MSI)
|
||||
rc = ahci_host_activate_multi_irqs(host, irq, sht);
|
||||
else
|
||||
rc = ahci_host_activate_single_irq(host, irq, sht);
|
||||
rc = ata_host_activate(host, irq, ahci_single_irq_intr,
|
||||
IRQF_SHARED, sht);
|
||||
return rc;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(ahci_host_activate);
|
||||
|
@ -146,6 +146,7 @@
|
||||
enum sata_rcar_type {
|
||||
RCAR_GEN1_SATA,
|
||||
RCAR_GEN2_SATA,
|
||||
RCAR_R8A7790_ES1_SATA,
|
||||
};
|
||||
|
||||
struct sata_rcar_priv {
|
||||
@ -763,6 +764,9 @@ static void sata_rcar_setup_port(struct ata_host *host)
|
||||
ap->udma_mask = ATA_UDMA6;
|
||||
ap->flags |= ATA_FLAG_SATA;
|
||||
|
||||
if (priv->type == RCAR_R8A7790_ES1_SATA)
|
||||
ap->flags |= ATA_FLAG_NO_DIPM;
|
||||
|
||||
ioaddr->cmd_addr = base + SDATA_REG;
|
||||
ioaddr->ctl_addr = base + SSDEVCON_REG;
|
||||
ioaddr->scr_addr = base + SCRSSTS_REG;
|
||||
@ -792,6 +796,7 @@ static void sata_rcar_init_controller(struct ata_host *host)
|
||||
sata_rcar_gen1_phy_init(priv);
|
||||
break;
|
||||
case RCAR_GEN2_SATA:
|
||||
case RCAR_R8A7790_ES1_SATA:
|
||||
sata_rcar_gen2_phy_init(priv);
|
||||
break;
|
||||
default:
|
||||
@ -837,10 +842,18 @@ static struct of_device_id sata_rcar_match[] = {
|
||||
.compatible = "renesas,sata-r8a7790",
|
||||
.data = (void *)RCAR_GEN2_SATA
|
||||
},
|
||||
{
|
||||
.compatible = "renesas,sata-r8a7790-es1",
|
||||
.data = (void *)RCAR_R8A7790_ES1_SATA
|
||||
},
|
||||
{
|
||||
.compatible = "renesas,sata-r8a7791",
|
||||
.data = (void *)RCAR_GEN2_SATA
|
||||
},
|
||||
{
|
||||
.compatible = "renesas,sata-r8a7793",
|
||||
.data = (void *)RCAR_GEN2_SATA
|
||||
},
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, sata_rcar_match);
|
||||
@ -849,7 +862,9 @@ static const struct platform_device_id sata_rcar_id_table[] = {
|
||||
{ "sata_rcar", RCAR_GEN1_SATA }, /* Deprecated by "sata-r8a7779" */
|
||||
{ "sata-r8a7779", RCAR_GEN1_SATA },
|
||||
{ "sata-r8a7790", RCAR_GEN2_SATA },
|
||||
{ "sata-r8a7790-es1", RCAR_R8A7790_ES1_SATA },
|
||||
{ "sata-r8a7791", RCAR_GEN2_SATA },
|
||||
{ "sata-r8a7793", RCAR_GEN2_SATA },
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(platform, sata_rcar_id_table);
|
||||
|
@ -361,9 +361,19 @@ static int __pm_genpd_save_device(struct pm_domain_data *pdd,
|
||||
struct device *dev = pdd->dev;
|
||||
int ret = 0;
|
||||
|
||||
if (gpd_data->need_restore)
|
||||
if (gpd_data->need_restore > 0)
|
||||
return 0;
|
||||
|
||||
/*
|
||||
* If the value of the need_restore flag is still unknown at this point,
|
||||
* we trust that pm_genpd_poweroff() has verified that the device is
|
||||
* already runtime PM suspended.
|
||||
*/
|
||||
if (gpd_data->need_restore < 0) {
|
||||
gpd_data->need_restore = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
mutex_unlock(&genpd->lock);
|
||||
|
||||
genpd_start_dev(genpd, dev);
|
||||
@ -373,7 +383,7 @@ static int __pm_genpd_save_device(struct pm_domain_data *pdd,
|
||||
mutex_lock(&genpd->lock);
|
||||
|
||||
if (!ret)
|
||||
gpd_data->need_restore = true;
|
||||
gpd_data->need_restore = 1;
|
||||
|
||||
return ret;
|
||||
}
|
||||
@ -389,12 +399,17 @@ static void __pm_genpd_restore_device(struct pm_domain_data *pdd,
|
||||
{
|
||||
struct generic_pm_domain_data *gpd_data = to_gpd_data(pdd);
|
||||
struct device *dev = pdd->dev;
|
||||
bool need_restore = gpd_data->need_restore;
|
||||
int need_restore = gpd_data->need_restore;
|
||||
|
||||
gpd_data->need_restore = false;
|
||||
gpd_data->need_restore = 0;
|
||||
mutex_unlock(&genpd->lock);
|
||||
|
||||
genpd_start_dev(genpd, dev);
|
||||
|
||||
/*
|
||||
* Call genpd_restore_dev() for recently added devices too (need_restore
|
||||
* is negative then).
|
||||
*/
|
||||
if (need_restore)
|
||||
genpd_restore_dev(genpd, dev);
|
||||
|
||||
@ -603,6 +618,7 @@ static void genpd_power_off_work_fn(struct work_struct *work)
|
||||
static int pm_genpd_runtime_suspend(struct device *dev)
|
||||
{
|
||||
struct generic_pm_domain *genpd;
|
||||
struct generic_pm_domain_data *gpd_data;
|
||||
bool (*stop_ok)(struct device *__dev);
|
||||
int ret;
|
||||
|
||||
@ -628,6 +644,16 @@ static int pm_genpd_runtime_suspend(struct device *dev)
|
||||
return 0;
|
||||
|
||||
mutex_lock(&genpd->lock);
|
||||
|
||||
/*
|
||||
* If we have an unknown state of the need_restore flag, it means none
|
||||
* of the runtime PM callbacks has been invoked yet. Let's update the
|
||||
* flag to reflect that the current state is active.
|
||||
*/
|
||||
gpd_data = to_gpd_data(dev->power.subsys_data->domain_data);
|
||||
if (gpd_data->need_restore < 0)
|
||||
gpd_data->need_restore = 0;
|
||||
|
||||
genpd->in_progress++;
|
||||
pm_genpd_poweroff(genpd);
|
||||
genpd->in_progress--;
|
||||
@ -1437,12 +1463,12 @@ int __pm_genpd_add_device(struct generic_pm_domain *genpd, struct device *dev,
|
||||
spin_unlock_irq(&dev->power.lock);
|
||||
|
||||
if (genpd->attach_dev)
|
||||
genpd->attach_dev(dev);
|
||||
genpd->attach_dev(genpd, dev);
|
||||
|
||||
mutex_lock(&gpd_data->lock);
|
||||
gpd_data->base.dev = dev;
|
||||
list_add_tail(&gpd_data->base.list_node, &genpd->dev_list);
|
||||
gpd_data->need_restore = genpd->status == GPD_STATE_POWER_OFF;
|
||||
gpd_data->need_restore = -1;
|
||||
gpd_data->td.constraint_changed = true;
|
||||
gpd_data->td.effective_constraint_ns = -1;
|
||||
mutex_unlock(&gpd_data->lock);
|
||||
@ -1499,7 +1525,7 @@ int pm_genpd_remove_device(struct generic_pm_domain *genpd,
|
||||
genpd->max_off_time_changed = true;
|
||||
|
||||
if (genpd->detach_dev)
|
||||
genpd->detach_dev(dev);
|
||||
genpd->detach_dev(genpd, dev);
|
||||
|
||||
spin_lock_irq(&dev->power.lock);
|
||||
|
||||
@ -1546,7 +1572,7 @@ void pm_genpd_dev_need_restore(struct device *dev, bool val)
|
||||
|
||||
psd = dev_to_psd(dev);
|
||||
if (psd && psd->domain_data)
|
||||
to_gpd_data(psd->domain_data)->need_restore = val;
|
||||
to_gpd_data(psd->domain_data)->need_restore = val ? 1 : 0;
|
||||
|
||||
spin_unlock_irqrestore(&dev->power.lock, flags);
|
||||
}
|
||||
|
@ -166,8 +166,8 @@ try_again:
|
||||
if (ret == -EPROBE_DEFER)
|
||||
dev_dbg(cpu_dev, "cpu%d clock not ready, retry\n", cpu);
|
||||
else
|
||||
dev_err(cpu_dev, "failed to get cpu%d clock: %d\n", ret,
|
||||
cpu);
|
||||
dev_err(cpu_dev, "failed to get cpu%d clock: %d\n", cpu,
|
||||
ret);
|
||||
} else {
|
||||
*cdev = cpu_dev;
|
||||
*creg = cpu_reg;
|
||||
|
@ -1022,7 +1022,8 @@ static struct cpufreq_policy *cpufreq_policy_restore(unsigned int cpu)
|
||||
|
||||
read_unlock_irqrestore(&cpufreq_driver_lock, flags);
|
||||
|
||||
policy->governor = NULL;
|
||||
if (policy)
|
||||
policy->governor = NULL;
|
||||
|
||||
return policy;
|
||||
}
|
||||
|
@ -271,7 +271,7 @@ struct pl330_config {
|
||||
#define DMAC_MODE_NS (1 << 0)
|
||||
unsigned int mode;
|
||||
unsigned int data_bus_width:10; /* In number of bits */
|
||||
unsigned int data_buf_dep:10;
|
||||
unsigned int data_buf_dep:11;
|
||||
unsigned int num_chan:4;
|
||||
unsigned int num_peri:6;
|
||||
u32 peri_ns;
|
||||
@ -2336,7 +2336,7 @@ static inline int get_burst_len(struct dma_pl330_desc *desc, size_t len)
|
||||
int burst_len;
|
||||
|
||||
burst_len = pl330->pcfg.data_bus_width / 8;
|
||||
burst_len *= pl330->pcfg.data_buf_dep;
|
||||
burst_len *= pl330->pcfg.data_buf_dep / pl330->pcfg.num_chan;
|
||||
burst_len >>= desc->rqcfg.brst_size;
|
||||
|
||||
/* src/dst_burst_len can't be more than 16 */
|
||||
@ -2459,16 +2459,25 @@ pl330_prep_dma_memcpy(struct dma_chan *chan, dma_addr_t dst,
|
||||
/* Select max possible burst size */
|
||||
burst = pl330->pcfg.data_bus_width / 8;
|
||||
|
||||
while (burst > 1) {
|
||||
if (!(len % burst))
|
||||
break;
|
||||
/*
|
||||
* Make sure we use a burst size that aligns with all the memcpy
|
||||
* parameters because our DMA programming algorithm doesn't cope with
|
||||
* transfers which straddle an entry in the DMA device's MFIFO.
|
||||
*/
|
||||
while ((src | dst | len) & (burst - 1))
|
||||
burst /= 2;
|
||||
}
|
||||
|
||||
desc->rqcfg.brst_size = 0;
|
||||
while (burst != (1 << desc->rqcfg.brst_size))
|
||||
desc->rqcfg.brst_size++;
|
||||
|
||||
/*
|
||||
* If burst size is smaller than bus width then make sure we only
|
||||
* transfer one at a time to avoid a burst stradling an MFIFO entry.
|
||||
*/
|
||||
if (desc->rqcfg.brst_size * 8 < pl330->pcfg.data_bus_width)
|
||||
desc->rqcfg.brst_len = 1;
|
||||
|
||||
desc->rqcfg.brst_len = get_burst_len(desc, len);
|
||||
|
||||
desc->txd.flags = flags;
|
||||
@ -2732,7 +2741,7 @@ pl330_probe(struct amba_device *adev, const struct amba_id *id)
|
||||
|
||||
|
||||
dev_info(&adev->dev,
|
||||
"Loaded driver for PL330 DMAC-%d\n", adev->periphid);
|
||||
"Loaded driver for PL330 DMAC-%x\n", adev->periphid);
|
||||
dev_info(&adev->dev,
|
||||
"\tDBUFF-%ux%ubytes Num_Chans-%u Num_Peri-%u Num_Events-%u\n",
|
||||
pcfg->data_buf_dep, pcfg->data_bus_width / 8, pcfg->num_chan,
|
||||
|
@ -230,30 +230,25 @@ static inline void sun6i_dma_dump_chan_regs(struct sun6i_dma_dev *sdev,
|
||||
readl(pchan->base + DMA_CHAN_CUR_PARA));
|
||||
}
|
||||
|
||||
static inline int convert_burst(u32 maxburst, u8 *burst)
|
||||
static inline s8 convert_burst(u32 maxburst)
|
||||
{
|
||||
switch (maxburst) {
|
||||
case 1:
|
||||
*burst = 0;
|
||||
break;
|
||||
return 0;
|
||||
case 8:
|
||||
*burst = 2;
|
||||
break;
|
||||
return 2;
|
||||
default:
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int convert_buswidth(enum dma_slave_buswidth addr_width, u8 *width)
|
||||
static inline s8 convert_buswidth(enum dma_slave_buswidth addr_width)
|
||||
{
|
||||
if ((addr_width < DMA_SLAVE_BUSWIDTH_1_BYTE) ||
|
||||
(addr_width > DMA_SLAVE_BUSWIDTH_4_BYTES))
|
||||
return -EINVAL;
|
||||
|
||||
*width = addr_width >> 1;
|
||||
return 0;
|
||||
return addr_width >> 1;
|
||||
}
|
||||
|
||||
static void *sun6i_dma_lli_add(struct sun6i_dma_lli *prev,
|
||||
@ -284,26 +279,25 @@ static inline int sun6i_dma_cfg_lli(struct sun6i_dma_lli *lli,
|
||||
struct dma_slave_config *config)
|
||||
{
|
||||
u8 src_width, dst_width, src_burst, dst_burst;
|
||||
int ret;
|
||||
|
||||
if (!config)
|
||||
return -EINVAL;
|
||||
|
||||
ret = convert_burst(config->src_maxburst, &src_burst);
|
||||
if (ret)
|
||||
return ret;
|
||||
src_burst = convert_burst(config->src_maxburst);
|
||||
if (src_burst)
|
||||
return src_burst;
|
||||
|
||||
ret = convert_burst(config->dst_maxburst, &dst_burst);
|
||||
if (ret)
|
||||
return ret;
|
||||
dst_burst = convert_burst(config->dst_maxburst);
|
||||
if (dst_burst)
|
||||
return dst_burst;
|
||||
|
||||
ret = convert_buswidth(config->src_addr_width, &src_width);
|
||||
if (ret)
|
||||
return ret;
|
||||
src_width = convert_buswidth(config->src_addr_width);
|
||||
if (src_width)
|
||||
return src_width;
|
||||
|
||||
ret = convert_buswidth(config->dst_addr_width, &dst_width);
|
||||
if (ret)
|
||||
return ret;
|
||||
dst_width = convert_buswidth(config->dst_addr_width);
|
||||
if (dst_width)
|
||||
return dst_width;
|
||||
|
||||
lli->cfg = DMA_CHAN_CFG_SRC_BURST(src_burst) |
|
||||
DMA_CHAN_CFG_SRC_WIDTH(src_width) |
|
||||
@ -542,11 +536,10 @@ static struct dma_async_tx_descriptor *sun6i_dma_prep_dma_memcpy(
|
||||
{
|
||||
struct sun6i_dma_dev *sdev = to_sun6i_dma_dev(chan->device);
|
||||
struct sun6i_vchan *vchan = to_sun6i_vchan(chan);
|
||||
struct dma_slave_config *sconfig = &vchan->cfg;
|
||||
struct sun6i_dma_lli *v_lli;
|
||||
struct sun6i_desc *txd;
|
||||
dma_addr_t p_lli;
|
||||
int ret;
|
||||
s8 burst, width;
|
||||
|
||||
dev_dbg(chan2dev(chan),
|
||||
"%s; chan: %d, dest: %pad, src: %pad, len: %zu. flags: 0x%08lx\n",
|
||||
@ -565,14 +558,21 @@ static struct dma_async_tx_descriptor *sun6i_dma_prep_dma_memcpy(
|
||||
goto err_txd_free;
|
||||
}
|
||||
|
||||
ret = sun6i_dma_cfg_lli(v_lli, src, dest, len, sconfig);
|
||||
if (ret)
|
||||
goto err_dma_free;
|
||||
v_lli->src = src;
|
||||
v_lli->dst = dest;
|
||||
v_lli->len = len;
|
||||
v_lli->para = NORMAL_WAIT;
|
||||
|
||||
burst = convert_burst(8);
|
||||
width = convert_buswidth(DMA_SLAVE_BUSWIDTH_4_BYTES);
|
||||
v_lli->cfg |= DMA_CHAN_CFG_SRC_DRQ(DRQ_SDRAM) |
|
||||
DMA_CHAN_CFG_DST_DRQ(DRQ_SDRAM) |
|
||||
DMA_CHAN_CFG_DST_LINEAR_MODE |
|
||||
DMA_CHAN_CFG_SRC_LINEAR_MODE;
|
||||
DMA_CHAN_CFG_SRC_LINEAR_MODE |
|
||||
DMA_CHAN_CFG_SRC_BURST(burst) |
|
||||
DMA_CHAN_CFG_SRC_WIDTH(width) |
|
||||
DMA_CHAN_CFG_DST_BURST(burst) |
|
||||
DMA_CHAN_CFG_DST_WIDTH(width);
|
||||
|
||||
sun6i_dma_lli_add(NULL, v_lli, p_lli, txd);
|
||||
|
||||
@ -580,8 +580,6 @@ static struct dma_async_tx_descriptor *sun6i_dma_prep_dma_memcpy(
|
||||
|
||||
return vchan_tx_prep(&vchan->vc, &txd->vd, flags);
|
||||
|
||||
err_dma_free:
|
||||
dma_pool_free(sdev->pool, v_lli, p_lli);
|
||||
err_txd_free:
|
||||
kfree(txd);
|
||||
return NULL;
|
||||
@ -915,6 +913,7 @@ static int sun6i_dma_probe(struct platform_device *pdev)
|
||||
sdc->slave.device_prep_dma_memcpy = sun6i_dma_prep_dma_memcpy;
|
||||
sdc->slave.device_control = sun6i_dma_control;
|
||||
sdc->slave.chancnt = NR_MAX_VCHANS;
|
||||
sdc->slave.copy_align = 4;
|
||||
|
||||
sdc->slave.dev = &pdev->dev;
|
||||
|
||||
|
@ -1637,8 +1637,7 @@ static int dispatch_ioctl(struct client *client,
|
||||
_IOC_SIZE(cmd) > sizeof(buffer))
|
||||
return -ENOTTY;
|
||||
|
||||
if (_IOC_DIR(cmd) == _IOC_READ)
|
||||
memset(&buffer, 0, _IOC_SIZE(cmd));
|
||||
memset(&buffer, 0, sizeof(buffer));
|
||||
|
||||
if (_IOC_DIR(cmd) & _IOC_WRITE)
|
||||
if (copy_from_user(&buffer, arg, _IOC_SIZE(cmd)))
|
||||
|
@ -495,6 +495,12 @@ static struct component_match *exynos_drm_match_add(struct device *dev)
|
||||
|
||||
mutex_lock(&drm_component_lock);
|
||||
|
||||
/* Do not retry to probe if there is no any kms driver regitered. */
|
||||
if (list_empty(&drm_component_list)) {
|
||||
mutex_unlock(&drm_component_lock);
|
||||
return ERR_PTR(-ENODEV);
|
||||
}
|
||||
|
||||
list_for_each_entry(cdev, &drm_component_list, list) {
|
||||
/*
|
||||
* Add components to master only in case that crtc and
|
||||
@ -585,10 +591,21 @@ static int exynos_drm_platform_probe(struct platform_device *pdev)
|
||||
goto err_unregister_mixer_drv;
|
||||
#endif
|
||||
|
||||
match = exynos_drm_match_add(&pdev->dev);
|
||||
if (IS_ERR(match)) {
|
||||
ret = PTR_ERR(match);
|
||||
goto err_unregister_hdmi_drv;
|
||||
}
|
||||
|
||||
ret = component_master_add_with_match(&pdev->dev, &exynos_drm_ops,
|
||||
match);
|
||||
if (ret < 0)
|
||||
goto err_unregister_hdmi_drv;
|
||||
|
||||
#ifdef CONFIG_DRM_EXYNOS_G2D
|
||||
ret = platform_driver_register(&g2d_driver);
|
||||
if (ret < 0)
|
||||
goto err_unregister_hdmi_drv;
|
||||
goto err_del_component_master;
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_DRM_EXYNOS_FIMC
|
||||
@ -619,23 +636,9 @@ static int exynos_drm_platform_probe(struct platform_device *pdev)
|
||||
goto err_unregister_ipp_drv;
|
||||
#endif
|
||||
|
||||
match = exynos_drm_match_add(&pdev->dev);
|
||||
if (IS_ERR(match)) {
|
||||
ret = PTR_ERR(match);
|
||||
goto err_unregister_resources;
|
||||
}
|
||||
|
||||
ret = component_master_add_with_match(&pdev->dev, &exynos_drm_ops,
|
||||
match);
|
||||
if (ret < 0)
|
||||
goto err_unregister_resources;
|
||||
|
||||
return ret;
|
||||
|
||||
err_unregister_resources:
|
||||
|
||||
#ifdef CONFIG_DRM_EXYNOS_IPP
|
||||
exynos_platform_device_ipp_unregister();
|
||||
err_unregister_ipp_drv:
|
||||
platform_driver_unregister(&ipp_driver);
|
||||
err_unregister_gsc_drv:
|
||||
@ -658,9 +661,11 @@ err_unregister_g2d_drv:
|
||||
|
||||
#ifdef CONFIG_DRM_EXYNOS_G2D
|
||||
platform_driver_unregister(&g2d_driver);
|
||||
err_unregister_hdmi_drv:
|
||||
err_del_component_master:
|
||||
#endif
|
||||
component_master_del(&pdev->dev, &exynos_drm_ops);
|
||||
|
||||
err_unregister_hdmi_drv:
|
||||
#ifdef CONFIG_DRM_EXYNOS_HDMI
|
||||
platform_driver_unregister(&hdmi_driver);
|
||||
err_unregister_mixer_drv:
|
||||
@ -741,6 +746,18 @@ static int exynos_drm_init(void)
|
||||
{
|
||||
int ret;
|
||||
|
||||
/*
|
||||
* Register device object only in case of Exynos SoC.
|
||||
*
|
||||
* Below codes resolves temporarily infinite loop issue incurred
|
||||
* by Exynos drm driver when using multi-platform kernel.
|
||||
* So these codes will be replaced with more generic way later.
|
||||
*/
|
||||
if (!of_machine_is_compatible("samsung,exynos3") &&
|
||||
!of_machine_is_compatible("samsung,exynos4") &&
|
||||
!of_machine_is_compatible("samsung,exynos5"))
|
||||
return -ENODEV;
|
||||
|
||||
exynos_drm_pdev = platform_device_register_simple("exynos-drm", -1,
|
||||
NULL, 0);
|
||||
if (IS_ERR(exynos_drm_pdev))
|
||||
|
@ -302,9 +302,12 @@ static void g2d_fini_cmdlist(struct g2d_data *g2d)
|
||||
struct exynos_drm_subdrv *subdrv = &g2d->subdrv;
|
||||
|
||||
kfree(g2d->cmdlist_node);
|
||||
dma_free_attrs(subdrv->drm_dev->dev, G2D_CMDLIST_POOL_SIZE,
|
||||
g2d->cmdlist_pool_virt,
|
||||
g2d->cmdlist_pool, &g2d->cmdlist_dma_attrs);
|
||||
|
||||
if (g2d->cmdlist_pool_virt && g2d->cmdlist_pool) {
|
||||
dma_free_attrs(subdrv->drm_dev->dev, G2D_CMDLIST_POOL_SIZE,
|
||||
g2d->cmdlist_pool_virt,
|
||||
g2d->cmdlist_pool, &g2d->cmdlist_dma_attrs);
|
||||
}
|
||||
}
|
||||
|
||||
static struct g2d_cmdlist_node *g2d_get_cmdlist(struct g2d_data *g2d)
|
||||
|
@ -1670,17 +1670,19 @@ int i915_driver_load(struct drm_device *dev, unsigned long flags)
|
||||
goto out_regs;
|
||||
|
||||
if (drm_core_check_feature(dev, DRIVER_MODESET)) {
|
||||
ret = i915_kick_out_vgacon(dev_priv);
|
||||
if (ret) {
|
||||
DRM_ERROR("failed to remove conflicting VGA console\n");
|
||||
goto out_gtt;
|
||||
}
|
||||
|
||||
/* WARNING: Apparently we must kick fbdev drivers before vgacon,
|
||||
* otherwise the vga fbdev driver falls over. */
|
||||
ret = i915_kick_out_firmware_fb(dev_priv);
|
||||
if (ret) {
|
||||
DRM_ERROR("failed to remove conflicting framebuffer drivers\n");
|
||||
goto out_gtt;
|
||||
}
|
||||
|
||||
ret = i915_kick_out_vgacon(dev_priv);
|
||||
if (ret) {
|
||||
DRM_ERROR("failed to remove conflicting VGA console\n");
|
||||
goto out_gtt;
|
||||
}
|
||||
}
|
||||
|
||||
pci_set_master(dev->pdev);
|
||||
|
@ -364,22 +364,9 @@ i915_gem_set_tiling(struct drm_device *dev, void *data,
|
||||
* has to also include the unfenced register the GPU uses
|
||||
* whilst executing a fenced command for an untiled object.
|
||||
*/
|
||||
|
||||
obj->map_and_fenceable =
|
||||
!i915_gem_obj_ggtt_bound(obj) ||
|
||||
(i915_gem_obj_ggtt_offset(obj) +
|
||||
obj->base.size <= dev_priv->gtt.mappable_end &&
|
||||
i915_gem_object_fence_ok(obj, args->tiling_mode));
|
||||
|
||||
/* Rebind if we need a change of alignment */
|
||||
if (!obj->map_and_fenceable) {
|
||||
u32 unfenced_align =
|
||||
i915_gem_get_gtt_alignment(dev, obj->base.size,
|
||||
args->tiling_mode,
|
||||
false);
|
||||
if (i915_gem_obj_ggtt_offset(obj) & (unfenced_align - 1))
|
||||
ret = i915_gem_object_ggtt_unbind(obj);
|
||||
}
|
||||
if (obj->map_and_fenceable &&
|
||||
!i915_gem_object_fence_ok(obj, args->tiling_mode))
|
||||
ret = i915_gem_object_ggtt_unbind(obj);
|
||||
|
||||
if (ret == 0) {
|
||||
obj->fence_dirty =
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user