Merge Official Source
Signed-off-by: Tianling Shen <cnsztl@immortalwrt.org>
This commit is contained in:
commit
4580230440
@ -5,7 +5,6 @@
|
||||
|
||||
config EXPERIMENTAL
|
||||
bool "Enable experimental features by default"
|
||||
default n
|
||||
help
|
||||
Set this option to build with latest bleeding edge features
|
||||
which may or may not work as expected.
|
||||
@ -42,7 +41,6 @@ menu "Global build settings"
|
||||
|
||||
config BUILDBOT
|
||||
bool "Set build defaults for automatic builds (e.g. via buildbot)"
|
||||
default n
|
||||
help
|
||||
This option changes several defaults to be more suitable for
|
||||
automatic builds. This includes the following changes:
|
||||
@ -75,10 +73,8 @@ menu "Global build settings"
|
||||
|
||||
config DISPLAY_SUPPORT
|
||||
bool "Show packages that require graphics support (local or remote)"
|
||||
default n
|
||||
|
||||
config BUILD_PATENTED
|
||||
default n
|
||||
bool "Compile with support for patented functionality"
|
||||
help
|
||||
When this option is disabled, software which provides patented functionality
|
||||
@ -86,7 +82,6 @@ menu "Global build settings"
|
||||
functionality, this optional support will get disabled for this package.
|
||||
|
||||
config BUILD_NLS
|
||||
default n
|
||||
bool "Compile with full language support"
|
||||
help
|
||||
When this option is enabled, packages are built with the full versions of
|
||||
@ -100,7 +95,6 @@ menu "Global build settings"
|
||||
config CLEAN_IPKG
|
||||
bool
|
||||
prompt "Remove ipkg/opkg status data files in final images"
|
||||
default n
|
||||
help
|
||||
This removes all ipkg/opkg status data files from the target directory
|
||||
before building the root filesystem.
|
||||
@ -108,14 +102,12 @@ menu "Global build settings"
|
||||
config IPK_FILES_CHECKSUMS
|
||||
bool
|
||||
prompt "Record files checksums in package metadata"
|
||||
default n
|
||||
help
|
||||
This makes file checksums part of package metadata. It increases size
|
||||
but provides you with pkg_check command to check for flash corruptions.
|
||||
|
||||
config INCLUDE_CONFIG
|
||||
bool "Include build configuration in firmware" if DEVEL
|
||||
default n
|
||||
help
|
||||
If enabled, buildinfo files will be stored in /etc/build.* of firmware.
|
||||
|
||||
@ -149,7 +141,6 @@ menu "Global build settings"
|
||||
config DEBUG
|
||||
bool
|
||||
prompt "Compile packages with debugging info"
|
||||
default n
|
||||
help
|
||||
Adds -g3 to the CFLAGS.
|
||||
|
||||
|
||||
@ -4,11 +4,9 @@
|
||||
|
||||
menuconfig DEVEL
|
||||
bool "Advanced configuration options (for developers)"
|
||||
default n
|
||||
|
||||
config BROKEN
|
||||
bool "Show broken platforms / packages / devices" if DEVEL
|
||||
default n
|
||||
|
||||
config BINARY_FOLDER
|
||||
string "Binary folder" if DEVEL
|
||||
@ -53,7 +51,6 @@ menuconfig DEVEL
|
||||
|
||||
config AUTOREMOVE
|
||||
bool "Automatic removal of build directories" if DEVEL
|
||||
default n
|
||||
help
|
||||
Automatically delete build directories after make target completed.
|
||||
This allows you to symlink build_dir into a scratch location, e.g. a ramdisk,
|
||||
@ -61,7 +58,6 @@ menuconfig DEVEL
|
||||
|
||||
config BUILD_ALL_HOST_TOOLS
|
||||
bool "Compile all host tools" if DEVEL
|
||||
default n
|
||||
help
|
||||
Compile all host host tools even if not needed. This is needed to prepare a
|
||||
universal precompiled host tools archive to use in another buildroot.
|
||||
@ -84,7 +80,6 @@ menuconfig DEVEL
|
||||
|
||||
config CCACHE
|
||||
bool "Use ccache" if DEVEL
|
||||
default n
|
||||
help
|
||||
Compiler cache; see https://ccache.samba.org/
|
||||
|
||||
|
||||
@ -59,7 +59,6 @@ menu "Target Images"
|
||||
config TARGET_INITRAMFS_FORCE
|
||||
bool "Force"
|
||||
depends on TARGET_ROOTFS_INITRAMFS
|
||||
default n
|
||||
help
|
||||
Ignore the initramfs passed by the bootloader.
|
||||
|
||||
@ -128,7 +127,6 @@ menu "Target Images"
|
||||
config TARGET_EXT4_JOURNAL
|
||||
bool "Create a journaling filesystem"
|
||||
depends on TARGET_ROOTFS_EXT4FS
|
||||
default n
|
||||
help
|
||||
Create an ext4 filesystem with a journal.
|
||||
|
||||
@ -233,7 +231,6 @@ menu "Target Images"
|
||||
config GRUB_FLOWCONTROL
|
||||
bool "Use RTE/CTS on serial console"
|
||||
depends on GRUB_SERIAL != ""
|
||||
default n
|
||||
|
||||
config GRUB_BOOTOPTS
|
||||
string "Extra kernel boot options"
|
||||
@ -324,7 +321,6 @@ menu "Target Images"
|
||||
|
||||
config TARGET_ROOTFS_PERSIST_VAR
|
||||
bool "Make /var persistent"
|
||||
default n
|
||||
help
|
||||
Do not symlink /var to /tmp, so that its content will persist
|
||||
across reboots. When enabled, /var/run will still be linked
|
||||
|
||||
@ -47,12 +47,10 @@ config KERNEL_MIPS_FP_SUPPORT
|
||||
|
||||
config KERNEL_ARM_PMU
|
||||
bool
|
||||
default n
|
||||
depends on (arm || aarch64)
|
||||
|
||||
config KERNEL_X86_VSYSCALL_EMULATION
|
||||
bool "Enable vsyscall emulation"
|
||||
default n
|
||||
depends on x86_64
|
||||
help
|
||||
This enables emulation of the legacy vsyscall page. Disabling
|
||||
@ -70,12 +68,10 @@ config KERNEL_X86_VSYSCALL_EMULATION
|
||||
|
||||
config KERNEL_PERF_EVENTS
|
||||
bool "Compile the kernel with performance events and counters"
|
||||
default n
|
||||
select KERNEL_ARM_PMU if (arm || aarch64)
|
||||
|
||||
config KERNEL_PROFILING
|
||||
bool "Compile the kernel with profiling enabled"
|
||||
default n
|
||||
select KERNEL_PERF_EVENTS
|
||||
help
|
||||
Enable the extended profiling support mechanisms used by profilers such
|
||||
@ -255,7 +251,6 @@ config KERNEL_KCOV_INSTRUMENT_ALL
|
||||
|
||||
config KERNEL_TASKSTATS
|
||||
bool "Compile the kernel with task resource/io statistics and accounting"
|
||||
default n
|
||||
help
|
||||
Enable the collection and publishing of task/io statistics and
|
||||
accounting. Enable this option to enable i/o monitoring in system
|
||||
@ -283,37 +278,30 @@ config KERNEL_KALLSYMS
|
||||
config KERNEL_FTRACE
|
||||
bool "Compile the kernel with tracing support"
|
||||
depends on !TARGET_uml
|
||||
default n
|
||||
|
||||
config KERNEL_FTRACE_SYSCALLS
|
||||
bool "Trace system calls"
|
||||
depends on KERNEL_FTRACE
|
||||
default n
|
||||
|
||||
config KERNEL_ENABLE_DEFAULT_TRACERS
|
||||
bool "Trace process context switches and events"
|
||||
depends on KERNEL_FTRACE
|
||||
default n
|
||||
|
||||
config KERNEL_FUNCTION_TRACER
|
||||
bool "Function tracer"
|
||||
depends on KERNEL_FTRACE
|
||||
default n
|
||||
|
||||
config KERNEL_FUNCTION_GRAPH_TRACER
|
||||
bool "Function graph tracer"
|
||||
depends on KERNEL_FUNCTION_TRACER
|
||||
default n
|
||||
|
||||
config KERNEL_DYNAMIC_FTRACE
|
||||
bool "Enable/disable function tracing dynamically"
|
||||
depends on KERNEL_FUNCTION_TRACER
|
||||
default n
|
||||
|
||||
config KERNEL_FUNCTION_PROFILER
|
||||
bool "Function profiler"
|
||||
depends on KERNEL_FUNCTION_TRACER
|
||||
default n
|
||||
|
||||
config KERNEL_IRQSOFF_TRACER
|
||||
bool "Interrupts-off Latency Tracer"
|
||||
@ -364,7 +352,6 @@ config KERNEL_HIST_TRIGGERS
|
||||
|
||||
config KERNEL_DEBUG_KERNEL
|
||||
bool
|
||||
default n
|
||||
|
||||
config KERNEL_DEBUG_INFO
|
||||
bool "Compile the kernel with debug information"
|
||||
@ -376,7 +363,6 @@ config KERNEL_DEBUG_INFO
|
||||
config KERNEL_DEBUG_INFO_BTF
|
||||
|
||||
bool "Enable additional BTF type information"
|
||||
default n
|
||||
depends on !HOST_OS_MACOS
|
||||
depends on KERNEL_DEBUG_INFO && !KERNEL_DEBUG_INFO_REDUCED
|
||||
select DWARVES
|
||||
@ -403,12 +389,10 @@ config KERNEL_DEBUG_INFO_REDUCED
|
||||
|
||||
config KERNEL_DEBUG_LL_UART_NONE
|
||||
bool
|
||||
default n
|
||||
depends on arm
|
||||
|
||||
config KERNEL_DEBUG_LL
|
||||
bool
|
||||
default n
|
||||
depends on arm
|
||||
select KERNEL_DEBUG_LL_UART_NONE
|
||||
help
|
||||
@ -417,7 +401,6 @@ config KERNEL_DEBUG_LL
|
||||
config KERNEL_DEBUG_VIRTUAL
|
||||
bool "Compile the kernel with VM translations debugging"
|
||||
select KERNEL_DEBUG_KERNEL
|
||||
default n
|
||||
help
|
||||
Enable checks sanity checks to catch invalid uses of
|
||||
virt_to_phys()/phys_to_virt() against the non-linear address space.
|
||||
@ -425,7 +408,6 @@ config KERNEL_DEBUG_VIRTUAL
|
||||
config KERNEL_DYNAMIC_DEBUG
|
||||
bool "Compile the kernel with dynamic printk"
|
||||
select KERNEL_DEBUG_FS
|
||||
default n
|
||||
help
|
||||
Compiles debug level messages into the kernel, which would not
|
||||
otherwise be available at runtime. These messages can then be
|
||||
@ -437,7 +419,6 @@ config KERNEL_DYNAMIC_DEBUG
|
||||
config KERNEL_EARLY_PRINTK
|
||||
bool "Compile the kernel with early printk"
|
||||
default y if TARGET_bcm53xx
|
||||
default n
|
||||
depends on arm
|
||||
select KERNEL_DEBUG_KERNEL
|
||||
select KERNEL_DEBUG_LL if arm
|
||||
@ -448,7 +429,6 @@ config KERNEL_EARLY_PRINTK
|
||||
|
||||
config KERNEL_KPROBES
|
||||
bool "Compile the kernel with kprobes support"
|
||||
default n
|
||||
select KERNEL_FTRACE
|
||||
select KERNEL_PERF_EVENTS
|
||||
help
|
||||
@ -465,7 +445,6 @@ config KERNEL_KPROBE_EVENTS
|
||||
|
||||
config KERNEL_BPF_EVENTS
|
||||
bool "Compile the kernel with BPF event support"
|
||||
default n
|
||||
select KERNEL_KPROBES
|
||||
help
|
||||
Allows to attach BPF programs to kprobe, uprobe and tracepoint events.
|
||||
@ -475,7 +454,6 @@ config KERNEL_BPF_EVENTS
|
||||
|
||||
config KERNEL_BPF_KPROBE_OVERRIDE
|
||||
bool
|
||||
default n
|
||||
depends on KERNEL_KPROBES
|
||||
|
||||
config KERNEL_AIO
|
||||
@ -496,7 +474,6 @@ config KERNEL_FANOTIFY
|
||||
|
||||
config KERNEL_BLK_DEV_BSG
|
||||
bool "Compile the kernel with SCSI generic v4 support for any block device"
|
||||
default n
|
||||
|
||||
config KERNEL_TRANSPARENT_HUGEPAGE
|
||||
bool
|
||||
@ -520,7 +497,6 @@ config KERNEL_HUGETLB_PAGE
|
||||
bool "Compile the kernel with HugeTLB support"
|
||||
select KERNEL_TRANSPARENT_HUGEPAGE
|
||||
select KERNEL_HUGETLBFS
|
||||
default n
|
||||
|
||||
config KERNEL_MAGIC_SYSRQ
|
||||
bool "Compile the kernel with SysRq support"
|
||||
@ -545,7 +521,6 @@ config KERNEL_ELF_CORE
|
||||
config KERNEL_PROVE_LOCKING
|
||||
bool "Enable kernel lock checking"
|
||||
select KERNEL_DEBUG_KERNEL
|
||||
default n
|
||||
|
||||
config KERNEL_SOFTLOCKUP_DETECTOR
|
||||
bool "Compile the kernel with detect Soft Lockups"
|
||||
@ -647,11 +622,9 @@ config USE_RFKILL
|
||||
|
||||
config USE_SPARSE
|
||||
bool "Enable sparse check during kernel build"
|
||||
default n
|
||||
|
||||
config KERNEL_DEVTMPFS
|
||||
bool "Compile the kernel with device tmpfs enabled"
|
||||
default n
|
||||
help
|
||||
devtmpfs is a simple, kernel-managed /dev filesystem. The kernel creates
|
||||
devices nodes for all registered devices to simplify boot, but leaves more
|
||||
@ -661,7 +634,6 @@ if KERNEL_DEVTMPFS
|
||||
|
||||
config KERNEL_DEVTMPFS_MOUNT
|
||||
bool "Automatically mount devtmpfs after root filesystem is mounted"
|
||||
default n
|
||||
|
||||
endif
|
||||
|
||||
@ -672,17 +644,14 @@ config KERNEL_KEYS
|
||||
config KERNEL_PERSISTENT_KEYRINGS
|
||||
bool "Enable kernel persistent keyrings"
|
||||
depends on KERNEL_KEYS
|
||||
default n
|
||||
|
||||
config KERNEL_KEYS_REQUEST_CACHE
|
||||
bool "Enable temporary caching of the last request_key() result"
|
||||
depends on KERNEL_KEYS
|
||||
default n
|
||||
|
||||
config KERNEL_BIG_KEYS
|
||||
bool "Enable large payload keys on kernel keyrings"
|
||||
depends on KERNEL_KEYS
|
||||
default n
|
||||
|
||||
#
|
||||
# CGROUP support symbols
|
||||
@ -696,7 +665,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_CGROUP_DEBUG
|
||||
bool "Example debug cgroup subsystem"
|
||||
default n
|
||||
help
|
||||
This option enables a simple cgroup subsystem that
|
||||
exports useful debugging information about the cgroups
|
||||
@ -707,7 +675,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_CGROUP_FREEZER
|
||||
bool "legacy Freezer cgroup subsystem"
|
||||
default n
|
||||
select KERNEL_FREEZER
|
||||
help
|
||||
Provides a way to freeze and unfreeze all tasks in a
|
||||
@ -717,7 +684,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_CGROUP_DEVICE
|
||||
bool "legacy Device controller for cgroups"
|
||||
default n
|
||||
help
|
||||
Provides a cgroup implementing whitelists for devices which
|
||||
a process in the cgroup can mknod or open.
|
||||
@ -725,7 +691,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_CGROUP_HUGETLB
|
||||
bool "HugeTLB controller"
|
||||
default n
|
||||
select KERNEL_HUGETLB_PAGE
|
||||
|
||||
config KERNEL_CGROUP_PIDS
|
||||
@ -754,7 +719,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_PROC_PID_CPUSET
|
||||
bool "Include legacy /proc/<pid>/cpuset file"
|
||||
default n
|
||||
depends on KERNEL_CPUSETS
|
||||
|
||||
config KERNEL_CGROUP_CPUACCT
|
||||
@ -820,7 +784,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_MEMCG_SWAP_ENABLED
|
||||
bool "Memory Resource Controller Swap Extension enabled by default"
|
||||
default n
|
||||
depends on KERNEL_MEMCG_SWAP
|
||||
help
|
||||
Memory Resource Controller Swap Extension comes with its price in
|
||||
@ -849,7 +812,6 @@ if KERNEL_CGROUPS
|
||||
config KERNEL_CGROUP_PERF
|
||||
bool "Enable perf_event per-cpu per-container group (cgroup) monitoring"
|
||||
select KERNEL_PERF_EVENTS
|
||||
default n
|
||||
help
|
||||
This option extends the per-cpu mode to restrict monitoring to
|
||||
threads which belong to the cgroup specified and run on the
|
||||
@ -926,7 +888,6 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_DEBUG_BLK_CGROUP
|
||||
bool "Enable Block IO controller debugging"
|
||||
default n
|
||||
depends on KERNEL_BLK_CGROUP
|
||||
help
|
||||
Enable some debugging help. Currently it exports additional stat
|
||||
@ -934,15 +895,12 @@ if KERNEL_CGROUPS
|
||||
|
||||
config KERNEL_NET_CLS_CGROUP
|
||||
bool "legacy Control Group Classifier"
|
||||
default n
|
||||
|
||||
config KERNEL_CGROUP_NET_CLASSID
|
||||
bool "legacy Network classid cgroup"
|
||||
default n
|
||||
|
||||
config KERNEL_CGROUP_NET_PRIO
|
||||
bool "legacy Network priority cgroup"
|
||||
default n
|
||||
|
||||
endif
|
||||
|
||||
@ -1168,7 +1126,6 @@ endif
|
||||
menu "Filesystem ACL and attr support options"
|
||||
config USE_FS_ACL_ATTR
|
||||
bool "Use filesystem ACL and attr support by default"
|
||||
default n
|
||||
help
|
||||
Make using ACLs (e.g. POSIX ACL, NFSv4 ACL) the default
|
||||
for kernel and packages, except tmpfs, flash filesystems,
|
||||
@ -1193,17 +1150,14 @@ menu "Filesystem ACL and attr support options"
|
||||
config KERNEL_F2FS_FS_POSIX_ACL
|
||||
bool "Enable POSIX ACL for F2FS Filesystems"
|
||||
select KERNEL_FS_POSIX_ACL
|
||||
default n
|
||||
|
||||
config KERNEL_JFFS2_FS_POSIX_ACL
|
||||
bool "Enable POSIX ACL for JFFS2 Filesystems"
|
||||
select KERNEL_FS_POSIX_ACL
|
||||
default n
|
||||
|
||||
config KERNEL_TMPFS_POSIX_ACL
|
||||
bool "Enable POSIX ACL for TMPFS Filesystems"
|
||||
select KERNEL_FS_POSIX_ACL
|
||||
default n
|
||||
|
||||
config KERNEL_CIFS_ACL
|
||||
bool "Enable CIFS ACLs"
|
||||
@ -1226,15 +1180,12 @@ menu "Filesystem ACL and attr support options"
|
||||
|
||||
config KERNEL_NFS_V3_ACL_SUPPORT
|
||||
bool "Enable ACLs for NFSv3"
|
||||
default n
|
||||
|
||||
config KERNEL_NFSD_V2_ACL_SUPPORT
|
||||
bool "Enable ACLs for NFSDv2"
|
||||
default n
|
||||
|
||||
config KERNEL_NFSD_V3_ACL_SUPPORT
|
||||
bool "Enable ACLs for NFSDv3"
|
||||
default n
|
||||
|
||||
config KERNEL_REISER_FS_POSIX_ACL
|
||||
bool "Enable POSIX ACLs for ReiserFS"
|
||||
|
||||
@ -1,2 +1,2 @@
|
||||
LINUX_VERSION-5.10 = .165
|
||||
LINUX_KERNEL_HASH-5.10.165 = 971defc48f19ed0a2a7ffd4b48234619cac28895c985c6d747f5b707ba47af0d
|
||||
LINUX_VERSION-5.10 = .166
|
||||
LINUX_KERNEL_HASH-5.10.166 = 0051a1780e5bda0efc68dafab7c728b8283d2b028fedb439418f478be7d3e1af
|
||||
|
||||
@ -1,2 +1,2 @@
|
||||
LINUX_VERSION-5.15 = .90
|
||||
LINUX_KERNEL_HASH-5.15.90 = e6fd430022686753af7516fe7544f96aab379509dc5b7829017bdcd92b393b42
|
||||
LINUX_VERSION-5.15 = .91
|
||||
LINUX_KERNEL_HASH-5.15.91 = a63c2bb1beb15f1aea9c63cf80559f5b7ab58afd2da2fa5e7670c515ebe1fe80
|
||||
|
||||
@ -232,7 +232,7 @@ export_partdevice() {
|
||||
while read line; do
|
||||
export -n "$line"
|
||||
done < "$uevent"
|
||||
if [ $BOOTDEV_MAJOR = $MAJOR -a $(($BOOTDEV_MINOR + $offset)) = $MINOR -a -b "/dev/$DEVNAME" ]; then
|
||||
if [ "$BOOTDEV_MAJOR" = "$MAJOR" -a $(($BOOTDEV_MINOR + $offset)) = "$MINOR" -a -b "/dev/$DEVNAME" ]; then
|
||||
export "$var=$DEVNAME"
|
||||
return 0
|
||||
fi
|
||||
|
||||
@ -9,7 +9,7 @@ include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=ltq-vdsl-vr9
|
||||
PKG_VERSION:=4.17.18.6
|
||||
PKG_RELEASE:=7
|
||||
PKG_RELEASE:=8
|
||||
|
||||
PKG_BASE_NAME:=drv_dsl_cpe_api
|
||||
PKG_SOURCE:=$(PKG_BASE_NAME)_vrx-$(PKG_VERSION).tar.gz
|
||||
|
||||
@ -0,0 +1,22 @@
|
||||
--- a/src/pm/drv_dsl_cpe_api_pm_vrx.c
|
||||
+++ b/src/pm/drv_dsl_cpe_api_pm_vrx.c
|
||||
@@ -1435,9 +1435,16 @@ DSL_Error_t DSL_DRV_PM_DEV_ReTxCountersG
|
||||
/* ignore zero value*/
|
||||
if (nEftrMin)
|
||||
{
|
||||
- /* Fw Format: kBit/s */
|
||||
- /* API format: bit/s */
|
||||
- pCounters->nEftrMin = nEftrMin*1000;
|
||||
+ if (nDirection == DSL_NEAR_END)
|
||||
+ {
|
||||
+ /* Fw Format: kBit/s */
|
||||
+ /* API format: bit/s */
|
||||
+ pCounters->nEftrMin = nEftrMin*1000;
|
||||
+ }
|
||||
+ else
|
||||
+ {
|
||||
+ pCounters->nEftrMin = nEftrMin;
|
||||
+ }
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -243,6 +243,22 @@ endef
|
||||
$(eval $(call KernelPackage,gpio-f7188x))
|
||||
|
||||
|
||||
define KernelPackage/lkdtm
|
||||
SUBMENU:=$(OTHER_MENU)
|
||||
TITLE:=Linux Kernel Dump Test Tool Module
|
||||
KCONFIG:=CONFIG_LKDTM
|
||||
FILES:=$(LINUX_DIR)/drivers/misc/lkdtm/lkdtm.ko
|
||||
AUTOLOAD:=$(call AutoProbe,lkdtm)
|
||||
endef
|
||||
|
||||
define KernelPackage/lkdtm/description
|
||||
This module enables testing of the different dumping mechanisms by inducing
|
||||
system failures at predefined crash points.
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,lkdtm))
|
||||
|
||||
|
||||
define KernelPackage/pinctrl-mcp23s08
|
||||
SUBMENU:=$(OTHER_MENU)
|
||||
TITLE:=Microchip MCP23xxx I/O expander
|
||||
|
||||
@ -8,9 +8,9 @@ PKG_LICENSE_FILES:=
|
||||
|
||||
PKG_SOURCE_URL:=https://github.com/openwrt/mt76
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_DATE:=2022-12-22
|
||||
PKG_SOURCE_VERSION:=5b509e80384ab019ac11aa90c81ec0dbb5b0d7f2
|
||||
PKG_MIRROR_HASH:=6fc25df4d28becd010ff4971b23731c08b53e69381a9e4c868091899712f78a9
|
||||
PKG_SOURCE_DATE:=2023-02-02
|
||||
PKG_SOURCE_VERSION:=b2360d59747c6fed2b65bc1c3563c10593c83f3e
|
||||
PKG_MIRROR_HASH:=f85f00fa8f549de348a115f92c4f0235e413ed924669aece390c7570882526dd
|
||||
|
||||
PKG_MAINTAINER:=Felix Fietkau <nbd@nbd.name>
|
||||
PKG_USE_NINJA:=0
|
||||
@ -40,7 +40,8 @@ define KernelPackage/mt76-default
|
||||
SUBMENU:=Wireless Drivers
|
||||
DEPENDS:= \
|
||||
+kmod-mac80211 \
|
||||
+@DRIVER_11AC_SUPPORT
|
||||
+@DRIVER_11AC_SUPPORT \
|
||||
+@KERNEL_PAGE_POOL
|
||||
endef
|
||||
|
||||
define KernelPackage/mt76
|
||||
|
||||
@ -9,7 +9,7 @@ include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=mbedtls
|
||||
PKG_VERSION:=2.28.2
|
||||
PKG_RELEASE:=1
|
||||
PKG_RELEASE:=2
|
||||
PKG_USE_MIPS16:=0
|
||||
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
|
||||
@ -0,0 +1,181 @@
|
||||
From 272d48fe7a2ff00285d4ee166d3a9beca1d5122f Mon Sep 17 00:00:00 2001
|
||||
From: Glenn Strauss <gstrauss@gluelogic.com>
|
||||
Date: Sun, 23 Oct 2022 19:48:18 -0400
|
||||
Subject: [PATCH 1/4] x509 crt verify SAN iPAddress
|
||||
|
||||
Signed-off-by: Glenn Strauss <gstrauss@gluelogic.com>
|
||||
---
|
||||
include/mbedtls/x509_crt.h | 2 +-
|
||||
library/x509_crt.c | 115 +++++++++++++++++++++++++++++--------
|
||||
2 files changed, 93 insertions(+), 24 deletions(-)
|
||||
|
||||
--- a/include/mbedtls/x509_crt.h
|
||||
+++ b/include/mbedtls/x509_crt.h
|
||||
@@ -597,7 +597,7 @@ int mbedtls_x509_crt_verify_info( char *
|
||||
* \param cn The expected Common Name. This will be checked to be
|
||||
* present in the certificate's subjectAltNames extension or,
|
||||
* if this extension is absent, as a CN component in its
|
||||
- * Subject name. Currently only DNS names are supported. This
|
||||
+ * Subject name. DNS names and IP addresses are supported. This
|
||||
* may be \c NULL if the CN need not be verified.
|
||||
* \param flags The address at which to store the result of the verification.
|
||||
* If the verification couldn't be completed, the flag value is
|
||||
--- a/library/x509_crt.c
|
||||
+++ b/library/x509_crt.c
|
||||
@@ -2986,6 +2986,54 @@ find_parent:
|
||||
}
|
||||
}
|
||||
|
||||
+#ifdef _WIN32
|
||||
+/* ??? */
|
||||
+#elif defined(__sun)
|
||||
+/* Solaris requires -lsocket -lnsl for inet_pton() */
|
||||
+#elif defined(__has_include)
|
||||
+#if __has_include(<sys/socket.h>)
|
||||
+#include <sys/socket.h>
|
||||
+#endif
|
||||
+#if __has_include(<arpa/inet.h>)
|
||||
+#include <arpa/inet.h>
|
||||
+#endif
|
||||
+#endif
|
||||
+
|
||||
+/* Use whether or not AF_INET6 is defined to indicate whether or not to use
|
||||
+ * the platform inet_pton() or a local implementation (below). The local
|
||||
+ * implementation may be used even in cases where the platform provides
|
||||
+ * inet_pton(), e.g. when there are different includes required and/or the
|
||||
+ * platform implementation requires dependencies on additional libraries.
|
||||
+ * Specifically, Windows requires custom includes and additional link
|
||||
+ * dependencies, and Solaris requires additional link dependencies.
|
||||
+ * Also, as a coarse heuristic, use the local implementation if the compiler
|
||||
+ * does not support __has_include(), or if the definition of AF_INET6 is not
|
||||
+ * provided by headers included (or not) via __has_include() above. */
|
||||
+#ifndef AF_INET6
|
||||
+
|
||||
+#define x509_cn_inet_pton( cn, dst ) ( 0 )
|
||||
+
|
||||
+#else
|
||||
+
|
||||
+static int x509_inet_pton_ipv6( const char *src, void *dst )
|
||||
+{
|
||||
+ return( inet_pton( AF_INET6, src, dst ) == 1 ? 0 : -1 );
|
||||
+}
|
||||
+
|
||||
+static int x509_inet_pton_ipv4( const char *src, void *dst )
|
||||
+{
|
||||
+ return( inet_pton( AF_INET, src, dst ) == 1 ? 0 : -1 );
|
||||
+}
|
||||
+
|
||||
+#endif /* AF_INET6 */
|
||||
+
|
||||
+static size_t x509_cn_inet_pton( const char *cn, void *dst )
|
||||
+{
|
||||
+ return( strchr( cn, ':' ) == NULL
|
||||
+ ? x509_inet_pton_ipv4( cn, dst ) == 0 ? 4 : 0
|
||||
+ : x509_inet_pton_ipv6( cn, dst ) == 0 ? 16 : 0 );
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Check for CN match
|
||||
*/
|
||||
@@ -3008,23 +3056,51 @@ static int x509_crt_check_cn( const mbed
|
||||
return( -1 );
|
||||
}
|
||||
|
||||
+static int x509_crt_check_san_ip( const mbedtls_x509_sequence *san,
|
||||
+ const char *cn, size_t cn_len )
|
||||
+{
|
||||
+ uint32_t ip[4];
|
||||
+ cn_len = x509_cn_inet_pton( cn, ip );
|
||||
+ if( cn_len == 0 )
|
||||
+ return( -1 );
|
||||
+
|
||||
+ for( const mbedtls_x509_sequence *cur = san; cur != NULL; cur = cur->next )
|
||||
+ {
|
||||
+ const unsigned char san_type = (unsigned char) cur->buf.tag &
|
||||
+ MBEDTLS_ASN1_TAG_VALUE_MASK;
|
||||
+ if( san_type == MBEDTLS_X509_SAN_IP_ADDRESS &&
|
||||
+ cur->buf.len == cn_len && memcmp( cur->buf.p, ip, cn_len ) == 0 )
|
||||
+ return( 0 );
|
||||
+ }
|
||||
+
|
||||
+ return( -1 );
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* Check for SAN match, see RFC 5280 Section 4.2.1.6
|
||||
*/
|
||||
-static int x509_crt_check_san( const mbedtls_x509_buf *name,
|
||||
+static int x509_crt_check_san( const mbedtls_x509_sequence *san,
|
||||
const char *cn, size_t cn_len )
|
||||
{
|
||||
- const unsigned char san_type = (unsigned char) name->tag &
|
||||
- MBEDTLS_ASN1_TAG_VALUE_MASK;
|
||||
-
|
||||
- /* dNSName */
|
||||
- if( san_type == MBEDTLS_X509_SAN_DNS_NAME )
|
||||
- return( x509_crt_check_cn( name, cn, cn_len ) );
|
||||
-
|
||||
- /* (We may handle other types here later.) */
|
||||
+ int san_ip = 0;
|
||||
+ for( const mbedtls_x509_sequence *cur = san; cur != NULL; cur = cur->next )
|
||||
+ {
|
||||
+ switch( (unsigned char) cur->buf.tag & MBEDTLS_ASN1_TAG_VALUE_MASK )
|
||||
+ {
|
||||
+ case MBEDTLS_X509_SAN_DNS_NAME: /* dNSName */
|
||||
+ if( x509_crt_check_cn( &cur->buf, cn, cn_len ) == 0 )
|
||||
+ return( 0 );
|
||||
+ break;
|
||||
+ case MBEDTLS_X509_SAN_IP_ADDRESS: /* iPAddress */
|
||||
+ san_ip = 1;
|
||||
+ break;
|
||||
+ /* (We may handle other types here later.) */
|
||||
+ default: /* Unrecognized type */
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
|
||||
- /* Unrecognized type */
|
||||
- return( -1 );
|
||||
+ return( san_ip ? x509_crt_check_san_ip( san, cn, cn_len ) : -1 );
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -3035,19 +3111,12 @@ static void x509_crt_verify_name( const
|
||||
uint32_t *flags )
|
||||
{
|
||||
const mbedtls_x509_name *name;
|
||||
- const mbedtls_x509_sequence *cur;
|
||||
size_t cn_len = strlen( cn );
|
||||
|
||||
if( crt->ext_types & MBEDTLS_X509_EXT_SUBJECT_ALT_NAME )
|
||||
{
|
||||
- for( cur = &crt->subject_alt_names; cur != NULL; cur = cur->next )
|
||||
- {
|
||||
- if( x509_crt_check_san( &cur->buf, cn, cn_len ) == 0 )
|
||||
- break;
|
||||
- }
|
||||
-
|
||||
- if( cur == NULL )
|
||||
- *flags |= MBEDTLS_X509_BADCERT_CN_MISMATCH;
|
||||
+ if( x509_crt_check_san( &crt->subject_alt_names, cn, cn_len ) == 0 )
|
||||
+ return;
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -3056,13 +3125,13 @@ static void x509_crt_verify_name( const
|
||||
if( MBEDTLS_OID_CMP( MBEDTLS_OID_AT_CN, &name->oid ) == 0 &&
|
||||
x509_crt_check_cn( &name->val, cn, cn_len ) == 0 )
|
||||
{
|
||||
- break;
|
||||
+ return;
|
||||
}
|
||||
}
|
||||
|
||||
- if( name == NULL )
|
||||
- *flags |= MBEDTLS_X509_BADCERT_CN_MISMATCH;
|
||||
}
|
||||
+
|
||||
+ *flags |= MBEDTLS_X509_BADCERT_CN_MISMATCH;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -151,6 +151,33 @@ CONFIGURE_ARGS += \
|
||||
--$(if $(CONFIG_WOLFSSL_HAS_ECC448),enable,disable)-curve448 \
|
||||
--$(if $(CONFIG_WOLFSSL_HAS_OPENVPN),enable,disable)-openvpn
|
||||
|
||||
define Package/libwolfsslcpu-crypto/preinst-aarch64
|
||||
#!/bin/sh
|
||||
exec >&2
|
||||
printf "[libwolfsslcpu-crypto] Checking for Arm v8-A Cryptographic Extension support: "
|
||||
if [ -n "$${IPKG_INSTROOT}" ]; then
|
||||
printf "...[offline]... "
|
||||
eval "$$(grep '^DISTRIB_TARGET=' "$${IPKG_INSTROOT}/etc/openwrt_release")"
|
||||
echo "$${DISTRIB_TARGET}" | grep '^bcm27xx/.*' > /dev/null && {
|
||||
echo "not supported"
|
||||
echo "Error: Target $${DISTRIB_TARGET} does not support Arm Cryptographic Extension."
|
||||
echo "Install the regular libwolfssl package instead of libwolfsslcpu-crypto."
|
||||
exit 1
|
||||
}
|
||||
else
|
||||
grep -q '^Features.*\baes\b' /proc/cpuinfo || {
|
||||
echo "not supported"
|
||||
echo "Error: Arm v8-A Cryptographic Extension not supported."
|
||||
echo "Install the regular libwolfssl package instead of libwolfsslcpu-crypto."
|
||||
echo "Contents of /proc/cpuinfo:"
|
||||
cat /proc/cpuinfo
|
||||
exit 1
|
||||
}
|
||||
fi
|
||||
echo OK
|
||||
exit 0
|
||||
endef
|
||||
|
||||
ifeq ($(BUILD_VARIANT),regular)
|
||||
CONFIGURE_ARGS += \
|
||||
--$(if $(CONFIG_WOLFSSL_HAS_AFALG),enable,disable)-afalg \
|
||||
@ -160,9 +187,7 @@ CONFIGURE_ARGS += \
|
||||
else ifdef CONFIG_aarch64
|
||||
CONFIGURE_ARGS += --enable-armasm
|
||||
TARGET_CFLAGS:=$(TARGET_CFLAGS:-mcpu%=-mcpu%+crypto)
|
||||
WOLFSSL_NOASM_REGEX:=^bcm27xx/.*
|
||||
Package/libwolfsslcpu-crypto/preinst=\
|
||||
$(subst @@WOLFSSL_NOASM_REGEX@@,$(WOLFSSL_NOASM_REGEX),$(file <preinst.arm-ce))
|
||||
Package/libwolfsslcpu-crypto/preinst=$(Package/libwolfsslcpu-crypto/preinst-aarch64)
|
||||
else ifdef CONFIG_TARGET_x86_64
|
||||
CONFIGURE_ARGS += --enable-intelasm
|
||||
endif
|
||||
|
||||
@ -1,25 +0,0 @@
|
||||
#!/bin/sh
|
||||
exec >&2
|
||||
printf "[libwolfsslcpu-crypto] Checking for Arm v8-A Cryptographic Extension support: "
|
||||
if [ -n "${IPKG_INSTROOT}" ]; then
|
||||
printf "...[offline]... "
|
||||
eval "$(grep '^DISTRIB_TARGET=' "${IPKG_INSTROOT}/etc/openwrt_release")"
|
||||
### @@WOLFSSL_NOASM_REGEX@@ is expanded from WOLFSSL_NOASM_REGEX in the Makefile
|
||||
echo "${DISTRIB_TARGET}" | grep '@@WOLFSSL_NOASM_REGEX@@' > /dev/null && {
|
||||
echo "not supported"
|
||||
echo "Error: Target ${DISTRIB_TARGET} does not support Arm Cryptographic Extension."
|
||||
echo "Install the regular libwolfssl package instead of libwolfsslcpu-crypto."
|
||||
exit 1
|
||||
}
|
||||
else
|
||||
grep -q '^Features.*\baes\b' /proc/cpuinfo || {
|
||||
echo "not supported"
|
||||
echo "Error: Arm v8-A Cryptographic Extension not supported."
|
||||
echo "Install the regular libwolfssl package instead of libwolfsslcpu-crypto."
|
||||
echo "Contents of /proc/cpuinfo:"
|
||||
cat /proc/cpuinfo
|
||||
exit 1
|
||||
}
|
||||
fi
|
||||
echo OK
|
||||
exit 0
|
||||
@ -10,7 +10,7 @@ include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=dsl_cpe_control_danube
|
||||
PKG_VERSION:=3.24.4.4
|
||||
PKG_RELEASE:=10
|
||||
PKG_RELEASE:=11
|
||||
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/dsl_cpe_control-$(PKG_VERSION)
|
||||
PKG_SOURCE_URL:=@OPENWRT
|
||||
|
||||
@ -9,7 +9,7 @@ include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=ltq-vdsl-vr11-app
|
||||
PKG_VERSION:=4.23.1
|
||||
PKG_RELEASE:=1
|
||||
PKG_RELEASE:=2
|
||||
PKG_BASE_NAME:=dsl_cpe_control
|
||||
|
||||
UGW_VERSION=8.5.2.10
|
||||
|
||||
@ -133,6 +133,17 @@ enum {
|
||||
PSTATE_MAP_L3,
|
||||
};
|
||||
|
||||
/* These values are exported via ubus and backwards compability
|
||||
* needs to be kept!
|
||||
*/
|
||||
enum {
|
||||
RAMODE_MAP_UNKNOWN = -1,
|
||||
RAMODE_MAP_MANUAL,
|
||||
RAMODE_MAP_AT_INIT,
|
||||
RAMODE_MAP_DYNAMIC,
|
||||
RAMODE_MAP_DYNAMIC_SOS,
|
||||
};
|
||||
|
||||
static DSL_CPE_ThreadCtrl_t thread;
|
||||
static struct ubus_context *ctx;
|
||||
static struct blob_buf b;
|
||||
@ -171,6 +182,15 @@ static inline void m_array(const char *id, const uint8_t *value, size_t len) {
|
||||
blobmsg_close_array(&b, c);
|
||||
}
|
||||
|
||||
static inline void m_array_u16(const char *id, const uint16_t *value, size_t len) {
|
||||
void *c = blobmsg_open_array(&b, id);
|
||||
|
||||
for (size_t i = 0; i < len; ++i)
|
||||
blobmsg_add_u16(&b, "", value[i]);
|
||||
|
||||
blobmsg_close_array(&b, c);
|
||||
}
|
||||
|
||||
static void m_vendor(const char *id, const uint8_t *value) {
|
||||
// ITU-T T.35: U.S.
|
||||
if (U16(value[0], value[1]) != 0xb500)
|
||||
@ -418,6 +438,31 @@ static void g997_line_inventory(int fd) {
|
||||
m_array("serial", out.data.SerialNumber, DSL_G997_LI_MAXLEN_SERIAL);
|
||||
}
|
||||
|
||||
static void pilot_tones_status(int fd) {
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
IOCTL(DSL_PilotTonesStatus_t, DSL_FIO_PILOT_TONES_STATUS_GET);
|
||||
|
||||
m_array_u16("pilot_tones", out.data.nPilotTone, out.data.nNumData);
|
||||
#endif
|
||||
}
|
||||
|
||||
static void band_border_status(int fd, DSL_AccessDir_t direction) {
|
||||
IOCTL(DSL_BandBorderStatus_t, DSL_FIO_BAND_BORDER_STATUS_GET);
|
||||
|
||||
void *c, *c2;
|
||||
|
||||
c = blobmsg_open_array(&b, "limits");
|
||||
|
||||
for (size_t i = 0; i < out.data.nNumData; i++) {
|
||||
c2 = blobmsg_open_table(&b, "");
|
||||
blobmsg_add_u16(&b, "first", out.data.nBandLimits[i].nFirstToneIndex);
|
||||
blobmsg_add_u16(&b, "last", out.data.nBandLimits[i].nLastToneIndex);
|
||||
blobmsg_close_table(&b, c2);
|
||||
}
|
||||
|
||||
blobmsg_close_array(&b, c);
|
||||
}
|
||||
|
||||
static void g977_get_bit_allocation(int fd, DSL_AccessDir_t direction) {
|
||||
IOCTL_DIR(DSL_G997_BitAllocationNsc_t, DSL_FIO_G997_BIT_ALLOCATION_NSC_GET, direction);
|
||||
|
||||
@ -639,19 +684,46 @@ static void band_plan_status(int fd, profile_t *profile) {
|
||||
#endif
|
||||
}
|
||||
|
||||
static void line_feature_config(int fd, DSL_AccessDir_t direction) {
|
||||
static void line_feature_config(int fd, DSL_AccessDir_t direction, bool *retx) {
|
||||
IOCTL_DIR(DSL_LineFeature_t, DSL_FIO_LINE_FEATURE_STATUS_GET, direction)
|
||||
|
||||
m_bool("trellis", out.data.bTrellisEnable);
|
||||
m_bool("bitswap", out.data.bBitswapEnable);
|
||||
m_bool("retx", out.data.bReTxEnable);
|
||||
m_bool("virtual_noise", out.data.bVirtualNoiseSupport);
|
||||
|
||||
*retx = out.data.bReTxEnable;
|
||||
}
|
||||
|
||||
static void g997_rate_adaptation_status(int fd, DSL_AccessDir_t direction) {
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
IOCTL_DIR(DSL_G997_RateAdaptationStatus_t, DSL_FIO_G997_RATE_ADAPTATION_STATUS_GET, direction);
|
||||
|
||||
int map = RAMODE_MAP_UNKNOWN;
|
||||
const char *str;
|
||||
switch (out.data.RA_MODE) {
|
||||
STR_CASE_MAP(DSL_G997_RA_MODE_MANUAL, "Manual", RAMODE_MAP_MANUAL)
|
||||
STR_CASE_MAP(DSL_G997_RA_MODE_AT_INIT, "At initialization", RAMODE_MAP_AT_INIT)
|
||||
STR_CASE_MAP(DSL_G997_RA_MODE_DYNAMIC, "Dynamic", RAMODE_MAP_DYNAMIC)
|
||||
STR_CASE_MAP(DSL_G997_RA_MODE_DYNAMIC_SOS, "Dynamic with SOS", RAMODE_MAP_DYNAMIC_SOS)
|
||||
default:
|
||||
str = NULL;
|
||||
break;
|
||||
};
|
||||
|
||||
if (str)
|
||||
m_str("ra_mode", str);
|
||||
|
||||
if (map != PSTATE_MAP_UNKNOWN)
|
||||
m_u32("ra_mode_num", map);
|
||||
#endif
|
||||
}
|
||||
|
||||
static void g997_channel_status(int fd, DSL_AccessDir_t direction) {
|
||||
IOCTL_DIR(DSL_G997_ChannelStatus_t, DSL_FIO_G997_CHANNEL_STATUS_GET, direction);
|
||||
|
||||
m_u32("interleave_delay", out.data.ActualInterleaveDelay * 10);
|
||||
m_double("inp", (double)out.data.ActualImpulseNoiseProtection / 10);
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
// prefer ACTNDR, see comments in drv_dsl_cpe_api_g997.h
|
||||
m_u32("data_rate", out.data.ActualNetDataRate);
|
||||
@ -672,6 +744,41 @@ static void g997_line_status(int fd, DSL_AccessDir_t direction) {
|
||||
m_u32("attndr", out.data.ATTNDR);
|
||||
}
|
||||
|
||||
static void pm_retx_counters_showtime(int fd, DSL_XTUDir_t direction) {
|
||||
#ifdef INCLUDE_DSL_CPE_PM_RETX_COUNTERS
|
||||
IOCTL_DIR(DSL_PM_ReTxCounters_t, DSL_FIO_PM_RETX_COUNTERS_SHOWTIME_GET, direction);
|
||||
|
||||
m_u32("mineftr", out.data.nEftrMin);
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
static void olr_statistics(int fd, DSL_AccessDir_t direction) {
|
||||
IOCTL_DIR(DSL_OlrStatistics_t, DSL_FIO_OLR_STATISTICS_GET, direction)
|
||||
|
||||
void *c = blobmsg_open_table(&b, "bitswap");
|
||||
m_u32("requested", out.data.nBitswapRequested + out.data.nBitswapRequested);
|
||||
m_u32("executed", out.data.nBitswapExecuted);
|
||||
m_u32("rejected", out.data.nBitswapRejected);
|
||||
m_u32("timeout", out.data.nBitswapTimeout);
|
||||
blobmsg_close_table(&b, c);
|
||||
|
||||
c = blobmsg_open_table(&b, "sra");
|
||||
m_u32("requested", out.data.nSraRequested);
|
||||
m_u32("executed", out.data.nSraExecuted);
|
||||
m_u32("rejected", out.data.nSraRejected);
|
||||
m_u32("timeout", out.data.nSraTimeout);
|
||||
blobmsg_close_table(&b, c);
|
||||
|
||||
c = blobmsg_open_table(&b, "sos");
|
||||
m_u32("requested", out.data.nSosRequested);
|
||||
m_u32("executed", out.data.nSosExecuted);
|
||||
m_u32("rejected", out.data.nSosRejected);
|
||||
m_u32("timeout", out.data.nSosTimeout);
|
||||
blobmsg_close_table(&b, c);
|
||||
}
|
||||
#endif
|
||||
|
||||
static void pm_line_sec_counters_total(int fd, DSL_XTUDir_t direction) {
|
||||
IOCTL_DIR(DSL_PM_LineSecCountersTotal_t, DSL_FIO_PM_LINE_SEC_COUNTERS_TOTAL_GET, direction)
|
||||
|
||||
@ -685,6 +792,21 @@ static void pm_line_sec_counters_total(int fd, DSL_XTUDir_t direction) {
|
||||
#endif
|
||||
}
|
||||
|
||||
static void pm_retx_counters_total(int fd, DSL_XTUDir_t direction) {
|
||||
#ifdef INCLUDE_DSL_CPE_PM_RETX_COUNTERS
|
||||
IOCTL_DIR(DSL_PM_ReTxCountersTotal_t, DSL_FIO_PM_RETX_COUNTERS_TOTAL_GET, direction);
|
||||
|
||||
m_u32("leftrs", out.data.nLeftr);
|
||||
#endif
|
||||
}
|
||||
|
||||
static void pm_channel_counters_total(int fd, DSL_XTUDir_t direction) {
|
||||
IOCTL_DIR(DSL_PM_ChannelCountersTotal_t, DSL_FIO_PM_CHANNEL_COUNTERS_TOTAL_GET, direction);
|
||||
|
||||
m_u32("cv_c", out.data.nCodeViolations);
|
||||
m_u32("fec_c", out.data.nFEC);
|
||||
}
|
||||
|
||||
static void pm_data_path_counters_total(int fd, DSL_XTUDir_t direction) {
|
||||
IOCTL_DIR(DSL_PM_DataPathCountersTotal_t, DSL_FIO_PM_DATA_PATH_COUNTERS_TOTAL_GET, direction);
|
||||
|
||||
@ -810,6 +932,17 @@ static int line_statistics(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
|
||||
blob_buf_init(&b, 0);
|
||||
|
||||
pilot_tones_status(fd);
|
||||
|
||||
c = blobmsg_open_table(&b, "bands");
|
||||
c2 = blobmsg_open_table(&b, "downstream");
|
||||
band_border_status(fd, DSL_DOWNSTREAM);
|
||||
blobmsg_close_table(&b, c2);
|
||||
c2 = blobmsg_open_table(&b, "upstream");
|
||||
band_border_status(fd, DSL_UPSTREAM);
|
||||
blobmsg_close_table(&b, c2);
|
||||
blobmsg_close_table(&b, c);
|
||||
|
||||
c = blobmsg_open_table(&b, "bits");
|
||||
c2 = blobmsg_open_table(&b, "downstream");
|
||||
g977_get_bit_allocation(fd, DSL_DOWNSTREAM);
|
||||
@ -862,6 +995,7 @@ static int metrics(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
standard_t standard = STD_UNKNOWN;
|
||||
profile_t profile = PROFILE_UNKNOWN;
|
||||
vector_t vector = VECTOR_UNKNOWN;
|
||||
bool retx_up = false, retx_down = false;
|
||||
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
fd = open(DSL_CPE_DEVICE_NAME "/0", O_RDWR, 0644);
|
||||
@ -908,9 +1042,12 @@ static int metrics(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
default:
|
||||
break;
|
||||
};
|
||||
line_feature_config(fd, DSL_UPSTREAM);
|
||||
line_feature_config(fd, DSL_UPSTREAM, &retx_up);
|
||||
g997_rate_adaptation_status(fd, DSL_UPSTREAM);
|
||||
g997_channel_status(fd, DSL_UPSTREAM);
|
||||
g997_line_status(fd, DSL_UPSTREAM);
|
||||
if (retx_up)
|
||||
pm_retx_counters_showtime(fd, DSL_FAR_END);
|
||||
blobmsg_close_table(&b, c);
|
||||
|
||||
c = blobmsg_open_table(&b, "downstream");
|
||||
@ -925,20 +1062,40 @@ static int metrics(struct ubus_context *ctx, struct ubus_object *obj,
|
||||
default:
|
||||
break;
|
||||
};
|
||||
line_feature_config(fd, DSL_DOWNSTREAM);
|
||||
line_feature_config(fd, DSL_DOWNSTREAM, &retx_down);
|
||||
g997_rate_adaptation_status(fd, DSL_DOWNSTREAM);
|
||||
g997_channel_status(fd, DSL_DOWNSTREAM);
|
||||
g997_line_status(fd, DSL_DOWNSTREAM);
|
||||
if (retx_down)
|
||||
pm_retx_counters_showtime(fd, DSL_NEAR_END);
|
||||
blobmsg_close_table(&b, c);
|
||||
|
||||
#ifndef INCLUDE_DSL_CPE_API_DANUBE
|
||||
c = blobmsg_open_table(&b, "olr");
|
||||
c2 = blobmsg_open_table(&b, "downstream");
|
||||
olr_statistics(fd, DSL_DOWNSTREAM);
|
||||
blobmsg_close_table(&b, c2);
|
||||
c2 = blobmsg_open_table(&b, "upstream");
|
||||
olr_statistics(fd, DSL_UPSTREAM);
|
||||
blobmsg_close_table(&b, c2);
|
||||
blobmsg_close_table(&b, c);
|
||||
#endif
|
||||
|
||||
c = blobmsg_open_table(&b, "errors");
|
||||
c2 = blobmsg_open_table(&b, "near");
|
||||
pm_line_sec_counters_total(fd, DSL_NEAR_END);
|
||||
if (retx_down)
|
||||
pm_retx_counters_total(fd, DSL_NEAR_END);
|
||||
pm_channel_counters_total(fd, DSL_NEAR_END);
|
||||
pm_data_path_counters_total(fd, DSL_NEAR_END);
|
||||
retx_statistics(fd, DSL_NEAR_END);
|
||||
blobmsg_close_table(&b, c2);
|
||||
|
||||
c2 = blobmsg_open_table(&b, "far");
|
||||
pm_line_sec_counters_total(fd, DSL_FAR_END);
|
||||
if (retx_up)
|
||||
pm_retx_counters_total(fd, DSL_FAR_END);
|
||||
pm_channel_counters_total(fd, DSL_FAR_END);
|
||||
pm_data_path_counters_total(fd, DSL_FAR_END);
|
||||
retx_statistics(fd, DSL_FAR_END);
|
||||
blobmsg_close_table(&b, c2);
|
||||
|
||||
@ -12,9 +12,9 @@ PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL=$(PROJECT_GIT)/project/fstools.git
|
||||
PKG_MIRROR_HASH:=edda9151c73c1adfe369f5e315347344727a540ad57d3e2b41b9f57f9d4313fe
|
||||
PKG_SOURCE_DATE:=2023-01-22
|
||||
PKG_SOURCE_VERSION:=1ea5855e980cd88766dd9f615e78e7dd6edfbb74
|
||||
PKG_MIRROR_HASH:=d2fc78b66c4e6ac5f51c77f92bd0d2322db78905a9dfea582fc7d975ea68ffe4
|
||||
PKG_SOURCE_DATE:=2023-02-04
|
||||
PKG_SOURCE_VERSION:=14d535e4485dc030deecbba9ab493c379df5c237
|
||||
CMAKE_INSTALL:=1
|
||||
|
||||
PKG_LICENSE:=GPL-2.0
|
||||
|
||||
@ -7,7 +7,7 @@ PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_URL=$(PROJECT_GIT)/project/ubus.git
|
||||
PKG_SOURCE_DATE:=2022-06-15
|
||||
PKG_SOURCE_VERSION:=9913aa61de739e3efe067a2d186021c20bcd65e2
|
||||
PKG_MIRROR_HASH:=2a9fd9e895835b15948ab211963b7489f8437cd1b2bf43e0e321bc960e105774
|
||||
PKG_MIRROR_HASH:=f6702e68d7c60388c11f40ca5ca8e932d0bf423325db5bee2c79404782bbcb52
|
||||
PKG_ABI_VERSION:=$(call abi_version_str,$(PKG_SOURCE_DATE))
|
||||
CMAKE_INSTALL:=1
|
||||
|
||||
|
||||
@ -158,7 +158,8 @@ parse_args() {
|
||||
return 1
|
||||
}
|
||||
[ -n "$o_subtarget" ] || o_subtarget="generic"
|
||||
o_bindir="bin/targets/$o_target/$o_subtarget"
|
||||
eval "$(grep ^CONFIG_BINARY_FOLDER= .config 2>/dev/null)"
|
||||
o_bindir="${CONFIG_BINARY_FOLDER:-bin}/targets/$o_target/$o_subtarget"
|
||||
}
|
||||
|
||||
start_qemu_armvirt() {
|
||||
|
||||
@ -21,18 +21,21 @@
|
||||
### -p --package-size Check IPK package size and not installed size
|
||||
### -h --help This message
|
||||
|
||||
CONFIG_TARGET=$(sed -n 's/^CONFIG_TARGET_BOARD="\(.*\)"$/\1/p' .config)
|
||||
CONFIG_SUBTARGET=$(sed -n 's/^CONFIG_TARGET_SUBTARGET="\(.*\)"$/\1/p' .config)
|
||||
CONFIG_ARCH=$(sed -n 's/^CONFIG_TARGET_ARCH_PACKAGES="\(.*\)"$/\1/p' .config)
|
||||
eval "$(grep \
|
||||
-e ^CONFIG_TARGET_BOARD= \
|
||||
-e ^CONFIG_TARGET_SUBTARGET= \
|
||||
-e ^CONFIG_TARGET_ARCH_PACKAGES= \
|
||||
-e ^CONFIG_BINARY_FOLDER= \
|
||||
.config 2>/dev/null \
|
||||
)"
|
||||
CONFIG_PACKAGES=$(sed -n 's/^CONFIG_PACKAGE_\(.*\)=y$/\1/p' .config | tr '\n' ' ')
|
||||
CONFIG_BIN_DIR=$(sed -n 's/^CONFIG_BINARY_DIR="\(.*\)"$/\1/p' .config)
|
||||
|
||||
TARGET=${TARGET:-$CONFIG_TARGET}
|
||||
SUBTARGET=${SUBTARGET:-$CONFIG_SUBTARGET}
|
||||
ARCH=${ARCH:-$CONFIG_ARCH}
|
||||
TARGET=${TARGET:-$CONFIG_TARGET_BOARD}
|
||||
SUBTARGET=${SUBTARGET:-$CONFIG_TARGET_SUBTARGET}
|
||||
ARCH=${ARCH:-$CONFIG_TARGET_ARCH_PACKAGES}
|
||||
PACKAGES=${PACKAGES:-$CONFIG_PACKAGES}
|
||||
BIN_DIR=${CONFIG_BIN_DIR:-./bin}
|
||||
BASE_URL="${BASE_URL:-https://downloads.immortalwrt.org/snapshots}"
|
||||
BIN_DIR=${CONFIG_BINARY_FOLDER:-./bin}
|
||||
BASE_URL="${BASE_URL:-https://downloads.openwrt.org/snapshots}"
|
||||
CHECK_INSTALLED="${CHECK_INSTALLED:-y}"
|
||||
|
||||
TARGET_URL="$BASE_URL/targets/$TARGET/$SUBTARGET/packages/Packages.gz"
|
||||
@ -72,6 +75,7 @@ package_size () {
|
||||
}
|
||||
|
||||
compare_sizes () {
|
||||
TOTAL_DIFF="0"
|
||||
for PACKAGE in $PACKAGES; do
|
||||
if [ "$PACKAGE" = "libc" ]; then
|
||||
continue
|
||||
@ -89,7 +93,8 @@ compare_sizes () {
|
||||
SIZE_LOCAL=$(tar tzvf "$PACKAGE_FILE" ./data.tar.gz | awk '{ print $3 }')
|
||||
fi
|
||||
SIZE_UPSTREAM=$(package_size "$TMP_INDEX" "$PACKAGE")
|
||||
SIZE_DIFF="$((SIZE_LOCAL-SIZE_UPSTREAM))"
|
||||
SIZE_DIFF="$((SIZE_LOCAL - SIZE_UPSTREAM))"
|
||||
TOTAL_DIFF="$((TOTAL_DIFF + SIZE_DIFF))"
|
||||
if [ "$SIZE_DIFF" -gt 0 ]; then
|
||||
SIZE_DIFF="+$SIZE_DIFF"
|
||||
fi
|
||||
@ -99,6 +104,7 @@ compare_sizes () {
|
||||
echo "$PACKAGE is missing upstream"
|
||||
fi
|
||||
done
|
||||
echo "~~~~~~~ total change ${TOTAL_DIFF}"
|
||||
}
|
||||
|
||||
if [ "$1" = "-h" ]; then
|
||||
|
||||
@ -1,10 +1,8 @@
|
||||
config AT91_DFBOOT
|
||||
bool "Build dataflashboot loader"
|
||||
depends on TARGET_at91
|
||||
default n
|
||||
|
||||
config FLEXIBITY_ROOT
|
||||
bool "Build Flexibity RootFS (with embedded kernel)"
|
||||
depends on TARGET_at91_flexibity
|
||||
default n
|
||||
|
||||
|
||||
@ -49,7 +49,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
#ifdef CONFIG_MACB_USE_HWSTAMP
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -3831,15 +3831,15 @@ static int macb_init(struct platform_dev
|
||||
@@ -3824,15 +3824,15 @@ static int macb_init(struct platform_dev
|
||||
if (!(bp->caps & MACB_CAPS_USRIO_DISABLED)) {
|
||||
val = 0;
|
||||
if (phy_interface_mode_is_rgmii(bp->phy_interface))
|
||||
@ -69,7 +69,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
macb_or_gem_writel(bp, USRIO, val);
|
||||
}
|
||||
@@ -4357,6 +4357,13 @@ static int fu540_c000_init(struct platfo
|
||||
@@ -4350,6 +4350,13 @@ static int fu540_c000_init(struct platfo
|
||||
return macb_init(pdev);
|
||||
}
|
||||
|
||||
@ -83,7 +83,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static const struct macb_config fu540_c000_config = {
|
||||
.caps = MACB_CAPS_GIGABIT_MODE_AVAILABLE | MACB_CAPS_JUMBO |
|
||||
MACB_CAPS_GEM_HAS_PTP,
|
||||
@@ -4364,12 +4371,14 @@ static const struct macb_config fu540_c0
|
||||
@@ -4357,12 +4364,14 @@ static const struct macb_config fu540_c0
|
||||
.clk_init = fu540_c000_clk_init,
|
||||
.init = fu540_c000_init,
|
||||
.jumbo_max_len = 10240,
|
||||
@ -98,7 +98,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config sama5d3macb_config = {
|
||||
@@ -4377,6 +4386,7 @@ static const struct macb_config sama5d3m
|
||||
@@ -4370,6 +4379,7 @@ static const struct macb_config sama5d3m
|
||||
| MACB_CAPS_USRIO_HAS_CLKEN | MACB_CAPS_USRIO_DEFAULT_IS_MII_GMII,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
@ -106,7 +106,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config pc302gem_config = {
|
||||
@@ -4384,6 +4394,7 @@ static const struct macb_config pc302gem
|
||||
@@ -4377,6 +4387,7 @@ static const struct macb_config pc302gem
|
||||
.dma_burst_length = 16,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
@ -114,7 +114,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config sama5d2_config = {
|
||||
@@ -4391,6 +4402,7 @@ static const struct macb_config sama5d2_
|
||||
@@ -4384,6 +4395,7 @@ static const struct macb_config sama5d2_
|
||||
.dma_burst_length = 16,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
@ -122,7 +122,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config sama5d3_config = {
|
||||
@@ -4400,6 +4412,7 @@ static const struct macb_config sama5d3_
|
||||
@@ -4393,6 +4405,7 @@ static const struct macb_config sama5d3_
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
.jumbo_max_len = 10240,
|
||||
@ -130,7 +130,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config sama5d4_config = {
|
||||
@@ -4407,18 +4420,21 @@ static const struct macb_config sama5d4_
|
||||
@@ -4400,18 +4413,21 @@ static const struct macb_config sama5d4_
|
||||
.dma_burst_length = 4,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
@ -152,7 +152,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config zynqmp_config = {
|
||||
@@ -4429,6 +4445,7 @@ static const struct macb_config zynqmp_c
|
||||
@@ -4422,6 +4438,7 @@ static const struct macb_config zynqmp_c
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
.jumbo_max_len = 10240,
|
||||
@ -160,7 +160,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct macb_config zynq_config = {
|
||||
@@ -4437,6 +4454,7 @@ static const struct macb_config zynq_con
|
||||
@@ -4430,6 +4447,7 @@ static const struct macb_config zynq_con
|
||||
.dma_burst_length = 16,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
@ -168,7 +168,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
};
|
||||
|
||||
static const struct of_device_id macb_dt_ids[] = {
|
||||
@@ -4557,6 +4575,8 @@ static int macb_probe(struct platform_de
|
||||
@@ -4550,6 +4568,8 @@ static int macb_probe(struct platform_de
|
||||
bp->wol |= MACB_WOL_HAS_MAGIC_PACKET;
|
||||
device_set_wakeup_capable(&pdev->dev, bp->wol & MACB_WOL_HAS_MAGIC_PACKET);
|
||||
|
||||
|
||||
@ -14,7 +14,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -3606,6 +3606,20 @@ static void macb_probe_queues(void __iom
|
||||
@@ -3599,6 +3599,20 @@ static void macb_probe_queues(void __iom
|
||||
*num_queues = hweight32(*queue_mask);
|
||||
}
|
||||
|
||||
@ -35,7 +35,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static int macb_clk_init(struct platform_device *pdev, struct clk **pclk,
|
||||
struct clk **hclk, struct clk **tx_clk,
|
||||
struct clk **rx_clk, struct clk **tsu_clk)
|
||||
@@ -4668,11 +4682,7 @@ err_out_free_netdev:
|
||||
@@ -4661,11 +4675,7 @@ err_out_free_netdev:
|
||||
free_netdev(dev);
|
||||
|
||||
err_disable_clocks:
|
||||
@ -48,7 +48,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
pm_runtime_set_suspended(&pdev->dev);
|
||||
pm_runtime_dont_use_autosuspend(&pdev->dev);
|
||||
@@ -4697,11 +4707,8 @@ static int macb_remove(struct platform_d
|
||||
@@ -4690,11 +4700,8 @@ static int macb_remove(struct platform_d
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
pm_runtime_dont_use_autosuspend(&pdev->dev);
|
||||
if (!pm_runtime_suspended(&pdev->dev)) {
|
||||
@ -62,7 +62,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
pm_runtime_set_suspended(&pdev->dev);
|
||||
}
|
||||
phylink_destroy(bp->phylink);
|
||||
@@ -4880,13 +4887,10 @@ static int __maybe_unused macb_runtime_s
|
||||
@@ -4873,13 +4880,10 @@ static int __maybe_unused macb_runtime_s
|
||||
struct net_device *netdev = dev_get_drvdata(dev);
|
||||
struct macb *bp = netdev_priv(netdev);
|
||||
|
||||
|
||||
@ -14,7 +14,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -4338,8 +4338,10 @@ static int fu540_c000_clk_init(struct pl
|
||||
@@ -4331,8 +4331,10 @@ static int fu540_c000_clk_init(struct pl
|
||||
return err;
|
||||
|
||||
mgmt = devm_kzalloc(&pdev->dev, sizeof(*mgmt), GFP_KERNEL);
|
||||
@ -27,7 +27,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
init.name = "sifive-gemgxl-mgmt";
|
||||
init.ops = &fu540_c000_ops;
|
||||
@@ -4350,16 +4352,26 @@ static int fu540_c000_clk_init(struct pl
|
||||
@@ -4343,16 +4345,26 @@ static int fu540_c000_clk_init(struct pl
|
||||
mgmt->hw.init = &init;
|
||||
|
||||
*tx_clk = devm_clk_register(&pdev->dev, &mgmt->hw);
|
||||
|
||||
@ -14,7 +14,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -4390,6 +4390,14 @@ static const struct macb_usrio_config ma
|
||||
@@ -4383,6 +4383,14 @@ static const struct macb_usrio_config ma
|
||||
.refclk = MACB_BIT(CLKEN),
|
||||
};
|
||||
|
||||
@ -29,7 +29,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static const struct macb_config fu540_c000_config = {
|
||||
.caps = MACB_CAPS_GIGABIT_MODE_AVAILABLE | MACB_CAPS_JUMBO |
|
||||
MACB_CAPS_GEM_HAS_PTP,
|
||||
@@ -4483,6 +4491,14 @@ static const struct macb_config zynq_con
|
||||
@@ -4476,6 +4484,14 @@ static const struct macb_config zynq_con
|
||||
.usrio = &macb_default_usrio,
|
||||
};
|
||||
|
||||
@ -44,7 +44,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static const struct of_device_id macb_dt_ids[] = {
|
||||
{ .compatible = "cdns,at32ap7000-macb" },
|
||||
{ .compatible = "cdns,at91sam9260-macb", .data = &at91sam9260_config },
|
||||
@@ -4500,6 +4516,7 @@ static const struct of_device_id macb_dt
|
||||
@@ -4493,6 +4509,7 @@ static const struct of_device_id macb_dt
|
||||
{ .compatible = "cdns,zynqmp-gem", .data = &zynqmp_config},
|
||||
{ .compatible = "cdns,zynq-gem", .data = &zynq_config },
|
||||
{ .compatible = "sifive,fu540-c000-gem", .data = &fu540_c000_config },
|
||||
|
||||
@ -14,7 +14,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -4499,6 +4499,14 @@ static const struct macb_config sama7g5_
|
||||
@@ -4492,6 +4492,14 @@ static const struct macb_config sama7g5_
|
||||
.usrio = &sama7g5_usrio,
|
||||
};
|
||||
|
||||
@ -29,7 +29,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static const struct of_device_id macb_dt_ids[] = {
|
||||
{ .compatible = "cdns,at32ap7000-macb" },
|
||||
{ .compatible = "cdns,at91sam9260-macb", .data = &at91sam9260_config },
|
||||
@@ -4517,6 +4525,7 @@ static const struct of_device_id macb_dt
|
||||
@@ -4510,6 +4518,7 @@ static const struct of_device_id macb_dt
|
||||
{ .compatible = "cdns,zynq-gem", .data = &zynq_config },
|
||||
{ .compatible = "sifive,fu540-c000-gem", .data = &fu540_c000_config },
|
||||
{ .compatible = "microchip,sama7g5-gem", .data = &sama7g5_gem_config },
|
||||
|
||||
@ -20,7 +20,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -3868,6 +3868,13 @@ static int macb_init(struct platform_dev
|
||||
@@ -3861,6 +3861,13 @@ static int macb_init(struct platform_dev
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -34,7 +34,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
#if defined(CONFIG_OF)
|
||||
/* 1518 rounded up */
|
||||
#define AT91ETHER_MAX_RBUFF_SZ 0x600
|
||||
@@ -4383,13 +4390,6 @@ static int fu540_c000_init(struct platfo
|
||||
@@ -4376,13 +4383,6 @@ static int fu540_c000_init(struct platfo
|
||||
return macb_init(pdev);
|
||||
}
|
||||
|
||||
@ -48,7 +48,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
static const struct macb_usrio_config sama7g5_usrio = {
|
||||
.mii = 0,
|
||||
.rmii = 1,
|
||||
@@ -4538,6 +4538,7 @@ static const struct macb_config default_
|
||||
@@ -4531,6 +4531,7 @@ static const struct macb_config default_
|
||||
.dma_burst_length = 16,
|
||||
.clk_init = macb_clk_init,
|
||||
.init = macb_init,
|
||||
|
||||
@ -7,7 +7,7 @@ include $(TOPDIR)/rules.mk
|
||||
ARCH:=mips
|
||||
BOARD:=ath25
|
||||
BOARDNAME:=Atheros AR231x/AR5312
|
||||
FEATURES:=squashfs low_mem small_flash
|
||||
FEATURES:=squashfs low_mem small_flash source-only
|
||||
SUBTARGETS:=generic
|
||||
|
||||
KERNEL_PATCHVER:=5.10
|
||||
|
||||
@ -10,14 +10,12 @@ if AG71XX
|
||||
|
||||
config AG71XX_DEBUG
|
||||
bool "Atheros AR71xx built-in ethernet driver debugging"
|
||||
default n
|
||||
help
|
||||
Atheros AR71xx built-in ethernet driver debugging messages.
|
||||
|
||||
config AG71XX_DEBUG_FS
|
||||
bool "Atheros AR71xx built-in ethernet driver debugfs support"
|
||||
depends on DEBUG_FS
|
||||
default n
|
||||
help
|
||||
Say Y, if you need access to various statistics provided by
|
||||
the ag71xx driver.
|
||||
|
||||
@ -13,7 +13,7 @@ Signed-off-by: Phil Elwell <phil@raspberrypi.org>
|
||||
|
||||
--- a/drivers/spi/spidev.c
|
||||
+++ b/drivers/spi/spidev.c
|
||||
@@ -761,7 +761,7 @@ static int spidev_probe(struct spi_devic
|
||||
@@ -759,7 +759,7 @@ static int spidev_probe(struct spi_devic
|
||||
* compatible string, it is a Linux implementation thing
|
||||
* rather than a description of the hardware.
|
||||
*/
|
||||
|
||||
@ -33,7 +33,7 @@ Signed-off-by: Jonathan Bell <jonathan@raspberrypi.org>
|
||||
#define USB_VENDOR_ID_BELKIN 0x050d
|
||||
#define USB_DEVICE_ID_FLIP_KVM 0x3201
|
||||
|
||||
@@ -1316,6 +1319,9 @@
|
||||
@@ -1315,6 +1318,9 @@
|
||||
#define USB_VENDOR_ID_XAT 0x2505
|
||||
#define USB_DEVICE_ID_XAT_CSR 0x0220
|
||||
|
||||
@ -53,7 +53,7 @@ Signed-off-by: Jonathan Bell <jonathan@raspberrypi.org>
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_MULTI_TOUCH), HID_QUIRK_MULTI_INPUT },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_PIXART_USB_OPTICAL_MOUSE), HID_QUIRK_ALWAYS_POLL },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_CHICONY, USB_DEVICE_ID_CHICONY_PIXART_USB_OPTICAL_MOUSE2), HID_QUIRK_ALWAYS_POLL },
|
||||
@@ -198,6 +199,7 @@ static const struct hid_device_id hid_qu
|
||||
@@ -197,6 +198,7 @@ static const struct hid_device_id hid_qu
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_WISEGROUP, USB_DEVICE_ID_QUAD_USB_JOYPAD), HID_QUIRK_NOGET | HID_QUIRK_MULTI_INPUT },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_XIN_MO, USB_DEVICE_ID_XIN_MO_DUAL_ARCADE), HID_QUIRK_MULTI_INPUT },
|
||||
{ HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_GROUP_AUDIO), HID_QUIRK_NOGET },
|
||||
|
||||
@ -15,7 +15,7 @@ Signed-off-by: Phil Elwell <phil@raspberrypi.com>
|
||||
|
||||
--- a/drivers/spi/spidev.c
|
||||
+++ b/drivers/spi/spidev.c
|
||||
@@ -680,6 +680,7 @@ static const struct file_operations spid
|
||||
@@ -678,6 +678,7 @@ static const struct file_operations spid
|
||||
static struct class *spidev_class;
|
||||
|
||||
static const struct spi_device_id spidev_spi_ids[] = {
|
||||
|
||||
@ -11,6 +11,7 @@ FEATURES:=squashfs usb
|
||||
SUBTARGETS:=generic mips74k legacy
|
||||
|
||||
KERNEL_PATCHVER:=5.10
|
||||
KERNEL_TESTING_PATCHVER:=5.15
|
||||
|
||||
define Target/Description
|
||||
Build firmware images for Broadcom based BCM47xx/53xx routers with MIPS CPU, *not* ARM.
|
||||
|
||||
177
target/linux/bcm47xx/config-5.15
Normal file
177
target/linux/bcm47xx/config-5.15
Normal file
@ -0,0 +1,177 @@
|
||||
CONFIG_ADM6996_PHY=y
|
||||
CONFIG_ARCH_32BIT_OFF_T=y
|
||||
CONFIG_ARCH_HIBERNATION_POSSIBLE=y
|
||||
CONFIG_ARCH_KEEP_MEMBLOCK=y
|
||||
CONFIG_ARCH_MMAP_RND_BITS_MAX=15
|
||||
CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15
|
||||
CONFIG_ARCH_SUSPEND_POSSIBLE=y
|
||||
CONFIG_BCM47XX=y
|
||||
CONFIG_BCM47XX_BCMA=y
|
||||
CONFIG_BCM47XX_NVRAM=y
|
||||
CONFIG_BCM47XX_SPROM=y
|
||||
CONFIG_BCM47XX_SSB=y
|
||||
CONFIG_BCM47XX_WDT=y
|
||||
CONFIG_BCMA=y
|
||||
CONFIG_BCMA_BLOCKIO=y
|
||||
CONFIG_BCMA_DEBUG=y
|
||||
CONFIG_BCMA_DRIVER_GMAC_CMN=y
|
||||
CONFIG_BCMA_DRIVER_GPIO=y
|
||||
CONFIG_BCMA_DRIVER_MIPS=y
|
||||
CONFIG_BCMA_DRIVER_PCI=y
|
||||
CONFIG_BCMA_DRIVER_PCI_HOSTMODE=y
|
||||
CONFIG_BCMA_HOST_PCI=y
|
||||
CONFIG_BCMA_HOST_PCI_POSSIBLE=y
|
||||
CONFIG_BCMA_HOST_SOC=y
|
||||
CONFIG_BCMA_NFLASH=y
|
||||
CONFIG_BCMA_PFLASH=y
|
||||
CONFIG_BCMA_SFLASH=y
|
||||
# CONFIG_BGMAC_BCMA is not set
|
||||
CONFIG_BLK_MQ_PCI=y
|
||||
CONFIG_CEVT_R4K=y
|
||||
CONFIG_CLONE_BACKWARDS=y
|
||||
CONFIG_CMDLINE="noinitrd console=ttyS0,115200"
|
||||
CONFIG_CMDLINE_BOOL=y
|
||||
# CONFIG_CMDLINE_OVERRIDE is not set
|
||||
# CONFIG_COMMON_CLK is not set
|
||||
CONFIG_COMPAT_32BIT_TIME=y
|
||||
# CONFIG_CPU_BMIPS is not set
|
||||
CONFIG_CPU_GENERIC_DUMP_TLB=y
|
||||
CONFIG_CPU_HAS_PREFETCH=y
|
||||
CONFIG_CPU_HAS_SYNC=y
|
||||
CONFIG_CPU_LITTLE_ENDIAN=y
|
||||
CONFIG_CPU_MIPS32=y
|
||||
CONFIG_CPU_MIPS32_R1=y
|
||||
# CONFIG_CPU_MIPS32_R2 is not set
|
||||
CONFIG_CPU_MIPSR1=y
|
||||
CONFIG_CPU_MIPSR2_IRQ_VI=y
|
||||
CONFIG_CPU_NEEDS_NO_SMARTMIPS_OR_MICROMIPS=y
|
||||
CONFIG_CPU_R4K_CACHE_TLB=y
|
||||
CONFIG_CPU_SUPPORTS_32BIT_KERNEL=y
|
||||
CONFIG_CPU_SUPPORTS_HIGHMEM=y
|
||||
CONFIG_CRYPTO_LIB_BLAKE2S_GENERIC=y
|
||||
CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2
|
||||
CONFIG_CRYPTO_RNG2=y
|
||||
CONFIG_CSRC_R4K=y
|
||||
CONFIG_DMA_NONCOHERENT=y
|
||||
# CONFIG_EARLY_PRINTK is not set
|
||||
CONFIG_FIXED_PHY=y
|
||||
CONFIG_FW_LOADER_PAGED_BUF=y
|
||||
CONFIG_GENERIC_ATOMIC64=y
|
||||
CONFIG_GENERIC_CLOCKEVENTS=y
|
||||
CONFIG_GENERIC_CMOS_UPDATE=y
|
||||
CONFIG_GENERIC_CPU_AUTOPROBE=y
|
||||
CONFIG_GENERIC_FIND_FIRST_BIT=y
|
||||
CONFIG_GENERIC_GETTIMEOFDAY=y
|
||||
CONFIG_GENERIC_IOMAP=y
|
||||
CONFIG_GENERIC_IRQ_CHIP=y
|
||||
CONFIG_GENERIC_IRQ_EFFECTIVE_AFF_MASK=y
|
||||
CONFIG_GENERIC_IRQ_SHOW=y
|
||||
CONFIG_GENERIC_LIB_ASHLDI3=y
|
||||
CONFIG_GENERIC_LIB_ASHRDI3=y
|
||||
CONFIG_GENERIC_LIB_CMPDI2=y
|
||||
CONFIG_GENERIC_LIB_LSHRDI3=y
|
||||
CONFIG_GENERIC_LIB_UCMPDI2=y
|
||||
CONFIG_GENERIC_PCI_IOMAP=y
|
||||
CONFIG_GENERIC_SCHED_CLOCK=y
|
||||
CONFIG_GENERIC_SMP_IDLE_THREAD=y
|
||||
CONFIG_GENERIC_TIME_VSYSCALL=y
|
||||
CONFIG_GPIOLIB_IRQCHIP=y
|
||||
CONFIG_GPIO_CDEV=y
|
||||
CONFIG_GPIO_WDT=y
|
||||
CONFIG_HANDLE_DOMAIN_IRQ=y
|
||||
CONFIG_HARDWARE_WATCHPOINTS=y
|
||||
CONFIG_HAS_DMA=y
|
||||
CONFIG_HAS_IOMEM=y
|
||||
CONFIG_HAS_IOPORT_MAP=y
|
||||
CONFIG_HW_RANDOM=y
|
||||
CONFIG_HZ_PERIODIC=y
|
||||
CONFIG_INITRAMFS_SOURCE=""
|
||||
CONFIG_IRQ_DOMAIN=y
|
||||
CONFIG_IRQ_FORCED_THREADING=y
|
||||
CONFIG_IRQ_MIPS_CPU=y
|
||||
CONFIG_IRQ_WORK=y
|
||||
CONFIG_LEDS_GPIO_REGISTER=y
|
||||
CONFIG_LOCK_DEBUGGING_SUPPORT=y
|
||||
CONFIG_MDIO_BUS=y
|
||||
CONFIG_MDIO_DEVICE=y
|
||||
CONFIG_MDIO_DEVRES=y
|
||||
CONFIG_MEMFD_CREATE=y
|
||||
CONFIG_MIGRATION=y
|
||||
CONFIG_MIPS=y
|
||||
CONFIG_MIPS_ASID_BITS=8
|
||||
CONFIG_MIPS_ASID_SHIFT=0
|
||||
CONFIG_MIPS_CLOCK_VSYSCALL=y
|
||||
# CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set
|
||||
CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER=y
|
||||
CONFIG_MIPS_EBPF_JIT=y
|
||||
CONFIG_MIPS_L1_CACHE_SHIFT=5
|
||||
CONFIG_MIPS_LD_CAN_LINK_VDSO=y
|
||||
CONFIG_MODULES_USE_ELF_REL=y
|
||||
CONFIG_MTD_BCM47XXSFLASH=y
|
||||
CONFIG_MTD_BCM47XX_PARTS=y
|
||||
CONFIG_MTD_NAND_BCM47XXNFLASH=y
|
||||
CONFIG_MTD_NAND_BRCMNAND=y
|
||||
CONFIG_MTD_NAND_BRCMNAND_BCMA=y
|
||||
CONFIG_MTD_NAND_CORE=y
|
||||
CONFIG_MTD_NAND_ECC=y
|
||||
CONFIG_MTD_PARSER_TRX=y
|
||||
CONFIG_MTD_PHYSMAP=y
|
||||
CONFIG_MTD_RAW_NAND=y
|
||||
CONFIG_NEED_DMA_MAP_STATE=y
|
||||
CONFIG_NEED_PER_CPU_KM=y
|
||||
CONFIG_NET_SELFTESTS=y
|
||||
CONFIG_NO_EXCEPT_FILL=y
|
||||
CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y
|
||||
# CONFIG_OF is not set
|
||||
CONFIG_PCI=y
|
||||
CONFIG_PCI_DISABLE_COMMON_QUIRKS=y
|
||||
CONFIG_PCI_DOMAINS=y
|
||||
CONFIG_PCI_DRIVERS_LEGACY=y
|
||||
CONFIG_PERF_USE_VMALLOC=y
|
||||
CONFIG_PGTABLE_LEVELS=2
|
||||
CONFIG_PHYLIB=y
|
||||
CONFIG_PTP_1588_CLOCK_OPTIONAL=y
|
||||
CONFIG_SERIAL_8250_EXTENDED=y
|
||||
CONFIG_SERIAL_8250_SHARE_IRQ=y
|
||||
CONFIG_SERIAL_MCTRL_GPIO=y
|
||||
CONFIG_SRCU=y
|
||||
CONFIG_SSB=y
|
||||
CONFIG_SSB_B43_PCI_BRIDGE=y
|
||||
CONFIG_SSB_BLOCKIO=y
|
||||
CONFIG_SSB_DRIVER_EXTIF=y
|
||||
CONFIG_SSB_DRIVER_GIGE=y
|
||||
CONFIG_SSB_DRIVER_GPIO=y
|
||||
CONFIG_SSB_DRIVER_MIPS=y
|
||||
CONFIG_SSB_DRIVER_PCICORE=y
|
||||
CONFIG_SSB_DRIVER_PCICORE_POSSIBLE=y
|
||||
CONFIG_SSB_EMBEDDED=y
|
||||
CONFIG_SSB_HOST_SOC=y
|
||||
CONFIG_SSB_PCICORE_HOSTMODE=y
|
||||
CONFIG_SSB_PCIHOST=y
|
||||
CONFIG_SSB_PCIHOST_POSSIBLE=y
|
||||
CONFIG_SSB_SERIAL=y
|
||||
CONFIG_SSB_SFLASH=y
|
||||
CONFIG_SSB_SPROM=y
|
||||
CONFIG_SWCONFIG=y
|
||||
CONFIG_SWCONFIG_B53=y
|
||||
CONFIG_SWCONFIG_B53_PHY_DRIVER=y
|
||||
CONFIG_SWCONFIG_B53_PHY_FIXUP=y
|
||||
CONFIG_SWPHY=y
|
||||
CONFIG_SYSCTL_EXCEPTION_TRACE=y
|
||||
CONFIG_SYS_HAS_CPU_BMIPS=y
|
||||
CONFIG_SYS_HAS_CPU_BMIPS32_3300=y
|
||||
CONFIG_SYS_HAS_CPU_MIPS32_R1=y
|
||||
CONFIG_SYS_HAS_CPU_MIPS32_R2=y
|
||||
CONFIG_SYS_HAS_EARLY_PRINTK=y
|
||||
CONFIG_SYS_SUPPORTS_32BIT_KERNEL=y
|
||||
CONFIG_SYS_SUPPORTS_ARBIT_HZ=y
|
||||
CONFIG_SYS_SUPPORTS_HIGHMEM=y
|
||||
CONFIG_SYS_SUPPORTS_LITTLE_ENDIAN=y
|
||||
CONFIG_SYS_SUPPORTS_MIPS16=y
|
||||
CONFIG_SYS_SUPPORTS_ZBOOT=y
|
||||
CONFIG_TARGET_ISA_REV=1
|
||||
CONFIG_TICK_CPU_ACCOUNTING=y
|
||||
CONFIG_TINY_SRCU=y
|
||||
CONFIG_USB_SUPPORT=y
|
||||
CONFIG_USE_GENERIC_EARLY_PRINTK_8250=y
|
||||
CONFIG_WATCHDOG_CORE=y
|
||||
@ -0,0 +1,33 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 1/9] mtd: rawnand: brcmnand: Assign soc as early as possible
|
||||
Date: Fri, 07 Jan 2022 10:46:06 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
In order to key off the brcmnand_probe() code in subsequent changes
|
||||
depending upon ctrl->soc, assign that variable as early as possible,
|
||||
instead of much later when we have checked that it is non-NULL.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 3 +--
|
||||
1 file changed, 1 insertion(+), 2 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -2998,6 +2998,7 @@ int brcmnand_probe(struct platform_devic
|
||||
|
||||
dev_set_drvdata(dev, ctrl);
|
||||
ctrl->dev = dev;
|
||||
+ ctrl->soc = soc;
|
||||
|
||||
init_completion(&ctrl->done);
|
||||
init_completion(&ctrl->dma_done);
|
||||
@@ -3138,8 +3139,6 @@ int brcmnand_probe(struct platform_devic
|
||||
* interesting ways
|
||||
*/
|
||||
if (soc) {
|
||||
- ctrl->soc = soc;
|
||||
-
|
||||
ret = devm_request_irq(dev, ctrl->irq, brcmnand_irq, 0,
|
||||
DRV_NAME, ctrl);
|
||||
|
||||
@ -0,0 +1,150 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 2/9] mtd: rawnand: brcmnand: Allow SoC to provide I/O operations
|
||||
Date: Fri, 07 Jan 2022 10:46:07 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
Allow a brcmnand_soc instance to provide a custom set of I/O operations
|
||||
which we will require when using this driver on a BCMA bus which is not
|
||||
directly memory mapped I/O. Update the nand_{read,write}_reg accordingly
|
||||
to use the SoC operations if provided.
|
||||
|
||||
To minimize the penalty on other SoCs which do support standard MMIO
|
||||
accesses, we use a static key which is disabled by default and gets
|
||||
enabled if a soc implementation does provide I/O operations.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 28 +++++++++++++++++++++--
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.h | 29 ++++++++++++++++++++++++
|
||||
2 files changed, 55 insertions(+), 2 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -25,6 +25,7 @@
|
||||
#include <linux/of.h>
|
||||
#include <linux/of_platform.h>
|
||||
#include <linux/slab.h>
|
||||
+#include <linux/static_key.h>
|
||||
#include <linux/list.h>
|
||||
#include <linux/log2.h>
|
||||
|
||||
@@ -207,6 +208,8 @@ enum {
|
||||
|
||||
struct brcmnand_host;
|
||||
|
||||
+static DEFINE_STATIC_KEY_FALSE(brcmnand_soc_has_ops_key);
|
||||
+
|
||||
struct brcmnand_controller {
|
||||
struct device *dev;
|
||||
struct nand_controller controller;
|
||||
@@ -592,15 +595,25 @@ enum {
|
||||
INTFC_CTLR_READY = BIT(31),
|
||||
};
|
||||
|
||||
+static inline bool brcmnand_non_mmio_ops(struct brcmnand_controller *ctrl)
|
||||
+{
|
||||
+ return static_branch_unlikely(&brcmnand_soc_has_ops_key);
|
||||
+}
|
||||
+
|
||||
static inline u32 nand_readreg(struct brcmnand_controller *ctrl, u32 offs)
|
||||
{
|
||||
+ if (brcmnand_non_mmio_ops(ctrl))
|
||||
+ return brcmnand_soc_read(ctrl->soc, offs);
|
||||
return brcmnand_readl(ctrl->nand_base + offs);
|
||||
}
|
||||
|
||||
static inline void nand_writereg(struct brcmnand_controller *ctrl, u32 offs,
|
||||
u32 val)
|
||||
{
|
||||
- brcmnand_writel(val, ctrl->nand_base + offs);
|
||||
+ if (brcmnand_non_mmio_ops(ctrl))
|
||||
+ brcmnand_soc_write(ctrl->soc, val, offs);
|
||||
+ else
|
||||
+ brcmnand_writel(val, ctrl->nand_base + offs);
|
||||
}
|
||||
|
||||
static int brcmnand_revision_init(struct brcmnand_controller *ctrl)
|
||||
@@ -766,13 +779,18 @@ static inline void brcmnand_rmw_reg(stru
|
||||
|
||||
static inline u32 brcmnand_read_fc(struct brcmnand_controller *ctrl, int word)
|
||||
{
|
||||
+ if (brcmnand_non_mmio_ops(ctrl))
|
||||
+ return brcmnand_soc_read(ctrl->soc, BRCMNAND_NON_MMIO_FC_ADDR);
|
||||
return __raw_readl(ctrl->nand_fc + word * 4);
|
||||
}
|
||||
|
||||
static inline void brcmnand_write_fc(struct brcmnand_controller *ctrl,
|
||||
int word, u32 val)
|
||||
{
|
||||
- __raw_writel(val, ctrl->nand_fc + word * 4);
|
||||
+ if (brcmnand_non_mmio_ops(ctrl))
|
||||
+ brcmnand_soc_write(ctrl->soc, val, BRCMNAND_NON_MMIO_FC_ADDR);
|
||||
+ else
|
||||
+ __raw_writel(val, ctrl->nand_fc + word * 4);
|
||||
}
|
||||
|
||||
static inline void edu_writel(struct brcmnand_controller *ctrl,
|
||||
@@ -3000,6 +3018,12 @@ int brcmnand_probe(struct platform_devic
|
||||
ctrl->dev = dev;
|
||||
ctrl->soc = soc;
|
||||
|
||||
+ /* Enable the static key if the soc provides I/O operations indicating
|
||||
+ * that a non-memory mapped IO access path must be used
|
||||
+ */
|
||||
+ if (brcmnand_soc_has_ops(ctrl->soc))
|
||||
+ static_branch_enable(&brcmnand_soc_has_ops_key);
|
||||
+
|
||||
init_completion(&ctrl->done);
|
||||
init_completion(&ctrl->dma_done);
|
||||
init_completion(&ctrl->edu_done);
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.h
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.h
|
||||
@@ -11,12 +11,25 @@
|
||||
|
||||
struct platform_device;
|
||||
struct dev_pm_ops;
|
||||
+struct brcmnand_io_ops;
|
||||
+
|
||||
+/* Special register offset constant to intercept a non-MMIO access
|
||||
+ * to the flash cache register space. This is intentionally large
|
||||
+ * not to overlap with an existing offset.
|
||||
+ */
|
||||
+#define BRCMNAND_NON_MMIO_FC_ADDR 0xffffffff
|
||||
|
||||
struct brcmnand_soc {
|
||||
bool (*ctlrdy_ack)(struct brcmnand_soc *soc);
|
||||
void (*ctlrdy_set_enabled)(struct brcmnand_soc *soc, bool en);
|
||||
void (*prepare_data_bus)(struct brcmnand_soc *soc, bool prepare,
|
||||
bool is_param);
|
||||
+ const struct brcmnand_io_ops *ops;
|
||||
+};
|
||||
+
|
||||
+struct brcmnand_io_ops {
|
||||
+ u32 (*read_reg)(struct brcmnand_soc *soc, u32 offset);
|
||||
+ void (*write_reg)(struct brcmnand_soc *soc, u32 val, u32 offset);
|
||||
};
|
||||
|
||||
static inline void brcmnand_soc_data_bus_prepare(struct brcmnand_soc *soc,
|
||||
@@ -58,6 +71,22 @@ static inline void brcmnand_writel(u32 v
|
||||
writel_relaxed(val, addr);
|
||||
}
|
||||
|
||||
+static inline bool brcmnand_soc_has_ops(struct brcmnand_soc *soc)
|
||||
+{
|
||||
+ return soc && soc->ops && soc->ops->read_reg && soc->ops->write_reg;
|
||||
+}
|
||||
+
|
||||
+static inline u32 brcmnand_soc_read(struct brcmnand_soc *soc, u32 offset)
|
||||
+{
|
||||
+ return soc->ops->read_reg(soc, offset);
|
||||
+}
|
||||
+
|
||||
+static inline void brcmnand_soc_write(struct brcmnand_soc *soc, u32 val,
|
||||
+ u32 offset)
|
||||
+{
|
||||
+ soc->ops->write_reg(soc, val, offset);
|
||||
+}
|
||||
+
|
||||
int brcmnand_probe(struct platform_device *pdev, struct brcmnand_soc *soc);
|
||||
int brcmnand_remove(struct platform_device *pdev);
|
||||
|
||||
@ -0,0 +1,52 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 3/9] mtd: rawnand: brcmnand: Avoid pdev in brcmnand_init_cs()
|
||||
Date: Fri, 07 Jan 2022 10:46:08 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
In preparation for encapsulating more of what the loop calling
|
||||
brcmnand_init_cs() does, avoid using platform_device when it is the
|
||||
device behind platform_device that we are using for printing errors.
|
||||
|
||||
No functional changes introduced.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 8 ++++----
|
||||
1 file changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -2771,7 +2771,7 @@ static const struct nand_controller_ops
|
||||
static int brcmnand_init_cs(struct brcmnand_host *host, struct device_node *dn)
|
||||
{
|
||||
struct brcmnand_controller *ctrl = host->ctrl;
|
||||
- struct platform_device *pdev = host->pdev;
|
||||
+ struct device *dev = ctrl->dev;
|
||||
struct mtd_info *mtd;
|
||||
struct nand_chip *chip;
|
||||
int ret;
|
||||
@@ -2779,7 +2779,7 @@ static int brcmnand_init_cs(struct brcmn
|
||||
|
||||
ret = of_property_read_u32(dn, "reg", &host->cs);
|
||||
if (ret) {
|
||||
- dev_err(&pdev->dev, "can't get chip-select\n");
|
||||
+ dev_err(dev, "can't get chip-select\n");
|
||||
return -ENXIO;
|
||||
}
|
||||
|
||||
@@ -2788,13 +2788,13 @@ static int brcmnand_init_cs(struct brcmn
|
||||
|
||||
nand_set_flash_node(chip, dn);
|
||||
nand_set_controller_data(chip, host);
|
||||
- mtd->name = devm_kasprintf(&pdev->dev, GFP_KERNEL, "brcmnand.%d",
|
||||
+ mtd->name = devm_kasprintf(dev, GFP_KERNEL, "brcmnand.%d",
|
||||
host->cs);
|
||||
if (!mtd->name)
|
||||
return -ENOMEM;
|
||||
|
||||
mtd->owner = THIS_MODULE;
|
||||
- mtd->dev.parent = &pdev->dev;
|
||||
+ mtd->dev.parent = dev;
|
||||
|
||||
chip->legacy.cmd_ctrl = brcmnand_cmd_ctrl;
|
||||
chip->legacy.cmdfunc = brcmnand_cmdfunc;
|
||||
@ -0,0 +1,63 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 4/9] mtd: rawnand: brcmnand: Move OF operations out of brcmnand_init_cs()
|
||||
Date: Fri, 07 Jan 2022 10:46:09 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
In order to initialize a given chip select object for use by the
|
||||
brcmnand driver, move all of the Device Tree specific routines outside
|
||||
of brcmnand_init_cs() in order to make it usable in a platform data
|
||||
configuration which will be necessary for supporting BCMA chips.
|
||||
|
||||
No functional changes introduced.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 20 +++++++++++---------
|
||||
1 file changed, 11 insertions(+), 9 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -2768,7 +2768,7 @@ static const struct nand_controller_ops
|
||||
.attach_chip = brcmnand_attach_chip,
|
||||
};
|
||||
|
||||
-static int brcmnand_init_cs(struct brcmnand_host *host, struct device_node *dn)
|
||||
+static int brcmnand_init_cs(struct brcmnand_host *host)
|
||||
{
|
||||
struct brcmnand_controller *ctrl = host->ctrl;
|
||||
struct device *dev = ctrl->dev;
|
||||
@@ -2777,16 +2777,9 @@ static int brcmnand_init_cs(struct brcmn
|
||||
int ret;
|
||||
u16 cfg_offs;
|
||||
|
||||
- ret = of_property_read_u32(dn, "reg", &host->cs);
|
||||
- if (ret) {
|
||||
- dev_err(dev, "can't get chip-select\n");
|
||||
- return -ENXIO;
|
||||
- }
|
||||
-
|
||||
mtd = nand_to_mtd(&host->chip);
|
||||
chip = &host->chip;
|
||||
|
||||
- nand_set_flash_node(chip, dn);
|
||||
nand_set_controller_data(chip, host);
|
||||
mtd->name = devm_kasprintf(dev, GFP_KERNEL, "brcmnand.%d",
|
||||
host->cs);
|
||||
@@ -3193,7 +3186,16 @@ int brcmnand_probe(struct platform_devic
|
||||
host->pdev = pdev;
|
||||
host->ctrl = ctrl;
|
||||
|
||||
- ret = brcmnand_init_cs(host, child);
|
||||
+ ret = of_property_read_u32(child, "reg", &host->cs);
|
||||
+ if (ret) {
|
||||
+ dev_err(dev, "can't get chip-select\n");
|
||||
+ devm_kfree(dev, host);
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
+ nand_set_flash_node(&host->chip, child);
|
||||
+
|
||||
+ ret = brcmnand_init_cs(host);
|
||||
if (ret) {
|
||||
devm_kfree(dev, host);
|
||||
continue; /* Try all chip-selects */
|
||||
@ -0,0 +1,91 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 5/9] mtd: rawnand: brcmnand: Allow working without interrupts
|
||||
Date: Fri, 07 Jan 2022 10:46:10 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
The BCMA devices include the brcmnand controller but they do not wire up
|
||||
any interrupt line, allow the main interrupt to be optional and update
|
||||
the completion path to also check for the lack of an interrupt line.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 52 +++++++++++-------------
|
||||
1 file changed, 24 insertions(+), 28 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -216,7 +216,7 @@ struct brcmnand_controller {
|
||||
void __iomem *nand_base;
|
||||
void __iomem *nand_fc; /* flash cache */
|
||||
void __iomem *flash_dma_base;
|
||||
- unsigned int irq;
|
||||
+ int irq;
|
||||
unsigned int dma_irq;
|
||||
int nand_version;
|
||||
|
||||
@@ -1610,7 +1610,7 @@ static bool brcmstb_nand_wait_for_comple
|
||||
bool err = false;
|
||||
int sts;
|
||||
|
||||
- if (mtd->oops_panic_write) {
|
||||
+ if (mtd->oops_panic_write || ctrl->irq < 0) {
|
||||
/* switch to interrupt polling and PIO mode */
|
||||
disable_ctrl_irqs(ctrl);
|
||||
sts = bcmnand_ctrl_poll_status(ctrl, NAND_CTRL_RDY,
|
||||
@@ -3144,33 +3144,29 @@ int brcmnand_probe(struct platform_devic
|
||||
}
|
||||
|
||||
/* IRQ */
|
||||
- ctrl->irq = platform_get_irq(pdev, 0);
|
||||
- if ((int)ctrl->irq < 0) {
|
||||
- dev_err(dev, "no IRQ defined\n");
|
||||
- ret = -ENODEV;
|
||||
- goto err;
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
- * Some SoCs integrate this controller (e.g., its interrupt bits) in
|
||||
- * interesting ways
|
||||
- */
|
||||
- if (soc) {
|
||||
- ret = devm_request_irq(dev, ctrl->irq, brcmnand_irq, 0,
|
||||
- DRV_NAME, ctrl);
|
||||
-
|
||||
- /* Enable interrupt */
|
||||
- ctrl->soc->ctlrdy_ack(ctrl->soc);
|
||||
- ctrl->soc->ctlrdy_set_enabled(ctrl->soc, true);
|
||||
- } else {
|
||||
- /* Use standard interrupt infrastructure */
|
||||
- ret = devm_request_irq(dev, ctrl->irq, brcmnand_ctlrdy_irq, 0,
|
||||
- DRV_NAME, ctrl);
|
||||
- }
|
||||
- if (ret < 0) {
|
||||
- dev_err(dev, "can't allocate IRQ %d: error %d\n",
|
||||
- ctrl->irq, ret);
|
||||
- goto err;
|
||||
+ ctrl->irq = platform_get_irq_optional(pdev, 0);
|
||||
+ if (ctrl->irq > 0) {
|
||||
+ /*
|
||||
+ * Some SoCs integrate this controller (e.g., its interrupt bits) in
|
||||
+ * interesting ways
|
||||
+ */
|
||||
+ if (soc) {
|
||||
+ ret = devm_request_irq(dev, ctrl->irq, brcmnand_irq, 0,
|
||||
+ DRV_NAME, ctrl);
|
||||
+
|
||||
+ /* Enable interrupt */
|
||||
+ ctrl->soc->ctlrdy_ack(ctrl->soc);
|
||||
+ ctrl->soc->ctlrdy_set_enabled(ctrl->soc, true);
|
||||
+ } else {
|
||||
+ /* Use standard interrupt infrastructure */
|
||||
+ ret = devm_request_irq(dev, ctrl->irq, brcmnand_ctlrdy_irq, 0,
|
||||
+ DRV_NAME, ctrl);
|
||||
+ }
|
||||
+ if (ret < 0) {
|
||||
+ dev_err(dev, "can't allocate IRQ %d: error %d\n",
|
||||
+ ctrl->irq, ret);
|
||||
+ goto err;
|
||||
+ }
|
||||
}
|
||||
|
||||
for_each_available_child_of_node(dn, child) {
|
||||
@ -0,0 +1,115 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 6/9] mtd: rawnand: brcmnand: Add platform data structure for BCMA
|
||||
Date: Fri, 07 Jan 2022 10:46:11 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
Update the BCMA's chipcommon nand flash driver to detect which
|
||||
chip-select is used and pass that information via platform data to the
|
||||
brcmnand driver. Make sure that the brcmnand platform data structure is
|
||||
always at the beginning of the platform data of the "nflash" device
|
||||
created by BCMA to allow brcmnand to safely de-reference it.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
MAINTAINERS | 1 +
|
||||
drivers/bcma/driver_chipcommon_nflash.c | 20 +++++++++++++++++++-
|
||||
include/linux/bcma/bcma_driver_chipcommon.h | 5 +++++
|
||||
include/linux/platform_data/brcmnand.h | 12 ++++++++++++
|
||||
4 files changed, 37 insertions(+), 1 deletion(-)
|
||||
create mode 100644 include/linux/platform_data/brcmnand.h
|
||||
|
||||
--- a/MAINTAINERS
|
||||
+++ b/MAINTAINERS
|
||||
@@ -3900,6 +3900,7 @@ L: linux-mtd@lists.infradead.org
|
||||
L: bcm-kernel-feedback-list@broadcom.com
|
||||
S: Maintained
|
||||
F: drivers/mtd/nand/raw/brcmnand/
|
||||
+F: include/linux/platform_data/brcmnand.h
|
||||
|
||||
BROADCOM STB PCIE DRIVER
|
||||
M: Jim Quinlan <jim2101024@gmail.com>
|
||||
--- a/drivers/bcma/driver_chipcommon_nflash.c
|
||||
+++ b/drivers/bcma/driver_chipcommon_nflash.c
|
||||
@@ -7,18 +7,28 @@
|
||||
|
||||
#include "bcma_private.h"
|
||||
|
||||
+#include <linux/bitops.h>
|
||||
#include <linux/platform_device.h>
|
||||
+#include <linux/platform_data/brcmnand.h>
|
||||
#include <linux/bcma/bcma.h>
|
||||
|
||||
+/* Alternate NAND controller driver name in order to allow both bcm47xxnflash
|
||||
+ * and bcma_brcmnand to be built into the same kernel image.
|
||||
+ */
|
||||
+static const char *bcma_nflash_alt_name = "bcma_brcmnand";
|
||||
+
|
||||
struct platform_device bcma_nflash_dev = {
|
||||
.name = "bcma_nflash",
|
||||
.num_resources = 0,
|
||||
};
|
||||
|
||||
+static const char *probes[] = { "bcm47xxpart", NULL };
|
||||
+
|
||||
/* Initialize NAND flash access */
|
||||
int bcma_nflash_init(struct bcma_drv_cc *cc)
|
||||
{
|
||||
struct bcma_bus *bus = cc->core->bus;
|
||||
+ u32 reg;
|
||||
|
||||
if (bus->chipinfo.id != BCMA_CHIP_ID_BCM4706 &&
|
||||
cc->core->id.rev != 38) {
|
||||
@@ -33,8 +43,16 @@ int bcma_nflash_init(struct bcma_drv_cc
|
||||
|
||||
cc->nflash.present = true;
|
||||
if (cc->core->id.rev == 38 &&
|
||||
- (cc->status & BCMA_CC_CHIPST_5357_NAND_BOOT))
|
||||
+ (cc->status & BCMA_CC_CHIPST_5357_NAND_BOOT)) {
|
||||
cc->nflash.boot = true;
|
||||
+ /* Determine the chip select that is being used */
|
||||
+ reg = bcma_cc_read32(cc, BCMA_CC_NAND_CS_NAND_SELECT) & 0xff;
|
||||
+ cc->nflash.brcmnand_info.chip_select = ffs(reg) - 1;
|
||||
+ cc->nflash.brcmnand_info.part_probe_types = probes;
|
||||
+ cc->nflash.brcmnand_info.ecc_stepsize = 512;
|
||||
+ cc->nflash.brcmnand_info.ecc_strength = 1;
|
||||
+ bcma_nflash_dev.name = bcma_nflash_alt_name;
|
||||
+ }
|
||||
|
||||
/* Prepare platform device, but don't register it yet. It's too early,
|
||||
* malloc (required by device_private_init) is not available yet. */
|
||||
--- a/include/linux/bcma/bcma_driver_chipcommon.h
|
||||
+++ b/include/linux/bcma/bcma_driver_chipcommon.h
|
||||
@@ -3,6 +3,7 @@
|
||||
#define LINUX_BCMA_DRIVER_CC_H_
|
||||
|
||||
#include <linux/platform_device.h>
|
||||
+#include <linux/platform_data/brcmnand.h>
|
||||
#include <linux/gpio.h>
|
||||
|
||||
/** ChipCommon core registers. **/
|
||||
@@ -599,6 +600,10 @@ struct bcma_sflash {
|
||||
|
||||
#ifdef CONFIG_BCMA_NFLASH
|
||||
struct bcma_nflash {
|
||||
+ /* Must be the fist member for the brcmnand driver to
|
||||
+ * de-reference that structure.
|
||||
+ */
|
||||
+ struct brcmnand_platform_data brcmnand_info;
|
||||
bool present;
|
||||
bool boot; /* This is the flash the SoC boots from */
|
||||
};
|
||||
--- /dev/null
|
||||
+++ b/include/linux/platform_data/brcmnand.h
|
||||
@@ -0,0 +1,12 @@
|
||||
+/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
+#ifndef BRCMNAND_PLAT_DATA_H
|
||||
+#define BRCMNAND_PLAT_DATA_H
|
||||
+
|
||||
+struct brcmnand_platform_data {
|
||||
+ int chip_select;
|
||||
+ const char * const *part_probe_types;
|
||||
+ unsigned int ecc_stepsize;
|
||||
+ unsigned int ecc_strength;
|
||||
+};
|
||||
+
|
||||
+#endif /* BRCMNAND_PLAT_DATA_H */
|
||||
@ -0,0 +1,124 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 7/9] mtd: rawnand: brcmnand: Allow platform data instantation
|
||||
Date: Fri, 07 Jan 2022 10:46:12 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
Make use of the recently refactored code in brcmnand_init_cs() and
|
||||
derive the chip-select from the platform data that is supplied. Update
|
||||
the various code paths to avoid relying on possibly non-existent
|
||||
resources, too.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 45 ++++++++++++++++++------
|
||||
1 file changed, 35 insertions(+), 10 deletions(-)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -9,6 +9,7 @@
|
||||
#include <linux/delay.h>
|
||||
#include <linux/device.h>
|
||||
#include <linux/platform_device.h>
|
||||
+#include <linux/platform_data/brcmnand.h>
|
||||
#include <linux/err.h>
|
||||
#include <linux/completion.h>
|
||||
#include <linux/interrupt.h>
|
||||
@@ -2768,7 +2769,8 @@ static const struct nand_controller_ops
|
||||
.attach_chip = brcmnand_attach_chip,
|
||||
};
|
||||
|
||||
-static int brcmnand_init_cs(struct brcmnand_host *host)
|
||||
+static int brcmnand_init_cs(struct brcmnand_host *host,
|
||||
+ const char * const *part_probe_types)
|
||||
{
|
||||
struct brcmnand_controller *ctrl = host->ctrl;
|
||||
struct device *dev = ctrl->dev;
|
||||
@@ -2821,7 +2823,7 @@ static int brcmnand_init_cs(struct brcmn
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
- ret = mtd_device_register(mtd, NULL, 0);
|
||||
+ ret = mtd_device_parse_register(mtd, part_probe_types, NULL, NULL, 0);
|
||||
if (ret)
|
||||
nand_cleanup(chip);
|
||||
|
||||
@@ -2990,17 +2992,15 @@ static int brcmnand_edu_setup(struct pla
|
||||
|
||||
int brcmnand_probe(struct platform_device *pdev, struct brcmnand_soc *soc)
|
||||
{
|
||||
+ struct brcmnand_platform_data *pd = dev_get_platdata(&pdev->dev);
|
||||
struct device *dev = &pdev->dev;
|
||||
struct device_node *dn = dev->of_node, *child;
|
||||
struct brcmnand_controller *ctrl;
|
||||
+ struct brcmnand_host *host;
|
||||
struct resource *res;
|
||||
int ret;
|
||||
|
||||
- /* We only support device-tree instantiation */
|
||||
- if (!dn)
|
||||
- return -ENODEV;
|
||||
-
|
||||
- if (!of_match_node(brcmnand_of_match, dn))
|
||||
+ if (dn && !of_match_node(brcmnand_of_match, dn))
|
||||
return -ENODEV;
|
||||
|
||||
ctrl = devm_kzalloc(dev, sizeof(*ctrl), GFP_KERNEL);
|
||||
@@ -3027,7 +3027,7 @@ int brcmnand_probe(struct platform_devic
|
||||
/* NAND register range */
|
||||
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
|
||||
ctrl->nand_base = devm_ioremap_resource(dev, res);
|
||||
- if (IS_ERR(ctrl->nand_base))
|
||||
+ if (IS_ERR(ctrl->nand_base) && !brcmnand_soc_has_ops(soc))
|
||||
return PTR_ERR(ctrl->nand_base);
|
||||
|
||||
/* Enable clock before using NAND registers */
|
||||
@@ -3171,7 +3171,6 @@ int brcmnand_probe(struct platform_devic
|
||||
|
||||
for_each_available_child_of_node(dn, child) {
|
||||
if (of_device_is_compatible(child, "brcm,nandcs")) {
|
||||
- struct brcmnand_host *host;
|
||||
|
||||
host = devm_kzalloc(dev, sizeof(*host), GFP_KERNEL);
|
||||
if (!host) {
|
||||
@@ -3191,7 +3190,7 @@ int brcmnand_probe(struct platform_devic
|
||||
|
||||
nand_set_flash_node(&host->chip, child);
|
||||
|
||||
- ret = brcmnand_init_cs(host);
|
||||
+ ret = brcmnand_init_cs(host, NULL);
|
||||
if (ret) {
|
||||
devm_kfree(dev, host);
|
||||
continue; /* Try all chip-selects */
|
||||
@@ -3201,6 +3200,32 @@ int brcmnand_probe(struct platform_devic
|
||||
}
|
||||
}
|
||||
|
||||
+ if (!list_empty(&ctrl->host_list))
|
||||
+ return 0;
|
||||
+
|
||||
+ if (!pd) {
|
||||
+ ret = -ENODEV;
|
||||
+ goto err;
|
||||
+ }
|
||||
+
|
||||
+ /* If we got there we must have been probing via platform data */
|
||||
+ host = devm_kzalloc(dev, sizeof(*host), GFP_KERNEL);
|
||||
+ if (!host) {
|
||||
+ ret = -ENOMEM;
|
||||
+ goto err;
|
||||
+ }
|
||||
+ host->pdev = pdev;
|
||||
+ host->ctrl = ctrl;
|
||||
+ host->cs = pd->chip_select;
|
||||
+ host->chip.ecc.size = pd->ecc_stepsize;
|
||||
+ host->chip.ecc.strength = pd->ecc_strength;
|
||||
+
|
||||
+ ret = brcmnand_init_cs(host, pd->part_probe_types);
|
||||
+ if (ret)
|
||||
+ goto err;
|
||||
+
|
||||
+ list_add_tail(&host->node, &ctrl->host_list);
|
||||
+
|
||||
/* No chip-selects could initialize properly */
|
||||
if (list_empty(&ctrl->host_list)) {
|
||||
ret = -ENODEV;
|
||||
@ -0,0 +1,29 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 8/9] mtd: rawnand: brcmnand: BCMA controller uses command shift of 0
|
||||
Date: Fri, 07 Jan 2022 10:46:13 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
For some odd and unexplained reason the BCMA NAND controller, albeit
|
||||
revision 3.4 uses a command shift of 0 instead of 24 as it should be,
|
||||
quirk that.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 6 ++++++
|
||||
1 file changed, 6 insertions(+)
|
||||
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -916,6 +916,12 @@ static void brcmnand_wr_corr_thresh(stru
|
||||
|
||||
static inline int brcmnand_cmd_shift(struct brcmnand_controller *ctrl)
|
||||
{
|
||||
+ /* Kludge for the BCMA-based NAND controller which does not actually
|
||||
+ * shift the command
|
||||
+ */
|
||||
+ if (ctrl->nand_version == 0x0304 && brcmnand_non_mmio_ops(ctrl))
|
||||
+ return 0;
|
||||
+
|
||||
if (ctrl->nand_version < 0x0602)
|
||||
return 24;
|
||||
return 0;
|
||||
@ -0,0 +1,201 @@
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Subject: [PATCH v3 9/9] mtd: rawnand: brcmnand: Add BCMA shim
|
||||
Date: Fri, 07 Jan 2022 10:46:14 -0800
|
||||
Content-Type: text/plain; charset="utf-8"
|
||||
|
||||
Add a BCMA shim to allow us to register the brcmnand driver using the
|
||||
BCMA bus which provides indirect memory mapped access to SoC registers.
|
||||
|
||||
There are a number of registers that need to be byte swapped because
|
||||
they are natively big endian, coming directly from the NAND chip, and
|
||||
there is no bus interface unlike the iProc or STB platforms that
|
||||
performs the byte swapping for us.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
---
|
||||
drivers/mtd/nand/raw/Kconfig | 13 +++
|
||||
drivers/mtd/nand/raw/brcmnand/Makefile | 2 +
|
||||
drivers/mtd/nand/raw/brcmnand/bcma_nand.c | 132 ++++++++++++++++++++++
|
||||
drivers/mtd/nand/raw/brcmnand/brcmnand.c | 4 +
|
||||
4 files changed, 151 insertions(+)
|
||||
create mode 100644 drivers/mtd/nand/raw/brcmnand/bcma_nand.c
|
||||
|
||||
--- a/drivers/mtd/nand/raw/Kconfig
|
||||
+++ b/drivers/mtd/nand/raw/Kconfig
|
||||
@@ -208,6 +208,19 @@ config MTD_NAND_BRCMNAND
|
||||
originally designed for Set-Top Box but is used on various BCM7xxx,
|
||||
BCM3xxx, BCM63xxx, iProc/Cygnus and more.
|
||||
|
||||
+if MTD_NAND_BRCMNAND
|
||||
+
|
||||
+config MTD_NAND_BRCMNAND_BCMA
|
||||
+ tristate "Broadcom BCMA NAND controller"
|
||||
+ depends on BCMA_NFLASH
|
||||
+ depends on BCMA
|
||||
+ help
|
||||
+ Enables the BRCMNAND controller over BCMA on BCM47186/BCM5358 SoCs.
|
||||
+ The glue driver will take care of performing the low-level I/O
|
||||
+ operations to interface the BRCMNAND controller over the BCMA bus.
|
||||
+
|
||||
+endif # MTD_NAND_BRCMNAND
|
||||
+
|
||||
config MTD_NAND_BCM47XXNFLASH
|
||||
tristate "BCM4706 BCMA NAND controller"
|
||||
depends on BCMA_NFLASH
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/Makefile
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/Makefile
|
||||
@@ -6,3 +6,5 @@ obj-$(CONFIG_MTD_NAND_BRCMNAND) += bcm6
|
||||
obj-$(CONFIG_MTD_NAND_BRCMNAND) += bcm6368_nand.o
|
||||
obj-$(CONFIG_MTD_NAND_BRCMNAND) += brcmstb_nand.o
|
||||
obj-$(CONFIG_MTD_NAND_BRCMNAND) += brcmnand.o
|
||||
+
|
||||
+obj-$(CONFIG_MTD_NAND_BRCMNAND_BCMA) += bcma_nand.o
|
||||
--- /dev/null
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/bcma_nand.c
|
||||
@@ -0,0 +1,132 @@
|
||||
+// SPDX-License-Identifier: GPL-2.0-only
|
||||
+/*
|
||||
+ * Copyright © 2021 Broadcom
|
||||
+ */
|
||||
+#include <linux/bcma/bcma.h>
|
||||
+#include <linux/bcma/bcma_driver_chipcommon.h>
|
||||
+#include <linux/device.h>
|
||||
+#include <linux/module.h>
|
||||
+#include <linux/platform_device.h>
|
||||
+
|
||||
+#include "brcmnand.h"
|
||||
+
|
||||
+struct brcmnand_bcma_soc {
|
||||
+ struct brcmnand_soc soc;
|
||||
+ struct bcma_drv_cc *cc;
|
||||
+};
|
||||
+
|
||||
+static inline bool brcmnand_bcma_needs_swapping(u32 offset)
|
||||
+{
|
||||
+ switch (offset) {
|
||||
+ case BCMA_CC_NAND_SPARE_RD0:
|
||||
+ case BCMA_CC_NAND_SPARE_RD4:
|
||||
+ case BCMA_CC_NAND_SPARE_RD8:
|
||||
+ case BCMA_CC_NAND_SPARE_RD12:
|
||||
+ case BCMA_CC_NAND_SPARE_WR0:
|
||||
+ case BCMA_CC_NAND_SPARE_WR4:
|
||||
+ case BCMA_CC_NAND_SPARE_WR8:
|
||||
+ case BCMA_CC_NAND_SPARE_WR12:
|
||||
+ case BCMA_CC_NAND_DEVID:
|
||||
+ case BCMA_CC_NAND_DEVID_X:
|
||||
+ case BCMA_CC_NAND_SPARE_RD16:
|
||||
+ case BCMA_CC_NAND_SPARE_RD20:
|
||||
+ case BCMA_CC_NAND_SPARE_RD24:
|
||||
+ case BCMA_CC_NAND_SPARE_RD28:
|
||||
+ return true;
|
||||
+ }
|
||||
+
|
||||
+ return false;
|
||||
+}
|
||||
+
|
||||
+static inline struct brcmnand_bcma_soc *to_bcma_soc(struct brcmnand_soc *soc)
|
||||
+{
|
||||
+ return container_of(soc, struct brcmnand_bcma_soc, soc);
|
||||
+}
|
||||
+
|
||||
+static u32 brcmnand_bcma_read_reg(struct brcmnand_soc *soc, u32 offset)
|
||||
+{
|
||||
+ struct brcmnand_bcma_soc *sc = to_bcma_soc(soc);
|
||||
+ u32 val;
|
||||
+
|
||||
+ /* Offset into the NAND block and deal with the flash cache separately */
|
||||
+ if (offset == BRCMNAND_NON_MMIO_FC_ADDR)
|
||||
+ offset = BCMA_CC_NAND_CACHE_DATA;
|
||||
+ else
|
||||
+ offset += BCMA_CC_NAND_REVISION;
|
||||
+
|
||||
+ val = bcma_cc_read32(sc->cc, offset);
|
||||
+
|
||||
+ /* Swap if necessary */
|
||||
+ if (brcmnand_bcma_needs_swapping(offset))
|
||||
+ val = be32_to_cpu(val);
|
||||
+ return val;
|
||||
+}
|
||||
+
|
||||
+static void brcmnand_bcma_write_reg(struct brcmnand_soc *soc, u32 val,
|
||||
+ u32 offset)
|
||||
+{
|
||||
+ struct brcmnand_bcma_soc *sc = to_bcma_soc(soc);
|
||||
+
|
||||
+ /* Offset into the NAND block */
|
||||
+ if (offset == BRCMNAND_NON_MMIO_FC_ADDR)
|
||||
+ offset = BCMA_CC_NAND_CACHE_DATA;
|
||||
+ else
|
||||
+ offset += BCMA_CC_NAND_REVISION;
|
||||
+
|
||||
+ /* Swap if necessary */
|
||||
+ if (brcmnand_bcma_needs_swapping(offset))
|
||||
+ val = cpu_to_be32(val);
|
||||
+
|
||||
+ bcma_cc_write32(sc->cc, offset, val);
|
||||
+}
|
||||
+
|
||||
+static struct brcmnand_io_ops brcmnand_bcma_io_ops = {
|
||||
+ .read_reg = brcmnand_bcma_read_reg,
|
||||
+ .write_reg = brcmnand_bcma_write_reg,
|
||||
+};
|
||||
+
|
||||
+static void brcmnand_bcma_prepare_data_bus(struct brcmnand_soc *soc, bool prepare,
|
||||
+ bool is_param)
|
||||
+{
|
||||
+ struct brcmnand_bcma_soc *sc = to_bcma_soc(soc);
|
||||
+
|
||||
+ /* Reset the cache address to ensure we are already accessing the
|
||||
+ * beginning of a sub-page.
|
||||
+ */
|
||||
+ bcma_cc_write32(sc->cc, BCMA_CC_NAND_CACHE_ADDR, 0);
|
||||
+}
|
||||
+
|
||||
+static int brcmnand_bcma_nand_probe(struct platform_device *pdev)
|
||||
+{
|
||||
+ struct bcma_nflash *nflash = dev_get_platdata(&pdev->dev);
|
||||
+ struct brcmnand_bcma_soc *soc;
|
||||
+
|
||||
+ soc = devm_kzalloc(&pdev->dev, sizeof(*soc), GFP_KERNEL);
|
||||
+ if (!soc)
|
||||
+ return -ENOMEM;
|
||||
+
|
||||
+ soc->cc = container_of(nflash, struct bcma_drv_cc, nflash);
|
||||
+ soc->soc.prepare_data_bus = brcmnand_bcma_prepare_data_bus;
|
||||
+ soc->soc.ops = &brcmnand_bcma_io_ops;
|
||||
+
|
||||
+ if (soc->cc->core->bus->chipinfo.id == BCMA_CHIP_ID_BCM4706) {
|
||||
+ dev_err(&pdev->dev, "Use bcm47xxnflash for 4706!\n");
|
||||
+ return -ENODEV;
|
||||
+ }
|
||||
+
|
||||
+ return brcmnand_probe(pdev, &soc->soc);
|
||||
+}
|
||||
+
|
||||
+static struct platform_driver brcmnand_bcma_nand_driver = {
|
||||
+ .probe = brcmnand_bcma_nand_probe,
|
||||
+ .remove = brcmnand_remove,
|
||||
+ .driver = {
|
||||
+ .name = "bcma_brcmnand",
|
||||
+ .pm = &brcmnand_pm_ops,
|
||||
+ }
|
||||
+};
|
||||
+module_platform_driver(brcmnand_bcma_nand_driver);
|
||||
+
|
||||
+MODULE_LICENSE("GPL v2");
|
||||
+MODULE_AUTHOR("Broadcom");
|
||||
+MODULE_DESCRIPTION("NAND controller driver glue for BCMA chips");
|
||||
--- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
+++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c
|
||||
@@ -598,7 +598,11 @@ enum {
|
||||
|
||||
static inline bool brcmnand_non_mmio_ops(struct brcmnand_controller *ctrl)
|
||||
{
|
||||
+#if IS_ENABLED(CONFIG_MTD_NAND_BRCMNAND_BCMA)
|
||||
return static_branch_unlikely(&brcmnand_soc_has_ops_key);
|
||||
+#else
|
||||
+ return false;
|
||||
+#endif
|
||||
}
|
||||
|
||||
static inline u32 nand_readreg(struct brcmnand_controller *ctrl, u32 offs)
|
||||
484
target/linux/bcm47xx/patches-5.15/159-cpu_fixes.patch
Normal file
484
target/linux/bcm47xx/patches-5.15/159-cpu_fixes.patch
Normal file
@ -0,0 +1,484 @@
|
||||
--- a/arch/mips/include/asm/r4kcache.h
|
||||
+++ b/arch/mips/include/asm/r4kcache.h
|
||||
@@ -27,6 +27,38 @@
|
||||
extern void (*r4k_blast_dcache)(void);
|
||||
extern void (*r4k_blast_icache)(void);
|
||||
|
||||
+#if defined(CONFIG_BCM47XX) && !defined(CONFIG_CPU_MIPS32_R2)
|
||||
+#include <asm/paccess.h>
|
||||
+#include <linux/ssb/ssb.h>
|
||||
+#define BCM4710_DUMMY_RREG() bcm4710_dummy_rreg()
|
||||
+
|
||||
+static inline unsigned long bcm4710_dummy_rreg(void)
|
||||
+{
|
||||
+ return *(volatile unsigned long *)(KSEG1ADDR(SSB_ENUM_BASE));
|
||||
+}
|
||||
+
|
||||
+#define BCM4710_FILL_TLB(addr) bcm4710_fill_tlb((void *)(addr))
|
||||
+
|
||||
+static inline unsigned long bcm4710_fill_tlb(void *addr)
|
||||
+{
|
||||
+ return *(unsigned long *)addr;
|
||||
+}
|
||||
+
|
||||
+#define BCM4710_PROTECTED_FILL_TLB(addr) bcm4710_protected_fill_tlb((void *)(addr))
|
||||
+
|
||||
+static inline void bcm4710_protected_fill_tlb(void *addr)
|
||||
+{
|
||||
+ unsigned long x;
|
||||
+ get_dbe(x, (unsigned long *)addr);;
|
||||
+}
|
||||
+
|
||||
+#else
|
||||
+#define BCM4710_DUMMY_RREG()
|
||||
+
|
||||
+#define BCM4710_FILL_TLB(addr)
|
||||
+#define BCM4710_PROTECTED_FILL_TLB(addr)
|
||||
+#endif
|
||||
+
|
||||
/*
|
||||
* This macro return a properly sign-extended address suitable as base address
|
||||
* for indexed cache operations. Two issues here:
|
||||
@@ -60,6 +92,7 @@ static inline void flush_icache_line_ind
|
||||
|
||||
static inline void flush_dcache_line_indexed(unsigned long addr)
|
||||
{
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
cache_op(Index_Writeback_Inv_D, addr);
|
||||
}
|
||||
|
||||
@@ -83,11 +116,13 @@ static inline void flush_icache_line(uns
|
||||
|
||||
static inline void flush_dcache_line(unsigned long addr)
|
||||
{
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
cache_op(Hit_Writeback_Inv_D, addr);
|
||||
}
|
||||
|
||||
static inline void invalidate_dcache_line(unsigned long addr)
|
||||
{
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
cache_op(Hit_Invalidate_D, addr);
|
||||
}
|
||||
|
||||
@@ -160,6 +195,7 @@ static inline int protected_flush_icache
|
||||
return protected_cache_op(Hit_Invalidate_I_Loongson2, addr);
|
||||
|
||||
default:
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
return protected_cache_op(Hit_Invalidate_I, addr);
|
||||
}
|
||||
}
|
||||
@@ -172,6 +208,7 @@ static inline int protected_flush_icache
|
||||
*/
|
||||
static inline int protected_writeback_dcache_line(unsigned long addr)
|
||||
{
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
return protected_cache_op(Hit_Writeback_Inv_D, addr);
|
||||
}
|
||||
|
||||
@@ -193,8 +230,51 @@ static inline void invalidate_tcache_pag
|
||||
unroll(times, _cache_op, insn, op, (addr) + (i++ * (lsize))); \
|
||||
} while (0)
|
||||
|
||||
+static inline void blast_dcache(void)
|
||||
+{
|
||||
+ unsigned long start = KSEG0;
|
||||
+ unsigned long dcache_size = current_cpu_data.dcache.waysize * current_cpu_data.dcache.ways;
|
||||
+ unsigned long end = (start + dcache_size);
|
||||
+
|
||||
+ do {
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
+ cache_op(Index_Writeback_Inv_D, start);
|
||||
+ start += current_cpu_data.dcache.linesz;
|
||||
+ } while(start < end);
|
||||
+}
|
||||
+
|
||||
+static inline void blast_dcache_page(unsigned long page)
|
||||
+{
|
||||
+ unsigned long start = page;
|
||||
+ unsigned long end = start + PAGE_SIZE;
|
||||
+
|
||||
+ BCM4710_FILL_TLB(start);
|
||||
+ do {
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
+ cache_op(Hit_Writeback_Inv_D, start);
|
||||
+ start += current_cpu_data.dcache.linesz;
|
||||
+ } while(start < end);
|
||||
+}
|
||||
+
|
||||
+static inline void blast_dcache_page_indexed(unsigned long page)
|
||||
+{
|
||||
+ unsigned long start = page;
|
||||
+ unsigned long end = start + PAGE_SIZE;
|
||||
+ unsigned long ws_inc = 1UL << current_cpu_data.dcache.waybit;
|
||||
+ unsigned long ws_end = current_cpu_data.dcache.ways <<
|
||||
+ current_cpu_data.dcache.waybit;
|
||||
+ unsigned long ws, addr;
|
||||
+ for (ws = 0; ws < ws_end; ws += ws_inc) {
|
||||
+ start = page + ws;
|
||||
+ for (addr = start; addr < end; addr += current_cpu_data.dcache.linesz) {
|
||||
+ BCM4710_DUMMY_RREG();
|
||||
+ cache_op(Index_Writeback_Inv_D, addr);
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
/* build blast_xxx, blast_xxx_page, blast_xxx_page_indexed */
|
||||
-#define __BUILD_BLAST_CACHE(pfx, desc, indexop, hitop, lsize, extra) \
|
||||
+#define __BUILD_BLAST_CACHE(pfx, desc, indexop, hitop, lsize, extra, war) \
|
||||
static inline void extra##blast_##pfx##cache##lsize(void) \
|
||||
{ \
|
||||
unsigned long start = INDEX_BASE; \
|
||||
@@ -204,6 +284,7 @@ static inline void extra##blast_##pfx##c
|
||||
current_cpu_data.desc.waybit; \
|
||||
unsigned long ws, addr; \
|
||||
\
|
||||
+ war \
|
||||
for (ws = 0; ws < ws_end; ws += ws_inc) \
|
||||
for (addr = start; addr < end; addr += lsize * 32) \
|
||||
cache_unroll(32, kernel_cache, indexop, \
|
||||
@@ -215,6 +296,7 @@ static inline void extra##blast_##pfx##c
|
||||
unsigned long start = page; \
|
||||
unsigned long end = page + PAGE_SIZE; \
|
||||
\
|
||||
+ war \
|
||||
do { \
|
||||
cache_unroll(32, kernel_cache, hitop, start, lsize); \
|
||||
start += lsize * 32; \
|
||||
@@ -231,32 +313,33 @@ static inline void extra##blast_##pfx##c
|
||||
current_cpu_data.desc.waybit; \
|
||||
unsigned long ws, addr; \
|
||||
\
|
||||
+ war \
|
||||
for (ws = 0; ws < ws_end; ws += ws_inc) \
|
||||
for (addr = start; addr < end; addr += lsize * 32) \
|
||||
cache_unroll(32, kernel_cache, indexop, \
|
||||
addr | ws, lsize); \
|
||||
}
|
||||
|
||||
-__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 16, )
|
||||
-__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 16, )
|
||||
-__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 16, )
|
||||
-__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 32, )
|
||||
-__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 32, )
|
||||
-__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I_Loongson2, 32, loongson2_)
|
||||
-__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 32, )
|
||||
-__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 64, )
|
||||
-__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 64, )
|
||||
-__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 64, )
|
||||
-__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 128, )
|
||||
-__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 128, )
|
||||
-__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 128, )
|
||||
-
|
||||
-__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 16, )
|
||||
-__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 32, )
|
||||
-__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 16, )
|
||||
-__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 32, )
|
||||
-__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 64, )
|
||||
-__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 128, )
|
||||
+__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 16, , )
|
||||
+__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 16, , BCM4710_FILL_TLB(start);)
|
||||
+__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 16, , )
|
||||
+__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 32, , )
|
||||
+__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 32, , BCM4710_FILL_TLB(start);)
|
||||
+__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I_Loongson2, 32, loongson2_, BCM4710_FILL_TLB(start);)
|
||||
+__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 32, , )
|
||||
+__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 64, , )
|
||||
+__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 64, , BCM4710_FILL_TLB(start);)
|
||||
+__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 64, , )
|
||||
+__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 128, , )
|
||||
+__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 128, , )
|
||||
+__BUILD_BLAST_CACHE(s, scache, Index_Writeback_Inv_SD, Hit_Writeback_Inv_SD, 128, , )
|
||||
+
|
||||
+__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 16, , )
|
||||
+__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 32, , )
|
||||
+__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 16, , )
|
||||
+__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 32, , )
|
||||
+__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 64, , )
|
||||
+__BUILD_BLAST_CACHE(inv_s, scache, Index_Writeback_Inv_SD, Hit_Invalidate_SD, 128, , )
|
||||
|
||||
#define __BUILD_BLAST_USER_CACHE(pfx, desc, indexop, hitop, lsize) \
|
||||
static inline void blast_##pfx##cache##lsize##_user_page(unsigned long page) \
|
||||
@@ -281,65 +364,36 @@ __BUILD_BLAST_USER_CACHE(d, dcache, Inde
|
||||
__BUILD_BLAST_USER_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 64)
|
||||
|
||||
/* build blast_xxx_range, protected_blast_xxx_range */
|
||||
-#define __BUILD_BLAST_CACHE_RANGE(pfx, desc, hitop, prot, extra) \
|
||||
+#define __BUILD_BLAST_CACHE_RANGE(pfx, desc, hitop, prot, extra, war, war2) \
|
||||
static inline void prot##extra##blast_##pfx##cache##_range(unsigned long start, \
|
||||
unsigned long end) \
|
||||
{ \
|
||||
unsigned long lsize = cpu_##desc##_line_size(); \
|
||||
- unsigned long lsize_2 = lsize * 2; \
|
||||
- unsigned long lsize_3 = lsize * 3; \
|
||||
- unsigned long lsize_4 = lsize * 4; \
|
||||
- unsigned long lsize_5 = lsize * 5; \
|
||||
- unsigned long lsize_6 = lsize * 6; \
|
||||
- unsigned long lsize_7 = lsize * 7; \
|
||||
- unsigned long lsize_8 = lsize * 8; \
|
||||
unsigned long addr = start & ~(lsize - 1); \
|
||||
- unsigned long aend = (end + lsize - 1) & ~(lsize - 1); \
|
||||
- int lines = (aend - addr) / lsize; \
|
||||
- \
|
||||
- while (lines >= 8) { \
|
||||
- prot##cache_op(hitop, addr); \
|
||||
- prot##cache_op(hitop, addr + lsize); \
|
||||
- prot##cache_op(hitop, addr + lsize_2); \
|
||||
- prot##cache_op(hitop, addr + lsize_3); \
|
||||
- prot##cache_op(hitop, addr + lsize_4); \
|
||||
- prot##cache_op(hitop, addr + lsize_5); \
|
||||
- prot##cache_op(hitop, addr + lsize_6); \
|
||||
- prot##cache_op(hitop, addr + lsize_7); \
|
||||
- addr += lsize_8; \
|
||||
- lines -= 8; \
|
||||
- } \
|
||||
+ unsigned long aend = (end - 1) & ~(lsize - 1); \
|
||||
\
|
||||
- if (lines & 0x4) { \
|
||||
- prot##cache_op(hitop, addr); \
|
||||
- prot##cache_op(hitop, addr + lsize); \
|
||||
- prot##cache_op(hitop, addr + lsize_2); \
|
||||
- prot##cache_op(hitop, addr + lsize_3); \
|
||||
- addr += lsize_4; \
|
||||
- } \
|
||||
- \
|
||||
- if (lines & 0x2) { \
|
||||
- prot##cache_op(hitop, addr); \
|
||||
- prot##cache_op(hitop, addr + lsize); \
|
||||
- addr += lsize_2; \
|
||||
- } \
|
||||
+ war \
|
||||
\
|
||||
- if (lines & 0x1) { \
|
||||
+ while (1) { \
|
||||
+ war2 \
|
||||
prot##cache_op(hitop, addr); \
|
||||
+ if (addr == aend) \
|
||||
+ break; \
|
||||
+ addr += lsize; \
|
||||
} \
|
||||
}
|
||||
|
||||
-__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, protected_, )
|
||||
-__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I, protected_, )
|
||||
-__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, protected_, )
|
||||
+__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, protected_, , BCM4710_PROTECTED_FILL_TLB(addr); BCM4710_PROTECTED_FILL_TLB(aend);, BCM4710_DUMMY_RREG();)
|
||||
+__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I, protected_, , , )
|
||||
+__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, protected_, , , )
|
||||
__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I_Loongson2, \
|
||||
- protected_, loongson2_)
|
||||
-__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, , )
|
||||
-__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I, , )
|
||||
-__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, , )
|
||||
+ protected_, loongson2_, , )
|
||||
+__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, , , BCM4710_FILL_TLB(addr); BCM4710_FILL_TLB(aend);, BCM4710_DUMMY_RREG();)
|
||||
+__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I, , , , )
|
||||
+__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, , , , )
|
||||
/* blast_inv_dcache_range */
|
||||
-__BUILD_BLAST_CACHE_RANGE(inv_d, dcache, Hit_Invalidate_D, , )
|
||||
-__BUILD_BLAST_CACHE_RANGE(inv_s, scache, Hit_Invalidate_SD, , )
|
||||
+__BUILD_BLAST_CACHE_RANGE(inv_d, dcache, Hit_Invalidate_D, , , , BCM4710_DUMMY_RREG();)
|
||||
+__BUILD_BLAST_CACHE_RANGE(inv_s, scache, Hit_Invalidate_SD, , , , )
|
||||
|
||||
/* Currently, this is very specific to Loongson-3 */
|
||||
#define __BUILD_BLAST_CACHE_NODE(pfx, desc, indexop, hitop, lsize) \
|
||||
--- a/arch/mips/include/asm/stackframe.h
|
||||
+++ b/arch/mips/include/asm/stackframe.h
|
||||
@@ -429,6 +429,10 @@
|
||||
#else
|
||||
.set push
|
||||
.set arch=r4000
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ nop
|
||||
+ nop
|
||||
+#endif
|
||||
eret
|
||||
.set pop
|
||||
#endif
|
||||
--- a/arch/mips/kernel/genex.S
|
||||
+++ b/arch/mips/kernel/genex.S
|
||||
@@ -22,6 +22,19 @@
|
||||
#include <asm/war.h>
|
||||
#include <asm/thread_info.h>
|
||||
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+# ifdef eret
|
||||
+# undef eret
|
||||
+# endif
|
||||
+# define eret \
|
||||
+ .set push; \
|
||||
+ .set noreorder; \
|
||||
+ nop; \
|
||||
+ nop; \
|
||||
+ eret; \
|
||||
+ .set pop;
|
||||
+#endif
|
||||
+
|
||||
__INIT
|
||||
|
||||
/*
|
||||
@@ -33,6 +46,9 @@
|
||||
NESTED(except_vec3_generic, 0, sp)
|
||||
.set push
|
||||
.set noat
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ nop
|
||||
+#endif
|
||||
mfc0 k1, CP0_CAUSE
|
||||
andi k1, k1, 0x7c
|
||||
#ifdef CONFIG_64BIT
|
||||
@@ -53,6 +69,9 @@ NESTED(except_vec3_r4000, 0, sp)
|
||||
.set push
|
||||
.set arch=r4000
|
||||
.set noat
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ nop
|
||||
+#endif
|
||||
mfc0 k1, CP0_CAUSE
|
||||
li k0, 31<<2
|
||||
andi k1, k1, 0x7c
|
||||
--- a/arch/mips/mm/c-r4k.c
|
||||
+++ b/arch/mips/mm/c-r4k.c
|
||||
@@ -38,6 +38,9 @@
|
||||
#include <asm/traps.h>
|
||||
#include <asm/mips-cps.h>
|
||||
|
||||
+/* For enabling BCM4710 cache workarounds */
|
||||
+static int bcm4710 = 0;
|
||||
+
|
||||
/*
|
||||
* Bits describing what cache ops an SMP callback function may perform.
|
||||
*
|
||||
@@ -190,6 +193,9 @@ static void r4k_blast_dcache_user_page_s
|
||||
{
|
||||
unsigned long dc_lsize = cpu_dcache_line_size();
|
||||
|
||||
+ if (bcm4710)
|
||||
+ r4k_blast_dcache_page = blast_dcache_page;
|
||||
+ else
|
||||
if (dc_lsize == 0)
|
||||
r4k_blast_dcache_user_page = (void *)cache_noop;
|
||||
else if (dc_lsize == 16)
|
||||
@@ -208,6 +214,9 @@ static void r4k_blast_dcache_page_indexe
|
||||
{
|
||||
unsigned long dc_lsize = cpu_dcache_line_size();
|
||||
|
||||
+ if (bcm4710)
|
||||
+ r4k_blast_dcache_page_indexed = blast_dcache_page_indexed;
|
||||
+ else
|
||||
if (dc_lsize == 0)
|
||||
r4k_blast_dcache_page_indexed = (void *)cache_noop;
|
||||
else if (dc_lsize == 16)
|
||||
@@ -227,6 +236,9 @@ static void r4k_blast_dcache_setup(void)
|
||||
{
|
||||
unsigned long dc_lsize = cpu_dcache_line_size();
|
||||
|
||||
+ if (bcm4710)
|
||||
+ r4k_blast_dcache = blast_dcache;
|
||||
+ else
|
||||
if (dc_lsize == 0)
|
||||
r4k_blast_dcache = (void *)cache_noop;
|
||||
else if (dc_lsize == 16)
|
||||
@@ -1817,6 +1829,17 @@ static void coherency_setup(void)
|
||||
* silly idea of putting something else there ...
|
||||
*/
|
||||
switch (current_cpu_type()) {
|
||||
+ case CPU_BMIPS3300:
|
||||
+ {
|
||||
+ u32 cm;
|
||||
+ cm = read_c0_diag();
|
||||
+ /* Enable icache */
|
||||
+ cm |= (1 << 31);
|
||||
+ /* Enable dcache */
|
||||
+ cm |= (1 << 30);
|
||||
+ write_c0_diag(cm);
|
||||
+ }
|
||||
+ break;
|
||||
case CPU_R4000PC:
|
||||
case CPU_R4000SC:
|
||||
case CPU_R4000MC:
|
||||
@@ -1863,6 +1886,15 @@ void r4k_cache_init(void)
|
||||
extern void build_copy_page(void);
|
||||
struct cpuinfo_mips *c = ¤t_cpu_data;
|
||||
|
||||
+ /* Check if special workarounds are required */
|
||||
+#if defined(CONFIG_BCM47XX) && !defined(CONFIG_CPU_MIPS32_R2)
|
||||
+ if (current_cpu_data.cputype == CPU_BMIPS32 && (current_cpu_data.processor_id & 0xff) == 0) {
|
||||
+ printk("Enabling BCM4710A0 cache workarounds.\n");
|
||||
+ bcm4710 = 1;
|
||||
+ } else
|
||||
+#endif
|
||||
+ bcm4710 = 0;
|
||||
+
|
||||
probe_pcache();
|
||||
probe_vcache();
|
||||
setup_scache();
|
||||
@@ -1935,7 +1967,15 @@ void r4k_cache_init(void)
|
||||
*/
|
||||
local_r4k___flush_cache_all(NULL);
|
||||
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ {
|
||||
+ static void (*_coherency_setup)(void);
|
||||
+ _coherency_setup = (void (*)(void)) KSEG1ADDR(coherency_setup);
|
||||
+ _coherency_setup();
|
||||
+ }
|
||||
+#else
|
||||
coherency_setup();
|
||||
+#endif
|
||||
board_cache_error_setup = r4k_cache_error_setup;
|
||||
|
||||
/*
|
||||
--- a/arch/mips/mm/tlbex.c
|
||||
+++ b/arch/mips/mm/tlbex.c
|
||||
@@ -985,6 +985,9 @@ void build_get_pgde32(u32 **p, unsigned
|
||||
uasm_i_srl(p, ptr, ptr, SMP_CPUID_PTRSHIFT);
|
||||
uasm_i_addu(p, ptr, tmp, ptr);
|
||||
#else
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ uasm_i_nop(p);
|
||||
+#endif
|
||||
UASM_i_LA_mostly(p, ptr, pgdc);
|
||||
#endif
|
||||
uasm_i_mfc0(p, tmp, C0_BADVADDR); /* get faulting address */
|
||||
@@ -1347,6 +1350,9 @@ static void build_r4000_tlb_refill_handl
|
||||
#ifdef CONFIG_64BIT
|
||||
build_get_pmde64(&p, &l, &r, K0, K1); /* get pmd in K1 */
|
||||
#else
|
||||
+# ifdef CONFIG_BCM47XX
|
||||
+ uasm_i_nop(&p);
|
||||
+# endif
|
||||
build_get_pgde32(&p, K0, K1); /* get pgd in K1 */
|
||||
#endif
|
||||
|
||||
@@ -1358,6 +1364,9 @@ static void build_r4000_tlb_refill_handl
|
||||
build_update_entries(&p, K0, K1);
|
||||
build_tlb_write_entry(&p, &l, &r, tlb_random);
|
||||
uasm_l_leave(&l, p);
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ uasm_i_nop(&p);
|
||||
+#endif
|
||||
uasm_i_eret(&p); /* return from trap */
|
||||
}
|
||||
#ifdef CONFIG_MIPS_HUGE_TLB_SUPPORT
|
||||
@@ -2059,6 +2068,9 @@ build_r4000_tlbchange_handler_head(u32 *
|
||||
#ifdef CONFIG_64BIT
|
||||
build_get_pmde64(p, l, r, wr.r1, wr.r2); /* get pmd in ptr */
|
||||
#else
|
||||
+# ifdef CONFIG_BCM47XX
|
||||
+ uasm_i_nop(p);
|
||||
+# endif
|
||||
build_get_pgde32(p, wr.r1, wr.r2); /* get pgd in ptr */
|
||||
#endif
|
||||
|
||||
@@ -2105,6 +2117,9 @@ build_r4000_tlbchange_handler_tail(u32 *
|
||||
build_tlb_write_entry(p, l, r, tlb_indexed);
|
||||
uasm_l_leave(l, *p);
|
||||
build_restore_work_registers(p);
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+ uasm_i_nop(p);
|
||||
+#endif
|
||||
uasm_i_eret(p); /* return from trap */
|
||||
|
||||
#ifdef CONFIG_64BIT
|
||||
78
target/linux/bcm47xx/patches-5.15/160-kmap_coherent.patch
Normal file
78
target/linux/bcm47xx/patches-5.15/160-kmap_coherent.patch
Normal file
@ -0,0 +1,78 @@
|
||||
From: Jeff Hansen <jhansen@cardaccess-inc.com>
|
||||
Subject: [PATCH] kmap_coherent
|
||||
|
||||
On ASUS WL-500gP there are some "Data bus error"s when executing simple
|
||||
commands liks "ps" or "cat /proc/1/cmdline".
|
||||
|
||||
This fixes OpenWrt ticket #1485: https://dev.openwrt.org/ticket/1485
|
||||
---
|
||||
--- a/arch/mips/include/asm/cpu-features.h
|
||||
+++ b/arch/mips/include/asm/cpu-features.h
|
||||
@@ -240,6 +240,9 @@
|
||||
#ifndef cpu_has_pindexed_dcache
|
||||
#define cpu_has_pindexed_dcache (cpu_data[0].dcache.flags & MIPS_CACHE_PINDEX)
|
||||
#endif
|
||||
+#ifndef cpu_use_kmap_coherent
|
||||
+#define cpu_use_kmap_coherent 1
|
||||
+#endif
|
||||
|
||||
/*
|
||||
* I-Cache snoops remote store. This only matters on SMP. Some multiprocessors
|
||||
--- a/arch/mips/include/asm/mach-bcm47xx/cpu-feature-overrides.h
|
||||
+++ b/arch/mips/include/asm/mach-bcm47xx/cpu-feature-overrides.h
|
||||
@@ -80,4 +80,6 @@
|
||||
#define cpu_scache_line_size() 0
|
||||
#define cpu_has_vz 0
|
||||
|
||||
+#define cpu_use_kmap_coherent 0
|
||||
+
|
||||
#endif /* __ASM_MACH_BCM47XX_CPU_FEATURE_OVERRIDES_H */
|
||||
--- a/arch/mips/mm/c-r4k.c
|
||||
+++ b/arch/mips/mm/c-r4k.c
|
||||
@@ -699,7 +699,7 @@ static inline void local_r4k_flush_cache
|
||||
map_coherent = (cpu_has_dc_aliases &&
|
||||
page_mapcount(page) &&
|
||||
!Page_dcache_dirty(page));
|
||||
- if (map_coherent)
|
||||
+ if (map_coherent && cpu_use_kmap_coherent)
|
||||
vaddr = kmap_coherent(page, addr);
|
||||
else
|
||||
vaddr = kmap_atomic(page);
|
||||
@@ -721,7 +721,7 @@ static inline void local_r4k_flush_cache
|
||||
}
|
||||
|
||||
if (vaddr) {
|
||||
- if (map_coherent)
|
||||
+ if (map_coherent && cpu_use_kmap_coherent)
|
||||
kunmap_coherent();
|
||||
else
|
||||
kunmap_atomic(vaddr);
|
||||
--- a/arch/mips/mm/init.c
|
||||
+++ b/arch/mips/mm/init.c
|
||||
@@ -172,7 +172,7 @@ void copy_user_highpage(struct page *to,
|
||||
void *vfrom, *vto;
|
||||
|
||||
vto = kmap_atomic(to);
|
||||
- if (cpu_has_dc_aliases &&
|
||||
+ if (cpu_has_dc_aliases && cpu_use_kmap_coherent &&
|
||||
page_mapcount(from) && !Page_dcache_dirty(from)) {
|
||||
vfrom = kmap_coherent(from, vaddr);
|
||||
copy_page(vto, vfrom);
|
||||
@@ -194,7 +194,7 @@ void copy_to_user_page(struct vm_area_st
|
||||
struct page *page, unsigned long vaddr, void *dst, const void *src,
|
||||
unsigned long len)
|
||||
{
|
||||
- if (cpu_has_dc_aliases &&
|
||||
+ if (cpu_has_dc_aliases && cpu_use_kmap_coherent &&
|
||||
page_mapcount(page) && !Page_dcache_dirty(page)) {
|
||||
void *vto = kmap_coherent(page, vaddr) + (vaddr & ~PAGE_MASK);
|
||||
memcpy(vto, src, len);
|
||||
@@ -212,7 +212,7 @@ void copy_from_user_page(struct vm_area_
|
||||
struct page *page, unsigned long vaddr, void *dst, const void *src,
|
||||
unsigned long len)
|
||||
{
|
||||
- if (cpu_has_dc_aliases &&
|
||||
+ if (cpu_has_dc_aliases && cpu_use_kmap_coherent &&
|
||||
page_mapcount(page) && !Page_dcache_dirty(page)) {
|
||||
void *vfrom = kmap_coherent(page, vaddr) + (vaddr & ~PAGE_MASK);
|
||||
memcpy(dst, vfrom, len);
|
||||
@ -0,0 +1,121 @@
|
||||
From b36f694256f41bc71571f467646d015dda128d14 Mon Sep 17 00:00:00 2001
|
||||
From: Hauke Mehrtens <hauke@hauke-m.de>
|
||||
Date: Sat, 9 Nov 2013 17:03:59 +0100
|
||||
Subject: [PATCH 210/210] b44: register adm switch
|
||||
|
||||
---
|
||||
drivers/net/ethernet/broadcom/b44.c | 57 +++++++++++++++++++++++++++++++++++
|
||||
drivers/net/ethernet/broadcom/b44.h | 3 ++
|
||||
2 files changed, 60 insertions(+)
|
||||
|
||||
--- a/drivers/net/ethernet/broadcom/b44.c
|
||||
+++ b/drivers/net/ethernet/broadcom/b44.c
|
||||
@@ -31,6 +31,8 @@
|
||||
#include <linux/ssb/ssb.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/phy.h>
|
||||
+#include <linux/platform_device.h>
|
||||
+#include <linux/platform_data/adm6996-gpio.h>
|
||||
|
||||
#include <linux/uaccess.h>
|
||||
#include <asm/io.h>
|
||||
@@ -2243,6 +2245,69 @@ static void b44_adjust_link(struct net_d
|
||||
}
|
||||
}
|
||||
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+static int b44_register_adm_switch(struct b44 *bp)
|
||||
+{
|
||||
+ int gpio;
|
||||
+ struct platform_device *pdev;
|
||||
+ struct adm6996_gpio_platform_data adm_data = {0};
|
||||
+ struct platform_device_info info = {0};
|
||||
+
|
||||
+ adm_data.model = ADM6996L;
|
||||
+ gpio = bcm47xx_nvram_gpio_pin("adm_eecs");
|
||||
+ if (gpio >= 0)
|
||||
+ adm_data.eecs = gpio;
|
||||
+ else
|
||||
+ adm_data.eecs = 2;
|
||||
+
|
||||
+ gpio = bcm47xx_nvram_gpio_pin("adm_eesk");
|
||||
+ if (gpio >= 0)
|
||||
+ adm_data.eesk = gpio;
|
||||
+ else
|
||||
+ adm_data.eesk = 3;
|
||||
+
|
||||
+ gpio = bcm47xx_nvram_gpio_pin("adm_eedi");
|
||||
+ if (gpio >= 0)
|
||||
+ adm_data.eedi = gpio;
|
||||
+ else
|
||||
+ adm_data.eedi = 4;
|
||||
+
|
||||
+ /*
|
||||
+ * We ignore the "adm_rc" GPIO here. The driver does not use it,
|
||||
+ * and it conflicts with the Reset button GPIO on the Linksys WRT54GSv1.
|
||||
+ */
|
||||
+
|
||||
+ info.parent = bp->sdev->dev;
|
||||
+ info.name = "adm6996_gpio";
|
||||
+ info.id = -1;
|
||||
+ info.data = &adm_data;
|
||||
+ info.size_data = sizeof(adm_data);
|
||||
+
|
||||
+ if (!bp->adm_switch) {
|
||||
+ pdev = platform_device_register_full(&info);
|
||||
+ if (IS_ERR(pdev))
|
||||
+ return PTR_ERR(pdev);
|
||||
+
|
||||
+ bp->adm_switch = pdev;
|
||||
+ }
|
||||
+ return 0;
|
||||
+}
|
||||
+static void b44_unregister_adm_switch(struct b44 *bp)
|
||||
+{
|
||||
+ if (bp->adm_switch)
|
||||
+ platform_device_unregister(bp->adm_switch);
|
||||
+}
|
||||
+#else
|
||||
+static int b44_register_adm_switch(struct b44 *bp)
|
||||
+{
|
||||
+ return 0;
|
||||
+}
|
||||
+static void b44_unregister_adm_switch(struct b44 *bp)
|
||||
+{
|
||||
+
|
||||
+}
|
||||
+#endif /* CONFIG_BCM47XX */
|
||||
+
|
||||
static int b44_register_phy_one(struct b44 *bp)
|
||||
{
|
||||
__ETHTOOL_DECLARE_LINK_MODE_MASK(mask) = { 0, };
|
||||
@@ -2279,6 +2344,9 @@ static int b44_register_phy_one(struct b
|
||||
if (!mdiobus_is_registered_device(bp->mii_bus, bp->phy_addr) &&
|
||||
(sprom->boardflags_lo & (B44_BOARDFLAG_ROBO | B44_BOARDFLAG_ADM))) {
|
||||
|
||||
+ if (sprom->boardflags_lo & B44_BOARDFLAG_ADM)
|
||||
+ b44_register_adm_switch(bp);
|
||||
+
|
||||
dev_info(sdev->dev,
|
||||
"could not find PHY at %i, use fixed one\n",
|
||||
bp->phy_addr);
|
||||
@@ -2473,6 +2541,7 @@ static void b44_remove_one(struct ssb_de
|
||||
unregister_netdev(dev);
|
||||
if (bp->flags & B44_FLAG_EXTERNAL_PHY)
|
||||
b44_unregister_phy_one(bp);
|
||||
+ b44_unregister_adm_switch(bp);
|
||||
ssb_device_disable(sdev, 0);
|
||||
ssb_bus_may_powerdown(sdev->bus);
|
||||
netif_napi_del(&bp->napi);
|
||||
--- a/drivers/net/ethernet/broadcom/b44.h
|
||||
+++ b/drivers/net/ethernet/broadcom/b44.h
|
||||
@@ -408,6 +408,9 @@ struct b44 {
|
||||
struct mii_bus *mii_bus;
|
||||
int old_link;
|
||||
struct mii_if_info mii_if;
|
||||
+
|
||||
+ /* platform device for associated switch */
|
||||
+ struct platform_device *adm_switch;
|
||||
};
|
||||
|
||||
#endif /* _B44_H */
|
||||
54
target/linux/bcm47xx/patches-5.15/210-b44_phy_fix.patch
Normal file
54
target/linux/bcm47xx/patches-5.15/210-b44_phy_fix.patch
Normal file
@ -0,0 +1,54 @@
|
||||
--- a/drivers/net/ethernet/broadcom/b44.c
|
||||
+++ b/drivers/net/ethernet/broadcom/b44.c
|
||||
@@ -429,10 +429,34 @@ static void b44_wap54g10_workaround(stru
|
||||
error:
|
||||
pr_warn("PHY: cannot reset MII transceiver isolate bit\n");
|
||||
}
|
||||
+
|
||||
+static void b44_bcm47xx_workarounds(struct b44 *bp)
|
||||
+{
|
||||
+ char buf[20];
|
||||
+ struct ssb_device *sdev = bp->sdev;
|
||||
+
|
||||
+ /* Toshiba WRC-1000, Siemens SE505 v1, Askey RT-210W, RT-220W */
|
||||
+ if (sdev->bus->sprom.board_num == 100) {
|
||||
+ bp->phy_addr = B44_PHY_ADDR_NO_LOCAL_PHY;
|
||||
+ } else {
|
||||
+ /* WL-HDD */
|
||||
+ if (bcm47xx_nvram_getenv("hardware_version", buf, sizeof(buf)) >= 0 &&
|
||||
+ !strncmp(buf, "WL300-", strlen("WL300-"))) {
|
||||
+ if (sdev->bus->sprom.et0phyaddr == 0 &&
|
||||
+ sdev->bus->sprom.et1phyaddr == 1)
|
||||
+ bp->phy_addr = B44_PHY_ADDR_NO_LOCAL_PHY;
|
||||
+ }
|
||||
+ }
|
||||
+ return;
|
||||
+}
|
||||
#else
|
||||
static inline void b44_wap54g10_workaround(struct b44 *bp)
|
||||
{
|
||||
}
|
||||
+
|
||||
+static inline void b44_bcm47xx_workarounds(struct b44 *bp)
|
||||
+{
|
||||
+}
|
||||
#endif
|
||||
|
||||
static int b44_setup_phy(struct b44 *bp)
|
||||
@@ -441,6 +465,7 @@ static int b44_setup_phy(struct b44 *bp)
|
||||
int err;
|
||||
|
||||
b44_wap54g10_workaround(bp);
|
||||
+ b44_bcm47xx_workarounds(bp);
|
||||
|
||||
if (bp->flags & B44_FLAG_EXTERNAL_PHY)
|
||||
return 0;
|
||||
@@ -2173,6 +2198,8 @@ static int b44_get_invariants(struct b44
|
||||
* valid PHY address. */
|
||||
bp->phy_addr &= 0x1F;
|
||||
|
||||
+ b44_bcm47xx_workarounds(bp);
|
||||
+
|
||||
memcpy(bp->dev->dev_addr, addr, ETH_ALEN);
|
||||
|
||||
if (!is_valid_ether_addr(&bp->dev->dev_addr[0])){
|
||||
@ -0,0 +1,25 @@
|
||||
This prevents the options from being delete with make kernel_oldconfig.
|
||||
---
|
||||
drivers/ssb/Kconfig | 2 ++
|
||||
1 file changed, 2 insertions(+)
|
||||
|
||||
--- a/drivers/bcma/Kconfig
|
||||
+++ b/drivers/bcma/Kconfig
|
||||
@@ -32,6 +32,7 @@ config BCMA_HOST_PCI
|
||||
config BCMA_HOST_SOC
|
||||
bool "Support for BCMA in a SoC"
|
||||
depends on HAS_IOMEM
|
||||
+ select USB_HCD_BCMA if USB_EHCI_HCD || USB_OHCI_HCD
|
||||
help
|
||||
Host interface for a Broadcom AIX bus directly mapped into
|
||||
the memory. This only works with the Broadcom SoCs from the
|
||||
--- a/drivers/ssb/Kconfig
|
||||
+++ b/drivers/ssb/Kconfig
|
||||
@@ -136,6 +136,7 @@ config SSB_SFLASH
|
||||
config SSB_EMBEDDED
|
||||
bool
|
||||
depends on SSB_DRIVER_MIPS && SSB_PCICORE_HOSTMODE
|
||||
+ select USB_HCD_SSB if USB_EHCI_HCD || USB_OHCI_HCD
|
||||
default y
|
||||
|
||||
config SSB_DRIVER_EXTIF
|
||||
21
target/linux/bcm47xx/patches-5.15/300-fork_cacheflush.patch
Normal file
21
target/linux/bcm47xx/patches-5.15/300-fork_cacheflush.patch
Normal file
@ -0,0 +1,21 @@
|
||||
From: Wolfram Joost <dbox2@frokaschwei.de>
|
||||
Subject: [PATCH] fork_cacheflush
|
||||
|
||||
On ASUS WL-500gP there are many unexpected "Segmentation fault"s that
|
||||
seem to be caused by a kernel. They can be avoided by:
|
||||
1) Disabling highpage
|
||||
2) Using flush_cache_mm in flush_cache_dup_mm
|
||||
|
||||
For details see OpenWrt ticket #2035 https://dev.openwrt.org/ticket/2035
|
||||
---
|
||||
--- a/arch/mips/include/asm/cacheflush.h
|
||||
+++ b/arch/mips/include/asm/cacheflush.h
|
||||
@@ -46,7 +46,7 @@
|
||||
extern void (*flush_cache_all)(void);
|
||||
extern void (*__flush_cache_all)(void);
|
||||
extern void (*flush_cache_mm)(struct mm_struct *mm);
|
||||
-#define flush_cache_dup_mm(mm) do { (void) (mm); } while (0)
|
||||
+#define flush_cache_dup_mm(mm) flush_cache_mm(mm)
|
||||
extern void (*flush_cache_range)(struct vm_area_struct *vma,
|
||||
unsigned long start, unsigned long end);
|
||||
extern void (*flush_cache_page)(struct vm_area_struct *vma, unsigned long page, unsigned long pfn);
|
||||
74
target/linux/bcm47xx/patches-5.15/310-no_highpage.patch
Normal file
74
target/linux/bcm47xx/patches-5.15/310-no_highpage.patch
Normal file
@ -0,0 +1,74 @@
|
||||
From: Jeff Hansen <jhansen@cardaccess-inc.com>
|
||||
Subject: [PATCH] no highpage
|
||||
|
||||
On ASUS WL-500gP there are many unexpected "Segmentation fault"s that
|
||||
seem to be caused by a kernel. They can be avoided by:
|
||||
1) Disabling highpage
|
||||
2) Using flush_cache_mm in flush_cache_dup_mm
|
||||
|
||||
For details see OpenWrt ticket #2035 https://dev.openwrt.org/ticket/2035
|
||||
---
|
||||
--- a/arch/mips/include/asm/page.h
|
||||
+++ b/arch/mips/include/asm/page.h
|
||||
@@ -71,6 +71,7 @@ static inline unsigned int page_size_ftl
|
||||
#endif /* CONFIG_MIPS_HUGE_TLB_SUPPORT */
|
||||
|
||||
#include <linux/pfn.h>
|
||||
+#include <asm/cpu-features.h>
|
||||
|
||||
extern void build_clear_page(void);
|
||||
extern void build_copy_page(void);
|
||||
@@ -110,11 +111,16 @@ static inline void clear_user_page(void
|
||||
flush_data_cache_page((unsigned long)addr);
|
||||
}
|
||||
|
||||
-struct vm_area_struct;
|
||||
-extern void copy_user_highpage(struct page *to, struct page *from,
|
||||
- unsigned long vaddr, struct vm_area_struct *vma);
|
||||
+static inline void copy_user_page(void *vto, void *vfrom, unsigned long vaddr,
|
||||
+ struct page *to)
|
||||
+{
|
||||
+ extern void (*flush_data_cache_page)(unsigned long addr);
|
||||
|
||||
-#define __HAVE_ARCH_COPY_USER_HIGHPAGE
|
||||
+ copy_page(vto, vfrom);
|
||||
+ if (!cpu_has_ic_fills_f_dc ||
|
||||
+ pages_do_alias((unsigned long)vto, vaddr & PAGE_MASK))
|
||||
+ flush_data_cache_page((unsigned long)vto);
|
||||
+}
|
||||
|
||||
/*
|
||||
* These are used to make use of C type-checking..
|
||||
--- a/arch/mips/mm/init.c
|
||||
+++ b/arch/mips/mm/init.c
|
||||
@@ -166,30 +166,6 @@ void kunmap_coherent(void)
|
||||
preempt_enable();
|
||||
}
|
||||
|
||||
-void copy_user_highpage(struct page *to, struct page *from,
|
||||
- unsigned long vaddr, struct vm_area_struct *vma)
|
||||
-{
|
||||
- void *vfrom, *vto;
|
||||
-
|
||||
- vto = kmap_atomic(to);
|
||||
- if (cpu_has_dc_aliases && cpu_use_kmap_coherent &&
|
||||
- page_mapcount(from) && !Page_dcache_dirty(from)) {
|
||||
- vfrom = kmap_coherent(from, vaddr);
|
||||
- copy_page(vto, vfrom);
|
||||
- kunmap_coherent();
|
||||
- } else {
|
||||
- vfrom = kmap_atomic(from);
|
||||
- copy_page(vto, vfrom);
|
||||
- kunmap_atomic(vfrom);
|
||||
- }
|
||||
- if ((!cpu_has_ic_fills_f_dc) ||
|
||||
- pages_do_alias((unsigned long)vto, vaddr & PAGE_MASK))
|
||||
- flush_data_cache_page((unsigned long)vto);
|
||||
- kunmap_atomic(vto);
|
||||
- /* Make sure this page is cleared on other CPU's too before using it */
|
||||
- smp_wmb();
|
||||
-}
|
||||
-
|
||||
void copy_to_user_page(struct vm_area_struct *vma,
|
||||
struct page *page, unsigned long vaddr, void *dst, const void *src,
|
||||
unsigned long len)
|
||||
@ -0,0 +1,89 @@
|
||||
From 3829e4f10a232964cc728c0479c8097922e5e073 Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 6 Jan 2022 19:51:38 -0800
|
||||
Subject: [PATCH] MIPS: BCM47XX: Add board entry for Linksys WRT320N v1
|
||||
|
||||
This router is based on a Broadcom BCM4717A1 chipset and supports
|
||||
802.11n Wi-Fi. Add a board entry for that router and register LEDs and
|
||||
buttons accordingly.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/board.c | 1 +
|
||||
arch/mips/bcm47xx/buttons.c | 9 +++++++++
|
||||
arch/mips/bcm47xx/leds.c | 10 ++++++++++
|
||||
arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h | 1 +
|
||||
4 files changed, 21 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/board.c
|
||||
+++ b/arch/mips/bcm47xx/board.c
|
||||
@@ -141,6 +141,7 @@ struct bcm47xx_board_type_list2 bcm47xx_
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT300NV11, "Linksys WRT300N V1.1"}, "WRT300N", "1.1"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT310NV1, "Linksys WRT310N V1"}, "WRT310N", "1.0"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT310NV2, "Linksys WRT310N V2"}, "WRT310N", "2.0"},
|
||||
+ {{BCM47XX_BOARD_LINKSYS_WRT320N_V1, "Linksys WRT320N V1"}, "WRT320N", "1.0"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT54G3GV2, "Linksys WRT54G3GV2-VF"}, "WRT54G3GV2-VF", "1.0"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT610NV1, "Linksys WRT610N V1"}, "WRT610N", "1.0"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT610NV2, "Linksys WRT610N V2"}, "WRT610N", "2.0"},
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -277,6 +277,12 @@ bcm47xx_buttons_linksys_wrt310nv1[] __in
|
||||
};
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_linksys_wrt320n_v1[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(5, KEY_WPS_BUTTON),
|
||||
+ BCM47XX_GPIO_KEY(8, KEY_RESTART),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_linksys_wrt54g3gv2[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(5, KEY_WIMAX),
|
||||
BCM47XX_GPIO_KEY(6, KEY_RESTART),
|
||||
@@ -608,6 +614,9 @@ int __init bcm47xx_buttons_register(void
|
||||
case BCM47XX_BOARD_LINKSYS_WRT310NV1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt310nv1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_LINKSYS_WRT320N_V1:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt320n_v1);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_LINKSYS_WRT54G3GV2:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt54g3gv2);
|
||||
break;
|
||||
--- a/arch/mips/bcm47xx/leds.c
|
||||
+++ b/arch/mips/bcm47xx/leds.c
|
||||
@@ -314,6 +314,13 @@ bcm47xx_leds_linksys_wrt310nv1[] __initc
|
||||
};
|
||||
|
||||
static const struct gpio_led
|
||||
+bcm47xx_leds_linksys_wrt320n_v1[] __initconst = {
|
||||
+ BCM47XX_GPIO_LED(1, "blue", "wlan", 1, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+ BCM47XX_GPIO_LED(2, "blue", "power", 0, LEDS_GPIO_DEFSTATE_ON),
|
||||
+ BCM47XX_GPIO_LED(4, "amber", "wps", 1, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_led
|
||||
bcm47xx_leds_linksys_wrt54g_generic[] __initconst = {
|
||||
BCM47XX_GPIO_LED(0, "unk", "dmz", 1, LEDS_GPIO_DEFSTATE_OFF),
|
||||
BCM47XX_GPIO_LED(1, "unk", "power", 0, LEDS_GPIO_DEFSTATE_ON),
|
||||
@@ -689,6 +696,9 @@ void __init bcm47xx_leds_register(void)
|
||||
case BCM47XX_BOARD_LINKSYS_WRT310NV1:
|
||||
bcm47xx_set_pdata(bcm47xx_leds_linksys_wrt310nv1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_LINKSYS_WRT320N_V1:
|
||||
+ bcm47xx_set_pdata(bcm47xx_leds_linksys_wrt320n_v1);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_LINKSYS_WRT54G3GV2:
|
||||
bcm47xx_set_pdata(bcm47xx_leds_linksys_wrt54g3gv2);
|
||||
break;
|
||||
--- a/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
+++ b/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
@@ -72,6 +72,7 @@ enum bcm47xx_board {
|
||||
BCM47XX_BOARD_LINKSYS_WRT300NV11,
|
||||
BCM47XX_BOARD_LINKSYS_WRT310NV1,
|
||||
BCM47XX_BOARD_LINKSYS_WRT310NV2,
|
||||
+ BCM47XX_BOARD_LINKSYS_WRT320N_V1,
|
||||
BCM47XX_BOARD_LINKSYS_WRT54G3GV2,
|
||||
BCM47XX_BOARD_LINKSYS_WRT54G_TYPE_0101,
|
||||
BCM47XX_BOARD_LINKSYS_WRT54G_TYPE_0467,
|
||||
@ -0,0 +1,60 @@
|
||||
From 15e690af5cc3cd8f5d14ee2aa3a093f80196110e Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 6 Jan 2022 19:51:40 -0800
|
||||
Subject: [PATCH] MIPS: BCM47XX: Add support for Netgear R6300 v1
|
||||
|
||||
Add support for the Netgear R6300 v1 Wi-Fi router using a Broadcom
|
||||
BCM4706 chipset and supporting 802.11n and 802.11ac.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/board.c | 1 +
|
||||
arch/mips/bcm47xx/buttons.c | 8 ++++++++
|
||||
arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h | 1 +
|
||||
3 files changed, 10 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/board.c
|
||||
+++ b/arch/mips/bcm47xx/board.c
|
||||
@@ -162,6 +162,7 @@ struct bcm47xx_board_type_list1 bcm47xx_
|
||||
{{BCM47XX_BOARD_LUXUL_XWR_600_V1, "Luxul XWR-600 V1"}, "luxul_xwr600_v1"},
|
||||
{{BCM47XX_BOARD_LUXUL_XWR_1750_V1, "Luxul XWR-1750 V1"}, "luxul_xwr1750_v1"},
|
||||
{{BCM47XX_BOARD_NETGEAR_R6200_V1, "Netgear R6200 V1"}, "U12H192T00_NETGEAR"},
|
||||
+ {{BCM47XX_BOARD_NETGEAR_R6300_V1, "Netgear R6300 V1"}, "U12H218T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614V8, "Netgear WGR614 V8"}, "U12H072T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614V9, "Netgear WGR614 V9"}, "U12H094T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614_V10, "Netgear WGR614 V10"}, "U12H139T01_NETGEAR"},
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -398,6 +398,11 @@ bcm47xx_buttons_netgear_r6200_v1[] __ini
|
||||
};
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_netgear_r6300_v1[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(6, KEY_RESTART),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_netgear_wndr3400v1[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(4, KEY_RESTART),
|
||||
BCM47XX_GPIO_KEY(6, KEY_WPS_BUTTON),
|
||||
@@ -683,6 +688,9 @@ int __init bcm47xx_buttons_register(void
|
||||
case BCM47XX_BOARD_NETGEAR_R6200_V1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_r6200_v1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_NETGEAR_R6300_V1:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_r6300_v1);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_NETGEAR_WNDR3400V1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wndr3400v1);
|
||||
break;
|
||||
--- a/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
+++ b/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
@@ -100,6 +100,7 @@ enum bcm47xx_board {
|
||||
BCM47XX_BOARD_MOTOROLA_WR850GV2V3,
|
||||
|
||||
BCM47XX_BOARD_NETGEAR_R6200_V1,
|
||||
+ BCM47XX_BOARD_NETGEAR_R6300_V1,
|
||||
BCM47XX_BOARD_NETGEAR_WGR614V8,
|
||||
BCM47XX_BOARD_NETGEAR_WGR614V9,
|
||||
BCM47XX_BOARD_NETGEAR_WGR614_V10,
|
||||
@ -0,0 +1,63 @@
|
||||
From 4da27b6d550427a0560a15df36de99cb17629216 Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 6 Jan 2022 19:51:41 -0800
|
||||
Subject: [PATCH] MIPS: BCM47XX: Add support for Netgear WN2500RP v1 & v2
|
||||
|
||||
Add support for the Netgear WN2500 RP v1 and v2 Wi-Fi range extenders
|
||||
based on the BCM5357 chipset and supporting 802.11n and 802.11ac.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/board.c | 2 ++
|
||||
arch/mips/bcm47xx/buttons.c | 9 +++++++++
|
||||
arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h | 2 ++
|
||||
3 files changed, 13 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/board.c
|
||||
+++ b/arch/mips/bcm47xx/board.c
|
||||
@@ -166,6 +166,8 @@ struct bcm47xx_board_type_list1 bcm47xx_
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614V8, "Netgear WGR614 V8"}, "U12H072T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614V9, "Netgear WGR614 V9"}, "U12H094T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WGR614_V10, "Netgear WGR614 V10"}, "U12H139T01_NETGEAR"},
|
||||
+ {{BCM47XX_BOARD_NETGEAR_WN2500RP_V1, "Netgear WN2500RP V1"}, "U12H197T00_NETGEAR"},
|
||||
+ {{BCM47XX_BOARD_NETGEAR_WN2500RP_V2, "Netgear WN2500RP V2"}, "U12H294T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNDR3300, "Netgear WNDR3300"}, "U12H093T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNDR3400V1, "Netgear WNDR3400 V1"}, "U12H155T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNDR3400V2, "Netgear WNDR3400 V2"}, "U12H187T00_NETGEAR"},
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -403,6 +403,12 @@ bcm47xx_buttons_netgear_r6300_v1[] __ini
|
||||
};
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_netgear_wn2500rp_v1[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(12, KEY_RESTART),
|
||||
+ BCM47XX_GPIO_KEY(31, KEY_WPS_BUTTON),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_netgear_wndr3400v1[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(4, KEY_RESTART),
|
||||
BCM47XX_GPIO_KEY(6, KEY_WPS_BUTTON),
|
||||
@@ -691,6 +697,9 @@ int __init bcm47xx_buttons_register(void
|
||||
case BCM47XX_BOARD_NETGEAR_R6300_V1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_r6300_v1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_NETGEAR_WN2500RP_V1:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wn2500rp_v1);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_NETGEAR_WNDR3400V1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wndr3400v1);
|
||||
break;
|
||||
--- a/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
+++ b/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
@@ -104,6 +104,8 @@ enum bcm47xx_board {
|
||||
BCM47XX_BOARD_NETGEAR_WGR614V8,
|
||||
BCM47XX_BOARD_NETGEAR_WGR614V9,
|
||||
BCM47XX_BOARD_NETGEAR_WGR614_V10,
|
||||
+ BCM47XX_BOARD_NETGEAR_WN2500RP_V1,
|
||||
+ BCM47XX_BOARD_NETGEAR_WN2500RP_V2,
|
||||
BCM47XX_BOARD_NETGEAR_WNDR3300,
|
||||
BCM47XX_BOARD_NETGEAR_WNDR3400V1,
|
||||
BCM47XX_BOARD_NETGEAR_WNDR3400V2,
|
||||
@ -0,0 +1,109 @@
|
||||
From c022e87162219d67d687df22c977d1c2fc95fb42 Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 14 Jul 2022 14:13:01 -0700
|
||||
Subject: [PATCH] MIPS: BCM47XX: Add support for Netgear WNR3500L v2
|
||||
|
||||
Add support for the Netgear WNR3500L v2 router based on the BCM47186
|
||||
chipset and supporting 802.11n Wi-Fi.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/board.c | 2 ++
|
||||
arch/mips/bcm47xx/buttons.c | 10 ++++++++++
|
||||
arch/mips/bcm47xx/leds.c | 11 +++++++++++
|
||||
arch/mips/bcm47xx/workarounds.c | 1 +
|
||||
arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h | 1 +
|
||||
5 files changed, 25 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/board.c
|
||||
+++ b/arch/mips/bcm47xx/board.c
|
||||
@@ -181,6 +181,7 @@ struct bcm47xx_board_type_list1 bcm47xx_
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR1000_V3, "Netgear WNR1000 V3"}, "U12H139T50_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR2000, "Netgear WNR2000"}, "U12H114T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR3500L, "Netgear WNR3500L"}, "U12H136T99_NETGEAR"},
|
||||
+ {{BCM47XX_BOARD_NETGEAR_WNR3500L_V2, "Netgear WNR3500L V2"}, "U12H172T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR3500U, "Netgear WNR3500U"}, "U12H136T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR3500V2, "Netgear WNR3500 V2"}, "U12H127T00_NETGEAR"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR3500V2VC, "Netgear WNR3500 V2vc"}, "U12H127T70_NETGEAR"},
|
||||
@@ -195,6 +196,7 @@ struct bcm47xx_board_type_list3 bcm47xx_
|
||||
{{BCM47XX_BOARD_PHICOMM_M1, "Phicomm M1"}, "0x0590", "80", "0x1104"},
|
||||
{{BCM47XX_BOARD_ZTE_H218N, "ZTE H218N"}, "0x053d", "1234", "0x1305"},
|
||||
{{BCM47XX_BOARD_NETGEAR_WNR3500L, "Netgear WNR3500L"}, "0x04CF", "3500", "02"},
|
||||
+ {{BCM47XX_BOARD_NETGEAR_WNR3500L_V2, "Netgear WNR3500L V2"}, "0x052b", "3500L", "02"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT54G_TYPE_0101, "Linksys WRT54G/GS/GL"}, "0x0101", "42", "0x10"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT54G_TYPE_0467, "Linksys WRT54G/GS/GL"}, "0x0467", "42", "0x10"},
|
||||
{{BCM47XX_BOARD_LINKSYS_WRT54G_TYPE_0708, "Linksys WRT54G/GS/GL"}, "0x0708", "42", "0x10"},
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -448,6 +448,13 @@ bcm47xx_buttons_netgear_wnr3500lv1[] __i
|
||||
};
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_netgear_wnr3500lv2[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(4, KEY_RESTART),
|
||||
+ BCM47XX_GPIO_KEY(6, KEY_WPS_BUTTON),
|
||||
+ BCM47XX_GPIO_KEY(8, KEY_RFKILL),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_netgear_wnr834bv2[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(6, KEY_RESTART),
|
||||
};
|
||||
@@ -718,6 +725,9 @@ int __init bcm47xx_buttons_register(void
|
||||
case BCM47XX_BOARD_NETGEAR_WNR3500L:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wnr3500lv1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_NETGEAR_WNR3500L_V2:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wnr3500lv2);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_NETGEAR_WNR834BV2:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_netgear_wnr834bv2);
|
||||
break;
|
||||
--- a/arch/mips/bcm47xx/leds.c
|
||||
+++ b/arch/mips/bcm47xx/leds.c
|
||||
@@ -520,6 +520,14 @@ bcm47xx_leds_netgear_wnr3500lv1[] __init
|
||||
};
|
||||
|
||||
static const struct gpio_led
|
||||
+bcm47xx_leds_netgear_wnr3500lv2[] __initconst = {
|
||||
+ BCM47XX_GPIO_LED(0, "blue", "wlan", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+ BCM47XX_GPIO_LED(1, "green", "wps", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+ BCM47XX_GPIO_LED(3, "green", "power", 0, LEDS_GPIO_DEFSTATE_ON),
|
||||
+ BCM47XX_GPIO_LED(7, "amber", "power", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_led
|
||||
bcm47xx_leds_netgear_wnr834bv2[] __initconst = {
|
||||
BCM47XX_GPIO_LED(2, "green", "power", 0, LEDS_GPIO_DEFSTATE_ON),
|
||||
BCM47XX_GPIO_LED(3, "amber", "power", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
@@ -780,6 +788,9 @@ void __init bcm47xx_leds_register(void)
|
||||
case BCM47XX_BOARD_NETGEAR_WNR3500L:
|
||||
bcm47xx_set_pdata(bcm47xx_leds_netgear_wnr3500lv1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_NETGEAR_WNR3500L_V2:
|
||||
+ bcm47xx_set_pdata(bcm47xx_leds_netgear_wnr3500lv2);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_NETGEAR_WNR834BV2:
|
||||
bcm47xx_set_pdata(bcm47xx_leds_netgear_wnr834bv2);
|
||||
break;
|
||||
--- a/arch/mips/bcm47xx/workarounds.c
|
||||
+++ b/arch/mips/bcm47xx/workarounds.c
|
||||
@@ -22,6 +22,7 @@ void __init bcm47xx_workarounds(void)
|
||||
|
||||
switch (board) {
|
||||
case BCM47XX_BOARD_NETGEAR_WNR3500L:
|
||||
+ case BCM47XX_BOARD_NETGEAR_WNR3500L_V2:
|
||||
bcm47xx_workarounds_enable_usb_power(12);
|
||||
break;
|
||||
case BCM47XX_BOARD_NETGEAR_WNDR3400V2:
|
||||
--- a/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
+++ b/arch/mips/include/asm/mach-bcm47xx/bcm47xx_board.h
|
||||
@@ -118,6 +118,7 @@ enum bcm47xx_board {
|
||||
BCM47XX_BOARD_NETGEAR_WNR1000_V3,
|
||||
BCM47XX_BOARD_NETGEAR_WNR2000,
|
||||
BCM47XX_BOARD_NETGEAR_WNR3500L,
|
||||
+ BCM47XX_BOARD_NETGEAR_WNR3500L_V2,
|
||||
BCM47XX_BOARD_NETGEAR_WNR3500U,
|
||||
BCM47XX_BOARD_NETGEAR_WNR3500V2,
|
||||
BCM47XX_BOARD_NETGEAR_WNR3500V2VC,
|
||||
@ -0,0 +1,67 @@
|
||||
From aecf89f2f8e8a604c33085c230a1f04ea325de64 Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 6 Jan 2022 19:51:39 -0800
|
||||
Subject: [PATCH] MIPS: BCM47XX: Add LEDs and buttons for Asus RTN-10U
|
||||
|
||||
Add the definitions for the buttons and LEDs used on the Asus RTN-10U
|
||||
router.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/buttons.c | 9 +++++++++
|
||||
arch/mips/bcm47xx/leds.c | 11 +++++++++++
|
||||
2 files changed, 20 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -27,6 +27,12 @@
|
||||
/* Asus */
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_asus_rtn10u[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(20, KEY_WPS_BUTTON),
|
||||
+ BCM47XX_GPIO_KEY(21, KEY_RESTART),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_asus_rtn12[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(0, KEY_WPS_BUTTON),
|
||||
BCM47XX_GPIO_KEY(1, KEY_RESTART),
|
||||
@@ -502,6 +508,9 @@ int __init bcm47xx_buttons_register(void
|
||||
int err;
|
||||
|
||||
switch (board) {
|
||||
+ case BCM47XX_BOARD_ASUS_RTN10U:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_asus_rtn10u);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_ASUS_RTN12:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_asus_rtn12);
|
||||
break;
|
||||
--- a/arch/mips/bcm47xx/leds.c
|
||||
+++ b/arch/mips/bcm47xx/leds.c
|
||||
@@ -30,6 +30,14 @@
|
||||
/* Asus */
|
||||
|
||||
static const struct gpio_led
|
||||
+bcm47xx_leds_asus_rtn10u[] __initconst = {
|
||||
+ BCM47XX_GPIO_LED(5, "green", "wlan", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+ BCM47XX_GPIO_LED(6, "green", "power", 1, LEDS_GPIO_DEFSTATE_ON),
|
||||
+ BCM47XX_GPIO_LED(7, "green", "wps", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+ BCM47XX_GPIO_LED(8, "green", "usb", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_led
|
||||
bcm47xx_leds_asus_rtn12[] __initconst = {
|
||||
BCM47XX_GPIO_LED(2, "unk", "power", 1, LEDS_GPIO_DEFSTATE_ON),
|
||||
BCM47XX_GPIO_LED(7, "unk", "wlan", 0, LEDS_GPIO_DEFSTATE_OFF),
|
||||
@@ -571,6 +579,9 @@ void __init bcm47xx_leds_register(void)
|
||||
enum bcm47xx_board board = bcm47xx_board_get();
|
||||
|
||||
switch (board) {
|
||||
+ case BCM47XX_BOARD_ASUS_RTN10U:
|
||||
+ bcm47xx_set_pdata(bcm47xx_leds_asus_rtn10u);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_ASUS_RTN12:
|
||||
bcm47xx_set_pdata(bcm47xx_leds_asus_rtn12);
|
||||
break;
|
||||
@ -0,0 +1,40 @@
|
||||
From eea175eedf3e2f71b9538d21e643e7a1be4923df Mon Sep 17 00:00:00 2001
|
||||
From: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Date: Thu, 6 Jan 2022 19:51:37 -0800
|
||||
Subject: [PATCH] MIPS: BCM47XX: Define Linksys WRT310N V2 buttons
|
||||
|
||||
Update the buttons registration code to register the two buttons (WPS,
|
||||
system rester) using the existing BCM47XX_BOARD_LINKSYS_WRT310NV2 board
|
||||
entry.
|
||||
|
||||
Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
|
||||
Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de>
|
||||
---
|
||||
arch/mips/bcm47xx/buttons.c | 9 +++++++++
|
||||
1 file changed, 9 insertions(+)
|
||||
|
||||
--- a/arch/mips/bcm47xx/buttons.c
|
||||
+++ b/arch/mips/bcm47xx/buttons.c
|
||||
@@ -289,6 +289,12 @@ bcm47xx_buttons_linksys_wrt320n_v1[] __i
|
||||
};
|
||||
|
||||
static const struct gpio_keys_button
|
||||
+bcm47xx_buttons_linksys_wrt310n_v2[] __initconst = {
|
||||
+ BCM47XX_GPIO_KEY(5, KEY_WPS_BUTTON),
|
||||
+ BCM47XX_GPIO_KEY(6, KEY_RESTART),
|
||||
+};
|
||||
+
|
||||
+static const struct gpio_keys_button
|
||||
bcm47xx_buttons_linksys_wrt54g3gv2[] __initconst = {
|
||||
BCM47XX_GPIO_KEY(5, KEY_WIMAX),
|
||||
BCM47XX_GPIO_KEY(6, KEY_RESTART),
|
||||
@@ -644,6 +650,9 @@ int __init bcm47xx_buttons_register(void
|
||||
case BCM47XX_BOARD_LINKSYS_WRT320N_V1:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt320n_v1);
|
||||
break;
|
||||
+ case BCM47XX_BOARD_LINKSYS_WRT310NV2:
|
||||
+ err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt310n_v2);
|
||||
+ break;
|
||||
case BCM47XX_BOARD_LINKSYS_WRT54G3GV2:
|
||||
err = bcm47xx_copy_bdata(bcm47xx_buttons_linksys_wrt54g3gv2);
|
||||
break;
|
||||
@ -0,0 +1,34 @@
|
||||
--- a/drivers/mtd/parsers/bcm47xxpart.c
|
||||
+++ b/drivers/mtd/parsers/bcm47xxpart.c
|
||||
@@ -98,6 +98,7 @@ static int bcm47xxpart_parse(struct mtd_
|
||||
int trx_num = 0; /* Number of found TRX partitions */
|
||||
int possible_nvram_sizes[] = { 0x8000, 0xF000, 0x10000, };
|
||||
int err;
|
||||
+ bool found_nvram = false;
|
||||
|
||||
/*
|
||||
* Some really old flashes (like AT45DB*) had smaller erasesize-s, but
|
||||
@@ -279,12 +280,23 @@ static int bcm47xxpart_parse(struct mtd_
|
||||
if (buf[0] == NVRAM_HEADER) {
|
||||
bcm47xxpart_add_part(&parts[curr_part++], "nvram",
|
||||
master->size - blocksize, 0);
|
||||
+ found_nvram = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
kfree(buf);
|
||||
|
||||
+ if (!found_nvram) {
|
||||
+ pr_err("can not find a nvram partition reserve last block\n");
|
||||
+ bcm47xxpart_add_part(&parts[curr_part++], "nvram_guess",
|
||||
+ master->size - blocksize * 2, MTD_WRITEABLE);
|
||||
+ for (i = 0; i < curr_part; i++) {
|
||||
+ if (parts[i].size + parts[i].offset == master->size)
|
||||
+ parts[i].offset -= blocksize * 2;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
/*
|
||||
* Assume that partitions end at the beginning of the one they are
|
||||
* followed by.
|
||||
@ -0,0 +1,42 @@
|
||||
From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <rafal@milecki.pl>
|
||||
Date: Sun, 7 Nov 2021 14:20:40 +0100
|
||||
Subject: [PATCH] net: bgmac: connect to PHY even if it is BGMAC_PHY_NOREGS
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Recent bgmac change was meant to just fix a race between "Generic PHY"
|
||||
and "bcm53xx" drivers after -EPROBE_DEFER. It modified bgmac to use
|
||||
phy_connect() only if there is a real PHY device connected.
|
||||
|
||||
That change broke bgmac on bcm47xx. bcma_phy_connect() now registers a
|
||||
fixed PHY with the bgmac_phy_connect_direct(). That fails as another
|
||||
fixed PHY (also using address 0) is already registered - by bcm47xx arch
|
||||
code bcm47xx_register_bus_complete().
|
||||
|
||||
This change brings origial behaviour. It connects Ethernet interface
|
||||
with pseudo-PHY (switch device) and adjusts Ethernet interface link to
|
||||
match connected switch.
|
||||
|
||||
This fixes:
|
||||
[ 2.548098] bgmac_bcma bcma0:1: Failed to register fixed PHY device
|
||||
[ 2.554584] bgmac_bcma bcma0:1: Cannot connect to phy
|
||||
|
||||
Fixes: b5375509184d ("net: bgmac: improve handling PHY")
|
||||
Link: https://lore.kernel.org/netdev/3639116e-9292-03ca-b9d9-d741118a4541@gmail.com/T/#u
|
||||
Signed-off-by: Rafał Miłecki <rafal@milecki.pl>
|
||||
---
|
||||
drivers/net/ethernet/broadcom/bgmac-bcma.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
--- a/drivers/net/ethernet/broadcom/bgmac-bcma.c
|
||||
+++ b/drivers/net/ethernet/broadcom/bgmac-bcma.c
|
||||
@@ -94,7 +94,7 @@ static int bcma_phy_connect(struct bgmac
|
||||
return 0;
|
||||
|
||||
/* Connect to the PHY */
|
||||
- if (bgmac->mii_bus && bgmac->phyaddr != BGMAC_PHY_NOREGS) {
|
||||
+ if (bgmac->mii_bus) {
|
||||
snprintf(bus_id, sizeof(bus_id), PHY_ID_FMT, bgmac->mii_bus->id,
|
||||
bgmac->phyaddr);
|
||||
phy_dev = phy_connect(bgmac->net_dev, bus_id, bgmac_adjust_link,
|
||||
17
target/linux/bcm47xx/patches-5.15/791-tg3-no-pci-sleep.patch
Normal file
17
target/linux/bcm47xx/patches-5.15/791-tg3-no-pci-sleep.patch
Normal file
@ -0,0 +1,17 @@
|
||||
When the Ethernet controller is powered down and someone wants to
|
||||
access the mdio bus like the witch driver (b53) the system crashed if
|
||||
PCI_D3hot was set before. This patch deactivates this power sawing mode
|
||||
when a switch driver is in use.
|
||||
|
||||
--- a/drivers/net/ethernet/broadcom/tg3.c
|
||||
+++ b/drivers/net/ethernet/broadcom/tg3.c
|
||||
@@ -4267,7 +4267,8 @@ static int tg3_power_down_prepare(struct
|
||||
static void tg3_power_down(struct tg3 *tp)
|
||||
{
|
||||
pci_wake_from_d3(tp->pdev, tg3_flag(tp, WOL_ENABLE));
|
||||
- pci_set_power_state(tp->pdev, PCI_D3hot);
|
||||
+ if (!tg3_flag(tp, ROBOSWITCH))
|
||||
+ pci_set_power_state(tp->pdev, PCI_D3hot);
|
||||
}
|
||||
|
||||
static void tg3_aux_stat_to_speed_duplex(struct tg3 *tp, u32 val, u32 *speed, u8 *duplex)
|
||||
@ -0,0 +1,73 @@
|
||||
From 597715c61ae75a05ab3310a34ff3857a006f0f63 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <zajec5@gmail.com>
|
||||
Date: Thu, 20 Nov 2014 21:32:42 +0100
|
||||
Subject: [PATCH] bcma: add table of serial flashes with smaller blocks
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
Signed-off-by: Rafał Miłecki <zajec5@gmail.com>
|
||||
---
|
||||
drivers/bcma/driver_chipcommon_sflash.c | 29 +++++++++++++++++++++++++++++
|
||||
1 file changed, 29 insertions(+)
|
||||
|
||||
--- a/drivers/bcma/driver_chipcommon_sflash.c
|
||||
+++ b/drivers/bcma/driver_chipcommon_sflash.c
|
||||
@@ -9,6 +9,7 @@
|
||||
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/bcma/bcma.h>
|
||||
+#include <bcm47xx_board.h>
|
||||
|
||||
static struct resource bcma_sflash_resource = {
|
||||
.name = "bcma_sflash",
|
||||
@@ -42,6 +43,13 @@ static const struct bcma_sflash_tbl_e bc
|
||||
{ NULL },
|
||||
};
|
||||
|
||||
+/* Some devices use smaller blocks (and have more of them) */
|
||||
+static const struct bcma_sflash_tbl_e bcma_sflash_st_shrink_tbl[] = {
|
||||
+ { "M25P16", 0x14, 0x1000, 512, },
|
||||
+ { "M25P32", 0x15, 0x1000, 1024, },
|
||||
+ { NULL },
|
||||
+};
|
||||
+
|
||||
static const struct bcma_sflash_tbl_e bcma_sflash_sst_tbl[] = {
|
||||
{ "SST25WF512", 1, 0x1000, 16, },
|
||||
{ "SST25VF512", 0x48, 0x1000, 16, },
|
||||
@@ -85,6 +93,24 @@ static void bcma_sflash_cmd(struct bcma_
|
||||
bcma_err(cc->core->bus, "SFLASH control command failed (timeout)!\n");
|
||||
}
|
||||
|
||||
+const struct bcma_sflash_tbl_e *bcma_sflash_shrink_flash(u32 id)
|
||||
+{
|
||||
+ enum bcm47xx_board board = bcm47xx_board_get();
|
||||
+ const struct bcma_sflash_tbl_e *e;
|
||||
+
|
||||
+ switch (board) {
|
||||
+ case BCM47XX_BOARD_NETGEAR_WGR614_V10:
|
||||
+ case BCM47XX_BOARD_NETGEAR_WNR1000_V3:
|
||||
+ for (e = bcma_sflash_st_shrink_tbl; e->name; e++) {
|
||||
+ if (e->id == id)
|
||||
+ return e;
|
||||
+ }
|
||||
+ return NULL;
|
||||
+ default:
|
||||
+ return NULL;
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
/* Initialize serial flash access */
|
||||
int bcma_sflash_init(struct bcma_drv_cc *cc)
|
||||
{
|
||||
@@ -115,6 +141,10 @@ int bcma_sflash_init(struct bcma_drv_cc
|
||||
case 0x13:
|
||||
return -ENOTSUPP;
|
||||
default:
|
||||
+ e = bcma_sflash_shrink_flash(id);
|
||||
+ if (e)
|
||||
+ break;
|
||||
+
|
||||
for (e = bcma_sflash_st_tbl; e->name; e++) {
|
||||
if (e->id == id)
|
||||
break;
|
||||
296
target/linux/bcm47xx/patches-5.15/820-wgt634u-nvram-fix.patch
Normal file
296
target/linux/bcm47xx/patches-5.15/820-wgt634u-nvram-fix.patch
Normal file
@ -0,0 +1,296 @@
|
||||
The Netgear wgt634u uses a different format for storing the
|
||||
configuration. This patch is needed to read out the correct
|
||||
configuration. The cfe_env.c file uses a different method way to read
|
||||
out the configuration than the in kernel cfe config reader.
|
||||
|
||||
--- a/drivers/firmware/broadcom/Makefile
|
||||
+++ b/drivers/firmware/broadcom/Makefile
|
||||
@@ -1,4 +1,4 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-only
|
||||
-obj-$(CONFIG_BCM47XX_NVRAM) += bcm47xx_nvram.o
|
||||
+obj-$(CONFIG_BCM47XX_NVRAM) += bcm47xx_nvram.o cfe_env.o
|
||||
obj-$(CONFIG_BCM47XX_SPROM) += bcm47xx_sprom.o
|
||||
obj-$(CONFIG_TEE_BNXT_FW) += tee_bnxt_fw.o
|
||||
--- /dev/null
|
||||
+++ b/drivers/firmware/broadcom/cfe_env.c
|
||||
@@ -0,0 +1,228 @@
|
||||
+/*
|
||||
+ * CFE environment variable access
|
||||
+ *
|
||||
+ * Copyright 2001-2003, Broadcom Corporation
|
||||
+ * Copyright 2006, Felix Fietkau <nbd@nbd.name>
|
||||
+ *
|
||||
+ * This program is free software; you can redistribute it and/or modify it
|
||||
+ * under the terms of the GNU General Public License as published by the
|
||||
+ * Free Software Foundation; either version 2 of the License, or (at your
|
||||
+ * option) any later version.
|
||||
+ */
|
||||
+
|
||||
+#include <linux/init.h>
|
||||
+#include <linux/module.h>
|
||||
+#include <linux/kernel.h>
|
||||
+#include <linux/string.h>
|
||||
+#include <asm/io.h>
|
||||
+#include <linux/uaccess.h>
|
||||
+
|
||||
+#define NVRAM_SIZE (0x1ff0)
|
||||
+static char _nvdata[NVRAM_SIZE];
|
||||
+static char _valuestr[256];
|
||||
+
|
||||
+/*
|
||||
+ * TLV types. These codes are used in the "type-length-value"
|
||||
+ * encoding of the items stored in the NVRAM device (flash or EEPROM)
|
||||
+ *
|
||||
+ * The layout of the flash/nvram is as follows:
|
||||
+ *
|
||||
+ * <type> <length> <data ...> <type> <length> <data ...> <type_end>
|
||||
+ *
|
||||
+ * The type code of "ENV_TLV_TYPE_END" marks the end of the list.
|
||||
+ * The "length" field marks the length of the data section, not
|
||||
+ * including the type and length fields.
|
||||
+ *
|
||||
+ * Environment variables are stored as follows:
|
||||
+ *
|
||||
+ * <type_env> <length> <flags> <name> = <value>
|
||||
+ *
|
||||
+ * If bit 0 (low bit) is set, the length is an 8-bit value.
|
||||
+ * If bit 0 (low bit) is clear, the length is a 16-bit value
|
||||
+ *
|
||||
+ * Bit 7 set indicates "user" TLVs. In this case, bit 0 still
|
||||
+ * indicates the size of the length field.
|
||||
+ *
|
||||
+ * Flags are from the constants below:
|
||||
+ *
|
||||
+ */
|
||||
+#define ENV_LENGTH_16BITS 0x00 /* for low bit */
|
||||
+#define ENV_LENGTH_8BITS 0x01
|
||||
+
|
||||
+#define ENV_TYPE_USER 0x80
|
||||
+
|
||||
+#define ENV_CODE_SYS(n,l) (((n)<<1)|(l))
|
||||
+#define ENV_CODE_USER(n,l) ((((n)<<1)|(l)) | ENV_TYPE_USER)
|
||||
+
|
||||
+/*
|
||||
+ * The actual TLV types we support
|
||||
+ */
|
||||
+
|
||||
+#define ENV_TLV_TYPE_END 0x00
|
||||
+#define ENV_TLV_TYPE_ENV ENV_CODE_SYS(0,ENV_LENGTH_8BITS)
|
||||
+
|
||||
+/*
|
||||
+ * Environment variable flags
|
||||
+ */
|
||||
+
|
||||
+#define ENV_FLG_NORMAL 0x00 /* normal read/write */
|
||||
+#define ENV_FLG_BUILTIN 0x01 /* builtin - not stored in flash */
|
||||
+#define ENV_FLG_READONLY 0x02 /* read-only - cannot be changed */
|
||||
+
|
||||
+#define ENV_FLG_MASK 0xFF /* mask of attributes we keep */
|
||||
+#define ENV_FLG_ADMIN 0x100 /* lets us internally override permissions */
|
||||
+
|
||||
+
|
||||
+/* *********************************************************************
|
||||
+ * _nvram_read(buffer,offset,length)
|
||||
+ *
|
||||
+ * Read data from the NVRAM device
|
||||
+ *
|
||||
+ * Input parameters:
|
||||
+ * buffer - destination buffer
|
||||
+ * offset - offset of data to read
|
||||
+ * length - number of bytes to read
|
||||
+ *
|
||||
+ * Return value:
|
||||
+ * number of bytes read, or <0 if error occured
|
||||
+ ********************************************************************* */
|
||||
+static int
|
||||
+_nvram_read(unsigned char *nv_buf, unsigned char *buffer, int offset, int length)
|
||||
+{
|
||||
+ int i;
|
||||
+ if (offset > NVRAM_SIZE)
|
||||
+ return -1;
|
||||
+
|
||||
+ for ( i = 0; i < length; i++) {
|
||||
+ buffer[i] = ((volatile unsigned char*)nv_buf)[offset + i];
|
||||
+ }
|
||||
+ return length;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static char*
|
||||
+_strnchr(const char *dest,int c,size_t cnt)
|
||||
+{
|
||||
+ while (*dest && (cnt > 0)) {
|
||||
+ if (*dest == c) return (char *) dest;
|
||||
+ dest++;
|
||||
+ cnt--;
|
||||
+ }
|
||||
+ return NULL;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+
|
||||
+/*
|
||||
+ * Core support API: Externally visible.
|
||||
+ */
|
||||
+
|
||||
+/*
|
||||
+ * Get the value of an NVRAM variable
|
||||
+ * @param name name of variable to get
|
||||
+ * @return value of variable or NULL if undefined
|
||||
+ */
|
||||
+
|
||||
+char *cfe_env_get(unsigned char *nv_buf, const char *name)
|
||||
+{
|
||||
+ int size;
|
||||
+ unsigned char *buffer;
|
||||
+ unsigned char *ptr;
|
||||
+ unsigned char *envval;
|
||||
+ unsigned int reclen;
|
||||
+ unsigned int rectype;
|
||||
+ int offset;
|
||||
+ int flg;
|
||||
+
|
||||
+ if (!strcmp(name, "nvram_type"))
|
||||
+ return "cfe";
|
||||
+
|
||||
+ size = NVRAM_SIZE;
|
||||
+ buffer = &_nvdata[0];
|
||||
+
|
||||
+ ptr = buffer;
|
||||
+ offset = 0;
|
||||
+
|
||||
+ /* Read the record type and length */
|
||||
+ if (_nvram_read(nv_buf, ptr,offset,1) != 1) {
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+ while ((*ptr != ENV_TLV_TYPE_END) && (size > 1)) {
|
||||
+
|
||||
+ /* Adjust pointer for TLV type */
|
||||
+ rectype = *(ptr);
|
||||
+ offset++;
|
||||
+ size--;
|
||||
+
|
||||
+ /*
|
||||
+ * Read the length. It can be either 1 or 2 bytes
|
||||
+ * depending on the code
|
||||
+ */
|
||||
+ if (rectype & ENV_LENGTH_8BITS) {
|
||||
+ /* Read the record type and length - 8 bits */
|
||||
+ if (_nvram_read(nv_buf, ptr,offset,1) != 1) {
|
||||
+ goto error;
|
||||
+ }
|
||||
+ reclen = *(ptr);
|
||||
+ size--;
|
||||
+ offset++;
|
||||
+ }
|
||||
+ else {
|
||||
+ /* Read the record type and length - 16 bits, MSB first */
|
||||
+ if (_nvram_read(nv_buf, ptr,offset,2) != 2) {
|
||||
+ goto error;
|
||||
+ }
|
||||
+ reclen = (((unsigned int) *(ptr)) << 8) + (unsigned int) *(ptr+1);
|
||||
+ size -= 2;
|
||||
+ offset += 2;
|
||||
+ }
|
||||
+
|
||||
+ if (reclen > size)
|
||||
+ break; /* should not happen, bad NVRAM */
|
||||
+
|
||||
+ switch (rectype) {
|
||||
+ case ENV_TLV_TYPE_ENV:
|
||||
+ /* Read the TLV data */
|
||||
+ if (_nvram_read(nv_buf, ptr,offset,reclen) != reclen)
|
||||
+ goto error;
|
||||
+ flg = *ptr++;
|
||||
+ envval = (unsigned char *) _strnchr(ptr,'=',(reclen-1));
|
||||
+ if (envval) {
|
||||
+ *envval++ = '\0';
|
||||
+ memcpy(_valuestr,envval,(reclen-1)-(envval-ptr));
|
||||
+ _valuestr[(reclen-1)-(envval-ptr)] = '\0';
|
||||
+#if 0
|
||||
+ printk(KERN_INFO "NVRAM:%s=%s\n", ptr, _valuestr);
|
||||
+#endif
|
||||
+ if(!strcmp(ptr, name)){
|
||||
+ return _valuestr;
|
||||
+ }
|
||||
+ if((strlen(ptr) > 1) && !strcmp(&ptr[1], name))
|
||||
+ return _valuestr;
|
||||
+ }
|
||||
+ break;
|
||||
+
|
||||
+ default:
|
||||
+ /* Unknown TLV type, skip it. */
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
+ * Advance to next TLV
|
||||
+ */
|
||||
+
|
||||
+ size -= (int)reclen;
|
||||
+ offset += reclen;
|
||||
+
|
||||
+ /* Read the next record type */
|
||||
+ ptr = buffer;
|
||||
+ if (_nvram_read(nv_buf, ptr,offset,1) != 1)
|
||||
+ goto error;
|
||||
+ }
|
||||
+
|
||||
+error:
|
||||
+ return NULL;
|
||||
+
|
||||
+}
|
||||
+
|
||||
--- a/drivers/firmware/broadcom/bcm47xx_nvram.c
|
||||
+++ b/drivers/firmware/broadcom/bcm47xx_nvram.c
|
||||
@@ -33,6 +33,8 @@ struct nvram_header {
|
||||
static char nvram_buf[NVRAM_SPACE];
|
||||
static size_t nvram_len;
|
||||
static const u32 nvram_sizes[] = {0x6000, 0x8000, 0xF000, 0x10000};
|
||||
+static int cfe_env;
|
||||
+extern char *cfe_env_get(char *nv_buf, const char *name);
|
||||
|
||||
/**
|
||||
* bcm47xx_nvram_is_valid - check for a valid NVRAM at specified memory
|
||||
@@ -80,6 +82,26 @@ static int bcm47xx_nvram_find_and_copy(v
|
||||
return -EEXIST;
|
||||
}
|
||||
|
||||
+ cfe_env = 0;
|
||||
+
|
||||
+ /* XXX: hack for supporting the CFE environment stuff on WGT634U */
|
||||
+ if (res_size >= 8 * 1024 * 1024) {
|
||||
+ u32 *src = (u32 *)(flash_start + 8 * 1024 * 1024 - 0x2000);
|
||||
+ u32 *dst = (u32 *)nvram_buf;
|
||||
+
|
||||
+ if ((*src & 0xff00ff) == 0x000001) {
|
||||
+ printk("early_nvram_init: WGT634U NVRAM found.\n");
|
||||
+
|
||||
+ for (i = 0; i < 0x1ff0; i++) {
|
||||
+ if (*src == 0xFFFFFFFF)
|
||||
+ break;
|
||||
+ *dst++ = *src++;
|
||||
+ }
|
||||
+ cfe_env = 1;
|
||||
+ return 0;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
/* TODO: when nvram is on nand flash check for bad blocks first. */
|
||||
|
||||
/* Try every possible flash size and check for NVRAM at its end */
|
||||
@@ -172,6 +194,13 @@ int bcm47xx_nvram_getenv(const char *nam
|
||||
if (!name)
|
||||
return -EINVAL;
|
||||
|
||||
+ if (cfe_env) {
|
||||
+ value = cfe_env_get(nvram_buf, name);
|
||||
+ if (!value)
|
||||
+ return -ENOENT;
|
||||
+ return snprintf(val, val_len, "%s", value);
|
||||
+ }
|
||||
+
|
||||
if (!nvram_len) {
|
||||
err = nvram_init();
|
||||
if (err)
|
||||
101
target/linux/bcm47xx/patches-5.15/830-huawei_e970_support.patch
Normal file
101
target/linux/bcm47xx/patches-5.15/830-huawei_e970_support.patch
Normal file
@ -0,0 +1,101 @@
|
||||
--- a/arch/mips/bcm47xx/setup.c
|
||||
+++ b/arch/mips/bcm47xx/setup.c
|
||||
@@ -37,6 +37,7 @@
|
||||
#include <linux/ssb/ssb.h>
|
||||
#include <linux/ssb/ssb_embedded.h>
|
||||
#include <linux/bcma/bcma_soc.h>
|
||||
+#include <linux/old_gpio_wdt.h>
|
||||
#include <asm/bootinfo.h>
|
||||
#include <asm/idle.h>
|
||||
#include <asm/prom.h>
|
||||
@@ -254,6 +255,33 @@ static struct fixed_phy_status bcm47xx_f
|
||||
.duplex = DUPLEX_FULL,
|
||||
};
|
||||
|
||||
+static struct gpio_wdt_platform_data gpio_wdt_data;
|
||||
+
|
||||
+static struct platform_device gpio_wdt_device = {
|
||||
+ .name = "gpio-wdt",
|
||||
+ .id = 0,
|
||||
+ .dev = {
|
||||
+ .platform_data = &gpio_wdt_data,
|
||||
+ },
|
||||
+};
|
||||
+
|
||||
+static int __init bcm47xx_register_gpio_watchdog(void)
|
||||
+{
|
||||
+ enum bcm47xx_board board = bcm47xx_board_get();
|
||||
+
|
||||
+ switch (board) {
|
||||
+ case BCM47XX_BOARD_HUAWEI_E970:
|
||||
+ pr_info("bcm47xx: detected Huawei E970 or similar, starting early gpio_wdt timer\n");
|
||||
+ gpio_wdt_data.gpio = 7;
|
||||
+ gpio_wdt_data.interval = HZ;
|
||||
+ gpio_wdt_data.first_interval = HZ / 5;
|
||||
+ return platform_device_register(&gpio_wdt_device);
|
||||
+ default:
|
||||
+ /* Nothing to do */
|
||||
+ return 0;
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
static int __init bcm47xx_register_bus_complete(void)
|
||||
{
|
||||
switch (bcm47xx_bus_type) {
|
||||
@@ -275,6 +303,7 @@ static int __init bcm47xx_register_bus_c
|
||||
bcm47xx_workarounds();
|
||||
|
||||
fixed_phy_add(PHY_POLL, 0, &bcm47xx_fixed_phy_status);
|
||||
+ bcm47xx_register_gpio_watchdog();
|
||||
return 0;
|
||||
}
|
||||
device_initcall(bcm47xx_register_bus_complete);
|
||||
--- a/arch/mips/configs/bcm47xx_defconfig
|
||||
+++ b/arch/mips/configs/bcm47xx_defconfig
|
||||
@@ -63,6 +63,7 @@ CONFIG_HW_RANDOM=y
|
||||
CONFIG_GPIO_SYSFS=y
|
||||
CONFIG_WATCHDOG=y
|
||||
CONFIG_BCM47XX_WDT=y
|
||||
+CONFIG_GPIO_WDT=y
|
||||
CONFIG_SSB_DRIVER_GIGE=y
|
||||
CONFIG_BCMA_DRIVER_GMAC_CMN=y
|
||||
CONFIG_USB=y
|
||||
--- a/drivers/ssb/embedded.c
|
||||
+++ b/drivers/ssb/embedded.c
|
||||
@@ -34,11 +34,36 @@ int ssb_watchdog_timer_set(struct ssb_bu
|
||||
}
|
||||
EXPORT_SYMBOL(ssb_watchdog_timer_set);
|
||||
|
||||
+#ifdef CONFIG_BCM47XX
|
||||
+#include <bcm47xx_board.h>
|
||||
+
|
||||
+static bool ssb_watchdog_supported(void)
|
||||
+{
|
||||
+ enum bcm47xx_board board = bcm47xx_board_get();
|
||||
+
|
||||
+ /* The Huawei E970 has a hardware watchdog using a GPIO */
|
||||
+ switch (board) {
|
||||
+ case BCM47XX_BOARD_HUAWEI_E970:
|
||||
+ return false;
|
||||
+ default:
|
||||
+ return true;
|
||||
+ }
|
||||
+}
|
||||
+#else
|
||||
+static bool ssb_watchdog_supported(void)
|
||||
+{
|
||||
+ return true;
|
||||
+}
|
||||
+#endif
|
||||
+
|
||||
int ssb_watchdog_register(struct ssb_bus *bus)
|
||||
{
|
||||
struct bcm47xx_wdt wdt = {};
|
||||
struct platform_device *pdev;
|
||||
|
||||
+ if (!ssb_watchdog_supported())
|
||||
+ return 0;
|
||||
+
|
||||
if (ssb_chipco_available(&bus->chipco)) {
|
||||
wdt.driver_data = &bus->chipco;
|
||||
wdt.timer_set = ssb_chipco_watchdog_timer_set_wdt;
|
||||
360
target/linux/bcm47xx/patches-5.15/831-old_gpio_wdt.patch
Normal file
360
target/linux/bcm47xx/patches-5.15/831-old_gpio_wdt.patch
Normal file
@ -0,0 +1,360 @@
|
||||
This generic GPIO watchdog is used on Huawei E970 (bcm47xx)
|
||||
|
||||
Signed-off-by: Mathias Adam <m.adam--openwrt@adamis.de>
|
||||
|
||||
--- a/drivers/watchdog/Kconfig
|
||||
+++ b/drivers/watchdog/Kconfig
|
||||
@@ -1664,6 +1664,15 @@ config WDT_MTX1
|
||||
Hardware driver for the MTX-1 boards. This is a watchdog timer that
|
||||
will reboot the machine after a 100 seconds timer expired.
|
||||
|
||||
+config GPIO_WDT
|
||||
+ tristate "GPIO Hardware Watchdog"
|
||||
+ help
|
||||
+ Hardware driver for GPIO-controlled watchdogs. GPIO pin and
|
||||
+ toggle interval settings are platform-specific. The driver
|
||||
+ will stop toggling the GPIO (i.e. machine reboots) after a
|
||||
+ 100 second timer expired and no process has written to
|
||||
+ /dev/watchdog during that time.
|
||||
+
|
||||
config SIBYTE_WDOG
|
||||
tristate "Sibyte SoC hardware watchdog"
|
||||
depends on CPU_SB1
|
||||
--- a/drivers/watchdog/Makefile
|
||||
+++ b/drivers/watchdog/Makefile
|
||||
@@ -159,6 +159,7 @@ obj-$(CONFIG_RC32434_WDT) += rc32434_wdt
|
||||
obj-$(CONFIG_INDYDOG) += indydog.o
|
||||
obj-$(CONFIG_JZ4740_WDT) += jz4740_wdt.o
|
||||
obj-$(CONFIG_WDT_MTX1) += mtx-1_wdt.o
|
||||
+obj-$(CONFIG_GPIO_WDT) += old_gpio_wdt.o
|
||||
obj-$(CONFIG_SIBYTE_WDOG) += sb_wdog.o
|
||||
obj-$(CONFIG_AR7_WDT) += ar7_wdt.o
|
||||
obj-$(CONFIG_TXX9_WDT) += txx9wdt.o
|
||||
--- /dev/null
|
||||
+++ b/drivers/watchdog/old_gpio_wdt.c
|
||||
@@ -0,0 +1,301 @@
|
||||
+/*
|
||||
+ * Driver for GPIO-controlled Hardware Watchdogs.
|
||||
+ *
|
||||
+ * Copyright (C) 2013 Mathias Adam <m.adam--linux@adamis.de>
|
||||
+ *
|
||||
+ * Replaces mtx1_wdt (driver for the MTX-1 Watchdog):
|
||||
+ *
|
||||
+ * (C) Copyright 2005 4G Systems <info@4g-systems.biz>,
|
||||
+ * All Rights Reserved.
|
||||
+ * http://www.4g-systems.biz
|
||||
+ *
|
||||
+ * (C) Copyright 2007 OpenWrt.org, Florian Fainelli <florian@openwrt.org>
|
||||
+ *
|
||||
+ * This program is free software; you can redistribute it and/or
|
||||
+ * modify it under the terms of the GNU General Public License
|
||||
+ * as published by the Free Software Foundation; either version
|
||||
+ * 2 of the License, or (at your option) any later version.
|
||||
+ *
|
||||
+ * Neither Michael Stickel nor 4G Systems admit liability nor provide
|
||||
+ * warranty for any of this software. This material is provided
|
||||
+ * "AS-IS" and at no charge.
|
||||
+ *
|
||||
+ * (c) Copyright 2005 4G Systems <info@4g-systems.biz>
|
||||
+ *
|
||||
+ * Release 0.01.
|
||||
+ * Author: Michael Stickel michael.stickel@4g-systems.biz
|
||||
+ *
|
||||
+ * Release 0.02.
|
||||
+ * Author: Florian Fainelli florian@openwrt.org
|
||||
+ * use the Linux watchdog/timer APIs
|
||||
+ *
|
||||
+ * Release 0.03.
|
||||
+ * Author: Mathias Adam <m.adam--linux@adamis.de>
|
||||
+ * make it a generic gpio watchdog driver
|
||||
+ *
|
||||
+ * The Watchdog is configured to reset the MTX-1
|
||||
+ * if it is not triggered for 100 seconds.
|
||||
+ * It should not be triggered more often than 1.6 seconds.
|
||||
+ *
|
||||
+ * A timer triggers the watchdog every 5 seconds, until
|
||||
+ * it is opened for the first time. After the first open
|
||||
+ * it MUST be triggered every 2..95 seconds.
|
||||
+ */
|
||||
+
|
||||
+#include <linux/module.h>
|
||||
+#include <linux/moduleparam.h>
|
||||
+#include <linux/types.h>
|
||||
+#include <linux/errno.h>
|
||||
+#include <linux/miscdevice.h>
|
||||
+#include <linux/fs.h>
|
||||
+#include <linux/init.h>
|
||||
+#include <linux/ioport.h>
|
||||
+#include <linux/timer.h>
|
||||
+#include <linux/completion.h>
|
||||
+#include <linux/jiffies.h>
|
||||
+#include <linux/watchdog.h>
|
||||
+#include <linux/platform_device.h>
|
||||
+#include <linux/io.h>
|
||||
+#include <linux/uaccess.h>
|
||||
+#include <linux/gpio.h>
|
||||
+#include <linux/old_gpio_wdt.h>
|
||||
+
|
||||
+static int ticks = 100 * HZ;
|
||||
+
|
||||
+static struct {
|
||||
+ struct completion stop;
|
||||
+ spinlock_t lock;
|
||||
+ int running;
|
||||
+ struct timer_list timer;
|
||||
+ int queue;
|
||||
+ int default_ticks;
|
||||
+ unsigned long inuse;
|
||||
+ unsigned gpio;
|
||||
+ unsigned int gstate;
|
||||
+ int interval;
|
||||
+ int first_interval;
|
||||
+} gpio_wdt_device;
|
||||
+
|
||||
+static void gpio_wdt_trigger(struct timer_list *unused)
|
||||
+{
|
||||
+ spin_lock(&gpio_wdt_device.lock);
|
||||
+ if (gpio_wdt_device.running && ticks > 0)
|
||||
+ ticks -= gpio_wdt_device.interval;
|
||||
+
|
||||
+ /* toggle wdt gpio */
|
||||
+ gpio_wdt_device.gstate = !gpio_wdt_device.gstate;
|
||||
+ gpio_set_value(gpio_wdt_device.gpio, gpio_wdt_device.gstate);
|
||||
+
|
||||
+ if (gpio_wdt_device.queue && ticks > 0)
|
||||
+ mod_timer(&gpio_wdt_device.timer, jiffies + gpio_wdt_device.interval);
|
||||
+ else
|
||||
+ complete(&gpio_wdt_device.stop);
|
||||
+ spin_unlock(&gpio_wdt_device.lock);
|
||||
+}
|
||||
+
|
||||
+static void gpio_wdt_reset(void)
|
||||
+{
|
||||
+ ticks = gpio_wdt_device.default_ticks;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static void gpio_wdt_start(void)
|
||||
+{
|
||||
+ unsigned long flags;
|
||||
+
|
||||
+ spin_lock_irqsave(&gpio_wdt_device.lock, flags);
|
||||
+ if (!gpio_wdt_device.queue) {
|
||||
+ gpio_wdt_device.queue = 1;
|
||||
+ gpio_wdt_device.gstate = 1;
|
||||
+ gpio_set_value(gpio_wdt_device.gpio, 1);
|
||||
+ mod_timer(&gpio_wdt_device.timer, jiffies + gpio_wdt_device.first_interval);
|
||||
+ }
|
||||
+ gpio_wdt_device.running++;
|
||||
+ spin_unlock_irqrestore(&gpio_wdt_device.lock, flags);
|
||||
+}
|
||||
+
|
||||
+static int gpio_wdt_stop(void)
|
||||
+{
|
||||
+ unsigned long flags;
|
||||
+
|
||||
+ spin_lock_irqsave(&gpio_wdt_device.lock, flags);
|
||||
+ if (gpio_wdt_device.queue) {
|
||||
+ gpio_wdt_device.queue = 0;
|
||||
+ gpio_wdt_device.gstate = 0;
|
||||
+ gpio_set_value(gpio_wdt_device.gpio, 0);
|
||||
+ }
|
||||
+ ticks = gpio_wdt_device.default_ticks;
|
||||
+ spin_unlock_irqrestore(&gpio_wdt_device.lock, flags);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+/* Filesystem functions */
|
||||
+
|
||||
+static int gpio_wdt_open(struct inode *inode, struct file *file)
|
||||
+{
|
||||
+ if (test_and_set_bit(0, &gpio_wdt_device.inuse))
|
||||
+ return -EBUSY;
|
||||
+ return nonseekable_open(inode, file);
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static int gpio_wdt_release(struct inode *inode, struct file *file)
|
||||
+{
|
||||
+ clear_bit(0, &gpio_wdt_device.inuse);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static long gpio_wdt_ioctl(struct file *file, unsigned int cmd,
|
||||
+ unsigned long arg)
|
||||
+{
|
||||
+ void __user *argp = (void __user *)arg;
|
||||
+ int __user *p = (int __user *)argp;
|
||||
+ unsigned int value;
|
||||
+ static const struct watchdog_info ident = {
|
||||
+ .options = WDIOF_CARDRESET,
|
||||
+ .identity = "GPIO WDT",
|
||||
+ };
|
||||
+
|
||||
+ switch (cmd) {
|
||||
+ case WDIOC_GETSUPPORT:
|
||||
+ if (copy_to_user(argp, &ident, sizeof(ident)))
|
||||
+ return -EFAULT;
|
||||
+ break;
|
||||
+ case WDIOC_GETSTATUS:
|
||||
+ case WDIOC_GETBOOTSTATUS:
|
||||
+ put_user(0, p);
|
||||
+ break;
|
||||
+ case WDIOC_SETOPTIONS:
|
||||
+ if (get_user(value, p))
|
||||
+ return -EFAULT;
|
||||
+ if (value & WDIOS_ENABLECARD)
|
||||
+ gpio_wdt_start();
|
||||
+ else if (value & WDIOS_DISABLECARD)
|
||||
+ gpio_wdt_stop();
|
||||
+ else
|
||||
+ return -EINVAL;
|
||||
+ return 0;
|
||||
+ case WDIOC_KEEPALIVE:
|
||||
+ gpio_wdt_reset();
|
||||
+ break;
|
||||
+ default:
|
||||
+ return -ENOTTY;
|
||||
+ }
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+
|
||||
+static ssize_t gpio_wdt_write(struct file *file, const char *buf,
|
||||
+ size_t count, loff_t *ppos)
|
||||
+{
|
||||
+ if (!count)
|
||||
+ return -EIO;
|
||||
+ gpio_wdt_reset();
|
||||
+ return count;
|
||||
+}
|
||||
+
|
||||
+static const struct file_operations gpio_wdt_fops = {
|
||||
+ .owner = THIS_MODULE,
|
||||
+ .llseek = no_llseek,
|
||||
+ .unlocked_ioctl = gpio_wdt_ioctl,
|
||||
+ .open = gpio_wdt_open,
|
||||
+ .write = gpio_wdt_write,
|
||||
+ .release = gpio_wdt_release,
|
||||
+};
|
||||
+
|
||||
+
|
||||
+static struct miscdevice gpio_wdt_misc = {
|
||||
+ .minor = WATCHDOG_MINOR,
|
||||
+ .name = "watchdog",
|
||||
+ .fops = &gpio_wdt_fops,
|
||||
+};
|
||||
+
|
||||
+
|
||||
+static int gpio_wdt_probe(struct platform_device *pdev)
|
||||
+{
|
||||
+ int ret;
|
||||
+ struct gpio_wdt_platform_data *gpio_wdt_data = pdev->dev.platform_data;
|
||||
+
|
||||
+ gpio_wdt_device.gpio = gpio_wdt_data->gpio;
|
||||
+ gpio_wdt_device.interval = gpio_wdt_data->interval;
|
||||
+ gpio_wdt_device.first_interval = gpio_wdt_data->first_interval;
|
||||
+ if (gpio_wdt_device.first_interval <= 0) {
|
||||
+ gpio_wdt_device.first_interval = gpio_wdt_device.interval;
|
||||
+ }
|
||||
+
|
||||
+ ret = gpio_request(gpio_wdt_device.gpio, "gpio-wdt");
|
||||
+ if (ret < 0) {
|
||||
+ dev_err(&pdev->dev, "failed to request gpio");
|
||||
+ return ret;
|
||||
+ }
|
||||
+
|
||||
+ spin_lock_init(&gpio_wdt_device.lock);
|
||||
+ init_completion(&gpio_wdt_device.stop);
|
||||
+ gpio_wdt_device.queue = 0;
|
||||
+ clear_bit(0, &gpio_wdt_device.inuse);
|
||||
+ timer_setup(&gpio_wdt_device.timer, gpio_wdt_trigger, 0L);
|
||||
+ gpio_wdt_device.default_ticks = ticks;
|
||||
+
|
||||
+ gpio_wdt_start();
|
||||
+ dev_info(&pdev->dev, "GPIO Hardware Watchdog driver (gpio=%i interval=%i/%i)\n",
|
||||
+ gpio_wdt_data->gpio, gpio_wdt_data->first_interval, gpio_wdt_data->interval);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int gpio_wdt_remove(struct platform_device *pdev)
|
||||
+{
|
||||
+ /* FIXME: do we need to lock this test ? */
|
||||
+ if (gpio_wdt_device.queue) {
|
||||
+ gpio_wdt_device.queue = 0;
|
||||
+ wait_for_completion(&gpio_wdt_device.stop);
|
||||
+ }
|
||||
+
|
||||
+ gpio_free(gpio_wdt_device.gpio);
|
||||
+ misc_deregister(&gpio_wdt_misc);
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static struct platform_driver gpio_wdt_driver = {
|
||||
+ .probe = gpio_wdt_probe,
|
||||
+ .remove = gpio_wdt_remove,
|
||||
+ .driver.name = "gpio-wdt",
|
||||
+ .driver.owner = THIS_MODULE,
|
||||
+};
|
||||
+
|
||||
+static int __init gpio_wdt_init(void)
|
||||
+{
|
||||
+ return platform_driver_register(&gpio_wdt_driver);
|
||||
+}
|
||||
+arch_initcall(gpio_wdt_init);
|
||||
+
|
||||
+/*
|
||||
+ * We do wdt initialization in two steps: arch_initcall probes the wdt
|
||||
+ * very early to start pinging the watchdog (misc devices are not yet
|
||||
+ * available), and later module_init() just registers the misc device.
|
||||
+ */
|
||||
+static int gpio_wdt_init_late(void)
|
||||
+{
|
||||
+ int ret;
|
||||
+
|
||||
+ ret = misc_register(&gpio_wdt_misc);
|
||||
+ if (ret < 0) {
|
||||
+ pr_err("GPIO_WDT: failed to register misc device\n");
|
||||
+ return ret;
|
||||
+ }
|
||||
+ return 0;
|
||||
+}
|
||||
+#ifndef MODULE
|
||||
+module_init(gpio_wdt_init_late);
|
||||
+#endif
|
||||
+
|
||||
+static void __exit gpio_wdt_exit(void)
|
||||
+{
|
||||
+ platform_driver_unregister(&gpio_wdt_driver);
|
||||
+}
|
||||
+module_exit(gpio_wdt_exit);
|
||||
+
|
||||
+MODULE_AUTHOR("Michael Stickel, Florian Fainelli, Mathias Adam");
|
||||
+MODULE_DESCRIPTION("Driver for GPIO hardware watchdogs");
|
||||
+MODULE_LICENSE("GPL");
|
||||
+MODULE_ALIAS_MISCDEV(WATCHDOG_MINOR);
|
||||
+MODULE_ALIAS("platform:gpio-wdt");
|
||||
--- /dev/null
|
||||
+++ b/include/linux/old_gpio_wdt.h
|
||||
@@ -0,0 +1,21 @@
|
||||
+/*
|
||||
+ * Definitions for the GPIO watchdog driver
|
||||
+ *
|
||||
+ * Copyright (C) 2013 Mathias Adam <m.adam--linux@adamis.de>
|
||||
+ *
|
||||
+ * This program is free software; you can redistribute it and/or modify
|
||||
+ * it under the terms of the GNU General Public License version 2 as
|
||||
+ * published by the Free Software Foundation.
|
||||
+ *
|
||||
+ */
|
||||
+
|
||||
+#ifndef _GPIO_WDT_H_
|
||||
+#define _GPIO_WDT_H_
|
||||
+
|
||||
+struct gpio_wdt_platform_data {
|
||||
+ int gpio; /* GPIO line number */
|
||||
+ int interval; /* watchdog reset interval in system ticks */
|
||||
+ int first_interval; /* first wd reset interval in system ticks */
|
||||
+};
|
||||
+
|
||||
+#endif /* _GPIO_WDT_H_ */
|
||||
@ -0,0 +1,30 @@
|
||||
From 5c81397a0147ea59c778d1de14ef54e2268221f6 Mon Sep 17 00:00:00 2001
|
||||
From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <zajec5@gmail.com>
|
||||
Date: Wed, 8 Apr 2015 06:58:11 +0200
|
||||
Subject: [PATCH] ssb: reject PCI writes setting CardBus bridge resources
|
||||
MIME-Version: 1.0
|
||||
Content-Type: text/plain; charset=UTF-8
|
||||
Content-Transfer-Encoding: 8bit
|
||||
|
||||
If SoC has a CardBus we can set resources of device at slot 1 only. It's
|
||||
impossigle to set bridge resources as it simply overwrites device 1
|
||||
configuration and usually results in Data bus error-s.
|
||||
|
||||
Signed-off-by: Rafał Miłecki <zajec5@gmail.com>
|
||||
---
|
||||
drivers/ssb/driver_pcicore.c | 4 ++++
|
||||
1 file changed, 4 insertions(+)
|
||||
|
||||
--- a/drivers/ssb/driver_pcicore.c
|
||||
+++ b/drivers/ssb/driver_pcicore.c
|
||||
@@ -165,6 +165,10 @@ static int ssb_extpci_write_config(struc
|
||||
WARN_ON(!pc->hostmode);
|
||||
if (unlikely(len != 1 && len != 2 && len != 4))
|
||||
goto out;
|
||||
+ /* CardBus SoCs allow configuring dev 1 resources only */
|
||||
+ if (extpci_core->cardbusmode && dev != 1 &&
|
||||
+ off >= PCI_BASE_ADDRESS_0 && off <= PCI_BASE_ADDRESS_5)
|
||||
+ goto out;
|
||||
addr = get_cfgspace_addr(pc, bus, dev, func, off);
|
||||
if (unlikely(!addr))
|
||||
goto out;
|
||||
46
target/linux/bcm47xx/patches-5.15/940-bcm47xx-yenta.patch
Normal file
46
target/linux/bcm47xx/patches-5.15/940-bcm47xx-yenta.patch
Normal file
@ -0,0 +1,46 @@
|
||||
--- a/drivers/pcmcia/yenta_socket.c
|
||||
+++ b/drivers/pcmcia/yenta_socket.c
|
||||
@@ -932,6 +932,8 @@ static unsigned int yenta_probe_irq(stru
|
||||
* Probe for usable interrupts using the force
|
||||
* register to generate bogus card status events.
|
||||
*/
|
||||
+#ifndef CONFIG_BCM47XX
|
||||
+ /* WRT54G3G does not like this */
|
||||
cb_writel(socket, CB_SOCKET_EVENT, -1);
|
||||
cb_writel(socket, CB_SOCKET_MASK, CB_CSTSMASK);
|
||||
reg = exca_readb(socket, I365_CSCINT);
|
||||
@@ -947,6 +949,7 @@ static unsigned int yenta_probe_irq(stru
|
||||
}
|
||||
cb_writel(socket, CB_SOCKET_MASK, 0);
|
||||
exca_writeb(socket, I365_CSCINT, reg);
|
||||
+#endif
|
||||
|
||||
mask = probe_irq_mask(val) & 0xffff;
|
||||
|
||||
@@ -1031,6 +1034,10 @@ static void yenta_get_socket_capabilitie
|
||||
else
|
||||
socket->socket.irq_mask = 0;
|
||||
|
||||
+ /* irq mask probing is broken for the WRT54G3G */
|
||||
+ if (socket->socket.irq_mask == 0)
|
||||
+ socket->socket.irq_mask = 0x6f8;
|
||||
+
|
||||
dev_info(&socket->dev->dev, "ISA IRQ mask 0x%04x, PCI irq %d\n",
|
||||
socket->socket.irq_mask, socket->cb_irq);
|
||||
}
|
||||
@@ -1262,6 +1269,15 @@ static int yenta_probe(struct pci_dev *d
|
||||
dev_info(&dev->dev, "Socket status: %08x\n",
|
||||
cb_readl(socket, CB_SOCKET_STATE));
|
||||
|
||||
+ /* Generate an interrupt on card insert/remove */
|
||||
+ config_writew(socket, CB_SOCKET_MASK, CB_CSTSMASK | CB_CDMASK);
|
||||
+
|
||||
+ /* Set up Multifunction Routing Status Register */
|
||||
+ config_writew(socket, 0x8C, 0x1000 /* MFUNC3 to GPIO3 */ | 0x2 /* MFUNC0 to INTA */);
|
||||
+
|
||||
+ /* Switch interrupts to parallelized */
|
||||
+ config_writeb(socket, 0x92, 0x64);
|
||||
+
|
||||
yenta_fixup_parent_bridge(dev->subordinate);
|
||||
|
||||
/* Register it with the pcmcia layer.. */
|
||||
@ -0,0 +1,11 @@
|
||||
--- a/drivers/ssb/driver_pcicore.c
|
||||
+++ b/drivers/ssb/driver_pcicore.c
|
||||
@@ -394,7 +394,7 @@ static void ssb_pcicore_init_hostmode(st
|
||||
/* Give some time to the PCI controller to configure itself with the new
|
||||
* values. Not waiting at this point causes crashes of the machine.
|
||||
*/
|
||||
- mdelay(10);
|
||||
+ mdelay(300);
|
||||
register_pci_controller(&ssb_pcicore_controller);
|
||||
}
|
||||
|
||||
24
target/linux/bcm47xx/patches-5.15/999-wl_exports.patch
Normal file
24
target/linux/bcm47xx/patches-5.15/999-wl_exports.patch
Normal file
@ -0,0 +1,24 @@
|
||||
--- a/drivers/firmware/broadcom/bcm47xx_nvram.c
|
||||
+++ b/drivers/firmware/broadcom/bcm47xx_nvram.c
|
||||
@@ -30,7 +30,8 @@ struct nvram_header {
|
||||
u32 config_ncdl; /* ncdl values for memc */
|
||||
};
|
||||
|
||||
-static char nvram_buf[NVRAM_SPACE];
|
||||
+char nvram_buf[NVRAM_SPACE];
|
||||
+EXPORT_SYMBOL(nvram_buf);
|
||||
static size_t nvram_len;
|
||||
static const u32 nvram_sizes[] = {0x6000, 0x8000, 0xF000, 0x10000};
|
||||
static int cfe_env;
|
||||
--- a/arch/mips/mm/cache.c
|
||||
+++ b/arch/mips/mm/cache.c
|
||||
@@ -63,6 +63,9 @@ void (*_dma_cache_wback_inv)(unsigned lo
|
||||
void (*_dma_cache_wback)(unsigned long start, unsigned long size);
|
||||
void (*_dma_cache_inv)(unsigned long start, unsigned long size);
|
||||
|
||||
+EXPORT_SYMBOL(_dma_cache_wback_inv);
|
||||
+EXPORT_SYMBOL(_dma_cache_inv);
|
||||
+
|
||||
#endif /* CONFIG_DMA_NONCOHERENT */
|
||||
|
||||
/*
|
||||
@ -33,7 +33,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
enum udp_conntrack {
|
||||
--- a/net/netfilter/nf_conntrack_proto_tcp.c
|
||||
+++ b/net/netfilter/nf_conntrack_proto_tcp.c
|
||||
@@ -1447,6 +1447,11 @@ void nf_conntrack_tcp_init_net(struct ne
|
||||
@@ -1457,6 +1457,11 @@ void nf_conntrack_tcp_init_net(struct ne
|
||||
tn->tcp_loose = nf_ct_tcp_loose;
|
||||
tn->tcp_be_liberal = nf_ct_tcp_be_liberal;
|
||||
tn->tcp_max_retrans = nf_ct_tcp_max_retrans;
|
||||
@ -58,7 +58,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
NF_SYSCTL_CT_PROTO_TCP_LOOSE,
|
||||
NF_SYSCTL_CT_PROTO_TCP_LIBERAL,
|
||||
NF_SYSCTL_CT_PROTO_TCP_MAX_RETRANS,
|
||||
@@ -758,6 +762,20 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
@@ -757,6 +761,20 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
.mode = 0644,
|
||||
.proc_handler = proc_dointvec_jiffies,
|
||||
},
|
||||
@ -79,7 +79,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
[NF_SYSCTL_CT_PROTO_TCP_LOOSE] = {
|
||||
.procname = "nf_conntrack_tcp_loose",
|
||||
.maxlen = sizeof(int),
|
||||
@@ -967,6 +985,12 @@ static void nf_conntrack_standalone_init
|
||||
@@ -960,6 +978,12 @@ static void nf_conntrack_standalone_init
|
||||
XASSIGN(LIBERAL, &tn->tcp_be_liberal);
|
||||
XASSIGN(MAX_RETRANS, &tn->tcp_max_retrans);
|
||||
#undef XASSIGN
|
||||
|
||||
@ -58,7 +58,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
NF_SYSCTL_CT_PROTO_TIMEOUT_ICMP,
|
||||
NF_SYSCTL_CT_PROTO_TIMEOUT_ICMPV6,
|
||||
#ifdef CONFIG_NF_CT_PROTO_SCTP
|
||||
@@ -810,6 +814,20 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
@@ -809,6 +813,20 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
.mode = 0644,
|
||||
.proc_handler = proc_dointvec_jiffies,
|
||||
},
|
||||
@ -79,7 +79,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
[NF_SYSCTL_CT_PROTO_TIMEOUT_ICMP] = {
|
||||
.procname = "nf_conntrack_icmp_timeout",
|
||||
.maxlen = sizeof(unsigned int),
|
||||
@@ -1078,6 +1096,10 @@ static int nf_conntrack_standalone_init_
|
||||
@@ -1070,6 +1088,10 @@ static int nf_conntrack_standalone_init_
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_ICMPV6].data = &nf_icmpv6_pernet(net)->timeout;
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_UDP].data = &un->timeouts[UDP_CT_UNREPLIED];
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_UDP_STREAM].data = &un->timeouts[UDP_CT_REPLIED];
|
||||
|
||||
@ -73,7 +73,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
|
||||
--- a/net/netfilter/nf_conntrack_proto_tcp.c
|
||||
+++ b/net/netfilter/nf_conntrack_proto_tcp.c
|
||||
@@ -1450,7 +1450,6 @@ void nf_conntrack_tcp_init_net(struct ne
|
||||
@@ -1460,7 +1460,6 @@ void nf_conntrack_tcp_init_net(struct ne
|
||||
|
||||
#if IS_ENABLED(CONFIG_NF_FLOW_TABLE)
|
||||
tn->offload_timeout = 30 * HZ;
|
||||
@ -109,7 +109,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
#endif
|
||||
NF_SYSCTL_CT_PROTO_TIMEOUT_ICMP,
|
||||
NF_SYSCTL_CT_PROTO_TIMEOUT_ICMPV6,
|
||||
@@ -773,12 +771,6 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
@@ -772,12 +770,6 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
.mode = 0644,
|
||||
.proc_handler = proc_dointvec_jiffies,
|
||||
},
|
||||
@ -122,7 +122,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
#endif
|
||||
[NF_SYSCTL_CT_PROTO_TCP_LOOSE] = {
|
||||
.procname = "nf_conntrack_tcp_loose",
|
||||
@@ -821,12 +813,6 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
@@ -820,12 +812,6 @@ static struct ctl_table nf_ct_sysctl_tab
|
||||
.mode = 0644,
|
||||
.proc_handler = proc_dointvec_jiffies,
|
||||
},
|
||||
@ -135,7 +135,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
#endif
|
||||
[NF_SYSCTL_CT_PROTO_TIMEOUT_ICMP] = {
|
||||
.procname = "nf_conntrack_icmp_timeout",
|
||||
@@ -1006,7 +992,6 @@ static void nf_conntrack_standalone_init
|
||||
@@ -999,7 +985,6 @@ static void nf_conntrack_standalone_init
|
||||
|
||||
#if IS_ENABLED(CONFIG_NF_FLOW_TABLE)
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_TCP_OFFLOAD].data = &tn->offload_timeout;
|
||||
@ -143,7 +143,7 @@ Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
|
||||
#endif
|
||||
|
||||
}
|
||||
@@ -1098,7 +1083,6 @@ static int nf_conntrack_standalone_init_
|
||||
@@ -1090,7 +1075,6 @@ static int nf_conntrack_standalone_init_
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_UDP_STREAM].data = &un->timeouts[UDP_CT_REPLIED];
|
||||
#if IS_ENABLED(CONFIG_NF_FLOW_TABLE)
|
||||
table[NF_SYSCTL_CT_PROTO_TIMEOUT_UDP_OFFLOAD].data = &un->offload_timeout;
|
||||
|
||||
@ -423,7 +423,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
if (bgmac->irq < 0)
|
||||
--- a/drivers/net/ethernet/cadence/macb_main.c
|
||||
+++ b/drivers/net/ethernet/cadence/macb_main.c
|
||||
@@ -4487,7 +4487,6 @@ static int macb_probe(struct platform_de
|
||||
@@ -4480,7 +4480,6 @@ static int macb_probe(struct platform_de
|
||||
struct net_device *dev;
|
||||
struct resource *regs;
|
||||
void __iomem *mem;
|
||||
@ -431,7 +431,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
struct macb *bp;
|
||||
int err, val;
|
||||
|
||||
@@ -4600,15 +4599,11 @@ static int macb_probe(struct platform_de
|
||||
@@ -4593,15 +4592,11 @@ static int macb_probe(struct platform_de
|
||||
if (bp->caps & MACB_CAPS_NEEDS_RSTONUBR)
|
||||
bp->rx_intr_mask |= MACB_BIT(RXUBR);
|
||||
|
||||
@ -1360,7 +1360,7 @@ Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
int irq;
|
||||
--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
|
||||
+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
|
||||
@@ -5008,7 +5008,7 @@ int stmmac_dvr_probe(struct device *devi
|
||||
@@ -5013,7 +5013,7 @@ int stmmac_dvr_probe(struct device *devi
|
||||
priv->wol_irq = res->wol_irq;
|
||||
priv->lpi_irq = res->lpi_irq;
|
||||
|
||||
|
||||
@ -37,8 +37,8 @@ Signed-off-by: Masahiro Yamada <masahiroy@kernel.org>
|
||||
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -432,7 +432,8 @@ HOSTCXX = g++
|
||||
endif
|
||||
@@ -433,7 +433,8 @@ endif
|
||||
HOSTPKG_CONFIG = pkg-config
|
||||
|
||||
export KBUILD_USERCFLAGS := -Wall -Wmissing-prototypes -Wstrict-prototypes \
|
||||
- -O2 -fomit-frame-pointer -std=gnu89
|
||||
|
||||
@ -49,7 +49,7 @@ Signed-off-by: Masahiro Yamada <masahiroy@kernel.org>
|
||||
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -516,7 +516,7 @@ KBUILD_CFLAGS := -Wall -Wundef -Werror
|
||||
@@ -517,7 +517,7 @@ KBUILD_CFLAGS := -Wall -Wundef -Werror
|
||||
-fno-strict-aliasing -fno-common -fshort-wchar -fno-PIE \
|
||||
-Werror=implicit-function-declaration -Werror=implicit-int \
|
||||
-Werror=return-type -Wno-format-security \
|
||||
|
||||
@ -32,8 +32,8 @@ Signed-off-by: Masahiro Yamada <masahiroy@kernel.org>
|
||||
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -432,7 +432,7 @@ HOSTCXX = g++
|
||||
endif
|
||||
@@ -433,7 +433,7 @@ endif
|
||||
HOSTPKG_CONFIG = pkg-config
|
||||
|
||||
export KBUILD_USERCFLAGS := -Wall -Wmissing-prototypes -Wstrict-prototypes \
|
||||
- -O2 -fomit-frame-pointer -std=gnu89 \
|
||||
|
||||
@ -287,7 +287,7 @@ Change-Id: I25d9eda8c6bdc7c3653b9f210a159d6c247c81e8
|
||||
struct pglist_data *pgdat;
|
||||
--- a/kernel/exit.c
|
||||
+++ b/kernel/exit.c
|
||||
@@ -422,6 +422,7 @@ assign_new_owner:
|
||||
@@ -469,6 +469,7 @@ assign_new_owner:
|
||||
goto retry;
|
||||
}
|
||||
WRITE_ONCE(mm->owner, c);
|
||||
|
||||
@ -0,0 +1,98 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 17 Nov 2022 00:35:04 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: do not overwrite mtu
|
||||
configuration running reset routine
|
||||
|
||||
Restore user configured MTU running mtk_hw_init() during tx timeout routine
|
||||
since it will be overwritten after a hw reset.
|
||||
|
||||
Reported-by: Felix Fietkau <nbd@nbd.name>
|
||||
Fixes: 9ea4d311509f ("net: ethernet: mediatek: add the whole ethernet reset into the reset process")
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3175,6 +3175,30 @@ static void mtk_dim_tx(struct work_struc
|
||||
dim->state = DIM_START_MEASURE;
|
||||
}
|
||||
|
||||
+static void mtk_set_mcr_max_rx(struct mtk_mac *mac, u32 val)
|
||||
+{
|
||||
+ struct mtk_eth *eth = mac->hw;
|
||||
+ u32 mcr_cur, mcr_new;
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
|
||||
+ return;
|
||||
+
|
||||
+ mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
|
||||
+ mcr_new = mcr_cur & ~MAC_MCR_MAX_RX_MASK;
|
||||
+
|
||||
+ if (val <= 1518)
|
||||
+ mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1518);
|
||||
+ else if (val <= 1536)
|
||||
+ mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1536);
|
||||
+ else if (val <= 1552)
|
||||
+ mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1552);
|
||||
+ else
|
||||
+ mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_2048);
|
||||
+
|
||||
+ if (mcr_new != mcr_cur)
|
||||
+ mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
|
||||
+}
|
||||
+
|
||||
static int mtk_hw_init(struct mtk_eth *eth)
|
||||
{
|
||||
u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
|
||||
@@ -3249,8 +3273,16 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
* up with the more appropriate value when mtk_mac_config call is being
|
||||
* invoked.
|
||||
*/
|
||||
- for (i = 0; i < MTK_MAC_COUNT; i++)
|
||||
+ for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
+ struct net_device *dev = eth->netdev[i];
|
||||
+
|
||||
mtk_w32(eth, MAC_MCR_FORCE_LINK_DOWN, MTK_MAC_MCR(i));
|
||||
+ if (dev) {
|
||||
+ struct mtk_mac *mac = netdev_priv(dev);
|
||||
+
|
||||
+ mtk_set_mcr_max_rx(mac, dev->mtu + MTK_RX_ETH_HLEN);
|
||||
+ }
|
||||
+ }
|
||||
|
||||
/* Indicates CDM to parse the MTK special tag from CPU
|
||||
* which also is working out for untag packets.
|
||||
@@ -3366,7 +3398,6 @@ static int mtk_change_mtu(struct net_dev
|
||||
int length = new_mtu + MTK_RX_ETH_HLEN;
|
||||
struct mtk_mac *mac = netdev_priv(dev);
|
||||
struct mtk_eth *eth = mac->hw;
|
||||
- u32 mcr_cur, mcr_new;
|
||||
|
||||
if (rcu_access_pointer(eth->prog) &&
|
||||
length > MTK_PP_MAX_BUF_SIZE) {
|
||||
@@ -3374,23 +3405,7 @@ static int mtk_change_mtu(struct net_dev
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
- if (!MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628)) {
|
||||
- mcr_cur = mtk_r32(mac->hw, MTK_MAC_MCR(mac->id));
|
||||
- mcr_new = mcr_cur & ~MAC_MCR_MAX_RX_MASK;
|
||||
-
|
||||
- if (length <= 1518)
|
||||
- mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1518);
|
||||
- else if (length <= 1536)
|
||||
- mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1536);
|
||||
- else if (length <= 1552)
|
||||
- mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_1552);
|
||||
- else
|
||||
- mcr_new |= MAC_MCR_MAX_RX(MAC_MCR_MAX_RX_2048);
|
||||
-
|
||||
- if (mcr_new != mcr_cur)
|
||||
- mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
|
||||
- }
|
||||
-
|
||||
+ mtk_set_mcr_max_rx(mac, length);
|
||||
dev->mtu = new_mtu;
|
||||
|
||||
return 0;
|
||||
@ -0,0 +1,36 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 17 Nov 2022 00:58:46 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: remove cpu_relax in
|
||||
mtk_pending_work
|
||||
|
||||
Get rid of cpu_relax in mtk_pending_work routine since MTK_RESETTING is
|
||||
set only in mtk_pending_work() and it runs holding rtnl lock
|
||||
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3436,11 +3436,8 @@ static void mtk_pending_work(struct work
|
||||
rtnl_lock();
|
||||
|
||||
dev_dbg(eth->dev, "[%s][%d] reset\n", __func__, __LINE__);
|
||||
+ set_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
- while (test_and_set_bit_lock(MTK_RESETTING, ð->state))
|
||||
- cpu_relax();
|
||||
-
|
||||
- dev_dbg(eth->dev, "[%s][%d] mtk_stop starts\n", __func__, __LINE__);
|
||||
/* stop all devices to make sure that dma is properly shut down */
|
||||
for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
if (!eth->netdev[i])
|
||||
@@ -3474,7 +3471,7 @@ static void mtk_pending_work(struct work
|
||||
|
||||
dev_dbg(eth->dev, "[%s][%d] reset done\n", __func__, __LINE__);
|
||||
|
||||
- clear_bit_unlock(MTK_RESETTING, ð->state);
|
||||
+ clear_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
rtnl_unlock();
|
||||
}
|
||||
@ -0,0 +1,63 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 17 Nov 2022 15:29:53 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: fix RSTCTRL_PPE{0,1} definitions
|
||||
|
||||
Fix RSTCTRL_PPE0 and RSTCTRL_PPE1 register mask definitions for
|
||||
MTK_NETSYS_V2.
|
||||
Remove duplicated definitions.
|
||||
|
||||
Fixes: 160d3a9b1929 ("net: ethernet: mtk_eth_soc: introduce MTK_NETSYS_V2 support")
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3238,16 +3238,17 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
return 0;
|
||||
}
|
||||
|
||||
- val = RSTCTRL_FE | RSTCTRL_PPE;
|
||||
if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
|
||||
-
|
||||
- val |= RSTCTRL_ETH;
|
||||
- if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
- val |= RSTCTRL_PPE1;
|
||||
+ val = RSTCTRL_PPE0_V2;
|
||||
+ } else {
|
||||
+ val = RSTCTRL_PPE0;
|
||||
}
|
||||
|
||||
- ethsys_reset(eth, val);
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
+ val |= RSTCTRL_PPE1;
|
||||
+
|
||||
+ ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
|
||||
|
||||
if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
@@ -444,18 +444,14 @@
|
||||
/* ethernet reset control register */
|
||||
#define ETHSYS_RSTCTRL 0x34
|
||||
#define RSTCTRL_FE BIT(6)
|
||||
-#define RSTCTRL_PPE BIT(31)
|
||||
-#define RSTCTRL_PPE1 BIT(30)
|
||||
+#define RSTCTRL_PPE0 BIT(31)
|
||||
+#define RSTCTRL_PPE0_V2 BIT(30)
|
||||
+#define RSTCTRL_PPE1 BIT(31)
|
||||
#define RSTCTRL_ETH BIT(23)
|
||||
|
||||
/* ethernet reset check idle register */
|
||||
#define ETHSYS_FE_RST_CHK_IDLE_EN 0x28
|
||||
|
||||
-/* ethernet reset control register */
|
||||
-#define ETHSYS_RSTCTRL 0x34
|
||||
-#define RSTCTRL_FE BIT(6)
|
||||
-#define RSTCTRL_PPE BIT(31)
|
||||
-
|
||||
/* ethernet dma channel agent map */
|
||||
#define ETHSYS_DMA_AG_MAP 0x408
|
||||
#define ETHSYS_DMA_AG_MAP_PDMA BIT(0)
|
||||
@ -0,0 +1,80 @@
|
||||
From: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Date: Thu, 24 Nov 2022 11:18:14 +0800
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: add wcid overwritten support for wed
|
||||
v1
|
||||
|
||||
All wed versions should enable the wcid overwritten feature,
|
||||
since the wcid size is controlled by the wlan driver.
|
||||
|
||||
Tested-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Co-developed-by: Bo Jiao <bo.jiao@mediatek.com>
|
||||
Signed-off-by: Bo Jiao <bo.jiao@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: David S. Miller <davem@davemloft.net>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -526,9 +526,9 @@ mtk_wed_dma_disable(struct mtk_wed_devic
|
||||
MTK_WED_WPDMA_RX_D_RX_DRV_EN);
|
||||
wed_clr(dev, MTK_WED_WDMA_GLO_CFG,
|
||||
MTK_WED_WDMA_GLO_CFG_TX_DDONE_CHK);
|
||||
-
|
||||
- mtk_wed_set_512_support(dev, false);
|
||||
}
|
||||
+
|
||||
+ mtk_wed_set_512_support(dev, false);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -1297,9 +1297,10 @@ mtk_wed_start(struct mtk_wed_device *dev
|
||||
if (mtk_wed_rro_cfg(dev))
|
||||
return;
|
||||
|
||||
- mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
|
||||
}
|
||||
|
||||
+ mtk_wed_set_512_support(dev, dev->wlan.wcid_512);
|
||||
+
|
||||
mtk_wed_dma_enable(dev);
|
||||
dev->running = true;
|
||||
}
|
||||
@@ -1365,11 +1366,13 @@ mtk_wed_attach(struct mtk_wed_device *de
|
||||
}
|
||||
|
||||
mtk_wed_hw_init_early(dev);
|
||||
- if (hw->version == 1)
|
||||
+ if (hw->version == 1) {
|
||||
regmap_update_bits(hw->hifsys, HIFSYS_DMA_AG_MAP,
|
||||
BIT(hw->index), 0);
|
||||
- else
|
||||
+ } else {
|
||||
+ dev->rev_id = wed_r32(dev, MTK_WED_REV_ID);
|
||||
ret = mtk_wed_wo_init(hw);
|
||||
+ }
|
||||
out:
|
||||
if (ret)
|
||||
mtk_wed_detach(dev);
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
|
||||
@@ -20,6 +20,8 @@ struct mtk_wdma_desc {
|
||||
__le32 info;
|
||||
} __packed __aligned(4);
|
||||
|
||||
+#define MTK_WED_REV_ID 0x004
|
||||
+
|
||||
#define MTK_WED_RESET 0x008
|
||||
#define MTK_WED_RESET_TX_BM BIT(0)
|
||||
#define MTK_WED_RESET_TX_FREE_AGENT BIT(4)
|
||||
--- a/include/linux/soc/mediatek/mtk_wed.h
|
||||
+++ b/include/linux/soc/mediatek/mtk_wed.h
|
||||
@@ -85,6 +85,9 @@ struct mtk_wed_device {
|
||||
int irq;
|
||||
u8 version;
|
||||
|
||||
+ /* used by wlan driver */
|
||||
+ u32 rev_id;
|
||||
+
|
||||
struct mtk_wed_ring tx_ring[MTK_WED_TX_QUEUES];
|
||||
struct mtk_wed_ring rx_ring[MTK_WED_RX_QUEUES];
|
||||
struct mtk_wed_ring txfree_ring;
|
||||
@ -0,0 +1,85 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 24 Nov 2022 16:22:51 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: return status value in
|
||||
mtk_wdma_rx_reset
|
||||
|
||||
Move MTK_WDMA_RESET_IDX configuration in mtk_wdma_rx_reset routine.
|
||||
Increase poll timeout to 10ms in order to be aligned with vendor sdk.
|
||||
This is a preliminary patch to add Wireless Ethernet Dispatcher reset
|
||||
support.
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -101,17 +101,21 @@ mtk_wdma_read_reset(struct mtk_wed_devic
|
||||
return wdma_r32(dev, MTK_WDMA_GLO_CFG);
|
||||
}
|
||||
|
||||
-static void
|
||||
+static int
|
||||
mtk_wdma_rx_reset(struct mtk_wed_device *dev)
|
||||
{
|
||||
u32 status, mask = MTK_WDMA_GLO_CFG_RX_DMA_BUSY;
|
||||
- int i;
|
||||
+ int i, ret;
|
||||
|
||||
wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_RX_DMA_EN);
|
||||
- if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
|
||||
- !(status & mask), 0, 1000))
|
||||
+ ret = readx_poll_timeout(mtk_wdma_read_reset, dev, status,
|
||||
+ !(status & mask), 0, 10000);
|
||||
+ if (ret)
|
||||
dev_err(dev->hw->dev, "rx reset failed\n");
|
||||
|
||||
+ wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
|
||||
+ wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
|
||||
+
|
||||
for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++) {
|
||||
if (dev->rx_wdma[i].desc)
|
||||
continue;
|
||||
@@ -119,6 +123,8 @@ mtk_wdma_rx_reset(struct mtk_wed_device
|
||||
wdma_w32(dev,
|
||||
MTK_WDMA_RING_RX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
|
||||
}
|
||||
+
|
||||
+ return ret;
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -565,9 +571,7 @@ mtk_wed_detach(struct mtk_wed_device *de
|
||||
|
||||
mtk_wed_stop(dev);
|
||||
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
|
||||
-
|
||||
+ mtk_wdma_rx_reset(dev);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WED);
|
||||
if (mtk_wed_get_rx_capa(dev)) {
|
||||
wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
|
||||
@@ -582,7 +586,6 @@ mtk_wed_detach(struct mtk_wed_device *de
|
||||
mtk_wed_wo_reset(dev);
|
||||
mtk_wed_free_rx_rings(dev);
|
||||
mtk_wed_wo_deinit(hw);
|
||||
- mtk_wdma_rx_reset(dev);
|
||||
}
|
||||
|
||||
if (dev->wlan.bus_type == MTK_WED_BUS_PCIE) {
|
||||
@@ -1006,11 +1009,7 @@ mtk_wed_reset_dma(struct mtk_wed_device
|
||||
wed_w32(dev, MTK_WED_RESET_IDX, 0);
|
||||
}
|
||||
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_RX);
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
|
||||
-
|
||||
- if (mtk_wed_get_rx_capa(dev))
|
||||
- mtk_wdma_rx_reset(dev);
|
||||
+ mtk_wdma_rx_reset(dev);
|
||||
|
||||
if (busy) {
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
|
||||
@ -0,0 +1,52 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 24 Nov 2022 16:22:52 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: move MTK_WDMA_RESET_IDX_TX
|
||||
configuration in mtk_wdma_tx_reset
|
||||
|
||||
Remove duplicated code. Increase poll timeout to 10ms in order to be
|
||||
aligned with vendor sdk.
|
||||
This is a preliminary patch to add Wireless Ethernet Dispatcher reset
|
||||
support.
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -135,16 +135,15 @@ mtk_wdma_tx_reset(struct mtk_wed_device
|
||||
|
||||
wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
|
||||
if (readx_poll_timeout(mtk_wdma_read_reset, dev, status,
|
||||
- !(status & mask), 0, 1000))
|
||||
+ !(status & mask), 0, 10000))
|
||||
dev_err(dev->hw->dev, "tx reset failed\n");
|
||||
|
||||
- for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++) {
|
||||
- if (dev->tx_wdma[i].desc)
|
||||
- continue;
|
||||
+ wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
|
||||
+ wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
|
||||
|
||||
+ for (i = 0; i < ARRAY_SIZE(dev->tx_wdma); i++)
|
||||
wdma_w32(dev,
|
||||
MTK_WDMA_RING_TX(i) + MTK_WED_RING_OFS_CPU_IDX, 0);
|
||||
- }
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -573,12 +572,6 @@ mtk_wed_detach(struct mtk_wed_device *de
|
||||
|
||||
mtk_wdma_rx_reset(dev);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WED);
|
||||
- if (mtk_wed_get_rx_capa(dev)) {
|
||||
- wdma_clr(dev, MTK_WDMA_GLO_CFG, MTK_WDMA_GLO_CFG_TX_DMA_EN);
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, MTK_WDMA_RESET_IDX_TX);
|
||||
- wdma_w32(dev, MTK_WDMA_RESET_IDX, 0);
|
||||
- }
|
||||
-
|
||||
mtk_wed_free_tx_buffer(dev);
|
||||
mtk_wed_free_tx_rings(dev);
|
||||
|
||||
@ -0,0 +1,98 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 24 Nov 2022 16:22:53 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: update mtk_wed_stop
|
||||
|
||||
Update mtk_wed_stop routine and rename old mtk_wed_stop() to
|
||||
mtk_wed_deinit(). This is a preliminary patch to add Wireless Ethernet
|
||||
Dispatcher reset support.
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -539,14 +539,8 @@ mtk_wed_dma_disable(struct mtk_wed_devic
|
||||
static void
|
||||
mtk_wed_stop(struct mtk_wed_device *dev)
|
||||
{
|
||||
- mtk_wed_dma_disable(dev);
|
||||
mtk_wed_set_ext_int(dev, false);
|
||||
|
||||
- wed_clr(dev, MTK_WED_CTRL,
|
||||
- MTK_WED_CTRL_WDMA_INT_AGENT_EN |
|
||||
- MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
|
||||
- MTK_WED_CTRL_WED_TX_BM_EN |
|
||||
- MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
|
||||
wed_w32(dev, MTK_WED_WPDMA_INT_TRIGGER, 0);
|
||||
wed_w32(dev, MTK_WED_WDMA_INT_TRIGGER, 0);
|
||||
wdma_w32(dev, MTK_WDMA_INT_MASK, 0);
|
||||
@@ -558,7 +552,27 @@ mtk_wed_stop(struct mtk_wed_device *dev)
|
||||
|
||||
wed_w32(dev, MTK_WED_EXT_INT_MASK1, 0);
|
||||
wed_w32(dev, MTK_WED_EXT_INT_MASK2, 0);
|
||||
- wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
|
||||
+}
|
||||
+
|
||||
+static void
|
||||
+mtk_wed_deinit(struct mtk_wed_device *dev)
|
||||
+{
|
||||
+ mtk_wed_stop(dev);
|
||||
+ mtk_wed_dma_disable(dev);
|
||||
+
|
||||
+ wed_clr(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_WDMA_INT_AGENT_EN |
|
||||
+ MTK_WED_CTRL_WPDMA_INT_AGENT_EN |
|
||||
+ MTK_WED_CTRL_WED_TX_BM_EN |
|
||||
+ MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
|
||||
+
|
||||
+ if (dev->hw->version == 1)
|
||||
+ return;
|
||||
+
|
||||
+ wed_clr(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_RX_ROUTE_QM_EN |
|
||||
+ MTK_WED_CTRL_WED_RX_BM_EN |
|
||||
+ MTK_WED_CTRL_RX_RRO_QM_EN);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -568,7 +582,7 @@ mtk_wed_detach(struct mtk_wed_device *de
|
||||
|
||||
mutex_lock(&hw_lock);
|
||||
|
||||
- mtk_wed_stop(dev);
|
||||
+ mtk_wed_deinit(dev);
|
||||
|
||||
mtk_wdma_rx_reset(dev);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WED);
|
||||
@@ -677,7 +691,7 @@ mtk_wed_hw_init_early(struct mtk_wed_dev
|
||||
{
|
||||
u32 mask, set;
|
||||
|
||||
- mtk_wed_stop(dev);
|
||||
+ mtk_wed_deinit(dev);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WED);
|
||||
mtk_wed_set_wpdma(dev);
|
||||
|
||||
--- a/include/linux/soc/mediatek/mtk_wed.h
|
||||
+++ b/include/linux/soc/mediatek/mtk_wed.h
|
||||
@@ -234,6 +234,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
|
||||
(_dev)->ops->ppe_check(_dev, _skb, _reason, _hash)
|
||||
#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) \
|
||||
(_dev)->ops->msg_update(_dev, _id, _msg, _len)
|
||||
+#define mtk_wed_device_stop(_dev) (_dev)->ops->stop(_dev)
|
||||
+#define mtk_wed_device_dma_reset(_dev) (_dev)->ops->reset_dma(_dev)
|
||||
#else
|
||||
static inline bool mtk_wed_device_active(struct mtk_wed_device *dev)
|
||||
{
|
||||
@@ -250,6 +252,8 @@ static inline bool mtk_wed_device_active
|
||||
#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) -ENODEV
|
||||
#define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash) do {} while (0)
|
||||
#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
|
||||
+#define mtk_wed_device_stop(_dev) do {} while (0)
|
||||
+#define mtk_wed_device_dma_reset(_dev) do {} while (0)
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@ -0,0 +1,309 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 24 Nov 2022 16:22:54 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: add mtk_wed_rx_reset routine
|
||||
|
||||
Introduce mtk_wed_rx_reset routine in order to reset rx DMA for Wireless
|
||||
Ethernet Dispatcher available on MT7986 SoC.
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -951,42 +951,130 @@ mtk_wed_ring_reset(struct mtk_wed_ring *
|
||||
}
|
||||
|
||||
static u32
|
||||
-mtk_wed_check_busy(struct mtk_wed_device *dev)
|
||||
+mtk_wed_check_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
|
||||
{
|
||||
- if (wed_r32(dev, MTK_WED_GLO_CFG) & MTK_WED_GLO_CFG_TX_DMA_BUSY)
|
||||
- return true;
|
||||
-
|
||||
- if (wed_r32(dev, MTK_WED_WPDMA_GLO_CFG) &
|
||||
- MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY)
|
||||
- return true;
|
||||
-
|
||||
- if (wed_r32(dev, MTK_WED_CTRL) & MTK_WED_CTRL_WDMA_INT_AGENT_BUSY)
|
||||
- return true;
|
||||
-
|
||||
- if (wed_r32(dev, MTK_WED_WDMA_GLO_CFG) &
|
||||
- MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
|
||||
- return true;
|
||||
-
|
||||
- if (wdma_r32(dev, MTK_WDMA_GLO_CFG) &
|
||||
- MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY)
|
||||
- return true;
|
||||
-
|
||||
- if (wed_r32(dev, MTK_WED_CTRL) &
|
||||
- (MTK_WED_CTRL_WED_TX_BM_BUSY | MTK_WED_CTRL_WED_TX_FREE_AGENT_BUSY))
|
||||
- return true;
|
||||
-
|
||||
- return false;
|
||||
+ return !!(wed_r32(dev, reg) & mask);
|
||||
}
|
||||
|
||||
static int
|
||||
-mtk_wed_poll_busy(struct mtk_wed_device *dev)
|
||||
+mtk_wed_poll_busy(struct mtk_wed_device *dev, u32 reg, u32 mask)
|
||||
{
|
||||
int sleep = 15000;
|
||||
int timeout = 100 * sleep;
|
||||
u32 val;
|
||||
|
||||
return read_poll_timeout(mtk_wed_check_busy, val, !val, sleep,
|
||||
- timeout, false, dev);
|
||||
+ timeout, false, dev, reg, mask);
|
||||
+}
|
||||
+
|
||||
+static int
|
||||
+mtk_wed_rx_reset(struct mtk_wed_device *dev)
|
||||
+{
|
||||
+ struct mtk_wed_wo *wo = dev->hw->wed_wo;
|
||||
+ u8 val = MTK_WED_WO_STATE_SER_RESET;
|
||||
+ int i, ret;
|
||||
+
|
||||
+ ret = mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
|
||||
+ MTK_WED_WO_CMD_CHANGE_STATE, &val,
|
||||
+ sizeof(val), true);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+
|
||||
+ wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG, MTK_WED_WPDMA_RX_D_RX_DRV_EN);
|
||||
+ ret = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_RX_D_RX_DRV_BUSY);
|
||||
+ if (ret) {
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_RX_D_DRV);
|
||||
+ } else {
|
||||
+ wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX,
|
||||
+ MTK_WED_WPDMA_RX_D_RST_CRX_IDX |
|
||||
+ MTK_WED_WPDMA_RX_D_RST_DRV_IDX);
|
||||
+
|
||||
+ wed_set(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE |
|
||||
+ MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE);
|
||||
+ wed_clr(dev, MTK_WED_WPDMA_RX_D_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE |
|
||||
+ MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE);
|
||||
+
|
||||
+ wed_w32(dev, MTK_WED_WPDMA_RX_D_RST_IDX, 0);
|
||||
+ }
|
||||
+
|
||||
+ /* reset rro qm */
|
||||
+ wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_RRO_QM_EN);
|
||||
+ ret = mtk_wed_poll_busy(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_RX_RRO_QM_BUSY);
|
||||
+ if (ret) {
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_RX_RRO_QM);
|
||||
+ } else {
|
||||
+ wed_set(dev, MTK_WED_RROQM_RST_IDX,
|
||||
+ MTK_WED_RROQM_RST_IDX_MIOD |
|
||||
+ MTK_WED_RROQM_RST_IDX_FDBK);
|
||||
+ wed_w32(dev, MTK_WED_RROQM_RST_IDX, 0);
|
||||
+ }
|
||||
+
|
||||
+ /* reset route qm */
|
||||
+ wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_RX_ROUTE_QM_EN);
|
||||
+ ret = mtk_wed_poll_busy(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_RX_ROUTE_QM_BUSY);
|
||||
+ if (ret)
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_RX_ROUTE_QM);
|
||||
+ else
|
||||
+ wed_set(dev, MTK_WED_RTQM_GLO_CFG,
|
||||
+ MTK_WED_RTQM_Q_RST);
|
||||
+
|
||||
+ /* reset tx wdma */
|
||||
+ mtk_wdma_tx_reset(dev);
|
||||
+
|
||||
+ /* reset tx wdma drv */
|
||||
+ wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_TX_DRV_EN);
|
||||
+ mtk_wed_poll_busy(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_WDMA_INT_AGENT_BUSY);
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_WDMA_TX_DRV);
|
||||
+
|
||||
+ /* reset wed rx dma */
|
||||
+ ret = mtk_wed_poll_busy(dev, MTK_WED_GLO_CFG,
|
||||
+ MTK_WED_GLO_CFG_RX_DMA_BUSY);
|
||||
+ wed_clr(dev, MTK_WED_GLO_CFG, MTK_WED_GLO_CFG_RX_DMA_EN);
|
||||
+ if (ret) {
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_WED_RX_DMA);
|
||||
+ } else {
|
||||
+ struct mtk_eth *eth = dev->hw->eth;
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
|
||||
+ wed_set(dev, MTK_WED_RESET_IDX,
|
||||
+ MTK_WED_RESET_IDX_RX_V2);
|
||||
+ else
|
||||
+ wed_set(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_RX);
|
||||
+ wed_w32(dev, MTK_WED_RESET_IDX, 0);
|
||||
+ }
|
||||
+
|
||||
+ /* reset rx bm */
|
||||
+ wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_RX_BM_EN);
|
||||
+ mtk_wed_poll_busy(dev, MTK_WED_CTRL,
|
||||
+ MTK_WED_CTRL_WED_RX_BM_BUSY);
|
||||
+ mtk_wed_reset(dev, MTK_WED_RESET_RX_BM);
|
||||
+
|
||||
+ /* wo change to enable state */
|
||||
+ val = MTK_WED_WO_STATE_ENABLE;
|
||||
+ ret = mtk_wed_mcu_send_msg(wo, MTK_WED_MODULE_ID_WO,
|
||||
+ MTK_WED_WO_CMD_CHANGE_STATE, &val,
|
||||
+ sizeof(val), true);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+
|
||||
+ /* wed_rx_ring_reset */
|
||||
+ for (i = 0; i < ARRAY_SIZE(dev->rx_ring); i++) {
|
||||
+ if (!dev->rx_ring[i].desc)
|
||||
+ continue;
|
||||
+
|
||||
+ mtk_wed_ring_reset(&dev->rx_ring[i], MTK_WED_RX_RING_SIZE,
|
||||
+ false);
|
||||
+ }
|
||||
+ mtk_wed_free_rx_buffer(dev);
|
||||
+
|
||||
+ return 0;
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -1004,19 +1092,23 @@ mtk_wed_reset_dma(struct mtk_wed_device
|
||||
true);
|
||||
}
|
||||
|
||||
- if (mtk_wed_poll_busy(dev))
|
||||
- busy = mtk_wed_check_busy(dev);
|
||||
-
|
||||
+ /* 1. reset WED tx DMA */
|
||||
+ wed_clr(dev, MTK_WED_GLO_CFG, MTK_WED_GLO_CFG_TX_DMA_EN);
|
||||
+ busy = mtk_wed_poll_busy(dev, MTK_WED_GLO_CFG,
|
||||
+ MTK_WED_GLO_CFG_TX_DMA_BUSY);
|
||||
if (busy) {
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WED_TX_DMA);
|
||||
} else {
|
||||
- wed_w32(dev, MTK_WED_RESET_IDX,
|
||||
- MTK_WED_RESET_IDX_TX |
|
||||
- MTK_WED_RESET_IDX_RX);
|
||||
+ wed_w32(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_IDX_TX);
|
||||
wed_w32(dev, MTK_WED_RESET_IDX, 0);
|
||||
}
|
||||
|
||||
- mtk_wdma_rx_reset(dev);
|
||||
+ /* 2. reset WDMA rx DMA */
|
||||
+ busy = !!mtk_wdma_rx_reset(dev);
|
||||
+ wed_clr(dev, MTK_WED_WDMA_GLO_CFG, MTK_WED_WDMA_GLO_CFG_RX_DRV_EN);
|
||||
+ if (!busy)
|
||||
+ busy = mtk_wed_poll_busy(dev, MTK_WED_WDMA_GLO_CFG,
|
||||
+ MTK_WED_WDMA_GLO_CFG_RX_DRV_BUSY);
|
||||
|
||||
if (busy) {
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WDMA_INT_AGENT);
|
||||
@@ -1033,6 +1125,9 @@ mtk_wed_reset_dma(struct mtk_wed_device
|
||||
MTK_WED_WDMA_GLO_CFG_RST_INIT_COMPLETE);
|
||||
}
|
||||
|
||||
+ /* 3. reset WED WPDMA tx */
|
||||
+ wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_TX_FREE_AGENT_EN);
|
||||
+
|
||||
for (i = 0; i < 100; i++) {
|
||||
val = wed_r32(dev, MTK_WED_TX_BM_INTF);
|
||||
if (FIELD_GET(MTK_WED_TX_BM_INTF_TKFIFO_FDEP, val) == 0x40)
|
||||
@@ -1040,8 +1135,19 @@ mtk_wed_reset_dma(struct mtk_wed_device
|
||||
}
|
||||
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_TX_FREE_AGENT);
|
||||
+ wed_clr(dev, MTK_WED_CTRL, MTK_WED_CTRL_WED_TX_BM_EN);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_TX_BM);
|
||||
|
||||
+ /* 4. reset WED WPDMA tx */
|
||||
+ busy = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_GLO_CFG_TX_DRV_BUSY);
|
||||
+ wed_clr(dev, MTK_WED_WPDMA_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_GLO_CFG_TX_DRV_EN |
|
||||
+ MTK_WED_WPDMA_GLO_CFG_RX_DRV_EN);
|
||||
+ if (!busy)
|
||||
+ busy = mtk_wed_poll_busy(dev, MTK_WED_WPDMA_GLO_CFG,
|
||||
+ MTK_WED_WPDMA_GLO_CFG_RX_DRV_BUSY);
|
||||
+
|
||||
if (busy) {
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_INT_AGENT);
|
||||
mtk_wed_reset(dev, MTK_WED_RESET_WPDMA_TX_DRV);
|
||||
@@ -1052,6 +1158,17 @@ mtk_wed_reset_dma(struct mtk_wed_device
|
||||
MTK_WED_WPDMA_RESET_IDX_RX);
|
||||
wed_w32(dev, MTK_WED_WPDMA_RESET_IDX, 0);
|
||||
}
|
||||
+
|
||||
+ dev->init_done = false;
|
||||
+ if (dev->hw->version == 1)
|
||||
+ return;
|
||||
+
|
||||
+ if (!busy) {
|
||||
+ wed_w32(dev, MTK_WED_RESET_IDX, MTK_WED_RESET_WPDMA_IDX_RX);
|
||||
+ wed_w32(dev, MTK_WED_RESET_IDX, 0);
|
||||
+ }
|
||||
+
|
||||
+ mtk_wed_rx_reset(dev);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -1274,6 +1391,9 @@ mtk_wed_start(struct mtk_wed_device *dev
|
||||
{
|
||||
int i;
|
||||
|
||||
+ if (mtk_wed_get_rx_capa(dev) && mtk_wed_rx_buffer_alloc(dev))
|
||||
+ return;
|
||||
+
|
||||
for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
|
||||
if (!dev->rx_wdma[i].desc)
|
||||
mtk_wed_wdma_rx_ring_setup(dev, i, 16);
|
||||
@@ -1362,10 +1482,6 @@ mtk_wed_attach(struct mtk_wed_device *de
|
||||
goto out;
|
||||
|
||||
if (mtk_wed_get_rx_capa(dev)) {
|
||||
- ret = mtk_wed_rx_buffer_alloc(dev);
|
||||
- if (ret)
|
||||
- goto out;
|
||||
-
|
||||
ret = mtk_wed_rro_alloc(dev);
|
||||
if (ret)
|
||||
goto out;
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_regs.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_regs.h
|
||||
@@ -24,11 +24,15 @@ struct mtk_wdma_desc {
|
||||
|
||||
#define MTK_WED_RESET 0x008
|
||||
#define MTK_WED_RESET_TX_BM BIT(0)
|
||||
+#define MTK_WED_RESET_RX_BM BIT(1)
|
||||
#define MTK_WED_RESET_TX_FREE_AGENT BIT(4)
|
||||
#define MTK_WED_RESET_WPDMA_TX_DRV BIT(8)
|
||||
#define MTK_WED_RESET_WPDMA_RX_DRV BIT(9)
|
||||
+#define MTK_WED_RESET_WPDMA_RX_D_DRV BIT(10)
|
||||
#define MTK_WED_RESET_WPDMA_INT_AGENT BIT(11)
|
||||
#define MTK_WED_RESET_WED_TX_DMA BIT(12)
|
||||
+#define MTK_WED_RESET_WED_RX_DMA BIT(13)
|
||||
+#define MTK_WED_RESET_WDMA_TX_DRV BIT(16)
|
||||
#define MTK_WED_RESET_WDMA_RX_DRV BIT(17)
|
||||
#define MTK_WED_RESET_WDMA_INT_AGENT BIT(19)
|
||||
#define MTK_WED_RESET_RX_RRO_QM BIT(20)
|
||||
@@ -158,6 +162,8 @@ struct mtk_wdma_desc {
|
||||
#define MTK_WED_RESET_IDX 0x20c
|
||||
#define MTK_WED_RESET_IDX_TX GENMASK(3, 0)
|
||||
#define MTK_WED_RESET_IDX_RX GENMASK(17, 16)
|
||||
+#define MTK_WED_RESET_IDX_RX_V2 GENMASK(7, 6)
|
||||
+#define MTK_WED_RESET_WPDMA_IDX_RX GENMASK(31, 30)
|
||||
|
||||
#define MTK_WED_TX_MIB(_n) (0x2a0 + (_n) * 4)
|
||||
#define MTK_WED_RX_MIB(_n) (0x2e0 + (_n) * 4)
|
||||
@@ -267,6 +273,9 @@ struct mtk_wdma_desc {
|
||||
|
||||
#define MTK_WED_WPDMA_RX_D_GLO_CFG 0x75c
|
||||
#define MTK_WED_WPDMA_RX_D_RX_DRV_EN BIT(0)
|
||||
+#define MTK_WED_WPDMA_RX_D_RX_DRV_BUSY BIT(1)
|
||||
+#define MTK_WED_WPDMA_RX_D_FSM_RETURN_IDLE BIT(3)
|
||||
+#define MTK_WED_WPDMA_RX_D_RST_INIT_COMPLETE BIT(4)
|
||||
#define MTK_WED_WPDMA_RX_D_INIT_PHASE_RXEN_SEL GENMASK(11, 7)
|
||||
#define MTK_WED_WPDMA_RX_D_RXD_READ_LEN GENMASK(31, 24)
|
||||
|
||||
@ -0,0 +1,103 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 24 Nov 2022 16:22:55 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: add reset to tx_ring_setup callback
|
||||
|
||||
Introduce reset parameter to mtk_wed_tx_ring_setup signature.
|
||||
This is a preliminary patch to add Wireless Ethernet Dispatcher reset
|
||||
support.
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -1188,7 +1188,8 @@ mtk_wed_ring_alloc(struct mtk_wed_device
|
||||
}
|
||||
|
||||
static int
|
||||
-mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
|
||||
+mtk_wed_wdma_rx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
|
||||
+ bool reset)
|
||||
{
|
||||
u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
|
||||
struct mtk_wed_ring *wdma;
|
||||
@@ -1197,8 +1198,8 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
|
||||
return -EINVAL;
|
||||
|
||||
wdma = &dev->rx_wdma[idx];
|
||||
- if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
|
||||
- true))
|
||||
+ if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
|
||||
+ desc_size, true))
|
||||
return -ENOMEM;
|
||||
|
||||
wdma_w32(dev, MTK_WDMA_RING_RX(idx) + MTK_WED_RING_OFS_BASE,
|
||||
@@ -1396,7 +1397,7 @@ mtk_wed_start(struct mtk_wed_device *dev
|
||||
|
||||
for (i = 0; i < ARRAY_SIZE(dev->rx_wdma); i++)
|
||||
if (!dev->rx_wdma[i].desc)
|
||||
- mtk_wed_wdma_rx_ring_setup(dev, i, 16);
|
||||
+ mtk_wed_wdma_rx_ring_setup(dev, i, 16, false);
|
||||
|
||||
mtk_wed_hw_init(dev);
|
||||
mtk_wed_configure_irq(dev, irq_mask);
|
||||
@@ -1505,7 +1506,8 @@ unlock:
|
||||
}
|
||||
|
||||
static int
|
||||
-mtk_wed_tx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
|
||||
+mtk_wed_tx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs,
|
||||
+ bool reset)
|
||||
{
|
||||
struct mtk_wed_ring *ring = &dev->tx_ring[idx];
|
||||
|
||||
@@ -1524,11 +1526,12 @@ mtk_wed_tx_ring_setup(struct mtk_wed_dev
|
||||
if (WARN_ON(idx >= ARRAY_SIZE(dev->tx_ring)))
|
||||
return -EINVAL;
|
||||
|
||||
- if (mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
|
||||
- sizeof(*ring->desc), true))
|
||||
+ if (!reset && mtk_wed_ring_alloc(dev, ring, MTK_WED_TX_RING_SIZE,
|
||||
+ sizeof(*ring->desc), true))
|
||||
return -ENOMEM;
|
||||
|
||||
- if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
|
||||
+ if (mtk_wed_wdma_rx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE,
|
||||
+ reset))
|
||||
return -ENOMEM;
|
||||
|
||||
ring->reg_base = MTK_WED_RING_TX(idx);
|
||||
--- a/include/linux/soc/mediatek/mtk_wed.h
|
||||
+++ b/include/linux/soc/mediatek/mtk_wed.h
|
||||
@@ -158,7 +158,7 @@ struct mtk_wed_device {
|
||||
struct mtk_wed_ops {
|
||||
int (*attach)(struct mtk_wed_device *dev);
|
||||
int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
|
||||
- void __iomem *regs);
|
||||
+ void __iomem *regs, bool reset);
|
||||
int (*rx_ring_setup)(struct mtk_wed_device *dev, int ring,
|
||||
void __iomem *regs);
|
||||
int (*txfree_ring_setup)(struct mtk_wed_device *dev,
|
||||
@@ -216,8 +216,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
|
||||
#define mtk_wed_device_active(_dev) !!(_dev)->ops
|
||||
#define mtk_wed_device_detach(_dev) (_dev)->ops->detach(_dev)
|
||||
#define mtk_wed_device_start(_dev, _mask) (_dev)->ops->start(_dev, _mask)
|
||||
-#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) \
|
||||
- (_dev)->ops->tx_ring_setup(_dev, _ring, _regs)
|
||||
+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs, _reset) \
|
||||
+ (_dev)->ops->tx_ring_setup(_dev, _ring, _regs, _reset)
|
||||
#define mtk_wed_device_txfree_ring_setup(_dev, _regs) \
|
||||
(_dev)->ops->txfree_ring_setup(_dev, _regs)
|
||||
#define mtk_wed_device_reg_read(_dev, _reg) \
|
||||
@@ -243,7 +243,7 @@ static inline bool mtk_wed_device_active
|
||||
}
|
||||
#define mtk_wed_device_detach(_dev) do {} while (0)
|
||||
#define mtk_wed_device_start(_dev, _mask) do {} while (0)
|
||||
-#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs) -ENODEV
|
||||
+#define mtk_wed_device_tx_ring_setup(_dev, _ring, _regs, _reset) -ENODEV
|
||||
#define mtk_wed_device_txfree_ring_setup(_dev, _ring, _regs) -ENODEV
|
||||
#define mtk_wed_device_reg_read(_dev, _reg) 0
|
||||
#define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
|
||||
@ -0,0 +1,103 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 1 Dec 2022 16:26:53 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: fix sleep while atomic in
|
||||
mtk_wed_wo_queue_refill
|
||||
|
||||
In order to fix the following sleep while atomic bug always alloc pages
|
||||
with GFP_ATOMIC in mtk_wed_wo_queue_refill since page_frag_alloc runs in
|
||||
spin_lock critical section.
|
||||
|
||||
[ 9.049719] Hardware name: MediaTek MT7986a RFB (DT)
|
||||
[ 9.054665] Call trace:
|
||||
[ 9.057096] dump_backtrace+0x0/0x154
|
||||
[ 9.060751] show_stack+0x14/0x1c
|
||||
[ 9.064052] dump_stack_lvl+0x64/0x7c
|
||||
[ 9.067702] dump_stack+0x14/0x2c
|
||||
[ 9.071001] ___might_sleep+0xec/0x120
|
||||
[ 9.074736] __might_sleep+0x4c/0x9c
|
||||
[ 9.078296] __alloc_pages+0x184/0x2e4
|
||||
[ 9.082030] page_frag_alloc_align+0x98/0x1ac
|
||||
[ 9.086369] mtk_wed_wo_queue_refill+0x134/0x234
|
||||
[ 9.090974] mtk_wed_wo_init+0x174/0x2c0
|
||||
[ 9.094881] mtk_wed_attach+0x7c8/0x7e0
|
||||
[ 9.098701] mt7915_mmio_wed_init+0x1f0/0x3a0 [mt7915e]
|
||||
[ 9.103940] mt7915_pci_probe+0xec/0x3bc [mt7915e]
|
||||
[ 9.108727] pci_device_probe+0xac/0x13c
|
||||
[ 9.112638] really_probe.part.0+0x98/0x2f4
|
||||
[ 9.116807] __driver_probe_device+0x94/0x13c
|
||||
[ 9.121147] driver_probe_device+0x40/0x114
|
||||
[ 9.125314] __driver_attach+0x7c/0x180
|
||||
[ 9.129133] bus_for_each_dev+0x5c/0x90
|
||||
[ 9.132953] driver_attach+0x20/0x2c
|
||||
[ 9.136513] bus_add_driver+0x104/0x1fc
|
||||
[ 9.140333] driver_register+0x74/0x120
|
||||
[ 9.144153] __pci_register_driver+0x40/0x50
|
||||
[ 9.148407] mt7915_init+0x5c/0x1000 [mt7915e]
|
||||
[ 9.152848] do_one_initcall+0x40/0x25c
|
||||
[ 9.156669] do_init_module+0x44/0x230
|
||||
[ 9.160403] load_module+0x1f30/0x2750
|
||||
[ 9.164135] __do_sys_init_module+0x150/0x200
|
||||
[ 9.168475] __arm64_sys_init_module+0x18/0x20
|
||||
[ 9.172901] invoke_syscall.constprop.0+0x4c/0xe0
|
||||
[ 9.177589] do_el0_svc+0x48/0xe0
|
||||
[ 9.180889] el0_svc+0x14/0x50
|
||||
[ 9.183929] el0t_64_sync_handler+0x9c/0x120
|
||||
[ 9.188183] el0t_64_sync+0x158/0x15c
|
||||
|
||||
Fixes: 799684448e3e ("net: ethernet: mtk_wed: introduce wed wo support")
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Reviewed-by: Pavan Chebbi <pavan.chebbi@broadcom.com>
|
||||
Link: https://lore.kernel.org/r/67ca94bdd3d9eaeb86e52b3050fbca0bcf7bb02f.1669908312.git.lorenzo@kernel.org
|
||||
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
@@ -133,17 +133,18 @@ mtk_wed_wo_dequeue(struct mtk_wed_wo *wo
|
||||
|
||||
static int
|
||||
mtk_wed_wo_queue_refill(struct mtk_wed_wo *wo, struct mtk_wed_wo_queue *q,
|
||||
- gfp_t gfp, bool rx)
|
||||
+ bool rx)
|
||||
{
|
||||
enum dma_data_direction dir = rx ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
|
||||
int n_buf = 0;
|
||||
|
||||
spin_lock_bh(&q->lock);
|
||||
while (q->queued < q->n_desc) {
|
||||
- void *buf = page_frag_alloc(&q->cache, q->buf_size, gfp);
|
||||
struct mtk_wed_wo_queue_entry *entry;
|
||||
dma_addr_t addr;
|
||||
+ void *buf;
|
||||
|
||||
+ buf = page_frag_alloc(&q->cache, q->buf_size, GFP_ATOMIC);
|
||||
if (!buf)
|
||||
break;
|
||||
|
||||
@@ -215,7 +216,7 @@ mtk_wed_wo_rx_run_queue(struct mtk_wed_w
|
||||
mtk_wed_mcu_rx_unsolicited_event(wo, skb);
|
||||
}
|
||||
|
||||
- if (mtk_wed_wo_queue_refill(wo, q, GFP_ATOMIC, true)) {
|
||||
+ if (mtk_wed_wo_queue_refill(wo, q, true)) {
|
||||
u32 index = (q->head - 1) % q->n_desc;
|
||||
|
||||
mtk_wed_wo_queue_kick(wo, q, index);
|
||||
@@ -432,7 +433,7 @@ mtk_wed_wo_hardware_init(struct mtk_wed_
|
||||
if (ret)
|
||||
goto error;
|
||||
|
||||
- mtk_wed_wo_queue_refill(wo, &wo->q_tx, GFP_KERNEL, false);
|
||||
+ mtk_wed_wo_queue_refill(wo, &wo->q_tx, false);
|
||||
mtk_wed_wo_queue_reset(wo, &wo->q_tx);
|
||||
|
||||
regs.desc_base = MTK_WED_WO_CCIF_DUMMY5;
|
||||
@@ -446,7 +447,7 @@ mtk_wed_wo_hardware_init(struct mtk_wed_
|
||||
if (ret)
|
||||
goto error;
|
||||
|
||||
- mtk_wed_wo_queue_refill(wo, &wo->q_rx, GFP_KERNEL, true);
|
||||
+ mtk_wed_wo_queue_refill(wo, &wo->q_rx, true);
|
||||
mtk_wed_wo_queue_reset(wo, &wo->q_rx);
|
||||
|
||||
/* rx queue irqmask */
|
||||
@ -0,0 +1,52 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Tue, 10 Jan 2023 10:31:26 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: get rid of queue lock for rx queue
|
||||
|
||||
Queue spinlock is currently held in mtk_wed_wo_queue_rx_clean and
|
||||
mtk_wed_wo_queue_refill routines for MTK Wireless Ethernet Dispatcher
|
||||
MCU rx queue. mtk_wed_wo_queue_refill() is running during initialization
|
||||
and in rx tasklet while mtk_wed_wo_queue_rx_clean() is running in
|
||||
mtk_wed_wo_hw_deinit() during hw de-init phase after rx tasklet has been
|
||||
disabled. Since mtk_wed_wo_queue_rx_clean and mtk_wed_wo_queue_refill
|
||||
routines can't run concurrently get rid of spinlock for mcu rx queue.
|
||||
|
||||
Reviewed-by: Alexander Duyck <alexanderduyck@fb.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Link: https://lore.kernel.org/r/36ec3b729542ea60898471d890796f745479ba32.1673342990.git.lorenzo@kernel.org
|
||||
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
@@ -138,7 +138,6 @@ mtk_wed_wo_queue_refill(struct mtk_wed_w
|
||||
enum dma_data_direction dir = rx ? DMA_FROM_DEVICE : DMA_TO_DEVICE;
|
||||
int n_buf = 0;
|
||||
|
||||
- spin_lock_bh(&q->lock);
|
||||
while (q->queued < q->n_desc) {
|
||||
struct mtk_wed_wo_queue_entry *entry;
|
||||
dma_addr_t addr;
|
||||
@@ -172,7 +171,6 @@ mtk_wed_wo_queue_refill(struct mtk_wed_w
|
||||
q->queued++;
|
||||
n_buf++;
|
||||
}
|
||||
- spin_unlock_bh(&q->lock);
|
||||
|
||||
return n_buf;
|
||||
}
|
||||
@@ -316,7 +314,6 @@ mtk_wed_wo_queue_rx_clean(struct mtk_wed
|
||||
{
|
||||
struct page *page;
|
||||
|
||||
- spin_lock_bh(&q->lock);
|
||||
for (;;) {
|
||||
void *buf = mtk_wed_wo_dequeue(wo, q, NULL, true);
|
||||
|
||||
@@ -325,7 +322,6 @@ mtk_wed_wo_queue_rx_clean(struct mtk_wed
|
||||
|
||||
skb_free_frag(buf);
|
||||
}
|
||||
- spin_unlock_bh(&q->lock);
|
||||
|
||||
if (!q->cache.va)
|
||||
return;
|
||||
@ -0,0 +1,75 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Thu, 12 Jan 2023 10:21:29 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: get rid of queue lock for tx queue
|
||||
|
||||
Similar to MTK Wireless Ethernet Dispatcher (WED) MCU rx queue,
|
||||
we do not need to protect WED MCU tx queue with a spin lock since
|
||||
the tx queue is accessed in the two following routines:
|
||||
- mtk_wed_wo_queue_tx_skb():
|
||||
it is run at initialization and during mt7915 normal operation.
|
||||
Moreover MCU messages are serialized through MCU mutex.
|
||||
- mtk_wed_wo_queue_tx_clean():
|
||||
it runs just at mt7915 driver module unload when no more messages
|
||||
are sent to the MCU.
|
||||
|
||||
Remove tx queue spinlock.
|
||||
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Link: https://lore.kernel.org/r/7bd0337b2a13ab1a63673b7c03fd35206b3b284e.1673515140.git.lorenzo@kernel.org
|
||||
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.c
|
||||
@@ -258,7 +258,6 @@ mtk_wed_wo_queue_alloc(struct mtk_wed_wo
|
||||
int n_desc, int buf_size, int index,
|
||||
struct mtk_wed_wo_queue_regs *regs)
|
||||
{
|
||||
- spin_lock_init(&q->lock);
|
||||
q->regs = *regs;
|
||||
q->n_desc = n_desc;
|
||||
q->buf_size = buf_size;
|
||||
@@ -290,7 +289,6 @@ mtk_wed_wo_queue_tx_clean(struct mtk_wed
|
||||
struct page *page;
|
||||
int i;
|
||||
|
||||
- spin_lock_bh(&q->lock);
|
||||
for (i = 0; i < q->n_desc; i++) {
|
||||
struct mtk_wed_wo_queue_entry *entry = &q->entry[i];
|
||||
|
||||
@@ -299,7 +297,6 @@ mtk_wed_wo_queue_tx_clean(struct mtk_wed
|
||||
skb_free_frag(entry->buf);
|
||||
entry->buf = NULL;
|
||||
}
|
||||
- spin_unlock_bh(&q->lock);
|
||||
|
||||
if (!q->cache.va)
|
||||
return;
|
||||
@@ -347,8 +344,6 @@ int mtk_wed_wo_queue_tx_skb(struct mtk_w
|
||||
int ret = 0, index;
|
||||
u32 ctrl;
|
||||
|
||||
- spin_lock_bh(&q->lock);
|
||||
-
|
||||
q->tail = mtk_wed_mmio_r32(wo, q->regs.dma_idx);
|
||||
index = (q->head + 1) % q->n_desc;
|
||||
if (q->tail == index) {
|
||||
@@ -379,8 +374,6 @@ int mtk_wed_wo_queue_tx_skb(struct mtk_w
|
||||
mtk_wed_wo_queue_kick(wo, q, q->head);
|
||||
mtk_wed_wo_kickout(wo);
|
||||
out:
|
||||
- spin_unlock_bh(&q->lock);
|
||||
-
|
||||
dev_kfree_skb(skb);
|
||||
|
||||
return ret;
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed_wo.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed_wo.h
|
||||
@@ -211,7 +211,6 @@ struct mtk_wed_wo_queue {
|
||||
struct mtk_wed_wo_queue_regs regs;
|
||||
|
||||
struct page_frag_cache cache;
|
||||
- spinlock_t lock;
|
||||
|
||||
struct mtk_wed_wo_queue_desc *desc;
|
||||
dma_addr_t desc_dma;
|
||||
@ -0,0 +1,70 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Sat, 14 Jan 2023 18:01:28 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce mtk_hw_reset utility
|
||||
routine
|
||||
|
||||
This is a preliminary patch to add Wireless Ethernet Dispatcher reset
|
||||
support.
|
||||
|
||||
Reviewed-by: Leon Romanovsky <leonro@nvidia.com>
|
||||
Tested-by: Daniel Golle <daniel@makrotopia.org>
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3199,6 +3199,27 @@ static void mtk_set_mcr_max_rx(struct mt
|
||||
mtk_w32(mac->hw, mcr_new, MTK_MAC_MCR(mac->id));
|
||||
}
|
||||
|
||||
+static void mtk_hw_reset(struct mtk_eth *eth)
|
||||
+{
|
||||
+ u32 val;
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
+ regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
|
||||
+ val = RSTCTRL_PPE0_V2;
|
||||
+ } else {
|
||||
+ val = RSTCTRL_PPE0;
|
||||
+ }
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
+ val |= RSTCTRL_PPE1;
|
||||
+
|
||||
+ ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
|
||||
+ regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
|
||||
+ 0x3ffffff);
|
||||
+}
|
||||
+
|
||||
static int mtk_hw_init(struct mtk_eth *eth)
|
||||
{
|
||||
u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
|
||||
@@ -3238,22 +3259,9 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
return 0;
|
||||
}
|
||||
|
||||
- if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
- regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN, 0);
|
||||
- val = RSTCTRL_PPE0_V2;
|
||||
- } else {
|
||||
- val = RSTCTRL_PPE0;
|
||||
- }
|
||||
-
|
||||
- if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
- val |= RSTCTRL_PPE1;
|
||||
-
|
||||
- ethsys_reset(eth, RSTCTRL_ETH | RSTCTRL_FE | val);
|
||||
+ mtk_hw_reset(eth);
|
||||
|
||||
if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
- regmap_write(eth->ethsys, ETHSYS_FE_RST_CHK_IDLE_EN,
|
||||
- 0x3ffffff);
|
||||
-
|
||||
/* Set FE to PDMAv2 if necessary */
|
||||
val = mtk_r32(eth, MTK_FE_GLO_MISC);
|
||||
mtk_w32(eth, val | BIT(4), MTK_FE_GLO_MISC);
|
||||
@ -0,0 +1,107 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Sat, 14 Jan 2023 18:01:29 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: introduce mtk_hw_warm_reset
|
||||
support
|
||||
|
||||
Introduce mtk_hw_warm_reset utility routine. This is a preliminary patch
|
||||
to align reset procedure to vendor sdk and avoid to power down the chip
|
||||
during hw reset.
|
||||
|
||||
Reviewed-by: Leon Romanovsky <leonro@nvidia.com>
|
||||
Tested-by: Daniel Golle <daniel@makrotopia.org>
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3220,7 +3220,54 @@ static void mtk_hw_reset(struct mtk_eth
|
||||
0x3ffffff);
|
||||
}
|
||||
|
||||
-static int mtk_hw_init(struct mtk_eth *eth)
|
||||
+static u32 mtk_hw_reset_read(struct mtk_eth *eth)
|
||||
+{
|
||||
+ u32 val;
|
||||
+
|
||||
+ regmap_read(eth->ethsys, ETHSYS_RSTCTRL, &val);
|
||||
+ return val;
|
||||
+}
|
||||
+
|
||||
+static void mtk_hw_warm_reset(struct mtk_eth *eth)
|
||||
+{
|
||||
+ u32 rst_mask, val;
|
||||
+
|
||||
+ regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, RSTCTRL_FE,
|
||||
+ RSTCTRL_FE);
|
||||
+ if (readx_poll_timeout_atomic(mtk_hw_reset_read, eth, val,
|
||||
+ val & RSTCTRL_FE, 1, 1000)) {
|
||||
+ dev_err(eth->dev, "warm reset failed\n");
|
||||
+ mtk_hw_reset(eth);
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2))
|
||||
+ rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0_V2;
|
||||
+ else
|
||||
+ rst_mask = RSTCTRL_ETH | RSTCTRL_PPE0;
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
+ rst_mask |= RSTCTRL_PPE1;
|
||||
+
|
||||
+ regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, rst_mask, rst_mask);
|
||||
+
|
||||
+ udelay(1);
|
||||
+ val = mtk_hw_reset_read(eth);
|
||||
+ if (!(val & rst_mask))
|
||||
+ dev_err(eth->dev, "warm reset stage0 failed %08x (%08x)\n",
|
||||
+ val, rst_mask);
|
||||
+
|
||||
+ rst_mask |= RSTCTRL_FE;
|
||||
+ regmap_update_bits(eth->ethsys, ETHSYS_RSTCTRL, rst_mask, ~rst_mask);
|
||||
+
|
||||
+ udelay(1);
|
||||
+ val = mtk_hw_reset_read(eth);
|
||||
+ if (val & rst_mask)
|
||||
+ dev_err(eth->dev, "warm reset stage1 failed %08x (%08x)\n",
|
||||
+ val, rst_mask);
|
||||
+}
|
||||
+
|
||||
+static int mtk_hw_init(struct mtk_eth *eth, bool reset)
|
||||
{
|
||||
u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
|
||||
ETHSYS_DMA_AG_MAP_PPE;
|
||||
@@ -3259,7 +3306,12 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
return 0;
|
||||
}
|
||||
|
||||
- mtk_hw_reset(eth);
|
||||
+ msleep(100);
|
||||
+
|
||||
+ if (reset)
|
||||
+ mtk_hw_warm_reset(eth);
|
||||
+ else
|
||||
+ mtk_hw_reset(eth);
|
||||
|
||||
if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
|
||||
/* Set FE to PDMAv2 if necessary */
|
||||
@@ -3464,7 +3516,7 @@ static void mtk_pending_work(struct work
|
||||
if (eth->dev->pins)
|
||||
pinctrl_select_state(eth->dev->pins->p,
|
||||
eth->dev->pins->default_state);
|
||||
- mtk_hw_init(eth);
|
||||
+ mtk_hw_init(eth, true);
|
||||
|
||||
/* restart DMA and enable IRQs */
|
||||
for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
@@ -4056,7 +4108,7 @@ static int mtk_probe(struct platform_dev
|
||||
eth->msg_enable = netif_msg_init(mtk_msg_level, MTK_DEFAULT_MSG_ENABLE);
|
||||
INIT_WORK(ð->pending_work, mtk_pending_work);
|
||||
|
||||
- err = mtk_hw_init(eth);
|
||||
+ err = mtk_hw_init(eth, false);
|
||||
if (err)
|
||||
goto err_wed_exit;
|
||||
|
||||
@ -0,0 +1,262 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Sat, 14 Jan 2023 18:01:30 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: align reset procedure to vendor
|
||||
sdk
|
||||
|
||||
Avoid to power-down the ethernet chip during hw reset and align reset
|
||||
procedure to vendor sdk.
|
||||
|
||||
Reviewed-by: Leon Romanovsky <leonro@nvidia.com>
|
||||
Tested-by: Daniel Golle <daniel@makrotopia.org>
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -2785,14 +2785,29 @@ static void mtk_dma_free(struct mtk_eth
|
||||
kfree(eth->scratch_head);
|
||||
}
|
||||
|
||||
+static bool mtk_hw_reset_check(struct mtk_eth *eth)
|
||||
+{
|
||||
+ u32 val = mtk_r32(eth, MTK_INT_STATUS2);
|
||||
+
|
||||
+ return (val & MTK_FE_INT_FQ_EMPTY) || (val & MTK_FE_INT_RFIFO_UF) ||
|
||||
+ (val & MTK_FE_INT_RFIFO_OV) || (val & MTK_FE_INT_TSO_FAIL) ||
|
||||
+ (val & MTK_FE_INT_TSO_ALIGN) || (val & MTK_FE_INT_TSO_ILLEGAL);
|
||||
+}
|
||||
+
|
||||
static void mtk_tx_timeout(struct net_device *dev, unsigned int txqueue)
|
||||
{
|
||||
struct mtk_mac *mac = netdev_priv(dev);
|
||||
struct mtk_eth *eth = mac->hw;
|
||||
|
||||
+ if (test_bit(MTK_RESETTING, ð->state))
|
||||
+ return;
|
||||
+
|
||||
+ if (!mtk_hw_reset_check(eth))
|
||||
+ return;
|
||||
+
|
||||
eth->netdev[mac->id]->stats.tx_errors++;
|
||||
- netif_err(eth, tx_err, dev,
|
||||
- "transmit timed out\n");
|
||||
+ netif_err(eth, tx_err, dev, "transmit timed out\n");
|
||||
+
|
||||
schedule_work(ð->pending_work);
|
||||
}
|
||||
|
||||
@@ -3274,15 +3289,17 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
const struct mtk_reg_map *reg_map = eth->soc->reg_map;
|
||||
int i, val, ret;
|
||||
|
||||
- if (test_and_set_bit(MTK_HW_INIT, ð->state))
|
||||
+ if (!reset && test_and_set_bit(MTK_HW_INIT, ð->state))
|
||||
return 0;
|
||||
|
||||
- pm_runtime_enable(eth->dev);
|
||||
- pm_runtime_get_sync(eth->dev);
|
||||
+ if (!reset) {
|
||||
+ pm_runtime_enable(eth->dev);
|
||||
+ pm_runtime_get_sync(eth->dev);
|
||||
|
||||
- ret = mtk_clk_enable(eth);
|
||||
- if (ret)
|
||||
- goto err_disable_pm;
|
||||
+ ret = mtk_clk_enable(eth);
|
||||
+ if (ret)
|
||||
+ goto err_disable_pm;
|
||||
+ }
|
||||
|
||||
if (eth->ethsys)
|
||||
regmap_update_bits(eth->ethsys, ETHSYS_DMA_AG_MAP, dma_mask,
|
||||
@@ -3408,8 +3425,10 @@ static int mtk_hw_init(struct mtk_eth *e
|
||||
return 0;
|
||||
|
||||
err_disable_pm:
|
||||
- pm_runtime_put_sync(eth->dev);
|
||||
- pm_runtime_disable(eth->dev);
|
||||
+ if (!reset) {
|
||||
+ pm_runtime_put_sync(eth->dev);
|
||||
+ pm_runtime_disable(eth->dev);
|
||||
+ }
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -3488,30 +3507,53 @@ static int mtk_do_ioctl(struct net_devic
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
+static void mtk_prepare_for_reset(struct mtk_eth *eth)
|
||||
+{
|
||||
+ u32 val;
|
||||
+ int i;
|
||||
+
|
||||
+ /* disabe FE P3 and P4 */
|
||||
+ val = mtk_r32(eth, MTK_FE_GLO_CFG) | MTK_FE_LINK_DOWN_P3;
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
+ val |= MTK_FE_LINK_DOWN_P4;
|
||||
+ mtk_w32(eth, val, MTK_FE_GLO_CFG);
|
||||
+
|
||||
+ /* adjust PPE configurations to prepare for reset */
|
||||
+ for (i = 0; i < ARRAY_SIZE(eth->ppe); i++)
|
||||
+ mtk_ppe_prepare_reset(eth->ppe[i]);
|
||||
+
|
||||
+ /* disable NETSYS interrupts */
|
||||
+ mtk_w32(eth, 0, MTK_FE_INT_ENABLE);
|
||||
+
|
||||
+ /* force link down GMAC */
|
||||
+ for (i = 0; i < 2; i++) {
|
||||
+ val = mtk_r32(eth, MTK_MAC_MCR(i)) & ~MAC_MCR_FORCE_LINK;
|
||||
+ mtk_w32(eth, val, MTK_MAC_MCR(i));
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
static void mtk_pending_work(struct work_struct *work)
|
||||
{
|
||||
struct mtk_eth *eth = container_of(work, struct mtk_eth, pending_work);
|
||||
- int err, i;
|
||||
unsigned long restart = 0;
|
||||
+ u32 val;
|
||||
+ int i;
|
||||
|
||||
rtnl_lock();
|
||||
-
|
||||
- dev_dbg(eth->dev, "[%s][%d] reset\n", __func__, __LINE__);
|
||||
set_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
+ mtk_prepare_for_reset(eth);
|
||||
+
|
||||
/* stop all devices to make sure that dma is properly shut down */
|
||||
for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
- if (!eth->netdev[i])
|
||||
+ if (!eth->netdev[i] || !netif_running(eth->netdev[i]))
|
||||
continue;
|
||||
+
|
||||
mtk_stop(eth->netdev[i]);
|
||||
__set_bit(i, &restart);
|
||||
}
|
||||
- dev_dbg(eth->dev, "[%s][%d] mtk_stop ends\n", __func__, __LINE__);
|
||||
|
||||
- /* restart underlying hardware such as power, clock, pin mux
|
||||
- * and the connected phy
|
||||
- */
|
||||
- mtk_hw_deinit(eth);
|
||||
+ usleep_range(15000, 16000);
|
||||
|
||||
if (eth->dev->pins)
|
||||
pinctrl_select_state(eth->dev->pins->p,
|
||||
@@ -3522,15 +3564,19 @@ static void mtk_pending_work(struct work
|
||||
for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
if (!test_bit(i, &restart))
|
||||
continue;
|
||||
- err = mtk_open(eth->netdev[i]);
|
||||
- if (err) {
|
||||
+
|
||||
+ if (mtk_open(eth->netdev[i])) {
|
||||
netif_alert(eth, ifup, eth->netdev[i],
|
||||
- "Driver up/down cycle failed, closing device.\n");
|
||||
+ "Driver up/down cycle failed\n");
|
||||
dev_close(eth->netdev[i]);
|
||||
}
|
||||
}
|
||||
|
||||
- dev_dbg(eth->dev, "[%s][%d] reset done\n", __func__, __LINE__);
|
||||
+ /* enabe FE P3 and P4 */
|
||||
+ val = mtk_r32(eth, MTK_FE_GLO_CFG) & ~MTK_FE_LINK_DOWN_P3;
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_RSTCTRL_PPE1))
|
||||
+ val &= ~MTK_FE_LINK_DOWN_P4;
|
||||
+ mtk_w32(eth, val, MTK_FE_GLO_CFG);
|
||||
|
||||
clear_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
@@ -72,12 +72,24 @@
|
||||
#define MTK_HW_LRO_REPLACE_DELTA 1000
|
||||
#define MTK_HW_LRO_SDL_REMAIN_ROOM 1522
|
||||
|
||||
+/* Frame Engine Global Configuration */
|
||||
+#define MTK_FE_GLO_CFG 0x00
|
||||
+#define MTK_FE_LINK_DOWN_P3 BIT(11)
|
||||
+#define MTK_FE_LINK_DOWN_P4 BIT(12)
|
||||
+
|
||||
/* Frame Engine Global Reset Register */
|
||||
#define MTK_RST_GL 0x04
|
||||
#define RST_GL_PSE BIT(0)
|
||||
|
||||
/* Frame Engine Interrupt Status Register */
|
||||
#define MTK_INT_STATUS2 0x08
|
||||
+#define MTK_FE_INT_ENABLE 0x0c
|
||||
+#define MTK_FE_INT_FQ_EMPTY BIT(8)
|
||||
+#define MTK_FE_INT_TSO_FAIL BIT(12)
|
||||
+#define MTK_FE_INT_TSO_ILLEGAL BIT(13)
|
||||
+#define MTK_FE_INT_TSO_ALIGN BIT(14)
|
||||
+#define MTK_FE_INT_RFIFO_OV BIT(18)
|
||||
+#define MTK_FE_INT_RFIFO_UF BIT(19)
|
||||
#define MTK_GDM1_AF BIT(28)
|
||||
#define MTK_GDM2_AF BIT(29)
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_ppe.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_ppe.c
|
||||
@@ -716,6 +716,33 @@ int mtk_foe_entry_idle_time(struct mtk_p
|
||||
return __mtk_foe_entry_idle_time(ppe, entry->data.ib1);
|
||||
}
|
||||
|
||||
+int mtk_ppe_prepare_reset(struct mtk_ppe *ppe)
|
||||
+{
|
||||
+ if (!ppe)
|
||||
+ return -EINVAL;
|
||||
+
|
||||
+ /* disable KA */
|
||||
+ ppe_clear(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_KEEPALIVE);
|
||||
+ ppe_clear(ppe, MTK_PPE_BIND_LMT1, MTK_PPE_NTU_KEEPALIVE);
|
||||
+ ppe_w32(ppe, MTK_PPE_KEEPALIVE, 0);
|
||||
+ usleep_range(10000, 11000);
|
||||
+
|
||||
+ /* set KA timer to maximum */
|
||||
+ ppe_set(ppe, MTK_PPE_BIND_LMT1, MTK_PPE_NTU_KEEPALIVE);
|
||||
+ ppe_w32(ppe, MTK_PPE_KEEPALIVE, 0xffffffff);
|
||||
+
|
||||
+ /* set KA tick select */
|
||||
+ ppe_set(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_TICK_SEL);
|
||||
+ ppe_set(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_KEEPALIVE);
|
||||
+ usleep_range(10000, 11000);
|
||||
+
|
||||
+ /* disable scan mode */
|
||||
+ ppe_clear(ppe, MTK_PPE_TB_CFG, MTK_PPE_TB_CFG_SCAN_MODE);
|
||||
+ usleep_range(10000, 11000);
|
||||
+
|
||||
+ return mtk_ppe_wait_busy(ppe);
|
||||
+}
|
||||
+
|
||||
struct mtk_ppe *mtk_ppe_init(struct mtk_eth *eth, void __iomem *base,
|
||||
int version, int index)
|
||||
{
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_ppe.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_ppe.h
|
||||
@@ -306,6 +306,7 @@ struct mtk_ppe *mtk_ppe_init(struct mtk_
|
||||
int version, int index);
|
||||
void mtk_ppe_start(struct mtk_ppe *ppe);
|
||||
int mtk_ppe_stop(struct mtk_ppe *ppe);
|
||||
+int mtk_ppe_prepare_reset(struct mtk_ppe *ppe);
|
||||
|
||||
void __mtk_ppe_check_skb(struct mtk_ppe *ppe, struct sk_buff *skb, u16 hash);
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_ppe_regs.h
|
||||
@@ -58,6 +58,12 @@
|
||||
#define MTK_PPE_TB_CFG_SCAN_MODE GENMASK(17, 16)
|
||||
#define MTK_PPE_TB_CFG_HASH_DEBUG GENMASK(19, 18)
|
||||
#define MTK_PPE_TB_CFG_INFO_SEL BIT(20)
|
||||
+#define MTK_PPE_TB_TICK_SEL BIT(24)
|
||||
+
|
||||
+#define MTK_PPE_BIND_LMT1 0x230
|
||||
+#define MTK_PPE_NTU_KEEPALIVE GENMASK(23, 16)
|
||||
+
|
||||
+#define MTK_PPE_KEEPALIVE 0x234
|
||||
|
||||
enum {
|
||||
MTK_PPE_SCAN_MODE_DISABLED,
|
||||
@ -0,0 +1,249 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Sat, 14 Jan 2023 18:01:31 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_eth_soc: add dma checks to
|
||||
mtk_hw_reset_check
|
||||
|
||||
Introduce mtk_hw_check_dma_hang routine to monitor possible dma hangs.
|
||||
|
||||
Reviewed-by: Leon Romanovsky <leonro@nvidia.com>
|
||||
Tested-by: Daniel Golle <daniel@makrotopia.org>
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -50,6 +50,7 @@ static const struct mtk_reg_map mtk_reg_
|
||||
.delay_irq = 0x0a0c,
|
||||
.irq_status = 0x0a20,
|
||||
.irq_mask = 0x0a28,
|
||||
+ .adma_rx_dbg0 = 0x0a38,
|
||||
.int_grp = 0x0a50,
|
||||
},
|
||||
.qdma = {
|
||||
@@ -79,6 +80,8 @@ static const struct mtk_reg_map mtk_reg_
|
||||
[0] = 0x2800,
|
||||
[1] = 0x2c00,
|
||||
},
|
||||
+ .pse_iq_sta = 0x0110,
|
||||
+ .pse_oq_sta = 0x0118,
|
||||
};
|
||||
|
||||
static const struct mtk_reg_map mt7628_reg_map = {
|
||||
@@ -109,6 +112,7 @@ static const struct mtk_reg_map mt7986_r
|
||||
.delay_irq = 0x620c,
|
||||
.irq_status = 0x6220,
|
||||
.irq_mask = 0x6228,
|
||||
+ .adma_rx_dbg0 = 0x6238,
|
||||
.int_grp = 0x6250,
|
||||
},
|
||||
.qdma = {
|
||||
@@ -138,6 +142,8 @@ static const struct mtk_reg_map mt7986_r
|
||||
[0] = 0x4800,
|
||||
[1] = 0x4c00,
|
||||
},
|
||||
+ .pse_iq_sta = 0x0180,
|
||||
+ .pse_oq_sta = 0x01a0,
|
||||
};
|
||||
|
||||
/* strings used by ethtool */
|
||||
@@ -3282,6 +3288,102 @@ static void mtk_hw_warm_reset(struct mtk
|
||||
val, rst_mask);
|
||||
}
|
||||
|
||||
+static bool mtk_hw_check_dma_hang(struct mtk_eth *eth)
|
||||
+{
|
||||
+ const struct mtk_reg_map *reg_map = eth->soc->reg_map;
|
||||
+ bool gmac1_tx, gmac2_tx, gdm1_tx, gdm2_tx;
|
||||
+ bool oq_hang, cdm1_busy, adma_busy;
|
||||
+ bool wtx_busy, cdm_full, oq_free;
|
||||
+ u32 wdidx, val, gdm1_fc, gdm2_fc;
|
||||
+ bool qfsm_hang, qfwd_hang;
|
||||
+ bool ret = false;
|
||||
+
|
||||
+ if (MTK_HAS_CAPS(eth->soc->caps, MTK_SOC_MT7628))
|
||||
+ return false;
|
||||
+
|
||||
+ /* WDMA sanity checks */
|
||||
+ wdidx = mtk_r32(eth, reg_map->wdma_base[0] + 0xc);
|
||||
+
|
||||
+ val = mtk_r32(eth, reg_map->wdma_base[0] + 0x204);
|
||||
+ wtx_busy = FIELD_GET(MTK_TX_DMA_BUSY, val);
|
||||
+
|
||||
+ val = mtk_r32(eth, reg_map->wdma_base[0] + 0x230);
|
||||
+ cdm_full = !FIELD_GET(MTK_CDM_TXFIFO_RDY, val);
|
||||
+
|
||||
+ oq_free = (!(mtk_r32(eth, reg_map->pse_oq_sta) & GENMASK(24, 16)) &&
|
||||
+ !(mtk_r32(eth, reg_map->pse_oq_sta + 0x4) & GENMASK(8, 0)) &&
|
||||
+ !(mtk_r32(eth, reg_map->pse_oq_sta + 0x10) & GENMASK(24, 16)));
|
||||
+
|
||||
+ if (wdidx == eth->reset.wdidx && wtx_busy && cdm_full && oq_free) {
|
||||
+ if (++eth->reset.wdma_hang_count > 2) {
|
||||
+ eth->reset.wdma_hang_count = 0;
|
||||
+ ret = true;
|
||||
+ }
|
||||
+ goto out;
|
||||
+ }
|
||||
+
|
||||
+ /* QDMA sanity checks */
|
||||
+ qfsm_hang = !!mtk_r32(eth, reg_map->qdma.qtx_cfg + 0x234);
|
||||
+ qfwd_hang = !mtk_r32(eth, reg_map->qdma.qtx_cfg + 0x308);
|
||||
+
|
||||
+ gdm1_tx = FIELD_GET(GENMASK(31, 16), mtk_r32(eth, MTK_FE_GDM1_FSM)) > 0;
|
||||
+ gdm2_tx = FIELD_GET(GENMASK(31, 16), mtk_r32(eth, MTK_FE_GDM2_FSM)) > 0;
|
||||
+ gmac1_tx = FIELD_GET(GENMASK(31, 24), mtk_r32(eth, MTK_MAC_FSM(0))) != 1;
|
||||
+ gmac2_tx = FIELD_GET(GENMASK(31, 24), mtk_r32(eth, MTK_MAC_FSM(1))) != 1;
|
||||
+ gdm1_fc = mtk_r32(eth, reg_map->gdm1_cnt + 0x24);
|
||||
+ gdm2_fc = mtk_r32(eth, reg_map->gdm1_cnt + 0x64);
|
||||
+
|
||||
+ if (qfsm_hang && qfwd_hang &&
|
||||
+ ((gdm1_tx && gmac1_tx && gdm1_fc < 1) ||
|
||||
+ (gdm2_tx && gmac2_tx && gdm2_fc < 1))) {
|
||||
+ if (++eth->reset.qdma_hang_count > 2) {
|
||||
+ eth->reset.qdma_hang_count = 0;
|
||||
+ ret = true;
|
||||
+ }
|
||||
+ goto out;
|
||||
+ }
|
||||
+
|
||||
+ /* ADMA sanity checks */
|
||||
+ oq_hang = !!(mtk_r32(eth, reg_map->pse_oq_sta) & GENMASK(8, 0));
|
||||
+ cdm1_busy = !!(mtk_r32(eth, MTK_FE_CDM1_FSM) & GENMASK(31, 16));
|
||||
+ adma_busy = !(mtk_r32(eth, reg_map->pdma.adma_rx_dbg0) & GENMASK(4, 0)) &&
|
||||
+ !(mtk_r32(eth, reg_map->pdma.adma_rx_dbg0) & BIT(6));
|
||||
+
|
||||
+ if (oq_hang && cdm1_busy && adma_busy) {
|
||||
+ if (++eth->reset.adma_hang_count > 2) {
|
||||
+ eth->reset.adma_hang_count = 0;
|
||||
+ ret = true;
|
||||
+ }
|
||||
+ goto out;
|
||||
+ }
|
||||
+
|
||||
+ eth->reset.wdma_hang_count = 0;
|
||||
+ eth->reset.qdma_hang_count = 0;
|
||||
+ eth->reset.adma_hang_count = 0;
|
||||
+out:
|
||||
+ eth->reset.wdidx = wdidx;
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
+static void mtk_hw_reset_monitor_work(struct work_struct *work)
|
||||
+{
|
||||
+ struct delayed_work *del_work = to_delayed_work(work);
|
||||
+ struct mtk_eth *eth = container_of(del_work, struct mtk_eth,
|
||||
+ reset.monitor_work);
|
||||
+
|
||||
+ if (test_bit(MTK_RESETTING, ð->state))
|
||||
+ goto out;
|
||||
+
|
||||
+ /* DMA stuck checks */
|
||||
+ if (mtk_hw_check_dma_hang(eth))
|
||||
+ schedule_work(ð->pending_work);
|
||||
+
|
||||
+out:
|
||||
+ schedule_delayed_work(ð->reset.monitor_work,
|
||||
+ MTK_DMA_MONITOR_TIMEOUT);
|
||||
+}
|
||||
+
|
||||
static int mtk_hw_init(struct mtk_eth *eth, bool reset)
|
||||
{
|
||||
u32 dma_mask = ETHSYS_DMA_AG_MAP_PDMA | ETHSYS_DMA_AG_MAP_QDMA |
|
||||
@@ -3614,6 +3716,7 @@ static int mtk_cleanup(struct mtk_eth *e
|
||||
mtk_unreg_dev(eth);
|
||||
mtk_free_dev(eth);
|
||||
cancel_work_sync(ð->pending_work);
|
||||
+ cancel_delayed_work_sync(ð->reset.monitor_work);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -4041,6 +4144,7 @@ static int mtk_probe(struct platform_dev
|
||||
|
||||
eth->rx_dim.mode = DIM_CQ_PERIOD_MODE_START_FROM_EQE;
|
||||
INIT_WORK(ð->rx_dim.work, mtk_dim_rx);
|
||||
+ INIT_DELAYED_WORK(ð->reset.monitor_work, mtk_hw_reset_monitor_work);
|
||||
|
||||
eth->tx_dim.mode = DIM_CQ_PERIOD_MODE_START_FROM_EQE;
|
||||
INIT_WORK(ð->tx_dim.work, mtk_dim_tx);
|
||||
@@ -4245,6 +4349,8 @@ static int mtk_probe(struct platform_dev
|
||||
NAPI_POLL_WEIGHT);
|
||||
|
||||
platform_set_drvdata(pdev, eth);
|
||||
+ schedule_delayed_work(ð->reset.monitor_work,
|
||||
+ MTK_DMA_MONITOR_TIMEOUT);
|
||||
|
||||
return 0;
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h
|
||||
@@ -256,6 +256,8 @@
|
||||
|
||||
#define MTK_RX_DONE_INT_V2 BIT(14)
|
||||
|
||||
+#define MTK_CDM_TXFIFO_RDY BIT(7)
|
||||
+
|
||||
/* QDMA Interrupt grouping registers */
|
||||
#define MTK_RLS_DONE_INT BIT(0)
|
||||
|
||||
@@ -537,6 +539,17 @@
|
||||
#define MT7628_SDM_RBCNT (MT7628_SDM_OFFSET + 0x10c)
|
||||
#define MT7628_SDM_CS_ERR (MT7628_SDM_OFFSET + 0x110)
|
||||
|
||||
+#define MTK_FE_CDM1_FSM 0x220
|
||||
+#define MTK_FE_CDM2_FSM 0x224
|
||||
+#define MTK_FE_CDM3_FSM 0x238
|
||||
+#define MTK_FE_CDM4_FSM 0x298
|
||||
+#define MTK_FE_CDM5_FSM 0x318
|
||||
+#define MTK_FE_CDM6_FSM 0x328
|
||||
+#define MTK_FE_GDM1_FSM 0x228
|
||||
+#define MTK_FE_GDM2_FSM 0x22C
|
||||
+
|
||||
+#define MTK_MAC_FSM(x) (0x1010C + ((x) * 0x100))
|
||||
+
|
||||
struct mtk_rx_dma {
|
||||
unsigned int rxd1;
|
||||
unsigned int rxd2;
|
||||
@@ -933,6 +946,7 @@ struct mtk_reg_map {
|
||||
u32 delay_irq; /* delay interrupt */
|
||||
u32 irq_status; /* interrupt status */
|
||||
u32 irq_mask; /* interrupt mask */
|
||||
+ u32 adma_rx_dbg0;
|
||||
u32 int_grp;
|
||||
} pdma;
|
||||
struct {
|
||||
@@ -959,6 +973,8 @@ struct mtk_reg_map {
|
||||
u32 gdma_to_ppe0;
|
||||
u32 ppe_base;
|
||||
u32 wdma_base[2];
|
||||
+ u32 pse_iq_sta;
|
||||
+ u32 pse_oq_sta;
|
||||
};
|
||||
|
||||
/* struct mtk_eth_data - This is the structure holding all differences
|
||||
@@ -1001,6 +1017,8 @@ struct mtk_soc_data {
|
||||
} txrx;
|
||||
};
|
||||
|
||||
+#define MTK_DMA_MONITOR_TIMEOUT msecs_to_jiffies(1000)
|
||||
+
|
||||
/* currently no SoC has more than 2 macs */
|
||||
#define MTK_MAX_DEVS 2
|
||||
|
||||
@@ -1123,6 +1141,14 @@ struct mtk_eth {
|
||||
struct rhashtable flow_table;
|
||||
|
||||
struct bpf_prog __rcu *prog;
|
||||
+
|
||||
+ struct {
|
||||
+ struct delayed_work monitor_work;
|
||||
+ u32 wdidx;
|
||||
+ u8 wdma_hang_count;
|
||||
+ u8 qdma_hang_count;
|
||||
+ u8 adma_hang_count;
|
||||
+ } reset;
|
||||
};
|
||||
|
||||
/* struct mtk_mac - the structure that holds the info about the MACs of the
|
||||
@ -0,0 +1,124 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Sat, 14 Jan 2023 18:01:32 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: add reset/reset_complete callbacks
|
||||
|
||||
Introduce reset and reset_complete wlan callback to schedule WLAN driver
|
||||
reset when ethernet/wed driver is resetting.
|
||||
|
||||
Tested-by: Daniel Golle <daniel@makrotopia.org>
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Signed-off-by: Paolo Abeni <pabeni@redhat.com>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c
|
||||
@@ -3645,6 +3645,11 @@ static void mtk_pending_work(struct work
|
||||
set_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
mtk_prepare_for_reset(eth);
|
||||
+ mtk_wed_fe_reset();
|
||||
+ /* Run again reset preliminary configuration in order to avoid any
|
||||
+ * possible race during FE reset since it can run releasing RTNL lock.
|
||||
+ */
|
||||
+ mtk_prepare_for_reset(eth);
|
||||
|
||||
/* stop all devices to make sure that dma is properly shut down */
|
||||
for (i = 0; i < MTK_MAC_COUNT; i++) {
|
||||
@@ -3682,6 +3687,8 @@ static void mtk_pending_work(struct work
|
||||
|
||||
clear_bit(MTK_RESETTING, ð->state);
|
||||
|
||||
+ mtk_wed_fe_reset_complete();
|
||||
+
|
||||
rtnl_unlock();
|
||||
}
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -205,6 +205,48 @@ mtk_wed_wo_reset(struct mtk_wed_device *
|
||||
iounmap(reg);
|
||||
}
|
||||
|
||||
+void mtk_wed_fe_reset(void)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ mutex_lock(&hw_lock);
|
||||
+
|
||||
+ for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
|
||||
+ struct mtk_wed_hw *hw = hw_list[i];
|
||||
+ struct mtk_wed_device *dev = hw->wed_dev;
|
||||
+ int err;
|
||||
+
|
||||
+ if (!dev || !dev->wlan.reset)
|
||||
+ continue;
|
||||
+
|
||||
+ /* reset callback blocks until WLAN reset is completed */
|
||||
+ err = dev->wlan.reset(dev);
|
||||
+ if (err)
|
||||
+ dev_err(dev->dev, "wlan reset failed: %d\n", err);
|
||||
+ }
|
||||
+
|
||||
+ mutex_unlock(&hw_lock);
|
||||
+}
|
||||
+
|
||||
+void mtk_wed_fe_reset_complete(void)
|
||||
+{
|
||||
+ int i;
|
||||
+
|
||||
+ mutex_lock(&hw_lock);
|
||||
+
|
||||
+ for (i = 0; i < ARRAY_SIZE(hw_list); i++) {
|
||||
+ struct mtk_wed_hw *hw = hw_list[i];
|
||||
+ struct mtk_wed_device *dev = hw->wed_dev;
|
||||
+
|
||||
+ if (!dev || !dev->wlan.reset_complete)
|
||||
+ continue;
|
||||
+
|
||||
+ dev->wlan.reset_complete(dev);
|
||||
+ }
|
||||
+
|
||||
+ mutex_unlock(&hw_lock);
|
||||
+}
|
||||
+
|
||||
static struct mtk_wed_hw *
|
||||
mtk_wed_assign(struct mtk_wed_device *dev)
|
||||
{
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.h
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.h
|
||||
@@ -128,6 +128,8 @@ void mtk_wed_add_hw(struct device_node *
|
||||
void mtk_wed_exit(void);
|
||||
int mtk_wed_flow_add(int index);
|
||||
void mtk_wed_flow_remove(int index);
|
||||
+void mtk_wed_fe_reset(void);
|
||||
+void mtk_wed_fe_reset_complete(void);
|
||||
#else
|
||||
static inline void
|
||||
mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth,
|
||||
@@ -147,6 +149,13 @@ static inline void mtk_wed_flow_remove(i
|
||||
{
|
||||
}
|
||||
|
||||
+static inline void mtk_wed_fe_reset(void)
|
||||
+{
|
||||
+}
|
||||
+
|
||||
+static inline void mtk_wed_fe_reset_complete(void)
|
||||
+{
|
||||
+}
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_DEBUG_FS
|
||||
--- a/include/linux/soc/mediatek/mtk_wed.h
|
||||
+++ b/include/linux/soc/mediatek/mtk_wed.h
|
||||
@@ -151,6 +151,8 @@ struct mtk_wed_device {
|
||||
void (*release_rx_buf)(struct mtk_wed_device *wed);
|
||||
void (*update_wo_rx_stats)(struct mtk_wed_device *wed,
|
||||
struct mtk_wed_wo_rx_stats *stats);
|
||||
+ int (*reset)(struct mtk_wed_device *wed);
|
||||
+ void (*reset_complete)(struct mtk_wed_device *wed);
|
||||
} wlan;
|
||||
#endif
|
||||
};
|
||||
@ -0,0 +1,106 @@
|
||||
From: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Date: Mon, 5 Dec 2022 12:34:42 +0100
|
||||
Subject: [PATCH] net: ethernet: mtk_wed: add reset to rx_ring_setup callback
|
||||
|
||||
This patch adds reset parameter to mtk_wed_rx_ring_setup signature
|
||||
in order to align rx_ring_setup callback to tx_ring_setup one introduced
|
||||
in 'commit 23dca7a90017 ("net: ethernet: mtk_wed: add reset to
|
||||
tx_ring_setup callback")'
|
||||
|
||||
Co-developed-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Sujuan Chen <sujuan.chen@mediatek.com>
|
||||
Signed-off-by: Lorenzo Bianconi <lorenzo@kernel.org>
|
||||
Reviewed-by: Leon Romanovsky <leonro@nvidia.com>
|
||||
Link: https://lore.kernel.org/r/29c6e7a5469e784406cf3e2920351d1207713d05.1670239984.git.lorenzo@kernel.org
|
||||
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
|
||||
---
|
||||
|
||||
--- a/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
+++ b/drivers/net/ethernet/mediatek/mtk_wed.c
|
||||
@@ -1259,7 +1259,8 @@ mtk_wed_wdma_rx_ring_setup(struct mtk_we
|
||||
}
|
||||
|
||||
static int
|
||||
-mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size)
|
||||
+mtk_wed_wdma_tx_ring_setup(struct mtk_wed_device *dev, int idx, int size,
|
||||
+ bool reset)
|
||||
{
|
||||
u32 desc_size = sizeof(struct mtk_wdma_desc) * dev->hw->version;
|
||||
struct mtk_wed_ring *wdma;
|
||||
@@ -1268,8 +1269,8 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
|
||||
return -EINVAL;
|
||||
|
||||
wdma = &dev->tx_wdma[idx];
|
||||
- if (mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE, desc_size,
|
||||
- true))
|
||||
+ if (!reset && mtk_wed_ring_alloc(dev, wdma, MTK_WED_WDMA_RING_SIZE,
|
||||
+ desc_size, true))
|
||||
return -ENOMEM;
|
||||
|
||||
wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_BASE,
|
||||
@@ -1279,6 +1280,9 @@ mtk_wed_wdma_tx_ring_setup(struct mtk_we
|
||||
wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_CPU_IDX, 0);
|
||||
wdma_w32(dev, MTK_WDMA_RING_TX(idx) + MTK_WED_RING_OFS_DMA_IDX, 0);
|
||||
|
||||
+ if (reset)
|
||||
+ mtk_wed_ring_reset(wdma, MTK_WED_WDMA_RING_SIZE, true);
|
||||
+
|
||||
if (!idx) {
|
||||
wed_w32(dev, MTK_WED_WDMA_RING_TX + MTK_WED_RING_OFS_BASE,
|
||||
wdma->desc_phys);
|
||||
@@ -1618,18 +1622,20 @@ mtk_wed_txfree_ring_setup(struct mtk_wed
|
||||
}
|
||||
|
||||
static int
|
||||
-mtk_wed_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs)
|
||||
+mtk_wed_rx_ring_setup(struct mtk_wed_device *dev, int idx, void __iomem *regs,
|
||||
+ bool reset)
|
||||
{
|
||||
struct mtk_wed_ring *ring = &dev->rx_ring[idx];
|
||||
|
||||
if (WARN_ON(idx >= ARRAY_SIZE(dev->rx_ring)))
|
||||
return -EINVAL;
|
||||
|
||||
- if (mtk_wed_ring_alloc(dev, ring, MTK_WED_RX_RING_SIZE,
|
||||
- sizeof(*ring->desc), false))
|
||||
+ if (!reset && mtk_wed_ring_alloc(dev, ring, MTK_WED_RX_RING_SIZE,
|
||||
+ sizeof(*ring->desc), false))
|
||||
return -ENOMEM;
|
||||
|
||||
- if (mtk_wed_wdma_tx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE))
|
||||
+ if (mtk_wed_wdma_tx_ring_setup(dev, idx, MTK_WED_WDMA_RING_SIZE,
|
||||
+ reset))
|
||||
return -ENOMEM;
|
||||
|
||||
ring->reg_base = MTK_WED_RING_RX_DATA(idx);
|
||||
--- a/include/linux/soc/mediatek/mtk_wed.h
|
||||
+++ b/include/linux/soc/mediatek/mtk_wed.h
|
||||
@@ -162,7 +162,7 @@ struct mtk_wed_ops {
|
||||
int (*tx_ring_setup)(struct mtk_wed_device *dev, int ring,
|
||||
void __iomem *regs, bool reset);
|
||||
int (*rx_ring_setup)(struct mtk_wed_device *dev, int ring,
|
||||
- void __iomem *regs);
|
||||
+ void __iomem *regs, bool reset);
|
||||
int (*txfree_ring_setup)(struct mtk_wed_device *dev,
|
||||
void __iomem *regs);
|
||||
int (*msg_update)(struct mtk_wed_device *dev, int cmd_id,
|
||||
@@ -230,8 +230,8 @@ mtk_wed_get_rx_capa(struct mtk_wed_devic
|
||||
(_dev)->ops->irq_get(_dev, _mask)
|
||||
#define mtk_wed_device_irq_set_mask(_dev, _mask) \
|
||||
(_dev)->ops->irq_set_mask(_dev, _mask)
|
||||
-#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) \
|
||||
- (_dev)->ops->rx_ring_setup(_dev, _ring, _regs)
|
||||
+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs, _reset) \
|
||||
+ (_dev)->ops->rx_ring_setup(_dev, _ring, _regs, _reset)
|
||||
#define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash) \
|
||||
(_dev)->ops->ppe_check(_dev, _skb, _reason, _hash)
|
||||
#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) \
|
||||
@@ -251,7 +251,7 @@ static inline bool mtk_wed_device_active
|
||||
#define mtk_wed_device_reg_write(_dev, _reg, _val) do {} while (0)
|
||||
#define mtk_wed_device_irq_get(_dev, _mask) 0
|
||||
#define mtk_wed_device_irq_set_mask(_dev, _mask) do {} while (0)
|
||||
-#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs) -ENODEV
|
||||
+#define mtk_wed_device_rx_ring_setup(_dev, _ring, _regs, _reset) -ENODEV
|
||||
#define mtk_wed_device_ppe_check(_dev, _skb, _reason, _hash) do {} while (0)
|
||||
#define mtk_wed_device_update_msg(_dev, _id, _msg, _len) -ENODEV
|
||||
#define mtk_wed_device_stop(_dev) do {} while (0)
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user