mirror of
https://github.com/torvalds/linux.git
synced 2026-06-06 05:27:07 +02:00
Merge a1bffa4874 ("Merge tag 'scsi-fixes' of git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi") into 'android-mainline'
Fixes up a merge issue in: net/ipv6/route.c on the way to a 5.9-rc7 release. Signed-off-by: Greg Kroah-Hartman <gregkh@google.com> Change-Id: I4eb508eb3761b95ad8f39dd79f03b3352481ceaf
This commit is contained in:
commit
fb3b36d52f
|
|
@ -1324,15 +1324,26 @@ PAGE_SIZE multiple when read back.
|
|||
pgmajfault
|
||||
Number of major page faults incurred
|
||||
|
||||
workingset_refault
|
||||
Number of refaults of previously evicted pages
|
||||
workingset_refault_anon
|
||||
Number of refaults of previously evicted anonymous pages.
|
||||
|
||||
workingset_activate
|
||||
Number of refaulted pages that were immediately activated
|
||||
workingset_refault_file
|
||||
Number of refaults of previously evicted file pages.
|
||||
|
||||
workingset_restore
|
||||
Number of restored pages which have been detected as an active
|
||||
workingset before they got reclaimed.
|
||||
workingset_activate_anon
|
||||
Number of refaulted anonymous pages that were immediately
|
||||
activated.
|
||||
|
||||
workingset_activate_file
|
||||
Number of refaulted file pages that were immediately activated.
|
||||
|
||||
workingset_restore_anon
|
||||
Number of restored anonymous pages which have been detected as
|
||||
an active workingset before they got reclaimed.
|
||||
|
||||
workingset_restore_file
|
||||
Number of restored file pages which have been detected as an
|
||||
active workingset before they got reclaimed.
|
||||
|
||||
workingset_nodereclaim
|
||||
Number of times a shadow node has been reclaimed
|
||||
|
|
|
|||
|
|
@ -67,7 +67,7 @@ Parameters::
|
|||
the value passed in <key_size>.
|
||||
|
||||
<key_type>
|
||||
Either 'logon' or 'user' kernel key type.
|
||||
Either 'logon', 'user' or 'encrypted' kernel key type.
|
||||
|
||||
<key_description>
|
||||
The kernel keyring key description crypt target should look for
|
||||
|
|
@ -121,6 +121,14 @@ submit_from_crypt_cpus
|
|||
thread because it benefits CFQ to have writes submitted using the
|
||||
same context.
|
||||
|
||||
no_read_workqueue
|
||||
Bypass dm-crypt internal workqueue and process read requests synchronously.
|
||||
|
||||
no_write_workqueue
|
||||
Bypass dm-crypt internal workqueue and process write requests synchronously.
|
||||
This option is automatically enabled for host-managed zoned block devices
|
||||
(e.g. host-managed SMR hard-disks).
|
||||
|
||||
integrity:<bytes>:<type>
|
||||
The device requires additional <bytes> metadata per-sector stored
|
||||
in per-bio integrity structure. This metadata must by provided
|
||||
|
|
|
|||
|
|
@ -182,9 +182,6 @@ in the order of reservations, but only after all previous records where
|
|||
already committed. It is thus possible for slow producers to temporarily hold
|
||||
off submitted records, that were reserved later.
|
||||
|
||||
Reservation/commit/consumer protocol is verified by litmus tests in
|
||||
Documentation/litmus_tests/bpf-rb/_.
|
||||
|
||||
One interesting implementation bit, that significantly simplifies (and thus
|
||||
speeds up as well) implementation of both producers and consumers is how data
|
||||
area is mapped twice contiguously back-to-back in the virtual memory. This
|
||||
|
|
@ -200,7 +197,7 @@ a self-pacing notifications of new data being availability.
|
|||
being available after commit only if consumer has already caught up right up to
|
||||
the record being committed. If not, consumer still has to catch up and thus
|
||||
will see new data anyways without needing an extra poll notification.
|
||||
Benchmarks (see tools/testing/selftests/bpf/benchs/bench_ringbuf.c_) show that
|
||||
Benchmarks (see tools/testing/selftests/bpf/benchs/bench_ringbufs.c) show that
|
||||
this allows to achieve a very high throughput without having to resort to
|
||||
tricks like "notify only every Nth sample", which are necessary with perf
|
||||
buffer. For extreme cases, when BPF program wants more manual control of
|
||||
|
|
|
|||
|
|
@ -1,38 +0,0 @@
|
|||
* Sony 1/2.5-Inch 8.51Mp CMOS Digital Image Sensor
|
||||
|
||||
The Sony imx274 is a 1/2.5-inch CMOS active pixel digital image sensor with
|
||||
an active array size of 3864H x 2202V. It is programmable through I2C
|
||||
interface. The I2C address is fixed to 0x1a as per sensor data sheet.
|
||||
Image data is sent through MIPI CSI-2, which is configured as 4 lanes
|
||||
at 1440 Mbps.
|
||||
|
||||
|
||||
Required Properties:
|
||||
- compatible: value should be "sony,imx274" for imx274 sensor
|
||||
- reg: I2C bus address of the device
|
||||
|
||||
Optional Properties:
|
||||
- reset-gpios: Sensor reset GPIO
|
||||
- clocks: Reference to the input clock.
|
||||
- clock-names: Should be "inck".
|
||||
- VANA-supply: Sensor 2.8v analog supply.
|
||||
- VDIG-supply: Sensor 1.8v digital core supply.
|
||||
- VDDL-supply: Sensor digital IO 1.2v supply.
|
||||
|
||||
The imx274 device node should contain one 'port' child node with
|
||||
an 'endpoint' subnode. For further reading on port node refer to
|
||||
Documentation/devicetree/bindings/media/video-interfaces.txt.
|
||||
|
||||
Example:
|
||||
sensor@1a {
|
||||
compatible = "sony,imx274";
|
||||
reg = <0x1a>;
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
reset-gpios = <&gpio_sensor 0 0>;
|
||||
port {
|
||||
sensor_out: endpoint {
|
||||
remote-endpoint = <&csiss_in>;
|
||||
};
|
||||
};
|
||||
};
|
||||
76
Documentation/devicetree/bindings/media/i2c/sony,imx274.yaml
Normal file
76
Documentation/devicetree/bindings/media/i2c/sony,imx274.yaml
Normal file
|
|
@ -0,0 +1,76 @@
|
|||
# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause)
|
||||
%YAML 1.2
|
||||
---
|
||||
$id: http://devicetree.org/schemas/media/i2c/sony,imx274.yaml#
|
||||
$schema: http://devicetree.org/meta-schemas/core.yaml#
|
||||
|
||||
title: Sony 1/2.5-Inch 8.51MP CMOS Digital Image Sensor
|
||||
|
||||
maintainers:
|
||||
- Leon Luo <leonl@leopardimaging.com>
|
||||
|
||||
description: |
|
||||
The Sony IMX274 is a 1/2.5-inch CMOS active pixel digital image sensor with an
|
||||
active array size of 3864H x 2202V. It is programmable through I2C interface.
|
||||
Image data is sent through MIPI CSI-2, which is configured as 4 lanes at 1440
|
||||
Mbps.
|
||||
|
||||
properties:
|
||||
compatible:
|
||||
const: sony,imx274
|
||||
|
||||
reg:
|
||||
const: 0x1a
|
||||
|
||||
reset-gpios:
|
||||
maxItems: 1
|
||||
|
||||
clocks:
|
||||
maxItems: 1
|
||||
|
||||
clock-names:
|
||||
const: inck
|
||||
|
||||
vana-supply:
|
||||
description: Sensor 2.8 V analog supply.
|
||||
maxItems: 1
|
||||
|
||||
vdig-supply:
|
||||
description: Sensor 1.8 V digital core supply.
|
||||
maxItems: 1
|
||||
|
||||
vddl-supply:
|
||||
description: Sensor digital IO 1.2 V supply.
|
||||
maxItems: 1
|
||||
|
||||
port:
|
||||
type: object
|
||||
description: Output video port. See ../video-interfaces.txt.
|
||||
|
||||
required:
|
||||
- compatible
|
||||
- reg
|
||||
- port
|
||||
|
||||
additionalProperties: false
|
||||
|
||||
examples:
|
||||
- |
|
||||
i2c0 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
|
||||
imx274: camera-sensor@1a {
|
||||
compatible = "sony,imx274";
|
||||
reg = <0x1a>;
|
||||
reset-gpios = <&gpio_sensor 0 0>;
|
||||
|
||||
port {
|
||||
sensor_out: endpoint {
|
||||
remote-endpoint = <&csiss_in>;
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
...
|
||||
|
|
@ -206,6 +206,7 @@ Userspace to kernel:
|
|||
``ETHTOOL_MSG_TSINFO_GET`` get timestamping info
|
||||
``ETHTOOL_MSG_CABLE_TEST_ACT`` action start cable test
|
||||
``ETHTOOL_MSG_CABLE_TEST_TDR_ACT`` action start raw TDR cable test
|
||||
``ETHTOOL_MSG_TUNNEL_INFO_GET`` get tunnel offload info
|
||||
===================================== ================================
|
||||
|
||||
Kernel to userspace:
|
||||
|
|
@ -239,6 +240,7 @@ Kernel to userspace:
|
|||
``ETHTOOL_MSG_TSINFO_GET_REPLY`` timestamping info
|
||||
``ETHTOOL_MSG_CABLE_TEST_NTF`` Cable test results
|
||||
``ETHTOOL_MSG_CABLE_TEST_TDR_NTF`` Cable test TDR results
|
||||
``ETHTOOL_MSG_TUNNEL_INFO_GET_REPLY`` tunnel offload info
|
||||
===================================== =================================
|
||||
|
||||
``GET`` requests are sent by userspace applications to retrieve device
|
||||
|
|
@ -1363,4 +1365,5 @@ are netlink only.
|
|||
``ETHTOOL_SFECPARAM`` n/a
|
||||
n/a ''ETHTOOL_MSG_CABLE_TEST_ACT''
|
||||
n/a ''ETHTOOL_MSG_CABLE_TEST_TDR_ACT''
|
||||
n/a ``ETHTOOL_MSG_TUNNEL_INFO_GET``
|
||||
=================================== =====================================
|
||||
|
|
|
|||
|
|
@ -701,23 +701,6 @@ Memory Consistency Flags
|
|||
:stub-columns: 0
|
||||
:widths: 3 1 4
|
||||
|
||||
* .. _`V4L2-FLAG-MEMORY-NON-CONSISTENT`:
|
||||
|
||||
- ``V4L2_FLAG_MEMORY_NON_CONSISTENT``
|
||||
- 0x00000001
|
||||
- A buffer is allocated either in consistent (it will be automatically
|
||||
coherent between the CPU and the bus) or non-consistent memory. The
|
||||
latter can provide performance gains, for instance the CPU cache
|
||||
sync/flush operations can be avoided if the buffer is accessed by the
|
||||
corresponding device only and the CPU does not read/write to/from that
|
||||
buffer. However, this requires extra care from the driver -- it must
|
||||
guarantee memory consistency by issuing a cache flush/sync when
|
||||
consistency is needed. If this flag is set V4L2 will attempt to
|
||||
allocate the buffer in non-consistent memory. The flag takes effect
|
||||
only if the buffer is used for :ref:`memory mapping <mmap>` I/O and the
|
||||
queue reports the :ref:`V4L2_BUF_CAP_SUPPORTS_MMAP_CACHE_HINTS
|
||||
<V4L2-BUF-CAP-SUPPORTS-MMAP-CACHE-HINTS>` capability.
|
||||
|
||||
.. c:type:: v4l2_memory
|
||||
|
||||
enum v4l2_memory
|
||||
|
|
|
|||
|
|
@ -120,13 +120,9 @@ than the number requested.
|
|||
If you want to just query the capabilities without making any
|
||||
other changes, then set ``count`` to 0, ``memory`` to
|
||||
``V4L2_MEMORY_MMAP`` and ``format.type`` to the buffer type.
|
||||
* - __u32
|
||||
- ``flags``
|
||||
- Specifies additional buffer management attributes.
|
||||
See :ref:`memory-flags`.
|
||||
|
||||
* - __u32
|
||||
- ``reserved``\ [6]
|
||||
- ``reserved``\ [7]
|
||||
- A place holder for future extensions. Drivers and applications
|
||||
must set the array to zero.
|
||||
|
||||
|
|
|
|||
|
|
@ -112,17 +112,10 @@ aborting or finishing any DMA in progress, an implicit
|
|||
``V4L2_MEMORY_MMAP`` and ``type`` set to the buffer type. This will
|
||||
free any previously allocated buffers, so this is typically something
|
||||
that will be done at the start of the application.
|
||||
* - union {
|
||||
- (anonymous)
|
||||
* - __u32
|
||||
- ``flags``
|
||||
- Specifies additional buffer management attributes.
|
||||
See :ref:`memory-flags`.
|
||||
* - __u32
|
||||
- ``reserved``\ [1]
|
||||
- Kept for backwards compatibility. Use ``flags`` instead.
|
||||
* - }
|
||||
-
|
||||
- A place holder for future extensions. Drivers and applications
|
||||
must set the array to zero.
|
||||
|
||||
.. tabularcolumns:: |p{6.1cm}|p{2.2cm}|p{8.7cm}|
|
||||
|
||||
|
|
@ -169,7 +162,6 @@ aborting or finishing any DMA in progress, an implicit
|
|||
- This capability is set by the driver to indicate that the queue supports
|
||||
cache and memory management hints. However, it's only valid when the
|
||||
queue is used for :ref:`memory mapping <mmap>` streaming I/O. See
|
||||
:ref:`V4L2_FLAG_MEMORY_NON_CONSISTENT <V4L2-FLAG-MEMORY-NON-CONSISTENT>`,
|
||||
:ref:`V4L2_BUF_FLAG_NO_CACHE_INVALIDATE <V4L2-BUF-FLAG-NO-CACHE-INVALIDATE>` and
|
||||
:ref:`V4L2_BUF_FLAG_NO_CACHE_CLEAN <V4L2-BUF-FLAG-NO-CACHE-CLEAN>`.
|
||||
|
||||
|
|
|
|||
|
|
@ -6173,3 +6173,23 @@ specific interfaces must be consistent, i.e. if one says the feature
|
|||
is supported, than the other should as well and vice versa. For arm64
|
||||
see Documentation/virt/kvm/devices/vcpu.rst "KVM_ARM_VCPU_PVTIME_CTRL".
|
||||
For x86 see Documentation/virt/kvm/msr.rst "MSR_KVM_STEAL_TIME".
|
||||
|
||||
8.25 KVM_CAP_S390_DIAG318
|
||||
-------------------------
|
||||
|
||||
:Architectures: s390
|
||||
|
||||
This capability enables a guest to set information about its control program
|
||||
(i.e. guest kernel type and version). The information is helpful during
|
||||
system/firmware service events, providing additional data about the guest
|
||||
environments running on the machine.
|
||||
|
||||
The information is associated with the DIAGNOSE 0x318 instruction, which sets
|
||||
an 8-byte value consisting of a one-byte Control Program Name Code (CPNC) and
|
||||
a 7-byte Control Program Version Code (CPVC). The CPNC determines what
|
||||
environment the control program is running in (e.g. Linux, z/VM...), and the
|
||||
CPVC is used for information specific to OS (e.g. Linux version, Linux
|
||||
distribution...)
|
||||
|
||||
If this capability is available, then the CPNC and CPVC can be synchronized
|
||||
between KVM and userspace via the sync regs mechanism (KVM_SYNC_DIAG318).
|
||||
|
|
|
|||
17
MAINTAINERS
17
MAINTAINERS
|
|
@ -4408,12 +4408,6 @@ T: git git://git.infradead.org/users/hch/configfs.git
|
|||
F: fs/configfs/
|
||||
F: include/linux/configfs.h
|
||||
|
||||
CONNECTOR
|
||||
M: Evgeniy Polyakov <zbr@ioremap.net>
|
||||
L: netdev@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/connector/
|
||||
|
||||
CONSOLE SUBSYSTEM
|
||||
M: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
|
||||
S: Supported
|
||||
|
|
@ -8329,8 +8323,9 @@ S: Supported
|
|||
F: drivers/pci/hotplug/rpaphp*
|
||||
|
||||
IBM Power SRIOV Virtual NIC Device Driver
|
||||
M: Thomas Falcon <tlfalcon@linux.ibm.com>
|
||||
M: John Allen <jallen@linux.ibm.com>
|
||||
M: Dany Madden <drt@linux.ibm.com>
|
||||
M: Lijun Pan <ljp@linux.ibm.com>
|
||||
M: Sukadev Bhattiprolu <sukadev@linux.ibm.com>
|
||||
L: netdev@vger.kernel.org
|
||||
S: Supported
|
||||
F: drivers/net/ethernet/ibm/ibmvnic.*
|
||||
|
|
@ -8344,7 +8339,7 @@ F: arch/powerpc/platforms/powernv/copy-paste.h
|
|||
F: arch/powerpc/platforms/powernv/vas*
|
||||
|
||||
IBM Power Virtual Ethernet Device Driver
|
||||
M: Thomas Falcon <tlfalcon@linux.ibm.com>
|
||||
M: Cristobal Forno <cforno12@linux.ibm.com>
|
||||
L: netdev@vger.kernel.org
|
||||
S: Supported
|
||||
F: drivers/net/ethernet/ibm/ibmveth.*
|
||||
|
|
@ -11049,6 +11044,7 @@ F: drivers/char/hw_random/mtk-rng.c
|
|||
|
||||
MEDIATEK SWITCH DRIVER
|
||||
M: Sean Wang <sean.wang@mediatek.com>
|
||||
M: Landen Chao <Landen.Chao@mediatek.com>
|
||||
L: netdev@vger.kernel.org
|
||||
S: Maintained
|
||||
F: drivers/net/dsa/mt7530.*
|
||||
|
|
@ -12062,6 +12058,7 @@ Q: http://patchwork.ozlabs.org/project/netdev/list/
|
|||
T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net.git
|
||||
T: git git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git
|
||||
F: Documentation/devicetree/bindings/net/
|
||||
F: drivers/connector/
|
||||
F: drivers/net/
|
||||
F: include/linux/etherdevice.h
|
||||
F: include/linux/fcdevice.h
|
||||
|
|
@ -16170,7 +16167,7 @@ M: Leon Luo <leonl@leopardimaging.com>
|
|||
L: linux-media@vger.kernel.org
|
||||
S: Maintained
|
||||
T: git git://linuxtv.org/media_tree.git
|
||||
F: Documentation/devicetree/bindings/media/i2c/imx274.txt
|
||||
F: Documentation/devicetree/bindings/media/i2c/sony,imx274.yaml
|
||||
F: drivers/media/i2c/imx274.c
|
||||
|
||||
SONY IMX290 SENSOR DRIVER
|
||||
|
|
|
|||
|
|
@ -116,7 +116,6 @@ spi2: spi@400 {
|
|||
switch0: ksz8563@0 {
|
||||
compatible = "microchip,ksz8563";
|
||||
reg = <0>;
|
||||
phy-mode = "mii";
|
||||
reset-gpios = <&pioA PIN_PD4 GPIO_ACTIVE_LOW>;
|
||||
|
||||
spi-max-frequency = <500000>;
|
||||
|
|
@ -140,6 +139,7 @@ port@2 {
|
|||
reg = <2>;
|
||||
label = "cpu";
|
||||
ethernet = <&macb0>;
|
||||
phy-mode = "mii";
|
||||
fixed-link {
|
||||
speed = <100>;
|
||||
full-duplex;
|
||||
|
|
|
|||
|
|
@ -298,15 +298,15 @@ static __always_inline int kvm_vcpu_dabt_get_rd(const struct kvm_vcpu *vcpu)
|
|||
return (kvm_vcpu_get_esr(vcpu) & ESR_ELx_SRT_MASK) >> ESR_ELx_SRT_SHIFT;
|
||||
}
|
||||
|
||||
static __always_inline bool kvm_vcpu_dabt_iss1tw(const struct kvm_vcpu *vcpu)
|
||||
static __always_inline bool kvm_vcpu_abt_iss1tw(const struct kvm_vcpu *vcpu)
|
||||
{
|
||||
return !!(kvm_vcpu_get_esr(vcpu) & ESR_ELx_S1PTW);
|
||||
}
|
||||
|
||||
/* Always check for S1PTW *before* using this. */
|
||||
static __always_inline bool kvm_vcpu_dabt_iswrite(const struct kvm_vcpu *vcpu)
|
||||
{
|
||||
return !!(kvm_vcpu_get_esr(vcpu) & ESR_ELx_WNR) ||
|
||||
kvm_vcpu_dabt_iss1tw(vcpu); /* AF/DBM update */
|
||||
return kvm_vcpu_get_esr(vcpu) & ESR_ELx_WNR;
|
||||
}
|
||||
|
||||
static inline bool kvm_vcpu_dabt_is_cm(const struct kvm_vcpu *vcpu)
|
||||
|
|
@ -335,6 +335,11 @@ static inline bool kvm_vcpu_trap_is_iabt(const struct kvm_vcpu *vcpu)
|
|||
return kvm_vcpu_trap_get_class(vcpu) == ESR_ELx_EC_IABT_LOW;
|
||||
}
|
||||
|
||||
static inline bool kvm_vcpu_trap_is_exec_fault(const struct kvm_vcpu *vcpu)
|
||||
{
|
||||
return kvm_vcpu_trap_is_iabt(vcpu) && !kvm_vcpu_abt_iss1tw(vcpu);
|
||||
}
|
||||
|
||||
static __always_inline u8 kvm_vcpu_trap_get_fault(const struct kvm_vcpu *vcpu)
|
||||
{
|
||||
return kvm_vcpu_get_esr(vcpu) & ESR_ELx_FSC;
|
||||
|
|
@ -372,6 +377,9 @@ static __always_inline int kvm_vcpu_sys_get_rt(struct kvm_vcpu *vcpu)
|
|||
|
||||
static inline bool kvm_is_write_fault(struct kvm_vcpu *vcpu)
|
||||
{
|
||||
if (kvm_vcpu_abt_iss1tw(vcpu))
|
||||
return true;
|
||||
|
||||
if (kvm_vcpu_trap_is_iabt(vcpu))
|
||||
return false;
|
||||
|
||||
|
|
|
|||
|
|
@ -449,7 +449,7 @@ static inline bool fixup_guest_exit(struct kvm_vcpu *vcpu, u64 *exit_code)
|
|||
kvm_vcpu_trap_get_fault_type(vcpu) == FSC_FAULT &&
|
||||
kvm_vcpu_dabt_isvalid(vcpu) &&
|
||||
!kvm_vcpu_abt_issea(vcpu) &&
|
||||
!kvm_vcpu_dabt_iss1tw(vcpu);
|
||||
!kvm_vcpu_abt_iss1tw(vcpu);
|
||||
|
||||
if (valid) {
|
||||
int ret = __vgic_v2_perform_cpuif_access(vcpu);
|
||||
|
|
|
|||
|
|
@ -1849,7 +1849,7 @@ static int user_mem_abort(struct kvm_vcpu *vcpu, phys_addr_t fault_ipa,
|
|||
struct kvm_s2_mmu *mmu = vcpu->arch.hw_mmu;
|
||||
|
||||
write_fault = kvm_is_write_fault(vcpu);
|
||||
exec_fault = kvm_vcpu_trap_is_iabt(vcpu);
|
||||
exec_fault = kvm_vcpu_trap_is_exec_fault(vcpu);
|
||||
VM_BUG_ON(write_fault && exec_fault);
|
||||
|
||||
if (fault_status == FSC_PERM && !write_fault && !exec_fault) {
|
||||
|
|
@ -2131,7 +2131,7 @@ int kvm_handle_guest_abort(struct kvm_vcpu *vcpu)
|
|||
goto out;
|
||||
}
|
||||
|
||||
if (kvm_vcpu_dabt_iss1tw(vcpu)) {
|
||||
if (kvm_vcpu_abt_iss1tw(vcpu)) {
|
||||
kvm_inject_dabt(vcpu, kvm_vcpu_get_hfar(vcpu));
|
||||
ret = 1;
|
||||
goto out_unlock;
|
||||
|
|
|
|||
|
|
@ -538,7 +538,7 @@ virtual_memmap_init(u64 start, u64 end, void *arg)
|
|||
if (map_start < map_end)
|
||||
memmap_init_zone((unsigned long)(map_end - map_start),
|
||||
args->nid, args->zone, page_to_pfn(map_start),
|
||||
MEMMAP_EARLY, NULL);
|
||||
MEMINIT_EARLY, NULL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -547,8 +547,8 @@ memmap_init (unsigned long size, int nid, unsigned long zone,
|
|||
unsigned long start_pfn)
|
||||
{
|
||||
if (!vmem_map) {
|
||||
memmap_init_zone(size, nid, zone, start_pfn, MEMMAP_EARLY,
|
||||
NULL);
|
||||
memmap_init_zone(size, nid, zone, start_pfn,
|
||||
MEMINIT_EARLY, NULL);
|
||||
} else {
|
||||
struct page *start;
|
||||
struct memmap_init_callback_data args;
|
||||
|
|
|
|||
|
|
@ -148,7 +148,7 @@ void __init plat_mem_setup(void)
|
|||
{
|
||||
struct cpuinfo_mips *c = ¤t_cpu_data;
|
||||
|
||||
if ((c->cputype == CPU_74K) || (c->cputype == CPU_1074K)) {
|
||||
if (c->cputype == CPU_74K) {
|
||||
pr_info("Using bcma bus\n");
|
||||
#ifdef CONFIG_BCM47XX_BCMA
|
||||
bcm47xx_bus_type = BCM47XX_BUS_TYPE_BCMA;
|
||||
|
|
|
|||
|
|
@ -47,6 +47,7 @@ static inline int __pure __get_cpu_type(const int cpu_type)
|
|||
case CPU_34K:
|
||||
case CPU_1004K:
|
||||
case CPU_74K:
|
||||
case CPU_1074K:
|
||||
case CPU_M14KC:
|
||||
case CPU_M14KEC:
|
||||
case CPU_INTERAPTIV:
|
||||
|
|
|
|||
|
|
@ -44,6 +44,10 @@ ifdef CONFIG_CPU_LOONGSON2F_WORKAROUNDS
|
|||
endif
|
||||
endif
|
||||
|
||||
# Some -march= flags enable MMI instructions, and GCC complains about that
|
||||
# support being enabled alongside -msoft-float. Thus explicitly disable MMI.
|
||||
cflags-y += $(call cc-option,-mno-loongson-mmi)
|
||||
|
||||
#
|
||||
# Loongson Machines' Support
|
||||
#
|
||||
|
|
|
|||
|
|
@ -95,10 +95,8 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
if (res)
|
||||
goto fault;
|
||||
|
||||
set_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lswc2_format.rt, value);
|
||||
set_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lswc2_format.rq, value_next);
|
||||
set_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lswc2_format.rt], 0, value);
|
||||
set_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lswc2_format.rq], 0, value_next);
|
||||
compute_return_epc(regs);
|
||||
own_fpu(1);
|
||||
}
|
||||
|
|
@ -130,15 +128,13 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
goto sigbus;
|
||||
|
||||
lose_fpu(1);
|
||||
value_next = get_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lswc2_format.rq);
|
||||
value_next = get_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lswc2_format.rq], 0);
|
||||
|
||||
StoreDW(addr + 8, value_next, res);
|
||||
if (res)
|
||||
goto fault;
|
||||
|
||||
value = get_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lswc2_format.rt);
|
||||
value = get_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lswc2_format.rt], 0);
|
||||
|
||||
StoreDW(addr, value, res);
|
||||
if (res)
|
||||
|
|
@ -204,8 +200,7 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
if (res)
|
||||
goto fault;
|
||||
|
||||
set_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lsdc2_format.rt, value);
|
||||
set_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lsdc2_format.rt], 0, value);
|
||||
compute_return_epc(regs);
|
||||
own_fpu(1);
|
||||
|
||||
|
|
@ -221,8 +216,7 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
if (res)
|
||||
goto fault;
|
||||
|
||||
set_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lsdc2_format.rt, value);
|
||||
set_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lsdc2_format.rt], 0, value);
|
||||
compute_return_epc(regs);
|
||||
own_fpu(1);
|
||||
break;
|
||||
|
|
@ -286,8 +280,7 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
goto sigbus;
|
||||
|
||||
lose_fpu(1);
|
||||
value = get_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lsdc2_format.rt);
|
||||
value = get_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lsdc2_format.rt], 0);
|
||||
|
||||
StoreW(addr, value, res);
|
||||
if (res)
|
||||
|
|
@ -305,8 +298,7 @@ static int loongson_cu2_call(struct notifier_block *nfb, unsigned long action,
|
|||
goto sigbus;
|
||||
|
||||
lose_fpu(1);
|
||||
value = get_fpr64(current->thread.fpu.fpr,
|
||||
insn.loongson3_lsdc2_format.rt);
|
||||
value = get_fpr64(¤t->thread.fpu.fpr[insn.loongson3_lsdc2_format.rt], 0);
|
||||
|
||||
StoreDW(addr, value, res);
|
||||
if (res)
|
||||
|
|
|
|||
|
|
@ -1260,26 +1260,44 @@ static inline pgd_t *pgd_offset_raw(pgd_t *pgd, unsigned long address)
|
|||
|
||||
#define pgd_offset(mm, address) pgd_offset_raw(READ_ONCE((mm)->pgd), address)
|
||||
|
||||
static inline p4d_t *p4d_offset(pgd_t *pgd, unsigned long address)
|
||||
static inline p4d_t *p4d_offset_lockless(pgd_t *pgdp, pgd_t pgd, unsigned long address)
|
||||
{
|
||||
if ((pgd_val(*pgd) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R1)
|
||||
return (p4d_t *) pgd_deref(*pgd) + p4d_index(address);
|
||||
return (p4d_t *) pgd;
|
||||
if ((pgd_val(pgd) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R1)
|
||||
return (p4d_t *) pgd_deref(pgd) + p4d_index(address);
|
||||
return (p4d_t *) pgdp;
|
||||
}
|
||||
#define p4d_offset_lockless p4d_offset_lockless
|
||||
|
||||
static inline p4d_t *p4d_offset(pgd_t *pgdp, unsigned long address)
|
||||
{
|
||||
return p4d_offset_lockless(pgdp, *pgdp, address);
|
||||
}
|
||||
|
||||
static inline pud_t *pud_offset(p4d_t *p4d, unsigned long address)
|
||||
static inline pud_t *pud_offset_lockless(p4d_t *p4dp, p4d_t p4d, unsigned long address)
|
||||
{
|
||||
if ((p4d_val(*p4d) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R2)
|
||||
return (pud_t *) p4d_deref(*p4d) + pud_index(address);
|
||||
return (pud_t *) p4d;
|
||||
if ((p4d_val(p4d) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R2)
|
||||
return (pud_t *) p4d_deref(p4d) + pud_index(address);
|
||||
return (pud_t *) p4dp;
|
||||
}
|
||||
#define pud_offset_lockless pud_offset_lockless
|
||||
|
||||
static inline pud_t *pud_offset(p4d_t *p4dp, unsigned long address)
|
||||
{
|
||||
return pud_offset_lockless(p4dp, *p4dp, address);
|
||||
}
|
||||
#define pud_offset pud_offset
|
||||
|
||||
static inline pmd_t *pmd_offset(pud_t *pud, unsigned long address)
|
||||
static inline pmd_t *pmd_offset_lockless(pud_t *pudp, pud_t pud, unsigned long address)
|
||||
{
|
||||
if ((pud_val(*pud) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R3)
|
||||
return (pmd_t *) pud_deref(*pud) + pmd_index(address);
|
||||
return (pmd_t *) pud;
|
||||
if ((pud_val(pud) & _REGION_ENTRY_TYPE_MASK) >= _REGION_ENTRY_TYPE_R3)
|
||||
return (pmd_t *) pud_deref(pud) + pmd_index(address);
|
||||
return (pmd_t *) pudp;
|
||||
}
|
||||
#define pmd_offset_lockless pmd_offset_lockless
|
||||
|
||||
static inline pmd_t *pmd_offset(pud_t *pudp, unsigned long address)
|
||||
{
|
||||
return pmd_offset_lockless(pudp, *pudp, address);
|
||||
}
|
||||
#define pmd_offset pmd_offset
|
||||
|
||||
|
|
|
|||
|
|
@ -652,6 +652,7 @@ static void __init kvm_guest_init(void)
|
|||
}
|
||||
|
||||
if (pv_tlb_flush_supported()) {
|
||||
pv_ops.mmu.flush_tlb_others = kvm_flush_tlb_others;
|
||||
pv_ops.mmu.tlb_remove_table = tlb_remove_table;
|
||||
pr_info("KVM setup pv remote TLB flush\n");
|
||||
}
|
||||
|
|
@ -764,14 +765,6 @@ static __init int activate_jump_labels(void)
|
|||
}
|
||||
arch_initcall(activate_jump_labels);
|
||||
|
||||
static void kvm_free_pv_cpu_mask(void)
|
||||
{
|
||||
unsigned int cpu;
|
||||
|
||||
for_each_possible_cpu(cpu)
|
||||
free_cpumask_var(per_cpu(__pv_cpu_mask, cpu));
|
||||
}
|
||||
|
||||
static __init int kvm_alloc_cpumask(void)
|
||||
{
|
||||
int cpu;
|
||||
|
|
@ -790,20 +783,11 @@ static __init int kvm_alloc_cpumask(void)
|
|||
|
||||
if (alloc)
|
||||
for_each_possible_cpu(cpu) {
|
||||
if (!zalloc_cpumask_var_node(
|
||||
per_cpu_ptr(&__pv_cpu_mask, cpu),
|
||||
GFP_KERNEL, cpu_to_node(cpu))) {
|
||||
goto zalloc_cpumask_fail;
|
||||
}
|
||||
zalloc_cpumask_var_node(per_cpu_ptr(&__pv_cpu_mask, cpu),
|
||||
GFP_KERNEL, cpu_to_node(cpu));
|
||||
}
|
||||
|
||||
apic->send_IPI_mask_allbutself = kvm_send_ipi_mask_allbutself;
|
||||
pv_ops.mmu.flush_tlb_others = kvm_flush_tlb_others;
|
||||
return 0;
|
||||
|
||||
zalloc_cpumask_fail:
|
||||
kvm_free_pv_cpu_mask();
|
||||
return -ENOMEM;
|
||||
}
|
||||
arch_initcall(kvm_alloc_cpumask);
|
||||
|
||||
|
|
|
|||
|
|
@ -2183,6 +2183,12 @@ static int iret_interception(struct vcpu_svm *svm)
|
|||
return 1;
|
||||
}
|
||||
|
||||
static int invd_interception(struct vcpu_svm *svm)
|
||||
{
|
||||
/* Treat an INVD instruction as a NOP and just skip it. */
|
||||
return kvm_skip_emulated_instruction(&svm->vcpu);
|
||||
}
|
||||
|
||||
static int invlpg_interception(struct vcpu_svm *svm)
|
||||
{
|
||||
if (!static_cpu_has(X86_FEATURE_DECODEASSISTS))
|
||||
|
|
@ -2774,7 +2780,7 @@ static int (*const svm_exit_handlers[])(struct vcpu_svm *svm) = {
|
|||
[SVM_EXIT_RDPMC] = rdpmc_interception,
|
||||
[SVM_EXIT_CPUID] = cpuid_interception,
|
||||
[SVM_EXIT_IRET] = iret_interception,
|
||||
[SVM_EXIT_INVD] = emulate_on_interception,
|
||||
[SVM_EXIT_INVD] = invd_interception,
|
||||
[SVM_EXIT_PAUSE] = pause_interception,
|
||||
[SVM_EXIT_HLT] = halt_interception,
|
||||
[SVM_EXIT_INVLPG] = invlpg_interception,
|
||||
|
|
|
|||
|
|
@ -129,6 +129,9 @@ static bool __read_mostly enable_preemption_timer = 1;
|
|||
module_param_named(preemption_timer, enable_preemption_timer, bool, S_IRUGO);
|
||||
#endif
|
||||
|
||||
extern bool __read_mostly allow_smaller_maxphyaddr;
|
||||
module_param(allow_smaller_maxphyaddr, bool, S_IRUGO);
|
||||
|
||||
#define KVM_VM_CR0_ALWAYS_OFF (X86_CR0_NW | X86_CR0_CD)
|
||||
#define KVM_VM_CR0_ALWAYS_ON_UNRESTRICTED_GUEST X86_CR0_NE
|
||||
#define KVM_VM_CR0_ALWAYS_ON \
|
||||
|
|
@ -4803,6 +4806,7 @@ static int handle_exception_nmi(struct kvm_vcpu *vcpu)
|
|||
* EPT will cause page fault only if we need to
|
||||
* detect illegal GPAs.
|
||||
*/
|
||||
WARN_ON_ONCE(!allow_smaller_maxphyaddr);
|
||||
kvm_fixup_and_inject_pf_error(vcpu, cr2, error_code);
|
||||
return 1;
|
||||
} else
|
||||
|
|
@ -5331,7 +5335,7 @@ static int handle_ept_violation(struct kvm_vcpu *vcpu)
|
|||
* would also use advanced VM-exit information for EPT violations to
|
||||
* reconstruct the page fault error code.
|
||||
*/
|
||||
if (unlikely(kvm_mmu_is_illegal_gpa(vcpu, gpa)))
|
||||
if (unlikely(allow_smaller_maxphyaddr && kvm_mmu_is_illegal_gpa(vcpu, gpa)))
|
||||
return kvm_emulate_instruction(vcpu, 0);
|
||||
|
||||
return kvm_mmu_page_fault(vcpu, gpa, error_code, NULL, 0);
|
||||
|
|
@ -8305,11 +8309,12 @@ static int __init vmx_init(void)
|
|||
vmx_check_vmcs12_offsets();
|
||||
|
||||
/*
|
||||
* Intel processors don't have problems with
|
||||
* GUEST_MAXPHYADDR < HOST_MAXPHYADDR so enable
|
||||
* it for VMX by default
|
||||
* Shadow paging doesn't have a (further) performance penalty
|
||||
* from GUEST_MAXPHYADDR < HOST_MAXPHYADDR so enable it
|
||||
* by default
|
||||
*/
|
||||
allow_smaller_maxphyaddr = true;
|
||||
if (!enable_ept)
|
||||
allow_smaller_maxphyaddr = true;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -552,7 +552,10 @@ static inline bool vmx_has_waitpkg(struct vcpu_vmx *vmx)
|
|||
|
||||
static inline bool vmx_need_pf_intercept(struct kvm_vcpu *vcpu)
|
||||
{
|
||||
return !enable_ept || cpuid_maxphyaddr(vcpu) < boot_cpu_data.x86_phys_bits;
|
||||
if (!enable_ept)
|
||||
return true;
|
||||
|
||||
return allow_smaller_maxphyaddr && cpuid_maxphyaddr(vcpu) < boot_cpu_data.x86_phys_bits;
|
||||
}
|
||||
|
||||
void dump_vmcs(void);
|
||||
|
|
|
|||
|
|
@ -188,7 +188,7 @@ static struct kvm_shared_msrs __percpu *shared_msrs;
|
|||
u64 __read_mostly host_efer;
|
||||
EXPORT_SYMBOL_GPL(host_efer);
|
||||
|
||||
bool __read_mostly allow_smaller_maxphyaddr;
|
||||
bool __read_mostly allow_smaller_maxphyaddr = 0;
|
||||
EXPORT_SYMBOL_GPL(allow_smaller_maxphyaddr);
|
||||
|
||||
static u64 __read_mostly host_xss;
|
||||
|
|
@ -976,6 +976,7 @@ int kvm_set_cr4(struct kvm_vcpu *vcpu, unsigned long cr4)
|
|||
unsigned long old_cr4 = kvm_read_cr4(vcpu);
|
||||
unsigned long pdptr_bits = X86_CR4_PGE | X86_CR4_PSE | X86_CR4_PAE |
|
||||
X86_CR4_SMEP;
|
||||
unsigned long mmu_role_bits = pdptr_bits | X86_CR4_SMAP | X86_CR4_PKE;
|
||||
|
||||
if (kvm_valid_cr4(vcpu, cr4))
|
||||
return 1;
|
||||
|
|
@ -1003,7 +1004,7 @@ int kvm_set_cr4(struct kvm_vcpu *vcpu, unsigned long cr4)
|
|||
if (kvm_x86_ops.set_cr4(vcpu, cr4))
|
||||
return 1;
|
||||
|
||||
if (((cr4 ^ old_cr4) & pdptr_bits) ||
|
||||
if (((cr4 ^ old_cr4) & mmu_role_bits) ||
|
||||
(!(cr4 & X86_CR4_PCIDE) && (old_cr4 & X86_CR4_PCIDE)))
|
||||
kvm_mmu_reset_context(vcpu);
|
||||
|
||||
|
|
@ -3221,9 +3222,22 @@ int kvm_get_msr_common(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
|
|||
case MSR_IA32_POWER_CTL:
|
||||
msr_info->data = vcpu->arch.msr_ia32_power_ctl;
|
||||
break;
|
||||
case MSR_IA32_TSC:
|
||||
msr_info->data = kvm_scale_tsc(vcpu, rdtsc()) + vcpu->arch.tsc_offset;
|
||||
case MSR_IA32_TSC: {
|
||||
/*
|
||||
* Intel SDM states that MSR_IA32_TSC read adds the TSC offset
|
||||
* even when not intercepted. AMD manual doesn't explicitly
|
||||
* state this but appears to behave the same.
|
||||
*
|
||||
* On userspace reads and writes, however, we unconditionally
|
||||
* operate L1's TSC value to ensure backwards-compatible
|
||||
* behavior for migration.
|
||||
*/
|
||||
u64 tsc_offset = msr_info->host_initiated ? vcpu->arch.l1_tsc_offset :
|
||||
vcpu->arch.tsc_offset;
|
||||
|
||||
msr_info->data = kvm_scale_tsc(vcpu, rdtsc()) + tsc_offset;
|
||||
break;
|
||||
}
|
||||
case MSR_MTRRcap:
|
||||
case 0x200 ... 0x2ff:
|
||||
return kvm_mtrr_get_msr(vcpu, msr_info->index, &msr_info->data);
|
||||
|
|
|
|||
|
|
@ -120,7 +120,7 @@ long __copy_user_flushcache(void *dst, const void __user *src, unsigned size)
|
|||
*/
|
||||
if (size < 8) {
|
||||
if (!IS_ALIGNED(dest, 4) || size != 4)
|
||||
clean_cache_range(dst, 1);
|
||||
clean_cache_range(dst, size);
|
||||
} else {
|
||||
if (!IS_ALIGNED(dest, 8)) {
|
||||
dest = ALIGN(dest, boot_cpu_data.x86_clflush_size);
|
||||
|
|
|
|||
|
|
@ -801,6 +801,52 @@ bool blk_queue_can_use_dma_map_merging(struct request_queue *q,
|
|||
}
|
||||
EXPORT_SYMBOL_GPL(blk_queue_can_use_dma_map_merging);
|
||||
|
||||
/**
|
||||
* blk_queue_set_zoned - configure a disk queue zoned model.
|
||||
* @disk: the gendisk of the queue to configure
|
||||
* @model: the zoned model to set
|
||||
*
|
||||
* Set the zoned model of the request queue of @disk according to @model.
|
||||
* When @model is BLK_ZONED_HM (host managed), this should be called only
|
||||
* if zoned block device support is enabled (CONFIG_BLK_DEV_ZONED option).
|
||||
* If @model specifies BLK_ZONED_HA (host aware), the effective model used
|
||||
* depends on CONFIG_BLK_DEV_ZONED settings and on the existence of partitions
|
||||
* on the disk.
|
||||
*/
|
||||
void blk_queue_set_zoned(struct gendisk *disk, enum blk_zoned_model model)
|
||||
{
|
||||
switch (model) {
|
||||
case BLK_ZONED_HM:
|
||||
/*
|
||||
* Host managed devices are supported only if
|
||||
* CONFIG_BLK_DEV_ZONED is enabled.
|
||||
*/
|
||||
WARN_ON_ONCE(!IS_ENABLED(CONFIG_BLK_DEV_ZONED));
|
||||
break;
|
||||
case BLK_ZONED_HA:
|
||||
/*
|
||||
* Host aware devices can be treated either as regular block
|
||||
* devices (similar to drive managed devices) or as zoned block
|
||||
* devices to take advantage of the zone command set, similarly
|
||||
* to host managed devices. We try the latter if there are no
|
||||
* partitions and zoned block device support is enabled, else
|
||||
* we do nothing special as far as the block layer is concerned.
|
||||
*/
|
||||
if (!IS_ENABLED(CONFIG_BLK_DEV_ZONED) ||
|
||||
disk_has_partitions(disk))
|
||||
model = BLK_ZONED_NONE;
|
||||
break;
|
||||
case BLK_ZONED_NONE:
|
||||
default:
|
||||
if (WARN_ON_ONCE(model != BLK_ZONED_NONE))
|
||||
model = BLK_ZONED_NONE;
|
||||
break;
|
||||
}
|
||||
|
||||
disk->queue->limits.zoned = model;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(blk_queue_set_zoned);
|
||||
|
||||
static int __init blk_settings_init(void)
|
||||
{
|
||||
blk_max_low_pfn = max_low_pfn - 1;
|
||||
|
|
|
|||
|
|
@ -176,6 +176,7 @@ static void lapic_timer_propagate_broadcast(struct acpi_processor *pr) { }
|
|||
static bool lapic_timer_needs_broadcast(struct acpi_processor *pr,
|
||||
struct acpi_processor_cx *cx)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -2224,7 +2224,7 @@ static int eni_init_one(struct pci_dev *pci_dev,
|
|||
|
||||
rc = dma_set_mask_and_coherent(&pci_dev->dev, DMA_BIT_MASK(32));
|
||||
if (rc < 0)
|
||||
goto out;
|
||||
goto err_disable;
|
||||
|
||||
rc = -ENOMEM;
|
||||
eni_dev = kmalloc(sizeof(struct eni_dev), GFP_KERNEL);
|
||||
|
|
|
|||
|
|
@ -761,14 +761,36 @@ static int __ref get_nid_for_pfn(unsigned long pfn)
|
|||
return pfn_to_nid(pfn);
|
||||
}
|
||||
|
||||
static int do_register_memory_block_under_node(int nid,
|
||||
struct memory_block *mem_blk)
|
||||
{
|
||||
int ret;
|
||||
|
||||
/*
|
||||
* If this memory block spans multiple nodes, we only indicate
|
||||
* the last processed node.
|
||||
*/
|
||||
mem_blk->nid = nid;
|
||||
|
||||
ret = sysfs_create_link_nowarn(&node_devices[nid]->dev.kobj,
|
||||
&mem_blk->dev.kobj,
|
||||
kobject_name(&mem_blk->dev.kobj));
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return sysfs_create_link_nowarn(&mem_blk->dev.kobj,
|
||||
&node_devices[nid]->dev.kobj,
|
||||
kobject_name(&node_devices[nid]->dev.kobj));
|
||||
}
|
||||
|
||||
/* register memory section under specified node if it spans that node */
|
||||
static int register_mem_sect_under_node(struct memory_block *mem_blk,
|
||||
void *arg)
|
||||
static int register_mem_block_under_node_early(struct memory_block *mem_blk,
|
||||
void *arg)
|
||||
{
|
||||
unsigned long memory_block_pfns = memory_block_size_bytes() / PAGE_SIZE;
|
||||
unsigned long start_pfn = section_nr_to_pfn(mem_blk->start_section_nr);
|
||||
unsigned long end_pfn = start_pfn + memory_block_pfns - 1;
|
||||
int ret, nid = *(int *)arg;
|
||||
int nid = *(int *)arg;
|
||||
unsigned long pfn;
|
||||
|
||||
for (pfn = start_pfn; pfn <= end_pfn; pfn++) {
|
||||
|
|
@ -785,38 +807,33 @@ static int register_mem_sect_under_node(struct memory_block *mem_blk,
|
|||
}
|
||||
|
||||
/*
|
||||
* We need to check if page belongs to nid only for the boot
|
||||
* case, during hotplug we know that all pages in the memory
|
||||
* block belong to the same node.
|
||||
* We need to check if page belongs to nid only at the boot
|
||||
* case because node's ranges can be interleaved.
|
||||
*/
|
||||
if (system_state == SYSTEM_BOOTING) {
|
||||
page_nid = get_nid_for_pfn(pfn);
|
||||
if (page_nid < 0)
|
||||
continue;
|
||||
if (page_nid != nid)
|
||||
continue;
|
||||
}
|
||||
page_nid = get_nid_for_pfn(pfn);
|
||||
if (page_nid < 0)
|
||||
continue;
|
||||
if (page_nid != nid)
|
||||
continue;
|
||||
|
||||
/*
|
||||
* If this memory block spans multiple nodes, we only indicate
|
||||
* the last processed node.
|
||||
*/
|
||||
mem_blk->nid = nid;
|
||||
|
||||
ret = sysfs_create_link_nowarn(&node_devices[nid]->dev.kobj,
|
||||
&mem_blk->dev.kobj,
|
||||
kobject_name(&mem_blk->dev.kobj));
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return sysfs_create_link_nowarn(&mem_blk->dev.kobj,
|
||||
&node_devices[nid]->dev.kobj,
|
||||
kobject_name(&node_devices[nid]->dev.kobj));
|
||||
return do_register_memory_block_under_node(nid, mem_blk);
|
||||
}
|
||||
/* mem section does not span the specified node */
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* During hotplug we know that all pages in the memory block belong to the same
|
||||
* node.
|
||||
*/
|
||||
static int register_mem_block_under_node_hotplug(struct memory_block *mem_blk,
|
||||
void *arg)
|
||||
{
|
||||
int nid = *(int *)arg;
|
||||
|
||||
return do_register_memory_block_under_node(nid, mem_blk);
|
||||
}
|
||||
|
||||
/*
|
||||
* Unregister a memory block device under the node it spans. Memory blocks
|
||||
* with multiple nodes cannot be offlined and therefore also never be removed.
|
||||
|
|
@ -832,11 +849,19 @@ void unregister_memory_block_under_nodes(struct memory_block *mem_blk)
|
|||
kobject_name(&node_devices[mem_blk->nid]->dev.kobj));
|
||||
}
|
||||
|
||||
int link_mem_sections(int nid, unsigned long start_pfn, unsigned long end_pfn)
|
||||
int link_mem_sections(int nid, unsigned long start_pfn, unsigned long end_pfn,
|
||||
enum meminit_context context)
|
||||
{
|
||||
walk_memory_blocks_func_t func;
|
||||
|
||||
if (context == MEMINIT_HOTPLUG)
|
||||
func = register_mem_block_under_node_hotplug;
|
||||
else
|
||||
func = register_mem_block_under_node_early;
|
||||
|
||||
return walk_memory_blocks(PFN_PHYS(start_pfn),
|
||||
PFN_PHYS(end_pfn - start_pfn), (void *)&nid,
|
||||
register_mem_sect_under_node);
|
||||
func);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HUGETLBFS
|
||||
|
|
|
|||
|
|
@ -217,7 +217,7 @@ struct regmap_field {
|
|||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
extern void regmap_debugfs_initcall(void);
|
||||
extern void regmap_debugfs_init(struct regmap *map, const char *name);
|
||||
extern void regmap_debugfs_init(struct regmap *map);
|
||||
extern void regmap_debugfs_exit(struct regmap *map);
|
||||
|
||||
static inline void regmap_debugfs_disable(struct regmap *map)
|
||||
|
|
@ -227,7 +227,7 @@ static inline void regmap_debugfs_disable(struct regmap *map)
|
|||
|
||||
#else
|
||||
static inline void regmap_debugfs_initcall(void) { }
|
||||
static inline void regmap_debugfs_init(struct regmap *map, const char *name) { }
|
||||
static inline void regmap_debugfs_init(struct regmap *map) { }
|
||||
static inline void regmap_debugfs_exit(struct regmap *map) { }
|
||||
static inline void regmap_debugfs_disable(struct regmap *map) { }
|
||||
#endif
|
||||
|
|
@ -259,7 +259,7 @@ bool regcache_set_val(struct regmap *map, void *base, unsigned int idx,
|
|||
int regcache_lookup_reg(struct regmap *map, unsigned int reg);
|
||||
|
||||
int _regmap_raw_write(struct regmap *map, unsigned int reg,
|
||||
const void *val, size_t val_len);
|
||||
const void *val, size_t val_len, bool noinc);
|
||||
|
||||
void regmap_async_complete_cb(struct regmap_async *async, int ret);
|
||||
|
||||
|
|
|
|||
|
|
@ -717,7 +717,7 @@ static int regcache_sync_block_raw_flush(struct regmap *map, const void **data,
|
|||
|
||||
map->cache_bypass = true;
|
||||
|
||||
ret = _regmap_raw_write(map, base, *data, count * val_bytes);
|
||||
ret = _regmap_raw_write(map, base, *data, count * val_bytes, false);
|
||||
if (ret)
|
||||
dev_err(map->dev, "Unable to sync registers %#x-%#x. %d\n",
|
||||
base, cur - map->reg_stride, ret);
|
||||
|
|
|
|||
|
|
@ -17,7 +17,6 @@
|
|||
|
||||
struct regmap_debugfs_node {
|
||||
struct regmap *map;
|
||||
const char *name;
|
||||
struct list_head link;
|
||||
};
|
||||
|
||||
|
|
@ -544,11 +543,12 @@ static const struct file_operations regmap_cache_bypass_fops = {
|
|||
.write = regmap_cache_bypass_write_file,
|
||||
};
|
||||
|
||||
void regmap_debugfs_init(struct regmap *map, const char *name)
|
||||
void regmap_debugfs_init(struct regmap *map)
|
||||
{
|
||||
struct rb_node *next;
|
||||
struct regmap_range_node *range_node;
|
||||
const char *devname = "dummy";
|
||||
const char *name = map->name;
|
||||
|
||||
/*
|
||||
* Userspace can initiate reads from the hardware over debugfs.
|
||||
|
|
@ -569,7 +569,6 @@ void regmap_debugfs_init(struct regmap *map, const char *name)
|
|||
if (!node)
|
||||
return;
|
||||
node->map = map;
|
||||
node->name = name;
|
||||
mutex_lock(®map_debugfs_early_lock);
|
||||
list_add(&node->link, ®map_debugfs_early_list);
|
||||
mutex_unlock(®map_debugfs_early_lock);
|
||||
|
|
@ -679,7 +678,7 @@ void regmap_debugfs_initcall(void)
|
|||
|
||||
mutex_lock(®map_debugfs_early_lock);
|
||||
list_for_each_entry_safe(node, tmp, ®map_debugfs_early_list, link) {
|
||||
regmap_debugfs_init(node->map, node->name);
|
||||
regmap_debugfs_init(node->map);
|
||||
list_del(&node->link);
|
||||
kfree(node);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -581,14 +581,34 @@ static void regmap_range_exit(struct regmap *map)
|
|||
kfree(map->selector_work_buf);
|
||||
}
|
||||
|
||||
static int regmap_set_name(struct regmap *map, const struct regmap_config *config)
|
||||
{
|
||||
if (config->name) {
|
||||
const char *name = kstrdup_const(config->name, GFP_KERNEL);
|
||||
|
||||
if (!name)
|
||||
return -ENOMEM;
|
||||
|
||||
kfree_const(map->name);
|
||||
map->name = name;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int regmap_attach_dev(struct device *dev, struct regmap *map,
|
||||
const struct regmap_config *config)
|
||||
{
|
||||
struct regmap **m;
|
||||
int ret;
|
||||
|
||||
map->dev = dev;
|
||||
|
||||
regmap_debugfs_init(map, config->name);
|
||||
ret = regmap_set_name(map, config);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
regmap_debugfs_init(map);
|
||||
|
||||
/* Add a devres resource for dev_get_regmap() */
|
||||
m = devres_alloc(dev_get_regmap_release, sizeof(*m), GFP_KERNEL);
|
||||
|
|
@ -687,13 +707,9 @@ struct regmap *__regmap_init(struct device *dev,
|
|||
goto err;
|
||||
}
|
||||
|
||||
if (config->name) {
|
||||
map->name = kstrdup_const(config->name, GFP_KERNEL);
|
||||
if (!map->name) {
|
||||
ret = -ENOMEM;
|
||||
goto err_map;
|
||||
}
|
||||
}
|
||||
ret = regmap_set_name(map, config);
|
||||
if (ret)
|
||||
goto err_map;
|
||||
|
||||
if (config->disable_locking) {
|
||||
map->lock = map->unlock = regmap_lock_unlock_none;
|
||||
|
|
@ -1137,7 +1153,7 @@ struct regmap *__regmap_init(struct device *dev,
|
|||
if (ret != 0)
|
||||
goto err_regcache;
|
||||
} else {
|
||||
regmap_debugfs_init(map, config->name);
|
||||
regmap_debugfs_init(map);
|
||||
}
|
||||
|
||||
return map;
|
||||
|
|
@ -1297,6 +1313,8 @@ EXPORT_SYMBOL_GPL(regmap_field_free);
|
|||
*/
|
||||
int regmap_reinit_cache(struct regmap *map, const struct regmap_config *config)
|
||||
{
|
||||
int ret;
|
||||
|
||||
regcache_exit(map);
|
||||
regmap_debugfs_exit(map);
|
||||
|
||||
|
|
@ -1309,7 +1327,11 @@ int regmap_reinit_cache(struct regmap *map, const struct regmap_config *config)
|
|||
map->readable_noinc_reg = config->readable_noinc_reg;
|
||||
map->cache_type = config->cache_type;
|
||||
|
||||
regmap_debugfs_init(map, config->name);
|
||||
ret = regmap_set_name(map, config);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
regmap_debugfs_init(map);
|
||||
|
||||
map->cache_bypass = false;
|
||||
map->cache_only = false;
|
||||
|
|
@ -1464,7 +1486,7 @@ static void regmap_set_work_buf_flag_mask(struct regmap *map, int max_bytes,
|
|||
}
|
||||
|
||||
static int _regmap_raw_write_impl(struct regmap *map, unsigned int reg,
|
||||
const void *val, size_t val_len)
|
||||
const void *val, size_t val_len, bool noinc)
|
||||
{
|
||||
struct regmap_range_node *range;
|
||||
unsigned long flags;
|
||||
|
|
@ -1523,7 +1545,7 @@ static int _regmap_raw_write_impl(struct regmap *map, unsigned int reg,
|
|||
win_residue, val_len / map->format.val_bytes);
|
||||
ret = _regmap_raw_write_impl(map, reg, val,
|
||||
win_residue *
|
||||
map->format.val_bytes);
|
||||
map->format.val_bytes, noinc);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
|
||||
|
|
@ -1537,7 +1559,7 @@ static int _regmap_raw_write_impl(struct regmap *map, unsigned int reg,
|
|||
win_residue = range->window_len - win_offset;
|
||||
}
|
||||
|
||||
ret = _regmap_select_page(map, ®, range, val_num);
|
||||
ret = _regmap_select_page(map, ®, range, noinc ? 1 : val_num);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
}
|
||||
|
|
@ -1745,7 +1767,8 @@ static int _regmap_bus_raw_write(void *context, unsigned int reg,
|
|||
map->work_buf +
|
||||
map->format.reg_bytes +
|
||||
map->format.pad_bytes,
|
||||
map->format.val_bytes);
|
||||
map->format.val_bytes,
|
||||
false);
|
||||
}
|
||||
|
||||
static inline void *_regmap_map_get_context(struct regmap *map)
|
||||
|
|
@ -1839,7 +1862,7 @@ int regmap_write_async(struct regmap *map, unsigned int reg, unsigned int val)
|
|||
EXPORT_SYMBOL_GPL(regmap_write_async);
|
||||
|
||||
int _regmap_raw_write(struct regmap *map, unsigned int reg,
|
||||
const void *val, size_t val_len)
|
||||
const void *val, size_t val_len, bool noinc)
|
||||
{
|
||||
size_t val_bytes = map->format.val_bytes;
|
||||
size_t val_count = val_len / val_bytes;
|
||||
|
|
@ -1860,7 +1883,7 @@ int _regmap_raw_write(struct regmap *map, unsigned int reg,
|
|||
|
||||
/* Write as many bytes as possible with chunk_size */
|
||||
for (i = 0; i < chunk_count; i++) {
|
||||
ret = _regmap_raw_write_impl(map, reg, val, chunk_bytes);
|
||||
ret = _regmap_raw_write_impl(map, reg, val, chunk_bytes, noinc);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
|
|
@ -1871,7 +1894,7 @@ int _regmap_raw_write(struct regmap *map, unsigned int reg,
|
|||
|
||||
/* Write remaining bytes */
|
||||
if (val_len)
|
||||
ret = _regmap_raw_write_impl(map, reg, val, val_len);
|
||||
ret = _regmap_raw_write_impl(map, reg, val, val_len, noinc);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
|
@ -1904,7 +1927,7 @@ int regmap_raw_write(struct regmap *map, unsigned int reg,
|
|||
|
||||
map->lock(map->lock_arg);
|
||||
|
||||
ret = _regmap_raw_write(map, reg, val, val_len);
|
||||
ret = _regmap_raw_write(map, reg, val, val_len, false);
|
||||
|
||||
map->unlock(map->lock_arg);
|
||||
|
||||
|
|
@ -1962,7 +1985,7 @@ int regmap_noinc_write(struct regmap *map, unsigned int reg,
|
|||
write_len = map->max_raw_write;
|
||||
else
|
||||
write_len = val_len;
|
||||
ret = _regmap_raw_write(map, reg, val, write_len);
|
||||
ret = _regmap_raw_write(map, reg, val, write_len, true);
|
||||
if (ret)
|
||||
goto out_unlock;
|
||||
val = ((u8 *)val) + write_len;
|
||||
|
|
@ -2439,7 +2462,7 @@ int regmap_raw_write_async(struct regmap *map, unsigned int reg,
|
|||
|
||||
map->async = true;
|
||||
|
||||
ret = _regmap_raw_write(map, reg, val, val_len);
|
||||
ret = _regmap_raw_write(map, reg, val, val_len, false);
|
||||
|
||||
map->async = false;
|
||||
|
||||
|
|
@ -2450,7 +2473,7 @@ int regmap_raw_write_async(struct regmap *map, unsigned int reg,
|
|||
EXPORT_SYMBOL_GPL(regmap_raw_write_async);
|
||||
|
||||
static int _regmap_raw_read(struct regmap *map, unsigned int reg, void *val,
|
||||
unsigned int val_len)
|
||||
unsigned int val_len, bool noinc)
|
||||
{
|
||||
struct regmap_range_node *range;
|
||||
int ret;
|
||||
|
|
@ -2463,7 +2486,7 @@ static int _regmap_raw_read(struct regmap *map, unsigned int reg, void *val,
|
|||
range = _regmap_range_lookup(map, reg);
|
||||
if (range) {
|
||||
ret = _regmap_select_page(map, ®, range,
|
||||
val_len / map->format.val_bytes);
|
||||
noinc ? 1 : val_len / map->format.val_bytes);
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
}
|
||||
|
|
@ -2501,7 +2524,7 @@ static int _regmap_bus_read(void *context, unsigned int reg,
|
|||
if (!map->format.parse_val)
|
||||
return -EINVAL;
|
||||
|
||||
ret = _regmap_raw_read(map, reg, work_val, map->format.val_bytes);
|
||||
ret = _regmap_raw_read(map, reg, work_val, map->format.val_bytes, false);
|
||||
if (ret == 0)
|
||||
*val = map->format.parse_val(work_val);
|
||||
|
||||
|
|
@ -2617,7 +2640,7 @@ int regmap_raw_read(struct regmap *map, unsigned int reg, void *val,
|
|||
|
||||
/* Read bytes that fit into whole chunks */
|
||||
for (i = 0; i < chunk_count; i++) {
|
||||
ret = _regmap_raw_read(map, reg, val, chunk_bytes);
|
||||
ret = _regmap_raw_read(map, reg, val, chunk_bytes, false);
|
||||
if (ret != 0)
|
||||
goto out;
|
||||
|
||||
|
|
@ -2628,7 +2651,7 @@ int regmap_raw_read(struct regmap *map, unsigned int reg, void *val,
|
|||
|
||||
/* Read remaining bytes */
|
||||
if (val_len) {
|
||||
ret = _regmap_raw_read(map, reg, val, val_len);
|
||||
ret = _regmap_raw_read(map, reg, val, val_len, false);
|
||||
if (ret != 0)
|
||||
goto out;
|
||||
}
|
||||
|
|
@ -2703,7 +2726,7 @@ int regmap_noinc_read(struct regmap *map, unsigned int reg,
|
|||
read_len = map->max_raw_read;
|
||||
else
|
||||
read_len = val_len;
|
||||
ret = _regmap_raw_read(map, reg, val, read_len);
|
||||
ret = _regmap_raw_read(map, reg, val, read_len, true);
|
||||
if (ret)
|
||||
goto out_unlock;
|
||||
val = ((u8 *)val) + read_len;
|
||||
|
|
|
|||
|
|
@ -66,7 +66,7 @@ static int psci_enter_domain_idle_state(struct cpuidle_device *dev,
|
|||
return -1;
|
||||
|
||||
/* Do runtime PM to manage a hierarchical CPU toplogy. */
|
||||
pm_runtime_put_sync_suspend(pd_dev);
|
||||
RCU_NONIDLE(pm_runtime_put_sync_suspend(pd_dev));
|
||||
|
||||
state = psci_get_domain_state();
|
||||
if (!state)
|
||||
|
|
@ -74,7 +74,7 @@ static int psci_enter_domain_idle_state(struct cpuidle_device *dev,
|
|||
|
||||
ret = psci_cpu_suspend_enter(state) ? -1 : idx;
|
||||
|
||||
pm_runtime_get_sync(pd_dev);
|
||||
RCU_NONIDLE(pm_runtime_get_sync(pd_dev));
|
||||
|
||||
cpu_pm_exit();
|
||||
|
||||
|
|
|
|||
|
|
@ -143,11 +143,6 @@ static void enter_s2idle_proper(struct cpuidle_driver *drv,
|
|||
|
||||
time_start = ns_to_ktime(local_clock());
|
||||
|
||||
/*
|
||||
* trace_suspend_resume() called by tick_freeze() for the last CPU
|
||||
* executing it contains RCU usage regarded as invalid in the idle
|
||||
* context, so tell RCU about that.
|
||||
*/
|
||||
tick_freeze();
|
||||
/*
|
||||
* The state used here cannot be a "coupled" one, because the "coupled"
|
||||
|
|
@ -160,11 +155,6 @@ static void enter_s2idle_proper(struct cpuidle_driver *drv,
|
|||
target_state->enter_s2idle(dev, drv, index);
|
||||
if (WARN_ON_ONCE(!irqs_disabled()))
|
||||
local_irq_disable();
|
||||
/*
|
||||
* timekeeping_resume() that will be called by tick_unfreeze() for the
|
||||
* first CPU executing it calls functions containing RCU read-side
|
||||
* critical sections, so tell RCU about that.
|
||||
*/
|
||||
if (!(target_state->flags & CPUIDLE_FLAG_RCU_IDLE))
|
||||
rcu_idle_exit();
|
||||
tick_unfreeze();
|
||||
|
|
|
|||
|
|
@ -1766,20 +1766,23 @@ static int devfreq_summary_show(struct seq_file *s, void *data)
|
|||
struct devfreq *p_devfreq = NULL;
|
||||
unsigned long cur_freq, min_freq, max_freq;
|
||||
unsigned int polling_ms;
|
||||
unsigned int timer;
|
||||
|
||||
seq_printf(s, "%-30s %-30s %-15s %10s %12s %12s %12s\n",
|
||||
seq_printf(s, "%-30s %-30s %-15s %-10s %10s %12s %12s %12s\n",
|
||||
"dev",
|
||||
"parent_dev",
|
||||
"governor",
|
||||
"timer",
|
||||
"polling_ms",
|
||||
"cur_freq_Hz",
|
||||
"min_freq_Hz",
|
||||
"max_freq_Hz");
|
||||
seq_printf(s, "%30s %30s %15s %10s %12s %12s %12s\n",
|
||||
seq_printf(s, "%30s %30s %15s %10s %10s %12s %12s %12s\n",
|
||||
"------------------------------",
|
||||
"------------------------------",
|
||||
"---------------",
|
||||
"----------",
|
||||
"----------",
|
||||
"------------",
|
||||
"------------",
|
||||
"------------");
|
||||
|
|
@ -1803,13 +1806,15 @@ static int devfreq_summary_show(struct seq_file *s, void *data)
|
|||
cur_freq = devfreq->previous_freq;
|
||||
get_freq_range(devfreq, &min_freq, &max_freq);
|
||||
polling_ms = devfreq->profile->polling_ms;
|
||||
timer = devfreq->profile->timer;
|
||||
mutex_unlock(&devfreq->lock);
|
||||
|
||||
seq_printf(s,
|
||||
"%-30s %-30s %-15s %10d %12ld %12ld %12ld\n",
|
||||
"%-30s %-30s %-15s %-10s %10d %12ld %12ld %12ld\n",
|
||||
dev_name(&devfreq->dev),
|
||||
p_devfreq ? dev_name(&p_devfreq->dev) : "null",
|
||||
devfreq->governor_name,
|
||||
polling_ms ? timer_name[timer] : "null",
|
||||
polling_ms,
|
||||
cur_freq,
|
||||
min_freq,
|
||||
|
|
|
|||
|
|
@ -836,7 +836,8 @@ static int tegra_devfreq_probe(struct platform_device *pdev)
|
|||
rate = clk_round_rate(tegra->emc_clock, ULONG_MAX);
|
||||
if (rate < 0) {
|
||||
dev_err(&pdev->dev, "Failed to round clock rate: %ld\n", rate);
|
||||
return rate;
|
||||
err = rate;
|
||||
goto disable_clk;
|
||||
}
|
||||
|
||||
tegra->max_freq = rate / KHZ;
|
||||
|
|
@ -897,6 +898,7 @@ static int tegra_devfreq_probe(struct platform_device *pdev)
|
|||
dev_pm_opp_remove_all_dynamic(&pdev->dev);
|
||||
|
||||
reset_control_reset(tegra->reset);
|
||||
disable_clk:
|
||||
clk_disable_unprepare(tegra->clock);
|
||||
|
||||
return err;
|
||||
|
|
|
|||
|
|
@ -59,6 +59,8 @@ static void dma_buf_release(struct dentry *dentry)
|
|||
struct dma_buf *dmabuf;
|
||||
|
||||
dmabuf = dentry->d_fsdata;
|
||||
if (unlikely(!dmabuf))
|
||||
return;
|
||||
|
||||
BUG_ON(dmabuf->vmapping_counter);
|
||||
|
||||
|
|
|
|||
|
|
@ -368,6 +368,7 @@ void intel_gvt_destroy_idle_vgpu(struct intel_vgpu *vgpu)
|
|||
static struct intel_vgpu *__intel_gvt_create_vgpu(struct intel_gvt *gvt,
|
||||
struct intel_vgpu_creation_params *param)
|
||||
{
|
||||
struct drm_i915_private *dev_priv = gvt->gt->i915;
|
||||
struct intel_vgpu *vgpu;
|
||||
int ret;
|
||||
|
||||
|
|
@ -436,7 +437,10 @@ static struct intel_vgpu *__intel_gvt_create_vgpu(struct intel_gvt *gvt,
|
|||
if (ret)
|
||||
goto out_clean_sched_policy;
|
||||
|
||||
ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_D);
|
||||
if (IS_BROADWELL(dev_priv))
|
||||
ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_B);
|
||||
else
|
||||
ret = intel_gvt_hypervisor_set_edid(vgpu, PORT_D);
|
||||
if (ret)
|
||||
goto out_clean_sched_policy;
|
||||
|
||||
|
|
|
|||
|
|
@ -118,11 +118,11 @@ static struct dev_pm_domain pm_domain = {
|
|||
|
||||
struct drm_i915_private *mock_gem_device(void)
|
||||
{
|
||||
#if IS_ENABLED(CONFIG_IOMMU_API) && defined(CONFIG_INTEL_IOMMU)
|
||||
static struct dev_iommu fake_iommu = { .priv = (void *)-1 };
|
||||
#endif
|
||||
struct drm_i915_private *i915;
|
||||
struct pci_dev *pdev;
|
||||
#if IS_ENABLED(CONFIG_IOMMU_API) && defined(CONFIG_INTEL_IOMMU)
|
||||
struct dev_iommu iommu;
|
||||
#endif
|
||||
int err;
|
||||
|
||||
pdev = kzalloc(sizeof(*pdev), GFP_KERNEL);
|
||||
|
|
@ -141,10 +141,8 @@ struct drm_i915_private *mock_gem_device(void)
|
|||
dma_coerce_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64));
|
||||
|
||||
#if IS_ENABLED(CONFIG_IOMMU_API) && defined(CONFIG_INTEL_IOMMU)
|
||||
/* HACK HACK HACK to disable iommu for the fake device; force identity mapping */
|
||||
memset(&iommu, 0, sizeof(iommu));
|
||||
iommu.priv = (void *)-1;
|
||||
pdev->dev.iommu = &iommu;
|
||||
/* HACK to disable iommu for the fake device; force identity mapping */
|
||||
pdev->dev.iommu = &fake_iommu;
|
||||
#endif
|
||||
|
||||
pci_set_drvdata(pdev, i915);
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ struct sun8i_mixer;
|
|||
|
||||
/* VI channel CSC units offsets */
|
||||
#define CCSC00_OFFSET 0xAA050
|
||||
#define CCSC01_OFFSET 0xFA000
|
||||
#define CCSC01_OFFSET 0xFA050
|
||||
#define CCSC10_OFFSET 0xA0000
|
||||
#define CCSC11_OFFSET 0xF0000
|
||||
|
||||
|
|
|
|||
|
|
@ -307,7 +307,7 @@ static struct regmap_config sun8i_mixer_regmap_config = {
|
|||
.reg_bits = 32,
|
||||
.val_bits = 32,
|
||||
.reg_stride = 4,
|
||||
.max_register = 0xbfffc, /* guessed */
|
||||
.max_register = 0xffffc, /* guessed */
|
||||
};
|
||||
|
||||
static int sun8i_mixer_of_get_id(struct device_node *node)
|
||||
|
|
|
|||
|
|
@ -1117,6 +1117,7 @@ static int vc4_hdmi_audio_init(struct vc4_hdmi *hdmi)
|
|||
card->num_links = 1;
|
||||
card->name = "vc4-hdmi";
|
||||
card->dev = dev;
|
||||
card->owner = THIS_MODULE;
|
||||
|
||||
/*
|
||||
* Be careful, snd_soc_register_card() calls dev_set_drvdata() and
|
||||
|
|
|
|||
|
|
@ -1285,6 +1285,8 @@ static void disable_device(struct ib_device *device)
|
|||
remove_client_context(device, cid);
|
||||
}
|
||||
|
||||
ib_cq_pool_destroy(device);
|
||||
|
||||
/* Pairs with refcount_set in enable_device */
|
||||
ib_device_put(device);
|
||||
wait_for_completion(&device->unreg_completion);
|
||||
|
|
@ -1328,6 +1330,8 @@ static int enable_device_and_get(struct ib_device *device)
|
|||
goto out;
|
||||
}
|
||||
|
||||
ib_cq_pool_init(device);
|
||||
|
||||
down_read(&clients_rwsem);
|
||||
xa_for_each_marked (&clients, index, client, CLIENT_REGISTERED) {
|
||||
ret = add_client_context(device, client);
|
||||
|
|
@ -1400,7 +1404,6 @@ int ib_register_device(struct ib_device *device, const char *name)
|
|||
goto dev_cleanup;
|
||||
}
|
||||
|
||||
ib_cq_pool_init(device);
|
||||
ret = enable_device_and_get(device);
|
||||
dev_set_uevent_suppress(&device->dev, false);
|
||||
/* Mark for userspace that device is ready */
|
||||
|
|
@ -1455,7 +1458,6 @@ static void __ib_unregister_device(struct ib_device *ib_dev)
|
|||
goto out;
|
||||
|
||||
disable_device(ib_dev);
|
||||
ib_cq_pool_destroy(ib_dev);
|
||||
|
||||
/* Expedite removing unregistered pointers from the hash table */
|
||||
free_netdevs(ib_dev);
|
||||
|
|
|
|||
|
|
@ -1725,23 +1725,6 @@ static blk_qc_t __process_bio(struct mapped_device *md, struct dm_table *map,
|
|||
return ret;
|
||||
}
|
||||
|
||||
static void dm_queue_split(struct mapped_device *md, struct dm_target *ti, struct bio **bio)
|
||||
{
|
||||
unsigned len, sector_count;
|
||||
|
||||
sector_count = bio_sectors(*bio);
|
||||
len = min_t(sector_t, max_io_len((*bio)->bi_iter.bi_sector, ti), sector_count);
|
||||
|
||||
if (sector_count > len) {
|
||||
struct bio *split = bio_split(*bio, len, GFP_NOIO, &md->queue->bio_split);
|
||||
|
||||
bio_chain(split, *bio);
|
||||
trace_block_split(md->queue, split, (*bio)->bi_iter.bi_sector);
|
||||
submit_bio_noacct(*bio);
|
||||
*bio = split;
|
||||
}
|
||||
}
|
||||
|
||||
static blk_qc_t dm_process_bio(struct mapped_device *md,
|
||||
struct dm_table *map, struct bio *bio)
|
||||
{
|
||||
|
|
@ -1762,21 +1745,21 @@ static blk_qc_t dm_process_bio(struct mapped_device *md,
|
|||
}
|
||||
|
||||
/*
|
||||
* If in ->queue_bio we need to use blk_queue_split(), otherwise
|
||||
* If in ->submit_bio we need to use blk_queue_split(), otherwise
|
||||
* queue_limits for abnormal requests (e.g. discard, writesame, etc)
|
||||
* won't be imposed.
|
||||
* If called from dm_wq_work() for deferred bio processing, bio
|
||||
* was already handled by following code with previous ->submit_bio.
|
||||
*/
|
||||
if (current->bio_list) {
|
||||
if (is_abnormal_io(bio))
|
||||
blk_queue_split(&bio);
|
||||
else
|
||||
dm_queue_split(md, ti, &bio);
|
||||
/* regular IO is split by __split_and_process_bio */
|
||||
}
|
||||
|
||||
if (dm_get_md_type(md) == DM_TYPE_NVME_BIO_BASED)
|
||||
return __process_bio(md, map, bio, ti);
|
||||
else
|
||||
return __split_and_process_bio(md, map, bio);
|
||||
return __split_and_process_bio(md, map, bio);
|
||||
}
|
||||
|
||||
static blk_qc_t dm_submit_bio(struct bio *bio)
|
||||
|
|
|
|||
|
|
@ -1199,7 +1199,7 @@ void cec_received_msg_ts(struct cec_adapter *adap,
|
|||
/* Cancel the pending timeout work */
|
||||
if (!cancel_delayed_work(&data->work)) {
|
||||
mutex_unlock(&adap->lock);
|
||||
flush_scheduled_work();
|
||||
cancel_delayed_work_sync(&data->work);
|
||||
mutex_lock(&adap->lock);
|
||||
}
|
||||
/*
|
||||
|
|
|
|||
|
|
@ -721,39 +721,14 @@ int vb2_verify_memory_type(struct vb2_queue *q,
|
|||
}
|
||||
EXPORT_SYMBOL(vb2_verify_memory_type);
|
||||
|
||||
static void set_queue_consistency(struct vb2_queue *q, bool consistent_mem)
|
||||
{
|
||||
q->dma_attrs &= ~DMA_ATTR_NON_CONSISTENT;
|
||||
|
||||
if (!vb2_queue_allows_cache_hints(q))
|
||||
return;
|
||||
if (!consistent_mem)
|
||||
q->dma_attrs |= DMA_ATTR_NON_CONSISTENT;
|
||||
}
|
||||
|
||||
static bool verify_consistency_attr(struct vb2_queue *q, bool consistent_mem)
|
||||
{
|
||||
bool queue_is_consistent = !(q->dma_attrs & DMA_ATTR_NON_CONSISTENT);
|
||||
|
||||
if (consistent_mem != queue_is_consistent) {
|
||||
dprintk(q, 1, "memory consistency model mismatch\n");
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
int vb2_core_reqbufs(struct vb2_queue *q, enum vb2_memory memory,
|
||||
unsigned int flags, unsigned int *count)
|
||||
unsigned int *count)
|
||||
{
|
||||
unsigned int num_buffers, allocated_buffers, num_planes = 0;
|
||||
unsigned plane_sizes[VB2_MAX_PLANES] = { };
|
||||
bool consistent_mem = true;
|
||||
unsigned int i;
|
||||
int ret;
|
||||
|
||||
if (flags & V4L2_FLAG_MEMORY_NON_CONSISTENT)
|
||||
consistent_mem = false;
|
||||
|
||||
if (q->streaming) {
|
||||
dprintk(q, 1, "streaming active\n");
|
||||
return -EBUSY;
|
||||
|
|
@ -765,8 +740,7 @@ int vb2_core_reqbufs(struct vb2_queue *q, enum vb2_memory memory,
|
|||
}
|
||||
|
||||
if (*count == 0 || q->num_buffers != 0 ||
|
||||
(q->memory != VB2_MEMORY_UNKNOWN && q->memory != memory) ||
|
||||
!verify_consistency_attr(q, consistent_mem)) {
|
||||
(q->memory != VB2_MEMORY_UNKNOWN && q->memory != memory)) {
|
||||
/*
|
||||
* We already have buffers allocated, so first check if they
|
||||
* are not in use and can be freed.
|
||||
|
|
@ -803,7 +777,6 @@ int vb2_core_reqbufs(struct vb2_queue *q, enum vb2_memory memory,
|
|||
num_buffers = min_t(unsigned int, num_buffers, VB2_MAX_FRAME);
|
||||
memset(q->alloc_devs, 0, sizeof(q->alloc_devs));
|
||||
q->memory = memory;
|
||||
set_queue_consistency(q, consistent_mem);
|
||||
|
||||
/*
|
||||
* Ask the driver how many buffers and planes per buffer it requires.
|
||||
|
|
@ -888,18 +861,14 @@ int vb2_core_reqbufs(struct vb2_queue *q, enum vb2_memory memory,
|
|||
EXPORT_SYMBOL_GPL(vb2_core_reqbufs);
|
||||
|
||||
int vb2_core_create_bufs(struct vb2_queue *q, enum vb2_memory memory,
|
||||
unsigned int flags, unsigned int *count,
|
||||
unsigned int *count,
|
||||
unsigned int requested_planes,
|
||||
const unsigned int requested_sizes[])
|
||||
{
|
||||
unsigned int num_planes = 0, num_buffers, allocated_buffers;
|
||||
unsigned plane_sizes[VB2_MAX_PLANES] = { };
|
||||
bool consistent_mem = true;
|
||||
int ret;
|
||||
|
||||
if (flags & V4L2_FLAG_MEMORY_NON_CONSISTENT)
|
||||
consistent_mem = false;
|
||||
|
||||
if (q->num_buffers == VB2_MAX_FRAME) {
|
||||
dprintk(q, 1, "maximum number of buffers already allocated\n");
|
||||
return -ENOBUFS;
|
||||
|
|
@ -912,15 +881,12 @@ int vb2_core_create_bufs(struct vb2_queue *q, enum vb2_memory memory,
|
|||
}
|
||||
memset(q->alloc_devs, 0, sizeof(q->alloc_devs));
|
||||
q->memory = memory;
|
||||
set_queue_consistency(q, consistent_mem);
|
||||
q->waiting_for_buffers = !q->is_output;
|
||||
} else {
|
||||
if (q->memory != memory) {
|
||||
dprintk(q, 1, "memory model mismatch\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
if (!verify_consistency_attr(q, consistent_mem))
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
num_buffers = min(*count, VB2_MAX_FRAME - q->num_buffers);
|
||||
|
|
@ -2581,7 +2547,7 @@ static int __vb2_init_fileio(struct vb2_queue *q, int read)
|
|||
fileio->memory = VB2_MEMORY_MMAP;
|
||||
fileio->type = q->type;
|
||||
q->fileio = fileio;
|
||||
ret = vb2_core_reqbufs(q, fileio->memory, 0, &fileio->count);
|
||||
ret = vb2_core_reqbufs(q, fileio->memory, &fileio->count);
|
||||
if (ret)
|
||||
goto err_kfree;
|
||||
|
||||
|
|
@ -2638,7 +2604,7 @@ static int __vb2_init_fileio(struct vb2_queue *q, int read)
|
|||
|
||||
err_reqbufs:
|
||||
fileio->count = 0;
|
||||
vb2_core_reqbufs(q, fileio->memory, 0, &fileio->count);
|
||||
vb2_core_reqbufs(q, fileio->memory, &fileio->count);
|
||||
|
||||
err_kfree:
|
||||
q->fileio = NULL;
|
||||
|
|
@ -2658,7 +2624,7 @@ static int __vb2_cleanup_fileio(struct vb2_queue *q)
|
|||
vb2_core_streamoff(q, q->type);
|
||||
q->fileio = NULL;
|
||||
fileio->count = 0;
|
||||
vb2_core_reqbufs(q, fileio->memory, 0, &fileio->count);
|
||||
vb2_core_reqbufs(q, fileio->memory, &fileio->count);
|
||||
kfree(fileio);
|
||||
dprintk(q, 3, "file io emulator closed\n");
|
||||
}
|
||||
|
|
|
|||
|
|
@ -42,11 +42,6 @@ struct vb2_dc_buf {
|
|||
struct dma_buf_attachment *db_attach;
|
||||
};
|
||||
|
||||
static inline bool vb2_dc_buffer_consistent(unsigned long attr)
|
||||
{
|
||||
return !(attr & DMA_ATTR_NON_CONSISTENT);
|
||||
}
|
||||
|
||||
/*********************************************/
|
||||
/* scatterlist table functions */
|
||||
/*********************************************/
|
||||
|
|
@ -341,13 +336,6 @@ static int
|
|||
vb2_dc_dmabuf_ops_begin_cpu_access(struct dma_buf *dbuf,
|
||||
enum dma_data_direction direction)
|
||||
{
|
||||
struct vb2_dc_buf *buf = dbuf->priv;
|
||||
struct sg_table *sgt = buf->dma_sgt;
|
||||
|
||||
if (vb2_dc_buffer_consistent(buf->attrs))
|
||||
return 0;
|
||||
|
||||
dma_sync_sg_for_cpu(buf->dev, sgt->sgl, sgt->nents, buf->dma_dir);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -355,13 +343,6 @@ static int
|
|||
vb2_dc_dmabuf_ops_end_cpu_access(struct dma_buf *dbuf,
|
||||
enum dma_data_direction direction)
|
||||
{
|
||||
struct vb2_dc_buf *buf = dbuf->priv;
|
||||
struct sg_table *sgt = buf->dma_sgt;
|
||||
|
||||
if (vb2_dc_buffer_consistent(buf->attrs))
|
||||
return 0;
|
||||
|
||||
dma_sync_sg_for_device(buf->dev, sgt->sgl, sgt->nents, buf->dma_dir);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -123,8 +123,7 @@ static void *vb2_dma_sg_alloc(struct device *dev, unsigned long dma_attrs,
|
|||
/*
|
||||
* NOTE: dma-sg allocates memory using the page allocator directly, so
|
||||
* there is no memory consistency guarantee, hence dma-sg ignores DMA
|
||||
* attributes passed from the upper layer. That means that
|
||||
* V4L2_FLAG_MEMORY_NON_CONSISTENT has no effect on dma-sg buffers.
|
||||
* attributes passed from the upper layer.
|
||||
*/
|
||||
buf->pages = kvmalloc_array(buf->num_pages, sizeof(struct page *),
|
||||
GFP_KERNEL | __GFP_ZERO);
|
||||
|
|
|
|||
|
|
@ -722,22 +722,12 @@ static void fill_buf_caps(struct vb2_queue *q, u32 *caps)
|
|||
#endif
|
||||
}
|
||||
|
||||
static void clear_consistency_attr(struct vb2_queue *q,
|
||||
int memory,
|
||||
unsigned int *flags)
|
||||
{
|
||||
if (!q->allow_cache_hints || memory != V4L2_MEMORY_MMAP)
|
||||
*flags &= ~V4L2_FLAG_MEMORY_NON_CONSISTENT;
|
||||
}
|
||||
|
||||
int vb2_reqbufs(struct vb2_queue *q, struct v4l2_requestbuffers *req)
|
||||
{
|
||||
int ret = vb2_verify_memory_type(q, req->memory, req->type);
|
||||
|
||||
fill_buf_caps(q, &req->capabilities);
|
||||
clear_consistency_attr(q, req->memory, &req->flags);
|
||||
return ret ? ret : vb2_core_reqbufs(q, req->memory,
|
||||
req->flags, &req->count);
|
||||
return ret ? ret : vb2_core_reqbufs(q, req->memory, &req->count);
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(vb2_reqbufs);
|
||||
|
||||
|
|
@ -769,7 +759,6 @@ int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|||
unsigned i;
|
||||
|
||||
fill_buf_caps(q, &create->capabilities);
|
||||
clear_consistency_attr(q, create->memory, &create->flags);
|
||||
create->index = q->num_buffers;
|
||||
if (create->count == 0)
|
||||
return ret != -EBUSY ? ret : 0;
|
||||
|
|
@ -813,7 +802,6 @@ int vb2_create_bufs(struct vb2_queue *q, struct v4l2_create_buffers *create)
|
|||
if (requested_sizes[i] == 0)
|
||||
return -EINVAL;
|
||||
return ret ? ret : vb2_core_create_bufs(q, create->memory,
|
||||
create->flags,
|
||||
&create->count,
|
||||
requested_planes,
|
||||
requested_sizes);
|
||||
|
|
@ -998,12 +986,11 @@ int vb2_ioctl_reqbufs(struct file *file, void *priv,
|
|||
int res = vb2_verify_memory_type(vdev->queue, p->memory, p->type);
|
||||
|
||||
fill_buf_caps(vdev->queue, &p->capabilities);
|
||||
clear_consistency_attr(vdev->queue, p->memory, &p->flags);
|
||||
if (res)
|
||||
return res;
|
||||
if (vb2_queue_is_busy(vdev, file))
|
||||
return -EBUSY;
|
||||
res = vb2_core_reqbufs(vdev->queue, p->memory, p->flags, &p->count);
|
||||
res = vb2_core_reqbufs(vdev->queue, p->memory, &p->count);
|
||||
/* If count == 0, then the owner has released all buffers and he
|
||||
is no longer owner of the queue. Otherwise we have a new owner. */
|
||||
if (res == 0)
|
||||
|
|
@ -1021,7 +1008,6 @@ int vb2_ioctl_create_bufs(struct file *file, void *priv,
|
|||
|
||||
p->index = vdev->queue->num_buffers;
|
||||
fill_buf_caps(vdev->queue, &p->capabilities);
|
||||
clear_consistency_attr(vdev->queue, p->memory, &p->flags);
|
||||
/*
|
||||
* If count == 0, then just check if memory and type are valid.
|
||||
* Any -EBUSY result from vb2_verify_memory_type can be mapped to 0.
|
||||
|
|
|
|||
|
|
@ -342,7 +342,7 @@ int dvb_vb2_reqbufs(struct dvb_vb2_ctx *ctx, struct dmx_requestbuffers *req)
|
|||
|
||||
ctx->buf_siz = req->size;
|
||||
ctx->buf_cnt = req->count;
|
||||
ret = vb2_core_reqbufs(&ctx->vb_q, VB2_MEMORY_MMAP, 0, &req->count);
|
||||
ret = vb2_core_reqbufs(&ctx->vb_q, VB2_MEMORY_MMAP, &req->count);
|
||||
if (ret) {
|
||||
ctx->state = DVB_VB2_STATE_NONE;
|
||||
dprintk(1, "[%s] count=%d size=%d errno=%d\n", ctx->name,
|
||||
|
|
|
|||
|
|
@ -246,9 +246,6 @@ struct v4l2_format32 {
|
|||
* @memory: buffer memory type
|
||||
* @format: frame format, for which buffers are requested
|
||||
* @capabilities: capabilities of this buffer type.
|
||||
* @flags: additional buffer management attributes (ignored unless the
|
||||
* queue has V4L2_BUF_CAP_SUPPORTS_MMAP_CACHE_HINTS capability and
|
||||
* configured for MMAP streaming I/O).
|
||||
* @reserved: future extensions
|
||||
*/
|
||||
struct v4l2_create_buffers32 {
|
||||
|
|
@ -257,8 +254,7 @@ struct v4l2_create_buffers32 {
|
|||
__u32 memory; /* enum v4l2_memory */
|
||||
struct v4l2_format32 format;
|
||||
__u32 capabilities;
|
||||
__u32 flags;
|
||||
__u32 reserved[6];
|
||||
__u32 reserved[7];
|
||||
};
|
||||
|
||||
static int __bufsize_v4l2_format(struct v4l2_format32 __user *p32, u32 *size)
|
||||
|
|
@ -359,8 +355,7 @@ static int get_v4l2_create32(struct v4l2_create_buffers __user *p64,
|
|||
{
|
||||
if (!access_ok(p32, sizeof(*p32)) ||
|
||||
copy_in_user(p64, p32,
|
||||
offsetof(struct v4l2_create_buffers32, format)) ||
|
||||
assign_in_user(&p64->flags, &p32->flags))
|
||||
offsetof(struct v4l2_create_buffers32, format)))
|
||||
return -EFAULT;
|
||||
return __get_v4l2_format32(&p64->format, &p32->format,
|
||||
aux_buf, aux_space);
|
||||
|
|
@ -422,7 +417,6 @@ static int put_v4l2_create32(struct v4l2_create_buffers __user *p64,
|
|||
copy_in_user(p32, p64,
|
||||
offsetof(struct v4l2_create_buffers32, format)) ||
|
||||
assign_in_user(&p32->capabilities, &p64->capabilities) ||
|
||||
assign_in_user(&p32->flags, &p64->flags) ||
|
||||
copy_in_user(p32->reserved, p64->reserved, sizeof(p64->reserved)))
|
||||
return -EFAULT;
|
||||
return __put_v4l2_format32(&p64->format, &p32->format);
|
||||
|
|
|
|||
|
|
@ -2042,6 +2042,9 @@ static int v4l_reqbufs(const struct v4l2_ioctl_ops *ops,
|
|||
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
CLEAR_AFTER_FIELD(p, capabilities);
|
||||
|
||||
return ops->vidioc_reqbufs(file, fh, p);
|
||||
}
|
||||
|
||||
|
|
@ -2081,7 +2084,7 @@ static int v4l_create_bufs(const struct v4l2_ioctl_ops *ops,
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
CLEAR_AFTER_FIELD(create, flags);
|
||||
CLEAR_AFTER_FIELD(create, capabilities);
|
||||
|
||||
v4l_sanitize_format(&create->format);
|
||||
|
||||
|
|
|
|||
|
|
@ -1320,7 +1320,7 @@ static void mmc_spi_dma_free(struct mmc_spi_host *host)
|
|||
DMA_BIDIRECTIONAL);
|
||||
}
|
||||
#else
|
||||
static inline mmc_spi_dma_alloc(struct mmc_spi_host *host) { return 0; }
|
||||
static inline int mmc_spi_dma_alloc(struct mmc_spi_host *host) { return 0; }
|
||||
static inline void mmc_spi_dma_free(struct mmc_spi_host *host) {}
|
||||
#endif
|
||||
|
||||
|
|
|
|||
|
|
@ -932,11 +932,19 @@ static void ksz8795_port_setup(struct ksz_device *dev, int port, bool cpu_port)
|
|||
ksz_port_cfg(dev, port, P_PRIO_CTRL, PORT_802_1P_ENABLE, true);
|
||||
|
||||
if (cpu_port) {
|
||||
if (!p->interface && dev->compat_interface) {
|
||||
dev_warn(dev->dev,
|
||||
"Using legacy switch \"phy-mode\" property, because it is missing on port %d node. "
|
||||
"Please update your device tree.\n",
|
||||
port);
|
||||
p->interface = dev->compat_interface;
|
||||
}
|
||||
|
||||
/* Configure MII interface for proper network communication. */
|
||||
ksz_read8(dev, REG_PORT_5_CTRL_6, &data8);
|
||||
data8 &= ~PORT_INTERFACE_TYPE;
|
||||
data8 &= ~PORT_GMII_1GPS_MODE;
|
||||
switch (dev->interface) {
|
||||
switch (p->interface) {
|
||||
case PHY_INTERFACE_MODE_MII:
|
||||
p->phydev.speed = SPEED_100;
|
||||
break;
|
||||
|
|
@ -952,11 +960,11 @@ static void ksz8795_port_setup(struct ksz_device *dev, int port, bool cpu_port)
|
|||
default:
|
||||
data8 &= ~PORT_RGMII_ID_IN_ENABLE;
|
||||
data8 &= ~PORT_RGMII_ID_OUT_ENABLE;
|
||||
if (dev->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
dev->interface == PHY_INTERFACE_MODE_RGMII_RXID)
|
||||
if (p->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
p->interface == PHY_INTERFACE_MODE_RGMII_RXID)
|
||||
data8 |= PORT_RGMII_ID_IN_ENABLE;
|
||||
if (dev->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
dev->interface == PHY_INTERFACE_MODE_RGMII_TXID)
|
||||
if (p->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
p->interface == PHY_INTERFACE_MODE_RGMII_TXID)
|
||||
data8 |= PORT_RGMII_ID_OUT_ENABLE;
|
||||
data8 |= PORT_GMII_1GPS_MODE;
|
||||
data8 |= PORT_INTERFACE_RGMII;
|
||||
|
|
@ -1252,7 +1260,7 @@ static int ksz8795_switch_init(struct ksz_device *dev)
|
|||
}
|
||||
|
||||
/* set the real number of ports */
|
||||
dev->ds->num_ports = dev->port_cnt;
|
||||
dev->ds->num_ports = dev->port_cnt + 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1208,7 +1208,7 @@ static void ksz9477_port_setup(struct ksz_device *dev, int port, bool cpu_port)
|
|||
|
||||
/* configure MAC to 1G & RGMII mode */
|
||||
ksz_pread8(dev, port, REG_PORT_XMII_CTRL_1, &data8);
|
||||
switch (dev->interface) {
|
||||
switch (p->interface) {
|
||||
case PHY_INTERFACE_MODE_MII:
|
||||
ksz9477_set_xmii(dev, 0, &data8);
|
||||
ksz9477_set_gbit(dev, false, &data8);
|
||||
|
|
@ -1229,11 +1229,11 @@ static void ksz9477_port_setup(struct ksz_device *dev, int port, bool cpu_port)
|
|||
ksz9477_set_gbit(dev, true, &data8);
|
||||
data8 &= ~PORT_RGMII_ID_IG_ENABLE;
|
||||
data8 &= ~PORT_RGMII_ID_EG_ENABLE;
|
||||
if (dev->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
dev->interface == PHY_INTERFACE_MODE_RGMII_RXID)
|
||||
if (p->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
p->interface == PHY_INTERFACE_MODE_RGMII_RXID)
|
||||
data8 |= PORT_RGMII_ID_IG_ENABLE;
|
||||
if (dev->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
dev->interface == PHY_INTERFACE_MODE_RGMII_TXID)
|
||||
if (p->interface == PHY_INTERFACE_MODE_RGMII_ID ||
|
||||
p->interface == PHY_INTERFACE_MODE_RGMII_TXID)
|
||||
data8 |= PORT_RGMII_ID_EG_ENABLE;
|
||||
p->phydev.speed = SPEED_1000;
|
||||
break;
|
||||
|
|
@ -1269,23 +1269,32 @@ static void ksz9477_config_cpu_port(struct dsa_switch *ds)
|
|||
dev->cpu_port = i;
|
||||
dev->host_mask = (1 << dev->cpu_port);
|
||||
dev->port_mask |= dev->host_mask;
|
||||
p = &dev->ports[i];
|
||||
|
||||
/* Read from XMII register to determine host port
|
||||
* interface. If set specifically in device tree
|
||||
* note the difference to help debugging.
|
||||
*/
|
||||
interface = ksz9477_get_interface(dev, i);
|
||||
if (!dev->interface)
|
||||
dev->interface = interface;
|
||||
if (interface && interface != dev->interface)
|
||||
if (!p->interface) {
|
||||
if (dev->compat_interface) {
|
||||
dev_warn(dev->dev,
|
||||
"Using legacy switch \"phy-mode\" property, because it is missing on port %d node. "
|
||||
"Please update your device tree.\n",
|
||||
i);
|
||||
p->interface = dev->compat_interface;
|
||||
} else {
|
||||
p->interface = interface;
|
||||
}
|
||||
}
|
||||
if (interface && interface != p->interface)
|
||||
dev_info(dev->dev,
|
||||
"use %s instead of %s\n",
|
||||
phy_modes(dev->interface),
|
||||
phy_modes(p->interface),
|
||||
phy_modes(interface));
|
||||
|
||||
/* enable cpu port */
|
||||
ksz9477_port_setup(dev, i, true);
|
||||
p = &dev->ports[dev->cpu_port];
|
||||
p->vid_member = dev->port_mask;
|
||||
p->on = 1;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -388,6 +388,8 @@ int ksz_switch_register(struct ksz_device *dev,
|
|||
const struct ksz_dev_ops *ops)
|
||||
{
|
||||
phy_interface_t interface;
|
||||
struct device_node *port;
|
||||
unsigned int port_num;
|
||||
int ret;
|
||||
|
||||
if (dev->pdata)
|
||||
|
|
@ -421,10 +423,19 @@ int ksz_switch_register(struct ksz_device *dev,
|
|||
/* Host port interface will be self detected, or specifically set in
|
||||
* device tree.
|
||||
*/
|
||||
for (port_num = 0; port_num < dev->port_cnt; ++port_num)
|
||||
dev->ports[port_num].interface = PHY_INTERFACE_MODE_NA;
|
||||
if (dev->dev->of_node) {
|
||||
ret = of_get_phy_mode(dev->dev->of_node, &interface);
|
||||
if (ret == 0)
|
||||
dev->interface = interface;
|
||||
dev->compat_interface = interface;
|
||||
for_each_available_child_of_node(dev->dev->of_node, port) {
|
||||
if (of_property_read_u32(port, "reg", &port_num))
|
||||
continue;
|
||||
if (port_num >= dev->port_cnt)
|
||||
return -EINVAL;
|
||||
of_get_phy_mode(port, &dev->ports[port_num].interface);
|
||||
}
|
||||
dev->synclko_125 = of_property_read_bool(dev->dev->of_node,
|
||||
"microchip,synclko-125");
|
||||
}
|
||||
|
|
|
|||
|
|
@ -39,6 +39,7 @@ struct ksz_port {
|
|||
u32 freeze:1; /* MIB counter freeze is enabled */
|
||||
|
||||
struct ksz_port_mib mib;
|
||||
phy_interface_t interface;
|
||||
};
|
||||
|
||||
struct ksz_device {
|
||||
|
|
@ -72,7 +73,7 @@ struct ksz_device {
|
|||
int mib_cnt;
|
||||
int mib_port_cnt;
|
||||
int last_port; /* ports after that not used */
|
||||
phy_interface_t interface;
|
||||
phy_interface_t compat_interface;
|
||||
u32 regs_size;
|
||||
bool phy_errata_9477;
|
||||
bool synclko_125;
|
||||
|
|
|
|||
|
|
@ -585,7 +585,10 @@ static int felix_setup(struct dsa_switch *ds)
|
|||
if (err)
|
||||
return err;
|
||||
|
||||
ocelot_init(ocelot);
|
||||
err = ocelot_init(ocelot);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
if (ocelot->ptp) {
|
||||
err = ocelot_init_timestamp(ocelot, &ocelot_ptp_clock_info);
|
||||
if (err) {
|
||||
|
|
@ -640,10 +643,13 @@ static void felix_teardown(struct dsa_switch *ds)
|
|||
{
|
||||
struct ocelot *ocelot = ds->priv;
|
||||
struct felix *felix = ocelot_to_felix(ocelot);
|
||||
int port;
|
||||
|
||||
if (felix->info->mdio_bus_free)
|
||||
felix->info->mdio_bus_free(ocelot);
|
||||
|
||||
for (port = 0; port < ocelot->num_phys_ports; port++)
|
||||
ocelot_deinit_port(ocelot, port);
|
||||
ocelot_deinit_timestamp(ocelot);
|
||||
/* stop workqueue thread */
|
||||
ocelot_deinit(ocelot);
|
||||
|
|
|
|||
|
|
@ -645,17 +645,17 @@ static struct vcap_field vsc9959_vcap_is2_keys[] = {
|
|||
[VCAP_IS2_HK_DIP_EQ_SIP] = {118, 1},
|
||||
/* IP4_TCP_UDP (TYPE=100) */
|
||||
[VCAP_IS2_HK_TCP] = {119, 1},
|
||||
[VCAP_IS2_HK_L4_SPORT] = {120, 16},
|
||||
[VCAP_IS2_HK_L4_DPORT] = {136, 16},
|
||||
[VCAP_IS2_HK_L4_DPORT] = {120, 16},
|
||||
[VCAP_IS2_HK_L4_SPORT] = {136, 16},
|
||||
[VCAP_IS2_HK_L4_RNG] = {152, 8},
|
||||
[VCAP_IS2_HK_L4_SPORT_EQ_DPORT] = {160, 1},
|
||||
[VCAP_IS2_HK_L4_SEQUENCE_EQ0] = {161, 1},
|
||||
[VCAP_IS2_HK_L4_URG] = {162, 1},
|
||||
[VCAP_IS2_HK_L4_ACK] = {163, 1},
|
||||
[VCAP_IS2_HK_L4_PSH] = {164, 1},
|
||||
[VCAP_IS2_HK_L4_RST] = {165, 1},
|
||||
[VCAP_IS2_HK_L4_SYN] = {166, 1},
|
||||
[VCAP_IS2_HK_L4_FIN] = {167, 1},
|
||||
[VCAP_IS2_HK_L4_FIN] = {162, 1},
|
||||
[VCAP_IS2_HK_L4_SYN] = {163, 1},
|
||||
[VCAP_IS2_HK_L4_RST] = {164, 1},
|
||||
[VCAP_IS2_HK_L4_PSH] = {165, 1},
|
||||
[VCAP_IS2_HK_L4_ACK] = {166, 1},
|
||||
[VCAP_IS2_HK_L4_URG] = {167, 1},
|
||||
[VCAP_IS2_HK_L4_1588_DOM] = {168, 8},
|
||||
[VCAP_IS2_HK_L4_1588_VER] = {176, 4},
|
||||
/* IP4_OTHER (TYPE=101) */
|
||||
|
|
|
|||
|
|
@ -659,17 +659,17 @@ static struct vcap_field vsc9953_vcap_is2_keys[] = {
|
|||
[VCAP_IS2_HK_DIP_EQ_SIP] = {122, 1},
|
||||
/* IP4_TCP_UDP (TYPE=100) */
|
||||
[VCAP_IS2_HK_TCP] = {123, 1},
|
||||
[VCAP_IS2_HK_L4_SPORT] = {124, 16},
|
||||
[VCAP_IS2_HK_L4_DPORT] = {140, 16},
|
||||
[VCAP_IS2_HK_L4_DPORT] = {124, 16},
|
||||
[VCAP_IS2_HK_L4_SPORT] = {140, 16},
|
||||
[VCAP_IS2_HK_L4_RNG] = {156, 8},
|
||||
[VCAP_IS2_HK_L4_SPORT_EQ_DPORT] = {164, 1},
|
||||
[VCAP_IS2_HK_L4_SEQUENCE_EQ0] = {165, 1},
|
||||
[VCAP_IS2_HK_L4_URG] = {166, 1},
|
||||
[VCAP_IS2_HK_L4_ACK] = {167, 1},
|
||||
[VCAP_IS2_HK_L4_PSH] = {168, 1},
|
||||
[VCAP_IS2_HK_L4_RST] = {169, 1},
|
||||
[VCAP_IS2_HK_L4_SYN] = {170, 1},
|
||||
[VCAP_IS2_HK_L4_FIN] = {171, 1},
|
||||
[VCAP_IS2_HK_L4_FIN] = {166, 1},
|
||||
[VCAP_IS2_HK_L4_SYN] = {167, 1},
|
||||
[VCAP_IS2_HK_L4_RST] = {168, 1},
|
||||
[VCAP_IS2_HK_L4_PSH] = {169, 1},
|
||||
[VCAP_IS2_HK_L4_ACK] = {170, 1},
|
||||
[VCAP_IS2_HK_L4_URG] = {171, 1},
|
||||
/* IP4_OTHER (TYPE=101) */
|
||||
[VCAP_IS2_HK_IP4_L3_PROTO] = {123, 8},
|
||||
[VCAP_IS2_HK_L3_PAYLOAD] = {131, 56},
|
||||
|
|
@ -1008,7 +1008,7 @@ static const struct felix_info seville_info_vsc9953 = {
|
|||
.vcap_is2_keys = vsc9953_vcap_is2_keys,
|
||||
.vcap_is2_actions = vsc9953_vcap_is2_actions,
|
||||
.vcap = vsc9953_vcap_props,
|
||||
.shared_queue_sz = 128 * 1024,
|
||||
.shared_queue_sz = 2048 * 1024,
|
||||
.num_mact_rows = 2048,
|
||||
.num_ports = 10,
|
||||
.mdio_bus_alloc = vsc9953_mdio_bus_alloc,
|
||||
|
|
|
|||
|
|
@ -452,13 +452,19 @@ int rtl8366_vlan_del(struct dsa_switch *ds, int port,
|
|||
return ret;
|
||||
|
||||
if (vid == vlanmc.vid) {
|
||||
/* clear VLAN member configurations */
|
||||
vlanmc.vid = 0;
|
||||
vlanmc.priority = 0;
|
||||
vlanmc.member = 0;
|
||||
vlanmc.untag = 0;
|
||||
vlanmc.fid = 0;
|
||||
|
||||
/* Remove this port from the VLAN */
|
||||
vlanmc.member &= ~BIT(port);
|
||||
vlanmc.untag &= ~BIT(port);
|
||||
/*
|
||||
* If no ports are members of this VLAN
|
||||
* anymore then clear the whole member
|
||||
* config so it can be reused.
|
||||
*/
|
||||
if (!vlanmc.member && vlanmc.untag) {
|
||||
vlanmc.vid = 0;
|
||||
vlanmc.priority = 0;
|
||||
vlanmc.fid = 0;
|
||||
}
|
||||
ret = smi->ops->set_vlan_mc(smi, i, &vlanmc);
|
||||
if (ret) {
|
||||
dev_err(smi->dev,
|
||||
|
|
|
|||
|
|
@ -3782,6 +3782,7 @@ static int bnxt_hwrm_func_qstat_ext(struct bnxt *bp,
|
|||
return -EOPNOTSUPP;
|
||||
|
||||
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_FUNC_QSTATS_EXT, -1, -1);
|
||||
req.fid = cpu_to_le16(0xffff);
|
||||
req.flags = FUNC_QSTATS_EXT_REQ_FLAGS_COUNTER_MASK;
|
||||
mutex_lock(&bp->hwrm_cmd_lock);
|
||||
rc = _hwrm_send_message(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
|
||||
|
|
@ -3852,7 +3853,7 @@ static void bnxt_init_stats(struct bnxt *bp)
|
|||
tx_masks = stats->hw_masks;
|
||||
tx_count = sizeof(struct tx_port_stats_ext) / 8;
|
||||
|
||||
flags = FUNC_QSTATS_EXT_REQ_FLAGS_COUNTER_MASK;
|
||||
flags = PORT_QSTATS_EXT_REQ_FLAGS_COUNTER_MASK;
|
||||
rc = bnxt_hwrm_port_qstats_ext(bp, flags);
|
||||
if (rc) {
|
||||
mask = (1ULL << 40) - 1;
|
||||
|
|
@ -4305,7 +4306,7 @@ static int bnxt_hwrm_do_send_msg(struct bnxt *bp, void *msg, u32 msg_len,
|
|||
u32 bar_offset = BNXT_GRCPF_REG_CHIMP_COMM;
|
||||
u16 dst = BNXT_HWRM_CHNL_CHIMP;
|
||||
|
||||
if (test_bit(BNXT_STATE_FW_FATAL_COND, &bp->state))
|
||||
if (BNXT_NO_FW_ACCESS(bp))
|
||||
return -EBUSY;
|
||||
|
||||
if (msg_len > BNXT_HWRM_MAX_REQ_LEN) {
|
||||
|
|
@ -5723,7 +5724,7 @@ static int hwrm_ring_free_send_msg(struct bnxt *bp,
|
|||
struct hwrm_ring_free_output *resp = bp->hwrm_cmd_resp_addr;
|
||||
u16 error_code;
|
||||
|
||||
if (test_bit(BNXT_STATE_FW_FATAL_COND, &bp->state))
|
||||
if (BNXT_NO_FW_ACCESS(bp))
|
||||
return 0;
|
||||
|
||||
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_RING_FREE, cmpl_ring_id, -1);
|
||||
|
|
@ -7817,7 +7818,7 @@ static int bnxt_set_tpa(struct bnxt *bp, bool set_tpa)
|
|||
|
||||
if (set_tpa)
|
||||
tpa_flags = bp->flags & BNXT_FLAG_TPA;
|
||||
else if (test_bit(BNXT_STATE_FW_FATAL_COND, &bp->state))
|
||||
else if (BNXT_NO_FW_ACCESS(bp))
|
||||
return 0;
|
||||
for (i = 0; i < bp->nr_vnics; i++) {
|
||||
rc = bnxt_hwrm_vnic_set_tpa(bp, i, tpa_flags);
|
||||
|
|
@ -9311,18 +9312,16 @@ static ssize_t bnxt_show_temp(struct device *dev,
|
|||
struct hwrm_temp_monitor_query_output *resp;
|
||||
struct bnxt *bp = dev_get_drvdata(dev);
|
||||
u32 len = 0;
|
||||
int rc;
|
||||
|
||||
resp = bp->hwrm_cmd_resp_addr;
|
||||
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_TEMP_MONITOR_QUERY, -1, -1);
|
||||
mutex_lock(&bp->hwrm_cmd_lock);
|
||||
if (!_hwrm_send_message_silent(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT))
|
||||
rc = _hwrm_send_message(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
|
||||
if (!rc)
|
||||
len = sprintf(buf, "%u\n", resp->temp * 1000); /* display millidegree */
|
||||
mutex_unlock(&bp->hwrm_cmd_lock);
|
||||
|
||||
if (len)
|
||||
return len;
|
||||
|
||||
return sprintf(buf, "unknown\n");
|
||||
return rc ?: len;
|
||||
}
|
||||
static SENSOR_DEVICE_ATTR(temp1_input, 0444, bnxt_show_temp, NULL, 0);
|
||||
|
||||
|
|
@ -9342,7 +9341,16 @@ static void bnxt_hwmon_close(struct bnxt *bp)
|
|||
|
||||
static void bnxt_hwmon_open(struct bnxt *bp)
|
||||
{
|
||||
struct hwrm_temp_monitor_query_input req = {0};
|
||||
struct pci_dev *pdev = bp->pdev;
|
||||
int rc;
|
||||
|
||||
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_TEMP_MONITOR_QUERY, -1, -1);
|
||||
rc = hwrm_send_message_silent(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
|
||||
if (rc == -EACCES || rc == -EOPNOTSUPP) {
|
||||
bnxt_hwmon_close(bp);
|
||||
return;
|
||||
}
|
||||
|
||||
if (bp->hwmon_dev)
|
||||
return;
|
||||
|
|
@ -11779,6 +11787,10 @@ static void bnxt_remove_one(struct pci_dev *pdev)
|
|||
if (BNXT_PF(bp))
|
||||
bnxt_sriov_disable(bp);
|
||||
|
||||
clear_bit(BNXT_STATE_IN_FW_RESET, &bp->state);
|
||||
bnxt_cancel_sp_work(bp);
|
||||
bp->sp_event = 0;
|
||||
|
||||
bnxt_dl_fw_reporters_destroy(bp, true);
|
||||
if (BNXT_PF(bp))
|
||||
devlink_port_type_clear(&bp->dl_port);
|
||||
|
|
@ -11786,9 +11798,6 @@ static void bnxt_remove_one(struct pci_dev *pdev)
|
|||
unregister_netdev(dev);
|
||||
bnxt_dl_unregister(bp);
|
||||
bnxt_shutdown_tc(bp);
|
||||
clear_bit(BNXT_STATE_IN_FW_RESET, &bp->state);
|
||||
bnxt_cancel_sp_work(bp);
|
||||
bp->sp_event = 0;
|
||||
|
||||
bnxt_clear_int_mode(bp);
|
||||
bnxt_hwrm_func_drv_unrgtr(bp);
|
||||
|
|
@ -12089,7 +12098,7 @@ static int bnxt_init_mac_addr(struct bnxt *bp)
|
|||
static void bnxt_vpd_read_info(struct bnxt *bp)
|
||||
{
|
||||
struct pci_dev *pdev = bp->pdev;
|
||||
int i, len, pos, ro_size;
|
||||
int i, len, pos, ro_size, size;
|
||||
ssize_t vpd_size;
|
||||
u8 *vpd_data;
|
||||
|
||||
|
|
@ -12124,7 +12133,8 @@ static void bnxt_vpd_read_info(struct bnxt *bp)
|
|||
if (len + pos > vpd_size)
|
||||
goto read_sn;
|
||||
|
||||
strlcpy(bp->board_partno, &vpd_data[pos], min(len, BNXT_VPD_FLD_LEN));
|
||||
size = min(len, BNXT_VPD_FLD_LEN - 1);
|
||||
memcpy(bp->board_partno, &vpd_data[pos], size);
|
||||
|
||||
read_sn:
|
||||
pos = pci_vpd_find_info_keyword(vpd_data, i, ro_size,
|
||||
|
|
@ -12137,7 +12147,8 @@ static void bnxt_vpd_read_info(struct bnxt *bp)
|
|||
if (len + pos > vpd_size)
|
||||
goto exit;
|
||||
|
||||
strlcpy(bp->board_serialno, &vpd_data[pos], min(len, BNXT_VPD_FLD_LEN));
|
||||
size = min(len, BNXT_VPD_FLD_LEN - 1);
|
||||
memcpy(bp->board_serialno, &vpd_data[pos], size);
|
||||
exit:
|
||||
kfree(vpd_data);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1737,6 +1737,10 @@ struct bnxt {
|
|||
#define BNXT_STATE_FW_FATAL_COND 6
|
||||
#define BNXT_STATE_DRV_REGISTERED 7
|
||||
|
||||
#define BNXT_NO_FW_ACCESS(bp) \
|
||||
(test_bit(BNXT_STATE_FW_FATAL_COND, &(bp)->state) || \
|
||||
pci_channel_offline((bp)->pdev))
|
||||
|
||||
struct bnxt_irq *irq_tbl;
|
||||
int total_irqs;
|
||||
u8 mac_addr[ETH_ALEN];
|
||||
|
|
|
|||
|
|
@ -1322,6 +1322,9 @@ static int bnxt_get_regs_len(struct net_device *dev)
|
|||
struct bnxt *bp = netdev_priv(dev);
|
||||
int reg_len;
|
||||
|
||||
if (!BNXT_PF(bp))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
reg_len = BNXT_PXP_REG_LEN;
|
||||
|
||||
if (bp->fw_cap & BNXT_FW_CAP_PCIE_STATS_SUPPORTED)
|
||||
|
|
@ -1788,9 +1791,12 @@ static int bnxt_set_pauseparam(struct net_device *dev,
|
|||
if (!BNXT_PHY_CFG_ABLE(bp))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
mutex_lock(&bp->link_lock);
|
||||
if (epause->autoneg) {
|
||||
if (!(link_info->autoneg & BNXT_AUTONEG_SPEED))
|
||||
return -EINVAL;
|
||||
if (!(link_info->autoneg & BNXT_AUTONEG_SPEED)) {
|
||||
rc = -EINVAL;
|
||||
goto pause_exit;
|
||||
}
|
||||
|
||||
link_info->autoneg |= BNXT_AUTONEG_FLOW_CTRL;
|
||||
if (bp->hwrm_spec_code >= 0x10201)
|
||||
|
|
@ -1811,11 +1817,11 @@ static int bnxt_set_pauseparam(struct net_device *dev,
|
|||
if (epause->tx_pause)
|
||||
link_info->req_flow_ctrl |= BNXT_LINK_PAUSE_TX;
|
||||
|
||||
if (netif_running(dev)) {
|
||||
mutex_lock(&bp->link_lock);
|
||||
if (netif_running(dev))
|
||||
rc = bnxt_hwrm_set_pause(bp);
|
||||
mutex_unlock(&bp->link_lock);
|
||||
}
|
||||
|
||||
pause_exit:
|
||||
mutex_unlock(&bp->link_lock);
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
|
@ -2552,8 +2558,7 @@ static int bnxt_set_eee(struct net_device *dev, struct ethtool_eee *edata)
|
|||
struct bnxt *bp = netdev_priv(dev);
|
||||
struct ethtool_eee *eee = &bp->eee;
|
||||
struct bnxt_link_info *link_info = &bp->link_info;
|
||||
u32 advertising =
|
||||
_bnxt_fw_to_ethtool_adv_spds(link_info->advertising, 0);
|
||||
u32 advertising;
|
||||
int rc = 0;
|
||||
|
||||
if (!BNXT_PHY_CFG_ABLE(bp))
|
||||
|
|
@ -2562,19 +2567,23 @@ static int bnxt_set_eee(struct net_device *dev, struct ethtool_eee *edata)
|
|||
if (!(bp->flags & BNXT_FLAG_EEE_CAP))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
mutex_lock(&bp->link_lock);
|
||||
advertising = _bnxt_fw_to_ethtool_adv_spds(link_info->advertising, 0);
|
||||
if (!edata->eee_enabled)
|
||||
goto eee_ok;
|
||||
|
||||
if (!(link_info->autoneg & BNXT_AUTONEG_SPEED)) {
|
||||
netdev_warn(dev, "EEE requires autoneg\n");
|
||||
return -EINVAL;
|
||||
rc = -EINVAL;
|
||||
goto eee_exit;
|
||||
}
|
||||
if (edata->tx_lpi_enabled) {
|
||||
if (bp->lpi_tmr_hi && (edata->tx_lpi_timer > bp->lpi_tmr_hi ||
|
||||
edata->tx_lpi_timer < bp->lpi_tmr_lo)) {
|
||||
netdev_warn(dev, "Valid LPI timer range is %d and %d microsecs\n",
|
||||
bp->lpi_tmr_lo, bp->lpi_tmr_hi);
|
||||
return -EINVAL;
|
||||
rc = -EINVAL;
|
||||
goto eee_exit;
|
||||
} else if (!bp->lpi_tmr_hi) {
|
||||
edata->tx_lpi_timer = eee->tx_lpi_timer;
|
||||
}
|
||||
|
|
@ -2584,7 +2593,8 @@ static int bnxt_set_eee(struct net_device *dev, struct ethtool_eee *edata)
|
|||
} else if (edata->advertised & ~advertising) {
|
||||
netdev_warn(dev, "EEE advertised %x must be a subset of autoneg advertised speeds %x\n",
|
||||
edata->advertised, advertising);
|
||||
return -EINVAL;
|
||||
rc = -EINVAL;
|
||||
goto eee_exit;
|
||||
}
|
||||
|
||||
eee->advertised = edata->advertised;
|
||||
|
|
@ -2596,6 +2606,8 @@ static int bnxt_set_eee(struct net_device *dev, struct ethtool_eee *edata)
|
|||
if (netif_running(dev))
|
||||
rc = bnxt_hwrm_set_link_setting(bp, false, true);
|
||||
|
||||
eee_exit:
|
||||
mutex_unlock(&bp->link_lock);
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -647,8 +647,7 @@ static void macb_mac_link_up(struct phylink_config *config,
|
|||
ctrl |= GEM_BIT(GBE);
|
||||
}
|
||||
|
||||
/* We do not support MLO_PAUSE_RX yet */
|
||||
if (tx_pause)
|
||||
if (rx_pause)
|
||||
ctrl |= MACB_BIT(PAE);
|
||||
|
||||
macb_set_tx_clk(bp->tx_clk, speed, ndev);
|
||||
|
|
|
|||
|
|
@ -1911,13 +1911,16 @@ int cxgb4_del_filter(struct net_device *dev, int filter_id,
|
|||
static int configure_filter_tcb(struct adapter *adap, unsigned int tid,
|
||||
struct filter_entry *f)
|
||||
{
|
||||
if (f->fs.hitcnts)
|
||||
if (f->fs.hitcnts) {
|
||||
set_tcb_field(adap, f, tid, TCB_TIMESTAMP_W,
|
||||
TCB_TIMESTAMP_V(TCB_TIMESTAMP_M) |
|
||||
TCB_TIMESTAMP_V(TCB_TIMESTAMP_M),
|
||||
TCB_TIMESTAMP_V(0ULL),
|
||||
1);
|
||||
set_tcb_field(adap, f, tid, TCB_RTT_TS_RECENT_AGE_W,
|
||||
TCB_RTT_TS_RECENT_AGE_V(TCB_RTT_TS_RECENT_AGE_M),
|
||||
TCB_TIMESTAMP_V(0ULL) |
|
||||
TCB_RTT_TS_RECENT_AGE_V(0ULL),
|
||||
1);
|
||||
}
|
||||
|
||||
if (f->fs.newdmac)
|
||||
set_tcb_tflag(adap, f, tid, TF_CCTRL_ECE_S, 1,
|
||||
|
|
|
|||
|
|
@ -229,7 +229,7 @@ void cxgb4_free_mps_ref_entries(struct adapter *adap)
|
|||
{
|
||||
struct mps_entries_ref *mps_entry, *tmp;
|
||||
|
||||
if (!list_empty(&adap->mps_ref))
|
||||
if (list_empty(&adap->mps_ref))
|
||||
return;
|
||||
|
||||
spin_lock(&adap->mps_ref_lock);
|
||||
|
|
|
|||
|
|
@ -85,7 +85,7 @@ MODULE_PARM_DESC (rx_copybreak, "de2104x Breakpoint at which Rx packets are copi
|
|||
#define DSL CONFIG_DE2104X_DSL
|
||||
#endif
|
||||
|
||||
#define DE_RX_RING_SIZE 64
|
||||
#define DE_RX_RING_SIZE 128
|
||||
#define DE_TX_RING_SIZE 64
|
||||
#define DE_RING_BYTES \
|
||||
((sizeof(struct de_desc) * DE_RX_RING_SIZE) + \
|
||||
|
|
|
|||
|
|
@ -66,8 +66,8 @@ struct dpmac_cmd_get_counter {
|
|||
};
|
||||
|
||||
struct dpmac_rsp_get_counter {
|
||||
u64 pad;
|
||||
u64 counter;
|
||||
__le64 pad;
|
||||
__le64 counter;
|
||||
};
|
||||
|
||||
#endif /* _FSL_DPMAC_CMD_H */
|
||||
|
|
|
|||
|
|
@ -1053,7 +1053,6 @@ static int enetc_pf_probe(struct pci_dev *pdev,
|
|||
|
||||
err_reg_netdev:
|
||||
enetc_teardown_serdes(priv);
|
||||
enetc_mdio_remove(pf);
|
||||
enetc_free_msix(priv);
|
||||
err_alloc_msix:
|
||||
enetc_free_si_resources(priv);
|
||||
|
|
@ -1061,6 +1060,7 @@ static int enetc_pf_probe(struct pci_dev *pdev,
|
|||
si->ndev = NULL;
|
||||
free_netdev(ndev);
|
||||
err_alloc_netdev:
|
||||
enetc_mdio_remove(pf);
|
||||
enetc_of_put_phy(pf);
|
||||
err_map_pf_space:
|
||||
enetc_pci_remove(pdev);
|
||||
|
|
|
|||
|
|
@ -334,7 +334,7 @@ static void hns_dsaf_xge_srst_by_port_acpi(struct dsaf_device *dsaf_dev,
|
|||
* bit6-11 for ppe0-5
|
||||
* bit12-17 for roce0-5
|
||||
* bit18-19 for com/dfx
|
||||
* @enable: false - request reset , true - drop reset
|
||||
* @dereset: false - request reset , true - drop reset
|
||||
*/
|
||||
static void
|
||||
hns_dsaf_srst_chns(struct dsaf_device *dsaf_dev, u32 msk, bool dereset)
|
||||
|
|
@ -357,7 +357,7 @@ hns_dsaf_srst_chns(struct dsaf_device *dsaf_dev, u32 msk, bool dereset)
|
|||
* bit6-11 for ppe0-5
|
||||
* bit12-17 for roce0-5
|
||||
* bit18-19 for com/dfx
|
||||
* @enable: false - request reset , true - drop reset
|
||||
* @dereset: false - request reset , true - drop reset
|
||||
*/
|
||||
static void
|
||||
hns_dsaf_srst_chns_acpi(struct dsaf_device *dsaf_dev, u32 msk, bool dereset)
|
||||
|
|
|
|||
|
|
@ -463,8 +463,8 @@ static int __lb_clean_rings(struct hns_nic_priv *priv,
|
|||
|
||||
/**
|
||||
* nic_run_loopback_test - run loopback test
|
||||
* @nic_dev: net device
|
||||
* @loopback_type: loopback type
|
||||
* @ndev: net device
|
||||
* @loop_mode: loopback mode
|
||||
*/
|
||||
static int __lb_run_test(struct net_device *ndev,
|
||||
enum hnae_loop loop_mode)
|
||||
|
|
@ -572,7 +572,7 @@ static int __lb_down(struct net_device *ndev, enum hnae_loop loop)
|
|||
|
||||
/**
|
||||
* hns_nic_self_test - self test
|
||||
* @dev: net device
|
||||
* @ndev: net device
|
||||
* @eth_test: test cmd
|
||||
* @data: test result
|
||||
*/
|
||||
|
|
@ -633,7 +633,7 @@ static void hns_nic_self_test(struct net_device *ndev,
|
|||
|
||||
/**
|
||||
* hns_nic_get_drvinfo - get net driver info
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @drvinfo: driver info
|
||||
*/
|
||||
static void hns_nic_get_drvinfo(struct net_device *net_dev,
|
||||
|
|
@ -658,7 +658,7 @@ static void hns_nic_get_drvinfo(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_get_ringparam - get ring parameter
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @param: ethtool parameter
|
||||
*/
|
||||
static void hns_get_ringparam(struct net_device *net_dev,
|
||||
|
|
@ -683,7 +683,7 @@ static void hns_get_ringparam(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_get_pauseparam - get pause parameter
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @param: pause parameter
|
||||
*/
|
||||
static void hns_get_pauseparam(struct net_device *net_dev,
|
||||
|
|
@ -701,7 +701,7 @@ static void hns_get_pauseparam(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_set_pauseparam - set pause parameter
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @param: pause parameter
|
||||
*
|
||||
* Return 0 on success, negative on failure
|
||||
|
|
@ -725,7 +725,7 @@ static int hns_set_pauseparam(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_get_coalesce - get coalesce info.
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @ec: coalesce info.
|
||||
*
|
||||
* Return 0 on success, negative on failure.
|
||||
|
|
@ -769,7 +769,7 @@ static int hns_get_coalesce(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_set_coalesce - set coalesce info.
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @ec: coalesce info.
|
||||
*
|
||||
* Return 0 on success, negative on failure.
|
||||
|
|
@ -808,7 +808,7 @@ static int hns_set_coalesce(struct net_device *net_dev,
|
|||
|
||||
/**
|
||||
* hns_get_channels - get channel info.
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @ch: channel info.
|
||||
*/
|
||||
static void
|
||||
|
|
@ -825,7 +825,7 @@ hns_get_channels(struct net_device *net_dev, struct ethtool_channels *ch)
|
|||
|
||||
/**
|
||||
* get_ethtool_stats - get detail statistics.
|
||||
* @dev: net device
|
||||
* @netdev: net device
|
||||
* @stats: statistics info.
|
||||
* @data: statistics data.
|
||||
*/
|
||||
|
|
@ -883,8 +883,8 @@ static void hns_get_ethtool_stats(struct net_device *netdev,
|
|||
|
||||
/**
|
||||
* get_strings: Return a set of strings that describe the requested objects
|
||||
* @dev: net device
|
||||
* @stats: string set ID.
|
||||
* @netdev: net device
|
||||
* @stringset: string set ID.
|
||||
* @data: objects data.
|
||||
*/
|
||||
static void hns_get_strings(struct net_device *netdev, u32 stringset, u8 *data)
|
||||
|
|
@ -972,7 +972,7 @@ static void hns_get_strings(struct net_device *netdev, u32 stringset, u8 *data)
|
|||
|
||||
/**
|
||||
* nic_get_sset_count - get string set count witch returned by nic_get_strings.
|
||||
* @dev: net device
|
||||
* @netdev: net device
|
||||
* @stringset: string set index, 0: self test string; 1: statistics string.
|
||||
*
|
||||
* Return string set count.
|
||||
|
|
@ -1006,7 +1006,7 @@ static int hns_get_sset_count(struct net_device *netdev, int stringset)
|
|||
|
||||
/**
|
||||
* hns_phy_led_set - set phy LED status.
|
||||
* @dev: net device
|
||||
* @netdev: net device
|
||||
* @value: LED state.
|
||||
*
|
||||
* Return 0 on success, negative on failure.
|
||||
|
|
@ -1028,7 +1028,7 @@ static int hns_phy_led_set(struct net_device *netdev, int value)
|
|||
|
||||
/**
|
||||
* nic_set_phys_id - set phy identify LED.
|
||||
* @dev: net device
|
||||
* @netdev: net device
|
||||
* @state: LED state.
|
||||
*
|
||||
* Return 0 on success, negative on failure.
|
||||
|
|
@ -1104,9 +1104,9 @@ hns_set_phys_id(struct net_device *netdev, enum ethtool_phys_id_state state)
|
|||
|
||||
/**
|
||||
* hns_get_regs - get net device register
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
* @cmd: ethtool cmd
|
||||
* @date: register data
|
||||
* @data: register data
|
||||
*/
|
||||
static void hns_get_regs(struct net_device *net_dev, struct ethtool_regs *cmd,
|
||||
void *data)
|
||||
|
|
@ -1126,7 +1126,7 @@ static void hns_get_regs(struct net_device *net_dev, struct ethtool_regs *cmd,
|
|||
|
||||
/**
|
||||
* nic_get_regs_len - get total register len.
|
||||
* @dev: net device
|
||||
* @net_dev: net device
|
||||
*
|
||||
* Return total register len.
|
||||
*/
|
||||
|
|
@ -1151,7 +1151,7 @@ static int hns_get_regs_len(struct net_device *net_dev)
|
|||
|
||||
/**
|
||||
* hns_nic_nway_reset - nway reset
|
||||
* @dev: net device
|
||||
* @netdev: net device
|
||||
*
|
||||
* Return 0 on success, negative on failure
|
||||
*/
|
||||
|
|
|
|||
|
|
@ -1654,6 +1654,7 @@ static void hinic_diag_test(struct net_device *netdev,
|
|||
}
|
||||
|
||||
netif_carrier_off(netdev);
|
||||
netif_tx_disable(netdev);
|
||||
|
||||
err = do_lp_test(nic_dev, eth_test->flags, LP_DEFAULT_TIME,
|
||||
&test_index);
|
||||
|
|
@ -1662,9 +1663,12 @@ static void hinic_diag_test(struct net_device *netdev,
|
|||
data[test_index] = 1;
|
||||
}
|
||||
|
||||
netif_tx_wake_all_queues(netdev);
|
||||
|
||||
err = hinic_port_link_state(nic_dev, &link_state);
|
||||
if (!err && link_state == HINIC_LINK_STATE_UP)
|
||||
netif_carrier_on(netdev);
|
||||
|
||||
}
|
||||
|
||||
static int hinic_set_phys_id(struct net_device *netdev,
|
||||
|
|
|
|||
|
|
@ -47,8 +47,12 @@
|
|||
|
||||
#define MGMT_MSG_TIMEOUT 5000
|
||||
|
||||
#define SET_FUNC_PORT_MBOX_TIMEOUT 30000
|
||||
|
||||
#define SET_FUNC_PORT_MGMT_TIMEOUT 25000
|
||||
|
||||
#define UPDATE_FW_MGMT_TIMEOUT 20000
|
||||
|
||||
#define mgmt_to_pfhwdev(pf_mgmt) \
|
||||
container_of(pf_mgmt, struct hinic_pfhwdev, pf_to_mgmt)
|
||||
|
||||
|
|
@ -361,16 +365,22 @@ int hinic_msg_to_mgmt(struct hinic_pf_to_mgmt *pf_to_mgmt,
|
|||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (cmd == HINIC_PORT_CMD_SET_FUNC_STATE)
|
||||
timeout = SET_FUNC_PORT_MGMT_TIMEOUT;
|
||||
if (HINIC_IS_VF(hwif)) {
|
||||
if (cmd == HINIC_PORT_CMD_SET_FUNC_STATE)
|
||||
timeout = SET_FUNC_PORT_MBOX_TIMEOUT;
|
||||
|
||||
if (HINIC_IS_VF(hwif))
|
||||
return hinic_mbox_to_pf(pf_to_mgmt->hwdev, mod, cmd, buf_in,
|
||||
in_size, buf_out, out_size, 0);
|
||||
else
|
||||
in_size, buf_out, out_size, timeout);
|
||||
} else {
|
||||
if (cmd == HINIC_PORT_CMD_SET_FUNC_STATE)
|
||||
timeout = SET_FUNC_PORT_MGMT_TIMEOUT;
|
||||
else if (cmd == HINIC_PORT_CMD_UPDATE_FW)
|
||||
timeout = UPDATE_FW_MGMT_TIMEOUT;
|
||||
|
||||
return msg_to_mgmt_sync(pf_to_mgmt, mod, cmd, buf_in, in_size,
|
||||
buf_out, out_size, MGMT_DIRECT_SEND,
|
||||
MSG_NOT_RESP, timeout);
|
||||
}
|
||||
}
|
||||
|
||||
static void recv_mgmt_msg_work_handler(struct work_struct *work)
|
||||
|
|
|
|||
|
|
@ -174,6 +174,24 @@ static int create_txqs(struct hinic_dev *nic_dev)
|
|||
return err;
|
||||
}
|
||||
|
||||
static void enable_txqs_napi(struct hinic_dev *nic_dev)
|
||||
{
|
||||
int num_txqs = hinic_hwdev_num_qps(nic_dev->hwdev);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < num_txqs; i++)
|
||||
napi_enable(&nic_dev->txqs[i].napi);
|
||||
}
|
||||
|
||||
static void disable_txqs_napi(struct hinic_dev *nic_dev)
|
||||
{
|
||||
int num_txqs = hinic_hwdev_num_qps(nic_dev->hwdev);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < num_txqs; i++)
|
||||
napi_disable(&nic_dev->txqs[i].napi);
|
||||
}
|
||||
|
||||
/**
|
||||
* free_txqs - Free the Logical Tx Queues of specific NIC device
|
||||
* @nic_dev: the specific NIC device
|
||||
|
|
@ -400,6 +418,8 @@ int hinic_open(struct net_device *netdev)
|
|||
goto err_create_txqs;
|
||||
}
|
||||
|
||||
enable_txqs_napi(nic_dev);
|
||||
|
||||
err = create_rxqs(nic_dev);
|
||||
if (err) {
|
||||
netif_err(nic_dev, drv, netdev,
|
||||
|
|
@ -484,6 +504,7 @@ int hinic_open(struct net_device *netdev)
|
|||
}
|
||||
|
||||
err_create_rxqs:
|
||||
disable_txqs_napi(nic_dev);
|
||||
free_txqs(nic_dev);
|
||||
|
||||
err_create_txqs:
|
||||
|
|
@ -497,6 +518,9 @@ int hinic_close(struct net_device *netdev)
|
|||
struct hinic_dev *nic_dev = netdev_priv(netdev);
|
||||
unsigned int flags;
|
||||
|
||||
/* Disable txq napi firstly to aviod rewaking txq in free_tx_poll */
|
||||
disable_txqs_napi(nic_dev);
|
||||
|
||||
down(&nic_dev->mgmt_lock);
|
||||
|
||||
flags = nic_dev->flags;
|
||||
|
|
|
|||
|
|
@ -543,18 +543,25 @@ static int rx_request_irq(struct hinic_rxq *rxq)
|
|||
if (err) {
|
||||
netif_err(nic_dev, drv, rxq->netdev,
|
||||
"Failed to set RX interrupt coalescing attribute\n");
|
||||
rx_del_napi(rxq);
|
||||
return err;
|
||||
goto err_req_irq;
|
||||
}
|
||||
|
||||
err = request_irq(rq->irq, rx_irq, 0, rxq->irq_name, rxq);
|
||||
if (err) {
|
||||
rx_del_napi(rxq);
|
||||
return err;
|
||||
}
|
||||
if (err)
|
||||
goto err_req_irq;
|
||||
|
||||
cpumask_set_cpu(qp->q_id % num_online_cpus(), &rq->affinity_mask);
|
||||
return irq_set_affinity_hint(rq->irq, &rq->affinity_mask);
|
||||
err = irq_set_affinity_hint(rq->irq, &rq->affinity_mask);
|
||||
if (err)
|
||||
goto err_irq_affinity;
|
||||
|
||||
return 0;
|
||||
|
||||
err_irq_affinity:
|
||||
free_irq(rq->irq, rxq);
|
||||
err_req_irq:
|
||||
rx_del_napi(rxq);
|
||||
return err;
|
||||
}
|
||||
|
||||
static void rx_free_irq(struct hinic_rxq *rxq)
|
||||
|
|
|
|||
|
|
@ -717,8 +717,8 @@ static int free_tx_poll(struct napi_struct *napi, int budget)
|
|||
netdev_txq = netdev_get_tx_queue(txq->netdev, qp->q_id);
|
||||
|
||||
__netif_tx_lock(netdev_txq, smp_processor_id());
|
||||
|
||||
netif_wake_subqueue(nic_dev->netdev, qp->q_id);
|
||||
if (!netif_testing(nic_dev->netdev))
|
||||
netif_wake_subqueue(nic_dev->netdev, qp->q_id);
|
||||
|
||||
__netif_tx_unlock(netdev_txq);
|
||||
|
||||
|
|
@ -745,18 +745,6 @@ static int free_tx_poll(struct napi_struct *napi, int budget)
|
|||
return budget;
|
||||
}
|
||||
|
||||
static void tx_napi_add(struct hinic_txq *txq, int weight)
|
||||
{
|
||||
netif_napi_add(txq->netdev, &txq->napi, free_tx_poll, weight);
|
||||
napi_enable(&txq->napi);
|
||||
}
|
||||
|
||||
static void tx_napi_del(struct hinic_txq *txq)
|
||||
{
|
||||
napi_disable(&txq->napi);
|
||||
netif_napi_del(&txq->napi);
|
||||
}
|
||||
|
||||
static irqreturn_t tx_irq(int irq, void *data)
|
||||
{
|
||||
struct hinic_txq *txq = data;
|
||||
|
|
@ -790,7 +778,7 @@ static int tx_request_irq(struct hinic_txq *txq)
|
|||
|
||||
qp = container_of(sq, struct hinic_qp, sq);
|
||||
|
||||
tx_napi_add(txq, nic_dev->tx_weight);
|
||||
netif_napi_add(txq->netdev, &txq->napi, free_tx_poll, nic_dev->tx_weight);
|
||||
|
||||
hinic_hwdev_msix_set(nic_dev->hwdev, sq->msix_entry,
|
||||
TX_IRQ_NO_PENDING, TX_IRQ_NO_COALESC,
|
||||
|
|
@ -807,14 +795,14 @@ static int tx_request_irq(struct hinic_txq *txq)
|
|||
if (err) {
|
||||
netif_err(nic_dev, drv, txq->netdev,
|
||||
"Failed to set TX interrupt coalescing attribute\n");
|
||||
tx_napi_del(txq);
|
||||
netif_napi_del(&txq->napi);
|
||||
return err;
|
||||
}
|
||||
|
||||
err = request_irq(sq->irq, tx_irq, 0, txq->irq_name, txq);
|
||||
if (err) {
|
||||
dev_err(&pdev->dev, "Failed to request Tx irq\n");
|
||||
tx_napi_del(txq);
|
||||
netif_napi_del(&txq->napi);
|
||||
return err;
|
||||
}
|
||||
|
||||
|
|
@ -826,7 +814,7 @@ static void tx_free_irq(struct hinic_txq *txq)
|
|||
struct hinic_sq *sq = txq->sq;
|
||||
|
||||
free_irq(sq->irq, txq);
|
||||
tx_napi_del(txq);
|
||||
netif_napi_del(&txq->napi);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -2032,16 +2032,18 @@ static int do_reset(struct ibmvnic_adapter *adapter,
|
|||
|
||||
} else {
|
||||
rc = reset_tx_pools(adapter);
|
||||
if (rc)
|
||||
if (rc) {
|
||||
netdev_dbg(adapter->netdev, "reset tx pools failed (%d)\n",
|
||||
rc);
|
||||
goto out;
|
||||
}
|
||||
|
||||
rc = reset_rx_pools(adapter);
|
||||
if (rc)
|
||||
if (rc) {
|
||||
netdev_dbg(adapter->netdev, "reset rx pools failed (%d)\n",
|
||||
rc);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
ibmvnic_disable_irqs(adapter);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1115,7 +1115,7 @@ static int i40e_quiesce_vf_pci(struct i40e_vf *vf)
|
|||
static int i40e_getnum_vf_vsi_vlan_filters(struct i40e_vsi *vsi)
|
||||
{
|
||||
struct i40e_mac_filter *f;
|
||||
int num_vlans = 0, bkt;
|
||||
u16 num_vlans = 0, bkt;
|
||||
|
||||
hash_for_each(vsi->mac_filter_hash, bkt, f, hlist) {
|
||||
if (f->vlan >= 0 && f->vlan <= I40E_MAX_VLANID)
|
||||
|
|
@ -1134,8 +1134,8 @@ static int i40e_getnum_vf_vsi_vlan_filters(struct i40e_vsi *vsi)
|
|||
*
|
||||
* Called to get number of VLANs and VLAN list present in mac_filter_hash.
|
||||
**/
|
||||
static void i40e_get_vlan_list_sync(struct i40e_vsi *vsi, int *num_vlans,
|
||||
s16 **vlan_list)
|
||||
static void i40e_get_vlan_list_sync(struct i40e_vsi *vsi, u16 *num_vlans,
|
||||
s16 **vlan_list)
|
||||
{
|
||||
struct i40e_mac_filter *f;
|
||||
int i = 0;
|
||||
|
|
@ -1169,11 +1169,11 @@ static void i40e_get_vlan_list_sync(struct i40e_vsi *vsi, int *num_vlans,
|
|||
**/
|
||||
static i40e_status
|
||||
i40e_set_vsi_promisc(struct i40e_vf *vf, u16 seid, bool multi_enable,
|
||||
bool unicast_enable, s16 *vl, int num_vlans)
|
||||
bool unicast_enable, s16 *vl, u16 num_vlans)
|
||||
{
|
||||
i40e_status aq_ret, aq_tmp = 0;
|
||||
struct i40e_pf *pf = vf->pf;
|
||||
struct i40e_hw *hw = &pf->hw;
|
||||
i40e_status aq_ret;
|
||||
int i;
|
||||
|
||||
/* No VLAN to set promisc on, set on VSI */
|
||||
|
|
@ -1222,6 +1222,9 @@ i40e_set_vsi_promisc(struct i40e_vf *vf, u16 seid, bool multi_enable,
|
|||
vf->vf_id,
|
||||
i40e_stat_str(&pf->hw, aq_ret),
|
||||
i40e_aq_str(&pf->hw, aq_err));
|
||||
|
||||
if (!aq_tmp)
|
||||
aq_tmp = aq_ret;
|
||||
}
|
||||
|
||||
aq_ret = i40e_aq_set_vsi_uc_promisc_on_vlan(hw, seid,
|
||||
|
|
@ -1235,8 +1238,15 @@ i40e_set_vsi_promisc(struct i40e_vf *vf, u16 seid, bool multi_enable,
|
|||
vf->vf_id,
|
||||
i40e_stat_str(&pf->hw, aq_ret),
|
||||
i40e_aq_str(&pf->hw, aq_err));
|
||||
|
||||
if (!aq_tmp)
|
||||
aq_tmp = aq_ret;
|
||||
}
|
||||
}
|
||||
|
||||
if (aq_tmp)
|
||||
aq_ret = aq_tmp;
|
||||
|
||||
return aq_ret;
|
||||
}
|
||||
|
||||
|
|
@ -1258,7 +1268,7 @@ static i40e_status i40e_config_vf_promiscuous_mode(struct i40e_vf *vf,
|
|||
i40e_status aq_ret = I40E_SUCCESS;
|
||||
struct i40e_pf *pf = vf->pf;
|
||||
struct i40e_vsi *vsi;
|
||||
int num_vlans;
|
||||
u16 num_vlans;
|
||||
s16 *vl;
|
||||
|
||||
vsi = i40e_find_vsi_from_id(pf, vsi_id);
|
||||
|
|
|
|||
|
|
@ -299,18 +299,14 @@ extern char igc_driver_name[];
|
|||
#define IGC_RX_HDR_LEN IGC_RXBUFFER_256
|
||||
|
||||
/* Transmit and receive latency (for PTP timestamps) */
|
||||
/* FIXME: These values were estimated using the ones that i225 has as
|
||||
* basis, they seem to provide good numbers with ptp4l/phc2sys, but we
|
||||
* need to confirm them.
|
||||
*/
|
||||
#define IGC_I225_TX_LATENCY_10 9542
|
||||
#define IGC_I225_TX_LATENCY_100 1024
|
||||
#define IGC_I225_TX_LATENCY_1000 178
|
||||
#define IGC_I225_TX_LATENCY_2500 64
|
||||
#define IGC_I225_RX_LATENCY_10 20662
|
||||
#define IGC_I225_RX_LATENCY_100 2213
|
||||
#define IGC_I225_RX_LATENCY_1000 448
|
||||
#define IGC_I225_RX_LATENCY_2500 160
|
||||
#define IGC_I225_TX_LATENCY_10 240
|
||||
#define IGC_I225_TX_LATENCY_100 58
|
||||
#define IGC_I225_TX_LATENCY_1000 80
|
||||
#define IGC_I225_TX_LATENCY_2500 1325
|
||||
#define IGC_I225_RX_LATENCY_10 6450
|
||||
#define IGC_I225_RX_LATENCY_100 185
|
||||
#define IGC_I225_RX_LATENCY_1000 300
|
||||
#define IGC_I225_RX_LATENCY_2500 1485
|
||||
|
||||
/* RX and TX descriptor control thresholds.
|
||||
* PTHRESH - MAC will consider prefetch if it has fewer than this number of
|
||||
|
|
|
|||
|
|
@ -364,6 +364,7 @@ static void igc_ptp_tx_hwtstamp(struct igc_adapter *adapter)
|
|||
struct sk_buff *skb = adapter->ptp_tx_skb;
|
||||
struct skb_shared_hwtstamps shhwtstamps;
|
||||
struct igc_hw *hw = &adapter->hw;
|
||||
int adjust = 0;
|
||||
u64 regval;
|
||||
|
||||
if (WARN_ON_ONCE(!skb))
|
||||
|
|
@ -373,6 +374,24 @@ static void igc_ptp_tx_hwtstamp(struct igc_adapter *adapter)
|
|||
regval |= (u64)rd32(IGC_TXSTMPH) << 32;
|
||||
igc_ptp_systim_to_hwtstamp(adapter, &shhwtstamps, regval);
|
||||
|
||||
switch (adapter->link_speed) {
|
||||
case SPEED_10:
|
||||
adjust = IGC_I225_TX_LATENCY_10;
|
||||
break;
|
||||
case SPEED_100:
|
||||
adjust = IGC_I225_TX_LATENCY_100;
|
||||
break;
|
||||
case SPEED_1000:
|
||||
adjust = IGC_I225_TX_LATENCY_1000;
|
||||
break;
|
||||
case SPEED_2500:
|
||||
adjust = IGC_I225_TX_LATENCY_2500;
|
||||
break;
|
||||
}
|
||||
|
||||
shhwtstamps.hwtstamp =
|
||||
ktime_add_ns(shhwtstamps.hwtstamp, adjust);
|
||||
|
||||
/* Clear the lock early before calling skb_tstamp_tx so that
|
||||
* applications are not woken up before the lock bit is clear. We use
|
||||
* a copy of the skb pointer to ensure other threads can't change it
|
||||
|
|
|
|||
|
|
@ -230,8 +230,8 @@ static int xrx200_poll_rx(struct napi_struct *napi, int budget)
|
|||
}
|
||||
|
||||
if (rx < budget) {
|
||||
napi_complete(&ch->napi);
|
||||
ltq_dma_enable_irq(&ch->dma);
|
||||
if (napi_complete_done(&ch->napi, rx))
|
||||
ltq_dma_enable_irq(&ch->dma);
|
||||
}
|
||||
|
||||
return rx;
|
||||
|
|
@ -268,9 +268,12 @@ static int xrx200_tx_housekeeping(struct napi_struct *napi, int budget)
|
|||
net_dev->stats.tx_bytes += bytes;
|
||||
netdev_completed_queue(ch->priv->net_dev, pkts, bytes);
|
||||
|
||||
if (netif_queue_stopped(net_dev))
|
||||
netif_wake_queue(net_dev);
|
||||
|
||||
if (pkts < budget) {
|
||||
napi_complete(&ch->napi);
|
||||
ltq_dma_enable_irq(&ch->dma);
|
||||
if (napi_complete_done(&ch->napi, pkts))
|
||||
ltq_dma_enable_irq(&ch->dma);
|
||||
}
|
||||
|
||||
return pkts;
|
||||
|
|
@ -342,10 +345,12 @@ static irqreturn_t xrx200_dma_irq(int irq, void *ptr)
|
|||
{
|
||||
struct xrx200_chan *ch = ptr;
|
||||
|
||||
ltq_dma_disable_irq(&ch->dma);
|
||||
ltq_dma_ack_irq(&ch->dma);
|
||||
if (napi_schedule_prep(&ch->napi)) {
|
||||
__napi_schedule(&ch->napi);
|
||||
ltq_dma_disable_irq(&ch->dma);
|
||||
}
|
||||
|
||||
napi_schedule(&ch->napi);
|
||||
ltq_dma_ack_irq(&ch->dma);
|
||||
|
||||
return IRQ_HANDLED;
|
||||
}
|
||||
|
|
@ -499,7 +504,7 @@ static int xrx200_probe(struct platform_device *pdev)
|
|||
|
||||
/* setup NAPI */
|
||||
netif_napi_add(net_dev, &priv->chan_rx.napi, xrx200_poll_rx, 32);
|
||||
netif_napi_add(net_dev, &priv->chan_tx.napi, xrx200_tx_housekeeping, 32);
|
||||
netif_tx_napi_add(net_dev, &priv->chan_tx.napi, xrx200_tx_housekeeping, 32);
|
||||
|
||||
platform_set_drvdata(pdev, priv);
|
||||
|
||||
|
|
|
|||
|
|
@ -2029,11 +2029,11 @@ mvneta_xdp_put_buff(struct mvneta_port *pp, struct mvneta_rx_queue *rxq,
|
|||
struct skb_shared_info *sinfo = xdp_get_shared_info_from_buff(xdp);
|
||||
int i;
|
||||
|
||||
page_pool_put_page(rxq->page_pool, virt_to_head_page(xdp->data),
|
||||
sync_len, napi);
|
||||
for (i = 0; i < sinfo->nr_frags; i++)
|
||||
page_pool_put_full_page(rxq->page_pool,
|
||||
skb_frag_page(&sinfo->frags[i]), napi);
|
||||
page_pool_put_page(rxq->page_pool, virt_to_head_page(xdp->data),
|
||||
sync_len, napi);
|
||||
}
|
||||
|
||||
static int
|
||||
|
|
@ -2383,8 +2383,12 @@ static int mvneta_rx_swbm(struct napi_struct *napi,
|
|||
mvneta_swbm_rx_frame(pp, rx_desc, rxq, &xdp_buf,
|
||||
&size, page, &ps);
|
||||
} else {
|
||||
if (unlikely(!xdp_buf.data_hard_start))
|
||||
if (unlikely(!xdp_buf.data_hard_start)) {
|
||||
rx_desc->buf_phys_addr = 0;
|
||||
page_pool_put_full_page(rxq->page_pool, page,
|
||||
true);
|
||||
continue;
|
||||
}
|
||||
|
||||
mvneta_swbm_add_rx_fragment(pp, rx_desc, rxq, &xdp_buf,
|
||||
&size, page);
|
||||
|
|
|
|||
|
|
@ -600,7 +600,7 @@ struct mlx5e_rq {
|
|||
struct dim dim; /* Dynamic Interrupt Moderation */
|
||||
|
||||
/* XDP */
|
||||
struct bpf_prog *xdp_prog;
|
||||
struct bpf_prog __rcu *xdp_prog;
|
||||
struct mlx5e_xdpsq *xdpsq;
|
||||
DECLARE_BITMAP(flags, 8);
|
||||
struct page_pool *page_pool;
|
||||
|
|
@ -1005,7 +1005,6 @@ int mlx5e_update_nic_rx(struct mlx5e_priv *priv);
|
|||
void mlx5e_update_carrier(struct mlx5e_priv *priv);
|
||||
int mlx5e_close(struct net_device *netdev);
|
||||
int mlx5e_open(struct net_device *netdev);
|
||||
void mlx5e_update_ndo_stats(struct mlx5e_priv *priv);
|
||||
|
||||
void mlx5e_queue_update_stats(struct mlx5e_priv *priv);
|
||||
int mlx5e_bits_invert(unsigned long a, int size);
|
||||
|
|
|
|||
|
|
@ -51,7 +51,7 @@ static void mlx5e_monitor_counters_work(struct work_struct *work)
|
|||
monitor_counters_work);
|
||||
|
||||
mutex_lock(&priv->state_lock);
|
||||
mlx5e_update_ndo_stats(priv);
|
||||
mlx5e_stats_update_ndo_stats(priv);
|
||||
mutex_unlock(&priv->state_lock);
|
||||
mlx5e_monitor_counter_arm(priv);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -490,11 +490,8 @@ bool mlx5e_fec_in_caps(struct mlx5_core_dev *dev, int fec_policy)
|
|||
int err;
|
||||
int i;
|
||||
|
||||
if (!MLX5_CAP_GEN(dev, pcam_reg))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
if (!MLX5_CAP_PCAM_REG(dev, pplm))
|
||||
return -EOPNOTSUPP;
|
||||
if (!MLX5_CAP_GEN(dev, pcam_reg) || !MLX5_CAP_PCAM_REG(dev, pplm))
|
||||
return false;
|
||||
|
||||
MLX5_SET(pplm_reg, in, local_port, 1);
|
||||
err = mlx5_core_access_reg(dev, in, sz, out, sz, MLX5_REG_PPLM, 0, 0);
|
||||
|
|
|
|||
|
|
@ -699,6 +699,7 @@ mlx5_tc_ct_entry_add_rule(struct mlx5_tc_ct_priv *ct_priv,
|
|||
err_rule:
|
||||
mlx5e_mod_hdr_detach(ct_priv->esw->dev,
|
||||
&esw->offloads.mod_hdr, zone_rule->mh);
|
||||
mapping_remove(ct_priv->labels_mapping, attr->ct_attr.ct_labels_id);
|
||||
err_mod_hdr:
|
||||
kfree(spec);
|
||||
return err;
|
||||
|
|
@ -958,12 +959,22 @@ mlx5_tc_ct_add_no_trk_match(struct mlx5e_priv *priv,
|
|||
return 0;
|
||||
}
|
||||
|
||||
void mlx5_tc_ct_match_del(struct mlx5e_priv *priv, struct mlx5_ct_attr *ct_attr)
|
||||
{
|
||||
struct mlx5_tc_ct_priv *ct_priv = mlx5_tc_ct_get_ct_priv(priv);
|
||||
|
||||
if (!ct_priv || !ct_attr->ct_labels_id)
|
||||
return;
|
||||
|
||||
mapping_remove(ct_priv->labels_mapping, ct_attr->ct_labels_id);
|
||||
}
|
||||
|
||||
int
|
||||
mlx5_tc_ct_parse_match(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack)
|
||||
mlx5_tc_ct_match_add(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct mlx5_tc_ct_priv *ct_priv = mlx5_tc_ct_get_ct_priv(priv);
|
||||
struct flow_rule *rule = flow_cls_offload_flow_rule(f);
|
||||
|
|
|
|||
|
|
@ -87,12 +87,15 @@ mlx5_tc_ct_init(struct mlx5_rep_uplink_priv *uplink_priv);
|
|||
void
|
||||
mlx5_tc_ct_clean(struct mlx5_rep_uplink_priv *uplink_priv);
|
||||
|
||||
void
|
||||
mlx5_tc_ct_match_del(struct mlx5e_priv *priv, struct mlx5_ct_attr *ct_attr);
|
||||
|
||||
int
|
||||
mlx5_tc_ct_parse_match(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack);
|
||||
mlx5_tc_ct_match_add(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack);
|
||||
int
|
||||
mlx5_tc_ct_add_no_trk_match(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec);
|
||||
|
|
@ -130,12 +133,15 @@ mlx5_tc_ct_clean(struct mlx5_rep_uplink_priv *uplink_priv)
|
|||
{
|
||||
}
|
||||
|
||||
static inline void
|
||||
mlx5_tc_ct_match_del(struct mlx5e_priv *priv, struct mlx5_ct_attr *ct_attr) {}
|
||||
|
||||
static inline int
|
||||
mlx5_tc_ct_parse_match(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack)
|
||||
mlx5_tc_ct_match_add(struct mlx5e_priv *priv,
|
||||
struct mlx5_flow_spec *spec,
|
||||
struct flow_cls_offload *f,
|
||||
struct mlx5_ct_attr *ct_attr,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct flow_rule *rule = flow_cls_offload_flow_rule(f);
|
||||
|
||||
|
|
|
|||
|
|
@ -20,6 +20,11 @@ enum mlx5e_icosq_wqe_type {
|
|||
};
|
||||
|
||||
/* General */
|
||||
static inline bool mlx5e_skb_is_multicast(struct sk_buff *skb)
|
||||
{
|
||||
return skb->pkt_type == PACKET_MULTICAST || skb->pkt_type == PACKET_BROADCAST;
|
||||
}
|
||||
|
||||
void mlx5e_trigger_irq(struct mlx5e_icosq *sq);
|
||||
void mlx5e_completion_event(struct mlx5_core_cq *mcq, struct mlx5_eqe *eqe);
|
||||
void mlx5e_cq_error_event(struct mlx5_core_cq *mcq, enum mlx5_event event);
|
||||
|
|
|
|||
|
|
@ -122,7 +122,7 @@ mlx5e_xmit_xdp_buff(struct mlx5e_xdpsq *sq, struct mlx5e_rq *rq,
|
|||
bool mlx5e_xdp_handle(struct mlx5e_rq *rq, struct mlx5e_dma_info *di,
|
||||
u32 *len, struct xdp_buff *xdp)
|
||||
{
|
||||
struct bpf_prog *prog = READ_ONCE(rq->xdp_prog);
|
||||
struct bpf_prog *prog = rcu_dereference(rq->xdp_prog);
|
||||
u32 act;
|
||||
int err;
|
||||
|
||||
|
|
|
|||
|
|
@ -31,7 +31,6 @@ struct sk_buff *mlx5e_xsk_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq,
|
|||
{
|
||||
struct xdp_buff *xdp = wi->umr.dma_info[page_idx].xsk;
|
||||
u32 cqe_bcnt32 = cqe_bcnt;
|
||||
bool consumed;
|
||||
|
||||
/* Check packet size. Note LRO doesn't use linear SKB */
|
||||
if (unlikely(cqe_bcnt > rq->hw_mtu)) {
|
||||
|
|
@ -51,10 +50,6 @@ struct sk_buff *mlx5e_xsk_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq,
|
|||
xsk_buff_dma_sync_for_cpu(xdp);
|
||||
prefetch(xdp->data);
|
||||
|
||||
rcu_read_lock();
|
||||
consumed = mlx5e_xdp_handle(rq, NULL, &cqe_bcnt32, xdp);
|
||||
rcu_read_unlock();
|
||||
|
||||
/* Possible flows:
|
||||
* - XDP_REDIRECT to XSKMAP:
|
||||
* The page is owned by the userspace from now.
|
||||
|
|
@ -70,7 +65,7 @@ struct sk_buff *mlx5e_xsk_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq,
|
|||
* allocated first from the Reuse Ring, so it has enough space.
|
||||
*/
|
||||
|
||||
if (likely(consumed)) {
|
||||
if (likely(mlx5e_xdp_handle(rq, NULL, &cqe_bcnt32, xdp))) {
|
||||
if (likely(__test_and_clear_bit(MLX5E_RQ_FLAG_XDP_XMIT, rq->flags)))
|
||||
__set_bit(page_idx, wi->xdp_xmit_bitmap); /* non-atomic */
|
||||
return NULL; /* page/packet was consumed by XDP */
|
||||
|
|
@ -88,7 +83,6 @@ struct sk_buff *mlx5e_xsk_skb_from_cqe_linear(struct mlx5e_rq *rq,
|
|||
u32 cqe_bcnt)
|
||||
{
|
||||
struct xdp_buff *xdp = wi->di->xsk;
|
||||
bool consumed;
|
||||
|
||||
/* wi->offset is not used in this function, because xdp->data and the
|
||||
* DMA address point directly to the necessary place. Furthermore, the
|
||||
|
|
@ -107,11 +101,7 @@ struct sk_buff *mlx5e_xsk_skb_from_cqe_linear(struct mlx5e_rq *rq,
|
|||
return NULL;
|
||||
}
|
||||
|
||||
rcu_read_lock();
|
||||
consumed = mlx5e_xdp_handle(rq, NULL, &cqe_bcnt, xdp);
|
||||
rcu_read_unlock();
|
||||
|
||||
if (likely(consumed))
|
||||
if (likely(mlx5e_xdp_handle(rq, NULL, &cqe_bcnt, xdp)))
|
||||
return NULL; /* page/packet was consumed by XDP */
|
||||
|
||||
/* XDP_PASS: copy the data from the UMEM to a new SKB. The frame reuse
|
||||
|
|
|
|||
|
|
@ -106,8 +106,7 @@ int mlx5e_open_xsk(struct mlx5e_priv *priv, struct mlx5e_params *params,
|
|||
void mlx5e_close_xsk(struct mlx5e_channel *c)
|
||||
{
|
||||
clear_bit(MLX5E_CHANNEL_STATE_XSK, c->state);
|
||||
napi_synchronize(&c->napi);
|
||||
synchronize_rcu(); /* Sync with the XSK wakeup. */
|
||||
synchronize_rcu(); /* Sync with the XSK wakeup and with NAPI. */
|
||||
|
||||
mlx5e_close_rq(&c->xskrq);
|
||||
mlx5e_close_cq(&c->xskrq.cq);
|
||||
|
|
|
|||
|
|
@ -234,7 +234,7 @@ mlx5e_get_ktls_rx_priv_ctx(struct tls_context *tls_ctx)
|
|||
|
||||
/* Re-sync */
|
||||
/* Runs in work context */
|
||||
static struct mlx5_wqe_ctrl_seg *
|
||||
static int
|
||||
resync_post_get_progress_params(struct mlx5e_icosq *sq,
|
||||
struct mlx5e_ktls_offload_context_rx *priv_rx)
|
||||
{
|
||||
|
|
@ -258,15 +258,19 @@ resync_post_get_progress_params(struct mlx5e_icosq *sq,
|
|||
PROGRESS_PARAMS_PADDED_SIZE, DMA_FROM_DEVICE);
|
||||
if (unlikely(dma_mapping_error(pdev, buf->dma_addr))) {
|
||||
err = -ENOMEM;
|
||||
goto err_out;
|
||||
goto err_free;
|
||||
}
|
||||
|
||||
buf->priv_rx = priv_rx;
|
||||
|
||||
BUILD_BUG_ON(MLX5E_KTLS_GET_PROGRESS_WQEBBS != 1);
|
||||
|
||||
spin_lock(&sq->channel->async_icosq_lock);
|
||||
|
||||
if (unlikely(!mlx5e_wqc_has_room_for(&sq->wq, sq->cc, sq->pc, 1))) {
|
||||
spin_unlock(&sq->channel->async_icosq_lock);
|
||||
err = -ENOSPC;
|
||||
goto err_out;
|
||||
goto err_dma_unmap;
|
||||
}
|
||||
|
||||
pi = mlx5e_icosq_get_next_pi(sq, 1);
|
||||
|
|
@ -294,12 +298,18 @@ resync_post_get_progress_params(struct mlx5e_icosq *sq,
|
|||
};
|
||||
icosq_fill_wi(sq, pi, &wi);
|
||||
sq->pc++;
|
||||
mlx5e_notify_hw(&sq->wq, sq->pc, sq->uar_map, cseg);
|
||||
spin_unlock(&sq->channel->async_icosq_lock);
|
||||
|
||||
return cseg;
|
||||
return 0;
|
||||
|
||||
err_dma_unmap:
|
||||
dma_unmap_single(pdev, buf->dma_addr, PROGRESS_PARAMS_PADDED_SIZE, DMA_FROM_DEVICE);
|
||||
err_free:
|
||||
kfree(buf);
|
||||
err_out:
|
||||
priv_rx->stats->tls_resync_req_skip++;
|
||||
return ERR_PTR(err);
|
||||
return err;
|
||||
}
|
||||
|
||||
/* Function is called with elevated refcount.
|
||||
|
|
@ -309,10 +319,8 @@ static void resync_handle_work(struct work_struct *work)
|
|||
{
|
||||
struct mlx5e_ktls_offload_context_rx *priv_rx;
|
||||
struct mlx5e_ktls_rx_resync_ctx *resync;
|
||||
struct mlx5_wqe_ctrl_seg *cseg;
|
||||
struct mlx5e_channel *c;
|
||||
struct mlx5e_icosq *sq;
|
||||
struct mlx5_wq_cyc *wq;
|
||||
|
||||
resync = container_of(work, struct mlx5e_ktls_rx_resync_ctx, work);
|
||||
priv_rx = container_of(resync, struct mlx5e_ktls_offload_context_rx, resync);
|
||||
|
|
@ -324,18 +332,9 @@ static void resync_handle_work(struct work_struct *work)
|
|||
|
||||
c = resync->priv->channels.c[priv_rx->rxq];
|
||||
sq = &c->async_icosq;
|
||||
wq = &sq->wq;
|
||||
|
||||
spin_lock(&c->async_icosq_lock);
|
||||
|
||||
cseg = resync_post_get_progress_params(sq, priv_rx);
|
||||
if (IS_ERR(cseg)) {
|
||||
if (resync_post_get_progress_params(sq, priv_rx))
|
||||
refcount_dec(&resync->refcnt);
|
||||
goto unlock;
|
||||
}
|
||||
mlx5e_notify_hw(wq, sq->pc, sq->uar_map, cseg);
|
||||
unlock:
|
||||
spin_unlock(&c->async_icosq_lock);
|
||||
}
|
||||
|
||||
static void resync_init(struct mlx5e_ktls_rx_resync_ctx *resync,
|
||||
|
|
@ -386,16 +385,17 @@ void mlx5e_ktls_handle_get_psv_completion(struct mlx5e_icosq_wqe_info *wi,
|
|||
struct mlx5e_ktls_offload_context_rx *priv_rx;
|
||||
struct mlx5e_ktls_rx_resync_ctx *resync;
|
||||
u8 tracker_state, auth_state, *ctx;
|
||||
struct device *dev;
|
||||
u32 hw_seq;
|
||||
|
||||
priv_rx = buf->priv_rx;
|
||||
resync = &priv_rx->resync;
|
||||
|
||||
dev = resync->priv->mdev->device;
|
||||
if (unlikely(test_bit(MLX5E_PRIV_RX_FLAG_DELETING, priv_rx->flags)))
|
||||
goto out;
|
||||
|
||||
dma_sync_single_for_cpu(resync->priv->mdev->device, buf->dma_addr,
|
||||
PROGRESS_PARAMS_PADDED_SIZE, DMA_FROM_DEVICE);
|
||||
dma_sync_single_for_cpu(dev, buf->dma_addr, PROGRESS_PARAMS_PADDED_SIZE,
|
||||
DMA_FROM_DEVICE);
|
||||
|
||||
ctx = buf->progress.ctx;
|
||||
tracker_state = MLX5_GET(tls_progress_params, ctx, record_tracker_state);
|
||||
|
|
@ -411,6 +411,7 @@ void mlx5e_ktls_handle_get_psv_completion(struct mlx5e_icosq_wqe_info *wi,
|
|||
priv_rx->stats->tls_resync_req_end++;
|
||||
out:
|
||||
refcount_dec(&resync->refcnt);
|
||||
dma_unmap_single(dev, buf->dma_addr, PROGRESS_PARAMS_PADDED_SIZE, DMA_FROM_DEVICE);
|
||||
kfree(buf);
|
||||
}
|
||||
|
||||
|
|
@ -659,7 +660,7 @@ void mlx5e_ktls_del_rx(struct net_device *netdev, struct tls_context *tls_ctx)
|
|||
priv_rx = mlx5e_get_ktls_rx_priv_ctx(tls_ctx);
|
||||
set_bit(MLX5E_PRIV_RX_FLAG_DELETING, priv_rx->flags);
|
||||
mlx5e_set_ktls_rx_priv_ctx(tls_ctx, NULL);
|
||||
napi_synchronize(&priv->channels.c[priv_rx->rxq]->napi);
|
||||
synchronize_rcu(); /* Sync with NAPI */
|
||||
if (!cancel_work_sync(&priv_rx->rule.work))
|
||||
/* completion is needed, as the priv_rx in the add flow
|
||||
* is maintained on the wqe info (wi), not on the socket.
|
||||
|
|
|
|||
|
|
@ -35,7 +35,6 @@
|
|||
#include <net/sock.h>
|
||||
|
||||
#include "en.h"
|
||||
#include "accel/tls.h"
|
||||
#include "fpga/sdk.h"
|
||||
#include "en_accel/tls.h"
|
||||
|
||||
|
|
@ -51,9 +50,14 @@ static const struct counter_desc mlx5e_tls_sw_stats_desc[] = {
|
|||
|
||||
#define NUM_TLS_SW_COUNTERS ARRAY_SIZE(mlx5e_tls_sw_stats_desc)
|
||||
|
||||
static bool is_tls_atomic_stats(struct mlx5e_priv *priv)
|
||||
{
|
||||
return priv->tls && !mlx5_accel_is_ktls_device(priv->mdev);
|
||||
}
|
||||
|
||||
int mlx5e_tls_get_count(struct mlx5e_priv *priv)
|
||||
{
|
||||
if (!priv->tls)
|
||||
if (!is_tls_atomic_stats(priv))
|
||||
return 0;
|
||||
|
||||
return NUM_TLS_SW_COUNTERS;
|
||||
|
|
@ -63,7 +67,7 @@ int mlx5e_tls_get_strings(struct mlx5e_priv *priv, uint8_t *data)
|
|||
{
|
||||
unsigned int i, idx = 0;
|
||||
|
||||
if (!priv->tls)
|
||||
if (!is_tls_atomic_stats(priv))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < NUM_TLS_SW_COUNTERS; i++)
|
||||
|
|
@ -77,7 +81,7 @@ int mlx5e_tls_get_stats(struct mlx5e_priv *priv, u64 *data)
|
|||
{
|
||||
int i, idx = 0;
|
||||
|
||||
if (!priv->tls)
|
||||
if (!is_tls_atomic_stats(priv))
|
||||
return 0;
|
||||
|
||||
for (i = 0; i < NUM_TLS_SW_COUNTERS; i++)
|
||||
|
|
|
|||
|
|
@ -158,16 +158,6 @@ static void mlx5e_update_carrier_work(struct work_struct *work)
|
|||
mutex_unlock(&priv->state_lock);
|
||||
}
|
||||
|
||||
void mlx5e_update_ndo_stats(struct mlx5e_priv *priv)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = mlx5e_nic_stats_grps_num(priv) - 1; i >= 0; i--)
|
||||
if (mlx5e_nic_stats_grps[i]->update_stats_mask &
|
||||
MLX5E_NDO_UPDATE_STATS)
|
||||
mlx5e_nic_stats_grps[i]->update_stats(priv);
|
||||
}
|
||||
|
||||
static void mlx5e_update_stats_work(struct work_struct *work)
|
||||
{
|
||||
struct mlx5e_priv *priv = container_of(work, struct mlx5e_priv,
|
||||
|
|
@ -399,7 +389,7 @@ static int mlx5e_alloc_rq(struct mlx5e_channel *c,
|
|||
|
||||
if (params->xdp_prog)
|
||||
bpf_prog_inc(params->xdp_prog);
|
||||
rq->xdp_prog = params->xdp_prog;
|
||||
RCU_INIT_POINTER(rq->xdp_prog, params->xdp_prog);
|
||||
|
||||
rq_xdp_ix = rq->ix;
|
||||
if (xsk)
|
||||
|
|
@ -408,7 +398,7 @@ static int mlx5e_alloc_rq(struct mlx5e_channel *c,
|
|||
if (err < 0)
|
||||
goto err_rq_wq_destroy;
|
||||
|
||||
rq->buff.map_dir = rq->xdp_prog ? DMA_BIDIRECTIONAL : DMA_FROM_DEVICE;
|
||||
rq->buff.map_dir = params->xdp_prog ? DMA_BIDIRECTIONAL : DMA_FROM_DEVICE;
|
||||
rq->buff.headroom = mlx5e_get_rq_headroom(mdev, params, xsk);
|
||||
pool_size = 1 << params->log_rq_mtu_frames;
|
||||
|
||||
|
|
@ -564,8 +554,8 @@ static int mlx5e_alloc_rq(struct mlx5e_channel *c,
|
|||
}
|
||||
|
||||
err_rq_wq_destroy:
|
||||
if (rq->xdp_prog)
|
||||
bpf_prog_put(rq->xdp_prog);
|
||||
if (params->xdp_prog)
|
||||
bpf_prog_put(params->xdp_prog);
|
||||
xdp_rxq_info_unreg(&rq->xdp_rxq);
|
||||
page_pool_destroy(rq->page_pool);
|
||||
mlx5_wq_destroy(&rq->wq_ctrl);
|
||||
|
|
@ -575,10 +565,16 @@ static int mlx5e_alloc_rq(struct mlx5e_channel *c,
|
|||
|
||||
static void mlx5e_free_rq(struct mlx5e_rq *rq)
|
||||
{
|
||||
struct mlx5e_channel *c = rq->channel;
|
||||
struct bpf_prog *old_prog = NULL;
|
||||
int i;
|
||||
|
||||
if (rq->xdp_prog)
|
||||
bpf_prog_put(rq->xdp_prog);
|
||||
/* drop_rq has neither channel nor xdp_prog. */
|
||||
if (c)
|
||||
old_prog = rcu_dereference_protected(rq->xdp_prog,
|
||||
lockdep_is_held(&c->priv->state_lock));
|
||||
if (old_prog)
|
||||
bpf_prog_put(old_prog);
|
||||
|
||||
switch (rq->wq_type) {
|
||||
case MLX5_WQ_TYPE_LINKED_LIST_STRIDING_RQ:
|
||||
|
|
@ -867,7 +863,7 @@ void mlx5e_activate_rq(struct mlx5e_rq *rq)
|
|||
void mlx5e_deactivate_rq(struct mlx5e_rq *rq)
|
||||
{
|
||||
clear_bit(MLX5E_RQ_STATE_ENABLED, &rq->state);
|
||||
napi_synchronize(&rq->channel->napi); /* prevent mlx5e_post_rx_wqes */
|
||||
synchronize_rcu(); /* Sync with NAPI to prevent mlx5e_post_rx_wqes. */
|
||||
}
|
||||
|
||||
void mlx5e_close_rq(struct mlx5e_rq *rq)
|
||||
|
|
@ -1312,12 +1308,10 @@ void mlx5e_tx_disable_queue(struct netdev_queue *txq)
|
|||
|
||||
static void mlx5e_deactivate_txqsq(struct mlx5e_txqsq *sq)
|
||||
{
|
||||
struct mlx5e_channel *c = sq->channel;
|
||||
struct mlx5_wq_cyc *wq = &sq->wq;
|
||||
|
||||
clear_bit(MLX5E_SQ_STATE_ENABLED, &sq->state);
|
||||
/* prevent netif_tx_wake_queue */
|
||||
napi_synchronize(&c->napi);
|
||||
synchronize_rcu(); /* Sync with NAPI to prevent netif_tx_wake_queue. */
|
||||
|
||||
mlx5e_tx_disable_queue(sq->txq);
|
||||
|
||||
|
|
@ -1392,10 +1386,8 @@ void mlx5e_activate_icosq(struct mlx5e_icosq *icosq)
|
|||
|
||||
void mlx5e_deactivate_icosq(struct mlx5e_icosq *icosq)
|
||||
{
|
||||
struct mlx5e_channel *c = icosq->channel;
|
||||
|
||||
clear_bit(MLX5E_SQ_STATE_ENABLED, &icosq->state);
|
||||
napi_synchronize(&c->napi);
|
||||
synchronize_rcu(); /* Sync with NAPI. */
|
||||
}
|
||||
|
||||
void mlx5e_close_icosq(struct mlx5e_icosq *sq)
|
||||
|
|
@ -1474,7 +1466,7 @@ void mlx5e_close_xdpsq(struct mlx5e_xdpsq *sq)
|
|||
struct mlx5e_channel *c = sq->channel;
|
||||
|
||||
clear_bit(MLX5E_SQ_STATE_ENABLED, &sq->state);
|
||||
napi_synchronize(&c->napi);
|
||||
synchronize_rcu(); /* Sync with NAPI. */
|
||||
|
||||
mlx5e_destroy_sq(c->mdev, sq->sqn);
|
||||
mlx5e_free_xdpsq_descs(sq);
|
||||
|
|
@ -3567,6 +3559,7 @@ void mlx5e_fold_sw_stats64(struct mlx5e_priv *priv, struct rtnl_link_stats64 *s)
|
|||
|
||||
s->rx_packets += rq_stats->packets + xskrq_stats->packets;
|
||||
s->rx_bytes += rq_stats->bytes + xskrq_stats->bytes;
|
||||
s->multicast += rq_stats->mcast_packets + xskrq_stats->mcast_packets;
|
||||
|
||||
for (j = 0; j < priv->max_opened_tc; j++) {
|
||||
struct mlx5e_sq_stats *sq_stats = &channel_stats->sq[j];
|
||||
|
|
@ -3582,7 +3575,6 @@ void
|
|||
mlx5e_get_stats(struct net_device *dev, struct rtnl_link_stats64 *stats)
|
||||
{
|
||||
struct mlx5e_priv *priv = netdev_priv(dev);
|
||||
struct mlx5e_vport_stats *vstats = &priv->stats.vport;
|
||||
struct mlx5e_pport_stats *pstats = &priv->stats.pport;
|
||||
|
||||
/* In switchdev mode, monitor counters doesn't monitor
|
||||
|
|
@ -3617,12 +3609,6 @@ mlx5e_get_stats(struct net_device *dev, struct rtnl_link_stats64 *stats)
|
|||
stats->rx_errors = stats->rx_length_errors + stats->rx_crc_errors +
|
||||
stats->rx_frame_errors;
|
||||
stats->tx_errors = stats->tx_aborted_errors + stats->tx_carrier_errors;
|
||||
|
||||
/* vport multicast also counts packets that are dropped due to steering
|
||||
* or rx out of buffer
|
||||
*/
|
||||
stats->multicast =
|
||||
VPORT_COUNTER_GET(vstats, received_eth_multicast.packets);
|
||||
}
|
||||
|
||||
static void mlx5e_set_rx_mode(struct net_device *dev)
|
||||
|
|
@ -4330,6 +4316,16 @@ static int mlx5e_xdp_allowed(struct mlx5e_priv *priv, struct bpf_prog *prog)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void mlx5e_rq_replace_xdp_prog(struct mlx5e_rq *rq, struct bpf_prog *prog)
|
||||
{
|
||||
struct bpf_prog *old_prog;
|
||||
|
||||
old_prog = rcu_replace_pointer(rq->xdp_prog, prog,
|
||||
lockdep_is_held(&rq->channel->priv->state_lock));
|
||||
if (old_prog)
|
||||
bpf_prog_put(old_prog);
|
||||
}
|
||||
|
||||
static int mlx5e_xdp_set(struct net_device *netdev, struct bpf_prog *prog)
|
||||
{
|
||||
struct mlx5e_priv *priv = netdev_priv(netdev);
|
||||
|
|
@ -4388,29 +4384,10 @@ static int mlx5e_xdp_set(struct net_device *netdev, struct bpf_prog *prog)
|
|||
*/
|
||||
for (i = 0; i < priv->channels.num; i++) {
|
||||
struct mlx5e_channel *c = priv->channels.c[i];
|
||||
bool xsk_open = test_bit(MLX5E_CHANNEL_STATE_XSK, c->state);
|
||||
|
||||
clear_bit(MLX5E_RQ_STATE_ENABLED, &c->rq.state);
|
||||
if (xsk_open)
|
||||
clear_bit(MLX5E_RQ_STATE_ENABLED, &c->xskrq.state);
|
||||
napi_synchronize(&c->napi);
|
||||
/* prevent mlx5e_poll_rx_cq from accessing rq->xdp_prog */
|
||||
|
||||
old_prog = xchg(&c->rq.xdp_prog, prog);
|
||||
if (old_prog)
|
||||
bpf_prog_put(old_prog);
|
||||
|
||||
if (xsk_open) {
|
||||
old_prog = xchg(&c->xskrq.xdp_prog, prog);
|
||||
if (old_prog)
|
||||
bpf_prog_put(old_prog);
|
||||
}
|
||||
|
||||
set_bit(MLX5E_RQ_STATE_ENABLED, &c->rq.state);
|
||||
if (xsk_open)
|
||||
set_bit(MLX5E_RQ_STATE_ENABLED, &c->xskrq.state);
|
||||
/* napi_schedule in case we have missed anything */
|
||||
napi_schedule(&c->napi);
|
||||
mlx5e_rq_replace_xdp_prog(&c->rq, prog);
|
||||
if (test_bit(MLX5E_CHANNEL_STATE_XSK, c->state))
|
||||
mlx5e_rq_replace_xdp_prog(&c->xskrq, prog);
|
||||
}
|
||||
|
||||
unlock:
|
||||
|
|
@ -5200,7 +5177,7 @@ static const struct mlx5e_profile mlx5e_nic_profile = {
|
|||
.enable = mlx5e_nic_enable,
|
||||
.disable = mlx5e_nic_disable,
|
||||
.update_rx = mlx5e_update_nic_rx,
|
||||
.update_stats = mlx5e_update_ndo_stats,
|
||||
.update_stats = mlx5e_stats_update_ndo_stats,
|
||||
.update_carrier = mlx5e_update_carrier,
|
||||
.rx_handlers = &mlx5e_rx_handlers_nic,
|
||||
.max_tc = MLX5E_MAX_NUM_TC,
|
||||
|
|
|
|||
|
|
@ -1171,7 +1171,7 @@ static const struct mlx5e_profile mlx5e_rep_profile = {
|
|||
.cleanup_tx = mlx5e_cleanup_rep_tx,
|
||||
.enable = mlx5e_rep_enable,
|
||||
.update_rx = mlx5e_update_rep_rx,
|
||||
.update_stats = mlx5e_update_ndo_stats,
|
||||
.update_stats = mlx5e_stats_update_ndo_stats,
|
||||
.rx_handlers = &mlx5e_rx_handlers_rep,
|
||||
.max_tc = 1,
|
||||
.rq_groups = MLX5E_NUM_RQ_GROUPS(REGULAR),
|
||||
|
|
@ -1189,7 +1189,7 @@ static const struct mlx5e_profile mlx5e_uplink_rep_profile = {
|
|||
.enable = mlx5e_uplink_rep_enable,
|
||||
.disable = mlx5e_uplink_rep_disable,
|
||||
.update_rx = mlx5e_update_rep_rx,
|
||||
.update_stats = mlx5e_update_ndo_stats,
|
||||
.update_stats = mlx5e_stats_update_ndo_stats,
|
||||
.update_carrier = mlx5e_update_carrier,
|
||||
.rx_handlers = &mlx5e_rx_handlers_rep,
|
||||
.max_tc = MLX5E_MAX_NUM_TC,
|
||||
|
|
|
|||
|
|
@ -53,6 +53,7 @@
|
|||
#include "en/xsk/rx.h"
|
||||
#include "en/health.h"
|
||||
#include "en/params.h"
|
||||
#include "en/txrx.h"
|
||||
|
||||
static struct sk_buff *
|
||||
mlx5e_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq, struct mlx5e_mpw_info *wi,
|
||||
|
|
@ -1080,6 +1081,9 @@ static inline void mlx5e_build_rx_skb(struct mlx5_cqe64 *cqe,
|
|||
mlx5e_enable_ecn(rq, skb);
|
||||
|
||||
skb->protocol = eth_type_trans(skb, netdev);
|
||||
|
||||
if (unlikely(mlx5e_skb_is_multicast(skb)))
|
||||
stats->mcast_packets++;
|
||||
}
|
||||
|
||||
static inline void mlx5e_complete_rx_cqe(struct mlx5e_rq *rq,
|
||||
|
|
@ -1132,7 +1136,6 @@ mlx5e_skb_from_cqe_linear(struct mlx5e_rq *rq, struct mlx5_cqe64 *cqe,
|
|||
struct xdp_buff xdp;
|
||||
struct sk_buff *skb;
|
||||
void *va, *data;
|
||||
bool consumed;
|
||||
u32 frag_size;
|
||||
|
||||
va = page_address(di->page) + wi->offset;
|
||||
|
|
@ -1144,11 +1147,8 @@ mlx5e_skb_from_cqe_linear(struct mlx5e_rq *rq, struct mlx5_cqe64 *cqe,
|
|||
prefetchw(va); /* xdp_frame data area */
|
||||
prefetch(data);
|
||||
|
||||
rcu_read_lock();
|
||||
mlx5e_fill_xdp_buff(rq, va, rx_headroom, cqe_bcnt, &xdp);
|
||||
consumed = mlx5e_xdp_handle(rq, di, &cqe_bcnt, &xdp);
|
||||
rcu_read_unlock();
|
||||
if (consumed)
|
||||
if (mlx5e_xdp_handle(rq, di, &cqe_bcnt, &xdp))
|
||||
return NULL; /* page/packet was consumed by XDP */
|
||||
|
||||
rx_headroom = xdp.data - xdp.data_hard_start;
|
||||
|
|
@ -1438,7 +1438,6 @@ mlx5e_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq, struct mlx5e_mpw_info *wi,
|
|||
struct sk_buff *skb;
|
||||
void *va, *data;
|
||||
u32 frag_size;
|
||||
bool consumed;
|
||||
|
||||
/* Check packet size. Note LRO doesn't use linear SKB */
|
||||
if (unlikely(cqe_bcnt > rq->hw_mtu)) {
|
||||
|
|
@ -1455,11 +1454,8 @@ mlx5e_skb_from_cqe_mpwrq_linear(struct mlx5e_rq *rq, struct mlx5e_mpw_info *wi,
|
|||
prefetchw(va); /* xdp_frame data area */
|
||||
prefetch(data);
|
||||
|
||||
rcu_read_lock();
|
||||
mlx5e_fill_xdp_buff(rq, va, rx_headroom, cqe_bcnt32, &xdp);
|
||||
consumed = mlx5e_xdp_handle(rq, di, &cqe_bcnt32, &xdp);
|
||||
rcu_read_unlock();
|
||||
if (consumed) {
|
||||
if (mlx5e_xdp_handle(rq, di, &cqe_bcnt32, &xdp)) {
|
||||
if (__test_and_clear_bit(MLX5E_RQ_FLAG_XDP_XMIT, rq->flags))
|
||||
__set_bit(page_idx, wi->xdp_xmit_bitmap); /* non-atomic */
|
||||
return NULL; /* page/packet was consumed by XDP */
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user