mirror of
https://github.com/hardkernel/linux.git
synced 2026-03-25 12:00:22 +09:00
Merge 5.15.112 into android14-5.15-lts
Changes in 5.15.112 ring-buffer: Ensure proper resetting of atomic variables in ring_buffer_reset_online_cpus crypto: ccp - Clear PSP interrupt status register before calling handler ubifs: Fix AA deadlock when setting xattr for encrypted file ubifs: Fix memory leak in do_rename bus: mhi: Move host MHI code to "host" directory bus: mhi: host: Remove duplicate ee check for syserr bus: mhi: host: Use mhi_tryset_pm_state() for setting fw error state bus: mhi: host: Range check CHDBOFF and ERDBOFF mailbox: zynq: Switch to flexible array to simplify code mailbox: zynqmp: Fix counts of child nodes ASoC: soc-pcm: use GFP_ATOMIC for dpcm structure ASoC: soc-pcm: align BE 'atomicity' with that of the FE ASoC: soc-pcm: Fix and cleanup DPCM locking ASoC: soc-pcm: serialize BE triggers ASoC: soc-pcm: test refcount before triggering ASoC: soc-pcm: fix BE handling of PAUSE_RELEASE fs/ntfs3: Fix null-ptr-deref on inode->i_op in ntfs_lookup() drm/hyperv: Don't overwrite dirt_needed value set by host scsi: qedi: Fix use after free bug in qedi_remove() net/ncsi: clear Tx enable mode when handling a Config required AEN net/sched: cls_api: remove block_cb from driver_list before freeing sit: update dev->needed_headroom in ipip6_tunnel_bind_dev() selftests: srv6: make srv6_end_dt46_l3vpn_test more robust net: dsa: mv88e6xxx: add mv88e6321 rsvd2cpu writeback: fix call of incorrect macro watchdog: dw_wdt: Fix the error handling path of dw_wdt_drv_probe() RISC-V: mm: Enable huge page support to kernel_page_present() function net/sched: act_mirred: Add carrier check r8152: fix flow control issue of RTL8156A r8152: fix the poor throughput for 2.5G devices r8152: move setting r8153b_rx_agg_chg_indicate() sfc: Fix module EEPROM reporting for QSFP modules rxrpc: Fix hard call timeout units octeontx2-af: Secure APR table update with the lock octeontx2-af: Skip PFs if not enabled octeontx2-pf: Disable packet I/O for graceful exit octeontx2-vf: Detach LF resources on probe cleanup ionic: remove noise from ethtool rxnfc error msg ethtool: Fix uninitialized number of lanes ionic: catch failure from devlink_alloc af_packet: Don't send zero-byte data in packet_sendmsg_spkt(). drm/amdgpu: add a missing lock for AMDGPU_SCHED ALSA: caiaq: input: Add error handling for unsupported input methods in `snd_usb_caiaq_input_init` net: dsa: mt7530: fix corrupt frames using trgmii on 40 MHz XTAL MT7621 virtio_net: split free_unused_bufs() virtio_net: suppress cpu stall when free_unused_bufs net: enetc: check the index of the SFI rather than the handle perf scripts intel-pt-events.py: Fix IPC output for Python 2 perf vendor events power9: Remove UTF-8 characters from JSON files perf pmu: zfree() expects a pointer to a pointer to zero it after freeing its contents perf map: Delete two variable initialisations before null pointer checks in sort__sym_from_cmp() crypto: sun8i-ss - Fix a test in sun8i_ss_setup_ivs() crypto: engine - check if BH is disabled during completion crypto: api - Add scaffolding to change completion function signature crypto: engine - Use crypto_request_complete crypto: engine - fix crypto_queue backlog handling perf symbols: Fix return incorrect build_id size in elf_read_build_id() perf evlist: Refactor evlist__for_each_cpu() perf stat: Separate bperf from bpf_profiler btrfs: fix btrfs_prev_leaf() to not return the same key twice btrfs: zoned: fix wrong use of bitops API in btrfs_ensure_empty_zones btrfs: fix encoded write i_size corruption with no-holes btrfs: don't free qgroup space unless specified btrfs: zero the buffer before marking it dirty in btrfs_redirty_list_add btrfs: print-tree: parent bytenr must be aligned to sector size btrfs: fix space cache inconsistency after error loading it from disk cifs: fix pcchunk length type in smb2_copychunk_range cifs: release leases for deferred close handles when freezing platform/x86: touchscreen_dmi: Add upside-down quirk for GDIX1002 ts on the Juno Tablet platform/x86: touchscreen_dmi: Add info for the Dexp Ursus KX210i inotify: Avoid reporting event with invalid wd smb3: fix problem remounting a share after shutdown SMB3: force unmount was failing to close deferred close files sh: math-emu: fix macro redefined warning sh: mcount.S: fix build error when PRINTK is not enabled sh: init: use OF_EARLY_FLATTREE for early init sh: nmi_debug: fix return value of __setup handler remoteproc: stm32: Call of_node_put() on iteration error remoteproc: st: Call of_node_put() on iteration error remoteproc: imx_rproc: Call of_node_put() on iteration error ARM: dts: exynos: fix WM8960 clock name in Itop Elite ARM: dts: s5pv210: correct MIPI CSIS clock name drm/bridge: lt8912b: Fix DSI Video Mode drm/msm: fix NULL-deref on snapshot tear down drm/msm: fix NULL-deref on irq uninstall f2fs: fix potential corruption when moving a directory drm/panel: otm8009a: Set backlight parent to panel device drm/amd/display: fix flickering caused by S/G mode drm/amdgpu: fix an amdgpu_irq_put() issue in gmc_v9_0_hw_fini() drm/amdgpu/gfx: disable gfx9 cp_ecc_error_irq only when enabling legacy gfx ras drm/amdgpu: Fix vram recover doesn't work after whole GPU reset (v2) drm/amdgpu: disable sdma ecc irq only when sdma RAS is enabled in suspend HID: wacom: Set a default resolution for older tablets HID: wacom: insert timestamp to packed Bluetooth (BT) events fs/ntfs3: Refactoring of various minor issues ASoC: soc-pcm: Fix DPCM lockdep warning due to nested stream locks ASoC: soc-compress: Inherit atomicity from DAI link for Compress FE ASoC: soc-pcm: Move debugfs removal out of spinlock ASoC: DPCM: Don't pick up BE without substream ASoC: soc-pcm.c: call __soc_pcm_close() in soc_pcm_close() drm/i915/dg2: Support 4k@30 on HDMI drm/i915/dg2: Add additional HDMI pixel clock frequencies drm/i915/dg2: Add HDMI pixel clock frequencies 267.30 and 319.89 MHz drm/msm: Remove struct_mutex usage drm/msm/adreno: fix runtime PM imbalance at gpu load drm/amd/display: Refine condition of cursor visibility for pipe-split drm/amd/display: Add NULL plane_state check for cursor disable logic wifi: rtw88: rtw8821c: Fix rfe_option field width ksmbd: set RSS capable in FSCTL_QUERY_NETWORK_INTERFACE_INFO ksmbd: fix multi session connection failure ksmbd: replace sessions list in connection with xarray ksmbd: add channel rwlock ksmbd: fix kernel oops from idr_remove() ksmbd: fix racy issue while destroying session on multichannel ksmbd: fix deadlock in ksmbd_find_crypto_ctx() ksmbd: not allow guest user on multichannel locking/rwsem: Add __always_inline annotation to __down_read_common() and inlined callers ext4: fix WARNING in mb_find_extent ext4: avoid a potential slab-out-of-bounds in ext4_group_desc_csum ext4: fix data races when using cached status extents ext4: check iomap type only if ext4_iomap_begin() does not fail ext4: improve error recovery code paths in __ext4_remount() ext4: improve error handling from ext4_dirhash() ext4: fix deadlock when converting an inline directory in nojournal mode ext4: add bounds checking in get_max_inline_xattr_value_size() ext4: bail out of ext4_xattr_ibody_get() fails for any reason ext4: remove a BUG_ON in ext4_mb_release_group_pa() ext4: fix invalid free tracking in ext4_xattr_move_to_block() drm/msm/adreno: adreno_gpu: Use suspend() instead of idle() on load error serial: 8250: Fix serial8250_tx_empty() race with DMA Tx drbd: correctly submit flush bio on barrier RISC-V: Fix up a cherry-pick warning in setup_vm_final() drm/amd/display: Fix hang when skipping modeset Linux 5.15.112 Change-Id: Ie61cc0aea78266c2c5adb0a889f55affa78883e5 Signed-off-by: Greg Kroah-Hartman <gregkh@google.com>
This commit is contained in:
2
Makefile
2
Makefile
@@ -1,7 +1,7 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
VERSION = 5
|
||||
PATCHLEVEL = 15
|
||||
SUBLEVEL = 111
|
||||
SUBLEVEL = 112
|
||||
EXTRAVERSION =
|
||||
NAME = Trick or Treat
|
||||
|
||||
|
||||
@@ -179,7 +179,7 @@
|
||||
compatible = "wlf,wm8960";
|
||||
reg = <0x1a>;
|
||||
clocks = <&pmu_system_controller 0>;
|
||||
clock-names = "MCLK1";
|
||||
clock-names = "mclk";
|
||||
wlf,shared-lrclk;
|
||||
#sound-dai-cells = <0>;
|
||||
};
|
||||
|
||||
@@ -582,7 +582,7 @@
|
||||
interrupts = <29>;
|
||||
clocks = <&clocks CLK_CSIS>,
|
||||
<&clocks SCLK_CSIS>;
|
||||
clock-names = "clk_csis",
|
||||
clock-names = "csis",
|
||||
"sclk_csis";
|
||||
bus-width = <4>;
|
||||
status = "disabled";
|
||||
|
||||
@@ -714,6 +714,7 @@ static void __init setup_vm_final(void)
|
||||
{
|
||||
uintptr_t va, map_size;
|
||||
phys_addr_t pa, start, end;
|
||||
unsigned long idx __maybe_unused;
|
||||
u64 i;
|
||||
|
||||
/**
|
||||
@@ -733,7 +734,7 @@ static void __init setup_vm_final(void)
|
||||
* directly in swapper_pg_dir in addition to the pgd entry that points
|
||||
* to fixmap_pte.
|
||||
*/
|
||||
unsigned long idx = pgd_index(__fix_to_virt(FIX_FDT));
|
||||
idx = pgd_index(__fix_to_virt(FIX_FDT));
|
||||
|
||||
set_pgd(&swapper_pg_dir[idx], early_pg_dir[idx]);
|
||||
#endif
|
||||
|
||||
@@ -217,18 +217,26 @@ bool kernel_page_present(struct page *page)
|
||||
pgd = pgd_offset_k(addr);
|
||||
if (!pgd_present(*pgd))
|
||||
return false;
|
||||
if (pgd_leaf(*pgd))
|
||||
return true;
|
||||
|
||||
p4d = p4d_offset(pgd, addr);
|
||||
if (!p4d_present(*p4d))
|
||||
return false;
|
||||
if (p4d_leaf(*p4d))
|
||||
return true;
|
||||
|
||||
pud = pud_offset(p4d, addr);
|
||||
if (!pud_present(*pud))
|
||||
return false;
|
||||
if (pud_leaf(*pud))
|
||||
return true;
|
||||
|
||||
pmd = pmd_offset(pud, addr);
|
||||
if (!pmd_present(*pmd))
|
||||
return false;
|
||||
if (pmd_leaf(*pmd))
|
||||
return true;
|
||||
|
||||
pte = pte_offset_kernel(pmd, addr);
|
||||
return pte_present(*pte);
|
||||
|
||||
@@ -15,7 +15,7 @@ config SH_STANDARD_BIOS
|
||||
|
||||
config STACK_DEBUG
|
||||
bool "Check for stack overflows"
|
||||
depends on DEBUG_KERNEL
|
||||
depends on DEBUG_KERNEL && PRINTK
|
||||
help
|
||||
This option will cause messages to be printed if free stack space
|
||||
drops below a certain limit. Saying Y here will add overhead to
|
||||
|
||||
@@ -64,7 +64,7 @@ ENTRY(_stext)
|
||||
ldc r0, r6_bank
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_OF_FLATTREE
|
||||
#ifdef CONFIG_OF_EARLY_FLATTREE
|
||||
mov r4, r12 ! Store device tree blob pointer in r12
|
||||
#endif
|
||||
|
||||
@@ -315,7 +315,7 @@ ENTRY(_stext)
|
||||
10:
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_OF_FLATTREE
|
||||
#ifdef CONFIG_OF_EARLY_FLATTREE
|
||||
mov.l 8f, r0 ! Make flat device tree available early.
|
||||
jsr @r0
|
||||
mov r12, r4
|
||||
@@ -346,7 +346,7 @@ ENTRY(stack_start)
|
||||
5: .long start_kernel
|
||||
6: .long cpu_init
|
||||
7: .long init_thread_union
|
||||
#if defined(CONFIG_OF_FLATTREE)
|
||||
#if defined(CONFIG_OF_EARLY_FLATTREE)
|
||||
8: .long sh_fdt_init
|
||||
#endif
|
||||
|
||||
|
||||
@@ -49,7 +49,7 @@ static int __init nmi_debug_setup(char *str)
|
||||
register_die_notifier(&nmi_debug_nb);
|
||||
|
||||
if (*str != '=')
|
||||
return 0;
|
||||
return 1;
|
||||
|
||||
for (p = str + 1; *p; p = sep + 1) {
|
||||
sep = strchr(p, ',');
|
||||
@@ -70,6 +70,6 @@ static int __init nmi_debug_setup(char *str)
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
__setup("nmi_debug", nmi_debug_setup);
|
||||
|
||||
@@ -244,7 +244,7 @@ void __init __weak plat_early_device_setup(void)
|
||||
{
|
||||
}
|
||||
|
||||
#ifdef CONFIG_OF_FLATTREE
|
||||
#ifdef CONFIG_OF_EARLY_FLATTREE
|
||||
void __ref sh_fdt_init(phys_addr_t dt_phys)
|
||||
{
|
||||
static int done = 0;
|
||||
@@ -326,7 +326,7 @@ void __init setup_arch(char **cmdline_p)
|
||||
/* Let earlyprintk output early console messages */
|
||||
sh_early_platform_driver_probe("earlyprintk", 1, 1);
|
||||
|
||||
#ifdef CONFIG_OF_FLATTREE
|
||||
#ifdef CONFIG_OF_EARLY_FLATTREE
|
||||
#ifdef CONFIG_USE_BUILTIN_DTB
|
||||
unflatten_and_copy_device_tree();
|
||||
#else
|
||||
|
||||
@@ -67,7 +67,3 @@
|
||||
} while (0)
|
||||
|
||||
#define abort() return 0
|
||||
|
||||
#define __BYTE_ORDER __LITTLE_ENDIAN
|
||||
|
||||
|
||||
|
||||
@@ -943,6 +943,9 @@ EXPORT_SYMBOL_GPL(crypto_enqueue_request);
|
||||
void crypto_enqueue_request_head(struct crypto_queue *queue,
|
||||
struct crypto_async_request *request)
|
||||
{
|
||||
if (unlikely(queue->qlen >= queue->max_qlen))
|
||||
queue->backlog = queue->backlog->prev;
|
||||
|
||||
queue->qlen++;
|
||||
list_add(&request->list, &queue->list);
|
||||
}
|
||||
|
||||
@@ -53,7 +53,8 @@ static void crypto_finalize_request(struct crypto_engine *engine,
|
||||
dev_err(engine->dev, "failed to unprepare request\n");
|
||||
}
|
||||
}
|
||||
req->complete(req, err);
|
||||
lockdep_assert_in_softirq();
|
||||
crypto_request_complete(req, err);
|
||||
|
||||
kthread_queue_work(engine->kworker, &engine->pump_requests);
|
||||
}
|
||||
@@ -128,9 +129,6 @@ start_request:
|
||||
if (!engine->retry_support)
|
||||
engine->cur_req = async_req;
|
||||
|
||||
if (backlog)
|
||||
backlog->complete(backlog, -EINPROGRESS);
|
||||
|
||||
if (engine->busy)
|
||||
was_busy = true;
|
||||
else
|
||||
@@ -213,9 +211,12 @@ req_err_1:
|
||||
}
|
||||
|
||||
req_err_2:
|
||||
async_req->complete(async_req, ret);
|
||||
crypto_request_complete(async_req, ret);
|
||||
|
||||
retry:
|
||||
if (backlog)
|
||||
crypto_request_complete(backlog, -EINPROGRESS);
|
||||
|
||||
/* If retry mechanism is supported, send new requests to engine */
|
||||
if (engine->retry_support) {
|
||||
spin_lock_irqsave(&engine->queue_lock, flags);
|
||||
|
||||
@@ -1301,7 +1301,7 @@ static void submit_one_flush(struct drbd_device *device, struct issue_flush_cont
|
||||
bio_set_dev(bio, device->ldev->backing_bdev);
|
||||
bio->bi_private = octx;
|
||||
bio->bi_end_io = one_flush_endio;
|
||||
bio->bi_opf = REQ_OP_FLUSH | REQ_PREFLUSH;
|
||||
bio->bi_opf = REQ_OP_WRITE | REQ_PREFLUSH;
|
||||
|
||||
device->flush_jif = jiffies;
|
||||
set_bit(FLUSH_PENDING, &device->flags);
|
||||
|
||||
@@ -39,4 +39,4 @@ obj-$(CONFIG_VEXPRESS_CONFIG) += vexpress-config.o
|
||||
obj-$(CONFIG_DA8XX_MSTPRI) += da8xx-mstpri.o
|
||||
|
||||
# MHI
|
||||
obj-$(CONFIG_MHI_BUS) += mhi/
|
||||
obj-y += mhi/
|
||||
|
||||
@@ -2,30 +2,7 @@
|
||||
#
|
||||
# MHI bus
|
||||
#
|
||||
# Copyright (c) 2018-2020, The Linux Foundation. All rights reserved.
|
||||
# Copyright (c) 2021, Linaro Ltd.
|
||||
#
|
||||
|
||||
config MHI_BUS
|
||||
tristate "Modem Host Interface (MHI) bus"
|
||||
help
|
||||
Bus driver for MHI protocol. Modem Host Interface (MHI) is a
|
||||
communication protocol used by the host processors to control
|
||||
and communicate with modem devices over a high speed peripheral
|
||||
bus or shared memory.
|
||||
|
||||
config MHI_BUS_DEBUG
|
||||
bool "Debugfs support for the MHI bus"
|
||||
depends on MHI_BUS && DEBUG_FS
|
||||
help
|
||||
Enable debugfs support for use with the MHI transport. Allows
|
||||
reading and/or modifying some values within the MHI controller
|
||||
for debug and test purposes.
|
||||
|
||||
config MHI_BUS_PCI_GENERIC
|
||||
tristate "MHI PCI controller driver"
|
||||
depends on MHI_BUS
|
||||
depends on PCI
|
||||
help
|
||||
This driver provides MHI PCI controller driver for devices such as
|
||||
Qualcomm SDX55 based PCIe modems.
|
||||
|
||||
source "drivers/bus/mhi/host/Kconfig"
|
||||
|
||||
@@ -1,6 +1,2 @@
|
||||
# core layer
|
||||
obj-y += core/
|
||||
|
||||
obj-$(CONFIG_MHI_BUS_PCI_GENERIC) += mhi_pci_generic.o
|
||||
mhi_pci_generic-y += pci_generic.o
|
||||
|
||||
# Host MHI stack
|
||||
obj-y += host/
|
||||
|
||||
31
drivers/bus/mhi/host/Kconfig
Normal file
31
drivers/bus/mhi/host/Kconfig
Normal file
@@ -0,0 +1,31 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
#
|
||||
# MHI bus
|
||||
#
|
||||
# Copyright (c) 2018-2020, The Linux Foundation. All rights reserved.
|
||||
#
|
||||
|
||||
config MHI_BUS
|
||||
tristate "Modem Host Interface (MHI) bus"
|
||||
help
|
||||
Bus driver for MHI protocol. Modem Host Interface (MHI) is a
|
||||
communication protocol used by the host processors to control
|
||||
and communicate with modem devices over a high speed peripheral
|
||||
bus or shared memory.
|
||||
|
||||
config MHI_BUS_DEBUG
|
||||
bool "Debugfs support for the MHI bus"
|
||||
depends on MHI_BUS && DEBUG_FS
|
||||
help
|
||||
Enable debugfs support for use with the MHI transport. Allows
|
||||
reading and/or modifying some values within the MHI controller
|
||||
for debug and test purposes.
|
||||
|
||||
config MHI_BUS_PCI_GENERIC
|
||||
tristate "MHI PCI controller driver"
|
||||
depends on MHI_BUS
|
||||
depends on PCI
|
||||
help
|
||||
This driver provides MHI PCI controller driver for devices such as
|
||||
Qualcomm SDX55 based PCIe modems.
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
obj-$(CONFIG_MHI_BUS) += mhi.o
|
||||
|
||||
mhi-y := init.o main.o pm.o boot.o
|
||||
mhi-$(CONFIG_MHI_BUS_DEBUG) += debugfs.o
|
||||
|
||||
obj-$(CONFIG_MHI_BUS_PCI_GENERIC) += mhi_pci_generic.o
|
||||
mhi_pci_generic-y += pci_generic.o
|
||||
@@ -390,6 +390,7 @@ void mhi_fw_load_handler(struct mhi_controller *mhi_cntrl)
|
||||
{
|
||||
const struct firmware *firmware = NULL;
|
||||
struct device *dev = &mhi_cntrl->mhi_dev->dev;
|
||||
enum mhi_pm_state new_state;
|
||||
const char *fw_name;
|
||||
void *buf;
|
||||
dma_addr_t dma_addr;
|
||||
@@ -507,14 +508,18 @@ error_ready_state:
|
||||
}
|
||||
|
||||
error_fw_load:
|
||||
mhi_cntrl->pm_state = MHI_PM_FW_DL_ERR;
|
||||
wake_up_all(&mhi_cntrl->state_event);
|
||||
write_lock_irq(&mhi_cntrl->pm_lock);
|
||||
new_state = mhi_tryset_pm_state(mhi_cntrl, MHI_PM_FW_DL_ERR);
|
||||
write_unlock_irq(&mhi_cntrl->pm_lock);
|
||||
if (new_state == MHI_PM_FW_DL_ERR)
|
||||
wake_up_all(&mhi_cntrl->state_event);
|
||||
}
|
||||
|
||||
int mhi_download_amss_image(struct mhi_controller *mhi_cntrl)
|
||||
{
|
||||
struct image_info *image_info = mhi_cntrl->fbc_image;
|
||||
struct device *dev = &mhi_cntrl->mhi_dev->dev;
|
||||
enum mhi_pm_state new_state;
|
||||
int ret;
|
||||
|
||||
if (!image_info)
|
||||
@@ -525,8 +530,11 @@ int mhi_download_amss_image(struct mhi_controller *mhi_cntrl)
|
||||
&image_info->mhi_buf[image_info->entries - 1]);
|
||||
if (ret) {
|
||||
dev_err(dev, "MHI did not load AMSS, ret:%d\n", ret);
|
||||
mhi_cntrl->pm_state = MHI_PM_FW_DL_ERR;
|
||||
wake_up_all(&mhi_cntrl->state_event);
|
||||
write_lock_irq(&mhi_cntrl->pm_lock);
|
||||
new_state = mhi_tryset_pm_state(mhi_cntrl, MHI_PM_FW_DL_ERR);
|
||||
write_unlock_irq(&mhi_cntrl->pm_lock);
|
||||
if (new_state == MHI_PM_FW_DL_ERR)
|
||||
wake_up_all(&mhi_cntrl->state_event);
|
||||
}
|
||||
|
||||
return ret;
|
||||
@@ -517,6 +517,12 @@ int mhi_init_mmio(struct mhi_controller *mhi_cntrl)
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
if (val >= mhi_cntrl->reg_len - (8 * MHI_DEV_WAKE_DB)) {
|
||||
dev_err(dev, "CHDB offset: 0x%x is out of range: 0x%zx\n",
|
||||
val, mhi_cntrl->reg_len - (8 * MHI_DEV_WAKE_DB));
|
||||
return -ERANGE;
|
||||
}
|
||||
|
||||
/* Setup wake db */
|
||||
mhi_cntrl->wake_db = base + val + (8 * MHI_DEV_WAKE_DB);
|
||||
mhi_cntrl->wake_set = false;
|
||||
@@ -534,6 +540,12 @@ int mhi_init_mmio(struct mhi_controller *mhi_cntrl)
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
if (val >= mhi_cntrl->reg_len - (8 * mhi_cntrl->total_ev_rings)) {
|
||||
dev_err(dev, "ERDB offset: 0x%x is out of range: 0x%zx\n",
|
||||
val, mhi_cntrl->reg_len - (8 * mhi_cntrl->total_ev_rings));
|
||||
return -ERANGE;
|
||||
}
|
||||
|
||||
/* Setup event db address for each ev_ring */
|
||||
mhi_event = mhi_cntrl->mhi_event;
|
||||
for (i = 0; i < mhi_cntrl->total_ev_rings; i++, val += 8, mhi_event++) {
|
||||
@@ -489,7 +489,7 @@ irqreturn_t mhi_intvec_threaded_handler(int irq_number, void *priv)
|
||||
}
|
||||
write_unlock_irq(&mhi_cntrl->pm_lock);
|
||||
|
||||
if (pm_state != MHI_PM_SYS_ERR_DETECT || ee == mhi_cntrl->ee)
|
||||
if (pm_state != MHI_PM_SYS_ERR_DETECT)
|
||||
goto exit_intvec;
|
||||
|
||||
switch (ee) {
|
||||
@@ -132,7 +132,7 @@ static int sun8i_ss_setup_ivs(struct skcipher_request *areq)
|
||||
}
|
||||
rctx->p_iv[i] = a;
|
||||
/* we need to setup all others IVs only in the decrypt way */
|
||||
if (rctx->op_dir & SS_ENCRYPTION)
|
||||
if (rctx->op_dir == SS_ENCRYPTION)
|
||||
return 0;
|
||||
todo = min(len, sg_dma_len(sg));
|
||||
len -= todo;
|
||||
|
||||
@@ -42,6 +42,9 @@ static irqreturn_t psp_irq_handler(int irq, void *data)
|
||||
/* Read the interrupt status: */
|
||||
status = ioread32(psp->io_regs + psp->vdata->intsts_reg);
|
||||
|
||||
/* Clear the interrupt status by writing the same value we read. */
|
||||
iowrite32(status, psp->io_regs + psp->vdata->intsts_reg);
|
||||
|
||||
/* invoke subdevice interrupt handlers */
|
||||
if (status) {
|
||||
if (psp->sev_irq_handler)
|
||||
@@ -51,9 +54,6 @@ static irqreturn_t psp_irq_handler(int irq, void *data)
|
||||
psp->tee_irq_handler(irq, psp->tee_irq_data, status);
|
||||
}
|
||||
|
||||
/* Clear the interrupt status by writing the same value we read. */
|
||||
iowrite32(status, psp->io_regs + psp->vdata->intsts_reg);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
||||
|
||||
@@ -4368,7 +4368,11 @@ static int amdgpu_device_recover_vram(struct amdgpu_device *adev)
|
||||
dev_info(adev->dev, "recover vram bo from shadow start\n");
|
||||
mutex_lock(&adev->shadow_list_lock);
|
||||
list_for_each_entry(vmbo, &adev->shadow_list, shadow_list) {
|
||||
shadow = &vmbo->bo;
|
||||
/* If vm is compute context or adev is APU, shadow will be NULL */
|
||||
if (!vmbo->shadow)
|
||||
continue;
|
||||
shadow = vmbo->shadow;
|
||||
|
||||
/* No need to recover an evicted BO */
|
||||
if (shadow->tbo.resource->mem_type != TTM_PL_TT ||
|
||||
shadow->tbo.resource->start == AMDGPU_BO_INVALID_OFFSET ||
|
||||
|
||||
@@ -66,6 +66,7 @@ static int amdgpu_sched_process_priority_override(struct amdgpu_device *adev,
|
||||
{
|
||||
struct fd f = fdget(fd);
|
||||
struct amdgpu_fpriv *fpriv;
|
||||
struct amdgpu_ctx_mgr *mgr;
|
||||
struct amdgpu_ctx *ctx;
|
||||
uint32_t id;
|
||||
int r;
|
||||
@@ -79,8 +80,11 @@ static int amdgpu_sched_process_priority_override(struct amdgpu_device *adev,
|
||||
return r;
|
||||
}
|
||||
|
||||
idr_for_each_entry(&fpriv->ctx_mgr.ctx_handles, ctx, id)
|
||||
mgr = &fpriv->ctx_mgr;
|
||||
mutex_lock(&mgr->lock);
|
||||
idr_for_each_entry(&mgr->ctx_handles, ctx, id)
|
||||
amdgpu_ctx_priority_override(ctx, priority);
|
||||
mutex_unlock(&mgr->lock);
|
||||
|
||||
fdput(f);
|
||||
return 0;
|
||||
|
||||
@@ -4018,7 +4018,8 @@ static int gfx_v9_0_hw_fini(void *handle)
|
||||
{
|
||||
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
|
||||
|
||||
amdgpu_irq_put(adev, &adev->gfx.cp_ecc_error_irq, 0);
|
||||
if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__GFX))
|
||||
amdgpu_irq_put(adev, &adev->gfx.cp_ecc_error_irq, 0);
|
||||
amdgpu_irq_put(adev, &adev->gfx.priv_reg_irq, 0);
|
||||
amdgpu_irq_put(adev, &adev->gfx.priv_inst_irq, 0);
|
||||
|
||||
|
||||
@@ -1819,7 +1819,6 @@ static int gmc_v9_0_hw_fini(void *handle)
|
||||
return 0;
|
||||
}
|
||||
|
||||
amdgpu_irq_put(adev, &adev->gmc.ecc_irq, 0);
|
||||
amdgpu_irq_put(adev, &adev->gmc.vm_fault, 0);
|
||||
|
||||
return 0;
|
||||
|
||||
@@ -2044,9 +2044,11 @@ static int sdma_v4_0_hw_fini(void *handle)
|
||||
if (amdgpu_sriov_vf(adev))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < adev->sdma.num_instances; i++) {
|
||||
amdgpu_irq_put(adev, &adev->sdma.ecc_irq,
|
||||
AMDGPU_SDMA_IRQ_INSTANCE0 + i);
|
||||
if (amdgpu_ras_is_supported(adev, AMDGPU_RAS_BLOCK__SDMA)) {
|
||||
for (i = 0; i < adev->sdma.num_instances; i++) {
|
||||
amdgpu_irq_put(adev, &adev->sdma.ecc_irq,
|
||||
AMDGPU_SDMA_IRQ_INSTANCE0 + i);
|
||||
}
|
||||
}
|
||||
|
||||
sdma_v4_0_ctx_switch_enable(adev, false);
|
||||
|
||||
@@ -8944,6 +8944,13 @@ static void amdgpu_dm_commit_cursors(struct drm_atomic_state *state)
|
||||
handle_cursor_update(plane, old_plane_state);
|
||||
}
|
||||
|
||||
static inline uint32_t get_mem_type(struct drm_framebuffer *fb)
|
||||
{
|
||||
struct amdgpu_bo *abo = gem_to_amdgpu_bo(fb->obj[0]);
|
||||
|
||||
return abo->tbo.resource ? abo->tbo.resource->mem_type : 0;
|
||||
}
|
||||
|
||||
static void amdgpu_dm_commit_planes(struct drm_atomic_state *state,
|
||||
struct dc_state *dc_state,
|
||||
struct drm_device *dev,
|
||||
@@ -9013,6 +9020,8 @@ static void amdgpu_dm_commit_planes(struct drm_atomic_state *state,
|
||||
continue;
|
||||
|
||||
dc_plane = dm_new_plane_state->dc_state;
|
||||
if (!dc_plane)
|
||||
continue;
|
||||
|
||||
bundle->surface_updates[planes_count].surface = dc_plane;
|
||||
if (new_pcrtc_state->color_mgmt_changed) {
|
||||
@@ -9064,11 +9073,13 @@ static void amdgpu_dm_commit_planes(struct drm_atomic_state *state,
|
||||
|
||||
/*
|
||||
* Only allow immediate flips for fast updates that don't
|
||||
* change FB pitch, DCC state, rotation or mirroing.
|
||||
* change memory domain, FB pitch, DCC state, rotation or
|
||||
* mirroring.
|
||||
*/
|
||||
bundle->flip_addrs[planes_count].flip_immediate =
|
||||
crtc->state->async_flip &&
|
||||
acrtc_state->update_type == UPDATE_TYPE_FAST;
|
||||
acrtc_state->update_type == UPDATE_TYPE_FAST &&
|
||||
get_mem_type(old_plane_state->fb) == get_mem_type(fb);
|
||||
|
||||
timestamp_ns = ktime_get_ns();
|
||||
bundle->flip_addrs[planes_count].flip_timestamp_in_us = div_u64(timestamp_ns, 1000);
|
||||
@@ -10541,8 +10552,9 @@ static int dm_update_plane_state(struct dc *dc,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (dm_old_plane_state->dc_state)
|
||||
dc_plane_state_release(dm_old_plane_state->dc_state);
|
||||
|
||||
dc_plane_state_release(dm_old_plane_state->dc_state);
|
||||
dm_new_plane_state->dc_state = NULL;
|
||||
|
||||
*lock_and_validation_needed = true;
|
||||
|
||||
@@ -1434,6 +1434,9 @@ bool dc_remove_plane_from_context(
|
||||
struct dc_stream_status *stream_status = NULL;
|
||||
struct resource_pool *pool = dc->res_pool;
|
||||
|
||||
if (!plane_state)
|
||||
return true;
|
||||
|
||||
for (i = 0; i < context->stream_count; i++)
|
||||
if (context->streams[i] == stream) {
|
||||
stream_status = &context->stream_status[i];
|
||||
|
||||
@@ -3211,13 +3211,11 @@ void dcn10_update_dchub(struct dce_hwseq *hws, struct dchub_init_data *dh_data)
|
||||
|
||||
static bool dcn10_can_pipe_disable_cursor(struct pipe_ctx *pipe_ctx)
|
||||
{
|
||||
struct pipe_ctx *test_pipe;
|
||||
struct pipe_ctx *test_pipe, *split_pipe;
|
||||
const struct scaler_data *scl_data = &pipe_ctx->plane_res.scl_data;
|
||||
const struct rect *r1 = &scl_data->recout, *r2;
|
||||
int r1_r = r1->x + r1->width, r1_b = r1->y + r1->height, r2_r, r2_b;
|
||||
struct rect r1 = scl_data->recout, r2, r2_half;
|
||||
int r1_r = r1.x + r1.width, r1_b = r1.y + r1.height, r2_r, r2_b;
|
||||
int cur_layer = pipe_ctx->plane_state->layer_index;
|
||||
bool upper_pipe_exists = false;
|
||||
struct fixed31_32 one = dc_fixpt_from_int(1);
|
||||
|
||||
/**
|
||||
* Disable the cursor if there's another pipe above this with a
|
||||
@@ -3226,26 +3224,35 @@ static bool dcn10_can_pipe_disable_cursor(struct pipe_ctx *pipe_ctx)
|
||||
*/
|
||||
for (test_pipe = pipe_ctx->top_pipe; test_pipe;
|
||||
test_pipe = test_pipe->top_pipe) {
|
||||
if (!test_pipe->plane_state->visible)
|
||||
// Skip invisible layer and pipe-split plane on same layer
|
||||
if (!test_pipe->plane_state ||
|
||||
!test_pipe->plane_state->visible ||
|
||||
test_pipe->plane_state->layer_index == cur_layer)
|
||||
continue;
|
||||
|
||||
r2 = &test_pipe->plane_res.scl_data.recout;
|
||||
r2_r = r2->x + r2->width;
|
||||
r2_b = r2->y + r2->height;
|
||||
r2 = test_pipe->plane_res.scl_data.recout;
|
||||
r2_r = r2.x + r2.width;
|
||||
r2_b = r2.y + r2.height;
|
||||
split_pipe = test_pipe;
|
||||
|
||||
if (r1->x >= r2->x && r1->y >= r2->y && r1_r <= r2_r && r1_b <= r2_b)
|
||||
/**
|
||||
* There is another half plane on same layer because of
|
||||
* pipe-split, merge together per same height.
|
||||
*/
|
||||
for (split_pipe = pipe_ctx->top_pipe; split_pipe;
|
||||
split_pipe = split_pipe->top_pipe)
|
||||
if (split_pipe->plane_state->layer_index == test_pipe->plane_state->layer_index) {
|
||||
r2_half = split_pipe->plane_res.scl_data.recout;
|
||||
r2.x = (r2_half.x < r2.x) ? r2_half.x : r2.x;
|
||||
r2.width = r2.width + r2_half.width;
|
||||
r2_r = r2.x + r2.width;
|
||||
break;
|
||||
}
|
||||
|
||||
if (r1.x >= r2.x && r1.y >= r2.y && r1_r <= r2_r && r1_b <= r2_b)
|
||||
return true;
|
||||
|
||||
if (test_pipe->plane_state->layer_index < cur_layer)
|
||||
upper_pipe_exists = true;
|
||||
}
|
||||
|
||||
// if plane scaled, assume an upper plane can handle cursor if it exists.
|
||||
if (upper_pipe_exists &&
|
||||
(scl_data->ratios.horz.value != one.value ||
|
||||
scl_data->ratios.vert.value != one.value))
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
@@ -494,7 +494,6 @@ static int lt8912_attach_dsi(struct lt8912 *lt)
|
||||
dsi->format = MIPI_DSI_FMT_RGB888;
|
||||
|
||||
dsi->mode_flags = MIPI_DSI_MODE_VIDEO |
|
||||
MIPI_DSI_MODE_VIDEO_BURST |
|
||||
MIPI_DSI_MODE_LPM |
|
||||
MIPI_DSI_MODE_NO_EOT_PACKET;
|
||||
|
||||
|
||||
@@ -198,8 +198,6 @@ static int hyperv_vmbus_probe(struct hv_device *hdev,
|
||||
if (ret)
|
||||
drm_warn(dev, "Failed to update vram location.\n");
|
||||
|
||||
hv->dirt_needed = true;
|
||||
|
||||
ret = hyperv_mode_config_init(hv);
|
||||
if (ret)
|
||||
goto err_vmbus_close;
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -107,7 +107,7 @@ reset_set(void *data, u64 val)
|
||||
* try to reset an active GPU.
|
||||
*/
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
release_firmware(adreno_gpu->fw[ADRENO_FW_PM4]);
|
||||
adreno_gpu->fw[ADRENO_FW_PM4] = NULL;
|
||||
@@ -133,7 +133,7 @@ reset_set(void *data, u64 val)
|
||||
gpu->funcs->recover(gpu);
|
||||
|
||||
pm_runtime_put_sync(&gpu->pdev->dev);
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -406,20 +406,21 @@ struct msm_gpu *adreno_load_gpu(struct drm_device *dev)
|
||||
|
||||
ret = pm_runtime_get_sync(&pdev->dev);
|
||||
if (ret < 0) {
|
||||
pm_runtime_put_sync(&pdev->dev);
|
||||
pm_runtime_put_noidle(&pdev->dev);
|
||||
DRM_DEV_ERROR(dev->dev, "Couldn't power up the GPU: %d\n", ret);
|
||||
return NULL;
|
||||
goto err_disable_rpm;
|
||||
}
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
ret = msm_gpu_hw_init(gpu);
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
pm_runtime_put_autosuspend(&pdev->dev);
|
||||
mutex_unlock(&gpu->lock);
|
||||
if (ret) {
|
||||
DRM_DEV_ERROR(dev->dev, "gpu hw init failed: %d\n", ret);
|
||||
return NULL;
|
||||
goto err_put_rpm;
|
||||
}
|
||||
|
||||
pm_runtime_put_autosuspend(&pdev->dev);
|
||||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
if (gpu->funcs->debugfs_init) {
|
||||
gpu->funcs->debugfs_init(gpu, dev->primary);
|
||||
@@ -428,6 +429,13 @@ struct msm_gpu *adreno_load_gpu(struct drm_device *dev)
|
||||
#endif
|
||||
|
||||
return gpu;
|
||||
|
||||
err_put_rpm:
|
||||
pm_runtime_put_sync_suspend(&pdev->dev);
|
||||
err_disable_rpm:
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void set_gpu_pdev(struct drm_device *dev,
|
||||
|
||||
@@ -29,14 +29,14 @@ static int msm_gpu_show(struct seq_file *m, void *arg)
|
||||
struct msm_gpu *gpu = priv->gpu;
|
||||
int ret;
|
||||
|
||||
ret = mutex_lock_interruptible(&show_priv->dev->struct_mutex);
|
||||
ret = mutex_lock_interruptible(&gpu->lock);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
drm_printf(&p, "%s Status:\n", gpu->name);
|
||||
gpu->funcs->show(gpu, show_priv->state, &p);
|
||||
|
||||
mutex_unlock(&show_priv->dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -48,9 +48,9 @@ static int msm_gpu_release(struct inode *inode, struct file *file)
|
||||
struct msm_drm_private *priv = show_priv->dev->dev_private;
|
||||
struct msm_gpu *gpu = priv->gpu;
|
||||
|
||||
mutex_lock(&show_priv->dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
gpu->funcs->gpu_state_put(show_priv->state);
|
||||
mutex_unlock(&show_priv->dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
kfree(show_priv);
|
||||
|
||||
@@ -72,7 +72,7 @@ static int msm_gpu_open(struct inode *inode, struct file *file)
|
||||
if (!show_priv)
|
||||
return -ENOMEM;
|
||||
|
||||
ret = mutex_lock_interruptible(&dev->struct_mutex);
|
||||
ret = mutex_lock_interruptible(&gpu->lock);
|
||||
if (ret)
|
||||
goto free_priv;
|
||||
|
||||
@@ -81,7 +81,7 @@ static int msm_gpu_open(struct inode *inode, struct file *file)
|
||||
show_priv->state = gpu->funcs->gpu_state_get(gpu);
|
||||
pm_runtime_put_sync(&gpu->pdev->dev);
|
||||
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
if (IS_ERR(show_priv->state)) {
|
||||
ret = PTR_ERR(show_priv->state);
|
||||
|
||||
@@ -359,13 +359,16 @@ static int msm_drm_uninit(struct device *dev)
|
||||
msm_fbdev_free(ddev);
|
||||
#endif
|
||||
|
||||
msm_disp_snapshot_destroy(ddev);
|
||||
if (kms)
|
||||
msm_disp_snapshot_destroy(ddev);
|
||||
|
||||
drm_mode_config_cleanup(ddev);
|
||||
|
||||
pm_runtime_get_sync(dev);
|
||||
msm_irq_uninstall(ddev);
|
||||
pm_runtime_put_sync(dev);
|
||||
if (kms) {
|
||||
pm_runtime_get_sync(dev);
|
||||
msm_irq_uninstall(ddev);
|
||||
pm_runtime_put_sync(dev);
|
||||
}
|
||||
|
||||
if (kms && kms->funcs)
|
||||
kms->funcs->destroy(kms);
|
||||
|
||||
@@ -150,7 +150,7 @@ int msm_gpu_hw_init(struct msm_gpu *gpu)
|
||||
{
|
||||
int ret;
|
||||
|
||||
WARN_ON(!mutex_is_locked(&gpu->dev->struct_mutex));
|
||||
WARN_ON(!mutex_is_locked(&gpu->lock));
|
||||
|
||||
if (!gpu->needs_hw_init)
|
||||
return 0;
|
||||
@@ -361,7 +361,7 @@ static void recover_worker(struct kthread_work *work)
|
||||
char *comm = NULL, *cmd = NULL;
|
||||
int i;
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
DRM_DEV_ERROR(dev->dev, "%s: hangcheck recover!\n", gpu->name);
|
||||
|
||||
@@ -442,7 +442,7 @@ static void recover_worker(struct kthread_work *work)
|
||||
}
|
||||
}
|
||||
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
msm_gpu_retire(gpu);
|
||||
}
|
||||
@@ -450,12 +450,11 @@ static void recover_worker(struct kthread_work *work)
|
||||
static void fault_worker(struct kthread_work *work)
|
||||
{
|
||||
struct msm_gpu *gpu = container_of(work, struct msm_gpu, fault_work);
|
||||
struct drm_device *dev = gpu->dev;
|
||||
struct msm_gem_submit *submit;
|
||||
struct msm_ringbuffer *cur_ring = gpu->funcs->active_ring(gpu);
|
||||
char *comm = NULL, *cmd = NULL;
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
submit = find_submit(cur_ring, cur_ring->memptrs->fence + 1);
|
||||
if (submit && submit->fault_dumped)
|
||||
@@ -490,7 +489,7 @@ resume_smmu:
|
||||
memset(&gpu->fault_info, 0, sizeof(gpu->fault_info));
|
||||
gpu->aspace->mmu->funcs->resume_translation(gpu->aspace->mmu);
|
||||
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
}
|
||||
|
||||
static void hangcheck_timer_reset(struct msm_gpu *gpu)
|
||||
@@ -734,7 +733,7 @@ void msm_gpu_submit(struct msm_gpu *gpu, struct msm_gem_submit *submit)
|
||||
struct msm_ringbuffer *ring = submit->ring;
|
||||
unsigned long flags;
|
||||
|
||||
WARN_ON(!mutex_is_locked(&dev->struct_mutex));
|
||||
WARN_ON(!mutex_is_locked(&gpu->lock));
|
||||
|
||||
pm_runtime_get_sync(&gpu->pdev->dev);
|
||||
|
||||
@@ -849,6 +848,7 @@ int msm_gpu_init(struct drm_device *drm, struct platform_device *pdev,
|
||||
|
||||
INIT_LIST_HEAD(&gpu->active_list);
|
||||
mutex_init(&gpu->active_lock);
|
||||
mutex_init(&gpu->lock);
|
||||
kthread_init_work(&gpu->retire_work, retire_worker);
|
||||
kthread_init_work(&gpu->recover_work, recover_worker);
|
||||
kthread_init_work(&gpu->fault_work, fault_worker);
|
||||
|
||||
@@ -143,13 +143,23 @@ struct msm_gpu {
|
||||
*/
|
||||
struct list_head active_list;
|
||||
|
||||
/**
|
||||
* lock:
|
||||
*
|
||||
* General lock for serializing all the gpu things.
|
||||
*
|
||||
* TODO move to per-ring locking where feasible (ie. submit/retire
|
||||
* path, etc)
|
||||
*/
|
||||
struct mutex lock;
|
||||
|
||||
/**
|
||||
* active_submits:
|
||||
*
|
||||
* The number of submitted but not yet retired submits, used to
|
||||
* determine transitions between active and idle.
|
||||
*
|
||||
* Protected by lock
|
||||
* Protected by active_lock
|
||||
*/
|
||||
int active_submits;
|
||||
|
||||
@@ -530,28 +540,28 @@ static inline struct msm_gpu_state *msm_gpu_crashstate_get(struct msm_gpu *gpu)
|
||||
{
|
||||
struct msm_gpu_state *state = NULL;
|
||||
|
||||
mutex_lock(&gpu->dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
if (gpu->crashstate) {
|
||||
kref_get(&gpu->crashstate->ref);
|
||||
state = gpu->crashstate;
|
||||
}
|
||||
|
||||
mutex_unlock(&gpu->dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
return state;
|
||||
}
|
||||
|
||||
static inline void msm_gpu_crashstate_put(struct msm_gpu *gpu)
|
||||
{
|
||||
mutex_lock(&gpu->dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
if (gpu->crashstate) {
|
||||
if (gpu->funcs->gpu_state_put(gpu->crashstate))
|
||||
gpu->crashstate = NULL;
|
||||
}
|
||||
|
||||
mutex_unlock(&gpu->dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -155,9 +155,12 @@ static int perf_open(struct inode *inode, struct file *file)
|
||||
struct msm_gpu *gpu = priv->gpu;
|
||||
int ret = 0;
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
if (!gpu)
|
||||
return -ENODEV;
|
||||
|
||||
if (perf->open || !gpu) {
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
if (perf->open) {
|
||||
ret = -EBUSY;
|
||||
goto out;
|
||||
}
|
||||
@@ -171,7 +174,7 @@ static int perf_open(struct inode *inode, struct file *file)
|
||||
perf->next_jiffies = jiffies + SAMPLE_TIME;
|
||||
|
||||
out:
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -86,7 +86,7 @@ struct msm_rd_state {
|
||||
struct msm_gem_submit *submit;
|
||||
|
||||
/* fifo access is synchronized on the producer side by
|
||||
* struct_mutex held by submit code (otherwise we could
|
||||
* gpu->lock held by submit code (otherwise we could
|
||||
* end up w/ cmds logged in different order than they
|
||||
* were executed). And read_lock synchronizes the reads
|
||||
*/
|
||||
@@ -181,9 +181,12 @@ static int rd_open(struct inode *inode, struct file *file)
|
||||
uint32_t gpu_id;
|
||||
int ret = 0;
|
||||
|
||||
mutex_lock(&dev->struct_mutex);
|
||||
if (!gpu)
|
||||
return -ENODEV;
|
||||
|
||||
if (rd->open || !gpu) {
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
if (rd->open) {
|
||||
ret = -EBUSY;
|
||||
goto out;
|
||||
}
|
||||
@@ -203,7 +206,7 @@ static int rd_open(struct inode *inode, struct file *file)
|
||||
rd_write_section(rd, RD_GPU_ID, &gpu_id, sizeof(gpu_id));
|
||||
|
||||
out:
|
||||
mutex_unlock(&dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -343,11 +346,10 @@ out_unlock:
|
||||
msm_gem_unlock(&obj->base);
|
||||
}
|
||||
|
||||
/* called under struct_mutex */
|
||||
/* called under gpu->lock */
|
||||
void msm_rd_dump_submit(struct msm_rd_state *rd, struct msm_gem_submit *submit,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
struct drm_device *dev = submit->dev;
|
||||
struct task_struct *task;
|
||||
char msg[256];
|
||||
int i, n;
|
||||
@@ -358,7 +360,7 @@ void msm_rd_dump_submit(struct msm_rd_state *rd, struct msm_gem_submit *submit,
|
||||
/* writing into fifo is serialized by caller, and
|
||||
* rd->read_lock is used to serialize the reads
|
||||
*/
|
||||
WARN_ON(!mutex_is_locked(&dev->struct_mutex));
|
||||
WARN_ON(!mutex_is_locked(&submit->gpu->lock));
|
||||
|
||||
if (fmt) {
|
||||
va_list args;
|
||||
|
||||
@@ -32,11 +32,11 @@ static struct dma_fence *msm_job_run(struct drm_sched_job *job)
|
||||
pm_runtime_get_sync(&gpu->pdev->dev);
|
||||
|
||||
/* TODO move submit path over to using a per-ring lock.. */
|
||||
mutex_lock(&gpu->dev->struct_mutex);
|
||||
mutex_lock(&gpu->lock);
|
||||
|
||||
msm_gpu_submit(gpu, submit);
|
||||
|
||||
mutex_unlock(&gpu->dev->struct_mutex);
|
||||
mutex_unlock(&gpu->lock);
|
||||
|
||||
pm_runtime_put(&gpu->pdev->dev);
|
||||
|
||||
|
||||
@@ -444,7 +444,7 @@ static int otm8009a_probe(struct mipi_dsi_device *dsi)
|
||||
DRM_MODE_CONNECTOR_DSI);
|
||||
|
||||
ctx->bl_dev = devm_backlight_device_register(dev, dev_name(dev),
|
||||
dsi->host->dev, ctx,
|
||||
dev, ctx,
|
||||
&otm8009a_backlight_ops,
|
||||
NULL);
|
||||
if (IS_ERR(ctx->bl_dev)) {
|
||||
|
||||
@@ -1272,6 +1272,9 @@ static void wacom_intuos_pro2_bt_pen(struct wacom_wac *wacom)
|
||||
|
||||
struct input_dev *pen_input = wacom->pen_input;
|
||||
unsigned char *data = wacom->data;
|
||||
int number_of_valid_frames = 0;
|
||||
int time_interval = 15000000;
|
||||
ktime_t time_packet_received = ktime_get();
|
||||
int i;
|
||||
|
||||
if (wacom->features.type == INTUOSP2_BT ||
|
||||
@@ -1292,12 +1295,30 @@ static void wacom_intuos_pro2_bt_pen(struct wacom_wac *wacom)
|
||||
wacom->id[0] |= (wacom->serial[0] >> 32) & 0xFFFFF;
|
||||
}
|
||||
|
||||
/* number of valid frames */
|
||||
for (i = 0; i < pen_frames; i++) {
|
||||
unsigned char *frame = &data[i*pen_frame_len + 1];
|
||||
bool valid = frame[0] & 0x80;
|
||||
|
||||
if (valid)
|
||||
number_of_valid_frames++;
|
||||
}
|
||||
|
||||
if (number_of_valid_frames) {
|
||||
if (wacom->hid_data.time_delayed)
|
||||
time_interval = ktime_get() - wacom->hid_data.time_delayed;
|
||||
time_interval /= number_of_valid_frames;
|
||||
wacom->hid_data.time_delayed = time_packet_received;
|
||||
}
|
||||
|
||||
for (i = 0; i < number_of_valid_frames; i++) {
|
||||
unsigned char *frame = &data[i*pen_frame_len + 1];
|
||||
bool valid = frame[0] & 0x80;
|
||||
bool prox = frame[0] & 0x40;
|
||||
bool range = frame[0] & 0x20;
|
||||
bool invert = frame[0] & 0x10;
|
||||
int frames_number_reversed = number_of_valid_frames - i - 1;
|
||||
int event_timestamp = time_packet_received - frames_number_reversed * time_interval;
|
||||
|
||||
if (!valid)
|
||||
continue;
|
||||
@@ -1310,6 +1331,7 @@ static void wacom_intuos_pro2_bt_pen(struct wacom_wac *wacom)
|
||||
wacom->tool[0] = 0;
|
||||
wacom->id[0] = 0;
|
||||
wacom->serial[0] = 0;
|
||||
wacom->hid_data.time_delayed = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1346,6 +1368,7 @@ static void wacom_intuos_pro2_bt_pen(struct wacom_wac *wacom)
|
||||
get_unaligned_le16(&frame[11]));
|
||||
}
|
||||
}
|
||||
|
||||
if (wacom->tool[0]) {
|
||||
input_report_abs(pen_input, ABS_PRESSURE, get_unaligned_le16(&frame[5]));
|
||||
if (wacom->features.type == INTUOSP2_BT ||
|
||||
@@ -1369,6 +1392,9 @@ static void wacom_intuos_pro2_bt_pen(struct wacom_wac *wacom)
|
||||
|
||||
wacom->shared->stylus_in_proximity = prox;
|
||||
|
||||
/* add timestamp to unpack the frames */
|
||||
input_set_timestamp(pen_input, event_timestamp);
|
||||
|
||||
input_sync(pen_input);
|
||||
}
|
||||
}
|
||||
@@ -1857,6 +1883,7 @@ static void wacom_map_usage(struct input_dev *input, struct hid_usage *usage,
|
||||
int fmax = field->logical_maximum;
|
||||
unsigned int equivalent_usage = wacom_equivalent_usage(usage->hid);
|
||||
int resolution_code = code;
|
||||
int resolution = hidinput_calc_abs_res(field, resolution_code);
|
||||
|
||||
if (equivalent_usage == HID_DG_TWIST) {
|
||||
resolution_code = ABS_RZ;
|
||||
@@ -1877,8 +1904,15 @@ static void wacom_map_usage(struct input_dev *input, struct hid_usage *usage,
|
||||
switch (type) {
|
||||
case EV_ABS:
|
||||
input_set_abs_params(input, code, fmin, fmax, fuzz, 0);
|
||||
input_abs_set_res(input, code,
|
||||
hidinput_calc_abs_res(field, resolution_code));
|
||||
|
||||
/* older tablet may miss physical usage */
|
||||
if ((code == ABS_X || code == ABS_Y) && !resolution) {
|
||||
resolution = WACOM_INTUOS_RES;
|
||||
hid_warn(input,
|
||||
"Wacom usage (%d) missing resolution \n",
|
||||
code);
|
||||
}
|
||||
input_abs_set_res(input, code, resolution);
|
||||
break;
|
||||
case EV_KEY:
|
||||
case EV_MSC:
|
||||
|
||||
@@ -321,6 +321,7 @@ struct hid_data {
|
||||
int bat_connected;
|
||||
int ps_connected;
|
||||
bool pad_input_event_flag;
|
||||
int time_delayed;
|
||||
};
|
||||
|
||||
struct wacom_remote_data {
|
||||
|
||||
@@ -110,7 +110,7 @@ struct zynqmp_ipi_pdata {
|
||||
unsigned int method;
|
||||
u32 local_id;
|
||||
int num_mboxes;
|
||||
struct zynqmp_ipi_mbox *ipi_mboxes;
|
||||
struct zynqmp_ipi_mbox ipi_mboxes[];
|
||||
};
|
||||
|
||||
static struct device_driver zynqmp_ipi_mbox_driver = {
|
||||
@@ -634,8 +634,13 @@ static int zynqmp_ipi_probe(struct platform_device *pdev)
|
||||
struct zynqmp_ipi_mbox *mbox;
|
||||
int num_mboxes, ret = -EINVAL;
|
||||
|
||||
num_mboxes = of_get_child_count(np);
|
||||
pdata = devm_kzalloc(dev, sizeof(*pdata) + (num_mboxes * sizeof(*mbox)),
|
||||
num_mboxes = of_get_available_child_count(np);
|
||||
if (num_mboxes == 0) {
|
||||
dev_err(dev, "mailbox nodes not available\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
pdata = devm_kzalloc(dev, struct_size(pdata, ipi_mboxes, num_mboxes),
|
||||
GFP_KERNEL);
|
||||
if (!pdata)
|
||||
return -ENOMEM;
|
||||
@@ -649,8 +654,6 @@ static int zynqmp_ipi_probe(struct platform_device *pdev)
|
||||
}
|
||||
|
||||
pdata->num_mboxes = num_mboxes;
|
||||
pdata->ipi_mboxes = (struct zynqmp_ipi_mbox *)
|
||||
((char *)pdata + sizeof(*pdata));
|
||||
|
||||
mbox = pdata->ipi_mboxes;
|
||||
for_each_available_child_of_node(np, nc) {
|
||||
|
||||
@@ -441,9 +441,9 @@ mt7530_pad_clk_setup(struct dsa_switch *ds, phy_interface_t interface)
|
||||
else
|
||||
ssc_delta = 0x87;
|
||||
if (priv->id == ID_MT7621) {
|
||||
/* PLL frequency: 150MHz: 1.2GBit */
|
||||
/* PLL frequency: 125MHz: 1.0GBit */
|
||||
if (xtal == HWTRAP_XTAL_40MHZ)
|
||||
ncpo1 = 0x0780;
|
||||
ncpo1 = 0x0640;
|
||||
if (xtal == HWTRAP_XTAL_25MHZ)
|
||||
ncpo1 = 0x0a00;
|
||||
} else { /* PLL frequency: 250MHz: 2.0Gbit */
|
||||
|
||||
@@ -4575,6 +4575,7 @@ static const struct mv88e6xxx_ops mv88e6321_ops = {
|
||||
.set_cpu_port = mv88e6095_g1_set_cpu_port,
|
||||
.set_egress_port = mv88e6095_g1_set_egress_port,
|
||||
.watchdog_ops = &mv88e6390_watchdog_ops,
|
||||
.mgmt_rsvd2cpu = mv88e6352_g2_mgmt_rsvd2cpu,
|
||||
.reset = mv88e6352_g1_reset,
|
||||
.vtu_getnext = mv88e6185_g1_vtu_getnext,
|
||||
.vtu_loadpurge = mv88e6185_g1_vtu_loadpurge,
|
||||
|
||||
@@ -1270,7 +1270,7 @@ static int enetc_psfp_parse_clsflower(struct enetc_ndev_priv *priv,
|
||||
int index;
|
||||
|
||||
index = enetc_get_free_index(priv);
|
||||
if (sfi->handle < 0) {
|
||||
if (index < 0) {
|
||||
NL_SET_ERR_MSG_MOD(extack, "No Stream Filter resource!");
|
||||
err = -ENOSPC;
|
||||
goto free_fmi;
|
||||
|
||||
@@ -157,7 +157,7 @@ EXPORT_SYMBOL(otx2_mbox_init);
|
||||
*/
|
||||
int otx2_mbox_regions_init(struct otx2_mbox *mbox, void **hwbase,
|
||||
struct pci_dev *pdev, void *reg_base,
|
||||
int direction, int ndevs)
|
||||
int direction, int ndevs, unsigned long *pf_bmap)
|
||||
{
|
||||
struct otx2_mbox_dev *mdev;
|
||||
int devid, err;
|
||||
@@ -169,6 +169,9 @@ int otx2_mbox_regions_init(struct otx2_mbox *mbox, void **hwbase,
|
||||
mbox->hwbase = hwbase[0];
|
||||
|
||||
for (devid = 0; devid < ndevs; devid++) {
|
||||
if (!test_bit(devid, pf_bmap))
|
||||
continue;
|
||||
|
||||
mdev = &mbox->dev[devid];
|
||||
mdev->mbase = hwbase[devid];
|
||||
mdev->hwbase = hwbase[devid];
|
||||
|
||||
@@ -96,9 +96,10 @@ void otx2_mbox_destroy(struct otx2_mbox *mbox);
|
||||
int otx2_mbox_init(struct otx2_mbox *mbox, void __force *hwbase,
|
||||
struct pci_dev *pdev, void __force *reg_base,
|
||||
int direction, int ndevs);
|
||||
|
||||
int otx2_mbox_regions_init(struct otx2_mbox *mbox, void __force **hwbase,
|
||||
struct pci_dev *pdev, void __force *reg_base,
|
||||
int direction, int ndevs);
|
||||
int direction, int ndevs, unsigned long *bmap);
|
||||
void otx2_mbox_msg_send(struct otx2_mbox *mbox, int devid);
|
||||
int otx2_mbox_wait_for_rsp(struct otx2_mbox *mbox, int devid);
|
||||
int otx2_mbox_busy_poll_for_rsp(struct otx2_mbox *mbox, int devid);
|
||||
|
||||
@@ -2196,7 +2196,7 @@ static inline void rvu_afvf_mbox_up_handler(struct work_struct *work)
|
||||
}
|
||||
|
||||
static int rvu_get_mbox_regions(struct rvu *rvu, void **mbox_addr,
|
||||
int num, int type)
|
||||
int num, int type, unsigned long *pf_bmap)
|
||||
{
|
||||
struct rvu_hwinfo *hw = rvu->hw;
|
||||
int region;
|
||||
@@ -2208,6 +2208,9 @@ static int rvu_get_mbox_regions(struct rvu *rvu, void **mbox_addr,
|
||||
*/
|
||||
if (type == TYPE_AFVF) {
|
||||
for (region = 0; region < num; region++) {
|
||||
if (!test_bit(region, pf_bmap))
|
||||
continue;
|
||||
|
||||
if (hw->cap.per_pf_mbox_regs) {
|
||||
bar4 = rvu_read64(rvu, BLKADDR_RVUM,
|
||||
RVU_AF_PFX_BAR4_ADDR(0)) +
|
||||
@@ -2229,6 +2232,9 @@ static int rvu_get_mbox_regions(struct rvu *rvu, void **mbox_addr,
|
||||
* RVU_AF_PF_BAR4_ADDR register.
|
||||
*/
|
||||
for (region = 0; region < num; region++) {
|
||||
if (!test_bit(region, pf_bmap))
|
||||
continue;
|
||||
|
||||
if (hw->cap.per_pf_mbox_regs) {
|
||||
bar4 = rvu_read64(rvu, BLKADDR_RVUM,
|
||||
RVU_AF_PFX_BAR4_ADDR(region));
|
||||
@@ -2257,12 +2263,33 @@ static int rvu_mbox_init(struct rvu *rvu, struct mbox_wq_info *mw,
|
||||
int err = -EINVAL, i, dir, dir_up;
|
||||
void __iomem *reg_base;
|
||||
struct rvu_work *mwork;
|
||||
unsigned long *pf_bmap;
|
||||
void **mbox_regions;
|
||||
const char *name;
|
||||
u64 cfg;
|
||||
|
||||
pf_bmap = bitmap_zalloc(num, GFP_KERNEL);
|
||||
if (!pf_bmap)
|
||||
return -ENOMEM;
|
||||
|
||||
/* RVU VFs */
|
||||
if (type == TYPE_AFVF)
|
||||
bitmap_set(pf_bmap, 0, num);
|
||||
|
||||
if (type == TYPE_AFPF) {
|
||||
/* Mark enabled PFs in bitmap */
|
||||
for (i = 0; i < num; i++) {
|
||||
cfg = rvu_read64(rvu, BLKADDR_RVUM, RVU_PRIV_PFX_CFG(i));
|
||||
if (cfg & BIT_ULL(20))
|
||||
set_bit(i, pf_bmap);
|
||||
}
|
||||
}
|
||||
|
||||
mbox_regions = kcalloc(num, sizeof(void *), GFP_KERNEL);
|
||||
if (!mbox_regions)
|
||||
return -ENOMEM;
|
||||
if (!mbox_regions) {
|
||||
err = -ENOMEM;
|
||||
goto free_bitmap;
|
||||
}
|
||||
|
||||
switch (type) {
|
||||
case TYPE_AFPF:
|
||||
@@ -2270,7 +2297,7 @@ static int rvu_mbox_init(struct rvu *rvu, struct mbox_wq_info *mw,
|
||||
dir = MBOX_DIR_AFPF;
|
||||
dir_up = MBOX_DIR_AFPF_UP;
|
||||
reg_base = rvu->afreg_base;
|
||||
err = rvu_get_mbox_regions(rvu, mbox_regions, num, TYPE_AFPF);
|
||||
err = rvu_get_mbox_regions(rvu, mbox_regions, num, TYPE_AFPF, pf_bmap);
|
||||
if (err)
|
||||
goto free_regions;
|
||||
break;
|
||||
@@ -2279,7 +2306,7 @@ static int rvu_mbox_init(struct rvu *rvu, struct mbox_wq_info *mw,
|
||||
dir = MBOX_DIR_PFVF;
|
||||
dir_up = MBOX_DIR_PFVF_UP;
|
||||
reg_base = rvu->pfreg_base;
|
||||
err = rvu_get_mbox_regions(rvu, mbox_regions, num, TYPE_AFVF);
|
||||
err = rvu_get_mbox_regions(rvu, mbox_regions, num, TYPE_AFVF, pf_bmap);
|
||||
if (err)
|
||||
goto free_regions;
|
||||
break;
|
||||
@@ -2310,16 +2337,19 @@ static int rvu_mbox_init(struct rvu *rvu, struct mbox_wq_info *mw,
|
||||
}
|
||||
|
||||
err = otx2_mbox_regions_init(&mw->mbox, mbox_regions, rvu->pdev,
|
||||
reg_base, dir, num);
|
||||
reg_base, dir, num, pf_bmap);
|
||||
if (err)
|
||||
goto exit;
|
||||
|
||||
err = otx2_mbox_regions_init(&mw->mbox_up, mbox_regions, rvu->pdev,
|
||||
reg_base, dir_up, num);
|
||||
reg_base, dir_up, num, pf_bmap);
|
||||
if (err)
|
||||
goto exit;
|
||||
|
||||
for (i = 0; i < num; i++) {
|
||||
if (!test_bit(i, pf_bmap))
|
||||
continue;
|
||||
|
||||
mwork = &mw->mbox_wrk[i];
|
||||
mwork->rvu = rvu;
|
||||
INIT_WORK(&mwork->work, mbox_handler);
|
||||
@@ -2328,8 +2358,7 @@ static int rvu_mbox_init(struct rvu *rvu, struct mbox_wq_info *mw,
|
||||
mwork->rvu = rvu;
|
||||
INIT_WORK(&mwork->work, mbox_up_handler);
|
||||
}
|
||||
kfree(mbox_regions);
|
||||
return 0;
|
||||
goto free_regions;
|
||||
|
||||
exit:
|
||||
destroy_workqueue(mw->mbox_wq);
|
||||
@@ -2338,6 +2367,8 @@ unmap_regions:
|
||||
iounmap((void __iomem *)mbox_regions[num]);
|
||||
free_regions:
|
||||
kfree(mbox_regions);
|
||||
free_bitmap:
|
||||
bitmap_free(pf_bmap);
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
@@ -60,13 +60,14 @@ static int rvu_get_lmtaddr(struct rvu *rvu, u16 pcifunc,
|
||||
u64 iova, u64 *lmt_addr)
|
||||
{
|
||||
u64 pa, val, pf;
|
||||
int err;
|
||||
int err = 0;
|
||||
|
||||
if (!iova) {
|
||||
dev_err(rvu->dev, "%s Requested Null address for transulation\n", __func__);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
mutex_lock(&rvu->rsrc_lock);
|
||||
rvu_write64(rvu, BLKADDR_RVUM, RVU_AF_SMMU_ADDR_REQ, iova);
|
||||
pf = rvu_get_pf(pcifunc) & 0x1F;
|
||||
val = BIT_ULL(63) | BIT_ULL(14) | BIT_ULL(13) | pf << 8 |
|
||||
@@ -76,12 +77,13 @@ static int rvu_get_lmtaddr(struct rvu *rvu, u16 pcifunc,
|
||||
err = rvu_poll_reg(rvu, BLKADDR_RVUM, RVU_AF_SMMU_ADDR_RSP_STS, BIT_ULL(0), false);
|
||||
if (err) {
|
||||
dev_err(rvu->dev, "%s LMTLINE iova transulation failed\n", __func__);
|
||||
return err;
|
||||
goto exit;
|
||||
}
|
||||
val = rvu_read64(rvu, BLKADDR_RVUM, RVU_AF_SMMU_ADDR_RSP_STS);
|
||||
if (val & ~0x1ULL) {
|
||||
dev_err(rvu->dev, "%s LMTLINE iova transulation failed err:%llx\n", __func__, val);
|
||||
return -EIO;
|
||||
err = -EIO;
|
||||
goto exit;
|
||||
}
|
||||
/* PA[51:12] = RVU_AF_SMMU_TLN_FLIT0[57:18]
|
||||
* PA[11:0] = IOVA[11:0]
|
||||
@@ -89,8 +91,9 @@ static int rvu_get_lmtaddr(struct rvu *rvu, u16 pcifunc,
|
||||
pa = rvu_read64(rvu, BLKADDR_RVUM, RVU_AF_SMMU_TLN_FLIT0) >> 18;
|
||||
pa &= GENMASK_ULL(39, 0);
|
||||
*lmt_addr = (pa << 12) | (iova & 0xFFF);
|
||||
|
||||
return 0;
|
||||
exit:
|
||||
mutex_unlock(&rvu->rsrc_lock);
|
||||
return err;
|
||||
}
|
||||
|
||||
static int rvu_update_lmtaddr(struct rvu *rvu, u16 pcifunc, u64 lmt_addr)
|
||||
|
||||
@@ -1761,13 +1761,22 @@ int otx2_open(struct net_device *netdev)
|
||||
otx2_dmacflt_reinstall_flows(pf);
|
||||
|
||||
err = otx2_rxtx_enable(pf, true);
|
||||
if (err)
|
||||
/* If a mbox communication error happens at this point then interface
|
||||
* will end up in a state such that it is in down state but hardware
|
||||
* mcam entries are enabled to receive the packets. Hence disable the
|
||||
* packet I/O.
|
||||
*/
|
||||
if (err == EIO)
|
||||
goto err_disable_rxtx;
|
||||
else if (err)
|
||||
goto err_tx_stop_queues;
|
||||
|
||||
otx2_do_set_rx_mode(pf);
|
||||
|
||||
return 0;
|
||||
|
||||
err_disable_rxtx:
|
||||
otx2_rxtx_enable(pf, false);
|
||||
err_tx_stop_queues:
|
||||
netif_tx_stop_all_queues(netdev);
|
||||
netif_carrier_off(netdev);
|
||||
|
||||
@@ -630,7 +630,7 @@ static int otx2vf_probe(struct pci_dev *pdev, const struct pci_device_id *id)
|
||||
|
||||
err = otx2vf_realloc_msix_vectors(vf);
|
||||
if (err)
|
||||
goto err_mbox_destroy;
|
||||
goto err_detach_rsrc;
|
||||
|
||||
err = otx2_set_real_num_queues(netdev, qcount, qcount);
|
||||
if (err)
|
||||
|
||||
@@ -65,6 +65,8 @@ struct ionic *ionic_devlink_alloc(struct device *dev)
|
||||
struct devlink *dl;
|
||||
|
||||
dl = devlink_alloc(&ionic_dl_ops, sizeof(struct ionic), dev);
|
||||
if (!dl)
|
||||
return NULL;
|
||||
|
||||
return devlink_priv(dl);
|
||||
}
|
||||
|
||||
@@ -724,7 +724,7 @@ static int ionic_get_rxnfc(struct net_device *netdev,
|
||||
info->data = lif->nxqs;
|
||||
break;
|
||||
default:
|
||||
netdev_err(netdev, "Command parameter %d is not supported\n",
|
||||
netdev_dbg(netdev, "Command parameter %d is not supported\n",
|
||||
info->cmd);
|
||||
err = -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
@@ -974,12 +974,15 @@ static u32 efx_mcdi_phy_module_type(struct efx_nic *efx)
|
||||
|
||||
/* A QSFP+ NIC may actually have an SFP+ module attached.
|
||||
* The ID is page 0, byte 0.
|
||||
* QSFP28 is of type SFF_8636, however, this is treated
|
||||
* the same by ethtool, so we can also treat them the same.
|
||||
*/
|
||||
switch (efx_mcdi_phy_get_module_eeprom_byte(efx, 0, 0)) {
|
||||
case 0x3:
|
||||
case 0x3: /* SFP */
|
||||
return MC_CMD_MEDIA_SFP_PLUS;
|
||||
case 0xc:
|
||||
case 0xd:
|
||||
case 0xc: /* QSFP */
|
||||
case 0xd: /* QSFP+ */
|
||||
case 0x11: /* QSFP28 */
|
||||
return MC_CMD_MEDIA_QSFP_PLUS;
|
||||
default:
|
||||
return 0;
|
||||
@@ -1077,7 +1080,7 @@ int efx_mcdi_phy_get_module_info(struct efx_nic *efx, struct ethtool_modinfo *mo
|
||||
|
||||
case MC_CMD_MEDIA_QSFP_PLUS:
|
||||
modinfo->type = ETH_MODULE_SFF_8436;
|
||||
modinfo->eeprom_len = ETH_MODULE_SFF_8436_LEN;
|
||||
modinfo->eeprom_len = ETH_MODULE_SFF_8436_MAX_LEN;
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
@@ -199,6 +199,7 @@
|
||||
#define OCP_EEE_AR 0xa41a
|
||||
#define OCP_EEE_DATA 0xa41c
|
||||
#define OCP_PHY_STATUS 0xa420
|
||||
#define OCP_INTR_EN 0xa424
|
||||
#define OCP_NCTL_CFG 0xa42c
|
||||
#define OCP_POWER_CFG 0xa430
|
||||
#define OCP_EEE_CFG 0xa432
|
||||
@@ -620,6 +621,9 @@ enum spd_duplex {
|
||||
#define PHY_STAT_LAN_ON 3
|
||||
#define PHY_STAT_PWRDN 5
|
||||
|
||||
/* OCP_INTR_EN */
|
||||
#define INTR_SPEED_FORCE BIT(3)
|
||||
|
||||
/* OCP_NCTL_CFG */
|
||||
#define PGA_RETURN_EN BIT(1)
|
||||
|
||||
@@ -3016,12 +3020,16 @@ static int rtl_enable(struct r8152 *tp)
|
||||
ocp_write_byte(tp, MCU_TYPE_PLA, PLA_CR, ocp_data);
|
||||
|
||||
switch (tp->version) {
|
||||
case RTL_VER_08:
|
||||
case RTL_VER_09:
|
||||
case RTL_VER_14:
|
||||
r8153b_rx_agg_chg_indicate(tp);
|
||||
case RTL_VER_01:
|
||||
case RTL_VER_02:
|
||||
case RTL_VER_03:
|
||||
case RTL_VER_04:
|
||||
case RTL_VER_05:
|
||||
case RTL_VER_06:
|
||||
case RTL_VER_07:
|
||||
break;
|
||||
default:
|
||||
r8153b_rx_agg_chg_indicate(tp);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -3075,7 +3083,6 @@ static void r8153_set_rx_early_timeout(struct r8152 *tp)
|
||||
640 / 8);
|
||||
ocp_write_word(tp, MCU_TYPE_USB, USB_RX_EXTRA_AGGR_TMR,
|
||||
ocp_data);
|
||||
r8153b_rx_agg_chg_indicate(tp);
|
||||
break;
|
||||
|
||||
default:
|
||||
@@ -3109,7 +3116,6 @@ static void r8153_set_rx_early_size(struct r8152 *tp)
|
||||
case RTL_VER_15:
|
||||
ocp_write_word(tp, MCU_TYPE_USB, USB_RX_EARLY_SIZE,
|
||||
ocp_data / 8);
|
||||
r8153b_rx_agg_chg_indicate(tp);
|
||||
break;
|
||||
default:
|
||||
WARN_ON_ONCE(1);
|
||||
@@ -5979,6 +5985,25 @@ static void rtl8153_disable(struct r8152 *tp)
|
||||
r8153_aldps_en(tp, true);
|
||||
}
|
||||
|
||||
static u32 fc_pause_on_auto(struct r8152 *tp)
|
||||
{
|
||||
return (ALIGN(mtu_to_size(tp->netdev->mtu), 1024) + 6 * 1024);
|
||||
}
|
||||
|
||||
static u32 fc_pause_off_auto(struct r8152 *tp)
|
||||
{
|
||||
return (ALIGN(mtu_to_size(tp->netdev->mtu), 1024) + 14 * 1024);
|
||||
}
|
||||
|
||||
static void r8156_fc_parameter(struct r8152 *tp)
|
||||
{
|
||||
u32 pause_on = tp->fc_pause_on ? tp->fc_pause_on : fc_pause_on_auto(tp);
|
||||
u32 pause_off = tp->fc_pause_off ? tp->fc_pause_off : fc_pause_off_auto(tp);
|
||||
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_FULL, pause_on / 16);
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_EMPTY, pause_off / 16);
|
||||
}
|
||||
|
||||
static int rtl8156_enable(struct r8152 *tp)
|
||||
{
|
||||
u32 ocp_data;
|
||||
@@ -5987,6 +6012,7 @@ static int rtl8156_enable(struct r8152 *tp)
|
||||
if (test_bit(RTL8152_UNPLUG, &tp->flags))
|
||||
return -ENODEV;
|
||||
|
||||
r8156_fc_parameter(tp);
|
||||
set_tx_qlen(tp);
|
||||
rtl_set_eee_plus(tp);
|
||||
r8153_set_rx_early_timeout(tp);
|
||||
@@ -6018,9 +6044,24 @@ static int rtl8156_enable(struct r8152 *tp)
|
||||
ocp_write_word(tp, MCU_TYPE_USB, USB_L1_CTRL, ocp_data);
|
||||
}
|
||||
|
||||
ocp_data = ocp_read_word(tp, MCU_TYPE_USB, USB_FW_TASK);
|
||||
ocp_data &= ~FC_PATCH_TASK;
|
||||
ocp_write_word(tp, MCU_TYPE_USB, USB_FW_TASK, ocp_data);
|
||||
usleep_range(1000, 2000);
|
||||
ocp_data |= FC_PATCH_TASK;
|
||||
ocp_write_word(tp, MCU_TYPE_USB, USB_FW_TASK, ocp_data);
|
||||
|
||||
return rtl_enable(tp);
|
||||
}
|
||||
|
||||
static void rtl8156_disable(struct r8152 *tp)
|
||||
{
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_FULL, 0);
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_EMPTY, 0);
|
||||
|
||||
rtl8153_disable(tp);
|
||||
}
|
||||
|
||||
static int rtl8156b_enable(struct r8152 *tp)
|
||||
{
|
||||
u32 ocp_data;
|
||||
@@ -6422,25 +6463,6 @@ static void rtl8153c_up(struct r8152 *tp)
|
||||
r8153b_u1u2en(tp, true);
|
||||
}
|
||||
|
||||
static inline u32 fc_pause_on_auto(struct r8152 *tp)
|
||||
{
|
||||
return (ALIGN(mtu_to_size(tp->netdev->mtu), 1024) + 6 * 1024);
|
||||
}
|
||||
|
||||
static inline u32 fc_pause_off_auto(struct r8152 *tp)
|
||||
{
|
||||
return (ALIGN(mtu_to_size(tp->netdev->mtu), 1024) + 14 * 1024);
|
||||
}
|
||||
|
||||
static void r8156_fc_parameter(struct r8152 *tp)
|
||||
{
|
||||
u32 pause_on = tp->fc_pause_on ? tp->fc_pause_on : fc_pause_on_auto(tp);
|
||||
u32 pause_off = tp->fc_pause_off ? tp->fc_pause_off : fc_pause_off_auto(tp);
|
||||
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_FULL, pause_on / 16);
|
||||
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_EMPTY, pause_off / 16);
|
||||
}
|
||||
|
||||
static void rtl8156_change_mtu(struct r8152 *tp)
|
||||
{
|
||||
u32 rx_max_size = mtu_to_size(tp->netdev->mtu);
|
||||
@@ -7531,6 +7553,11 @@ static void r8156_hw_phy_cfg(struct r8152 *tp)
|
||||
((swap_a & 0x1f) << 8) |
|
||||
((swap_a >> 8) & 0x1f));
|
||||
}
|
||||
|
||||
/* Notify the MAC when the speed is changed to force mode. */
|
||||
data = ocp_reg_read(tp, OCP_INTR_EN);
|
||||
data |= INTR_SPEED_FORCE;
|
||||
ocp_reg_write(tp, OCP_INTR_EN, data);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
@@ -7926,6 +7953,11 @@ static void r8156b_hw_phy_cfg(struct r8152 *tp)
|
||||
break;
|
||||
}
|
||||
|
||||
/* Notify the MAC when the speed is changed to force mode. */
|
||||
data = ocp_reg_read(tp, OCP_INTR_EN);
|
||||
data |= INTR_SPEED_FORCE;
|
||||
ocp_reg_write(tp, OCP_INTR_EN, data);
|
||||
|
||||
if (rtl_phy_patch_request(tp, true, true))
|
||||
return;
|
||||
|
||||
@@ -9366,7 +9398,7 @@ static int rtl_ops_init(struct r8152 *tp)
|
||||
case RTL_VER_10:
|
||||
ops->init = r8156_init;
|
||||
ops->enable = rtl8156_enable;
|
||||
ops->disable = rtl8153_disable;
|
||||
ops->disable = rtl8156_disable;
|
||||
ops->up = rtl8156_up;
|
||||
ops->down = rtl8156_down;
|
||||
ops->unload = rtl8153_unload;
|
||||
|
||||
@@ -2814,6 +2814,27 @@ static void free_receive_page_frags(struct virtnet_info *vi)
|
||||
put_page(vi->rq[i].alloc_frag.page);
|
||||
}
|
||||
|
||||
static void virtnet_sq_free_unused_buf(struct virtqueue *vq, void *buf)
|
||||
{
|
||||
if (!is_xdp_frame(buf))
|
||||
dev_kfree_skb(buf);
|
||||
else
|
||||
xdp_return_frame(ptr_to_xdp(buf));
|
||||
}
|
||||
|
||||
static void virtnet_rq_free_unused_buf(struct virtqueue *vq, void *buf)
|
||||
{
|
||||
struct virtnet_info *vi = vq->vdev->priv;
|
||||
int i = vq2rxq(vq);
|
||||
|
||||
if (vi->mergeable_rx_bufs)
|
||||
put_page(virt_to_head_page(buf));
|
||||
else if (vi->big_packets)
|
||||
give_pages(&vi->rq[i], buf);
|
||||
else
|
||||
put_page(virt_to_head_page(buf));
|
||||
}
|
||||
|
||||
static void free_unused_bufs(struct virtnet_info *vi)
|
||||
{
|
||||
void *buf;
|
||||
@@ -2821,26 +2842,16 @@ static void free_unused_bufs(struct virtnet_info *vi)
|
||||
|
||||
for (i = 0; i < vi->max_queue_pairs; i++) {
|
||||
struct virtqueue *vq = vi->sq[i].vq;
|
||||
while ((buf = virtqueue_detach_unused_buf(vq)) != NULL) {
|
||||
if (!is_xdp_frame(buf))
|
||||
dev_kfree_skb(buf);
|
||||
else
|
||||
xdp_return_frame(ptr_to_xdp(buf));
|
||||
}
|
||||
while ((buf = virtqueue_detach_unused_buf(vq)) != NULL)
|
||||
virtnet_sq_free_unused_buf(vq, buf);
|
||||
cond_resched();
|
||||
}
|
||||
|
||||
for (i = 0; i < vi->max_queue_pairs; i++) {
|
||||
struct virtqueue *vq = vi->rq[i].vq;
|
||||
|
||||
while ((buf = virtqueue_detach_unused_buf(vq)) != NULL) {
|
||||
if (vi->mergeable_rx_bufs) {
|
||||
put_page(virt_to_head_page(buf));
|
||||
} else if (vi->big_packets) {
|
||||
give_pages(&vi->rq[i], buf);
|
||||
} else {
|
||||
put_page(virt_to_head_page(buf));
|
||||
}
|
||||
}
|
||||
while ((buf = virtqueue_detach_unused_buf(vq)) != NULL)
|
||||
virtnet_rq_free_unused_buf(vq, buf);
|
||||
cond_resched();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ static int rtw8821c_read_efuse(struct rtw_dev *rtwdev, u8 *log_map)
|
||||
|
||||
map = (struct rtw8821c_efuse *)log_map;
|
||||
|
||||
efuse->rfe_option = map->rfe_option;
|
||||
efuse->rfe_option = map->rfe_option & 0x1f;
|
||||
efuse->rf_board_option = map->rf_board_option;
|
||||
efuse->crystal_cap = map->xtal_k;
|
||||
efuse->pa_type_2g = map->pa_type;
|
||||
|
||||
@@ -327,6 +327,22 @@ static const struct ts_dmi_data dexp_ursus_7w_data = {
|
||||
.properties = dexp_ursus_7w_props,
|
||||
};
|
||||
|
||||
static const struct property_entry dexp_ursus_kx210i_props[] = {
|
||||
PROPERTY_ENTRY_U32("touchscreen-min-x", 5),
|
||||
PROPERTY_ENTRY_U32("touchscreen-min-y", 2),
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-x", 1720),
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-y", 1137),
|
||||
PROPERTY_ENTRY_STRING("firmware-name", "gsl1680-dexp-ursus-kx210i.fw"),
|
||||
PROPERTY_ENTRY_U32("silead,max-fingers", 10),
|
||||
PROPERTY_ENTRY_BOOL("silead,home-button"),
|
||||
{ }
|
||||
};
|
||||
|
||||
static const struct ts_dmi_data dexp_ursus_kx210i_data = {
|
||||
.acpi_name = "MSSL1680:00",
|
||||
.properties = dexp_ursus_kx210i_props,
|
||||
};
|
||||
|
||||
static const struct property_entry digma_citi_e200_props[] = {
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-x", 1980),
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-y", 1500),
|
||||
@@ -381,6 +397,11 @@ static const struct ts_dmi_data glavey_tm800a550l_data = {
|
||||
.properties = glavey_tm800a550l_props,
|
||||
};
|
||||
|
||||
static const struct ts_dmi_data gdix1002_00_upside_down_data = {
|
||||
.acpi_name = "GDIX1002:00",
|
||||
.properties = gdix1001_upside_down_props,
|
||||
};
|
||||
|
||||
static const struct property_entry gp_electronic_t701_props[] = {
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-x", 960),
|
||||
PROPERTY_ENTRY_U32("touchscreen-size-y", 640),
|
||||
@@ -1161,6 +1182,14 @@ const struct dmi_system_id touchscreen_dmi_table[] = {
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "7W"),
|
||||
},
|
||||
},
|
||||
{
|
||||
/* DEXP Ursus KX210i */
|
||||
.driver_data = (void *)&dexp_ursus_kx210i_data,
|
||||
.matches = {
|
||||
DMI_MATCH(DMI_SYS_VENDOR, "INSYDE Corp."),
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "S107I"),
|
||||
},
|
||||
},
|
||||
{
|
||||
/* Digma Citi E200 */
|
||||
.driver_data = (void *)&digma_citi_e200_data,
|
||||
@@ -1280,6 +1309,18 @@ const struct dmi_system_id touchscreen_dmi_table[] = {
|
||||
DMI_MATCH(DMI_BIOS_VERSION, "jumperx.T87.KFBNEEA"),
|
||||
},
|
||||
},
|
||||
{
|
||||
/* Juno Tablet */
|
||||
.driver_data = (void *)&gdix1002_00_upside_down_data,
|
||||
.matches = {
|
||||
DMI_MATCH(DMI_SYS_VENDOR, "Default string"),
|
||||
/* Both product- and board-name being "Default string" is somewhat rare */
|
||||
DMI_MATCH(DMI_PRODUCT_NAME, "Default string"),
|
||||
DMI_MATCH(DMI_BOARD_NAME, "Default string"),
|
||||
/* Above matches are too generic, add partial bios-version match */
|
||||
DMI_MATCH(DMI_BIOS_VERSION, "JP2V1."),
|
||||
},
|
||||
},
|
||||
{
|
||||
/* Mediacom WinPad 7.0 W700 (same hw as Wintron surftab 7") */
|
||||
.driver_data = (void *)&trekstor_surftab_wintron70_data,
|
||||
|
||||
@@ -452,6 +452,7 @@ static int imx_rproc_prepare(struct rproc *rproc)
|
||||
|
||||
rmem = of_reserved_mem_lookup(it.node);
|
||||
if (!rmem) {
|
||||
of_node_put(it.node);
|
||||
dev_err(priv->dev, "unable to acquire memory-region\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -464,10 +465,12 @@ static int imx_rproc_prepare(struct rproc *rproc)
|
||||
imx_rproc_mem_alloc, imx_rproc_mem_release,
|
||||
it.node->name);
|
||||
|
||||
if (mem)
|
||||
if (mem) {
|
||||
rproc_coredump_add_segment(rproc, da, rmem->size);
|
||||
else
|
||||
} else {
|
||||
of_node_put(it.node);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
rproc_add_carveout(rproc, mem);
|
||||
}
|
||||
|
||||
@@ -129,6 +129,7 @@ static int st_rproc_parse_fw(struct rproc *rproc, const struct firmware *fw)
|
||||
while (of_phandle_iterator_next(&it) == 0) {
|
||||
rmem = of_reserved_mem_lookup(it.node);
|
||||
if (!rmem) {
|
||||
of_node_put(it.node);
|
||||
dev_err(dev, "unable to acquire memory-region\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -150,8 +151,10 @@ static int st_rproc_parse_fw(struct rproc *rproc, const struct firmware *fw)
|
||||
it.node->name);
|
||||
}
|
||||
|
||||
if (!mem)
|
||||
if (!mem) {
|
||||
of_node_put(it.node);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
rproc_add_carveout(rproc, mem);
|
||||
index++;
|
||||
|
||||
@@ -223,11 +223,13 @@ static int stm32_rproc_prepare(struct rproc *rproc)
|
||||
while (of_phandle_iterator_next(&it) == 0) {
|
||||
rmem = of_reserved_mem_lookup(it.node);
|
||||
if (!rmem) {
|
||||
of_node_put(it.node);
|
||||
dev_err(dev, "unable to acquire memory-region\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (stm32_rproc_pa_to_da(rproc, rmem->base, &da) < 0) {
|
||||
of_node_put(it.node);
|
||||
dev_err(dev, "memory region not valid %pa\n",
|
||||
&rmem->base);
|
||||
return -EINVAL;
|
||||
@@ -254,8 +256,10 @@ static int stm32_rproc_prepare(struct rproc *rproc)
|
||||
it.node->name);
|
||||
}
|
||||
|
||||
if (!mem)
|
||||
if (!mem) {
|
||||
of_node_put(it.node);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
rproc_add_carveout(rproc, mem);
|
||||
index++;
|
||||
|
||||
@@ -2455,6 +2455,9 @@ static void __qedi_remove(struct pci_dev *pdev, int mode)
|
||||
qedi_ops->ll2->stop(qedi->cdev);
|
||||
}
|
||||
|
||||
cancel_delayed_work_sync(&qedi->recovery_work);
|
||||
cancel_delayed_work_sync(&qedi->board_disable_work);
|
||||
|
||||
qedi_free_iscsi_pf_param(qedi);
|
||||
|
||||
rval = qedi_ops->common->update_drv_state(qedi->cdev, false);
|
||||
|
||||
@@ -349,6 +349,13 @@ static inline void serial8250_do_prepare_rx_dma(struct uart_8250_port *p)
|
||||
if (dma->prepare_rx_dma)
|
||||
dma->prepare_rx_dma(p);
|
||||
}
|
||||
|
||||
static inline bool serial8250_tx_dma_running(struct uart_8250_port *p)
|
||||
{
|
||||
struct uart_8250_dma *dma = p->dma;
|
||||
|
||||
return dma && dma->tx_running;
|
||||
}
|
||||
#else
|
||||
static inline int serial8250_tx_dma(struct uart_8250_port *p)
|
||||
{
|
||||
@@ -364,6 +371,11 @@ static inline int serial8250_request_dma(struct uart_8250_port *p)
|
||||
return -1;
|
||||
}
|
||||
static inline void serial8250_release_dma(struct uart_8250_port *p) { }
|
||||
|
||||
static inline bool serial8250_tx_dma_running(struct uart_8250_port *p)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
#endif
|
||||
|
||||
static inline int ns16550a_goto_highspeed(struct uart_8250_port *up)
|
||||
|
||||
@@ -1988,19 +1988,25 @@ static int serial8250_tx_threshold_handle_irq(struct uart_port *port)
|
||||
static unsigned int serial8250_tx_empty(struct uart_port *port)
|
||||
{
|
||||
struct uart_8250_port *up = up_to_u8250p(port);
|
||||
unsigned int result = 0;
|
||||
unsigned long flags;
|
||||
unsigned int lsr;
|
||||
|
||||
serial8250_rpm_get(up);
|
||||
|
||||
spin_lock_irqsave(&port->lock, flags);
|
||||
lsr = serial_port_in(port, UART_LSR);
|
||||
up->lsr_saved_flags |= lsr & LSR_SAVE_FLAGS;
|
||||
if (!serial8250_tx_dma_running(up)) {
|
||||
lsr = serial_port_in(port, UART_LSR);
|
||||
up->lsr_saved_flags |= lsr & LSR_SAVE_FLAGS;
|
||||
|
||||
if ((lsr & BOTH_EMPTY) == BOTH_EMPTY)
|
||||
result = TIOCSER_TEMT;
|
||||
}
|
||||
spin_unlock_irqrestore(&port->lock, flags);
|
||||
|
||||
serial8250_rpm_put(up);
|
||||
|
||||
return (lsr & BOTH_EMPTY) == BOTH_EMPTY ? TIOCSER_TEMT : 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
unsigned int serial8250_do_get_mctrl(struct uart_port *port)
|
||||
|
||||
@@ -637,7 +637,7 @@ static int dw_wdt_drv_probe(struct platform_device *pdev)
|
||||
|
||||
ret = dw_wdt_init_timeouts(dw_wdt, dev);
|
||||
if (ret)
|
||||
goto out_disable_clk;
|
||||
goto out_assert_rst;
|
||||
|
||||
wdd = &dw_wdt->wdd;
|
||||
wdd->ops = &dw_wdt_ops;
|
||||
@@ -668,12 +668,15 @@ static int dw_wdt_drv_probe(struct platform_device *pdev)
|
||||
|
||||
ret = watchdog_register_device(wdd);
|
||||
if (ret)
|
||||
goto out_disable_pclk;
|
||||
goto out_assert_rst;
|
||||
|
||||
dw_wdt_dbgfs_init(dw_wdt);
|
||||
|
||||
return 0;
|
||||
|
||||
out_assert_rst:
|
||||
reset_control_assert(dw_wdt->rst);
|
||||
|
||||
out_disable_pclk:
|
||||
clk_disable_unprepare(dw_wdt->pclk);
|
||||
|
||||
|
||||
@@ -121,7 +121,8 @@ static u64 block_rsv_release_bytes(struct btrfs_fs_info *fs_info,
|
||||
} else {
|
||||
num_bytes = 0;
|
||||
}
|
||||
if (block_rsv->qgroup_rsv_reserved >= block_rsv->qgroup_rsv_size) {
|
||||
if (qgroup_to_release_ret &&
|
||||
block_rsv->qgroup_rsv_reserved >= block_rsv->qgroup_rsv_size) {
|
||||
qgroup_to_release = block_rsv->qgroup_rsv_reserved -
|
||||
block_rsv->qgroup_rsv_size;
|
||||
block_rsv->qgroup_rsv_reserved = block_rsv->qgroup_rsv_size;
|
||||
|
||||
@@ -4189,10 +4189,12 @@ int btrfs_del_items(struct btrfs_trans_handle *trans, struct btrfs_root *root,
|
||||
int btrfs_prev_leaf(struct btrfs_root *root, struct btrfs_path *path)
|
||||
{
|
||||
struct btrfs_key key;
|
||||
struct btrfs_key orig_key;
|
||||
struct btrfs_disk_key found_key;
|
||||
int ret;
|
||||
|
||||
btrfs_item_key_to_cpu(path->nodes[0], &key, 0);
|
||||
orig_key = key;
|
||||
|
||||
if (key.offset > 0) {
|
||||
key.offset--;
|
||||
@@ -4209,8 +4211,36 @@ int btrfs_prev_leaf(struct btrfs_root *root, struct btrfs_path *path)
|
||||
|
||||
btrfs_release_path(path);
|
||||
ret = btrfs_search_slot(NULL, root, &key, path, 0, 0);
|
||||
if (ret < 0)
|
||||
if (ret <= 0)
|
||||
return ret;
|
||||
|
||||
/*
|
||||
* Previous key not found. Even if we were at slot 0 of the leaf we had
|
||||
* before releasing the path and calling btrfs_search_slot(), we now may
|
||||
* be in a slot pointing to the same original key - this can happen if
|
||||
* after we released the path, one of more items were moved from a
|
||||
* sibling leaf into the front of the leaf we had due to an insertion
|
||||
* (see push_leaf_right()).
|
||||
* If we hit this case and our slot is > 0 and just decrement the slot
|
||||
* so that the caller does not process the same key again, which may or
|
||||
* may not break the caller, depending on its logic.
|
||||
*/
|
||||
if (path->slots[0] < btrfs_header_nritems(path->nodes[0])) {
|
||||
btrfs_item_key(path->nodes[0], &found_key, path->slots[0]);
|
||||
ret = comp_keys(&found_key, &orig_key);
|
||||
if (ret == 0) {
|
||||
if (path->slots[0] > 0) {
|
||||
path->slots[0]--;
|
||||
return 0;
|
||||
}
|
||||
/*
|
||||
* At slot 0, same key as before, it means orig_key is
|
||||
* the lowest, leftmost, key in the tree. We're done.
|
||||
*/
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
btrfs_item_key(path->nodes[0], &found_key, 0);
|
||||
ret = comp_keys(&found_key, &key);
|
||||
/*
|
||||
|
||||
@@ -47,13 +47,13 @@ void btrfs_inode_safe_disk_i_size_write(struct btrfs_inode *inode, u64 new_i_siz
|
||||
u64 start, end, i_size;
|
||||
int ret;
|
||||
|
||||
spin_lock(&inode->lock);
|
||||
i_size = new_i_size ?: i_size_read(&inode->vfs_inode);
|
||||
if (btrfs_fs_incompat(fs_info, NO_HOLES)) {
|
||||
inode->disk_i_size = i_size;
|
||||
return;
|
||||
goto out_unlock;
|
||||
}
|
||||
|
||||
spin_lock(&inode->lock);
|
||||
ret = find_contiguous_extent_bit(&inode->file_extent_tree, 0, &start,
|
||||
&end, EXTENT_DIRTY);
|
||||
if (!ret && start == 0)
|
||||
@@ -61,6 +61,7 @@ void btrfs_inode_safe_disk_i_size_write(struct btrfs_inode *inode, u64 new_i_siz
|
||||
else
|
||||
i_size = 0;
|
||||
inode->disk_i_size = i_size;
|
||||
out_unlock:
|
||||
spin_unlock(&inode->lock);
|
||||
}
|
||||
|
||||
|
||||
@@ -825,15 +825,16 @@ static int __load_free_space_cache(struct btrfs_root *root, struct inode *inode,
|
||||
}
|
||||
spin_lock(&ctl->tree_lock);
|
||||
ret = link_free_space(ctl, e);
|
||||
ctl->total_bitmaps++;
|
||||
recalculate_thresholds(ctl);
|
||||
spin_unlock(&ctl->tree_lock);
|
||||
if (ret) {
|
||||
spin_unlock(&ctl->tree_lock);
|
||||
btrfs_err(fs_info,
|
||||
"Duplicate entries in free space cache, dumping");
|
||||
kmem_cache_free(btrfs_free_space_cachep, e);
|
||||
goto free_cache;
|
||||
}
|
||||
ctl->total_bitmaps++;
|
||||
recalculate_thresholds(ctl);
|
||||
spin_unlock(&ctl->tree_lock);
|
||||
list_add_tail(&e->list, &bitmaps);
|
||||
}
|
||||
|
||||
|
||||
@@ -147,10 +147,10 @@ static void print_extent_item(struct extent_buffer *eb, int slot, int type)
|
||||
pr_cont("shared data backref parent %llu count %u\n",
|
||||
offset, btrfs_shared_data_ref_count(eb, sref));
|
||||
/*
|
||||
* offset is supposed to be a tree block which
|
||||
* must be aligned to nodesize.
|
||||
* Offset is supposed to be a tree block which must be
|
||||
* aligned to sectorsize.
|
||||
*/
|
||||
if (!IS_ALIGNED(offset, eb->fs_info->nodesize))
|
||||
if (!IS_ALIGNED(offset, eb->fs_info->sectorsize))
|
||||
pr_info(
|
||||
"\t\t\t(parent %llu not aligned to sectorsize %u)\n",
|
||||
offset, eb->fs_info->sectorsize);
|
||||
|
||||
@@ -1014,12 +1014,12 @@ int btrfs_ensure_empty_zones(struct btrfs_device *device, u64 start, u64 size)
|
||||
return -ERANGE;
|
||||
|
||||
/* All the zones are conventional */
|
||||
if (find_next_bit(zinfo->seq_zones, begin, end) == end)
|
||||
if (find_next_bit(zinfo->seq_zones, end, begin) == end)
|
||||
return 0;
|
||||
|
||||
/* All the zones are sequential and empty */
|
||||
if (find_next_zero_bit(zinfo->seq_zones, begin, end) == end &&
|
||||
find_next_zero_bit(zinfo->empty_zones, begin, end) == end)
|
||||
if (find_next_zero_bit(zinfo->seq_zones, end, begin) == end &&
|
||||
find_next_zero_bit(zinfo->empty_zones, end, begin) == end)
|
||||
return 0;
|
||||
|
||||
for (pos = start; pos < start + size; pos += zinfo->zone_size) {
|
||||
@@ -1347,11 +1347,11 @@ void btrfs_redirty_list_add(struct btrfs_transaction *trans,
|
||||
!list_empty(&eb->release_list))
|
||||
return;
|
||||
|
||||
memzero_extent_buffer(eb, 0, eb->len);
|
||||
set_bit(EXTENT_BUFFER_NO_CHECK, &eb->bflags);
|
||||
set_extent_buffer_dirty(eb);
|
||||
set_extent_bits_nowait(&trans->dirty_pages, eb->start,
|
||||
eb->start + eb->len - 1, EXTENT_DIRTY);
|
||||
memzero_extent_buffer(eb, 0, eb->len);
|
||||
set_bit(EXTENT_BUFFER_NO_CHECK, &eb->bflags);
|
||||
|
||||
spin_lock(&trans->releasing_ebs_lock);
|
||||
list_add_tail(&eb->release_list, &trans->releasing_ebs);
|
||||
|
||||
@@ -715,6 +715,7 @@ static void cifs_umount_begin(struct super_block *sb)
|
||||
tcon->tidStatus = CifsExiting;
|
||||
spin_unlock(&cifs_tcp_ses_lock);
|
||||
|
||||
cifs_close_all_deferred_files(tcon);
|
||||
/* cancel_brl_requests(tcon); */ /* BB mark all brl mids as exiting */
|
||||
/* cancel_notify_requests(tcon); */
|
||||
if (tcon->ses && tcon->ses->server) {
|
||||
@@ -730,6 +731,20 @@ static void cifs_umount_begin(struct super_block *sb)
|
||||
return;
|
||||
}
|
||||
|
||||
static int cifs_freeze(struct super_block *sb)
|
||||
{
|
||||
struct cifs_sb_info *cifs_sb = CIFS_SB(sb);
|
||||
struct cifs_tcon *tcon;
|
||||
|
||||
if (cifs_sb == NULL)
|
||||
return 0;
|
||||
|
||||
tcon = cifs_sb_master_tcon(cifs_sb);
|
||||
|
||||
cifs_close_all_deferred_files(tcon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_CIFS_STATS2
|
||||
static int cifs_show_stats(struct seq_file *s, struct dentry *root)
|
||||
{
|
||||
@@ -761,6 +776,7 @@ static const struct super_operations cifs_super_ops = {
|
||||
as opens */
|
||||
.show_options = cifs_show_options,
|
||||
.umount_begin = cifs_umount_begin,
|
||||
.freeze_fs = cifs_freeze,
|
||||
#ifdef CONFIG_CIFS_STATS2
|
||||
.show_stats = cifs_show_stats,
|
||||
#endif
|
||||
|
||||
@@ -2474,6 +2474,13 @@ cifs_match_super(struct super_block *sb, void *data)
|
||||
|
||||
spin_lock(&cifs_tcp_ses_lock);
|
||||
cifs_sb = CIFS_SB(sb);
|
||||
|
||||
/* We do not want to use a superblock that has been shutdown */
|
||||
if (CIFS_MOUNT_SHUTDOWN & cifs_sb->mnt_cifs_flags) {
|
||||
spin_unlock(&cifs_tcp_ses_lock);
|
||||
return 0;
|
||||
}
|
||||
|
||||
tlink = cifs_get_tlink(cifs_sb_master_tlink(cifs_sb));
|
||||
if (tlink == NULL) {
|
||||
/* can not match superblock if tlink were ever null */
|
||||
|
||||
@@ -1893,7 +1893,7 @@ smb2_copychunk_range(const unsigned int xid,
|
||||
pcchunk->SourceOffset = cpu_to_le64(src_off);
|
||||
pcchunk->TargetOffset = cpu_to_le64(dest_off);
|
||||
pcchunk->Length =
|
||||
cpu_to_le32(min_t(u32, len, tcon->max_bytes_chunk));
|
||||
cpu_to_le32(min_t(u64, len, tcon->max_bytes_chunk));
|
||||
|
||||
/* Request server copy to target from src identified by key */
|
||||
kfree(retbuf);
|
||||
|
||||
@@ -303,6 +303,22 @@ struct ext4_group_desc * ext4_get_group_desc(struct super_block *sb,
|
||||
return desc;
|
||||
}
|
||||
|
||||
static ext4_fsblk_t ext4_valid_block_bitmap_padding(struct super_block *sb,
|
||||
ext4_group_t block_group,
|
||||
struct buffer_head *bh)
|
||||
{
|
||||
ext4_grpblk_t next_zero_bit;
|
||||
unsigned long bitmap_size = sb->s_blocksize * 8;
|
||||
unsigned int offset = num_clusters_in_group(sb, block_group);
|
||||
|
||||
if (bitmap_size <= offset)
|
||||
return 0;
|
||||
|
||||
next_zero_bit = ext4_find_next_zero_bit(bh->b_data, bitmap_size, offset);
|
||||
|
||||
return (next_zero_bit < bitmap_size ? next_zero_bit : 0);
|
||||
}
|
||||
|
||||
/*
|
||||
* Return the block number which was discovered to be invalid, or 0 if
|
||||
* the block bitmap is valid.
|
||||
@@ -401,6 +417,15 @@ static int ext4_validate_block_bitmap(struct super_block *sb,
|
||||
EXT4_GROUP_INFO_BBITMAP_CORRUPT);
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
blk = ext4_valid_block_bitmap_padding(sb, block_group, bh);
|
||||
if (unlikely(blk != 0)) {
|
||||
ext4_unlock_group(sb, block_group);
|
||||
ext4_error(sb, "bg %u: block %llu: padding at end of block bitmap is not set",
|
||||
block_group, blk);
|
||||
ext4_mark_group_bitmap_corrupted(sb, block_group,
|
||||
EXT4_GROUP_INFO_BBITMAP_CORRUPT);
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
set_buffer_verified(bh);
|
||||
verified:
|
||||
ext4_unlock_group(sb, block_group);
|
||||
|
||||
@@ -269,14 +269,12 @@ static void __es_find_extent_range(struct inode *inode,
|
||||
|
||||
/* see if the extent has been cached */
|
||||
es->es_lblk = es->es_len = es->es_pblk = 0;
|
||||
if (tree->cache_es) {
|
||||
es1 = tree->cache_es;
|
||||
if (in_range(lblk, es1->es_lblk, es1->es_len)) {
|
||||
es_debug("%u cached by [%u/%u) %llu %x\n",
|
||||
lblk, es1->es_lblk, es1->es_len,
|
||||
ext4_es_pblock(es1), ext4_es_status(es1));
|
||||
goto out;
|
||||
}
|
||||
es1 = READ_ONCE(tree->cache_es);
|
||||
if (es1 && in_range(lblk, es1->es_lblk, es1->es_len)) {
|
||||
es_debug("%u cached by [%u/%u) %llu %x\n",
|
||||
lblk, es1->es_lblk, es1->es_len,
|
||||
ext4_es_pblock(es1), ext4_es_status(es1));
|
||||
goto out;
|
||||
}
|
||||
|
||||
es1 = __es_tree_search(&tree->root, lblk);
|
||||
@@ -295,7 +293,7 @@ out:
|
||||
}
|
||||
|
||||
if (es1 && matching_fn(es1)) {
|
||||
tree->cache_es = es1;
|
||||
WRITE_ONCE(tree->cache_es, es1);
|
||||
es->es_lblk = es1->es_lblk;
|
||||
es->es_len = es1->es_len;
|
||||
es->es_pblk = es1->es_pblk;
|
||||
@@ -934,14 +932,12 @@ int ext4_es_lookup_extent(struct inode *inode, ext4_lblk_t lblk,
|
||||
|
||||
/* find extent in cache firstly */
|
||||
es->es_lblk = es->es_len = es->es_pblk = 0;
|
||||
if (tree->cache_es) {
|
||||
es1 = tree->cache_es;
|
||||
if (in_range(lblk, es1->es_lblk, es1->es_len)) {
|
||||
es_debug("%u cached by [%u/%u)\n",
|
||||
lblk, es1->es_lblk, es1->es_len);
|
||||
found = 1;
|
||||
goto out;
|
||||
}
|
||||
es1 = READ_ONCE(tree->cache_es);
|
||||
if (es1 && in_range(lblk, es1->es_lblk, es1->es_len)) {
|
||||
es_debug("%u cached by [%u/%u)\n",
|
||||
lblk, es1->es_lblk, es1->es_len);
|
||||
found = 1;
|
||||
goto out;
|
||||
}
|
||||
|
||||
node = tree->root.rb_node;
|
||||
|
||||
@@ -277,7 +277,11 @@ static int __ext4fs_dirhash(const struct inode *dir, const char *name, int len,
|
||||
}
|
||||
default:
|
||||
hinfo->hash = 0;
|
||||
return -1;
|
||||
hinfo->minor_hash = 0;
|
||||
ext4_warning(dir->i_sb,
|
||||
"invalid/unsupported hash tree version %u",
|
||||
hinfo->hash_version);
|
||||
return -EINVAL;
|
||||
}
|
||||
hash = hash & ~1;
|
||||
if (hash == (EXT4_HTREE_EOF_32BIT << 1))
|
||||
|
||||
@@ -33,6 +33,7 @@ static int get_max_inline_xattr_value_size(struct inode *inode,
|
||||
struct ext4_xattr_ibody_header *header;
|
||||
struct ext4_xattr_entry *entry;
|
||||
struct ext4_inode *raw_inode;
|
||||
void *end;
|
||||
int free, min_offs;
|
||||
|
||||
if (!EXT4_INODE_HAS_XATTR_SPACE(inode))
|
||||
@@ -56,14 +57,23 @@ static int get_max_inline_xattr_value_size(struct inode *inode,
|
||||
raw_inode = ext4_raw_inode(iloc);
|
||||
header = IHDR(inode, raw_inode);
|
||||
entry = IFIRST(header);
|
||||
end = (void *)raw_inode + EXT4_SB(inode->i_sb)->s_inode_size;
|
||||
|
||||
/* Compute min_offs. */
|
||||
for (; !IS_LAST_ENTRY(entry); entry = EXT4_XATTR_NEXT(entry)) {
|
||||
while (!IS_LAST_ENTRY(entry)) {
|
||||
void *next = EXT4_XATTR_NEXT(entry);
|
||||
|
||||
if (next >= end) {
|
||||
EXT4_ERROR_INODE(inode,
|
||||
"corrupt xattr in inline inode");
|
||||
return 0;
|
||||
}
|
||||
if (!entry->e_value_inum && entry->e_value_size) {
|
||||
size_t offs = le16_to_cpu(entry->e_value_offs);
|
||||
if (offs < min_offs)
|
||||
min_offs = offs;
|
||||
}
|
||||
entry = next;
|
||||
}
|
||||
free = min_offs -
|
||||
((void *)entry - (void *)IFIRST(header)) - sizeof(__u32);
|
||||
@@ -350,7 +360,7 @@ static int ext4_update_inline_data(handle_t *handle, struct inode *inode,
|
||||
|
||||
error = ext4_xattr_ibody_get(inode, i.name_index, i.name,
|
||||
value, len);
|
||||
if (error == -ENODATA)
|
||||
if (error < 0)
|
||||
goto out;
|
||||
|
||||
BUFFER_TRACE(is.iloc.bh, "get_write_access");
|
||||
@@ -1185,6 +1195,7 @@ static int ext4_finish_convert_inline_dir(handle_t *handle,
|
||||
ext4_initialize_dirent_tail(dir_block,
|
||||
inode->i_sb->s_blocksize);
|
||||
set_buffer_uptodate(dir_block);
|
||||
unlock_buffer(dir_block);
|
||||
err = ext4_handle_dirty_dirblock(handle, inode, dir_block);
|
||||
if (err)
|
||||
return err;
|
||||
@@ -1259,6 +1270,7 @@ static int ext4_convert_inline_data_nolock(handle_t *handle,
|
||||
if (!S_ISDIR(inode->i_mode)) {
|
||||
memcpy(data_bh->b_data, buf, inline_size);
|
||||
set_buffer_uptodate(data_bh);
|
||||
unlock_buffer(data_bh);
|
||||
error = ext4_handle_dirty_metadata(handle,
|
||||
inode, data_bh);
|
||||
} else {
|
||||
@@ -1266,7 +1278,6 @@ static int ext4_convert_inline_data_nolock(handle_t *handle,
|
||||
buf, inline_size);
|
||||
}
|
||||
|
||||
unlock_buffer(data_bh);
|
||||
out_restore:
|
||||
if (error)
|
||||
ext4_restore_inline_data(handle, inode, iloc, buf, inline_size);
|
||||
|
||||
@@ -3485,7 +3485,7 @@ static int ext4_iomap_overwrite_begin(struct inode *inode, loff_t offset,
|
||||
*/
|
||||
flags &= ~IOMAP_WRITE;
|
||||
ret = ext4_iomap_begin(inode, offset, length, flags, iomap, srcmap);
|
||||
WARN_ON_ONCE(iomap->type != IOMAP_MAPPED);
|
||||
WARN_ON_ONCE(!ret && iomap->type != IOMAP_MAPPED);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -4832,7 +4832,11 @@ ext4_mb_release_group_pa(struct ext4_buddy *e4b,
|
||||
trace_ext4_mb_release_group_pa(sb, pa);
|
||||
BUG_ON(pa->pa_deleted == 0);
|
||||
ext4_get_group_no_and_offset(sb, pa->pa_pstart, &group, &bit);
|
||||
BUG_ON(group != e4b->bd_group && pa->pa_len != 0);
|
||||
if (unlikely(group != e4b->bd_group && pa->pa_len != 0)) {
|
||||
ext4_warning(sb, "bad group: expected %u, group %u, pa_start %llu",
|
||||
e4b->bd_group, group, pa->pa_pstart);
|
||||
return 0;
|
||||
}
|
||||
mb_free_blocks(pa->pa_inode, e4b, bit, pa->pa_len);
|
||||
atomic_add(pa->pa_len, &EXT4_SB(sb)->s_mb_discarded);
|
||||
trace_ext4_mballoc_discard(sb, NULL, group, bit, pa->pa_len);
|
||||
|
||||
@@ -674,7 +674,7 @@ static struct stats dx_show_leaf(struct inode *dir,
|
||||
len = de->name_len;
|
||||
if (!IS_ENCRYPTED(dir)) {
|
||||
/* Directory is not encrypted */
|
||||
ext4fs_dirhash(dir, de->name,
|
||||
(void) ext4fs_dirhash(dir, de->name,
|
||||
de->name_len, &h);
|
||||
printk("%*.s:(U)%x.%u ", len,
|
||||
name, h.hash,
|
||||
@@ -709,8 +709,9 @@ static struct stats dx_show_leaf(struct inode *dir,
|
||||
if (IS_CASEFOLDED(dir))
|
||||
h.hash = EXT4_DIRENT_HASH(de);
|
||||
else
|
||||
ext4fs_dirhash(dir, de->name,
|
||||
de->name_len, &h);
|
||||
(void) ext4fs_dirhash(dir,
|
||||
de->name,
|
||||
de->name_len, &h);
|
||||
printk("%*.s:(E)%x.%u ", len, name,
|
||||
h.hash, (unsigned) ((char *) de
|
||||
- base));
|
||||
@@ -720,7 +721,8 @@ static struct stats dx_show_leaf(struct inode *dir,
|
||||
#else
|
||||
int len = de->name_len;
|
||||
char *name = de->name;
|
||||
ext4fs_dirhash(dir, de->name, de->name_len, &h);
|
||||
(void) ext4fs_dirhash(dir, de->name,
|
||||
de->name_len, &h);
|
||||
printk("%*.s:%x.%u ", len, name, h.hash,
|
||||
(unsigned) ((char *) de - base));
|
||||
#endif
|
||||
@@ -849,8 +851,14 @@ dx_probe(struct ext4_filename *fname, struct inode *dir,
|
||||
hinfo->seed = EXT4_SB(dir->i_sb)->s_hash_seed;
|
||||
/* hash is already computed for encrypted casefolded directory */
|
||||
if (fname && fname_name(fname) &&
|
||||
!(IS_ENCRYPTED(dir) && IS_CASEFOLDED(dir)))
|
||||
ext4fs_dirhash(dir, fname_name(fname), fname_len(fname), hinfo);
|
||||
!(IS_ENCRYPTED(dir) && IS_CASEFOLDED(dir))) {
|
||||
int ret = ext4fs_dirhash(dir, fname_name(fname),
|
||||
fname_len(fname), hinfo);
|
||||
if (ret < 0) {
|
||||
ret_err = ERR_PTR(ret);
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
hash = hinfo->hash;
|
||||
|
||||
if (root->info.unused_flags & 1) {
|
||||
@@ -1111,7 +1119,12 @@ static int htree_dirblock_to_tree(struct file *dir_file,
|
||||
hinfo->minor_hash = 0;
|
||||
}
|
||||
} else {
|
||||
ext4fs_dirhash(dir, de->name, de->name_len, hinfo);
|
||||
err = ext4fs_dirhash(dir, de->name,
|
||||
de->name_len, hinfo);
|
||||
if (err < 0) {
|
||||
count = err;
|
||||
goto errout;
|
||||
}
|
||||
}
|
||||
if ((hinfo->hash < start_hash) ||
|
||||
((hinfo->hash == start_hash) &&
|
||||
@@ -1313,8 +1326,12 @@ static int dx_make_map(struct inode *dir, struct buffer_head *bh,
|
||||
if (de->name_len && de->inode) {
|
||||
if (ext4_hash_in_dirent(dir))
|
||||
h.hash = EXT4_DIRENT_HASH(de);
|
||||
else
|
||||
ext4fs_dirhash(dir, de->name, de->name_len, &h);
|
||||
else {
|
||||
int err = ext4fs_dirhash(dir, de->name,
|
||||
de->name_len, &h);
|
||||
if (err < 0)
|
||||
return err;
|
||||
}
|
||||
map_tail--;
|
||||
map_tail->hash = h.hash;
|
||||
map_tail->offs = ((char *) de - base)>>2;
|
||||
@@ -1452,10 +1469,9 @@ int ext4_fname_setup_ci_filename(struct inode *dir, const struct qstr *iname,
|
||||
hinfo->hash_version = DX_HASH_SIPHASH;
|
||||
hinfo->seed = NULL;
|
||||
if (cf_name->name)
|
||||
ext4fs_dirhash(dir, cf_name->name, cf_name->len, hinfo);
|
||||
return ext4fs_dirhash(dir, cf_name->name, cf_name->len, hinfo);
|
||||
else
|
||||
ext4fs_dirhash(dir, iname->name, iname->len, hinfo);
|
||||
return 0;
|
||||
return ext4fs_dirhash(dir, iname->name, iname->len, hinfo);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -2298,10 +2314,15 @@ static int make_indexed_dir(handle_t *handle, struct ext4_filename *fname,
|
||||
fname->hinfo.seed = EXT4_SB(dir->i_sb)->s_hash_seed;
|
||||
|
||||
/* casefolded encrypted hashes are computed on fname setup */
|
||||
if (!ext4_hash_in_dirent(dir))
|
||||
ext4fs_dirhash(dir, fname_name(fname),
|
||||
fname_len(fname), &fname->hinfo);
|
||||
|
||||
if (!ext4_hash_in_dirent(dir)) {
|
||||
int err = ext4fs_dirhash(dir, fname_name(fname),
|
||||
fname_len(fname), &fname->hinfo);
|
||||
if (err < 0) {
|
||||
brelse(bh2);
|
||||
brelse(bh);
|
||||
return err;
|
||||
}
|
||||
}
|
||||
memset(frames, 0, sizeof(frames));
|
||||
frame = frames;
|
||||
frame->entries = entries;
|
||||
|
||||
@@ -5979,9 +5979,6 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
|
||||
}
|
||||
|
||||
#ifdef CONFIG_QUOTA
|
||||
/* Release old quota file names */
|
||||
for (i = 0; i < EXT4_MAXQUOTAS; i++)
|
||||
kfree(old_opts.s_qf_names[i]);
|
||||
if (enable_quota) {
|
||||
if (sb_any_quota_suspended(sb))
|
||||
dquot_resume(sb, -1);
|
||||
@@ -5991,6 +5988,9 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
|
||||
goto restore_opts;
|
||||
}
|
||||
}
|
||||
/* Release old quota file names */
|
||||
for (i = 0; i < EXT4_MAXQUOTAS; i++)
|
||||
kfree(old_opts.s_qf_names[i]);
|
||||
#endif
|
||||
if (!test_opt(sb, BLOCK_VALIDITY) && sbi->s_system_blks)
|
||||
ext4_release_system_zone(sb);
|
||||
@@ -6011,6 +6011,13 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
|
||||
return 0;
|
||||
|
||||
restore_opts:
|
||||
/*
|
||||
* If there was a failing r/w to ro transition, we may need to
|
||||
* re-enable quota
|
||||
*/
|
||||
if ((sb->s_flags & SB_RDONLY) && !(old_sb_flags & SB_RDONLY) &&
|
||||
sb_any_quota_suspended(sb))
|
||||
dquot_resume(sb, -1);
|
||||
sb->s_flags = old_sb_flags;
|
||||
sbi->s_mount_opt = old_opts.s_mount_opt;
|
||||
sbi->s_mount_opt2 = old_opts.s_mount_opt2;
|
||||
|
||||
@@ -825,7 +825,7 @@ void wbc_detach_inode(struct writeback_control *wbc)
|
||||
* is okay. The main goal is avoiding keeping an inode on
|
||||
* the wrong wb for an extended period of time.
|
||||
*/
|
||||
if (hweight32(history) > WB_FRN_HIST_THR_SLOTS)
|
||||
if (hweight16(history) > WB_FRN_HIST_THR_SLOTS)
|
||||
inode_switch_wbs(inode, max_id);
|
||||
}
|
||||
|
||||
|
||||
@@ -120,8 +120,8 @@ out:
|
||||
return rc;
|
||||
}
|
||||
|
||||
static int calc_ntlmv2_hash(struct ksmbd_session *sess, char *ntlmv2_hash,
|
||||
char *dname)
|
||||
static int calc_ntlmv2_hash(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
char *ntlmv2_hash, char *dname)
|
||||
{
|
||||
int ret, len, conv_len;
|
||||
wchar_t *domain = NULL;
|
||||
@@ -157,7 +157,7 @@ static int calc_ntlmv2_hash(struct ksmbd_session *sess, char *ntlmv2_hash,
|
||||
}
|
||||
|
||||
conv_len = smb_strtoUTF16(uniname, user_name(sess->user), len,
|
||||
sess->conn->local_nls);
|
||||
conn->local_nls);
|
||||
if (conv_len < 0 || conv_len > len) {
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
@@ -181,7 +181,7 @@ static int calc_ntlmv2_hash(struct ksmbd_session *sess, char *ntlmv2_hash,
|
||||
}
|
||||
|
||||
conv_len = smb_strtoUTF16((__le16 *)domain, dname, len,
|
||||
sess->conn->local_nls);
|
||||
conn->local_nls);
|
||||
if (conv_len < 0 || conv_len > len) {
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
@@ -214,27 +214,28 @@ out:
|
||||
*
|
||||
* Return: 0 on success, error number on error
|
||||
*/
|
||||
int ksmbd_auth_ntlmv2(struct ksmbd_session *sess, struct ntlmv2_resp *ntlmv2,
|
||||
int blen, char *domain_name)
|
||||
int ksmbd_auth_ntlmv2(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
struct ntlmv2_resp *ntlmv2, int blen, char *domain_name,
|
||||
char *cryptkey)
|
||||
{
|
||||
char ntlmv2_hash[CIFS_ENCPWD_SIZE];
|
||||
char ntlmv2_rsp[CIFS_HMAC_MD5_HASH_SIZE];
|
||||
struct ksmbd_crypto_ctx *ctx;
|
||||
struct ksmbd_crypto_ctx *ctx = NULL;
|
||||
char *construct = NULL;
|
||||
int rc, len;
|
||||
|
||||
rc = calc_ntlmv2_hash(conn, sess, ntlmv2_hash, domain_name);
|
||||
if (rc) {
|
||||
ksmbd_debug(AUTH, "could not get v2 hash rc %d\n", rc);
|
||||
goto out;
|
||||
}
|
||||
|
||||
ctx = ksmbd_crypto_ctx_find_hmacmd5();
|
||||
if (!ctx) {
|
||||
ksmbd_debug(AUTH, "could not crypto alloc hmacmd5\n");
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
rc = calc_ntlmv2_hash(sess, ntlmv2_hash, domain_name);
|
||||
if (rc) {
|
||||
ksmbd_debug(AUTH, "could not get v2 hash rc %d\n", rc);
|
||||
goto out;
|
||||
}
|
||||
|
||||
rc = crypto_shash_setkey(CRYPTO_HMACMD5_TFM(ctx),
|
||||
ntlmv2_hash,
|
||||
CIFS_HMAC_MD5_HASH_SIZE);
|
||||
@@ -256,7 +257,7 @@ int ksmbd_auth_ntlmv2(struct ksmbd_session *sess, struct ntlmv2_resp *ntlmv2,
|
||||
goto out;
|
||||
}
|
||||
|
||||
memcpy(construct, sess->ntlmssp.cryptkey, CIFS_CRYPTO_KEY_SIZE);
|
||||
memcpy(construct, cryptkey, CIFS_CRYPTO_KEY_SIZE);
|
||||
memcpy(construct + CIFS_CRYPTO_KEY_SIZE, &ntlmv2->blob_signature, blen);
|
||||
|
||||
rc = crypto_shash_update(CRYPTO_HMACMD5(ctx), construct, len);
|
||||
@@ -270,6 +271,8 @@ int ksmbd_auth_ntlmv2(struct ksmbd_session *sess, struct ntlmv2_resp *ntlmv2,
|
||||
ksmbd_debug(AUTH, "Could not generate md5 hash\n");
|
||||
goto out;
|
||||
}
|
||||
ksmbd_release_crypto_ctx(ctx);
|
||||
ctx = NULL;
|
||||
|
||||
rc = ksmbd_gen_sess_key(sess, ntlmv2_hash, ntlmv2_rsp);
|
||||
if (rc) {
|
||||
@@ -280,7 +283,8 @@ int ksmbd_auth_ntlmv2(struct ksmbd_session *sess, struct ntlmv2_resp *ntlmv2,
|
||||
if (memcmp(ntlmv2->ntlmv2_hash, ntlmv2_rsp, CIFS_HMAC_MD5_HASH_SIZE) != 0)
|
||||
rc = -EINVAL;
|
||||
out:
|
||||
ksmbd_release_crypto_ctx(ctx);
|
||||
if (ctx)
|
||||
ksmbd_release_crypto_ctx(ctx);
|
||||
kfree(construct);
|
||||
return rc;
|
||||
}
|
||||
@@ -295,7 +299,8 @@ out:
|
||||
* Return: 0 on success, error number on error
|
||||
*/
|
||||
int ksmbd_decode_ntlmssp_auth_blob(struct authenticate_message *authblob,
|
||||
int blob_len, struct ksmbd_session *sess)
|
||||
int blob_len, struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess)
|
||||
{
|
||||
char *domain_name;
|
||||
unsigned int nt_off, dn_off;
|
||||
@@ -325,16 +330,17 @@ int ksmbd_decode_ntlmssp_auth_blob(struct authenticate_message *authblob,
|
||||
|
||||
/* TODO : use domain name that imported from configuration file */
|
||||
domain_name = smb_strndup_from_utf16((const char *)authblob + dn_off,
|
||||
dn_len, true, sess->conn->local_nls);
|
||||
dn_len, true, conn->local_nls);
|
||||
if (IS_ERR(domain_name))
|
||||
return PTR_ERR(domain_name);
|
||||
|
||||
/* process NTLMv2 authentication */
|
||||
ksmbd_debug(AUTH, "decode_ntlmssp_authenticate_blob dname%s\n",
|
||||
domain_name);
|
||||
ret = ksmbd_auth_ntlmv2(sess, (struct ntlmv2_resp *)((char *)authblob + nt_off),
|
||||
ret = ksmbd_auth_ntlmv2(conn, sess,
|
||||
(struct ntlmv2_resp *)((char *)authblob + nt_off),
|
||||
nt_len - CIFS_ENCPWD_SIZE,
|
||||
domain_name);
|
||||
domain_name, conn->ntlmssp.cryptkey);
|
||||
kfree(domain_name);
|
||||
return ret;
|
||||
}
|
||||
@@ -348,7 +354,7 @@ int ksmbd_decode_ntlmssp_auth_blob(struct authenticate_message *authblob,
|
||||
*
|
||||
*/
|
||||
int ksmbd_decode_ntlmssp_neg_blob(struct negotiate_message *negblob,
|
||||
int blob_len, struct ksmbd_session *sess)
|
||||
int blob_len, struct ksmbd_conn *conn)
|
||||
{
|
||||
if (blob_len < sizeof(struct negotiate_message)) {
|
||||
ksmbd_debug(AUTH, "negotiate blob len %d too small\n",
|
||||
@@ -362,7 +368,7 @@ int ksmbd_decode_ntlmssp_neg_blob(struct negotiate_message *negblob,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
sess->ntlmssp.client_flags = le32_to_cpu(negblob->NegotiateFlags);
|
||||
conn->ntlmssp.client_flags = le32_to_cpu(negblob->NegotiateFlags);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -376,14 +382,14 @@ int ksmbd_decode_ntlmssp_neg_blob(struct negotiate_message *negblob,
|
||||
*/
|
||||
unsigned int
|
||||
ksmbd_build_ntlmssp_challenge_blob(struct challenge_message *chgblob,
|
||||
struct ksmbd_session *sess)
|
||||
struct ksmbd_conn *conn)
|
||||
{
|
||||
struct target_info *tinfo;
|
||||
wchar_t *name;
|
||||
__u8 *target_name;
|
||||
unsigned int flags, blob_off, blob_len, type, target_info_len = 0;
|
||||
int len, uni_len, conv_len;
|
||||
int cflags = sess->ntlmssp.client_flags;
|
||||
int cflags = conn->ntlmssp.client_flags;
|
||||
|
||||
memcpy(chgblob->Signature, NTLMSSP_SIGNATURE, 8);
|
||||
chgblob->MessageType = NtLmChallenge;
|
||||
@@ -404,7 +410,7 @@ ksmbd_build_ntlmssp_challenge_blob(struct challenge_message *chgblob,
|
||||
if (cflags & NTLMSSP_REQUEST_TARGET)
|
||||
flags |= NTLMSSP_REQUEST_TARGET;
|
||||
|
||||
if (sess->conn->use_spnego &&
|
||||
if (conn->use_spnego &&
|
||||
(cflags & NTLMSSP_NEGOTIATE_EXTENDED_SEC))
|
||||
flags |= NTLMSSP_NEGOTIATE_EXTENDED_SEC;
|
||||
|
||||
@@ -415,7 +421,7 @@ ksmbd_build_ntlmssp_challenge_blob(struct challenge_message *chgblob,
|
||||
return -ENOMEM;
|
||||
|
||||
conv_len = smb_strtoUTF16((__le16 *)name, ksmbd_netbios_name(), len,
|
||||
sess->conn->local_nls);
|
||||
conn->local_nls);
|
||||
if (conv_len < 0 || conv_len > len) {
|
||||
kfree(name);
|
||||
return -EINVAL;
|
||||
@@ -431,8 +437,8 @@ ksmbd_build_ntlmssp_challenge_blob(struct challenge_message *chgblob,
|
||||
chgblob->TargetName.BufferOffset = cpu_to_le32(blob_off);
|
||||
|
||||
/* Initialize random conn challenge */
|
||||
get_random_bytes(sess->ntlmssp.cryptkey, sizeof(__u64));
|
||||
memcpy(chgblob->Challenge, sess->ntlmssp.cryptkey,
|
||||
get_random_bytes(conn->ntlmssp.cryptkey, sizeof(__u64));
|
||||
memcpy(chgblob->Challenge, conn->ntlmssp.cryptkey,
|
||||
CIFS_CRYPTO_KEY_SIZE);
|
||||
|
||||
/* Add Target Information to security buffer */
|
||||
@@ -632,8 +638,9 @@ struct derivation {
|
||||
bool binding;
|
||||
};
|
||||
|
||||
static int generate_key(struct ksmbd_session *sess, struct kvec label,
|
||||
struct kvec context, __u8 *key, unsigned int key_size)
|
||||
static int generate_key(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
struct kvec label, struct kvec context, __u8 *key,
|
||||
unsigned int key_size)
|
||||
{
|
||||
unsigned char zero = 0x0;
|
||||
__u8 i[4] = {0, 0, 0, 1};
|
||||
@@ -693,8 +700,8 @@ static int generate_key(struct ksmbd_session *sess, struct kvec label,
|
||||
goto smb3signkey_ret;
|
||||
}
|
||||
|
||||
if (sess->conn->cipher_type == SMB2_ENCRYPTION_AES256_CCM ||
|
||||
sess->conn->cipher_type == SMB2_ENCRYPTION_AES256_GCM)
|
||||
if (conn->cipher_type == SMB2_ENCRYPTION_AES256_CCM ||
|
||||
conn->cipher_type == SMB2_ENCRYPTION_AES256_GCM)
|
||||
rc = crypto_shash_update(CRYPTO_HMACSHA256(ctx), L256, 4);
|
||||
else
|
||||
rc = crypto_shash_update(CRYPTO_HMACSHA256(ctx), L128, 4);
|
||||
@@ -729,17 +736,17 @@ static int generate_smb3signingkey(struct ksmbd_session *sess,
|
||||
if (!chann)
|
||||
return 0;
|
||||
|
||||
if (sess->conn->dialect >= SMB30_PROT_ID && signing->binding)
|
||||
if (conn->dialect >= SMB30_PROT_ID && signing->binding)
|
||||
key = chann->smb3signingkey;
|
||||
else
|
||||
key = sess->smb3signingkey;
|
||||
|
||||
rc = generate_key(sess, signing->label, signing->context, key,
|
||||
rc = generate_key(conn, sess, signing->label, signing->context, key,
|
||||
SMB3_SIGN_KEY_SIZE);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
if (!(sess->conn->dialect >= SMB30_PROT_ID && signing->binding))
|
||||
if (!(conn->dialect >= SMB30_PROT_ID && signing->binding))
|
||||
memcpy(chann->smb3signingkey, key, SMB3_SIGN_KEY_SIZE);
|
||||
|
||||
ksmbd_debug(AUTH, "dumping generated AES signing keys\n");
|
||||
@@ -793,30 +800,31 @@ struct derivation_twin {
|
||||
struct derivation decryption;
|
||||
};
|
||||
|
||||
static int generate_smb3encryptionkey(struct ksmbd_session *sess,
|
||||
static int generate_smb3encryptionkey(struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess,
|
||||
const struct derivation_twin *ptwin)
|
||||
{
|
||||
int rc;
|
||||
|
||||
rc = generate_key(sess, ptwin->encryption.label,
|
||||
rc = generate_key(conn, sess, ptwin->encryption.label,
|
||||
ptwin->encryption.context, sess->smb3encryptionkey,
|
||||
SMB3_ENC_DEC_KEY_SIZE);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
rc = generate_key(sess, ptwin->decryption.label,
|
||||
rc = generate_key(conn, sess, ptwin->decryption.label,
|
||||
ptwin->decryption.context,
|
||||
sess->smb3decryptionkey, SMB3_ENC_DEC_KEY_SIZE);
|
||||
if (rc)
|
||||
return rc;
|
||||
|
||||
ksmbd_debug(AUTH, "dumping generated AES encryption keys\n");
|
||||
ksmbd_debug(AUTH, "Cipher type %d\n", sess->conn->cipher_type);
|
||||
ksmbd_debug(AUTH, "Cipher type %d\n", conn->cipher_type);
|
||||
ksmbd_debug(AUTH, "Session Id %llu\n", sess->id);
|
||||
ksmbd_debug(AUTH, "Session Key %*ph\n",
|
||||
SMB2_NTLMV2_SESSKEY_SIZE, sess->sess_key);
|
||||
if (sess->conn->cipher_type == SMB2_ENCRYPTION_AES256_CCM ||
|
||||
sess->conn->cipher_type == SMB2_ENCRYPTION_AES256_GCM) {
|
||||
if (conn->cipher_type == SMB2_ENCRYPTION_AES256_CCM ||
|
||||
conn->cipher_type == SMB2_ENCRYPTION_AES256_GCM) {
|
||||
ksmbd_debug(AUTH, "ServerIn Key %*ph\n",
|
||||
SMB3_GCM256_CRYPTKEY_SIZE, sess->smb3encryptionkey);
|
||||
ksmbd_debug(AUTH, "ServerOut Key %*ph\n",
|
||||
@@ -830,7 +838,8 @@ static int generate_smb3encryptionkey(struct ksmbd_session *sess,
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ksmbd_gen_smb30_encryptionkey(struct ksmbd_session *sess)
|
||||
int ksmbd_gen_smb30_encryptionkey(struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess)
|
||||
{
|
||||
struct derivation_twin twin;
|
||||
struct derivation *d;
|
||||
@@ -847,10 +856,11 @@ int ksmbd_gen_smb30_encryptionkey(struct ksmbd_session *sess)
|
||||
d->context.iov_base = "ServerIn ";
|
||||
d->context.iov_len = 10;
|
||||
|
||||
return generate_smb3encryptionkey(sess, &twin);
|
||||
return generate_smb3encryptionkey(conn, sess, &twin);
|
||||
}
|
||||
|
||||
int ksmbd_gen_smb311_encryptionkey(struct ksmbd_session *sess)
|
||||
int ksmbd_gen_smb311_encryptionkey(struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess)
|
||||
{
|
||||
struct derivation_twin twin;
|
||||
struct derivation *d;
|
||||
@@ -867,7 +877,7 @@ int ksmbd_gen_smb311_encryptionkey(struct ksmbd_session *sess)
|
||||
d->context.iov_base = sess->Preauth_HashValue;
|
||||
d->context.iov_len = 64;
|
||||
|
||||
return generate_smb3encryptionkey(sess, &twin);
|
||||
return generate_smb3encryptionkey(conn, sess, &twin);
|
||||
}
|
||||
|
||||
int ksmbd_gen_preauth_integrity_hash(struct ksmbd_conn *conn, char *buf,
|
||||
|
||||
@@ -38,16 +38,17 @@ struct kvec;
|
||||
int ksmbd_crypt_message(struct ksmbd_conn *conn, struct kvec *iov,
|
||||
unsigned int nvec, int enc);
|
||||
void ksmbd_copy_gss_neg_header(void *buf);
|
||||
int ksmbd_auth_ntlm(struct ksmbd_session *sess, char *pw_buf);
|
||||
int ksmbd_auth_ntlmv2(struct ksmbd_session *sess, struct ntlmv2_resp *ntlmv2,
|
||||
int blen, char *domain_name);
|
||||
int ksmbd_auth_ntlmv2(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
struct ntlmv2_resp *ntlmv2, int blen, char *domain_name,
|
||||
char *cryptkey);
|
||||
int ksmbd_decode_ntlmssp_auth_blob(struct authenticate_message *authblob,
|
||||
int blob_len, struct ksmbd_session *sess);
|
||||
int blob_len, struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess);
|
||||
int ksmbd_decode_ntlmssp_neg_blob(struct negotiate_message *negblob,
|
||||
int blob_len, struct ksmbd_session *sess);
|
||||
int blob_len, struct ksmbd_conn *conn);
|
||||
unsigned int
|
||||
ksmbd_build_ntlmssp_challenge_blob(struct challenge_message *chgblob,
|
||||
struct ksmbd_session *sess);
|
||||
struct ksmbd_conn *conn);
|
||||
int ksmbd_krb5_authenticate(struct ksmbd_session *sess, char *in_blob,
|
||||
int in_len, char *out_blob, int *out_len);
|
||||
int ksmbd_sign_smb2_pdu(struct ksmbd_conn *conn, char *key, struct kvec *iov,
|
||||
@@ -58,8 +59,10 @@ int ksmbd_gen_smb30_signingkey(struct ksmbd_session *sess,
|
||||
struct ksmbd_conn *conn);
|
||||
int ksmbd_gen_smb311_signingkey(struct ksmbd_session *sess,
|
||||
struct ksmbd_conn *conn);
|
||||
int ksmbd_gen_smb30_encryptionkey(struct ksmbd_session *sess);
|
||||
int ksmbd_gen_smb311_encryptionkey(struct ksmbd_session *sess);
|
||||
int ksmbd_gen_smb30_encryptionkey(struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess);
|
||||
int ksmbd_gen_smb311_encryptionkey(struct ksmbd_conn *conn,
|
||||
struct ksmbd_session *sess);
|
||||
int ksmbd_gen_preauth_integrity_hash(struct ksmbd_conn *conn, char *buf,
|
||||
__u8 *pi_hash);
|
||||
int ksmbd_gen_sd_hash(struct ksmbd_conn *conn, char *sd_buf, int len,
|
||||
|
||||
@@ -36,6 +36,7 @@ void ksmbd_conn_free(struct ksmbd_conn *conn)
|
||||
list_del(&conn->conns_list);
|
||||
write_unlock(&conn_list_lock);
|
||||
|
||||
xa_destroy(&conn->sessions);
|
||||
kvfree(conn->request_buf);
|
||||
kfree(conn->preauth_info);
|
||||
kfree(conn);
|
||||
@@ -66,12 +67,12 @@ struct ksmbd_conn *ksmbd_conn_alloc(void)
|
||||
|
||||
init_waitqueue_head(&conn->req_running_q);
|
||||
INIT_LIST_HEAD(&conn->conns_list);
|
||||
INIT_LIST_HEAD(&conn->sessions);
|
||||
INIT_LIST_HEAD(&conn->requests);
|
||||
INIT_LIST_HEAD(&conn->async_requests);
|
||||
spin_lock_init(&conn->request_lock);
|
||||
spin_lock_init(&conn->credits_lock);
|
||||
ida_init(&conn->async_ida);
|
||||
xa_init(&conn->sessions);
|
||||
|
||||
spin_lock_init(&conn->llist_lock);
|
||||
INIT_LIST_HEAD(&conn->lock_list);
|
||||
|
||||
@@ -20,13 +20,6 @@
|
||||
|
||||
#define KSMBD_SOCKET_BACKLOG 16
|
||||
|
||||
/*
|
||||
* WARNING
|
||||
*
|
||||
* This is nothing but a HACK. Session status should move to channel
|
||||
* or to session. As of now we have 1 tcp_conn : 1 ksmbd_session, but
|
||||
* we need to change it to 1 tcp_conn : N ksmbd_sessions.
|
||||
*/
|
||||
enum {
|
||||
KSMBD_SESS_NEW = 0,
|
||||
KSMBD_SESS_GOOD,
|
||||
@@ -55,7 +48,7 @@ struct ksmbd_conn {
|
||||
struct nls_table *local_nls;
|
||||
struct list_head conns_list;
|
||||
/* smb session 1 per user */
|
||||
struct list_head sessions;
|
||||
struct xarray sessions;
|
||||
unsigned long last_active;
|
||||
/* How many request are running currently */
|
||||
atomic_t req_running;
|
||||
@@ -72,12 +65,7 @@ struct ksmbd_conn {
|
||||
int connection_type;
|
||||
struct ksmbd_stats stats;
|
||||
char ClientGUID[SMB2_CLIENT_GUID_SIZE];
|
||||
union {
|
||||
/* pending trans request table */
|
||||
struct trans_state *recent_trans;
|
||||
/* Used by ntlmssp */
|
||||
char *ntlmssp_cryptkey;
|
||||
};
|
||||
struct ntlmssp_auth ntlmssp;
|
||||
|
||||
spinlock_t llist_lock;
|
||||
struct list_head lock_list;
|
||||
|
||||
@@ -16,7 +16,8 @@
|
||||
#include "user_session.h"
|
||||
|
||||
struct ksmbd_tree_conn_status
|
||||
ksmbd_tree_conn_connect(struct ksmbd_session *sess, char *share_name)
|
||||
ksmbd_tree_conn_connect(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
char *share_name)
|
||||
{
|
||||
struct ksmbd_tree_conn_status status = {-ENOENT, NULL};
|
||||
struct ksmbd_tree_connect_response *resp = NULL;
|
||||
@@ -41,7 +42,7 @@ ksmbd_tree_conn_connect(struct ksmbd_session *sess, char *share_name)
|
||||
goto out_error;
|
||||
}
|
||||
|
||||
peer_addr = KSMBD_TCP_PEER_SOCKADDR(sess->conn);
|
||||
peer_addr = KSMBD_TCP_PEER_SOCKADDR(conn);
|
||||
resp = ksmbd_ipc_tree_connect_request(sess,
|
||||
sc,
|
||||
tree_conn,
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
|
||||
struct ksmbd_share_config;
|
||||
struct ksmbd_user;
|
||||
struct ksmbd_conn;
|
||||
|
||||
struct ksmbd_tree_connect {
|
||||
int id;
|
||||
@@ -40,7 +41,8 @@ static inline int test_tree_conn_flag(struct ksmbd_tree_connect *tree_conn,
|
||||
struct ksmbd_session;
|
||||
|
||||
struct ksmbd_tree_conn_status
|
||||
ksmbd_tree_conn_connect(struct ksmbd_session *sess, char *share_name);
|
||||
ksmbd_tree_conn_connect(struct ksmbd_conn *conn, struct ksmbd_session *sess,
|
||||
char *share_name);
|
||||
|
||||
int ksmbd_tree_conn_disconnect(struct ksmbd_session *sess,
|
||||
struct ksmbd_tree_connect *tree_conn);
|
||||
|
||||
@@ -67,3 +67,13 @@ int ksmbd_anonymous_user(struct ksmbd_user *user)
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool ksmbd_compare_user(struct ksmbd_user *u1, struct ksmbd_user *u2)
|
||||
{
|
||||
if (strcmp(u1->name, u2->name))
|
||||
return false;
|
||||
if (memcmp(u1->passkey, u2->passkey, u1->passkey_sz))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -64,4 +64,5 @@ struct ksmbd_user *ksmbd_login_user(const char *account);
|
||||
struct ksmbd_user *ksmbd_alloc_user(struct ksmbd_login_response *resp);
|
||||
void ksmbd_free_user(struct ksmbd_user *user);
|
||||
int ksmbd_anonymous_user(struct ksmbd_user *user);
|
||||
bool ksmbd_compare_user(struct ksmbd_user *u1, struct ksmbd_user *u2);
|
||||
#endif /* __USER_CONFIG_MANAGEMENT_H__ */
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user