ramips: remove Linux 5.4 support
We're at 5.10 stable, this can finally go. Signed-off-by: Rui Salvaterra <rsalvaterra@gmail.com>
This commit is contained in:
		| @@ -1,195 +0,0 @@ | |||||||
| CONFIG_AR8216_PHY=y |  | ||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_AT803X_PHY=y |  | ||||||
| CONFIG_BLK_MQ_PCI=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CEVT_SYSTICK_QUIRK=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLKEVT_RT3352=y |  | ||||||
| CONFIG_CLKSRC_MMIO=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=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_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DEBUG_PINCTRL=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_MT7620A_EVAL is not set |  | ||||||
| # CONFIG_DTB_OMEGA2P is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| # CONFIG_DTB_VOCORE2 is not set |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| CONFIG_ETHERNET_PACKET_MANGLE=y |  | ||||||
| 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_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_PHY=y |  | ||||||
| CONFIG_GENERIC_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| # CONFIG_GPIO_MT7621 is not set |  | ||||||
| CONFIG_GPIO_RALINK=y |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_ICPLUS_PHY=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_INTC=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_MARVELL_PHY=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MFD_SYSCON=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=5 |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| # CONFIG_MT7621_WDT is not set |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS_LIMIT=16384 |  | ||||||
| CONFIG_MTD_SPLIT_JIMAGE_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_SEAMA_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_TPLINK_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_MTD_VIRT_CONCAT=y |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NEED_PER_CPU_KM=y |  | ||||||
| CONFIG_NET_RALINK_GSW_MT7620=y |  | ||||||
| CONFIG_NET_RALINK_MDIO=y |  | ||||||
| CONFIG_NET_RALINK_MDIO_MT7620=y |  | ||||||
| CONFIG_NET_RALINK_MT7620=y |  | ||||||
| # CONFIG_NET_RALINK_RT3050 is not set |  | ||||||
| CONFIG_NET_RALINK_SOC=y |  | ||||||
| # CONFIG_NET_VENDOR_MEDIATEK is not set |  | ||||||
| CONFIG_NET_VENDOR_RALINK=y |  | ||||||
| CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PCI=y |  | ||||||
| CONFIG_PCI_DOMAINS=y |  | ||||||
| CONFIG_PCI_DRIVERS_LEGACY=y |  | ||||||
| # CONFIG_PCI_MT7621 is not set |  | ||||||
| # CONFIG_PCI_MT7621_PHY is not set |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| CONFIG_PHY_RALINK_USB=y |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| # CONFIG_PINCTRL_AW9523 is not set |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| CONFIG_RALINK_WDT=y |  | ||||||
| CONFIG_REGMAP=y |  | ||||||
| CONFIG_REGMAP_MMIO=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_SERIAL_8250_RT288X=y |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| CONFIG_SOC_MT7620=y |  | ||||||
| # CONFIG_SOC_MT7621 is not set |  | ||||||
| # CONFIG_SOC_RT288X is not set |  | ||||||
| # CONFIG_SOC_RT305X is not set |  | ||||||
| # CONFIG_SOC_RT3883 is not set |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| # CONFIG_SPI_MT7621 is not set |  | ||||||
| CONFIG_SPI_RT2880=y |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWCONFIG=y |  | ||||||
| CONFIG_SWCONFIG_LEDS=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TIMER_OF=y |  | ||||||
| CONFIG_TIMER_PROBE=y |  | ||||||
| CONFIG_TINY_SRCU=y |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
| @@ -1,282 +0,0 @@ | |||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_AT803X_PHY=y |  | ||||||
| CONFIG_BLK_MQ_PCI=y |  | ||||||
| CONFIG_BOARD_SCACHE=y |  | ||||||
| CONFIG_BOUNCE=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLKSRC_MIPS_GIC=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMMON_CLK=y |  | ||||||
| # CONFIG_COMMON_CLK_BOSTON is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=y |  | ||||||
| CONFIG_CPU_MIPSR2_IRQ_EI=y |  | ||||||
| CONFIG_CPU_MIPSR2_IRQ_VI=y |  | ||||||
| CONFIG_CPU_NEEDS_NO_SMARTMIPS_OR_MICROMIPS=y |  | ||||||
| CONFIG_CPU_R4K_CACHE_TLB=y |  | ||||||
| CONFIG_CPU_RMAP=y |  | ||||||
| CONFIG_CPU_SUPPORTS_32BIT_KERNEL=y |  | ||||||
| CONFIG_CPU_SUPPORTS_HIGHMEM=y |  | ||||||
| CONFIG_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRC16=y |  | ||||||
| CONFIG_CRYPTO_ACOMP2=y |  | ||||||
| CONFIG_CRYPTO_AEAD=y |  | ||||||
| CONFIG_CRYPTO_AEAD2=y |  | ||||||
| CONFIG_CRYPTO_DEFLATE=y |  | ||||||
| CONFIG_CRYPTO_HASH2=y |  | ||||||
| CONFIG_CRYPTO_HASH_INFO=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_LZO=y |  | ||||||
| CONFIG_CRYPTO_MANAGER=y |  | ||||||
| CONFIG_CRYPTO_MANAGER2=y |  | ||||||
| CONFIG_CRYPTO_NULL2=y |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DEBUG_PINCTRL=y |  | ||||||
| CONFIG_DIMLIB=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_GNUBEE1 is not set |  | ||||||
| # CONFIG_DTB_GNUBEE2 is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| CONFIG_FIXED_PHY=y |  | ||||||
| CONFIG_FW_LOADER_PAGED_BUF=y |  | ||||||
| CONFIG_GENERIC_ATOMIC64=y |  | ||||||
| CONFIG_GENERIC_CLOCKEVENTS=y |  | ||||||
| CONFIG_GENERIC_CLOCKEVENTS_BROADCAST=y |  | ||||||
| CONFIG_GENERIC_CMOS_UPDATE=y |  | ||||||
| CONFIG_GENERIC_CPU_AUTOPROBE=y |  | ||||||
| CONFIG_GENERIC_GETTIMEOFDAY=y |  | ||||||
| CONFIG_GENERIC_IOMAP=y |  | ||||||
| CONFIG_GENERIC_IRQ_CHIP=y |  | ||||||
| CONFIG_GENERIC_IRQ_EFFECTIVE_AFF_MASK=y |  | ||||||
| CONFIG_GENERIC_IRQ_IPI=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_PHY=y |  | ||||||
| CONFIG_GENERIC_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| CONFIG_GPIOLIB_IRQCHIP=y |  | ||||||
| CONFIG_GPIO_GENERIC=y |  | ||||||
| CONFIG_GPIO_MT7621=y |  | ||||||
| # CONFIG_GPIO_RALINK is not set |  | ||||||
| CONFIG_GPIO_WATCHDOG=y |  | ||||||
| # CONFIG_GPIO_WATCHDOG_ARCH_INITCALL is not set |  | ||||||
| CONFIG_GRO_CELLS=y |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HIGHMEM=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_I2C=y |  | ||||||
| CONFIG_I2C_BOARDINFO=y |  | ||||||
| CONFIG_I2C_CHARDEV=y |  | ||||||
| CONFIG_I2C_GPIO=y |  | ||||||
| CONFIG_I2C_MT7621=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_DOMAIN_HIERARCHY=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LED_TRIGGER_PHY=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_LZO_COMPRESS=y |  | ||||||
| CONFIG_LZO_DECOMPRESS=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MFD_SYSCON=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIKROTIK=y |  | ||||||
| CONFIG_MIKROTIK_RB_SYSFS=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| CONFIG_MIPS_CM=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| CONFIG_MIPS_CPC=y |  | ||||||
| CONFIG_MIPS_CPS=y |  | ||||||
| # CONFIG_MIPS_CPS_NS16550_BOOL is not set |  | ||||||
| CONFIG_MIPS_CPU_SCACHE=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_GIC=y |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=5 |  | ||||||
| CONFIG_MIPS_MT=y |  | ||||||
| CONFIG_MIPS_MT_FPAFF=y |  | ||||||
| CONFIG_MIPS_MT_SMP=y |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_NR_CPU_NR_MAP=4 |  | ||||||
| CONFIG_MIPS_PERF_SHARED_TC_COUNTERS=y |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| CONFIG_MT7621_WDT=y |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_NAND_CORE=y |  | ||||||
| CONFIG_MTD_NAND_ECC_SW_HAMMING=y |  | ||||||
| CONFIG_MTD_NAND_MT7621=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_RAW_NAND=y |  | ||||||
| CONFIG_MTD_ROUTERBOOT_PARTS=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPLIT_FIT_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_MINOR_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_SEAMA_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_TPLINK_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_TRX_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_MTD_UBI=y |  | ||||||
| CONFIG_MTD_UBI_BEB_LIMIT=20 |  | ||||||
| CONFIG_MTD_UBI_BLOCK=y |  | ||||||
| CONFIG_MTD_UBI_WL_THRESHOLD=4096 |  | ||||||
| CONFIG_MTD_VIRT_CONCAT=y |  | ||||||
| # CONFIG_MTK_HSDMA is not set |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NET_DEVLINK=y |  | ||||||
| CONFIG_NET_DSA=y |  | ||||||
| CONFIG_NET_DSA_MT7530=y |  | ||||||
| CONFIG_NET_DSA_TAG_MTK=y |  | ||||||
| CONFIG_NET_FLOW_LIMIT=y |  | ||||||
| CONFIG_NET_MEDIATEK_SOC=y |  | ||||||
| CONFIG_NET_SWITCHDEV=y |  | ||||||
| CONFIG_NET_VENDOR_MEDIATEK=y |  | ||||||
| # CONFIG_NET_VENDOR_RALINK is not set |  | ||||||
| CONFIG_NR_CPUS=4 |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PADATA=y |  | ||||||
| CONFIG_PCI=y |  | ||||||
| CONFIG_PCI_DISABLE_COMMON_QUIRKS=y |  | ||||||
| CONFIG_PCI_DOMAINS=y |  | ||||||
| CONFIG_PCI_DOMAINS_GENERIC=y |  | ||||||
| CONFIG_PCI_DRIVERS_GENERIC=y |  | ||||||
| CONFIG_PCI_MT7621=y |  | ||||||
| CONFIG_PCI_MT7621_PHY=y |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| CONFIG_PHYLINK=y |  | ||||||
| # CONFIG_PHY_RALINK_USB is not set |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| CONFIG_PINCTRL_AW9523=y |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| CONFIG_PINCTRL_SX150X=y |  | ||||||
| CONFIG_POWER_RESET=y |  | ||||||
| CONFIG_POWER_RESET_GPIO=y |  | ||||||
| CONFIG_POWER_SUPPLY=y |  | ||||||
| CONFIG_QUEUED_RWLOCKS=y |  | ||||||
| CONFIG_QUEUED_SPINLOCKS=y |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| # CONFIG_RALINK_WDT is not set |  | ||||||
| CONFIG_RATIONAL=y |  | ||||||
| CONFIG_REGMAP=y |  | ||||||
| CONFIG_REGMAP_MMIO=y |  | ||||||
| CONFIG_REGULATOR=y |  | ||||||
| CONFIG_REGULATOR_FIXED_VOLTAGE=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_RFS_ACCEL=y |  | ||||||
| CONFIG_RPS=y |  | ||||||
| CONFIG_RTC_CLASS=y |  | ||||||
| CONFIG_RTC_DRV_BQ32K=y |  | ||||||
| CONFIG_RTC_DRV_PCF8563=y |  | ||||||
| CONFIG_RTC_I2C_AND_SPI=y |  | ||||||
| CONFIG_RTC_MC146818_LIB=y |  | ||||||
| CONFIG_SCHED_SMT=y |  | ||||||
| CONFIG_SERIAL_8250_NR_UARTS=3 |  | ||||||
| CONFIG_SERIAL_8250_RUNTIME_UARTS=3 |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| CONFIG_SGL_ALLOC=y |  | ||||||
| CONFIG_SMP=y |  | ||||||
| CONFIG_SMP_UP=y |  | ||||||
| # CONFIG_SOC_MT7620 is not set |  | ||||||
| CONFIG_SOC_MT7621=y |  | ||||||
| # CONFIG_SOC_RT288X is not set |  | ||||||
| # CONFIG_SOC_RT305X is not set |  | ||||||
| # CONFIG_SOC_RT3883 is not set |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| CONFIG_SPI_MT7621=y |  | ||||||
| # CONFIG_SPI_RT2880 is not set |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYNC_R4K=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_HOTPLUG_CPU=y |  | ||||||
| CONFIG_SYS_SUPPORTS_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS_CPS=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MULTITHREADING=y |  | ||||||
| CONFIG_SYS_SUPPORTS_SCHED_SMT=y |  | ||||||
| CONFIG_SYS_SUPPORTS_SMP=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TIMER_OF=y |  | ||||||
| CONFIG_TIMER_PROBE=y |  | ||||||
| CONFIG_TREE_RCU=y |  | ||||||
| CONFIG_TREE_SRCU=y |  | ||||||
| CONFIG_UBIFS_FS=y |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
| CONFIG_WEAK_ORDERING=y |  | ||||||
| CONFIG_WEAK_REORDERING_BEYOND_LLSC=y |  | ||||||
| CONFIG_XPS=y |  | ||||||
| CONFIG_ZLIB_DEFLATE=y |  | ||||||
| CONFIG_ZLIB_INFLATE=y |  | ||||||
| @@ -1,192 +0,0 @@ | |||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_AT803X_PHY=y |  | ||||||
| CONFIG_BLK_MQ_PCI=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CEVT_SYSTICK_QUIRK=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLKEVT_RT3352=y |  | ||||||
| CONFIG_CLKSRC_MMIO=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=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_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DEBUG_PINCTRL=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_MT7620A_EVAL is not set |  | ||||||
| # CONFIG_DTB_OMEGA2P is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| # CONFIG_DTB_VOCORE2 is not set |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| 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_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_PHY=y |  | ||||||
| CONFIG_GENERIC_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| CONFIG_GPIOLIB_IRQCHIP=y |  | ||||||
| CONFIG_GPIO_GENERIC=y |  | ||||||
| CONFIG_GPIO_MT7621=y |  | ||||||
| # CONFIG_GPIO_RALINK is not set |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_ICPLUS_PHY=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_INTC=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MFD_SYSCON=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=5 |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| CONFIG_MT7621_WDT=y |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPLIT_TPLINK_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_TRX_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NEED_PER_CPU_KM=y |  | ||||||
| CONFIG_NET_RALINK_ESW_RT3050=y |  | ||||||
| # CONFIG_NET_RALINK_MT7620 is not set |  | ||||||
| CONFIG_NET_RALINK_RT3050=y |  | ||||||
| CONFIG_NET_RALINK_SOC=y |  | ||||||
| # CONFIG_NET_VENDOR_MEDIATEK is not set |  | ||||||
| CONFIG_NET_VENDOR_RALINK=y |  | ||||||
| CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PCI=y |  | ||||||
| CONFIG_PCI_DOMAINS=y |  | ||||||
| CONFIG_PCI_DRIVERS_LEGACY=y |  | ||||||
| # CONFIG_PCI_MT7621 is not set |  | ||||||
| # CONFIG_PCI_MT7621_PHY is not set |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| CONFIG_PHY_RALINK_USB=y |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| # CONFIG_PINCTRL_AW9523 is not set |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| # CONFIG_PWM_MEDIATEK is not set |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| # CONFIG_RALINK_WDT is not set |  | ||||||
| CONFIG_REGMAP=y |  | ||||||
| CONFIG_REGMAP_MMIO=y |  | ||||||
| CONFIG_REGULATOR=y |  | ||||||
| CONFIG_REGULATOR_FIXED_VOLTAGE=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_SERIAL_8250_NR_UARTS=3 |  | ||||||
| CONFIG_SERIAL_8250_RUNTIME_UARTS=3 |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| CONFIG_SOC_MT7620=y |  | ||||||
| # CONFIG_SOC_MT7621 is not set |  | ||||||
| # CONFIG_SOC_RT288X is not set |  | ||||||
| # CONFIG_SOC_RT305X is not set |  | ||||||
| # CONFIG_SOC_RT3883 is not set |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| CONFIG_SPI_MT7621=y |  | ||||||
| # CONFIG_SPI_RT2880 is not set |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWCONFIG=y |  | ||||||
| CONFIG_SWCONFIG_LEDS=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TIMER_OF=y |  | ||||||
| CONFIG_TIMER_PROBE=y |  | ||||||
| CONFIG_TINY_SRCU=y |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
| @@ -1,192 +0,0 @@ | |||||||
| From: Paul Burton <paul.burton@mips.com> |  | ||||||
| Date: Wed, 9 Oct 2019 23:09:45 +0000 |  | ||||||
| Subject: MIPS: cmdline: Clean up boot_command_line initialization |  | ||||||
|  |  | ||||||
| Our current code to initialize boot_command_line is a mess. Some of this |  | ||||||
| is due to the addition of too many options over the years, and some of |  | ||||||
| this is due to workarounds for early_init_dt_scan_chosen() performing |  | ||||||
| actions specific to options from other architectures that probably |  | ||||||
| shouldn't be in generic code. |  | ||||||
|  |  | ||||||
| Clean this up by introducing a new bootcmdline_init() function that |  | ||||||
| simplifies the initialization somewhat. The major changes are: |  | ||||||
|  |  | ||||||
| - Because bootcmdline_init() is a function it can return early in the |  | ||||||
|   CONFIG_CMDLINE_OVERRIDE case. |  | ||||||
|  |  | ||||||
| - We clear boot_command_line rather than inheriting whatever |  | ||||||
|   early_init_dt_scan_chosen() may have left us. This means we no longer |  | ||||||
|   need to set boot_command_line to a space character in an attempt to |  | ||||||
|   prevent early_init_dt_scan_chosen() from copying CONFIG_CMDLINE into |  | ||||||
|   boot_command_line without us knowing about it. |  | ||||||
|  |  | ||||||
| - Indirection via USE_PROM_CMDLINE, USE_DTB_CMDLINE, EXTEND_WITH_PROM & |  | ||||||
|   BUILTIN_EXTEND_WITH_PROM macros is removed; they seemingly served only |  | ||||||
|   to obfuscate the code. |  | ||||||
|  |  | ||||||
| - The logic is cleaner, clearer & commented. |  | ||||||
|  |  | ||||||
| Two minor drawbacks of this approach are: |  | ||||||
|  |  | ||||||
| 1) We call of_scan_flat_dt(), which means we scan through the DT again. |  | ||||||
|    The overhead is fairly minimal & shouldn't be noticeable. |  | ||||||
|  |  | ||||||
| 2) cmdline_scan_chosen() duplicates a small amount of the logic from |  | ||||||
|    early_init_dt_scan_chosen(). Alternatives might be to allow the |  | ||||||
|    generic FDT code to keep & expose a copy of the arguments taken from |  | ||||||
|    the /chosen node's bootargs property, or to introduce a function like |  | ||||||
|    early_init_dt_scan_chosen() that retrieves them without modification |  | ||||||
|    to handle CONFIG_CMDLINE. Neither of these sounds particularly |  | ||||||
|    cleaner though, and this way we at least keep the extra work in |  | ||||||
|    arch/mips. |  | ||||||
|  |  | ||||||
| Origin: upstream, https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=7784cac697351f0cc0a4bb619594c0c99348c5aa |  | ||||||
| Signed-off-by: Paul Burton <paul.burton@mips.com> |  | ||||||
| Cc: linux-mips@vger.kernel.org |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/setup.c |  | ||||||
| +++ b/arch/mips/kernel/setup.c |  | ||||||
| @@ -538,11 +538,88 @@ static void __init check_kernel_sections |  | ||||||
|  	} |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -#define USE_PROM_CMDLINE	IS_ENABLED(CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER) |  | ||||||
| -#define USE_DTB_CMDLINE		IS_ENABLED(CONFIG_MIPS_CMDLINE_FROM_DTB) |  | ||||||
| -#define EXTEND_WITH_PROM	IS_ENABLED(CONFIG_MIPS_CMDLINE_DTB_EXTEND) |  | ||||||
| -#define BUILTIN_EXTEND_WITH_PROM	\ |  | ||||||
| -	IS_ENABLED(CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND) |  | ||||||
| +static void __init bootcmdline_append(const char *s, size_t max) |  | ||||||
| +{ |  | ||||||
| +	if (!s[0] || !max) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	if (boot_command_line[0]) |  | ||||||
| +		strlcat(boot_command_line, " ", COMMAND_LINE_SIZE); |  | ||||||
| + |  | ||||||
| +	strlcat(boot_command_line, s, max); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int __init bootcmdline_scan_chosen(unsigned long node, const char *uname, |  | ||||||
| +					  int depth, void *data) |  | ||||||
| +{ |  | ||||||
| +	bool *dt_bootargs = data; |  | ||||||
| +	const char *p; |  | ||||||
| +	int l; |  | ||||||
| + |  | ||||||
| +	if (depth != 1 || !data || |  | ||||||
| +	    (strcmp(uname, "chosen") != 0 && strcmp(uname, "chosen@0") != 0)) |  | ||||||
| +		return 0; |  | ||||||
| + |  | ||||||
| +	p = of_get_flat_dt_prop(node, "bootargs", &l); |  | ||||||
| +	if (p != NULL && l > 0) { |  | ||||||
| +		bootcmdline_append(p, min(l, COMMAND_LINE_SIZE)); |  | ||||||
| +		*dt_bootargs = true; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return 1; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void __init bootcmdline_init(char **cmdline_p) |  | ||||||
| +{ |  | ||||||
| +	bool dt_bootargs = false; |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * If CMDLINE_OVERRIDE is enabled then initializing the command line is |  | ||||||
| +	 * trivial - we simply use the built-in command line unconditionally & |  | ||||||
| +	 * unmodified. |  | ||||||
| +	 */ |  | ||||||
| +	if (IS_ENABLED(CONFIG_CMDLINE_OVERRIDE)) { |  | ||||||
| +		strlcpy(boot_command_line, builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| +		return; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * If the user specified a built-in command line & |  | ||||||
| +	 * MIPS_CMDLINE_BUILTIN_EXTEND, then the built-in command line is |  | ||||||
| +	 * prepended to arguments from the bootloader or DT so we'll copy them |  | ||||||
| +	 * to the start of boot_command_line here. Otherwise, empty |  | ||||||
| +	 * boot_command_line to undo anything early_init_dt_scan_chosen() did. |  | ||||||
| +	 */ |  | ||||||
| +	if (IS_ENABLED(CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND)) |  | ||||||
| +		strlcpy(boot_command_line, builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| +	else |  | ||||||
| +		boot_command_line[0] = 0; |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * If we're configured to take boot arguments from DT, look for those |  | ||||||
| +	 * now. |  | ||||||
| +	 */ |  | ||||||
| +	if (IS_ENABLED(CONFIG_MIPS_CMDLINE_FROM_DTB)) |  | ||||||
| +		of_scan_flat_dt(bootcmdline_scan_chosen, &dt_bootargs); |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * If we didn't get any arguments from DT (regardless of whether that's |  | ||||||
| +	 * because we weren't configured to look for them, or because we looked |  | ||||||
| +	 * & found none) then we'll take arguments from the bootloader. |  | ||||||
| +	 * plat_mem_setup() should have filled arcs_cmdline with arguments from |  | ||||||
| +	 * the bootloader. |  | ||||||
| +	 */ |  | ||||||
| +	if (IS_ENABLED(CONFIG_MIPS_CMDLINE_DTB_EXTEND) || !dt_bootargs) |  | ||||||
| +		bootcmdline_append(arcs_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * If the user specified a built-in command line & we didn't already |  | ||||||
| +	 * prepend it, we append it to boot_command_line here. |  | ||||||
| +	 */ |  | ||||||
| +	if (IS_ENABLED(CONFIG_CMDLINE_BOOL) && |  | ||||||
| +	    !IS_ENABLED(CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND)) |  | ||||||
| +		bootcmdline_append(builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| +} |  | ||||||
|   |  | ||||||
|  /* |  | ||||||
|   * arch_mem_init - initialize memory management subsystem |  | ||||||
| @@ -570,48 +647,12 @@ static void __init arch_mem_init(char ** |  | ||||||
|  { |  | ||||||
|  	extern void plat_mem_setup(void); |  | ||||||
|   |  | ||||||
| -	/* |  | ||||||
| -	 * Initialize boot_command_line to an innocuous but non-empty string in |  | ||||||
| -	 * order to prevent early_init_dt_scan_chosen() from copying |  | ||||||
| -	 * CONFIG_CMDLINE into it without our knowledge. We handle |  | ||||||
| -	 * CONFIG_CMDLINE ourselves below & don't want to duplicate its |  | ||||||
| -	 * content because repeating arguments can be problematic. |  | ||||||
| -	 */ |  | ||||||
| -	strlcpy(boot_command_line, " ", COMMAND_LINE_SIZE); |  | ||||||
| - |  | ||||||
|  	/* call board setup routine */ |  | ||||||
|  	plat_mem_setup(); |  | ||||||
|  	memblock_set_bottom_up(true); |  | ||||||
|   |  | ||||||
| -#if defined(CONFIG_CMDLINE_BOOL) && defined(CONFIG_CMDLINE_OVERRIDE) |  | ||||||
| -	strlcpy(boot_command_line, builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| -#else |  | ||||||
| -	if ((USE_PROM_CMDLINE && arcs_cmdline[0]) || |  | ||||||
| -	    (USE_DTB_CMDLINE && !boot_command_line[0])) |  | ||||||
| -		strlcpy(boot_command_line, arcs_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| - |  | ||||||
| -	if (EXTEND_WITH_PROM && arcs_cmdline[0]) { |  | ||||||
| -		if (boot_command_line[0]) |  | ||||||
| -			strlcat(boot_command_line, " ", COMMAND_LINE_SIZE); |  | ||||||
| -		strlcat(boot_command_line, arcs_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| -	} |  | ||||||
| - |  | ||||||
| -#if defined(CONFIG_CMDLINE_BOOL) |  | ||||||
| -	if (builtin_cmdline[0]) { |  | ||||||
| -		if (boot_command_line[0]) |  | ||||||
| -			strlcat(boot_command_line, " ", COMMAND_LINE_SIZE); |  | ||||||
| -		strlcat(boot_command_line, builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| -	} |  | ||||||
| - |  | ||||||
| -	if (BUILTIN_EXTEND_WITH_PROM && arcs_cmdline[0]) { |  | ||||||
| -		if (boot_command_line[0]) |  | ||||||
| -			strlcat(boot_command_line, " ", COMMAND_LINE_SIZE); |  | ||||||
| -		strlcat(boot_command_line, arcs_cmdline, COMMAND_LINE_SIZE); |  | ||||||
| -	} |  | ||||||
| -#endif |  | ||||||
| -#endif |  | ||||||
| +	bootcmdline_init(cmdline_p); |  | ||||||
|  	strlcpy(command_line, boot_command_line, COMMAND_LINE_SIZE); |  | ||||||
| - |  | ||||||
|  	*cmdline_p = command_line; |  | ||||||
|   |  | ||||||
|  	parse_early_param(); |  | ||||||
| @@ -1,44 +0,0 @@ | |||||||
| From b7340422cc16c5deff100812f38114bb5ec81203 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Paul Burton <paul.burton@mips.com> |  | ||||||
| Date: Sat, 12 Oct 2019 20:43:36 +0000 |  | ||||||
| Subject: [PATCH] MIPS: Always define builtin_cmdline |  | ||||||
|  |  | ||||||
| Commit 7784cac69735 ("MIPS: cmdline: Clean up boot_command_line |  | ||||||
| initialization") made use of builtin_cmdline conditional upon plain C if |  | ||||||
| statements rather than preprocessor #ifdef's. This caused build failures |  | ||||||
| for configurations with CONFIG_CMDLINE_BOOL=n where builtin_cmdline |  | ||||||
| wasn't defined, for example: |  | ||||||
|  |  | ||||||
|    arch/mips/kernel/setup.c: In function 'bootcmdline_init': |  | ||||||
| >> arch/mips/kernel/setup.c:582:30: error: 'builtin_cmdline' undeclared |  | ||||||
|     (first use in this function); did you mean 'builtin_driver'? |  | ||||||
|       strlcpy(boot_command_line, builtin_cmdline, COMMAND_LINE_SIZE); |  | ||||||
|                                  ^~~~~~~~~~~~~~~ |  | ||||||
|                                  builtin_driver |  | ||||||
|    arch/mips/kernel/setup.c:582:30: note: each undeclared identifier is |  | ||||||
|     reported only once for each function it appears in |  | ||||||
|  |  | ||||||
| Fix this by defining builtin_cmdline as an empty string in the affected |  | ||||||
| configurations. All of the paths that use it should be optimized out |  | ||||||
| anyway so the data itself gets optimized away too. |  | ||||||
|  |  | ||||||
| Signed-off-by: Paul Burton <paul.burton@mips.com> |  | ||||||
| Fixes: 7784cac69735 ("MIPS: cmdline: Clean up boot_command_line initialization") |  | ||||||
| Reported-by: kbuild test robot <lkp@intel.com> |  | ||||||
| Reported-by: Nathan Chancellor <natechancellor@gmail.com> |  | ||||||
| Cc: linux-mips@vger.kernel.org |  | ||||||
| --- |  | ||||||
|  arch/mips/kernel/setup.c | 2 ++ |  | ||||||
|  1 file changed, 2 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/setup.c |  | ||||||
| +++ b/arch/mips/kernel/setup.c |  | ||||||
| @@ -68,6 +68,8 @@ char __initdata arcs_cmdline[COMMAND_LIN |  | ||||||
|   |  | ||||||
|  #ifdef CONFIG_CMDLINE_BOOL |  | ||||||
|  static char __initdata builtin_cmdline[COMMAND_LINE_SIZE] = CONFIG_CMDLINE; |  | ||||||
| +#else |  | ||||||
| +static const char builtin_cmdline[] __initconst = ""; |  | ||||||
|  #endif |  | ||||||
|   |  | ||||||
|  /* |  | ||||||
| @@ -1,45 +0,0 @@ | |||||||
| From: Tobias Wolf <dev-NTEO@vplace.de> |  | ||||||
| Subject: [v2] MIPS: Fix memory reservation in bootmem_init for certain non-usermem setups |  | ||||||
|  |  | ||||||
| Commit 67a3ba25aa95 ("MIPS: Fix incorrect mem=X@Y handling") introduced a new |  | ||||||
| issue for rt288x where "PHYS_OFFSET" is 0x0 but the calculated "ramstart" is |  | ||||||
| not. As the prerequisite of custom memory map has been removed, this results |  | ||||||
| in the full memory range of 0x0 - 0x8000000 to be marked as reserved for this |  | ||||||
| platform. |  | ||||||
|  |  | ||||||
| v2: Correctly compare that usermem is not null. |  | ||||||
|  |  | ||||||
| This patch adds the originally intended prerequisite again. |  | ||||||
|  |  | ||||||
| Signed-off-by: Tobias Wolf <dev-NTEO@vplace.de> |  | ||||||
| --- |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/setup.c |  | ||||||
| +++ b/arch/mips/kernel/setup.c |  | ||||||
| @@ -287,6 +287,8 @@ static unsigned long __init init_initrd( |  | ||||||
|   * Initialize the bootmem allocator. It also setup initrd related data |  | ||||||
|   * if needed. |  | ||||||
|   */ |  | ||||||
| +static int usermem __initdata; |  | ||||||
| + |  | ||||||
|  #if defined(CONFIG_SGI_IP27) || (defined(CONFIG_CPU_LOONGSON3) && defined(CONFIG_NUMA)) |  | ||||||
|   |  | ||||||
|  static void __init bootmem_init(void) |  | ||||||
| @@ -325,7 +327,7 @@ static void __init bootmem_init(void) |  | ||||||
|  	/* |  | ||||||
|  	 * Reserve any memory between the start of RAM and PHYS_OFFSET |  | ||||||
|  	 */ |  | ||||||
| -	if (ramstart > PHYS_OFFSET) |  | ||||||
| +	if (usermem && ramstart > PHYS_OFFSET) |  | ||||||
|  		memblock_reserve(PHYS_OFFSET, ramstart - PHYS_OFFSET); |  | ||||||
|   |  | ||||||
|  	if (PFN_UP(ramstart) > ARCH_PFN_OFFSET) { |  | ||||||
| @@ -386,8 +388,6 @@ static void __init bootmem_init(void) |  | ||||||
|   |  | ||||||
|  #endif	/* CONFIG_SGI_IP27 */ |  | ||||||
|   |  | ||||||
| -static int usermem __initdata; |  | ||||||
| - |  | ||||||
|  static int __init early_parse_mem(char *p) |  | ||||||
|  { |  | ||||||
|  	phys_addr_t start, size; |  | ||||||
| @@ -1,82 +0,0 @@ | |||||||
| From ce3d4a4111a5f7e6b4e74bceae5faa6ce388e8ec Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 14 Jul 2013 23:08:11 +0200 |  | ||||||
| Subject: [PATCH 05/53] MIPS: use set_mode() to enable/disable the cevt-r4k |  | ||||||
|  irq |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/Kconfig |    5 +++++ |  | ||||||
|  1 file changed, 5 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/Kconfig |  | ||||||
| +++ b/arch/mips/ralink/Kconfig |  | ||||||
| @@ -1,12 +1,17 @@ |  | ||||||
|  # SPDX-License-Identifier: GPL-2.0 |  | ||||||
|  if RALINK |  | ||||||
|   |  | ||||||
| +config CEVT_SYSTICK_QUIRK |  | ||||||
| +	bool |  | ||||||
| +	default n |  | ||||||
| + |  | ||||||
|  config CLKEVT_RT3352 |  | ||||||
|  	bool |  | ||||||
|  	depends on SOC_RT305X || SOC_MT7620 |  | ||||||
|  	default y |  | ||||||
|  	select TIMER_OF |  | ||||||
|  	select CLKSRC_MMIO |  | ||||||
| +	select CEVT_SYSTICK_QUIRK |  | ||||||
|   |  | ||||||
|  config RALINK_ILL_ACC |  | ||||||
|  	bool |  | ||||||
| --- a/arch/mips/kernel/cevt-r4k.c |  | ||||||
| +++ b/arch/mips/kernel/cevt-r4k.c |  | ||||||
| @@ -15,6 +15,26 @@ |  | ||||||
|  #include <asm/time.h> |  | ||||||
|  #include <asm/cevt-r4k.h> |  | ||||||
|   |  | ||||||
| +static int mips_state_oneshot(struct clock_event_device *evt) |  | ||||||
| +{ |  | ||||||
| +	if (!cp0_timer_irq_installed) { |  | ||||||
| +		cp0_timer_irq_installed = 1; |  | ||||||
| +		setup_irq(evt->irq, &c0_compare_irqaction); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int mips_state_shutdown(struct clock_event_device *evt) |  | ||||||
| +{ |  | ||||||
| +	if (cp0_timer_irq_installed) { |  | ||||||
| +		cp0_timer_irq_installed = 0; |  | ||||||
| +		remove_irq(evt->irq, &c0_compare_irqaction); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static int mips_next_event(unsigned long delta, |  | ||||||
|  			   struct clock_event_device *evt) |  | ||||||
|  { |  | ||||||
| @@ -281,17 +301,21 @@ int r4k_clockevent_init(void) |  | ||||||
|  	cd->rating		= 300; |  | ||||||
|  	cd->irq			= irq; |  | ||||||
|  	cd->cpumask		= cpumask_of(cpu); |  | ||||||
| +	cd->set_state_shutdown	= mips_state_shutdown; |  | ||||||
| +	cd->set_state_oneshot	= mips_state_oneshot; |  | ||||||
|  	cd->set_next_event	= mips_next_event; |  | ||||||
|  	cd->event_handler	= mips_event_handler; |  | ||||||
|   |  | ||||||
|  	clockevents_config_and_register(cd, mips_hpt_frequency, min_delta, 0x7fffffff); |  | ||||||
|   |  | ||||||
| +#ifndef CONFIG_CEVT_SYSTICK_QUIRK |  | ||||||
|  	if (cp0_timer_irq_installed) |  | ||||||
|  		return 0; |  | ||||||
|   |  | ||||||
|  	cp0_timer_irq_installed = 1; |  | ||||||
|   |  | ||||||
|  	setup_irq(irq, &c0_compare_irqaction); |  | ||||||
| +#endif |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -1,200 +0,0 @@ | |||||||
| From bd30f19a006fb52bac80c6463c49dd2f4159f4ac Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 28 Jul 2013 16:26:41 +0200 |  | ||||||
| Subject: [PATCH 06/53] MIPS: ralink: add cpu frequency scaling |  | ||||||
|  |  | ||||||
| This feature will break udelay() and cause the delay loop to have longer delays |  | ||||||
| when the frequency is scaled causing a performance hit. |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/cevt-rt3352.c |   38 ++++++++++++++++++++++++++++++++++++++ |  | ||||||
|  1 file changed, 38 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/cevt-rt3352.c |  | ||||||
| +++ b/arch/mips/ralink/cevt-rt3352.c |  | ||||||
| @@ -29,6 +29,10 @@ |  | ||||||
|  /* enable the counter */ |  | ||||||
|  #define CFG_CNT_EN		0x1 |  | ||||||
|   |  | ||||||
| +/* mt7620 frequency scaling defines */ |  | ||||||
| +#define CLK_LUT_CFG	0x40 |  | ||||||
| +#define SLEEP_EN	BIT(31) |  | ||||||
| + |  | ||||||
|  struct systick_device { |  | ||||||
|  	void __iomem *membase; |  | ||||||
|  	struct clock_event_device dev; |  | ||||||
| @@ -36,21 +40,53 @@ struct systick_device { |  | ||||||
|  	int freq_scale; |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| +static void (*systick_freq_scaling)(struct systick_device *sdev, int status); |  | ||||||
| + |  | ||||||
|  static int systick_set_oneshot(struct clock_event_device *evt); |  | ||||||
|  static int systick_shutdown(struct clock_event_device *evt); |  | ||||||
|   |  | ||||||
| +static inline void mt7620_freq_scaling(struct systick_device *sdev, int status) |  | ||||||
| +{ |  | ||||||
| +	if (sdev->freq_scale == status) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	sdev->freq_scale = status; |  | ||||||
| + |  | ||||||
| +	pr_info("%s: %s autosleep mode\n", sdev->dev.name, |  | ||||||
| +			(status) ? ("enable") : ("disable")); |  | ||||||
| +	if (status) |  | ||||||
| +		rt_sysc_w32(rt_sysc_r32(CLK_LUT_CFG) | SLEEP_EN, CLK_LUT_CFG); |  | ||||||
| +	else |  | ||||||
| +		rt_sysc_w32(rt_sysc_r32(CLK_LUT_CFG) & ~SLEEP_EN, CLK_LUT_CFG); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline unsigned int read_count(struct systick_device *sdev) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(sdev->membase + SYSTICK_COUNT); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline unsigned int read_compare(struct systick_device *sdev) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(sdev->membase + SYSTICK_COMPARE); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void write_compare(struct systick_device *sdev, unsigned int val) |  | ||||||
| +{ |  | ||||||
| +	iowrite32(val, sdev->membase + SYSTICK_COMPARE); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static int systick_next_event(unsigned long delta, |  | ||||||
|  				struct clock_event_device *evt) |  | ||||||
|  { |  | ||||||
|  	struct systick_device *sdev; |  | ||||||
| -	u32 count; |  | ||||||
| +	int res; |  | ||||||
|   |  | ||||||
|  	sdev = container_of(evt, struct systick_device, dev); |  | ||||||
| -	count = ioread32(sdev->membase + SYSTICK_COUNT); |  | ||||||
| -	count = (count + delta) % SYSTICK_FREQ; |  | ||||||
| -	iowrite32(count, sdev->membase + SYSTICK_COMPARE); |  | ||||||
| +	delta += read_count(sdev); |  | ||||||
| +	write_compare(sdev, delta); |  | ||||||
| +	res = ((int)(read_count(sdev) - delta) >= 0) ? -ETIME : 0; |  | ||||||
|   |  | ||||||
| -	return 0; |  | ||||||
| +	return res; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static void systick_event_handler(struct clock_event_device *dev) |  | ||||||
| @@ -60,20 +96,25 @@ static void systick_event_handler(struct |  | ||||||
|   |  | ||||||
|  static irqreturn_t systick_interrupt(int irq, void *dev_id) |  | ||||||
|  { |  | ||||||
| -	struct clock_event_device *dev = (struct clock_event_device *) dev_id; |  | ||||||
| +	int ret = 0; |  | ||||||
| +	struct clock_event_device *cdev; |  | ||||||
| +	struct systick_device *sdev; |  | ||||||
|   |  | ||||||
| -	dev->event_handler(dev); |  | ||||||
| +	if (read_c0_cause() & STATUSF_IP7) { |  | ||||||
| +		cdev = (struct clock_event_device *) dev_id; |  | ||||||
| +		sdev = container_of(cdev, struct systick_device, dev); |  | ||||||
| + |  | ||||||
| +		/* Clear Count/Compare Interrupt */ |  | ||||||
| +		write_compare(sdev, read_compare(sdev)); |  | ||||||
| +		cdev->event_handler(cdev); |  | ||||||
| +		ret = 1; |  | ||||||
| +	} |  | ||||||
|   |  | ||||||
| -	return IRQ_HANDLED; |  | ||||||
| +	return IRQ_RETVAL(ret); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static struct systick_device systick = { |  | ||||||
|  	.dev = { |  | ||||||
| -		/* |  | ||||||
| -		 * cevt-r4k uses 300, make sure systick |  | ||||||
| -		 * gets used if available |  | ||||||
| -		 */ |  | ||||||
| -		.rating			= 310, |  | ||||||
|  		.features		= CLOCK_EVT_FEAT_ONESHOT, |  | ||||||
|  		.set_next_event		= systick_next_event, |  | ||||||
|  		.set_state_shutdown	= systick_shutdown, |  | ||||||
| @@ -95,9 +136,15 @@ static int systick_shutdown(struct clock |  | ||||||
|  	sdev = container_of(evt, struct systick_device, dev); |  | ||||||
|   |  | ||||||
|  	if (sdev->irq_requested) |  | ||||||
| -		free_irq(systick.dev.irq, &systick_irqaction); |  | ||||||
| +		remove_irq(systick.dev.irq, &systick_irqaction); |  | ||||||
|  	sdev->irq_requested = 0; |  | ||||||
| -	iowrite32(0, systick.membase + SYSTICK_CONFIG); |  | ||||||
| +	iowrite32(CFG_CNT_EN, systick.membase + SYSTICK_CONFIG); |  | ||||||
| + |  | ||||||
| +	if (systick_freq_scaling) |  | ||||||
| +		systick_freq_scaling(sdev, 0); |  | ||||||
| + |  | ||||||
| +	if (systick_freq_scaling) |  | ||||||
| +		systick_freq_scaling(sdev, 1); |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -117,34 +164,48 @@ static int systick_set_oneshot(struct cl |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static const struct of_device_id systick_match[] = { |  | ||||||
| +	{ .compatible = "ralink,mt7620a-systick", .data = mt7620_freq_scaling}, |  | ||||||
| +	{}, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
|  static int __init ralink_systick_init(struct device_node *np) |  | ||||||
|  { |  | ||||||
| +	const struct of_device_id *match; |  | ||||||
| +	int rating = 200; |  | ||||||
|  	int ret; |  | ||||||
|   |  | ||||||
|  	systick.membase = of_iomap(np, 0); |  | ||||||
|  	if (!systick.membase) |  | ||||||
|  		return -ENXIO; |  | ||||||
|   |  | ||||||
| -	systick_irqaction.name = np->name; |  | ||||||
| -	systick.dev.name = np->name; |  | ||||||
| -	clockevents_calc_mult_shift(&systick.dev, SYSTICK_FREQ, 60); |  | ||||||
| -	systick.dev.max_delta_ns = clockevent_delta2ns(0x7fff, &systick.dev); |  | ||||||
| -	systick.dev.max_delta_ticks = 0x7fff; |  | ||||||
| -	systick.dev.min_delta_ns = clockevent_delta2ns(0x3, &systick.dev); |  | ||||||
| -	systick.dev.min_delta_ticks = 0x3; |  | ||||||
| +	match = of_match_node(systick_match, np); |  | ||||||
| +	if (match) { |  | ||||||
| +		systick_freq_scaling = match->data; |  | ||||||
| +		/* |  | ||||||
| +		 * cevt-r4k uses 300, make sure systick |  | ||||||
| +		 * gets used if available |  | ||||||
| +		 */ |  | ||||||
| +		rating = 310; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* enable counter than register clock source */ |  | ||||||
| +	iowrite32(CFG_CNT_EN, systick.membase + SYSTICK_CONFIG); |  | ||||||
| +	clocksource_mmio_init(systick.membase + SYSTICK_COUNT, np->name, |  | ||||||
| +			SYSTICK_FREQ, rating, 16, clocksource_mmio_readl_up); |  | ||||||
| + |  | ||||||
| +	/* register clock event */ |  | ||||||
|  	systick.dev.irq = irq_of_parse_and_map(np, 0); |  | ||||||
|  	if (!systick.dev.irq) { |  | ||||||
|  		pr_err("%pOFn: request_irq failed", np); |  | ||||||
|  		return -EINVAL; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	ret = clocksource_mmio_init(systick.membase + SYSTICK_COUNT, np->name, |  | ||||||
| -				    SYSTICK_FREQ, 301, 16, |  | ||||||
| -				    clocksource_mmio_readl_up); |  | ||||||
| -	if (ret) |  | ||||||
| -		return ret; |  | ||||||
| - |  | ||||||
| -	clockevents_register_device(&systick.dev); |  | ||||||
| +	systick_irqaction.name = np->name; |  | ||||||
| +	systick.dev.name = np->name; |  | ||||||
| +	systick.dev.rating = rating; |  | ||||||
| +	systick.dev.cpumask = cpumask_of(0); |  | ||||||
| +	clockevents_config_and_register(&systick.dev, SYSTICK_FREQ, 0x3, 0x7fff); |  | ||||||
|   |  | ||||||
|  	pr_info("%pOFn: running - mult: %d, shift: %d\n", |  | ||||||
|  			np, systick.dev.mult, systick.dev.shift); |  | ||||||
| @@ -1,21 +0,0 @@ | |||||||
| From 67b7bff0fd364c194e653f69baa623ba2141bd4c Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 4 Aug 2014 18:46:02 +0200 |  | ||||||
| Subject: [PATCH 07/53] MIPS: ralink: copy the commandline from the devicetree |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/of.c |    2 ++ |  | ||||||
|  1 file changed, 2 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/of.c |  | ||||||
| +++ b/arch/mips/ralink/of.c |  | ||||||
| @@ -82,6 +82,8 @@ void __init plat_mem_setup(void) |  | ||||||
|   |  | ||||||
|  	__dt_setup_arch(dtb); |  | ||||||
|   |  | ||||||
| +	strlcpy(arcs_cmdline, boot_command_line, COMMAND_LINE_SIZE); |  | ||||||
| + |  | ||||||
|  	of_scan_flat_dt(early_init_dt_find_memory, NULL); |  | ||||||
|  	if (memory_dtb) |  | ||||||
|  		of_scan_flat_dt(early_init_dt_scan_memory, NULL); |  | ||||||
| @@ -1,63 +0,0 @@ | |||||||
| From f15d27f9c90ede4b16eb37f9ae573ef81c2b6996 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: David Bauer <mail@david-bauer.net> |  | ||||||
| Date: Thu, 31 Dec 2020 18:49:12 +0100 |  | ||||||
| Subject: [PATCH] MIPS: add bootargs-override property |  | ||||||
|  |  | ||||||
| Add support for the bootargs-override property to the chosen node |  | ||||||
| similar to the one used on ipq806x or mpc85xx. |  | ||||||
|  |  | ||||||
| This is necessary, as the U-Boot used on some boards, notably the |  | ||||||
| Ubiquiti UniFi 6 Lite, overwrite the bootargs property of the chosen |  | ||||||
| node leading to a kernel panic when loading OpenWrt. |  | ||||||
|  |  | ||||||
| Signed-off-by: David Bauer <mail@david-bauer.net> |  | ||||||
| --- |  | ||||||
|  arch/mips/kernel/setup.c | 30 ++++++++++++++++++++++++++++++ |  | ||||||
|  1 file changed, 30 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/setup.c |  | ||||||
| +++ b/arch/mips/kernel/setup.c |  | ||||||
| @@ -571,8 +571,28 @@ static int __init bootcmdline_scan_chose |  | ||||||
|  	return 1; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static int __init bootcmdline_scan_chosen_override(unsigned long node, const char *uname, |  | ||||||
| +						   int depth, void *data) |  | ||||||
| +{ |  | ||||||
| +	bool *dt_bootargs = data; |  | ||||||
| +	const char *p; |  | ||||||
| +	int l; |  | ||||||
| + |  | ||||||
| +	if (depth != 1 || !data || strcmp(uname, "chosen") != 0) |  | ||||||
| +		return 0; |  | ||||||
| + |  | ||||||
| +	p = of_get_flat_dt_prop(node, "bootargs-override", &l); |  | ||||||
| +	if (p != NULL && l > 0) { |  | ||||||
| +		strlcpy(boot_command_line, p, COMMAND_LINE_SIZE); |  | ||||||
| +		*dt_bootargs = true; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return 1; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static void __init bootcmdline_init(char **cmdline_p) |  | ||||||
|  { |  | ||||||
| +	bool dt_bootargs_override = false; |  | ||||||
|  	bool dt_bootargs = false; |  | ||||||
|   |  | ||||||
|  	/* |  | ||||||
| @@ -586,6 +606,14 @@ static void __init bootcmdline_init(char |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	/* |  | ||||||
| +	 * If bootargs-override in the chosen node is set, use this as the |  | ||||||
| +	 * command line |  | ||||||
| +	 */ |  | ||||||
| +	of_scan_flat_dt(bootcmdline_scan_chosen_override, &dt_bootargs_override); |  | ||||||
| +	if (dt_bootargs_override) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
|  	 * If the user specified a built-in command line & |  | ||||||
|  	 * MIPS_CMDLINE_BUILTIN_EXTEND, then the built-in command line is |  | ||||||
|  	 * prepended to arguments from the bootloader or DT so we'll copy them |  | ||||||
| @@ -1,29 +0,0 @@ | |||||||
| From 5ede027f6c4a57ed25da872420508b7f1168b36b Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 7 Dec 2015 17:15:32 +0100 |  | ||||||
| Subject: [PATCH 13/53] owrt: hack: fix mt7688 cache issue |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  arch/mips/kernel/setup.c |    2 +- |  | ||||||
|  1 file changed, 1 insertion(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/setup.c |  | ||||||
| +++ b/arch/mips/kernel/setup.c |  | ||||||
| @@ -723,8 +723,6 @@ static void __init arch_mem_init(char ** |  | ||||||
|  		memblock_reserve(crashk_res.start, |  | ||||||
|  				 crashk_res.end - crashk_res.start + 1); |  | ||||||
|  #endif |  | ||||||
| -	device_tree_init(); |  | ||||||
| - |  | ||||||
|  	/* |  | ||||||
|  	 * In order to reduce the possibility of kernel panic when failed to |  | ||||||
|  	 * get IO TLB memory under CONFIG_SWIOTLB, it is better to allocate |  | ||||||
| @@ -841,6 +839,7 @@ void __init setup_arch(char **cmdline_p) |  | ||||||
|   |  | ||||||
|  	cpu_cache_init(); |  | ||||||
|  	paging_init(); |  | ||||||
| +	device_tree_init(); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  unsigned long kernelsp[NR_CPUS]; |  | ||||||
| @@ -1,25 +0,0 @@ | |||||||
| From 9e6ce539092a1dd605a20bf73c655a9de58d8641 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 7 Dec 2015 17:18:05 +0100 |  | ||||||
| Subject: [PATCH 15/53] arch: mips: do not select illegal access driver by |  | ||||||
|  default |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/Kconfig |    4 ++-- |  | ||||||
|  1 file changed, 2 insertions(+), 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/Kconfig |  | ||||||
| +++ b/arch/mips/ralink/Kconfig |  | ||||||
| @@ -14,9 +14,9 @@ config CLKEVT_RT3352 |  | ||||||
|  	select CEVT_SYSTICK_QUIRK |  | ||||||
|   |  | ||||||
|  config RALINK_ILL_ACC |  | ||||||
| -	bool |  | ||||||
| +	bool "illegal access irq" |  | ||||||
|  	depends on SOC_RT305X |  | ||||||
| -	default y |  | ||||||
| +	default n |  | ||||||
|   |  | ||||||
|  config IRQ_INTC |  | ||||||
|  	bool |  | ||||||
| @@ -1,165 +0,0 @@ | |||||||
| From 4267880319bc1a2270d352e0ded6d6386242a7ef Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Tue, 12 Aug 2014 20:49:27 +0200 |  | ||||||
| Subject: [PATCH 24/53] GPIO: add named gpio exports |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/gpio/gpiolib-of.c     |   68 +++++++++++++++++++++++++++++++++++++++++ |  | ||||||
|  drivers/gpio/gpiolib-sysfs.c  |   10 +++++- |  | ||||||
|  include/asm-generic/gpio.h    |    6 ++++ |  | ||||||
|  include/linux/gpio/consumer.h |    8 +++++ |  | ||||||
|  4 files changed, 91 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/gpio/gpiolib-of.c |  | ||||||
| +++ b/drivers/gpio/gpiolib-of.c |  | ||||||
| @@ -19,6 +19,8 @@ |  | ||||||
|  #include <linux/pinctrl/pinctrl.h> |  | ||||||
|  #include <linux/slab.h> |  | ||||||
|  #include <linux/gpio/machine.h> |  | ||||||
| +#include <linux/init.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
|   |  | ||||||
|  #include "gpiolib.h" |  | ||||||
|  #include "gpiolib-of.h" |  | ||||||
| @@ -915,3 +917,68 @@ void of_gpiochip_remove(struct gpio_chip |  | ||||||
|  { |  | ||||||
|  	of_node_put(chip->of_node); |  | ||||||
|  } |  | ||||||
| + |  | ||||||
| +static struct of_device_id gpio_export_ids[] = { |  | ||||||
| +	{ .compatible = "gpio-export" }, |  | ||||||
| +	{ /* sentinel */ } |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int of_gpio_export_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct device_node *np = pdev->dev.of_node; |  | ||||||
| +	struct device_node *cnp; |  | ||||||
| +	u32 val; |  | ||||||
| +	int nb = 0; |  | ||||||
| + |  | ||||||
| +	for_each_child_of_node(np, cnp) { |  | ||||||
| +		const char *name = NULL; |  | ||||||
| +		int gpio; |  | ||||||
| +		bool dmc; |  | ||||||
| +		int max_gpio = 1; |  | ||||||
| +		int i; |  | ||||||
| + |  | ||||||
| +		of_property_read_string(cnp, "gpio-export,name", &name); |  | ||||||
| + |  | ||||||
| +		if (!name) |  | ||||||
| +			max_gpio = of_gpio_count(cnp); |  | ||||||
| + |  | ||||||
| +		for (i = 0; i < max_gpio; i++) { |  | ||||||
| +			unsigned flags = 0; |  | ||||||
| +			enum of_gpio_flags of_flags; |  | ||||||
| + |  | ||||||
| +			gpio = of_get_gpio_flags(cnp, i, &of_flags); |  | ||||||
| +			if (!gpio_is_valid(gpio)) |  | ||||||
| +				return gpio; |  | ||||||
| + |  | ||||||
| +			if (of_flags == OF_GPIO_ACTIVE_LOW) |  | ||||||
| +				flags |= GPIOF_ACTIVE_LOW; |  | ||||||
| + |  | ||||||
| +			if (!of_property_read_u32(cnp, "gpio-export,output", &val)) |  | ||||||
| +				flags |= val ? GPIOF_OUT_INIT_HIGH : GPIOF_OUT_INIT_LOW; |  | ||||||
| +			else |  | ||||||
| +				flags |= GPIOF_IN; |  | ||||||
| + |  | ||||||
| +			if (devm_gpio_request_one(&pdev->dev, gpio, flags, name ? name : of_node_full_name(np))) |  | ||||||
| +				continue; |  | ||||||
| + |  | ||||||
| +			dmc = of_property_read_bool(cnp, "gpio-export,direction_may_change"); |  | ||||||
| +			gpio_export_with_name(gpio, dmc, name); |  | ||||||
| +			nb++; |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	dev_info(&pdev->dev, "%d gpio(s) exported\n", nb); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static struct platform_driver gpio_export_driver = { |  | ||||||
| +	.driver		= { |  | ||||||
| +		.name		= "gpio-export", |  | ||||||
| +		.owner	= THIS_MODULE, |  | ||||||
| +		.of_match_table	= of_match_ptr(gpio_export_ids), |  | ||||||
| +	}, |  | ||||||
| +	.probe		= of_gpio_export_probe, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +module_platform_driver(gpio_export_driver); |  | ||||||
| --- a/drivers/gpio/gpiolib-sysfs.c |  | ||||||
| +++ b/drivers/gpio/gpiolib-sysfs.c |  | ||||||
| @@ -571,7 +571,7 @@ static struct class gpio_class = { |  | ||||||
|   * |  | ||||||
|   * Returns zero on success, else an error. |  | ||||||
|   */ |  | ||||||
| -int gpiod_export(struct gpio_desc *desc, bool direction_may_change) |  | ||||||
| +int __gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name) |  | ||||||
|  { |  | ||||||
|  	struct gpio_chip	*chip; |  | ||||||
|  	struct gpio_device	*gdev; |  | ||||||
| @@ -633,6 +633,8 @@ int gpiod_export(struct gpio_desc *desc, |  | ||||||
|  	offset = gpio_chip_hwgpio(desc); |  | ||||||
|  	if (chip->names && chip->names[offset]) |  | ||||||
|  		ioname = chip->names[offset]; |  | ||||||
| +	if (name) |  | ||||||
| +		ioname = name; |  | ||||||
|   |  | ||||||
|  	dev = device_create_with_groups(&gpio_class, &gdev->dev, |  | ||||||
|  					MKDEV(0, 0), data, gpio_groups, |  | ||||||
| @@ -654,6 +656,12 @@ err_unlock: |  | ||||||
|  	gpiod_dbg(desc, "%s: status %d\n", __func__, status); |  | ||||||
|  	return status; |  | ||||||
|  } |  | ||||||
| +EXPORT_SYMBOL_GPL(__gpiod_export); |  | ||||||
| + |  | ||||||
| +int gpiod_export(struct gpio_desc *desc, bool direction_may_change) |  | ||||||
| +{ |  | ||||||
| +	return __gpiod_export(desc, direction_may_change, NULL); |  | ||||||
| +} |  | ||||||
|  EXPORT_SYMBOL_GPL(gpiod_export); |  | ||||||
|   |  | ||||||
|  static int match_export(struct device *dev, const void *desc) |  | ||||||
| --- a/include/asm-generic/gpio.h |  | ||||||
| +++ b/include/asm-generic/gpio.h |  | ||||||
| @@ -127,6 +127,12 @@ static inline int gpio_export(unsigned g |  | ||||||
|  	return gpiod_export(gpio_to_desc(gpio), direction_may_change); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +int __gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name); |  | ||||||
| +static inline int gpio_export_with_name(unsigned gpio, bool direction_may_change, const char *name) |  | ||||||
| +{ |  | ||||||
| +	return __gpiod_export(gpio_to_desc(gpio), direction_may_change, name); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static inline int gpio_export_link(struct device *dev, const char *name, |  | ||||||
|  				   unsigned gpio) |  | ||||||
|  { |  | ||||||
| --- a/include/linux/gpio/consumer.h |  | ||||||
| +++ b/include/linux/gpio/consumer.h |  | ||||||
| @@ -668,6 +668,7 @@ static inline void devm_acpi_dev_remove_ |  | ||||||
|   |  | ||||||
|  #if IS_ENABLED(CONFIG_GPIOLIB) && IS_ENABLED(CONFIG_GPIO_SYSFS) |  | ||||||
|   |  | ||||||
| +int _gpiod_export(struct gpio_desc *desc, bool direction_may_change, const char *name); |  | ||||||
|  int gpiod_export(struct gpio_desc *desc, bool direction_may_change); |  | ||||||
|  int gpiod_export_link(struct device *dev, const char *name, |  | ||||||
|  		      struct gpio_desc *desc); |  | ||||||
| @@ -675,6 +676,13 @@ void gpiod_unexport(struct gpio_desc *de |  | ||||||
|   |  | ||||||
|  #else  /* CONFIG_GPIOLIB && CONFIG_GPIO_SYSFS */ |  | ||||||
|   |  | ||||||
| +static inline int _gpiod_export(struct gpio_desc *desc, |  | ||||||
| +			       bool direction_may_change, |  | ||||||
| +			       const char *name) |  | ||||||
| +{ |  | ||||||
| +	return -ENOSYS; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static inline int gpiod_export(struct gpio_desc *desc, |  | ||||||
|  			       bool direction_may_change) |  | ||||||
|  { |  | ||||||
| @@ -1,59 +0,0 @@ | |||||||
| From d410e5478c622c01fcf31427533df5f433df9146 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 28 Jul 2013 19:45:30 +0200 |  | ||||||
| Subject: [PATCH 26/53] DT: Add documentation for gpio-ralink |  | ||||||
|  |  | ||||||
| Describe gpio-ralink binding. |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| Cc: linux-mips@linux-mips.org |  | ||||||
| Cc: devicetree@vger.kernel.org |  | ||||||
| Cc: linux-gpio@vger.kernel.org |  | ||||||
| --- |  | ||||||
|  .../devicetree/bindings/gpio/gpio-ralink.txt       |   40 ++++++++++++++++++++ |  | ||||||
|  1 file changed, 40 insertions(+) |  | ||||||
|  create mode 100644 Documentation/devicetree/bindings/gpio/gpio-ralink.txt |  | ||||||
|  |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/Documentation/devicetree/bindings/gpio/gpio-ralink.txt |  | ||||||
| @@ -0,0 +1,40 @@ |  | ||||||
| +Ralink SoC GPIO controller bindings |  | ||||||
| + |  | ||||||
| +Required properties: |  | ||||||
| +- compatible: |  | ||||||
| +  - "ralink,rt2880-gpio" for Ralink controllers |  | ||||||
| +- #gpio-cells : Should be two. |  | ||||||
| +  - first cell is the pin number |  | ||||||
| +  - second cell is used to specify optional parameters (unused) |  | ||||||
| +- gpio-controller : Marks the device node as a GPIO controller |  | ||||||
| +- reg : Physical base address and length of the controller's registers |  | ||||||
| +- interrupt-parent: phandle to the INTC device node |  | ||||||
| +- interrupts : Specify the INTC interrupt number |  | ||||||
| +- ngpios : Specify the number of GPIOs |  | ||||||
| +- ralink,register-map : The register layout depends on the GPIO bank and actual |  | ||||||
| +		SoC type. Register offsets need to be in this order. |  | ||||||
| +		[ INT, EDGE, RENA, FENA, DATA, DIR, POL, SET, RESET, TOGGLE ] |  | ||||||
| + |  | ||||||
| +Optional properties: |  | ||||||
| +- ralink,gpio-base : Specify the GPIO chips base number |  | ||||||
| + |  | ||||||
| +Example: |  | ||||||
| + |  | ||||||
| +	gpio0: gpio@600 { |  | ||||||
| +		compatible = "ralink,rt5350-gpio", "ralink,rt2880-gpio"; |  | ||||||
| + |  | ||||||
| +		#gpio-cells = <2>; |  | ||||||
| +		gpio-controller; |  | ||||||
| + |  | ||||||
| +		reg = <0x600 0x34>; |  | ||||||
| + |  | ||||||
| +		interrupt-parent = <&intc>; |  | ||||||
| +		interrupts = <6>; |  | ||||||
| + |  | ||||||
| +		ngpios = <24>; |  | ||||||
| +		ralink,gpio-base = <0>; |  | ||||||
| +		ralink,register-map = [ 00 04 08 0c |  | ||||||
| +				20 24 28 2c |  | ||||||
| +				30 34 ]; |  | ||||||
| + |  | ||||||
| +	}; |  | ||||||
| @@ -1,416 +0,0 @@ | |||||||
| From 69fdd2c4f937796b934e89c33acde9d082e27bfd Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 4 Aug 2014 20:36:29 +0200 |  | ||||||
| Subject: [PATCH 27/53] GPIO: MIPS: ralink: add gpio driver for ralink SoC |  | ||||||
|  |  | ||||||
| Add gpio driver for Ralink SoC. This driver makes the gpio core on |  | ||||||
| RT2880, RT305x, rt3352, rt3662, rt3883, rt5350 and mt7620 work. |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| Cc: linux-mips@linux-mips.org |  | ||||||
| Cc: linux-gpio@vger.kernel.org |  | ||||||
| --- |  | ||||||
|  arch/mips/include/asm/mach-ralink/gpio.h |   24 ++ |  | ||||||
|  drivers/gpio/Kconfig                     |    6 + |  | ||||||
|  drivers/gpio/Makefile                    |    1 + |  | ||||||
|  drivers/gpio/gpio-ralink.c               |  355 ++++++++++++++++++++++++++++++ |  | ||||||
|  4 files changed, 386 insertions(+) |  | ||||||
|  create mode 100644 arch/mips/include/asm/mach-ralink/gpio.h |  | ||||||
|  create mode 100644 drivers/gpio/gpio-ralink.c |  | ||||||
|  |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/arch/mips/include/asm/mach-ralink/gpio.h |  | ||||||
| @@ -0,0 +1,24 @@ |  | ||||||
| +/* |  | ||||||
| + *  Ralink SoC GPIO API support |  | ||||||
| + * |  | ||||||
| + *  Copyright (C) 2008-2009 Gabor Juhos <juhosg@openwrt.org> |  | ||||||
| + *  Copyright (C) 2008 Imre Kaloz <kaloz@openwrt.org> |  | ||||||
| + * |  | ||||||
| + *  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 __ASM_MACH_RALINK_GPIO_H |  | ||||||
| +#define __ASM_MACH_RALINK_GPIO_H |  | ||||||
| + |  | ||||||
| +#define ARCH_NR_GPIOS	128 |  | ||||||
| +#include <asm-generic/gpio.h> |  | ||||||
| + |  | ||||||
| +#define gpio_get_value	__gpio_get_value |  | ||||||
| +#define gpio_set_value	__gpio_set_value |  | ||||||
| +#define gpio_cansleep	__gpio_cansleep |  | ||||||
| +#define gpio_to_irq	__gpio_to_irq |  | ||||||
| + |  | ||||||
| +#endif /* __ASM_MACH_RALINK_GPIO_H */ |  | ||||||
| --- a/drivers/gpio/Kconfig |  | ||||||
| +++ b/drivers/gpio/Kconfig |  | ||||||
| @@ -471,6 +471,12 @@ config GPIO_SNPS_CREG |  | ||||||
|  	  where only several fields in register belong to GPIO lines and |  | ||||||
|  	  each GPIO line owns a field with different length and on/off value. |  | ||||||
|   |  | ||||||
| +config GPIO_RALINK |  | ||||||
| +	bool "Ralink GPIO Support" |  | ||||||
| +	depends on RALINK |  | ||||||
| +	help |  | ||||||
| +	  Say yes here to support the Ralink SoC GPIO device |  | ||||||
| + |  | ||||||
|  config GPIO_SPEAR_SPICS |  | ||||||
|  	bool "ST SPEAr13xx SPI Chip Select as GPIO support" |  | ||||||
|  	depends on PLAT_SPEAR |  | ||||||
| --- a/drivers/gpio/Makefile |  | ||||||
| +++ b/drivers/gpio/Makefile |  | ||||||
| @@ -112,6 +112,7 @@ obj-$(CONFIG_GPIO_PISOSR)		+= gpio-pisos |  | ||||||
|  obj-$(CONFIG_GPIO_PL061)		+= gpio-pl061.o |  | ||||||
|  obj-$(CONFIG_GPIO_PMIC_EIC_SPRD)	+= gpio-pmic-eic-sprd.o |  | ||||||
|  obj-$(CONFIG_GPIO_PXA)			+= gpio-pxa.o |  | ||||||
| +obj-$(CONFIG_GPIO_RALINK)		+= gpio-ralink.o |  | ||||||
|  obj-$(CONFIG_GPIO_RASPBERRYPI_EXP)	+= gpio-raspberrypi-exp.o |  | ||||||
|  obj-$(CONFIG_GPIO_RC5T583)		+= gpio-rc5t583.o |  | ||||||
|  obj-$(CONFIG_GPIO_RCAR)			+= gpio-rcar.o |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/drivers/gpio/gpio-ralink.c |  | ||||||
| @@ -0,0 +1,341 @@ |  | ||||||
| +/* |  | ||||||
| + * 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. |  | ||||||
| + * |  | ||||||
| + * Copyright (C) 2009-2011 Gabor Juhos <juhosg@openwrt.org> |  | ||||||
| + * Copyright (C) 2013 John Crispin <blogic@openwrt.org> |  | ||||||
| + */ |  | ||||||
| + |  | ||||||
| +#include <linux/module.h> |  | ||||||
| +#include <linux/io.h> |  | ||||||
| +#include <linux/gpio.h> |  | ||||||
| +#include <linux/spinlock.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
| +#include <linux/of_irq.h> |  | ||||||
| +#include <linux/irqdomain.h> |  | ||||||
| +#include <linux/interrupt.h> |  | ||||||
| + |  | ||||||
| +enum ralink_gpio_reg { |  | ||||||
| +	GPIO_REG_INT = 0, |  | ||||||
| +	GPIO_REG_EDGE, |  | ||||||
| +	GPIO_REG_RENA, |  | ||||||
| +	GPIO_REG_FENA, |  | ||||||
| +	GPIO_REG_DATA, |  | ||||||
| +	GPIO_REG_DIR, |  | ||||||
| +	GPIO_REG_POL, |  | ||||||
| +	GPIO_REG_SET, |  | ||||||
| +	GPIO_REG_RESET, |  | ||||||
| +	GPIO_REG_TOGGLE, |  | ||||||
| +	GPIO_REG_MAX |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +struct ralink_gpio_chip { |  | ||||||
| +	struct gpio_chip chip; |  | ||||||
| +	u8 regs[GPIO_REG_MAX]; |  | ||||||
| + |  | ||||||
| +	spinlock_t lock; |  | ||||||
| +	void __iomem *membase; |  | ||||||
| +	struct irq_domain *domain; |  | ||||||
| +	int irq; |  | ||||||
| + |  | ||||||
| +	u32 rising; |  | ||||||
| +	u32 falling; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +#define MAP_MAX	4 |  | ||||||
| +static struct irq_domain *irq_map[MAP_MAX]; |  | ||||||
| +static int irq_map_count; |  | ||||||
| +static atomic_t irq_refcount = ATOMIC_INIT(0); |  | ||||||
| + |  | ||||||
| +static inline struct ralink_gpio_chip *to_ralink_gpio(struct gpio_chip *chip) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg; |  | ||||||
| + |  | ||||||
| +	rg = container_of(chip, struct ralink_gpio_chip, chip); |  | ||||||
| + |  | ||||||
| +	return rg; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void rt_gpio_w32(struct ralink_gpio_chip *rg, u8 reg, u32 val) |  | ||||||
| +{ |  | ||||||
| +	iowrite32(val, rg->membase + rg->regs[reg]); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline u32 rt_gpio_r32(struct ralink_gpio_chip *rg, u8 reg) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(rg->membase + rg->regs[reg]); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void ralink_gpio_set(struct gpio_chip *chip, unsigned offset, int value) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg = to_ralink_gpio(chip); |  | ||||||
| + |  | ||||||
| +	rt_gpio_w32(rg, (value) ? GPIO_REG_SET : GPIO_REG_RESET, BIT(offset)); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_get(struct gpio_chip *chip, unsigned offset) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg = to_ralink_gpio(chip); |  | ||||||
| + |  | ||||||
| +	return !!(rt_gpio_r32(rg, GPIO_REG_DATA) & BIT(offset)); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_direction_input(struct gpio_chip *chip, unsigned offset) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg = to_ralink_gpio(chip); |  | ||||||
| +	unsigned long flags; |  | ||||||
| +	u32 t; |  | ||||||
| + |  | ||||||
| +	spin_lock_irqsave(&rg->lock, flags); |  | ||||||
| +	t = rt_gpio_r32(rg, GPIO_REG_DIR); |  | ||||||
| +	t &= ~BIT(offset); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_DIR, t); |  | ||||||
| +	spin_unlock_irqrestore(&rg->lock, flags); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_direction_output(struct gpio_chip *chip, |  | ||||||
| +					unsigned offset, int value) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg = to_ralink_gpio(chip); |  | ||||||
| +	unsigned long flags; |  | ||||||
| +	u32 t; |  | ||||||
| + |  | ||||||
| +	spin_lock_irqsave(&rg->lock, flags); |  | ||||||
| +	ralink_gpio_set(chip, offset, value); |  | ||||||
| +	t = rt_gpio_r32(rg, GPIO_REG_DIR); |  | ||||||
| +	t |= BIT(offset); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_DIR, t); |  | ||||||
| +	spin_unlock_irqrestore(&rg->lock, flags); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_to_irq(struct gpio_chip *chip, unsigned pin) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg = to_ralink_gpio(chip); |  | ||||||
| + |  | ||||||
| +	if (rg->irq < 1) |  | ||||||
| +		return -1; |  | ||||||
| + |  | ||||||
| +	return irq_create_mapping(rg->domain, pin); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void ralink_gpio_irq_handler(struct irq_desc *desc) |  | ||||||
| +{ |  | ||||||
| +	int i; |  | ||||||
| + |  | ||||||
| +	for (i = 0; i < irq_map_count; i++) { |  | ||||||
| +		struct irq_domain *domain = irq_map[i]; |  | ||||||
| +		struct ralink_gpio_chip *rg; |  | ||||||
| +		unsigned long pending; |  | ||||||
| +		int bit; |  | ||||||
| + |  | ||||||
| +		rg = (struct ralink_gpio_chip *) domain->host_data; |  | ||||||
| +		pending = rt_gpio_r32(rg, GPIO_REG_INT); |  | ||||||
| + |  | ||||||
| +		for_each_set_bit(bit, &pending, rg->chip.ngpio) { |  | ||||||
| +			u32 map = irq_find_mapping(domain, bit); |  | ||||||
| +			generic_handle_irq(map); |  | ||||||
| +			rt_gpio_w32(rg, GPIO_REG_INT, BIT(bit)); |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void ralink_gpio_irq_unmask(struct irq_data *d) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg; |  | ||||||
| +	unsigned long flags; |  | ||||||
| +	u32 rise, fall; |  | ||||||
| + |  | ||||||
| +	rg = (struct ralink_gpio_chip *) d->domain->host_data; |  | ||||||
| +	rise = rt_gpio_r32(rg, GPIO_REG_RENA); |  | ||||||
| +	fall = rt_gpio_r32(rg, GPIO_REG_FENA); |  | ||||||
| + |  | ||||||
| +	spin_lock_irqsave(&rg->lock, flags); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_RENA, rise | (BIT(d->hwirq) & rg->rising)); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_FENA, fall | (BIT(d->hwirq) & rg->falling)); |  | ||||||
| +	spin_unlock_irqrestore(&rg->lock, flags); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void ralink_gpio_irq_mask(struct irq_data *d) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg; |  | ||||||
| +	unsigned long flags; |  | ||||||
| +	u32 rise, fall; |  | ||||||
| + |  | ||||||
| +	rg = (struct ralink_gpio_chip *) d->domain->host_data; |  | ||||||
| +	rise = rt_gpio_r32(rg, GPIO_REG_RENA); |  | ||||||
| +	fall = rt_gpio_r32(rg, GPIO_REG_FENA); |  | ||||||
| + |  | ||||||
| +	spin_lock_irqsave(&rg->lock, flags); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_FENA, fall & ~BIT(d->hwirq)); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_RENA, rise & ~BIT(d->hwirq)); |  | ||||||
| +	spin_unlock_irqrestore(&rg->lock, flags); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_irq_type(struct irq_data *d, unsigned int type) |  | ||||||
| +{ |  | ||||||
| +	struct ralink_gpio_chip *rg; |  | ||||||
| +	u32 mask = BIT(d->hwirq); |  | ||||||
| + |  | ||||||
| +	rg = (struct ralink_gpio_chip *) d->domain->host_data; |  | ||||||
| + |  | ||||||
| +	if (type == IRQ_TYPE_PROBE) { |  | ||||||
| +		if ((rg->rising | rg->falling) & mask) |  | ||||||
| +			return 0; |  | ||||||
| + |  | ||||||
| +		type = IRQ_TYPE_EDGE_RISING | IRQ_TYPE_EDGE_FALLING; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (type & IRQ_TYPE_EDGE_RISING) |  | ||||||
| +		rg->rising |= mask; |  | ||||||
| +	else |  | ||||||
| +		rg->rising &= ~mask; |  | ||||||
| + |  | ||||||
| +	if (type & IRQ_TYPE_EDGE_FALLING) |  | ||||||
| +		rg->falling |= mask; |  | ||||||
| +	else |  | ||||||
| +		rg->falling &= ~mask; |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static struct irq_chip ralink_gpio_irq_chip = { |  | ||||||
| +	.name		= "GPIO", |  | ||||||
| +	.irq_unmask	= ralink_gpio_irq_unmask, |  | ||||||
| +	.irq_mask	= ralink_gpio_irq_mask, |  | ||||||
| +	.irq_mask_ack	= ralink_gpio_irq_mask, |  | ||||||
| +	.irq_set_type	= ralink_gpio_irq_type, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int gpio_map(struct irq_domain *d, unsigned int irq, irq_hw_number_t hw) |  | ||||||
| +{ |  | ||||||
| +	irq_set_chip_and_handler(irq, &ralink_gpio_irq_chip, handle_level_irq); |  | ||||||
| +	irq_set_handler_data(irq, d); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct irq_domain_ops irq_domain_ops = { |  | ||||||
| +	.xlate = irq_domain_xlate_onecell, |  | ||||||
| +	.map = gpio_map, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static void ralink_gpio_irq_init(struct device_node *np, |  | ||||||
| +				 struct ralink_gpio_chip *rg) |  | ||||||
| +{ |  | ||||||
| +	if (irq_map_count >= MAP_MAX) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	rg->irq = irq_of_parse_and_map(np, 0); |  | ||||||
| +	if (!rg->irq) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	rg->domain = irq_domain_add_linear(np, rg->chip.ngpio, |  | ||||||
| +					   &irq_domain_ops, rg); |  | ||||||
| +	if (!rg->domain) { |  | ||||||
| +		dev_err(rg->chip.parent, "irq_domain_add_linear failed\n"); |  | ||||||
| +		return; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	irq_map[irq_map_count++] = rg->domain; |  | ||||||
| + |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_RENA, 0x0); |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_FENA, 0x0); |  | ||||||
| + |  | ||||||
| +	if (!atomic_read(&irq_refcount)) |  | ||||||
| +		irq_set_chained_handler(rg->irq, ralink_gpio_irq_handler); |  | ||||||
| +	atomic_inc(&irq_refcount); |  | ||||||
| + |  | ||||||
| +	dev_info(rg->chip.parent, "registering %d irq handlers\n", rg->chip.ngpio); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int ralink_gpio_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct device_node *np = pdev->dev.of_node; |  | ||||||
| +	struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |  | ||||||
| +	struct ralink_gpio_chip *rg; |  | ||||||
| +	const __be32 *ngpio, *gpiobase; |  | ||||||
| + |  | ||||||
| +	if (!res) { |  | ||||||
| +		dev_err(&pdev->dev, "failed to find resource\n"); |  | ||||||
| +		return -ENOMEM; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	rg = devm_kzalloc(&pdev->dev, |  | ||||||
| +			sizeof(struct ralink_gpio_chip), GFP_KERNEL); |  | ||||||
| +	if (!rg) |  | ||||||
| +		return -ENOMEM; |  | ||||||
| + |  | ||||||
| +	rg->membase = devm_ioremap_resource(&pdev->dev, res); |  | ||||||
| +	if (!rg->membase) { |  | ||||||
| +		dev_err(&pdev->dev, "cannot remap I/O memory region\n"); |  | ||||||
| +		return -ENOMEM; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (of_property_read_u8_array(np, "ralink,register-map", |  | ||||||
| +			rg->regs, GPIO_REG_MAX)) { |  | ||||||
| +		dev_err(&pdev->dev, "failed to read register definition\n"); |  | ||||||
| +		return -EINVAL; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	ngpio = of_get_property(np, "ngpios", NULL); |  | ||||||
| +	if (!ngpio) { |  | ||||||
| +		dev_err(&pdev->dev, "failed to read number of pins\n"); |  | ||||||
| +		return -EINVAL; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	gpiobase = of_get_property(np, "ralink,gpio-base", NULL); |  | ||||||
| +	if (gpiobase) |  | ||||||
| +		rg->chip.base = be32_to_cpu(*gpiobase); |  | ||||||
| +	else |  | ||||||
| +		rg->chip.base = -1; |  | ||||||
| + |  | ||||||
| +	spin_lock_init(&rg->lock); |  | ||||||
| + |  | ||||||
| +	rg->chip.parent = &pdev->dev; |  | ||||||
| +	rg->chip.label = dev_name(&pdev->dev); |  | ||||||
| +	rg->chip.of_node = np; |  | ||||||
| +	rg->chip.ngpio = be32_to_cpu(*ngpio); |  | ||||||
| +	rg->chip.direction_input = ralink_gpio_direction_input; |  | ||||||
| +	rg->chip.direction_output = ralink_gpio_direction_output; |  | ||||||
| +	rg->chip.get = ralink_gpio_get; |  | ||||||
| +	rg->chip.set = ralink_gpio_set; |  | ||||||
| +	rg->chip.request = gpiochip_generic_request; |  | ||||||
| +	rg->chip.to_irq = ralink_gpio_to_irq; |  | ||||||
| +	rg->chip.free = gpiochip_generic_free; |  | ||||||
| + |  | ||||||
| +	/* set polarity to low for all lines */ |  | ||||||
| +	rt_gpio_w32(rg, GPIO_REG_POL, 0); |  | ||||||
| + |  | ||||||
| +	dev_info(&pdev->dev, "registering %d gpios\n", rg->chip.ngpio); |  | ||||||
| + |  | ||||||
| +	ralink_gpio_irq_init(np, rg); |  | ||||||
| + |  | ||||||
| +	return gpiochip_add(&rg->chip); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct of_device_id ralink_gpio_match[] = { |  | ||||||
| +	{ .compatible = "ralink,rt2880-gpio" }, |  | ||||||
| +	{}, |  | ||||||
| +}; |  | ||||||
| +MODULE_DEVICE_TABLE(of, ralink_gpio_match); |  | ||||||
| + |  | ||||||
| +static struct platform_driver ralink_gpio_driver = { |  | ||||||
| +	.probe = ralink_gpio_probe, |  | ||||||
| +	.driver = { |  | ||||||
| +		.name = "rt2880_gpio", |  | ||||||
| +		.owner = THIS_MODULE, |  | ||||||
| +		.of_match_table = ralink_gpio_match, |  | ||||||
| +	}, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int __init ralink_gpio_init(void) |  | ||||||
| +{ |  | ||||||
| +	return platform_driver_register(&ralink_gpio_driver); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +subsys_initcall(ralink_gpio_init); |  | ||||||
| @@ -1,44 +0,0 @@ | |||||||
| From 57fa7f2f4ef6f78ce1d30509c0d111aa3791b524 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Daniel Santos <daniel.santos@pobox.com> |  | ||||||
| Date: Sun, 4 Nov 2018 20:24:32 -0600 |  | ||||||
| Subject: gpio-ralink: Add support for GPIO as interrupt-controller |  | ||||||
|  |  | ||||||
| Signed-off-by: Daniel Santos <daniel.santos@pobox.com> |  | ||||||
| --- |  | ||||||
|  Documentation/devicetree/bindings/gpio/gpio-ralink.txt | 6 ++++++ |  | ||||||
|  drivers/gpio/gpio-ralink.c                             | 2 +- |  | ||||||
|  2 files changed, 7 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/Documentation/devicetree/bindings/gpio/gpio-ralink.txt |  | ||||||
| +++ b/Documentation/devicetree/bindings/gpio/gpio-ralink.txt |  | ||||||
| @@ -17,6 +17,9 @@ Required properties: |  | ||||||
|   |  | ||||||
|  Optional properties: |  | ||||||
|  - ralink,gpio-base : Specify the GPIO chips base number |  | ||||||
| +- interrupt-controller : marks this as an interrupt controller |  | ||||||
| +- #interrupt-cells : a standard two-cell interrupt flag, see |  | ||||||
| +  interrupt-controller/interrupts.txt |  | ||||||
|   |  | ||||||
|  Example: |  | ||||||
|   |  | ||||||
| @@ -28,6 +31,9 @@ Example: |  | ||||||
|   |  | ||||||
|  		reg = <0x600 0x34>; |  | ||||||
|   |  | ||||||
| +		interrupt-controller; |  | ||||||
| +		#interrupt-cells = <2>; |  | ||||||
| + |  | ||||||
|  		interrupt-parent = <&intc>; |  | ||||||
|  		interrupts = <6>; |  | ||||||
|   |  | ||||||
| --- a/drivers/gpio/gpio-ralink.c |  | ||||||
| +++ b/drivers/gpio/gpio-ralink.c |  | ||||||
| @@ -220,7 +220,7 @@ static int gpio_map(struct irq_domain *d |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static const struct irq_domain_ops irq_domain_ops = { |  | ||||||
| -	.xlate = irq_domain_xlate_onecell, |  | ||||||
| +	.xlate = irq_domain_xlate_twocell, |  | ||||||
|  	.map = gpio_map, |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| @@ -1,246 +0,0 @@ | |||||||
| From 975e76214cd2516eb6cfff4c3eec581872645e88 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Thu, 19 Sep 2013 01:50:59 +0200 |  | ||||||
| Subject: [PATCH 31/53] uvc: add iPassion iP2970 support |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/media/usb/uvc/uvc_driver.c |   12 +++ |  | ||||||
|  drivers/media/usb/uvc/uvc_status.c |    2 + |  | ||||||
|  drivers/media/usb/uvc/uvc_video.c  |  147 ++++++++++++++++++++++++++++++++++++ |  | ||||||
|  drivers/media/usb/uvc/uvcvideo.h   |    5 +- |  | ||||||
|  4 files changed, 165 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/media/usb/uvc/uvc_driver.c |  | ||||||
| +++ b/drivers/media/usb/uvc/uvc_driver.c |  | ||||||
| @@ -2916,6 +2916,18 @@ static const struct usb_device_id uvc_id |  | ||||||
|  	  .bInterfaceSubClass	= 1, |  | ||||||
|  	  .bInterfaceProtocol	= 0, |  | ||||||
|  	  .driver_info		= UVC_INFO_META(V4L2_META_FMT_D4XX) }, |  | ||||||
| +	/* iPassion iP2970 */ |  | ||||||
| +	{ .match_flags          = USB_DEVICE_ID_MATCH_DEVICE |  | ||||||
| +				| USB_DEVICE_ID_MATCH_INT_INFO, |  | ||||||
| +	 .idVendor		= 0x1B3B, |  | ||||||
| +	 .idProduct		= 0x2970, |  | ||||||
| +	 .bInterfaceClass	= USB_CLASS_VIDEO, |  | ||||||
| +	 .bInterfaceSubClass	= 1, |  | ||||||
| +	 .bInterfaceProtocol	= 0, |  | ||||||
| +	 .driver_info		= UVC_QUIRK_PROBE_MINMAX |  | ||||||
| +				| UVC_QUIRK_STREAM_NO_FID |  | ||||||
| +				| UVC_QUIRK_MOTION |  | ||||||
| +				| UVC_QUIRK_SINGLE_ISO }, |  | ||||||
|  	/* Generic USB Video Class */ |  | ||||||
|  	{ USB_INTERFACE_INFO(USB_CLASS_VIDEO, 1, UVC_PC_PROTOCOL_UNDEFINED) }, |  | ||||||
|  	{ USB_INTERFACE_INFO(USB_CLASS_VIDEO, 1, UVC_PC_PROTOCOL_15) }, |  | ||||||
| --- a/drivers/media/usb/uvc/uvc_status.c |  | ||||||
| +++ b/drivers/media/usb/uvc/uvc_status.c |  | ||||||
| @@ -223,6 +223,7 @@ static void uvc_status_complete(struct u |  | ||||||
|  			if (uvc_event_control(urb, status, len)) |  | ||||||
|  				/* The URB will be resubmitted in work context. */ |  | ||||||
|  				return; |  | ||||||
| +			dev->motion = 1; |  | ||||||
|  			break; |  | ||||||
|  		} |  | ||||||
|   |  | ||||||
| @@ -271,6 +272,7 @@ int uvc_status_init(struct uvc_device *d |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	pipe = usb_rcvintpipe(dev->udev, ep->desc.bEndpointAddress); |  | ||||||
| +	dev->motion = 0; |  | ||||||
|   |  | ||||||
|  	/* For high-speed interrupt endpoints, the bInterval value is used as |  | ||||||
|  	 * an exponent of two. Some developers forgot about it. |  | ||||||
| --- a/drivers/media/usb/uvc/uvc_video.c |  | ||||||
| +++ b/drivers/media/usb/uvc/uvc_video.c |  | ||||||
| @@ -16,6 +16,11 @@ |  | ||||||
|  #include <linux/wait.h> |  | ||||||
|  #include <linux/atomic.h> |  | ||||||
|  #include <asm/unaligned.h> |  | ||||||
| +#include <linux/skbuff.h> |  | ||||||
| +#include <linux/kobject.h> |  | ||||||
| +#include <linux/netlink.h> |  | ||||||
| +#include <linux/kobject.h> |  | ||||||
| +#include <linux/workqueue.h> |  | ||||||
|   |  | ||||||
|  #include <media/v4l2-common.h> |  | ||||||
|   |  | ||||||
| @@ -1188,9 +1193,149 @@ static void uvc_video_decode_data(struct |  | ||||||
|  	uvc_urb->async_operations++; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +struct bh_priv { |  | ||||||
| +	unsigned long	seen; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +struct bh_event { |  | ||||||
| +	const char		*name; |  | ||||||
| +	struct sk_buff		*skb; |  | ||||||
| +	struct work_struct	work; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +#define BH_ERR(fmt, args...) printk(KERN_ERR "%s: " fmt, "webcam", ##args ) |  | ||||||
| +#define BH_DBG(fmt, args...) do {} while (0) |  | ||||||
| +#define BH_SKB_SIZE     2048 |  | ||||||
| + |  | ||||||
| +extern u64 uevent_next_seqnum(void); |  | ||||||
| +static int seen = 0; |  | ||||||
| + |  | ||||||
| +static int bh_event_add_var(struct bh_event *event, int argv, |  | ||||||
| +		const char *format, ...) |  | ||||||
| +{ |  | ||||||
| +	static char buf[128]; |  | ||||||
| +	char *s; |  | ||||||
| +	va_list args; |  | ||||||
| +	int len; |  | ||||||
| + |  | ||||||
| +	if (argv) |  | ||||||
| +		return 0; |  | ||||||
| + |  | ||||||
| +	va_start(args, format); |  | ||||||
| +	len = vsnprintf(buf, sizeof(buf), format, args); |  | ||||||
| +	va_end(args); |  | ||||||
| + |  | ||||||
| +	if (len >= sizeof(buf)) { |  | ||||||
| +		BH_ERR("buffer size too small\n"); |  | ||||||
| +		WARN_ON(1); |  | ||||||
| +		return -ENOMEM; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	s = skb_put(event->skb, len + 1); |  | ||||||
| +	strcpy(s, buf); |  | ||||||
| + |  | ||||||
| +	BH_DBG("added variable '%s'\n", s); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int motion_hotplug_fill_event(struct bh_event *event) |  | ||||||
| +{ |  | ||||||
| +	int s = jiffies; |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	if (!seen) |  | ||||||
| +		seen = jiffies; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "HOME=%s", "/"); |  | ||||||
| +	if (ret) |  | ||||||
| +		return ret; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "PATH=%s", |  | ||||||
| +		"/sbin:/bin:/usr/sbin:/usr/bin"); |  | ||||||
| +	if (ret) |  | ||||||
| +		return ret; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "SUBSYSTEM=usb"); |  | ||||||
| +	if (ret) |  | ||||||
| +		return ret; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "ACTION=motion"); |  | ||||||
| +	if (ret) |  | ||||||
| +		return ret; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "SEEN=%d", s - seen); |  | ||||||
| +	if (ret) |  | ||||||
| +		return ret; |  | ||||||
| +	seen = s; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "SEQNUM=%llu", uevent_next_seqnum()); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void motion_hotplug_work(struct work_struct *work) |  | ||||||
| +{ |  | ||||||
| +	struct bh_event *event = container_of(work, struct bh_event, work); |  | ||||||
| +	int ret = 0; |  | ||||||
| + |  | ||||||
| +	event->skb = alloc_skb(BH_SKB_SIZE, GFP_KERNEL); |  | ||||||
| +	if (!event->skb) |  | ||||||
| +		goto out_free_event; |  | ||||||
| + |  | ||||||
| +	ret = bh_event_add_var(event, 0, "%s@", "add"); |  | ||||||
| +	if (ret) |  | ||||||
| +		goto out_free_skb; |  | ||||||
| + |  | ||||||
| +	ret = motion_hotplug_fill_event(event); |  | ||||||
| +	if (ret) |  | ||||||
| +		goto out_free_skb; |  | ||||||
| + |  | ||||||
| +	NETLINK_CB(event->skb).dst_group = 1; |  | ||||||
| +	broadcast_uevent(event->skb, 0, 1, GFP_KERNEL); |  | ||||||
| + |  | ||||||
| +out_free_skb: |  | ||||||
| +	if (ret) { |  | ||||||
| +		BH_ERR("work error %d\n", ret); |  | ||||||
| +		kfree_skb(event->skb); |  | ||||||
| +	} |  | ||||||
| +out_free_event: |  | ||||||
| +	kfree(event); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int motion_hotplug_create_event(void) |  | ||||||
| +{ |  | ||||||
| +	struct bh_event *event; |  | ||||||
| + |  | ||||||
| +	event = kzalloc(sizeof(*event), GFP_KERNEL); |  | ||||||
| +	if (!event) |  | ||||||
| +		return -ENOMEM; |  | ||||||
| + |  | ||||||
| +	event->name = "motion"; |  | ||||||
| + |  | ||||||
| +	INIT_WORK(&event->work, (void *)(void *)motion_hotplug_work); |  | ||||||
| +	schedule_work(&event->work); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +#define MOTION_FLAG_OFFSET	4 |  | ||||||
|  static void uvc_video_decode_end(struct uvc_streaming *stream, |  | ||||||
|  		struct uvc_buffer *buf, const u8 *data, int len) |  | ||||||
|  { |  | ||||||
| +	if ((stream->dev->quirks & UVC_QUIRK_MOTION) && |  | ||||||
| +			(data[len - 2] == 0xff) && (data[len - 1] == 0xd9)) { |  | ||||||
| +		u8 *mem; |  | ||||||
| +		buf->state = UVC_BUF_STATE_READY; |  | ||||||
| +		mem = (u8 *) (buf->mem + MOTION_FLAG_OFFSET); |  | ||||||
| +		if ( stream->dev->motion ) { |  | ||||||
| +			stream->dev->motion = 0; |  | ||||||
| +			motion_hotplug_create_event(); |  | ||||||
| +		} else { |  | ||||||
| +			*mem &= 0x7f; |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	/* Mark the buffer as done if the EOF marker is set. */ |  | ||||||
|  	if (data[1] & UVC_STREAM_EOF && buf->bytesused != 0) { |  | ||||||
|  		uvc_trace(UVC_TRACE_FRAME, "Frame complete (EOF found).\n"); |  | ||||||
| @@ -1747,6 +1892,8 @@ static int uvc_init_video_isoc(struct uv |  | ||||||
|  	if (npackets == 0) |  | ||||||
|  		return -ENOMEM; |  | ||||||
|   |  | ||||||
| +	if (stream->dev->quirks & UVC_QUIRK_SINGLE_ISO) |  | ||||||
| +		npackets = 1; |  | ||||||
|  	size = npackets * psize; |  | ||||||
|   |  | ||||||
|  	for_each_uvc_urb(uvc_urb, stream) { |  | ||||||
| --- a/drivers/media/usb/uvc/uvcvideo.h |  | ||||||
| +++ b/drivers/media/usb/uvc/uvcvideo.h |  | ||||||
| @@ -199,7 +199,9 @@ |  | ||||||
|  #define UVC_QUIRK_RESTORE_CTRLS_ON_INIT	0x00000400 |  | ||||||
|  #define UVC_QUIRK_FORCE_Y8		0x00000800 |  | ||||||
|  #define UVC_QUIRK_FORCE_BPP		0x00001000 |  | ||||||
| - |  | ||||||
| +#define UVC_QUIRK_MOTION		0x00001000 |  | ||||||
| +#define UVC_QUIRK_SINGLE_ISO		0x00002000 |  | ||||||
| +  |  | ||||||
|  /* Format flags */ |  | ||||||
|  #define UVC_FMT_FLAG_COMPRESSED		0x00000001 |  | ||||||
|  #define UVC_FMT_FLAG_STREAM		0x00000002 |  | ||||||
| @@ -666,6 +668,7 @@ struct uvc_device { |  | ||||||
|  	u8 *status; |  | ||||||
|  	struct input_dev *input; |  | ||||||
|  	char input_phys[64]; |  | ||||||
| +	int motion; |  | ||||||
|   |  | ||||||
|  	struct uvc_ctrl_work { |  | ||||||
|  		struct work_struct work; |  | ||||||
| @@ -1,20 +0,0 @@ | |||||||
| From ee9081b2726a5ca8cde5497afdc5425e21ff8f8b Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 15 Jul 2013 00:39:21 +0200 |  | ||||||
| Subject: [PATCH 37/53] mtd: cfi cmdset 0002 force word write |  | ||||||
|  |  | ||||||
| --- |  | ||||||
|  drivers/mtd/chips/cfi_cmdset_0002.c |    9 +++++++-- |  | ||||||
|  1 file changed, 7 insertions(+), 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/mtd/chips/cfi_cmdset_0002.c |  | ||||||
| +++ b/drivers/mtd/chips/cfi_cmdset_0002.c |  | ||||||
| @@ -40,7 +40,7 @@ |  | ||||||
|  #include <linux/mtd/xip.h> |  | ||||||
|   |  | ||||||
|  #define AMD_BOOTLOC_BUG |  | ||||||
| -#define FORCE_WORD_WRITE 0 |  | ||||||
| +#define FORCE_WORD_WRITE 1 |  | ||||||
|   |  | ||||||
|  #define MAX_RETRIES 3 |  | ||||||
|   |  | ||||||
| @@ -1,44 +0,0 @@ | |||||||
| From da6015e7f19d749f135f7ac55c4ec47b06faa868 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Fri, 9 Aug 2013 20:12:59 +0200 |  | ||||||
| Subject: [PATCH 41/53] DT: Add documentation for spi-rt2880 |  | ||||||
|  |  | ||||||
| Describe the SPI master found on the MIPS based Ralink RT2880 SoC. |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  .../devicetree/bindings/spi/spi-rt2880.txt         |   28 ++++++++++++++++++++ |  | ||||||
|  1 file changed, 28 insertions(+) |  | ||||||
|  create mode 100644 Documentation/devicetree/bindings/spi/spi-rt2880.txt |  | ||||||
|  |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/Documentation/devicetree/bindings/spi/spi-rt2880.txt |  | ||||||
| @@ -0,0 +1,28 @@ |  | ||||||
| +Ralink SoC RT2880 SPI master controller. |  | ||||||
| + |  | ||||||
| +This SPI controller is found on most wireless SoCs made by ralink. |  | ||||||
| + |  | ||||||
| +Required properties: |  | ||||||
| +- compatible : "ralink,rt2880-spi" |  | ||||||
| +- reg : The register base for the controller. |  | ||||||
| +- #address-cells : <1>, as required by generic SPI binding. |  | ||||||
| +- #size-cells : <0>, also as required by generic SPI binding. |  | ||||||
| + |  | ||||||
| +Child nodes as per the generic SPI binding. |  | ||||||
| + |  | ||||||
| +Example: |  | ||||||
| + |  | ||||||
| +	spi@b00 { |  | ||||||
| +		compatible = "ralink,rt2880-spi"; |  | ||||||
| +		reg = <0xb00 0x100>; |  | ||||||
| + |  | ||||||
| +		#address-cells = <1>; |  | ||||||
| +		#size-cells = <0>; |  | ||||||
| + |  | ||||||
| +		m25p80@0 { |  | ||||||
| +			compatible = "m25p80"; |  | ||||||
| +			reg = <0>; |  | ||||||
| +			spi-max-frequency = <10000000>; |  | ||||||
| +		}; |  | ||||||
| +	}; |  | ||||||
| + |  | ||||||
| @@ -1,574 +0,0 @@ | |||||||
| From 683af4ebb91a1600df1946ac4769d916b8a1be65 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 27 Jul 2014 11:15:12 +0100 |  | ||||||
| Subject: [PATCH 42/53] SPI: ralink: add Ralink SoC spi driver |  | ||||||
|  |  | ||||||
| Add the driver needed to make SPI work on Ralink SoC. |  | ||||||
|  |  | ||||||
| Signed-off-by: Gabor Juhos <juhosg@openwrt.org> |  | ||||||
| Acked-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/spi/Kconfig      |    6 + |  | ||||||
|  drivers/spi/Makefile     |    1 + |  | ||||||
|  drivers/spi/spi-rt2880.c |  530 ++++++++++++++++++++++++++++++++++++++++++++++ |  | ||||||
|  3 files changed, 537 insertions(+) |  | ||||||
|  create mode 100644 drivers/spi/spi-rt2880.c |  | ||||||
|  |  | ||||||
| --- a/drivers/spi/Kconfig |  | ||||||
| +++ b/drivers/spi/Kconfig |  | ||||||
| @@ -605,6 +605,12 @@ config SPI_QCOM_GENI |  | ||||||
|  	  This driver can also be built as a module.  If so, the module |  | ||||||
|  	  will be called spi-geni-qcom. |  | ||||||
|   |  | ||||||
| +config SPI_RT2880 |  | ||||||
| +	tristate "Ralink RT288x SPI Controller" |  | ||||||
| +	depends on RALINK |  | ||||||
| +	help |  | ||||||
| +	  This selects a driver for the Ralink RT288x/RT305x SPI Controller. |  | ||||||
| + |  | ||||||
|  config SPI_S3C24XX |  | ||||||
|  	tristate "Samsung S3C24XX series SPI" |  | ||||||
|  	depends on ARCH_S3C24XX |  | ||||||
| --- a/drivers/spi/Makefile |  | ||||||
| +++ b/drivers/spi/Makefile |  | ||||||
| @@ -87,6 +87,7 @@ obj-$(CONFIG_SPI_QUP)			+= spi-qup.o |  | ||||||
|  obj-$(CONFIG_SPI_ROCKCHIP)		+= spi-rockchip.o |  | ||||||
|  obj-$(CONFIG_SPI_RB4XX)			+= spi-rb4xx.o |  | ||||||
|  obj-$(CONFIG_SPI_RSPI)			+= spi-rspi.o |  | ||||||
| +obj-$(CONFIG_SPI_RT2880)		+= spi-rt2880.o |  | ||||||
|  obj-$(CONFIG_SPI_S3C24XX)		+= spi-s3c24xx-hw.o |  | ||||||
|  spi-s3c24xx-hw-y			:= spi-s3c24xx.o |  | ||||||
|  spi-s3c24xx-hw-$(CONFIG_SPI_S3C24XX_FIQ) += spi-s3c24xx-fiq.o |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/drivers/spi/spi-rt2880.c |  | ||||||
| @@ -0,0 +1,530 @@ |  | ||||||
| +/* |  | ||||||
| + * spi-rt2880.c -- Ralink RT288x/RT305x SPI controller driver |  | ||||||
| + * |  | ||||||
| + * Copyright (C) 2011 Sergiy <piratfm@gmail.com> |  | ||||||
| + * Copyright (C) 2011-2013 Gabor Juhos <juhosg@openwrt.org> |  | ||||||
| + * |  | ||||||
| + * Some parts are based on spi-orion.c: |  | ||||||
| + *   Author: Shadi Ammouri <shadi@marvell.com> |  | ||||||
| + *   Copyright (C) 2007-2008 Marvell Ltd. |  | ||||||
| + * |  | ||||||
| + * 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. |  | ||||||
| + */ |  | ||||||
| + |  | ||||||
| +#include <linux/init.h> |  | ||||||
| +#include <linux/module.h> |  | ||||||
| +#include <linux/clk.h> |  | ||||||
| +#include <linux/err.h> |  | ||||||
| +#include <linux/delay.h> |  | ||||||
| +#include <linux/io.h> |  | ||||||
| +#include <linux/reset.h> |  | ||||||
| +#include <linux/spi/spi.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
| +#include <linux/gpio.h> |  | ||||||
| + |  | ||||||
| +#define DRIVER_NAME			"spi-rt2880" |  | ||||||
| + |  | ||||||
| +#define RAMIPS_SPI_STAT			0x00 |  | ||||||
| +#define RAMIPS_SPI_CFG			0x10 |  | ||||||
| +#define RAMIPS_SPI_CTL			0x14 |  | ||||||
| +#define RAMIPS_SPI_DATA			0x20 |  | ||||||
| +#define RAMIPS_SPI_ADDR			0x24 |  | ||||||
| +#define RAMIPS_SPI_BS			0x28 |  | ||||||
| +#define RAMIPS_SPI_USER			0x2C |  | ||||||
| +#define RAMIPS_SPI_TXFIFO		0x30 |  | ||||||
| +#define RAMIPS_SPI_RXFIFO		0x34 |  | ||||||
| +#define RAMIPS_SPI_FIFO_STAT		0x38 |  | ||||||
| +#define RAMIPS_SPI_MODE			0x3C |  | ||||||
| +#define RAMIPS_SPI_DEV_OFFSET		0x40 |  | ||||||
| +#define RAMIPS_SPI_DMA			0x80 |  | ||||||
| +#define RAMIPS_SPI_DMASTAT		0x84 |  | ||||||
| +#define RAMIPS_SPI_ARBITER		0xF0 |  | ||||||
| + |  | ||||||
| +/* SPISTAT register bit field */ |  | ||||||
| +#define SPISTAT_BUSY			BIT(0) |  | ||||||
| + |  | ||||||
| +/* SPICFG register bit field */ |  | ||||||
| +#define SPICFG_ADDRMODE			BIT(12) |  | ||||||
| +#define SPICFG_RXENVDIS			BIT(11) |  | ||||||
| +#define SPICFG_RXCAP			BIT(10) |  | ||||||
| +#define SPICFG_SPIENMODE		BIT(9) |  | ||||||
| +#define SPICFG_MSBFIRST			BIT(8) |  | ||||||
| +#define SPICFG_SPICLKPOL		BIT(6) |  | ||||||
| +#define SPICFG_RXCLKEDGE_FALLING	BIT(5) |  | ||||||
| +#define SPICFG_TXCLKEDGE_FALLING	BIT(4) |  | ||||||
| +#define SPICFG_HIZSPI			BIT(3) |  | ||||||
| +#define SPICFG_SPICLK_PRESCALE_MASK	0x7 |  | ||||||
| +#define SPICFG_SPICLK_DIV2		0 |  | ||||||
| +#define SPICFG_SPICLK_DIV4		1 |  | ||||||
| +#define SPICFG_SPICLK_DIV8		2 |  | ||||||
| +#define SPICFG_SPICLK_DIV16		3 |  | ||||||
| +#define SPICFG_SPICLK_DIV32		4 |  | ||||||
| +#define SPICFG_SPICLK_DIV64		5 |  | ||||||
| +#define SPICFG_SPICLK_DIV128		6 |  | ||||||
| +#define SPICFG_SPICLK_DISABLE		7 |  | ||||||
| + |  | ||||||
| +/* SPICTL register bit field */ |  | ||||||
| +#define SPICTL_START			BIT(4) |  | ||||||
| +#define SPICTL_HIZSDO			BIT(3) |  | ||||||
| +#define SPICTL_STARTWR			BIT(2) |  | ||||||
| +#define SPICTL_STARTRD			BIT(1) |  | ||||||
| +#define SPICTL_SPIENA			BIT(0) |  | ||||||
| + |  | ||||||
| +/* SPIUSER register bit field */ |  | ||||||
| +#define SPIUSER_USERMODE		BIT(21) |  | ||||||
| +#define SPIUSER_INSTR_PHASE		BIT(20) |  | ||||||
| +#define SPIUSER_ADDR_PHASE_MASK		0x7 |  | ||||||
| +#define SPIUSER_ADDR_PHASE_OFFSET	17 |  | ||||||
| +#define SPIUSER_MODE_PHASE		BIT(16) |  | ||||||
| +#define SPIUSER_DUMMY_PHASE_MASK	0x3 |  | ||||||
| +#define SPIUSER_DUMMY_PHASE_OFFSET	14 |  | ||||||
| +#define SPIUSER_DATA_PHASE_MASK		0x3 |  | ||||||
| +#define SPIUSER_DATA_PHASE_OFFSET	12 |  | ||||||
| +#define SPIUSER_DATA_READ		(BIT(0) << SPIUSER_DATA_PHASE_OFFSET) |  | ||||||
| +#define SPIUSER_DATA_WRITE		(BIT(1) << SPIUSER_DATA_PHASE_OFFSET) |  | ||||||
| +#define SPIUSER_ADDR_TYPE_OFFSET	9 |  | ||||||
| +#define SPIUSER_MODE_TYPE_OFFSET	6 |  | ||||||
| +#define SPIUSER_DUMMY_TYPE_OFFSET	3 |  | ||||||
| +#define SPIUSER_DATA_TYPE_OFFSET	0 |  | ||||||
| +#define SPIUSER_TRANSFER_MASK		0x7 |  | ||||||
| +#define SPIUSER_TRANSFER_SINGLE		BIT(0) |  | ||||||
| +#define SPIUSER_TRANSFER_DUAL		BIT(1) |  | ||||||
| +#define SPIUSER_TRANSFER_QUAD		BIT(2) |  | ||||||
| + |  | ||||||
| +#define SPIUSER_TRANSFER_TYPE(type) ( \ |  | ||||||
| +	(type << SPIUSER_ADDR_TYPE_OFFSET) | \ |  | ||||||
| +	(type << SPIUSER_MODE_TYPE_OFFSET) | \ |  | ||||||
| +	(type << SPIUSER_DUMMY_TYPE_OFFSET) | \ |  | ||||||
| +	(type << SPIUSER_DATA_TYPE_OFFSET) \ |  | ||||||
| +) |  | ||||||
| + |  | ||||||
| +/* SPIFIFOSTAT register bit field */ |  | ||||||
| +#define SPIFIFOSTAT_TXEMPTY		BIT(19) |  | ||||||
| +#define SPIFIFOSTAT_RXEMPTY		BIT(18) |  | ||||||
| +#define SPIFIFOSTAT_TXFULL		BIT(17) |  | ||||||
| +#define SPIFIFOSTAT_RXFULL		BIT(16) |  | ||||||
| +#define SPIFIFOSTAT_FIFO_MASK		0xff |  | ||||||
| +#define SPIFIFOSTAT_TX_OFFSET		8 |  | ||||||
| +#define SPIFIFOSTAT_RX_OFFSET		0 |  | ||||||
| + |  | ||||||
| +#define SPI_FIFO_DEPTH			16 |  | ||||||
| + |  | ||||||
| +/* SPIMODE register bit field */ |  | ||||||
| +#define SPIMODE_MODE_OFFSET		24 |  | ||||||
| +#define SPIMODE_DUMMY_OFFSET		0 |  | ||||||
| + |  | ||||||
| +/* SPIARB register bit field */ |  | ||||||
| +#define SPICTL_ARB_EN			BIT(31) |  | ||||||
| +#define SPICTL_CSCTL1			BIT(16) |  | ||||||
| +#define SPI1_POR			BIT(1) |  | ||||||
| +#define SPI0_POR			BIT(0) |  | ||||||
| + |  | ||||||
| +#define RT2880_SPI_MODE_BITS	(SPI_CPOL | SPI_CPHA | SPI_LSB_FIRST | \ |  | ||||||
| +		SPI_CS_HIGH) |  | ||||||
| + |  | ||||||
| +static atomic_t hw_reset_count = ATOMIC_INIT(0); |  | ||||||
| + |  | ||||||
| +struct rt2880_spi { |  | ||||||
| +	struct spi_master	*master; |  | ||||||
| +	void __iomem		*base; |  | ||||||
| +	u32			speed; |  | ||||||
| +	u16			wait_loops; |  | ||||||
| +	u16			mode; |  | ||||||
| +	struct clk		*clk; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static inline struct rt2880_spi *spidev_to_rt2880_spi(struct spi_device *spi) |  | ||||||
| +{ |  | ||||||
| +	return spi_master_get_devdata(spi->master); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline u32 rt2880_spi_read(struct rt2880_spi *rs, u32 reg) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(rs->base + reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void rt2880_spi_write(struct rt2880_spi *rs, u32 reg, |  | ||||||
| +		const u32 val) |  | ||||||
| +{ |  | ||||||
| +	iowrite32(val, rs->base + reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void rt2880_spi_setbits(struct rt2880_spi *rs, u32 reg, u32 mask) |  | ||||||
| +{ |  | ||||||
| +	void __iomem *addr = rs->base + reg; |  | ||||||
| + |  | ||||||
| +	iowrite32((ioread32(addr) | mask), addr); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void rt2880_spi_clrbits(struct rt2880_spi *rs, u32 reg, u32 mask) |  | ||||||
| +{ |  | ||||||
| +	void __iomem *addr = rs->base + reg; |  | ||||||
| + |  | ||||||
| +	iowrite32((ioread32(addr) & ~mask), addr); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static u32 rt2880_spi_baudrate_get(struct spi_device *spi, unsigned int speed) |  | ||||||
| +{ |  | ||||||
| +	struct rt2880_spi *rs = spidev_to_rt2880_spi(spi); |  | ||||||
| +	u32 rate; |  | ||||||
| +	u32 prescale; |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * the supported rates are: 2, 4, 8, ... 128 |  | ||||||
| +	 * round up as we look for equal or less speed |  | ||||||
| +	 */ |  | ||||||
| +	rate = DIV_ROUND_UP(clk_get_rate(rs->clk), speed); |  | ||||||
| +	rate = roundup_pow_of_two(rate); |  | ||||||
| + |  | ||||||
| +	/* Convert the rate to SPI clock divisor value.	*/ |  | ||||||
| +	prescale = ilog2(rate / 2); |  | ||||||
| + |  | ||||||
| +	/* some tolerance. double and add 100 */ |  | ||||||
| +	rs->wait_loops = (8 * HZ * loops_per_jiffy) / |  | ||||||
| +		(clk_get_rate(rs->clk) / rate); |  | ||||||
| +	rs->wait_loops = (rs->wait_loops << 1) + 100; |  | ||||||
| +	rs->speed = speed; |  | ||||||
| + |  | ||||||
| +	dev_dbg(&spi->dev, "speed: %lu/%u, rate: %u, prescal: %u, loops: %hu\n", |  | ||||||
| +			clk_get_rate(rs->clk) / rate, speed, rate, prescale, |  | ||||||
| +			rs->wait_loops); |  | ||||||
| + |  | ||||||
| +	return prescale; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static u32 get_arbiter_offset(struct spi_master *master) |  | ||||||
| +{ |  | ||||||
| +	u32 offset; |  | ||||||
| + |  | ||||||
| +	offset = RAMIPS_SPI_ARBITER; |  | ||||||
| +	if (master->bus_num == 1) |  | ||||||
| +		offset -= RAMIPS_SPI_DEV_OFFSET; |  | ||||||
| + |  | ||||||
| +	return offset; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void rt2880_spi_set_cs(struct spi_device *spi, bool enable) |  | ||||||
| +{ |  | ||||||
| +	struct rt2880_spi *rs = spidev_to_rt2880_spi(spi); |  | ||||||
| + |  | ||||||
| +	if (enable) |  | ||||||
| +		rt2880_spi_setbits(rs, RAMIPS_SPI_CTL, SPICTL_SPIENA); |  | ||||||
| +	else |  | ||||||
| +		rt2880_spi_clrbits(rs, RAMIPS_SPI_CTL, SPICTL_SPIENA); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_wait_ready(struct rt2880_spi *rs, int len) |  | ||||||
| +{ |  | ||||||
| +	int loop = rs->wait_loops * len; |  | ||||||
| + |  | ||||||
| +	while ((rt2880_spi_read(rs, RAMIPS_SPI_STAT) & SPISTAT_BUSY) && --loop) |  | ||||||
| +		cpu_relax(); |  | ||||||
| + |  | ||||||
| +	if (loop) |  | ||||||
| +		return 0; |  | ||||||
| + |  | ||||||
| +	return -ETIMEDOUT; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void rt2880_dump_reg(struct spi_master *master) |  | ||||||
| +{ |  | ||||||
| +	struct rt2880_spi *rs = spi_master_get_devdata(master); |  | ||||||
| + |  | ||||||
| +	dev_dbg(&master->dev, "stat: %08x, cfg: %08x, ctl: %08x, " \ |  | ||||||
| +			"data: %08x, arb: %08x\n", |  | ||||||
| +			rt2880_spi_read(rs, RAMIPS_SPI_STAT), |  | ||||||
| +			rt2880_spi_read(rs, RAMIPS_SPI_CFG), |  | ||||||
| +			rt2880_spi_read(rs, RAMIPS_SPI_CTL), |  | ||||||
| +			rt2880_spi_read(rs, RAMIPS_SPI_DATA), |  | ||||||
| +			rt2880_spi_read(rs, get_arbiter_offset(master))); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_transfer_one(struct spi_master *master, |  | ||||||
| +		struct spi_device *spi, struct spi_transfer *xfer) |  | ||||||
| +{ |  | ||||||
| +	struct rt2880_spi *rs = spi_master_get_devdata(master); |  | ||||||
| +	unsigned len; |  | ||||||
| +	const u8 *tx = xfer->tx_buf; |  | ||||||
| +	u8 *rx = xfer->rx_buf; |  | ||||||
| +	int err = 0; |  | ||||||
| + |  | ||||||
| +	/* change clock speed  */ |  | ||||||
| +	if (unlikely(rs->speed != xfer->speed_hz)) { |  | ||||||
| +		u32 reg; |  | ||||||
| +		reg = rt2880_spi_read(rs, RAMIPS_SPI_CFG); |  | ||||||
| +		reg &= ~SPICFG_SPICLK_PRESCALE_MASK; |  | ||||||
| +		reg |= rt2880_spi_baudrate_get(spi, xfer->speed_hz); |  | ||||||
| +		rt2880_spi_write(rs, RAMIPS_SPI_CFG, reg); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (tx) { |  | ||||||
| +		len = xfer->len; |  | ||||||
| +		while (len-- > 0) { |  | ||||||
| +			rt2880_spi_write(rs, RAMIPS_SPI_DATA, *tx++); |  | ||||||
| +			rt2880_spi_setbits(rs, RAMIPS_SPI_CTL, SPICTL_STARTWR); |  | ||||||
| +			err = rt2880_spi_wait_ready(rs, 1); |  | ||||||
| +			if (err) { |  | ||||||
| +				dev_err(&spi->dev, "TX failed, err=%d\n", err); |  | ||||||
| +				goto out; |  | ||||||
| +			} |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (rx) { |  | ||||||
| +		len = xfer->len; |  | ||||||
| +		while (len-- > 0) { |  | ||||||
| +			rt2880_spi_setbits(rs, RAMIPS_SPI_CTL, SPICTL_STARTRD); |  | ||||||
| +			err = rt2880_spi_wait_ready(rs, 1); |  | ||||||
| +			if (err) { |  | ||||||
| +				dev_err(&spi->dev, "RX failed, err=%d\n", err); |  | ||||||
| +				goto out; |  | ||||||
| +			} |  | ||||||
| +			*rx++ = (u8) rt2880_spi_read(rs, RAMIPS_SPI_DATA); |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +out: |  | ||||||
| +	return err; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +/* copy from spi.c */ |  | ||||||
| +static void spi_set_cs(struct spi_device *spi, bool enable) |  | ||||||
| +{ |  | ||||||
| +	if (spi->mode & SPI_CS_HIGH) |  | ||||||
| +		enable = !enable; |  | ||||||
| + |  | ||||||
| +	if (spi->cs_gpio >= 0) |  | ||||||
| +		gpio_set_value(spi->cs_gpio, !enable); |  | ||||||
| +	else if (spi->master->set_cs) |  | ||||||
| +		spi->master->set_cs(spi, !enable); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_setup(struct spi_device *spi) |  | ||||||
| +{ |  | ||||||
| +	struct spi_master *master = spi->master; |  | ||||||
| +	struct rt2880_spi *rs = spi_master_get_devdata(master); |  | ||||||
| +	u32 reg, old_reg, arbit_off; |  | ||||||
| + |  | ||||||
| +	if ((spi->max_speed_hz > master->max_speed_hz) || |  | ||||||
| +			(spi->max_speed_hz < master->min_speed_hz)) { |  | ||||||
| +		dev_err(&spi->dev, "invalide requested speed %d Hz\n", |  | ||||||
| +				spi->max_speed_hz); |  | ||||||
| +		return -EINVAL; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (!(master->bits_per_word_mask & |  | ||||||
| +				BIT(spi->bits_per_word - 1))) { |  | ||||||
| +		dev_err(&spi->dev, "invalide bits_per_word %d\n", |  | ||||||
| +				spi->bits_per_word); |  | ||||||
| +		return -EINVAL; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* the hardware seems can't work on mode0 force it to mode3 */ |  | ||||||
| +	if ((spi->mode & (SPI_CPOL | SPI_CPHA)) == SPI_MODE_0) { |  | ||||||
| +		dev_warn(&spi->dev, "force spi mode3\n"); |  | ||||||
| +		spi->mode |= SPI_MODE_3; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* chip polarity */ |  | ||||||
| +	arbit_off = get_arbiter_offset(master); |  | ||||||
| +	reg = old_reg = rt2880_spi_read(rs, arbit_off); |  | ||||||
| +	if (spi->mode & SPI_CS_HIGH) { |  | ||||||
| +		switch (master->bus_num) { |  | ||||||
| +		case 1: |  | ||||||
| +			reg |= SPI1_POR; |  | ||||||
| +			break; |  | ||||||
| +		default: |  | ||||||
| +			reg |= SPI0_POR; |  | ||||||
| +			break; |  | ||||||
| +		} |  | ||||||
| +	} else { |  | ||||||
| +		switch (master->bus_num) { |  | ||||||
| +		case 1: |  | ||||||
| +			reg &= ~SPI1_POR; |  | ||||||
| +			break; |  | ||||||
| +		default: |  | ||||||
| +			reg &= ~SPI0_POR; |  | ||||||
| +			break; |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* enable spi1 */ |  | ||||||
| +	if (master->bus_num == 1) |  | ||||||
| +		reg |= SPICTL_ARB_EN; |  | ||||||
| + |  | ||||||
| +	if (reg != old_reg) |  | ||||||
| +		rt2880_spi_write(rs, arbit_off, reg); |  | ||||||
| + |  | ||||||
| +	/* deselected the spi device */ |  | ||||||
| +	spi_set_cs(spi, false); |  | ||||||
| + |  | ||||||
| +	rt2880_dump_reg(master); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_prepare_message(struct spi_master *master, |  | ||||||
| +		struct spi_message *msg) |  | ||||||
| +{ |  | ||||||
| +	struct rt2880_spi *rs = spi_master_get_devdata(master); |  | ||||||
| +	struct spi_device *spi = msg->spi; |  | ||||||
| +	u32 reg; |  | ||||||
| + |  | ||||||
| +	if ((rs->mode == spi->mode) && (rs->speed == spi->max_speed_hz)) |  | ||||||
| +		return 0; |  | ||||||
| + |  | ||||||
| +#if 0 |  | ||||||
| +	/* set spido to tri-state */ |  | ||||||
| +	rt2880_spi_setbits(rs, RAMIPS_SPI_CTL, SPICTL_HIZSDO); |  | ||||||
| +#endif |  | ||||||
| + |  | ||||||
| +	reg = rt2880_spi_read(rs, RAMIPS_SPI_CFG); |  | ||||||
| + |  | ||||||
| +	reg &= ~(SPICFG_MSBFIRST | SPICFG_SPICLKPOL | |  | ||||||
| +			SPICFG_RXCLKEDGE_FALLING | |  | ||||||
| +			SPICFG_TXCLKEDGE_FALLING | |  | ||||||
| +			SPICFG_SPICLK_PRESCALE_MASK); |  | ||||||
| + |  | ||||||
| +	/* MSB */ |  | ||||||
| +	if (!(spi->mode & SPI_LSB_FIRST)) |  | ||||||
| +		reg |= SPICFG_MSBFIRST; |  | ||||||
| + |  | ||||||
| +	/* spi mode */ |  | ||||||
| +	switch (spi->mode & (SPI_CPOL | SPI_CPHA)) { |  | ||||||
| +	case SPI_MODE_0: |  | ||||||
| +		reg |= SPICFG_TXCLKEDGE_FALLING; |  | ||||||
| +		break; |  | ||||||
| +	case SPI_MODE_1: |  | ||||||
| +		reg |= SPICFG_RXCLKEDGE_FALLING; |  | ||||||
| +		break; |  | ||||||
| +	case SPI_MODE_2: |  | ||||||
| +		reg |= SPICFG_SPICLKPOL | SPICFG_RXCLKEDGE_FALLING; |  | ||||||
| +		break; |  | ||||||
| +	case SPI_MODE_3: |  | ||||||
| +		reg |= SPICFG_SPICLKPOL | SPICFG_TXCLKEDGE_FALLING; |  | ||||||
| +		break; |  | ||||||
| +	} |  | ||||||
| +	rs->mode = spi->mode; |  | ||||||
| + |  | ||||||
| +#if 0 |  | ||||||
| +	/* set spiclk and spiena to tri-state */ |  | ||||||
| +	reg |= SPICFG_HIZSPI; |  | ||||||
| +#endif |  | ||||||
| + |  | ||||||
| +	/* clock divide */ |  | ||||||
| +	reg |= rt2880_spi_baudrate_get(spi, spi->max_speed_hz); |  | ||||||
| + |  | ||||||
| +	rt2880_spi_write(rs, RAMIPS_SPI_CFG, reg); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct spi_master *master; |  | ||||||
| +	struct rt2880_spi *rs; |  | ||||||
| +	void __iomem *base; |  | ||||||
| +	struct resource *r; |  | ||||||
| +	struct clk *clk; |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	r = platform_get_resource(pdev, IORESOURCE_MEM, 0); |  | ||||||
| +	base = devm_ioremap_resource(&pdev->dev, r); |  | ||||||
| +	if (IS_ERR(base)) |  | ||||||
| +		return PTR_ERR(base); |  | ||||||
| + |  | ||||||
| +	clk = devm_clk_get(&pdev->dev, NULL); |  | ||||||
| +	if (IS_ERR(clk)) { |  | ||||||
| +		dev_err(&pdev->dev, "unable to get SYS clock\n"); |  | ||||||
| +		return PTR_ERR(clk); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	ret = clk_prepare_enable(clk); |  | ||||||
| +	if (ret) |  | ||||||
| +		goto err_clk; |  | ||||||
| + |  | ||||||
| +	master = spi_alloc_master(&pdev->dev, sizeof(*rs)); |  | ||||||
| +	if (master == NULL) { |  | ||||||
| +		dev_dbg(&pdev->dev, "master allocation failed\n"); |  | ||||||
| +		ret = -ENOMEM; |  | ||||||
| +		goto err_clk; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	master->dev.of_node = pdev->dev.of_node; |  | ||||||
| +	master->mode_bits = RT2880_SPI_MODE_BITS; |  | ||||||
| +	master->bits_per_word_mask = SPI_BPW_MASK(8); |  | ||||||
| +	master->min_speed_hz = clk_get_rate(clk) / 128; |  | ||||||
| +	master->max_speed_hz = clk_get_rate(clk) / 2; |  | ||||||
| +	master->flags = SPI_MASTER_HALF_DUPLEX; |  | ||||||
| +	master->setup = rt2880_spi_setup; |  | ||||||
| +	master->prepare_message = rt2880_spi_prepare_message; |  | ||||||
| +	master->set_cs = rt2880_spi_set_cs; |  | ||||||
| +	master->transfer_one = rt2880_spi_transfer_one, |  | ||||||
| + |  | ||||||
| +	dev_set_drvdata(&pdev->dev, master); |  | ||||||
| + |  | ||||||
| +	rs = spi_master_get_devdata(master); |  | ||||||
| +	rs->master = master; |  | ||||||
| +	rs->base = base; |  | ||||||
| +	rs->clk = clk; |  | ||||||
| + |  | ||||||
| +	if (atomic_inc_return(&hw_reset_count) == 1) |  | ||||||
| +		device_reset(&pdev->dev); |  | ||||||
| + |  | ||||||
| +	ret = devm_spi_register_master(&pdev->dev, master); |  | ||||||
| +	if (ret < 0) { |  | ||||||
| +		dev_err(&pdev->dev, "devm_spi_register_master error.\n"); |  | ||||||
| +		goto err_master; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| + |  | ||||||
| +err_master: |  | ||||||
| +	spi_master_put(master); |  | ||||||
| +	kfree(master); |  | ||||||
| +err_clk: |  | ||||||
| +	clk_disable_unprepare(clk); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt2880_spi_remove(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct spi_master *master; |  | ||||||
| +	struct rt2880_spi *rs; |  | ||||||
| + |  | ||||||
| +	master = dev_get_drvdata(&pdev->dev); |  | ||||||
| +	rs = spi_master_get_devdata(master); |  | ||||||
| + |  | ||||||
| +	clk_disable_unprepare(rs->clk); |  | ||||||
| +	atomic_dec(&hw_reset_count); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +MODULE_ALIAS("platform:" DRIVER_NAME); |  | ||||||
| + |  | ||||||
| +static const struct of_device_id rt2880_spi_match[] = { |  | ||||||
| +	{ .compatible = "ralink,rt2880-spi" }, |  | ||||||
| +	{}, |  | ||||||
| +}; |  | ||||||
| +MODULE_DEVICE_TABLE(of, rt2880_spi_match); |  | ||||||
| + |  | ||||||
| +static struct platform_driver rt2880_spi_driver = { |  | ||||||
| +	.driver = { |  | ||||||
| +		.name = DRIVER_NAME, |  | ||||||
| +		.owner = THIS_MODULE, |  | ||||||
| +		.of_match_table = rt2880_spi_match, |  | ||||||
| +	}, |  | ||||||
| +	.probe = rt2880_spi_probe, |  | ||||||
| +	.remove = rt2880_spi_remove, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +module_platform_driver(rt2880_spi_driver); |  | ||||||
| + |  | ||||||
| +MODULE_DESCRIPTION("Ralink SPI driver"); |  | ||||||
| +MODULE_AUTHOR("Sergiy <piratfm@gmail.com>"); |  | ||||||
| +MODULE_AUTHOR("Gabor Juhos <juhosg@openwrt.org>"); |  | ||||||
| +MODULE_LICENSE("GPL"); |  | ||||||
| @@ -1,507 +0,0 @@ | |||||||
| From 723b8beaabf3c3c4b1ce69480141f1e926f3f3b2 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 27 Jul 2014 09:52:56 +0100 |  | ||||||
| Subject: [PATCH 44/53] i2c: MIPS: adds ralink I2C driver |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  .../devicetree/bindings/i2c/i2c-ralink.txt         |   27 ++ |  | ||||||
|  drivers/i2c/busses/Kconfig                         |    4 + |  | ||||||
|  drivers/i2c/busses/Makefile                        |    1 + |  | ||||||
|  drivers/i2c/busses/i2c-ralink.c                    |  327 ++++++++++++++++++++ |  | ||||||
|  4 files changed, 359 insertions(+) |  | ||||||
|  create mode 100644 Documentation/devicetree/bindings/i2c/i2c-ralink.txt |  | ||||||
|  create mode 100644 drivers/i2c/busses/i2c-ralink.c |  | ||||||
|  |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/Documentation/devicetree/bindings/i2c/i2c-ralink.txt |  | ||||||
| @@ -0,0 +1,27 @@ |  | ||||||
| +I2C for Ralink platforms |  | ||||||
| + |  | ||||||
| +Required properties : |  | ||||||
| +- compatible : Must be "link,rt3052-i2c" |  | ||||||
| +- reg: physical base address of the controller and length of memory mapped |  | ||||||
| +     region. |  | ||||||
| +- #address-cells = <1>; |  | ||||||
| +- #size-cells = <0>; |  | ||||||
| + |  | ||||||
| +Optional properties: |  | ||||||
| +- Child nodes conforming to i2c bus binding |  | ||||||
| + |  | ||||||
| +Example : |  | ||||||
| + |  | ||||||
| +palmbus@10000000 { |  | ||||||
| +	i2c@900 { |  | ||||||
| +		compatible = "link,rt3052-i2c"; |  | ||||||
| +		reg = <0x900 0x100>; |  | ||||||
| +		#address-cells = <1>; |  | ||||||
| +		#size-cells = <0>; |  | ||||||
| + |  | ||||||
| +		hwmon@4b { |  | ||||||
| +			compatible = "national,lm92"; |  | ||||||
| +			reg = <0x4b>; |  | ||||||
| +		}; |  | ||||||
| +	}; |  | ||||||
| +}; |  | ||||||
| --- a/drivers/i2c/busses/Kconfig |  | ||||||
| +++ b/drivers/i2c/busses/Kconfig |  | ||||||
| @@ -922,6 +922,11 @@ config I2C_RK3X |  | ||||||
|  	  This driver can also be built as a module. If so, the module will |  | ||||||
|  	  be called i2c-rk3x. |  | ||||||
|   |  | ||||||
| +config I2C_RALINK |  | ||||||
| +	tristate "Ralink I2C Controller" |  | ||||||
| +	depends on RALINK && !SOC_MT7621 |  | ||||||
| +	select OF_I2C |  | ||||||
| + |  | ||||||
|  config HAVE_S3C2410_I2C |  | ||||||
|  	bool |  | ||||||
|  	help |  | ||||||
| --- a/drivers/i2c/busses/Makefile |  | ||||||
| +++ b/drivers/i2c/busses/Makefile |  | ||||||
| @@ -91,6 +91,7 @@ obj-$(CONFIG_I2C_PNX)		+= i2c-pnx.o |  | ||||||
|  obj-$(CONFIG_I2C_PUV3)		+= i2c-puv3.o |  | ||||||
|  obj-$(CONFIG_I2C_PXA)		+= i2c-pxa.o |  | ||||||
|  obj-$(CONFIG_I2C_PXA_PCI)	+= i2c-pxa-pci.o |  | ||||||
| +obj-$(CONFIG_I2C_RALINK)	+= i2c-ralink.o |  | ||||||
|  obj-$(CONFIG_I2C_QCOM_GENI)	+= i2c-qcom-geni.o |  | ||||||
|  obj-$(CONFIG_I2C_QUP)		+= i2c-qup.o |  | ||||||
|  obj-$(CONFIG_I2C_RIIC)		+= i2c-riic.o |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/drivers/i2c/busses/i2c-ralink.c |  | ||||||
| @@ -0,0 +1,435 @@ |  | ||||||
| +/* |  | ||||||
| + * drivers/i2c/busses/i2c-ralink.c |  | ||||||
| + * |  | ||||||
| + * Copyright (C) 2013 Steven Liu <steven_liu@mediatek.com> |  | ||||||
| + * Copyright (C) 2016 Michael Lee <igvtee@gmail.com> |  | ||||||
| + * |  | ||||||
| + * Improve driver for i2cdetect from i2c-tools to detect i2c devices on the bus. |  | ||||||
| + * (C) 2014 Sittisak <sittisaks@hotmail.com> |  | ||||||
| + * |  | ||||||
| + * This software is licensed under the terms of the GNU General Public |  | ||||||
| + * License version 2, as published by the Free Software Foundation, and |  | ||||||
| + * may be copied, distributed, and modified under those terms. |  | ||||||
| + * |  | ||||||
| + * This program is distributed in the hope that it will be useful, |  | ||||||
| + * but WITHOUT ANY WARRANTY; without even the implied warranty of |  | ||||||
| + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the |  | ||||||
| + * GNU General Public License for more details. |  | ||||||
| + * |  | ||||||
| + */ |  | ||||||
| + |  | ||||||
| +#include <linux/interrupt.h> |  | ||||||
| +#include <linux/kernel.h> |  | ||||||
| +#include <linux/module.h> |  | ||||||
| +#include <linux/reset.h> |  | ||||||
| +#include <linux/delay.h> |  | ||||||
| +#include <linux/slab.h> |  | ||||||
| +#include <linux/init.h> |  | ||||||
| +#include <linux/errno.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
| +#include <linux/of_platform.h> |  | ||||||
| +#include <linux/i2c.h> |  | ||||||
| +#include <linux/io.h> |  | ||||||
| +#include <linux/err.h> |  | ||||||
| +#include <linux/clk.h> |  | ||||||
| + |  | ||||||
| +#define REG_CONFIG_REG		0x00 |  | ||||||
| +#define REG_CLKDIV_REG		0x04 |  | ||||||
| +#define REG_DEVADDR_REG		0x08 |  | ||||||
| +#define REG_ADDR_REG		0x0C |  | ||||||
| +#define REG_DATAOUT_REG		0x10 |  | ||||||
| +#define REG_DATAIN_REG		0x14 |  | ||||||
| +#define REG_STATUS_REG		0x18 |  | ||||||
| +#define REG_STARTXFR_REG	0x1C |  | ||||||
| +#define REG_BYTECNT_REG		0x20 |  | ||||||
| + |  | ||||||
| +/* REG_CONFIG_REG */ |  | ||||||
| +#define I2C_ADDRLEN_OFFSET	5 |  | ||||||
| +#define I2C_DEVADLEN_OFFSET	2 |  | ||||||
| +#define I2C_ADDRLEN_MASK	0x3 |  | ||||||
| +#define I2C_ADDR_DIS		BIT(1) |  | ||||||
| +#define I2C_DEVADDR_DIS		BIT(0) |  | ||||||
| +#define I2C_ADDRLEN_8		(7 << I2C_ADDRLEN_OFFSET) |  | ||||||
| +#define I2C_DEVADLEN_7		(6 << I2C_DEVADLEN_OFFSET) |  | ||||||
| +#define I2C_CONF_DEFAULT	(I2C_ADDRLEN_8 | I2C_DEVADLEN_7) |  | ||||||
| + |  | ||||||
| +/* REG_CLKDIV_REG */ |  | ||||||
| +#define I2C_CLKDIV_MASK		0xffff |  | ||||||
| + |  | ||||||
| +/* REG_DEVADDR_REG */ |  | ||||||
| +#define I2C_DEVADDR_MASK	0x7f |  | ||||||
| + |  | ||||||
| +/* REG_ADDR_REG */ |  | ||||||
| +#define I2C_ADDR_MASK		0xff |  | ||||||
| + |  | ||||||
| +/* REG_STATUS_REG */ |  | ||||||
| +#define I2C_STARTERR		BIT(4) |  | ||||||
| +#define I2C_ACKERR		BIT(3) |  | ||||||
| +#define I2C_DATARDY		BIT(2) |  | ||||||
| +#define I2C_SDOEMPTY		BIT(1) |  | ||||||
| +#define I2C_BUSY		BIT(0) |  | ||||||
| + |  | ||||||
| +/* REG_STARTXFR_REG */ |  | ||||||
| +#define NOSTOP_CMD		BIT(2) |  | ||||||
| +#define NODATA_CMD		BIT(1) |  | ||||||
| +#define READ_CMD		BIT(0) |  | ||||||
| + |  | ||||||
| +/* REG_BYTECNT_REG */ |  | ||||||
| +#define BYTECNT_MAX		64 |  | ||||||
| +#define SET_BYTECNT(x)		(x - 1) |  | ||||||
| + |  | ||||||
| +/* timeout waiting for I2C devices to respond (clock streching) */ |  | ||||||
| +#define TIMEOUT_MS              1000 |  | ||||||
| +#define DELAY_INTERVAL_US       100 |  | ||||||
| + |  | ||||||
| +struct rt_i2c { |  | ||||||
| +	void __iomem *base; |  | ||||||
| +	struct clk *clk; |  | ||||||
| +	struct device *dev; |  | ||||||
| +	struct i2c_adapter adap; |  | ||||||
| +	u32 cur_clk; |  | ||||||
| +	u32 clk_div; |  | ||||||
| +	u32 flags; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static void rt_i2c_w32(struct rt_i2c *i2c, u32 val, unsigned reg) |  | ||||||
| +{ |  | ||||||
| +	iowrite32(val, i2c->base + reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static u32 rt_i2c_r32(struct rt_i2c *i2c, unsigned reg) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(i2c->base + reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int poll_down_timeout(void __iomem *addr, u32 mask) |  | ||||||
| +{ |  | ||||||
| +	unsigned long timeout = jiffies + msecs_to_jiffies(TIMEOUT_MS); |  | ||||||
| + |  | ||||||
| +	do { |  | ||||||
| +		if (!(readl_relaxed(addr) & mask)) |  | ||||||
| +			return 0; |  | ||||||
| + |  | ||||||
| +		usleep_range(DELAY_INTERVAL_US, DELAY_INTERVAL_US + 50); |  | ||||||
| +	} while (time_before(jiffies, timeout)); |  | ||||||
| + |  | ||||||
| +	return (readl_relaxed(addr) & mask) ? -EAGAIN : 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_wait_idle(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	ret = poll_down_timeout(i2c->base + REG_STATUS_REG, I2C_BUSY); |  | ||||||
| +	if (ret < 0) |  | ||||||
| +		dev_dbg(i2c->dev, "idle err(%d)\n", ret); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int poll_up_timeout(void __iomem *addr, u32 mask) |  | ||||||
| +{ |  | ||||||
| +	unsigned long timeout = jiffies + msecs_to_jiffies(TIMEOUT_MS); |  | ||||||
| +	u32 status; |  | ||||||
| + |  | ||||||
| +	do { |  | ||||||
| +		status = readl_relaxed(addr); |  | ||||||
| + |  | ||||||
| +		/* check error status */ |  | ||||||
| +		if (status & I2C_STARTERR) |  | ||||||
| +			return -EAGAIN; |  | ||||||
| +		else if (status & I2C_ACKERR) |  | ||||||
| +			return -ENXIO; |  | ||||||
| +		else if (status & mask) |  | ||||||
| +			return 0; |  | ||||||
| + |  | ||||||
| +		usleep_range(DELAY_INTERVAL_US, DELAY_INTERVAL_US + 50); |  | ||||||
| +	} while (time_before(jiffies, timeout)); |  | ||||||
| + |  | ||||||
| +	return -ETIMEDOUT; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_wait_rx_done(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	ret = poll_up_timeout(i2c->base + REG_STATUS_REG, I2C_DATARDY); |  | ||||||
| +	if (ret < 0) |  | ||||||
| +		dev_dbg(i2c->dev, "rx err(%d)\n", ret); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_wait_tx_done(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	ret = poll_up_timeout(i2c->base + REG_STATUS_REG, I2C_SDOEMPTY); |  | ||||||
| +	if (ret < 0) |  | ||||||
| +		dev_dbg(i2c->dev, "tx err(%d)\n", ret); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void rt_i2c_reset(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	device_reset(i2c->adap.dev.parent); |  | ||||||
| +	barrier(); |  | ||||||
| +	rt_i2c_w32(i2c, i2c->clk_div, REG_CLKDIV_REG); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void rt_i2c_dump_reg(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	dev_dbg(i2c->dev, "conf %08x, clkdiv %08x, devaddr %08x, " \ |  | ||||||
| +			"addr %08x, dataout %08x, datain %08x, " \ |  | ||||||
| +			"status %08x, startxfr %08x, bytecnt %08x\n", |  | ||||||
| +			rt_i2c_r32(i2c, REG_CONFIG_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_CLKDIV_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_DEVADDR_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_ADDR_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_DATAOUT_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_DATAIN_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_STATUS_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_STARTXFR_REG), |  | ||||||
| +			rt_i2c_r32(i2c, REG_BYTECNT_REG)); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_master_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, |  | ||||||
| +		int num) |  | ||||||
| +{ |  | ||||||
| +	struct rt_i2c *i2c; |  | ||||||
| +	struct i2c_msg *pmsg; |  | ||||||
| +	unsigned char addr; |  | ||||||
| +	int i, j, ret; |  | ||||||
| +	u32 cmd; |  | ||||||
| + |  | ||||||
| +	i2c = i2c_get_adapdata(adap); |  | ||||||
| + |  | ||||||
| +	for (i = 0; i < num; i++) { |  | ||||||
| +		pmsg = &msgs[i]; |  | ||||||
| +		if (i == (num - 1)) |  | ||||||
| +			cmd = 0; |  | ||||||
| +		else |  | ||||||
| +			cmd = NOSTOP_CMD; |  | ||||||
| + |  | ||||||
| +		dev_dbg(i2c->dev, "addr: 0x%x, len: %d, flags: 0x%x, stop: %d\n", |  | ||||||
| +				pmsg->addr, pmsg->len, pmsg->flags, |  | ||||||
| +				(cmd == 0)? 1 : 0); |  | ||||||
| + |  | ||||||
| +		/* wait hardware idle */ |  | ||||||
| +		if ((ret = rt_i2c_wait_idle(i2c))) |  | ||||||
| +			goto err_timeout; |  | ||||||
| + |  | ||||||
| +		if (pmsg->flags & I2C_M_TEN) { |  | ||||||
| +			rt_i2c_w32(i2c, I2C_CONF_DEFAULT, REG_CONFIG_REG); |  | ||||||
| +			/* 10 bits address */ |  | ||||||
| +			addr = 0x78 | ((pmsg->addr >> 8) & 0x03); |  | ||||||
| +			rt_i2c_w32(i2c, addr & I2C_DEVADDR_MASK, |  | ||||||
| +					REG_DEVADDR_REG); |  | ||||||
| +			rt_i2c_w32(i2c, pmsg->addr & I2C_ADDR_MASK, |  | ||||||
| +					REG_ADDR_REG); |  | ||||||
| +		} else { |  | ||||||
| +			rt_i2c_w32(i2c, I2C_CONF_DEFAULT | I2C_ADDR_DIS, |  | ||||||
| +					REG_CONFIG_REG); |  | ||||||
| +			/* 7 bits address */ |  | ||||||
| +			rt_i2c_w32(i2c, pmsg->addr & I2C_DEVADDR_MASK, |  | ||||||
| +					REG_DEVADDR_REG); |  | ||||||
| +		} |  | ||||||
| + |  | ||||||
| +		/* buffer length */ |  | ||||||
| +		if (pmsg->len == 0) |  | ||||||
| +			cmd |= NODATA_CMD; |  | ||||||
| +		else |  | ||||||
| +			rt_i2c_w32(i2c, SET_BYTECNT(pmsg->len), |  | ||||||
| +					REG_BYTECNT_REG); |  | ||||||
| + |  | ||||||
| +		j = 0; |  | ||||||
| +		if (pmsg->flags & I2C_M_RD) { |  | ||||||
| +			cmd |= READ_CMD; |  | ||||||
| +			/* start transfer */ |  | ||||||
| +			barrier(); |  | ||||||
| +			rt_i2c_w32(i2c, cmd, REG_STARTXFR_REG); |  | ||||||
| +			do { |  | ||||||
| +				/* wait */ |  | ||||||
| +				if ((ret = rt_i2c_wait_rx_done(i2c))) |  | ||||||
| +					goto err_timeout; |  | ||||||
| +				/* read data */ |  | ||||||
| +				if (pmsg->len) |  | ||||||
| +					pmsg->buf[j] = rt_i2c_r32(i2c, |  | ||||||
| +							REG_DATAIN_REG); |  | ||||||
| +				j++; |  | ||||||
| +			} while (j < pmsg->len); |  | ||||||
| +		} else { |  | ||||||
| +			do { |  | ||||||
| +				/* write data */ |  | ||||||
| +				if (pmsg->len) |  | ||||||
| +					rt_i2c_w32(i2c, pmsg->buf[j], |  | ||||||
| +							REG_DATAOUT_REG); |  | ||||||
| +				/* start transfer */ |  | ||||||
| +				if (j == 0) { |  | ||||||
| +					barrier(); |  | ||||||
| +					rt_i2c_w32(i2c, cmd, REG_STARTXFR_REG); |  | ||||||
| +				} |  | ||||||
| +				/* wait */ |  | ||||||
| +				if ((ret = rt_i2c_wait_tx_done(i2c))) |  | ||||||
| +					goto err_timeout; |  | ||||||
| +				j++; |  | ||||||
| +			} while (j < pmsg->len); |  | ||||||
| +		} |  | ||||||
| +	} |  | ||||||
| +	/* the return value is number of executed messages */ |  | ||||||
| +	ret = i; |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| + |  | ||||||
| +err_timeout: |  | ||||||
| +	rt_i2c_dump_reg(i2c); |  | ||||||
| +	rt_i2c_reset(i2c); |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static u32 rt_i2c_func(struct i2c_adapter *a) |  | ||||||
| +{ |  | ||||||
| +	return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct i2c_algorithm rt_i2c_algo = { |  | ||||||
| +	.master_xfer	= rt_i2c_master_xfer, |  | ||||||
| +	.functionality	= rt_i2c_func, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static const struct of_device_id i2c_rt_dt_ids[] = { |  | ||||||
| +	{ .compatible = "ralink,rt2880-i2c" }, |  | ||||||
| +	{ /* sentinel */ } |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +MODULE_DEVICE_TABLE(of, i2c_rt_dt_ids); |  | ||||||
| + |  | ||||||
| +static struct i2c_adapter_quirks rt_i2c_quirks = { |  | ||||||
| +        .max_write_len = BYTECNT_MAX, |  | ||||||
| +        .max_read_len = BYTECNT_MAX, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int rt_i2c_init(struct rt_i2c *i2c) |  | ||||||
| +{ |  | ||||||
| +	u32 reg; |  | ||||||
| + |  | ||||||
| +	/* i2c_sclk = periph_clk / ((2 * clk_div) + 5) */ |  | ||||||
| +	i2c->clk_div = (clk_get_rate(i2c->clk) - (5 * i2c->cur_clk)) / |  | ||||||
| +		(2 * i2c->cur_clk); |  | ||||||
| +	if (i2c->clk_div < 8) |  | ||||||
| +		i2c->clk_div = 8; |  | ||||||
| +	if (i2c->clk_div > I2C_CLKDIV_MASK) |  | ||||||
| +		i2c->clk_div = I2C_CLKDIV_MASK; |  | ||||||
| + |  | ||||||
| +	/* check support combinde/repeated start message */ |  | ||||||
| +	rt_i2c_w32(i2c, NOSTOP_CMD, REG_STARTXFR_REG); |  | ||||||
| +	reg = rt_i2c_r32(i2c, REG_STARTXFR_REG) & NOSTOP_CMD; |  | ||||||
| + |  | ||||||
| +	rt_i2c_reset(i2c); |  | ||||||
| + |  | ||||||
| +	return reg; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct resource *res; |  | ||||||
| +	struct rt_i2c *i2c; |  | ||||||
| +	struct i2c_adapter *adap; |  | ||||||
| +	const struct of_device_id *match; |  | ||||||
| +	int ret, restart; |  | ||||||
| + |  | ||||||
| +	match = of_match_device(i2c_rt_dt_ids, &pdev->dev); |  | ||||||
| + |  | ||||||
| +	res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |  | ||||||
| +	if (!res) { |  | ||||||
| +		dev_err(&pdev->dev, "no memory resource found\n"); |  | ||||||
| +		return -ENODEV; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	i2c = devm_kzalloc(&pdev->dev, sizeof(struct rt_i2c), GFP_KERNEL); |  | ||||||
| +	if (!i2c) { |  | ||||||
| +		dev_err(&pdev->dev, "failed to allocate i2c_adapter\n"); |  | ||||||
| +		return -ENOMEM; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	i2c->base = devm_ioremap_resource(&pdev->dev, res); |  | ||||||
| +	if (IS_ERR(i2c->base)) |  | ||||||
| +		return PTR_ERR(i2c->base); |  | ||||||
| + |  | ||||||
| +	i2c->clk = devm_clk_get(&pdev->dev, NULL); |  | ||||||
| +	if (IS_ERR(i2c->clk)) { |  | ||||||
| +		dev_err(&pdev->dev, "no clock defined\n"); |  | ||||||
| +		return -ENODEV; |  | ||||||
| +	} |  | ||||||
| +	clk_prepare_enable(i2c->clk); |  | ||||||
| +	i2c->dev = &pdev->dev; |  | ||||||
| + |  | ||||||
| +	if (of_property_read_u32(pdev->dev.of_node, |  | ||||||
| +				"clock-frequency", &i2c->cur_clk)) |  | ||||||
| +		i2c->cur_clk = 100000; |  | ||||||
| + |  | ||||||
| +	adap = &i2c->adap; |  | ||||||
| +	adap->owner = THIS_MODULE; |  | ||||||
| +	adap->class = I2C_CLASS_HWMON | I2C_CLASS_SPD; |  | ||||||
| +	adap->algo = &rt_i2c_algo; |  | ||||||
| +	adap->retries = 3; |  | ||||||
| +	adap->dev.parent = &pdev->dev; |  | ||||||
| +	i2c_set_adapdata(adap, i2c); |  | ||||||
| +	adap->dev.of_node = pdev->dev.of_node; |  | ||||||
| +	strlcpy(adap->name, dev_name(&pdev->dev), sizeof(adap->name)); |  | ||||||
| +	adap->quirks = &rt_i2c_quirks; |  | ||||||
| + |  | ||||||
| +	platform_set_drvdata(pdev, i2c); |  | ||||||
| + |  | ||||||
| +	restart = rt_i2c_init(i2c); |  | ||||||
| + |  | ||||||
| +	ret = i2c_add_adapter(adap); |  | ||||||
| +	if (ret < 0) { |  | ||||||
| +		dev_err(&pdev->dev, "failed to add adapter\n"); |  | ||||||
| +		clk_disable_unprepare(i2c->clk); |  | ||||||
| +		return ret; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	dev_info(&pdev->dev, "clock %uKHz, re-start %ssupport\n", |  | ||||||
| +			i2c->cur_clk/1000, restart ? "" : "not "); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int rt_i2c_remove(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct rt_i2c *i2c = platform_get_drvdata(pdev); |  | ||||||
| + |  | ||||||
| +	i2c_del_adapter(&i2c->adap); |  | ||||||
| +	clk_disable_unprepare(i2c->clk); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static struct platform_driver rt_i2c_driver = { |  | ||||||
| +	.probe		= rt_i2c_probe, |  | ||||||
| +	.remove		= rt_i2c_remove, |  | ||||||
| +	.driver		= { |  | ||||||
| +		.owner	= THIS_MODULE, |  | ||||||
| +		.name	= "i2c-ralink", |  | ||||||
| +		.of_match_table = i2c_rt_dt_ids, |  | ||||||
| +	}, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int __init i2c_rt_init (void) |  | ||||||
| +{ |  | ||||||
| +	return platform_driver_register(&rt_i2c_driver); |  | ||||||
| +} |  | ||||||
| +subsys_initcall(i2c_rt_init); |  | ||||||
| + |  | ||||||
| +static void __exit i2c_rt_exit (void) |  | ||||||
| +{ |  | ||||||
| +	platform_driver_unregister(&rt_i2c_driver); |  | ||||||
| +} |  | ||||||
| +module_exit(i2c_rt_exit); |  | ||||||
| + |  | ||||||
| +MODULE_AUTHOR("Steven Liu <steven_liu@mediatek.com>"); |  | ||||||
| +MODULE_DESCRIPTION("Ralink I2c host driver"); |  | ||||||
| +MODULE_LICENSE("GPL"); |  | ||||||
| +MODULE_ALIAS("platform:Ralink-I2C"); |  | ||||||
| @@ -1,43 +0,0 @@ | |||||||
| From 23147af14531cbdada194b94120ef8774f46292d Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Thu, 13 Nov 2014 19:08:40 +0100 |  | ||||||
| Subject: [PATCH 46/53] mmc: MIPS: ralink: add sdhci for mt7620a SoC |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/mmc/host/Kconfig             |    2 + |  | ||||||
|  drivers/mmc/host/Makefile            |    1 + |  | ||||||
|  drivers/mmc/host/mtk-mmc/Kconfig     |   16 + |  | ||||||
|  drivers/mmc/host/mtk-mmc/Makefile    |   42 + |  | ||||||
|  drivers/mmc/host/mtk-mmc/board.h     |  137 ++ |  | ||||||
|  drivers/mmc/host/mtk-mmc/dbg.c       |  347 ++++ |  | ||||||
|  drivers/mmc/host/mtk-mmc/dbg.h       |  156 ++ |  | ||||||
|  drivers/mmc/host/mtk-mmc/mt6575_sd.h | 1001 +++++++++++ |  | ||||||
|  drivers/mmc/host/mtk-mmc/sd.c        | 3060 ++++++++++++++++++++++++++++++++++ |  | ||||||
|  9 files changed, 4762 insertions(+) |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/Kconfig |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/Makefile |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/board.h |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/dbg.c |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/dbg.h |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/mt6575_sd.h |  | ||||||
|  create mode 100644 drivers/mmc/host/mtk-mmc/sd.c |  | ||||||
|  |  | ||||||
| --- a/drivers/mmc/host/Kconfig |  | ||||||
| +++ b/drivers/mmc/host/Kconfig |  | ||||||
| @@ -1019,3 +1019,5 @@ config MMC_SDHCI_AM654 |  | ||||||
|  	  If you have a controller with this interface, say Y or M here. |  | ||||||
|   |  | ||||||
|  	  If unsure, say N. |  | ||||||
| + |  | ||||||
| +source "drivers/mmc/host/mtk-mmc/Kconfig" |  | ||||||
| --- a/drivers/mmc/host/Makefile |  | ||||||
| +++ b/drivers/mmc/host/Makefile |  | ||||||
| @@ -3,6 +3,7 @@ |  | ||||||
|  # Makefile for MMC/SD host controller drivers |  | ||||||
|  # |  | ||||||
|   |  | ||||||
| +obj-$(CONFIG_MTK_MMC) 		+= mtk-mmc/ |  | ||||||
|  obj-$(CONFIG_MMC_ARMMMCI) += armmmci.o |  | ||||||
|  armmmci-y := mmci.o |  | ||||||
|  armmmci-$(CONFIG_MMC_QCOM_DML) += mmci_qcom_dml.o |  | ||||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							| @@ -1,22 +0,0 @@ | |||||||
| From a7eb46e0ea4a11e4dfb56ab129bf816d1059a6c5 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 7 Dec 2015 17:31:08 +0100 |  | ||||||
| Subject: [PATCH 51/53] serial: add ugly custom baud rate hack |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/tty/serial/serial_core.c |    3 +++ |  | ||||||
|  1 file changed, 3 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/drivers/tty/serial/serial_core.c |  | ||||||
| +++ b/drivers/tty/serial/serial_core.c |  | ||||||
| @@ -423,6 +423,9 @@ uart_get_baud_rate(struct uart_port *por |  | ||||||
|  		break; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| +	if (tty_termios_baud_rate(termios) == 2500000) |  | ||||||
| +		return 250000; |  | ||||||
| + |  | ||||||
|  	for (try = 0; try < 2; try++) { |  | ||||||
|  		baud = tty_termios_baud_rate(termios); |  | ||||||
|   |  | ||||||
| @@ -1,217 +0,0 @@ | |||||||
| From fc8f96309c21c1bc3276427309cd7d361347d66e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Mon, 7 Dec 2015 17:16:50 +0100 |  | ||||||
| Subject: [PATCH 52/53] pwm: add mediatek support |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/pwm/Kconfig        |    9 +++ |  | ||||||
|  drivers/pwm/Makefile       |    1 + |  | ||||||
|  drivers/pwm/pwm-mediatek.c |  173 ++++++++++++++++++++++++++++++++++++++++++++ |  | ||||||
|  3 files changed, 183 insertions(+) |  | ||||||
|  create mode 100644 drivers/pwm/pwm-mediatek.c |  | ||||||
|  |  | ||||||
| --- a/drivers/pwm/Kconfig |  | ||||||
| +++ b/drivers/pwm/Kconfig |  | ||||||
| @@ -316,6 +316,15 @@ config PWM_MEDIATEK |  | ||||||
|  	  To compile this driver as a module, choose M here: the module |  | ||||||
|  	  will be called pwm-mediatek. |  | ||||||
|   |  | ||||||
| +config PWM_MEDIATEK_RAMIPS |  | ||||||
| +	tristate "Mediatek PWM support" |  | ||||||
| +	depends on RALINK && OF |  | ||||||
| +	help |  | ||||||
| +	  Generic PWM framework driver for Mediatek ARM SoC. |  | ||||||
| + |  | ||||||
| +	  To compile this driver as a module, choose M here: the module |  | ||||||
| +	  will be called pwm-mxs. |  | ||||||
| + |  | ||||||
|  config PWM_MXS |  | ||||||
|  	tristate "Freescale MXS PWM support" |  | ||||||
|  	depends on ARCH_MXS && OF |  | ||||||
| --- a/drivers/pwm/Makefile |  | ||||||
| +++ b/drivers/pwm/Makefile |  | ||||||
| @@ -29,6 +29,7 @@ obj-$(CONFIG_PWM_LPSS_PCI)	+= pwm-lpss-p |  | ||||||
|  obj-$(CONFIG_PWM_LPSS_PLATFORM)	+= pwm-lpss-platform.o |  | ||||||
|  obj-$(CONFIG_PWM_MESON)		+= pwm-meson.o |  | ||||||
|  obj-$(CONFIG_PWM_MEDIATEK)	+= pwm-mediatek.o |  | ||||||
| +obj-$(CONFIG_PWM_MEDIATEK_RAMIPS)	+= pwm-mediatek-ramips.o |  | ||||||
|  obj-$(CONFIG_PWM_MTK_DISP)	+= pwm-mtk-disp.o |  | ||||||
|  obj-$(CONFIG_PWM_MXS)		+= pwm-mxs.o |  | ||||||
|  obj-$(CONFIG_PWM_OMAP_DMTIMER)	+= pwm-omap-dmtimer.o |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/drivers/pwm/pwm-mediatek-ramips.c |  | ||||||
| @@ -0,0 +1,173 @@ |  | ||||||
| +/* |  | ||||||
| + * Mediatek Pulse Width Modulator driver |  | ||||||
| + * |  | ||||||
| + * Copyright (C) 2015 John Crispin <blogic@openwrt.org> |  | ||||||
| + * |  | ||||||
| + * This file is licensed under the terms of the GNU General Public |  | ||||||
| + * License version 2. This program is licensed "as is" without any |  | ||||||
| + * warranty of any kind, whether express or implied. |  | ||||||
| + */ |  | ||||||
| + |  | ||||||
| +#include <linux/err.h> |  | ||||||
| +#include <linux/io.h> |  | ||||||
| +#include <linux/ioport.h> |  | ||||||
| +#include <linux/kernel.h> |  | ||||||
| +#include <linux/module.h> |  | ||||||
| +#include <linux/of.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
| +#include <linux/pwm.h> |  | ||||||
| +#include <linux/slab.h> |  | ||||||
| +#include <linux/types.h> |  | ||||||
| + |  | ||||||
| +#define NUM_PWM		4 |  | ||||||
| + |  | ||||||
| +/* PWM registers and bits definitions */ |  | ||||||
| +#define PWMCON			0x00 |  | ||||||
| +#define PWMHDUR			0x04 |  | ||||||
| +#define PWMLDUR			0x08 |  | ||||||
| +#define PWMGDUR			0x0c |  | ||||||
| +#define PWMWAVENUM		0x28 |  | ||||||
| +#define PWMDWIDTH		0x2c |  | ||||||
| +#define PWMTHRES		0x30 |  | ||||||
| + |  | ||||||
| +/** |  | ||||||
| + * struct mtk_pwm_chip - struct representing pwm chip |  | ||||||
| + * |  | ||||||
| + * @mmio_base: base address of pwm chip |  | ||||||
| + * @chip: linux pwm chip representation |  | ||||||
| + */ |  | ||||||
| +struct mtk_pwm_chip { |  | ||||||
| +	void __iomem *mmio_base; |  | ||||||
| +	struct pwm_chip chip; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static inline struct mtk_pwm_chip *to_mtk_pwm_chip(struct pwm_chip *chip) |  | ||||||
| +{ |  | ||||||
| +	return container_of(chip, struct mtk_pwm_chip, chip); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline u32 mtk_pwm_readl(struct mtk_pwm_chip *chip, unsigned int num, |  | ||||||
| +				  unsigned long offset) |  | ||||||
| +{ |  | ||||||
| +	return ioread32(chip->mmio_base + 0x10 + (num * 0x40) + offset); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline void mtk_pwm_writel(struct mtk_pwm_chip *chip, |  | ||||||
| +				    unsigned int num, unsigned long offset, |  | ||||||
| +				    unsigned long val) |  | ||||||
| +{ |  | ||||||
| +	iowrite32(val, chip->mmio_base + 0x10 + (num * 0x40) + offset); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int mtk_pwm_config(struct pwm_chip *chip, struct pwm_device *pwm, |  | ||||||
| +			    int duty_ns, int period_ns) |  | ||||||
| +{ |  | ||||||
| +	struct mtk_pwm_chip *pc = to_mtk_pwm_chip(chip); |  | ||||||
| +	u32 resolution = 100 / 4; |  | ||||||
| +	u32 clkdiv = 0; |  | ||||||
| + |  | ||||||
| +	while (period_ns / resolution  > 8191) { |  | ||||||
| +		clkdiv++; |  | ||||||
| +		resolution *= 2; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if (clkdiv > 7) |  | ||||||
| +		return -1; |  | ||||||
| + |  | ||||||
| +	mtk_pwm_writel(pc, pwm->hwpwm, PWMCON, BIT(15) | BIT(3) | clkdiv); |  | ||||||
| +	mtk_pwm_writel(pc, pwm->hwpwm, PWMDWIDTH, period_ns / resolution); |  | ||||||
| +	mtk_pwm_writel(pc, pwm->hwpwm, PWMTHRES, duty_ns / resolution); |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int mtk_pwm_enable(struct pwm_chip *chip, struct pwm_device *pwm) |  | ||||||
| +{ |  | ||||||
| +	struct mtk_pwm_chip *pc = to_mtk_pwm_chip(chip); |  | ||||||
| +	u32 val; |  | ||||||
| + |  | ||||||
| +	val = ioread32(pc->mmio_base); |  | ||||||
| +	val |= BIT(pwm->hwpwm); |  | ||||||
| +	iowrite32(val, pc->mmio_base); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void mtk_pwm_disable(struct pwm_chip *chip, struct pwm_device *pwm) |  | ||||||
| +{ |  | ||||||
| +	struct mtk_pwm_chip *pc = to_mtk_pwm_chip(chip); |  | ||||||
| +	u32 val; |  | ||||||
| + |  | ||||||
| +	val = ioread32(pc->mmio_base); |  | ||||||
| +	val &= ~BIT(pwm->hwpwm); |  | ||||||
| +	iowrite32(val, pc->mmio_base); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct pwm_ops mtk_pwm_ops = { |  | ||||||
| +	.config = mtk_pwm_config, |  | ||||||
| +	.enable = mtk_pwm_enable, |  | ||||||
| +	.disable = mtk_pwm_disable, |  | ||||||
| +	.owner = THIS_MODULE, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static int mtk_pwm_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct mtk_pwm_chip *pc; |  | ||||||
| +	struct resource *r; |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	pc = devm_kzalloc(&pdev->dev, sizeof(*pc), GFP_KERNEL); |  | ||||||
| +	if (!pc) |  | ||||||
| +		return -ENOMEM; |  | ||||||
| + |  | ||||||
| +	r = platform_get_resource(pdev, IORESOURCE_MEM, 0); |  | ||||||
| +	pc->mmio_base = devm_ioremap_resource(&pdev->dev, r); |  | ||||||
| +	if (IS_ERR(pc->mmio_base)) |  | ||||||
| +		return PTR_ERR(pc->mmio_base); |  | ||||||
| + |  | ||||||
| +	platform_set_drvdata(pdev, pc); |  | ||||||
| + |  | ||||||
| +	pc->chip.dev = &pdev->dev; |  | ||||||
| +	pc->chip.ops = &mtk_pwm_ops; |  | ||||||
| +	pc->chip.base = -1; |  | ||||||
| +	pc->chip.npwm = NUM_PWM; |  | ||||||
| + |  | ||||||
| +	ret = pwmchip_add(&pc->chip); |  | ||||||
| +	if (ret < 0) |  | ||||||
| +		dev_err(&pdev->dev, "pwmchip_add() failed: %d\n", ret); |  | ||||||
| + |  | ||||||
| +	return ret; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int mtk_pwm_remove(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct mtk_pwm_chip *pc = platform_get_drvdata(pdev); |  | ||||||
| +	int i; |  | ||||||
| + |  | ||||||
| +	for (i = 0; i < NUM_PWM; i++) |  | ||||||
| +		pwm_disable(&pc->chip.pwms[i]); |  | ||||||
| + |  | ||||||
| +	return pwmchip_remove(&pc->chip); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct of_device_id mtk_pwm_of_match[] = { |  | ||||||
| +	{ .compatible = "mediatek,mt7628-pwm" }, |  | ||||||
| +	{ } |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +MODULE_DEVICE_TABLE(of, mtk_pwm_of_match); |  | ||||||
| + |  | ||||||
| +static struct platform_driver mtk_pwm_driver = { |  | ||||||
| +	.driver = { |  | ||||||
| +		.name = "mtk-pwm", |  | ||||||
| +		.owner = THIS_MODULE, |  | ||||||
| +		.of_match_table = mtk_pwm_of_match, |  | ||||||
| +	}, |  | ||||||
| +	.probe = mtk_pwm_probe, |  | ||||||
| +	.remove = mtk_pwm_remove, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +module_platform_driver(mtk_pwm_driver); |  | ||||||
| + |  | ||||||
| +MODULE_LICENSE("GPL"); |  | ||||||
| +MODULE_AUTHOR("John Crispin <blogic@openwrt.org>"); |  | ||||||
| +MODULE_ALIAS("platform:mtk-pwm"); |  | ||||||
| @@ -1,15 +0,0 @@ | |||||||
| --- a/drivers/usb/dwc2/platform.c |  | ||||||
| +++ b/drivers/usb/dwc2/platform.c |  | ||||||
| @@ -431,6 +431,12 @@ static int dwc2_driver_probe(struct plat |  | ||||||
|  	if (retval) |  | ||||||
|  		return retval; |  | ||||||
|   |  | ||||||
| +	/* Enable USB port before any regs access */ |  | ||||||
| +	if (readl(hsotg->regs + PCGCTL) & 0x0f) { |  | ||||||
| +		writel(0x00, hsotg->regs + PCGCTL); |  | ||||||
| +		/* TODO: mdelay(25) here? vendor driver don't use it */ |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	hsotg->needs_byte_swap = dwc2_check_core_endianness(hsotg); |  | ||||||
|   |  | ||||||
|  	retval = dwc2_get_dr_mode(hsotg); |  | ||||||
| @@ -1,10 +0,0 @@ | |||||||
| --- a/arch/mips/ralink/Kconfig |  | ||||||
| +++ b/arch/mips/ralink/Kconfig |  | ||||||
| @@ -57,6 +57,7 @@ choice |  | ||||||
|  		select COMMON_CLK |  | ||||||
|  		select CLKSRC_MIPS_GIC |  | ||||||
|  		select HAVE_PCI if PCI_MT7621 |  | ||||||
| +		select WEAK_REORDERING_BEYOND_LLSC |  | ||||||
|  endchoice |  | ||||||
|   |  | ||||||
|  choice |  | ||||||
| @@ -1,19 +0,0 @@ | |||||||
| --- a/arch/mips/kernel/mips-cm.c |  | ||||||
| +++ b/arch/mips/kernel/mips-cm.c |  | ||||||
| @@ -232,6 +232,7 @@ int mips_cm_probe(void) |  | ||||||
|   |  | ||||||
|  	/* disable CM regions */ |  | ||||||
|  	write_gcr_reg0_base(CM_GCR_REGn_BASE_BASEADDR); |  | ||||||
| +	/* |  | ||||||
|  	write_gcr_reg0_mask(CM_GCR_REGn_MASK_ADDRMASK); |  | ||||||
|  	write_gcr_reg1_base(CM_GCR_REGn_BASE_BASEADDR); |  | ||||||
|  	write_gcr_reg1_mask(CM_GCR_REGn_MASK_ADDRMASK); |  | ||||||
| @@ -239,7 +240,7 @@ int mips_cm_probe(void) |  | ||||||
|  	write_gcr_reg2_mask(CM_GCR_REGn_MASK_ADDRMASK); |  | ||||||
|  	write_gcr_reg3_base(CM_GCR_REGn_BASE_BASEADDR); |  | ||||||
|  	write_gcr_reg3_mask(CM_GCR_REGn_MASK_ADDRMASK); |  | ||||||
| - |  | ||||||
| +*/ |  | ||||||
|  	/* probe for an L2-only sync region */ |  | ||||||
|  	mips_cm_probe_l2sync(); |  | ||||||
|   |  | ||||||
| @@ -1,133 +0,0 @@ | |||||||
| From b327cd58c3fec1c6382128e929eab9bc0d68e912 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sun, 8 Mar 2020 10:19:27 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: simplify |  | ||||||
|  'mt7621_pcie_init_virtual_bridges' function |  | ||||||
|  |  | ||||||
| Function 'mt7621_pcie_init_virtual_bridges' is a bit mess and can be |  | ||||||
| refactorized properly in a cleaner way. Introduce new 'pcie_rmw' inline |  | ||||||
| function helper to do clear and set the correct bits this function needs |  | ||||||
| to work. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200308091928.17177-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 85 +++++++++++++-------------------- |  | ||||||
|  1 file changed, 33 insertions(+), 52 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -57,13 +57,13 @@ |  | ||||||
|  #define RALINK_PCI_IOBASE		0x002C |  | ||||||
|   |  | ||||||
|  /* PCICFG virtual bridges */ |  | ||||||
| -#define MT7621_BR0_MASK			GENMASK(19, 16) |  | ||||||
| -#define MT7621_BR1_MASK			GENMASK(23, 20) |  | ||||||
| -#define MT7621_BR2_MASK			GENMASK(27, 24) |  | ||||||
| -#define MT7621_BR_ALL_MASK		GENMASK(27, 16) |  | ||||||
| -#define MT7621_BR0_SHIFT		16 |  | ||||||
| -#define MT7621_BR1_SHIFT		20 |  | ||||||
| -#define MT7621_BR2_SHIFT		24 |  | ||||||
| +#define PCIE_P2P_MAX			3 |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM_SHIFT(p)	(16 + (p) * 4) |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM0_SHIFT	PCIE_P2P_BR_DEVNUM_SHIFT(0) |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM1_SHIFT	PCIE_P2P_BR_DEVNUM_SHIFT(1) |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM2_SHIFT	PCIE_P2P_BR_DEVNUM_SHIFT(2) |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM_MASK		0xf |  | ||||||
| +#define PCIE_P2P_BR_DEVNUM_MASK_FULL	(0xfff << PCIE_P2P_BR_DEVNUM0_SHIFT) |  | ||||||
|   |  | ||||||
|  /* PCIe RC control registers */ |  | ||||||
|  #define MT7621_PCIE_OFFSET		0x2000 |  | ||||||
| @@ -154,6 +154,15 @@ static inline void pcie_write(struct mt7 |  | ||||||
|  	writel(val, pcie->base + reg); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static inline void pcie_rmw(struct mt7621_pcie *pcie, u32 reg, u32 clr, u32 set) |  | ||||||
| +{ |  | ||||||
| +	u32 val = readl(pcie->base + reg); |  | ||||||
| + |  | ||||||
| +	val &= ~clr; |  | ||||||
| +	val |= set; |  | ||||||
| +	writel(val, pcie->base + reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static inline u32 pcie_port_read(struct mt7621_pcie_port *port, u32 reg) |  | ||||||
|  { |  | ||||||
|  	return readl(port->base + reg); |  | ||||||
| @@ -554,7 +563,9 @@ static void mt7621_pcie_enable_ports(str |  | ||||||
|  static int mt7621_pcie_init_virtual_bridges(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	u32 pcie_link_status = 0; |  | ||||||
| -	u32 val = 0; |  | ||||||
| +	u32 n; |  | ||||||
| +	int i; |  | ||||||
| +	u32 p2p_br_devnum[PCIE_P2P_MAX]; |  | ||||||
|  	struct mt7621_pcie_port *port; |  | ||||||
|   |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
| @@ -567,50 +578,20 @@ static int mt7621_pcie_init_virtual_brid |  | ||||||
|  	if (pcie_link_status == 0) |  | ||||||
|  		return -1; |  | ||||||
|   |  | ||||||
| -	/* |  | ||||||
| -	 * pcie(2/1/0) link status	pcie2_num	pcie1_num	pcie0_num |  | ||||||
| -	 * 3'b000			x		x		x |  | ||||||
| -	 * 3'b001			x		x		0 |  | ||||||
| -	 * 3'b010			x		0		x |  | ||||||
| -	 * 3'b011			x		1		0 |  | ||||||
| -	 * 3'b100			0		x		x |  | ||||||
| -	 * 3'b101			1		x		0 |  | ||||||
| -	 * 3'b110			1		0		x |  | ||||||
| -	 * 3'b111			2		1		0 |  | ||||||
| -	 */ |  | ||||||
| -	switch (pcie_link_status) { |  | ||||||
| -	case 2: |  | ||||||
| -		val = pcie_read(pcie, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		val &= ~(MT7621_BR0_MASK | MT7621_BR1_MASK); |  | ||||||
| -		val |= 0x1 << MT7621_BR0_SHIFT; |  | ||||||
| -		val |= 0x0 << MT7621_BR1_SHIFT; |  | ||||||
| -		pcie_write(pcie, val, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		break; |  | ||||||
| -	case 4: |  | ||||||
| -		val = pcie_read(pcie, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		val &= ~MT7621_BR_ALL_MASK; |  | ||||||
| -		val |= 0x1 << MT7621_BR0_SHIFT; |  | ||||||
| -		val |= 0x2 << MT7621_BR1_SHIFT; |  | ||||||
| -		val |= 0x0 << MT7621_BR2_SHIFT; |  | ||||||
| -		pcie_write(pcie, val, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		break; |  | ||||||
| -	case 5: |  | ||||||
| -		val = pcie_read(pcie, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		val &= ~MT7621_BR_ALL_MASK; |  | ||||||
| -		val |= 0x0 << MT7621_BR0_SHIFT; |  | ||||||
| -		val |= 0x2 << MT7621_BR1_SHIFT; |  | ||||||
| -		val |= 0x1 << MT7621_BR2_SHIFT; |  | ||||||
| -		pcie_write(pcie, val, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		break; |  | ||||||
| -	case 6: |  | ||||||
| -		val = pcie_read(pcie, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		val &= ~MT7621_BR_ALL_MASK; |  | ||||||
| -		val |= 0x2 << MT7621_BR0_SHIFT; |  | ||||||
| -		val |= 0x0 << MT7621_BR1_SHIFT; |  | ||||||
| -		val |= 0x1 << MT7621_BR2_SHIFT; |  | ||||||
| -		pcie_write(pcie, val, RALINK_PCI_PCICFG_ADDR); |  | ||||||
| -		break; |  | ||||||
| -	} |  | ||||||
| +	n = 0; |  | ||||||
| +	for (i = 0; i < PCIE_P2P_MAX; i++) |  | ||||||
| +		if (pcie_link_status & BIT(i)) |  | ||||||
| +			p2p_br_devnum[i] = n++; |  | ||||||
| + |  | ||||||
| +	for (i = 0; i < PCIE_P2P_MAX; i++) |  | ||||||
| +		if ((pcie_link_status & BIT(i)) == 0) |  | ||||||
| +			p2p_br_devnum[i] = n++; |  | ||||||
| + |  | ||||||
| +	pcie_rmw(pcie, RALINK_PCI_CONFIG_ADDR, |  | ||||||
| +		 PCIE_P2P_BR_DEVNUM_MASK_FULL, |  | ||||||
| +		 (p2p_br_devnum[0] << PCIE_P2P_BR_DEVNUM0_SHIFT) | |  | ||||||
| +		 (p2p_br_devnum[1] << PCIE_P2P_BR_DEVNUM1_SHIFT) | |  | ||||||
| +		 (p2p_br_devnum[2] << PCIE_P2P_BR_DEVNUM2_SHIFT)); |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -1,74 +0,0 @@ | |||||||
| From 550fabd71d7fcdfe099bbf41e00e28719737161e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Tue, 10 Mar 2020 12:34:59 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: enable clock bit for each port |  | ||||||
|  |  | ||||||
| The clock related code concerns me from the very beginning because |  | ||||||
| there are some set ups got from legacy driver that are not documented |  | ||||||
| anywhere. According to the programming guide 0x7c is 'CPE_ROSC_SEL1' |  | ||||||
| register and 0x80 is 'CPU_CPE_CN'. I do think this set up is not needed |  | ||||||
| at all and the proper thing to do is just enable the clock bit for each |  | ||||||
| pcie port. Hence remove useless code and do the right thing which is |  | ||||||
| setting up the clock bit for each port enabled. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200310113459.30539-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 17 ++++++----------- |  | ||||||
|  1 file changed, 6 insertions(+), 11 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -45,8 +45,6 @@ |  | ||||||
|   |  | ||||||
|  /* rt_sysc_membase relative registers */ |  | ||||||
|  #define RALINK_CLKCFG1			0x30 |  | ||||||
| -#define RALINK_PCIE_CLK_GEN		0x7c |  | ||||||
| -#define RALINK_PCIE_CLK_GEN1		0x80 |  | ||||||
|   |  | ||||||
|  /* Host-PCI bridge registers */ |  | ||||||
|  #define RALINK_PCI_PCICFG_ADDR		0x0000 |  | ||||||
| @@ -85,10 +83,6 @@ |  | ||||||
|  #define PCIE_PORT_CLK_EN(x)		BIT(24 + (x)) |  | ||||||
|  #define PCIE_PORT_LINKUP		BIT(0) |  | ||||||
|   |  | ||||||
| -#define PCIE_CLK_GEN_EN			BIT(31) |  | ||||||
| -#define PCIE_CLK_GEN_DIS		0 |  | ||||||
| -#define PCIE_CLK_GEN1_DIS		GENMASK(30, 24) |  | ||||||
| -#define PCIE_CLK_GEN1_EN		(BIT(27) | BIT(25)) |  | ||||||
|  #define MEMORY_BASE			0x0 |  | ||||||
|  #define PERST_MODE_MASK			GENMASK(11, 10) |  | ||||||
|  #define PERST_MODE_GPIO			BIT(10) |  | ||||||
| @@ -233,6 +227,11 @@ static inline bool mt7621_pcie_port_is_l |  | ||||||
|  	return (pcie_port_read(port, RALINK_PCI_STATUS) & PCIE_PORT_LINKUP) != 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static inline void mt7621_pcie_port_clk_enable(struct mt7621_pcie_port *port) |  | ||||||
| +{ |  | ||||||
| +	rt_sysc_m32(0, PCIE_PORT_CLK_EN(port->slot), RALINK_CLKCFG1); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static inline void mt7621_pcie_port_clk_disable(struct mt7621_pcie_port *port) |  | ||||||
|  { |  | ||||||
|  	rt_sysc_m32(PCIE_PORT_CLK_EN(port->slot), 0, RALINK_CLKCFG1); |  | ||||||
| @@ -501,11 +500,6 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|  		} |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	rt_sysc_m32(0x30, 2 << 4, SYSC_REG_SYSTEM_CONFIG1); |  | ||||||
| -	rt_sysc_m32(PCIE_CLK_GEN_EN, PCIE_CLK_GEN_DIS, RALINK_PCIE_CLK_GEN); |  | ||||||
| -	rt_sysc_m32(PCIE_CLK_GEN1_DIS, PCIE_CLK_GEN1_EN, RALINK_PCIE_CLK_GEN1); |  | ||||||
| -	rt_sysc_m32(PCIE_CLK_GEN_DIS, PCIE_CLK_GEN_EN, RALINK_PCIE_CLK_GEN); |  | ||||||
| -	msleep(50); |  | ||||||
|  	reset_control_deassert(pcie->rst); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -542,6 +536,7 @@ static void mt7621_pcie_enable_ports(str |  | ||||||
|   |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
|  		if (port->enabled) { |  | ||||||
| +			mt7621_pcie_port_clk_enable(port); |  | ||||||
|  			mt7621_pcie_enable_port(port); |  | ||||||
|  			dev_info(dev, "PCIE%d enabled\n", num_slots_enabled); |  | ||||||
|  			num_slots_enabled++; |  | ||||||
| @@ -1,222 +0,0 @@ | |||||||
| From 227a8bf421ff8b085444e51e471ef06a87228cfd Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 13 Mar 2020 21:09:08 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: use gpios for properly reset |  | ||||||
|  |  | ||||||
| Original driver code was using three gpio's for reset |  | ||||||
| asserts and deasserts the pcis. Instead of using that |  | ||||||
| a general reset control with a perst gpio was introduced |  | ||||||
| and it seems it is partially working but sometimes there |  | ||||||
| are some unexpected hangs on boot. This commit make use of |  | ||||||
| the three original gpios using 'reset-gpios' property of |  | ||||||
| the device tree and removes the reset line and perst gpio. |  | ||||||
| According to the mediatek aplication note v0.1 there are |  | ||||||
| three gpios used for pcie ports reset control: gpio#19, |  | ||||||
| gpio#8 and gpio#7 for slots 0, 1 and 2 respectively. |  | ||||||
| This schema can be used separately for mt7621A but in some |  | ||||||
| boards due to pin share issue, if the PCM and I2S function |  | ||||||
| are enable at the same time, there are no enough GPIO to |  | ||||||
| control per-port PCIe reset. In those cases gpio#19 is enought |  | ||||||
| for reset the three ports together. Because of this we just |  | ||||||
| try to get the three gpios but if some of them fail we are not |  | ||||||
| failing in boot process, just prints a kernel notice and take |  | ||||||
| after into account if the descriptor is or not valid in order |  | ||||||
| to use it. All of them are set as GPIO output low configuration. |  | ||||||
| The gpio descriptor's API takes device tree property into account |  | ||||||
| and invert value if the pin is configured as active low. |  | ||||||
| So we also have to properly request pins from device tree |  | ||||||
| and set values correct in assert and deassert functions. |  | ||||||
| After this changes the order to make all assert and |  | ||||||
| deassert in the 'probe' process makes more sense: |  | ||||||
| * Parse device tree. |  | ||||||
| * make assert of the RC's and EP's before doing anything else. |  | ||||||
| * make deassert of the RC's before initializing the phy. |  | ||||||
| * Init the phy. |  | ||||||
| * make deassert of the EP's before initialize pci ports. |  | ||||||
| * Normal PCI initialization. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200313200913.24321-2-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 84 ++++++++++++++++++++------------- |  | ||||||
|  1 file changed, 51 insertions(+), 33 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -95,6 +95,7 @@ |  | ||||||
|   * @pcie: pointer to PCIe host info |  | ||||||
|   * @phy: pointer to PHY control block |  | ||||||
|   * @pcie_rst: pointer to port reset control |  | ||||||
| + * @gpio_rst: gpio reset |  | ||||||
|   * @slot: port slot |  | ||||||
|   * @enabled: indicates if port is enabled |  | ||||||
|   */ |  | ||||||
| @@ -104,6 +105,7 @@ struct mt7621_pcie_port { |  | ||||||
|  	struct mt7621_pcie *pcie; |  | ||||||
|  	struct phy *phy; |  | ||||||
|  	struct reset_control *pcie_rst; |  | ||||||
| +	struct gpio_desc *gpio_rst; |  | ||||||
|  	u32 slot; |  | ||||||
|  	bool enabled; |  | ||||||
|  }; |  | ||||||
| @@ -117,8 +119,6 @@ struct mt7621_pcie_port { |  | ||||||
|   * @offset: IO / Memory offset |  | ||||||
|   * @dev: Pointer to PCIe device |  | ||||||
|   * @ports: pointer to PCIe port information |  | ||||||
| - * @perst: gpio reset |  | ||||||
| - * @rst: pointer to pcie reset |  | ||||||
|   * @resets_inverted: depends on chip revision |  | ||||||
|   * reset lines are inverted. |  | ||||||
|   */ |  | ||||||
| @@ -133,8 +133,6 @@ struct mt7621_pcie { |  | ||||||
|  		resource_size_t io; |  | ||||||
|  	} offset; |  | ||||||
|  	struct list_head ports; |  | ||||||
| -	struct gpio_desc *perst; |  | ||||||
| -	struct reset_control *rst; |  | ||||||
|  	bool resets_inverted; |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| @@ -210,16 +208,16 @@ static void write_config(struct mt7621_p |  | ||||||
|  	pcie_write(pcie, val, RALINK_PCI_CONFIG_DATA); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static inline void mt7621_perst_gpio_pcie_assert(struct mt7621_pcie *pcie) |  | ||||||
| +static inline void mt7621_rst_gpio_pcie_assert(struct mt7621_pcie_port *port) |  | ||||||
|  { |  | ||||||
| -	gpiod_set_value(pcie->perst, 0); |  | ||||||
| -	mdelay(PERST_DELAY_US); |  | ||||||
| +	if (port->gpio_rst) |  | ||||||
| +		gpiod_set_value(port->gpio_rst, 1); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static inline void mt7621_perst_gpio_pcie_deassert(struct mt7621_pcie *pcie) |  | ||||||
| +static inline void mt7621_rst_gpio_pcie_deassert(struct mt7621_pcie_port *port) |  | ||||||
|  { |  | ||||||
| -	gpiod_set_value(pcie->perst, 1); |  | ||||||
| -	mdelay(PERST_DELAY_US); |  | ||||||
| +	if (port->gpio_rst) |  | ||||||
| +		gpiod_set_value(port->gpio_rst, 0); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static inline bool mt7621_pcie_port_is_linkup(struct mt7621_pcie_port *port) |  | ||||||
| @@ -367,6 +365,13 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|  	if (IS_ERR(port->phy)) |  | ||||||
|  		return PTR_ERR(port->phy); |  | ||||||
|   |  | ||||||
| +	port->gpio_rst = devm_gpiod_get_index_optional(dev, "reset", slot, |  | ||||||
| +						       GPIOD_OUT_LOW); |  | ||||||
| +	if (IS_ERR(port->gpio_rst)) { |  | ||||||
| +		dev_err(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
| +		return PTR_ERR(port->gpio_rst); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	port->slot = slot; |  | ||||||
|  	port->pcie = pcie; |  | ||||||
|   |  | ||||||
| @@ -383,12 +388,6 @@ static int mt7621_pcie_parse_dt(struct m |  | ||||||
|  	struct resource regs; |  | ||||||
|  	int err; |  | ||||||
|   |  | ||||||
| -	pcie->perst = devm_gpiod_get(dev, "perst", GPIOD_OUT_HIGH); |  | ||||||
| -	if (IS_ERR(pcie->perst)) { |  | ||||||
| -		dev_err(dev, "failed to get gpio perst\n"); |  | ||||||
| -		return PTR_ERR(pcie->perst); |  | ||||||
| -	} |  | ||||||
| - |  | ||||||
|  	err = of_address_to_resource(node, 0, ®s); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "missing \"reg\" property\n"); |  | ||||||
| @@ -399,12 +398,6 @@ static int mt7621_pcie_parse_dt(struct m |  | ||||||
|  	if (IS_ERR(pcie->base)) |  | ||||||
|  		return PTR_ERR(pcie->base); |  | ||||||
|   |  | ||||||
| -	pcie->rst = devm_reset_control_get_exclusive(dev, "pcie"); |  | ||||||
| -	if (PTR_ERR(pcie->rst) == -EPROBE_DEFER) { |  | ||||||
| -		dev_err(dev, "failed to get pcie reset control\n"); |  | ||||||
| -		return PTR_ERR(pcie->rst); |  | ||||||
| -	} |  | ||||||
| - |  | ||||||
|  	for_each_available_child_of_node(node, child) { |  | ||||||
|  		int slot; |  | ||||||
|   |  | ||||||
| @@ -458,16 +451,49 @@ static int mt7621_pcie_init_port(struct |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static void mt7621_pcie_reset_assert(struct mt7621_pcie *pcie) |  | ||||||
| +{ |  | ||||||
| +	struct mt7621_pcie_port *port; |  | ||||||
| + |  | ||||||
| +	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
| +		/* PCIe RC reset assert */ |  | ||||||
| +		mt7621_control_assert(port); |  | ||||||
| + |  | ||||||
| +		/* PCIe EP reset assert */ |  | ||||||
| +		mt7621_rst_gpio_pcie_assert(port); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	mdelay(PERST_DELAY_US); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void mt7621_pcie_reset_rc_deassert(struct mt7621_pcie *pcie) |  | ||||||
| +{ |  | ||||||
| +	struct mt7621_pcie_port *port; |  | ||||||
| + |  | ||||||
| +	list_for_each_entry(port, &pcie->ports, list) |  | ||||||
| +		mt7621_control_deassert(port); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static void mt7621_pcie_reset_ep_deassert(struct mt7621_pcie *pcie) |  | ||||||
| +{ |  | ||||||
| +	struct mt7621_pcie_port *port; |  | ||||||
| + |  | ||||||
| +	list_for_each_entry(port, &pcie->ports, list) |  | ||||||
| +		mt7621_rst_gpio_pcie_deassert(port); |  | ||||||
| + |  | ||||||
| +	mdelay(PERST_DELAY_US); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static void mt7621_pcie_init_ports(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = pcie->dev; |  | ||||||
|  	struct mt7621_pcie_port *port, *tmp; |  | ||||||
| -	u32 val = 0; |  | ||||||
|  	int err; |  | ||||||
|   |  | ||||||
|  	rt_sysc_m32(PERST_MODE_MASK, PERST_MODE_GPIO, MT7621_GPIO_MODE); |  | ||||||
|   |  | ||||||
| -	mt7621_perst_gpio_pcie_assert(pcie); |  | ||||||
| +	mt7621_pcie_reset_assert(pcie); |  | ||||||
| +	mt7621_pcie_reset_rc_deassert(pcie); |  | ||||||
|   |  | ||||||
|  	list_for_each_entry_safe(port, tmp, &pcie->ports, list) { |  | ||||||
|  		u32 slot = port->slot; |  | ||||||
| @@ -476,16 +502,10 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|  		if (err) { |  | ||||||
|  			dev_err(dev, "Initiating port %d failed\n", slot); |  | ||||||
|  			list_del(&port->list); |  | ||||||
| -		} else { |  | ||||||
| -			val = read_config(pcie, slot, PCIE_FTS_NUM); |  | ||||||
| -			dev_info(dev, "Port %d N_FTS = %x\n", slot, |  | ||||||
| -				 (unsigned int)val); |  | ||||||
|  		} |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	reset_control_assert(pcie->rst); |  | ||||||
| - |  | ||||||
| -	mt7621_perst_gpio_pcie_deassert(pcie); |  | ||||||
| +	mt7621_pcie_reset_ep_deassert(pcie); |  | ||||||
|   |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
|  		u32 slot = port->slot; |  | ||||||
| @@ -499,8 +519,6 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|  			port->enabled = false; |  | ||||||
|  		} |  | ||||||
|  	} |  | ||||||
| - |  | ||||||
| -	reset_control_deassert(pcie->rst); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static void mt7621_pcie_enable_port(struct mt7621_pcie_port *port) |  | ||||||
| @@ -1,45 +0,0 @@ | |||||||
| From e462e7d3211479df42357a620fa788a2257556b7 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 13 Mar 2020 21:09:09 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: change value for 'PERST_DELAY_MS' |  | ||||||
|  |  | ||||||
| Value of 'PERST_DELAY_MS' is too high and it is ok just |  | ||||||
| to set up to 100 ms. Update also define name from |  | ||||||
| 'PERST_DELAY_US' into 'PERST_DELAY_MS' |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200313200913.24321-3-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 6 +++--- |  | ||||||
|  1 file changed, 3 insertions(+), 3 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -86,7 +86,7 @@ |  | ||||||
|  #define MEMORY_BASE			0x0 |  | ||||||
|  #define PERST_MODE_MASK			GENMASK(11, 10) |  | ||||||
|  #define PERST_MODE_GPIO			BIT(10) |  | ||||||
| -#define PERST_DELAY_US			1000 |  | ||||||
| +#define PERST_DELAY_MS			100 |  | ||||||
|   |  | ||||||
|  /** |  | ||||||
|   * struct mt7621_pcie_port - PCIe port information |  | ||||||
| @@ -463,7 +463,7 @@ static void mt7621_pcie_reset_assert(str |  | ||||||
|  		mt7621_rst_gpio_pcie_assert(port); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	mdelay(PERST_DELAY_US); |  | ||||||
| +	mdelay(PERST_DELAY_MS); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static void mt7621_pcie_reset_rc_deassert(struct mt7621_pcie *pcie) |  | ||||||
| @@ -481,7 +481,7 @@ static void mt7621_pcie_reset_ep_deasser |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) |  | ||||||
|  		mt7621_rst_gpio_pcie_deassert(port); |  | ||||||
|   |  | ||||||
| -	mdelay(PERST_DELAY_US); |  | ||||||
| +	mdelay(PERST_DELAY_MS); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static void mt7621_pcie_init_ports(struct mt7621_pcie *pcie) |  | ||||||
| @@ -1,76 +0,0 @@ | |||||||
| From 4d6a758f2cd2122a7d895f913854c13da62ba6df Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 13 Mar 2020 21:09:12 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: release gpios after pci initialization |  | ||||||
|  |  | ||||||
| R3G's LEDs fail to initialize because one of them uses GPIO8 |  | ||||||
| Hence, release the GPIO resources after PCIe initialization |  | ||||||
| and properly release also in driver error path. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200313200913.24321-6-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 23 ++++++++++++++++++----- |  | ||||||
|  1 file changed, 18 insertions(+), 5 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -484,6 +484,15 @@ static void mt7621_pcie_reset_ep_deasser |  | ||||||
|  	mdelay(PERST_DELAY_MS); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static void mt7621_pcie_release_gpios(struct mt7621_pcie *pcie) |  | ||||||
| +{ |  | ||||||
| +	struct mt7621_pcie_port *port; |  | ||||||
| + |  | ||||||
| +	list_for_each_entry(port, &pcie->ports, list) |  | ||||||
| +		if (port->gpio_rst) |  | ||||||
| +			gpiod_put(port->gpio_rst); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static void mt7621_pcie_init_ports(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = pcie->dev; |  | ||||||
| @@ -683,7 +692,8 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pcie_init_virtual_bridges(pcie); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Nothing is connected in virtual bridges. Exiting..."); |  | ||||||
| -		return 0; |  | ||||||
| +		err = 0; |  | ||||||
| +		goto out_release_gpios; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	mt7621_pcie_enable_ports(pcie); |  | ||||||
| @@ -691,7 +701,7 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pci_parse_request_of_pci_ranges(pcie); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error requesting pci resources from ranges"); |  | ||||||
| -		return err; |  | ||||||
| +		goto out_release_gpios; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	setup_cm_memory_region(pcie); |  | ||||||
| @@ -699,16 +709,19 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pcie_request_resources(pcie, &res); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error requesting resources\n"); |  | ||||||
| -		return err; |  | ||||||
| +		goto out_release_gpios; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	err = mt7621_pcie_register_host(bridge, &res); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error registering host\n"); |  | ||||||
| -		return err; |  | ||||||
| +		goto out_release_gpios; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	return 0; |  | ||||||
| +out_release_gpios: |  | ||||||
| +	mt7621_pcie_release_gpios(pcie); |  | ||||||
| + |  | ||||||
| +	return err; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static const struct of_device_id mt7621_pci_ids[] = { |  | ||||||
| @@ -1,46 +0,0 @@ | |||||||
| From 4be54c3a495f08c05a8e485566e5b88cd3537f16 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 13 Mar 2020 21:09:13 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: delete no more needed |  | ||||||
|  'mt7621_reset_port' |  | ||||||
|  |  | ||||||
| After review all the resets at the beggining the function |  | ||||||
| 'mt7621_reset_port' is not needed anymore. Hence delete it |  | ||||||
| and its uses. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200313200913.24321-7-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 13 ------------- |  | ||||||
|  1 file changed, 13 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -255,13 +255,6 @@ static inline void mt7621_control_deasse |  | ||||||
|  		reset_control_assert(port->pcie_rst); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static void mt7621_reset_port(struct mt7621_pcie_port *port) |  | ||||||
| -{ |  | ||||||
| -	mt7621_control_assert(port); |  | ||||||
| -	msleep(100); |  | ||||||
| -	mt7621_control_deassert(port); |  | ||||||
| -} |  | ||||||
| - |  | ||||||
|  static void setup_cm_memory_region(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	struct resource *mem_resource = &pcie->mem; |  | ||||||
| @@ -427,12 +420,6 @@ static int mt7621_pcie_init_port(struct |  | ||||||
|  	u32 slot = port->slot; |  | ||||||
|  	int err; |  | ||||||
|   |  | ||||||
| -	/* |  | ||||||
| -	 * Any MT7621 Ralink pcie controller that doesn't have 0x0101 at |  | ||||||
| -	 * the end of the chip_id has inverted PCI resets. |  | ||||||
| -	 */ |  | ||||||
| -	mt7621_reset_port(port); |  | ||||||
| - |  | ||||||
|  	err = phy_init(port->phy); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "failed to initialize port%d phy\n", slot); |  | ||||||
| @@ -1,234 +0,0 @@ | |||||||
| From bf0c6782e5b9a6deee4e223655325dc004fae8dd Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sun, 15 Mar 2020 17:01:54 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci-phy: add 'mt7621_phy_rmw' to simplify |  | ||||||
|  code |  | ||||||
|  |  | ||||||
| In order to simplify driver code and decrease a bit LOC add new |  | ||||||
| function 'mt7621_phy_rmw' where clear and set bits are passed as |  | ||||||
| arguments. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200315160154.10292-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c | 158 +++++++++++------------- |  | ||||||
|  1 file changed, 71 insertions(+), 87 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| @@ -120,17 +120,25 @@ static inline void phy_write(struct mt76 |  | ||||||
|  	regmap_write(phy->regmap, reg, val); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static inline void mt7621_phy_rmw(struct mt7621_pci_phy *phy, |  | ||||||
| +				  u32 reg, u32 clr, u32 set) |  | ||||||
| +{ |  | ||||||
| +	u32 val = phy_read(phy, reg); |  | ||||||
| + |  | ||||||
| +	val &= ~clr; |  | ||||||
| +	val |= set; |  | ||||||
| +	phy_write(phy, val, reg); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static void mt7621_bypass_pipe_rst(struct mt7621_pci_phy *phy, |  | ||||||
|  				   struct mt7621_pci_phy_instance *instance) |  | ||||||
|  { |  | ||||||
|  	u32 offset = (instance->index != 1) ? |  | ||||||
|  		RG_PE1_PIPE_REG : RG_PE1_PIPE_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| -	u32 reg; |  | ||||||
|   |  | ||||||
| -	reg = phy_read(phy, offset); |  | ||||||
| -	reg &= ~(RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC); |  | ||||||
| -	reg |= (RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC); |  | ||||||
| -	phy_write(phy, reg, offset); |  | ||||||
| +	mt7621_phy_rmw(phy, offset, |  | ||||||
| +		       RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC, |  | ||||||
| +		       RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static void mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy, |  | ||||||
| @@ -139,97 +147,77 @@ static void mt7621_set_phy_for_ssc(struc |  | ||||||
|  	struct device *dev = phy->dev; |  | ||||||
|  	u32 reg = rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0); |  | ||||||
|  	u32 offset; |  | ||||||
| -	u32 val; |  | ||||||
|   |  | ||||||
|  	reg = (reg >> 6) & 0x7; |  | ||||||
|  	/* Set PCIe Port PHY to disable SSC */ |  | ||||||
|  	/* Debug Xtal Type */ |  | ||||||
| -	val = phy_read(phy, RG_PE1_FRC_H_XTAL_REG); |  | ||||||
| -	val &= ~(RG_PE1_FRC_H_XTAL_TYPE | RG_PE1_H_XTAL_TYPE); |  | ||||||
| -	val |= RG_PE1_FRC_H_XTAL_TYPE; |  | ||||||
| -	val |= RG_PE1_H_XTAL_TYPE_VAL(0x00); |  | ||||||
| -	phy_write(phy, val, RG_PE1_FRC_H_XTAL_REG); |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_FRC_H_XTAL_REG, |  | ||||||
| +		       RG_PE1_FRC_H_XTAL_TYPE | RG_PE1_H_XTAL_TYPE, |  | ||||||
| +		       RG_PE1_FRC_H_XTAL_TYPE | RG_PE1_H_XTAL_TYPE_VAL(0x00)); |  | ||||||
|   |  | ||||||
|  	/* disable port */ |  | ||||||
|  	offset = (instance->index != 1) ? |  | ||||||
|  		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| -	val = phy_read(phy, offset); |  | ||||||
| -	val &= ~(RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
| -	val |= RG_PE1_FRC_PHY_EN; |  | ||||||
| -	phy_write(phy, val, offset); |  | ||||||
| - |  | ||||||
| -	/* Set Pre-divider ratio (for host mode) */ |  | ||||||
| -	val = phy_read(phy, RG_PE1_H_PLL_REG); |  | ||||||
| -	val &= ~(RG_PE1_H_PLL_PREDIV); |  | ||||||
| +	mt7621_phy_rmw(phy, offset, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
|   |  | ||||||
|  	if (reg <= 5 && reg >= 3) { /* 40MHz Xtal */ |  | ||||||
| -		val |= RG_PE1_H_PLL_PREDIV_VAL(0x01); |  | ||||||
| -		phy_write(phy, val, RG_PE1_H_PLL_REG); |  | ||||||
| +		/* Set Pre-divider ratio (for host mode) */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV_VAL(0x01)); |  | ||||||
|  		dev_info(dev, "Xtal is 40MHz\n"); |  | ||||||
| -	} else { /* 25MHz | 20MHz Xtal */ |  | ||||||
| -		val |= RG_PE1_H_PLL_PREDIV_VAL(0x00); |  | ||||||
| -		phy_write(phy, val, RG_PE1_H_PLL_REG); |  | ||||||
| -		if (reg >= 6) { |  | ||||||
| -			dev_info(dev, "Xtal is 25MHz\n"); |  | ||||||
| - |  | ||||||
| -			/* Select feedback clock */ |  | ||||||
| -			val = phy_read(phy, RG_PE1_H_PLL_FBKSEL_REG); |  | ||||||
| -			val &= ~(RG_PE1_H_PLL_FBKSEL); |  | ||||||
| -			val |= RG_PE1_H_PLL_FBKSEL_VAL(0x01); |  | ||||||
| -			phy_write(phy, val, RG_PE1_H_PLL_FBKSEL_REG); |  | ||||||
| - |  | ||||||
| -			/* DDS NCPO PCW (for host mode) */ |  | ||||||
| -			val = phy_read(phy, RG_PE1_H_LCDDS_SSC_PRD_REG); |  | ||||||
| -			val &= ~(RG_PE1_H_LCDDS_SSC_PRD); |  | ||||||
| -			val |= RG_PE1_H_LCDDS_SSC_PRD_VAL(0x18000000); |  | ||||||
| -			phy_write(phy, val, RG_PE1_H_LCDDS_SSC_PRD_REG); |  | ||||||
| - |  | ||||||
| -			/* DDS SSC dither period control */ |  | ||||||
| -			val = phy_read(phy, RG_PE1_H_LCDDS_SSC_PRD_REG); |  | ||||||
| -			val &= ~(RG_PE1_H_LCDDS_SSC_PRD); |  | ||||||
| -			val |= RG_PE1_H_LCDDS_SSC_PRD_VAL(0x18d); |  | ||||||
| -			phy_write(phy, val, RG_PE1_H_LCDDS_SSC_PRD_REG); |  | ||||||
| - |  | ||||||
| -			/* DDS SSC dither amplitude control */ |  | ||||||
| -			val = phy_read(phy, RG_PE1_H_LCDDS_SSC_DELTA_REG); |  | ||||||
| -			val &= ~(RG_PE1_H_LCDDS_SSC_DELTA | |  | ||||||
| -				 RG_PE1_H_LCDDS_SSC_DELTA1); |  | ||||||
| -			val |= RG_PE1_H_LCDDS_SSC_DELTA_VAL(0x4a); |  | ||||||
| -			val |= RG_PE1_H_LCDDS_SSC_DELTA1_VAL(0x4a); |  | ||||||
| -			phy_write(phy, val, RG_PE1_H_LCDDS_SSC_DELTA_REG); |  | ||||||
| -		} else { |  | ||||||
| -			dev_info(dev, "Xtal is 20MHz\n"); |  | ||||||
| -		} |  | ||||||
| +	} else if (reg >= 6) { /* 25MHz Xal */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV_VAL(0x00)); |  | ||||||
| +		/* Select feedback clock */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_PLL_FBKSEL_REG, |  | ||||||
| +			       RG_PE1_H_PLL_FBKSEL, |  | ||||||
| +			       RG_PE1_H_PLL_FBKSEL_VAL(0x01)); |  | ||||||
| +		/* DDS NCPO PCW (for host mode) */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_LCDDS_SSC_PRD_REG, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_PRD, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_PRD_VAL(0x18000000)); |  | ||||||
| +		/* DDS SSC dither period control */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_LCDDS_SSC_PRD_REG, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_PRD, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_PRD_VAL(0x18d)); |  | ||||||
| +		/* DDS SSC dither amplitude control */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_LCDDS_SSC_DELTA_REG, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_DELTA | |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_DELTA1, |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_DELTA_VAL(0x4a) | |  | ||||||
| +			       RG_PE1_H_LCDDS_SSC_DELTA1_VAL(0x4a)); |  | ||||||
| +		dev_info(dev, "Xtal is 25MHz\n"); |  | ||||||
| +	} else { /* 20MHz Xtal */ |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV, |  | ||||||
| +			       RG_PE1_H_PLL_PREDIV_VAL(0x00)); |  | ||||||
| + |  | ||||||
| +		dev_info(dev, "Xtal is 20MHz\n"); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	/* DDS clock inversion */ |  | ||||||
| -	val = phy_read(phy, RG_PE1_LCDDS_CLK_PH_INV_REG); |  | ||||||
| -	val &= ~(RG_PE1_LCDDS_CLK_PH_INV); |  | ||||||
| -	val |= RG_PE1_LCDDS_CLK_PH_INV; |  | ||||||
| -	phy_write(phy, val, RG_PE1_LCDDS_CLK_PH_INV_REG); |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_LCDDS_CLK_PH_INV_REG, |  | ||||||
| +		       RG_PE1_LCDDS_CLK_PH_INV, RG_PE1_LCDDS_CLK_PH_INV); |  | ||||||
|   |  | ||||||
|  	/* Set PLL bits */ |  | ||||||
| -	val = phy_read(phy, RG_PE1_H_PLL_REG); |  | ||||||
| -	val &= ~(RG_PE1_H_PLL_BC | RG_PE1_H_PLL_BP | RG_PE1_H_PLL_IR | |  | ||||||
| -		 RG_PE1_H_PLL_IC | RG_PE1_PLL_DIVEN); |  | ||||||
| -	val |= RG_PE1_H_PLL_BC_VAL(0x02); |  | ||||||
| -	val |= RG_PE1_H_PLL_BP_VAL(0x06); |  | ||||||
| -	val |= RG_PE1_H_PLL_IR_VAL(0x02); |  | ||||||
| -	val |= RG_PE1_H_PLL_IC_VAL(0x01); |  | ||||||
| -	val |= RG_PE1_PLL_DIVEN_VAL(0x02); |  | ||||||
| -	phy_write(phy, val, RG_PE1_H_PLL_REG); |  | ||||||
| - |  | ||||||
| -	val = phy_read(phy, RG_PE1_H_PLL_BR_REG); |  | ||||||
| -	val &= ~(RG_PE1_H_PLL_BR); |  | ||||||
| -	val |= RG_PE1_H_PLL_BR_VAL(0x00); |  | ||||||
| -	phy_write(phy, val, RG_PE1_H_PLL_BR_REG); |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
| +		       RG_PE1_H_PLL_BC | RG_PE1_H_PLL_BP | RG_PE1_H_PLL_IR | |  | ||||||
| +		       RG_PE1_H_PLL_IC | RG_PE1_PLL_DIVEN, |  | ||||||
| +		       RG_PE1_H_PLL_BC_VAL(0x02) | RG_PE1_H_PLL_BP_VAL(0x06) | |  | ||||||
| +		       RG_PE1_H_PLL_IR_VAL(0x02) | RG_PE1_H_PLL_IC_VAL(0x01) | |  | ||||||
| +		       RG_PE1_PLL_DIVEN_VAL(0x02)); |  | ||||||
| + |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_H_PLL_BR_REG, |  | ||||||
| +		       RG_PE1_H_PLL_BR, RG_PE1_H_PLL_BR_VAL(0x00)); |  | ||||||
|   |  | ||||||
|  	if (reg <= 5 && reg >= 3) { /* 40MHz Xtal */ |  | ||||||
|  		/* set force mode enable of da_pe1_mstckdiv */ |  | ||||||
| -		val = phy_read(phy, RG_PE1_MSTCKDIV_REG); |  | ||||||
| -		val &= ~(RG_PE1_MSTCKDIV | RG_PE1_FRC_MSTCKDIV); |  | ||||||
| -		val |= (RG_PE1_MSTCKDIV_VAL(0x01) | RG_PE1_FRC_MSTCKDIV); |  | ||||||
| -		phy_write(phy, val, RG_PE1_MSTCKDIV_REG); |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_MSTCKDIV_REG, |  | ||||||
| +			       RG_PE1_MSTCKDIV | RG_PE1_FRC_MSTCKDIV, |  | ||||||
| +			       RG_PE1_MSTCKDIV_VAL(0x01) | RG_PE1_FRC_MSTCKDIV); |  | ||||||
|  	} |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -252,13 +240,11 @@ static int mt7621_pci_phy_power_on(struc |  | ||||||
|  	struct mt7621_pci_phy *mphy = dev_get_drvdata(phy->dev.parent); |  | ||||||
|  	u32 offset = (instance->index != 1) ? |  | ||||||
|  		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| -	u32 val; |  | ||||||
|   |  | ||||||
|  	/* Enable PHY and disable force mode */ |  | ||||||
| -	val = phy_read(mphy, offset); |  | ||||||
| -	val &= ~(RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
| -	val |= (RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
| -	phy_write(mphy, val, offset); |  | ||||||
| +	mt7621_phy_rmw(mphy, offset, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -269,13 +255,11 @@ static int mt7621_pci_phy_power_off(stru |  | ||||||
|  	struct mt7621_pci_phy *mphy = dev_get_drvdata(phy->dev.parent); |  | ||||||
|  	u32 offset = (instance->index != 1) ? |  | ||||||
|  		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| -	u32 val; |  | ||||||
|   |  | ||||||
|  	/* Disable PHY */ |  | ||||||
| -	val = phy_read(mphy, offset); |  | ||||||
| -	val &= ~(RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
| -	val |= RG_PE1_FRC_PHY_EN; |  | ||||||
| -	phy_write(mphy, val, offset); |  | ||||||
| +	mt7621_phy_rmw(mphy, offset, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN); |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -1,131 +0,0 @@ | |||||||
| From 3faf4e1c537de86058fc22a851cd979489b9185e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Wed, 18 Mar 2020 10:44:45 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: fix io space and properly set resource |  | ||||||
|  limits |  | ||||||
|  |  | ||||||
| Function 'mt7621_pci_parse_request_of_pci_ranges' is using |  | ||||||
| 'of_pci_range_to_resource' to get both mem and io resources. |  | ||||||
| Internally this function calls to 'pci_address_to_pio' which |  | ||||||
| returns -1 if io space address is an address > IO_SPACE_LIMIT |  | ||||||
| which is 0xFFFF for mips. This mt7621 soc has io space in physical |  | ||||||
| address 0x1e160000. In order to fix this, overwrite invalid io |  | ||||||
| 0xffffffff  with properly values from the device tree and set |  | ||||||
| mapped address of this resource as io port base memory address |  | ||||||
| calling 'set_io_port_base' function. There is also need to properly |  | ||||||
| setup resource limits and io and memory windows with properly |  | ||||||
| parsed values instead of set them as 'no limit' which it is wrong. |  | ||||||
| For any reason I don't really know legacy driver sets up mem window |  | ||||||
| as 0xFFFFFFFF and any other value seems to does not work as expected, |  | ||||||
| so set up also here with same values. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200318094445.19669-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 43 +++++++++++++++++++-------------- |  | ||||||
|  1 file changed, 25 insertions(+), 18 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -118,6 +118,7 @@ struct mt7621_pcie_port { |  | ||||||
|   * @busn: bus range |  | ||||||
|   * @offset: IO / Memory offset |  | ||||||
|   * @dev: Pointer to PCIe device |  | ||||||
| + * @io_map_base: virtual memory base address for io |  | ||||||
|   * @ports: pointer to PCIe port information |  | ||||||
|   * @resets_inverted: depends on chip revision |  | ||||||
|   * reset lines are inverted. |  | ||||||
| @@ -132,6 +133,7 @@ struct mt7621_pcie { |  | ||||||
|  		resource_size_t mem; |  | ||||||
|  		resource_size_t io; |  | ||||||
|  	} offset; |  | ||||||
| +	unsigned long io_map_base; |  | ||||||
|  	struct list_head ports; |  | ||||||
|  	bool resets_inverted; |  | ||||||
|  }; |  | ||||||
| @@ -291,22 +293,21 @@ static int mt7621_pci_parse_request_of_p |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	for_each_of_pci_range(&parser, &range) { |  | ||||||
| -		struct resource *res = NULL; |  | ||||||
| - |  | ||||||
|  		switch (range.flags & IORESOURCE_TYPE_BITS) { |  | ||||||
|  		case IORESOURCE_IO: |  | ||||||
| -			ioremap(range.cpu_addr, range.size); |  | ||||||
| -			res = &pcie->io; |  | ||||||
| +			pcie->io_map_base = |  | ||||||
| +				(unsigned long)ioremap(range.cpu_addr, |  | ||||||
| +						       range.size); |  | ||||||
| +			of_pci_range_to_resource(&range, node, &pcie->io); |  | ||||||
| +			pcie->io.start = range.cpu_addr; |  | ||||||
| +			pcie->io.end = range.cpu_addr + range.size - 1; |  | ||||||
|  			pcie->offset.io = 0x00000000UL; |  | ||||||
|  			break; |  | ||||||
|  		case IORESOURCE_MEM: |  | ||||||
| -			res = &pcie->mem; |  | ||||||
| +			of_pci_range_to_resource(&range, node, &pcie->mem); |  | ||||||
|  			pcie->offset.mem = 0x00000000UL; |  | ||||||
|  			break; |  | ||||||
|  		} |  | ||||||
| - |  | ||||||
| -		if (res) |  | ||||||
| -			of_pci_range_to_resource(&range, node, res); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	err = of_pci_parse_bus_range(node, &pcie->busn); |  | ||||||
| @@ -318,6 +319,8 @@ static int mt7621_pci_parse_request_of_p |  | ||||||
|  		pcie->busn.flags = IORESOURCE_BUS; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| +	set_io_port_base(pcie->io_map_base); |  | ||||||
| + |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -548,6 +551,10 @@ static void mt7621_pcie_enable_ports(str |  | ||||||
|  	u32 slot; |  | ||||||
|  	u32 val; |  | ||||||
|   |  | ||||||
| +	/* Setup MEMWIN and IOWIN */ |  | ||||||
| +	pcie_write(pcie, 0xffffffff, RALINK_PCI_MEMBASE); |  | ||||||
| +	pcie_write(pcie, pcie->io.start, RALINK_PCI_IOBASE); |  | ||||||
| + |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
|  		if (port->enabled) { |  | ||||||
|  			mt7621_pcie_port_clk_enable(port); |  | ||||||
| @@ -668,11 +675,17 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  		return err; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| +	err = mt7621_pci_parse_request_of_pci_ranges(pcie); |  | ||||||
| +	if (err) { |  | ||||||
| +		dev_err(dev, "Error requesting pci resources from ranges"); |  | ||||||
| +		goto out_release_gpios; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	/* set resources limits */ |  | ||||||
| -	iomem_resource.start = 0; |  | ||||||
| -	iomem_resource.end = ~0UL; /* no limit */ |  | ||||||
| -	ioport_resource.start = 0; |  | ||||||
| -	ioport_resource.end = ~0UL; /* no limit */ |  | ||||||
| +	iomem_resource.start = pcie->mem.start; |  | ||||||
| +	iomem_resource.end = pcie->mem.end; |  | ||||||
| +	ioport_resource.start = pcie->io.start; |  | ||||||
| +	ioport_resource.end = pcie->io.end; |  | ||||||
|   |  | ||||||
|  	mt7621_pcie_init_ports(pcie); |  | ||||||
|   |  | ||||||
| @@ -685,12 +698,6 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|   |  | ||||||
|  	mt7621_pcie_enable_ports(pcie); |  | ||||||
|   |  | ||||||
| -	err = mt7621_pci_parse_request_of_pci_ranges(pcie); |  | ||||||
| -	if (err) { |  | ||||||
| -		dev_err(dev, "Error requesting pci resources from ranges"); |  | ||||||
| -		goto out_release_gpios; |  | ||||||
| -	} |  | ||||||
| - |  | ||||||
|  	setup_cm_memory_region(pcie); |  | ||||||
|   |  | ||||||
|  	err = mt7621_pcie_request_resources(pcie, &res); |  | ||||||
| @@ -1,28 +0,0 @@ | |||||||
| From 0a3085ae142d8f5cf905b104bc66db3721a2fa33 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Thu, 19 Mar 2020 10:57:33 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: fix register to set up virtual bridges |  | ||||||
|  |  | ||||||
| Instead of being using PCI Configuration and Status Register to |  | ||||||
| set up virtual bridges we are using CONFIG_ADDR Register which is |  | ||||||
| wrong. Hence, set the correct value. |  | ||||||
|  |  | ||||||
| Fixes: 9a5e71a68d20 ("staging: mt7621-pci: simplify 'mt7621_pcie_init_virtual_bridges' function") |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200319095733.1557-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 2 +- |  | ||||||
|  1 file changed, 1 insertion(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -603,7 +603,7 @@ static int mt7621_pcie_init_virtual_brid |  | ||||||
|  		if ((pcie_link_status & BIT(i)) == 0) |  | ||||||
|  			p2p_br_devnum[i] = n++; |  | ||||||
|   |  | ||||||
| -	pcie_rmw(pcie, RALINK_PCI_CONFIG_ADDR, |  | ||||||
| +	pcie_rmw(pcie, RALINK_PCI_PCICFG_ADDR, |  | ||||||
|  		 PCIE_P2P_BR_DEVNUM_MASK_FULL, |  | ||||||
|  		 (p2p_br_devnum[0] << PCIE_P2P_BR_DEVNUM0_SHIFT) | |  | ||||||
|  		 (p2p_br_devnum[1] << PCIE_P2P_BR_DEVNUM1_SHIFT) | |  | ||||||
| @@ -1,34 +0,0 @@ | |||||||
| From 23a788c23ed10e0d79092fcb693dcf0e357e1f7e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Thu, 19 Mar 2020 17:14:16 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: don't return if get gpio fails |  | ||||||
|  |  | ||||||
| In some platforms gpio's are not used for reset but |  | ||||||
| for other purposes. Because of that when we try to |  | ||||||
| get them are valid gpio's but are already assigned |  | ||||||
| to do other function. To avoid those kind of problems |  | ||||||
| in those platforms just notice the fail in the kernel |  | ||||||
| but continue doing normal boot. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200319161416.19033-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 6 ++---- |  | ||||||
|  1 file changed, 2 insertions(+), 4 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -363,10 +363,8 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|   |  | ||||||
|  	port->gpio_rst = devm_gpiod_get_index_optional(dev, "reset", slot, |  | ||||||
|  						       GPIOD_OUT_LOW); |  | ||||||
| -	if (IS_ERR(port->gpio_rst)) { |  | ||||||
| -		dev_err(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
| -		return PTR_ERR(port->gpio_rst); |  | ||||||
| -	} |  | ||||||
| +	if (IS_ERR(port->gpio_rst)) |  | ||||||
| +		dev_notice(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
|   |  | ||||||
|  	port->slot = slot; |  | ||||||
|  	port->pcie = pcie; |  | ||||||
| @@ -1,272 +0,0 @@ | |||||||
| From 91eb47531421f0e8c9bc4594b4a7caa0e59dc83e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 20 Mar 2020 12:01:19 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci-phy: avoid to create to different phys |  | ||||||
|  for a dual port one |  | ||||||
|  |  | ||||||
| This soc has two phy's for the pcie one of them using just a different |  | ||||||
| register for settig it up but sharing all the rest of the config. Until |  | ||||||
| now we was presenting this schema as three different phy's in the device |  | ||||||
| tree using the 'phy-cells' node property to discriminate an index and |  | ||||||
| setting up a complete phy for the dual port index. This sometimes worked |  | ||||||
| properly but reconfiguring the same registers twice presents sometimes |  | ||||||
| some unstable pcie links and the ports was not properly being detected. |  | ||||||
| The problems only appears on hard resets and soft resets was properly |  | ||||||
| working. Instead of having this schema just set two phy's in the device |  | ||||||
| ree and use the 'phy-cells' property to say if the port has or not a dual |  | ||||||
| port. Doing this configuration and set up becomes easier, LOC is decreased |  | ||||||
| and the behaviour also gets deterministic with properly and stable pcie |  | ||||||
| links in both hard and soft resets. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200320110123.9907-2-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c | 144 ++++++++++-------------- |  | ||||||
|  1 file changed, 59 insertions(+), 85 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| @@ -78,31 +78,21 @@ |  | ||||||
|  #define MAX_PHYS	2 |  | ||||||
|   |  | ||||||
|  /** |  | ||||||
| - * struct mt7621_pci_phy_instance - Mt7621 Pcie PHY device |  | ||||||
| - * @phy: pointer to the kernel PHY device |  | ||||||
| - * @port_base: base register |  | ||||||
| - * @index: internal ID to identify the Mt7621 PCIe PHY |  | ||||||
| - */ |  | ||||||
| -struct mt7621_pci_phy_instance { |  | ||||||
| -	struct phy *phy; |  | ||||||
| -	void __iomem *port_base; |  | ||||||
| -	u32 index; |  | ||||||
| -}; |  | ||||||
| - |  | ||||||
| -/** |  | ||||||
|   * struct mt7621_pci_phy - Mt7621 Pcie PHY core |  | ||||||
|   * @dev: pointer to device |  | ||||||
|   * @regmap: kernel regmap pointer |  | ||||||
| - * @phys: pointer to Mt7621 PHY device |  | ||||||
| - * @nphys: number of PHY devices for this core |  | ||||||
| + * @phy: pointer to the kernel PHY device |  | ||||||
| + * @port_base: base register |  | ||||||
| + * @has_dual_port: if the phy has dual ports. |  | ||||||
|   * @bypass_pipe_rst: mark if 'mt7621_bypass_pipe_rst' |  | ||||||
|   * needs to be executed. Depends on chip revision. |  | ||||||
|   */ |  | ||||||
|  struct mt7621_pci_phy { |  | ||||||
|  	struct device *dev; |  | ||||||
|  	struct regmap *regmap; |  | ||||||
| -	struct mt7621_pci_phy_instance **phys; |  | ||||||
| -	int nphys; |  | ||||||
| +	struct phy *phy; |  | ||||||
| +	void __iomem *port_base; |  | ||||||
| +	bool has_dual_port; |  | ||||||
|  	bool bypass_pipe_rst; |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| @@ -130,23 +120,23 @@ static inline void mt7621_phy_rmw(struct |  | ||||||
|  	phy_write(phy, val, reg); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static void mt7621_bypass_pipe_rst(struct mt7621_pci_phy *phy, |  | ||||||
| -				   struct mt7621_pci_phy_instance *instance) |  | ||||||
| +static void mt7621_bypass_pipe_rst(struct mt7621_pci_phy *phy) |  | ||||||
|  { |  | ||||||
| -	u32 offset = (instance->index != 1) ? |  | ||||||
| -		RG_PE1_PIPE_REG : RG_PE1_PIPE_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_PIPE_REG, 0, RG_PE1_PIPE_RST); |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_PIPE_REG, 0, RG_PE1_PIPE_CMD_FRC); |  | ||||||
|   |  | ||||||
| -	mt7621_phy_rmw(phy, offset, |  | ||||||
| -		       RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC, |  | ||||||
| -		       RG_PE1_PIPE_RST | RG_PE1_PIPE_CMD_FRC); |  | ||||||
| +	if (phy->has_dual_port) { |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_PIPE_REG + RG_P0_TO_P1_WIDTH, |  | ||||||
| +			       0, RG_PE1_PIPE_RST); |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_PIPE_REG + RG_P0_TO_P1_WIDTH, |  | ||||||
| +			       0, RG_PE1_PIPE_CMD_FRC); |  | ||||||
| +	} |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static void mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy, |  | ||||||
| -				   struct mt7621_pci_phy_instance *instance) |  | ||||||
| +static void mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = phy->dev; |  | ||||||
|  	u32 reg = rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0); |  | ||||||
| -	u32 offset; |  | ||||||
|   |  | ||||||
|  	reg = (reg >> 6) & 0x7; |  | ||||||
|  	/* Set PCIe Port PHY to disable SSC */ |  | ||||||
| @@ -156,10 +146,13 @@ static void mt7621_set_phy_for_ssc(struc |  | ||||||
|  		       RG_PE1_FRC_H_XTAL_TYPE | RG_PE1_H_XTAL_TYPE_VAL(0x00)); |  | ||||||
|   |  | ||||||
|  	/* disable port */ |  | ||||||
| -	offset = (instance->index != 1) ? |  | ||||||
| -		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| -	mt7621_phy_rmw(phy, offset, |  | ||||||
| -		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
| +	mt7621_phy_rmw(phy, RG_PE1_FRC_PHY_REG, |  | ||||||
| +		       RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
| + |  | ||||||
| +	if (phy->has_dual_port) { |  | ||||||
| +		mt7621_phy_rmw(phy, RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH, |  | ||||||
| +			       RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
| +	} |  | ||||||
|   |  | ||||||
|  	if (reg <= 5 && reg >= 3) { /* 40MHz Xtal */ |  | ||||||
|  		/* Set Pre-divider ratio (for host mode) */ |  | ||||||
| @@ -223,43 +216,44 @@ static void mt7621_set_phy_for_ssc(struc |  | ||||||
|   |  | ||||||
|  static int mt7621_pci_phy_init(struct phy *phy) |  | ||||||
|  { |  | ||||||
| -	struct mt7621_pci_phy_instance *instance = phy_get_drvdata(phy); |  | ||||||
| -	struct mt7621_pci_phy *mphy = dev_get_drvdata(phy->dev.parent); |  | ||||||
| +	struct mt7621_pci_phy *mphy = phy_get_drvdata(phy); |  | ||||||
|   |  | ||||||
|  	if (mphy->bypass_pipe_rst) |  | ||||||
| -		mt7621_bypass_pipe_rst(mphy, instance); |  | ||||||
| +		mt7621_bypass_pipe_rst(mphy); |  | ||||||
|   |  | ||||||
| -	mt7621_set_phy_for_ssc(mphy, instance); |  | ||||||
| +	mt7621_set_phy_for_ssc(mphy); |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static int mt7621_pci_phy_power_on(struct phy *phy) |  | ||||||
|  { |  | ||||||
| -	struct mt7621_pci_phy_instance *instance = phy_get_drvdata(phy); |  | ||||||
| -	struct mt7621_pci_phy *mphy = dev_get_drvdata(phy->dev.parent); |  | ||||||
| -	u32 offset = (instance->index != 1) ? |  | ||||||
| -		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| +	struct mt7621_pci_phy *mphy = phy_get_drvdata(phy); |  | ||||||
|   |  | ||||||
|  	/* Enable PHY and disable force mode */ |  | ||||||
| -	mt7621_phy_rmw(mphy, offset, |  | ||||||
| -		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, |  | ||||||
| -		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN); |  | ||||||
| +	mt7621_phy_rmw(mphy, RG_PE1_FRC_PHY_REG, |  | ||||||
| +		       RG_PE1_FRC_PHY_EN, RG_PE1_PHY_EN); |  | ||||||
| + |  | ||||||
| +	if (mphy->has_dual_port) { |  | ||||||
| +		mt7621_phy_rmw(mphy, RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH, |  | ||||||
| +			       RG_PE1_FRC_PHY_EN, RG_PE1_PHY_EN); |  | ||||||
| +	} |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static int mt7621_pci_phy_power_off(struct phy *phy) |  | ||||||
|  { |  | ||||||
| -	struct mt7621_pci_phy_instance *instance = phy_get_drvdata(phy); |  | ||||||
| -	struct mt7621_pci_phy *mphy = dev_get_drvdata(phy->dev.parent); |  | ||||||
| -	u32 offset = (instance->index != 1) ? |  | ||||||
| -		RG_PE1_FRC_PHY_REG : RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH; |  | ||||||
| +	struct mt7621_pci_phy *mphy = phy_get_drvdata(phy); |  | ||||||
|   |  | ||||||
|  	/* Disable PHY */ |  | ||||||
| -	mt7621_phy_rmw(mphy, offset, |  | ||||||
| -		       RG_PE1_FRC_PHY_EN | RG_PE1_PHY_EN, |  | ||||||
| -		       RG_PE1_FRC_PHY_EN); |  | ||||||
| +	mt7621_phy_rmw(mphy, RG_PE1_FRC_PHY_REG, |  | ||||||
| +		       RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
| + |  | ||||||
| +	if (mphy->has_dual_port) { |  | ||||||
| +		mt7621_phy_rmw(mphy, RG_PE1_FRC_PHY_REG + RG_P0_TO_P1_WIDTH, |  | ||||||
| +			       RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
| +	} |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
| @@ -282,13 +276,15 @@ static struct phy *mt7621_pcie_phy_of_xl |  | ||||||
|  { |  | ||||||
|  	struct mt7621_pci_phy *mt7621_phy = dev_get_drvdata(dev); |  | ||||||
|   |  | ||||||
| -	if (args->args_count == 0) |  | ||||||
| -		return mt7621_phy->phys[0]->phy; |  | ||||||
| - |  | ||||||
|  	if (WARN_ON(args->args[0] >= MAX_PHYS)) |  | ||||||
|  		return ERR_PTR(-ENODEV); |  | ||||||
|   |  | ||||||
| -	return mt7621_phy->phys[args->args[0]]->phy; |  | ||||||
| +	mt7621_phy->has_dual_port = args->args[0]; |  | ||||||
| + |  | ||||||
| +	dev_info(dev, "PHY for 0x%08x (dual port = %d)\n", |  | ||||||
| +		 (unsigned int)mt7621_phy->port_base, mt7621_phy->has_dual_port); |  | ||||||
| + |  | ||||||
| +	return mt7621_phy->phy; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static const struct soc_device_attribute mt7621_pci_quirks_match[] = { |  | ||||||
| @@ -309,19 +305,11 @@ static int mt7621_pci_phy_probe(struct p |  | ||||||
|  	struct phy_provider *provider; |  | ||||||
|  	struct mt7621_pci_phy *phy; |  | ||||||
|  	struct resource *res; |  | ||||||
| -	int port; |  | ||||||
| -	void __iomem *port_base; |  | ||||||
|   |  | ||||||
|  	phy = devm_kzalloc(dev, sizeof(*phy), GFP_KERNEL); |  | ||||||
|  	if (!phy) |  | ||||||
|  		return -ENOMEM; |  | ||||||
|   |  | ||||||
| -	phy->nphys = MAX_PHYS; |  | ||||||
| -	phy->phys = devm_kcalloc(dev, phy->nphys, |  | ||||||
| -				 sizeof(*phy->phys), GFP_KERNEL); |  | ||||||
| -	if (!phy->phys) |  | ||||||
| -		return -ENOMEM; |  | ||||||
| - |  | ||||||
|  	attr = soc_device_match(mt7621_pci_quirks_match); |  | ||||||
|  	if (attr) |  | ||||||
|  		phy->bypass_pipe_rst = true; |  | ||||||
| @@ -335,39 +323,25 @@ static int mt7621_pci_phy_probe(struct p |  | ||||||
|  		return -ENXIO; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	port_base = devm_ioremap_resource(dev, res); |  | ||||||
| -	if (IS_ERR(port_base)) { |  | ||||||
| +	phy->port_base = devm_ioremap_resource(dev, res); |  | ||||||
| +	if (IS_ERR(phy->port_base)) { |  | ||||||
|  		dev_err(dev, "failed to remap phy regs\n"); |  | ||||||
| -		return PTR_ERR(port_base); |  | ||||||
| +		return PTR_ERR(phy->port_base); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	phy->regmap = devm_regmap_init_mmio(phy->dev, port_base, |  | ||||||
| +	phy->regmap = devm_regmap_init_mmio(phy->dev, phy->port_base, |  | ||||||
|  					    &mt7621_pci_phy_regmap_config); |  | ||||||
|  	if (IS_ERR(phy->regmap)) |  | ||||||
|  		return PTR_ERR(phy->regmap); |  | ||||||
|   |  | ||||||
| -	for (port = 0; port < MAX_PHYS; port++) { |  | ||||||
| -		struct mt7621_pci_phy_instance *instance; |  | ||||||
| -		struct phy *pphy; |  | ||||||
| - |  | ||||||
| -		instance = devm_kzalloc(dev, sizeof(*instance), GFP_KERNEL); |  | ||||||
| -		if (!instance) |  | ||||||
| -			return -ENOMEM; |  | ||||||
| - |  | ||||||
| -		phy->phys[port] = instance; |  | ||||||
| - |  | ||||||
| -		pphy = devm_phy_create(dev, dev->of_node, &mt7621_pci_phy_ops); |  | ||||||
| -		if (IS_ERR(phy)) { |  | ||||||
| -			dev_err(dev, "failed to create phy\n"); |  | ||||||
| -			return PTR_ERR(phy); |  | ||||||
| -		} |  | ||||||
| - |  | ||||||
| -		instance->port_base = port_base; |  | ||||||
| -		instance->phy = pphy; |  | ||||||
| -		instance->index = port; |  | ||||||
| -		phy_set_drvdata(pphy, instance); |  | ||||||
| +	phy->phy = devm_phy_create(dev, dev->of_node, &mt7621_pci_phy_ops); |  | ||||||
| +	if (IS_ERR(phy)) { |  | ||||||
| +		dev_err(dev, "failed to create phy\n"); |  | ||||||
| +		return PTR_ERR(phy); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| +	phy_set_drvdata(phy->phy, phy); |  | ||||||
| + |  | ||||||
|  	provider = devm_of_phy_provider_register(dev, mt7621_pcie_phy_of_xlate); |  | ||||||
|   |  | ||||||
|  	return PTR_ERR_OR_ZERO(provider); |  | ||||||
| @@ -1,42 +0,0 @@ | |||||||
| From c752b54bda4d772426c5eeb56978d2e41bd525b4 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 20 Mar 2020 12:01:21 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: use only two phys from device tree |  | ||||||
|  |  | ||||||
| In order to align work with the mt7621-pci-phy part of |  | ||||||
| the driver and device tree which is now using only two |  | ||||||
| real phys one of them dual ported properly parse the |  | ||||||
| device tree and don't call phy initialization for the |  | ||||||
| slot 1 because is being taking into account when the |  | ||||||
| phy for the slot 0 is instantiated. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200320110123.9907-4-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 7 ++++++- |  | ||||||
|  1 file changed, 6 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -358,7 +358,7 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|   |  | ||||||
|  	snprintf(name, sizeof(name), "pcie-phy%d", slot); |  | ||||||
|  	port->phy = devm_phy_get(dev, name); |  | ||||||
| -	if (IS_ERR(port->phy)) |  | ||||||
| +	if (IS_ERR(port->phy) && slot != 1) |  | ||||||
|  		return PTR_ERR(port->phy); |  | ||||||
|   |  | ||||||
|  	port->gpio_rst = devm_gpiod_get_index_optional(dev, "reset", slot, |  | ||||||
| @@ -495,6 +495,11 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|  	list_for_each_entry_safe(port, tmp, &pcie->ports, list) { |  | ||||||
|  		u32 slot = port->slot; |  | ||||||
|   |  | ||||||
| +		if (slot == 1) { |  | ||||||
| +			port->enabled = true; |  | ||||||
| +			continue; |  | ||||||
| +		} |  | ||||||
| + |  | ||||||
|  		err = mt7621_pcie_init_port(port); |  | ||||||
|  		if (err) { |  | ||||||
|  			dev_err(dev, "Initiating port %d failed\n", slot); |  | ||||||
| @@ -1,26 +0,0 @@ | |||||||
| From b59343b7de448c30e5b098484a7c7c5cb300df2f Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 20 Mar 2020 12:01:22 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: change variable to print for slot |  | ||||||
|  |  | ||||||
| We are using the counter to print the slot which has been |  | ||||||
| enabled. Use the correct associated slot for the port instead. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200320110123.9907-5-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 2 +- |  | ||||||
|  1 file changed, 1 insertion(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -562,7 +562,7 @@ static void mt7621_pcie_enable_ports(str |  | ||||||
|  		if (port->enabled) { |  | ||||||
|  			mt7621_pcie_port_clk_enable(port); |  | ||||||
|  			mt7621_pcie_enable_port(port); |  | ||||||
| -			dev_info(dev, "PCIE%d enabled\n", num_slots_enabled); |  | ||||||
| +			dev_info(dev, "PCIE%d enabled\n", port->slot); |  | ||||||
|  			num_slots_enabled++; |  | ||||||
|  		} |  | ||||||
|  	} |  | ||||||
| @@ -1,33 +0,0 @@ | |||||||
| From 87068309300c707d659ce79232eae827604804a4 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 20 Mar 2020 12:01:23 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: be sure gpio descriptor is null on fails |  | ||||||
|  |  | ||||||
| Function 'devm_gpiod_get_index_optional' returns NULL if the |  | ||||||
| descriptor is invalid and the error associated for the error |  | ||||||
| pointer is ENOENT. Sometimes if the pin is just assigned the |  | ||||||
| error associated for the pointer might not be ENOENT but other. |  | ||||||
| In order to avoid weirds behaviours if this happen set descriptor |  | ||||||
| to NULL in the driver port structure. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200320110123.9907-6-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 4 +++- |  | ||||||
|  1 file changed, 3 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -363,8 +363,10 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|   |  | ||||||
|  	port->gpio_rst = devm_gpiod_get_index_optional(dev, "reset", slot, |  | ||||||
|  						       GPIOD_OUT_LOW); |  | ||||||
| -	if (IS_ERR(port->gpio_rst)) |  | ||||||
| +	if (IS_ERR(port->gpio_rst)) { |  | ||||||
|  		dev_notice(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
| +		port->gpio_rst = NULL; |  | ||||||
| +	} |  | ||||||
|   |  | ||||||
|  	port->slot = slot; |  | ||||||
|  	port->pcie = pcie; |  | ||||||
| @@ -1,79 +0,0 @@ | |||||||
| From d81fe3c13aa6f4ab1ec318212d2007175e6d05aa Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Fri, 20 Mar 2020 16:38:37 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: avoid to poweroff the phy for slot one |  | ||||||
|  |  | ||||||
| Phy for slot 0 and 1 is shared and handled properly in slot 0. |  | ||||||
| If there is only one port in use,(slot 0) we shall not call the |  | ||||||
| 'phy_power_off' function with an invalid slot because kernel |  | ||||||
| will crash with an unaligned access fault like the following: |  | ||||||
|  |  | ||||||
| mt7621-pci 1e140000.pcie: Error applying setting, reverse things back |  | ||||||
| mt7621-pci-phy 1e149000.pcie-phy: PHY for 0xbe149000 (dual port = 1) |  | ||||||
| mt7621-pci-phy 1e14a000.pcie-phy: PHY for 0xbe14a000 (dual port = 0) |  | ||||||
| mt7621-pci-phy 1e149000.pcie-phy: Xtal is 40MHz |  | ||||||
| mt7621-pci-phy 1e14a000.pcie-phy: Xtal is 40MHz |  | ||||||
| mt7621-pci 1e140000.pcie: pcie1 no card, disable it (RST & CLK) |  | ||||||
| Unhandled kernel unaligned access[#1]: |  | ||||||
| CPU: 3 PID: 111 Comm: kworker/3:2 Not tainted 5.6.0-rc3-00347-g825c6f470c62-dirty #9 |  | ||||||
| Workqueue: events deferred_probe_work_func |  | ||||||
| $ 0   : 00000000 00000001 5f60d043 8fe1ba80 |  | ||||||
| $ 4   : 0000010d 01eb9000 00000000 00000000 |  | ||||||
| $ 8   : 294b4c00 80940000 00000008 000000ce |  | ||||||
| $12   : 2e303030 00000000 00000000 65696370 |  | ||||||
| $16   : ffffffed 0000010d 8e373cd0 8214c1e0 |  | ||||||
| $20   : 00000000 82144c80 82144680 8214c250 |  | ||||||
| $24   : 00000018 803ef8f4 |  | ||||||
| $28   : 8e372000 8e373c60 8214c080 803940e8 |  | ||||||
| Hi    : 00000125 |  | ||||||
| Lo    : 122f2000 |  | ||||||
| epc   : 807b3328 mutex_lock+0x8/0x44 |  | ||||||
| ra    : 803940e8 phy_power_off+0x28/0xb0 |  | ||||||
| Status: 1100fc03        KERNEL EXL IE |  | ||||||
| Cause : 00800010 (ExcCode 04) |  | ||||||
| BadVA : 0000010d |  | ||||||
| PrId  : 0001992f (MIPS 1004Kc) |  | ||||||
| Modules linked in: |  | ||||||
| Process kworker/3:2 (pid: 111, threadinfo=(ptrval), task=(ptrval), tls=00000000) |  | ||||||
| Stack : 8e373cd0 803fe4f4 8e372000 8e373c90 8214c080 804fde1c 8e373c98 808d62f4 |  | ||||||
|          8e373c78 00000000 8214c254 804fe648 1e160000 804f27b8 00000001 808d62f4 |  | ||||||
|          00000000 00000001 8214c228 808d62f4 80930000 809a0000 8fd47e10 808d63d4 |  | ||||||
|          808d62d4 8fd47e10 808d0000 808d0000 8e373cd0 8e373cd0 809e2a74 809db510 |  | ||||||
|          809db510 00000006 00000001 00000000 00000000 00000000 01000000 1e1440ff |  | ||||||
|          ... |  | ||||||
| Call Trace: |  | ||||||
| [<807b3328>] mutex_lock+0x8/0x44 |  | ||||||
| [<803940e8>] phy_power_off+0x28/0xb0 |  | ||||||
| [<804fe648>] mt7621_pci_probe+0xc20/0xd18 |  | ||||||
| [<80402ab8>] platform_drv_probe+0x40/0x94 |  | ||||||
| [<80400a74>] really_probe+0x104/0x364 |  | ||||||
| [<803feb74>] bus_for_each_drv+0x84/0xdc |  | ||||||
| [<80400924>] __device_attach+0xdc/0x120 |  | ||||||
| [<803ffb5c>] bus_probe_device+0xa0/0xbc |  | ||||||
| [<80400124>] deferred_probe_work_func+0x7c/0xbc |  | ||||||
| [<800420e8>] process_one_work+0x230/0x450 |  | ||||||
| [<80042638>] worker_thread+0x330/0x5fc |  | ||||||
| [<80048eb0>] kthread+0x12c/0x134 |  | ||||||
| [<80007438>] ret_from_kernel_thread+0x14/0x1c |  | ||||||
| Code: 24050002  27bdfff8  8f830000 <c0850000> 14a00005  00000000  00600825  e0810000  1020fffa |  | ||||||
|  |  | ||||||
| Fixes: bf516f413f4e ("staging: mt7621-pci: use only two phys from device tree") |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200320153837.20415-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 3 ++- |  | ||||||
|  1 file changed, 2 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -517,7 +517,8 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|  		if (!mt7621_pcie_port_is_linkup(port)) { |  | ||||||
|  			dev_err(dev, "pcie%d no card, disable it (RST & CLK)\n", |  | ||||||
|  				slot); |  | ||||||
| -			phy_power_off(port->phy); |  | ||||||
| +			if (slot != 1) |  | ||||||
| +				phy_power_off(port->phy); |  | ||||||
|  			mt7621_control_assert(port); |  | ||||||
|  			mt7621_pcie_port_clk_disable(port); |  | ||||||
|  			port->enabled = false; |  | ||||||
| @@ -1,91 +0,0 @@ | |||||||
| From 9d789a7728c37e8730b6a9cca60cf155f18537ea Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sat, 21 Mar 2020 08:26:50 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: delete release gpios related code |  | ||||||
|  |  | ||||||
| Making gpio8 and gpio9 vendor specific and putting them |  | ||||||
| into the specific dts file makes not needed to release |  | ||||||
| gpios anymore because we are not occupying those pins |  | ||||||
| in the first place if it is not necessary. When the |  | ||||||
| device tree is parsed we can also check and return for |  | ||||||
| the error because we rely in the fact that the related |  | ||||||
| device for the board is correct. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200321072650.7784-3-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 27 +++++++-------------------- |  | ||||||
|  1 file changed, 7 insertions(+), 20 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -364,8 +364,8 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|  	port->gpio_rst = devm_gpiod_get_index_optional(dev, "reset", slot, |  | ||||||
|  						       GPIOD_OUT_LOW); |  | ||||||
|  	if (IS_ERR(port->gpio_rst)) { |  | ||||||
| -		dev_notice(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
| -		port->gpio_rst = NULL; |  | ||||||
| +		dev_err(dev, "Failed to get GPIO for PCIe%d\n", slot); |  | ||||||
| +		return PTR_ERR(port->gpio_rst); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	port->slot = slot; |  | ||||||
| @@ -474,15 +474,6 @@ static void mt7621_pcie_reset_ep_deasser |  | ||||||
|  	mdelay(PERST_DELAY_MS); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static void mt7621_pcie_release_gpios(struct mt7621_pcie *pcie) |  | ||||||
| -{ |  | ||||||
| -	struct mt7621_pcie_port *port; |  | ||||||
| - |  | ||||||
| -	list_for_each_entry(port, &pcie->ports, list) |  | ||||||
| -		if (port->gpio_rst) |  | ||||||
| -			gpiod_put(port->gpio_rst); |  | ||||||
| -} |  | ||||||
| - |  | ||||||
|  static void mt7621_pcie_init_ports(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = pcie->dev; |  | ||||||
| @@ -684,7 +675,7 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pci_parse_request_of_pci_ranges(pcie); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error requesting pci resources from ranges"); |  | ||||||
| -		goto out_release_gpios; |  | ||||||
| +		return err; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	/* set resources limits */ |  | ||||||
| @@ -698,8 +689,7 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pcie_init_virtual_bridges(pcie); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Nothing is connected in virtual bridges. Exiting..."); |  | ||||||
| -		err = 0; |  | ||||||
| -		goto out_release_gpios; |  | ||||||
| +		return 0; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	mt7621_pcie_enable_ports(pcie); |  | ||||||
| @@ -709,19 +699,16 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	err = mt7621_pcie_request_resources(pcie, &res); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error requesting resources\n"); |  | ||||||
| -		goto out_release_gpios; |  | ||||||
| +		return err; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	err = mt7621_pcie_register_host(bridge, &res); |  | ||||||
|  	if (err) { |  | ||||||
|  		dev_err(dev, "Error registering host\n"); |  | ||||||
| -		goto out_release_gpios; |  | ||||||
| +		return err; |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -out_release_gpios: |  | ||||||
| -	mt7621_pcie_release_gpios(pcie); |  | ||||||
| - |  | ||||||
| -	return err; |  | ||||||
| +	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
|  static const struct of_device_id mt7621_pci_ids[] = { |  | ||||||
| @@ -1,29 +0,0 @@ | |||||||
| From 60a15339ceab9fc2a6cdc85fd54b66b2c947ab4e Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sat, 21 Mar 2020 14:36:21 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: use builtin_platform_driver() |  | ||||||
|  |  | ||||||
| Macro builtin_platform_driver can be used for builtin drivers |  | ||||||
| that don't do anything in driver init. So, use the macro |  | ||||||
| builtin_platform_driver and remove some boilerplate code. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200321133624.31388-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 7 +------ |  | ||||||
|  1 file changed, 1 insertion(+), 6 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -725,9 +725,4 @@ static struct platform_driver mt7621_pci |  | ||||||
|  	}, |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| -static int __init mt7621_pci_init(void) |  | ||||||
| -{ |  | ||||||
| -	return platform_driver_register(&mt7621_pci_driver); |  | ||||||
| -} |  | ||||||
| - |  | ||||||
| -module_init(mt7621_pci_init); |  | ||||||
| +builtin_platform_driver(mt7621_pci_driver); |  | ||||||
| @@ -1,32 +0,0 @@ | |||||||
| From ffe3dee4081055b4f58bc50dd3f5c97de42cf126 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sat, 21 Mar 2020 14:36:23 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci-phy: use builtin_platform_driver() |  | ||||||
|  |  | ||||||
| Macro builtin_platform_driver can be used for builtin drivers |  | ||||||
| that don't do anything in driver init. So, use the macro |  | ||||||
| builtin_platform_driver and remove some boilerplate code. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200321133624.31388-3-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c | 7 +------ |  | ||||||
|  1 file changed, 1 insertion(+), 6 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| @@ -361,12 +361,7 @@ static struct platform_driver mt7621_pci |  | ||||||
|  	}, |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| -static int __init mt7621_pci_phy_drv_init(void) |  | ||||||
| -{ |  | ||||||
| -	return platform_driver_register(&mt7621_pci_phy_driver); |  | ||||||
| -} |  | ||||||
| - |  | ||||||
| -module_init(mt7621_pci_phy_drv_init); |  | ||||||
| +builtin_platform_driver(mt7621_pci_phy_driver); |  | ||||||
|   |  | ||||||
|  MODULE_AUTHOR("Sergio Paracuellos <sergio.paracuellos@gmail.com>"); |  | ||||||
|  MODULE_DESCRIPTION("MediaTek MT7621 PCIe PHY driver"); |  | ||||||
| @@ -1,68 +0,0 @@ | |||||||
| From ff83e3023cb8fc3b5dfc12e0c91bf1eb9dc4c4c6 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sat, 21 Mar 2020 14:36:24 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci-phy: re-do 'xtal_mode' detection |  | ||||||
|  |  | ||||||
| Detection of the Xtal mode is using magic numbers that |  | ||||||
| can be avoided using properly some definitions and a more |  | ||||||
| accurate variable name from 'reg' into 'xtal_mode'. This |  | ||||||
| increase readability. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200321133624.31388-4-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c | 15 ++++++++++----- |  | ||||||
|  1 file changed, 10 insertions(+), 5 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci-phy/pci-mt7621-phy.c |  | ||||||
| @@ -75,6 +75,9 @@ |  | ||||||
|   |  | ||||||
|  #define RG_PE1_FRC_MSTCKDIV			BIT(5) |  | ||||||
|   |  | ||||||
| +#define XTAL_MODE_SEL_SHIFT			6 |  | ||||||
| +#define XTAL_MODE_SEL_MASK			0x7 |  | ||||||
| + |  | ||||||
|  #define MAX_PHYS	2 |  | ||||||
|   |  | ||||||
|  /** |  | ||||||
| @@ -136,9 +139,11 @@ static void mt7621_bypass_pipe_rst(struc |  | ||||||
|  static void mt7621_set_phy_for_ssc(struct mt7621_pci_phy *phy) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = phy->dev; |  | ||||||
| -	u32 reg = rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0); |  | ||||||
| +	u32 xtal_mode; |  | ||||||
| + |  | ||||||
| +	xtal_mode = (rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0) |  | ||||||
| +		     >> XTAL_MODE_SEL_SHIFT) & XTAL_MODE_SEL_MASK; |  | ||||||
|   |  | ||||||
| -	reg = (reg >> 6) & 0x7; |  | ||||||
|  	/* Set PCIe Port PHY to disable SSC */ |  | ||||||
|  	/* Debug Xtal Type */ |  | ||||||
|  	mt7621_phy_rmw(phy, RG_PE1_FRC_H_XTAL_REG, |  | ||||||
| @@ -154,13 +159,13 @@ static void mt7621_set_phy_for_ssc(struc |  | ||||||
|  			       RG_PE1_PHY_EN, RG_PE1_FRC_PHY_EN); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
| -	if (reg <= 5 && reg >= 3) { /* 40MHz Xtal */ |  | ||||||
| +	if (xtal_mode <= 5 && xtal_mode >= 3) { /* 40MHz Xtal */ |  | ||||||
|  		/* Set Pre-divider ratio (for host mode) */ |  | ||||||
|  		mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
|  			       RG_PE1_H_PLL_PREDIV, |  | ||||||
|  			       RG_PE1_H_PLL_PREDIV_VAL(0x01)); |  | ||||||
|  		dev_info(dev, "Xtal is 40MHz\n"); |  | ||||||
| -	} else if (reg >= 6) { /* 25MHz Xal */ |  | ||||||
| +	} else if (xtal_mode >= 6) { /* 25MHz Xal */ |  | ||||||
|  		mt7621_phy_rmw(phy, RG_PE1_H_PLL_REG, |  | ||||||
|  			       RG_PE1_H_PLL_PREDIV, |  | ||||||
|  			       RG_PE1_H_PLL_PREDIV_VAL(0x00)); |  | ||||||
| @@ -206,7 +211,7 @@ static void mt7621_set_phy_for_ssc(struc |  | ||||||
|  	mt7621_phy_rmw(phy, RG_PE1_H_PLL_BR_REG, |  | ||||||
|  		       RG_PE1_H_PLL_BR, RG_PE1_H_PLL_BR_VAL(0x00)); |  | ||||||
|   |  | ||||||
| -	if (reg <= 5 && reg >= 3) { /* 40MHz Xtal */ |  | ||||||
| +	if (xtal_mode <= 5 && xtal_mode >= 3) { /* 40MHz Xtal */ |  | ||||||
|  		/* set force mode enable of da_pe1_mstckdiv */ |  | ||||||
|  		mt7621_phy_rmw(phy, RG_PE1_MSTCKDIV_REG, |  | ||||||
|  			       RG_PE1_MSTCKDIV | RG_PE1_FRC_MSTCKDIV, |  | ||||||
| @@ -1,35 +0,0 @@ | |||||||
| From 4f0f36b67564311a4ce4441510ef94848febbab2 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Sun, 22 Mar 2020 08:21:28 +0100 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: avoid to set 'iomem_resource' addresses |  | ||||||
|  |  | ||||||
| Setting up kernel resource 'iomem_resource' for PCI with |  | ||||||
| addresses parsed from device tree gots into a conflict within |  | ||||||
| the usb xhci driver: |  | ||||||
|  |  | ||||||
| xhci-mtk 1e1c0000.xhci: can't request region for resource [mem 0x1e1c0000-0x1e1c0fff] |  | ||||||
| xhci-mtk: probe of 1e1c0000.xhci failed with error -16 |  | ||||||
|  |  | ||||||
| Don't assign it and maintain the default addresses for this |  | ||||||
| resource seems to fix the problem. Checking legacy driver it |  | ||||||
| is being only  setting the 'ioport_resource'. |  | ||||||
|  |  | ||||||
| Fixes: 09dd629eeabb ("staging: mt7621-pci: fix io space and properly set resource limits") |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200322072128.4454-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 2 -- |  | ||||||
|  1 file changed, 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -679,8 +679,6 @@ static int mt7621_pci_probe(struct platf |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	/* set resources limits */ |  | ||||||
| -	iomem_resource.start = pcie->mem.start; |  | ||||||
| -	iomem_resource.end = pcie->mem.end; |  | ||||||
|  	ioport_resource.start = pcie->io.start; |  | ||||||
|  	ioport_resource.end = pcie->io.end; |  | ||||||
|   |  | ||||||
| @@ -1,65 +0,0 @@ | |||||||
| From 5fcded5e857cf66c9592e4be28c4dab4520c9177 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Thu, 9 Apr 2020 13:16:52 +0200 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: properly power off dual-ported pcie phy |  | ||||||
|  |  | ||||||
| Pcie phy for pcie0 and pcie1 is shared using a dual ported |  | ||||||
| one. Current code was assuming that if nothing is connected |  | ||||||
| in pcie0 it won't be also nothing connected in pcie1. This |  | ||||||
| assumtion is wrong for some devices such us 'Mikrotik rbm33g' |  | ||||||
| and 'ZyXEL LTE3301-PLUS' where only connecting a card to the |  | ||||||
| second bus on the phy is possible. For such devices kernel |  | ||||||
| hangs in the same point because of the wrong poweroff of the |  | ||||||
| phy getting the following trace: |  | ||||||
|  |  | ||||||
| mt7621-pci-phy 1e149000.pcie-phy: PHY for 0xbe149000 (dual port = 1) |  | ||||||
| mt7621-pci-phy 1e14a000.pcie-phy: PHY for 0xbe14a000 (dual port = 0) |  | ||||||
| mt7621-pci-phy 1e149000.pcie-phy: Xtal is 40MHz |  | ||||||
| mt7621-pci-phy 1e14a000.pcie-phy: Xtal is 40MHz |  | ||||||
| mt7621-pci 1e140000.pcie: pcie0 no card, disable it (RST & CLK) |  | ||||||
| [hangs] |  | ||||||
|  |  | ||||||
| The wrong assumption is located in the 'mt7621_pcie_init_ports' |  | ||||||
| function where we are just making a power off of the phy for |  | ||||||
| slots 0 and 2 if nothing is connected in them. Hence, only |  | ||||||
| poweroff the phy if nothing is connected in both slot 0 and |  | ||||||
| slot 1 avoiding the kernel to hang. |  | ||||||
|  |  | ||||||
| Fixes: 5737cfe87a9c ("staging: mt7621-pci: avoid to poweroff the phy for slot one") |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200409111652.30964-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 12 ++++++++++-- |  | ||||||
|  1 file changed, 10 insertions(+), 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -502,17 +502,25 @@ static void mt7621_pcie_init_ports(struc |  | ||||||
|   |  | ||||||
|  	mt7621_pcie_reset_ep_deassert(pcie); |  | ||||||
|   |  | ||||||
| +	tmp = NULL; |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
|  		u32 slot = port->slot; |  | ||||||
|   |  | ||||||
|  		if (!mt7621_pcie_port_is_linkup(port)) { |  | ||||||
|  			dev_err(dev, "pcie%d no card, disable it (RST & CLK)\n", |  | ||||||
|  				slot); |  | ||||||
| -			if (slot != 1) |  | ||||||
| -				phy_power_off(port->phy); |  | ||||||
|  			mt7621_control_assert(port); |  | ||||||
|  			mt7621_pcie_port_clk_disable(port); |  | ||||||
|  			port->enabled = false; |  | ||||||
| + |  | ||||||
| +			if (slot == 0) { |  | ||||||
| +				tmp = port; |  | ||||||
| +				continue; |  | ||||||
| +			} |  | ||||||
| + |  | ||||||
| +			if (slot == 1 && tmp && !tmp->enabled) |  | ||||||
| +				phy_power_off(tmp->phy); |  | ||||||
| + |  | ||||||
|  		} |  | ||||||
|  	} |  | ||||||
|  } |  | ||||||
| @@ -1,157 +0,0 @@ | |||||||
| From fab6710e4c51f4eb622f95a08322ab5fdbe3f295 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Mon, 13 Apr 2020 07:59:42 +0200 |  | ||||||
| Subject: [PATCH] staging: mt7621-pci: fix PCIe interrupt mapping |  | ||||||
|  |  | ||||||
| MT7621 has three assigned interrupts for the pcie. This |  | ||||||
| interrupts should properly being mapped taking into account |  | ||||||
| which devices are finally connected in which bus according |  | ||||||
| to link status. So the irq mappings should be as follows |  | ||||||
| according to link status (three bits indicating which devices |  | ||||||
| are link up): |  | ||||||
|  |  | ||||||
| * For PCIe Bus 1 slot 0: |  | ||||||
|   - status = 0x2 || status = 0x6 => IRQ = pcie1_irq (24). |  | ||||||
|   - status = 0x4 => IRQ = pcie2_irq (25). |  | ||||||
|   - default => IRQ = pcie0_irq (23). |  | ||||||
| * For PCIe Bus 2 slot 0: |  | ||||||
|   - status = 0x5 || status = 0x6 => IRQ = pcie2_irq (25). |  | ||||||
|   - default => IRQ = pcie1_irq (24). |  | ||||||
| * For PCIe Bus 2 slot 1: |  | ||||||
|   - status = 0x5 || status = 0x6 => IRQ = pcie2_irq (25). |  | ||||||
|   - default => IRQ = pcie1_irq (24). |  | ||||||
| * For PCIe Bus 3 any slot: |  | ||||||
|   - default => IRQ = pcie2_irq (25). |  | ||||||
|  |  | ||||||
| Because of this, the function 'of_irq_parse_and_map_pci' cannot |  | ||||||
| be used and we need to change device tree information from using |  | ||||||
| the 'interrupt-map' and 'interrupt-map-mask' properties into an |  | ||||||
| 'interrupts' property to be able to get irq information from the |  | ||||||
| ports using the 'platform_get_irq' and storing an 'irq-map' into |  | ||||||
| the pcie driver data node to properly map correct irq using a |  | ||||||
| new 'mt7621_map_irq' function where this map will be read and the |  | ||||||
| correct irq returned. |  | ||||||
|  |  | ||||||
| Fixes: 46d093124df4 ("staging: mt7621-pci: improve interrupt mapping") |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Link: https://lore.kernel.org/r/20200413055942.2714-1-sergio.paracuellos@gmail.com |  | ||||||
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| --- |  | ||||||
|  drivers/staging/mt7621-dts/mt7621.dtsi  |  9 +++---- |  | ||||||
|  drivers/staging/mt7621-pci/pci-mt7621.c | 36 +++++++++++++++++++++++-- |  | ||||||
|  2 files changed, 38 insertions(+), 7 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| +++ b/drivers/staging/mt7621-pci/pci-mt7621.c |  | ||||||
| @@ -97,6 +97,7 @@ |  | ||||||
|   * @pcie_rst: pointer to port reset control |  | ||||||
|   * @gpio_rst: gpio reset |  | ||||||
|   * @slot: port slot |  | ||||||
| + * @irq: GIC irq |  | ||||||
|   * @enabled: indicates if port is enabled |  | ||||||
|   */ |  | ||||||
|  struct mt7621_pcie_port { |  | ||||||
| @@ -107,6 +108,7 @@ struct mt7621_pcie_port { |  | ||||||
|  	struct reset_control *pcie_rst; |  | ||||||
|  	struct gpio_desc *gpio_rst; |  | ||||||
|  	u32 slot; |  | ||||||
| +	int irq; |  | ||||||
|  	bool enabled; |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| @@ -120,6 +122,7 @@ struct mt7621_pcie_port { |  | ||||||
|   * @dev: Pointer to PCIe device |  | ||||||
|   * @io_map_base: virtual memory base address for io |  | ||||||
|   * @ports: pointer to PCIe port information |  | ||||||
| + * @irq_map: irq mapping info according pcie link status |  | ||||||
|   * @resets_inverted: depends on chip revision |  | ||||||
|   * reset lines are inverted. |  | ||||||
|   */ |  | ||||||
| @@ -135,6 +138,7 @@ struct mt7621_pcie { |  | ||||||
|  	} offset; |  | ||||||
|  	unsigned long io_map_base; |  | ||||||
|  	struct list_head ports; |  | ||||||
| +	int irq_map[PCIE_P2P_MAX]; |  | ||||||
|  	bool resets_inverted; |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| @@ -279,6 +283,16 @@ static void setup_cm_memory_region(struc |  | ||||||
|  	} |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static int mt7621_map_irq(const struct pci_dev *pdev, u8 slot, u8 pin) |  | ||||||
| +{ |  | ||||||
| +	struct mt7621_pcie *pcie = pdev->bus->sysdata; |  | ||||||
| +	struct device *dev = pcie->dev; |  | ||||||
| +	int irq = pcie->irq_map[slot]; |  | ||||||
| + |  | ||||||
| +	dev_info(dev, "bus=%d slot=%d irq=%d\n", pdev->bus->number, slot, irq); |  | ||||||
| +	return irq; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static int mt7621_pci_parse_request_of_pci_ranges(struct mt7621_pcie *pcie) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = pcie->dev; |  | ||||||
| @@ -330,6 +344,7 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|  { |  | ||||||
|  	struct mt7621_pcie_port *port; |  | ||||||
|  	struct device *dev = pcie->dev; |  | ||||||
| +	struct platform_device *pdev = to_platform_device(dev); |  | ||||||
|  	struct device_node *pnode = dev->of_node; |  | ||||||
|  	struct resource regs; |  | ||||||
|  	char name[10]; |  | ||||||
| @@ -371,6 +386,12 @@ static int mt7621_pcie_parse_port(struct |  | ||||||
|  	port->slot = slot; |  | ||||||
|  	port->pcie = pcie; |  | ||||||
|   |  | ||||||
| +	port->irq = platform_get_irq(pdev, slot); |  | ||||||
| +	if (port->irq < 0) { |  | ||||||
| +		dev_err(dev, "Failed to get IRQ for PCIe%d\n", slot); |  | ||||||
| +		return -ENXIO; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	INIT_LIST_HEAD(&port->list); |  | ||||||
|  	list_add_tail(&port->list, &pcie->ports); |  | ||||||
|   |  | ||||||
| @@ -585,13 +606,15 @@ static int mt7621_pcie_init_virtual_brid |  | ||||||
|  { |  | ||||||
|  	u32 pcie_link_status = 0; |  | ||||||
|  	u32 n; |  | ||||||
| -	int i; |  | ||||||
| +	int i = 0; |  | ||||||
|  	u32 p2p_br_devnum[PCIE_P2P_MAX]; |  | ||||||
| +	int irqs[PCIE_P2P_MAX]; |  | ||||||
|  	struct mt7621_pcie_port *port; |  | ||||||
|   |  | ||||||
|  	list_for_each_entry(port, &pcie->ports, list) { |  | ||||||
|  		u32 slot = port->slot; |  | ||||||
|   |  | ||||||
| +		irqs[i++] = port->irq; |  | ||||||
|  		if (port->enabled) |  | ||||||
|  			pcie_link_status |= BIT(slot); |  | ||||||
|  	} |  | ||||||
| @@ -614,6 +637,15 @@ static int mt7621_pcie_init_virtual_brid |  | ||||||
|  		 (p2p_br_devnum[1] << PCIE_P2P_BR_DEVNUM1_SHIFT) | |  | ||||||
|  		 (p2p_br_devnum[2] << PCIE_P2P_BR_DEVNUM2_SHIFT)); |  | ||||||
|   |  | ||||||
| +	/* Assign IRQs */ |  | ||||||
| +	n = 0; |  | ||||||
| +	for (i = 0; i < PCIE_P2P_MAX; i++) |  | ||||||
| +		if (pcie_link_status & BIT(i)) |  | ||||||
| +			pcie->irq_map[n++] = irqs[i]; |  | ||||||
| + |  | ||||||
| +	for (i = n; i < PCIE_P2P_MAX; i++) |  | ||||||
| +		pcie->irq_map[i] = -1; |  | ||||||
| + |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -638,7 +670,7 @@ static int mt7621_pcie_register_host(str |  | ||||||
|  	host->busnr = pcie->busn.start; |  | ||||||
|  	host->dev.parent = pcie->dev; |  | ||||||
|  	host->ops = &mt7621_pci_ops; |  | ||||||
| -	host->map_irq = of_irq_parse_and_map_pci; |  | ||||||
| +	host->map_irq = mt7621_map_irq; |  | ||||||
|  	host->swizzle_irq = pci_common_swizzle; |  | ||||||
|  	host->sysdata = pcie; |  | ||||||
|   |  | ||||||
| @@ -1,26 +0,0 @@ | |||||||
| From 1f0400d0e2c410b04f246aefb2e9b5155eb4b0bf Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Date: Tue, 13 Oct 2020 10:05:47 +0800 |  | ||||||
| Subject: mips: ralink: enable zboot support |  | ||||||
|  |  | ||||||
| Some of these ralink devices come with an ancient u-boot which can't |  | ||||||
| extract LZMA properly when image gets too big. |  | ||||||
| Enable zboot support to get a self-extracting kernel instead of relying |  | ||||||
| on broken u-boot support. |  | ||||||
|  |  | ||||||
| Signed-off-by: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de> |  | ||||||
| --- |  | ||||||
|  arch/mips/Kconfig | 1 + |  | ||||||
|  1 file changed, 1 insertion(+) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/Kconfig |  | ||||||
| +++ b/arch/mips/Kconfig |  | ||||||
| @@ -631,6 +631,7 @@ config RALINK |  | ||||||
|  	select SYS_SUPPORTS_32BIT_KERNEL |  | ||||||
|  	select SYS_SUPPORTS_LITTLE_ENDIAN |  | ||||||
|  	select SYS_SUPPORTS_MIPS16 |  | ||||||
| +	select SYS_SUPPORTS_ZBOOT |  | ||||||
|  	select SYS_HAS_EARLY_PRINTK |  | ||||||
|  	select CLKDEV_LOOKUP |  | ||||||
|  	select ARCH_HAS_RESET_CONTROLLER |  | ||||||
| @@ -1,45 +0,0 @@ | |||||||
| From 3f9ef7785a9cd69cb75f5e2ea4ca79a24752e496 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sander Vanheule <sander@svanheule.net> |  | ||||||
| Date: Wed, 3 Feb 2021 10:21:41 +0100 |  | ||||||
| Subject: MIPS: ralink: manage low reset lines |  | ||||||
|  |  | ||||||
| Reset lines with indices smaller than 8 are currently considered invalid |  | ||||||
| by the rt2880-reset reset controller. |  | ||||||
|  |  | ||||||
| The MT7621 SoC uses a number of these low reset lines. The DTS defines |  | ||||||
| reset lines "hsdma", "fe", and "mcm" with respective values 5, 6, and 2. |  | ||||||
| As a result of the above restriction, these resets cannot be asserted or |  | ||||||
| de-asserted by the reset controller. In cases where the bootloader does |  | ||||||
| not de-assert these lines, this results in e.g. the MT7621's internal |  | ||||||
| switch staying in reset. |  | ||||||
|  |  | ||||||
| Change the reset controller to only ignore the system reset, so all |  | ||||||
| reset lines with index greater than 0 are considered valid. |  | ||||||
|  |  | ||||||
| Signed-off-by: Sander Vanheule <sander@svanheule.net> |  | ||||||
| Acked-by: John Crispin <john@phrozen.org> |  | ||||||
| Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/reset.c | 4 ++-- |  | ||||||
|  1 file changed, 2 insertions(+), 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/reset.c |  | ||||||
| +++ b/arch/mips/ralink/reset.c |  | ||||||
| @@ -27,7 +27,7 @@ static int ralink_assert_device(struct r |  | ||||||
|  { |  | ||||||
|  	u32 val; |  | ||||||
|   |  | ||||||
| -	if (id < 8) |  | ||||||
| +	if (id == 0) |  | ||||||
|  		return -1; |  | ||||||
|   |  | ||||||
|  	val = rt_sysc_r32(SYSC_REG_RESET_CTRL); |  | ||||||
| @@ -42,7 +42,7 @@ static int ralink_deassert_device(struct |  | ||||||
|  { |  | ||||||
|  	u32 val; |  | ||||||
|   |  | ||||||
| -	if (id < 8) |  | ||||||
| +	if (id == 0) |  | ||||||
|  		return -1; |  | ||||||
|   |  | ||||||
|  	val = rt_sysc_r32(SYSC_REG_RESET_CTRL); |  | ||||||
| @@ -1,97 +0,0 @@ | |||||||
| --- a/drivers/misc/Makefile |  | ||||||
| +++ b/drivers/misc/Makefile |  | ||||||
| @@ -52,6 +52,7 @@ obj-$(CONFIG_ECHO)		+= echo/ |  | ||||||
|  obj-$(CONFIG_VEXPRESS_SYSCFG)	+= vexpress-syscfg.o |  | ||||||
|  obj-$(CONFIG_CXL_BASE)		+= cxl/ |  | ||||||
|  obj-$(CONFIG_PCI_ENDPOINT_TEST)	+= pci_endpoint_test.o |  | ||||||
| +obj-$(CONFIG_SOC_MT7620)	+= linkit.o |  | ||||||
|  obj-$(CONFIG_OCXL)		+= ocxl/ |  | ||||||
|  obj-y				+= cardreader/ |  | ||||||
|  obj-$(CONFIG_PVPANIC)   	+= pvpanic.o |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/drivers/misc/linkit.c |  | ||||||
| @@ -0,0 +1,84 @@ |  | ||||||
| +/* |  | ||||||
| + *  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 |  | ||||||
| + *  publishhed by the Free Software Foundation. |  | ||||||
| + * |  | ||||||
| + *  Copyright (C) 2015 John Crispin <blogic@openwrt.org> |  | ||||||
| + */ |  | ||||||
| + |  | ||||||
| +#include <linux/module.h> |  | ||||||
| +#include <linux/platform_device.h> |  | ||||||
| +#include <linux/of.h> |  | ||||||
| +#include <linux/mtd/mtd.h> |  | ||||||
| +#include <linux/gpio.h> |  | ||||||
| + |  | ||||||
| +#define LINKIT_LATCH_GPIO	11 |  | ||||||
| + |  | ||||||
| +struct linkit_hw_data { |  | ||||||
| +	char board[16]; |  | ||||||
| +	char rev[16]; |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +static void sanify_string(char *s) |  | ||||||
| +{ |  | ||||||
| +	int i; |  | ||||||
| + |  | ||||||
| +	for (i = 0; i < 15; i++) |  | ||||||
| +		if (s[i] <= 0x20) |  | ||||||
| +			s[i] = '\0'; |  | ||||||
| +	s[15] = '\0'; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int linkit_probe(struct platform_device *pdev) |  | ||||||
| +{ |  | ||||||
| +	struct linkit_hw_data hw; |  | ||||||
| +	struct mtd_info *mtd; |  | ||||||
| +	size_t retlen; |  | ||||||
| +	int ret; |  | ||||||
| + |  | ||||||
| +	mtd = get_mtd_device_nm("factory"); |  | ||||||
| +	if (IS_ERR(mtd)) |  | ||||||
| +		return PTR_ERR(mtd); |  | ||||||
| + |  | ||||||
| +	ret = mtd_read(mtd, 0x400, sizeof(hw), &retlen, (u_char *) &hw); |  | ||||||
| +	put_mtd_device(mtd); |  | ||||||
| + |  | ||||||
| +	sanify_string(hw.board); |  | ||||||
| +	sanify_string(hw.rev); |  | ||||||
| + |  | ||||||
| +	dev_info(&pdev->dev, "Version  : %s\n", hw.board); |  | ||||||
| +	dev_info(&pdev->dev, "Revision : %s\n", hw.rev); |  | ||||||
| + |  | ||||||
| +	if (!strcmp(hw.board, "LINKITS7688")) { |  | ||||||
| +		dev_info(&pdev->dev, "setting up bootstrap latch\n"); |  | ||||||
| + |  | ||||||
| +		if (devm_gpio_request(&pdev->dev, LINKIT_LATCH_GPIO, "bootstrap")) { |  | ||||||
| +			dev_err(&pdev->dev, "failed to setup bootstrap gpio\n"); |  | ||||||
| +			return -1; |  | ||||||
| +		} |  | ||||||
| +		gpio_direction_output(LINKIT_LATCH_GPIO, 0); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct of_device_id linkit_match[] = { |  | ||||||
| +	{ .compatible = "mediatek,linkit" }, |  | ||||||
| +	{}, |  | ||||||
| +}; |  | ||||||
| +MODULE_DEVICE_TABLE(of, linkit_match); |  | ||||||
| + |  | ||||||
| +static struct platform_driver linkit_driver = { |  | ||||||
| +	.probe = linkit_probe, |  | ||||||
| +	.driver = { |  | ||||||
| +		.name = "mtk-linkit", |  | ||||||
| +		.owner = THIS_MODULE, |  | ||||||
| +		.of_match_table = linkit_match, |  | ||||||
| +	}, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
| +int __init linkit_init(void) |  | ||||||
| +{ |  | ||||||
| +	return platform_driver_register(&linkit_driver); |  | ||||||
| +} |  | ||||||
| +late_initcall_sync(linkit_init); |  | ||||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							| @@ -1,85 +0,0 @@ | |||||||
| From 3d5f4da8296b23eb3abf8b13122b0d06a215e79c Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Weijie Gao <weijie.gao@mediatek.com> |  | ||||||
| Date: Wed, 1 Apr 2020 02:07:59 +0800 |  | ||||||
| Subject: [PATCH 2/2] dt-bindings: add documentation for mt7621-nand driver |  | ||||||
|  |  | ||||||
| This patch adds documentation for MediaTek MT7621 NAND flash controller |  | ||||||
| driver. |  | ||||||
|  |  | ||||||
| Signed-off-by: Weijie Gao <weijie.gao@mediatek.com> |  | ||||||
| --- |  | ||||||
|  .../bindings/mtd/mediatek,mt7621-nfc.yaml          | 68 ++++++++++++++++++++++ |  | ||||||
|  1 file changed, 68 insertions(+) |  | ||||||
|  create mode 100644 Documentation/devicetree/bindings/mtd/mediatek,mt7621-nfc.yaml |  | ||||||
|  |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/Documentation/devicetree/bindings/mtd/mediatek,mt7621-nfc.yaml |  | ||||||
| @@ -0,0 +1,68 @@ |  | ||||||
| +# SPDX-License-Identifier: GPL-2.0 |  | ||||||
| +%YAML 1.2 |  | ||||||
| +--- |  | ||||||
| +$id: http://devicetree.org/schemas/mtd/mediatek,mt7621-nfc.yaml# |  | ||||||
| +$schema: http://devicetree.org/meta-schemas/core.yaml# |  | ||||||
| + |  | ||||||
| +title: MediaTek MT7621 SoC NAND Flash Controller (NFC) DT binding |  | ||||||
| + |  | ||||||
| +maintainers: |  | ||||||
| +  - Weijie Gao <weijie.gao@mediatek.com> |  | ||||||
| + |  | ||||||
| +description: | |  | ||||||
| +  This driver uses a single node to describe both NAND Flash controller |  | ||||||
| +  interface (NFI) and ECC engine for MT7621 SoC. |  | ||||||
| +  MT7621 supports only one chip select. |  | ||||||
| + |  | ||||||
| +properties: |  | ||||||
| +  "#address-cells": false |  | ||||||
| +  "#size-cells": false |  | ||||||
| + |  | ||||||
| +  compatible: |  | ||||||
| +    enum: |  | ||||||
| +      - mediatek,mt7621-nfc |  | ||||||
| + |  | ||||||
| +  reg: |  | ||||||
| +    items: |  | ||||||
| +      - description: Register base of NFI core |  | ||||||
| +      - description: Register base of ECC engine |  | ||||||
| + |  | ||||||
| +  reg-names: |  | ||||||
| +    items: |  | ||||||
| +      - const: nfi |  | ||||||
| +      - const: ecc |  | ||||||
| + |  | ||||||
| +  clocks: |  | ||||||
| +    items: |  | ||||||
| +      - description: Source clock for NFI core, fixed 125MHz |  | ||||||
| + |  | ||||||
| +  clock-names: |  | ||||||
| +    items: |  | ||||||
| +      - const: nfi_clk |  | ||||||
| + |  | ||||||
| +required: |  | ||||||
| +  - compatible |  | ||||||
| +  - reg |  | ||||||
| +  - reg-names |  | ||||||
| +  - clocks |  | ||||||
| +  - clock-names |  | ||||||
| + |  | ||||||
| +examples: |  | ||||||
| +  - | |  | ||||||
| +    nficlock: nficlock { |  | ||||||
| +    	#clock-cells = <0>; |  | ||||||
| +    	compatible = "fixed-clock"; |  | ||||||
| + |  | ||||||
| +    	clock-frequency = <125000000>; |  | ||||||
| +    }; |  | ||||||
| + |  | ||||||
| +    nand@1e003000 { |  | ||||||
| +    	compatible = "mediatek,mt7621-nfc"; |  | ||||||
| + |  | ||||||
| +    	reg = <0x1e003000 0x800 |  | ||||||
| +    	       0x1e003800 0x800>; |  | ||||||
| +    	reg-names = "nfi", "ecc"; |  | ||||||
| + |  | ||||||
| +    	clocks = <&nficlock>; |  | ||||||
| +    	clock-names = "nfi_clk"; |  | ||||||
| +    }; |  | ||||||
| @@ -1,61 +0,0 @@ | |||||||
| There is a variant of MT7621 which contains only one CPU core instead of 2. |  | ||||||
| This is not reflected in the config register, so the kernel detects more |  | ||||||
| physical cores, which leads to a hang on SMP bringup. |  | ||||||
| Add a hack to detect missing cores. |  | ||||||
|  |  | ||||||
| Signed-off-by: Felix Fietkau <nbd@nbd.name> |  | ||||||
|  |  | ||||||
| --- a/arch/mips/kernel/smp-cps.c |  | ||||||
| +++ b/arch/mips/kernel/smp-cps.c |  | ||||||
| @@ -43,6 +43,11 @@ static unsigned core_vpe_count(unsigned |  | ||||||
|  	return mips_cps_numvps(cluster, core); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +bool __weak plat_cpu_core_present(int core) |  | ||||||
| +{ |  | ||||||
| +	return true; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static void __init cps_smp_setup(void) |  | ||||||
|  { |  | ||||||
|  	unsigned int nclusters, ncores, nvpes, core_vpes; |  | ||||||
| @@ -60,6 +65,8 @@ static void __init cps_smp_setup(void) |  | ||||||
|   |  | ||||||
|  		ncores = mips_cps_numcores(cl); |  | ||||||
|  		for (c = 0; c < ncores; c++) { |  | ||||||
| +			if (!plat_cpu_core_present(c)) |  | ||||||
| +				continue; |  | ||||||
|  			core_vpes = core_vpe_count(cl, c); |  | ||||||
|   |  | ||||||
|  			if (c > 0) |  | ||||||
| --- a/arch/mips/ralink/mt7621.c |  | ||||||
| +++ b/arch/mips/ralink/mt7621.c |  | ||||||
| @@ -13,6 +13,7 @@ |  | ||||||
|  #include <asm/mips-cps.h> |  | ||||||
|  #include <asm/mach-ralink/ralink_regs.h> |  | ||||||
|  #include <asm/mach-ralink/mt7621.h> |  | ||||||
| +#include <asm/mips-boards/launch.h> |  | ||||||
|   |  | ||||||
|  #include <pinmux.h> |  | ||||||
|   |  | ||||||
| @@ -160,6 +161,20 @@ void __init ralink_of_remap(void) |  | ||||||
|  		panic("Failed to remap core resources"); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +bool plat_cpu_core_present(int core) |  | ||||||
| +{ |  | ||||||
| +	struct cpulaunch *launch = (struct cpulaunch *)CKSEG0ADDR(CPULAUNCH); |  | ||||||
| + |  | ||||||
| +	if (!core) |  | ||||||
| +		return true; |  | ||||||
| +	launch += core * 2; /* 2 VPEs per core */ |  | ||||||
| +	if (!(launch->flags & LAUNCH_FREADY)) |  | ||||||
| +		return false; |  | ||||||
| +	if (launch->flags & (LAUNCH_FGO | LAUNCH_FGONE)) |  | ||||||
| +		return false; |  | ||||||
| +	return true; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  void prom_soc_init(struct ralink_soc_info *soc_info) |  | ||||||
|  { |  | ||||||
|  	void __iomem *sysc = (void __iomem *) KSEG1ADDR(MT7621_SYSC_BASE); |  | ||||||
| @@ -1,87 +0,0 @@ | |||||||
| --- a/arch/mips/ralink/mt7621.c |  | ||||||
| +++ b/arch/mips/ralink/mt7621.c |  | ||||||
| @@ -7,6 +7,7 @@ |  | ||||||
|   |  | ||||||
|  #include <linux/kernel.h> |  | ||||||
|  #include <linux/init.h> |  | ||||||
| +#include <linux/jiffies.h> |  | ||||||
|   |  | ||||||
|  #include <asm/mipsregs.h> |  | ||||||
|  #include <asm/smp-ops.h> |  | ||||||
| @@ -14,6 +15,7 @@ |  | ||||||
|  #include <asm/mach-ralink/ralink_regs.h> |  | ||||||
|  #include <asm/mach-ralink/mt7621.h> |  | ||||||
|  #include <asm/mips-boards/launch.h> |  | ||||||
| +#include <asm/delay.h> |  | ||||||
|   |  | ||||||
|  #include <pinmux.h> |  | ||||||
|   |  | ||||||
| @@ -175,6 +177,58 @@ bool plat_cpu_core_present(int core) |  | ||||||
|  	return true; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +#define LPS_PREC 8 |  | ||||||
| +/* |  | ||||||
| +*  Re-calibration lpj(loop-per-jiffy). |  | ||||||
| +*  (derived from kernel/calibrate.c) |  | ||||||
| +*/ |  | ||||||
| +static int udelay_recal(void) |  | ||||||
| +{ |  | ||||||
| +	unsigned int i, lpj = 0; |  | ||||||
| +	unsigned long ticks, loopbit; |  | ||||||
| +	int lps_precision = LPS_PREC; |  | ||||||
| + |  | ||||||
| +	lpj = (1<<12); |  | ||||||
| + |  | ||||||
| +	while ((lpj <<= 1) != 0) { |  | ||||||
| +		/* wait for "start of" clock tick */ |  | ||||||
| +		ticks = jiffies; |  | ||||||
| +		while (ticks == jiffies) |  | ||||||
| +			/* nothing */; |  | ||||||
| + |  | ||||||
| +		/* Go .. */ |  | ||||||
| +		ticks = jiffies; |  | ||||||
| +		__delay(lpj); |  | ||||||
| +		ticks = jiffies - ticks; |  | ||||||
| +		if (ticks) |  | ||||||
| +			break; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	/* |  | ||||||
| +	 * Do a binary approximation to get lpj set to |  | ||||||
| +	 * equal one clock (up to lps_precision bits) |  | ||||||
| +	 */ |  | ||||||
| +	lpj >>= 1; |  | ||||||
| +	loopbit = lpj; |  | ||||||
| +	while (lps_precision-- && (loopbit >>= 1)) { |  | ||||||
| +		lpj |= loopbit; |  | ||||||
| +		ticks = jiffies; |  | ||||||
| +		while (ticks == jiffies) |  | ||||||
| +			/* nothing */; |  | ||||||
| +		ticks = jiffies; |  | ||||||
| +		__delay(lpj); |  | ||||||
| +		if (jiffies != ticks)   /* longer than 1 tick */ |  | ||||||
| +			lpj &= ~loopbit; |  | ||||||
| +	} |  | ||||||
| +	printk(KERN_INFO "%d CPUs re-calibrate udelay(lpj = %d)\n", NR_CPUS, lpj); |  | ||||||
| + |  | ||||||
| +	for(i=0; i< NR_CPUS; i++) |  | ||||||
| +		cpu_data[i].udelay_val = lpj; |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| +device_initcall(udelay_recal); |  | ||||||
| + |  | ||||||
|  void prom_soc_init(struct ralink_soc_info *soc_info) |  | ||||||
|  { |  | ||||||
|  	void __iomem *sysc = (void __iomem *) KSEG1ADDR(MT7621_SYSC_BASE); |  | ||||||
| --- a/arch/mips/ralink/Kconfig |  | ||||||
| +++ b/arch/mips/ralink/Kconfig |  | ||||||
| @@ -58,6 +58,7 @@ choice |  | ||||||
|  		select CLKSRC_MIPS_GIC |  | ||||||
|  		select HAVE_PCI if PCI_MT7621 |  | ||||||
|  		select WEAK_REORDERING_BEYOND_LLSC |  | ||||||
| +		select GENERIC_CLOCKEVENTS_BROADCAST |  | ||||||
|  endchoice |  | ||||||
|   |  | ||||||
|  choice |  | ||||||
| @@ -1,224 +0,0 @@ | |||||||
| --- a/arch/mips/include/asm/mach-ralink/mt7621.h |  | ||||||
| +++ b/arch/mips/include/asm/mach-ralink/mt7621.h |  | ||||||
| @@ -17,6 +17,10 @@ |  | ||||||
|  #define SYSC_REG_CHIP_REV		0x0c |  | ||||||
|  #define SYSC_REG_SYSTEM_CONFIG0		0x10 |  | ||||||
|  #define SYSC_REG_SYSTEM_CONFIG1		0x14 |  | ||||||
| +#define SYSC_REG_CLKCFG0		0x2c |  | ||||||
| +#define SYSC_REG_CUR_CLK_STS		0x44 |  | ||||||
| + |  | ||||||
| +#define MEMC_REG_CPU_PLL		0x648 |  | ||||||
|   |  | ||||||
|  #define CHIP_REV_PKG_MASK		0x1 |  | ||||||
|  #define CHIP_REV_PKG_SHIFT		16 |  | ||||||
| @@ -24,6 +28,22 @@ |  | ||||||
|  #define CHIP_REV_VER_SHIFT		8 |  | ||||||
|  #define CHIP_REV_ECO_MASK		0xf |  | ||||||
|   |  | ||||||
| +#define XTAL_MODE_SEL_MASK		0x7 |  | ||||||
| +#define XTAL_MODE_SEL_SHIFT		6 |  | ||||||
| + |  | ||||||
| +#define CPU_CLK_SEL_MASK		0x3 |  | ||||||
| +#define CPU_CLK_SEL_SHIFT		30 |  | ||||||
| + |  | ||||||
| +#define CUR_CPU_FDIV_MASK		0x1f |  | ||||||
| +#define CUR_CPU_FDIV_SHIFT		8 |  | ||||||
| +#define CUR_CPU_FFRAC_MASK		0x1f |  | ||||||
| +#define CUR_CPU_FFRAC_SHIFT		0 |  | ||||||
| + |  | ||||||
| +#define CPU_PLL_PREDIV_MASK		0x3 |  | ||||||
| +#define CPU_PLL_PREDIV_SHIFT		12 |  | ||||||
| +#define CPU_PLL_FBDIV_MASK		0x7f |  | ||||||
| +#define CPU_PLL_FBDIV_SHIFT		4 |  | ||||||
| + |  | ||||||
|  #define MT7621_DRAM_BASE                0x0 |  | ||||||
|  #define MT7621_DDR2_SIZE_MIN		32 |  | ||||||
|  #define MT7621_DDR2_SIZE_MAX		256 |  | ||||||
| --- a/arch/mips/ralink/mt7621.c |  | ||||||
| +++ b/arch/mips/ralink/mt7621.c |  | ||||||
| @@ -8,6 +8,10 @@ |  | ||||||
|  #include <linux/kernel.h> |  | ||||||
|  #include <linux/init.h> |  | ||||||
|  #include <linux/jiffies.h> |  | ||||||
| +#include <linux/clk.h> |  | ||||||
| +#include <linux/clkdev.h> |  | ||||||
| +#include <linux/clk-provider.h> |  | ||||||
| +#include <dt-bindings/clock/mt7621-clk.h> |  | ||||||
|   |  | ||||||
|  #include <asm/mipsregs.h> |  | ||||||
|  #include <asm/smp-ops.h> |  | ||||||
| @@ -16,16 +20,12 @@ |  | ||||||
|  #include <asm/mach-ralink/mt7621.h> |  | ||||||
|  #include <asm/mips-boards/launch.h> |  | ||||||
|  #include <asm/delay.h> |  | ||||||
| +#include <asm/time.h> |  | ||||||
|   |  | ||||||
|  #include <pinmux.h> |  | ||||||
|   |  | ||||||
|  #include "common.h" |  | ||||||
|   |  | ||||||
| -#define SYSC_REG_SYSCFG		0x10 |  | ||||||
| -#define SYSC_REG_CPLL_CLKCFG0	0x2c |  | ||||||
| -#define SYSC_REG_CUR_CLK_STS	0x44 |  | ||||||
| -#define CPU_CLK_SEL		(BIT(30) | BIT(31)) |  | ||||||
| - |  | ||||||
|  #define MT7621_GPIO_MODE_UART1		1 |  | ||||||
|  #define MT7621_GPIO_MODE_I2C		2 |  | ||||||
|  #define MT7621_GPIO_MODE_UART3_MASK	0x3 |  | ||||||
| @@ -111,49 +111,89 @@ static struct rt2880_pmx_group mt7621_pi |  | ||||||
|  	{ 0 } |  | ||||||
|  }; |  | ||||||
|   |  | ||||||
| +static struct clk *clks[MT7621_CLK_MAX]; |  | ||||||
| +static struct clk_onecell_data clk_data = { |  | ||||||
| +	.clks = clks, |  | ||||||
| +	.clk_num = ARRAY_SIZE(clks), |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
|  phys_addr_t mips_cpc_default_phys_base(void) |  | ||||||
|  { |  | ||||||
|  	panic("Cannot detect cpc address"); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -void __init ralink_clk_init(void) |  | ||||||
| +static struct clk *__init mt7621_add_sys_clkdev( |  | ||||||
| +	const char *id, unsigned long rate) |  | ||||||
|  { |  | ||||||
| -	int cpu_fdiv = 0; |  | ||||||
| -	int cpu_ffrac = 0; |  | ||||||
| -	int fbdiv = 0; |  | ||||||
| -	u32 clk_sts, syscfg; |  | ||||||
| -	u8 clk_sel = 0, xtal_mode; |  | ||||||
| -	u32 cpu_clk; |  | ||||||
| +	struct clk *clk; |  | ||||||
| +	int err; |  | ||||||
| + |  | ||||||
| +	clk = clk_register_fixed_rate(NULL, id, NULL, 0, rate); |  | ||||||
| +	if (IS_ERR(clk)) |  | ||||||
| +		panic("failed to allocate %s clock structure", id); |  | ||||||
| + |  | ||||||
| +	err = clk_register_clkdev(clk, id, NULL); |  | ||||||
| +	if (err) |  | ||||||
| +		panic("unable to register %s clock device", id); |  | ||||||
|   |  | ||||||
| -	if ((rt_sysc_r32(SYSC_REG_CPLL_CLKCFG0) & CPU_CLK_SEL) != 0) |  | ||||||
| -		clk_sel = 1; |  | ||||||
| +	return clk; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +void __init ralink_clk_init(void) |  | ||||||
| +{ |  | ||||||
| +	u32 syscfg, xtal_sel, clkcfg, clk_sel, curclk, ffiv, ffrac; |  | ||||||
| +	u32 pll, prediv, fbdiv; |  | ||||||
| +	u32 xtal_clk, cpu_clk, bus_clk; |  | ||||||
| +	const static u32 prediv_tbl[] = {0, 1, 2, 2}; |  | ||||||
| + |  | ||||||
| +	syscfg = rt_sysc_r32(SYSC_REG_SYSTEM_CONFIG0); |  | ||||||
| +	xtal_sel = (syscfg >> XTAL_MODE_SEL_SHIFT) & XTAL_MODE_SEL_MASK; |  | ||||||
| + |  | ||||||
| +	clkcfg = rt_sysc_r32(SYSC_REG_CLKCFG0); |  | ||||||
| +	clk_sel = (clkcfg >> CPU_CLK_SEL_SHIFT) & CPU_CLK_SEL_MASK; |  | ||||||
| + |  | ||||||
| +	curclk = rt_sysc_r32(SYSC_REG_CUR_CLK_STS); |  | ||||||
| +	ffiv = (curclk >> CUR_CPU_FDIV_SHIFT) & CUR_CPU_FDIV_MASK; |  | ||||||
| +	ffrac = (curclk >> CUR_CPU_FFRAC_SHIFT) & CUR_CPU_FFRAC_MASK; |  | ||||||
| + |  | ||||||
| +	if (xtal_sel <= 2) |  | ||||||
| +		xtal_clk = 20 * 1000 * 1000; |  | ||||||
| +	else if (xtal_sel <= 5) |  | ||||||
| +		xtal_clk = 40 * 1000 * 1000; |  | ||||||
| +	else |  | ||||||
| +		xtal_clk = 25 * 1000 * 1000; |  | ||||||
|   |  | ||||||
|  	switch (clk_sel) { |  | ||||||
|  	case 0: |  | ||||||
| -		clk_sts = rt_sysc_r32(SYSC_REG_CUR_CLK_STS); |  | ||||||
| -		cpu_fdiv = ((clk_sts >> 8) & 0x1F); |  | ||||||
| -		cpu_ffrac = (clk_sts & 0x1F); |  | ||||||
| -		cpu_clk = (500 * cpu_ffrac / cpu_fdiv) * 1000 * 1000; |  | ||||||
| +		cpu_clk = 500 * 1000 * 1000; |  | ||||||
|  		break; |  | ||||||
| - |  | ||||||
|  	case 1: |  | ||||||
| -		fbdiv = ((rt_sysc_r32(0x648) >> 4) & 0x7F) + 1; |  | ||||||
| -		syscfg = rt_sysc_r32(SYSC_REG_SYSCFG); |  | ||||||
| -		xtal_mode = (syscfg >> 6) & 0x7; |  | ||||||
| -		if (xtal_mode >= 6) { |  | ||||||
| -			/* 25Mhz Xtal */ |  | ||||||
| -			cpu_clk = 25 * fbdiv * 1000 * 1000; |  | ||||||
| -		} else if (xtal_mode >= 3) { |  | ||||||
| -			/* 40Mhz Xtal */ |  | ||||||
| -			cpu_clk = 40 * fbdiv * 1000 * 1000; |  | ||||||
| -		} else { |  | ||||||
| -			/* 20Mhz Xtal */ |  | ||||||
| -			cpu_clk = 20 * fbdiv * 1000 * 1000; |  | ||||||
| -		} |  | ||||||
| +		pll = rt_memc_r32(MEMC_REG_CPU_PLL); |  | ||||||
| +		fbdiv = (pll >> CPU_PLL_FBDIV_SHIFT) & CPU_PLL_FBDIV_MASK; |  | ||||||
| +		prediv = (pll >> CPU_PLL_PREDIV_SHIFT) & CPU_PLL_PREDIV_MASK; |  | ||||||
| +		cpu_clk = ((fbdiv + 1) * xtal_clk) >> prediv_tbl[prediv]; |  | ||||||
|  		break; |  | ||||||
| +	default: |  | ||||||
| +		cpu_clk = xtal_clk; |  | ||||||
|  	} |  | ||||||
| + |  | ||||||
| +	cpu_clk = cpu_clk / ffiv * ffrac; |  | ||||||
| +	bus_clk = cpu_clk / 4; |  | ||||||
| + |  | ||||||
| +	clks[MT7621_CLK_CPU] = mt7621_add_sys_clkdev("cpu", cpu_clk); |  | ||||||
| +	clks[MT7621_CLK_BUS] = mt7621_add_sys_clkdev("bus", bus_clk); |  | ||||||
| + |  | ||||||
| +	pr_info("CPU Clock: %dMHz\n", cpu_clk / 1000000); |  | ||||||
| +	mips_hpt_frequency = cpu_clk / 2; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static void __init mt7621_clocks_init_dt(struct device_node *np) |  | ||||||
| +{ |  | ||||||
| +	of_clk_add_provider(np, of_clk_src_onecell_get, &clk_data); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +CLK_OF_DECLARE(ar7100, "mediatek,mt7621-pll", mt7621_clocks_init_dt); |  | ||||||
| + |  | ||||||
|  void __init ralink_of_remap(void) |  | ||||||
|  { |  | ||||||
|  	rt_sysc_membase = plat_of_remap_node("mtk,mt7621-sysc"); |  | ||||||
| --- a/arch/mips/ralink/timer-gic.c |  | ||||||
| +++ b/arch/mips/ralink/timer-gic.c |  | ||||||
| @@ -9,14 +9,14 @@ |  | ||||||
|   |  | ||||||
|  #include <linux/of.h> |  | ||||||
|  #include <linux/clk-provider.h> |  | ||||||
| -#include <linux/clocksource.h> |  | ||||||
| +#include <asm/time.h> |  | ||||||
|   |  | ||||||
|  #include "common.h" |  | ||||||
|   |  | ||||||
|  void __init plat_time_init(void) |  | ||||||
|  { |  | ||||||
|  	ralink_of_remap(); |  | ||||||
| - |  | ||||||
| +	ralink_clk_init(); |  | ||||||
|  	of_clk_init(NULL); |  | ||||||
|  	timer_probe(); |  | ||||||
|  } |  | ||||||
| --- /dev/null |  | ||||||
| +++ b/include/dt-bindings/clock/mt7621-clk.h |  | ||||||
| @@ -0,0 +1,18 @@ |  | ||||||
| +/* |  | ||||||
| + * Copyright (C) 2018 Weijie Gao <hackpascal@gmail.com> |  | ||||||
| + * |  | ||||||
| + * 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 __DT_BINDINGS_MT7621_CLK_H |  | ||||||
| +#define __DT_BINDINGS_MT7621_CLK_H |  | ||||||
| + |  | ||||||
| +#define MT7621_CLK_CPU		0 |  | ||||||
| +#define MT7621_CLK_BUS		1 |  | ||||||
| + |  | ||||||
| +#define MT7621_CLK_MAX		2 |  | ||||||
| + |  | ||||||
| +#endif /* __DT_BINDINGS_MT7621_CLK_H */ |  | ||||||
| @@ -1,125 +0,0 @@ | |||||||
| From b5a52351a66f3c2a7a207548aa87d78ff2d336c0 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Date: Wed, 10 Jul 2019 00:24:48 +0800 |  | ||||||
| Subject: [PATCH] MIPS: ralink: mt7621: add memory detection support |  | ||||||
|  |  | ||||||
| mt7621 has the following memory map: |  | ||||||
| 0x0-0x1c000000: lower 448m memory |  | ||||||
| 0x1c000000-0x2000000: peripheral registers |  | ||||||
| 0x20000000-0x2400000: higher 64m memory |  | ||||||
|  |  | ||||||
| detect_memory_region in arch/mips/kernel/setup.c only add the first |  | ||||||
| memory region and isn't suitable for 512m memory detection because |  | ||||||
| it may accidentally read the memory area for peripheral registers. |  | ||||||
|  |  | ||||||
| This commit adds memory detection capability for mt7621: |  | ||||||
| 1. add the highmem area when 512m is detected. |  | ||||||
| 2. guard memcmp from accessing peripheral registers: |  | ||||||
|      This only happens when some weird user decided to change |  | ||||||
|      kernel load address to 256m or higher address. Since this |  | ||||||
|      is a quite unusual case, we just skip 512m testing and return |  | ||||||
|      256m as memory size. |  | ||||||
|  |  | ||||||
| Signed-off-by: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| --- |  | ||||||
|  arch/mips/include/asm/mach-ralink/mt7621.h |  7 ++--- |  | ||||||
|  arch/mips/ralink/mt7621.c                  | 30 +++++++++++++++++++--- |  | ||||||
|  2 files changed, 30 insertions(+), 7 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/include/asm/mach-ralink/mt7621.h |  | ||||||
| +++ b/arch/mips/include/asm/mach-ralink/mt7621.h |  | ||||||
| @@ -44,9 +44,10 @@ |  | ||||||
|  #define CPU_PLL_FBDIV_MASK		0x7f |  | ||||||
|  #define CPU_PLL_FBDIV_SHIFT		4 |  | ||||||
|   |  | ||||||
| -#define MT7621_DRAM_BASE                0x0 |  | ||||||
| -#define MT7621_DDR2_SIZE_MIN		32 |  | ||||||
| -#define MT7621_DDR2_SIZE_MAX		256 |  | ||||||
| +#define MT7621_LOWMEM_BASE		0x0 |  | ||||||
| +#define MT7621_LOWMEM_MAX_SIZE		0x1C000000 |  | ||||||
| +#define MT7621_HIGHMEM_BASE		0x20000000 |  | ||||||
| +#define MT7621_HIGHMEM_SIZE		0x4000000 |  | ||||||
|   |  | ||||||
|  #define MT7621_CHIP_NAME0		0x3637544D |  | ||||||
|  #define MT7621_CHIP_NAME1		0x20203132 |  | ||||||
| --- a/arch/mips/ralink/mt7621.c |  | ||||||
| +++ b/arch/mips/ralink/mt7621.c |  | ||||||
| @@ -13,6 +13,7 @@ |  | ||||||
|  #include <linux/clk-provider.h> |  | ||||||
|  #include <dt-bindings/clock/mt7621-clk.h> |  | ||||||
|   |  | ||||||
| +#include <asm/bootinfo.h> |  | ||||||
|  #include <asm/mipsregs.h> |  | ||||||
|  #include <asm/smp-ops.h> |  | ||||||
|  #include <asm/mips-cps.h> |  | ||||||
| @@ -55,6 +56,8 @@ |  | ||||||
|  #define MT7621_GPIO_MODE_SDHCI_SHIFT	18 |  | ||||||
|  #define MT7621_GPIO_MODE_SDHCI_GPIO	1 |  | ||||||
|   |  | ||||||
| +static void *detect_magic __initdata = detect_memory_region; |  | ||||||
| + |  | ||||||
|  static struct rt2880_pmx_func uart1_grp[] =  { FUNC("uart1", 0, 1, 2) }; |  | ||||||
|  static struct rt2880_pmx_func i2c_grp[] =  { FUNC("i2c", 0, 3, 2) }; |  | ||||||
|  static struct rt2880_pmx_func uart3_grp[] = { |  | ||||||
| @@ -139,6 +142,28 @@ static struct clk *__init mt7621_add_sys |  | ||||||
|  	return clk; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +void __init mt7621_memory_detect(void) |  | ||||||
| +{ |  | ||||||
| +	void *dm = &detect_magic; |  | ||||||
| +	phys_addr_t size; |  | ||||||
| + |  | ||||||
| +	for (size = 32 * SZ_1M; size < 256 * SZ_1M; size <<= 1) { |  | ||||||
| +		if (!__builtin_memcmp(dm, dm + size, sizeof(detect_magic))) |  | ||||||
| +			break; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	if ((size == 256 * SZ_1M) && |  | ||||||
| +	    (CPHYSADDR(dm + size) < MT7621_LOWMEM_MAX_SIZE) && |  | ||||||
| +	    __builtin_memcmp(dm, dm + size, sizeof(detect_magic))) { |  | ||||||
| +		add_memory_region(MT7621_LOWMEM_BASE, MT7621_LOWMEM_MAX_SIZE, |  | ||||||
| +				  BOOT_MEM_RAM); |  | ||||||
| +		add_memory_region(MT7621_HIGHMEM_BASE, MT7621_HIGHMEM_SIZE, |  | ||||||
| +				  BOOT_MEM_RAM); |  | ||||||
| +	} else { |  | ||||||
| +		add_memory_region(MT7621_LOWMEM_BASE, size, BOOT_MEM_RAM); |  | ||||||
| +	} |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  void __init ralink_clk_init(void) |  | ||||||
|  { |  | ||||||
|  	u32 syscfg, xtal_sel, clkcfg, clk_sel, curclk, ffiv, ffrac; |  | ||||||
| @@ -317,10 +342,7 @@ void prom_soc_init(struct ralink_soc_inf |  | ||||||
|  		(rev >> CHIP_REV_VER_SHIFT) & CHIP_REV_VER_MASK, |  | ||||||
|  		(rev & CHIP_REV_ECO_MASK)); |  | ||||||
|   |  | ||||||
| -	soc_info->mem_size_min = MT7621_DDR2_SIZE_MIN; |  | ||||||
| -	soc_info->mem_size_max = MT7621_DDR2_SIZE_MAX; |  | ||||||
| -	soc_info->mem_base = MT7621_DRAM_BASE; |  | ||||||
| - |  | ||||||
| +	soc_info->mem_detect = mt7621_memory_detect; |  | ||||||
|  	rt2880_pinmux_data = mt7621_pinmux_data; |  | ||||||
|   |  | ||||||
|   |  | ||||||
| --- a/arch/mips/ralink/common.h |  | ||||||
| +++ b/arch/mips/ralink/common.h |  | ||||||
| @@ -17,6 +17,7 @@ struct ralink_soc_info { |  | ||||||
|  	unsigned long mem_size; |  | ||||||
|  	unsigned long mem_size_min; |  | ||||||
|  	unsigned long mem_size_max; |  | ||||||
| +	void (*mem_detect)(void); |  | ||||||
|  }; |  | ||||||
|  extern struct ralink_soc_info soc_info; |  | ||||||
|   |  | ||||||
| --- a/arch/mips/ralink/of.c |  | ||||||
| +++ b/arch/mips/ralink/of.c |  | ||||||
| @@ -87,6 +87,8 @@ void __init plat_mem_setup(void) |  | ||||||
|  	of_scan_flat_dt(early_init_dt_find_memory, NULL); |  | ||||||
|  	if (memory_dtb) |  | ||||||
|  		of_scan_flat_dt(early_init_dt_scan_memory, NULL); |  | ||||||
| +	else if (soc_info.mem_detect) |  | ||||||
| +		soc_info.mem_detect(); |  | ||||||
|  	else if (soc_info.mem_size) |  | ||||||
|  		add_memory_region(soc_info.mem_base, soc_info.mem_size * SZ_1M, |  | ||||||
|  				  BOOT_MEM_RAM); |  | ||||||
| @@ -1,15 +0,0 @@ | |||||||
| --- a/arch/mips/ralink/irq-gic.c |  | ||||||
| +++ b/arch/mips/ralink/irq-gic.c |  | ||||||
| @@ -13,6 +13,12 @@ |  | ||||||
|   |  | ||||||
|  int get_c0_perfcount_int(void) |  | ||||||
|  { |  | ||||||
| +	/* |  | ||||||
| +	 * Performance counter events are routed through GIC. |  | ||||||
| +	 * Prevent them from firing on CPU IRQ7 as well |  | ||||||
| +	 */ |  | ||||||
| +	clear_c0_status(IE_SW0 << 7); |  | ||||||
| + |  | ||||||
|  	return gic_get_c0_perfcount_int(); |  | ||||||
|  } |  | ||||||
|  EXPORT_SYMBOL_GPL(get_c0_perfcount_int); |  | ||||||
| @@ -1,85 +0,0 @@ | |||||||
| From 5d7b644aad721ecca20bd8976b38fb243fdc84f9 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Date: Sun, 15 Mar 2020 20:13:37 +0800 |  | ||||||
| Subject: [PATCH] gpio: mmio: introduce BGPIOF_NO_SET_ON_INPUT |  | ||||||
| MIME-Version: 1.0 |  | ||||||
| Content-Type: text/plain; charset=UTF-8 |  | ||||||
| Content-Transfer-Encoding: 8bit |  | ||||||
|  |  | ||||||
| Some gpio controllers ignores pin value writing when that pin is |  | ||||||
| configured as input mode. As a result, bgpio_dir_out should set |  | ||||||
| pin to output before configuring pin values or gpio pin values |  | ||||||
| can't be set up properly. |  | ||||||
| Introduce two variants of bgpio_dir_out: bgpio_dir_out_val_first |  | ||||||
| and bgpio_dir_out_dir_first, and assign direction_output according |  | ||||||
| to a new flag: BGPIOF_NO_SET_ON_INPUT. |  | ||||||
|  |  | ||||||
| Signed-off-by: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Tested-by: René van Dorst <opensource@vdorst.com> |  | ||||||
| Reviewed-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Signed-off-by: Bartosz Golaszewski <bgolaszewski@baylibre.com> |  | ||||||
| --- |  | ||||||
|  drivers/gpio/gpio-mmio.c    | 23 +++++++++++++++++++---- |  | ||||||
|  include/linux/gpio/driver.h |  1 + |  | ||||||
|  2 files changed, 20 insertions(+), 4 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/gpio/gpio-mmio.c |  | ||||||
| +++ b/drivers/gpio/gpio-mmio.c |  | ||||||
| @@ -381,12 +381,10 @@ static int bgpio_get_dir(struct gpio_chi |  | ||||||
|  	return 1; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| -static int bgpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val) |  | ||||||
| +static void bgpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val) |  | ||||||
|  { |  | ||||||
|  	unsigned long flags; |  | ||||||
|   |  | ||||||
| -	gc->set(gc, gpio, val); |  | ||||||
| - |  | ||||||
|  	spin_lock_irqsave(&gc->bgpio_lock, flags); |  | ||||||
|   |  | ||||||
|  	gc->bgpio_dir |= bgpio_line2mask(gc, gpio); |  | ||||||
| @@ -397,7 +395,21 @@ static int bgpio_dir_out(struct gpio_chi |  | ||||||
|  		gc->write_reg(gc->reg_dir_out, gc->bgpio_dir); |  | ||||||
|   |  | ||||||
|  	spin_unlock_irqrestore(&gc->bgpio_lock, flags); |  | ||||||
| +} |  | ||||||
|   |  | ||||||
| +static int bgpio_dir_out_dir_first(struct gpio_chip *gc, unsigned int gpio, |  | ||||||
| +				   int val) |  | ||||||
| +{ |  | ||||||
| +	bgpio_dir_out(gc, gpio, val); |  | ||||||
| +	gc->set(gc, gpio, val); |  | ||||||
| +	return 0; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int bgpio_dir_out_val_first(struct gpio_chip *gc, unsigned int gpio, |  | ||||||
| +				   int val) |  | ||||||
| +{ |  | ||||||
| +	gc->set(gc, gpio, val); |  | ||||||
| +	bgpio_dir_out(gc, gpio, val); |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -530,7 +542,10 @@ static int bgpio_setup_direction(struct |  | ||||||
|  	if (dirout || dirin) { |  | ||||||
|  		gc->reg_dir_out = dirout; |  | ||||||
|  		gc->reg_dir_in = dirin; |  | ||||||
| -		gc->direction_output = bgpio_dir_out; |  | ||||||
| +		if (flags & BGPIOF_NO_SET_ON_INPUT) |  | ||||||
| +			gc->direction_output = bgpio_dir_out_dir_first; |  | ||||||
| +		else |  | ||||||
| +			gc->direction_output = bgpio_dir_out_val_first; |  | ||||||
|  		gc->direction_input = bgpio_dir_in; |  | ||||||
|  		gc->get_direction = bgpio_get_dir; |  | ||||||
|  	} else { |  | ||||||
| --- a/include/linux/gpio/driver.h |  | ||||||
| +++ b/include/linux/gpio/driver.h |  | ||||||
| @@ -567,6 +567,7 @@ int bgpio_init(struct gpio_chip *gc, str |  | ||||||
|  #define BGPIOF_BIG_ENDIAN_BYTE_ORDER	BIT(3) |  | ||||||
|  #define BGPIOF_READ_OUTPUT_REG_SET	BIT(4) /* reg_set stores output value */ |  | ||||||
|  #define BGPIOF_NO_OUTPUT		BIT(5) /* only input */ |  | ||||||
| +#define BGPIOF_NO_SET_ON_INPUT		BIT(6) |  | ||||||
|   |  | ||||||
|  int gpiochip_irq_map(struct irq_domain *d, unsigned int irq, |  | ||||||
|  		     irq_hw_number_t hwirq); |  | ||||||
| @@ -1,33 +0,0 @@ | |||||||
| From ad65f02fd73e9a700f1693a4513ae923ca07beb0 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Date: Sun, 15 Mar 2020 20:13:38 +0800 |  | ||||||
| Subject: [PATCH] gpio: mt7621: add BGPIOF_NO_SET_ON_INPUT flag |  | ||||||
| MIME-Version: 1.0 |  | ||||||
| Content-Type: text/plain; charset=UTF-8 |  | ||||||
| Content-Transfer-Encoding: 8bit |  | ||||||
|  |  | ||||||
| DSET/DCLR registers only works on output pins. Add corresponding |  | ||||||
| BGPIOF_NO_SET_ON_INPUT flag to bgpio_init call to fix direction_out |  | ||||||
| behavior. |  | ||||||
|  |  | ||||||
| Signed-off-by: Chuanhong Guo <gch981213@gmail.com> |  | ||||||
| Tested-by: René van Dorst <opensource@vdorst.com> |  | ||||||
| Reviewed-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Signed-off-by: Bartosz Golaszewski <bgolaszewski@baylibre.com> |  | ||||||
| --- |  | ||||||
|  drivers/gpio/gpio-mt7621.c | 4 ++-- |  | ||||||
|  1 file changed, 2 insertions(+), 2 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/gpio/gpio-mt7621.c |  | ||||||
| +++ b/drivers/gpio/gpio-mt7621.c |  | ||||||
| @@ -227,8 +227,8 @@ mediatek_gpio_bank_probe(struct device * |  | ||||||
|  	ctrl = mtk->base + GPIO_REG_DCLR + (rg->bank * GPIO_BANK_STRIDE); |  | ||||||
|  	diro = mtk->base + GPIO_REG_CTRL + (rg->bank * GPIO_BANK_STRIDE); |  | ||||||
|   |  | ||||||
| -	ret = bgpio_init(&rg->chip, dev, 4, |  | ||||||
| -			 dat, set, ctrl, diro, NULL, 0); |  | ||||||
| +	ret = bgpio_init(&rg->chip, dev, 4, dat, set, ctrl, diro, NULL, |  | ||||||
| +			 BGPIOF_NO_SET_ON_INPUT); |  | ||||||
|  	if (ret) { |  | ||||||
|  		dev_err(dev, "bgpio_init() failed\n"); |  | ||||||
|  		return ret; |  | ||||||
| @@ -1,20 +0,0 @@ | |||||||
| --- a/drivers/net/ethernet/Kconfig |  | ||||||
| +++ b/drivers/net/ethernet/Kconfig |  | ||||||
| @@ -160,6 +160,7 @@ source "drivers/net/ethernet/pasemi/Kcon |  | ||||||
|  source "drivers/net/ethernet/pensando/Kconfig" |  | ||||||
|  source "drivers/net/ethernet/qlogic/Kconfig" |  | ||||||
|  source "drivers/net/ethernet/qualcomm/Kconfig" |  | ||||||
| +source "drivers/net/ethernet/ralink/Kconfig" |  | ||||||
|  source "drivers/net/ethernet/rdc/Kconfig" |  | ||||||
|  source "drivers/net/ethernet/realtek/Kconfig" |  | ||||||
|  source "drivers/net/ethernet/renesas/Kconfig" |  | ||||||
| --- a/drivers/net/ethernet/Makefile |  | ||||||
| +++ b/drivers/net/ethernet/Makefile |  | ||||||
| @@ -72,6 +72,7 @@ obj-$(CONFIG_NET_VENDOR_PACKET_ENGINES) |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_PASEMI) += pasemi/ |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_QLOGIC) += qlogic/ |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_QUALCOMM) += qualcomm/ |  | ||||||
| +obj-$(CONFIG_NET_VENDOR_RALINK) += ralink/ |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_REALTEK) += realtek/ |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_RENESAS) += renesas/ |  | ||||||
|  obj-$(CONFIG_NET_VENDOR_RDC) += rdc/ |  | ||||||
| @@ -1,19 +0,0 @@ | |||||||
| --- a/arch/mips/include/asm/mach-ralink/mt7620.h |  | ||||||
| +++ b/arch/mips/include/asm/mach-ralink/mt7620.h |  | ||||||
| @@ -135,4 +135,16 @@ static inline int mt7620_get_eco(void) |  | ||||||
|  	return rt_sysc_r32(SYSC_REG_CHIP_REV) & CHIP_REV_ECO_MASK; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static inline int mt7620_get_chipver(void) |  | ||||||
| +{ |  | ||||||
| +	return (rt_sysc_r32(SYSC_REG_CHIP_REV) >> CHIP_REV_VER_SHIFT) & |  | ||||||
| +		CHIP_REV_VER_MASK; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static inline int mt7620_get_pkg(void) |  | ||||||
| +{ |  | ||||||
| +	return (rt_sysc_r32(SYSC_REG_CHIP_REV) >> CHIP_REV_PKG_SHIFT) & |  | ||||||
| +		CHIP_REV_PKG_MASK; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  #endif |  | ||||||
| @@ -1,89 +0,0 @@ | |||||||
| From f798b7588bd7397bbab958281ca6c88d08714941 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Date: Thu, 12 Mar 2020 12:29:15 +0100 |  | ||||||
| Subject: [PATCH] MIPS: ralink: mt7621: introduce 'soc_device' initialization |  | ||||||
|  |  | ||||||
| mt7621 SoC has its own 'ralink_soc_info' structure with some |  | ||||||
| information about the soc itself. Pcie controller and pcie phy |  | ||||||
| drivers for this soc which are still in staging git tree make uses |  | ||||||
| of 'soc_device_attribute' looking for revision 'E2' in order to |  | ||||||
| know if reset lines are or not inverted. This way of doing things |  | ||||||
| seems to be necessary in order to make things clean and properly. |  | ||||||
| Hence, introduce this 'soc_device' to be able to properly use those |  | ||||||
| attributes in drivers. Also set 'data' pointer points to the struct |  | ||||||
| 'ralink_soc_info' to be able to export also current soc information |  | ||||||
| using this mechanism. |  | ||||||
|  |  | ||||||
| Cc: Paul Burton <paul.burton@mips.com> |  | ||||||
| Cc: ralf@linux-mips.org |  | ||||||
| Cc: jhogan@kernel.org |  | ||||||
| Cc: john@phrozen.org |  | ||||||
| Cc: NeilBrown <neil@brown.name> |  | ||||||
| Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |  | ||||||
| Cc: linux-mips@vger.kernel.org |  | ||||||
|  |  | ||||||
| Signed-off-by: Sergio Paracuellos <sergio.paracuellos@gmail.com> |  | ||||||
| Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de> |  | ||||||
| --- |  | ||||||
|  arch/mips/ralink/mt7621.c | 32 +++++++++++++++++++++++++++++++- |  | ||||||
|  1 file changed, 31 insertions(+), 1 deletion(-) |  | ||||||
|  |  | ||||||
| --- a/arch/mips/ralink/mt7621.c |  | ||||||
| +++ b/arch/mips/ralink/mt7621.c |  | ||||||
| @@ -7,6 +7,8 @@ |  | ||||||
|   |  | ||||||
|  #include <linux/kernel.h> |  | ||||||
|  #include <linux/init.h> |  | ||||||
| +#include <linux/slab.h> |  | ||||||
| +#include <linux/sys_soc.h> |  | ||||||
|  #include <linux/jiffies.h> |  | ||||||
|  #include <linux/clk.h> |  | ||||||
|  #include <linux/clkdev.h> |  | ||||||
| @@ -294,6 +296,33 @@ static int udelay_recal(void) |  | ||||||
|  } |  | ||||||
|  device_initcall(udelay_recal); |  | ||||||
|   |  | ||||||
| +static void soc_dev_init(struct ralink_soc_info *soc_info, u32 rev) |  | ||||||
| +{ |  | ||||||
| +	struct soc_device *soc_dev; |  | ||||||
| +	struct soc_device_attribute *soc_dev_attr; |  | ||||||
| + |  | ||||||
| +	soc_dev_attr = kzalloc(sizeof(*soc_dev_attr), GFP_KERNEL); |  | ||||||
| +	if (!soc_dev_attr) |  | ||||||
| +		return; |  | ||||||
| + |  | ||||||
| +	soc_dev_attr->soc_id = "mt7621"; |  | ||||||
| +	soc_dev_attr->family = "Ralink"; |  | ||||||
| + |  | ||||||
| +	if (((rev >> CHIP_REV_VER_SHIFT) & CHIP_REV_VER_MASK) == 1 && |  | ||||||
| +	    (rev & CHIP_REV_ECO_MASK) == 1) |  | ||||||
| +		soc_dev_attr->revision = "E2"; |  | ||||||
| +	else |  | ||||||
| +		soc_dev_attr->revision = "E1"; |  | ||||||
| + |  | ||||||
| +	soc_dev_attr->data = soc_info; |  | ||||||
| + |  | ||||||
| +	soc_dev = soc_device_register(soc_dev_attr); |  | ||||||
| +	if (IS_ERR(soc_dev)) { |  | ||||||
| +		kfree(soc_dev_attr); |  | ||||||
| +		return; |  | ||||||
| +	} |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  void prom_soc_init(struct ralink_soc_info *soc_info) |  | ||||||
|  { |  | ||||||
|  	void __iomem *sysc = (void __iomem *) KSEG1ADDR(MT7621_SYSC_BASE); |  | ||||||
| @@ -345,11 +374,12 @@ void prom_soc_init(struct ralink_soc_inf |  | ||||||
|  	soc_info->mem_detect = mt7621_memory_detect; |  | ||||||
|  	rt2880_pinmux_data = mt7621_pinmux_data; |  | ||||||
|   |  | ||||||
| - |  | ||||||
|  	if (!register_cps_smp_ops()) |  | ||||||
|  		return; |  | ||||||
|  	if (!register_cmp_smp_ops()) |  | ||||||
|  		return; |  | ||||||
|  	if (!register_vsmp_smp_ops()) |  | ||||||
|  		return; |  | ||||||
| + |  | ||||||
| +	soc_dev_init(soc_info, rev); |  | ||||||
|  } |  | ||||||
| @@ -1,14 +0,0 @@ | |||||||
| --- a/drivers/mtd/spi-nor/spi-nor.c |  | ||||||
| +++ b/drivers/mtd/spi-nor/spi-nor.c |  | ||||||
| @@ -2306,6 +2306,11 @@ static const struct flash_info spi_nor_i |  | ||||||
|  			SPI_NOR_4B_OPCODES | SPI_NOR_HAS_LOCK | SPI_NOR_HAS_TB) |  | ||||||
|  			.fixups = &gd25q256_fixups, |  | ||||||
|  	}, |  | ||||||
| +	{ |  | ||||||
| +		"gd25q512", INFO(0xc84020, 0, 64 * 1024, 1024, |  | ||||||
| +			SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ | |  | ||||||
| +			SPI_NOR_HAS_LOCK | SPI_NOR_HAS_TB | SPI_NOR_4B_OPCODES) |  | ||||||
| +	}, |  | ||||||
|   |  | ||||||
|  	/* Intel/Numonyx -- xxxs33b */ |  | ||||||
|  	{ "160s33b",  INFO(0x898911, 0, 64 * 1024,  32, 0) }, |  | ||||||
| @@ -1,34 +0,0 @@ | |||||||
| From bd0f89de5476ca25e73fae829ba3e1dafae1d90d Mon Sep 17 00:00:00 2001 |  | ||||||
| From: =?UTF-8?q?Ren=C3=A9=20van=20Dorst?= <opensource@vdorst.com> |  | ||||||
| Date: Fri, 21 Jun 2019 10:04:05 +0200 |  | ||||||
| Subject: [PATCH] net: ethernet: mediatek: support net-labels |  | ||||||
|  |  | ||||||
| With this patch, device name can be set within dts file in the same way as dsa |  | ||||||
| port can. |  | ||||||
| Add: label = "wan"; to GMAC node. |  | ||||||
|  |  | ||||||
| Signed-off-by: René van Dorst <opensource@vdorst.com> |  | ||||||
| --- |  | ||||||
|  drivers/net/ethernet/mediatek/mtk_eth_soc.c | 4 ++++ |  | ||||||
|  1 file changed, 4 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c |  | ||||||
| +++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c |  | ||||||
| @@ -2940,6 +2940,7 @@ static const struct net_device_ops mtk_n |  | ||||||
|   |  | ||||||
|  static int mtk_add_mac(struct mtk_eth *eth, struct device_node *np) |  | ||||||
|  { |  | ||||||
| +	const char *name = of_get_property(np, "label", NULL); |  | ||||||
|  	const __be32 *_id = of_get_property(np, "reg", NULL); |  | ||||||
|  	struct phylink *phylink; |  | ||||||
|  	int phy_mode, id, err; |  | ||||||
| @@ -3032,6 +3033,9 @@ static int mtk_add_mac(struct mtk_eth *e |  | ||||||
|   |  | ||||||
|  	eth->netdev[id]->max_mtu = MTK_MAX_RX_LENGTH - MTK_RX_ETH_HLEN; |  | ||||||
|   |  | ||||||
| +	if (name) |  | ||||||
| +		strlcpy(eth->netdev[id]->name, name, IFNAMSIZ); |  | ||||||
| + |  | ||||||
|  	return 0; |  | ||||||
|   |  | ||||||
|  free_netdev: |  | ||||||
| @@ -1,34 +0,0 @@ | |||||||
| From 52d14545d2fc276b1bf9ccf48d4612fab6edfb6a Mon Sep 17 00:00:00 2001 |  | ||||||
| From: David Bauer <mail@david-bauer.net> |  | ||||||
| Date: Thu, 6 May 2021 17:49:55 +0200 |  | ||||||
| Subject: [PATCH] mtd: spi-nor: Add support for BoHong bh25q128as |  | ||||||
|  |  | ||||||
| Add MTD support for the BoHong bh25q128as SPI NOR chip. |  | ||||||
| The chip has 16MB of total capacity, divided into a total of 256 |  | ||||||
| sectors, each 64KB sized. The chip also supports 4KB sectors. |  | ||||||
| Additionally, it supports dual and quad read modes. |  | ||||||
|  |  | ||||||
| Functionality was verified on an Tenbay WR1800K / MTK MT7621 board. |  | ||||||
|  |  | ||||||
| Signed-off-by: David Bauer <mail@david-bauer.net> |  | ||||||
| --- |  | ||||||
|  drivers/mtd/spi-nor/Makefile |  1 + |  | ||||||
|  drivers/mtd/spi-nor/bohong.c | 21 +++++++++++++++++++++ |  | ||||||
|  drivers/mtd/spi-nor/core.c   |  1 + |  | ||||||
|  drivers/mtd/spi-nor/core.h   |  1 + |  | ||||||
|  4 files changed, 24 insertions(+) |  | ||||||
|  create mode 100644 drivers/mtd/spi-nor/bohong.c |  | ||||||
|  |  | ||||||
| --- a/drivers/mtd/spi-nor/spi-nor.c |  | ||||||
| +++ b/drivers/mtd/spi-nor/spi-nor.c |  | ||||||
| @@ -2233,6 +2233,10 @@ static const struct flash_info spi_nor_i |  | ||||||
|   |  | ||||||
|  	{ "at45db081d", INFO(0x1f2500, 0, 64 * 1024, 16, SECT_4K) }, |  | ||||||
|   |  | ||||||
| +	/* BoHong Microelectronics */ |  | ||||||
| +	{ "bh25q128as", INFO(0x684018, 0, 64 * 1024, 256, |  | ||||||
| +			SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_READ) }, |  | ||||||
| + |  | ||||||
|  	/* EON -- en25xxx */ |  | ||||||
|  	{ "en25f32",    INFO(0x1c3116, 0, 64 * 1024,   64, SECT_4K) }, |  | ||||||
|  	{ "en25p32",    INFO(0x1c2016, 0, 64 * 1024,   64, 0) }, |  | ||||||
| @@ -1,11 +0,0 @@ | |||||||
| --- a/drivers/staging/mt7621-pinctrl/pinctrl-rt2880.c |  | ||||||
| +++ b/drivers/staging/mt7621-pinctrl/pinctrl-rt2880.c |  | ||||||
| @@ -354,7 +354,7 @@ static int rt2880_pinmux_probe(struct pl |  | ||||||
|  		if (!of_device_is_available(np)) |  | ||||||
|  			continue; |  | ||||||
|   |  | ||||||
| -		ngpio = of_get_property(np, "ralink,num-gpios", NULL); |  | ||||||
| +		ngpio = of_get_property(np, "ngpios", NULL); |  | ||||||
|  		gpiobase = of_get_property(np, "ralink,gpio-base", NULL); |  | ||||||
|  		if (!ngpio || !gpiobase) { |  | ||||||
|  			dev_err(&pdev->dev, "failed to load chip info\n"); |  | ||||||
| @@ -1,72 +0,0 @@ | |||||||
| From: AngeloGioacchino Del Regno |  | ||||||
|         <angelogioacchino.delregno@somainline.org> |  | ||||||
| To: linus.walleij@linaro.org |  | ||||||
| Cc: linux-kernel@vger.kernel.org, konrad.dybcio@somainline.org, |  | ||||||
|         marijn.suijten@somainline.org, martin.botka@somainline.org, |  | ||||||
|         phone-devel@vger.kernel.org, linux-gpio@vger.kernel.org, |  | ||||||
|         devicetree@vger.kernel.org, robh+dt@kernel.org, |  | ||||||
|         AngeloGioacchino Del Regno |  | ||||||
|         <angelogioacchino.delregno@somainline.org> |  | ||||||
| Subject: [PATCH v5 1/2] pinctrl: Add driver for Awinic AW9523/B I2C GPIO |  | ||||||
|  Expander |  | ||||||
| Date: Mon, 25 Jan 2021 19:22:18 +0100 |  | ||||||
|  |  | ||||||
| The Awinic AW9523(B) is a multi-function I2C gpio expander in a |  | ||||||
| TQFN-24L package, featuring PWM (max 37mA per pin, or total max |  | ||||||
| power 3.2Watts) for LED driving capability. |  | ||||||
|  |  | ||||||
| It has two ports with 8 pins per port (for a total of 16 pins), |  | ||||||
| configurable as either PWM with 1/256 stepping or GPIO input/output, |  | ||||||
| 1.8V logic input; each GPIO can be configured as input or output |  | ||||||
| independently from each other. |  | ||||||
|  |  | ||||||
| This IC also has an internal interrupt controller, which is capable |  | ||||||
| of generating an interrupt for each GPIO, depending on the |  | ||||||
| configuration, and will raise an interrupt on the INTN pin to |  | ||||||
| advertise this to an external interrupt controller. |  | ||||||
|  |  | ||||||
| Signed-off-by: AngeloGioacchino Del Regno <angelogioacchino.delregno@somainline.org> |  | ||||||
| --- |  | ||||||
|  drivers/pinctrl/Kconfig          |   17 + |  | ||||||
|  drivers/pinctrl/Makefile         |    1 + |  | ||||||
|  drivers/pinctrl/pinctrl-aw9523.c | 1122 ++++++++++++++++++++++++++++++ |  | ||||||
|  3 files changed, 1140 insertions(+) |  | ||||||
|  create mode 100644 drivers/pinctrl/pinctrl-aw9523.c |  | ||||||
|  |  | ||||||
| --- a/drivers/pinctrl/Kconfig |  | ||||||
| +++ b/drivers/pinctrl/Kconfig |  | ||||||
| @@ -109,6 +109,24 @@ config PINCTRL_AMD |  | ||||||
|  	  Requires ACPI/FDT device enumeration code to set up a platform |  | ||||||
|  	  device. |  | ||||||
|   |  | ||||||
| +config PINCTRL_AW9523 |  | ||||||
| +	bool "Awinic AW9523/AW9523B I2C GPIO expander pinctrl driver" |  | ||||||
| +	depends on OF && I2C |  | ||||||
| +	select PINMUX |  | ||||||
| +	select PINCONF |  | ||||||
| +	select GENERIC_PINCONF |  | ||||||
| +	select GPIOLIB |  | ||||||
| +	select GPIOLIB_IRQCHIP |  | ||||||
| +	select REGMAP |  | ||||||
| +	select REGMAP_I2C |  | ||||||
| +	help |  | ||||||
| +	  The Awinic AW9523/AW9523B is a multi-function I2C GPIO |  | ||||||
| +	  expander with PWM functionality. This driver bundles a |  | ||||||
| +	  pinctrl driver to select the function muxing and a GPIO |  | ||||||
| +	  driver to handle GPIO, when the GPIO function is selected. |  | ||||||
| + |  | ||||||
| +	  Say yes to enable pinctrl and GPIO support for the AW9523(B). |  | ||||||
| + |  | ||||||
|  config PINCTRL_BM1880 |  | ||||||
|  	bool "Bitmain BM1880 Pinctrl driver" |  | ||||||
|  	depends on OF && (ARCH_BITMAIN || COMPILE_TEST) |  | ||||||
| --- a/drivers/pinctrl/Makefile |  | ||||||
| +++ b/drivers/pinctrl/Makefile |  | ||||||
| @@ -14,6 +14,7 @@ obj-$(CONFIG_PINCTRL_AXP209)	+= pinctrl- |  | ||||||
|  obj-$(CONFIG_PINCTRL_AT91)	+= pinctrl-at91.o |  | ||||||
|  obj-$(CONFIG_PINCTRL_AT91PIO4)	+= pinctrl-at91-pio4.o |  | ||||||
|  obj-$(CONFIG_PINCTRL_AMD)	+= pinctrl-amd.o |  | ||||||
| +obj-$(CONFIG_PINCTRL_AW9523)	+= pinctrl-aw9523.o |  | ||||||
|  obj-$(CONFIG_PINCTRL_BM1880)	+= pinctrl-bm1880.o |  | ||||||
|  obj-$(CONFIG_PINCTRL_DA850_PUPD) += pinctrl-da850-pupd.o |  | ||||||
|  obj-$(CONFIG_PINCTRL_DIGICOLOR)	+= pinctrl-digicolor.o |  | ||||||
| @@ -1,47 +0,0 @@ | |||||||
| From 0b6eb1e68290243d439ee330ea8d0b239a5aec69 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: John Crispin <blogic@openwrt.org> |  | ||||||
| Date: Sun, 27 Jul 2014 09:38:50 +0100 |  | ||||||
| Subject: [PATCH 34/53] NET: multi phy support |  | ||||||
|  |  | ||||||
| Signed-off-by: John Crispin <blogic@openwrt.org> |  | ||||||
| --- |  | ||||||
|  drivers/net/phy/phy.c |    9 ++++++--- |  | ||||||
|  include/linux/phy.h   |    1 + |  | ||||||
|  2 files changed, 7 insertions(+), 3 deletions(-) |  | ||||||
|  |  | ||||||
| --- a/drivers/net/phy/phy.c |  | ||||||
| +++ b/drivers/net/phy/phy.c |  | ||||||
| @@ -549,7 +549,10 @@ static int phy_check_link_status(struct |  | ||||||
|  		phy_link_up(phydev); |  | ||||||
|  	} else if (!phydev->link && phydev->state != PHY_NOLINK) { |  | ||||||
|  		phydev->state = PHY_NOLINK; |  | ||||||
| -		phy_link_down(phydev, true); |  | ||||||
| +		if (!phydev->no_auto_carrier_off) |  | ||||||
| +			phy_link_down(phydev, true); |  | ||||||
| +		else |  | ||||||
| +			phy_link_down(phydev, false); |  | ||||||
|  	} |  | ||||||
|   |  | ||||||
|  	return 0; |  | ||||||
| @@ -947,7 +950,10 @@ void phy_state_machine(struct work_struc |  | ||||||
|  	case PHY_HALTED: |  | ||||||
|  		if (phydev->link) { |  | ||||||
|  			phydev->link = 0; |  | ||||||
| -			phy_link_down(phydev, true); |  | ||||||
| +			if (!phydev->no_auto_carrier_off) |  | ||||||
| +				phy_link_down(phydev, true); |  | ||||||
| +			else |  | ||||||
| +				phy_link_down(phydev, false); |  | ||||||
|  		} |  | ||||||
|  		do_suspend = true; |  | ||||||
|  		break; |  | ||||||
| --- a/include/linux/phy.h |  | ||||||
| +++ b/include/linux/phy.h |  | ||||||
| @@ -381,6 +381,7 @@ struct phy_device { |  | ||||||
|  	unsigned suspended_by_mdio_bus:1; |  | ||||||
|  	unsigned sysfs_links:1; |  | ||||||
|  	unsigned loopback_enabled:1; |  | ||||||
| +	unsigned no_auto_carrier_off:1; |  | ||||||
|   |  | ||||||
|  	unsigned autoneg:1; |  | ||||||
|  	/* The most recently read link state */ |  | ||||||
| @@ -1,188 +0,0 @@ | |||||||
| From 924453aa9d2324e5611f8e2b71df746d8f0c79f1 Mon Sep 17 00:00:00 2001 |  | ||||||
| From: =?UTF-8?q?Ren=C3=A9=20van=20Dorst?= <opensource@vdorst.com> |  | ||||||
| Date: Fri, 13 Nov 2020 16:11:32 +0100 |  | ||||||
| Subject: [PATCH] net: phy: at803x: add support for SFP module in |  | ||||||
|  RGMII-to-x-base mode |  | ||||||
| MIME-Version: 1.0 |  | ||||||
| Content-Type: text/plain; charset=UTF-8 |  | ||||||
| Content-Transfer-Encoding: 8bit |  | ||||||
|  |  | ||||||
| Signed-off-by: René van Dorst <opensource@vdorst.com> |  | ||||||
| --- |  | ||||||
|  drivers/net/phy/at803x.c | 91 ++++++++++++++++++++++++++++++++++++++++ |  | ||||||
|  1 file changed, 91 insertions(+) |  | ||||||
|  |  | ||||||
| --- a/drivers/net/phy/at803x.c |  | ||||||
| +++ b/drivers/net/phy/at803x.c |  | ||||||
| @@ -14,6 +14,8 @@ |  | ||||||
|  #include <linux/etherdevice.h> |  | ||||||
|  #include <linux/of_gpio.h> |  | ||||||
|  #include <linux/gpio/consumer.h> |  | ||||||
| +#include <linux/sfp.h> |  | ||||||
| +#include <linux/phylink.h> |  | ||||||
|   |  | ||||||
|  #define AT803X_SPECIFIC_STATUS			0x11 |  | ||||||
|  #define AT803X_SS_SPEED_MASK			(3 << 14) |  | ||||||
| @@ -52,9 +54,18 @@ |  | ||||||
|   |  | ||||||
|  #define AT803X_MODE_CFG_MASK			0x0F |  | ||||||
|  #define AT803X_MODE_CFG_SGMII			0x01 |  | ||||||
| +#define AT803X_MODE_CFG_BX1000_RGMII_50		0x02 |  | ||||||
| +#define AT803X_MODE_CFG_BX1000_RGMII_75		0x03 |  | ||||||
| +#define AT803X_MODE_FIBER			0x01 |  | ||||||
| +#define AT803X_MODE_COPPER			0x00 |  | ||||||
|   |  | ||||||
|  #define AT803X_PSSR			0x11	/*PHY-Specific Status Register*/ |  | ||||||
|  #define AT803X_PSSR_MR_AN_COMPLETE	0x0200 |  | ||||||
| +#define	 PSSR_LINK			BIT(10) |  | ||||||
| +#define	 PSSR_SYNC_STATUS		BIT(8) |  | ||||||
| +#define	 PSSR_DUPLEX			BIT(13) |  | ||||||
| +#define	 PSSR_SPEED_1000		BIT(15) |  | ||||||
| +#define	 PSSR_SPEED_100			BIT(14) |  | ||||||
|   |  | ||||||
|  #define AT803X_DEBUG_REG_0			0x00 |  | ||||||
|  #define AT803X_DEBUG_RX_CLK_DLY_EN		BIT(15) |  | ||||||
| @@ -274,18 +285,80 @@ static int at803x_resume(struct phy_devi |  | ||||||
|  	return phy_modify(phydev, MII_BMCR, BMCR_PDOWN | BMCR_ISOLATE, 0); |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static int at803x_mode(struct phy_device *phydev) |  | ||||||
| +{ |  | ||||||
| +	int mode; |  | ||||||
| + |  | ||||||
| +	mode = phy_read(phydev, AT803X_REG_CHIP_CONFIG) & AT803X_MODE_CFG_MASK; |  | ||||||
| + |  | ||||||
| +	if (mode == AT803X_MODE_CFG_BX1000_RGMII_50 || |  | ||||||
| +	    mode == AT803X_MODE_CFG_BX1000_RGMII_75) |  | ||||||
| +		return AT803X_MODE_FIBER; |  | ||||||
| +	return AT803X_MODE_COPPER; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static int at803x_sfp_insert(void *upstream, const struct sfp_eeprom_id *id) |  | ||||||
| +{ |  | ||||||
| +	__ETHTOOL_DECLARE_LINK_MODE_MASK(at803x_support) = { 0, }; |  | ||||||
| +	__ETHTOOL_DECLARE_LINK_MODE_MASK(support) = { 0, }; |  | ||||||
| +	struct phy_device *phydev = upstream; |  | ||||||
| +	phy_interface_t iface; |  | ||||||
| + |  | ||||||
| +	phylink_set(at803x_support, 1000baseX_Full); |  | ||||||
| +	/* AT803x only support 1000baseX but SGMII works fine when module runs |  | ||||||
| +	 * at 1Gbit. |  | ||||||
| +	 */ |  | ||||||
| +	phylink_set(at803x_support, 1000baseT_Full); |  | ||||||
| + |  | ||||||
| +	sfp_parse_support(phydev->sfp_bus, id, support); |  | ||||||
| + |  | ||||||
| +	// Limit to interfaces that both sides support |  | ||||||
| +	linkmode_and(support, support, at803x_support); |  | ||||||
| + |  | ||||||
| +	if (linkmode_empty(support)) |  | ||||||
| +		goto unsupported_mode; |  | ||||||
| + |  | ||||||
| +	iface = sfp_select_interface(phydev->sfp_bus, support); |  | ||||||
| + |  | ||||||
| +	if (iface != PHY_INTERFACE_MODE_SGMII && |  | ||||||
| +	    iface != PHY_INTERFACE_MODE_1000BASEX) |  | ||||||
| +		goto unsupported_mode; |  | ||||||
| + |  | ||||||
| +	dev_info(&phydev->mdio.dev, "SFP interface %s", phy_modes(iface)); |  | ||||||
| + |  | ||||||
| +	return 0; |  | ||||||
| + |  | ||||||
| +unsupported_mode: |  | ||||||
| +	dev_info(&phydev->mdio.dev, "incompatible SFP module inserted;" |  | ||||||
| +		 "Only SGMII at 1Gbit/1000BASEX are supported!\n"); |  | ||||||
| +	return -EINVAL; |  | ||||||
| +} |  | ||||||
| + |  | ||||||
| +static const struct sfp_upstream_ops at803x_sfp_ops = { |  | ||||||
| +	.attach = phy_sfp_attach, |  | ||||||
| +	.detach = phy_sfp_detach, |  | ||||||
| +	.module_insert = at803x_sfp_insert, |  | ||||||
| +}; |  | ||||||
| + |  | ||||||
|  static int at803x_probe(struct phy_device *phydev) |  | ||||||
|  { |  | ||||||
|  	struct device *dev = &phydev->mdio.dev; |  | ||||||
|  	struct at803x_priv *priv; |  | ||||||
|  	int ret = 0; |  | ||||||
|   |  | ||||||
| +	if (at803x_mode(phydev) == AT803X_MODE_FIBER) { |  | ||||||
| +		ret = phy_sfp_probe(phydev, &at803x_sfp_ops); |  | ||||||
| +		if (ret < 0) |  | ||||||
| +			return ret; |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
|  	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); |  | ||||||
|  	if (!priv) |  | ||||||
|  		return -ENOMEM; |  | ||||||
|   |  | ||||||
|  	phydev->priv = priv; |  | ||||||
|   |  | ||||||
| +#if 0 |  | ||||||
|  	/* Some bootloaders leave the fiber page selected. |  | ||||||
|  	 * Switch to the copper page, as otherwise we read |  | ||||||
|  	 * the PHY capabilities from the fiber side. |  | ||||||
| @@ -295,6 +368,7 @@ static int at803x_probe(struct phy_devic |  | ||||||
|  		ret = at803x_write_page(phydev, AT803X_PAGE_COPPER); |  | ||||||
|  		mutex_unlock(&phydev->mdio.bus->mdio_lock); |  | ||||||
|  	} |  | ||||||
| +#endif |  | ||||||
|   |  | ||||||
|  	return ret; |  | ||||||
|  } |  | ||||||
| @@ -419,6 +493,7 @@ static int at803x_get_features(struct ph |  | ||||||
|  	if (err) |  | ||||||
|  		return err; |  | ||||||
|   |  | ||||||
| +#if 0 |  | ||||||
|  	if (!(phydev->phy_id & phydev->drv->phy_id_mask) == (ATH8031_PHY_ID & phydev->drv->phy_id_mask)) |  | ||||||
|  		return 0; |  | ||||||
|   |  | ||||||
| @@ -436,6 +511,7 @@ static int at803x_get_features(struct ph |  | ||||||
|  	 */ |  | ||||||
|  	linkmode_clear_bit(ETHTOOL_LINK_MODE_1000baseX_Full_BIT, |  | ||||||
|  			   phydev->supported); |  | ||||||
| +#endif |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| @@ -443,6 +519,10 @@ static int at803x_read_status(struct phy |  | ||||||
|  { |  | ||||||
|  	int ss, err, old_link = phydev->link; |  | ||||||
|   |  | ||||||
| +	/* Handle (Fiber) SGMII to RGMII mode */ |  | ||||||
| +	if (at803x_mode(phydev) == AT803X_MODE_FIBER) |  | ||||||
| +		return genphy_c37_read_status(phydev); |  | ||||||
| + |  | ||||||
|  	/* Update the link, but return if there was an error */ |  | ||||||
|  	err = genphy_update_link(phydev); |  | ||||||
|  	if (err) |  | ||||||
| @@ -497,6 +577,19 @@ static int at803x_read_status(struct phy |  | ||||||
|  	return 0; |  | ||||||
|  } |  | ||||||
|   |  | ||||||
| +static int at803x_config_aneg(struct phy_device *phydev) |  | ||||||
| +{ |  | ||||||
| +	/* Handle (Fiber) SerDes to RGMII mode */ |  | ||||||
| +	if (at803x_mode(phydev) == AT803X_MODE_FIBER) { |  | ||||||
| +		pr_warn("%s: fiber\n", __func__); |  | ||||||
| +		return genphy_c37_config_aneg(phydev); |  | ||||||
| +	} |  | ||||||
| + |  | ||||||
| +	pr_warn("%s: enter\n", __func__); |  | ||||||
| + |  | ||||||
| +	return genphy_config_aneg(phydev); |  | ||||||
| +} |  | ||||||
| + |  | ||||||
|  static struct phy_driver at803x_driver[] = { |  | ||||||
|  { |  | ||||||
|  	/* ATHEROS 8035 */ |  | ||||||
| @@ -532,6 +625,7 @@ static struct phy_driver at803x_driver[] |  | ||||||
|  	/* ATHEROS 8031 */ |  | ||||||
|  	.phy_id			= ATH8031_PHY_ID, |  | ||||||
|  	.name			= "Atheros 8031 ethernet", |  | ||||||
| +	.config_aneg		= at803x_config_aneg, |  | ||||||
|  	.phy_id_mask		= AT803X_PHY_ID_MASK, |  | ||||||
|  	.probe			= at803x_probe, |  | ||||||
|  	.config_init		= at803x_config_init, |  | ||||||
| @@ -1,177 +0,0 @@ | |||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_BLK_MQ_PCI=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=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_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_RT2880_EVAL is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| CONFIG_FIXED_PHY=y |  | ||||||
| CONFIG_FW_LOADER_PAGED_BUF=y |  | ||||||
| CONFIG_GENERIC_ALLOCATOR=y |  | ||||||
| CONFIG_GENERIC_ATOMIC64=y |  | ||||||
| CONFIG_GENERIC_CLOCKEVENTS=y |  | ||||||
| CONFIG_GENERIC_CMOS_UPDATE=y |  | ||||||
| CONFIG_GENERIC_CPU_AUTOPROBE=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_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| CONFIG_GPIO_RALINK=y |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IP17XX_PHY=y |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_INTC=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=4 |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT_4=y |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPLIT_LZMA_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_WRGG_FW=y |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NEED_PER_CPU_KM=y |  | ||||||
| CONFIG_NET_RALINK_MDIO=y |  | ||||||
| CONFIG_NET_RALINK_MDIO_RT2880=y |  | ||||||
| CONFIG_NET_RALINK_RT2880=y |  | ||||||
| CONFIG_NET_RALINK_SOC=y |  | ||||||
| CONFIG_NET_VENDOR_RALINK=y |  | ||||||
| CONFIG_NLS=m |  | ||||||
| CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PCI=y |  | ||||||
| CONFIG_PCI_DOMAINS=y |  | ||||||
| CONFIG_PCI_DRIVERS_LEGACY=y |  | ||||||
| # CONFIG_PCI_MT7621 is not set |  | ||||||
| # CONFIG_PCI_MT7621_PHY is not set |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| # CONFIG_PHY_RALINK_USB is not set |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| # CONFIG_PINCTRL_AW9523 is not set |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| CONFIG_RALINK_WDT=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_SERIAL_8250_RT288X=y |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| # CONFIG_SOC_MT7620 is not set |  | ||||||
| # CONFIG_SOC_MT7621 is not set |  | ||||||
| CONFIG_SOC_RT288X=y |  | ||||||
| # CONFIG_SOC_RT305X is not set |  | ||||||
| # CONFIG_SOC_RT3883 is not set |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| # CONFIG_SPI_MT7621 is not set |  | ||||||
| CONFIG_SPI_RT2880=y |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWCONFIG=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TINY_SRCU=y |  | ||||||
| CONFIG_USB=m |  | ||||||
| CONFIG_USB_COMMON=m |  | ||||||
| CONFIG_USB_EHCI_HCD=m |  | ||||||
| CONFIG_USB_EHCI_HCD_PLATFORM=m |  | ||||||
| CONFIG_USB_OHCI_HCD=m |  | ||||||
| CONFIG_USB_OHCI_HCD_PLATFORM=m |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
| @@ -1,176 +0,0 @@ | |||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CEVT_SYSTICK_QUIRK=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLKEVT_RT3352=y |  | ||||||
| CONFIG_CLKSRC_MMIO=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=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_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DEBUG_PINCTRL=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_RT305X_EVAL is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| 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_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_PHY=y |  | ||||||
| CONFIG_GENERIC_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| CONFIG_GPIO_RALINK=y |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_INTC=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MFD_SYSCON=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=5 |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS_LIMIT=16384 |  | ||||||
| CONFIG_MTD_SPLIT_JIMAGE_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_SEAMA_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NEED_PER_CPU_KM=y |  | ||||||
| CONFIG_NET_RALINK_ESW_RT3050=y |  | ||||||
| CONFIG_NET_RALINK_RT3050=y |  | ||||||
| CONFIG_NET_RALINK_SOC=y |  | ||||||
| CONFIG_NET_VENDOR_RALINK=y |  | ||||||
| CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PCI_DRIVERS_LEGACY=y |  | ||||||
| # CONFIG_PCI_MT7621 is not set |  | ||||||
| # CONFIG_PCI_MT7621_PHY is not set |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| CONFIG_PHY_RALINK_USB=y |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| # CONFIG_PINCTRL_AW9523 is not set |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| # CONFIG_RALINK_ILL_ACC is not set |  | ||||||
| CONFIG_RALINK_WDT=y |  | ||||||
| CONFIG_REGMAP=y |  | ||||||
| CONFIG_REGMAP_MMIO=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_SERIAL_8250_RT288X=y |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| # CONFIG_SOC_MT7620 is not set |  | ||||||
| # CONFIG_SOC_MT7621 is not set |  | ||||||
| # CONFIG_SOC_RT288X is not set |  | ||||||
| CONFIG_SOC_RT305X=y |  | ||||||
| # CONFIG_SOC_RT3883 is not set |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| # CONFIG_SPI_MT7621 is not set |  | ||||||
| CONFIG_SPI_RT2880=y |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWCONFIG=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TIMER_OF=y |  | ||||||
| CONFIG_TIMER_PROBE=y |  | ||||||
| CONFIG_TINY_SRCU=y |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
| @@ -1,178 +0,0 @@ | |||||||
| CONFIG_AR8216_PHY=y |  | ||||||
| CONFIG_ARCH_32BIT_OFF_T=y |  | ||||||
| CONFIG_ARCH_CLOCKSOURCE_DATA=y |  | ||||||
| CONFIG_ARCH_HIBERNATION_POSSIBLE=y |  | ||||||
| CONFIG_ARCH_MMAP_RND_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_MMAP_RND_COMPAT_BITS_MAX=15 |  | ||||||
| CONFIG_ARCH_SUSPEND_POSSIBLE=y |  | ||||||
| CONFIG_BLK_MQ_PCI=y |  | ||||||
| CONFIG_CEVT_R4K=y |  | ||||||
| CONFIG_CLKDEV_LOOKUP=y |  | ||||||
| CONFIG_CLONE_BACKWARDS=y |  | ||||||
| CONFIG_CMDLINE="rootfstype=squashfs,jffs2" |  | ||||||
| CONFIG_CMDLINE_BOOL=y |  | ||||||
| # CONFIG_CMDLINE_OVERRIDE is not set |  | ||||||
| CONFIG_COMPAT_32BIT_TIME=y |  | ||||||
| CONFIG_CPU_GENERIC_DUMP_TLB=y |  | ||||||
| CONFIG_CPU_HAS_LOAD_STORE_LR=y |  | ||||||
| CONFIG_CPU_HAS_PREFETCH=y |  | ||||||
| CONFIG_CPU_HAS_RIXI=y |  | ||||||
| CONFIG_CPU_HAS_SYNC=y |  | ||||||
| CONFIG_CPU_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_CPU_MIPS32=y |  | ||||||
| # CONFIG_CPU_MIPS32_R1 is not set |  | ||||||
| CONFIG_CPU_MIPS32_R2=y |  | ||||||
| CONFIG_CPU_MIPSR2=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_CPU_SUPPORTS_MSA=y |  | ||||||
| CONFIG_CRYPTO_LIB_POLY1305_RSIZE=2 |  | ||||||
| CONFIG_CRYPTO_RNG2=y |  | ||||||
| CONFIG_CSRC_R4K=y |  | ||||||
| CONFIG_DEBUG_PINCTRL=y |  | ||||||
| CONFIG_DMA_NONCOHERENT=y |  | ||||||
| CONFIG_DMA_NONCOHERENT_CACHE_SYNC=y |  | ||||||
| # CONFIG_DTB_RT3883_EVAL is not set |  | ||||||
| CONFIG_DTB_RT_NONE=y |  | ||||||
| CONFIG_DTC=y |  | ||||||
| CONFIG_EARLY_PRINTK=y |  | ||||||
| CONFIG_ETHERNET_PACKET_MANGLE=y |  | ||||||
| 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_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_PHY=y |  | ||||||
| CONFIG_GENERIC_PINCONF=y |  | ||||||
| CONFIG_GENERIC_SCHED_CLOCK=y |  | ||||||
| CONFIG_GENERIC_SMP_IDLE_THREAD=y |  | ||||||
| CONFIG_GENERIC_TIME_VSYSCALL=y |  | ||||||
| CONFIG_GPIOLIB=y |  | ||||||
| CONFIG_GPIO_RALINK=y |  | ||||||
| CONFIG_HANDLE_DOMAIN_IRQ=y |  | ||||||
| CONFIG_HARDWARE_WATCHPOINTS=y |  | ||||||
| CONFIG_HAS_DMA=y |  | ||||||
| CONFIG_HAS_IOMEM=y |  | ||||||
| CONFIG_HAS_IOPORT_MAP=y |  | ||||||
| CONFIG_HZ_PERIODIC=y |  | ||||||
| CONFIG_INITRAMFS_SOURCE="" |  | ||||||
| CONFIG_IRQCHIP=y |  | ||||||
| CONFIG_IRQ_DOMAIN=y |  | ||||||
| CONFIG_IRQ_FORCED_THREADING=y |  | ||||||
| CONFIG_IRQ_INTC=y |  | ||||||
| CONFIG_IRQ_MIPS_CPU=y |  | ||||||
| CONFIG_IRQ_WORK=y |  | ||||||
| CONFIG_LIBFDT=y |  | ||||||
| CONFIG_LOCK_DEBUGGING_SUPPORT=y |  | ||||||
| CONFIG_MDIO_BUS=y |  | ||||||
| CONFIG_MDIO_DEVICE=y |  | ||||||
| CONFIG_MEMFD_CREATE=y |  | ||||||
| CONFIG_MFD_SYSCON=y |  | ||||||
| CONFIG_MIGRATION=y |  | ||||||
| CONFIG_MIPS=y |  | ||||||
| CONFIG_MIPS_ASID_BITS=8 |  | ||||||
| CONFIG_MIPS_ASID_SHIFT=0 |  | ||||||
| CONFIG_MIPS_CBPF_JIT=y |  | ||||||
| CONFIG_MIPS_CLOCK_VSYSCALL=y |  | ||||||
| # CONFIG_MIPS_CMDLINE_BUILTIN_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_DTB_EXTEND is not set |  | ||||||
| # CONFIG_MIPS_CMDLINE_FROM_BOOTLOADER is not set |  | ||||||
| CONFIG_MIPS_CMDLINE_FROM_DTB=y |  | ||||||
| # CONFIG_MIPS_ELF_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_L1_CACHE_SHIFT=5 |  | ||||||
| # CONFIG_MIPS_NO_APPENDED_DTB is not set |  | ||||||
| CONFIG_MIPS_RAW_APPENDED_DTB=y |  | ||||||
| CONFIG_MIPS_SPRAM=y |  | ||||||
| CONFIG_MODULES_USE_ELF_REL=y |  | ||||||
| # CONFIG_MTD_CFI_INTELEXT is not set |  | ||||||
| CONFIG_MTD_CMDLINE_PARTS=y |  | ||||||
| CONFIG_MTD_PHYSMAP=y |  | ||||||
| CONFIG_MTD_SPI_NOR=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS=y |  | ||||||
| CONFIG_MTD_SPI_NOR_USE_4K_SECTORS_LIMIT=16384 |  | ||||||
| CONFIG_MTD_SPLIT_SEAMA_FW=y |  | ||||||
| CONFIG_MTD_SPLIT_UIMAGE_FW=y |  | ||||||
| CONFIG_NEED_DMA_MAP_STATE=y |  | ||||||
| CONFIG_NEED_PER_CPU_KM=y |  | ||||||
| CONFIG_NET_RALINK_MDIO=y |  | ||||||
| CONFIG_NET_RALINK_MDIO_RT2880=y |  | ||||||
| CONFIG_NET_RALINK_RT3883=y |  | ||||||
| CONFIG_NET_RALINK_SOC=y |  | ||||||
| CONFIG_NET_VENDOR_RALINK=y |  | ||||||
| CONFIG_NO_GENERIC_PCI_IOPORT_MAP=y |  | ||||||
| CONFIG_NVMEM=y |  | ||||||
| CONFIG_OF=y |  | ||||||
| CONFIG_OF_ADDRESS=y |  | ||||||
| CONFIG_OF_EARLY_FLATTREE=y |  | ||||||
| CONFIG_OF_FLATTREE=y |  | ||||||
| CONFIG_OF_GPIO=y |  | ||||||
| CONFIG_OF_IRQ=y |  | ||||||
| CONFIG_OF_KOBJ=y |  | ||||||
| CONFIG_OF_MDIO=y |  | ||||||
| CONFIG_OF_NET=y |  | ||||||
| CONFIG_PCI=y |  | ||||||
| CONFIG_PCI_DOMAINS=y |  | ||||||
| CONFIG_PCI_DRIVERS_LEGACY=y |  | ||||||
| # CONFIG_PCI_MT7621 is not set |  | ||||||
| # CONFIG_PCI_MT7621_PHY is not set |  | ||||||
| CONFIG_PERF_USE_VMALLOC=y |  | ||||||
| CONFIG_PGTABLE_LEVELS=2 |  | ||||||
| CONFIG_PHYLIB=y |  | ||||||
| CONFIG_PHY_RALINK_USB=y |  | ||||||
| CONFIG_PINCTRL=y |  | ||||||
| # CONFIG_PINCTRL_AW9523 is not set |  | ||||||
| CONFIG_PINCTRL_RT2880=y |  | ||||||
| # CONFIG_PINCTRL_SINGLE is not set |  | ||||||
| CONFIG_RALINK=y |  | ||||||
| CONFIG_RALINK_WDT=y |  | ||||||
| CONFIG_REGMAP=y |  | ||||||
| CONFIG_REGMAP_MMIO=y |  | ||||||
| CONFIG_RESET_CONTROLLER=y |  | ||||||
| CONFIG_RTL8366_SMI=y |  | ||||||
| CONFIG_RTL8367B_PHY=y |  | ||||||
| CONFIG_RTL8367_PHY=y |  | ||||||
| CONFIG_SERIAL_8250_RT288X=y |  | ||||||
| CONFIG_SERIAL_MCTRL_GPIO=y |  | ||||||
| CONFIG_SERIAL_OF_PLATFORM=y |  | ||||||
| # CONFIG_SOC_MT7620 is not set |  | ||||||
| # CONFIG_SOC_MT7621 is not set |  | ||||||
| # CONFIG_SOC_RT288X is not set |  | ||||||
| # CONFIG_SOC_RT305X is not set |  | ||||||
| CONFIG_SOC_RT3883=y |  | ||||||
| CONFIG_SPI=y |  | ||||||
| CONFIG_SPI_MASTER=y |  | ||||||
| CONFIG_SPI_MEM=y |  | ||||||
| # CONFIG_SPI_MT7621 is not set |  | ||||||
| CONFIG_SPI_RT2880=y |  | ||||||
| CONFIG_SRCU=y |  | ||||||
| CONFIG_SWCONFIG=y |  | ||||||
| CONFIG_SWPHY=y |  | ||||||
| CONFIG_SYSCTL_EXCEPTION_TRACE=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_LITTLE_ENDIAN=y |  | ||||||
| CONFIG_SYS_SUPPORTS_MIPS16=y |  | ||||||
| CONFIG_SYS_SUPPORTS_ZBOOT=y |  | ||||||
| CONFIG_TARGET_ISA_REV=2 |  | ||||||
| CONFIG_TICK_CPU_ACCOUNTING=y |  | ||||||
| CONFIG_TINY_SRCU=y |  | ||||||
| CONFIG_USB_SUPPORT=y |  | ||||||
| CONFIG_USE_OF=y |  | ||||||
| CONFIG_WATCHDOG_CORE=y |  | ||||||
		Reference in New Issue
	
	Block a user
	 Rui Salvaterra
					Rui Salvaterra