diff --git a/package/boot/uboot-envtools/files/ramips b/package/boot/uboot-envtools/files/ramips index cca394a03b01bd..97e9fc2b1c0f75 100644 --- a/package/boot/uboot-envtools/files/ramips +++ b/package/boot/uboot-envtools/files/ramips @@ -146,6 +146,10 @@ xiaomi,mi-router-cr6608|\ xiaomi,mi-router-cr6609) ubootenv_add_uci_config "/dev/mtd1" "0x0" "0x10000" "0x20000" ;; +dna,valokuitu-plus-ex400) + ubootenv_add_uci_config "/dev/ubi0_0" "0x0" "0x1f000" "0x1f000" "1" + ubootenv_add_uci_config "/dev/ubi0_1" "0x0" "0x1f000" "0x1f000" "1" + ;; netgear,wax214v2) ubootenv_add_uci_config "/dev/mtd1" "0x0" "0x20000" "0x20000" ubootenv_add_uci_sys_config "/dev/mtd1" "0x20000" "0x8000" "0x20000" diff --git a/target/linux/omap/Makefile b/target/linux/omap/Makefile index a3c61efc9ab254..67db2aa07d639e 100644 --- a/target/linux/omap/Makefile +++ b/target/linux/omap/Makefile @@ -12,7 +12,7 @@ CPU_TYPE:=cortex-a8 CPU_SUBTYPE:=vfpv3 SUBTARGETS:=generic -KERNEL_PATCHVER:=6.1 +KERNEL_PATCHVER:=6.6 KERNELNAME:=zImage dtbs diff --git a/target/linux/omap/config-6.1 b/target/linux/omap/config-6.6 similarity index 96% rename from target/linux/omap/config-6.1 rename to target/linux/omap/config-6.6 index 94c6b5922d47dc..f85a68f0aad886 100644 --- a/target/linux/omap/config-6.1 +++ b/target/linux/omap/config-6.6 @@ -10,7 +10,6 @@ CONFIG_ARCH_MULTIPLATFORM=y CONFIG_ARCH_MULTI_V6_V7=y CONFIG_ARCH_MULTI_V7=y CONFIG_ARCH_NEEDS_CPU_IDLE_COUPLED=y -CONFIG_ARCH_NR_GPIO=0 CONFIG_ARCH_OMAP=y CONFIG_ARCH_OMAP2PLUS=y CONFIG_ARCH_OMAP2PLUS_TYPICAL=y @@ -20,6 +19,7 @@ CONFIG_ARCH_OPTIONAL_KERNEL_RWX=y CONFIG_ARCH_OPTIONAL_KERNEL_RWX_DEFAULT=y CONFIG_ARCH_SELECT_MEMORY_MODEL=y CONFIG_ARCH_SPARSEMEM_ENABLE=y +CONFIG_ARCH_STACKWALK=y CONFIG_ARCH_SUSPEND_POSSIBLE=y CONFIG_ARM=y CONFIG_ARM_APPENDED_DTB=y @@ -63,6 +63,7 @@ CONFIG_BLK_DEV_SD=y CONFIG_BLK_PM=y CONFIG_BOUNCE=y CONFIG_BSD_PROCESS_ACCT=y +CONFIG_BUFFER_HEAD=y CONFIG_CACHE_L2X0=y CONFIG_CC_HAVE_STACKPROTECTOR_TLS=y CONFIG_CC_IMPLICIT_FALLTHROUGH="-Wimplicit-fallthrough=5" @@ -123,6 +124,7 @@ CONFIG_CPU_IDLE_GOV_LADDER=y CONFIG_CPU_IDLE_GOV_MENU=y CONFIG_CPU_IDLE_MULTIPLE_DRIVERS=y CONFIG_CPU_LITTLE_ENDIAN=y +CONFIG_CPU_MITIGATIONS=y CONFIG_CPU_PABRT_V7=y CONFIG_CPU_PM=y CONFIG_CPU_RMAP=y @@ -157,6 +159,7 @@ CONFIG_CRYPTO_DRBG_HMAC=y CONFIG_CRYPTO_DRBG_MENU=y CONFIG_CRYPTO_ECB=y CONFIG_CRYPTO_ENGINE=y +CONFIG_CRYPTO_GENIV=y CONFIG_CRYPTO_GHASH_ARM_CE=y CONFIG_CRYPTO_HASH_INFO=y CONFIG_CRYPTO_HMAC=y @@ -164,10 +167,13 @@ CONFIG_CRYPTO_HW=y CONFIG_CRYPTO_JITTERENTROPY=y CONFIG_CRYPTO_LIB_BLAKE2S_GENERIC=y CONFIG_CRYPTO_LIB_DES=y +CONFIG_CRYPTO_LIB_GF128MUL=y CONFIG_CRYPTO_LIB_SHA1=y CONFIG_CRYPTO_LIB_SHA256=y CONFIG_CRYPTO_LIB_UTILS=y CONFIG_CRYPTO_LZO=y +# CONFIG_CRYPTO_MANAGER_DISABLE_TESTS is not set +# CONFIG_CRYPTO_MANAGER_EXTRA_TESTS is not set CONFIG_CRYPTO_MD5=y CONFIG_CRYPTO_RNG=y CONFIG_CRYPTO_RNG2=y @@ -178,8 +184,10 @@ CONFIG_CRYPTO_SHA1_ARM=y CONFIG_CRYPTO_SHA1_ARM_NEON=y CONFIG_CRYPTO_SHA256=y CONFIG_CRYPTO_SHA256_ARM=y +CONFIG_CRYPTO_SHA3=y CONFIG_CRYPTO_SHA512=y CONFIG_CRYPTO_SHA512_ARM=y +CONFIG_CRYPTO_SIG2=y CONFIG_CRYPTO_SIMD=y CONFIG_CRYPTO_ZSTD=y CONFIG_CURRENT_POINTER_IN_TPIDRURO=y @@ -201,7 +209,6 @@ CONFIG_DRM_BRIDGE=y CONFIG_DRM_DISPLAY_CONNECTOR=y CONFIG_DRM_KMS_HELPER=y CONFIG_DRM_MIPI_DSI=y -CONFIG_DRM_NOMODESET=y CONFIG_DRM_OMAP=y CONFIG_DRM_PANEL=y CONFIG_DRM_PANEL_BRIDGE=y @@ -228,16 +235,16 @@ CONFIG_EXTCON_USB_GPIO=y CONFIG_F2FS_FS=y CONFIG_FANOTIFY=y CONFIG_FAT_FS=y -CONFIG_FB_CMDLINE=y CONFIG_FHANDLE=y CONFIG_FIXED_PHY=y CONFIG_FIX_EARLYCON_MEM=y CONFIG_FS_IOMAP=y CONFIG_FS_MBCACHE=y +CONFIG_FUNCTION_ALIGNMENT=0 CONFIG_FWNODE_MDIO=y CONFIG_FW_LOADER_PAGED_BUF=y CONFIG_FW_LOADER_SYSFS=y -CONFIG_GCC11_NO_ARRAY_BOUNDS=y +CONFIG_GCC10_NO_ARRAY_BOUNDS=y CONFIG_GENERIC_ALLOCATOR=y CONFIG_GENERIC_ARCH_TOPOLOGY=y CONFIG_GENERIC_BUG=y @@ -283,6 +290,7 @@ CONFIG_HARDEN_BRANCH_PREDICTOR=y CONFIG_HARDIRQS_SW_RESEND=y CONFIG_HAS_DMA=y CONFIG_HAS_IOMEM=y +CONFIG_HAS_IOPORT=y CONFIG_HAS_IOPORT_MAP=y CONFIG_HAVE_SMP=y CONFIG_HDMI=y @@ -330,8 +338,8 @@ CONFIG_LEDS_GPIO=y CONFIG_LEDS_PWM=y CONFIG_LEDS_TRIGGER_BACKLIGHT=y CONFIG_LEDS_TRIGGER_CPU=y -CONFIG_LEDS_TRIGGER_GPIO=y CONFIG_LEDS_TRIGGER_ONESHOT=y +CONFIG_LEGACY_DIRECT_IO=y CONFIG_LIBCRC32C=y CONFIG_LIBFDT=y CONFIG_LOCKD=y @@ -346,7 +354,6 @@ CONFIG_MDIO_BUS=y CONFIG_MDIO_DEVICE=y CONFIG_MDIO_DEVRES=y # CONFIG_MDIO_GPIO is not set -CONFIG_MEMFD_CREATE=y CONFIG_MEMORY=y CONFIG_MEMORY_ISOLATION=y CONFIG_MFD_CORE=y @@ -368,6 +375,7 @@ CONFIG_MMC_SDHCI=y CONFIG_MMC_SDHCI_EXTERNAL_DMA=y CONFIG_MMC_SDHCI_OMAP=y CONFIG_MMC_SDHCI_PLTFM=y +CONFIG_MMU_LAZY_TLB_REFCOUNT=y CONFIG_MODULES_USE_ELF_REL=y CONFIG_MSDOS_FS=y CONFIG_MTD_CMDLINE_PARTS=y @@ -394,14 +402,19 @@ CONFIG_MTD_UBI_WL_THRESHOLD=4096 # CONFIG_MUSB_PIO_ONLY is not set CONFIG_MUTEX_SPIN_ON_OWNER=y CONFIG_NEED_DMA_MAP_STATE=y +CONFIG_NEED_SRCU_NMI_SAFE=y CONFIG_NEON=y CONFIG_NET_DEVLINK=y +CONFIG_NET_EGRESS=y CONFIG_NET_FLOW_LIMIT=y +CONFIG_NET_HANDSHAKE=y +CONFIG_NET_INGRESS=y CONFIG_NET_KEY=y CONFIG_NET_KEY_MIGRATE=y CONFIG_NET_PTP_CLASSIFY=y CONFIG_NET_SELFTESTS=y CONFIG_NET_SWITCHDEV=y +CONFIG_NET_XGRESS=y CONFIG_NFS_ACL_SUPPORT=y CONFIG_NFS_FS=y CONFIG_NFS_USE_KERNEL_DNS=y @@ -437,7 +450,6 @@ CONFIG_OMAP2_DSS_SDI=y CONFIG_OMAP2_DSS_SLEEP_AFTER_VENC_RESET=y CONFIG_OMAP2_DSS_VENC=y # CONFIG_OMAP3_L2_AUX_SECURE_SAVE_RESTORE is not set -# CONFIG_OMAP3_SDRC_AC_TIMING is not set CONFIG_OMAP3_THERMAL=y CONFIG_OMAP4_DSS_HDMI=y CONFIG_OMAP4_DSS_HDMI_CEC=y @@ -488,7 +500,6 @@ CONFIG_POWER_SUPPLY=y CONFIG_PPS=y CONFIG_PREEMPT_NONE_BUILD=y CONFIG_PRINTK_TIME=y -CONFIG_PRINT_QUOTA_WARNING=y CONFIG_PROC_EVENTS=y CONFIG_PROFILING=y CONFIG_PTP_1588_CLOCK=y @@ -618,12 +629,11 @@ CONFIG_SPI_MASTER=y CONFIG_SPI_MEM=y CONFIG_SPI_OMAP24XX=y CONFIG_SPI_TI_QSPI=y +CONFIG_SQUASHFS_DECOMP_MULTI_PERCPU=y CONFIG_SRAM=y CONFIG_SRAM_EXEC=y -CONFIG_SRCU=y CONFIG_STACKTRACE=y CONFIG_SUNRPC=y -CONFIG_SUNRPC_GSS=y CONFIG_SWPHY=y CONFIG_SWP_EMULATE=y CONFIG_SYNC_FILE=y @@ -677,7 +687,6 @@ CONFIG_USB_EHCI_HCD_OMAP=y # CONFIG_USB_EHCI_HCD_PLATFORM is not set CONFIG_USB_GADGET=y CONFIG_USB_INVENTRA_DMA=y -CONFIG_USB_MUSB_AM35X=y CONFIG_USB_MUSB_DSPS=y CONFIG_USB_MUSB_DUAL_ROLE=y CONFIG_USB_MUSB_HDRC=y @@ -693,6 +702,8 @@ CONFIG_VFAT_FS=y CONFIG_VFP=y CONFIG_VFPv3=y CONFIG_VIDEOMODE_HELPERS=y +CONFIG_VIDEO_CMDLINE=y +CONFIG_VIDEO_NOMODESET=y CONFIG_WATCHDOG_CORE=y CONFIG_XFRM_ALGO=y CONFIG_XFRM_MIGRATE=y diff --git a/target/linux/omap/image/Makefile b/target/linux/omap/image/Makefile index 507c91b2cc9aa5..591628c53f084c 100644 --- a/target/linux/omap/image/Makefile +++ b/target/linux/omap/image/Makefile @@ -33,6 +33,7 @@ define Device/Default PROFILES := Default KERNEL_NAME := zImage KERNEL := kernel-bin + DTS_DIR := $(DTS_DIR)/ti/omap DEVICE_DTS = $(lastword $(subst _, ,$(1))) IMAGES := sdcard.img.gz IMAGE/sdcard.img.gz := omap-sdcard | append-metadata | gzip diff --git a/target/linux/omap/patches/900-use-cpsw-ethernet-driver.patch b/target/linux/omap/patches-6.6/900-use-cpsw-ethernet-driver.patch similarity index 89% rename from target/linux/omap/patches/900-use-cpsw-ethernet-driver.patch rename to target/linux/omap/patches-6.6/900-use-cpsw-ethernet-driver.patch index 17c07fbdfba111..31fa0028c6eed0 100644 --- a/target/linux/omap/patches/900-use-cpsw-ethernet-driver.patch +++ b/target/linux/omap/patches-6.6/900-use-cpsw-ethernet-driver.patch @@ -17,9 +17,9 @@ devices in OpenWrt usable again with the default network config.) Signed-off-by: Jan Hoffmann --- ---- a/arch/arm/boot/dts/am335x-bone-common.dtsi -+++ b/arch/arm/boot/dts/am335x-bone-common.dtsi -@@ -353,27 +353,24 @@ +--- a/arch/arm/boot/dts/ti/omap/am335x-bone-common.dtsi ++++ b/arch/arm/boot/dts/ti/omap/am335x-bone-common.dtsi +@@ -358,27 +358,24 @@ }; }; @@ -52,8 +52,8 @@ Signed-off-by: Jan Hoffmann ethphy0: ethernet-phy@0 { reg = <0>; ---- a/arch/arm/boot/dts/am335x-evm.dts -+++ b/arch/arm/boot/dts/am335x-evm.dts +--- a/arch/arm/boot/dts/ti/omap/am335x-evm.dts ++++ b/arch/arm/boot/dts/ti/omap/am335x-evm.dts @@ -682,31 +682,28 @@ }; }; diff --git a/target/linux/ramips/dts/mt7621_dna_valokuitu-plus-ex400.dts b/target/linux/ramips/dts/mt7621_dna_valokuitu-plus-ex400.dts new file mode 100644 index 00000000000000..98b2bbf7b64dc7 --- /dev/null +++ b/target/linux/ramips/dts/mt7621_dna_valokuitu-plus-ex400.dts @@ -0,0 +1,130 @@ +// SPDX-License-Identifier: GPL-2.0-or-later OR MIT + +#include "mt7621.dtsi" + +#include +#include +#include + +/ { + compatible = "dna,valokuitu-plus-ex400", "mediatek,mt7621-soc"; + model = "DNA Valokuitu Plus EX400"; + + aliases { + ethernet0 = &gmac0; + label-mac-device = &gmac0; + led-boot = &led_status_red; + led-failsafe = &led_status_red; + led-running = &led_status_green; + led-upgrade = &led_update_green; + }; + + chosen { + bootargs-override = "console=ttyS0,115200 rootfstype=squashfs,jffs2"; + }; + + keys { + compatible = "gpio-keys"; + + reset { + label = "reset"; + gpios = <&gpio 18 GPIO_ACTIVE_LOW>; + linux,code = ; + }; + }; + + leds { + compatible = "gpio-leds"; + + led_status_green: led-0 { + color = ; + function = LED_FUNCTION_STATUS; + gpios = <&gpio 8 GPIO_ACTIVE_LOW>; + }; + + led_status_red: led-1 { + color = ; + function = LED_FUNCTION_STATUS; + gpios = <&gpio 11 GPIO_ACTIVE_HIGH>; + }; + + led_update_green: led-2 { + color = ; + function = LED_FUNCTION_PROGRAMMING; + gpios = <&gpio 12 GPIO_ACTIVE_LOW>; + }; + }; +}; + +&pcie { + status = "okay"; +}; + +&nand { + status = "okay"; + + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + partition@0 { + reg = <0x00 0x100000>; + label = "uboot"; + read-only; + }; + + partition@100000 { + reg = <0x100000 0xff00000>; + label = "ubi"; + + volumes { + ubi-volume-env1 { + volname = "env1"; + + nvmem-layout { + compatible = "u-boot,env"; + + ethaddr: ethaddr { + #nvmem-cell-cells = <1>; + }; + }; + }; + }; + }; + }; +}; + +&gmac1 { + label = "wan"; + phy-handle = <ðphy0>; + nvmem-cells = <ðaddr 1>; + nvmem-cell-names = "mac-address"; + status = "okay"; +}; + +&i2c { + status = "okay"; +}; + +ðphy0 { + /delete-property/ interrupts; +}; + +&state_default { + gpio { + groups = "uart2", "uart3"; + function = "gpio"; + }; +}; + +&switch0 { + ports { + port@1 { + label = "lan"; + nvmem-cells = <ðaddr 0>; + nvmem-cell-names = "mac-address"; + status = "okay"; + }; + }; +}; diff --git a/target/linux/ramips/image/mt7621.mk b/target/linux/ramips/image/mt7621.mk index 18dbbcadf31d7b..bf700674ef53b0 100644 --- a/target/linux/ramips/image/mt7621.mk +++ b/target/linux/ramips/image/mt7621.mk @@ -36,6 +36,68 @@ define Build/arcadyan-trx rm $@.hsqs $@.tail endef +define Build/dna-header + BC='$(STAGING_DIR_HOST)/bin/bc' ;\ + ubifsofs="1024" ;\ + ubifs="$$(stat -c%s $@)" ;\ + pkginfoofs="$$(echo $${ubifsofs} + $${ubifs} | $${BC})" ;\ + pkginfo="0" ;\ + scrofs="$$(echo $${pkginfoofs} + $${pkginfo} | $${BC})" ;\ + scr="0" ;\ + sigofs="$$(echo $${scrofs} + $${scr} | $${BC})" ;\ + sig="0" ;\ + md5ofs="$$(echo $${sigofs} + $${sig} | $${BC})" ;\ + md5="32" ;\ + size="$$(echo $${md5ofs} + $${md5} | $${BC})" ;\ + echo "IntenoIopY" > $@.tmp ;\ + echo "version 5" >> $@.tmp ;\ + echo "integrity MD5SUM" >> $@.tmp ;\ + echo "board EX400" >> $@.tmp ;\ + echo "chip 7621" >> $@.tmp ;\ + echo "arch all mipsel_1004kc" >> $@.tmp ;\ + echo "model EX400" >> $@.tmp ;\ + echo "release EX400-X-DNA-4.3.6.100-R-210518_0935" >> $@.tmp ;\ + echo "customer DNA" >> $@.tmp ;\ + echo "ubifsofs $${ubifsofs}" >> $@.tmp ;\ + echo "ubifs $${ubifs}" >> $@.tmp ;\ + echo "pkginfoofs $${pkginfoofs}" >> $@.tmp ;\ + echo "pkginfo $${pkginfo}" >> $@.tmp ;\ + echo "scrofs $${scrofs}" >> $@.tmp ;\ + echo "scr $${scr}" >> $@.tmp ;\ + echo "sigofs $${sigofs}" >> $@.tmp ;\ + echo "sig $${sig}" >> $@.tmp ;\ + echo "md5ofs $${md5ofs}" >> $@.tmp ;\ + echo "md5 $${md5}" >> $@.tmp ;\ + echo "size $${size}" >> $@.tmp + + dd if=$@.tmp of=$@.tmp2 bs=1024 count=1 conv=sync + cat $@.tmp2 $@ > $@.tmp + rm $@.tmp2 + mv $@.tmp $@ +endef + +define Build/dna-bootfs + mkdir -p $@.ubifs-dir/boot + + # populate the boot fs with the dtb and with either initramfs kernel or + # the normal kernel + $(CP) $(KDIR)/image-$(firstword $(DEVICE_DTS)).dtb $@.ubifs-dir/boot/dtb + + $(if $(findstring with-initrd,$(word 1,$(1))),\ + ( \ + $(CP) $@ $@.ubifs-dir/boot/uImage \ + ) , \ + ( \ + $(CP) $(IMAGE_KERNEL) $@.ubifs-dir/boot/uImage \ + ) \ + ) + + # create ubifs + $(STAGING_DIR_HOST)/bin/mkfs.ubifs ${MKUBIFS_OPTS} -r $@.ubifs-dir/ -o $@.new + rm -rf $@.ubifs-dir + mv $@.new $@ +endef + define Build/gemtek-trailer printf "%s%08X" ".GEMTEK." "$$(cksum $@ | cut -d ' ' -f1)" >> $@ endef @@ -103,6 +165,10 @@ define Build/iodata-mstc-header2 mv $@.new $@ endef +define Build/kernel-initramfs-bin + $(CP) $(KDIR)/vmlinux-initramfs $@ +endef + define Build/znet-header $(eval version=$(word 1,$(1))) $(eval magic=$(if $(word 2,$(1)),$(word 2,$(1)),ZNET)) @@ -988,6 +1054,27 @@ define Device/d-team_pbr-m1 endef TARGET_DEVICES += d-team_pbr-m1 +define Device/dna_valokuitu-plus-ex400 + $(Device/dsa-migration) + IMAGE_SIZE := 117m + PAGESIZE := 2048 + MKUBIFS_OPTS := --min-io-size=$$(PAGESIZE) --leb-size=124KiB --max-leb-cnt=96 \ + --log-lebs=2 --space-fixup --squash-uids + DEVICE_VENDOR := DNA + DEVICE_MODEL := Valokuitu Plus EX400 + KERNEL := kernel-bin | lzma | uImage lzma + KERNEL_INITRAMFS := kernel-bin | append-dtb | lzma | uImage lzma + IMAGES := factory.bin sysupgrade.tar + IMAGE/factory.bin := kernel-initramfs-bin | lzma | uImage lzma | \ + dna-bootfs with-initrd | dna-header | \ + append-md5sum-ascii-salted + IMAGE/sysupgrade.tar := dna-bootfs | sysupgrade-tar kernel=$$$$@ | check-size | \ + append-metadata + DEVICE_IMG_NAME = $$(DEVICE_IMG_PREFIX)-$$(2) + DEVICE_PACKAGES := kmod-mt7603 kmod-mt7615-firmware kmod-usb3 +endef +TARGET_DEVICES += dna_valokuitu-plus-ex400 + define Device/edimax_ra21s $(Device/dsa-migration) $(Device/uimage-lzma-loader) diff --git a/target/linux/ramips/mt7621/base-files/etc/board.d/02_network b/target/linux/ramips/mt7621/base-files/etc/board.d/02_network index b7e3a49b43bfa1..f251daddd5efea 100644 --- a/target/linux/ramips/mt7621/base-files/etc/board.d/02_network +++ b/target/linux/ramips/mt7621/base-files/etc/board.d/02_network @@ -67,6 +67,7 @@ ramips_setup_interfaces() ucidef_set_interface_lan "lan" ;; asiarf,ap7621-001|\ + dna,valokuitu-plus-ex400|\ humax,e10|\ keenetic,kn-3510|\ openfi,5pro|\ diff --git a/target/linux/ramips/mt7621/base-files/etc/init.d/bootcount b/target/linux/ramips/mt7621/base-files/etc/init.d/bootcount index 06846cd4ca40fc..b83223e7ddd757 100755 --- a/target/linux/ramips/mt7621/base-files/etc/init.d/bootcount +++ b/target/linux/ramips/mt7621/base-files/etc/init.d/bootcount @@ -32,6 +32,10 @@ boot() { samknows,whitebox-v8) fw_setenv bootcount 0 ;; + dna,valokuitu-plus-ex400) + fw_setenv boot_cnt_primary 0 + fw_setenv boot_cnt_alt 0 + ;; zyxel,lte3301-plus) [ $(printf %d $(fw_printenv -n DebugFlag)) -gt 0 ] || fw_setenv DebugFlag 1 [ $(printf %d $(fw_printenv -n Image1Stable)) -gt 0 ] || fw_setenv Image1Stable 1 diff --git a/target/linux/ramips/mt7621/base-files/lib/upgrade/dna.sh b/target/linux/ramips/mt7621/base-files/lib/upgrade/dna.sh new file mode 100644 index 00000000000000..d699516ff6f2d5 --- /dev/null +++ b/target/linux/ramips/mt7621/base-files/lib/upgrade/dna.sh @@ -0,0 +1,44 @@ +# +# Copyright (C) 2023 Mauri Sandberg +# + +# The vendor UBI is split in volumes 0-3. Volumes 0 and 1 contain U-Boot +# environments env1 and env2, respectively. The vendor root file systems +# are in volumes 2 (rootfs_0) and 3 (rootfs_1). Drop the two roots and +# explicitly use rootfs_0 as a boot partition that contains the dtb and the +# OpenWrt kernel. This is because the vendor U-Boot expects to find them there. +# Then continue upgrade with the default method - a SquashFS rootfs will be +# installed and the rest of UBI will be used as an overlay. + +# The 'kernel' inside the sysupgrage.tar is an UBIFS image that contains +# /boot/dtb and /boot/kernel. The 'root' is an OpenWrt SquashFS root + +. /lib/functions.sh +. /lib/upgrade/nand.sh + +dna_do_upgrade () { + tar -xaf $1 + + # get the size of the new bootfs + local _bootfs_size=$(wc -c < ./sysupgrade-dna_valokuitu-plus-ex400/kernel) + [ -n "$_bootfs_size" -a "$_bootfs_size" -gt "0" ] || nand_do_upgrade_failed + + # remove existing rootfses and recreate rootfs_0 + ubirmvol /dev/ubi0 --name=rootfs_0 > /dev/null 2>&1 + ubirmvol /dev/ubi0 --name=rootfs_1 > /dev/null 2>&1 + ubirmvol /dev/ubi0 --name=rootfs > /dev/null 2>&1 + ubirmvol /dev/ubi0 --name=rootfs_data > /dev/null 2>&1 + ubimkvol /dev/ubi0 --type=static --size=${_bootfs_size} --name=rootfs_0 + + # update the rootfs_0 contents + local _kern_ubivol=$( nand_find_volume "ubi0" "rootfs_0" ) + ubiupdatevol /dev/${_kern_ubivol} sysupgrade-dna_valokuitu-plus-ex400/kernel + + fw_setenv root_vol rootfs_0 + fw_setenv boot_cnt_primary 0 + fw_setenv boot_cnt_alt 0 + + # proceed to upgrade the default way + CI_KERNPART=none + nand_do_upgrade "$1" +} diff --git a/target/linux/ramips/mt7621/base-files/lib/upgrade/platform.sh b/target/linux/ramips/mt7621/base-files/lib/upgrade/platform.sh index bad7e30ca65ebf..f0d41b09140515 100755 --- a/target/linux/ramips/mt7621/base-files/lib/upgrade/platform.sh +++ b/target/linux/ramips/mt7621/base-files/lib/upgrade/platform.sh @@ -150,6 +150,9 @@ platform_do_upgrade() { buffalo,wsr-2533dhpls) buffalo_do_upgrade "$1" ;; + dna,valokuitu-plus-ex400) + dna_do_upgrade "$1" + ;; elecom,wrc-x1800gs) [ "$(fw_printenv -n bootmenu_delay)" != "0" ] || \ fw_setenv bootmenu_delay 3 diff --git a/target/linux/realtek/base-files/etc/uci-defaults/04_dlinkfan b/target/linux/realtek/base-files/etc/uci-defaults/04_dlinkfan new file mode 100644 index 00000000000000..1a5fd3606f24c8 --- /dev/null +++ b/target/linux/realtek/base-files/etc/uci-defaults/04_dlinkfan @@ -0,0 +1,26 @@ +# +# Copyright (C) 2024 openwrt.org +# + +. /lib/functions.sh + +board=$(board_name) + +case "$board" in +d-link,dgs-1210-28mp-f) + # Enable fan control + FAN_CTRL='/sys/class/hwmon/hwmon0' + echo 1 > "$FAN_PATH/pwm1_enable" + + # Set fan script execution in crontab + grep -s -q fan_ctrl.sh /etc/crontabs/root && exit 0 + + echo "# dlink fan script runs every 5 minutes" >> /etc/crontabs/root + echo "*/5 * * * * /sbin/fan_ctrl.sh" >> /etc/crontabs/root + + # Execute one time after initial flash (instead of waiting 5 min for cron) + /sbin/fan_ctrl.sh + ;; +esac + +exit 0 diff --git a/target/linux/realtek/base-files/sbin/fan_ctrl.sh b/target/linux/realtek/base-files/sbin/fan_ctrl.sh new file mode 100755 index 00000000000000..e7b661d7bb6685 --- /dev/null +++ b/target/linux/realtek/base-files/sbin/fan_ctrl.sh @@ -0,0 +1,13 @@ +#!/bin/sh + +PSU_TEMP=$(cut -c1-2 /sys/class/hwmon/hwmon0/temp1_input) + +FAN_CTRL='/sys/class/hwmon/hwmon0/pwm1' + +PSU_THRESH=51000 + +if [ "$PSU_TEMP" -ge "$PSU_THRESH" ];then + echo "250" > $FAN_CTRL +else + echo "156" > $FAN_CTRL +fi diff --git a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28.dts b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28.dts index 0bcb196b7c9732..29ff8153fbf7bf 100644 --- a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28.dts +++ b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28.dts @@ -3,6 +3,7 @@ #include "rtl838x.dtsi" #include "rtl83xx_d-link_dgs-1210_common.dtsi" #include "rtl83xx_d-link_dgs-1210_gpio.dtsi" +#include "rtl83xx_d-link_dgs-1210_gpio_sfp.dtsi" #include "rtl8382_d-link_dgs-1210-28_common.dtsi" / { diff --git a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28_common.dtsi b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28_common.dtsi index 17866d5f038f3c..d5b984b0a6f1e9 100644 --- a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28_common.dtsi +++ b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28_common.dtsi @@ -34,10 +34,11 @@ EXTERNAL_PHY(22) EXTERNAL_PHY(23) - EXTERNAL_SFP_PHY(24) - EXTERNAL_SFP_PHY(25) - EXTERNAL_SFP_PHY(26) - EXTERNAL_SFP_PHY(27) + /* External phy RTL8214FC */ + EXTERNAL_SFP_PHY_FULL(24, 0) + EXTERNAL_SFP_PHY_FULL(25, 1) + EXTERNAL_SFP_PHY_FULL(26, 2) + EXTERNAL_SFP_PHY_FULL(27, 3) }; }; diff --git a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28mp-f.dts b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28mp-f.dts index ce008229b3334f..4c20a4ae6e2aa6 100644 --- a/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28mp-f.dts +++ b/target/linux/realtek/dts/rtl8382_d-link_dgs-1210-28mp-f.dts @@ -3,11 +3,28 @@ #include "rtl838x.dtsi" #include "rtl83xx_d-link_dgs-1210_common.dtsi" #include "rtl83xx_d-link_dgs-1210_gpio.dtsi" +#include "rtl83xx_d-link_dgs-1210_gpio_sfp.dtsi" #include "rtl8382_d-link_dgs-1210-28_common.dtsi" / { compatible = "d-link,dgs-1210-28mp-f", "realtek,rtl8382-soc", "realtek,rtl838x-soc"; model = "D-Link DGS-1210-28MP F"; + + /* LM63 */ + i2c-gpio-4 { + compatible = "i2c-gpio"; + sda-gpios = <&gpio1 32 (GPIO_ACTIVE_HIGH | GPIO_OPEN_DRAIN)>; + scl-gpios = <&gpio1 31 GPIO_ACTIVE_HIGH>; + i2c-gpio,delay-us = <2>; + i2c-gpio,scl-open-drain; /* should be replaced by i2c-gpio,scl-has-no-pullup in kernel 6.6 */ + #address-cells = <1>; + #size-cells = <0>; + + lm63@4c { + compatible = "national,lm63"; + reg = <0x4c>; + }; + }; }; &leds { diff --git a/target/linux/realtek/dts/rtl8393_d-link_dgs-1210-52.dts b/target/linux/realtek/dts/rtl8393_d-link_dgs-1210-52.dts index 5b876e7c431dae..3ddf56f4f5ca5a 100644 --- a/target/linux/realtek/dts/rtl8393_d-link_dgs-1210-52.dts +++ b/target/linux/realtek/dts/rtl8393_d-link_dgs-1210-52.dts @@ -3,7 +3,7 @@ #include "rtl839x.dtsi" #include "rtl83xx_d-link_dgs-1210_common.dtsi" #include "rtl83xx_d-link_dgs-1210_gpio.dtsi" -#include "rtl839x_d-link_dgs-1210_gpio.dtsi" +#include "rtl83xx_d-link_dgs-1210_gpio_sfp.dtsi" / { compatible = "d-link,dgs-1210-52", "realtek,rtl8393-soc"; diff --git a/target/linux/realtek/dts/rtl839x_d-link_dgs-1210_gpio.dtsi b/target/linux/realtek/dts/rtl83xx_d-link_dgs-1210_gpio_sfp.dtsi similarity index 100% rename from target/linux/realtek/dts/rtl839x_d-link_dgs-1210_gpio.dtsi rename to target/linux/realtek/dts/rtl83xx_d-link_dgs-1210_gpio_sfp.dtsi diff --git a/target/linux/realtek/files-5.15/drivers/net/dsa/rtl83xx/dsa.c b/target/linux/realtek/files-5.15/drivers/net/dsa/rtl83xx/dsa.c index 9eb444515f46b3..ee87de8e0784f6 100644 --- a/target/linux/realtek/files-5.15/drivers/net/dsa/rtl83xx/dsa.c +++ b/target/linux/realtek/files-5.15/drivers/net/dsa/rtl83xx/dsa.c @@ -109,6 +109,20 @@ static enum dsa_tag_protocol rtl83xx_get_tag_protocol(struct dsa_switch *ds, return DSA_TAG_PROTO_TRAILER; } +static void rtl83xx_vlan_set_pvid(struct rtl838x_switch_priv *priv, + int port, int pvid) +{ + /* Set both inner and outer PVID of the port */ + priv->r->vlan_port_pvid_set(port, PBVLAN_TYPE_INNER, pvid); + priv->r->vlan_port_pvid_set(port, PBVLAN_TYPE_OUTER, pvid); + priv->r->vlan_port_pvidmode_set(port, PBVLAN_TYPE_INNER, + PBVLAN_MODE_UNTAG_AND_PRITAG); + priv->r->vlan_port_pvidmode_set(port, PBVLAN_TYPE_OUTER, + PBVLAN_MODE_UNTAG_AND_PRITAG); + + priv->ports[port].pvid = pvid; +} + /* Initialize all VLANS */ static void rtl83xx_vlan_setup(struct rtl838x_switch_priv *priv) { @@ -132,17 +146,22 @@ static void rtl83xx_vlan_setup(struct rtl838x_switch_priv *priv) info.l2_tunnel_list_id = -1; } - /* Initialize all vlans 0-4095 */ - for (int i = 0; i < MAX_VLANS; i ++) + /* Initialize normal VLANs 1-4095 */ + for (int i = 1; i < MAX_VLANS; i ++) priv->r->vlan_set_tagged(i, &info); - /* reset PVIDs; defaults to 1 on reset */ + /* + * Initialize the special VLAN 0 and reset PVIDs. The CPU port PVID + * is applied to packets from the CPU for untagged destinations, + * regardless if the actual ingress VID. Any port with untagged + * egress VLAN(s) must therefore be a member of VLAN 0 to support + * CPU port as ingress when VLAN filtering is enabled. + */ for (int i = 0; i <= priv->cpu_port; i++) { - priv->r->vlan_port_pvid_set(i, PBVLAN_TYPE_INNER, 1); - priv->r->vlan_port_pvid_set(i, PBVLAN_TYPE_OUTER, 1); - priv->r->vlan_port_pvidmode_set(i, PBVLAN_TYPE_INNER, PBVLAN_MODE_UNTAG_AND_PRITAG); - priv->r->vlan_port_pvidmode_set(i, PBVLAN_TYPE_OUTER, PBVLAN_MODE_UNTAG_AND_PRITAG); + rtl83xx_vlan_set_pvid(priv, i, 0); + info.tagged_ports |= BIT_ULL(i); } + priv->r->vlan_set_tagged(0, &info); /* Set forwarding action based on inner VLAN tag */ for (int i = 0; i < priv->cpu_port; i++) @@ -1392,20 +1411,6 @@ static int rtl83xx_vlan_prepare(struct dsa_switch *ds, int port, return 0; } -static void rtl83xx_vlan_set_pvid(struct rtl838x_switch_priv *priv, - int port, int pvid) -{ - /* Set both inner and outer PVID of the port */ - priv->r->vlan_port_pvid_set(port, PBVLAN_TYPE_INNER, pvid); - priv->r->vlan_port_pvid_set(port, PBVLAN_TYPE_OUTER, pvid); - priv->r->vlan_port_pvidmode_set(port, PBVLAN_TYPE_INNER, - PBVLAN_MODE_UNTAG_AND_PRITAG); - priv->r->vlan_port_pvidmode_set(port, PBVLAN_TYPE_OUTER, - PBVLAN_MODE_UNTAG_AND_PRITAG); - - priv->ports[port].pvid = pvid; -} - static int rtl83xx_vlan_add(struct dsa_switch *ds, int port, const struct switchdev_obj_port_vlan *vlan, struct netlink_ext_ack *extack) @@ -1417,7 +1422,8 @@ static int rtl83xx_vlan_add(struct dsa_switch *ds, int port, pr_debug("%s port %d, vid %d, flags %x\n", __func__, port, vlan->vid, vlan->flags); - if(!vlan->vid) return 0; + /* Let no one mess with our special VLAN 0 */ + if (!vlan->vid) return 0; if (vlan->vid > 4095) { dev_err(priv->dev, "VLAN out of range: %d", vlan->vid); @@ -1430,10 +1436,20 @@ static int rtl83xx_vlan_add(struct dsa_switch *ds, int port, mutex_lock(&priv->reg_mutex); - if (vlan->flags & BRIDGE_VLAN_INFO_PVID) - rtl83xx_vlan_set_pvid(priv, port, vlan->vid); - else if (priv->ports[port].pvid == vlan->vid) - rtl83xx_vlan_set_pvid(priv, port, 0); + /* + * Realtek switches copy frames as-is to/from the CPU. For a proper + * VLAN handling the 12 bit RVID field (= VLAN id) for incoming traffic + * and the 1 bit RVID_SEL field (0 = use inner tag, 1 = use outer tag) + * for outgoing traffic of the CPU tag structure need to be handled. As + * of now no such logic is in place. So for the CPU port keep the fixed + * PVID=0 from initial setup in place and ignore all subsequent settings. + */ + if (port != priv->cpu_port) { + if (vlan->flags & BRIDGE_VLAN_INFO_PVID) + rtl83xx_vlan_set_pvid(priv, port, vlan->vid); + else if (priv->ports[port].pvid == vlan->vid) + rtl83xx_vlan_set_pvid(priv, port, 0); + } /* Get port memberships of this vlan */ priv->r->vlan_tables_read(vlan->vid, &info); @@ -1477,6 +1493,9 @@ static int rtl83xx_vlan_del(struct dsa_switch *ds, int port, pr_debug("%s: port %d, vid %d, flags %x\n", __func__, port, vlan->vid, vlan->flags); + /* Let no one mess with our special VLAN 0 */ + if (!vlan->vid) return 0; + if (vlan->vid > 4095) { dev_err(priv->dev, "VLAN out of range: %d", vlan->vid); return -ENOTSUPP; diff --git a/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.c b/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.c index e6c06c4452221b..7ad9b5f0291d9c 100644 --- a/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.c +++ b/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.c @@ -1622,7 +1622,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, } /* - * On all RealTek switch platforms the hardware periodically reads the link status of all + * On all Realtek switch platforms the hardware periodically reads the link status of all * PHYs. This is to some degree programmable, so that one can tell the hardware to read * specific C22 registers from specific pages, or C45 registers, to determine the current * link speed, duplex, flow-control, ... @@ -1639,7 +1639,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * abstractions. * * Additionally at least the RTL838x and RTL839x devices are known to have a so called - * raw mode. Using the special MAX_PAGE-1 with the MDIO controller found in RealTek + * raw mode. Using the special MAX_PAGE-1 with the MDIO controller found in Realtek * SoCs allows to access the PHY in raw mode, ie. bypassing the cache and paging engine * of the MDIO controller. E.g. for RTL838x this is 0xfff. * @@ -1648,9 +1648,9 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * when they are not attached to an Realtek SoC. The paradigm should be to keep the PHY * implementation bus independent. * - * As if this is not enough the PHYs consist of 8 ports that all can be programmed - * individually. Writing to port 0 can configure the whole why while other operations - * need to be replicated per port. + * As if this is not enough the PHY packages consist of 4 or 8 ports that all can be + * programmed individually. Some registers are only available on port 0 and configure + * the whole package. * * To bring all this together we need a tricky bus design that intercepts select page * calls but lets raw page accesses through. And especially knows how to handle raw @@ -1661,7 +1661,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * the accesses and the state of the bus with the attributes page[], raw[] and portaddr * of the bus_priv structure. The page selection works as follows: * - * phy_write(phydev, RTL821X_PAGE_SELECT, 12) : store internal page 12 in driver + * phy_write(phydev, RTMDIO_PAGE_SELECT, 12) : store internal page 12 in driver * phy_write(phydev, 7, 33) : write page=12, reg=7, val=33 * * or simply @@ -1670,8 +1670,8 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * * The port selection works as follows and must be called under a held mdio bus lock * - * __mdiobus_write(bus, RTL821X_PORT_SELECT, 4) : switch to port paddr - * __phy_write(phydev, RTL821X_PAGE_SELECT, 11) : store internal page 11 in driver + * __mdiobus_write(bus, RTMDIO_PORT_SELECT, 4) : switch to port 4 + * __phy_write(phydev, RTMDIO_PAGE_SELECT, 11) : store internal page 11 in driver * __phy_write(phydev, 8, 19) : write page=11, reg=8, val=19, port=4 * * Any Realtek PHY that will be connected to this bus must simply provide the standard @@ -1689,75 +1689,57 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * return __phy_write(phydev, RTL821X_PAGE_SELECT, page); * } * - * In case there are non Realtek PHYs attached to the logic might need to be + * In case there are non Realtek PHYs attached to the bus the logic might need to be * reimplemented. For now it should be sufficient. */ -#define RTL821X_PAGE_SELECT 0x1f -#define RTL821X_PORT_SELECT 0x2000 -#define RTL838X_PAGE_RAW 0xfff -#define RTL839X_PAGE_RAW 0x1fff -#define RTL930X_PAGE_RAW 0xfff -#define RTL931X_PAGE_RAW 0x1fff -#define RTMDIO_READ 0x0 -#define RTMDIO_WRITE 0x1 +#define RTMDIO_PAGE_SELECT 0x1f +#define RTMDIO_PORT_SELECT 0x2000 +#define RTMDIO_READ 0x1 +#define RTMDIO_WRITE 0x2 +#define RTMDIO_ABS 0x4 +#define RTMDIO_PKG 0x8 /* - * Provide a generic read/write function so we can access multiple ports on a shared PHY - * package of the bus with separate addresses individually. This basically resembles the + * Provide a generic read/write function so we can access arbitrary ports on the bus. + * E.g. other ports of a PHY package on the bus. This basically resembles the kernel * phy_read_paged() and phy_write_paged() functions. To inform the bus that we are - * workin on a not default port (8, 16, 24, ...) we send a RTL821X_PORT_SELECT command - * at the beginning and the end to switch the port handling logic. + * working on a not default port send a RTMDIO_PORT_SELECT command at the beginning + * and the end to switch the port handling logic. */ -static int rtmdio_read_page(struct phy_device *phydev) -{ - if (WARN_ONCE(!phydev->drv->read_page, - "read_page callback not available, PHY driver not loaded?\n")) - return -EOPNOTSUPP; - - return phydev->drv->read_page(phydev); -} - -static int rtmdio_write_page(struct phy_device *phydev, int page) -{ - if (WARN_ONCE(!phydev->drv->write_page, - "write_page callback not available, PHY driver not loaded?\n")) - return -EOPNOTSUPP; - - return phydev->drv->write_page(phydev, page); -} - -static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, - int page, u32 regnum, u16 val) +static int rtmdio_access(struct phy_device *phydev, int op, int port, + int page, u32 regnum, u16 val) { int r, ret = 0, oldpage; - struct phy_package_shared *shared = phydev->shared; - if (!shared) - return -EIO; + if (op & RTMDIO_PKG) { + if (!phydev->shared) + return -EIO; + port = phydev->shared->addr + port; + } /* lock and inform bus about non default addressing */ phy_lock_mdio_bus(phydev); __mdiobus_write(phydev->mdio.bus, phydev->mdio.addr, - RTL821X_PORT_SELECT, shared->addr + port); + RTMDIO_PORT_SELECT, port); - oldpage = ret = rtmdio_read_page(phydev); + oldpage = ret = __phy_read(phydev, RTMDIO_PAGE_SELECT); if (oldpage >= 0 && oldpage != page) { - ret = rtmdio_write_page(phydev, page); + ret = __phy_write(phydev, RTMDIO_PAGE_SELECT, page); if (ret < 0) oldpage = ret; } if (oldpage >= 0) { - if (op == RTMDIO_WRITE) + if (op & RTMDIO_WRITE) ret = __phy_write(phydev, regnum, val); else ret = __phy_read(phydev, regnum); } if (oldpage >= 0) { - r = rtmdio_write_page(phydev, oldpage); + r = __phy_write(phydev, RTMDIO_PAGE_SELECT, oldpage); if (ret >= 0 && r < 0) ret = r; } else @@ -1765,7 +1747,7 @@ static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, /* reset bus to default adressing and unlock it */ __mdiobus_write(phydev->mdio.bus, phydev->mdio.addr, - RTL821X_PORT_SELECT, 0); + RTMDIO_PORT_SELECT, -1); phy_unlock_mdio_bus(phydev); return ret; @@ -1775,40 +1757,53 @@ static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, * To make use of the shared package functions provide wrappers that align with kernel * naming conventions. The package() functions are useful to change settings on the * package as a whole. The package_port() functions will allow to target the PHYs - * individually. + * of a package individually. The port() only functions allow to access arbitrary ports + * on the bus through a PHY. */ int phy_package_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val) { - return rtmdio_package_rw(phydev, RTMDIO_WRITE, port, page, regnum, val); + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_PKG, port, page, regnum, val); } int phy_package_write_paged(struct phy_device *phydev, int page, u32 regnum, u16 val) { - return rtmdio_package_rw(phydev, RTMDIO_WRITE, 0, page, regnum, val); + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_PKG, 0, page, regnum, val); +} + +int phy_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val) +{ + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_ABS, port, page, regnum, val); } int phy_package_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum) { - return rtmdio_package_rw(phydev, RTMDIO_READ, port, page, regnum, 0); + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_PKG, port, page, regnum, 0); } int phy_package_read_paged(struct phy_device *phydev, int page, u32 regnum) { - return rtmdio_package_rw(phydev, RTMDIO_READ, 0, page, regnum, 0); + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_PKG, 0, page, regnum, 0); } -/* These are the core functions of our fancy Realtek SoC MDIO bus. */ +int phy_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum) +{ + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_ABS, port, page, regnum, 0); +} + +/* These are the core functions of our new Realtek SoC MDIO bus. */ static int rtmdio_read_c45(struct mii_bus *bus, int addr, int devnum, int regnum) { int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - err = (*bus_priv->read_mmd_phy)(portaddr, devnum, regnum, &val); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + err = (*bus_priv->read_mmd_phy)(addr, devnum, regnum, &val); pr_debug("rd_MMD(adr=%d, dev=%d, reg=%d) = %d, err = %d\n", - portaddr, devnum, regnum, val, err); + addr, devnum, regnum, val, err); return err ? err : val; } @@ -1817,21 +1812,23 @@ static int rtmdio_83xx_read(struct mii_bus *bus, int addr, int regnum) int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - if (portaddr >= 24 && portaddr <= 27 && eth_priv->id == 0x8380) - return rtl838x_read_sds_phy(portaddr, regnum); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; - if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[portaddr]) - return rtl839x_read_sds_phy(portaddr, regnum); + if (addr >= 24 && addr <= 27 && eth_priv->id == 0x8380) + return rtl838x_read_sds_phy(addr, regnum); - if (regnum == RTL821X_PAGE_SELECT && bus_priv->page[portaddr] != RTL838X_PAGE_RAW) - return bus_priv->page[portaddr]; + if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[addr]) + return rtl839x_read_sds_phy(addr, regnum); - bus_priv->raw[portaddr] = (bus_priv->page[portaddr] == RTL838X_PAGE_RAW); - err = (*bus_priv->read_phy)(portaddr, bus_priv->page[portaddr], regnum, &val); + if (regnum == RTMDIO_PAGE_SELECT && bus_priv->page[addr] != bus_priv->rawpage) + return bus_priv->page[addr]; + + bus_priv->raw[addr] = (bus_priv->page[addr] == bus_priv->rawpage); + err = (*bus_priv->read_phy)(addr, bus_priv->page[addr], regnum, &val); pr_debug("rd_PHY(adr=%d, pag=%d, reg=%d) = %d, err = %d\n", - portaddr, bus_priv->page[portaddr], regnum, val, err); + addr, bus_priv->page[addr], regnum, val, err); return err ? err : val; } @@ -1840,24 +1837,26 @@ static int rtmdio_93xx_read(struct mii_bus *bus, int addr, int regnum) int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - if (regnum == RTL821X_PAGE_SELECT && bus_priv->page[portaddr] != RTL930X_PAGE_RAW) - return bus_priv->page[portaddr]; + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + if (regnum == RTMDIO_PAGE_SELECT && bus_priv->page[addr] != bus_priv->rawpage) + return bus_priv->page[addr]; - bus_priv->raw[portaddr] = (bus_priv->page[portaddr] == RTL930X_PAGE_RAW); - if (eth_priv->phy_is_internal[portaddr]) { + bus_priv->raw[addr] = (bus_priv->page[addr] == bus_priv->rawpage); + if (eth_priv->phy_is_internal[addr]) { if (eth_priv->family_id == RTL9300_FAMILY_ID) - return rtl930x_read_sds_phy(eth_priv->sds_id[portaddr], - bus_priv->page[portaddr], regnum); + return rtl930x_read_sds_phy(eth_priv->sds_id[addr], + bus_priv->page[addr], regnum); else - return rtl931x_read_sds_phy(eth_priv->sds_id[portaddr], - bus_priv->page[portaddr], regnum); + return rtl931x_read_sds_phy(eth_priv->sds_id[addr], + bus_priv->page[addr], regnum); } - err = (*bus_priv->read_phy)(portaddr, bus_priv->page[portaddr], regnum, &val); + err = (*bus_priv->read_phy)(addr, bus_priv->page[addr], regnum, &val); pr_debug("rd_PHY(adr=%d, pag=%d, reg=%d) = %d, err = %d\n", - portaddr, bus_priv->page[portaddr], regnum, val, err); + addr, bus_priv->page[addr], regnum, val, err); return err ? err : val; } @@ -1865,83 +1864,91 @@ static int rtmdio_write_c45(struct mii_bus *bus, int addr, int devnum, int regnu { int err; struct rtl838x_bus_priv *bus_priv = bus->priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - err = (*bus_priv->write_mmd_phy)(portaddr, devnum, regnum, val); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + err = (*bus_priv->write_mmd_phy)(addr, devnum, regnum, val); pr_debug("wr_MMD(adr=%d, dev=%d, reg=%d, val=%d) err = %d\n", - portaddr, devnum, regnum, val, err); + addr, devnum, regnum, val, err); return err; } static int rtmdio_83xx_write(struct mii_bus *bus, int addr, int regnum, u16 val) { + int err, page, offset = 0; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - int err, page = bus_priv->page[portaddr], offset = 0; - if (regnum == RTL821X_PORT_SELECT) { - bus_priv->portaddr = val; + if (regnum == RTMDIO_PORT_SELECT) { + bus_priv->extaddr = (s16)val; return 0; } - if (portaddr >= 24 && portaddr <= 27 && eth_priv->id == 0x8380) { - if (portaddr == 26) + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + page = bus_priv->page[addr]; + + if (addr >= 24 && addr <= 27 && eth_priv->id == 0x8380) { + if (addr == 26) offset = 0x100; sw_w32(val, RTL838X_SDS4_FIB_REG0 + offset + (regnum << 2)); return 0; } - if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[portaddr]) - return rtl839x_write_sds_phy(portaddr, regnum, val); + if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[addr]) + return rtl839x_write_sds_phy(addr, regnum, val); - if (regnum == RTL821X_PAGE_SELECT) - bus_priv->page[portaddr] = val; + if (regnum == RTMDIO_PAGE_SELECT) + bus_priv->page[addr] = val; - if (!bus_priv->raw[portaddr] && (regnum != RTL821X_PAGE_SELECT || page == RTL838X_PAGE_RAW)) { - bus_priv->raw[portaddr] = (page == RTL838X_PAGE_RAW); - err = (*bus_priv->write_phy)(portaddr, page, regnum, val); + if (!bus_priv->raw[addr] && (regnum != RTMDIO_PAGE_SELECT || page == bus_priv->rawpage)) { + bus_priv->raw[addr] = (page == bus_priv->rawpage); + err = (*bus_priv->write_phy)(addr, page, regnum, val); pr_debug("wr_PHY(adr=%d, pag=%d, reg=%d, val=%d) err = %d\n", - portaddr, page, regnum, val, err); + addr, page, regnum, val, err); return err; } - bus_priv->raw[portaddr] = false; + bus_priv->raw[addr] = false; return 0; } static int rtmdio_93xx_write(struct mii_bus *bus, int addr, int regnum, u16 val) { + int err, page; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - int err, page = bus_priv->page[portaddr]; - if (regnum == RTL821X_PORT_SELECT) { - bus_priv->portaddr = val; + if (regnum == RTMDIO_PORT_SELECT) { + bus_priv->extaddr = (s16)val; return 0; } - if (regnum == RTL821X_PAGE_SELECT) - bus_priv->page[portaddr] = val; + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + page = bus_priv->page[addr]; + + if (regnum == RTMDIO_PAGE_SELECT) + bus_priv->page[addr] = val; - if (!bus_priv->raw[portaddr] && (regnum != RTL821X_PAGE_SELECT || page == RTL930X_PAGE_RAW)) { - bus_priv->raw[portaddr] = (page == RTL930X_PAGE_RAW); - if (eth_priv->phy_is_internal[portaddr]) { + if (!bus_priv->raw[addr] && (regnum != RTMDIO_PAGE_SELECT || page == bus_priv->rawpage)) { + bus_priv->raw[addr] = (page == bus_priv->rawpage); + if (eth_priv->phy_is_internal[addr]) { if (eth_priv->family_id == RTL9300_FAMILY_ID) - return rtl930x_write_sds_phy(eth_priv->sds_id[portaddr], + return rtl930x_write_sds_phy(eth_priv->sds_id[addr], page, regnum, val); else - return rtl931x_write_sds_phy(eth_priv->sds_id[portaddr], + return rtl931x_write_sds_phy(eth_priv->sds_id[addr], page, regnum, val); } - err = (*bus_priv->write_phy)(portaddr, page, regnum, val); + err = (*bus_priv->write_phy)(addr, page, regnum, val); pr_debug("wr_PHY(adr=%d, pag=%d, reg=%d, val=%d) err = %d\n", - portaddr, page, regnum, val, err); + addr, page, regnum, val, err); } - bus_priv->raw[portaddr] = false; + bus_priv->raw[addr] = false; return 0; } @@ -2244,11 +2251,11 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv = priv->mii_bus->priv; bus_priv->eth_priv = priv; - for (i = 0; i < 64; i++) { + for (i=0; i < 64; i++) { bus_priv->page[i] = 0; bus_priv->raw[i] = false; } - bus_priv->portaddr = 0; + bus_priv->extaddr = -1; switch(priv->family_id) { case RTL8380_FAMILY_ID: @@ -2260,6 +2267,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl838x_write_mmd_phy; bus_priv->read_phy = rtl838x_read_phy; bus_priv->write_phy = rtl838x_write_phy; + bus_priv->rawpage = 0xfff; break; case RTL8390_FAMILY_ID: priv->mii_bus->name = "rtl839x-eth-mdio"; @@ -2270,6 +2278,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl839x_write_mmd_phy; bus_priv->read_phy = rtl839x_read_phy; bus_priv->write_phy = rtl839x_write_phy; + bus_priv->rawpage = 0x1fff; break; case RTL9300_FAMILY_ID: priv->mii_bus->name = "rtl930x-eth-mdio"; @@ -2280,6 +2289,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl930x_write_mmd_phy; bus_priv->read_phy = rtl930x_read_phy; bus_priv->write_phy = rtl930x_write_phy; + bus_priv->rawpage = 0xfff; priv->mii_bus->probe_capabilities = MDIOBUS_C22_C45; break; case RTL9310_FAMILY_ID: @@ -2291,6 +2301,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl931x_write_mmd_phy; bus_priv->read_phy = rtl931x_read_phy; bus_priv->write_phy = rtl931x_write_phy; + bus_priv->rawpage = 0x1fff; priv->mii_bus->probe_capabilities = MDIOBUS_C22_C45; break; } diff --git a/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.h b/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.h index 0f49eae23da1e5..d6d88fc2ed01b8 100644 --- a/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.h +++ b/target/linux/realtek/files-5.15/drivers/net/ethernet/rtl838x_eth.h @@ -410,7 +410,8 @@ struct dsa_tag; struct rtl838x_bus_priv { struct rtl838x_eth_priv *eth_priv; - int portaddr; + int extaddr; + int rawpage; int page[64]; bool raw[64]; int (*read_mmd_phy)(u32 port, u32 addr, u32 reg, u32 *val); diff --git a/target/linux/realtek/files-5.15/drivers/net/phy/rtl83xx-phy.c b/target/linux/realtek/files-5.15/drivers/net/phy/rtl83xx-phy.c index 0c8b1dfd4dcd27..df5e2e444067ab 100644 --- a/target/linux/realtek/files-5.15/drivers/net/phy/rtl83xx-phy.c +++ b/target/linux/realtek/files-5.15/drivers/net/phy/rtl83xx-phy.c @@ -22,8 +22,10 @@ extern struct rtl83xx_soc_info soc_info; extern struct mutex smi_lock; extern int phy_package_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val); extern int phy_package_write_paged(struct phy_device *phydev, int page, u32 regnum, u16 val); +extern int phy_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val); extern int phy_package_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum); extern int phy_package_read_paged(struct phy_device *phydev, int page, u32 regnum); +extern int phy_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum); #define PHY_PAGE_2 2 #define PHY_PAGE_4 4 diff --git a/target/linux/realtek/files-6.6/drivers/net/dsa/rtl83xx/dsa.c b/target/linux/realtek/files-6.6/drivers/net/dsa/rtl83xx/dsa.c index 2f9b3ba8c14709..d61122e330d8f2 100644 --- a/target/linux/realtek/files-6.6/drivers/net/dsa/rtl83xx/dsa.c +++ b/target/linux/realtek/files-6.6/drivers/net/dsa/rtl83xx/dsa.c @@ -683,6 +683,7 @@ static void rtl83xx_phylink_get_caps(struct dsa_switch *ds, int port, __set_bit(PHY_INTERFACE_MODE_GMII, config->supported_interfaces); __set_bit(PHY_INTERFACE_MODE_QSGMII, config->supported_interfaces); __set_bit(PHY_INTERFACE_MODE_SGMII, config->supported_interfaces); + __set_bit(PHY_INTERFACE_MODE_XGMII, config->supported_interfaces); __set_bit(PHY_INTERFACE_MODE_1000BASEX, config->supported_interfaces); } diff --git a/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.c b/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.c index 4439059345102d..07664f9f382f3a 100644 --- a/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.c +++ b/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.c @@ -1629,7 +1629,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, } /* - * On all RealTek switch platforms the hardware periodically reads the link status of all + * On all Realtek switch platforms the hardware periodically reads the link status of all * PHYs. This is to some degree programmable, so that one can tell the hardware to read * specific C22 registers from specific pages, or C45 registers, to determine the current * link speed, duplex, flow-control, ... @@ -1646,7 +1646,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * abstractions. * * Additionally at least the RTL838x and RTL839x devices are known to have a so called - * raw mode. Using the special MAX_PAGE-1 with the MDIO controller found in RealTek + * raw mode. Using the special MAX_PAGE-1 with the MDIO controller found in Realtek * SoCs allows to access the PHY in raw mode, ie. bypassing the cache and paging engine * of the MDIO controller. E.g. for RTL838x this is 0xfff. * @@ -1655,9 +1655,9 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * when they are not attached to an Realtek SoC. The paradigm should be to keep the PHY * implementation bus independent. * - * As if this is not enough the PHYs consist of 8 ports that all can be programmed - * individually. Writing to port 0 can configure the whole why while other operations - * need to be replicated per port. + * As if this is not enough the PHY packages consist of 4 or 8 ports that all can be + * programmed individually. Some registers are only available on port 0 and configure + * the whole package. * * To bring all this together we need a tricky bus design that intercepts select page * calls but lets raw page accesses through. And especially knows how to handle raw @@ -1668,7 +1668,7 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * the accesses and the state of the bus with the attributes page[], raw[] and portaddr * of the bus_priv structure. The page selection works as follows: * - * phy_write(phydev, RTL821X_PAGE_SELECT, 12) : store internal page 12 in driver + * phy_write(phydev, RTMDIO_PAGE_SELECT, 12) : store internal page 12 in driver * phy_write(phydev, 7, 33) : write page=12, reg=7, val=33 * * or simply @@ -1677,8 +1677,8 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * * The port selection works as follows and must be called under a held mdio bus lock * - * __mdiobus_write(bus, RTL821X_PORT_SELECT, 4) : switch to port paddr - * __phy_write(phydev, RTL821X_PAGE_SELECT, 11) : store internal page 11 in driver + * __mdiobus_write(bus, RTMDIO_PORT_SELECT, 4) : switch to port 4 + * __phy_write(phydev, RTMDIO_PAGE_SELECT, 11) : store internal page 11 in driver * __phy_write(phydev, 8, 19) : write page=11, reg=8, val=19, port=4 * * Any Realtek PHY that will be connected to this bus must simply provide the standard @@ -1696,75 +1696,57 @@ static int rtl838x_set_link_ksettings(struct net_device *ndev, * return __phy_write(phydev, RTL821X_PAGE_SELECT, page); * } * - * In case there are non Realtek PHYs attached to the logic might need to be + * In case there are non Realtek PHYs attached to the bus the logic might need to be * reimplemented. For now it should be sufficient. */ -#define RTL821X_PAGE_SELECT 0x1f -#define RTL821X_PORT_SELECT 0x2000 -#define RTL838X_PAGE_RAW 0xfff -#define RTL839X_PAGE_RAW 0x1fff -#define RTL930X_PAGE_RAW 0xfff -#define RTL931X_PAGE_RAW 0x1fff -#define RTMDIO_READ 0x0 -#define RTMDIO_WRITE 0x1 +#define RTMDIO_PAGE_SELECT 0x1f +#define RTMDIO_PORT_SELECT 0x2000 +#define RTMDIO_READ 0x1 +#define RTMDIO_WRITE 0x2 +#define RTMDIO_ABS 0x4 +#define RTMDIO_PKG 0x8 /* - * Provide a generic read/write function so we can access multiple ports on a shared PHY - * package of the bus with separate addresses individually. This basically resembles the + * Provide a generic read/write function so we can access arbitrary ports on the bus. + * E.g. other ports of a PHY package on the bus. This basically resembles the kernel * phy_read_paged() and phy_write_paged() functions. To inform the bus that we are - * workin on a not default port (8, 16, 24, ...) we send a RTL821X_PORT_SELECT command - * at the beginning and the end to switch the port handling logic. + * working on a not default port send a RTMDIO_PORT_SELECT command at the beginning + * and the end to switch the port handling logic. */ -static int rtmdio_read_page(struct phy_device *phydev) -{ - if (WARN_ONCE(!phydev->drv->read_page, - "read_page callback not available, PHY driver not loaded?\n")) - return -EOPNOTSUPP; - - return phydev->drv->read_page(phydev); -} - -static int rtmdio_write_page(struct phy_device *phydev, int page) -{ - if (WARN_ONCE(!phydev->drv->write_page, - "write_page callback not available, PHY driver not loaded?\n")) - return -EOPNOTSUPP; - - return phydev->drv->write_page(phydev, page); -} - -static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, - int page, u32 regnum, u16 val) +static int rtmdio_access(struct phy_device *phydev, int op, int port, + int page, u32 regnum, u16 val) { int r, ret = 0, oldpage; - struct phy_package_shared *shared = phydev->shared; - if (!shared) - return -EIO; + if (op & RTMDIO_PKG) { + if (!phydev->shared) + return -EIO; + port = phydev->shared->base_addr + port; + } /* lock and inform bus about non default addressing */ phy_lock_mdio_bus(phydev); __mdiobus_write(phydev->mdio.bus, phydev->mdio.addr, - RTL821X_PORT_SELECT, shared->base_addr + port); + RTMDIO_PORT_SELECT, port); - oldpage = ret = rtmdio_read_page(phydev); + oldpage = ret = __phy_read(phydev, RTMDIO_PAGE_SELECT); if (oldpage >= 0 && oldpage != page) { - ret = rtmdio_write_page(phydev, page); + ret = __phy_write(phydev, RTMDIO_PAGE_SELECT, page); if (ret < 0) oldpage = ret; } if (oldpage >= 0) { - if (op == RTMDIO_WRITE) + if (op & RTMDIO_WRITE) ret = __phy_write(phydev, regnum, val); else ret = __phy_read(phydev, regnum); } if (oldpage >= 0) { - r = rtmdio_write_page(phydev, oldpage); + r = __phy_write(phydev, RTMDIO_PAGE_SELECT, oldpage); if (ret >= 0 && r < 0) ret = r; } else @@ -1772,7 +1754,7 @@ static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, /* reset bus to default adressing and unlock it */ __mdiobus_write(phydev->mdio.bus, phydev->mdio.addr, - RTL821X_PORT_SELECT, 0); + RTMDIO_PORT_SELECT, -1); phy_unlock_mdio_bus(phydev); return ret; @@ -1782,40 +1764,53 @@ static int rtmdio_package_rw(struct phy_device *phydev, int op, int port, * To make use of the shared package functions provide wrappers that align with kernel * naming conventions. The package() functions are useful to change settings on the * package as a whole. The package_port() functions will allow to target the PHYs - * individually. + * of a package individually. The port() only functions allow to access arbitrary ports + * on the bus through a PHY. */ int phy_package_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val) { - return rtmdio_package_rw(phydev, RTMDIO_WRITE, port, page, regnum, val); + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_PKG, port, page, regnum, val); } int phy_package_write_paged(struct phy_device *phydev, int page, u32 regnum, u16 val) { - return rtmdio_package_rw(phydev, RTMDIO_WRITE, 0, page, regnum, val); + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_PKG, 0, page, regnum, val); +} + +int phy_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val) +{ + return rtmdio_access(phydev, RTMDIO_WRITE | RTMDIO_ABS, port, page, regnum, val); } int phy_package_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum) { - return rtmdio_package_rw(phydev, RTMDIO_READ, port, page, regnum, 0); + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_PKG, port, page, regnum, 0); } int phy_package_read_paged(struct phy_device *phydev, int page, u32 regnum) { - return rtmdio_package_rw(phydev, RTMDIO_READ, 0, page, regnum, 0); + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_PKG, 0, page, regnum, 0); } -/* These are the core functions of our fancy Realtek SoC MDIO bus. */ +int phy_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum) +{ + return rtmdio_access(phydev, RTMDIO_READ | RTMDIO_ABS, port, page, regnum, 0); +} + +/* These are the core functions of our new Realtek SoC MDIO bus. */ static int rtmdio_read_c45(struct mii_bus *bus, int addr, int devnum, int regnum) { int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - err = (*bus_priv->read_mmd_phy)(portaddr, devnum, regnum, &val); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + err = (*bus_priv->read_mmd_phy)(addr, devnum, regnum, &val); pr_debug("rd_MMD(adr=%d, dev=%d, reg=%d) = %d, err = %d\n", - portaddr, devnum, regnum, val, err); + addr, devnum, regnum, val, err); return err ? err : val; } @@ -1824,21 +1819,23 @@ static int rtmdio_83xx_read(struct mii_bus *bus, int addr, int regnum) int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - if (portaddr >= 24 && portaddr <= 27 && eth_priv->id == 0x8380) - return rtl838x_read_sds_phy(portaddr, regnum); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; - if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[portaddr]) - return rtl839x_read_sds_phy(portaddr, regnum); + if (addr >= 24 && addr <= 27 && eth_priv->id == 0x8380) + return rtl838x_read_sds_phy(addr, regnum); - if (regnum == RTL821X_PAGE_SELECT && bus_priv->page[portaddr] != RTL838X_PAGE_RAW) - return bus_priv->page[portaddr]; + if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[addr]) + return rtl839x_read_sds_phy(addr, regnum); - bus_priv->raw[portaddr] = (bus_priv->page[portaddr] == RTL838X_PAGE_RAW); - err = (*bus_priv->read_phy)(portaddr, bus_priv->page[portaddr], regnum, &val); + if (regnum == RTMDIO_PAGE_SELECT && bus_priv->page[addr] != bus_priv->rawpage) + return bus_priv->page[addr]; + + bus_priv->raw[addr] = (bus_priv->page[addr] == bus_priv->rawpage); + err = (*bus_priv->read_phy)(addr, bus_priv->page[addr], regnum, &val); pr_debug("rd_PHY(adr=%d, pag=%d, reg=%d) = %d, err = %d\n", - portaddr, bus_priv->page[portaddr], regnum, val, err); + addr, bus_priv->page[addr], regnum, val, err); return err ? err : val; } @@ -1847,24 +1844,26 @@ static int rtmdio_93xx_read(struct mii_bus *bus, int addr, int regnum) int err, val; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - if (regnum == RTL821X_PAGE_SELECT && bus_priv->page[portaddr] != RTL930X_PAGE_RAW) - return bus_priv->page[portaddr]; + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + if (regnum == RTMDIO_PAGE_SELECT && bus_priv->page[addr] != bus_priv->rawpage) + return bus_priv->page[addr]; - bus_priv->raw[portaddr] = (bus_priv->page[portaddr] == RTL930X_PAGE_RAW); - if (eth_priv->phy_is_internal[portaddr]) { + bus_priv->raw[addr] = (bus_priv->page[addr] == bus_priv->rawpage); + if (eth_priv->phy_is_internal[addr]) { if (eth_priv->family_id == RTL9300_FAMILY_ID) - return rtl930x_read_sds_phy(eth_priv->sds_id[portaddr], - bus_priv->page[portaddr], regnum); + return rtl930x_read_sds_phy(eth_priv->sds_id[addr], + bus_priv->page[addr], regnum); else - return rtl931x_read_sds_phy(eth_priv->sds_id[portaddr], - bus_priv->page[portaddr], regnum); + return rtl931x_read_sds_phy(eth_priv->sds_id[addr], + bus_priv->page[addr], regnum); } - err = (*bus_priv->read_phy)(portaddr, bus_priv->page[portaddr], regnum, &val); + err = (*bus_priv->read_phy)(addr, bus_priv->page[addr], regnum, &val); pr_debug("rd_PHY(adr=%d, pag=%d, reg=%d) = %d, err = %d\n", - portaddr, bus_priv->page[portaddr], regnum, val, err); + addr, bus_priv->page[addr], regnum, val, err); return err ? err : val; } @@ -1872,83 +1871,91 @@ static int rtmdio_write_c45(struct mii_bus *bus, int addr, int devnum, int regnu { int err; struct rtl838x_bus_priv *bus_priv = bus->priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - err = (*bus_priv->write_mmd_phy)(portaddr, devnum, regnum, val); + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + + err = (*bus_priv->write_mmd_phy)(addr, devnum, regnum, val); pr_debug("wr_MMD(adr=%d, dev=%d, reg=%d, val=%d) err = %d\n", - portaddr, devnum, regnum, val, err); + addr, devnum, regnum, val, err); return err; } static int rtmdio_83xx_write(struct mii_bus *bus, int addr, int regnum, u16 val) { + int err, page, offset = 0; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - int err, page = bus_priv->page[portaddr], offset = 0; - if (regnum == RTL821X_PORT_SELECT) { - bus_priv->portaddr = val; + if (regnum == RTMDIO_PORT_SELECT) { + bus_priv->extaddr = (s16)val; return 0; } - if (portaddr >= 24 && portaddr <= 27 && eth_priv->id == 0x8380) { - if (portaddr == 26) + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + page = bus_priv->page[addr]; + + if (addr >= 24 && addr <= 27 && eth_priv->id == 0x8380) { + if (addr == 26) offset = 0x100; sw_w32(val, RTL838X_SDS4_FIB_REG0 + offset + (regnum << 2)); return 0; } - if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[portaddr]) - return rtl839x_write_sds_phy(portaddr, regnum, val); + if (eth_priv->family_id == RTL8390_FAMILY_ID && eth_priv->phy_is_internal[addr]) + return rtl839x_write_sds_phy(addr, regnum, val); - if (regnum == RTL821X_PAGE_SELECT) - bus_priv->page[portaddr] = val; + if (regnum == RTMDIO_PAGE_SELECT) + bus_priv->page[addr] = val; - if (!bus_priv->raw[portaddr] && (regnum != RTL821X_PAGE_SELECT || page == RTL838X_PAGE_RAW)) { - bus_priv->raw[portaddr] = (page == RTL838X_PAGE_RAW); - err = (*bus_priv->write_phy)(portaddr, page, regnum, val); + if (!bus_priv->raw[addr] && (regnum != RTMDIO_PAGE_SELECT || page == bus_priv->rawpage)) { + bus_priv->raw[addr] = (page == bus_priv->rawpage); + err = (*bus_priv->write_phy)(addr, page, regnum, val); pr_debug("wr_PHY(adr=%d, pag=%d, reg=%d, val=%d) err = %d\n", - portaddr, page, regnum, val, err); + addr, page, regnum, val, err); return err; } - bus_priv->raw[portaddr] = false; + bus_priv->raw[addr] = false; return 0; } static int rtmdio_93xx_write(struct mii_bus *bus, int addr, int regnum, u16 val) { + int err, page; struct rtl838x_bus_priv *bus_priv = bus->priv; struct rtl838x_eth_priv *eth_priv = bus_priv->eth_priv; - int portaddr = bus_priv->portaddr ? bus_priv->portaddr : addr; - int err, page = bus_priv->page[portaddr]; - if (regnum == RTL821X_PORT_SELECT) { - bus_priv->portaddr = val; + if (regnum == RTMDIO_PORT_SELECT) { + bus_priv->extaddr = (s16)val; return 0; } - if (regnum == RTL821X_PAGE_SELECT) - bus_priv->page[portaddr] = val; + if (bus_priv->extaddr >= 0) + addr = bus_priv->extaddr; + page = bus_priv->page[addr]; + + if (regnum == RTMDIO_PAGE_SELECT) + bus_priv->page[addr] = val; - if (!bus_priv->raw[portaddr] && (regnum != RTL821X_PAGE_SELECT || page == RTL930X_PAGE_RAW)) { - bus_priv->raw[portaddr] = (page == RTL930X_PAGE_RAW); - if (eth_priv->phy_is_internal[portaddr]) { + if (!bus_priv->raw[addr] && (regnum != RTMDIO_PAGE_SELECT || page == bus_priv->rawpage)) { + bus_priv->raw[addr] = (page == bus_priv->rawpage); + if (eth_priv->phy_is_internal[addr]) { if (eth_priv->family_id == RTL9300_FAMILY_ID) - return rtl930x_write_sds_phy(eth_priv->sds_id[portaddr], + return rtl930x_write_sds_phy(eth_priv->sds_id[addr], page, regnum, val); else - return rtl931x_write_sds_phy(eth_priv->sds_id[portaddr], + return rtl931x_write_sds_phy(eth_priv->sds_id[addr], page, regnum, val); } - err = (*bus_priv->write_phy)(portaddr, page, regnum, val); + err = (*bus_priv->write_phy)(addr, page, regnum, val); pr_debug("wr_PHY(adr=%d, pag=%d, reg=%d, val=%d) err = %d\n", - portaddr, page, regnum, val, err); + addr, page, regnum, val, err); } - bus_priv->raw[portaddr] = false; + bus_priv->raw[addr] = false; return 0; } @@ -2217,7 +2224,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->page[i] = 0; bus_priv->raw[i] = false; } - bus_priv->portaddr = 0; + bus_priv->extaddr = -1; switch(priv->family_id) { case RTL8380_FAMILY_ID: @@ -2229,6 +2236,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl838x_write_mmd_phy; bus_priv->read_phy = rtl838x_read_phy; bus_priv->write_phy = rtl838x_write_phy; + bus_priv->rawpage = 0xfff; break; case RTL8390_FAMILY_ID: priv->mii_bus->name = "rtl839x-eth-mdio"; @@ -2239,6 +2247,7 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl839x_write_mmd_phy; bus_priv->read_phy = rtl839x_read_phy; bus_priv->write_phy = rtl839x_write_phy; + bus_priv->rawpage = 0x1fff; break; case RTL9300_FAMILY_ID: priv->mii_bus->name = "rtl930x-eth-mdio"; @@ -2249,16 +2258,18 @@ static int rtl838x_mdio_init(struct rtl838x_eth_priv *priv) bus_priv->write_mmd_phy = rtl930x_write_mmd_phy; bus_priv->read_phy = rtl930x_read_phy; bus_priv->write_phy = rtl930x_write_phy; + bus_priv->rawpage = 0xfff; break; case RTL9310_FAMILY_ID: priv->mii_bus->name = "rtl931x-eth-mdio"; priv->mii_bus->read = rtmdio_93xx_read; priv->mii_bus->write = rtmdio_93xx_write; - priv->mii_bus->reset = rtmdio_931x_reset; + priv->mii_bus->reset = rtmdio_931x_reset; bus_priv->read_mmd_phy = rtl931x_read_mmd_phy; bus_priv->write_mmd_phy = rtl931x_write_mmd_phy; bus_priv->read_phy = rtl931x_read_phy; bus_priv->write_phy = rtl931x_write_phy; + bus_priv->rawpage = 0x1fff; break; } priv->mii_bus->read_c45 = rtmdio_read_c45; diff --git a/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.h b/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.h index 0f49eae23da1e5..d6d88fc2ed01b8 100644 --- a/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.h +++ b/target/linux/realtek/files-6.6/drivers/net/ethernet/rtl838x_eth.h @@ -410,7 +410,8 @@ struct dsa_tag; struct rtl838x_bus_priv { struct rtl838x_eth_priv *eth_priv; - int portaddr; + int extaddr; + int rawpage; int page[64]; bool raw[64]; int (*read_mmd_phy)(u32 port, u32 addr, u32 reg, u32 *val); diff --git a/target/linux/realtek/files-6.6/drivers/net/phy/rtl83xx-phy.c b/target/linux/realtek/files-6.6/drivers/net/phy/rtl83xx-phy.c index 0c8b1dfd4dcd27..df5e2e444067ab 100644 --- a/target/linux/realtek/files-6.6/drivers/net/phy/rtl83xx-phy.c +++ b/target/linux/realtek/files-6.6/drivers/net/phy/rtl83xx-phy.c @@ -22,8 +22,10 @@ extern struct rtl83xx_soc_info soc_info; extern struct mutex smi_lock; extern int phy_package_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val); extern int phy_package_write_paged(struct phy_device *phydev, int page, u32 regnum, u16 val); +extern int phy_port_write_paged(struct phy_device *phydev, int port, int page, u32 regnum, u16 val); extern int phy_package_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum); extern int phy_package_read_paged(struct phy_device *phydev, int page, u32 regnum); +extern int phy_port_read_paged(struct phy_device *phydev, int port, int page, u32 regnum); #define PHY_PAGE_2 2 #define PHY_PAGE_4 4 diff --git a/target/linux/realtek/image/rtl838x.mk b/target/linux/realtek/image/rtl838x.mk index 05574e5375d68f..c44e3a74f7ecca 100644 --- a/target/linux/realtek/image/rtl838x.mk +++ b/target/linux/realtek/image/rtl838x.mk @@ -71,7 +71,7 @@ define Device/d-link_dgs-1210-28mp-f SOC := rtl8382 DEVICE_MODEL := DGS-1210-28MP DEVICE_VARIANT := F - DEVICE_PACKAGES += realtek-poe + DEVICE_PACKAGES += realtek-poe kmod-hwmon-lm63 endef TARGET_DEVICES += d-link_dgs-1210-28mp-f