Linux 6.1
-----BEGIN PGP SIGNATURE----- iQFSBAABCAA8FiEEq68RxlopcLEwq+PEeb4+QwBBGIYFAmOWVnYeHHRvcnZhbGRz QGxpbnV4LWZvdW5kYXRpb24ub3JnAAoJEHm+PkMAQRiGyoMIAIanupJbCZV9/ogv WeYmjNwng0AjTTnh6Lo+arXrQQd2GAa/TnAF0h+vYlQ6BEPo/Da0GZwqdoMBr9/K gMpHqGgv9y2nr9c8/0uKLNdqPXPNN79kF1FMOKW9DidGlsjtobgxNzJ3V0rD5G8p yXP3rKO1J5CA6FSP2CDtacuE0rZUCqCgafI7lQ0e9nRaCL5tUvkjWn1I8GZOr+CF FI0k1/5KYy4pCfNUDi2CwWWbOkZwOiEAdUD+7AfdHasHLxUOc2c6GJlnnIJSTT6C Qg8QsDRX37yslMz3UBIlkcDxHPhSNGb4QuhXVppPdLIUpNAEM1hSfJBlOrR7rQjZ /dV4OhA= =QmNi -----END PGP SIGNATURE----- Merge tag 'v6.1' into android-mainline Linux 6.1 Signed-off-by: Greg Kroah-Hartman <gregkh@google.com> Change-Id: Ia7a26a07d400b1d19940feccd8950e28b13552ef
This commit is contained in:
commit
5a26ea7c4a
@ -535,6 +535,7 @@ ForEachMacros:
|
||||
- 'perf_hpp_list__for_each_sort_list_safe'
|
||||
- 'perf_pmu__for_each_hybrid_pmu'
|
||||
- 'ping_portaddr_for_each_entry'
|
||||
- 'ping_portaddr_for_each_entry_rcu'
|
||||
- 'plist_for_each'
|
||||
- 'plist_for_each_continue'
|
||||
- 'plist_for_each_entry'
|
||||
|
3
.mailmap
3
.mailmap
@ -287,6 +287,7 @@ Matthew Wilcox <willy@infradead.org> <willy@linux.intel.com>
|
||||
Matthew Wilcox <willy@infradead.org> <willy@parisc-linux.org>
|
||||
Matthias Fuchs <socketcan@esd.eu> <matthias.fuchs@esd.eu>
|
||||
Matthieu CASTET <castet.matthieu@free.fr>
|
||||
Matti Vaittinen <mazziesaccount@gmail.com> <matti.vaittinen@fi.rohmeurope.com>
|
||||
Matt Ranostay <matt.ranostay@konsulko.com> <matt@ranostay.consulting>
|
||||
Matt Ranostay <mranostay@gmail.com> Matthew Ranostay <mranostay@embeddedalley.com>
|
||||
Matt Ranostay <mranostay@gmail.com> <matt.ranostay@intel.com>
|
||||
@ -372,6 +373,8 @@ Ricardo Ribalda <ribalda@kernel.org> <ricardo.ribalda@gmail.com>
|
||||
Roman Gushchin <roman.gushchin@linux.dev> <guro@fb.com>
|
||||
Roman Gushchin <roman.gushchin@linux.dev> <guroan@gmail.com>
|
||||
Roman Gushchin <roman.gushchin@linux.dev> <klamm@yandex-team.ru>
|
||||
Muchun Song <muchun.song@linux.dev> <songmuchun@bytedance.com>
|
||||
Muchun Song <muchun.song@linux.dev> <smuchun@gmail.com>
|
||||
Ross Zwisler <zwisler@kernel.org> <ross.zwisler@linux.intel.com>
|
||||
Rudolf Marek <R.Marek@sh.cvut.cz>
|
||||
Rui Saraiva <rmps@joel.ist.utl.pt>
|
||||
|
42
Documentation/loongarch/booting.rst
Normal file
42
Documentation/loongarch/booting.rst
Normal file
@ -0,0 +1,42 @@
|
||||
.. SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
=======================
|
||||
Booting Linux/LoongArch
|
||||
=======================
|
||||
|
||||
:Author: Yanteng Si <siyanteng@loongson.cn>
|
||||
:Date: 18 Nov 2022
|
||||
|
||||
Information passed from BootLoader to kernel
|
||||
============================================
|
||||
|
||||
LoongArch supports ACPI and FDT. The information that needs to be passed
|
||||
to the kernel includes the memmap, the initrd, the command line, optionally
|
||||
the ACPI/FDT tables, and so on.
|
||||
|
||||
The kernel is passed the following arguments on `kernel_entry` :
|
||||
|
||||
- a0 = efi_boot: `efi_boot` is a flag indicating whether
|
||||
this boot environment is fully UEFI-compliant.
|
||||
|
||||
- a1 = cmdline: `cmdline` is a pointer to the kernel command line.
|
||||
|
||||
- a2 = systemtable: `systemtable` points to the EFI system table.
|
||||
All pointers involved at this stage are in physical addresses.
|
||||
|
||||
Header of Linux/LoongArch kernel images
|
||||
=======================================
|
||||
|
||||
Linux/LoongArch kernel images are EFI images. Being PE files, they have
|
||||
a 64-byte header structured like::
|
||||
|
||||
u32 MZ_MAGIC /* "MZ", MS-DOS header */
|
||||
u32 res0 = 0 /* Reserved */
|
||||
u64 kernel_entry /* Kernel entry point */
|
||||
u64 _end - _text /* Kernel image effective size */
|
||||
u64 load_offset /* Kernel image load offset from start of RAM */
|
||||
u64 res1 = 0 /* Reserved */
|
||||
u64 res2 = 0 /* Reserved */
|
||||
u64 res3 = 0 /* Reserved */
|
||||
u32 LINUX_PE_MAGIC /* Magic number */
|
||||
u32 pe_header - _head /* Offset to the PE header */
|
@ -9,6 +9,7 @@ LoongArch Architecture
|
||||
:numbered:
|
||||
|
||||
introduction
|
||||
booting
|
||||
irq-chip-model
|
||||
|
||||
features
|
||||
|
48
Documentation/translations/zh_CN/loongarch/booting.rst
Normal file
48
Documentation/translations/zh_CN/loongarch/booting.rst
Normal file
@ -0,0 +1,48 @@
|
||||
.. SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
.. include:: ../disclaimer-zh_CN.rst
|
||||
|
||||
:Original: Documentation/loongarch/booting.rst
|
||||
|
||||
:翻译:
|
||||
|
||||
司延腾 Yanteng Si <siyanteng@loongson.cn>
|
||||
|
||||
====================
|
||||
启动 Linux/LoongArch
|
||||
====================
|
||||
|
||||
:作者: 司延腾 <siyanteng@loongson.cn>
|
||||
:日期: 2022年11月18日
|
||||
|
||||
BootLoader传递给内核的信息
|
||||
==========================
|
||||
|
||||
LoongArch支持ACPI和FDT启动,需要传递给内核的信息包括memmap、initrd、cmdline、可
|
||||
选的ACPI/FDT表等。
|
||||
|
||||
内核在 `kernel_entry` 入口处被传递以下参数:
|
||||
|
||||
- a0 = efi_boot: `efi_boot` 是一个标志,表示这个启动环境是否完全符合UEFI
|
||||
的要求。
|
||||
|
||||
- a1 = cmdline: `cmdline` 是一个指向内核命令行的指针。
|
||||
|
||||
- a2 = systemtable: `systemtable` 指向EFI的系统表,在这个阶段涉及的所有
|
||||
指针都是物理地址。
|
||||
|
||||
Linux/LoongArch内核镜像文件头
|
||||
=============================
|
||||
|
||||
内核镜像是EFI镜像。作为PE文件,它们有一个64字节的头部结构体,如下所示::
|
||||
|
||||
u32 MZ_MAGIC /* "MZ", MS-DOS 头 */
|
||||
u32 res0 = 0 /* 保留 */
|
||||
u64 kernel_entry /* 内核入口点 */
|
||||
u64 _end - _text /* 内核镜像有效大小 */
|
||||
u64 load_offset /* 加载内核镜像相对内存起始地址的偏移量 */
|
||||
u64 res1 = 0 /* 保留 */
|
||||
u64 res2 = 0 /* 保留 */
|
||||
u64 res3 = 0 /* 保留 */
|
||||
u32 LINUX_PE_MAGIC /* 魔术数 */
|
||||
u32 pe_header - _head /* 到PE头的偏移量 */
|
@ -14,6 +14,7 @@ LoongArch体系结构
|
||||
:numbered:
|
||||
|
||||
introduction
|
||||
booting
|
||||
irq-chip-model
|
||||
|
||||
features
|
||||
|
@ -5299,7 +5299,7 @@ M: Johannes Weiner <hannes@cmpxchg.org>
|
||||
M: Michal Hocko <mhocko@kernel.org>
|
||||
M: Roman Gushchin <roman.gushchin@linux.dev>
|
||||
M: Shakeel Butt <shakeelb@google.com>
|
||||
R: Muchun Song <songmuchun@bytedance.com>
|
||||
R: Muchun Song <muchun.song@linux.dev>
|
||||
L: cgroups@vger.kernel.org
|
||||
L: linux-mm@kvack.org
|
||||
S: Maintained
|
||||
@ -9439,7 +9439,7 @@ F: drivers/net/ethernet/huawei/hinic/
|
||||
|
||||
HUGETLB SUBSYSTEM
|
||||
M: Mike Kravetz <mike.kravetz@oracle.com>
|
||||
M: Muchun Song <songmuchun@bytedance.com>
|
||||
M: Muchun Song <muchun.song@linux.dev>
|
||||
L: linux-mm@kvack.org
|
||||
S: Maintained
|
||||
F: Documentation/ABI/testing/sysfs-kernel-mm-hugepages
|
||||
|
2
Makefile
2
Makefile
@ -2,7 +2,7 @@
|
||||
VERSION = 6
|
||||
PATCHLEVEL = 1
|
||||
SUBLEVEL = 0
|
||||
EXTRAVERSION = -rc8
|
||||
EXTRAVERSION =
|
||||
NAME = Hurr durr I'ma ninja sloth
|
||||
|
||||
# *DOCUMENTATION*
|
||||
|
@ -1270,10 +1270,10 @@ dma_apbh: dma-apbh@33000000 {
|
||||
clocks = <&clks IMX7D_NAND_USDHC_BUS_RAWNAND_CLK>;
|
||||
};
|
||||
|
||||
gpmi: nand-controller@33002000 {
|
||||
gpmi: nand-controller@33002000{
|
||||
compatible = "fsl,imx7d-gpmi-nand";
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
#size-cells = <1>;
|
||||
reg = <0x33002000 0x2000>, <0x33004000 0x4000>;
|
||||
reg-names = "gpmi-nand", "bch";
|
||||
interrupts = <GIC_SPI 14 IRQ_TYPE_LEVEL_HIGH>;
|
||||
|
@ -26,7 +26,7 @@ static void sama5_l2c310_write_sec(unsigned long val, unsigned reg)
|
||||
static void __init sama5_secure_cache_init(void)
|
||||
{
|
||||
sam_secure_init();
|
||||
if (sam_linux_is_optee_available())
|
||||
if (IS_ENABLED(CONFIG_OUTER_CACHE) && sam_linux_is_optee_available())
|
||||
outer_cache.write_sec = sama5_l2c310_write_sec;
|
||||
}
|
||||
|
||||
|
@ -105,6 +105,19 @@ static inline bool is_write_fault(unsigned int fsr)
|
||||
return (fsr & FSR_WRITE) && !(fsr & FSR_CM);
|
||||
}
|
||||
|
||||
static inline bool is_translation_fault(unsigned int fsr)
|
||||
{
|
||||
int fs = fsr_fs(fsr);
|
||||
#ifdef CONFIG_ARM_LPAE
|
||||
if ((fs & FS_MMU_NOLL_MASK) == FS_TRANS_NOLL)
|
||||
return true;
|
||||
#else
|
||||
if (fs == FS_L1_TRANS || fs == FS_L2_TRANS)
|
||||
return true;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
static void die_kernel_fault(const char *msg, struct mm_struct *mm,
|
||||
unsigned long addr, unsigned int fsr,
|
||||
struct pt_regs *regs)
|
||||
@ -140,7 +153,8 @@ __do_kernel_fault(struct mm_struct *mm, unsigned long addr, unsigned int fsr,
|
||||
if (addr < PAGE_SIZE) {
|
||||
msg = "NULL pointer dereference";
|
||||
} else {
|
||||
if (kfence_handle_page_fault(addr, is_write_fault(fsr), regs))
|
||||
if (is_translation_fault(fsr) &&
|
||||
kfence_handle_page_fault(addr, is_write_fault(fsr), regs))
|
||||
return;
|
||||
|
||||
msg = "paging request";
|
||||
@ -208,7 +222,7 @@ static inline bool is_permission_fault(unsigned int fsr)
|
||||
{
|
||||
int fs = fsr_fs(fsr);
|
||||
#ifdef CONFIG_ARM_LPAE
|
||||
if ((fs & FS_PERM_NOLL_MASK) == FS_PERM_NOLL)
|
||||
if ((fs & FS_MMU_NOLL_MASK) == FS_PERM_NOLL)
|
||||
return true;
|
||||
#else
|
||||
if (fs == FS_L1_PERM || fs == FS_L2_PERM)
|
||||
|
@ -14,8 +14,9 @@
|
||||
|
||||
#ifdef CONFIG_ARM_LPAE
|
||||
#define FSR_FS_AEA 17
|
||||
#define FS_TRANS_NOLL 0x4
|
||||
#define FS_PERM_NOLL 0xC
|
||||
#define FS_PERM_NOLL_MASK 0x3C
|
||||
#define FS_MMU_NOLL_MASK 0x3C
|
||||
|
||||
static inline int fsr_fs(unsigned int fsr)
|
||||
{
|
||||
@ -23,8 +24,10 @@ static inline int fsr_fs(unsigned int fsr)
|
||||
}
|
||||
#else
|
||||
#define FSR_FS_AEA 22
|
||||
#define FS_L1_PERM 0xD
|
||||
#define FS_L2_PERM 0xF
|
||||
#define FS_L1_TRANS 0x5
|
||||
#define FS_L2_TRANS 0x7
|
||||
#define FS_L1_PERM 0xD
|
||||
#define FS_L2_PERM 0xF
|
||||
|
||||
static inline int fsr_fs(unsigned int fsr)
|
||||
{
|
||||
|
@ -78,16 +78,6 @@ extern void calculate_cpu_foreign_map(void);
|
||||
*/
|
||||
extern void show_ipi_list(struct seq_file *p, int prec);
|
||||
|
||||
/*
|
||||
* This function sends a 'reschedule' IPI to another CPU.
|
||||
* it goes straight through and wastes no time serializing
|
||||
* anything. Worst case is that we lose a reschedule ...
|
||||
*/
|
||||
static inline void smp_send_reschedule(int cpu)
|
||||
{
|
||||
loongson_send_ipi_single(cpu, SMP_RESCHEDULE);
|
||||
}
|
||||
|
||||
static inline void arch_send_call_function_single_ipi(int cpu)
|
||||
{
|
||||
loongson_send_ipi_single(cpu, SMP_CALL_FUNCTION);
|
||||
|
@ -149,6 +149,17 @@ void loongson_send_ipi_mask(const struct cpumask *mask, unsigned int action)
|
||||
ipi_write_action(cpu_logical_map(i), (u32)action);
|
||||
}
|
||||
|
||||
/*
|
||||
* This function sends a 'reschedule' IPI to another CPU.
|
||||
* it goes straight through and wastes no time serializing
|
||||
* anything. Worst case is that we lose a reschedule ...
|
||||
*/
|
||||
void smp_send_reschedule(int cpu)
|
||||
{
|
||||
loongson_send_ipi_single(cpu, SMP_RESCHEDULE);
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(smp_send_reschedule);
|
||||
|
||||
irqreturn_t loongson_ipi_interrupt(int irq, void *dev)
|
||||
{
|
||||
unsigned int action;
|
||||
|
@ -10,6 +10,8 @@
|
||||
#include <asm/regdef.h>
|
||||
#include <asm/stackframe.h>
|
||||
|
||||
#define INVTLB_ADDR_GFALSE_AND_ASID 5
|
||||
|
||||
#define PTRS_PER_PGD_BITS (PAGE_SHIFT - 3)
|
||||
#define PTRS_PER_PUD_BITS (PAGE_SHIFT - 3)
|
||||
#define PTRS_PER_PMD_BITS (PAGE_SHIFT - 3)
|
||||
@ -136,13 +138,10 @@ tlb_huge_update_load:
|
||||
ori t0, ra, _PAGE_VALID
|
||||
st.d t0, t1, 0
|
||||
#endif
|
||||
tlbsrch
|
||||
addu16i.d t1, zero, -(CSR_TLBIDX_EHINV >> 16)
|
||||
addi.d ra, t1, 0
|
||||
csrxchg ra, t1, LOONGARCH_CSR_TLBIDX
|
||||
tlbwr
|
||||
|
||||
csrxchg zero, t1, LOONGARCH_CSR_TLBIDX
|
||||
csrrd ra, LOONGARCH_CSR_ASID
|
||||
csrrd t1, LOONGARCH_CSR_BADV
|
||||
andi ra, ra, CSR_ASID_ASID
|
||||
invtlb INVTLB_ADDR_GFALSE_AND_ASID, ra, t1
|
||||
|
||||
/*
|
||||
* A huge PTE describes an area the size of the
|
||||
@ -287,13 +286,11 @@ tlb_huge_update_store:
|
||||
ori t0, ra, (_PAGE_VALID | _PAGE_DIRTY | _PAGE_MODIFIED)
|
||||
st.d t0, t1, 0
|
||||
#endif
|
||||
tlbsrch
|
||||
addu16i.d t1, zero, -(CSR_TLBIDX_EHINV >> 16)
|
||||
addi.d ra, t1, 0
|
||||
csrxchg ra, t1, LOONGARCH_CSR_TLBIDX
|
||||
tlbwr
|
||||
csrrd ra, LOONGARCH_CSR_ASID
|
||||
csrrd t1, LOONGARCH_CSR_BADV
|
||||
andi ra, ra, CSR_ASID_ASID
|
||||
invtlb INVTLB_ADDR_GFALSE_AND_ASID, ra, t1
|
||||
|
||||
csrxchg zero, t1, LOONGARCH_CSR_TLBIDX
|
||||
/*
|
||||
* A huge PTE describes an area the size of the
|
||||
* configured huge page size. This is twice the
|
||||
@ -436,6 +433,11 @@ tlb_huge_update_modify:
|
||||
ori t0, ra, (_PAGE_VALID | _PAGE_DIRTY | _PAGE_MODIFIED)
|
||||
st.d t0, t1, 0
|
||||
#endif
|
||||
csrrd ra, LOONGARCH_CSR_ASID
|
||||
csrrd t1, LOONGARCH_CSR_BADV
|
||||
andi ra, ra, CSR_ASID_ASID
|
||||
invtlb INVTLB_ADDR_GFALSE_AND_ASID, ra, t1
|
||||
|
||||
/*
|
||||
* A huge PTE describes an area the size of the
|
||||
* configured huge page size. This is twice the
|
||||
@ -466,7 +468,7 @@ tlb_huge_update_modify:
|
||||
addu16i.d t1, zero, (PS_HUGE_SIZE << (CSR_TLBIDX_PS_SHIFT - 16))
|
||||
csrxchg t1, t0, LOONGARCH_CSR_TLBIDX
|
||||
|
||||
tlbwr
|
||||
tlbfill
|
||||
|
||||
/* Reset default page size */
|
||||
addu16i.d t0, zero, (CSR_TLBIDX_PS >> 16)
|
||||
|
@ -109,7 +109,7 @@ struct clk *ahci_platform_find_clk(struct ahci_host_priv *hpriv, const char *con
|
||||
int i;
|
||||
|
||||
for (i = 0; i < hpriv->n_clks; i++) {
|
||||
if (!strcmp(hpriv->clks[i].id, con_id))
|
||||
if (hpriv->clks[i].id && !strcmp(hpriv->clks[i].id, con_id))
|
||||
return hpriv->clks[i].clk;
|
||||
}
|
||||
|
||||
|
@ -2056,6 +2056,11 @@ static int btusb_setup_csr(struct hci_dev *hdev)
|
||||
|
||||
rp = (struct hci_rp_read_local_version *)skb->data;
|
||||
|
||||
bt_dev_info(hdev, "CSR: Setting up dongle with HCI ver=%u rev=%04x; LMP ver=%u subver=%04x; manufacturer=%u",
|
||||
le16_to_cpu(rp->hci_ver), le16_to_cpu(rp->hci_rev),
|
||||
le16_to_cpu(rp->lmp_ver), le16_to_cpu(rp->lmp_subver),
|
||||
le16_to_cpu(rp->manufacturer));
|
||||
|
||||
/* Detect a wide host of Chinese controllers that aren't CSR.
|
||||
*
|
||||
* Known fake bcdDevices: 0x0100, 0x0134, 0x1915, 0x2520, 0x7558, 0x8891
|
||||
@ -2118,6 +2123,7 @@ static int btusb_setup_csr(struct hci_dev *hdev)
|
||||
* without these the controller will lock up.
|
||||
*/
|
||||
set_bit(HCI_QUIRK_BROKEN_STORED_LINK_KEY, &hdev->quirks);
|
||||
set_bit(HCI_QUIRK_BROKEN_ERR_DATA_REPORTING, &hdev->quirks);
|
||||
set_bit(HCI_QUIRK_BROKEN_FILTER_CLEAR_ALL, &hdev->quirks);
|
||||
set_bit(HCI_QUIRK_NO_SUSPEND_NOTIFIER, &hdev->quirks);
|
||||
|
||||
|
@ -226,7 +226,10 @@ static int __init amd_gpio_init(void)
|
||||
ioport_unmap(gp.pm);
|
||||
goto out;
|
||||
}
|
||||
return 0;
|
||||
|
||||
out:
|
||||
pci_dev_put(pdev);
|
||||
return err;
|
||||
}
|
||||
|
||||
@ -234,6 +237,7 @@ static void __exit amd_gpio_exit(void)
|
||||
{
|
||||
gpiochip_remove(&gp.chip);
|
||||
ioport_unmap(gp.pm);
|
||||
pci_dev_put(gp.pdev);
|
||||
}
|
||||
|
||||
module_init(amd_gpio_init);
|
||||
|
@ -610,6 +610,7 @@ static int rockchip_gpiolib_register(struct rockchip_pin_bank *bank)
|
||||
return -ENODATA;
|
||||
|
||||
pctldev = of_pinctrl_get(pctlnp);
|
||||
of_node_put(pctlnp);
|
||||
if (!pctldev)
|
||||
return -ENODEV;
|
||||
|
||||
|
@ -526,12 +526,13 @@ static int gpiochip_setup_dev(struct gpio_device *gdev)
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* From this point, the .release() function cleans up gpio_device */
|
||||
gdev->dev.release = gpiodevice_release;
|
||||
|
||||
ret = gpiochip_sysfs_register(gdev);
|
||||
if (ret)
|
||||
goto err_remove_device;
|
||||
|
||||
/* From this point, the .release() function cleans up gpio_device */
|
||||
gdev->dev.release = gpiodevice_release;
|
||||
dev_dbg(&gdev->dev, "registered GPIOs %d to %d on %s\n", gdev->base,
|
||||
gdev->base + gdev->ngpio - 1, gdev->chip->label ? : "generic");
|
||||
|
||||
@ -597,10 +598,10 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
struct fwnode_handle *fwnode = NULL;
|
||||
struct gpio_device *gdev;
|
||||
unsigned long flags;
|
||||
int base = gc->base;
|
||||
unsigned int i;
|
||||
u32 ngpios = 0;
|
||||
int base = 0;
|
||||
int ret = 0;
|
||||
u32 ngpios;
|
||||
|
||||
if (gc->fwnode)
|
||||
fwnode = gc->fwnode;
|
||||
@ -647,17 +648,12 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
else
|
||||
gdev->owner = THIS_MODULE;
|
||||
|
||||
gdev->descs = kcalloc(gc->ngpio, sizeof(gdev->descs[0]), GFP_KERNEL);
|
||||
if (!gdev->descs) {
|
||||
ret = -ENOMEM;
|
||||
goto err_free_dev_name;
|
||||
}
|
||||
|
||||
/*
|
||||
* Try the device properties if the driver didn't supply the number
|
||||
* of GPIO lines.
|
||||
*/
|
||||
if (gc->ngpio == 0) {
|
||||
ngpios = gc->ngpio;
|
||||
if (ngpios == 0) {
|
||||
ret = device_property_read_u32(&gdev->dev, "ngpios", &ngpios);
|
||||
if (ret == -ENODATA)
|
||||
/*
|
||||
@ -668,7 +664,7 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
*/
|
||||
ngpios = 0;
|
||||
else if (ret)
|
||||
goto err_free_descs;
|
||||
goto err_free_dev_name;
|
||||
|
||||
gc->ngpio = ngpios;
|
||||
}
|
||||
@ -676,13 +672,19 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
if (gc->ngpio == 0) {
|
||||
chip_err(gc, "tried to insert a GPIO chip with zero lines\n");
|
||||
ret = -EINVAL;
|
||||
goto err_free_descs;
|
||||
goto err_free_dev_name;
|
||||
}
|
||||
|
||||
if (gc->ngpio > FASTPATH_NGPIO)
|
||||
chip_warn(gc, "line cnt %u is greater than fast path cnt %u\n",
|
||||
gc->ngpio, FASTPATH_NGPIO);
|
||||
|
||||
gdev->descs = kcalloc(gc->ngpio, sizeof(*gdev->descs), GFP_KERNEL);
|
||||
if (!gdev->descs) {
|
||||
ret = -ENOMEM;
|
||||
goto err_free_dev_name;
|
||||
}
|
||||
|
||||
gdev->label = kstrdup_const(gc->label ?: "unknown", GFP_KERNEL);
|
||||
if (!gdev->label) {
|
||||
ret = -ENOMEM;
|
||||
@ -701,11 +703,13 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
* it may be a pipe dream. It will not happen before we get rid
|
||||
* of the sysfs interface anyways.
|
||||
*/
|
||||
base = gc->base;
|
||||
if (base < 0) {
|
||||
base = gpiochip_find_base(gc->ngpio);
|
||||
if (base < 0) {
|
||||
ret = base;
|
||||
spin_unlock_irqrestore(&gpio_lock, flags);
|
||||
ret = base;
|
||||
base = 0;
|
||||
goto err_free_label;
|
||||
}
|
||||
/*
|
||||
@ -816,6 +820,11 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
err_free_gpiochip_mask:
|
||||
gpiochip_remove_pin_ranges(gc);
|
||||
gpiochip_free_valid_mask(gc);
|
||||
if (gdev->dev.release) {
|
||||
/* release() has been registered by gpiochip_setup_dev() */
|
||||
put_device(&gdev->dev);
|
||||
goto err_print_message;
|
||||
}
|
||||
err_remove_from_list:
|
||||
spin_lock_irqsave(&gpio_lock, flags);
|
||||
list_del(&gdev->list);
|
||||
@ -829,13 +838,14 @@ int gpiochip_add_data_with_key(struct gpio_chip *gc, void *data,
|
||||
err_free_ida:
|
||||
ida_free(&gpio_ida, gdev->id);
|
||||
err_free_gdev:
|
||||
kfree(gdev);
|
||||
err_print_message:
|
||||
/* failures here can mean systems won't boot... */
|
||||
if (ret != -EPROBE_DEFER) {
|
||||
pr_err("%s: GPIOs %d..%d (%s) failed to register, %d\n", __func__,
|
||||
gdev->base, gdev->base + gdev->ngpio - 1,
|
||||
base, base + (int)ngpios - 1,
|
||||
gc->label ? : "generic", ret);
|
||||
}
|
||||
kfree(gdev);
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(gpiochip_add_data_with_key);
|
||||
|
@ -907,13 +907,13 @@ static void sdma_v4_0_ring_emit_fence(struct amdgpu_ring *ring, u64 addr, u64 se
|
||||
|
||||
|
||||
/**
|
||||
* sdma_v4_0_gfx_stop - stop the gfx async dma engines
|
||||
* sdma_v4_0_gfx_enable - enable the gfx async dma engines
|
||||
*
|
||||
* @adev: amdgpu_device pointer
|
||||
*
|
||||
* Stop the gfx async dma ring buffers (VEGA10).
|
||||
* @enable: enable SDMA RB/IB
|
||||
* control the gfx async dma ring buffers (VEGA10).
|
||||
*/
|
||||
static void sdma_v4_0_gfx_stop(struct amdgpu_device *adev)
|
||||
static void sdma_v4_0_gfx_enable(struct amdgpu_device *adev, bool enable)
|
||||
{
|
||||
u32 rb_cntl, ib_cntl;
|
||||
int i;
|
||||
@ -922,10 +922,10 @@ static void sdma_v4_0_gfx_stop(struct amdgpu_device *adev)
|
||||
|
||||
for (i = 0; i < adev->sdma.num_instances; i++) {
|
||||
rb_cntl = RREG32_SDMA(i, mmSDMA0_GFX_RB_CNTL);
|
||||
rb_cntl = REG_SET_FIELD(rb_cntl, SDMA0_GFX_RB_CNTL, RB_ENABLE, 0);
|
||||
rb_cntl = REG_SET_FIELD(rb_cntl, SDMA0_GFX_RB_CNTL, RB_ENABLE, enable ? 1 : 0);
|
||||
WREG32_SDMA(i, mmSDMA0_GFX_RB_CNTL, rb_cntl);
|
||||
ib_cntl = RREG32_SDMA(i, mmSDMA0_GFX_IB_CNTL);
|
||||
ib_cntl = REG_SET_FIELD(ib_cntl, SDMA0_GFX_IB_CNTL, IB_ENABLE, 0);
|
||||
ib_cntl = REG_SET_FIELD(ib_cntl, SDMA0_GFX_IB_CNTL, IB_ENABLE, enable ? 1 : 0);
|
||||
WREG32_SDMA(i, mmSDMA0_GFX_IB_CNTL, ib_cntl);
|
||||
}
|
||||
}
|
||||
@ -1044,7 +1044,7 @@ static void sdma_v4_0_enable(struct amdgpu_device *adev, bool enable)
|
||||
int i;
|
||||
|
||||
if (!enable) {
|
||||
sdma_v4_0_gfx_stop(adev);
|
||||
sdma_v4_0_gfx_enable(adev, enable);
|
||||
sdma_v4_0_rlc_stop(adev);
|
||||
if (adev->sdma.has_page_queue)
|
||||
sdma_v4_0_page_stop(adev);
|
||||
@ -1960,8 +1960,10 @@ static int sdma_v4_0_suspend(void *handle)
|
||||
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
|
||||
|
||||
/* SMU saves SDMA state for us */
|
||||
if (adev->in_s0ix)
|
||||
if (adev->in_s0ix) {
|
||||
sdma_v4_0_gfx_enable(adev, false);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return sdma_v4_0_hw_fini(adev);
|
||||
}
|
||||
@ -1971,8 +1973,12 @@ static int sdma_v4_0_resume(void *handle)
|
||||
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
|
||||
|
||||
/* SMU restores SDMA state for us */
|
||||
if (adev->in_s0ix)
|
||||
if (adev->in_s0ix) {
|
||||
sdma_v4_0_enable(adev, true);
|
||||
sdma_v4_0_gfx_enable(adev, true);
|
||||
amdgpu_ttm_set_buffer_funcs_status(adev, true);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return sdma_v4_0_hw_init(adev);
|
||||
}
|
||||
|
@ -1153,7 +1153,7 @@ struct vba_vars_st {
|
||||
double UrgBurstFactorLumaPre[DC__NUM_DPP__MAX];
|
||||
double UrgBurstFactorChromaPre[DC__NUM_DPP__MAX];
|
||||
bool NotUrgentLatencyHidingPre[DC__NUM_DPP__MAX];
|
||||
bool LinkCapacitySupport[DC__NUM_DPP__MAX];
|
||||
bool LinkCapacitySupport[DC__VOLTAGE_STATES];
|
||||
bool VREADY_AT_OR_AFTER_VSYNC[DC__NUM_DPP__MAX];
|
||||
unsigned int MIN_DST_Y_NEXT_START[DC__NUM_DPP__MAX];
|
||||
unsigned int VFrontPorch[DC__NUM_DPP__MAX];
|
||||
|
@ -2720,6 +2720,9 @@ static u32 *dw_hdmi_bridge_atomic_get_output_bus_fmts(struct drm_bridge *bridge,
|
||||
* if supported. In any case the default RGB888 format is added
|
||||
*/
|
||||
|
||||
/* Default 8bit RGB fallback */
|
||||
output_fmts[i++] = MEDIA_BUS_FMT_RGB888_1X24;
|
||||
|
||||
if (max_bpc >= 16 && info->bpc == 16) {
|
||||
if (info->color_formats & DRM_COLOR_FORMAT_YCBCR444)
|
||||
output_fmts[i++] = MEDIA_BUS_FMT_YUV16_1X48;
|
||||
@ -2753,9 +2756,6 @@ static u32 *dw_hdmi_bridge_atomic_get_output_bus_fmts(struct drm_bridge *bridge,
|
||||
if (info->color_formats & DRM_COLOR_FORMAT_YCBCR444)
|
||||
output_fmts[i++] = MEDIA_BUS_FMT_YUV8_1X24;
|
||||
|
||||
/* Default 8bit RGB fallback */
|
||||
output_fmts[i++] = MEDIA_BUS_FMT_RGB888_1X24;
|
||||
|
||||
*num_output_fmts = i;
|
||||
|
||||
return output_fmts;
|
||||
|
@ -931,9 +931,9 @@ static void ti_sn_bridge_set_video_timings(struct ti_sn65dsi86 *pdata)
|
||||
&pdata->bridge.encoder->crtc->state->adjusted_mode;
|
||||
u8 hsync_polarity = 0, vsync_polarity = 0;
|
||||
|
||||
if (mode->flags & DRM_MODE_FLAG_PHSYNC)
|
||||
if (mode->flags & DRM_MODE_FLAG_NHSYNC)
|
||||
hsync_polarity = CHA_HSYNC_POLARITY;
|
||||
if (mode->flags & DRM_MODE_FLAG_PVSYNC)
|
||||
if (mode->flags & DRM_MODE_FLAG_NVSYNC)
|
||||
vsync_polarity = CHA_VSYNC_POLARITY;
|
||||
|
||||
ti_sn65dsi86_write_u16(pdata, SN_CHA_ACTIVE_LINE_LENGTH_LOW_REG,
|
||||
|
@ -571,12 +571,20 @@ static void drm_gem_shmem_vm_open(struct vm_area_struct *vma)
|
||||
{
|
||||
struct drm_gem_object *obj = vma->vm_private_data;
|
||||
struct drm_gem_shmem_object *shmem = to_drm_gem_shmem_obj(obj);
|
||||
int ret;
|
||||
|
||||
WARN_ON(shmem->base.import_attach);
|
||||
|
||||
ret = drm_gem_shmem_get_pages(shmem);
|
||||
WARN_ON_ONCE(ret != 0);
|
||||
mutex_lock(&shmem->pages_lock);
|
||||
|
||||
/*
|
||||
* We should have already pinned the pages when the buffer was first
|
||||
* mmap'd, vm_open() just grabs an additional reference for the new
|
||||
* mm the vma is getting copied into (ie. on fork()).
|
||||
*/
|
||||
if (!WARN_ON_ONCE(!shmem->pages_use_count))
|
||||
shmem->pages_use_count++;
|
||||
|
||||
mutex_unlock(&shmem->pages_lock);
|
||||
|
||||
drm_gem_vm_open(vma);
|
||||
}
|
||||
@ -622,10 +630,8 @@ int drm_gem_shmem_mmap(struct drm_gem_shmem_object *shmem, struct vm_area_struct
|
||||
}
|
||||
|
||||
ret = drm_gem_shmem_get_pages(shmem);
|
||||
if (ret) {
|
||||
drm_gem_vm_close(vma);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
|
||||
vma->vm_flags |= VM_PFNMAP | VM_DONTEXPAND | VM_DONTDUMP;
|
||||
vma->vm_page_prot = vm_get_page_prot(vma->vm_flags);
|
||||
|
@ -1085,21 +1085,21 @@ int vmw_mksstat_add_ioctl(struct drm_device *dev, void *data,
|
||||
reset_ppn_array(pdesc->strsPPNs, ARRAY_SIZE(pdesc->strsPPNs));
|
||||
|
||||
/* Pin mksGuestStat user pages and store those in the instance descriptor */
|
||||
nr_pinned_stat = pin_user_pages(arg->stat, num_pages_stat, FOLL_LONGTERM, pages_stat, NULL);
|
||||
nr_pinned_stat = pin_user_pages_fast(arg->stat, num_pages_stat, FOLL_LONGTERM, pages_stat);
|
||||
if (num_pages_stat != nr_pinned_stat)
|
||||
goto err_pin_stat;
|
||||
|
||||
for (i = 0; i < num_pages_stat; ++i)
|
||||
pdesc->statPPNs[i] = page_to_pfn(pages_stat[i]);
|
||||
|
||||
nr_pinned_info = pin_user_pages(arg->info, num_pages_info, FOLL_LONGTERM, pages_info, NULL);
|
||||
nr_pinned_info = pin_user_pages_fast(arg->info, num_pages_info, FOLL_LONGTERM, pages_info);
|
||||
if (num_pages_info != nr_pinned_info)
|
||||
goto err_pin_info;
|
||||
|
||||
for (i = 0; i < num_pages_info; ++i)
|
||||
pdesc->infoPPNs[i] = page_to_pfn(pages_info[i]);
|
||||
|
||||
nr_pinned_strs = pin_user_pages(arg->strs, num_pages_strs, FOLL_LONGTERM, pages_strs, NULL);
|
||||
nr_pinned_strs = pin_user_pages_fast(arg->strs, num_pages_strs, FOLL_LONGTERM, pages_strs);
|
||||
if (num_pages_strs != nr_pinned_strs)
|
||||
goto err_pin_strs;
|
||||
|
||||
|
@ -949,6 +949,10 @@ int vmw_kms_sou_init_display(struct vmw_private *dev_priv)
|
||||
struct drm_device *dev = &dev_priv->drm;
|
||||
int i, ret;
|
||||
|
||||
/* Screen objects won't work if GMR's aren't available */
|
||||
if (!dev_priv->has_gmr)
|
||||
return -ENOSYS;
|
||||
|
||||
if (!(dev_priv->capabilities & SVGA_CAP_SCREEN_OBJECT_2)) {
|
||||
return -ENOSYS;
|
||||
}
|
||||
|
@ -1315,6 +1315,9 @@ static s32 snto32(__u32 value, unsigned n)
|
||||
if (!value || !n)
|
||||
return 0;
|
||||
|
||||
if (n > 32)
|
||||
n = 32;
|
||||
|
||||
switch (n) {
|
||||
case 8: return ((__s8)value);
|
||||
case 16: return ((__s16)value);
|
||||
|
@ -274,6 +274,7 @@
|
||||
#define USB_DEVICE_ID_CH_AXIS_295 0x001c
|
||||
|
||||
#define USB_VENDOR_ID_CHERRY 0x046a
|
||||
#define USB_DEVICE_ID_CHERRY_MOUSE_000C 0x000c
|
||||
#define USB_DEVICE_ID_CHERRY_CYMOTION 0x0023
|
||||
#define USB_DEVICE_ID_CHERRY_CYMOTION_SOLAR 0x0027
|
||||
|
||||
@ -917,6 +918,7 @@
|
||||
#define USB_DEVICE_ID_MS_XBOX_ONE_S_CONTROLLER 0x02fd
|
||||
#define USB_DEVICE_ID_MS_PIXART_MOUSE 0x00cb
|
||||
#define USB_DEVICE_ID_8BITDO_SN30_PRO_PLUS 0x02e0
|
||||
#define USB_DEVICE_ID_MS_MOUSE_0783 0x0783
|
||||
|
||||
#define USB_VENDOR_ID_MOJO 0x8282
|
||||
#define USB_DEVICE_ID_RETRO_ADAPTER 0x3201
|
||||
@ -1215,6 +1217,7 @@
|
||||
#define USB_DEVICE_ID_SYNAPTICS_DELL_K15A 0x6e21
|
||||
#define USB_DEVICE_ID_SYNAPTICS_ACER_ONE_S1002 0x73f4
|
||||
#define USB_DEVICE_ID_SYNAPTICS_ACER_ONE_S1003 0x73f5
|
||||
#define USB_DEVICE_ID_SYNAPTICS_ACER_SWITCH5_017 0x73f6
|
||||
#define USB_DEVICE_ID_SYNAPTICS_ACER_SWITCH5 0x81a7
|
||||
|
||||
#define USB_VENDOR_ID_TEXAS_INSTRUMENTS 0x2047
|
||||
@ -1381,6 +1384,7 @@
|
||||
|
||||
#define USB_VENDOR_ID_PRIMAX 0x0461
|
||||
#define USB_DEVICE_ID_PRIMAX_MOUSE_4D22 0x4d22
|
||||
#define USB_DEVICE_ID_PRIMAX_MOUSE_4E2A 0x4e2a
|
||||
#define USB_DEVICE_ID_PRIMAX_KEYBOARD 0x4e05
|
||||
#define USB_DEVICE_ID_PRIMAX_REZEL 0x4e72
|
||||
#define USB_DEVICE_ID_PRIMAX_PIXART_MOUSE_4D0F 0x4d0f
|
||||
|
@ -121,6 +121,11 @@ static const struct hid_device_id ite_devices[] = {
|
||||
USB_VENDOR_ID_SYNAPTICS,
|
||||
USB_DEVICE_ID_SYNAPTICS_ACER_ONE_S1003),
|
||||
.driver_data = QUIRK_TOUCHPAD_ON_OFF_REPORT },
|
||||
/* ITE8910 USB kbd ctlr, with Synaptics touchpad connected to it. */
|
||||
{ HID_DEVICE(BUS_USB, HID_GROUP_GENERIC,
|
||||
USB_VENDOR_ID_SYNAPTICS,
|
||||
USB_DEVICE_ID_SYNAPTICS_ACER_SWITCH5_017),
|
||||
.driver_data = QUIRK_TOUCHPAD_ON_OFF_REPORT },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(hid, ite_devices);
|
||||
|
@ -872,6 +872,12 @@ static ssize_t lg4ff_alternate_modes_store(struct device *dev, struct device_att
|
||||
return -ENOMEM;
|
||||
|
||||
i = strlen(lbuf);
|
||||
|
||||
if (i == 0) {
|
||||
kfree(lbuf);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (lbuf[i-1] == '\n') {
|
||||
if (i == 1) {
|
||||
kfree(lbuf);
|
||||
|
@ -4269,21 +4269,6 @@ static void hidpp_remove(struct hid_device *hdev)
|
||||
mutex_destroy(&hidpp->send_mutex);
|
||||
}
|
||||
|
||||
static const struct hid_device_id unhandled_hidpp_devices[] = {
|
||||
/* Logitech Harmony Adapter for PS3, handled in hid-sony */
|
||||
{ HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_HARMONY_PS3) },
|
||||
/* Handled in hid-generic */
|
||||
{ HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_DINOVO_EDGE_KBD) },
|
||||
{}
|
||||
};
|
||||
|
||||
static bool hidpp_match(struct hid_device *hdev,
|
||||
bool ignore_special_driver)
|
||||
{
|
||||
/* Refuse to handle devices handled by other HID drivers */
|
||||
return !hid_match_id(hdev, unhandled_hidpp_devices);
|
||||
}
|
||||
|
||||
#define LDJ_DEVICE(product) \
|
||||
HID_DEVICE(BUS_USB, HID_GROUP_LOGITECH_DJ_DEVICE, \
|
||||
USB_VENDOR_ID_LOGITECH, (product))
|
||||
@ -4367,9 +4352,15 @@ static const struct hid_device_id hidpp_devices[] = {
|
||||
{ /* MX5500 keyboard over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb30b),
|
||||
.driver_data = HIDPP_QUIRK_HIDPP_CONSUMER_VENDOR_KEYS },
|
||||
|
||||
{ /* And try to enable HID++ for all the Logitech Bluetooth devices */
|
||||
HID_DEVICE(BUS_BLUETOOTH, HID_GROUP_ANY, USB_VENDOR_ID_LOGITECH, HID_ANY_ID) },
|
||||
{ /* M-RCQ142 V470 Cordless Laser Mouse over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb008) },
|
||||
{ /* MX Master mouse over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb012) },
|
||||
{ /* MX Ergo trackball over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb01d) },
|
||||
{ HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb01e) },
|
||||
{ /* MX Master 3 mouse over Bluetooth */
|
||||
HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_LOGITECH, 0xb023) },
|
||||
{}
|
||||
};
|
||||
|
||||
@ -4383,7 +4374,6 @@ static const struct hid_usage_id hidpp_usages[] = {
|
||||
static struct hid_driver hidpp_driver = {
|
||||
.name = "logitech-hidpp-device",
|
||||
.id_table = hidpp_devices,
|
||||
.match = hidpp_match,
|
||||
.report_fixup = hidpp_report_fixup,
|
||||
.probe = hidpp_probe,
|
||||
.remove = hidpp_remove,
|
||||
|
@ -54,6 +54,7 @@ static const struct hid_device_id hid_quirks[] = {
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_FLIGHT_SIM_YOKE), HID_QUIRK_NOGET },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_PEDALS), HID_QUIRK_NOGET },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_THROTTLE), HID_QUIRK_NOGET },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CHERRY, USB_DEVICE_ID_CHERRY_MOUSE_000C), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB), HID_QUIRK_NO_INIT_REPORTS },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB_RAPIDFIRE), HID_QUIRK_NO_INIT_REPORTS | HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K70RGB), HID_QUIRK_NO_INIT_REPORTS },
|
||||
@ -122,6 +123,7 @@ static const struct hid_device_id hid_quirks[] = {
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_MOUSE_C05A), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_MOUSE_C06A), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_MCS, USB_DEVICE_ID_MCS_GAMEPADBLOCK), HID_QUIRK_MULTI_INPUT },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_MOUSE_0783), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_PIXART_MOUSE), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_POWER_COVER), HID_QUIRK_NO_INIT_REPORTS },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_SURFACE3_COVER), HID_QUIRK_NO_INIT_REPORTS },
|
||||
@ -146,6 +148,7 @@ static const struct hid_device_id hid_quirks[] = {
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN), HID_QUIRK_NO_INIT_REPORTS },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_USB_OPTICAL_MOUSE), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PRIMAX, USB_DEVICE_ID_PRIMAX_MOUSE_4D22), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PRIMAX, USB_DEVICE_ID_PRIMAX_MOUSE_4E2A), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PRIMAX, USB_DEVICE_ID_PRIMAX_PIXART_MOUSE_4D0F), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PRIMAX, USB_DEVICE_ID_PRIMAX_PIXART_MOUSE_4D65), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_PRIMAX, USB_DEVICE_ID_PRIMAX_PIXART_MOUSE_4E22), HID_QUIRK_ALWAYS_POLL },
|
||||
|
@ -192,6 +192,7 @@ static int uclogic_probe(struct hid_device *hdev,
|
||||
* than the pen, so use QUIRK_MULTI_INPUT for all tablets.
|
||||
*/
|
||||
hdev->quirks |= HID_QUIRK_MULTI_INPUT;
|
||||
hdev->quirks |= HID_QUIRK_HIDINPUT_FORCE;
|
||||
|
||||
/* Allocate and assign driver data */
|
||||
drvdata = devm_kzalloc(&hdev->dev, sizeof(*drvdata), GFP_KERNEL);
|
||||
|
@ -1193,7 +1193,7 @@ __u8 *uclogic_rdesc_template_apply(const __u8 *template_ptr,
|
||||
p[sizeof(btn_head)] < param_num) {
|
||||
v = param_list[p[sizeof(btn_head)]];
|
||||
put_unaligned((__u8)0x2A, p); /* Usage Maximum */
|
||||
put_unaligned_le16((__force u16)cpu_to_le16(v), p + 1);
|
||||
put_unaligned((__force u16)cpu_to_le16(v), (s16 *)(p + 1));
|
||||
p += sizeof(btn_head) + 1;
|
||||
} else {
|
||||
p++;
|
||||
|
@ -66,6 +66,6 @@ endmenu
|
||||
|
||||
config I2C_HID_CORE
|
||||
tristate
|
||||
default y if I2C_HID_ACPI=y || I2C_HID_OF=y || I2C_HID_OF_GOODIX=y
|
||||
default m if I2C_HID_ACPI=m || I2C_HID_OF=m || I2C_HID_OF_GOODIX=m
|
||||
default y if I2C_HID_ACPI=y || I2C_HID_OF=y || I2C_HID_OF_ELAN=y || I2C_HID_OF_GOODIX=y
|
||||
default m if I2C_HID_ACPI=m || I2C_HID_OF=m || I2C_HID_OF_ELAN=m || I2C_HID_OF_GOODIX=m
|
||||
select HID
|
||||
|
@ -1402,7 +1402,7 @@ static void domain_update_iotlb(struct dmar_domain *domain)
|
||||
* check because it applies only to the built-in QAT devices and it doesn't
|
||||
* grant additional privileges.
|
||||
*/
|
||||
#define BUGGY_QAT_DEVID_MASK 0x494c
|
||||
#define BUGGY_QAT_DEVID_MASK 0x4940
|
||||
static bool dev_needs_extra_dtlb_flush(struct pci_dev *pdev)
|
||||
{
|
||||
if (pdev->vendor != PCI_VENDOR_ID_INTEL)
|
||||
|
@ -145,6 +145,8 @@ bool v4l2_valid_dv_timings(const struct v4l2_dv_timings *t,
|
||||
const struct v4l2_bt_timings *bt = &t->bt;
|
||||
const struct v4l2_bt_timings_cap *cap = &dvcap->bt;
|
||||
u32 caps = cap->capabilities;
|
||||
const u32 max_vert = 10240;
|
||||
u32 max_hor = 3 * bt->width;
|
||||
|
||||
if (t->type != V4L2_DV_BT_656_1120)
|
||||
return false;
|
||||
@ -166,14 +168,20 @@ bool v4l2_valid_dv_timings(const struct v4l2_dv_timings *t,
|
||||
if (!bt->interlaced &&
|
||||
(bt->il_vbackporch || bt->il_vsync || bt->il_vfrontporch))
|
||||
return false;
|
||||
if (bt->hfrontporch > 2 * bt->width ||
|
||||
bt->hsync > 1024 || bt->hbackporch > 1024)
|
||||
/*
|
||||
* Some video receivers cannot properly separate the frontporch,
|
||||
* backporch and sync values, and instead they only have the total
|
||||
* blanking. That can be assigned to any of these three fields.
|
||||
* So just check that none of these are way out of range.
|
||||
*/
|
||||
if (bt->hfrontporch > max_hor ||
|
||||
bt->hsync > max_hor || bt->hbackporch > max_hor)
|
||||
return false;
|
||||
if (bt->vfrontporch > 4096 ||
|
||||
bt->vsync > 128 || bt->vbackporch > 4096)
|
||||
if (bt->vfrontporch > max_vert ||
|
||||
bt->vsync > max_vert || bt->vbackporch > max_vert)
|
||||
return false;
|
||||
if (bt->interlaced && (bt->il_vfrontporch > 4096 ||
|
||||
bt->il_vsync > 128 || bt->il_vbackporch > 4096))
|
||||
if (bt->interlaced && (bt->il_vfrontporch > max_vert ||
|
||||
bt->il_vsync > max_vert || bt->il_vbackporch > max_vert))
|
||||
return false;
|
||||
return fnc == NULL || fnc(t, fnc_handle);
|
||||
}
|
||||
|
@ -3247,7 +3247,7 @@ static int bond_na_rcv(const struct sk_buff *skb, struct bonding *bond,
|
||||
goto out;
|
||||
|
||||
saddr = &combined->ip6.saddr;
|
||||
daddr = &combined->ip6.saddr;
|
||||
daddr = &combined->ip6.daddr;
|
||||
|
||||
slave_dbg(bond->dev, slave->dev, "%s: %s/%d av %d sv %d sip %pI6c tip %pI6c\n",
|
||||
__func__, slave->dev->name, bond_slave_state(slave),
|
||||
|
@ -796,9 +796,9 @@ static int can327_netdev_close(struct net_device *dev)
|
||||
|
||||
netif_stop_queue(dev);
|
||||
|
||||
/* Give UART one final chance to flush. */
|
||||
clear_bit(TTY_DO_WRITE_WAKEUP, &elm->tty->flags);
|
||||
flush_work(&elm->tx_work);
|
||||
/* We don't flush the UART TX queue here, as we want final stop
|
||||
* commands (like the above dummy char) to be flushed out.
|
||||
*/
|
||||
|
||||
can_rx_offload_disable(&elm->offload);
|
||||
elm->can.state = CAN_STATE_STOPPED;
|
||||
@ -1069,12 +1069,15 @@ static void can327_ldisc_close(struct tty_struct *tty)
|
||||
{
|
||||
struct can327 *elm = (struct can327 *)tty->disc_data;
|
||||
|
||||
/* unregister_netdev() calls .ndo_stop() so we don't have to.
|
||||
* Our .ndo_stop() also flushes the TTY write wakeup handler,
|
||||
* so we can safely set elm->tty = NULL after this.
|
||||
*/
|
||||
/* unregister_netdev() calls .ndo_stop() so we don't have to. */
|
||||
unregister_candev(elm->dev);
|
||||
|
||||
/* Give UART one final chance to flush.
|
||||
* No need to clear TTY_DO_WRITE_WAKEUP since .write_wakeup() is
|
||||
* serialised against .close() and will not be called once we return.
|
||||
*/
|
||||
flush_work(&elm->tx_work);
|
||||
|
||||
/* Mark channel as dead */
|
||||
spin_lock_bh(&elm->lock);
|
||||
tty->disc_data = NULL;
|
||||
|
@ -864,12 +864,14 @@ static void slcan_close(struct tty_struct *tty)
|
||||
{
|
||||
struct slcan *sl = (struct slcan *)tty->disc_data;
|
||||
|
||||
/* unregister_netdev() calls .ndo_stop() so we don't have to.
|
||||
* Our .ndo_stop() also flushes the TTY write wakeup handler,
|
||||
* so we can safely set sl->tty = NULL after this.
|
||||
*/
|
||||
unregister_candev(sl->dev);
|
||||
|
||||
/*
|
||||
* The netdev needn't be UP (so .ndo_stop() is not called). Hence make
|
||||
* sure this is not running before freeing it up.
|
||||
*/
|
||||
flush_work(&sl->tx_work);
|
||||
|
||||
/* Mark channel as dead */
|
||||
spin_lock_bh(&sl->lock);
|
||||
tty->disc_data = NULL;
|
||||
|
@ -234,6 +234,10 @@ static void esd_usb_rx_event(struct esd_usb_net_priv *priv,
|
||||
u8 rxerr = msg->msg.rx.data[2];
|
||||
u8 txerr = msg->msg.rx.data[3];
|
||||
|
||||
netdev_dbg(priv->netdev,
|
||||
"CAN_ERR_EV_EXT: dlc=%#02x state=%02x ecc=%02x rec=%02x tec=%02x\n",
|
||||
msg->msg.rx.dlc, state, ecc, rxerr, txerr);
|
||||
|
||||
skb = alloc_can_err_skb(priv->netdev, &cf);
|
||||
if (skb == NULL) {
|
||||
stats->rx_dropped++;
|
||||
@ -260,6 +264,8 @@ static void esd_usb_rx_event(struct esd_usb_net_priv *priv,
|
||||
break;
|
||||
default:
|
||||
priv->can.state = CAN_STATE_ERROR_ACTIVE;
|
||||
txerr = 0;
|
||||
rxerr = 0;
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
|
@ -833,10 +833,13 @@ static void mv88e6xxx_get_caps(struct dsa_switch *ds, int port,
|
||||
|
||||
chip->info->ops->phylink_get_caps(chip, port, config);
|
||||
|
||||
/* Internal ports need GMII for PHYLIB */
|
||||
if (mv88e6xxx_phy_is_internal(ds, port))
|
||||
if (mv88e6xxx_phy_is_internal(ds, port)) {
|
||||
__set_bit(PHY_INTERFACE_MODE_INTERNAL,
|
||||
config->supported_interfaces);
|
||||
/* Internal ports with no phy-mode need GMII for PHYLIB */
|
||||
__set_bit(PHY_INTERFACE_MODE_GMII,
|
||||
config->supported_interfaces);
|
||||
}
|
||||
}
|
||||
|
||||
static void mv88e6xxx_mac_config(struct dsa_switch *ds, int port,
|
||||
|
@ -95,6 +95,8 @@ static int sja1105_setup_devlink_regions(struct dsa_switch *ds)
|
||||
if (IS_ERR(region)) {
|
||||
while (--i >= 0)
|
||||
dsa_devlink_region_destroy(priv->regions[i]);
|
||||
|
||||
kfree(priv->regions);
|
||||
return PTR_ERR(region);
|
||||
}
|
||||
|
||||
|
@ -1038,7 +1038,7 @@ static int sja1105_init_l2_policing(struct sja1105_private *priv)
|
||||
|
||||
policing[bcast].sharindx = port;
|
||||
/* Only SJA1110 has multicast policers */
|
||||
if (mcast <= table->ops->max_entry_count)
|
||||
if (mcast < table->ops->max_entry_count)
|
||||
policing[mcast].sharindx = port;
|
||||
}
|
||||
|
||||
|
@ -258,6 +258,7 @@ static int greth_init_rings(struct greth_private *greth)
|
||||
if (dma_mapping_error(greth->dev, dma_addr)) {
|
||||
if (netif_msg_ifup(greth))
|
||||
dev_err(greth->dev, "Could not create initial DMA mapping\n");
|
||||
dev_kfree_skb(skb);
|
||||
goto cleanup;
|
||||
}
|
||||
greth->rx_skbuff[i] = skb;
|
||||
|
@ -71,13 +71,14 @@ config BCM63XX_ENET
|
||||
config BCMGENET
|
||||
tristate "Broadcom GENET internal MAC support"
|
||||
depends on HAS_IOMEM
|
||||
depends on PTP_1588_CLOCK_OPTIONAL || !ARCH_BCM2835
|
||||
select MII
|
||||
select PHYLIB
|
||||
select FIXED_PHY
|
||||
select BCM7XXX_PHY
|
||||
select MDIO_BCM_UNIMAC
|
||||
select DIMLIB
|
||||
select BROADCOM_PHY if (ARCH_BCM2835 && PTP_1588_CLOCK_OPTIONAL)
|
||||
select BROADCOM_PHY if ARCH_BCM2835
|
||||
help
|
||||
This driver supports the built-in Ethernet MACs found in the
|
||||
Broadcom BCM7xxx Set Top Box family chipset.
|
||||
|
@ -2239,7 +2239,7 @@ static int nicvf_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
||||
err = register_netdev(netdev);
|
||||
if (err) {
|
||||
dev_err(dev, "Failed to register netdevice\n");
|
||||
goto err_unregister_interrupts;
|
||||
goto err_destroy_workqueue;
|
||||
}
|
||||
|
||||
nic->msg_enable = debug;
|
||||
@ -2248,6 +2248,8 @@ static int nicvf_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
|
||||
|
||||
return 0;
|
||||
|
||||
err_destroy_workqueue:
|
||||
destroy_workqueue(nic->nicvf_rx_mode_wq);
|
||||
err_unregister_interrupts:
|
||||
nicvf_unregister_interrupts(nic);
|
||||
err_free_netdev:
|
||||
|
@ -132,6 +132,7 @@ int dpaa2_switch_acl_entry_add(struct dpaa2_switch_filter_block *filter_block,
|
||||
DMA_TO_DEVICE);
|
||||
if (unlikely(dma_mapping_error(dev, acl_entry_cfg->key_iova))) {
|
||||
dev_err(dev, "DMA mapping failed\n");
|
||||
kfree(cmd_buff);
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
@ -142,6 +143,7 @@ int dpaa2_switch_acl_entry_add(struct dpaa2_switch_filter_block *filter_block,
|
||||
DMA_TO_DEVICE);
|
||||
if (err) {
|
||||
dev_err(dev, "dpsw_acl_add_entry() failed %d\n", err);
|
||||
kfree(cmd_buff);
|
||||
return err;
|
||||
}
|
||||
|
||||
@ -172,6 +174,7 @@ dpaa2_switch_acl_entry_remove(struct dpaa2_switch_filter_block *block,
|
||||
DMA_TO_DEVICE);
|
||||
if (unlikely(dma_mapping_error(dev, acl_entry_cfg->key_iova))) {
|
||||
dev_err(dev, "DMA mapping failed\n");
|
||||
kfree(cmd_buff);
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
@ -182,6 +185,7 @@ dpaa2_switch_acl_entry_remove(struct dpaa2_switch_filter_block *block,
|
||||
DMA_TO_DEVICE);
|
||||
if (err) {
|
||||
dev_err(dev, "dpsw_acl_remove_entry() failed %d\n", err);
|
||||
kfree(cmd_buff);
|
||||
return err;
|
||||
}
|
||||
|
||||
|
@ -1220,7 +1220,8 @@ fec_restart(struct net_device *ndev)
|
||||
writel(0, fep->hwp + FEC_IMASK);
|
||||
|
||||
/* Init the interrupt coalescing */
|
||||
fec_enet_itr_coal_set(ndev);
|
||||
if (fep->quirks & FEC_QUIRK_HAS_COALESCE)
|
||||
fec_enet_itr_coal_set(ndev);
|
||||
}
|
||||
|
||||
static int fec_enet_ipc_handle_init(struct fec_enet_private *fep)
|
||||
|
@ -283,7 +283,7 @@ static int hisi_femac_rx(struct net_device *dev, int limit)
|
||||
skb->protocol = eth_type_trans(skb, dev);
|
||||
napi_gro_receive(&priv->napi, skb);
|
||||
dev->stats.rx_packets++;
|
||||
dev->stats.rx_bytes += skb->len;
|
||||
dev->stats.rx_bytes += len;
|
||||
next:
|
||||
pos = (pos + 1) % rxq->num;
|
||||
if (rx_pkts_num >= limit)
|
||||
|
@ -550,7 +550,7 @@ static int hix5hd2_rx(struct net_device *dev, int limit)
|
||||
skb->protocol = eth_type_trans(skb, dev);
|
||||
napi_gro_receive(&priv->napi, skb);
|
||||
dev->stats.rx_packets++;
|
||||
dev->stats.rx_bytes += skb->len;
|
||||
dev->stats.rx_bytes += len;
|
||||
next:
|
||||
pos = dma_ring_incr(pos, RX_DESC_NUM);
|
||||
}
|
||||
|
@ -5936,9 +5936,9 @@ static netdev_tx_t e1000_xmit_frame(struct sk_buff *skb,
|
||||
e1000_tx_queue(tx_ring, tx_flags, count);
|
||||
/* Make sure there is space in the ring for the next send. */
|
||||
e1000_maybe_stop_tx(tx_ring,
|
||||
(MAX_SKB_FRAGS *
|
||||
((MAX_SKB_FRAGS + 1) *
|
||||
DIV_ROUND_UP(PAGE_SIZE,
|
||||
adapter->tx_fifo_limit) + 2));
|
||||
adapter->tx_fifo_limit) + 4));
|
||||
|
||||
if (!netdev_xmit_more() ||
|
||||
netif_xmit_stopped(netdev_get_tx_queue(netdev, 0))) {
|
||||
|
@ -4464,11 +4464,7 @@ static int i40e_check_fdir_input_set(struct i40e_vsi *vsi,
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
/* First 4 bytes of L4 header */
|
||||
if (usr_ip4_spec->l4_4_bytes == htonl(0xFFFFFFFF))
|
||||
new_mask |= I40E_L4_SRC_MASK | I40E_L4_DST_MASK;
|
||||
else if (!usr_ip4_spec->l4_4_bytes)
|
||||
new_mask &= ~(I40E_L4_SRC_MASK | I40E_L4_DST_MASK);
|
||||
else
|
||||
if (usr_ip4_spec->l4_4_bytes)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
/* Filtering on Type of Service is not supported. */
|
||||
@ -4507,11 +4503,7 @@ static int i40e_check_fdir_input_set(struct i40e_vsi *vsi,
|
||||
else
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
if (usr_ip6_spec->l4_4_bytes == htonl(0xFFFFFFFF))
|
||||
new_mask |= I40E_L4_SRC_MASK | I40E_L4_DST_MASK;
|
||||
else if (!usr_ip6_spec->l4_4_bytes)
|
||||
new_mask &= ~(I40E_L4_SRC_MASK | I40E_L4_DST_MASK);
|
||||
else
|
||||
if (usr_ip6_spec->l4_4_bytes)
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
/* Filtering on Traffic class is not supported. */
|
||||
|
@ -10654,6 +10654,21 @@ static int i40e_rebuild_channels(struct i40e_vsi *vsi)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* i40e_clean_xps_state - clean xps state for every tx_ring
|
||||
* @vsi: ptr to the VSI
|
||||
**/
|
||||
static void i40e_clean_xps_state(struct i40e_vsi *vsi)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (vsi->tx_rings)
|
||||
for (i = 0; i < vsi->num_queue_pairs; i++)
|
||||
if (vsi->tx_rings[i])
|
||||
clear_bit(__I40E_TX_XPS_INIT_DONE,
|
||||
vsi->tx_rings[i]->state);
|
||||
}
|
||||
|
||||
/**
|
||||
* i40e_prep_for_reset - prep for the core to reset
|
||||
* @pf: board private structure
|
||||
@ -10678,8 +10693,10 @@ static void i40e_prep_for_reset(struct i40e_pf *pf)
|
||||
i40e_pf_quiesce_all_vsi(pf);
|
||||
|
||||
for (v = 0; v < pf->num_alloc_vsi; v++) {
|
||||
if (pf->vsi[v])
|
||||
if (pf->vsi[v]) {
|
||||
i40e_clean_xps_state(pf->vsi[v]);
|
||||
pf->vsi[v]->seid = 0;
|
||||
}
|
||||
}
|
||||
|
||||
i40e_shutdown_adminq(&pf->hw);
|
||||
|
@ -1578,6 +1578,7 @@ bool i40e_reset_vf(struct i40e_vf *vf, bool flr)
|
||||
i40e_cleanup_reset_vf(vf);
|
||||
|
||||
i40e_flush(hw);
|
||||
usleep_range(20000, 40000);
|
||||
clear_bit(I40E_VF_STATE_RESETTING, &vf->vf_states);
|
||||
|
||||
return true;
|
||||
@ -1701,6 +1702,7 @@ bool i40e_reset_all_vfs(struct i40e_pf *pf, bool flr)
|
||||
}
|
||||
|
||||
i40e_flush(hw);
|
||||
usleep_range(20000, 40000);
|
||||
clear_bit(__I40E_VF_DISABLE, pf->state);
|
||||
|
||||
return true;
|
||||
|
@ -1413,6 +1413,8 @@ static int igb_intr_test(struct igb_adapter *adapter, u64 *data)
|
||||
*data = 1;
|
||||
return -1;
|
||||
}
|
||||
wr32(E1000_IVAR_MISC, E1000_IVAR_VALID << 8);
|
||||
wr32(E1000_EIMS, BIT(0));
|
||||
} else if (adapter->flags & IGB_FLAG_HAS_MSI) {
|
||||
shared_int = false;
|
||||
if (request_irq(irq,
|
||||
|
@ -4271,7 +4271,7 @@ static void mvneta_percpu_elect(struct mvneta_port *pp)
|
||||
/* Use the cpu associated to the rxq when it is online, in all
|
||||
* the other cases, use the cpu 0 which can't be offline.
|
||||
*/
|
||||
if (cpu_online(pp->rxq_def))
|
||||
if (pp->rxq_def < nr_cpu_ids && cpu_online(pp->rxq_def))
|
||||
elected_cpu = pp->rxq_def;
|
||||
|
||||
max_cpu = num_present_cpus();
|
||||
|
@ -1134,7 +1134,12 @@ int otx2_init_tc(struct otx2_nic *nic)
|
||||
return err;
|
||||
|
||||
tc->flow_ht_params = tc_flow_ht_params;
|
||||
return rhashtable_init(&tc->flow_table, &tc->flow_ht_params);
|
||||
err = rhashtable_init(&tc->flow_table, &tc->flow_ht_params);
|
||||
if (err) {
|
||||
kfree(tc->tc_entries_bitmap);
|
||||
tc->tc_entries_bitmap = NULL;
|
||||
}
|
||||
return err;
|
||||
}
|
||||
EXPORT_SYMBOL(otx2_init_tc);
|
||||
|
||||
|
@ -359,7 +359,7 @@ static int regmap_encx24j600_phy_reg_read(void *context, unsigned int reg,
|
||||
goto err_out;
|
||||
|
||||
usleep_range(26, 100);
|
||||
while ((ret = regmap_read(ctx->regmap, MISTAT, &mistat) != 0) &&
|
||||
while (((ret = regmap_read(ctx->regmap, MISTAT, &mistat)) == 0) &&
|
||||
(mistat & BUSY))
|
||||
cpu_relax();
|
||||
|
||||
@ -397,7 +397,7 @@ static int regmap_encx24j600_phy_reg_write(void *context, unsigned int reg,
|
||||
goto err_out;
|
||||
|
||||
usleep_range(26, 100);
|
||||
while ((ret = regmap_read(ctx->regmap, MISTAT, &mistat) != 0) &&
|
||||
while (((ret = regmap_read(ctx->regmap, MISTAT, &mistat)) == 0) &&
|
||||
(mistat & BUSY))
|
||||
cpu_relax();
|
||||
|
||||
|
@ -317,7 +317,7 @@ int sparx5_fdma_xmit(struct sparx5 *sparx5, u32 *ifh, struct sk_buff *skb)
|
||||
next_dcb_hw = sparx5_fdma_next_dcb(tx, tx->curr_entry);
|
||||
db_hw = &next_dcb_hw->db[0];
|
||||
if (!(db_hw->status & FDMA_DCB_STATUS_DONE))
|
||||
tx->dropped++;
|
||||
return -EINVAL;
|
||||
db = list_first_entry(&tx->db_list, struct sparx5_db, list);
|
||||
list_move_tail(&db->list, &tx->db_list);
|
||||
next_dcb_hw->nextptr = FDMA_DCB_INVALID_DATA;
|
||||
|
@ -887,6 +887,8 @@ static int mchp_sparx5_probe(struct platform_device *pdev)
|
||||
|
||||
cleanup_ports:
|
||||
sparx5_cleanup_ports(sparx5);
|
||||
if (sparx5->mact_queue)
|
||||
destroy_workqueue(sparx5->mact_queue);
|
||||
cleanup_config:
|
||||
kfree(configs);
|
||||
cleanup_pnode:
|
||||
@ -911,6 +913,7 @@ static int mchp_sparx5_remove(struct platform_device *pdev)
|
||||
sparx5_cleanup_ports(sparx5);
|
||||
/* Unregister netdevs */
|
||||
sparx5_unregister_notifier_blocks(sparx5);
|
||||
destroy_workqueue(sparx5->mact_queue);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -234,9 +234,8 @@ netdev_tx_t sparx5_port_xmit_impl(struct sk_buff *skb, struct net_device *dev)
|
||||
sparx5_set_port_ifh(ifh, port->portno);
|
||||
|
||||
if (sparx5->ptp && skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP) {
|
||||
ret = sparx5_ptp_txtstamp_request(port, skb);
|
||||
if (ret)
|
||||
return ret;
|
||||
if (sparx5_ptp_txtstamp_request(port, skb) < 0)
|
||||
return NETDEV_TX_BUSY;
|
||||
|
||||
sparx5_set_port_ifh_rew_op(ifh, SPARX5_SKB_CB(skb)->rew_op);
|
||||
sparx5_set_port_ifh_pdu_type(ifh, SPARX5_SKB_CB(skb)->pdu_type);
|
||||
@ -250,23 +249,31 @@ netdev_tx_t sparx5_port_xmit_impl(struct sk_buff *skb, struct net_device *dev)
|
||||
else
|
||||
ret = sparx5_inject(sparx5, ifh, skb, dev);
|
||||
|
||||
if (ret == NETDEV_TX_OK) {
|
||||
stats->tx_bytes += skb->len;
|
||||
stats->tx_packets++;
|
||||
if (ret == -EBUSY)
|
||||
goto busy;
|
||||
if (ret < 0)
|
||||
goto drop;
|
||||
|
||||
if (skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP &&
|
||||
SPARX5_SKB_CB(skb)->rew_op == IFH_REW_OP_TWO_STEP_PTP)
|
||||
return ret;
|
||||
stats->tx_bytes += skb->len;
|
||||
stats->tx_packets++;
|
||||
sparx5->tx.packets++;
|
||||
|
||||
dev_kfree_skb_any(skb);
|
||||
} else {
|
||||
stats->tx_dropped++;
|
||||
if (skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP &&
|
||||
SPARX5_SKB_CB(skb)->rew_op == IFH_REW_OP_TWO_STEP_PTP)
|
||||
return NETDEV_TX_OK;
|
||||
|
||||
if (skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP &&
|
||||
SPARX5_SKB_CB(skb)->rew_op == IFH_REW_OP_TWO_STEP_PTP)
|
||||
sparx5_ptp_txtstamp_release(port, skb);
|
||||
}
|
||||
return ret;
|
||||
dev_consume_skb_any(skb);
|
||||
return NETDEV_TX_OK;
|
||||
drop:
|
||||
stats->tx_dropped++;
|
||||
sparx5->tx.dropped++;
|
||||
dev_kfree_skb_any(skb);
|
||||
return NETDEV_TX_OK;
|
||||
busy:
|
||||
if (skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP &&
|
||||
SPARX5_SKB_CB(skb)->rew_op == IFH_REW_OP_TWO_STEP_PTP)
|
||||
sparx5_ptp_txtstamp_release(port, skb);
|
||||
return NETDEV_TX_BUSY;
|
||||
}
|
||||
|
||||
static enum hrtimer_restart sparx5_injection_timeout(struct hrtimer *tmr)
|
||||
|
@ -498,7 +498,14 @@ enum {
|
||||
|
||||
#define GDMA_DRV_CAP_FLAG_1_EQ_SHARING_MULTI_VPORT BIT(0)
|
||||
|
||||
#define GDMA_DRV_CAP_FLAGS1 GDMA_DRV_CAP_FLAG_1_EQ_SHARING_MULTI_VPORT
|
||||
/* Advertise to the NIC firmware: the NAPI work_done variable race is fixed,
|
||||
* so the driver is able to reliably support features like busy_poll.
|
||||
*/
|
||||
#define GDMA_DRV_CAP_FLAG_1_NAPI_WKDONE_FIX BIT(2)
|
||||
|
||||
#define GDMA_DRV_CAP_FLAGS1 \
|
||||
(GDMA_DRV_CAP_FLAG_1_EQ_SHARING_MULTI_VPORT | \
|
||||
GDMA_DRV_CAP_FLAG_1_NAPI_WKDONE_FIX)
|
||||
|
||||
#define GDMA_DRV_CAP_FLAGS2 0
|
||||
|
||||
|
@ -1303,10 +1303,11 @@ static void mana_poll_rx_cq(struct mana_cq *cq)
|
||||
xdp_do_flush();
|
||||
}
|
||||
|
||||
static void mana_cq_handler(void *context, struct gdma_queue *gdma_queue)
|
||||
static int mana_cq_handler(void *context, struct gdma_queue *gdma_queue)
|
||||
{
|
||||
struct mana_cq *cq = context;
|
||||
u8 arm_bit;
|
||||
int w;
|
||||
|
||||
WARN_ON_ONCE(cq->gdma_cq != gdma_queue);
|
||||
|
||||
@ -1315,26 +1316,31 @@ static void mana_cq_handler(void *context, struct gdma_queue *gdma_queue)
|
||||
else
|
||||
mana_poll_tx_cq(cq);
|
||||
|
||||
if (cq->work_done < cq->budget &&
|
||||
napi_complete_done(&cq->napi, cq->work_done)) {
|
||||
w = cq->work_done;
|
||||
|
||||
if (w < cq->budget &&
|
||||
napi_complete_done(&cq->napi, w)) {
|
||||
arm_bit = SET_ARM_BIT;
|
||||
} else {
|
||||
arm_bit = 0;
|
||||
}
|
||||
|
||||
mana_gd_ring_cq(gdma_queue, arm_bit);
|
||||
|
||||
return w;
|
||||
}
|
||||
|
||||
static int mana_poll(struct napi_struct *napi, int budget)
|
||||
{
|
||||
struct mana_cq *cq = container_of(napi, struct mana_cq, napi);
|
||||
int w;
|
||||
|
||||
cq->work_done = 0;
|
||||
cq->budget = budget;
|
||||
|
||||
mana_cq_handler(cq, cq->gdma_cq);
|
||||
w = mana_cq_handler(cq, cq->gdma_cq);
|
||||
|
||||
return min(cq->work_done, budget);
|
||||
return min(w, budget);
|
||||
}
|
||||
|
||||
static void mana_schedule_napi(void *context, struct gdma_queue *gdma_queue)
|
||||
|
@ -282,7 +282,7 @@ netdev_tx_t nfp_nfdk_tx(struct sk_buff *skb, struct net_device *netdev)
|
||||
dma_len = skb_headlen(skb);
|
||||
if (skb_is_gso(skb))
|
||||
type = NFDK_DESC_TX_TYPE_TSO;
|
||||
else if (!nr_frags && dma_len < NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
else if (!nr_frags && dma_len <= NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
type = NFDK_DESC_TX_TYPE_SIMPLE;
|
||||
else
|
||||
type = NFDK_DESC_TX_TYPE_GATHER;
|
||||
@ -927,7 +927,7 @@ nfp_nfdk_tx_xdp_buf(struct nfp_net_dp *dp, struct nfp_net_rx_ring *rx_ring,
|
||||
dma_len = pkt_len;
|
||||
dma_addr = rxbuf->dma_addr + dma_off;
|
||||
|
||||
if (dma_len < NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
if (dma_len <= NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
type = NFDK_DESC_TX_TYPE_SIMPLE;
|
||||
else
|
||||
type = NFDK_DESC_TX_TYPE_GATHER;
|
||||
@ -1325,7 +1325,7 @@ nfp_nfdk_ctrl_tx_one(struct nfp_net *nn, struct nfp_net_r_vector *r_vec,
|
||||
txbuf = &tx_ring->ktxbufs[wr_idx];
|
||||
|
||||
dma_len = skb_headlen(skb);
|
||||
if (dma_len < NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
if (dma_len <= NFDK_TX_MAX_DATA_PER_HEAD)
|
||||
type = NFDK_DESC_TX_TYPE_SIMPLE;
|
||||
else
|
||||
type = NFDK_DESC_TX_TYPE_GATHER;
|
||||
|
@ -841,7 +841,7 @@ static bool ravb_rx_gbeth(struct net_device *ndev, int *quota, int q)
|
||||
napi_gro_receive(&priv->napi[q],
|
||||
priv->rx_1st_skb);
|
||||
stats->rx_packets++;
|
||||
stats->rx_bytes += priv->rx_1st_skb->len;
|
||||
stats->rx_bytes += pkt_len;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -108,10 +108,10 @@ static struct stmmac_axi *stmmac_axi_setup(struct platform_device *pdev)
|
||||
|
||||
axi->axi_lpi_en = of_property_read_bool(np, "snps,lpi_en");
|
||||
axi->axi_xit_frm = of_property_read_bool(np, "snps,xit_frm");
|
||||
axi->axi_kbbe = of_property_read_bool(np, "snps,axi_kbbe");
|
||||
axi->axi_fb = of_property_read_bool(np, "snps,axi_fb");
|
||||
axi->axi_mb = of_property_read_bool(np, "snps,axi_mb");
|
||||
axi->axi_rb = of_property_read_bool(np, "snps,axi_rb");
|
||||
axi->axi_kbbe = of_property_read_bool(np, "snps,kbbe");
|
||||
axi->axi_fb = of_property_read_bool(np, "snps,fb");
|
||||
axi->axi_mb = of_property_read_bool(np, "snps,mb");
|
||||
axi->axi_rb = of_property_read_bool(np, "snps,rb");
|
||||
|
||||
if (of_property_read_u32(np, "snps,wr_osr_lmt", &axi->axi_wr_osr_lmt))
|
||||
axi->axi_wr_osr_lmt = 1;
|
||||
|
@ -1454,7 +1454,7 @@ static void am65_cpsw_nuss_mac_link_up(struct phylink_config *config, struct phy
|
||||
|
||||
if (speed == SPEED_1000)
|
||||
mac_control |= CPSW_SL_CTL_GIG;
|
||||
if (speed == SPEED_10 && interface == PHY_INTERFACE_MODE_RGMII)
|
||||
if (speed == SPEED_10 && phy_interface_mode_is_rgmii(interface))
|
||||
/* Can be used with in band mode only */
|
||||
mac_control |= CPSW_SL_CTL_EXT_EN;
|
||||
if (speed == SPEED_100 && interface == PHY_INTERFACE_MODE_RMII)
|
||||
|
@ -885,7 +885,7 @@ static int ca8210_spi_transfer(
|
||||
|
||||
dev_dbg(&spi->dev, "%s called\n", __func__);
|
||||
|
||||
cas_ctl = kmalloc(sizeof(*cas_ctl), GFP_ATOMIC);
|
||||
cas_ctl = kzalloc(sizeof(*cas_ctl), GFP_ATOMIC);
|
||||
if (!cas_ctl)
|
||||
return -ENOMEM;
|
||||
|
||||
|
@ -970,7 +970,7 @@ static int cc2520_hw_init(struct cc2520_private *priv)
|
||||
|
||||
if (timeout-- <= 0) {
|
||||
dev_err(&priv->spi->dev, "oscillator start failed!\n");
|
||||
return ret;
|
||||
return -ETIMEDOUT;
|
||||
}
|
||||
udelay(1);
|
||||
} while (!(status & CC2520_STATUS_XOSC32M_STABLE));
|
||||
|
@ -3698,6 +3698,7 @@ static const struct nla_policy macsec_rtnl_policy[IFLA_MACSEC_MAX + 1] = {
|
||||
[IFLA_MACSEC_SCB] = { .type = NLA_U8 },
|
||||
[IFLA_MACSEC_REPLAY_PROTECT] = { .type = NLA_U8 },
|
||||
[IFLA_MACSEC_VALIDATION] = { .type = NLA_U8 },
|
||||
[IFLA_MACSEC_OFFLOAD] = { .type = NLA_U8 },
|
||||
};
|
||||
|
||||
static void macsec_free_netdev(struct net_device *dev)
|
||||
|
@ -98,6 +98,7 @@ int fwnode_mdiobus_phy_device_register(struct mii_bus *mdio,
|
||||
*/
|
||||
rc = phy_device_register(phy);
|
||||
if (rc) {
|
||||
device_set_node(&phy->mdio.dev, NULL);
|
||||
fwnode_handle_put(child);
|
||||
return rc;
|
||||
}
|
||||
@ -153,7 +154,8 @@ int fwnode_mdiobus_register_phy(struct mii_bus *bus,
|
||||
/* All data is now stored in the phy struct, so register it */
|
||||
rc = phy_device_register(phy);
|
||||
if (rc) {
|
||||
fwnode_handle_put(phy->mdio.dev.fwnode);
|
||||
phy->mdio.dev.fwnode = NULL;
|
||||
fwnode_handle_put(child);
|
||||
goto clean_phy;
|
||||
}
|
||||
} else if (is_of_node(child)) {
|
||||
|
@ -68,8 +68,9 @@ static int of_mdiobus_register_device(struct mii_bus *mdio,
|
||||
/* All data is now stored in the mdiodev struct; register it. */
|
||||
rc = mdio_device_register(mdiodev);
|
||||
if (rc) {
|
||||
device_set_node(&mdiodev->dev, NULL);
|
||||
fwnode_handle_put(fwnode);
|
||||
mdio_device_free(mdiodev);
|
||||
of_node_put(child);
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
@ -21,6 +21,7 @@
|
||||
#include <linux/slab.h>
|
||||
#include <linux/string.h>
|
||||
#include <linux/unistd.h>
|
||||
#include <linux/property.h>
|
||||
|
||||
void mdio_device_free(struct mdio_device *mdiodev)
|
||||
{
|
||||
@ -30,6 +31,7 @@ EXPORT_SYMBOL(mdio_device_free);
|
||||
|
||||
static void mdio_device_release(struct device *dev)
|
||||
{
|
||||
fwnode_handle_put(dev->fwnode);
|
||||
kfree(to_mdio_device(dev));
|
||||
}
|
||||
|
||||
|
@ -9,6 +9,7 @@
|
||||
#include <linux/module.h>
|
||||
#include <linux/bitfield.h>
|
||||
#include <linux/hwmon.h>
|
||||
#include <linux/mutex.h>
|
||||
#include <linux/phy.h>
|
||||
#include <linux/polynomial.h>
|
||||
#include <linux/netdevice.h>
|
||||
@ -70,6 +71,14 @@
|
||||
#define VPSPEC1_TEMP_STA 0x0E
|
||||
#define VPSPEC1_TEMP_STA_DATA GENMASK(9, 0)
|
||||
|
||||
/* Mailbox */
|
||||
#define VSPEC1_MBOX_DATA 0x5
|
||||
#define VSPEC1_MBOX_ADDRLO 0x6
|
||||
#define VSPEC1_MBOX_CMD 0x7
|
||||
#define VSPEC1_MBOX_CMD_ADDRHI GENMASK(7, 0)
|
||||
#define VSPEC1_MBOX_CMD_RD (0 << 8)
|
||||
#define VSPEC1_MBOX_CMD_READY BIT(15)
|
||||
|
||||
/* WoL */
|
||||
#define VPSPEC2_WOL_CTL 0x0E06
|
||||
#define VPSPEC2_WOL_AD01 0x0E08
|
||||
@ -77,7 +86,13 @@
|
||||
#define VPSPEC2_WOL_AD45 0x0E0A
|
||||
#define WOL_EN BIT(0)
|
||||
|
||||
/* Internal registers, access via mbox */
|
||||
#define REG_GPIO0_OUT 0xd3ce00
|
||||
|
||||
struct gpy_priv {
|
||||
/* serialize mailbox acesses */
|
||||
struct mutex mbox_lock;
|
||||
|
||||
u8 fw_major;
|
||||
u8 fw_minor;
|
||||
};
|
||||
@ -187,6 +202,45 @@ static int gpy_hwmon_register(struct phy_device *phydev)
|
||||
}
|
||||
#endif
|
||||
|
||||
static int gpy_mbox_read(struct phy_device *phydev, u32 addr)
|
||||
{
|
||||
struct gpy_priv *priv = phydev->priv;
|
||||
int val, ret;
|
||||
u16 cmd;
|
||||
|
||||
mutex_lock(&priv->mbox_lock);
|
||||
|
||||
ret = phy_write_mmd(phydev, MDIO_MMD_VEND1, VSPEC1_MBOX_ADDRLO,
|
||||
addr);
|
||||
if (ret)
|
||||
goto out;
|
||||
|
||||
cmd = VSPEC1_MBOX_CMD_RD;
|
||||
cmd |= FIELD_PREP(VSPEC1_MBOX_CMD_ADDRHI, addr >> 16);
|
||||
|
||||
ret = phy_write_mmd(phydev, MDIO_MMD_VEND1, VSPEC1_MBOX_CMD, cmd);
|
||||
if (ret)
|
||||
goto out;
|
||||
|
||||
/* The mbox read is used in the interrupt workaround. It was observed
|
||||
* that a read might take up to 2.5ms. This is also the time for which
|
||||
* the interrupt line is stuck low. To be on the safe side, poll the
|
||||
* ready bit for 10ms.
|
||||
*/
|
||||
ret = phy_read_mmd_poll_timeout(phydev, MDIO_MMD_VEND1,
|
||||
VSPEC1_MBOX_CMD, val,
|
||||
(val & VSPEC1_MBOX_CMD_READY),
|
||||
500, 10000, false);
|
||||
if (ret)
|
||||
goto out;
|
||||
|
||||
ret = phy_read_mmd(phydev, MDIO_MMD_VEND1, VSPEC1_MBOX_DATA);
|
||||
|
||||
out:
|
||||
mutex_unlock(&priv->mbox_lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int gpy_config_init(struct phy_device *phydev)
|
||||
{
|
||||
int ret;
|
||||
@ -201,6 +255,13 @@ static int gpy_config_init(struct phy_device *phydev)
|
||||
return ret < 0 ? ret : 0;
|
||||
}
|
||||
|
||||
static bool gpy_has_broken_mdint(struct phy_device *phydev)
|
||||
{
|
||||
/* At least these PHYs are known to have broken interrupt handling */
|
||||
return phydev->drv->phy_id == PHY_ID_GPY215B ||
|
||||
phydev->drv->phy_id == PHY_ID_GPY215C;
|
||||
}
|
||||
|
||||
static int gpy_probe(struct phy_device *phydev)
|
||||
{
|
||||
struct device *dev = &phydev->mdio.dev;
|
||||
@ -218,6 +279,7 @@ static int gpy_probe(struct phy_device *phydev)
|
||||
if (!priv)
|
||||
return -ENOMEM;
|
||||
phydev->priv = priv;
|
||||
mutex_init(&priv->mbox_lock);
|
||||
|
||||
fw_version = phy_read(phydev, PHY_FWV);
|
||||
if (fw_version < 0)
|
||||
@ -492,6 +554,29 @@ static irqreturn_t gpy_handle_interrupt(struct phy_device *phydev)
|
||||
if (!(reg & PHY_IMASK_MASK))
|
||||
return IRQ_NONE;
|
||||
|
||||
/* The PHY might leave the interrupt line asserted even after PHY_ISTAT
|
||||
* is read. To avoid interrupt storms, delay the interrupt handling as
|
||||
* long as the PHY drives the interrupt line. An internal bus read will
|
||||
* stall as long as the interrupt line is asserted, thus just read a
|
||||
* random register here.
|
||||
* Because we cannot access the internal bus at all while the interrupt
|
||||
* is driven by the PHY, there is no way to make the interrupt line
|
||||
* unstuck (e.g. by changing the pinmux to GPIO input) during that time
|
||||
* frame. Therefore, polling is the best we can do and won't do any more
|
||||
* harm.
|
||||
* It was observed that this bug happens on link state and link speed
|
||||
* changes on a GPY215B and GYP215C independent of the firmware version
|
||||
* (which doesn't mean that this list is exhaustive).
|
||||
*/
|
||||
if (gpy_has_broken_mdint(phydev) &&
|
||||
(reg & (PHY_IMASK_LSTC | PHY_IMASK_LSPC))) {
|
||||
reg = gpy_mbox_read(phydev, REG_GPIO0_OUT);
|
||||
if (reg < 0) {
|
||||
phy_error(phydev);
|
||||
return IRQ_NONE;
|
||||
}
|
||||
}
|
||||
|
||||
phy_trigger_machine(phydev);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
|
@ -450,12 +450,12 @@ plip_bh_timeout_error(struct net_device *dev, struct net_local *nl,
|
||||
}
|
||||
rcv->state = PLIP_PK_DONE;
|
||||
if (rcv->skb) {
|
||||
kfree_skb(rcv->skb);
|
||||
dev_kfree_skb_irq(rcv->skb);
|
||||
rcv->skb = NULL;
|
||||
}
|
||||
snd->state = PLIP_PK_DONE;
|
||||
if (snd->skb) {
|
||||
dev_kfree_skb(snd->skb);
|
||||
dev_consume_skb_irq(snd->skb);
|
||||
snd->skb = NULL;
|
||||
}
|
||||
spin_unlock_irq(&nl->lock);
|
||||
|
@ -914,6 +914,7 @@ static int tbnet_open(struct net_device *dev)
|
||||
eof_mask, tbnet_start_poll, net);
|
||||
if (!ring) {
|
||||
netdev_err(dev, "failed to allocate Rx ring\n");
|
||||
tb_xdomain_release_out_hopid(xd, hopid);
|
||||
tb_ring_free(net->tx_ring.ring);
|
||||
net->tx_ring.ring = NULL;
|
||||
return -ENOMEM;
|
||||
|
@ -75,8 +75,14 @@ vmxnet3_enable_all_intrs(struct vmxnet3_adapter *adapter)
|
||||
|
||||
for (i = 0; i < adapter->intr.num_intrs; i++)
|
||||
vmxnet3_enable_intr(adapter, i);
|
||||
adapter->shared->devRead.intrConf.intrCtrl &=
|
||||
if (!VMXNET3_VERSION_GE_6(adapter) ||
|
||||
!adapter->queuesExtEnabled) {
|
||||
adapter->shared->devRead.intrConf.intrCtrl &=
|
||||
cpu_to_le32(~VMXNET3_IC_DISABLE_ALL);
|
||||
} else {
|
||||
adapter->shared->devReadExt.intrConfExt.intrCtrl &=
|
||||
cpu_to_le32(~VMXNET3_IC_DISABLE_ALL);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -85,8 +91,14 @@ vmxnet3_disable_all_intrs(struct vmxnet3_adapter *adapter)
|
||||
{
|
||||
int i;
|
||||
|
||||
adapter->shared->devRead.intrConf.intrCtrl |=
|
||||
if (!VMXNET3_VERSION_GE_6(adapter) ||
|
||||
!adapter->queuesExtEnabled) {
|
||||
adapter->shared->devRead.intrConf.intrCtrl |=
|
||||
cpu_to_le32(VMXNET3_IC_DISABLE_ALL);
|
||||
} else {
|
||||
adapter->shared->devReadExt.intrConfExt.intrCtrl |=
|
||||
cpu_to_le32(VMXNET3_IC_DISABLE_ALL);
|
||||
}
|
||||
for (i = 0; i < adapter->intr.num_intrs; i++)
|
||||
vmxnet3_disable_intr(adapter, i);
|
||||
}
|
||||
@ -1396,6 +1408,7 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq,
|
||||
};
|
||||
u32 num_pkts = 0;
|
||||
bool skip_page_frags = false;
|
||||
bool encap_lro = false;
|
||||
struct Vmxnet3_RxCompDesc *rcd;
|
||||
struct vmxnet3_rx_ctx *ctx = &rq->rx_ctx;
|
||||
u16 segCnt = 0, mss = 0;
|
||||
@ -1556,13 +1569,18 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq,
|
||||
if (VMXNET3_VERSION_GE_2(adapter) &&
|
||||
rcd->type == VMXNET3_CDTYPE_RXCOMP_LRO) {
|
||||
struct Vmxnet3_RxCompDescExt *rcdlro;
|
||||
union Vmxnet3_GenericDesc *gdesc;
|
||||
|
||||
rcdlro = (struct Vmxnet3_RxCompDescExt *)rcd;
|
||||
gdesc = (union Vmxnet3_GenericDesc *)rcd;
|
||||
|
||||
segCnt = rcdlro->segCnt;
|
||||
WARN_ON_ONCE(segCnt == 0);
|
||||
mss = rcdlro->mss;
|
||||
if (unlikely(segCnt <= 1))
|
||||
segCnt = 0;
|
||||
encap_lro = (le32_to_cpu(gdesc->dword[0]) &
|
||||
(1UL << VMXNET3_RCD_HDR_INNER_SHIFT));
|
||||
} else {
|
||||
segCnt = 0;
|
||||
}
|
||||
@ -1630,7 +1648,7 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq,
|
||||
vmxnet3_rx_csum(adapter, skb,
|
||||
(union Vmxnet3_GenericDesc *)rcd);
|
||||
skb->protocol = eth_type_trans(skb, adapter->netdev);
|
||||
if (!rcd->tcp ||
|
||||
if ((!rcd->tcp && !encap_lro) ||
|
||||
!(adapter->netdev->features & NETIF_F_LRO))
|
||||
goto not_lro;
|
||||
|
||||
@ -1639,7 +1657,7 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq,
|
||||
SKB_GSO_TCPV4 : SKB_GSO_TCPV6;
|
||||
skb_shinfo(skb)->gso_size = mss;
|
||||
skb_shinfo(skb)->gso_segs = segCnt;
|
||||
} else if (segCnt != 0 || skb->len > mtu) {
|
||||
} else if ((segCnt != 0 || skb->len > mtu) && !encap_lro) {
|
||||
u32 hlen;
|
||||
|
||||
hlen = vmxnet3_get_hdr_len(adapter, skb,
|
||||
@ -1668,6 +1686,7 @@ vmxnet3_rq_rx_complete(struct vmxnet3_rx_queue *rq,
|
||||
napi_gro_receive(&rq->napi, skb);
|
||||
|
||||
ctx->skb = NULL;
|
||||
encap_lro = false;
|
||||
num_pkts++;
|
||||
}
|
||||
|
||||
|
@ -332,6 +332,7 @@ struct iosm_mux *ipc_mux_init(struct ipc_mux_config *mux_cfg,
|
||||
if (!ipc_mux->ul_adb.pp_qlt[i]) {
|
||||
for (j = i - 1; j >= 0; j--)
|
||||
kfree(ipc_mux->ul_adb.pp_qlt[j]);
|
||||
kfree(ipc_mux);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
@ -530,7 +530,7 @@ static int xenvif_tx_check_gop(struct xenvif_queue *queue,
|
||||
const bool sharedslot = nr_frags &&
|
||||
frag_get_pending_idx(&shinfo->frags[0]) ==
|
||||
copy_pending_idx(skb, copy_count(skb) - 1);
|
||||
int i, err;
|
||||
int i, err = 0;
|
||||
|
||||
for (i = 0; i < copy_count(skb); i++) {
|
||||
int newerr;
|
||||
|
@ -1862,6 +1862,12 @@ static int netfront_resume(struct xenbus_device *dev)
|
||||
netif_tx_unlock_bh(info->netdev);
|
||||
|
||||
xennet_disconnect_backend(info);
|
||||
|
||||
rtnl_lock();
|
||||
if (info->queues)
|
||||
xennet_destroy_queues(info);
|
||||
rtnl_unlock();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -3095,10 +3095,6 @@ static int nvme_init_identify(struct nvme_ctrl *ctrl)
|
||||
if (!ctrl->identified) {
|
||||
unsigned int i;
|
||||
|
||||
ret = nvme_init_subsystem(ctrl, id);
|
||||
if (ret)
|
||||
goto out_free;
|
||||
|
||||
/*
|
||||
* Check for quirks. Quirk can depend on firmware version,
|
||||
* so, in principle, the set of quirks present can change
|
||||
@ -3111,6 +3107,10 @@ static int nvme_init_identify(struct nvme_ctrl *ctrl)
|
||||
if (quirk_matches(id, &core_quirks[i]))
|
||||
ctrl->quirks |= core_quirks[i].quirks;
|
||||
}
|
||||
|
||||
ret = nvme_init_subsystem(ctrl, id);
|
||||
if (ret)
|
||||
goto out_free;
|
||||
}
|
||||
memcpy(ctrl->subsys->firmware_rev, id->fr,
|
||||
sizeof(ctrl->subsys->firmware_rev));
|
||||
|
@ -758,7 +758,6 @@ static void qeth_l2_br2dev_worker(struct work_struct *work)
|
||||
struct list_head *iter;
|
||||
int err = 0;
|
||||
|
||||
kfree(br2dev_event_work);
|
||||
QETH_CARD_TEXT_(card, 4, "b2dw%04lx", event);
|
||||
QETH_CARD_TEXT_(card, 4, "ma%012llx", ether_addr_to_u64(addr));
|
||||
|
||||
@ -815,6 +814,7 @@ static void qeth_l2_br2dev_worker(struct work_struct *work)
|
||||
dev_put(brdev);
|
||||
dev_put(lsyncdev);
|
||||
dev_put(dstdev);
|
||||
kfree(br2dev_event_work);
|
||||
}
|
||||
|
||||
static int qeth_l2_br2dev_queue_work(struct net_device *brdev,
|
||||
|
@ -68,6 +68,7 @@ struct css_task_iter {
|
||||
struct list_head iters_node; /* css_set->task_iters */
|
||||
};
|
||||
|
||||
extern struct file_system_type cgroup_fs_type;
|
||||
extern struct cgroup_root cgrp_dfl_root;
|
||||
extern struct css_set init_css_set;
|
||||
|
||||
|
@ -33,11 +33,13 @@
|
||||
* can use the extra bits to store other information besides PFN.
|
||||
*/
|
||||
#ifdef MAX_PHYSMEM_BITS
|
||||
#define SWP_PFN_BITS (MAX_PHYSMEM_BITS - PAGE_SHIFT)
|
||||
#define SWP_PFN_BITS (MAX_PHYSMEM_BITS - PAGE_SHIFT)
|
||||
#else /* MAX_PHYSMEM_BITS */
|
||||
#define SWP_PFN_BITS (BITS_PER_LONG - PAGE_SHIFT)
|
||||
#define SWP_PFN_BITS min_t(int, \
|
||||
sizeof(phys_addr_t) * 8 - PAGE_SHIFT, \
|
||||
SWP_TYPE_SHIFT)
|
||||
#endif /* MAX_PHYSMEM_BITS */
|
||||
#define SWP_PFN_MASK (BIT(SWP_PFN_BITS) - 1)
|
||||
#define SWP_PFN_MASK (BIT(SWP_PFN_BITS) - 1)
|
||||
|
||||
/**
|
||||
* Migration swap entry specific bitfield definitions. Layout:
|
||||
|
@ -228,6 +228,17 @@ enum {
|
||||
*/
|
||||
HCI_QUIRK_VALID_LE_STATES,
|
||||
|
||||
/* When this quirk is set, then erroneous data reporting
|
||||
* is ignored. This is mainly due to the fact that the HCI
|
||||
* Read Default Erroneous Data Reporting command is advertised,
|
||||
* but not supported; these controllers often reply with unknown
|
||||
* command and tend to lock up randomly. Needing a hard reset.
|
||||
*
|
||||
* This quirk can be set before hci_register_dev is called or
|
||||
* during the hdev->setup vendor callback.
|
||||
*/
|
||||
HCI_QUIRK_BROKEN_ERR_DATA_REPORTING,
|
||||
|
||||
/*
|
||||
* When this quirk is set, then the hci_suspend_notifier is not
|
||||
* registered. This is intended for devices which drop completely
|
||||
@ -1424,7 +1435,6 @@ struct hci_std_codecs_v2 {
|
||||
} __packed;
|
||||
|
||||
struct hci_vnd_codec_v2 {
|
||||
__u8 id;
|
||||
__le16 cid;
|
||||
__le16 vid;
|
||||
__u8 transport;
|
||||
|
@ -16,9 +16,6 @@
|
||||
#define PING_HTABLE_SIZE 64
|
||||
#define PING_HTABLE_MASK (PING_HTABLE_SIZE-1)
|
||||
|
||||
#define ping_portaddr_for_each_entry(__sk, node, list) \
|
||||
hlist_nulls_for_each_entry(__sk, node, list, sk_nulls_node)
|
||||
|
||||
/*
|
||||
* gid_t is either uint or ushort. We want to pass it to
|
||||
* proc_dointvec_minmax(), so it must not be larger than MAX_INT
|
||||
|
@ -2707,8 +2707,10 @@ static __cold void io_tctx_exit_cb(struct callback_head *cb)
|
||||
/*
|
||||
* When @in_idle, we're in cancellation and it's racy to remove the
|
||||
* node. It'll be removed by the end of cancellation, just ignore it.
|
||||
* tctx can be NULL if the queueing of this task_work raced with
|
||||
* work cancelation off the exec path.
|
||||
*/
|
||||
if (!atomic_read(&tctx->in_idle))
|
||||
if (tctx && !atomic_read(&tctx->in_idle))
|
||||
io_uring_del_tctx_node((unsigned long)work->ctx);
|
||||
complete(&work->completion);
|
||||
}
|
||||
|
@ -167,7 +167,6 @@ struct cgroup_mgctx {
|
||||
extern spinlock_t css_set_lock;
|
||||
extern struct cgroup_subsys *cgroup_subsys[];
|
||||
extern struct list_head cgroup_roots;
|
||||
extern struct file_system_type cgroup_fs_type;
|
||||
|
||||
/* iterate across the hierarchies */
|
||||
#define for_each_root(root) \
|
||||
|
2
mm/gup.c
2
mm/gup.c
@ -2852,7 +2852,7 @@ static int gup_pud_range(p4d_t *p4dp, p4d_t p4d, unsigned long addr, unsigned lo
|
||||
next = pud_addr_end(addr, end);
|
||||
if (unlikely(!pud_present(pud)))
|
||||
return 0;
|
||||
if (unlikely(pud_huge(pud))) {
|
||||
if (unlikely(pud_huge(pud) || pud_devmap(pud))) {
|
||||
if (!gup_huge_pud(pud, pudp, addr, next, flags,
|
||||
pages, nr))
|
||||
return 0;
|
||||
|
@ -4832,6 +4832,7 @@ static ssize_t memcg_write_event_control(struct kernfs_open_file *of,
|
||||
unsigned int efd, cfd;
|
||||
struct fd efile;
|
||||
struct fd cfile;
|
||||
struct dentry *cdentry;
|
||||
const char *name;
|
||||
char *endp;
|
||||
int ret;
|
||||
@ -4885,6 +4886,16 @@ static ssize_t memcg_write_event_control(struct kernfs_open_file *of,
|
||||
if (ret < 0)
|
||||
goto out_put_cfile;
|
||||
|
||||
/*
|
||||
* The control file must be a regular cgroup1 file. As a regular cgroup
|
||||
* file can't be renamed, it's safe to access its name afterwards.
|
||||
*/
|
||||
cdentry = cfile.file->f_path.dentry;
|
||||
if (cdentry->d_sb->s_type != &cgroup_fs_type || !d_is_reg(cdentry)) {
|
||||
ret = -EINVAL;
|
||||
goto out_put_cfile;
|
||||
}
|
||||
|
||||
/*
|
||||
* Determine the event callbacks and set them in @event. This used
|
||||
* to be done via struct cftype but cgroup core no longer knows
|
||||
@ -4893,7 +4904,7 @@ static ssize_t memcg_write_event_control(struct kernfs_open_file *of,
|
||||
*
|
||||
* DO NOT ADD NEW FILES.
|
||||
*/
|
||||
name = cfile.file->f_path.dentry->d_name.name;
|
||||
name = cdentry->d_name.name;
|
||||
|
||||
if (!strcmp(name, "memory.usage_in_bytes")) {
|
||||
event->register_event = mem_cgroup_usage_register_event;
|
||||
@ -4917,7 +4928,7 @@ static ssize_t memcg_write_event_control(struct kernfs_open_file *of,
|
||||
* automatically removed on cgroup destruction but the removal is
|
||||
* asynchronous, so take an extra ref on @css.
|
||||
*/
|
||||
cfile_css = css_tryget_online_from_dir(cfile.file->f_path.dentry->d_parent,
|
||||
cfile_css = css_tryget_online_from_dir(cdentry->d_parent,
|
||||
&memory_cgrp_subsys);
|
||||
ret = -EINVAL;
|
||||
if (IS_ERR(cfile_css))
|
||||
|
14
mm/mmap.c
14
mm/mmap.c
@ -226,8 +226,7 @@ SYSCALL_DEFINE1(brk, unsigned long, brk)
|
||||
/* Search one past newbrk */
|
||||
mas_set(&mas, newbrk);
|
||||
brkvma = mas_find(&mas, oldbrk);
|
||||
BUG_ON(brkvma == NULL);
|
||||
if (brkvma->vm_start >= oldbrk)
|
||||
if (!brkvma || brkvma->vm_start >= oldbrk)
|
||||
goto out; /* mapping intersects with an existing non-brk vma. */
|
||||
/*
|
||||
* mm->brk must be protected by write mmap_lock.
|
||||
@ -2947,9 +2946,9 @@ static int do_brk_flags(struct ma_state *mas, struct vm_area_struct *vma,
|
||||
* Expand the existing vma if possible; Note that singular lists do not
|
||||
* occur after forking, so the expand will only happen on new VMAs.
|
||||
*/
|
||||
if (vma &&
|
||||
(!vma->anon_vma || list_is_singular(&vma->anon_vma_chain)) &&
|
||||
((vma->vm_flags & ~VM_SOFTDIRTY) == flags)) {
|
||||
if (vma && vma->vm_end == addr && !vma_policy(vma) &&
|
||||
can_vma_merge_after(vma, flags, NULL, NULL,
|
||||
addr >> PAGE_SHIFT, NULL_VM_UFFD_CTX, NULL)) {
|
||||
mas_set_range(mas, vma->vm_start, addr + len - 1);
|
||||
if (mas_preallocate(mas, vma, GFP_KERNEL))
|
||||
return -ENOMEM;
|
||||
@ -3036,11 +3035,6 @@ int vm_brk_flags(unsigned long addr, unsigned long request, unsigned long flags)
|
||||
goto munmap_failed;
|
||||
|
||||
vma = mas_prev(&mas, 0);
|
||||
if (!vma || vma->vm_end != addr || vma_policy(vma) ||
|
||||
!can_vma_merge_after(vma, flags, NULL, NULL,
|
||||
addr >> PAGE_SHIFT, NULL_VM_UFFD_CTX, NULL))
|
||||
vma = NULL;
|
||||
|
||||
ret = do_brk_flags(&mas, vma, addr, len, flags);
|
||||
populate = ((mm->def_flags & VM_LOCKED) != 0);
|
||||
mmap_write_unlock(mm);
|
||||
|
11
mm/shmem.c
11
mm/shmem.c
@ -948,6 +948,15 @@ static void shmem_undo_range(struct inode *inode, loff_t lstart, loff_t lend,
|
||||
index++;
|
||||
}
|
||||
|
||||
/*
|
||||
* When undoing a failed fallocate, we want none of the partial folio
|
||||
* zeroing and splitting below, but shall want to truncate the whole
|
||||
* folio when !uptodate indicates that it was added by this fallocate,
|
||||
* even when [lstart, lend] covers only a part of the folio.
|
||||
*/
|
||||
if (unfalloc)
|
||||
goto whole_folios;
|
||||
|
||||
same_folio = (lstart >> PAGE_SHIFT) == (lend >> PAGE_SHIFT);
|
||||
folio = shmem_get_partial_folio(inode, lstart >> PAGE_SHIFT);
|
||||
if (folio) {
|
||||
@ -973,6 +982,8 @@ static void shmem_undo_range(struct inode *inode, loff_t lstart, loff_t lend,
|
||||
folio_put(folio);
|
||||
}
|
||||
|
||||
whole_folios:
|
||||
|
||||
index = start;
|
||||
while (index < end) {
|
||||
cond_resched();
|
||||
|
@ -972,6 +972,7 @@ static int get_l2cap_conn(char *buf, bdaddr_t *addr, u8 *addr_type,
|
||||
hci_dev_lock(hdev);
|
||||
hcon = hci_conn_hash_lookup_le(hdev, addr, *addr_type);
|
||||
hci_dev_unlock(hdev);
|
||||
hci_dev_put(hdev);
|
||||
|
||||
if (!hcon)
|
||||
return -ENOENT;
|
||||
|
@ -737,7 +737,7 @@ static int __init bt_init(void)
|
||||
|
||||
err = bt_sysfs_init();
|
||||
if (err < 0)
|
||||
return err;
|
||||
goto cleanup_led;
|
||||
|
||||
err = sock_register(&bt_sock_family_ops);
|
||||
if (err)
|
||||
@ -773,6 +773,8 @@ static int __init bt_init(void)
|
||||
sock_unregister(PF_BLUETOOTH);
|
||||
cleanup_sysfs:
|
||||
bt_sysfs_cleanup();
|
||||
cleanup_led:
|
||||
bt_leds_cleanup();
|
||||
return err;
|
||||
}
|
||||
|
||||
|
@ -72,9 +72,8 @@ static void hci_read_codec_capabilities(struct hci_dev *hdev, __u8 transport,
|
||||
continue;
|
||||
}
|
||||
|
||||
skb = __hci_cmd_sync(hdev, HCI_OP_READ_LOCAL_CODEC_CAPS,
|
||||
sizeof(*cmd), cmd,
|
||||
HCI_CMD_TIMEOUT);
|
||||
skb = __hci_cmd_sync_sk(hdev, HCI_OP_READ_LOCAL_CODEC_CAPS,
|
||||
sizeof(*cmd), cmd, 0, HCI_CMD_TIMEOUT, NULL);
|
||||
if (IS_ERR(skb)) {
|
||||
bt_dev_err(hdev, "Failed to read codec capabilities (%ld)",
|
||||
PTR_ERR(skb));
|
||||
@ -127,8 +126,8 @@ void hci_read_supported_codecs(struct hci_dev *hdev)
|
||||
struct hci_op_read_local_codec_caps caps;
|
||||
__u8 i;
|
||||
|
||||
skb = __hci_cmd_sync(hdev, HCI_OP_READ_LOCAL_CODECS, 0, NULL,
|
||||
HCI_CMD_TIMEOUT);
|
||||
skb = __hci_cmd_sync_sk(hdev, HCI_OP_READ_LOCAL_CODECS, 0, NULL,
|
||||
0, HCI_CMD_TIMEOUT, NULL);
|
||||
|
||||
if (IS_ERR(skb)) {
|
||||
bt_dev_err(hdev, "Failed to read local supported codecs (%ld)",
|
||||
@ -158,7 +157,8 @@ void hci_read_supported_codecs(struct hci_dev *hdev)
|
||||
for (i = 0; i < std_codecs->num; i++) {
|
||||
caps.id = std_codecs->codec[i];
|
||||
caps.direction = 0x00;
|
||||
hci_read_codec_capabilities(hdev, LOCAL_CODEC_ACL_MASK, &caps);
|
||||
hci_read_codec_capabilities(hdev,
|
||||
LOCAL_CODEC_ACL_MASK | LOCAL_CODEC_SCO_MASK, &caps);
|
||||
}
|
||||
|
||||
skb_pull(skb, flex_array_size(std_codecs, codec, std_codecs->num)
|
||||
@ -178,7 +178,8 @@ void hci_read_supported_codecs(struct hci_dev *hdev)
|
||||
caps.cid = vnd_codecs->codec[i].cid;
|
||||
caps.vid = vnd_codecs->codec[i].vid;
|
||||
caps.direction = 0x00;
|
||||
hci_read_codec_capabilities(hdev, LOCAL_CODEC_ACL_MASK, &caps);
|
||||
hci_read_codec_capabilities(hdev,
|
||||
LOCAL_CODEC_ACL_MASK | LOCAL_CODEC_SCO_MASK, &caps);
|
||||
}
|
||||
|
||||
error:
|
||||
@ -194,8 +195,8 @@ void hci_read_supported_codecs_v2(struct hci_dev *hdev)
|
||||
struct hci_op_read_local_codec_caps caps;
|
||||
__u8 i;
|
||||
|
||||
skb = __hci_cmd_sync(hdev, HCI_OP_READ_LOCAL_CODECS_V2, 0, NULL,
|
||||
HCI_CMD_TIMEOUT);
|
||||
skb = __hci_cmd_sync_sk(hdev, HCI_OP_READ_LOCAL_CODECS_V2, 0, NULL,
|
||||
0, HCI_CMD_TIMEOUT, NULL);
|
||||
|
||||
if (IS_ERR(skb)) {
|
||||
bt_dev_err(hdev, "Failed to read local supported codecs (%ld)",
|
||||
|
@ -2764,7 +2764,8 @@ int hci_register_suspend_notifier(struct hci_dev *hdev)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
if (!test_bit(HCI_QUIRK_NO_SUSPEND_NOTIFIER, &hdev->quirks)) {
|
||||
if (!hdev->suspend_notifier.notifier_call &&
|
||||
!test_bit(HCI_QUIRK_NO_SUSPEND_NOTIFIER, &hdev->quirks)) {
|
||||
hdev->suspend_notifier.notifier_call = hci_suspend_notifier;
|
||||
ret = register_pm_notifier(&hdev->suspend_notifier);
|
||||
}
|
||||
@ -2776,8 +2777,11 @@ int hci_unregister_suspend_notifier(struct hci_dev *hdev)
|
||||
{
|
||||
int ret = 0;
|
||||
|
||||
if (!test_bit(HCI_QUIRK_NO_SUSPEND_NOTIFIER, &hdev->quirks))
|
||||
if (hdev->suspend_notifier.notifier_call) {
|
||||
ret = unregister_pm_notifier(&hdev->suspend_notifier);
|
||||
if (!ret)
|
||||
hdev->suspend_notifier.notifier_call = NULL;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
@ -269,7 +269,7 @@ void hci_req_add_ev(struct hci_request *req, u16 opcode, u32 plen,
|
||||
void hci_req_add(struct hci_request *req, u16 opcode, u32 plen,
|
||||
const void *param)
|
||||
{
|
||||
bt_dev_err(req->hdev, "HCI_REQ-0x%4.4x", opcode);
|
||||
bt_dev_dbg(req->hdev, "HCI_REQ-0x%4.4x", opcode);
|
||||
hci_req_add_ev(req, opcode, plen, param, 0);
|
||||
}
|
||||
|
||||
|
@ -12,6 +12,7 @@
|
||||
#include <net/bluetooth/mgmt.h>
|
||||
|
||||
#include "hci_request.h"
|
||||
#include "hci_codec.h"
|
||||
#include "hci_debugfs.h"
|
||||
#include "smp.h"
|
||||
#include "eir.h"
|
||||
@ -3780,7 +3781,8 @@ static int hci_read_page_scan_activity_sync(struct hci_dev *hdev)
|
||||
static int hci_read_def_err_data_reporting_sync(struct hci_dev *hdev)
|
||||
{
|
||||
if (!(hdev->commands[18] & 0x04) ||
|
||||
!(hdev->features[0][6] & LMP_ERR_DATA_REPORTING))
|
||||
!(hdev->features[0][6] & LMP_ERR_DATA_REPORTING) ||
|
||||
test_bit(HCI_QUIRK_BROKEN_ERR_DATA_REPORTING, &hdev->quirks))
|
||||
return 0;
|
||||
|
||||
return __hci_cmd_sync_status(hdev, HCI_OP_READ_DEF_ERR_DATA_REPORTING,
|
||||
@ -4238,11 +4240,12 @@ static int hci_set_event_mask_page_2_sync(struct hci_dev *hdev)
|
||||
/* Read local codec list if the HCI command is supported */
|
||||
static int hci_read_local_codecs_sync(struct hci_dev *hdev)
|
||||
{
|
||||
if (!(hdev->commands[29] & 0x20))
|
||||
return 0;
|
||||
if (hdev->commands[45] & 0x04)
|
||||
hci_read_supported_codecs_v2(hdev);
|
||||
else if (hdev->commands[29] & 0x20)
|
||||
hci_read_supported_codecs(hdev);
|
||||
|
||||
return __hci_cmd_sync_status(hdev, HCI_OP_READ_LOCAL_CODECS, 0, NULL,
|
||||
HCI_CMD_TIMEOUT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Read local pairing options if the HCI command is supported */
|
||||
@ -4298,7 +4301,8 @@ static int hci_set_err_data_report_sync(struct hci_dev *hdev)
|
||||
bool enabled = hci_dev_test_flag(hdev, HCI_WIDEBAND_SPEECH_ENABLED);
|
||||
|
||||
if (!(hdev->commands[18] & 0x08) ||
|
||||
!(hdev->features[0][6] & LMP_ERR_DATA_REPORTING))
|
||||
!(hdev->features[0][6] & LMP_ERR_DATA_REPORTING) ||
|
||||
test_bit(HCI_QUIRK_BROKEN_ERR_DATA_REPORTING, &hdev->quirks))
|
||||
return 0;
|
||||
|
||||
if (enabled == hdev->err_data_reporting)
|
||||
@ -4457,6 +4461,9 @@ static const struct {
|
||||
HCI_QUIRK_BROKEN(STORED_LINK_KEY,
|
||||
"HCI Delete Stored Link Key command is advertised, "
|
||||
"but not supported."),
|
||||
HCI_QUIRK_BROKEN(ERR_DATA_REPORTING,
|
||||
"HCI Read Default Erroneous Data Reporting command is "
|
||||
"advertised, but not supported."),
|
||||
HCI_QUIRK_BROKEN(READ_TRANSMIT_POWER,
|
||||
"HCI Read Transmit Power Level command is advertised, "
|
||||
"but not supported."),
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user