Merge remote-tracking branch 'common/android-4.9' into hikey-4.9

Change-Id: Ib72a79566fc44bd93c2901b60daa16242ecb4053
This commit is contained in:
Dmitry Shmidt
2017-12-08 10:13:53 -08:00
239 changed files with 8523 additions and 1753 deletions
+2
View File
@@ -436,6 +436,8 @@ sysrq.txt
- info on the magic SysRq key. - info on the magic SysRq key.
target/ target/
- directory with info on generating TCM v4 fabric .ko modules - directory with info on generating TCM v4 fabric .ko modules
tee.txt
- info on the TEE subsystem and drivers
this_cpu_ops.txt this_cpu_ops.txt
- List rationale behind and the way to use this_cpu operations. - List rationale behind and the way to use this_cpu operations.
thermal/ thermal/
+36 -1
View File
@@ -51,6 +51,18 @@ Description:
Controls the dirty page count condition for the in-place-update Controls the dirty page count condition for the in-place-update
policies. policies.
What: /sys/fs/f2fs/<disk>/min_hot_blocks
Date: March 2017
Contact: "Jaegeuk Kim" <jaegeuk@kernel.org>
Description:
Controls the dirty page count condition for redefining hot data.
What: /sys/fs/f2fs/<disk>/min_ssr_sections
Date: October 2017
Contact: "Chao Yu" <yuchao0@huawei.com>
Description:
Controls the fee section threshold to trigger SSR allocation.
What: /sys/fs/f2fs/<disk>/max_small_discards What: /sys/fs/f2fs/<disk>/max_small_discards
Date: November 2013 Date: November 2013
Contact: "Jaegeuk Kim" <jaegeuk.kim@samsung.com> Contact: "Jaegeuk Kim" <jaegeuk.kim@samsung.com>
@@ -102,6 +114,12 @@ Contact: "Jaegeuk Kim" <jaegeuk@kernel.org>
Description: Description:
Controls the idle timing. Controls the idle timing.
What: /sys/fs/f2fs/<disk>/iostat_enable
Date: August 2017
Contact: "Chao Yu" <yuchao0@huawei.com>
Description:
Controls to enable/disable IO stat.
What: /sys/fs/f2fs/<disk>/ra_nid_pages What: /sys/fs/f2fs/<disk>/ra_nid_pages
Date: October 2015 Date: October 2015
Contact: "Chao Yu" <chao2.yu@samsung.com> Contact: "Chao Yu" <chao2.yu@samsung.com>
@@ -122,6 +140,12 @@ Contact: "Shuoran Liu" <liushuoran@huawei.com>
Description: Description:
Shows total written kbytes issued to disk. Shows total written kbytes issued to disk.
What: /sys/fs/f2fs/<disk>/feature
Date: July 2017
Contact: "Jaegeuk Kim" <jaegeuk@kernel.org>
Description:
Shows all enabled features in current device.
What: /sys/fs/f2fs/<disk>/inject_rate What: /sys/fs/f2fs/<disk>/inject_rate
Date: May 2016 Date: May 2016
Contact: "Sheng Yong" <shengyong1@huawei.com> Contact: "Sheng Yong" <shengyong1@huawei.com>
@@ -138,7 +162,18 @@ What: /sys/fs/f2fs/<disk>/reserved_blocks
Date: June 2017 Date: June 2017
Contact: "Chao Yu" <yuchao0@huawei.com> Contact: "Chao Yu" <yuchao0@huawei.com>
Description: Description:
Controls current reserved blocks in system. Controls target reserved blocks in system, the threshold
is soft, it could exceed current available user space.
What: /sys/fs/f2fs/<disk>/current_reserved_blocks
Date: October 2017
Contact: "Yunlong Song" <yunlong.song@huawei.com>
Contact: "Chao Yu" <yuchao0@huawei.com>
Description:
Shows current reserved blocks in system, it may be temporarily
smaller than target_reserved_blocks, but will gradually
increase to target_reserved_blocks when more free blocks are
freed by user later.
What: /sys/fs/f2fs/<disk>/gc_urgent What: /sys/fs/f2fs/<disk>/gc_urgent
Date: August 2017 Date: August 2017
@@ -0,0 +1,31 @@
OP-TEE Device Tree Bindings
OP-TEE is a piece of software using hardware features to provide a Trusted
Execution Environment. The security can be provided with ARM TrustZone, but
also by virtualization or a separate chip.
We're using "linaro" as the first part of the compatible property for
the reference implementation maintained by Linaro.
* OP-TEE based on ARM TrustZone required properties:
- compatible : should contain "linaro,optee-tz"
- method : The method of calling the OP-TEE Trusted OS. Permitted
values are:
"smc" : SMC #0, with the register assignments specified
in drivers/tee/optee/optee_smc.h
"hvc" : HVC #0, with the register assignments specified
in drivers/tee/optee/optee_smc.h
Example:
firmware {
optee {
compatible = "linaro,optee-tz";
method = "smc";
};
};
@@ -34,6 +34,10 @@ Required properties:
- reg: I2C address - reg: I2C address
Optional properties:
- smbus-timeout-disable: When set, the smbus timeout function will be disabled.
This is not supported on all chips.
Example: Example:
temp-sensor@1a { temp-sensor@1a {
@@ -156,6 +156,7 @@ lacie LaCie
lantiq Lantiq Semiconductor lantiq Lantiq Semiconductor
lenovo Lenovo Group Ltd. lenovo Lenovo Group Ltd.
lg LG Corporation lg LG Corporation
linaro Linaro Limited
linux Linux-specific binding linux Linux-specific binding
lltc Linear Technology Corporation lltc Linear Technology Corporation
lsi LSI Corp. (LSI Logic) lsi LSI Corp. (LSI Logic)
+1
View File
@@ -308,6 +308,7 @@ Code Seq#(hex) Include File Comments
0xA3 80-8F Port ACL in development: 0xA3 80-8F Port ACL in development:
<mailto:tlewis@mindspring.com> <mailto:tlewis@mindspring.com>
0xA3 90-9F linux/dtlk.h 0xA3 90-9F linux/dtlk.h
0xA4 00-1F uapi/linux/tee.h Generic TEE subsystem
0xAA 00-3F linux/uapi/linux/userfaultfd.h 0xAA 00-3F linux/uapi/linux/userfaultfd.h
0xAB 00-1F linux/nbd.h 0xAB 00-1F linux/nbd.h
0xAC 00-1F linux/raw.h 0xAC 00-1F linux/raw.h
+118
View File
@@ -0,0 +1,118 @@
TEE subsystem
This document describes the TEE subsystem in Linux.
A TEE (Trusted Execution Environment) is a trusted OS running in some
secure environment, for example, TrustZone on ARM CPUs, or a separate
secure co-processor etc. A TEE driver handles the details needed to
communicate with the TEE.
This subsystem deals with:
- Registration of TEE drivers
- Managing shared memory between Linux and the TEE
- Providing a generic API to the TEE
The TEE interface
=================
include/uapi/linux/tee.h defines the generic interface to a TEE.
User space (the client) connects to the driver by opening /dev/tee[0-9]* or
/dev/teepriv[0-9]*.
- TEE_IOC_SHM_ALLOC allocates shared memory and returns a file descriptor
which user space can mmap. When user space doesn't need the file
descriptor any more, it should be closed. When shared memory isn't needed
any longer it should be unmapped with munmap() to allow the reuse of
memory.
- TEE_IOC_VERSION lets user space know which TEE this driver handles and
the its capabilities.
- TEE_IOC_OPEN_SESSION opens a new session to a Trusted Application.
- TEE_IOC_INVOKE invokes a function in a Trusted Application.
- TEE_IOC_CANCEL may cancel an ongoing TEE_IOC_OPEN_SESSION or TEE_IOC_INVOKE.
- TEE_IOC_CLOSE_SESSION closes a session to a Trusted Application.
There are two classes of clients, normal clients and supplicants. The latter is
a helper process for the TEE to access resources in Linux, for example file
system access. A normal client opens /dev/tee[0-9]* and a supplicant opens
/dev/teepriv[0-9].
Much of the communication between clients and the TEE is opaque to the
driver. The main job for the driver is to receive requests from the
clients, forward them to the TEE and send back the results. In the case of
supplicants the communication goes in the other direction, the TEE sends
requests to the supplicant which then sends back the result.
OP-TEE driver
=============
The OP-TEE driver handles OP-TEE [1] based TEEs. Currently it is only the ARM
TrustZone based OP-TEE solution that is supported.
Lowest level of communication with OP-TEE builds on ARM SMC Calling
Convention (SMCCC) [2], which is the foundation for OP-TEE's SMC interface
[3] used internally by the driver. Stacked on top of that is OP-TEE Message
Protocol [4].
OP-TEE SMC interface provides the basic functions required by SMCCC and some
additional functions specific for OP-TEE. The most interesting functions are:
- OPTEE_SMC_FUNCID_CALLS_UID (part of SMCCC) returns the version information
which is then returned by TEE_IOC_VERSION
- OPTEE_SMC_CALL_GET_OS_UUID returns the particular OP-TEE implementation, used
to tell, for instance, a TrustZone OP-TEE apart from an OP-TEE running on a
separate secure co-processor.
- OPTEE_SMC_CALL_WITH_ARG drives the OP-TEE message protocol
- OPTEE_SMC_GET_SHM_CONFIG lets the driver and OP-TEE agree on which memory
range to used for shared memory between Linux and OP-TEE.
The GlobalPlatform TEE Client API [5] is implemented on top of the generic
TEE API.
Picture of the relationship between the different components in the
OP-TEE architecture.
User space Kernel Secure world
~~~~~~~~~~ ~~~~~~ ~~~~~~~~~~~~
+--------+ +-------------+
| Client | | Trusted |
+--------+ | Application |
/\ +-------------+
|| +----------+ /\
|| |tee- | ||
|| |supplicant| \/
|| +----------+ +-------------+
\/ /\ | TEE Internal|
+-------+ || | API |
+ TEE | || +--------+--------+ +-------------+
| Client| || | TEE | OP-TEE | | OP-TEE |
| API | \/ | subsys | driver | | Trusted OS |
+-------+----------------+----+-------+----+-----------+-------------+
| Generic TEE API | | OP-TEE MSG |
| IOCTL (TEE_IOC_*) | | SMCCC (OPTEE_SMC_CALL_*) |
+-----------------------------+ +------------------------------+
RPC (Remote Procedure Call) are requests from secure world to kernel driver
or tee-supplicant. An RPC is identified by a special range of SMCCC return
values from OPTEE_SMC_CALL_WITH_ARG. RPC messages which are intended for the
kernel are handled by the kernel driver. Other RPC messages will be forwarded to
tee-supplicant without further involvement of the driver, except switching
shared memory buffer representation.
References:
[1] https://github.com/OP-TEE/optee_os
[2] http://infocenter.arm.com/help/topic/com.arm.doc.den0028a/index.html
[3] drivers/tee/optee/optee_smc.h
[4] drivers/tee/optee/optee_msg.h
[5] http://www.globalplatform.org/specificationsdevice.asp look for
"TEE Client API Specification v1.0" and click download.
+13
View File
@@ -9010,6 +9010,11 @@ F: arch/*/oprofile/
F: drivers/oprofile/ F: drivers/oprofile/
F: include/linux/oprofile.h F: include/linux/oprofile.h
OP-TEE DRIVER
M: Jens Wiklander <jens.wiklander@linaro.org>
S: Maintained
F: drivers/tee/optee/
ORACLE CLUSTER FILESYSTEM 2 (OCFS2) ORACLE CLUSTER FILESYSTEM 2 (OCFS2)
M: Mark Fasheh <mfasheh@versity.com> M: Mark Fasheh <mfasheh@versity.com>
M: Joel Becker <jlbec@evilplan.org> M: Joel Becker <jlbec@evilplan.org>
@@ -10663,6 +10668,14 @@ F: drivers/hwtracing/stm/
F: include/linux/stm.h F: include/linux/stm.h
F: include/uapi/linux/stm.h F: include/uapi/linux/stm.h
TEE SUBSYSTEM
M: Jens Wiklander <jens.wiklander@linaro.org>
S: Maintained
F: include/linux/tee_drv.h
F: include/uapi/linux/tee.h
F: drivers/tee/
F: Documentation/tee.txt
THUNDERBOLT DRIVER THUNDERBOLT DRIVER
M: Andreas Noever <andreas.noever@gmail.com> M: Andreas Noever <andreas.noever@gmail.com>
S: Maintained S: Maintained
+1 -1
View File
@@ -1,6 +1,6 @@
VERSION = 4 VERSION = 4
PATCHLEVEL = 9 PATCHLEVEL = 9
SUBLEVEL = 65 SUBLEVEL = 67
EXTRAVERSION = EXTRAVERSION =
NAME = Roaring Lionus NAME = Roaring Lionus
@@ -192,7 +192,7 @@
interrupts-extended = <&intc 83 &omap3_pmx_core 0x11a>; interrupts-extended = <&intc 83 &omap3_pmx_core 0x11a>;
pinctrl-names = "default"; pinctrl-names = "default";
pinctrl-0 = <&mmc1_pins &mmc1_cd>; pinctrl-0 = <&mmc1_pins &mmc1_cd>;
cd-gpios = <&gpio4 31 IRQ_TYPE_LEVEL_LOW>; /* gpio127 */ cd-gpios = <&gpio4 31 GPIO_ACTIVE_LOW>; /* gpio127 */
vmmc-supply = <&vmmc1>; vmmc-supply = <&vmmc1>;
bus-width = <4>; bus-width = <4>;
cap-power-off-card; cap-power-off-card;
@@ -249,9 +249,9 @@
OMAP3_CORE1_IOPAD(0x2110, PIN_INPUT | MUX_MODE0) /* cam_xclka.cam_xclka */ OMAP3_CORE1_IOPAD(0x2110, PIN_INPUT | MUX_MODE0) /* cam_xclka.cam_xclka */
OMAP3_CORE1_IOPAD(0x2112, PIN_INPUT | MUX_MODE0) /* cam_pclk.cam_pclk */ OMAP3_CORE1_IOPAD(0x2112, PIN_INPUT | MUX_MODE0) /* cam_pclk.cam_pclk */
OMAP3_CORE1_IOPAD(0x2114, PIN_INPUT | MUX_MODE0) /* cam_d0.cam_d0 */ OMAP3_CORE1_IOPAD(0x2116, PIN_INPUT | MUX_MODE0) /* cam_d0.cam_d0 */
OMAP3_CORE1_IOPAD(0x2116, PIN_INPUT | MUX_MODE0) /* cam_d1.cam_d1 */ OMAP3_CORE1_IOPAD(0x2118, PIN_INPUT | MUX_MODE0) /* cam_d1.cam_d1 */
OMAP3_CORE1_IOPAD(0x2118, PIN_INPUT | MUX_MODE0) /* cam_d2.cam_d2 */ OMAP3_CORE1_IOPAD(0x211a, PIN_INPUT | MUX_MODE0) /* cam_d2.cam_d2 */
OMAP3_CORE1_IOPAD(0x211c, PIN_INPUT | MUX_MODE0) /* cam_d3.cam_d3 */ OMAP3_CORE1_IOPAD(0x211c, PIN_INPUT | MUX_MODE0) /* cam_d3.cam_d3 */
OMAP3_CORE1_IOPAD(0x211e, PIN_INPUT | MUX_MODE0) /* cam_d4.cam_d4 */ OMAP3_CORE1_IOPAD(0x211e, PIN_INPUT | MUX_MODE0) /* cam_d4.cam_d4 */
OMAP3_CORE1_IOPAD(0x2120, PIN_INPUT | MUX_MODE0) /* cam_d5.cam_d5 */ OMAP3_CORE1_IOPAD(0x2120, PIN_INPUT | MUX_MODE0) /* cam_d5.cam_d5 */
+1 -1
View File
@@ -162,7 +162,7 @@ static struct ti_st_plat_data wilink7_pdata = {
.nshutdown_gpio = 162, .nshutdown_gpio = 162,
.dev_name = "/dev/ttyO1", .dev_name = "/dev/ttyO1",
.flow_cntrl = 1, .flow_cntrl = 1,
.baud_rate = 300000, .baud_rate = 3000000,
}; };
static struct platform_device wl128x_device = { static struct platform_device wl128x_device = {
+2 -2
View File
@@ -126,8 +126,8 @@ static const struct prot_bits section_bits[] = {
.val = PMD_SECT_USER, .val = PMD_SECT_USER,
.set = "USR", .set = "USR",
}, { }, {
.mask = L_PMD_SECT_RDONLY, .mask = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
.val = L_PMD_SECT_RDONLY, .val = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
.set = "ro", .set = "ro",
.clear = "RW", .clear = "RW",
#elif __LINUX_ARM_ARCH__ >= 6 #elif __LINUX_ARM_ARCH__ >= 6
+2 -2
View File
@@ -619,8 +619,8 @@ static struct section_perm ro_perms[] = {
.start = (unsigned long)_stext, .start = (unsigned long)_stext,
.end = (unsigned long)__init_begin, .end = (unsigned long)__init_begin,
#ifdef CONFIG_ARM_LPAE #ifdef CONFIG_ARM_LPAE
.mask = ~L_PMD_SECT_RDONLY, .mask = ~(L_PMD_SECT_RDONLY | PMD_SECT_AP2),
.prot = L_PMD_SECT_RDONLY, .prot = L_PMD_SECT_RDONLY | PMD_SECT_AP2,
#else #else
.mask = ~(PMD_SECT_APX | PMD_SECT_AP_WRITE), .mask = ~(PMD_SECT_APX | PMD_SECT_AP_WRITE),
.prot = PMD_SECT_APX | PMD_SECT_AP_WRITE, .prot = PMD_SECT_APX | PMD_SECT_AP_WRITE,
+14
View File
@@ -91,6 +91,8 @@ extern unsigned long empty_zero_page[PAGE_SIZE / sizeof(unsigned long)];
((pte_val(pte) & (PTE_VALID | PTE_USER | PTE_UXN)) == (PTE_VALID | PTE_UXN)) ((pte_val(pte) & (PTE_VALID | PTE_USER | PTE_UXN)) == (PTE_VALID | PTE_UXN))
#define pte_valid_young(pte) \ #define pte_valid_young(pte) \
((pte_val(pte) & (PTE_VALID | PTE_AF)) == (PTE_VALID | PTE_AF)) ((pte_val(pte) & (PTE_VALID | PTE_AF)) == (PTE_VALID | PTE_AF))
#define pte_valid_user(pte) \
((pte_val(pte) & (PTE_VALID | PTE_USER)) == (PTE_VALID | PTE_USER))
/* /*
* Could the pte be present in the TLB? We must check mm_tlb_flush_pending * Could the pte be present in the TLB? We must check mm_tlb_flush_pending
@@ -100,6 +102,18 @@ extern unsigned long empty_zero_page[PAGE_SIZE / sizeof(unsigned long)];
#define pte_accessible(mm, pte) \ #define pte_accessible(mm, pte) \
(mm_tlb_flush_pending(mm) ? pte_present(pte) : pte_valid_young(pte)) (mm_tlb_flush_pending(mm) ? pte_present(pte) : pte_valid_young(pte))
/*
* p??_access_permitted() is true for valid user mappings (subject to the
* write permission check) other than user execute-only which do not have the
* PTE_USER bit set. PROT_NONE mappings do not have the PTE_VALID bit set.
*/
#define pte_access_permitted(pte, write) \
(pte_valid_user(pte) && (!(write) || pte_write(pte)))
#define pmd_access_permitted(pmd, write) \
(pte_access_permitted(pmd_pte(pmd), (write)))
#define pud_access_permitted(pud, write) \
(pte_access_permitted(pud_pte(pud), (write)))
static inline pte_t clear_pte_bit(pte_t pte, pgprot_t prot) static inline pte_t clear_pte_bit(pte_t pte, pgprot_t prot)
{ {
pte_val(pte) &= ~pgprot_val(prot); pte_val(pte) &= ~pgprot_val(prot);
+2 -4
View File
@@ -220,10 +220,8 @@ void update_vsyscall(struct timekeeper *tk)
if (!use_syscall) { if (!use_syscall) {
/* tkr_mono.cycle_last == tkr_raw.cycle_last */ /* tkr_mono.cycle_last == tkr_raw.cycle_last */
vdso_data->cs_cycle_last = tk->tkr_mono.cycle_last; vdso_data->cs_cycle_last = tk->tkr_mono.cycle_last;
vdso_data->raw_time_sec = tk->raw_time.tv_sec; vdso_data->raw_time_sec = tk->raw_sec;
vdso_data->raw_time_nsec = (tk->raw_time.tv_nsec << vdso_data->raw_time_nsec = tk->tkr_raw.xtime_nsec;
tk->tkr_raw.shift) +
tk->tkr_raw.xtime_nsec;
vdso_data->xtime_clock_sec = tk->xtime_sec; vdso_data->xtime_clock_sec = tk->xtime_sec;
vdso_data->xtime_clock_nsec = tk->tkr_mono.xtime_nsec; vdso_data->xtime_clock_nsec = tk->tkr_mono.xtime_nsec;
vdso_data->cs_mono_mult = tk->tkr_mono.mult; vdso_data->cs_mono_mult = tk->tkr_mono.mult;
+1 -1
View File
@@ -309,7 +309,7 @@ ENTRY(__kernel_clock_getres)
b.ne 4f b.ne 4f
ldr x2, 6f ldr x2, 6f
2: 2:
cbz w1, 3f cbz x1, 3f
stp xzr, x2, [x1] stp xzr, x2, [x1]
3: /* res == NULL. */ 3: /* res == NULL. */
+1 -1
View File
@@ -330,7 +330,7 @@ bcm47xx_leds_linksys_wrt54g3gv2[] __initconst = {
/* Verified on: WRT54GS V1.0 */ /* Verified on: WRT54GS V1.0 */
static const struct gpio_led static const struct gpio_led
bcm47xx_leds_linksys_wrt54g_type_0101[] __initconst = { bcm47xx_leds_linksys_wrt54g_type_0101[] __initconst = {
BCM47XX_GPIO_LED(0, "green", "wlan", 0, LEDS_GPIO_DEFSTATE_OFF), BCM47XX_GPIO_LED(0, "green", "wlan", 1, LEDS_GPIO_DEFSTATE_OFF),
BCM47XX_GPIO_LED(1, "green", "power", 0, LEDS_GPIO_DEFSTATE_ON), BCM47XX_GPIO_LED(1, "green", "power", 0, LEDS_GPIO_DEFSTATE_ON),
BCM47XX_GPIO_LED(7, "green", "dmz", 1, LEDS_GPIO_DEFSTATE_OFF), BCM47XX_GPIO_LED(7, "green", "dmz", 1, LEDS_GPIO_DEFSTATE_OFF),
}; };
-1
View File
@@ -22,7 +22,6 @@ dtb-$(CONFIG_DT_NONE) += \
bcm63268-comtrend-vr-3032u.dtb \ bcm63268-comtrend-vr-3032u.dtb \
bcm93384wvg.dtb \ bcm93384wvg.dtb \
bcm93384wvg_viper.dtb \ bcm93384wvg_viper.dtb \
bcm96358nb4ser.dtb \
bcm96368mvwg.dtb \ bcm96368mvwg.dtb \
bcm9ejtagprb.dtb \ bcm9ejtagprb.dtb \
bcm97125cbmb.dtb \ bcm97125cbmb.dtb \
+5 -3
View File
@@ -19,6 +19,9 @@
#include <asm/asmmacro-64.h> #include <asm/asmmacro-64.h>
#endif #endif
/* preprocessor replaces the fp in ".set fp=64" with $30 otherwise */
#undef fp
/* /*
* Helper macros for generating raw instruction encodings. * Helper macros for generating raw instruction encodings.
*/ */
@@ -105,6 +108,7 @@
.macro fpu_save_16odd thread .macro fpu_save_16odd thread
.set push .set push
.set mips64r2 .set mips64r2
.set fp=64
SET_HARDFLOAT SET_HARDFLOAT
sdc1 $f1, THREAD_FPR1(\thread) sdc1 $f1, THREAD_FPR1(\thread)
sdc1 $f3, THREAD_FPR3(\thread) sdc1 $f3, THREAD_FPR3(\thread)
@@ -163,6 +167,7 @@
.macro fpu_restore_16odd thread .macro fpu_restore_16odd thread
.set push .set push
.set mips64r2 .set mips64r2
.set fp=64
SET_HARDFLOAT SET_HARDFLOAT
ldc1 $f1, THREAD_FPR1(\thread) ldc1 $f1, THREAD_FPR1(\thread)
ldc1 $f3, THREAD_FPR3(\thread) ldc1 $f3, THREAD_FPR3(\thread)
@@ -234,9 +239,6 @@
.endm .endm
#ifdef TOOLCHAIN_SUPPORTS_MSA #ifdef TOOLCHAIN_SUPPORTS_MSA
/* preprocessor replaces the fp in ".set fp=64" with $30 otherwise */
#undef fp
.macro _cfcmsa rd, cs .macro _cfcmsa rd, cs
.set push .set push
.set mips32r2 .set mips32r2
+17
View File
@@ -647,6 +647,19 @@ static const struct user_regset_view user_mips64_view = {
.n = ARRAY_SIZE(mips64_regsets), .n = ARRAY_SIZE(mips64_regsets),
}; };
#ifdef CONFIG_MIPS32_N32
static const struct user_regset_view user_mipsn32_view = {
.name = "mipsn32",
.e_flags = EF_MIPS_ABI2,
.e_machine = ELF_ARCH,
.ei_osabi = ELF_OSABI,
.regsets = mips64_regsets,
.n = ARRAY_SIZE(mips64_regsets),
};
#endif /* CONFIG_MIPS32_N32 */
#endif /* CONFIG_64BIT */ #endif /* CONFIG_64BIT */
const struct user_regset_view *task_user_regset_view(struct task_struct *task) const struct user_regset_view *task_user_regset_view(struct task_struct *task)
@@ -657,6 +670,10 @@ const struct user_regset_view *task_user_regset_view(struct task_struct *task)
#ifdef CONFIG_MIPS32_O32 #ifdef CONFIG_MIPS32_O32
if (test_tsk_thread_flag(task, TIF_32BIT_REGS)) if (test_tsk_thread_flag(task, TIF_32BIT_REGS))
return &user_mips_view; return &user_mips_view;
#endif
#ifdef CONFIG_MIPS32_N32
if (test_tsk_thread_flag(task, TIF_32BIT_ADDR))
return &user_mipsn32_view;
#endif #endif
return &user_mips64_view; return &user_mips64_view;
#endif #endif
+1 -1
View File
@@ -121,7 +121,7 @@ static int wait_pciephy_busy(void)
else else
break; break;
if (retry++ > WAITRETRY_MAX) { if (retry++ > WAITRETRY_MAX) {
printk(KERN_WARN "PCIE-PHY retry failed.\n"); pr_warn("PCIE-PHY retry failed.\n");
return -1; return -1;
} }
} }
+2 -2
View File
@@ -141,8 +141,8 @@ static struct rt2880_pmx_func i2c_grp_mt7628[] = {
FUNC("i2c", 0, 4, 2), FUNC("i2c", 0, 4, 2),
}; };
static struct rt2880_pmx_func refclk_grp_mt7628[] = { FUNC("reclk", 0, 36, 1) }; static struct rt2880_pmx_func refclk_grp_mt7628[] = { FUNC("refclk", 0, 37, 1) };
static struct rt2880_pmx_func perst_grp_mt7628[] = { FUNC("perst", 0, 37, 1) }; static struct rt2880_pmx_func perst_grp_mt7628[] = { FUNC("perst", 0, 36, 1) };
static struct rt2880_pmx_func wdt_grp_mt7628[] = { FUNC("wdt", 0, 38, 1) }; static struct rt2880_pmx_func wdt_grp_mt7628[] = { FUNC("wdt", 0, 38, 1) };
static struct rt2880_pmx_func spi_grp_mt7628[] = { FUNC("spi", 0, 7, 4) }; static struct rt2880_pmx_func spi_grp_mt7628[] = { FUNC("spi", 0, 7, 4) };
+3 -3
View File
@@ -690,15 +690,15 @@ cas_action:
/* ELF32 Process entry path */ /* ELF32 Process entry path */
lws_compare_and_swap_2: lws_compare_and_swap_2:
#ifdef CONFIG_64BIT #ifdef CONFIG_64BIT
/* Clip the input registers */ /* Clip the input registers. We don't need to clip %r23 as we
only use it for word operations */
depdi 0, 31, 32, %r26 depdi 0, 31, 32, %r26
depdi 0, 31, 32, %r25 depdi 0, 31, 32, %r25
depdi 0, 31, 32, %r24 depdi 0, 31, 32, %r24
depdi 0, 31, 32, %r23
#endif #endif
/* Check the validity of the size pointer */ /* Check the validity of the size pointer */
subi,>>= 4, %r23, %r0 subi,>>= 3, %r23, %r0
b,n lws_exit_nosys b,n lws_exit_nosys
/* Jump to the functions which will load the old and new values into /* Jump to the functions which will load the old and new values into
+1 -1
View File
@@ -102,7 +102,7 @@ static void check_syscall_restart(struct pt_regs *regs, struct k_sigaction *ka,
static void do_signal(struct task_struct *tsk) static void do_signal(struct task_struct *tsk)
{ {
sigset_t *oldset = sigmask_to_save(); sigset_t *oldset = sigmask_to_save();
struct ksignal ksig; struct ksignal ksig = { .sig = 0 };
int ret; int ret;
int is32 = is_32bit_task(); int is32 = is_32bit_task();
+8
View File
@@ -0,0 +1,8 @@
#ifndef _ASM_S390_PROTOTYPES_H
#include <linux/kvm_host.h>
#include <linux/ftrace.h>
#include <asm/fpu/api.h>
#include <asm-generic/asm-prototypes.h>
#endif /* _ASM_S390_PROTOTYPES_H */
+1 -1
View File
@@ -34,8 +34,8 @@ static inline void restore_access_regs(unsigned int *acrs)
save_access_regs(&prev->thread.acrs[0]); \ save_access_regs(&prev->thread.acrs[0]); \
save_ri_cb(prev->thread.ri_cb); \ save_ri_cb(prev->thread.ri_cb); \
} \ } \
update_cr_regs(next); \
if (next->mm) { \ if (next->mm) { \
update_cr_regs(next); \
set_cpu_flag(CIF_FPU); \ set_cpu_flag(CIF_FPU); \
restore_access_regs(&next->thread.acrs[0]); \ restore_access_regs(&next->thread.acrs[0]); \
restore_ri_cb(next->thread.ri_cb, prev->thread.ri_cb); \ restore_ri_cb(next->thread.ri_cb, prev->thread.ri_cb); \
+3 -2
View File
@@ -1548,6 +1548,7 @@ static struct s390_insn opcode_e7[] = {
{ "vfsq", 0xce, INSTR_VRR_VV000MM }, { "vfsq", 0xce, INSTR_VRR_VV000MM },
{ "vfs", 0xe2, INSTR_VRR_VVV00MM }, { "vfs", 0xe2, INSTR_VRR_VVV00MM },
{ "vftci", 0x4a, INSTR_VRI_VVIMM }, { "vftci", 0x4a, INSTR_VRI_VVIMM },
{ "", 0, INSTR_INVALID }
}; };
static struct s390_insn opcode_eb[] = { static struct s390_insn opcode_eb[] = {
@@ -1953,7 +1954,7 @@ void show_code(struct pt_regs *regs)
{ {
char *mode = user_mode(regs) ? "User" : "Krnl"; char *mode = user_mode(regs) ? "User" : "Krnl";
unsigned char code[64]; unsigned char code[64];
char buffer[64], *ptr; char buffer[128], *ptr;
mm_segment_t old_fs; mm_segment_t old_fs;
unsigned long addr; unsigned long addr;
int start, end, opsize, hops, i; int start, end, opsize, hops, i;
@@ -2016,7 +2017,7 @@ void show_code(struct pt_regs *regs)
start += opsize; start += opsize;
pr_cont("%s", buffer); pr_cont("%s", buffer);
ptr = buffer; ptr = buffer;
ptr += sprintf(ptr, "\n "); ptr += sprintf(ptr, "\n\t ");
hops++; hops++;
} }
pr_cont("\n"); pr_cont("\n");
+3 -1
View File
@@ -345,8 +345,10 @@ static __init void detect_machine_facilities(void)
S390_lowcore.machine_flags |= MACHINE_FLAG_IDTE; S390_lowcore.machine_flags |= MACHINE_FLAG_IDTE;
if (test_facility(40)) if (test_facility(40))
S390_lowcore.machine_flags |= MACHINE_FLAG_LPP; S390_lowcore.machine_flags |= MACHINE_FLAG_LPP;
if (test_facility(50) && test_facility(73)) if (test_facility(50) && test_facility(73)) {
S390_lowcore.machine_flags |= MACHINE_FLAG_TE; S390_lowcore.machine_flags |= MACHINE_FLAG_TE;
__ctl_set_bit(0, 55);
}
if (test_facility(51)) if (test_facility(51))
S390_lowcore.machine_flags |= MACHINE_FLAG_TLB_LC; S390_lowcore.machine_flags |= MACHINE_FLAG_TLB_LC;
if (test_facility(129)) { if (test_facility(129)) {
+1
View File
@@ -120,6 +120,7 @@ int copy_thread(unsigned long clone_flags, unsigned long new_stackp,
memset(&p->thread.per_user, 0, sizeof(p->thread.per_user)); memset(&p->thread.per_user, 0, sizeof(p->thread.per_user));
memset(&p->thread.per_event, 0, sizeof(p->thread.per_event)); memset(&p->thread.per_event, 0, sizeof(p->thread.per_event));
clear_tsk_thread_flag(p, TIF_SINGLE_STEP); clear_tsk_thread_flag(p, TIF_SINGLE_STEP);
p->thread.per_flags = 0;
/* Initialize per thread user and system timer values */ /* Initialize per thread user and system timer values */
ti = task_thread_info(p); ti = task_thread_info(p);
ti->user_timer = 0; ti->user_timer = 0;
+2 -2
View File
@@ -47,11 +47,13 @@ void exit_thread_runtime_instr(void)
{ {
struct task_struct *task = current; struct task_struct *task = current;
preempt_disable();
if (!task->thread.ri_cb) if (!task->thread.ri_cb)
return; return;
disable_runtime_instr(); disable_runtime_instr();
kfree(task->thread.ri_cb); kfree(task->thread.ri_cb);
task->thread.ri_cb = NULL; task->thread.ri_cb = NULL;
preempt_enable();
} }
SYSCALL_DEFINE1(s390_runtime_instr, int, command) SYSCALL_DEFINE1(s390_runtime_instr, int, command)
@@ -62,9 +64,7 @@ SYSCALL_DEFINE1(s390_runtime_instr, int, command)
return -EOPNOTSUPP; return -EOPNOTSUPP;
if (command == S390_RUNTIME_INSTR_STOP) { if (command == S390_RUNTIME_INSTR_STOP) {
preempt_disable();
exit_thread_runtime_instr(); exit_thread_runtime_instr();
preempt_enable();
return 0; return 0;
} }
+11 -1
View File
@@ -246,9 +246,14 @@ static inline void kvm_apic_set_ldr(struct kvm_lapic *apic, u32 id)
recalculate_apic_map(apic->vcpu->kvm); recalculate_apic_map(apic->vcpu->kvm);
} }
static inline u32 kvm_apic_calc_x2apic_ldr(u32 id)
{
return ((id >> 4) << 16) | (1 << (id & 0xf));
}
static inline void kvm_apic_set_x2apic_id(struct kvm_lapic *apic, u32 id) static inline void kvm_apic_set_x2apic_id(struct kvm_lapic *apic, u32 id)
{ {
u32 ldr = ((id >> 4) << 16) | (1 << (id & 0xf)); u32 ldr = kvm_apic_calc_x2apic_ldr(id);
kvm_lapic_set_reg(apic, APIC_ID, id); kvm_lapic_set_reg(apic, APIC_ID, id);
kvm_lapic_set_reg(apic, APIC_LDR, ldr); kvm_lapic_set_reg(apic, APIC_LDR, ldr);
@@ -2029,6 +2034,7 @@ static int kvm_apic_state_fixup(struct kvm_vcpu *vcpu,
{ {
if (apic_x2apic_mode(vcpu->arch.apic)) { if (apic_x2apic_mode(vcpu->arch.apic)) {
u32 *id = (u32 *)(s->regs + APIC_ID); u32 *id = (u32 *)(s->regs + APIC_ID);
u32 *ldr = (u32 *)(s->regs + APIC_LDR);
if (vcpu->kvm->arch.x2apic_format) { if (vcpu->kvm->arch.x2apic_format) {
if (*id != vcpu->vcpu_id) if (*id != vcpu->vcpu_id)
@@ -2039,6 +2045,10 @@ static int kvm_apic_state_fixup(struct kvm_vcpu *vcpu,
else else
*id <<= 24; *id <<= 24;
} }
/* In x2APIC mode, the LDR is fixed and based on the id */
if (set)
*ldr = kvm_apic_calc_x2apic_ldr(*id);
} }
return 0; return 0;
+9
View File
@@ -2149,6 +2149,8 @@ static int ud_interception(struct vcpu_svm *svm)
int er; int er;
er = emulate_instruction(&svm->vcpu, EMULTYPE_TRAP_UD); er = emulate_instruction(&svm->vcpu, EMULTYPE_TRAP_UD);
if (er == EMULATE_USER_EXIT)
return 0;
if (er != EMULATE_DONE) if (er != EMULATE_DONE)
kvm_queue_exception(&svm->vcpu, UD_VECTOR); kvm_queue_exception(&svm->vcpu, UD_VECTOR);
return 1; return 1;
@@ -3583,6 +3585,13 @@ static int svm_set_msr(struct kvm_vcpu *vcpu, struct msr_data *msr)
u32 ecx = msr->index; u32 ecx = msr->index;
u64 data = msr->data; u64 data = msr->data;
switch (ecx) { switch (ecx) {
case MSR_IA32_CR_PAT:
if (!kvm_mtrr_valid(vcpu, MSR_IA32_CR_PAT, data))
return 1;
vcpu->arch.pat = data;
svm->vmcb->save.g_pat = data;
mark_dirty(svm->vmcb, VMCB_NPT);
break;
case MSR_IA32_TSC: case MSR_IA32_TSC:
kvm_write_tsc(vcpu, msr); kvm_write_tsc(vcpu, msr);
break; break;
+4
View File
@@ -5502,6 +5502,8 @@ static int handle_exception(struct kvm_vcpu *vcpu)
return 1; return 1;
} }
er = emulate_instruction(vcpu, EMULTYPE_TRAP_UD); er = emulate_instruction(vcpu, EMULTYPE_TRAP_UD);
if (er == EMULATE_USER_EXIT)
return 0;
if (er != EMULATE_DONE) if (er != EMULATE_DONE)
kvm_queue_exception(vcpu, UD_VECTOR); kvm_queue_exception(vcpu, UD_VECTOR);
return 1; return 1;
@@ -10714,6 +10716,8 @@ static void load_vmcs12_host_state(struct kvm_vcpu *vcpu,
vmcs_writel(GUEST_SYSENTER_EIP, vmcs12->host_ia32_sysenter_eip); vmcs_writel(GUEST_SYSENTER_EIP, vmcs12->host_ia32_sysenter_eip);
vmcs_writel(GUEST_IDTR_BASE, vmcs12->host_idtr_base); vmcs_writel(GUEST_IDTR_BASE, vmcs12->host_idtr_base);
vmcs_writel(GUEST_GDTR_BASE, vmcs12->host_gdtr_base); vmcs_writel(GUEST_GDTR_BASE, vmcs12->host_gdtr_base);
vmcs_write32(GUEST_IDTR_LIMIT, 0xFFFF);
vmcs_write32(GUEST_GDTR_LIMIT, 0xFFFF);
/* If not VM_EXIT_CLEAR_BNDCFGS, the L2 value propagates to L1. */ /* If not VM_EXIT_CLEAR_BNDCFGS, the L2 value propagates to L1. */
if (vmcs12->vm_exit_controls & VM_EXIT_CLEAR_BNDCFGS) if (vmcs12->vm_exit_controls & VM_EXIT_CLEAR_BNDCFGS)
+5
View File
@@ -1797,6 +1797,9 @@ static void kvm_setup_pvclock_page(struct kvm_vcpu *v)
*/ */
BUILD_BUG_ON(offsetof(struct pvclock_vcpu_time_info, version) != 0); BUILD_BUG_ON(offsetof(struct pvclock_vcpu_time_info, version) != 0);
if (guest_hv_clock.version & 1)
++guest_hv_clock.version; /* first time write, random junk */
vcpu->hv_clock.version = guest_hv_clock.version + 1; vcpu->hv_clock.version = guest_hv_clock.version + 1;
kvm_write_guest_cached(v->kvm, &vcpu->pv_time, kvm_write_guest_cached(v->kvm, &vcpu->pv_time,
&vcpu->hv_clock, &vcpu->hv_clock,
@@ -5576,6 +5579,8 @@ int x86_emulate_instruction(struct kvm_vcpu *vcpu,
if (reexecute_instruction(vcpu, cr2, write_fault_to_spt, if (reexecute_instruction(vcpu, cr2, write_fault_to_spt,
emulation_type)) emulation_type))
return EMULATE_DONE; return EMULATE_DONE;
if (ctxt->have_exception && inject_emulated_exception(vcpu))
return EMULATE_DONE;
if (emulation_type & EMULTYPE_SKIP) if (emulation_type & EMULTYPE_SKIP)
return EMULATE_FAIL; return EMULATE_FAIL;
return handle_emulation_failure(vcpu); return handle_emulation_failure(vcpu);
+1 -1
View File
@@ -896,7 +896,7 @@ EndTable
GrpTable: Grp3_1 GrpTable: Grp3_1
0: TEST Eb,Ib 0: TEST Eb,Ib
1: 1: TEST Eb,Ib
2: NOT Eb 2: NOT Eb
3: NEG Eb 3: NEG Eb
4: MUL AL,Eb 4: MUL AL,Eb
+10 -1
View File
@@ -1392,7 +1392,17 @@ good_area:
* make sure we exit gracefully rather than endlessly redo * make sure we exit gracefully rather than endlessly redo
* the fault. Since we never set FAULT_FLAG_RETRY_NOWAIT, if * the fault. Since we never set FAULT_FLAG_RETRY_NOWAIT, if
* we get VM_FAULT_RETRY back, the mmap_sem has been unlocked. * we get VM_FAULT_RETRY back, the mmap_sem has been unlocked.
*
* Note that handle_userfault() may also release and reacquire mmap_sem
* (and not return with VM_FAULT_RETRY), when returning to userland to
* repeat the page fault later with a VM_FAULT_NOPAGE retval
* (potentially after handling any pending signal during the return to
* userland). The return to userland is identified whenever
* FAULT_FLAG_USER|FAULT_FLAG_KILLABLE are both set in flags.
* Thus we have to be careful about not touching vma after handling the
* fault, so we read the pkey beforehand.
*/ */
pkey = vma_pkey(vma);
fault = handle_mm_fault(vma, address, flags); fault = handle_mm_fault(vma, address, flags);
major |= fault & VM_FAULT_MAJOR; major |= fault & VM_FAULT_MAJOR;
@@ -1419,7 +1429,6 @@ good_area:
return; return;
} }
pkey = vma_pkey(vma);
up_read(&mm->mmap_sem); up_read(&mm->mmap_sem);
if (unlikely(fault & VM_FAULT_ERROR)) { if (unlikely(fault & VM_FAULT_ERROR)) {
mm_fault_error(regs, error_code, address, &pkey, fault); mm_fault_error(regs, error_code, address, &pkey, fault);
+2
View File
@@ -284,6 +284,7 @@ EXPORT_SYMBOL(blk_stop_queue);
void blk_sync_queue(struct request_queue *q) void blk_sync_queue(struct request_queue *q)
{ {
del_timer_sync(&q->timeout); del_timer_sync(&q->timeout);
cancel_work_sync(&q->timeout_work);
if (q->mq_ops) { if (q->mq_ops) {
struct blk_mq_hw_ctx *hctx; struct blk_mq_hw_ctx *hctx;
@@ -722,6 +723,7 @@ struct request_queue *blk_alloc_queue_node(gfp_t gfp_mask, int node_id)
setup_timer(&q->backing_dev_info.laptop_mode_wb_timer, setup_timer(&q->backing_dev_info.laptop_mode_wb_timer,
laptop_mode_timer_fn, (unsigned long) q); laptop_mode_timer_fn, (unsigned long) q);
setup_timer(&q->timeout, blk_rq_timed_out_timer, (unsigned long) q); setup_timer(&q->timeout, blk_rq_timed_out_timer, (unsigned long) q);
INIT_WORK(&q->timeout_work, NULL);
INIT_LIST_HEAD(&q->queue_head); INIT_LIST_HEAD(&q->queue_head);
INIT_LIST_HEAD(&q->timeout_list); INIT_LIST_HEAD(&q->timeout_list);
INIT_LIST_HEAD(&q->icq_list); INIT_LIST_HEAD(&q->icq_list);
-3
View File
@@ -135,8 +135,6 @@ void blk_timeout_work(struct work_struct *work)
struct request *rq, *tmp; struct request *rq, *tmp;
int next_set = 0; int next_set = 0;
if (blk_queue_enter(q, true))
return;
spin_lock_irqsave(q->queue_lock, flags); spin_lock_irqsave(q->queue_lock, flags);
list_for_each_entry_safe(rq, tmp, &q->timeout_list, timeout_list) list_for_each_entry_safe(rq, tmp, &q->timeout_list, timeout_list)
@@ -146,7 +144,6 @@ void blk_timeout_work(struct work_struct *work)
mod_timer(&q->timeout, round_jiffies_up(next)); mod_timer(&q->timeout, round_jiffies_up(next));
spin_unlock_irqrestore(q->queue_lock, flags); spin_unlock_irqrestore(q->queue_lock, flags);
blk_queue_exit(q);
} }
/** /**
+2
View File
@@ -208,4 +208,6 @@ source "drivers/hisi/Kconfig"
source "drivers/fpga/Kconfig" source "drivers/fpga/Kconfig"
source "drivers/tee/Kconfig"
endmenu endmenu
+1
View File
@@ -175,4 +175,5 @@ obj-$(CONFIG_STM) += hwtracing/stm/
obj-$(CONFIG_ANDROID) += android/ obj-$(CONFIG_ANDROID) += android/
obj-$(CONFIG_NVMEM) += nvmem/ obj-$(CONFIG_NVMEM) += nvmem/
obj-$(CONFIG_FPGA) += fpga/ obj-$(CONFIG_FPGA) += fpga/
obj-$(CONFIG_TEE) += tee/
obj-$(CONFIG_HISILICON_PLATFORM)+= hisi/ obj-$(CONFIG_HISILICON_PLATFORM)+= hisi/
+7 -5
View File
@@ -482,8 +482,11 @@ static inline void __acpi_ec_enable_event(struct acpi_ec *ec)
{ {
if (!test_and_set_bit(EC_FLAGS_QUERY_ENABLED, &ec->flags)) if (!test_and_set_bit(EC_FLAGS_QUERY_ENABLED, &ec->flags))
ec_log_drv("event unblocked"); ec_log_drv("event unblocked");
if (!test_bit(EC_FLAGS_QUERY_PENDING, &ec->flags)) /*
advance_transaction(ec); * Unconditionally invoke this once after enabling the event
* handling mechanism to detect the pending events.
*/
advance_transaction(ec);
} }
static inline void __acpi_ec_disable_event(struct acpi_ec *ec) static inline void __acpi_ec_disable_event(struct acpi_ec *ec)
@@ -1458,11 +1461,10 @@ static int ec_install_handlers(struct acpi_ec *ec, bool handle_events)
if (test_bit(EC_FLAGS_STARTED, &ec->flags) && if (test_bit(EC_FLAGS_STARTED, &ec->flags) &&
ec->reference_count >= 1) ec->reference_count >= 1)
acpi_ec_enable_gpe(ec, true); acpi_ec_enable_gpe(ec, true);
/* EC is fully operational, allow queries */
acpi_ec_enable_event(ec);
} }
} }
/* EC is fully operational, allow queries */
acpi_ec_enable_event(ec);
return 0; return 0;
} }
+1 -1
View File
@@ -2329,8 +2329,8 @@ static void ata_eh_link_autopsy(struct ata_link *link)
if (dev->flags & ATA_DFLAG_DUBIOUS_XFER) if (dev->flags & ATA_DFLAG_DUBIOUS_XFER)
eflags |= ATA_EFLAG_DUBIOUS_XFER; eflags |= ATA_EFLAG_DUBIOUS_XFER;
ehc->i.action |= ata_eh_speed_down(dev, eflags, all_err_mask); ehc->i.action |= ata_eh_speed_down(dev, eflags, all_err_mask);
trace_ata_eh_link_autopsy(dev, ehc->i.action, all_err_mask);
} }
trace_ata_eh_link_autopsy(dev, ehc->i.action, all_err_mask);
DPRINTK("EXIT\n"); DPRINTK("EXIT\n");
} }
+1
View File
@@ -348,6 +348,7 @@ static int _of_add_opp_table_v2(struct device *dev, struct device_node *opp_np)
if (ret) { if (ret) {
dev_err(dev, "%s: Failed to add OPP, %d\n", __func__, dev_err(dev, "%s: Failed to add OPP, %d\n", __func__,
ret); ret);
of_node_put(np);
goto free_table; goto free_table;
} }
} }
+12 -2
View File
@@ -525,10 +525,20 @@ static struct clk_rcg2 sdcc1_apps_clk_src = {
}; };
static const struct freq_tbl ftbl_gcc_apps_clk[] = { static const struct freq_tbl ftbl_gcc_apps_clk[] = {
F(48000000, P_XO, 1, 0, 0), F(48000000, P_XO, 1, 0, 0),
F(200000000, P_FEPLL200, 1, 0, 0), F(200000000, P_FEPLL200, 1, 0, 0),
F(384000000, P_DDRPLLAPSS, 1, 0, 0),
F(413000000, P_DDRPLLAPSS, 1, 0, 0),
F(448000000, P_DDRPLLAPSS, 1, 0, 0),
F(488000000, P_DDRPLLAPSS, 1, 0, 0),
F(500000000, P_FEPLL500, 1, 0, 0), F(500000000, P_FEPLL500, 1, 0, 0),
F(626000000, P_DDRPLLAPSS, 1, 0, 0), F(512000000, P_DDRPLLAPSS, 1, 0, 0),
F(537000000, P_DDRPLLAPSS, 1, 0, 0),
F(565000000, P_DDRPLLAPSS, 1, 0, 0),
F(597000000, P_DDRPLLAPSS, 1, 0, 0),
F(632000000, P_DDRPLLAPSS, 1, 0, 0),
F(672000000, P_DDRPLLAPSS, 1, 0, 0),
F(716000000, P_DDRPLLAPSS, 1, 0, 0),
{ } { }
}; };
+2 -2
View File
@@ -468,8 +468,8 @@ static SUNXI_CCU_MUX_WITH_GATE(daudio0_clk, "daudio0", daudio_parents,
static SUNXI_CCU_MUX_WITH_GATE(daudio1_clk, "daudio1", daudio_parents, static SUNXI_CCU_MUX_WITH_GATE(daudio1_clk, "daudio1", daudio_parents,
0x0b4, 16, 2, BIT(31), CLK_SET_RATE_PARENT); 0x0b4, 16, 2, BIT(31), CLK_SET_RATE_PARENT);
static SUNXI_CCU_M_WITH_GATE(spdif_clk, "spdif", "pll-audio", static SUNXI_CCU_MUX_WITH_GATE(spdif_clk, "spdif", daudio_parents,
0x0c0, 0, 4, BIT(31), CLK_SET_RATE_PARENT); 0x0c0, 16, 2, BIT(31), CLK_SET_RATE_PARENT);
static SUNXI_CCU_GATE(usb_phy0_clk, "usb-phy0", "osc24M", static SUNXI_CCU_GATE(usb_phy0_clk, "usb-phy0", "osc24M",
0x0cc, BIT(8), 0); 0x0cc, BIT(8), 0);
+10
View File
@@ -752,6 +752,13 @@ static const struct sunxi_ccu_desc sun8i_a33_ccu_desc = {
.num_resets = ARRAY_SIZE(sun8i_a33_ccu_resets), .num_resets = ARRAY_SIZE(sun8i_a33_ccu_resets),
}; };
static struct ccu_mux_nb sun8i_a33_cpu_nb = {
.common = &cpux_clk.common,
.cm = &cpux_clk.mux,
.delay_us = 1, /* > 8 clock cycles at 24 MHz */
.bypass_index = 1, /* index of 24 MHz oscillator */
};
static void __init sun8i_a33_ccu_setup(struct device_node *node) static void __init sun8i_a33_ccu_setup(struct device_node *node)
{ {
void __iomem *reg; void __iomem *reg;
@@ -775,6 +782,9 @@ static void __init sun8i_a33_ccu_setup(struct device_node *node)
writel(val, reg + SUN8I_A33_PLL_MIPI_REG); writel(val, reg + SUN8I_A33_PLL_MIPI_REG);
sunxi_ccu_probe(node, reg, &sun8i_a33_ccu_desc); sunxi_ccu_probe(node, reg, &sun8i_a33_ccu_desc);
ccu_mux_notifier_register(pll_cpux_clk.common.hw.clk,
&sun8i_a33_cpu_nb);
} }
CLK_OF_DECLARE(sun8i_a33_ccu, "allwinner,sun8i-a33-ccu", CLK_OF_DECLARE(sun8i_a33_ccu, "allwinner,sun8i-a33-ccu",
sun8i_a33_ccu_setup); sun8i_a33_ccu_setup);
+1 -2
View File
@@ -265,8 +265,7 @@ static int of_dra7_atl_clk_probe(struct platform_device *pdev)
/* Get configuration for the ATL instances */ /* Get configuration for the ATL instances */
snprintf(prop, sizeof(prop), "atl%u", i); snprintf(prop, sizeof(prop), "atl%u", i);
of_node_get(node); cfg_node = of_get_child_by_name(node, prop);
cfg_node = of_find_node_by_name(node, prop);
if (cfg_node) { if (cfg_node) {
ret = of_property_read_u32(cfg_node, "bws", ret = of_property_read_u32(cfg_node, "bws",
&cdesc->bws); &cdesc->bws);
+2 -1
View File
@@ -273,7 +273,8 @@ struct mv_cesa_op_ctx {
#define CESA_TDMA_SRC_IN_SRAM BIT(30) #define CESA_TDMA_SRC_IN_SRAM BIT(30)
#define CESA_TDMA_END_OF_REQ BIT(29) #define CESA_TDMA_END_OF_REQ BIT(29)
#define CESA_TDMA_BREAK_CHAIN BIT(28) #define CESA_TDMA_BREAK_CHAIN BIT(28)
#define CESA_TDMA_TYPE_MSK GENMASK(27, 0) #define CESA_TDMA_SET_STATE BIT(27)
#define CESA_TDMA_TYPE_MSK GENMASK(26, 0)
#define CESA_TDMA_DUMMY 0 #define CESA_TDMA_DUMMY 0
#define CESA_TDMA_DATA 1 #define CESA_TDMA_DATA 1
#define CESA_TDMA_OP 2 #define CESA_TDMA_OP 2
+33 -1
View File
@@ -280,13 +280,32 @@ static void mv_cesa_ahash_std_prepare(struct ahash_request *req)
sreq->offset = 0; sreq->offset = 0;
} }
static void mv_cesa_ahash_dma_step(struct ahash_request *req)
{
struct mv_cesa_ahash_req *creq = ahash_request_ctx(req);
struct mv_cesa_req *base = &creq->base;
/* We must explicitly set the digest state. */
if (base->chain.first->flags & CESA_TDMA_SET_STATE) {
struct mv_cesa_engine *engine = base->engine;
int i;
/* Set the hash state in the IVDIG regs. */
for (i = 0; i < ARRAY_SIZE(creq->state); i++)
writel_relaxed(creq->state[i], engine->regs +
CESA_IVDIG(i));
}
mv_cesa_dma_step(base);
}
static void mv_cesa_ahash_step(struct crypto_async_request *req) static void mv_cesa_ahash_step(struct crypto_async_request *req)
{ {
struct ahash_request *ahashreq = ahash_request_cast(req); struct ahash_request *ahashreq = ahash_request_cast(req);
struct mv_cesa_ahash_req *creq = ahash_request_ctx(ahashreq); struct mv_cesa_ahash_req *creq = ahash_request_ctx(ahashreq);
if (mv_cesa_req_get_type(&creq->base) == CESA_DMA_REQ) if (mv_cesa_req_get_type(&creq->base) == CESA_DMA_REQ)
mv_cesa_dma_step(&creq->base); mv_cesa_ahash_dma_step(ahashreq);
else else
mv_cesa_ahash_std_step(ahashreq); mv_cesa_ahash_std_step(ahashreq);
} }
@@ -562,11 +581,15 @@ static int mv_cesa_ahash_dma_req_init(struct ahash_request *req)
struct mv_cesa_ahash_dma_iter iter; struct mv_cesa_ahash_dma_iter iter;
struct mv_cesa_op_ctx *op = NULL; struct mv_cesa_op_ctx *op = NULL;
unsigned int frag_len; unsigned int frag_len;
bool set_state = false;
int ret; int ret;
basereq->chain.first = NULL; basereq->chain.first = NULL;
basereq->chain.last = NULL; basereq->chain.last = NULL;
if (!mv_cesa_mac_op_is_first_frag(&creq->op_tmpl))
set_state = true;
if (creq->src_nents) { if (creq->src_nents) {
ret = dma_map_sg(cesa_dev->dev, req->src, creq->src_nents, ret = dma_map_sg(cesa_dev->dev, req->src, creq->src_nents,
DMA_TO_DEVICE); DMA_TO_DEVICE);
@@ -650,6 +673,15 @@ static int mv_cesa_ahash_dma_req_init(struct ahash_request *req)
basereq->chain.last->flags |= (CESA_TDMA_END_OF_REQ | basereq->chain.last->flags |= (CESA_TDMA_END_OF_REQ |
CESA_TDMA_BREAK_CHAIN); CESA_TDMA_BREAK_CHAIN);
if (set_state) {
/*
* Put the CESA_TDMA_SET_STATE flag on the first tdma desc to
* let the step logic know that the IVDIG registers should be
* explicitly set before launching a TDMA chain.
*/
basereq->chain.first->flags |= CESA_TDMA_SET_STATE;
}
return 0; return 0;
err_free_tdma: err_free_tdma:
+8 -1
View File
@@ -112,7 +112,14 @@ void mv_cesa_tdma_chain(struct mv_cesa_engine *engine,
last->next = dreq->chain.first; last->next = dreq->chain.first;
engine->chain.last = dreq->chain.last; engine->chain.last = dreq->chain.last;
if (!(last->flags & CESA_TDMA_BREAK_CHAIN)) /*
* Break the DMA chain if the CESA_TDMA_BREAK_CHAIN is set on
* the last element of the current chain, or if the request
* being queued needs the IV regs to be set before lauching
* the request.
*/
if (!(last->flags & CESA_TDMA_BREAK_CHAIN) &&
!(dreq->chain.first->flags & CESA_TDMA_SET_STATE))
last->next_dma = dreq->chain.first->cur_dma; last->next_dma = dreq->chain.first->cur_dma;
} }
} }
+1
View File
@@ -813,6 +813,7 @@ static int zx_dma_probe(struct platform_device *op)
INIT_LIST_HEAD(&d->slave.channels); INIT_LIST_HEAD(&d->slave.channels);
dma_cap_set(DMA_SLAVE, d->slave.cap_mask); dma_cap_set(DMA_SLAVE, d->slave.cap_mask);
dma_cap_set(DMA_MEMCPY, d->slave.cap_mask); dma_cap_set(DMA_MEMCPY, d->slave.cap_mask);
dma_cap_set(DMA_CYCLIC, d->slave.cap_mask);
dma_cap_set(DMA_PRIVATE, d->slave.cap_mask); dma_cap_set(DMA_PRIVATE, d->slave.cap_mask);
d->slave.dev = &op->dev; d->slave.dev = &op->dev;
d->slave.device_free_chan_resources = zx_dma_free_chan_resources; d->slave.device_free_chan_resources = zx_dma_free_chan_resources;
+7 -3
View File
@@ -126,7 +126,7 @@ static int mockup_gpio_probe(struct platform_device *pdev)
int i; int i;
int base; int base;
int ngpio; int ngpio;
char chip_name[sizeof(GPIO_NAME) + 3]; char *chip_name;
if (gpio_mockup_params_nr < 2) if (gpio_mockup_params_nr < 2)
return -EINVAL; return -EINVAL;
@@ -146,8 +146,12 @@ static int mockup_gpio_probe(struct platform_device *pdev)
ngpio = gpio_mockup_ranges[i * 2 + 1] - base; ngpio = gpio_mockup_ranges[i * 2 + 1] - base;
if (ngpio >= 0) { if (ngpio >= 0) {
sprintf(chip_name, "%s-%c", GPIO_NAME, chip_name = devm_kasprintf(dev, GFP_KERNEL,
pins_name_start + i); "%s-%c", GPIO_NAME,
pins_name_start + i);
if (!chip_name)
return -ENOMEM;
ret = mockup_gpio_add(dev, &cntr[i], ret = mockup_gpio_add(dev, &cntr[i],
chip_name, base, ngpio); chip_name, base, ngpio);
} else { } else {
+18 -20
View File
@@ -1788,34 +1788,32 @@ void amdgpu_atombios_scratch_regs_restore(struct amdgpu_device *adev)
WREG32(mmBIOS_SCRATCH_0 + i, adev->bios_scratch[i]); WREG32(mmBIOS_SCRATCH_0 + i, adev->bios_scratch[i]);
} }
/* Atom needs data in little endian format /* Atom needs data in little endian format so swap as appropriate when copying
* so swap as appropriate when copying data to * data to or from atom. Note that atom operates on dw units.
* or from atom. Note that atom operates on *
* dw units. * Use to_le=true when sending data to atom and provide at least
* ALIGN(num_bytes,4) bytes in the dst buffer.
*
* Use to_le=false when receiving data from atom and provide ALIGN(num_bytes,4)
* byes in the src buffer.
*/ */
void amdgpu_atombios_copy_swap(u8 *dst, u8 *src, u8 num_bytes, bool to_le) void amdgpu_atombios_copy_swap(u8 *dst, u8 *src, u8 num_bytes, bool to_le)
{ {
#ifdef __BIG_ENDIAN #ifdef __BIG_ENDIAN
u8 src_tmp[20], dst_tmp[20]; /* used for byteswapping */ u32 src_tmp[5], dst_tmp[5];
u32 *dst32, *src32;
int i; int i;
u8 align_num_bytes = ALIGN(num_bytes, 4);
memcpy(src_tmp, src, num_bytes);
src32 = (u32 *)src_tmp;
dst32 = (u32 *)dst_tmp;
if (to_le) { if (to_le) {
for (i = 0; i < ((num_bytes + 3) / 4); i++) memcpy(src_tmp, src, num_bytes);
dst32[i] = cpu_to_le32(src32[i]); for (i = 0; i < align_num_bytes / 4; i++)
memcpy(dst, dst_tmp, num_bytes); dst_tmp[i] = cpu_to_le32(src_tmp[i]);
memcpy(dst, dst_tmp, align_num_bytes);
} else { } else {
u8 dws = num_bytes & ~3; memcpy(src_tmp, src, align_num_bytes);
for (i = 0; i < ((num_bytes + 3) / 4); i++) for (i = 0; i < align_num_bytes / 4; i++)
dst32[i] = le32_to_cpu(src32[i]); dst_tmp[i] = le32_to_cpu(src_tmp[i]);
memcpy(dst, dst_tmp, dws); memcpy(dst, dst_tmp, num_bytes);
if (num_bytes % 4) {
for (i = 0; i < (num_bytes % 4); i++)
dst[dws+i] = dst_tmp[dws+i];
}
} }
#else #else
memcpy(dst, src, num_bytes); memcpy(dst, src, num_bytes);
+1 -1
View File
@@ -648,7 +648,7 @@ int amdgpu_vce_ring_parse_cs(struct amdgpu_cs_parser *p, uint32_t ib_idx)
uint32_t allocated = 0; uint32_t allocated = 0;
uint32_t tmp, handle = 0; uint32_t tmp, handle = 0;
uint32_t *size = &tmp; uint32_t *size = &tmp;
int i, r, idx = 0; int i, r = 0, idx = 0;
r = amdgpu_cs_sysvm_access_required(p); r = amdgpu_cs_sysvm_access_required(p);
if (r) if (r)
+1 -1
View File
@@ -744,7 +744,7 @@ error_free:
int amdgpu_vm_update_page_directory(struct amdgpu_device *adev, int amdgpu_vm_update_page_directory(struct amdgpu_device *adev,
struct amdgpu_vm *vm) struct amdgpu_vm *vm)
{ {
int r; int r = 0;
r = amdgpu_vm_update_pd_or_shadow(adev, vm, true); r = amdgpu_vm_update_pd_or_shadow(adev, vm, true);
if (r) if (r)
@@ -850,9 +850,9 @@ static int init_over_drive_limits(
const ATOM_Tonga_POWERPLAYTABLE *powerplay_table) const ATOM_Tonga_POWERPLAYTABLE *powerplay_table)
{ {
hwmgr->platform_descriptor.overdriveLimit.engineClock = hwmgr->platform_descriptor.overdriveLimit.engineClock =
le16_to_cpu(powerplay_table->ulMaxODEngineClock); le32_to_cpu(powerplay_table->ulMaxODEngineClock);
hwmgr->platform_descriptor.overdriveLimit.memoryClock = hwmgr->platform_descriptor.overdriveLimit.memoryClock =
le16_to_cpu(powerplay_table->ulMaxODMemoryClock); le32_to_cpu(powerplay_table->ulMaxODMemoryClock);
hwmgr->platform_descriptor.minOverdriveVDDC = 0; hwmgr->platform_descriptor.minOverdriveVDDC = 0;
hwmgr->platform_descriptor.maxOverdriveVDDC = 0; hwmgr->platform_descriptor.maxOverdriveVDDC = 0;
+2
View File
@@ -4,3 +4,5 @@ armada-y += armada_510.o
armada-$(CONFIG_DEBUG_FS) += armada_debugfs.o armada-$(CONFIG_DEBUG_FS) += armada_debugfs.o
obj-$(CONFIG_DRM_ARMADA) := armada.o obj-$(CONFIG_DRM_ARMADA) := armada.o
CFLAGS_armada_trace.o := -I$(src)
+6 -10
View File
@@ -348,14 +348,12 @@ static void drm_mm_insert_helper_range(struct drm_mm_node *hole_node,
BUG_ON(!hole_node->hole_follows || node->allocated); BUG_ON(!hole_node->hole_follows || node->allocated);
if (adj_start < start)
adj_start = start;
if (adj_end > end)
adj_end = end;
if (mm->color_adjust) if (mm->color_adjust)
mm->color_adjust(hole_node, color, &adj_start, &adj_end); mm->color_adjust(hole_node, color, &adj_start, &adj_end);
adj_start = max(adj_start, start);
adj_end = min(adj_end, end);
if (flags & DRM_MM_CREATE_TOP) if (flags & DRM_MM_CREATE_TOP)
adj_start = adj_end - size; adj_start = adj_end - size;
@@ -566,17 +564,15 @@ static struct drm_mm_node *drm_mm_search_free_in_range_generic(const struct drm_
flags & DRM_MM_SEARCH_BELOW) { flags & DRM_MM_SEARCH_BELOW) {
u64 hole_size = adj_end - adj_start; u64 hole_size = adj_end - adj_start;
if (adj_start < start)
adj_start = start;
if (adj_end > end)
adj_end = end;
if (mm->color_adjust) { if (mm->color_adjust) {
mm->color_adjust(entry, color, &adj_start, &adj_end); mm->color_adjust(entry, color, &adj_start, &adj_end);
if (adj_end <= adj_start) if (adj_end <= adj_start)
continue; continue;
} }
adj_start = max(adj_start, start);
adj_end = min(adj_end, end);
if (!check_free_hole(adj_start, adj_end, size, alignment)) if (!check_free_hole(adj_start, adj_end, size, alignment))
continue; continue;
@@ -521,9 +521,12 @@ static void ade_crtc_atomic_begin(struct drm_crtc *crtc,
{ {
struct ade_crtc *acrtc = to_ade_crtc(crtc); struct ade_crtc *acrtc = to_ade_crtc(crtc);
struct ade_hw_ctx *ctx = acrtc->ctx; struct ade_hw_ctx *ctx = acrtc->ctx;
struct drm_display_mode *mode = &crtc->state->mode;
struct drm_display_mode *adj_mode = &crtc->state->adjusted_mode;
if (!ctx->power_on) if (!ctx->power_on)
(void)ade_power_up(ctx); (void)ade_power_up(ctx);
ade_ldi_set_mode(acrtc, mode, adj_mode);
} }
static void ade_crtc_atomic_flush(struct drm_crtc *crtc, static void ade_crtc_atomic_flush(struct drm_crtc *crtc,
+1
View File
@@ -457,6 +457,7 @@ struct intel_crtc_scaler_state {
struct intel_pipe_wm { struct intel_pipe_wm {
struct intel_wm_level wm[5]; struct intel_wm_level wm[5];
struct intel_wm_level raw_wm[5];
uint32_t linetime; uint32_t linetime;
bool fbc_wm_enabled; bool fbc_wm_enabled;
bool pipe_enabled; bool pipe_enabled;
+3 -1
View File
@@ -430,7 +430,9 @@ static bool
gmbus_is_index_read(struct i2c_msg *msgs, int i, int num) gmbus_is_index_read(struct i2c_msg *msgs, int i, int num)
{ {
return (i + 1 < num && return (i + 1 < num &&
!(msgs[i].flags & I2C_M_RD) && msgs[i].len <= 2 && msgs[i].addr == msgs[i + 1].addr &&
!(msgs[i].flags & I2C_M_RD) &&
(msgs[i].len == 1 || msgs[i].len == 2) &&
(msgs[i + 1].flags & I2C_M_RD)); (msgs[i + 1].flags & I2C_M_RD));
} }
+30 -22
View File
@@ -27,7 +27,6 @@
#include <linux/cpufreq.h> #include <linux/cpufreq.h>
#include <drm/drm_plane_helper.h> #include <drm/drm_plane_helper.h>
#include <drm/drm_atomic_helper.h>
#include "i915_drv.h" #include "i915_drv.h"
#include "intel_drv.h" #include "intel_drv.h"
#include "../../../platform/x86/intel_ips.h" #include "../../../platform/x86/intel_ips.h"
@@ -2018,9 +2017,9 @@ static void ilk_compute_wm_level(const struct drm_i915_private *dev_priv,
const struct intel_crtc *intel_crtc, const struct intel_crtc *intel_crtc,
int level, int level,
struct intel_crtc_state *cstate, struct intel_crtc_state *cstate,
const struct intel_plane_state *pristate, struct intel_plane_state *pristate,
const struct intel_plane_state *sprstate, struct intel_plane_state *sprstate,
const struct intel_plane_state *curstate, struct intel_plane_state *curstate,
struct intel_wm_level *result) struct intel_wm_level *result)
{ {
uint16_t pri_latency = dev_priv->wm.pri_latency[level]; uint16_t pri_latency = dev_priv->wm.pri_latency[level];
@@ -2342,24 +2341,28 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate)
struct intel_pipe_wm *pipe_wm; struct intel_pipe_wm *pipe_wm;
struct drm_device *dev = state->dev; struct drm_device *dev = state->dev;
const struct drm_i915_private *dev_priv = to_i915(dev); const struct drm_i915_private *dev_priv = to_i915(dev);
struct drm_plane *plane; struct intel_plane *intel_plane;
const struct drm_plane_state *plane_state; struct intel_plane_state *pristate = NULL;
const struct intel_plane_state *pristate = NULL; struct intel_plane_state *sprstate = NULL;
const struct intel_plane_state *sprstate = NULL; struct intel_plane_state *curstate = NULL;
const struct intel_plane_state *curstate = NULL;
int level, max_level = ilk_wm_max_level(dev), usable_level; int level, max_level = ilk_wm_max_level(dev), usable_level;
struct ilk_wm_maximums max; struct ilk_wm_maximums max;
pipe_wm = &cstate->wm.ilk.optimal; pipe_wm = &cstate->wm.ilk.optimal;
drm_atomic_crtc_state_for_each_plane_state(plane, plane_state, &cstate->base) { for_each_intel_plane_on_crtc(dev, intel_crtc, intel_plane) {
const struct intel_plane_state *ps = to_intel_plane_state(plane_state); struct intel_plane_state *ps;
if (plane->type == DRM_PLANE_TYPE_PRIMARY) ps = intel_atomic_get_existing_plane_state(state,
intel_plane);
if (!ps)
continue;
if (intel_plane->base.type == DRM_PLANE_TYPE_PRIMARY)
pristate = ps; pristate = ps;
else if (plane->type == DRM_PLANE_TYPE_OVERLAY) else if (intel_plane->base.type == DRM_PLANE_TYPE_OVERLAY)
sprstate = ps; sprstate = ps;
else if (plane->type == DRM_PLANE_TYPE_CURSOR) else if (intel_plane->base.type == DRM_PLANE_TYPE_CURSOR)
curstate = ps; curstate = ps;
} }
@@ -2381,9 +2384,11 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate)
if (pipe_wm->sprites_scaled) if (pipe_wm->sprites_scaled)
usable_level = 0; usable_level = 0;
memset(&pipe_wm->wm, 0, sizeof(pipe_wm->wm));
ilk_compute_wm_level(dev_priv, intel_crtc, 0, cstate, ilk_compute_wm_level(dev_priv, intel_crtc, 0, cstate,
pristate, sprstate, curstate, &pipe_wm->wm[0]); pristate, sprstate, curstate, &pipe_wm->raw_wm[0]);
memset(&pipe_wm->wm, 0, sizeof(pipe_wm->wm));
pipe_wm->wm[0] = pipe_wm->raw_wm[0];
if (IS_HASWELL(dev) || IS_BROADWELL(dev)) if (IS_HASWELL(dev) || IS_BROADWELL(dev))
pipe_wm->linetime = hsw_compute_linetime_wm(cstate); pipe_wm->linetime = hsw_compute_linetime_wm(cstate);
@@ -2393,8 +2398,8 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate)
ilk_compute_wm_reg_maximums(dev, 1, &max); ilk_compute_wm_reg_maximums(dev, 1, &max);
for (level = 1; level <= usable_level; level++) { for (level = 1; level <= max_level; level++) {
struct intel_wm_level *wm = &pipe_wm->wm[level]; struct intel_wm_level *wm = &pipe_wm->raw_wm[level];
ilk_compute_wm_level(dev_priv, intel_crtc, level, cstate, ilk_compute_wm_level(dev_priv, intel_crtc, level, cstate,
pristate, sprstate, curstate, wm); pristate, sprstate, curstate, wm);
@@ -2404,10 +2409,13 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate)
* register maximums since such watermarks are * register maximums since such watermarks are
* always invalid. * always invalid.
*/ */
if (!ilk_validate_wm_level(level, &max, wm)) { if (level > usable_level)
memset(wm, 0, sizeof(*wm)); continue;
break;
} if (ilk_validate_wm_level(level, &max, wm))
pipe_wm->wm[level] = *wm;
else
usable_level = level;
} }
return 0; return 0;
+2 -1
View File
@@ -321,7 +321,8 @@ static void mtk_drm_unbind(struct device *dev)
{ {
struct mtk_drm_private *private = dev_get_drvdata(dev); struct mtk_drm_private *private = dev_get_drvdata(dev);
drm_put_dev(private->drm); drm_dev_unregister(private->drm);
drm_dev_unref(private->drm);
private->drm = NULL; private->drm = NULL;
} }
+2
View File
@@ -369,6 +369,7 @@ static int panel_simple_remove(struct device *dev)
drm_panel_remove(&panel->base); drm_panel_remove(&panel->base);
panel_simple_disable(&panel->base); panel_simple_disable(&panel->base);
panel_simple_unprepare(&panel->base);
if (panel->ddc) if (panel->ddc)
put_device(&panel->ddc->dev); put_device(&panel->ddc->dev);
@@ -384,6 +385,7 @@ static void panel_simple_shutdown(struct device *dev)
struct panel_simple *panel = dev_get_drvdata(dev); struct panel_simple *panel = dev_get_drvdata(dev);
panel_simple_disable(&panel->base); panel_simple_disable(&panel->base);
panel_simple_unprepare(&panel->base);
} }
static const struct drm_display_mode ampire_am800480r3tmqwa1h_mode = { static const struct drm_display_mode ampire_am800480r3tmqwa1h_mode = {
+18 -20
View File
@@ -45,34 +45,32 @@ static char *pre_emph_names[] = {
/***** radeon AUX functions *****/ /***** radeon AUX functions *****/
/* Atom needs data in little endian format /* Atom needs data in little endian format so swap as appropriate when copying
* so swap as appropriate when copying data to * data to or from atom. Note that atom operates on dw units.
* or from atom. Note that atom operates on *
* dw units. * Use to_le=true when sending data to atom and provide at least
* ALIGN(num_bytes,4) bytes in the dst buffer.
*
* Use to_le=false when receiving data from atom and provide ALIGN(num_bytes,4)
* byes in the src buffer.
*/ */
void radeon_atom_copy_swap(u8 *dst, u8 *src, u8 num_bytes, bool to_le) void radeon_atom_copy_swap(u8 *dst, u8 *src, u8 num_bytes, bool to_le)
{ {
#ifdef __BIG_ENDIAN #ifdef __BIG_ENDIAN
u8 src_tmp[20], dst_tmp[20]; /* used for byteswapping */ u32 src_tmp[5], dst_tmp[5];
u32 *dst32, *src32;
int i; int i;
u8 align_num_bytes = ALIGN(num_bytes, 4);
memcpy(src_tmp, src, num_bytes);
src32 = (u32 *)src_tmp;
dst32 = (u32 *)dst_tmp;
if (to_le) { if (to_le) {
for (i = 0; i < ((num_bytes + 3) / 4); i++) memcpy(src_tmp, src, num_bytes);
dst32[i] = cpu_to_le32(src32[i]); for (i = 0; i < align_num_bytes / 4; i++)
memcpy(dst, dst_tmp, num_bytes); dst_tmp[i] = cpu_to_le32(src_tmp[i]);
memcpy(dst, dst_tmp, align_num_bytes);
} else { } else {
u8 dws = num_bytes & ~3; memcpy(src_tmp, src, align_num_bytes);
for (i = 0; i < ((num_bytes + 3) / 4); i++) for (i = 0; i < align_num_bytes / 4; i++)
dst32[i] = le32_to_cpu(src32[i]); dst_tmp[i] = le32_to_cpu(src_tmp[i]);
memcpy(dst, dst_tmp, dws); memcpy(dst, dst_tmp, num_bytes);
if (num_bytes % 4) {
for (i = 0; i < (num_bytes % 4); i++)
dst[dws+i] = dst_tmp[dws+i];
}
} }
#else #else
memcpy(dst, src, num_bytes); memcpy(dst, src, num_bytes);
-1
View File
@@ -252,7 +252,6 @@ static int radeonfb_create(struct drm_fb_helper *helper,
} }
info->par = rfbdev; info->par = rfbdev;
info->skip_vt_switch = true;
ret = radeon_framebuffer_init(rdev->ddev, &rfbdev->rfb, &mode_cmd, gobj); ret = radeon_framebuffer_init(rdev->ddev, &rfbdev->rfb, &mode_cmd, gobj);
if (ret) { if (ret) {
+1 -1
View File
@@ -172,7 +172,7 @@ int sun4i_backend_update_layer_formats(struct sun4i_backend *backend,
ret = sun4i_backend_drm_format_to_layer(plane, fb->pixel_format, &val); ret = sun4i_backend_drm_format_to_layer(plane, fb->pixel_format, &val);
if (ret) { if (ret) {
DRM_DEBUG_DRIVER("Invalid format\n"); DRM_DEBUG_DRIVER("Invalid format\n");
return val; return ret;
} }
regmap_update_bits(backend->regs, SUN4I_BACKEND_ATTCTL_REG1(layer), regmap_update_bits(backend->regs, SUN4I_BACKEND_ATTCTL_REG1(layer),
+1
View File
@@ -473,6 +473,7 @@ static int ttm_buffer_object_transfer(struct ttm_buffer_object *bo,
INIT_LIST_HEAD(&fbo->lru); INIT_LIST_HEAD(&fbo->lru);
INIT_LIST_HEAD(&fbo->swap); INIT_LIST_HEAD(&fbo->swap);
INIT_LIST_HEAD(&fbo->io_reserve_lru); INIT_LIST_HEAD(&fbo->io_reserve_lru);
mutex_init(&fbo->wu_mutex);
fbo->moving = NULL; fbo->moving = NULL;
drm_vma_node_reset(&fbo->vma_node); drm_vma_node_reset(&fbo->vma_node);
atomic_set(&fbo->cpu_writers, 0); atomic_set(&fbo->cpu_writers, 0);
+21
View File
@@ -22,6 +22,7 @@
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ */
#include <linux/bitops.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/init.h> #include <linux/init.h>
#include <linux/slab.h> #include <linux/slab.h>
@@ -45,6 +46,7 @@ static const unsigned short normal_i2c[] = {
#define JC42_REG_TEMP 0x05 #define JC42_REG_TEMP 0x05
#define JC42_REG_MANID 0x06 #define JC42_REG_MANID 0x06
#define JC42_REG_DEVICEID 0x07 #define JC42_REG_DEVICEID 0x07
#define JC42_REG_SMBUS 0x22 /* NXP and Atmel, possibly others? */
/* Status bits in temperature register */ /* Status bits in temperature register */
#define JC42_ALARM_CRIT_BIT 15 #define JC42_ALARM_CRIT_BIT 15
@@ -73,6 +75,9 @@ static const unsigned short normal_i2c[] = {
#define ONS_MANID 0x1b09 /* ON Semiconductor */ #define ONS_MANID 0x1b09 /* ON Semiconductor */
#define STM_MANID 0x104a /* ST Microelectronics */ #define STM_MANID 0x104a /* ST Microelectronics */
/* SMBUS register */
#define SMBUS_STMOUT BIT(7) /* SMBus time-out, active low */
/* Supported chips */ /* Supported chips */
/* Analog Devices */ /* Analog Devices */
@@ -476,6 +481,22 @@ static int jc42_probe(struct i2c_client *client, const struct i2c_device_id *id)
data->extended = !!(cap & JC42_CAP_RANGE); data->extended = !!(cap & JC42_CAP_RANGE);
if (device_property_read_bool(dev, "smbus-timeout-disable")) {
int smbus;
/*
* Not all chips support this register, but from a
* quick read of various datasheets no chip appears
* incompatible with the below attempt to disable
* the timeout. And the whole thing is opt-in...
*/
smbus = i2c_smbus_read_word_swapped(client, JC42_REG_SMBUS);
if (smbus < 0)
return smbus;
i2c_smbus_write_word_swapped(client, JC42_REG_SMBUS,
smbus | SMBUS_STMOUT);
}
config = i2c_smbus_read_word_swapped(client, JC42_REG_CONFIG); config = i2c_smbus_read_word_swapped(client, JC42_REG_CONFIG);
if (config < 0) if (config < 0)
return config; return config;
+3
View File
@@ -1592,6 +1592,9 @@ static int i801_probe(struct pci_dev *dev, const struct pci_device_id *id)
/* Default timeout in interrupt mode: 200 ms */ /* Default timeout in interrupt mode: 200 ms */
priv->adapter.timeout = HZ / 5; priv->adapter.timeout = HZ / 5;
if (dev->irq == IRQ_NOTCONNECTED)
priv->features &= ~FEATURE_IRQ;
if (priv->features & FEATURE_IRQ) { if (priv->features & FEATURE_IRQ) {
u16 pcictl, pcists; u16 pcictl, pcists;
+1 -1
View File
@@ -119,7 +119,7 @@ static int cm3232_reg_init(struct cm3232_chip *chip)
if (ret < 0) if (ret < 0)
dev_err(&chip->client->dev, "Error writing reg_cmd\n"); dev_err(&chip->client->dev, "Error writing reg_cmd\n");
return 0; return ret;
} }
/** /**
+19 -6
View File
@@ -648,12 +648,19 @@ static void srp_path_rec_completion(int status,
static int srp_lookup_path(struct srp_rdma_ch *ch) static int srp_lookup_path(struct srp_rdma_ch *ch)
{ {
struct srp_target_port *target = ch->target; struct srp_target_port *target = ch->target;
int ret; int ret = -ENODEV;
ch->path.numb_path = 1; ch->path.numb_path = 1;
init_completion(&ch->done); init_completion(&ch->done);
/*
* Avoid that the SCSI host can be removed by srp_remove_target()
* before srp_path_rec_completion() is called.
*/
if (!scsi_host_get(target->scsi_host))
goto out;
ch->path_query_id = ib_sa_path_rec_get(&srp_sa_client, ch->path_query_id = ib_sa_path_rec_get(&srp_sa_client,
target->srp_host->srp_dev->dev, target->srp_host->srp_dev->dev,
target->srp_host->port, target->srp_host->port,
@@ -667,18 +674,24 @@ static int srp_lookup_path(struct srp_rdma_ch *ch)
GFP_KERNEL, GFP_KERNEL,
srp_path_rec_completion, srp_path_rec_completion,
ch, &ch->path_query); ch, &ch->path_query);
if (ch->path_query_id < 0) ret = ch->path_query_id;
return ch->path_query_id; if (ret < 0)
goto put;
ret = wait_for_completion_interruptible(&ch->done); ret = wait_for_completion_interruptible(&ch->done);
if (ret < 0) if (ret < 0)
return ret; goto put;
if (ch->status < 0) ret = ch->status;
if (ret < 0)
shost_printk(KERN_WARNING, target->scsi_host, shost_printk(KERN_WARNING, target->scsi_host,
PFX "Path record query failed\n"); PFX "Path record query failed\n");
return ch->status; put:
scsi_host_put(target->scsi_host);
out:
return ret;
} }
static int srp_send_req(struct srp_rdma_ch *ch, bool multich) static int srp_send_req(struct srp_rdma_ch *ch, bool multich)
+4 -5
View File
@@ -2750,7 +2750,7 @@ static int srpt_parse_i_port_id(u8 i_port_id[16], const char *name)
{ {
const char *p; const char *p;
unsigned len, count, leading_zero_bytes; unsigned len, count, leading_zero_bytes;
int ret, rc; int ret;
p = name; p = name;
if (strncasecmp(p, "0x", 2) == 0) if (strncasecmp(p, "0x", 2) == 0)
@@ -2762,10 +2762,9 @@ static int srpt_parse_i_port_id(u8 i_port_id[16], const char *name)
count = min(len / 2, 16U); count = min(len / 2, 16U);
leading_zero_bytes = 16 - count; leading_zero_bytes = 16 - count;
memset(i_port_id, 0, leading_zero_bytes); memset(i_port_id, 0, leading_zero_bytes);
rc = hex2bin(i_port_id + leading_zero_bytes, p, count); ret = hex2bin(i_port_id + leading_zero_bytes, p, count);
if (rc < 0) if (ret < 0)
pr_debug("hex2bin failed for srpt_parse_i_port_id: %d\n", rc); pr_debug("hex2bin failed for srpt_parse_i_port_id: %d\n", ret);
ret = 0;
out: out:
return ret; return ret;
} }
+6 -3
View File
@@ -1022,18 +1022,18 @@ static void __init gic_populate_ppi_partitions(struct device_node *gic_node)
int nr_parts; int nr_parts;
struct partition_affinity *parts; struct partition_affinity *parts;
parts_node = of_find_node_by_name(gic_node, "ppi-partitions"); parts_node = of_get_child_by_name(gic_node, "ppi-partitions");
if (!parts_node) if (!parts_node)
return; return;
nr_parts = of_get_child_count(parts_node); nr_parts = of_get_child_count(parts_node);
if (!nr_parts) if (!nr_parts)
return; goto out_put_node;
parts = kzalloc(sizeof(*parts) * nr_parts, GFP_KERNEL); parts = kzalloc(sizeof(*parts) * nr_parts, GFP_KERNEL);
if (WARN_ON(!parts)) if (WARN_ON(!parts))
return; goto out_put_node;
for_each_child_of_node(parts_node, child_part) { for_each_child_of_node(parts_node, child_part) {
struct partition_affinity *part; struct partition_affinity *part;
@@ -1100,6 +1100,9 @@ static void __init gic_populate_ppi_partitions(struct device_node *gic_node)
gic_data.ppi_descs[i] = desc; gic_data.ppi_descs[i] = desc;
} }
out_put_node:
of_node_put(parts_node);
} }
static void __init gic_of_setup_kvm_info(struct device_node *node) static void __init gic_of_setup_kvm_info(struct device_node *node)
+3 -2
View File
@@ -404,7 +404,8 @@ long bch_bucket_alloc(struct cache *ca, unsigned reserve, bool wait)
finish_wait(&ca->set->bucket_wait, &w); finish_wait(&ca->set->bucket_wait, &w);
out: out:
wake_up_process(ca->alloc_thread); if (ca->alloc_thread)
wake_up_process(ca->alloc_thread);
trace_bcache_alloc(ca, reserve); trace_bcache_alloc(ca, reserve);
@@ -476,7 +477,7 @@ int __bch_bucket_alloc_set(struct cache_set *c, unsigned reserve,
if (b == -1) if (b == -1)
goto err; goto err;
k->ptr[i] = PTR(ca->buckets[b].gen, k->ptr[i] = MAKE_PTR(ca->buckets[b].gen,
bucket_to_sector(c, b), bucket_to_sector(c, b),
ca->sb.nr_this_dev); ca->sb.nr_this_dev);
+1 -1
View File
@@ -584,7 +584,7 @@ static bool bch_extent_merge(struct btree_keys *bk, struct bkey *l, struct bkey
return false; return false;
for (i = 0; i < KEY_PTRS(l); i++) for (i = 0; i < KEY_PTRS(l); i++)
if (l->ptr[i] + PTR(0, KEY_SIZE(l), 0) != r->ptr[i] || if (l->ptr[i] + MAKE_PTR(0, KEY_SIZE(l), 0) != r->ptr[i] ||
PTR_BUCKET_NR(b->c, l, i) != PTR_BUCKET_NR(b->c, r, i)) PTR_BUCKET_NR(b->c, l, i) != PTR_BUCKET_NR(b->c, r, i))
return false; return false;
+1 -1
View File
@@ -508,7 +508,7 @@ static void journal_reclaim(struct cache_set *c)
continue; continue;
ja->cur_idx = next; ja->cur_idx = next;
k->ptr[n++] = PTR(0, k->ptr[n++] = MAKE_PTR(0,
bucket_to_sector(c, ca->sb.d[ja->cur_idx]), bucket_to_sector(c, ca->sb.d[ja->cur_idx]),
ca->sb.nr_this_dev); ca->sb.nr_this_dev);
} }
+6 -9
View File
@@ -937,7 +937,8 @@ static void __get_memory_limit(struct dm_bufio_client *c,
buffers = c->minimum_buffers; buffers = c->minimum_buffers;
*limit_buffers = buffers; *limit_buffers = buffers;
*threshold_buffers = buffers * DM_BUFIO_WRITEBACK_PERCENT / 100; *threshold_buffers = mult_frac(buffers,
DM_BUFIO_WRITEBACK_PERCENT, 100);
} }
/* /*
@@ -1856,19 +1857,15 @@ static int __init dm_bufio_init(void)
memset(&dm_bufio_caches, 0, sizeof dm_bufio_caches); memset(&dm_bufio_caches, 0, sizeof dm_bufio_caches);
memset(&dm_bufio_cache_names, 0, sizeof dm_bufio_cache_names); memset(&dm_bufio_cache_names, 0, sizeof dm_bufio_cache_names);
mem = (__u64)((totalram_pages - totalhigh_pages) * mem = (__u64)mult_frac(totalram_pages - totalhigh_pages,
DM_BUFIO_MEMORY_PERCENT / 100) << PAGE_SHIFT; DM_BUFIO_MEMORY_PERCENT, 100) << PAGE_SHIFT;
if (mem > ULONG_MAX) if (mem > ULONG_MAX)
mem = ULONG_MAX; mem = ULONG_MAX;
#ifdef CONFIG_MMU #ifdef CONFIG_MMU
/* if (mem > mult_frac(VMALLOC_TOTAL, DM_BUFIO_VMALLOC_PERCENT, 100))
* Get the size of vmalloc space the same way as VMALLOC_TOTAL mem = mult_frac(VMALLOC_TOTAL, DM_BUFIO_VMALLOC_PERCENT, 100);
* in fs/proc/internal.h
*/
if (mem > (VMALLOC_END - VMALLOC_START) * DM_BUFIO_VMALLOC_PERCENT / 100)
mem = (VMALLOC_END - VMALLOC_START) * DM_BUFIO_VMALLOC_PERCENT / 100;
#endif #endif
dm_bufio_default_cache_size = mem; dm_bufio_default_cache_size = mem;
+2 -1
View File
@@ -29,7 +29,6 @@ struct dm_kobject_holder {
* DM targets must _not_ deference a mapped_device to directly access its members! * DM targets must _not_ deference a mapped_device to directly access its members!
*/ */
struct mapped_device { struct mapped_device {
struct srcu_struct io_barrier;
struct mutex suspend_lock; struct mutex suspend_lock;
/* /*
@@ -127,6 +126,8 @@ struct mapped_device {
struct blk_mq_tag_set *tag_set; struct blk_mq_tag_set *tag_set;
bool use_blk_mq:1; bool use_blk_mq:1;
bool init_tio_pdu:1; bool init_tio_pdu:1;
struct srcu_struct io_barrier;
}; };
void dm_init_md_queue(struct mapped_device *md); void dm_init_md_queue(struct mapped_device *md);
+12 -7
View File
@@ -21,6 +21,7 @@
#include <linux/delay.h> #include <linux/delay.h>
#include <linux/wait.h> #include <linux/wait.h>
#include <linux/pr.h> #include <linux/pr.h>
#include <linux/vmalloc.h>
#define DM_MSG_PREFIX "core" #define DM_MSG_PREFIX "core"
@@ -1511,7 +1512,7 @@ static struct mapped_device *alloc_dev(int minor)
struct mapped_device *md; struct mapped_device *md;
void *old_md; void *old_md;
md = kzalloc_node(sizeof(*md), GFP_KERNEL, numa_node_id); md = vzalloc_node(sizeof(*md), numa_node_id);
if (!md) { if (!md) {
DMWARN("unable to allocate device, out of memory."); DMWARN("unable to allocate device, out of memory.");
return NULL; return NULL;
@@ -1605,7 +1606,7 @@ bad_io_barrier:
bad_minor: bad_minor:
module_put(THIS_MODULE); module_put(THIS_MODULE);
bad_module_get: bad_module_get:
kfree(md); kvfree(md);
return NULL; return NULL;
} }
@@ -1624,7 +1625,7 @@ static void free_dev(struct mapped_device *md)
free_minor(minor); free_minor(minor);
module_put(THIS_MODULE); module_put(THIS_MODULE);
kfree(md); kvfree(md);
} }
static void __bind_mempools(struct mapped_device *md, struct dm_table *t) static void __bind_mempools(struct mapped_device *md, struct dm_table *t)
@@ -2514,11 +2515,15 @@ struct mapped_device *dm_get_from_kobject(struct kobject *kobj)
md = container_of(kobj, struct mapped_device, kobj_holder.kobj); md = container_of(kobj, struct mapped_device, kobj_holder.kobj);
if (test_bit(DMF_FREEING, &md->flags) || spin_lock(&_minor_lock);
dm_deleting_md(md)) if (test_bit(DMF_FREEING, &md->flags) || dm_deleting_md(md)) {
return NULL; md = NULL;
goto out;
}
dm_get(md); dm_get(md);
out:
spin_unlock(&_minor_lock);
return md; return md;
} }
+6 -3
View File
@@ -286,11 +286,14 @@ static long ir_lirc_ioctl(struct file *filep, unsigned int cmd,
if (!dev->max_timeout) if (!dev->max_timeout)
return -ENOSYS; return -ENOSYS;
/* Check for multiply overflow */
if (val > U32_MAX / 1000)
return -EINVAL;
tmp = val * 1000; tmp = val * 1000;
if (tmp < dev->min_timeout || if (tmp < dev->min_timeout || tmp > dev->max_timeout)
tmp > dev->max_timeout) return -EINVAL;
return -EINVAL;
if (dev->s_timeout) if (dev->s_timeout)
ret = dev->s_timeout(dev, tmp); ret = dev->s_timeout(dev, tmp);
+17 -11
View File
@@ -101,18 +101,23 @@ static int as102_firmware_upload(struct as10x_bus_adapter_t *bus_adap,
unsigned char *cmd, unsigned char *cmd,
const struct firmware *firmware) { const struct firmware *firmware) {
struct as10x_fw_pkt_t fw_pkt; struct as10x_fw_pkt_t *fw_pkt;
int total_read_bytes = 0, errno = 0; int total_read_bytes = 0, errno = 0;
unsigned char addr_has_changed = 0; unsigned char addr_has_changed = 0;
fw_pkt = kmalloc(sizeof(*fw_pkt), GFP_KERNEL);
if (!fw_pkt)
return -ENOMEM;
for (total_read_bytes = 0; total_read_bytes < firmware->size; ) { for (total_read_bytes = 0; total_read_bytes < firmware->size; ) {
int read_bytes = 0, data_len = 0; int read_bytes = 0, data_len = 0;
/* parse intel hex line */ /* parse intel hex line */
read_bytes = parse_hex_line( read_bytes = parse_hex_line(
(u8 *) (firmware->data + total_read_bytes), (u8 *) (firmware->data + total_read_bytes),
fw_pkt.raw.address, fw_pkt->raw.address,
fw_pkt.raw.data, fw_pkt->raw.data,
&data_len, &data_len,
&addr_has_changed); &addr_has_changed);
@@ -122,28 +127,28 @@ static int as102_firmware_upload(struct as10x_bus_adapter_t *bus_adap,
/* detect the end of file */ /* detect the end of file */
total_read_bytes += read_bytes; total_read_bytes += read_bytes;
if (total_read_bytes == firmware->size) { if (total_read_bytes == firmware->size) {
fw_pkt.u.request[0] = 0x00; fw_pkt->u.request[0] = 0x00;
fw_pkt.u.request[1] = 0x03; fw_pkt->u.request[1] = 0x03;
/* send EOF command */ /* send EOF command */
errno = bus_adap->ops->upload_fw_pkt(bus_adap, errno = bus_adap->ops->upload_fw_pkt(bus_adap,
(uint8_t *) (uint8_t *)
&fw_pkt, 2, 0); fw_pkt, 2, 0);
if (errno < 0) if (errno < 0)
goto error; goto error;
} else { } else {
if (!addr_has_changed) { if (!addr_has_changed) {
/* prepare command to send */ /* prepare command to send */
fw_pkt.u.request[0] = 0x00; fw_pkt->u.request[0] = 0x00;
fw_pkt.u.request[1] = 0x01; fw_pkt->u.request[1] = 0x01;
data_len += sizeof(fw_pkt.u.request); data_len += sizeof(fw_pkt->u.request);
data_len += sizeof(fw_pkt.raw.address); data_len += sizeof(fw_pkt->raw.address);
/* send cmd to device */ /* send cmd to device */
errno = bus_adap->ops->upload_fw_pkt(bus_adap, errno = bus_adap->ops->upload_fw_pkt(bus_adap,
(uint8_t *) (uint8_t *)
&fw_pkt, fw_pkt,
data_len, data_len,
0); 0);
if (errno < 0) if (errno < 0)
@@ -152,6 +157,7 @@ static int as102_firmware_upload(struct as10x_bus_adapter_t *bus_adap,
} }
} }
error: error:
kfree(fw_pkt);
return (errno == 0) ? total_read_bytes : errno; return (errno == 0) ? total_read_bytes : errno;
} }
+1 -1
View File
@@ -1622,7 +1622,7 @@ static int cx231xx_usb_probe(struct usb_interface *interface,
nr = dev->devno; nr = dev->devno;
assoc_desc = udev->actconfig->intf_assoc[0]; assoc_desc = udev->actconfig->intf_assoc[0];
if (assoc_desc->bFirstInterface != ifnum) { if (!assoc_desc || assoc_desc->bFirstInterface != ifnum) {
dev_err(d, "Not found matching IAD interface\n"); dev_err(d, "Not found matching IAD interface\n");
retval = -ENODEV; retval = -ENODEV;
goto err_if; goto err_if;
+12 -4
View File
@@ -1219,6 +1219,16 @@ void v4l2_ctrl_fill(u32 id, const char **name, enum v4l2_ctrl_type *type,
} }
EXPORT_SYMBOL(v4l2_ctrl_fill); EXPORT_SYMBOL(v4l2_ctrl_fill);
static u32 user_flags(const struct v4l2_ctrl *ctrl)
{
u32 flags = ctrl->flags;
if (ctrl->is_ptr)
flags |= V4L2_CTRL_FLAG_HAS_PAYLOAD;
return flags;
}
static void fill_event(struct v4l2_event *ev, struct v4l2_ctrl *ctrl, u32 changes) static void fill_event(struct v4l2_event *ev, struct v4l2_ctrl *ctrl, u32 changes)
{ {
memset(ev->reserved, 0, sizeof(ev->reserved)); memset(ev->reserved, 0, sizeof(ev->reserved));
@@ -1226,7 +1236,7 @@ static void fill_event(struct v4l2_event *ev, struct v4l2_ctrl *ctrl, u32 change
ev->id = ctrl->id; ev->id = ctrl->id;
ev->u.ctrl.changes = changes; ev->u.ctrl.changes = changes;
ev->u.ctrl.type = ctrl->type; ev->u.ctrl.type = ctrl->type;
ev->u.ctrl.flags = ctrl->flags; ev->u.ctrl.flags = user_flags(ctrl);
if (ctrl->is_ptr) if (ctrl->is_ptr)
ev->u.ctrl.value64 = 0; ev->u.ctrl.value64 = 0;
else else
@@ -2550,10 +2560,8 @@ int v4l2_query_ext_ctrl(struct v4l2_ctrl_handler *hdl, struct v4l2_query_ext_ctr
else else
qc->id = ctrl->id; qc->id = ctrl->id;
strlcpy(qc->name, ctrl->name, sizeof(qc->name)); strlcpy(qc->name, ctrl->name, sizeof(qc->name));
qc->flags = ctrl->flags; qc->flags = user_flags(ctrl);
qc->type = ctrl->type; qc->type = ctrl->type;
if (ctrl->is_ptr)
qc->flags |= V4L2_CTRL_FLAG_HAS_PAYLOAD;
qc->elem_size = ctrl->elem_size; qc->elem_size = ctrl->elem_size;
qc->elems = ctrl->elems; qc->elems = ctrl->elems;
qc->nr_of_dims = ctrl->nr_of_dims; qc->nr_of_dims = ctrl->nr_of_dims;
+1
View File
@@ -701,6 +701,7 @@ static struct twl4030_ins omap3_wrst_seq[] = {
TWL_RESOURCE_RESET(RES_MAIN_REF), TWL_RESOURCE_RESET(RES_MAIN_REF),
TWL_RESOURCE_GROUP_RESET(RES_GRP_ALL, RES_TYPE_R0, RES_TYPE2_R2), TWL_RESOURCE_GROUP_RESET(RES_GRP_ALL, RES_TYPE_R0, RES_TYPE2_R2),
TWL_RESOURCE_RESET(RES_VUSB_3V1), TWL_RESOURCE_RESET(RES_VUSB_3V1),
TWL_RESOURCE_RESET(RES_VMMC1),
TWL_RESOURCE_GROUP_RESET(RES_GRP_ALL, RES_TYPE_R0, RES_TYPE2_R1), TWL_RESOURCE_GROUP_RESET(RES_GRP_ALL, RES_TYPE_R0, RES_TYPE2_R1),
TWL_RESOURCE_GROUP_RESET(RES_GRP_RC, RES_TYPE_ALL, RES_TYPE2_R0), TWL_RESOURCE_GROUP_RESET(RES_GRP_RC, RES_TYPE_ALL, RES_TYPE2_R0),
TWL_RESOURCE_ON(RES_RESET), TWL_RESOURCE_ON(RES_RESET),
+18 -1
View File
@@ -365,7 +365,8 @@ static ssize_t at24_eeprom_read_mac(struct at24_data *at24, char *buf,
memset(msg, 0, sizeof(msg)); memset(msg, 0, sizeof(msg));
msg[0].addr = client->addr; msg[0].addr = client->addr;
msg[0].buf = addrbuf; msg[0].buf = addrbuf;
addrbuf[0] = 0x90 + offset; /* EUI-48 starts from 0x9a, EUI-64 from 0x98 */
addrbuf[0] = 0xa0 - at24->chip.byte_len + offset;
msg[0].len = 1; msg[0].len = 1;
msg[1].addr = client->addr; msg[1].addr = client->addr;
msg[1].flags = I2C_M_RD; msg[1].flags = I2C_M_RD;
@@ -506,6 +507,9 @@ static int at24_read(void *priv, unsigned int off, void *val, size_t count)
if (unlikely(!count)) if (unlikely(!count))
return count; return count;
if (off + count > at24->chip.byte_len)
return -EINVAL;
/* /*
* Read data from chip, protecting against concurrent updates * Read data from chip, protecting against concurrent updates
* from this host, but not from other I2C masters. * from this host, but not from other I2C masters.
@@ -538,6 +542,9 @@ static int at24_write(void *priv, unsigned int off, void *val, size_t count)
if (unlikely(!count)) if (unlikely(!count))
return -EINVAL; return -EINVAL;
if (off + count > at24->chip.byte_len)
return -EINVAL;
/* /*
* Write data to chip, protecting against concurrent updates * Write data to chip, protecting against concurrent updates
* from this host, but not from other I2C masters. * from this host, but not from other I2C masters.
@@ -638,6 +645,16 @@ static int at24_probe(struct i2c_client *client, const struct i2c_device_id *id)
dev_warn(&client->dev, dev_warn(&client->dev,
"page_size looks suspicious (no power of 2)!\n"); "page_size looks suspicious (no power of 2)!\n");
/*
* REVISIT: the size of the EUI-48 byte array is 6 in at24mac402, while
* the call to ilog2() in AT24_DEVICE_MAGIC() rounds it down to 4.
*
* Eventually we'll get rid of the magic values altoghether in favor of
* real structs, but for now just manually set the right size.
*/
if (chip.flags & AT24_FLAG_MAC && chip.byte_len == 4)
chip.byte_len = 6;
/* Use I2C operations unless we're stuck with SMBus extensions. */ /* Use I2C operations unless we're stuck with SMBus extensions. */
if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) { if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) {
if (chip.flags & AT24_FLAG_ADDR16) if (chip.flags & AT24_FLAG_ADDR16)
+3
View File
@@ -155,6 +155,9 @@ static int mmc_bus_suspend(struct device *dev)
return ret; return ret;
ret = host->bus_ops->suspend(host); ret = host->bus_ops->suspend(host);
if (ret)
pm_generic_resume(dev);
return ret; return ret;
} }
+1 -1
View File
@@ -763,7 +763,7 @@ MMC_DEV_ATTR(enhanced_area_offset, "%llu\n",
MMC_DEV_ATTR(enhanced_area_size, "%u\n", card->ext_csd.enhanced_area_size); MMC_DEV_ATTR(enhanced_area_size, "%u\n", card->ext_csd.enhanced_area_size);
MMC_DEV_ATTR(raw_rpmb_size_mult, "%#x\n", card->ext_csd.raw_rpmb_size_mult); MMC_DEV_ATTR(raw_rpmb_size_mult, "%#x\n", card->ext_csd.raw_rpmb_size_mult);
MMC_DEV_ATTR(rel_sectors, "%#x\n", card->ext_csd.rel_sectors); MMC_DEV_ATTR(rel_sectors, "%#x\n", card->ext_csd.rel_sectors);
MMC_DEV_ATTR(ocr, "%08x\n", card->ocr); MMC_DEV_ATTR(ocr, "0x%08x\n", card->ocr);
static ssize_t mmc_fwrev_show(struct device *dev, static ssize_t mmc_fwrev_show(struct device *dev,
struct device_attribute *attr, struct device_attribute *attr,
+1 -1
View File
@@ -683,7 +683,7 @@ MMC_DEV_ATTR(manfid, "0x%06x\n", card->cid.manfid);
MMC_DEV_ATTR(name, "%s\n", card->cid.prod_name); MMC_DEV_ATTR(name, "%s\n", card->cid.prod_name);
MMC_DEV_ATTR(oemid, "0x%04x\n", card->cid.oemid); MMC_DEV_ATTR(oemid, "0x%04x\n", card->cid.oemid);
MMC_DEV_ATTR(serial, "0x%08x\n", card->cid.serial); MMC_DEV_ATTR(serial, "0x%08x\n", card->cid.serial);
MMC_DEV_ATTR(ocr, "%08x\n", card->ocr); MMC_DEV_ATTR(ocr, "0x%08x\n", card->ocr);
static ssize_t mmc_dsr_show(struct device *dev, static ssize_t mmc_dsr_show(struct device *dev,
+11 -2
View File
@@ -116,6 +116,11 @@ static irqreturn_t mtk_ecc_irq(int irq, void *id)
op = ECC_DECODE; op = ECC_DECODE;
dec = readw(ecc->regs + ECC_DECDONE); dec = readw(ecc->regs + ECC_DECDONE);
if (dec & ecc->sectors) { if (dec & ecc->sectors) {
/*
* Clear decode IRQ status once again to ensure that
* there will be no extra IRQ.
*/
readw(ecc->regs + ECC_DECIRQ_STA);
ecc->sectors = 0; ecc->sectors = 0;
complete(&ecc->done); complete(&ecc->done);
} else { } else {
@@ -131,8 +136,6 @@ static irqreturn_t mtk_ecc_irq(int irq, void *id)
} }
} }
writel(0, ecc->regs + ECC_IRQ_REG(op));
return IRQ_HANDLED; return IRQ_HANDLED;
} }
@@ -342,6 +345,12 @@ void mtk_ecc_disable(struct mtk_ecc *ecc)
/* disable it */ /* disable it */
mtk_ecc_wait_idle(ecc, op); mtk_ecc_wait_idle(ecc, op);
if (op == ECC_DECODE)
/*
* Clear decode IRQ status in case there is a timeout to wait
* decode IRQ.
*/
readw(ecc->regs + ECC_DECIRQ_STA);
writew(0, ecc->regs + ECC_IRQ_REG(op)); writew(0, ecc->regs + ECC_IRQ_REG(op));
writew(ECC_OP_DISABLE, ecc->regs + ECC_CTL_REG(op)); writew(ECC_OP_DISABLE, ecc->regs + ECC_CTL_REG(op));
+6 -3
View File
@@ -2935,15 +2935,18 @@ static int panic_nand_write(struct mtd_info *mtd, loff_t to, size_t len,
size_t *retlen, const uint8_t *buf) size_t *retlen, const uint8_t *buf)
{ {
struct nand_chip *chip = mtd_to_nand(mtd); struct nand_chip *chip = mtd_to_nand(mtd);
int chipnr = (int)(to >> chip->chip_shift);
struct mtd_oob_ops ops; struct mtd_oob_ops ops;
int ret; int ret;
/* Wait for the device to get ready */
panic_nand_wait(mtd, chip, 400);
/* Grab the device */ /* Grab the device */
panic_nand_get_device(chip, mtd, FL_WRITING); panic_nand_get_device(chip, mtd, FL_WRITING);
chip->select_chip(mtd, chipnr);
/* Wait for the device to get ready */
panic_nand_wait(mtd, chip, 400);
memset(&ops, 0, sizeof(ops)); memset(&ops, 0, sizeof(ops));
ops.len = len; ops.len = len;
ops.datbuf = (uint8_t *)buf; ops.datbuf = (uint8_t *)buf;
+224 -115
View File
@@ -1133,129 +1133,172 @@ static u8 bch8_polynomial[] = {0xef, 0x51, 0x2e, 0x09, 0xed, 0x93, 0x9a, 0xc2,
0x97, 0x79, 0xe5, 0x24, 0xb5}; 0x97, 0x79, 0xe5, 0x24, 0xb5};
/** /**
* omap_calculate_ecc_bch - Generate bytes of ECC bytes * _omap_calculate_ecc_bch - Generate ECC bytes for one sector
* @mtd: MTD device structure * @mtd: MTD device structure
* @dat: The pointer to data on which ecc is computed * @dat: The pointer to data on which ecc is computed
* @ecc_code: The ecc_code buffer * @ecc_code: The ecc_code buffer
* @i: The sector number (for a multi sector page)
* *
* Support calculating of BCH4/8 ecc vectors for the page * Support calculating of BCH4/8/16 ECC vectors for one sector
* within a page. Sector number is in @i.
*/ */
static int __maybe_unused omap_calculate_ecc_bch(struct mtd_info *mtd, static int _omap_calculate_ecc_bch(struct mtd_info *mtd,
const u_char *dat, u_char *ecc_calc) const u_char *dat, u_char *ecc_calc, int i)
{ {
struct omap_nand_info *info = mtd_to_omap(mtd); struct omap_nand_info *info = mtd_to_omap(mtd);
int eccbytes = info->nand.ecc.bytes; int eccbytes = info->nand.ecc.bytes;
struct gpmc_nand_regs *gpmc_regs = &info->reg; struct gpmc_nand_regs *gpmc_regs = &info->reg;
u8 *ecc_code; u8 *ecc_code;
unsigned long nsectors, bch_val1, bch_val2, bch_val3, bch_val4; unsigned long bch_val1, bch_val2, bch_val3, bch_val4;
u32 val; u32 val;
int i, j; int j;
ecc_code = ecc_calc;
switch (info->ecc_opt) {
case OMAP_ECC_BCH8_CODE_HW_DETECTION_SW:
case OMAP_ECC_BCH8_CODE_HW:
bch_val1 = readl(gpmc_regs->gpmc_bch_result0[i]);
bch_val2 = readl(gpmc_regs->gpmc_bch_result1[i]);
bch_val3 = readl(gpmc_regs->gpmc_bch_result2[i]);
bch_val4 = readl(gpmc_regs->gpmc_bch_result3[i]);
*ecc_code++ = (bch_val4 & 0xFF);
*ecc_code++ = ((bch_val3 >> 24) & 0xFF);
*ecc_code++ = ((bch_val3 >> 16) & 0xFF);
*ecc_code++ = ((bch_val3 >> 8) & 0xFF);
*ecc_code++ = (bch_val3 & 0xFF);
*ecc_code++ = ((bch_val2 >> 24) & 0xFF);
*ecc_code++ = ((bch_val2 >> 16) & 0xFF);
*ecc_code++ = ((bch_val2 >> 8) & 0xFF);
*ecc_code++ = (bch_val2 & 0xFF);
*ecc_code++ = ((bch_val1 >> 24) & 0xFF);
*ecc_code++ = ((bch_val1 >> 16) & 0xFF);
*ecc_code++ = ((bch_val1 >> 8) & 0xFF);
*ecc_code++ = (bch_val1 & 0xFF);
break;
case OMAP_ECC_BCH4_CODE_HW_DETECTION_SW:
case OMAP_ECC_BCH4_CODE_HW:
bch_val1 = readl(gpmc_regs->gpmc_bch_result0[i]);
bch_val2 = readl(gpmc_regs->gpmc_bch_result1[i]);
*ecc_code++ = ((bch_val2 >> 12) & 0xFF);
*ecc_code++ = ((bch_val2 >> 4) & 0xFF);
*ecc_code++ = ((bch_val2 & 0xF) << 4) |
((bch_val1 >> 28) & 0xF);
*ecc_code++ = ((bch_val1 >> 20) & 0xFF);
*ecc_code++ = ((bch_val1 >> 12) & 0xFF);
*ecc_code++ = ((bch_val1 >> 4) & 0xFF);
*ecc_code++ = ((bch_val1 & 0xF) << 4);
break;
case OMAP_ECC_BCH16_CODE_HW:
val = readl(gpmc_regs->gpmc_bch_result6[i]);
ecc_code[0] = ((val >> 8) & 0xFF);
ecc_code[1] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result5[i]);
ecc_code[2] = ((val >> 24) & 0xFF);
ecc_code[3] = ((val >> 16) & 0xFF);
ecc_code[4] = ((val >> 8) & 0xFF);
ecc_code[5] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result4[i]);
ecc_code[6] = ((val >> 24) & 0xFF);
ecc_code[7] = ((val >> 16) & 0xFF);
ecc_code[8] = ((val >> 8) & 0xFF);
ecc_code[9] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result3[i]);
ecc_code[10] = ((val >> 24) & 0xFF);
ecc_code[11] = ((val >> 16) & 0xFF);
ecc_code[12] = ((val >> 8) & 0xFF);
ecc_code[13] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result2[i]);
ecc_code[14] = ((val >> 24) & 0xFF);
ecc_code[15] = ((val >> 16) & 0xFF);
ecc_code[16] = ((val >> 8) & 0xFF);
ecc_code[17] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result1[i]);
ecc_code[18] = ((val >> 24) & 0xFF);
ecc_code[19] = ((val >> 16) & 0xFF);
ecc_code[20] = ((val >> 8) & 0xFF);
ecc_code[21] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result0[i]);
ecc_code[22] = ((val >> 24) & 0xFF);
ecc_code[23] = ((val >> 16) & 0xFF);
ecc_code[24] = ((val >> 8) & 0xFF);
ecc_code[25] = ((val >> 0) & 0xFF);
break;
default:
return -EINVAL;
}
/* ECC scheme specific syndrome customizations */
switch (info->ecc_opt) {
case OMAP_ECC_BCH4_CODE_HW_DETECTION_SW:
/* Add constant polynomial to remainder, so that
* ECC of blank pages results in 0x0 on reading back
*/
for (j = 0; j < eccbytes; j++)
ecc_calc[j] ^= bch4_polynomial[j];
break;
case OMAP_ECC_BCH4_CODE_HW:
/* Set 8th ECC byte as 0x0 for ROM compatibility */
ecc_calc[eccbytes - 1] = 0x0;
break;
case OMAP_ECC_BCH8_CODE_HW_DETECTION_SW:
/* Add constant polynomial to remainder, so that
* ECC of blank pages results in 0x0 on reading back
*/
for (j = 0; j < eccbytes; j++)
ecc_calc[j] ^= bch8_polynomial[j];
break;
case OMAP_ECC_BCH8_CODE_HW:
/* Set 14th ECC byte as 0x0 for ROM compatibility */
ecc_calc[eccbytes - 1] = 0x0;
break;
case OMAP_ECC_BCH16_CODE_HW:
break;
default:
return -EINVAL;
}
return 0;
}
/**
* omap_calculate_ecc_bch_sw - ECC generator for sector for SW based correction
* @mtd: MTD device structure
* @dat: The pointer to data on which ecc is computed
* @ecc_code: The ecc_code buffer
*
* Support calculating of BCH4/8/16 ECC vectors for one sector. This is used
* when SW based correction is required as ECC is required for one sector
* at a time.
*/
static int omap_calculate_ecc_bch_sw(struct mtd_info *mtd,
const u_char *dat, u_char *ecc_calc)
{
return _omap_calculate_ecc_bch(mtd, dat, ecc_calc, 0);
}
/**
* omap_calculate_ecc_bch_multi - Generate ECC for multiple sectors
* @mtd: MTD device structure
* @dat: The pointer to data on which ecc is computed
* @ecc_code: The ecc_code buffer
*
* Support calculating of BCH4/8/16 ecc vectors for the entire page in one go.
*/
static int omap_calculate_ecc_bch_multi(struct mtd_info *mtd,
const u_char *dat, u_char *ecc_calc)
{
struct omap_nand_info *info = mtd_to_omap(mtd);
int eccbytes = info->nand.ecc.bytes;
unsigned long nsectors;
int i, ret;
nsectors = ((readl(info->reg.gpmc_ecc_config) >> 4) & 0x7) + 1; nsectors = ((readl(info->reg.gpmc_ecc_config) >> 4) & 0x7) + 1;
for (i = 0; i < nsectors; i++) { for (i = 0; i < nsectors; i++) {
ecc_code = ecc_calc; ret = _omap_calculate_ecc_bch(mtd, dat, ecc_calc, i);
switch (info->ecc_opt) { if (ret)
case OMAP_ECC_BCH8_CODE_HW_DETECTION_SW: return ret;
case OMAP_ECC_BCH8_CODE_HW:
bch_val1 = readl(gpmc_regs->gpmc_bch_result0[i]);
bch_val2 = readl(gpmc_regs->gpmc_bch_result1[i]);
bch_val3 = readl(gpmc_regs->gpmc_bch_result2[i]);
bch_val4 = readl(gpmc_regs->gpmc_bch_result3[i]);
*ecc_code++ = (bch_val4 & 0xFF);
*ecc_code++ = ((bch_val3 >> 24) & 0xFF);
*ecc_code++ = ((bch_val3 >> 16) & 0xFF);
*ecc_code++ = ((bch_val3 >> 8) & 0xFF);
*ecc_code++ = (bch_val3 & 0xFF);
*ecc_code++ = ((bch_val2 >> 24) & 0xFF);
*ecc_code++ = ((bch_val2 >> 16) & 0xFF);
*ecc_code++ = ((bch_val2 >> 8) & 0xFF);
*ecc_code++ = (bch_val2 & 0xFF);
*ecc_code++ = ((bch_val1 >> 24) & 0xFF);
*ecc_code++ = ((bch_val1 >> 16) & 0xFF);
*ecc_code++ = ((bch_val1 >> 8) & 0xFF);
*ecc_code++ = (bch_val1 & 0xFF);
break;
case OMAP_ECC_BCH4_CODE_HW_DETECTION_SW:
case OMAP_ECC_BCH4_CODE_HW:
bch_val1 = readl(gpmc_regs->gpmc_bch_result0[i]);
bch_val2 = readl(gpmc_regs->gpmc_bch_result1[i]);
*ecc_code++ = ((bch_val2 >> 12) & 0xFF);
*ecc_code++ = ((bch_val2 >> 4) & 0xFF);
*ecc_code++ = ((bch_val2 & 0xF) << 4) |
((bch_val1 >> 28) & 0xF);
*ecc_code++ = ((bch_val1 >> 20) & 0xFF);
*ecc_code++ = ((bch_val1 >> 12) & 0xFF);
*ecc_code++ = ((bch_val1 >> 4) & 0xFF);
*ecc_code++ = ((bch_val1 & 0xF) << 4);
break;
case OMAP_ECC_BCH16_CODE_HW:
val = readl(gpmc_regs->gpmc_bch_result6[i]);
ecc_code[0] = ((val >> 8) & 0xFF);
ecc_code[1] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result5[i]);
ecc_code[2] = ((val >> 24) & 0xFF);
ecc_code[3] = ((val >> 16) & 0xFF);
ecc_code[4] = ((val >> 8) & 0xFF);
ecc_code[5] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result4[i]);
ecc_code[6] = ((val >> 24) & 0xFF);
ecc_code[7] = ((val >> 16) & 0xFF);
ecc_code[8] = ((val >> 8) & 0xFF);
ecc_code[9] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result3[i]);
ecc_code[10] = ((val >> 24) & 0xFF);
ecc_code[11] = ((val >> 16) & 0xFF);
ecc_code[12] = ((val >> 8) & 0xFF);
ecc_code[13] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result2[i]);
ecc_code[14] = ((val >> 24) & 0xFF);
ecc_code[15] = ((val >> 16) & 0xFF);
ecc_code[16] = ((val >> 8) & 0xFF);
ecc_code[17] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result1[i]);
ecc_code[18] = ((val >> 24) & 0xFF);
ecc_code[19] = ((val >> 16) & 0xFF);
ecc_code[20] = ((val >> 8) & 0xFF);
ecc_code[21] = ((val >> 0) & 0xFF);
val = readl(gpmc_regs->gpmc_bch_result0[i]);
ecc_code[22] = ((val >> 24) & 0xFF);
ecc_code[23] = ((val >> 16) & 0xFF);
ecc_code[24] = ((val >> 8) & 0xFF);
ecc_code[25] = ((val >> 0) & 0xFF);
break;
default:
return -EINVAL;
}
/* ECC scheme specific syndrome customizations */ ecc_calc += eccbytes;
switch (info->ecc_opt) {
case OMAP_ECC_BCH4_CODE_HW_DETECTION_SW:
/* Add constant polynomial to remainder, so that
* ECC of blank pages results in 0x0 on reading back */
for (j = 0; j < eccbytes; j++)
ecc_calc[j] ^= bch4_polynomial[j];
break;
case OMAP_ECC_BCH4_CODE_HW:
/* Set 8th ECC byte as 0x0 for ROM compatibility */
ecc_calc[eccbytes - 1] = 0x0;
break;
case OMAP_ECC_BCH8_CODE_HW_DETECTION_SW:
/* Add constant polynomial to remainder, so that
* ECC of blank pages results in 0x0 on reading back */
for (j = 0; j < eccbytes; j++)
ecc_calc[j] ^= bch8_polynomial[j];
break;
case OMAP_ECC_BCH8_CODE_HW:
/* Set 14th ECC byte as 0x0 for ROM compatibility */
ecc_calc[eccbytes - 1] = 0x0;
break;
case OMAP_ECC_BCH16_CODE_HW:
break;
default:
return -EINVAL;
}
ecc_calc += eccbytes;
} }
return 0; return 0;
@@ -1496,7 +1539,7 @@ static int omap_write_page_bch(struct mtd_info *mtd, struct nand_chip *chip,
chip->write_buf(mtd, buf, mtd->writesize); chip->write_buf(mtd, buf, mtd->writesize);
/* Update ecc vector from GPMC result registers */ /* Update ecc vector from GPMC result registers */
chip->ecc.calculate(mtd, buf, &ecc_calc[0]); omap_calculate_ecc_bch_multi(mtd, buf, &ecc_calc[0]);
ret = mtd_ooblayout_set_eccbytes(mtd, ecc_calc, chip->oob_poi, 0, ret = mtd_ooblayout_set_eccbytes(mtd, ecc_calc, chip->oob_poi, 0,
chip->ecc.total); chip->ecc.total);
@@ -1508,6 +1551,72 @@ static int omap_write_page_bch(struct mtd_info *mtd, struct nand_chip *chip,
return 0; return 0;
} }
/**
* omap_write_subpage_bch - BCH hardware ECC based subpage write
* @mtd: mtd info structure
* @chip: nand chip info structure
* @offset: column address of subpage within the page
* @data_len: data length
* @buf: data buffer
* @oob_required: must write chip->oob_poi to OOB
* @page: page number to write
*
* OMAP optimized subpage write method.
*/
static int omap_write_subpage_bch(struct mtd_info *mtd,
struct nand_chip *chip, u32 offset,
u32 data_len, const u8 *buf,
int oob_required, int page)
{
u8 *ecc_calc = chip->buffers->ecccalc;
int ecc_size = chip->ecc.size;
int ecc_bytes = chip->ecc.bytes;
int ecc_steps = chip->ecc.steps;
u32 start_step = offset / ecc_size;
u32 end_step = (offset + data_len - 1) / ecc_size;
int step, ret = 0;
/*
* Write entire page at one go as it would be optimal
* as ECC is calculated by hardware.
* ECC is calculated for all subpages but we choose
* only what we want.
*/
/* Enable GPMC ECC engine */
chip->ecc.hwctl(mtd, NAND_ECC_WRITE);
/* Write data */
chip->write_buf(mtd, buf, mtd->writesize);
for (step = 0; step < ecc_steps; step++) {
/* mask ECC of un-touched subpages by padding 0xFF */
if (step < start_step || step > end_step)
memset(ecc_calc, 0xff, ecc_bytes);
else
ret = _omap_calculate_ecc_bch(mtd, buf, ecc_calc, step);
if (ret)
return ret;
buf += ecc_size;
ecc_calc += ecc_bytes;
}
/* copy calculated ECC for whole page to chip->buffer->oob */
/* this include masked-value(0xFF) for unwritten subpages */
ecc_calc = chip->buffers->ecccalc;
ret = mtd_ooblayout_set_eccbytes(mtd, ecc_calc, chip->oob_poi, 0,
chip->ecc.total);
if (ret)
return ret;
/* write OOB buffer to NAND device */
chip->write_buf(mtd, chip->oob_poi, mtd->oobsize);
return 0;
}
/** /**
* omap_read_page_bch - BCH ecc based page read function for entire page * omap_read_page_bch - BCH ecc based page read function for entire page
* @mtd: mtd info structure * @mtd: mtd info structure
@@ -1544,7 +1653,7 @@ static int omap_read_page_bch(struct mtd_info *mtd, struct nand_chip *chip,
chip->ecc.total); chip->ecc.total);
/* Calculate ecc bytes */ /* Calculate ecc bytes */
chip->ecc.calculate(mtd, buf, ecc_calc); omap_calculate_ecc_bch_multi(mtd, buf, ecc_calc);
ret = mtd_ooblayout_get_eccbytes(mtd, ecc_code, chip->oob_poi, 0, ret = mtd_ooblayout_get_eccbytes(mtd, ecc_code, chip->oob_poi, 0,
chip->ecc.total); chip->ecc.total);
@@ -2044,7 +2153,7 @@ static int omap_nand_probe(struct platform_device *pdev)
nand_chip->ecc.strength = 4; nand_chip->ecc.strength = 4;
nand_chip->ecc.hwctl = omap_enable_hwecc_bch; nand_chip->ecc.hwctl = omap_enable_hwecc_bch;
nand_chip->ecc.correct = nand_bch_correct_data; nand_chip->ecc.correct = nand_bch_correct_data;
nand_chip->ecc.calculate = omap_calculate_ecc_bch; nand_chip->ecc.calculate = omap_calculate_ecc_bch_sw;
mtd_set_ooblayout(mtd, &omap_sw_ooblayout_ops); mtd_set_ooblayout(mtd, &omap_sw_ooblayout_ops);
/* Reserve one byte for the OMAP marker */ /* Reserve one byte for the OMAP marker */
oobbytes_per_step = nand_chip->ecc.bytes + 1; oobbytes_per_step = nand_chip->ecc.bytes + 1;
@@ -2066,9 +2175,9 @@ static int omap_nand_probe(struct platform_device *pdev)
nand_chip->ecc.strength = 4; nand_chip->ecc.strength = 4;
nand_chip->ecc.hwctl = omap_enable_hwecc_bch; nand_chip->ecc.hwctl = omap_enable_hwecc_bch;
nand_chip->ecc.correct = omap_elm_correct_data; nand_chip->ecc.correct = omap_elm_correct_data;
nand_chip->ecc.calculate = omap_calculate_ecc_bch;
nand_chip->ecc.read_page = omap_read_page_bch; nand_chip->ecc.read_page = omap_read_page_bch;
nand_chip->ecc.write_page = omap_write_page_bch; nand_chip->ecc.write_page = omap_write_page_bch;
nand_chip->ecc.write_subpage = omap_write_subpage_bch;
mtd_set_ooblayout(mtd, &omap_ooblayout_ops); mtd_set_ooblayout(mtd, &omap_ooblayout_ops);
oobbytes_per_step = nand_chip->ecc.bytes; oobbytes_per_step = nand_chip->ecc.bytes;
@@ -2087,7 +2196,7 @@ static int omap_nand_probe(struct platform_device *pdev)
nand_chip->ecc.strength = 8; nand_chip->ecc.strength = 8;
nand_chip->ecc.hwctl = omap_enable_hwecc_bch; nand_chip->ecc.hwctl = omap_enable_hwecc_bch;
nand_chip->ecc.correct = nand_bch_correct_data; nand_chip->ecc.correct = nand_bch_correct_data;
nand_chip->ecc.calculate = omap_calculate_ecc_bch; nand_chip->ecc.calculate = omap_calculate_ecc_bch_sw;
mtd_set_ooblayout(mtd, &omap_sw_ooblayout_ops); mtd_set_ooblayout(mtd, &omap_sw_ooblayout_ops);
/* Reserve one byte for the OMAP marker */ /* Reserve one byte for the OMAP marker */
oobbytes_per_step = nand_chip->ecc.bytes + 1; oobbytes_per_step = nand_chip->ecc.bytes + 1;
@@ -2109,9 +2218,9 @@ static int omap_nand_probe(struct platform_device *pdev)
nand_chip->ecc.strength = 8; nand_chip->ecc.strength = 8;
nand_chip->ecc.hwctl = omap_enable_hwecc_bch; nand_chip->ecc.hwctl = omap_enable_hwecc_bch;
nand_chip->ecc.correct = omap_elm_correct_data; nand_chip->ecc.correct = omap_elm_correct_data;
nand_chip->ecc.calculate = omap_calculate_ecc_bch;
nand_chip->ecc.read_page = omap_read_page_bch; nand_chip->ecc.read_page = omap_read_page_bch;
nand_chip->ecc.write_page = omap_write_page_bch; nand_chip->ecc.write_page = omap_write_page_bch;
nand_chip->ecc.write_subpage = omap_write_subpage_bch;
mtd_set_ooblayout(mtd, &omap_ooblayout_ops); mtd_set_ooblayout(mtd, &omap_ooblayout_ops);
oobbytes_per_step = nand_chip->ecc.bytes; oobbytes_per_step = nand_chip->ecc.bytes;
@@ -2131,9 +2240,9 @@ static int omap_nand_probe(struct platform_device *pdev)
nand_chip->ecc.strength = 16; nand_chip->ecc.strength = 16;
nand_chip->ecc.hwctl = omap_enable_hwecc_bch; nand_chip->ecc.hwctl = omap_enable_hwecc_bch;
nand_chip->ecc.correct = omap_elm_correct_data; nand_chip->ecc.correct = omap_elm_correct_data;
nand_chip->ecc.calculate = omap_calculate_ecc_bch;
nand_chip->ecc.read_page = omap_read_page_bch; nand_chip->ecc.read_page = omap_read_page_bch;
nand_chip->ecc.write_page = omap_write_page_bch; nand_chip->ecc.write_page = omap_write_page_bch;
nand_chip->ecc.write_subpage = omap_write_subpage_bch;
mtd_set_ooblayout(mtd, &omap_ooblayout_ops); mtd_set_ooblayout(mtd, &omap_ooblayout_ops);
oobbytes_per_step = nand_chip->ecc.bytes; oobbytes_per_step = nand_chip->ecc.bytes;
+14 -11
View File
@@ -2366,9 +2366,9 @@ typhoon_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
* 4) Get the hardware address. * 4) Get the hardware address.
* 5) Put the card to sleep. * 5) Put the card to sleep.
*/ */
if (typhoon_reset(ioaddr, WaitSleep) < 0) { err = typhoon_reset(ioaddr, WaitSleep);
if (err < 0) {
err_msg = "could not reset 3XP"; err_msg = "could not reset 3XP";
err = -EIO;
goto error_out_dma; goto error_out_dma;
} }
@@ -2382,24 +2382,25 @@ typhoon_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
typhoon_init_interface(tp); typhoon_init_interface(tp);
typhoon_init_rings(tp); typhoon_init_rings(tp);
if(typhoon_boot_3XP(tp, TYPHOON_STATUS_WAITING_FOR_HOST) < 0) { err = typhoon_boot_3XP(tp, TYPHOON_STATUS_WAITING_FOR_HOST);
if (err < 0) {
err_msg = "cannot boot 3XP sleep image"; err_msg = "cannot boot 3XP sleep image";
err = -EIO;
goto error_out_reset; goto error_out_reset;
} }
INIT_COMMAND_WITH_RESPONSE(&xp_cmd, TYPHOON_CMD_READ_MAC_ADDRESS); INIT_COMMAND_WITH_RESPONSE(&xp_cmd, TYPHOON_CMD_READ_MAC_ADDRESS);
if(typhoon_issue_command(tp, 1, &xp_cmd, 1, xp_resp) < 0) { err = typhoon_issue_command(tp, 1, &xp_cmd, 1, xp_resp);
if (err < 0) {
err_msg = "cannot read MAC address"; err_msg = "cannot read MAC address";
err = -EIO;
goto error_out_reset; goto error_out_reset;
} }
*(__be16 *)&dev->dev_addr[0] = htons(le16_to_cpu(xp_resp[0].parm1)); *(__be16 *)&dev->dev_addr[0] = htons(le16_to_cpu(xp_resp[0].parm1));
*(__be32 *)&dev->dev_addr[2] = htonl(le32_to_cpu(xp_resp[0].parm2)); *(__be32 *)&dev->dev_addr[2] = htonl(le32_to_cpu(xp_resp[0].parm2));
if(!is_valid_ether_addr(dev->dev_addr)) { if (!is_valid_ether_addr(dev->dev_addr)) {
err_msg = "Could not obtain valid ethernet address, aborting"; err_msg = "Could not obtain valid ethernet address, aborting";
err = -EIO;
goto error_out_reset; goto error_out_reset;
} }
@@ -2407,7 +2408,8 @@ typhoon_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
* later when we print out the version reported. * later when we print out the version reported.
*/ */
INIT_COMMAND_WITH_RESPONSE(&xp_cmd, TYPHOON_CMD_READ_VERSIONS); INIT_COMMAND_WITH_RESPONSE(&xp_cmd, TYPHOON_CMD_READ_VERSIONS);
if(typhoon_issue_command(tp, 1, &xp_cmd, 3, xp_resp) < 0) { err = typhoon_issue_command(tp, 1, &xp_cmd, 3, xp_resp);
if (err < 0) {
err_msg = "Could not get Sleep Image version"; err_msg = "Could not get Sleep Image version";
goto error_out_reset; goto error_out_reset;
} }
@@ -2424,9 +2426,9 @@ typhoon_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
if(xp_resp[0].numDesc != 0) if(xp_resp[0].numDesc != 0)
tp->capabilities |= TYPHOON_WAKEUP_NEEDS_RESET; tp->capabilities |= TYPHOON_WAKEUP_NEEDS_RESET;
if(typhoon_sleep(tp, PCI_D3hot, 0) < 0) { err = typhoon_sleep(tp, PCI_D3hot, 0);
if (err < 0) {
err_msg = "cannot put adapter to sleep"; err_msg = "cannot put adapter to sleep";
err = -EIO;
goto error_out_reset; goto error_out_reset;
} }
@@ -2449,7 +2451,8 @@ typhoon_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
dev->features = dev->hw_features | dev->features = dev->hw_features |
NETIF_F_HW_VLAN_CTAG_RX | NETIF_F_RXCSUM; NETIF_F_HW_VLAN_CTAG_RX | NETIF_F_RXCSUM;
if(register_netdev(dev) < 0) { err = register_netdev(dev);
if (err < 0) {
err_msg = "unable to register netdev"; err_msg = "unable to register netdev";
goto error_out_reset; goto error_out_reset;
} }
+30
View File
@@ -3800,6 +3800,30 @@ static int hwrm_ring_alloc_send_msg(struct bnxt *bp,
return rc; return rc;
} }
static int bnxt_hwrm_set_async_event_cr(struct bnxt *bp, int idx)
{
int rc;
if (BNXT_PF(bp)) {
struct hwrm_func_cfg_input req = {0};
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_FUNC_CFG, -1, -1);
req.fid = cpu_to_le16(0xffff);
req.enables = cpu_to_le32(FUNC_CFG_REQ_ENABLES_ASYNC_EVENT_CR);
req.async_event_cr = cpu_to_le16(idx);
rc = hwrm_send_message(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
} else {
struct hwrm_func_vf_cfg_input req = {0};
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_FUNC_VF_CFG, -1, -1);
req.enables =
cpu_to_le32(FUNC_VF_CFG_REQ_ENABLES_ASYNC_EVENT_CR);
req.async_event_cr = cpu_to_le16(idx);
rc = hwrm_send_message(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
}
return rc;
}
static int bnxt_hwrm_ring_alloc(struct bnxt *bp) static int bnxt_hwrm_ring_alloc(struct bnxt *bp)
{ {
int i, rc = 0; int i, rc = 0;
@@ -3816,6 +3840,12 @@ static int bnxt_hwrm_ring_alloc(struct bnxt *bp)
goto err_out; goto err_out;
BNXT_CP_DB(cpr->cp_doorbell, cpr->cp_raw_cons); BNXT_CP_DB(cpr->cp_doorbell, cpr->cp_raw_cons);
bp->grp_info[i].cp_fw_ring_id = ring->fw_ring_id; bp->grp_info[i].cp_fw_ring_id = ring->fw_ring_id;
if (!i) {
rc = bnxt_hwrm_set_async_event_cr(bp, ring->fw_ring_id);
if (rc)
netdev_warn(bp->dev, "Failed to set async event completion ring.\n");
}
} }
for (i = 0; i < bp->tx_nr_rings; i++) { for (i = 0; i < bp->tx_nr_rings; i++) {
@@ -398,6 +398,7 @@
#define E1000_ICR_LSC 0x00000004 /* Link Status Change */ #define E1000_ICR_LSC 0x00000004 /* Link Status Change */
#define E1000_ICR_RXSEQ 0x00000008 /* Rx sequence error */ #define E1000_ICR_RXSEQ 0x00000008 /* Rx sequence error */
#define E1000_ICR_RXDMT0 0x00000010 /* Rx desc min. threshold (0) */ #define E1000_ICR_RXDMT0 0x00000010 /* Rx desc min. threshold (0) */
#define E1000_ICR_RXO 0x00000040 /* Receiver Overrun */
#define E1000_ICR_RXT0 0x00000080 /* Rx timer intr (ring 0) */ #define E1000_ICR_RXT0 0x00000080 /* Rx timer intr (ring 0) */
#define E1000_ICR_ECCER 0x00400000 /* Uncorrectable ECC Error */ #define E1000_ICR_ECCER 0x00400000 /* Uncorrectable ECC Error */
/* If this bit asserted, the driver should claim the interrupt */ /* If this bit asserted, the driver should claim the interrupt */
+8 -3
View File
@@ -410,6 +410,9 @@ void e1000e_clear_hw_cntrs_base(struct e1000_hw *hw)
* Checks to see of the link status of the hardware has changed. If a * Checks to see of the link status of the hardware has changed. If a
* change in link status has been detected, then we read the PHY registers * change in link status has been detected, then we read the PHY registers
* to get the current speed/duplex if link exists. * to get the current speed/duplex if link exists.
*
* Returns a negative error code (-E1000_ERR_*) or 0 (link down) or 1 (link
* up).
**/ **/
s32 e1000e_check_for_copper_link(struct e1000_hw *hw) s32 e1000e_check_for_copper_link(struct e1000_hw *hw)
{ {
@@ -423,7 +426,7 @@ s32 e1000e_check_for_copper_link(struct e1000_hw *hw)
* Change or Rx Sequence Error interrupt. * Change or Rx Sequence Error interrupt.
*/ */
if (!mac->get_link_status) if (!mac->get_link_status)
return 0; return 1;
/* First we want to see if the MII Status Register reports /* First we want to see if the MII Status Register reports
* link. If so, then we want to get the current speed/duplex * link. If so, then we want to get the current speed/duplex
@@ -461,10 +464,12 @@ s32 e1000e_check_for_copper_link(struct e1000_hw *hw)
* different link partner. * different link partner.
*/ */
ret_val = e1000e_config_fc_after_link_up(hw); ret_val = e1000e_config_fc_after_link_up(hw);
if (ret_val) if (ret_val) {
e_dbg("Error configuring flow control\n"); e_dbg("Error configuring flow control\n");
return ret_val;
}
return ret_val; return 1;
} }
/** /**
+27 -10
View File
@@ -1905,14 +1905,30 @@ static irqreturn_t e1000_msix_other(int __always_unused irq, void *data)
struct net_device *netdev = data; struct net_device *netdev = data;
struct e1000_adapter *adapter = netdev_priv(netdev); struct e1000_adapter *adapter = netdev_priv(netdev);
struct e1000_hw *hw = &adapter->hw; struct e1000_hw *hw = &adapter->hw;
u32 icr;
bool enable = true;
hw->mac.get_link_status = true; icr = er32(ICR);
if (icr & E1000_ICR_RXO) {
/* guard against interrupt when we're going down */ ew32(ICR, E1000_ICR_RXO);
if (!test_bit(__E1000_DOWN, &adapter->state)) { enable = false;
mod_timer(&adapter->watchdog_timer, jiffies + 1); /* napi poll will re-enable Other, make sure it runs */
ew32(IMS, E1000_IMS_OTHER); if (napi_schedule_prep(&adapter->napi)) {
adapter->total_rx_bytes = 0;
adapter->total_rx_packets = 0;
__napi_schedule(&adapter->napi);
}
} }
if (icr & E1000_ICR_LSC) {
ew32(ICR, E1000_ICR_LSC);
hw->mac.get_link_status = true;
/* guard against interrupt when we're going down */
if (!test_bit(__E1000_DOWN, &adapter->state))
mod_timer(&adapter->watchdog_timer, jiffies + 1);
}
if (enable && !test_bit(__E1000_DOWN, &adapter->state))
ew32(IMS, E1000_IMS_OTHER);
return IRQ_HANDLED; return IRQ_HANDLED;
} }
@@ -2683,7 +2699,8 @@ static int e1000e_poll(struct napi_struct *napi, int weight)
napi_complete_done(napi, work_done); napi_complete_done(napi, work_done);
if (!test_bit(__E1000_DOWN, &adapter->state)) { if (!test_bit(__E1000_DOWN, &adapter->state)) {
if (adapter->msix_entries) if (adapter->msix_entries)
ew32(IMS, adapter->rx_ring->ims_val); ew32(IMS, adapter->rx_ring->ims_val |
E1000_IMS_OTHER);
else else
e1000_irq_enable(adapter); e1000_irq_enable(adapter);
} }
@@ -4178,7 +4195,7 @@ static void e1000e_trigger_lsc(struct e1000_adapter *adapter)
struct e1000_hw *hw = &adapter->hw; struct e1000_hw *hw = &adapter->hw;
if (adapter->msix_entries) if (adapter->msix_entries)
ew32(ICS, E1000_ICS_OTHER); ew32(ICS, E1000_ICS_LSC | E1000_ICS_OTHER);
else else
ew32(ICS, E1000_ICS_LSC); ew32(ICS, E1000_ICS_LSC);
} }
@@ -5056,7 +5073,7 @@ static bool e1000e_has_link(struct e1000_adapter *adapter)
case e1000_media_type_copper: case e1000_media_type_copper:
if (hw->mac.get_link_status) { if (hw->mac.get_link_status) {
ret_val = hw->mac.ops.check_for_link(hw); ret_val = hw->mac.ops.check_for_link(hw);
link_active = !hw->mac.get_link_status; link_active = ret_val > 0;
} else { } else {
link_active = true; link_active = true;
} }
@@ -5074,7 +5091,7 @@ static bool e1000e_has_link(struct e1000_adapter *adapter)
break; break;
} }
if ((ret_val == E1000_ERR_PHY) && (hw->phy.type == e1000_phy_igp_3) && if ((ret_val == -E1000_ERR_PHY) && (hw->phy.type == e1000_phy_igp_3) &&
(er32(CTRL) & E1000_PHY_CTRL_GBE_DISABLE)) { (er32(CTRL) & E1000_PHY_CTRL_GBE_DISABLE)) {
/* See e1000_kmrn_lock_loss_workaround_ich8lan() */ /* See e1000_kmrn_lock_loss_workaround_ich8lan() */
e_info("Gigabit has been disabled, downgrading speed\n"); e_info("Gigabit has been disabled, downgrading speed\n");
+4 -3
View File
@@ -1744,6 +1744,7 @@ s32 e1000e_phy_has_link_generic(struct e1000_hw *hw, u32 iterations,
s32 ret_val = 0; s32 ret_val = 0;
u16 i, phy_status; u16 i, phy_status;
*success = false;
for (i = 0; i < iterations; i++) { for (i = 0; i < iterations; i++) {
/* Some PHYs require the MII_BMSR register to be read /* Some PHYs require the MII_BMSR register to be read
* twice due to the link bit being sticky. No harm doing * twice due to the link bit being sticky. No harm doing
@@ -1763,16 +1764,16 @@ s32 e1000e_phy_has_link_generic(struct e1000_hw *hw, u32 iterations,
ret_val = e1e_rphy(hw, MII_BMSR, &phy_status); ret_val = e1e_rphy(hw, MII_BMSR, &phy_status);
if (ret_val) if (ret_val)
break; break;
if (phy_status & BMSR_LSTATUS) if (phy_status & BMSR_LSTATUS) {
*success = true;
break; break;
}
if (usec_interval >= 1000) if (usec_interval >= 1000)
msleep(usec_interval / 1000); msleep(usec_interval / 1000);
else else
udelay(usec_interval); udelay(usec_interval);
} }
*success = (i < iterations);
return ret_val; return ret_val;
} }
@@ -1225,7 +1225,7 @@ static bool fm10k_clean_tx_irq(struct fm10k_q_vector *q_vector,
break; break;
/* prevent any other reads prior to eop_desc */ /* prevent any other reads prior to eop_desc */
read_barrier_depends(); smp_rmb();
/* if DD is not set pending work has not been completed */ /* if DD is not set pending work has not been completed */
if (!(eop_desc->flags & FM10K_TXD_FLAG_DONE)) if (!(eop_desc->flags & FM10K_TXD_FLAG_DONE))
+1 -1
View File
@@ -3604,7 +3604,7 @@ static bool i40e_clean_fdir_tx_irq(struct i40e_ring *tx_ring, int budget)
break; break;
/* prevent any other reads prior to eop_desc */ /* prevent any other reads prior to eop_desc */
read_barrier_depends(); smp_rmb();
/* if the descriptor isn't done, no work yet to do */ /* if the descriptor isn't done, no work yet to do */
if (!(eop_desc->cmd_type_offset_bsz & if (!(eop_desc->cmd_type_offset_bsz &

Some files were not shown because too many files have changed in this diff Show More