Merge branch 'for-linus' of git://android.kernel.org/kernel/tegra

* 'for-linus' of git://android.kernel.org/kernel/tegra:
[ARM] tegra: add MAINTAINERS entry
[ARM] tegra: harmony: Add harmony board file
[ARM] tegra: add pinmux support
[ARM] tegra: add GPIO support
[ARM] tegra: Add timer support
[ARM] tegra: SMP support
[ARM] tegra: Add clock support
[ARM] tegra: Add IRQ support
[ARM] tegra: initial tegra support

+6061 -5
+9
MAINTAINERS
··· 5565 5565 S: Maintained 5566 5566 F: net/ipv4/tcp_lp.c 5567 5567 5568 + TEGRA SUPPORT 5569 + M: Colin Cross <ccross@android.com> 5570 + M: Erik Gilling <konkers@android.com> 5571 + M: Olof Johansson <olof@lixom.net> 5572 + L: linux-tegra@vger.kernel.org 5573 + T: git git://android.git.kernel.org/kernel/tegra.git 5574 + S: Supported 5575 + F: arch/arm/mach-tegra 5576 + 5568 5577 TEHUTI ETHERNET DRIVER 5569 5578 M: Alexander Indenbaum <baum@tehutinetworks.net> 5570 5579 M: Andy Gospodarek <andy@greyhouse.net>
+20 -4
arch/arm/Kconfig
··· 558 558 Support for Nuvoton (Winbond logic dept.) NUC93X MCU,The NUC93X is a 559 559 low-power and high performance MPEG-4/JPEG multimedia controller chip. 560 560 561 + config ARCH_TEGRA 562 + bool "NVIDIA Tegra" 563 + select GENERIC_TIME 564 + select GENERIC_CLOCKEVENTS 565 + select GENERIC_GPIO 566 + select HAVE_CLK 567 + select COMMON_CLKDEV 568 + select ARCH_HAS_BARRIERS if CACHE_L2X0 569 + help 570 + This enables support for NVIDIA Tegra based systems (Tegra APX, 571 + Tegra 6xx and Tegra 2 series). 572 + 561 573 config ARCH_PNX4008 562 574 bool "Philips Nexperia PNX4008 Mobile" 563 575 select CPU_ARM926T ··· 919 907 920 908 source "arch/arm/plat-stmp3xxx/Kconfig" 921 909 910 + source "arch/arm/mach-tegra/Kconfig" 911 + 922 912 source "arch/arm/mach-u300/Kconfig" 923 913 924 914 source "arch/arm/mach-ux500/Kconfig" ··· 1108 1094 bool "Symmetric Multi-Processing (EXPERIMENTAL)" 1109 1095 depends on EXPERIMENTAL && (REALVIEW_EB_ARM11MP || REALVIEW_EB_A9MP ||\ 1110 1096 MACH_REALVIEW_PB11MP || MACH_REALVIEW_PBX || ARCH_OMAP4 ||\ 1111 - ARCH_U8500 || ARCH_VEXPRESS_CA9X4) 1097 + ARCH_U8500 || ARCH_VEXPRESS_CA9X4 || ARCH_TEGRA) 1112 1098 depends on GENERIC_CLOCKEVENTS 1113 1099 select USE_GENERIC_SMP_HELPERS 1114 - select HAVE_ARM_SCU if (ARCH_REALVIEW || ARCH_OMAP4 || ARCH_U8500 || ARCH_VEXPRESS_CA9X4) 1100 + select HAVE_ARM_SCU if (ARCH_REALVIEW || ARCH_OMAP4 || ARCH_U8500 || \ 1101 + ARCH_VEXPRESS_CA9X4 || ARCH_TEGRA) 1115 1102 help 1116 1103 This enables support for systems with more than one CPU. If you have 1117 1104 a system with only one CPU, like most personal computers, say N. If ··· 1182 1167 bool "Use local timer interrupts" 1183 1168 depends on SMP && (REALVIEW_EB_ARM11MP || MACH_REALVIEW_PB11MP || \ 1184 1169 REALVIEW_EB_A9MP || MACH_REALVIEW_PBX || ARCH_OMAP4 || \ 1185 - ARCH_U8500 || ARCH_VEXPRESS_CA9X4) 1170 + ARCH_U8500 || ARCH_VEXPRESS_CA9X4 || ARCH_TEGRA) 1186 1171 default y 1187 - select HAVE_ARM_TWD if (ARCH_REALVIEW || ARCH_VEXPRESS || ARCH_OMAP4 || ARCH_U8500) 1172 + select HAVE_ARM_TWD if (ARCH_REALVIEW || ARCH_VEXPRESS || ARCH_OMAP4 || \\ 1173 + ARCH_U8500 || ARCH_TEGRA 1188 1174 help 1189 1175 Enable support for local timers on SMP platforms, rather then the 1190 1176 legacy IPI broadcast method. Local timers allows the system
+1
arch/arm/Makefile
··· 179 179 machine-$(CONFIG_ARCH_SHMOBILE) := shmobile 180 180 machine-$(CONFIG_ARCH_STMP378X) := stmp378x 181 181 machine-$(CONFIG_ARCH_STMP37XX) := stmp37xx 182 + machine-$(CONFIG_ARCH_TEGRA) := tegra 182 183 machine-$(CONFIG_ARCH_U300) := u300 183 184 machine-$(CONFIG_ARCH_U8500) := ux500 184 185 machine-$(CONFIG_ARCH_VERSATILE) := versatile
+50
arch/arm/mach-tegra/Kconfig
··· 1 + if ARCH_TEGRA 2 + 3 + comment "NVIDIA Tegra options" 4 + 5 + choice 6 + prompt "Select Tegra processor family for target system" 7 + 8 + config ARCH_TEGRA_2x_SOC 9 + bool "Tegra 2 family" 10 + select CPU_V7 11 + select ARM_GIC 12 + select ARCH_REQUIRE_GPIOLIB 13 + help 14 + Support for NVIDIA Tegra AP20 and T20 processors, based on the 15 + ARM CortexA9MP CPU and the ARM PL310 L2 cache controller 16 + 17 + endchoice 18 + 19 + comment "Tegra board type" 20 + 21 + config MACH_HARMONY 22 + bool "Harmony board" 23 + help 24 + Support for nVidia Harmony development platform 25 + 26 + choice 27 + prompt "Low-level debug console UART" 28 + default TEGRA_DEBUG_UART_NONE 29 + 30 + config TEGRA_DEBUG_UART_NONE 31 + bool "None" 32 + 33 + config TEGRA_DEBUG_UARTA 34 + bool "UART-A" 35 + 36 + config TEGRA_DEBUG_UARTB 37 + bool "UART-B" 38 + 39 + config TEGRA_DEBUG_UARTC 40 + bool "UART-C" 41 + 42 + config TEGRA_DEBUG_UARTD 43 + bool "UART-D" 44 + 45 + config TEGRA_DEBUG_UARTE 46 + bool "UART-E" 47 + 48 + endchoice 49 + 50 + endif
+14
arch/arm/mach-tegra/Makefile
··· 1 + obj-y += common.o 2 + obj-y += io.o 3 + obj-y += irq.o 4 + obj-y += clock.o 5 + obj-y += timer.o 6 + obj-y += gpio.o 7 + obj-y += pinmux.o 8 + obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += clock.o 9 + obj-$(CONFIG_ARCH_TEGRA_2x_SOC) += tegra2_clocks.o 10 + obj-$(CONFIG_SMP) += platsmp.o localtimer.o headsmp.o 11 + obj-$(CONFIG_HOTPLUG_CPU) += hotplug.o 12 + 13 + obj-${CONFIG_MACH_HARMONY} += board-harmony.o 14 + obj-${CONFIG_MACH_HARMONY} += board-harmony-pinmux.o
+3
arch/arm/mach-tegra/Makefile.boot
··· 1 + zreladdr-$(CONFIG_ARCH_TEGRA_2x_SOC) := 0x00008000 2 + params_phys-$(CONFIG_ARCH_TEGRA_2x_SOC) := 0x00000100 3 + initrd_phys-$(CONFIG_ARCH_TEGRA_2x_SOC) := 0x00800000
+144
arch/arm/mach-tegra/board-harmony-pinmux.c
··· 1 + /* 2 + * arch/arm/mach-tegra/board-harmony-pinmux.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * This software is licensed under the terms of the GNU General Public 7 + * License version 2, as published by the Free Software Foundation, and 8 + * may be copied, distributed, and modified under those terms. 9 + * 10 + * This program is distributed in the hope that it will be useful, 11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 + * GNU General Public License for more details. 14 + * 15 + */ 16 + 17 + #include <linux/kernel.h> 18 + #include <mach/pinmux.h> 19 + 20 + #include "board-harmony.h" 21 + 22 + static struct tegra_pingroup_config harmony_pinmux[] = { 23 + {TEGRA_PINGROUP_ATA, TEGRA_MUX_IDE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 24 + {TEGRA_PINGROUP_ATB, TEGRA_MUX_SDIO4, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 25 + {TEGRA_PINGROUP_ATC, TEGRA_MUX_NAND, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 26 + {TEGRA_PINGROUP_ATD, TEGRA_MUX_GMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 27 + {TEGRA_PINGROUP_ATE, TEGRA_MUX_GMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 28 + {TEGRA_PINGROUP_CDEV1, TEGRA_MUX_OSC, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 29 + {TEGRA_PINGROUP_CDEV2, TEGRA_MUX_PLLP_OUT4, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 30 + {TEGRA_PINGROUP_CRTP, TEGRA_MUX_CRT, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 31 + {TEGRA_PINGROUP_CSUS, TEGRA_MUX_VI_SENSOR_CLK, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 32 + {TEGRA_PINGROUP_DAP1, TEGRA_MUX_DAP1, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 33 + {TEGRA_PINGROUP_DAP2, TEGRA_MUX_DAP2, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 34 + {TEGRA_PINGROUP_DAP3, TEGRA_MUX_DAP3, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 35 + {TEGRA_PINGROUP_DAP4, TEGRA_MUX_DAP4, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 36 + {TEGRA_PINGROUP_DDC, TEGRA_MUX_I2C2, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 37 + {TEGRA_PINGROUP_DTA, TEGRA_MUX_SDIO2, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 38 + {TEGRA_PINGROUP_DTB, TEGRA_MUX_RSVD1, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 39 + {TEGRA_PINGROUP_DTC, TEGRA_MUX_RSVD1, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 40 + {TEGRA_PINGROUP_DTD, TEGRA_MUX_SDIO2, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 41 + {TEGRA_PINGROUP_DTE, TEGRA_MUX_RSVD1, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 42 + {TEGRA_PINGROUP_DTF, TEGRA_MUX_I2C3, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 43 + {TEGRA_PINGROUP_GMA, TEGRA_MUX_SDIO4, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 44 + {TEGRA_PINGROUP_GMB, TEGRA_MUX_GMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 45 + {TEGRA_PINGROUP_GMC, TEGRA_MUX_UARTD, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 46 + {TEGRA_PINGROUP_GMD, TEGRA_MUX_GMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 47 + {TEGRA_PINGROUP_GME, TEGRA_MUX_SDIO4, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 48 + {TEGRA_PINGROUP_GPU, TEGRA_MUX_GMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 49 + {TEGRA_PINGROUP_GPU7, TEGRA_MUX_RTCK, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 50 + {TEGRA_PINGROUP_GPV, TEGRA_MUX_PCIE, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 51 + {TEGRA_PINGROUP_HDINT, TEGRA_MUX_HDMI, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 52 + {TEGRA_PINGROUP_I2CP, TEGRA_MUX_I2C, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 53 + {TEGRA_PINGROUP_IRRX, TEGRA_MUX_UARTA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 54 + {TEGRA_PINGROUP_IRTX, TEGRA_MUX_UARTA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 55 + {TEGRA_PINGROUP_KBCA, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 56 + {TEGRA_PINGROUP_KBCB, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 57 + {TEGRA_PINGROUP_KBCC, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 58 + {TEGRA_PINGROUP_KBCD, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 59 + {TEGRA_PINGROUP_KBCE, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 60 + {TEGRA_PINGROUP_KBCF, TEGRA_MUX_KBC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 61 + {TEGRA_PINGROUP_LCSN, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 62 + {TEGRA_PINGROUP_LD0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 63 + {TEGRA_PINGROUP_LD1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 64 + {TEGRA_PINGROUP_LD10, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 65 + {TEGRA_PINGROUP_LD11, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 66 + {TEGRA_PINGROUP_LD12, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 67 + {TEGRA_PINGROUP_LD13, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 68 + {TEGRA_PINGROUP_LD14, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 69 + {TEGRA_PINGROUP_LD15, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 70 + {TEGRA_PINGROUP_LD16, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 71 + {TEGRA_PINGROUP_LD17, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 72 + {TEGRA_PINGROUP_LD2, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 73 + {TEGRA_PINGROUP_LD3, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 74 + {TEGRA_PINGROUP_LD4, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 75 + {TEGRA_PINGROUP_LD5, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 76 + {TEGRA_PINGROUP_LD6, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 77 + {TEGRA_PINGROUP_LD7, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 78 + {TEGRA_PINGROUP_LD8, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 79 + {TEGRA_PINGROUP_LD9, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 80 + {TEGRA_PINGROUP_LDC, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 81 + {TEGRA_PINGROUP_LDI, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 82 + {TEGRA_PINGROUP_LHP0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 83 + {TEGRA_PINGROUP_LHP1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 84 + {TEGRA_PINGROUP_LHP2, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 85 + {TEGRA_PINGROUP_LHS, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 86 + {TEGRA_PINGROUP_LM0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 87 + {TEGRA_PINGROUP_LM1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 88 + {TEGRA_PINGROUP_LPP, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 89 + {TEGRA_PINGROUP_LPW0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 90 + {TEGRA_PINGROUP_LPW1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 91 + {TEGRA_PINGROUP_LPW2, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 92 + {TEGRA_PINGROUP_LSC0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 93 + {TEGRA_PINGROUP_LSC1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 94 + {TEGRA_PINGROUP_LSCK, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 95 + {TEGRA_PINGROUP_LSDA, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 96 + {TEGRA_PINGROUP_LSDI, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 97 + {TEGRA_PINGROUP_LSPI, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 98 + {TEGRA_PINGROUP_LVP0, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 99 + {TEGRA_PINGROUP_LVP1, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_NORMAL}, 100 + {TEGRA_PINGROUP_LVS, TEGRA_MUX_DISPLAYA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 101 + {TEGRA_PINGROUP_OWC, TEGRA_MUX_RSVD2, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 102 + {TEGRA_PINGROUP_PMC, TEGRA_MUX_PWR_ON, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 103 + {TEGRA_PINGROUP_PTA, TEGRA_MUX_HDMI, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 104 + {TEGRA_PINGROUP_RM, TEGRA_MUX_I2C, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 105 + {TEGRA_PINGROUP_SDB, TEGRA_MUX_PWM, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 106 + {TEGRA_PINGROUP_SDC, TEGRA_MUX_PWM, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 107 + {TEGRA_PINGROUP_SDD, TEGRA_MUX_PWM, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 108 + {TEGRA_PINGROUP_SDIO1, TEGRA_MUX_SDIO1, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 109 + {TEGRA_PINGROUP_SLXA, TEGRA_MUX_PCIE, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 110 + {TEGRA_PINGROUP_SLXC, TEGRA_MUX_SPDIF, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 111 + {TEGRA_PINGROUP_SLXD, TEGRA_MUX_SPDIF, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 112 + {TEGRA_PINGROUP_SLXK, TEGRA_MUX_PCIE, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 113 + {TEGRA_PINGROUP_SPDI, TEGRA_MUX_RSVD2, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 114 + {TEGRA_PINGROUP_SPDO, TEGRA_MUX_RSVD2, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 115 + {TEGRA_PINGROUP_SPIA, TEGRA_MUX_GMI, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 116 + {TEGRA_PINGROUP_SPIB, TEGRA_MUX_GMI, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 117 + {TEGRA_PINGROUP_SPIC, TEGRA_MUX_GMI, TEGRA_PUPD_PULL_UP, TEGRA_TRI_NORMAL}, 118 + {TEGRA_PINGROUP_SPID, TEGRA_MUX_SPI1, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 119 + {TEGRA_PINGROUP_SPIE, TEGRA_MUX_SPI1, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 120 + {TEGRA_PINGROUP_SPIF, TEGRA_MUX_SPI1, TEGRA_PUPD_PULL_DOWN, TEGRA_TRI_TRISTATE}, 121 + {TEGRA_PINGROUP_SPIG, TEGRA_MUX_SPI2_ALT, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 122 + {TEGRA_PINGROUP_SPIH, TEGRA_MUX_SPI2_ALT, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 123 + {TEGRA_PINGROUP_UAA, TEGRA_MUX_ULPI, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 124 + {TEGRA_PINGROUP_UAB, TEGRA_MUX_ULPI, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 125 + {TEGRA_PINGROUP_UAC, TEGRA_MUX_RSVD2, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 126 + {TEGRA_PINGROUP_UAD, TEGRA_MUX_IRDA, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 127 + {TEGRA_PINGROUP_UCA, TEGRA_MUX_UARTC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 128 + {TEGRA_PINGROUP_UCB, TEGRA_MUX_UARTC, TEGRA_PUPD_PULL_UP, TEGRA_TRI_TRISTATE}, 129 + {TEGRA_PINGROUP_UDA, TEGRA_MUX_ULPI, TEGRA_PUPD_NORMAL, TEGRA_TRI_TRISTATE}, 130 + {TEGRA_PINGROUP_CK32, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 131 + {TEGRA_PINGROUP_DDRC, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 132 + {TEGRA_PINGROUP_PMCA, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 133 + {TEGRA_PINGROUP_PMCB, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 134 + {TEGRA_PINGROUP_PMCC, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 135 + {TEGRA_PINGROUP_PMCD, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 136 + {TEGRA_PINGROUP_PMCE, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 137 + {TEGRA_PINGROUP_XM2C, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 138 + {TEGRA_PINGROUP_XM2D, TEGRA_MUX_NONE, TEGRA_PUPD_NORMAL, TEGRA_TRI_NORMAL}, 139 + }; 140 + 141 + void harmony_pinmux_init(void) 142 + { 143 + tegra_pinmux_config_table(harmony_pinmux, ARRAY_SIZE(harmony_pinmux)); 144 + }
+127
arch/arm/mach-tegra/board-harmony.c
··· 1 + /* 2 + * arch/arm/mach-tegra/board-harmony.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * This software is licensed under the terms of the GNU General Public 7 + * License version 2, as published by the Free Software Foundation, and 8 + * may be copied, distributed, and modified under those terms. 9 + * 10 + * This program is distributed in the hope that it will be useful, 11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 + * GNU General Public License for more details. 14 + * 15 + */ 16 + 17 + #include <linux/kernel.h> 18 + #include <linux/init.h> 19 + #include <linux/platform_device.h> 20 + #include <linux/serial_8250.h> 21 + #include <linux/clk.h> 22 + #include <linux/dma-mapping.h> 23 + #include <linux/pda_power.h> 24 + #include <linux/io.h> 25 + 26 + #include <asm/mach-types.h> 27 + #include <asm/mach/arch.h> 28 + #include <asm/mach/time.h> 29 + #include <asm/setup.h> 30 + 31 + #include <mach/iomap.h> 32 + #include <mach/irqs.h> 33 + 34 + #include "board.h" 35 + #include "board-harmony.h" 36 + #include "clock.h" 37 + 38 + /* NVidia bootloader tags */ 39 + #define ATAG_NVIDIA 0x41000801 40 + 41 + #define ATAG_NVIDIA_RM 0x1 42 + #define ATAG_NVIDIA_DISPLAY 0x2 43 + #define ATAG_NVIDIA_FRAMEBUFFER 0x3 44 + #define ATAG_NVIDIA_CHIPSHMOO 0x4 45 + #define ATAG_NVIDIA_CHIPSHMOOPHYS 0x5 46 + #define ATAG_NVIDIA_PRESERVED_MEM_0 0x10000 47 + #define ATAG_NVIDIA_PRESERVED_MEM_N 2 48 + #define ATAG_NVIDIA_FORCE_32 0x7fffffff 49 + 50 + struct tag_tegra { 51 + __u32 bootarg_key; 52 + __u32 bootarg_len; 53 + char bootarg[1]; 54 + }; 55 + 56 + static int __init parse_tag_nvidia(const struct tag *tag) 57 + { 58 + 59 + return 0; 60 + } 61 + __tagtable(ATAG_NVIDIA, parse_tag_nvidia); 62 + 63 + static struct plat_serial8250_port debug_uart_platform_data[] = { 64 + { 65 + .membase = IO_ADDRESS(TEGRA_UARTD_BASE), 66 + .mapbase = TEGRA_UARTD_BASE, 67 + .irq = INT_UARTD, 68 + .flags = UPF_BOOT_AUTOCONF, 69 + .iotype = UPIO_MEM, 70 + .regshift = 2, 71 + .uartclk = 216000000, 72 + }, { 73 + .flags = 0 74 + } 75 + }; 76 + 77 + static struct platform_device debug_uart = { 78 + .name = "serial8250", 79 + .id = PLAT8250_DEV_PLATFORM, 80 + .dev = { 81 + .platform_data = debug_uart_platform_data, 82 + }, 83 + }; 84 + 85 + static struct platform_device *harmony_devices[] __initdata = { 86 + &debug_uart, 87 + }; 88 + 89 + static void __init tegra_harmony_fixup(struct machine_desc *desc, 90 + struct tag *tags, char **cmdline, struct meminfo *mi) 91 + { 92 + mi->nr_banks = 2; 93 + mi->bank[0].start = PHYS_OFFSET; 94 + mi->bank[0].node = PHYS_TO_NID(PHYS_OFFSET); 95 + mi->bank[0].size = 448 * SZ_1M; 96 + mi->bank[1].start = SZ_512M; 97 + mi->bank[1].node = PHYS_TO_NID(SZ_512M); 98 + mi->bank[1].size = SZ_512M; 99 + } 100 + 101 + static __initdata struct tegra_clk_init_table harmony_clk_init_table[] = { 102 + /* name parent rate enabled */ 103 + { "uartd", "pll_p", 216000000, true }, 104 + { NULL, NULL, 0, 0}, 105 + }; 106 + 107 + static void __init tegra_harmony_init(void) 108 + { 109 + tegra_common_init(); 110 + 111 + tegra_clk_init_from_table(harmony_clk_init_table); 112 + 113 + harmony_pinmux_init(); 114 + 115 + platform_add_devices(harmony_devices, ARRAY_SIZE(harmony_devices)); 116 + } 117 + 118 + MACHINE_START(HARMONY, "harmony") 119 + .boot_params = 0x00000100, 120 + .phys_io = IO_APB_PHYS, 121 + .io_pg_offst = ((IO_APB_VIRT) >> 18) & 0xfffc, 122 + .fixup = tegra_harmony_fixup, 123 + .init_irq = tegra_init_irq, 124 + .init_machine = tegra_harmony_init, 125 + .map_io = tegra_map_common_io, 126 + .timer = &tegra_timer, 127 + MACHINE_END
+22
arch/arm/mach-tegra/board-harmony.h
··· 1 + /* 2 + * arch/arm/mach-tegra/board-harmony.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * This software is licensed under the terms of the GNU General Public 7 + * License version 2, as published by the Free Software Foundation, and 8 + * may be copied, distributed, and modified under those terms. 9 + * 10 + * This program is distributed in the hope that it will be useful, 11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 + * GNU General Public License for more details. 14 + * 15 + */ 16 + 17 + #ifndef _MACH_TEGRA_BOARD_HARMONY_H 18 + #define _MACH_TEGRA_BOARD_HARMONY_H 19 + 20 + void harmony_pinmux_init(void); 21 + 22 + #endif
+32
arch/arm/mach-tegra/board.h
··· 1 + /* 2 + * arch/arm/mach-tegra/board.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_BOARD_H 22 + #define __MACH_TEGRA_BOARD_H 23 + 24 + #include <linux/types.h> 25 + 26 + void __init tegra_common_init(void); 27 + void __init tegra_map_common_io(void); 28 + void __init tegra_init_irq(void); 29 + void __init tegra_init_clock(void); 30 + 31 + extern struct sys_timer tegra_timer; 32 + #endif
+488
arch/arm/mach-tegra/clock.c
··· 1 + /* 2 + * 3 + * Copyright (C) 2010 Google, Inc. 4 + * 5 + * Author: 6 + * Colin Cross <ccross@google.com> 7 + * 8 + * This software is licensed under the terms of the GNU General Public 9 + * License version 2, as published by the Free Software Foundation, and 10 + * may be copied, distributed, and modified under those terms. 11 + * 12 + * This program is distributed in the hope that it will be useful, 13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 + * GNU General Public License for more details. 16 + * 17 + */ 18 + 19 + #include <linux/kernel.h> 20 + #include <linux/clk.h> 21 + #include <linux/list.h> 22 + #include <linux/init.h> 23 + #include <linux/module.h> 24 + #include <linux/debugfs.h> 25 + #include <linux/slab.h> 26 + #include <linux/seq_file.h> 27 + #include <asm/clkdev.h> 28 + 29 + #include "clock.h" 30 + 31 + static LIST_HEAD(clocks); 32 + 33 + static DEFINE_SPINLOCK(clock_lock); 34 + 35 + struct clk *tegra_get_clock_by_name(const char *name) 36 + { 37 + struct clk *c; 38 + struct clk *ret = NULL; 39 + unsigned long flags; 40 + spin_lock_irqsave(&clock_lock, flags); 41 + list_for_each_entry(c, &clocks, node) { 42 + if (strcmp(c->name, name) == 0) { 43 + ret = c; 44 + break; 45 + } 46 + } 47 + spin_unlock_irqrestore(&clock_lock, flags); 48 + return ret; 49 + } 50 + 51 + int clk_reparent(struct clk *c, struct clk *parent) 52 + { 53 + pr_debug("%s: %s\n", __func__, c->name); 54 + if (c->refcnt && c->parent) 55 + clk_disable_locked(c->parent); 56 + c->parent = parent; 57 + if (c->refcnt && c->parent) 58 + clk_enable_locked(c->parent); 59 + list_del(&c->sibling); 60 + list_add_tail(&c->sibling, &parent->children); 61 + return 0; 62 + } 63 + 64 + static void propagate_rate(struct clk *c) 65 + { 66 + struct clk *clkp; 67 + pr_debug("%s: %s\n", __func__, c->name); 68 + list_for_each_entry(clkp, &c->children, sibling) { 69 + pr_debug(" %s\n", clkp->name); 70 + if (clkp->ops->recalculate_rate) 71 + clkp->ops->recalculate_rate(clkp); 72 + propagate_rate(clkp); 73 + } 74 + } 75 + 76 + void clk_init(struct clk *c) 77 + { 78 + unsigned long flags; 79 + 80 + spin_lock_irqsave(&clock_lock, flags); 81 + 82 + INIT_LIST_HEAD(&c->children); 83 + INIT_LIST_HEAD(&c->sibling); 84 + 85 + if (c->ops && c->ops->init) 86 + c->ops->init(c); 87 + 88 + list_add(&c->node, &clocks); 89 + 90 + if (c->parent) 91 + list_add_tail(&c->sibling, &c->parent->children); 92 + 93 + spin_unlock_irqrestore(&clock_lock, flags); 94 + } 95 + 96 + int clk_enable_locked(struct clk *c) 97 + { 98 + int ret; 99 + pr_debug("%s: %s\n", __func__, c->name); 100 + if (c->refcnt == 0) { 101 + if (c->parent) { 102 + ret = clk_enable_locked(c->parent); 103 + if (ret) 104 + return ret; 105 + } 106 + 107 + if (c->ops && c->ops->enable) { 108 + ret = c->ops->enable(c); 109 + if (ret) { 110 + if (c->parent) 111 + clk_disable_locked(c->parent); 112 + return ret; 113 + } 114 + c->state = ON; 115 + #ifdef CONFIG_DEBUG_FS 116 + c->set = 1; 117 + #endif 118 + } 119 + } 120 + c->refcnt++; 121 + 122 + return 0; 123 + } 124 + 125 + int clk_enable(struct clk *c) 126 + { 127 + int ret; 128 + unsigned long flags; 129 + spin_lock_irqsave(&clock_lock, flags); 130 + ret = clk_enable_locked(c); 131 + spin_unlock_irqrestore(&clock_lock, flags); 132 + return ret; 133 + } 134 + EXPORT_SYMBOL(clk_enable); 135 + 136 + void clk_disable_locked(struct clk *c) 137 + { 138 + pr_debug("%s: %s\n", __func__, c->name); 139 + if (c->refcnt == 0) { 140 + WARN(1, "Attempting to disable clock %s with refcnt 0", c->name); 141 + return; 142 + } 143 + if (c->refcnt == 1) { 144 + if (c->ops && c->ops->disable) 145 + c->ops->disable(c); 146 + 147 + if (c->parent) 148 + clk_disable_locked(c->parent); 149 + 150 + c->state = OFF; 151 + } 152 + c->refcnt--; 153 + } 154 + 155 + void clk_disable(struct clk *c) 156 + { 157 + unsigned long flags; 158 + spin_lock_irqsave(&clock_lock, flags); 159 + clk_disable_locked(c); 160 + spin_unlock_irqrestore(&clock_lock, flags); 161 + } 162 + EXPORT_SYMBOL(clk_disable); 163 + 164 + int clk_set_parent_locked(struct clk *c, struct clk *parent) 165 + { 166 + int ret; 167 + 168 + pr_debug("%s: %s\n", __func__, c->name); 169 + 170 + if (!c->ops || !c->ops->set_parent) 171 + return -ENOSYS; 172 + 173 + ret = c->ops->set_parent(c, parent); 174 + 175 + if (ret) 176 + return ret; 177 + 178 + propagate_rate(c); 179 + 180 + return 0; 181 + } 182 + 183 + int clk_set_parent(struct clk *c, struct clk *parent) 184 + { 185 + int ret; 186 + unsigned long flags; 187 + spin_lock_irqsave(&clock_lock, flags); 188 + ret = clk_set_parent_locked(c, parent); 189 + spin_unlock_irqrestore(&clock_lock, flags); 190 + return ret; 191 + } 192 + EXPORT_SYMBOL(clk_set_parent); 193 + 194 + struct clk *clk_get_parent(struct clk *c) 195 + { 196 + return c->parent; 197 + } 198 + EXPORT_SYMBOL(clk_get_parent); 199 + 200 + int clk_set_rate(struct clk *c, unsigned long rate) 201 + { 202 + int ret = 0; 203 + unsigned long flags; 204 + 205 + spin_lock_irqsave(&clock_lock, flags); 206 + 207 + pr_debug("%s: %s\n", __func__, c->name); 208 + 209 + if (c->ops && c->ops->set_rate) 210 + ret = c->ops->set_rate(c, rate); 211 + else 212 + ret = -ENOSYS; 213 + 214 + propagate_rate(c); 215 + 216 + spin_unlock_irqrestore(&clock_lock, flags); 217 + 218 + return ret; 219 + } 220 + EXPORT_SYMBOL(clk_set_rate); 221 + 222 + unsigned long clk_get_rate(struct clk *c) 223 + { 224 + unsigned long flags; 225 + unsigned long ret; 226 + 227 + spin_lock_irqsave(&clock_lock, flags); 228 + 229 + pr_debug("%s: %s\n", __func__, c->name); 230 + 231 + ret = c->rate; 232 + 233 + spin_unlock_irqrestore(&clock_lock, flags); 234 + return ret; 235 + } 236 + EXPORT_SYMBOL(clk_get_rate); 237 + 238 + static int tegra_clk_init_one_from_table(struct tegra_clk_init_table *table) 239 + { 240 + struct clk *c; 241 + struct clk *p; 242 + 243 + int ret = 0; 244 + 245 + c = tegra_get_clock_by_name(table->name); 246 + 247 + if (!c) { 248 + pr_warning("Unable to initialize clock %s\n", 249 + table->name); 250 + return -ENODEV; 251 + } 252 + 253 + if (table->parent) { 254 + p = tegra_get_clock_by_name(table->parent); 255 + if (!p) { 256 + pr_warning("Unable to find parent %s of clock %s\n", 257 + table->parent, table->name); 258 + return -ENODEV; 259 + } 260 + 261 + if (c->parent != p) { 262 + ret = clk_set_parent(c, p); 263 + if (ret) { 264 + pr_warning("Unable to set parent %s of clock %s: %d\n", 265 + table->parent, table->name, ret); 266 + return -EINVAL; 267 + } 268 + } 269 + } 270 + 271 + if (table->rate && table->rate != clk_get_rate(c)) { 272 + ret = clk_set_rate(c, table->rate); 273 + if (ret) { 274 + pr_warning("Unable to set clock %s to rate %lu: %d\n", 275 + table->name, table->rate, ret); 276 + return -EINVAL; 277 + } 278 + } 279 + 280 + if (table->enabled) { 281 + ret = clk_enable(c); 282 + if (ret) { 283 + pr_warning("Unable to enable clock %s: %d\n", 284 + table->name, ret); 285 + return -EINVAL; 286 + } 287 + } 288 + 289 + return 0; 290 + } 291 + 292 + void tegra_clk_init_from_table(struct tegra_clk_init_table *table) 293 + { 294 + for (; table->name; table++) 295 + tegra_clk_init_one_from_table(table); 296 + } 297 + EXPORT_SYMBOL(tegra_clk_init_from_table); 298 + 299 + void tegra_periph_reset_deassert(struct clk *c) 300 + { 301 + tegra2_periph_reset_deassert(c); 302 + } 303 + EXPORT_SYMBOL(tegra_periph_reset_deassert); 304 + 305 + void tegra_periph_reset_assert(struct clk *c) 306 + { 307 + tegra2_periph_reset_assert(c); 308 + } 309 + EXPORT_SYMBOL(tegra_periph_reset_assert); 310 + 311 + int __init tegra_init_clock(void) 312 + { 313 + tegra2_init_clocks(); 314 + 315 + return 0; 316 + } 317 + 318 + #ifdef CONFIG_DEBUG_FS 319 + static struct dentry *clk_debugfs_root; 320 + 321 + 322 + static void clock_tree_show_one(struct seq_file *s, struct clk *c, int level) 323 + { 324 + struct clk *child; 325 + struct clk *safe; 326 + const char *state = "uninit"; 327 + char div[5] = {0}; 328 + 329 + if (c->state == ON) 330 + state = "on"; 331 + else if (c->state == OFF) 332 + state = "off"; 333 + 334 + if (c->mul != 0 && c->div != 0) { 335 + BUG_ON(c->mul > 2); 336 + if (c->mul > c->div) 337 + snprintf(div, sizeof(div), "x%d", c->mul / c->div); 338 + else 339 + snprintf(div, sizeof(div), "%d%s", c->div / c->mul, 340 + (c->div % c->mul) ? ".5" : ""); 341 + } 342 + 343 + seq_printf(s, "%*s%-*s %-6s %-3d %-5s %-10lu\n", 344 + level * 3 + 1, c->set ? "" : "*", 345 + 30 - level * 3, c->name, 346 + state, c->refcnt, div, c->rate); 347 + list_for_each_entry_safe(child, safe, &c->children, sibling) { 348 + clock_tree_show_one(s, child, level + 1); 349 + } 350 + } 351 + 352 + static int clock_tree_show(struct seq_file *s, void *data) 353 + { 354 + struct clk *c; 355 + unsigned long flags; 356 + seq_printf(s, " clock state ref div rate \n"); 357 + seq_printf(s, "-----------------------------------------------------------\n"); 358 + spin_lock_irqsave(&clock_lock, flags); 359 + list_for_each_entry(c, &clocks, node) 360 + if (c->parent == NULL) 361 + clock_tree_show_one(s, c, 0); 362 + spin_unlock_irqrestore(&clock_lock, flags); 363 + return 0; 364 + } 365 + 366 + static int clock_tree_open(struct inode *inode, struct file *file) 367 + { 368 + return single_open(file, clock_tree_show, inode->i_private); 369 + } 370 + 371 + static const struct file_operations clock_tree_fops = { 372 + .open = clock_tree_open, 373 + .read = seq_read, 374 + .llseek = seq_lseek, 375 + .release = single_release, 376 + }; 377 + 378 + static int possible_parents_show(struct seq_file *s, void *data) 379 + { 380 + struct clk *c = s->private; 381 + int i; 382 + 383 + for (i = 0; c->inputs[i].input; i++) { 384 + char *first = (i == 0) ? "" : " "; 385 + seq_printf(s, "%s%s", first, c->inputs[i].input->name); 386 + } 387 + seq_printf(s, "\n"); 388 + return 0; 389 + } 390 + 391 + static int possible_parents_open(struct inode *inode, struct file *file) 392 + { 393 + return single_open(file, possible_parents_show, inode->i_private); 394 + } 395 + 396 + static const struct file_operations possible_parents_fops = { 397 + .open = possible_parents_open, 398 + .read = seq_read, 399 + .llseek = seq_lseek, 400 + .release = single_release, 401 + }; 402 + 403 + static int clk_debugfs_register_one(struct clk *c) 404 + { 405 + struct dentry *d, *child, *child_tmp; 406 + 407 + d = debugfs_create_dir(c->name, clk_debugfs_root); 408 + if (!d) 409 + return -ENOMEM; 410 + c->dent = d; 411 + 412 + d = debugfs_create_u8("refcnt", S_IRUGO, c->dent, (u8 *)&c->refcnt); 413 + if (!d) 414 + goto err_out; 415 + 416 + d = debugfs_create_u32("rate", S_IRUGO, c->dent, (u32 *)&c->rate); 417 + if (!d) 418 + goto err_out; 419 + 420 + d = debugfs_create_x32("flags", S_IRUGO, c->dent, (u32 *)&c->flags); 421 + if (!d) 422 + goto err_out; 423 + 424 + if (c->inputs) { 425 + d = debugfs_create_file("possible_parents", S_IRUGO, c->dent, 426 + c, &possible_parents_fops); 427 + if (!d) 428 + goto err_out; 429 + } 430 + 431 + return 0; 432 + 433 + err_out: 434 + d = c->dent; 435 + list_for_each_entry_safe(child, child_tmp, &d->d_subdirs, d_u.d_child) 436 + debugfs_remove(child); 437 + debugfs_remove(c->dent); 438 + return -ENOMEM; 439 + } 440 + 441 + static int clk_debugfs_register(struct clk *c) 442 + { 443 + int err; 444 + struct clk *pa = c->parent; 445 + 446 + if (pa && !pa->dent) { 447 + err = clk_debugfs_register(pa); 448 + if (err) 449 + return err; 450 + } 451 + 452 + if (!c->dent) { 453 + err = clk_debugfs_register_one(c); 454 + if (err) 455 + return err; 456 + } 457 + return 0; 458 + } 459 + 460 + static int __init clk_debugfs_init(void) 461 + { 462 + struct clk *c; 463 + struct dentry *d; 464 + int err = -ENOMEM; 465 + 466 + d = debugfs_create_dir("clock", NULL); 467 + if (!d) 468 + return -ENOMEM; 469 + clk_debugfs_root = d; 470 + 471 + d = debugfs_create_file("clock_tree", S_IRUGO, clk_debugfs_root, NULL, 472 + &clock_tree_fops); 473 + if (!d) 474 + goto err_out; 475 + 476 + list_for_each_entry(c, &clocks, node) { 477 + err = clk_debugfs_register(c); 478 + if (err) 479 + goto err_out; 480 + } 481 + return 0; 482 + err_out: 483 + debugfs_remove_recursive(clk_debugfs_root); 484 + return err; 485 + } 486 + 487 + late_initcall(clk_debugfs_init); 488 + #endif
+147
arch/arm/mach-tegra/clock.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/clock.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #ifndef __MACH_TEGRA_CLOCK_H 21 + #define __MACH_TEGRA_CLOCK_H 22 + 23 + #include <linux/list.h> 24 + #include <asm/clkdev.h> 25 + 26 + #define DIV_BUS (1 << 0) 27 + #define DIV_U71 (1 << 1) 28 + #define DIV_U71_FIXED (1 << 2) 29 + #define DIV_2 (1 << 3) 30 + #define PLL_FIXED (1 << 4) 31 + #define PLL_HAS_CPCON (1 << 5) 32 + #define MUX (1 << 6) 33 + #define PLLD (1 << 7) 34 + #define PERIPH_NO_RESET (1 << 8) 35 + #define PERIPH_NO_ENB (1 << 9) 36 + #define PERIPH_EMC_ENB (1 << 10) 37 + #define PERIPH_MANUAL_RESET (1 << 11) 38 + #define PLL_ALT_MISC_REG (1 << 12) 39 + #define ENABLE_ON_INIT (1 << 28) 40 + 41 + struct clk; 42 + 43 + struct clk_mux_sel { 44 + struct clk *input; 45 + u32 value; 46 + }; 47 + 48 + struct clk_pll_table { 49 + unsigned long input_rate; 50 + unsigned long output_rate; 51 + u16 n; 52 + u16 m; 53 + u8 p; 54 + u8 cpcon; 55 + }; 56 + 57 + struct clk_ops { 58 + void (*init)(struct clk *); 59 + int (*enable)(struct clk *); 60 + void (*disable)(struct clk *); 61 + void (*recalc)(struct clk *); 62 + int (*set_parent)(struct clk *, struct clk *); 63 + int (*set_rate)(struct clk *, unsigned long); 64 + unsigned long (*get_rate)(struct clk *); 65 + long (*round_rate)(struct clk *, unsigned long); 66 + unsigned long (*recalculate_rate)(struct clk *); 67 + }; 68 + 69 + enum clk_state { 70 + UNINITIALIZED = 0, 71 + ON, 72 + OFF, 73 + }; 74 + 75 + struct clk { 76 + /* node for master clocks list */ 77 + struct list_head node; 78 + struct list_head children; /* list of children */ 79 + struct list_head sibling; /* node for children */ 80 + #ifdef CONFIG_DEBUG_FS 81 + struct dentry *dent; 82 + struct dentry *parent_dent; 83 + #endif 84 + struct clk_ops *ops; 85 + struct clk *parent; 86 + struct clk_lookup lookup; 87 + unsigned long rate; 88 + u32 flags; 89 + u32 refcnt; 90 + const char *name; 91 + u32 reg; 92 + u32 reg_shift; 93 + unsigned int clk_num; 94 + enum clk_state state; 95 + #ifdef CONFIG_DEBUG_FS 96 + bool set; 97 + #endif 98 + 99 + /* PLL */ 100 + unsigned long input_min; 101 + unsigned long input_max; 102 + unsigned long cf_min; 103 + unsigned long cf_max; 104 + unsigned long vco_min; 105 + unsigned long vco_max; 106 + u32 m; 107 + u32 n; 108 + u32 p; 109 + u32 cpcon; 110 + const struct clk_pll_table *pll_table; 111 + 112 + /* DIV */ 113 + u32 div; 114 + u32 mul; 115 + 116 + /* MUX */ 117 + const struct clk_mux_sel *inputs; 118 + u32 sel; 119 + u32 reg_mask; 120 + }; 121 + 122 + 123 + struct clk_duplicate { 124 + const char *name; 125 + struct clk_lookup lookup; 126 + }; 127 + 128 + struct tegra_clk_init_table { 129 + const char *name; 130 + const char *parent; 131 + unsigned long rate; 132 + bool enabled; 133 + }; 134 + 135 + void tegra2_init_clocks(void); 136 + void tegra2_periph_reset_deassert(struct clk *c); 137 + void tegra2_periph_reset_assert(struct clk *c); 138 + void clk_init(struct clk *clk); 139 + struct clk *tegra_get_clock_by_name(const char *name); 140 + unsigned long clk_measure_input_freq(void); 141 + void clk_disable_locked(struct clk *c); 142 + int clk_enable_locked(struct clk *c); 143 + int clk_set_parent_locked(struct clk *c, struct clk *parent); 144 + int clk_reparent(struct clk *c, struct clk *parent); 145 + void tegra_clk_init_from_table(struct tegra_clk_init_table *table); 146 + 147 + #endif
+61
arch/arm/mach-tegra/common.c
··· 1 + /* 2 + * arch/arm/mach-tegra/board-harmony.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@android.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #include <linux/init.h> 21 + #include <linux/io.h> 22 + 23 + #include <asm/hardware/cache-l2x0.h> 24 + 25 + #include <mach/iomap.h> 26 + 27 + #include "board.h" 28 + #include "clock.h" 29 + 30 + static __initdata struct tegra_clk_init_table common_clk_init_table[] = { 31 + /* name parent rate enabled */ 32 + { "clk_m", NULL, 0, true }, 33 + { "pll_p", "clk_m", 216000000, true }, 34 + { "pll_p_out1", "pll_p", 28800000, true }, 35 + { "pll_p_out2", "pll_p", 48000000, true }, 36 + { "pll_p_out3", "pll_p", 72000000, true }, 37 + { "pll_p_out4", "pll_p", 108000000, true }, 38 + { "sys", "pll_p_out4", 108000000, true }, 39 + { "hclk", "sys", 108000000, true }, 40 + { "pclk", "hclk", 54000000, true }, 41 + { NULL, NULL, 0, 0}, 42 + }; 43 + 44 + void __init tegra_init_cache(void) 45 + { 46 + #ifdef CONFIG_CACHE_L2X0 47 + void __iomem *p = IO_ADDRESS(TEGRA_ARM_PERIF_BASE) + 0x3000; 48 + 49 + writel(0x331, p + L2X0_TAG_LATENCY_CTRL); 50 + writel(0x441, p + L2X0_DATA_LATENCY_CTRL); 51 + 52 + l2x0_init(p, 0x6C080001, 0x8200c3fe); 53 + #endif 54 + } 55 + 56 + void __init tegra_common_init(void) 57 + { 58 + tegra_init_clock(); 59 + tegra_clk_init_from_table(common_clk_init_table); 60 + tegra_init_cache(); 61 + }
+247
arch/arm/mach-tegra/gpio-names.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/gpio-names.h 3 + * 4 + * Copyright (c) 2010 Google, Inc 5 + * 6 + * Author: 7 + * Erik Gilling <konkers@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + */ 18 + 19 + #ifndef __MACH_TEGRA_GPIO_NAMES_H 20 + #define __MACH_TEGRA_GPIO_NAMES_H 21 + 22 + #define TEGRA_GPIO_PA0 0 23 + #define TEGRA_GPIO_PA1 1 24 + #define TEGRA_GPIO_PA2 2 25 + #define TEGRA_GPIO_PA3 3 26 + #define TEGRA_GPIO_PA4 4 27 + #define TEGRA_GPIO_PA5 5 28 + #define TEGRA_GPIO_PA6 6 29 + #define TEGRA_GPIO_PA7 7 30 + #define TEGRA_GPIO_PB0 8 31 + #define TEGRA_GPIO_PB1 9 32 + #define TEGRA_GPIO_PB2 10 33 + #define TEGRA_GPIO_PB3 11 34 + #define TEGRA_GPIO_PB4 12 35 + #define TEGRA_GPIO_PB5 13 36 + #define TEGRA_GPIO_PB6 14 37 + #define TEGRA_GPIO_PB7 15 38 + #define TEGRA_GPIO_PC0 16 39 + #define TEGRA_GPIO_PC1 17 40 + #define TEGRA_GPIO_PC2 18 41 + #define TEGRA_GPIO_PC3 19 42 + #define TEGRA_GPIO_PC4 20 43 + #define TEGRA_GPIO_PC5 21 44 + #define TEGRA_GPIO_PC6 22 45 + #define TEGRA_GPIO_PC7 23 46 + #define TEGRA_GPIO_PD0 24 47 + #define TEGRA_GPIO_PD1 25 48 + #define TEGRA_GPIO_PD2 26 49 + #define TEGRA_GPIO_PD3 27 50 + #define TEGRA_GPIO_PD4 28 51 + #define TEGRA_GPIO_PD5 29 52 + #define TEGRA_GPIO_PD6 30 53 + #define TEGRA_GPIO_PD7 31 54 + #define TEGRA_GPIO_PE0 32 55 + #define TEGRA_GPIO_PE1 33 56 + #define TEGRA_GPIO_PE2 34 57 + #define TEGRA_GPIO_PE3 35 58 + #define TEGRA_GPIO_PE4 36 59 + #define TEGRA_GPIO_PE5 37 60 + #define TEGRA_GPIO_PE6 38 61 + #define TEGRA_GPIO_PE7 39 62 + #define TEGRA_GPIO_PF0 40 63 + #define TEGRA_GPIO_PF1 41 64 + #define TEGRA_GPIO_PF2 42 65 + #define TEGRA_GPIO_PF3 43 66 + #define TEGRA_GPIO_PF4 44 67 + #define TEGRA_GPIO_PF5 45 68 + #define TEGRA_GPIO_PF6 46 69 + #define TEGRA_GPIO_PF7 47 70 + #define TEGRA_GPIO_PG0 48 71 + #define TEGRA_GPIO_PG1 49 72 + #define TEGRA_GPIO_PG2 50 73 + #define TEGRA_GPIO_PG3 51 74 + #define TEGRA_GPIO_PG4 52 75 + #define TEGRA_GPIO_PG5 53 76 + #define TEGRA_GPIO_PG6 54 77 + #define TEGRA_GPIO_PG7 55 78 + #define TEGRA_GPIO_PH0 56 79 + #define TEGRA_GPIO_PH1 57 80 + #define TEGRA_GPIO_PH2 58 81 + #define TEGRA_GPIO_PH3 59 82 + #define TEGRA_GPIO_PH4 60 83 + #define TEGRA_GPIO_PH5 61 84 + #define TEGRA_GPIO_PH6 62 85 + #define TEGRA_GPIO_PH7 63 86 + #define TEGRA_GPIO_PI0 64 87 + #define TEGRA_GPIO_PI1 65 88 + #define TEGRA_GPIO_PI2 66 89 + #define TEGRA_GPIO_PI3 67 90 + #define TEGRA_GPIO_PI4 68 91 + #define TEGRA_GPIO_PI5 69 92 + #define TEGRA_GPIO_PI6 70 93 + #define TEGRA_GPIO_PI7 71 94 + #define TEGRA_GPIO_PJ0 72 95 + #define TEGRA_GPIO_PJ1 73 96 + #define TEGRA_GPIO_PJ2 74 97 + #define TEGRA_GPIO_PJ3 75 98 + #define TEGRA_GPIO_PJ4 76 99 + #define TEGRA_GPIO_PJ5 77 100 + #define TEGRA_GPIO_PJ6 78 101 + #define TEGRA_GPIO_PJ7 79 102 + #define TEGRA_GPIO_PK0 80 103 + #define TEGRA_GPIO_PK1 81 104 + #define TEGRA_GPIO_PK2 82 105 + #define TEGRA_GPIO_PK3 83 106 + #define TEGRA_GPIO_PK4 84 107 + #define TEGRA_GPIO_PK5 85 108 + #define TEGRA_GPIO_PK6 86 109 + #define TEGRA_GPIO_PK7 87 110 + #define TEGRA_GPIO_PL0 88 111 + #define TEGRA_GPIO_PL1 89 112 + #define TEGRA_GPIO_PL2 90 113 + #define TEGRA_GPIO_PL3 91 114 + #define TEGRA_GPIO_PL4 92 115 + #define TEGRA_GPIO_PL5 93 116 + #define TEGRA_GPIO_PL6 94 117 + #define TEGRA_GPIO_PL7 95 118 + #define TEGRA_GPIO_PM0 96 119 + #define TEGRA_GPIO_PM1 97 120 + #define TEGRA_GPIO_PM2 98 121 + #define TEGRA_GPIO_PM3 99 122 + #define TEGRA_GPIO_PM4 100 123 + #define TEGRA_GPIO_PM5 101 124 + #define TEGRA_GPIO_PM6 102 125 + #define TEGRA_GPIO_PM7 103 126 + #define TEGRA_GPIO_PN0 104 127 + #define TEGRA_GPIO_PN1 105 128 + #define TEGRA_GPIO_PN2 106 129 + #define TEGRA_GPIO_PN3 107 130 + #define TEGRA_GPIO_PN4 108 131 + #define TEGRA_GPIO_PN5 109 132 + #define TEGRA_GPIO_PN6 110 133 + #define TEGRA_GPIO_PN7 111 134 + #define TEGRA_GPIO_PO0 112 135 + #define TEGRA_GPIO_PO1 113 136 + #define TEGRA_GPIO_PO2 114 137 + #define TEGRA_GPIO_PO3 115 138 + #define TEGRA_GPIO_PO4 116 139 + #define TEGRA_GPIO_PO5 117 140 + #define TEGRA_GPIO_PO6 118 141 + #define TEGRA_GPIO_PO7 119 142 + #define TEGRA_GPIO_PP0 120 143 + #define TEGRA_GPIO_PP1 121 144 + #define TEGRA_GPIO_PP2 122 145 + #define TEGRA_GPIO_PP3 123 146 + #define TEGRA_GPIO_PP4 124 147 + #define TEGRA_GPIO_PP5 125 148 + #define TEGRA_GPIO_PP6 126 149 + #define TEGRA_GPIO_PP7 127 150 + #define TEGRA_GPIO_PQ0 128 151 + #define TEGRA_GPIO_PQ1 129 152 + #define TEGRA_GPIO_PQ2 130 153 + #define TEGRA_GPIO_PQ3 131 154 + #define TEGRA_GPIO_PQ4 132 155 + #define TEGRA_GPIO_PQ5 133 156 + #define TEGRA_GPIO_PQ6 134 157 + #define TEGRA_GPIO_PQ7 135 158 + #define TEGRA_GPIO_PR0 136 159 + #define TEGRA_GPIO_PR1 137 160 + #define TEGRA_GPIO_PR2 138 161 + #define TEGRA_GPIO_PR3 139 162 + #define TEGRA_GPIO_PR4 140 163 + #define TEGRA_GPIO_PR5 141 164 + #define TEGRA_GPIO_PR6 142 165 + #define TEGRA_GPIO_PR7 143 166 + #define TEGRA_GPIO_PS0 144 167 + #define TEGRA_GPIO_PS1 145 168 + #define TEGRA_GPIO_PS2 146 169 + #define TEGRA_GPIO_PS3 147 170 + #define TEGRA_GPIO_PS4 148 171 + #define TEGRA_GPIO_PS5 149 172 + #define TEGRA_GPIO_PS6 150 173 + #define TEGRA_GPIO_PS7 151 174 + #define TEGRA_GPIO_PT0 152 175 + #define TEGRA_GPIO_PT1 153 176 + #define TEGRA_GPIO_PT2 154 177 + #define TEGRA_GPIO_PT3 155 178 + #define TEGRA_GPIO_PT4 156 179 + #define TEGRA_GPIO_PT5 157 180 + #define TEGRA_GPIO_PT6 158 181 + #define TEGRA_GPIO_PT7 159 182 + #define TEGRA_GPIO_PU0 160 183 + #define TEGRA_GPIO_PU1 161 184 + #define TEGRA_GPIO_PU2 162 185 + #define TEGRA_GPIO_PU3 163 186 + #define TEGRA_GPIO_PU4 164 187 + #define TEGRA_GPIO_PU5 165 188 + #define TEGRA_GPIO_PU6 166 189 + #define TEGRA_GPIO_PU7 167 190 + #define TEGRA_GPIO_PV0 168 191 + #define TEGRA_GPIO_PV1 169 192 + #define TEGRA_GPIO_PV2 170 193 + #define TEGRA_GPIO_PV3 171 194 + #define TEGRA_GPIO_PV4 172 195 + #define TEGRA_GPIO_PV5 173 196 + #define TEGRA_GPIO_PV6 174 197 + #define TEGRA_GPIO_PV7 175 198 + #define TEGRA_GPIO_PW0 176 199 + #define TEGRA_GPIO_PW1 177 200 + #define TEGRA_GPIO_PW2 178 201 + #define TEGRA_GPIO_PW3 179 202 + #define TEGRA_GPIO_PW4 180 203 + #define TEGRA_GPIO_PW5 181 204 + #define TEGRA_GPIO_PW6 182 205 + #define TEGRA_GPIO_PW7 183 206 + #define TEGRA_GPIO_PX0 184 207 + #define TEGRA_GPIO_PX1 185 208 + #define TEGRA_GPIO_PX2 186 209 + #define TEGRA_GPIO_PX3 187 210 + #define TEGRA_GPIO_PX4 188 211 + #define TEGRA_GPIO_PX5 189 212 + #define TEGRA_GPIO_PX6 190 213 + #define TEGRA_GPIO_PX7 191 214 + #define TEGRA_GPIO_PY0 192 215 + #define TEGRA_GPIO_PY1 193 216 + #define TEGRA_GPIO_PY2 194 217 + #define TEGRA_GPIO_PY3 195 218 + #define TEGRA_GPIO_PY4 196 219 + #define TEGRA_GPIO_PY5 197 220 + #define TEGRA_GPIO_PY6 198 221 + #define TEGRA_GPIO_PY7 199 222 + #define TEGRA_GPIO_PZ0 200 223 + #define TEGRA_GPIO_PZ1 201 224 + #define TEGRA_GPIO_PZ2 202 225 + #define TEGRA_GPIO_PZ3 203 226 + #define TEGRA_GPIO_PZ4 204 227 + #define TEGRA_GPIO_PZ5 205 228 + #define TEGRA_GPIO_PZ6 206 229 + #define TEGRA_GPIO_PZ7 207 230 + #define TEGRA_GPIO_PAA0 208 231 + #define TEGRA_GPIO_PAA1 209 232 + #define TEGRA_GPIO_PAA2 210 233 + #define TEGRA_GPIO_PAA3 211 234 + #define TEGRA_GPIO_PAA4 212 235 + #define TEGRA_GPIO_PAA5 213 236 + #define TEGRA_GPIO_PAA6 214 237 + #define TEGRA_GPIO_PAA7 215 238 + #define TEGRA_GPIO_PBB0 216 239 + #define TEGRA_GPIO_PBB1 217 240 + #define TEGRA_GPIO_PBB2 218 241 + #define TEGRA_GPIO_PBB3 219 242 + #define TEGRA_GPIO_PBB4 220 243 + #define TEGRA_GPIO_PBB5 221 244 + #define TEGRA_GPIO_PBB6 222 245 + #define TEGRA_GPIO_PBB7 223 246 + 247 + #endif
+348
arch/arm/mach-tegra/gpio.c
··· 1 + /* 2 + * arch/arm/mach-tegra/gpio.c 3 + * 4 + * Copyright (c) 2010 Google, Inc 5 + * 6 + * Author: 7 + * Erik Gilling <konkers@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #include <linux/init.h> 21 + #include <linux/irq.h> 22 + 23 + #include <linux/io.h> 24 + #include <linux/gpio.h> 25 + 26 + #include <mach/iomap.h> 27 + 28 + #define GPIO_BANK(x) ((x) >> 5) 29 + #define GPIO_PORT(x) (((x) >> 3) & 0x3) 30 + #define GPIO_BIT(x) ((x) & 0x7) 31 + 32 + #define GPIO_REG(x) (IO_TO_VIRT(TEGRA_GPIO_BASE) + \ 33 + GPIO_BANK(x) * 0x80 + \ 34 + GPIO_PORT(x) * 4) 35 + 36 + #define GPIO_CNF(x) (GPIO_REG(x) + 0x00) 37 + #define GPIO_OE(x) (GPIO_REG(x) + 0x10) 38 + #define GPIO_OUT(x) (GPIO_REG(x) + 0X20) 39 + #define GPIO_IN(x) (GPIO_REG(x) + 0x30) 40 + #define GPIO_INT_STA(x) (GPIO_REG(x) + 0x40) 41 + #define GPIO_INT_ENB(x) (GPIO_REG(x) + 0x50) 42 + #define GPIO_INT_LVL(x) (GPIO_REG(x) + 0x60) 43 + #define GPIO_INT_CLR(x) (GPIO_REG(x) + 0x70) 44 + 45 + #define GPIO_MSK_CNF(x) (GPIO_REG(x) + 0x800) 46 + #define GPIO_MSK_OE(x) (GPIO_REG(x) + 0x810) 47 + #define GPIO_MSK_OUT(x) (GPIO_REG(x) + 0X820) 48 + #define GPIO_MSK_INT_STA(x) (GPIO_REG(x) + 0x840) 49 + #define GPIO_MSK_INT_ENB(x) (GPIO_REG(x) + 0x850) 50 + #define GPIO_MSK_INT_LVL(x) (GPIO_REG(x) + 0x860) 51 + 52 + #define GPIO_INT_LVL_MASK 0x010101 53 + #define GPIO_INT_LVL_EDGE_RISING 0x000101 54 + #define GPIO_INT_LVL_EDGE_FALLING 0x000100 55 + #define GPIO_INT_LVL_EDGE_BOTH 0x010100 56 + #define GPIO_INT_LVL_LEVEL_HIGH 0x000001 57 + #define GPIO_INT_LVL_LEVEL_LOW 0x000000 58 + 59 + struct tegra_gpio_bank { 60 + int bank; 61 + int irq; 62 + spinlock_t lvl_lock[4]; 63 + }; 64 + 65 + 66 + static struct tegra_gpio_bank tegra_gpio_banks[] = { 67 + {.bank = 0, .irq = INT_GPIO1}, 68 + {.bank = 1, .irq = INT_GPIO2}, 69 + {.bank = 2, .irq = INT_GPIO3}, 70 + {.bank = 3, .irq = INT_GPIO4}, 71 + {.bank = 4, .irq = INT_GPIO5}, 72 + {.bank = 5, .irq = INT_GPIO6}, 73 + {.bank = 6, .irq = INT_GPIO7}, 74 + }; 75 + 76 + static int tegra_gpio_compose(int bank, int port, int bit) 77 + { 78 + return (bank << 5) | ((port & 0x3) << 3) | (bit & 0x7); 79 + } 80 + 81 + static void tegra_gpio_mask_write(u32 reg, int gpio, int value) 82 + { 83 + u32 val; 84 + 85 + val = 0x100 << GPIO_BIT(gpio); 86 + if (value) 87 + val |= 1 << GPIO_BIT(gpio); 88 + __raw_writel(val, reg); 89 + } 90 + 91 + void tegra_gpio_enable(int gpio) 92 + { 93 + tegra_gpio_mask_write(GPIO_MSK_CNF(gpio), gpio, 1); 94 + } 95 + 96 + void tegra_gpio_disable(int gpio) 97 + { 98 + tegra_gpio_mask_write(GPIO_MSK_CNF(gpio), gpio, 0); 99 + } 100 + 101 + static void tegra_gpio_set(struct gpio_chip *chip, unsigned offset, int value) 102 + { 103 + tegra_gpio_mask_write(GPIO_MSK_OUT(offset), offset, value); 104 + } 105 + 106 + static int tegra_gpio_get(struct gpio_chip *chip, unsigned offset) 107 + { 108 + return (__raw_readl(GPIO_IN(offset)) >> GPIO_BIT(offset)) & 0x1; 109 + } 110 + 111 + static int tegra_gpio_direction_input(struct gpio_chip *chip, unsigned offset) 112 + { 113 + tegra_gpio_mask_write(GPIO_MSK_OE(offset), offset, 0); 114 + return 0; 115 + } 116 + 117 + static int tegra_gpio_direction_output(struct gpio_chip *chip, unsigned offset, 118 + int value) 119 + { 120 + tegra_gpio_set(chip, offset, value); 121 + tegra_gpio_mask_write(GPIO_MSK_OE(offset), offset, 1); 122 + return 0; 123 + } 124 + 125 + 126 + 127 + static struct gpio_chip tegra_gpio_chip = { 128 + .label = "tegra-gpio", 129 + .direction_input = tegra_gpio_direction_input, 130 + .get = tegra_gpio_get, 131 + .direction_output = tegra_gpio_direction_output, 132 + .set = tegra_gpio_set, 133 + .base = 0, 134 + .ngpio = ARCH_NR_GPIOS, 135 + }; 136 + 137 + static void tegra_gpio_irq_ack(unsigned int irq) 138 + { 139 + int gpio = irq - INT_GPIO_BASE; 140 + 141 + __raw_writel(1 << GPIO_BIT(gpio), GPIO_INT_CLR(gpio)); 142 + } 143 + 144 + static void tegra_gpio_irq_mask(unsigned int irq) 145 + { 146 + int gpio = irq - INT_GPIO_BASE; 147 + 148 + tegra_gpio_mask_write(GPIO_MSK_INT_ENB(gpio), gpio, 0); 149 + } 150 + 151 + static void tegra_gpio_irq_unmask(unsigned int irq) 152 + { 153 + int gpio = irq - INT_GPIO_BASE; 154 + 155 + tegra_gpio_mask_write(GPIO_MSK_INT_ENB(gpio), gpio, 1); 156 + } 157 + 158 + static int tegra_gpio_irq_set_type(unsigned int irq, unsigned int type) 159 + { 160 + int gpio = irq - INT_GPIO_BASE; 161 + struct tegra_gpio_bank *bank = get_irq_chip_data(irq); 162 + int port = GPIO_PORT(gpio); 163 + int lvl_type; 164 + int val; 165 + unsigned long flags; 166 + 167 + switch (type & IRQ_TYPE_SENSE_MASK) { 168 + case IRQ_TYPE_EDGE_RISING: 169 + lvl_type = GPIO_INT_LVL_EDGE_RISING; 170 + break; 171 + 172 + case IRQ_TYPE_EDGE_FALLING: 173 + lvl_type = GPIO_INT_LVL_EDGE_FALLING; 174 + break; 175 + 176 + case IRQ_TYPE_EDGE_BOTH: 177 + lvl_type = GPIO_INT_LVL_EDGE_BOTH; 178 + break; 179 + 180 + case IRQ_TYPE_LEVEL_HIGH: 181 + lvl_type = GPIO_INT_LVL_LEVEL_HIGH; 182 + break; 183 + 184 + case IRQ_TYPE_LEVEL_LOW: 185 + lvl_type = GPIO_INT_LVL_LEVEL_LOW; 186 + break; 187 + 188 + default: 189 + return -EINVAL; 190 + } 191 + 192 + spin_lock_irqsave(&bank->lvl_lock[port], flags); 193 + 194 + val = __raw_readl(GPIO_INT_LVL(gpio)); 195 + val &= ~(GPIO_INT_LVL_MASK << GPIO_BIT(gpio)); 196 + val |= lvl_type << GPIO_BIT(gpio); 197 + __raw_writel(val, GPIO_INT_LVL(gpio)); 198 + 199 + spin_unlock_irqrestore(&bank->lvl_lock[port], flags); 200 + 201 + if (type & (IRQ_TYPE_LEVEL_LOW | IRQ_TYPE_LEVEL_HIGH)) 202 + __set_irq_handler_unlocked(irq, handle_level_irq); 203 + else if (type & (IRQ_TYPE_EDGE_FALLING | IRQ_TYPE_EDGE_RISING)) 204 + __set_irq_handler_unlocked(irq, handle_edge_irq); 205 + 206 + return 0; 207 + } 208 + 209 + static void tegra_gpio_irq_handler(unsigned int irq, struct irq_desc *desc) 210 + { 211 + struct tegra_gpio_bank *bank; 212 + int port; 213 + int pin; 214 + int unmasked = 0; 215 + 216 + desc->chip->ack(irq); 217 + 218 + bank = get_irq_data(irq); 219 + 220 + for (port = 0; port < 4; port++) { 221 + int gpio = tegra_gpio_compose(bank->bank, port, 0); 222 + unsigned long sta = __raw_readl(GPIO_INT_STA(gpio)) & 223 + __raw_readl(GPIO_INT_ENB(gpio)); 224 + u32 lvl = __raw_readl(GPIO_INT_LVL(gpio)); 225 + 226 + for_each_set_bit(pin, &sta, 8) { 227 + __raw_writel(1 << pin, GPIO_INT_CLR(gpio)); 228 + 229 + /* if gpio is edge triggered, clear condition 230 + * before executing the hander so that we don't 231 + * miss edges 232 + */ 233 + if (lvl & (0x100 << pin)) { 234 + unmasked = 1; 235 + desc->chip->unmask(irq); 236 + } 237 + 238 + generic_handle_irq(gpio_to_irq(gpio + pin)); 239 + } 240 + } 241 + 242 + if (!unmasked) 243 + desc->chip->unmask(irq); 244 + 245 + } 246 + 247 + 248 + static struct irq_chip tegra_gpio_irq_chip = { 249 + .name = "GPIO", 250 + .ack = tegra_gpio_irq_ack, 251 + .mask = tegra_gpio_irq_mask, 252 + .unmask = tegra_gpio_irq_unmask, 253 + .set_type = tegra_gpio_irq_set_type, 254 + }; 255 + 256 + 257 + /* This lock class tells lockdep that GPIO irqs are in a different 258 + * category than their parents, so it won't report false recursion. 259 + */ 260 + static struct lock_class_key gpio_lock_class; 261 + 262 + static int __init tegra_gpio_init(void) 263 + { 264 + struct tegra_gpio_bank *bank; 265 + int i; 266 + int j; 267 + 268 + for (i = 0; i < 7; i++) { 269 + for (j = 0; j < 4; j++) { 270 + int gpio = tegra_gpio_compose(i, j, 0); 271 + __raw_writel(0x00, GPIO_INT_ENB(gpio)); 272 + } 273 + } 274 + 275 + gpiochip_add(&tegra_gpio_chip); 276 + 277 + for (i = INT_GPIO_BASE; i < (INT_GPIO_BASE + ARCH_NR_GPIOS); i++) { 278 + bank = &tegra_gpio_banks[GPIO_BANK(irq_to_gpio(i))]; 279 + 280 + lockdep_set_class(&irq_desc[i].lock, &gpio_lock_class); 281 + set_irq_chip_data(i, bank); 282 + set_irq_chip(i, &tegra_gpio_irq_chip); 283 + set_irq_handler(i, handle_simple_irq); 284 + set_irq_flags(i, IRQF_VALID); 285 + } 286 + 287 + for (i = 0; i < ARRAY_SIZE(tegra_gpio_banks); i++) { 288 + bank = &tegra_gpio_banks[i]; 289 + 290 + set_irq_chained_handler(bank->irq, tegra_gpio_irq_handler); 291 + set_irq_data(bank->irq, bank); 292 + 293 + for (j = 0; j < 4; j++) 294 + spin_lock_init(&bank->lvl_lock[j]); 295 + } 296 + 297 + return 0; 298 + } 299 + 300 + postcore_initcall(tegra_gpio_init); 301 + 302 + #ifdef CONFIG_DEBUG_FS 303 + 304 + #include <linux/debugfs.h> 305 + #include <linux/seq_file.h> 306 + 307 + static int dbg_gpio_show(struct seq_file *s, void *unused) 308 + { 309 + int i; 310 + int j; 311 + 312 + for (i = 0; i < 7; i++) { 313 + for (j = 0; j < 4; j++) { 314 + int gpio = tegra_gpio_compose(i, j, 0); 315 + seq_printf(s, "%d:%d %02x %02x %02x %02x %02x %02x %06x\n", 316 + i, j, 317 + __raw_readl(GPIO_CNF(gpio)), 318 + __raw_readl(GPIO_OE(gpio)), 319 + __raw_readl(GPIO_OUT(gpio)), 320 + __raw_readl(GPIO_IN(gpio)), 321 + __raw_readl(GPIO_INT_STA(gpio)), 322 + __raw_readl(GPIO_INT_ENB(gpio)), 323 + __raw_readl(GPIO_INT_LVL(gpio))); 324 + } 325 + } 326 + return 0; 327 + } 328 + 329 + static int dbg_gpio_open(struct inode *inode, struct file *file) 330 + { 331 + return single_open(file, dbg_gpio_show, &inode->i_private); 332 + } 333 + 334 + static const struct file_operations debug_fops = { 335 + .open = dbg_gpio_open, 336 + .read = seq_read, 337 + .llseek = seq_lseek, 338 + .release = single_release, 339 + }; 340 + 341 + static int __init tegra_gpio_debuginit(void) 342 + { 343 + (void) debugfs_create_file("tegra_gpio", S_IRUGO, 344 + NULL, NULL, &debug_fops); 345 + return 0; 346 + } 347 + late_initcall(tegra_gpio_debuginit); 348 + #endif
+61
arch/arm/mach-tegra/headsmp.S
··· 1 + #include <linux/linkage.h> 2 + #include <linux/init.h> 3 + 4 + .section ".text.head", "ax" 5 + __CPUINIT 6 + 7 + /* 8 + * Tegra specific entry point for secondary CPUs. 9 + * The secondary kernel init calls v7_flush_dcache_all before it enables 10 + * the L1; however, the L1 comes out of reset in an undefined state, so 11 + * the clean + invalidate performed by v7_flush_dcache_all causes a bunch 12 + * of cache lines with uninitialized data and uninitialized tags to get 13 + * written out to memory, which does really unpleasant things to the main 14 + * processor. We fix this by performing an invalidate, rather than a 15 + * clean + invalidate, before jumping into the kernel. 16 + */ 17 + ENTRY(v7_invalidate_l1) 18 + mov r0, #0 19 + mcr p15, 2, r0, c0, c0, 0 20 + mrc p15, 1, r0, c0, c0, 0 21 + 22 + ldr r1, =0x7fff 23 + and r2, r1, r0, lsr #13 24 + 25 + ldr r1, =0x3ff 26 + 27 + and r3, r1, r0, lsr #3 @ NumWays - 1 28 + add r2, r2, #1 @ NumSets 29 + 30 + and r0, r0, #0x7 31 + add r0, r0, #4 @ SetShift 32 + 33 + clz r1, r3 @ WayShift 34 + add r4, r3, #1 @ NumWays 35 + 1: sub r2, r2, #1 @ NumSets-- 36 + mov r3, r4 @ Temp = NumWays 37 + 2: subs r3, r3, #1 @ Temp-- 38 + mov r5, r3, lsl r1 39 + mov r6, r2, lsl r0 40 + orr r5, r5, r6 @ Reg = (Temp<<WayShift)|(NumSets<<SetShift) 41 + mcr p15, 0, r5, c7, c6, 2 42 + bgt 2b 43 + cmp r2, #0 44 + bgt 1b 45 + dsb 46 + isb 47 + mov pc, lr 48 + ENDPROC(v7_invalidate_l1) 49 + 50 + ENTRY(tegra_secondary_startup) 51 + msr cpsr_fsxc, #0xd3 52 + bl v7_invalidate_l1 53 + mrc p15, 0, r0, c0, c0, 5 54 + and r0, r0, #15 55 + ldr r1, =0x6000f100 56 + str r0, [r1] 57 + 1: ldr r2, [r1] 58 + cmp r0, r2 59 + beq 1b 60 + b secondary_startup 61 + ENDPROC(tegra_secondary_startup)
+140
arch/arm/mach-tegra/hotplug.c
··· 1 + /* 2 + * linux/arch/arm/mach-realview/hotplug.c 3 + * 4 + * Copyright (C) 2002 ARM Ltd. 5 + * All Rights Reserved 6 + * 7 + * This program is free software; you can redistribute it and/or modify 8 + * it under the terms of the GNU General Public License version 2 as 9 + * published by the Free Software Foundation. 10 + */ 11 + #include <linux/kernel.h> 12 + #include <linux/errno.h> 13 + #include <linux/smp.h> 14 + #include <linux/completion.h> 15 + 16 + #include <asm/cacheflush.h> 17 + 18 + static DECLARE_COMPLETION(cpu_killed); 19 + 20 + static inline void cpu_enter_lowpower(void) 21 + { 22 + unsigned int v; 23 + 24 + flush_cache_all(); 25 + asm volatile( 26 + " mcr p15, 0, %1, c7, c5, 0\n" 27 + " mcr p15, 0, %1, c7, c10, 4\n" 28 + /* 29 + * Turn off coherency 30 + */ 31 + " mrc p15, 0, %0, c1, c0, 1\n" 32 + " bic %0, %0, #0x20\n" 33 + " mcr p15, 0, %0, c1, c0, 1\n" 34 + " mrc p15, 0, %0, c1, c0, 0\n" 35 + " bic %0, %0, #0x04\n" 36 + " mcr p15, 0, %0, c1, c0, 0\n" 37 + : "=&r" (v) 38 + : "r" (0) 39 + : "cc"); 40 + } 41 + 42 + static inline void cpu_leave_lowpower(void) 43 + { 44 + unsigned int v; 45 + 46 + asm volatile( 47 + "mrc p15, 0, %0, c1, c0, 0\n" 48 + " orr %0, %0, #0x04\n" 49 + " mcr p15, 0, %0, c1, c0, 0\n" 50 + " mrc p15, 0, %0, c1, c0, 1\n" 51 + " orr %0, %0, #0x20\n" 52 + " mcr p15, 0, %0, c1, c0, 1\n" 53 + : "=&r" (v) 54 + : 55 + : "cc"); 56 + } 57 + 58 + static inline void platform_do_lowpower(unsigned int cpu) 59 + { 60 + /* 61 + * there is no power-control hardware on this platform, so all 62 + * we can do is put the core into WFI; this is safe as the calling 63 + * code will have already disabled interrupts 64 + */ 65 + for (;;) { 66 + /* 67 + * here's the WFI 68 + */ 69 + asm(".word 0xe320f003\n" 70 + : 71 + : 72 + : "memory", "cc"); 73 + 74 + /*if (pen_release == cpu) {*/ 75 + /* 76 + * OK, proper wakeup, we're done 77 + */ 78 + break; 79 + /*}*/ 80 + 81 + /* 82 + * getting here, means that we have come out of WFI without 83 + * having been woken up - this shouldn't happen 84 + * 85 + * The trouble is, letting people know about this is not really 86 + * possible, since we are currently running incoherently, and 87 + * therefore cannot safely call printk() or anything else 88 + */ 89 + #ifdef DEBUG 90 + printk(KERN_WARN "CPU%u: spurious wakeup call\n", cpu); 91 + #endif 92 + } 93 + } 94 + 95 + int platform_cpu_kill(unsigned int cpu) 96 + { 97 + return wait_for_completion_timeout(&cpu_killed, 5000); 98 + } 99 + 100 + /* 101 + * platform-specific code to shutdown a CPU 102 + * 103 + * Called with IRQs disabled 104 + */ 105 + void platform_cpu_die(unsigned int cpu) 106 + { 107 + #ifdef DEBUG 108 + unsigned int this_cpu = hard_smp_processor_id(); 109 + 110 + if (cpu != this_cpu) { 111 + printk(KERN_CRIT "Eek! platform_cpu_die running on %u, should be %u\n", 112 + this_cpu, cpu); 113 + BUG(); 114 + } 115 + #endif 116 + 117 + printk(KERN_NOTICE "CPU%u: shutdown\n", cpu); 118 + complete(&cpu_killed); 119 + 120 + /* 121 + * we're ready for shutdown now, so do it 122 + */ 123 + cpu_enter_lowpower(); 124 + platform_do_lowpower(cpu); 125 + 126 + /* 127 + * bring this CPU back into the world of cache 128 + * coherency, and then restore interrupts 129 + */ 130 + cpu_leave_lowpower(); 131 + } 132 + 133 + int platform_cpu_disable(unsigned int cpu) 134 + { 135 + /* 136 + * we don't allow CPU 0 to be shutdown (it is still too special 137 + * e.g. clock tick interrupts) 138 + */ 139 + return cpu == 0 ? -EPERM : 0; 140 + }
+30
arch/arm/mach-tegra/include/mach/barriers.h
··· 1 + /* 2 + * arch/arm/mach-realview/include/mach/barriers.h 3 + * 4 + * Copyright (C) 2010 ARM Ltd. 5 + * Written by Catalin Marinas <catalin.marinas@arm.com> 6 + * 7 + * This program is free software; you can redistribute it and/or modify 8 + * it under the terms of the GNU General Public License version 2 as 9 + * published by the Free Software Foundation. 10 + * 11 + * This program is distributed in the hope that it will be useful, 12 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 + * GNU General Public License for more details. 15 + * 16 + * You should have received a copy of the GNU General Public License 17 + * along with this program; if not, write to the Free Software 18 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 19 + */ 20 + 21 + #ifndef __MACH_BARRIERS_H 22 + #define __MACH_BARRIERS_H 23 + 24 + #include <asm/outercache.h> 25 + 26 + #define rmb() dmb() 27 + #define wmb() do { dsb(); outer_sync(); } while (0) 28 + #define mb() wmb() 29 + 30 + #endif /* __MACH_BARRIERS_H */
+26
arch/arm/mach-tegra/include/mach/clk.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/clk.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Erik Gilling <konkers@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #ifndef __MACH_CLK_H 21 + #define __MACH_CLK_H 22 + 23 + void tegra_periph_reset_deassert(struct clk *c); 24 + void tegra_periph_reset_assert(struct clk *c); 25 + 26 + #endif
+32
arch/arm/mach-tegra/include/mach/clkdev.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/clkdev.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #ifndef __MACH_CLKDEV_H 21 + #define __MACH_CLKDEV_H 22 + 23 + static inline int __clk_get(struct clk *clk) 24 + { 25 + return 1; 26 + } 27 + 28 + static inline void __clk_put(struct clk *clk) 29 + { 30 + } 31 + 32 + #endif
+46
arch/arm/mach-tegra/include/mach/debug-macro.S
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/debug-macro.S 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #include <mach/io.h> 22 + 23 + .macro addruart,rx, tmp 24 + mrc p15, 0, \rx, c1, c0 25 + tst \rx, #1 @ MMU enabled? 26 + ldreq \rx, =IO_APB_PHYS @ physical 27 + ldrne \rx, =IO_APB_VIRT @ virtual 28 + #if defined(CONFIG_TEGRA_DEBUG_UART_NONE) 29 + #error "A debug UART must be selected in the kernel config to use DEBUG_LL" 30 + #elif defined(CONFIG_TEGRA_DEBUG_UARTA) 31 + orr \rx, \rx, #0x6000 32 + #elif defined(CONFIG_TEGRA_DEBUG_UARTB) 33 + ldr \tmp, =0x6040 34 + orr \rx, \rx, \tmp 35 + #elif defined(CONFIG_TEGRA_DEBUG_UARTC) 36 + orr \rx, \rx, #0x6200 37 + #elif defined(CONFIG_TEGRA_DEBUG_UARTD) 38 + orr \rx, \rx, #0x6300 39 + #elif defined(CONFIG_TEGRA_DEBUG_UARTE) 40 + orr \rx, \rx, #0x6400 41 + #endif 42 + .endm 43 + 44 + #define UART_SHIFT 2 45 + #include <asm/hardware/debug-8250.S> 46 +
+118
arch/arm/mach-tegra/include/mach/entry-macro.S
··· 1 + /* arch/arm/mach-tegra/include/mach/entry-macro.S 2 + * 3 + * Copyright (C) 2009 Palm, Inc. 4 + * 5 + * This software is licensed under the terms of the GNU General Public 6 + * License version 2, as published by the Free Software Foundation, and 7 + * may be copied, distributed, and modified under those terms. 8 + * 9 + * This program is distributed in the hope that it will be useful, 10 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 + * GNU General Public License for more details. 13 + * 14 + */ 15 + #include <mach/iomap.h> 16 + #include <mach/io.h> 17 + 18 + #if defined(CONFIG_ARM_GIC) 19 + 20 + #include <asm/hardware/gic.h> 21 + 22 + /* Uses the GIC interrupt controller built into the cpu */ 23 + #define ICTRL_BASE (IO_CPU_VIRT + 0x100) 24 + 25 + .macro disable_fiq 26 + .endm 27 + 28 + .macro get_irqnr_preamble, base, tmp 29 + movw \base, #(ICTRL_BASE & 0x0000ffff) 30 + movt \base, #((ICTRL_BASE & 0xffff0000) >> 16) 31 + .endm 32 + 33 + .macro arch_ret_to_user, tmp1, tmp2 34 + .endm 35 + 36 + /* 37 + * The interrupt numbering scheme is defined in the 38 + * interrupt controller spec. To wit: 39 + * 40 + * Interrupts 0-15 are IPI 41 + * 16-28 are reserved 42 + * 29-31 are local. We allow 30 to be used for the watchdog. 43 + * 32-1020 are global 44 + * 1021-1022 are reserved 45 + * 1023 is "spurious" (no interrupt) 46 + * 47 + * For now, we ignore all local interrupts so only return an interrupt 48 + * if it's between 30 and 1020. The test_for_ipi routine below will 49 + * pick up on IPIs. 50 + * 51 + * A simple read from the controller will tell us the number of the 52 + * highest priority enabled interrupt. We then just need to check 53 + * whether it is in the valid range for an IRQ (30-1020 inclusive). 54 + */ 55 + 56 + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp 57 + 58 + /* bits 12-10 = src CPU, 9-0 = int # */ 59 + ldr \irqstat, [\base, #GIC_CPU_INTACK] 60 + 61 + ldr \tmp, =1021 62 + 63 + bic \irqnr, \irqstat, #0x1c00 64 + 65 + cmp \irqnr, #29 66 + cmpcc \irqnr, \irqnr 67 + cmpne \irqnr, \tmp 68 + cmpcs \irqnr, \irqnr 69 + 70 + .endm 71 + 72 + /* We assume that irqstat (the raw value of the IRQ acknowledge 73 + * register) is preserved from the macro above. 74 + * If there is an IPI, we immediately signal end of interrupt on the 75 + * controller, since this requires the original irqstat value which 76 + * we won't easily be able to recreate later. 77 + */ 78 + 79 + .macro test_for_ipi, irqnr, irqstat, base, tmp 80 + bic \irqnr, \irqstat, #0x1c00 81 + cmp \irqnr, #16 82 + strcc \irqstat, [\base, #GIC_CPU_EOI] 83 + cmpcs \irqnr, \irqnr 84 + .endm 85 + 86 + /* As above, this assumes that irqstat and base are preserved.. */ 87 + 88 + .macro test_for_ltirq, irqnr, irqstat, base, tmp 89 + bic \irqnr, \irqstat, #0x1c00 90 + mov \tmp, #0 91 + cmp \irqnr, #29 92 + moveq \tmp, #1 93 + streq \irqstat, [\base, #GIC_CPU_EOI] 94 + cmp \tmp, #0 95 + .endm 96 + 97 + #else 98 + /* legacy interrupt controller for AP16 */ 99 + .macro disable_fiq 100 + .endm 101 + 102 + .macro get_irqnr_preamble, base, tmp 103 + @ enable imprecise aborts 104 + cpsie a 105 + @ EVP base at 0xf010f000 106 + mov \base, #0xf0000000 107 + orr \base, #0x00100000 108 + orr \base, #0x0000f000 109 + .endm 110 + 111 + .macro arch_ret_to_user, tmp1, tmp2 112 + .endm 113 + 114 + .macro get_irqnr_and_base, irqnr, irqstat, base, tmp 115 + ldr \irqnr, [\base, #0x20] @ EVT_IRQ_STS 116 + cmp \irqnr, #0x80 117 + .endm 118 + #endif
+53
arch/arm/mach-tegra/include/mach/gpio.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/gpio.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Erik Gilling <konkers@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #ifndef __MACH_TEGRA_GPIO_H 21 + #define __MACH_TEGRA_GPIO_H 22 + 23 + #include <mach/irqs.h> 24 + 25 + #define ARCH_NR_GPIOS INT_GPIO_NR 26 + 27 + #include <asm-generic/gpio.h> 28 + 29 + #define gpio_get_value __gpio_get_value 30 + #define gpio_set_value __gpio_set_value 31 + #define gpio_cansleep __gpio_cansleep 32 + 33 + #define TEGRA_GPIO_TO_IRQ(gpio) (INT_GPIO_BASE + (gpio)) 34 + #define TEGRA_IRQ_TO_GPIO(irq) ((gpio) - INT_GPIO_BASE) 35 + 36 + static inline int gpio_to_irq(unsigned int gpio) 37 + { 38 + if (gpio < ARCH_NR_GPIOS) 39 + return INT_GPIO_BASE + gpio; 40 + return -EINVAL; 41 + } 42 + 43 + static inline int irq_to_gpio(unsigned int irq) 44 + { 45 + if ((irq >= INT_GPIO_BASE) && (irq < INT_GPIO_BASE + INT_GPIO_NR)) 46 + return irq - INT_GPIO_BASE; 47 + return -EINVAL; 48 + } 49 + 50 + void tegra_gpio_enable(int gpio); 51 + void tegra_gpio_disable(int gpio); 52 + 53 + #endif
+24
arch/arm/mach-tegra/include/mach/hardware.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/hardware.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_HARDWARE_H 22 + #define __MACH_TEGRA_HARDWARE_H 23 + 24 + #endif
+79
arch/arm/mach-tegra/include/mach/io.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/io.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_IO_H 22 + #define __MACH_TEGRA_IO_H 23 + 24 + #define IO_SPACE_LIMIT 0xffffffff 25 + 26 + /* On TEGRA, many peripherals are very closely packed in 27 + * two 256MB io windows (that actually only use about 64KB 28 + * at the start of each). 29 + * 30 + * We will just map the first 1MB of each window (to minimize 31 + * pt entries needed) and provide a macro to transform physical 32 + * io addresses to an appropriate void __iomem *. 33 + * 34 + */ 35 + 36 + #define IO_CPU_PHYS 0x50040000 37 + #define IO_CPU_VIRT 0xFE000000 38 + #define IO_CPU_SIZE SZ_16K 39 + 40 + #define IO_PPSB_PHYS 0x60000000 41 + #define IO_PPSB_VIRT 0xFE200000 42 + #define IO_PPSB_SIZE SZ_1M 43 + 44 + #define IO_APB_PHYS 0x70000000 45 + #define IO_APB_VIRT 0xFE300000 46 + #define IO_APB_SIZE SZ_1M 47 + 48 + #define IO_TO_VIRT_BETWEEN(p, st, sz) ((p) >= (st) && (p) < ((st) + (sz))) 49 + #define IO_TO_VIRT_XLATE(p, pst, vst) (((p) - (pst) + (vst))) 50 + 51 + #define IO_TO_VIRT(n) ( \ 52 + IO_TO_VIRT_BETWEEN((n), IO_PPSB_PHYS, IO_PPSB_SIZE) ? \ 53 + IO_TO_VIRT_XLATE((n), IO_PPSB_PHYS, IO_PPSB_VIRT) : \ 54 + IO_TO_VIRT_BETWEEN((n), IO_APB_PHYS, IO_APB_SIZE) ? \ 55 + IO_TO_VIRT_XLATE((n), IO_APB_PHYS, IO_APB_VIRT) : \ 56 + IO_TO_VIRT_BETWEEN((n), IO_CPU_PHYS, IO_CPU_SIZE) ? \ 57 + IO_TO_VIRT_XLATE((n), IO_CPU_PHYS, IO_CPU_VIRT) : \ 58 + 0) 59 + 60 + #ifndef __ASSEMBLER__ 61 + 62 + #define __arch_ioremap(p, s, t) tegra_ioremap(p, s, t) 63 + #define __arch_iounmap(v) tegra_iounmap(v) 64 + 65 + void __iomem *tegra_ioremap(unsigned long phys, size_t size, unsigned int type); 66 + void tegra_iounmap(volatile void __iomem *addr); 67 + 68 + #define IO_ADDRESS(n) ((void __iomem *) IO_TO_VIRT(n)) 69 + 70 + static inline void __iomem *__io(unsigned long addr) 71 + { 72 + return (void __iomem *)addr; 73 + } 74 + #define __io(a) __io(a) 75 + #define __mem_pci(a) (a) 76 + 77 + #endif 78 + 79 + #endif
+203
arch/arm/mach-tegra/include/mach/iomap.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/iomap.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_IOMAP_H 22 + #define __MACH_TEGRA_IOMAP_H 23 + 24 + #include <asm/sizes.h> 25 + 26 + #define TEGRA_ARM_PERIF_BASE 0x50040000 27 + #define TEGRA_ARM_PERIF_SIZE SZ_8K 28 + 29 + #define TEGRA_ARM_INT_DIST_BASE 0x50041000 30 + #define TEGRA_ARM_INT_DIST_SIZE SZ_4K 31 + 32 + #define TEGRA_DISPLAY_BASE 0x54200000 33 + #define TEGRA_DISPLAY_SIZE SZ_256K 34 + 35 + #define TEGRA_DISPLAY2_BASE 0x54240000 36 + #define TEGRA_DISPLAY2_SIZE SZ_256K 37 + 38 + #define TEGRA_PRIMARY_ICTLR_BASE 0x60004000 39 + #define TEGRA_PRIMARY_ICTLR_SIZE SZ_64 40 + 41 + #define TEGRA_SECONDARY_ICTLR_BASE 0x60004100 42 + #define TEGRA_SECONDARY_ICTLR_SIZE SZ_64 43 + 44 + #define TEGRA_TERTIARY_ICTLR_BASE 0x60004200 45 + #define TEGRA_TERTIARY_ICTLR_SIZE SZ_64 46 + 47 + #define TEGRA_QUATERNARY_ICTLR_BASE 0x60004300 48 + #define TEGRA_QUATERNARY_ICTLR_SIZE SZ_64 49 + 50 + #define TEGRA_TMR1_BASE 0x60005000 51 + #define TEGRA_TMR1_SIZE SZ_8 52 + 53 + #define TEGRA_TMR2_BASE 0x60005008 54 + #define TEGRA_TMR2_SIZE SZ_8 55 + 56 + #define TEGRA_TMRUS_BASE 0x60005010 57 + #define TEGRA_TMRUS_SIZE SZ_64 58 + 59 + #define TEGRA_TMR3_BASE 0x60005050 60 + #define TEGRA_TMR3_SIZE SZ_8 61 + 62 + #define TEGRA_TMR4_BASE 0x60005058 63 + #define TEGRA_TMR4_SIZE SZ_8 64 + 65 + #define TEGRA_CLK_RESET_BASE 0x60006000 66 + #define TEGRA_CLK_RESET_SIZE SZ_4K 67 + 68 + #define TEGRA_FLOW_CTRL_BASE 0x60007000 69 + #define TEGRA_FLOW_CTRL_SIZE 20 70 + 71 + #define TEGRA_STATMON_BASE 0x6000C4000 72 + #define TEGRA_STATMON_SIZE SZ_1K 73 + 74 + #define TEGRA_GPIO_BASE 0x6000D000 75 + #define TEGRA_GPIO_SIZE SZ_4K 76 + 77 + #define TEGRA_EXCEPTION_VECTORS_BASE 0x6000F000 78 + #define TEGRA_EXCEPTION_VECTORS_SIZE SZ_4K 79 + 80 + #define TEGRA_APB_MISC_BASE 0x70000000 81 + #define TEGRA_APB_MISC_SIZE SZ_4K 82 + 83 + #define TEGRA_AC97_BASE 0x70002000 84 + #define TEGRA_AC97_SIZE SZ_512 85 + 86 + #define TEGRA_SPDIF_BASE 0x70002400 87 + #define TEGRA_SPDIF_SIZE SZ_512 88 + 89 + #define TEGRA_I2S1_BASE 0x70002800 90 + #define TEGRA_I2S1_SIZE SZ_256 91 + 92 + #define TEGRA_I2S2_BASE 0x70002A00 93 + #define TEGRA_I2S2_SIZE SZ_256 94 + 95 + #define TEGRA_UARTA_BASE 0x70006000 96 + #define TEGRA_UARTA_SIZE SZ_64 97 + 98 + #define TEGRA_UARTB_BASE 0x70006040 99 + #define TEGRA_UARTB_SIZE SZ_64 100 + 101 + #define TEGRA_UARTC_BASE 0x70006200 102 + #define TEGRA_UARTC_SIZE SZ_256 103 + 104 + #define TEGRA_UARTD_BASE 0x70006300 105 + #define TEGRA_UARTD_SIZE SZ_256 106 + 107 + #define TEGRA_UARTE_BASE 0x70006400 108 + #define TEGRA_UARTE_SIZE SZ_256 109 + 110 + #define TEGRA_NAND_BASE 0x70008000 111 + #define TEGRA_NAND_SIZE SZ_256 112 + 113 + #define TEGRA_HSMMC_BASE 0x70008500 114 + #define TEGRA_HSMMC_SIZE SZ_256 115 + 116 + #define TEGRA_SNOR_BASE 0x70009000 117 + #define TEGRA_SNOR_SIZE SZ_4K 118 + 119 + #define TEGRA_PWFM_BASE 0x7000A000 120 + #define TEGRA_PWFM_SIZE SZ_256 121 + 122 + #define TEGRA_MIPI_BASE 0x7000B000 123 + #define TEGRA_MIPI_SIZE SZ_256 124 + 125 + #define TEGRA_I2C_BASE 0x7000C000 126 + #define TEGRA_I2C_SIZE SZ_256 127 + 128 + #define TEGRA_TWC_BASE 0x7000C100 129 + #define TEGRA_TWC_SIZE SZ_256 130 + 131 + #define TEGRA_SPI_BASE 0x7000C380 132 + #define TEGRA_SPI_SIZE 48 133 + 134 + #define TEGRA_I2C2_BASE 0x7000C400 135 + #define TEGRA_I2C2_SIZE SZ_256 136 + 137 + #define TEGRA_I2C3_BASE 0x7000C500 138 + #define TEGRA_I2C3_SIZE SZ_256 139 + 140 + #define TEGRA_OWR_BASE 0x7000D000 141 + #define TEGRA_OWR_SIZE 80 142 + 143 + #define TEGRA_DVC_BASE 0x7000D000 144 + #define TEGRA_DVC_SIZE SZ_512 145 + 146 + #define TEGRA_SPI1_BASE 0x7000D400 147 + #define TEGRA_SPI1_SIZE SZ_512 148 + 149 + #define TEGRA_SPI2_BASE 0x7000D600 150 + #define TEGRA_SPI2_SIZE SZ_512 151 + 152 + #define TEGRA_SPI3_BASE 0x7000D800 153 + #define TEGRA_SPI3_SIZE SZ_512 154 + 155 + #define TEGRA_SPI4_BASE 0x7000DA00 156 + #define TEGRA_SPI4_SIZE SZ_512 157 + 158 + #define TEGRA_RTC_BASE 0x7000E000 159 + #define TEGRA_RTC_SIZE SZ_256 160 + 161 + #define TEGRA_KBC_BASE 0x7000E200 162 + #define TEGRA_KBC_SIZE SZ_256 163 + 164 + #define TEGRA_PMC_BASE 0x7000E400 165 + #define TEGRA_PMC_SIZE SZ_256 166 + 167 + #define TEGRA_MC_BASE 0x7000F000 168 + #define TEGRA_MC_SIZE SZ_1K 169 + 170 + #define TEGRA_EMC_BASE 0x7000F400 171 + #define TEGRA_EMC_SIZE SZ_1K 172 + 173 + #define TEGRA_FUSE_BASE 0x7000F800 174 + #define TEGRA_FUSE_SIZE SZ_1K 175 + 176 + #define TEGRA_KFUSE_BASE 0x7000FC00 177 + #define TEGRA_KFUSE_SIZE SZ_1K 178 + 179 + #define TEGRA_CSITE_BASE 0x70040000 180 + #define TEGRA_CSITE_SIZE SZ_256K 181 + 182 + #define TEGRA_USB_BASE 0xC5000000 183 + #define TEGRA_USB_SIZE SZ_16K 184 + 185 + #define TEGRA_USB1_BASE 0xC5004000 186 + #define TEGRA_USB1_SIZE SZ_16K 187 + 188 + #define TEGRA_USB2_BASE 0xC5008000 189 + #define TEGRA_USB2_SIZE SZ_16K 190 + 191 + #define TEGRA_SDMMC1_BASE 0xC8000000 192 + #define TEGRA_SDMMC1_SIZE SZ_512 193 + 194 + #define TEGRA_SDMMC2_BASE 0xC8000200 195 + #define TEGRA_SDMMC2_SIZE SZ_512 196 + 197 + #define TEGRA_SDMMC3_BASE 0xC8000400 198 + #define TEGRA_SDMMC3_SIZE SZ_512 199 + 200 + #define TEGRA_SDMMC4_BASE 0xC8000600 201 + #define TEGRA_SDMMC4_SIZE SZ_512 202 + 203 + #endif
+173
arch/arm/mach-tegra/include/mach/irqs.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/irqs.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_IRQS_H 22 + #define __MACH_TEGRA_IRQS_H 23 + 24 + #define INT_GIC_BASE 0 25 + 26 + #define IRQ_LOCALTIMER 29 27 + 28 + /* Primary Interrupt Controller */ 29 + #define INT_PRI_BASE (INT_GIC_BASE + 32) 30 + #define INT_TMR1 (INT_PRI_BASE + 0) 31 + #define INT_TMR2 (INT_PRI_BASE + 1) 32 + #define INT_RTC (INT_PRI_BASE + 2) 33 + #define INT_I2S2 (INT_PRI_BASE + 3) 34 + #define INT_SHR_SEM_INBOX_IBF (INT_PRI_BASE + 4) 35 + #define INT_SHR_SEM_INBOX_IBE (INT_PRI_BASE + 5) 36 + #define INT_SHR_SEM_OUTBOX_IBF (INT_PRI_BASE + 6) 37 + #define INT_SHR_SEM_OUTBOX_IBE (INT_PRI_BASE + 7) 38 + #define INT_VDE_UCQ_ERROR (INT_PRI_BASE + 8) 39 + #define INT_VDE_SYNC_TOKEN (INT_PRI_BASE + 9) 40 + #define INT_VDE_BSE_V (INT_PRI_BASE + 10) 41 + #define INT_VDE_BSE_A (INT_PRI_BASE + 11) 42 + #define INT_VDE_SXE (INT_PRI_BASE + 12) 43 + #define INT_I2S1 (INT_PRI_BASE + 13) 44 + #define INT_SDMMC1 (INT_PRI_BASE + 14) 45 + #define INT_SDMMC2 (INT_PRI_BASE + 15) 46 + #define INT_XIO (INT_PRI_BASE + 16) 47 + #define INT_VDE (INT_PRI_BASE + 17) 48 + #define INT_AVP_UCQ (INT_PRI_BASE + 18) 49 + #define INT_SDMMC3 (INT_PRI_BASE + 19) 50 + #define INT_USB (INT_PRI_BASE + 20) 51 + #define INT_USB2 (INT_PRI_BASE + 21) 52 + #define INT_PRI_RES_22 (INT_PRI_BASE + 22) 53 + #define INT_EIDE (INT_PRI_BASE + 23) 54 + #define INT_NANDFLASH (INT_PRI_BASE + 24) 55 + #define INT_VCP (INT_PRI_BASE + 25) 56 + #define INT_APB_DMA (INT_PRI_BASE + 26) 57 + #define INT_AHB_DMA (INT_PRI_BASE + 27) 58 + #define INT_GNT_0 (INT_PRI_BASE + 28) 59 + #define INT_GNT_1 (INT_PRI_BASE + 29) 60 + #define INT_OWR (INT_PRI_BASE + 30) 61 + #define INT_SDMMC4 (INT_PRI_BASE + 31) 62 + 63 + /* Secondary Interrupt Controller */ 64 + #define INT_SEC_BASE (INT_PRI_BASE + 32) 65 + #define INT_GPIO1 (INT_SEC_BASE + 0) 66 + #define INT_GPIO2 (INT_SEC_BASE + 1) 67 + #define INT_GPIO3 (INT_SEC_BASE + 2) 68 + #define INT_GPIO4 (INT_SEC_BASE + 3) 69 + #define INT_UARTA (INT_SEC_BASE + 4) 70 + #define INT_UARTB (INT_SEC_BASE + 5) 71 + #define INT_I2C (INT_SEC_BASE + 6) 72 + #define INT_SPI (INT_SEC_BASE + 7) 73 + #define INT_TWC (INT_SEC_BASE + 8) 74 + #define INT_TMR3 (INT_SEC_BASE + 9) 75 + #define INT_TMR4 (INT_SEC_BASE + 10) 76 + #define INT_FLOW_RSM0 (INT_SEC_BASE + 11) 77 + #define INT_FLOW_RSM1 (INT_SEC_BASE + 12) 78 + #define INT_SPDIF (INT_SEC_BASE + 13) 79 + #define INT_UARTC (INT_SEC_BASE + 14) 80 + #define INT_MIPI (INT_SEC_BASE + 15) 81 + #define INT_EVENTA (INT_SEC_BASE + 16) 82 + #define INT_EVENTB (INT_SEC_BASE + 17) 83 + #define INT_EVENTC (INT_SEC_BASE + 18) 84 + #define INT_EVENTD (INT_SEC_BASE + 19) 85 + #define INT_VFIR (INT_SEC_BASE + 20) 86 + #define INT_DVC (INT_SEC_BASE + 21) 87 + #define INT_SYS_STATS_MON (INT_SEC_BASE + 22) 88 + #define INT_GPIO5 (INT_SEC_BASE + 23) 89 + #define INT_CPU0_PMU_INTR (INT_SEC_BASE + 24) 90 + #define INT_CPU2_PMU_INTR (INT_SEC_BASE + 25) 91 + #define INT_SEC_RES_26 (INT_SEC_BASE + 26) 92 + #define INT_S_LINK1 (INT_SEC_BASE + 27) 93 + #define INT_APB_DMA_COP (INT_SEC_BASE + 28) 94 + #define INT_AHB_DMA_COP (INT_SEC_BASE + 29) 95 + #define INT_DMA_TX (INT_SEC_BASE + 30) 96 + #define INT_DMA_RX (INT_SEC_BASE + 31) 97 + 98 + /* Tertiary Interrupt Controller */ 99 + #define INT_TRI_BASE (INT_SEC_BASE + 32) 100 + #define INT_HOST1X_COP_SYNCPT (INT_TRI_BASE + 0) 101 + #define INT_HOST1X_MPCORE_SYNCPT (INT_TRI_BASE + 1) 102 + #define INT_HOST1X_COP_GENERAL (INT_TRI_BASE + 2) 103 + #define INT_HOST1X_MPCORE_GENERAL (INT_TRI_BASE + 3) 104 + #define INT_MPE_GENERAL (INT_TRI_BASE + 4) 105 + #define INT_VI_GENERAL (INT_TRI_BASE + 5) 106 + #define INT_EPP_GENERAL (INT_TRI_BASE + 6) 107 + #define INT_ISP_GENERAL (INT_TRI_BASE + 7) 108 + #define INT_2D_GENERAL (INT_TRI_BASE + 8) 109 + #define INT_DISPLAY_GENERAL (INT_TRI_BASE + 9) 110 + #define INT_DISPLAY_B_GENERAL (INT_TRI_BASE + 10) 111 + #define INT_HDMI (INT_TRI_BASE + 11) 112 + #define INT_TVO_GENERAL (INT_TRI_BASE + 12) 113 + #define INT_MC_GENERAL (INT_TRI_BASE + 13) 114 + #define INT_EMC_GENERAL (INT_TRI_BASE + 14) 115 + #define INT_TRI_RES_15 (INT_TRI_BASE + 15) 116 + #define INT_TRI_RES_16 (INT_TRI_BASE + 16) 117 + #define INT_AC97 (INT_TRI_BASE + 17) 118 + #define INT_SPI_2 (INT_TRI_BASE + 18) 119 + #define INT_SPI_3 (INT_TRI_BASE + 19) 120 + #define INT_I2C2 (INT_TRI_BASE + 20) 121 + #define INT_KBC (INT_TRI_BASE + 21) 122 + #define INT_EXTERNAL_PMU (INT_TRI_BASE + 22) 123 + #define INT_GPIO6 (INT_TRI_BASE + 23) 124 + #define INT_TVDAC (INT_TRI_BASE + 24) 125 + #define INT_GPIO7 (INT_TRI_BASE + 25) 126 + #define INT_UARTD (INT_TRI_BASE + 26) 127 + #define INT_UARTE (INT_TRI_BASE + 27) 128 + #define INT_I2C3 (INT_TRI_BASE + 28) 129 + #define INT_SPI_4 (INT_TRI_BASE + 29) 130 + #define INT_TRI_RES_30 (INT_TRI_BASE + 30) 131 + #define INT_SW_RESERVED (INT_TRI_BASE + 31) 132 + 133 + /* Quaternary Interrupt Controller */ 134 + #define INT_QUAD_BASE (INT_TRI_BASE + 32) 135 + #define INT_SNOR (INT_QUAD_BASE + 0) 136 + #define INT_USB3 (INT_QUAD_BASE + 1) 137 + #define INT_PCIE_INTR (INT_QUAD_BASE + 2) 138 + #define INT_PCIE_MSI (INT_QUAD_BASE + 3) 139 + #define INT_QUAD_RES_4 (INT_QUAD_BASE + 4) 140 + #define INT_QUAD_RES_5 (INT_QUAD_BASE + 5) 141 + #define INT_QUAD_RES_6 (INT_QUAD_BASE + 6) 142 + #define INT_QUAD_RES_7 (INT_QUAD_BASE + 7) 143 + #define INT_APB_DMA_CH0 (INT_QUAD_BASE + 8) 144 + #define INT_APB_DMA_CH1 (INT_QUAD_BASE + 9) 145 + #define INT_APB_DMA_CH2 (INT_QUAD_BASE + 10) 146 + #define INT_APB_DMA_CH3 (INT_QUAD_BASE + 11) 147 + #define INT_APB_DMA_CH4 (INT_QUAD_BASE + 12) 148 + #define INT_APB_DMA_CH5 (INT_QUAD_BASE + 13) 149 + #define INT_APB_DMA_CH6 (INT_QUAD_BASE + 14) 150 + #define INT_APB_DMA_CH7 (INT_QUAD_BASE + 15) 151 + #define INT_APB_DMA_CH8 (INT_QUAD_BASE + 16) 152 + #define INT_APB_DMA_CH9 (INT_QUAD_BASE + 17) 153 + #define INT_APB_DMA_CH10 (INT_QUAD_BASE + 18) 154 + #define INT_APB_DMA_CH11 (INT_QUAD_BASE + 19) 155 + #define INT_APB_DMA_CH12 (INT_QUAD_BASE + 20) 156 + #define INT_APB_DMA_CH13 (INT_QUAD_BASE + 21) 157 + #define INT_APB_DMA_CH14 (INT_QUAD_BASE + 22) 158 + #define INT_APB_DMA_CH15 (INT_QUAD_BASE + 23) 159 + #define INT_QUAD_RES_24 (INT_QUAD_BASE + 24) 160 + #define INT_QUAD_RES_25 (INT_QUAD_BASE + 25) 161 + #define INT_QUAD_RES_26 (INT_QUAD_BASE + 26) 162 + #define INT_QUAD_RES_27 (INT_QUAD_BASE + 27) 163 + #define INT_QUAD_RES_28 (INT_QUAD_BASE + 28) 164 + #define INT_QUAD_RES_29 (INT_QUAD_BASE + 29) 165 + #define INT_QUAD_RES_30 (INT_QUAD_BASE + 30) 166 + #define INT_QUAD_RES_31 (INT_QUAD_BASE + 31) 167 + 168 + #define INT_GPIO_BASE (INT_QUAD_BASE + 32) 169 + #define INT_GPIO_NR (28 * 8) 170 + 171 + #define NR_IRQS (INT_GPIO_BASE + INT_GPIO_NR) 172 + 173 + #endif
+28
arch/arm/mach-tegra/include/mach/memory.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/memory.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_MEMORY_H 22 + #define __MACH_TEGRA_MEMORY_H 23 + 24 + /* physical offset of RAM */ 25 + #define PHYS_OFFSET UL(0) 26 + 27 + #endif 28 +
+348
arch/arm/mach-tegra/include/mach/pinmux.h
··· 1 + /* 2 + * linux/arch/arm/mach-tegra/include/mach/pinmux.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * This software is licensed under the terms of the GNU General Public 7 + * License version 2, as published by the Free Software Foundation, and 8 + * may be copied, distributed, and modified under those terms. 9 + * 10 + * This program is distributed in the hope that it will be useful, 11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 + * GNU General Public License for more details. 14 + * 15 + */ 16 + 17 + #ifndef __MACH_TEGRA_PINMUX_H 18 + #define __MACH_TEGRA_PINMUX_H 19 + 20 + enum tegra_pingroup { 21 + TEGRA_PINGROUP_ATA = 0, 22 + TEGRA_PINGROUP_ATB, 23 + TEGRA_PINGROUP_ATC, 24 + TEGRA_PINGROUP_ATD, 25 + TEGRA_PINGROUP_ATE, 26 + TEGRA_PINGROUP_CDEV1, 27 + TEGRA_PINGROUP_CDEV2, 28 + TEGRA_PINGROUP_CRTP, 29 + TEGRA_PINGROUP_CSUS, 30 + TEGRA_PINGROUP_DAP1, 31 + TEGRA_PINGROUP_DAP2, 32 + TEGRA_PINGROUP_DAP3, 33 + TEGRA_PINGROUP_DAP4, 34 + TEGRA_PINGROUP_DDC, 35 + TEGRA_PINGROUP_DTA, 36 + TEGRA_PINGROUP_DTB, 37 + TEGRA_PINGROUP_DTC, 38 + TEGRA_PINGROUP_DTD, 39 + TEGRA_PINGROUP_DTE, 40 + TEGRA_PINGROUP_DTF, 41 + TEGRA_PINGROUP_GMA, 42 + TEGRA_PINGROUP_GMB, 43 + TEGRA_PINGROUP_GMC, 44 + TEGRA_PINGROUP_GMD, 45 + TEGRA_PINGROUP_GME, 46 + TEGRA_PINGROUP_GPU, 47 + TEGRA_PINGROUP_GPU7, 48 + TEGRA_PINGROUP_GPV, 49 + TEGRA_PINGROUP_HDINT, 50 + TEGRA_PINGROUP_I2CP, 51 + TEGRA_PINGROUP_IRRX, 52 + TEGRA_PINGROUP_IRTX, 53 + TEGRA_PINGROUP_KBCA, 54 + TEGRA_PINGROUP_KBCB, 55 + TEGRA_PINGROUP_KBCC, 56 + TEGRA_PINGROUP_KBCD, 57 + TEGRA_PINGROUP_KBCE, 58 + TEGRA_PINGROUP_KBCF, 59 + TEGRA_PINGROUP_LCSN, 60 + TEGRA_PINGROUP_LD0, 61 + TEGRA_PINGROUP_LD1, 62 + TEGRA_PINGROUP_LD10, 63 + TEGRA_PINGROUP_LD11, 64 + TEGRA_PINGROUP_LD12, 65 + TEGRA_PINGROUP_LD13, 66 + TEGRA_PINGROUP_LD14, 67 + TEGRA_PINGROUP_LD15, 68 + TEGRA_PINGROUP_LD16, 69 + TEGRA_PINGROUP_LD17, 70 + TEGRA_PINGROUP_LD2, 71 + TEGRA_PINGROUP_LD3, 72 + TEGRA_PINGROUP_LD4, 73 + TEGRA_PINGROUP_LD5, 74 + TEGRA_PINGROUP_LD6, 75 + TEGRA_PINGROUP_LD7, 76 + TEGRA_PINGROUP_LD8, 77 + TEGRA_PINGROUP_LD9, 78 + TEGRA_PINGROUP_LDC, 79 + TEGRA_PINGROUP_LDI, 80 + TEGRA_PINGROUP_LHP0, 81 + TEGRA_PINGROUP_LHP1, 82 + TEGRA_PINGROUP_LHP2, 83 + TEGRA_PINGROUP_LHS, 84 + TEGRA_PINGROUP_LM0, 85 + TEGRA_PINGROUP_LM1, 86 + TEGRA_PINGROUP_LPP, 87 + TEGRA_PINGROUP_LPW0, 88 + TEGRA_PINGROUP_LPW1, 89 + TEGRA_PINGROUP_LPW2, 90 + TEGRA_PINGROUP_LSC0, 91 + TEGRA_PINGROUP_LSC1, 92 + TEGRA_PINGROUP_LSCK, 93 + TEGRA_PINGROUP_LSDA, 94 + TEGRA_PINGROUP_LSDI, 95 + TEGRA_PINGROUP_LSPI, 96 + TEGRA_PINGROUP_LVP0, 97 + TEGRA_PINGROUP_LVP1, 98 + TEGRA_PINGROUP_LVS, 99 + TEGRA_PINGROUP_OWC, 100 + TEGRA_PINGROUP_PMC, 101 + TEGRA_PINGROUP_PTA, 102 + TEGRA_PINGROUP_RM, 103 + TEGRA_PINGROUP_SDB, 104 + TEGRA_PINGROUP_SDC, 105 + TEGRA_PINGROUP_SDD, 106 + TEGRA_PINGROUP_SDIO1, 107 + TEGRA_PINGROUP_SLXA, 108 + TEGRA_PINGROUP_SLXC, 109 + TEGRA_PINGROUP_SLXD, 110 + TEGRA_PINGROUP_SLXK, 111 + TEGRA_PINGROUP_SPDI, 112 + TEGRA_PINGROUP_SPDO, 113 + TEGRA_PINGROUP_SPIA, 114 + TEGRA_PINGROUP_SPIB, 115 + TEGRA_PINGROUP_SPIC, 116 + TEGRA_PINGROUP_SPID, 117 + TEGRA_PINGROUP_SPIE, 118 + TEGRA_PINGROUP_SPIF, 119 + TEGRA_PINGROUP_SPIG, 120 + TEGRA_PINGROUP_SPIH, 121 + TEGRA_PINGROUP_UAA, 122 + TEGRA_PINGROUP_UAB, 123 + TEGRA_PINGROUP_UAC, 124 + TEGRA_PINGROUP_UAD, 125 + TEGRA_PINGROUP_UCA, 126 + TEGRA_PINGROUP_UCB, 127 + TEGRA_PINGROUP_UDA, 128 + /* these pin groups only have pullup and pull down control */ 129 + TEGRA_PINGROUP_CK32, 130 + TEGRA_PINGROUP_DDRC, 131 + TEGRA_PINGROUP_PMCA, 132 + TEGRA_PINGROUP_PMCB, 133 + TEGRA_PINGROUP_PMCC, 134 + TEGRA_PINGROUP_PMCD, 135 + TEGRA_PINGROUP_PMCE, 136 + TEGRA_PINGROUP_XM2C, 137 + TEGRA_PINGROUP_XM2D, 138 + TEGRA_MAX_PINGROUP, 139 + }; 140 + 141 + enum tegra_mux_func { 142 + TEGRA_MUX_RSVD = 0x8000, 143 + TEGRA_MUX_RSVD1 = 0x8000, 144 + TEGRA_MUX_RSVD2 = 0x8001, 145 + TEGRA_MUX_RSVD3 = 0x8002, 146 + TEGRA_MUX_RSVD4 = 0x8003, 147 + TEGRA_MUX_NONE = -1, 148 + TEGRA_MUX_AHB_CLK, 149 + TEGRA_MUX_APB_CLK, 150 + TEGRA_MUX_AUDIO_SYNC, 151 + TEGRA_MUX_CRT, 152 + TEGRA_MUX_DAP1, 153 + TEGRA_MUX_DAP2, 154 + TEGRA_MUX_DAP3, 155 + TEGRA_MUX_DAP4, 156 + TEGRA_MUX_DAP5, 157 + TEGRA_MUX_DISPLAYA, 158 + TEGRA_MUX_DISPLAYB, 159 + TEGRA_MUX_EMC_TEST0_DLL, 160 + TEGRA_MUX_EMC_TEST1_DLL, 161 + TEGRA_MUX_GMI, 162 + TEGRA_MUX_GMI_INT, 163 + TEGRA_MUX_HDMI, 164 + TEGRA_MUX_I2C, 165 + TEGRA_MUX_I2C2, 166 + TEGRA_MUX_I2C3, 167 + TEGRA_MUX_IDE, 168 + TEGRA_MUX_IRDA, 169 + TEGRA_MUX_KBC, 170 + TEGRA_MUX_MIO, 171 + TEGRA_MUX_MIPI_HS, 172 + TEGRA_MUX_NAND, 173 + TEGRA_MUX_OSC, 174 + TEGRA_MUX_OWR, 175 + TEGRA_MUX_PCIE, 176 + TEGRA_MUX_PLLA_OUT, 177 + TEGRA_MUX_PLLC_OUT1, 178 + TEGRA_MUX_PLLM_OUT1, 179 + TEGRA_MUX_PLLP_OUT2, 180 + TEGRA_MUX_PLLP_OUT3, 181 + TEGRA_MUX_PLLP_OUT4, 182 + TEGRA_MUX_PWM, 183 + TEGRA_MUX_PWR_INTR, 184 + TEGRA_MUX_PWR_ON, 185 + TEGRA_MUX_RTCK, 186 + TEGRA_MUX_SDIO1, 187 + TEGRA_MUX_SDIO2, 188 + TEGRA_MUX_SDIO3, 189 + TEGRA_MUX_SDIO4, 190 + TEGRA_MUX_SFLASH, 191 + TEGRA_MUX_SPDIF, 192 + TEGRA_MUX_SPI1, 193 + TEGRA_MUX_SPI2, 194 + TEGRA_MUX_SPI2_ALT, 195 + TEGRA_MUX_SPI3, 196 + TEGRA_MUX_SPI4, 197 + TEGRA_MUX_TRACE, 198 + TEGRA_MUX_TWC, 199 + TEGRA_MUX_UARTA, 200 + TEGRA_MUX_UARTB, 201 + TEGRA_MUX_UARTC, 202 + TEGRA_MUX_UARTD, 203 + TEGRA_MUX_UARTE, 204 + TEGRA_MUX_ULPI, 205 + TEGRA_MUX_VI, 206 + TEGRA_MUX_VI_SENSOR_CLK, 207 + TEGRA_MUX_XIO, 208 + TEGRA_MAX_MUX, 209 + }; 210 + 211 + enum tegra_pullupdown { 212 + TEGRA_PUPD_NORMAL = 0, 213 + TEGRA_PUPD_PULL_DOWN, 214 + TEGRA_PUPD_PULL_UP, 215 + }; 216 + 217 + enum tegra_tristate { 218 + TEGRA_TRI_NORMAL = 0, 219 + TEGRA_TRI_TRISTATE = 1, 220 + }; 221 + 222 + struct tegra_pingroup_config { 223 + enum tegra_pingroup pingroup; 224 + enum tegra_mux_func func; 225 + enum tegra_pullupdown pupd; 226 + enum tegra_tristate tristate; 227 + }; 228 + 229 + enum tegra_slew { 230 + TEGRA_SLEW_FASTEST = 0, 231 + TEGRA_SLEW_FAST, 232 + TEGRA_SLEW_SLOW, 233 + TEGRA_SLEW_SLOWEST, 234 + TEGRA_MAX_SLEW, 235 + }; 236 + 237 + enum tegra_pull_strength { 238 + TEGRA_PULL_0 = 0, 239 + TEGRA_PULL_1, 240 + TEGRA_PULL_2, 241 + TEGRA_PULL_3, 242 + TEGRA_PULL_4, 243 + TEGRA_PULL_5, 244 + TEGRA_PULL_6, 245 + TEGRA_PULL_7, 246 + TEGRA_PULL_8, 247 + TEGRA_PULL_9, 248 + TEGRA_PULL_10, 249 + TEGRA_PULL_11, 250 + TEGRA_PULL_12, 251 + TEGRA_PULL_13, 252 + TEGRA_PULL_14, 253 + TEGRA_PULL_15, 254 + TEGRA_PULL_16, 255 + TEGRA_PULL_17, 256 + TEGRA_PULL_18, 257 + TEGRA_PULL_19, 258 + TEGRA_PULL_20, 259 + TEGRA_PULL_21, 260 + TEGRA_PULL_22, 261 + TEGRA_PULL_23, 262 + TEGRA_PULL_24, 263 + TEGRA_PULL_25, 264 + TEGRA_PULL_26, 265 + TEGRA_PULL_27, 266 + TEGRA_PULL_28, 267 + TEGRA_PULL_29, 268 + TEGRA_PULL_30, 269 + TEGRA_PULL_31, 270 + TEGRA_MAX_PULL, 271 + }; 272 + 273 + enum tegra_drive_pingroup { 274 + TEGRA_DRIVE_PINGROUP_AO1 = 0, 275 + TEGRA_DRIVE_PINGROUP_AO2, 276 + TEGRA_DRIVE_PINGROUP_AT1, 277 + TEGRA_DRIVE_PINGROUP_AT2, 278 + TEGRA_DRIVE_PINGROUP_CDEV1, 279 + TEGRA_DRIVE_PINGROUP_CDEV2, 280 + TEGRA_DRIVE_PINGROUP_CSUS, 281 + TEGRA_DRIVE_PINGROUP_DAP1, 282 + TEGRA_DRIVE_PINGROUP_DAP2, 283 + TEGRA_DRIVE_PINGROUP_DAP3, 284 + TEGRA_DRIVE_PINGROUP_DAP4, 285 + TEGRA_DRIVE_PINGROUP_DBG, 286 + TEGRA_DRIVE_PINGROUP_LCD1, 287 + TEGRA_DRIVE_PINGROUP_LCD2, 288 + TEGRA_DRIVE_PINGROUP_SDMMC2, 289 + TEGRA_DRIVE_PINGROUP_SDMMC3, 290 + TEGRA_DRIVE_PINGROUP_SPI, 291 + TEGRA_DRIVE_PINGROUP_UAA, 292 + TEGRA_DRIVE_PINGROUP_UAB, 293 + TEGRA_DRIVE_PINGROUP_UART2, 294 + TEGRA_DRIVE_PINGROUP_UART3, 295 + TEGRA_DRIVE_PINGROUP_VI1, 296 + TEGRA_DRIVE_PINGROUP_VI2, 297 + TEGRA_DRIVE_PINGROUP_XM2A, 298 + TEGRA_DRIVE_PINGROUP_XM2C, 299 + TEGRA_DRIVE_PINGROUP_XM2D, 300 + TEGRA_DRIVE_PINGROUP_XM2CLK, 301 + TEGRA_DRIVE_PINGROUP_MEMCOMP, 302 + TEGRA_MAX_DRIVE_PINGROUP, 303 + }; 304 + 305 + enum tegra_drive { 306 + TEGRA_DRIVE_DIV_8 = 0, 307 + TEGRA_DRIVE_DIV_4, 308 + TEGRA_DRIVE_DIV_2, 309 + TEGRA_DRIVE_DIV_1, 310 + TEGRA_MAX_DRIVE, 311 + }; 312 + 313 + enum tegra_hsm { 314 + TEGRA_HSM_DISABLE = 0, 315 + TEGRA_HSM_ENABLE, 316 + }; 317 + 318 + enum tegra_schmitt { 319 + TEGRA_SCHMITT_DISABLE = 0, 320 + TEGRA_SCHMITT_ENABLE, 321 + }; 322 + 323 + struct tegra_drive_pingroup_config { 324 + enum tegra_drive_pingroup pingroup; 325 + enum tegra_hsm hsm; 326 + enum tegra_schmitt schmitt; 327 + enum tegra_drive drive; 328 + enum tegra_pull_strength pull_down; 329 + enum tegra_pull_strength pull_up; 330 + enum tegra_slew slew_rising; 331 + enum tegra_slew slew_falling; 332 + }; 333 + 334 + int tegra_pinmux_set_func(enum tegra_pingroup pg, enum tegra_mux_func func); 335 + int tegra_pinmux_set_tristate(enum tegra_pingroup pg, enum tegra_tristate tristate); 336 + int tegra_pinmux_set_pullupdown(enum tegra_pingroup pg, enum tegra_pullupdown pupd); 337 + 338 + void tegra_pinmux_config_pingroup(enum tegra_pingroup pingroup, 339 + enum tegra_mux_func func, enum tegra_pullupdown pupd, 340 + enum tegra_tristate tristate); 341 + 342 + void tegra_pinmux_config_table(struct tegra_pingroup_config *config, int len); 343 + 344 + void tegra_drive_pinmux_config_table(struct tegra_drive_pingroup_config *config, 345 + int len); 346 + 347 + #endif 348 +
+30
arch/arm/mach-tegra/include/mach/smp.h
··· 1 + #ifndef ASMARM_ARCH_SMP_H 2 + #define ASMARM_ARCH_SMP_H 3 + 4 + 5 + #include <asm/hardware/gic.h> 6 + 7 + #define hard_smp_processor_id() \ 8 + ({ \ 9 + unsigned int cpunum; \ 10 + __asm__("mrc p15, 0, %0, c0, c0, 5" \ 11 + : "=r" (cpunum)); \ 12 + cpunum &= 0x0F; \ 13 + }) 14 + 15 + /* 16 + * We use IRQ1 as the IPI 17 + */ 18 + static inline void smp_cross_call(const struct cpumask *mask) 19 + { 20 + gic_raise_softirq(mask, 1); 21 + } 22 + 23 + /* 24 + * Do nothing on MPcore. 25 + */ 26 + static inline void smp_cross_call_done(cpumask_t callmap) 27 + { 28 + } 29 + 30 + #endif
+39
arch/arm/mach-tegra/include/mach/system.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/system.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_SYSTEM_H 22 + #define __MACH_TEGRA_SYSTEM_H 23 + 24 + #include <mach/hardware.h> 25 + #include <mach/iomap.h> 26 + 27 + static inline void arch_idle(void) 28 + { 29 + } 30 + 31 + static inline void arch_reset(char mode, const char *cmd) 32 + { 33 + void __iomem *reset = IO_ADDRESS(TEGRA_CLK_RESET_BASE + 0x04); 34 + u32 reg = readl(reset); 35 + reg |= 0x04; 36 + writel(reg, reset); 37 + } 38 + 39 + #endif
+26
arch/arm/mach-tegra/include/mach/timex.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/timex.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_TIMEX_H 22 + #define __MACH_TEGRA_TIMEX_H 23 + 24 + #define CLOCK_TICK_RATE 1000000 25 + 26 + #endif
+78
arch/arm/mach-tegra/include/mach/uncompress.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/uncompress.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_UNCOMPRESS_H 22 + #define __MACH_TEGRA_UNCOMPRESS_H 23 + 24 + #include <linux/types.h> 25 + #include <linux/serial_reg.h> 26 + 27 + #include <mach/iomap.h> 28 + 29 + #if defined(CONFIG_TEGRA_DEBUG_UARTA) 30 + #define DEBUG_UART_BASE TEGRA_UARTA_BASE 31 + #elif defined(CONFIG_TEGRA_DEBUG_UARTB) 32 + #define DEBUG_UART_BASE TEGRA_UARTB_BASE 33 + #elif defined(CONFIG_TEGRA_DEBUG_UARTC) 34 + #define DEBUG_UART_BASE TEGRA_UARTC_BASE 35 + #elif defined(CONFIG_TEGRA_DEBUG_UARTD) 36 + #define DEBUG_UART_BASE TEGRA_UARTD_BASE 37 + #elif defined(CONFIG_TEGRA_DEBUG_UARTE) 38 + #define DEBUG_UART_BASE TEGRA_UARTE_BASE 39 + #else 40 + #define DEBUG_UART_BASE NULL 41 + #endif 42 + 43 + static void putc(int c) 44 + { 45 + volatile u8 *uart = (volatile u8 *)DEBUG_UART_BASE; 46 + int shift = 2; 47 + 48 + if (uart == NULL) 49 + return; 50 + 51 + while (!(uart[UART_LSR << shift] & UART_LSR_THRE)) 52 + barrier(); 53 + uart[UART_TX << shift] = c; 54 + } 55 + 56 + static inline void flush(void) 57 + { 58 + } 59 + 60 + static inline void arch_decomp_setup(void) 61 + { 62 + volatile u8 *uart = (volatile u8 *)DEBUG_UART_BASE; 63 + int shift = 2; 64 + 65 + if (uart == NULL) 66 + return; 67 + 68 + uart[UART_LCR << shift] |= UART_LCR_DLAB; 69 + uart[UART_DLL << shift] = 0x75; 70 + uart[UART_DLM << shift] = 0x0; 71 + uart[UART_LCR << shift] = 3; 72 + } 73 + 74 + static inline void arch_decomp_wdog(void) 75 + { 76 + } 77 + 78 + #endif
+28
arch/arm/mach-tegra/include/mach/vmalloc.h
··· 1 + /* 2 + * arch/arm/mach-tegra/include/mach/vmalloc.h 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #ifndef __MACH_TEGRA_VMALLOC_H 22 + #define __MACH_TEGRA_VMALLOC_H 23 + 24 + #include <asm/sizes.h> 25 + 26 + #define VMALLOC_END 0xFE000000 27 + 28 + #endif
+78
arch/arm/mach-tegra/io.c
··· 1 + /* 2 + * arch/arm/mach-tegra/io.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * Erik Gilling <konkers@google.com> 9 + * 10 + * This software is licensed under the terms of the GNU General Public 11 + * License version 2, as published by the Free Software Foundation, and 12 + * may be copied, distributed, and modified under those terms. 13 + * 14 + * This program is distributed in the hope that it will be useful, 15 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 + * GNU General Public License for more details. 18 + * 19 + */ 20 + 21 + #include <linux/kernel.h> 22 + #include <linux/module.h> 23 + #include <linux/init.h> 24 + #include <linux/mm.h> 25 + #include <linux/io.h> 26 + 27 + #include <mach/hardware.h> 28 + #include <asm/page.h> 29 + #include <asm/mach/map.h> 30 + 31 + #include "board.h" 32 + 33 + static struct map_desc tegra_io_desc[] __initdata = { 34 + { 35 + .virtual = IO_PPSB_VIRT, 36 + .pfn = __phys_to_pfn(IO_PPSB_PHYS), 37 + .length = IO_PPSB_SIZE, 38 + .type = MT_DEVICE, 39 + }, 40 + { 41 + .virtual = IO_APB_VIRT, 42 + .pfn = __phys_to_pfn(IO_APB_PHYS), 43 + .length = IO_APB_SIZE, 44 + .type = MT_DEVICE, 45 + }, 46 + { 47 + .virtual = IO_CPU_VIRT, 48 + .pfn = __phys_to_pfn(IO_CPU_PHYS), 49 + .length = IO_CPU_SIZE, 50 + .type = MT_DEVICE, 51 + }, 52 + }; 53 + 54 + void __init tegra_map_common_io(void) 55 + { 56 + iotable_init(tegra_io_desc, ARRAY_SIZE(tegra_io_desc)); 57 + } 58 + 59 + /* 60 + * Intercept ioremap() requests for addresses in our fixed mapping regions. 61 + */ 62 + void __iomem *tegra_ioremap(unsigned long p, size_t size, unsigned int type) 63 + { 64 + void __iomem *v = IO_ADDRESS(p); 65 + if (v == NULL) 66 + v = __arm_ioremap(p, size, type); 67 + return v; 68 + } 69 + EXPORT_SYMBOL(tegra_ioremap); 70 + 71 + void tegra_iounmap(volatile void __iomem *addr) 72 + { 73 + unsigned long virt = (unsigned long)addr; 74 + 75 + if (virt >= VMALLOC_START && virt < VMALLOC_END) 76 + __iounmap(addr); 77 + } 78 + EXPORT_SYMBOL(tegra_iounmap);
+34
arch/arm/mach-tegra/irq.c
··· 1 + /* 2 + * Copyright (C) 2010 Google, Inc. 3 + * 4 + * Author: 5 + * Colin Cross <ccross@google.com> 6 + * 7 + * This software is licensed under the terms of the GNU General Public 8 + * License version 2, as published by the Free Software Foundation, and 9 + * may be copied, distributed, and modified under those terms. 10 + * 11 + * This program is distributed in the hope that it will be useful, 12 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 + * GNU General Public License for more details. 15 + * 16 + */ 17 + 18 + #include <linux/kernel.h> 19 + #include <linux/init.h> 20 + #include <linux/interrupt.h> 21 + #include <linux/irq.h> 22 + #include <linux/io.h> 23 + 24 + #include <asm/hardware/gic.h> 25 + 26 + #include <mach/iomap.h> 27 + 28 + #include "board.h" 29 + 30 + void __init tegra_init_irq(void) 31 + { 32 + gic_dist_init(0, IO_ADDRESS(TEGRA_ARM_INT_DIST_BASE), 29); 33 + gic_cpu_init(0, IO_ADDRESS(TEGRA_ARM_PERIF_BASE + 0x100)); 34 + }
+25
arch/arm/mach-tegra/localtimer.c
··· 1 + /* 2 + * arch/arm/mach-tegra/localtimer.c 3 + * 4 + * Copyright (C) 2002 ARM Ltd. 5 + * All Rights Reserved 6 + * 7 + * This program is free software; you can redistribute it and/or modify 8 + * it under the terms of the GNU General Public License version 2 as 9 + * published by the Free Software Foundation. 10 + */ 11 + #include <linux/init.h> 12 + #include <linux/smp.h> 13 + #include <linux/clockchips.h> 14 + #include <asm/irq.h> 15 + #include <asm/smp_twd.h> 16 + #include <asm/localtimer.h> 17 + 18 + /* 19 + * Setup the local clock events for a CPU. 20 + */ 21 + void __cpuinit local_timer_setup(struct clock_event_device *evt) 22 + { 23 + evt->irq = IRQ_LOCALTIMER; 24 + twd_timer_setup(evt); 25 + }
+945
arch/arm/mach-tegra/pinmux.c
··· 1 + /* 2 + * linux/arch/arm/mach-tegra/pinmux.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * This software is licensed under the terms of the GNU General Public 7 + * License version 2, as published by the Free Software Foundation, and 8 + * may be copied, distributed, and modified under those terms. 9 + * 10 + * This program is distributed in the hope that it will be useful, 11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 + * GNU General Public License for more details. 14 + * 15 + */ 16 + 17 + 18 + #include <linux/kernel.h> 19 + #include <linux/errno.h> 20 + #include <linux/spinlock.h> 21 + #include <linux/io.h> 22 + 23 + #include <mach/iomap.h> 24 + #include <mach/pinmux.h> 25 + 26 + 27 + #define TEGRA_TRI_STATE(x) (0x14 + (4 * (x))) 28 + #define TEGRA_PP_MUX_CTL(x) (0x80 + (4 * (x))) 29 + #define TEGRA_PP_PU_PD(x) (0xa0 + (4 * (x))) 30 + 31 + #define REG_A 0 32 + #define REG_B 1 33 + #define REG_C 2 34 + #define REG_D 3 35 + #define REG_E 4 36 + #define REG_F 5 37 + #define REG_G 6 38 + 39 + #define REG_N -1 40 + 41 + #define HSM_EN(reg) (((reg) >> 2) & 0x1) 42 + #define SCHMT_EN(reg) (((reg) >> 3) & 0x1) 43 + #define LPMD(reg) (((reg) >> 4) & 0x3) 44 + #define DRVDN(reg) (((reg) >> 12) & 0x1f) 45 + #define DRVUP(reg) (((reg) >> 20) & 0x1f) 46 + #define SLWR(reg) (((reg) >> 28) & 0x3) 47 + #define SLWF(reg) (((reg) >> 30) & 0x3) 48 + 49 + struct tegra_pingroup_desc { 50 + const char *name; 51 + int funcs[4]; 52 + s8 tri_reg; /* offset into the TRISTATE_REG_* register bank */ 53 + s8 tri_bit; /* offset into the TRISTATE_REG_* register bit */ 54 + s8 mux_reg; /* offset into the PIN_MUX_CTL_* register bank */ 55 + s8 mux_bit; /* offset into the PIN_MUX_CTL_* register bit */ 56 + s8 pupd_reg; /* offset into the PULL_UPDOWN_REG_* register bank */ 57 + s8 pupd_bit; /* offset into the PULL_UPDOWN_REG_* register bit */ 58 + }; 59 + 60 + #define PINGROUP(pg_name, f0, f1, f2, f3, \ 61 + tri_r, tri_b, mux_r, mux_b, pupd_r, pupd_b) \ 62 + [TEGRA_PINGROUP_ ## pg_name] = { \ 63 + .name = #pg_name, \ 64 + .funcs = { \ 65 + TEGRA_MUX_ ## f0, \ 66 + TEGRA_MUX_ ## f1, \ 67 + TEGRA_MUX_ ## f2, \ 68 + TEGRA_MUX_ ## f3, \ 69 + }, \ 70 + .tri_reg = REG_ ## tri_r, \ 71 + .tri_bit = tri_b, \ 72 + .mux_reg = REG_ ## mux_r, \ 73 + .mux_bit = mux_b, \ 74 + .pupd_reg = REG_ ## pupd_r, \ 75 + .pupd_bit = pupd_b, \ 76 + } 77 + 78 + static const struct tegra_pingroup_desc pingroups[TEGRA_MAX_PINGROUP] = { 79 + PINGROUP(ATA, IDE, NAND, GMI, RSVD, A, 0, A, 24, A, 0), 80 + PINGROUP(ATB, IDE, NAND, GMI, SDIO4, A, 1, A, 16, A, 2), 81 + PINGROUP(ATC, IDE, NAND, GMI, SDIO4, A, 2, A, 22, A, 4), 82 + PINGROUP(ATD, IDE, NAND, GMI, SDIO4, A, 3, A, 20, A, 6), 83 + PINGROUP(ATE, IDE, NAND, GMI, RSVD, B, 25, A, 12, A, 8), 84 + PINGROUP(CDEV1, OSC, PLLA_OUT, PLLM_OUT1, AUDIO_SYNC, A, 4, C, 2, C, 0), 85 + PINGROUP(CDEV2, OSC, AHB_CLK, APB_CLK, PLLP_OUT4, A, 5, C, 4, C, 2), 86 + PINGROUP(CRTP, CRT, RSVD, RSVD, RSVD, D, 14, G, 20, B, 24), 87 + PINGROUP(CSUS, PLLC_OUT1, PLLP_OUT2, PLLP_OUT3, VI_SENSOR_CLK, A, 6, C, 6, D, 24), 88 + PINGROUP(DAP1, DAP1, RSVD, GMI, SDIO2, A, 7, C, 20, A, 10), 89 + PINGROUP(DAP2, DAP2, TWC, RSVD, GMI, A, 8, C, 22, A, 12), 90 + PINGROUP(DAP3, DAP3, RSVD, RSVD, RSVD, A, 9, C, 24, A, 14), 91 + PINGROUP(DAP4, DAP4, RSVD, GMI, RSVD, A, 10, C, 26, A, 16), 92 + PINGROUP(DDC, I2C2, RSVD, RSVD, RSVD, B, 31, C, 0, E, 28), 93 + PINGROUP(DTA, RSVD, SDIO2, VI, RSVD, A, 11, B, 20, A, 18), 94 + PINGROUP(DTB, RSVD, RSVD, VI, SPI1, A, 12, B, 22, A, 20), 95 + PINGROUP(DTC, RSVD, RSVD, VI, RSVD, A, 13, B, 26, A, 22), 96 + PINGROUP(DTD, RSVD, SDIO2, VI, RSVD, A, 14, B, 28, A, 24), 97 + PINGROUP(DTE, RSVD, RSVD, VI, SPI1, A, 15, B, 30, A, 26), 98 + PINGROUP(DTF, I2C3, RSVD, VI, RSVD, D, 12, G, 30, A, 28), 99 + PINGROUP(GMA, UARTE, SPI3, GMI, SDIO4, A, 28, B, 0, E, 20), 100 + PINGROUP(GMB, IDE, NAND, GMI, GMI_INT, B, 29, C, 28, E, 22), 101 + PINGROUP(GMC, UARTD, SPI4, GMI, SFLASH, A, 29, B, 2, E, 24), 102 + PINGROUP(GMD, RSVD, NAND, GMI, SFLASH, B, 30, C, 30, E, 26), 103 + PINGROUP(GME, RSVD, DAP5, GMI, SDIO4, B, 0, D, 0, C, 24), 104 + PINGROUP(GPU, PWM, UARTA, GMI, RSVD, A, 16, D, 4, B, 20), 105 + PINGROUP(GPU7, RTCK, RSVD, RSVD, RSVD, D, 11, G, 28, B, 6), 106 + PINGROUP(GPV, PCIE, RSVD, RSVD, RSVD, A, 17, D, 2, A, 30), 107 + PINGROUP(HDINT, HDMI, RSVD, RSVD, RSVD, C, 23, B, 4, D, 22), 108 + PINGROUP(I2CP, I2C, RSVD, RSVD, RSVD, A, 18, C, 8, B, 2), 109 + PINGROUP(IRRX, UARTA, UARTB, GMI, SPI4, A, 20, C, 18, C, 22), 110 + PINGROUP(IRTX, UARTA, UARTB, GMI, SPI4, A, 19, C, 16, C, 20), 111 + PINGROUP(KBCA, KBC, NAND, SDIO2, EMC_TEST0_DLL, A, 22, C, 10, B, 8), 112 + PINGROUP(KBCB, KBC, NAND, SDIO2, MIO, A, 21, C, 12, B, 10), 113 + PINGROUP(KBCC, KBC, NAND, TRACE, EMC_TEST1_DLL, B, 26, C, 14, B, 12), 114 + PINGROUP(KBCD, KBC, NAND, SDIO2, MIO, D, 10, G, 26, B, 14), 115 + PINGROUP(KBCE, KBC, NAND, OWR, RSVD, A, 26, A, 28, E, 2), 116 + PINGROUP(KBCF, KBC, NAND, TRACE, MIO, A, 27, A, 26, E, 0), 117 + PINGROUP(LCSN, DISPLAYA, DISPLAYB, SPI3, RSVD, C, 31, E, 12, D, 20), 118 + PINGROUP(LD0, DISPLAYA, DISPLAYB, XIO, RSVD, C, 0, F, 0, D, 12), 119 + PINGROUP(LD1, DISPLAYA, DISPLAYB, XIO, RSVD, C, 1, F, 2, D, 12), 120 + PINGROUP(LD10, DISPLAYA, DISPLAYB, XIO, RSVD, C, 10, F, 20, D, 12), 121 + PINGROUP(LD11, DISPLAYA, DISPLAYB, XIO, RSVD, C, 11, F, 22, D, 12), 122 + PINGROUP(LD12, DISPLAYA, DISPLAYB, XIO, RSVD, C, 12, F, 24, D, 12), 123 + PINGROUP(LD13, DISPLAYA, DISPLAYB, XIO, RSVD, C, 13, F, 26, D, 12), 124 + PINGROUP(LD14, DISPLAYA, DISPLAYB, XIO, RSVD, C, 14, F, 28, D, 12), 125 + PINGROUP(LD15, DISPLAYA, DISPLAYB, XIO, RSVD, C, 15, F, 30, D, 12), 126 + PINGROUP(LD16, DISPLAYA, DISPLAYB, XIO, RSVD, C, 16, G, 0, D, 12), 127 + PINGROUP(LD17, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 17, G, 2, D, 12), 128 + PINGROUP(LD2, DISPLAYA, DISPLAYB, XIO, RSVD, C, 2, F, 4, D, 12), 129 + PINGROUP(LD3, DISPLAYA, DISPLAYB, XIO, RSVD, C, 3, F, 6, D, 12), 130 + PINGROUP(LD4, DISPLAYA, DISPLAYB, XIO, RSVD, C, 4, F, 8, D, 12), 131 + PINGROUP(LD5, DISPLAYA, DISPLAYB, XIO, RSVD, C, 5, F, 10, D, 12), 132 + PINGROUP(LD6, DISPLAYA, DISPLAYB, XIO, RSVD, C, 6, F, 12, D, 12), 133 + PINGROUP(LD7, DISPLAYA, DISPLAYB, XIO, RSVD, C, 7, F, 14, D, 12), 134 + PINGROUP(LD8, DISPLAYA, DISPLAYB, XIO, RSVD, C, 8, F, 16, D, 12), 135 + PINGROUP(LD9, DISPLAYA, DISPLAYB, XIO, RSVD, C, 9, F, 18, D, 12), 136 + PINGROUP(LDC, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 30, E, 14, D, 20), 137 + PINGROUP(LDI, DISPLAYA, DISPLAYB, RSVD, RSVD, D, 6, G, 16, D, 18), 138 + PINGROUP(LHP0, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 18, G, 10, D, 16), 139 + PINGROUP(LHP1, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 19, G, 4, D, 14), 140 + PINGROUP(LHP2, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 20, G, 6, D, 14), 141 + PINGROUP(LHS, DISPLAYA, DISPLAYB, XIO, RSVD, D, 7, E, 22, D, 22), 142 + PINGROUP(LM0, DISPLAYA, DISPLAYB, SPI3, RSVD, C, 24, E, 26, D, 22), 143 + PINGROUP(LM1, DISPLAYA, DISPLAYB, RSVD, CRT, C, 25, E, 28, D, 22), 144 + PINGROUP(LPP, DISPLAYA, DISPLAYB, RSVD, RSVD, D, 8, G, 14, D, 18), 145 + PINGROUP(LPW0, DISPLAYA, DISPLAYB, SPI3, HDMI, D, 3, E, 0, D, 20), 146 + PINGROUP(LPW1, DISPLAYA, DISPLAYB, RSVD, RSVD, D, 4, E, 2, D, 20), 147 + PINGROUP(LPW2, DISPLAYA, DISPLAYB, SPI3, HDMI, D, 5, E, 4, D, 20), 148 + PINGROUP(LSC0, DISPLAYA, DISPLAYB, XIO, RSVD, C, 27, E, 18, D, 22), 149 + PINGROUP(LSC1, DISPLAYA, DISPLAYB, SPI3, HDMI, C, 28, E, 20, D, 20), 150 + PINGROUP(LSCK, DISPLAYA, DISPLAYB, SPI3, HDMI, C, 29, E, 16, D, 20), 151 + PINGROUP(LSDA, DISPLAYA, DISPLAYB, SPI3, HDMI, D, 1, E, 8, D, 20), 152 + PINGROUP(LSDI, DISPLAYA, DISPLAYB, SPI3, RSVD, D, 2, E, 6, D, 20), 153 + PINGROUP(LSPI, DISPLAYA, DISPLAYB, XIO, HDMI, D, 0, E, 10, D, 22), 154 + PINGROUP(LVP0, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 21, E, 30, D, 22), 155 + PINGROUP(LVP1, DISPLAYA, DISPLAYB, RSVD, RSVD, C, 22, G, 8, D, 16), 156 + PINGROUP(LVS, DISPLAYA, DISPLAYB, XIO, RSVD, C, 26, E, 24, D, 22), 157 + PINGROUP(OWC, OWR, RSVD, RSVD, RSVD, A, 31, B, 8, E, 30), 158 + PINGROUP(PMC, PWR_ON, PWR_INTR, RSVD, RSVD, A, 23, G, 18, N, -1), 159 + PINGROUP(PTA, I2C2, HDMI, GMI, RSVD, A, 24, G, 22, B, 4), 160 + PINGROUP(RM, I2C, RSVD, RSVD, RSVD, A, 25, A, 14, B, 0), 161 + PINGROUP(SDB, UARTA, PWM, SDIO3, SPI2, D, 15, D, 10, N, -1), 162 + PINGROUP(SDC, PWM, TWC, SDIO3, SPI3, B, 1, D, 12, D, 28), 163 + PINGROUP(SDD, UARTA, PWM, SDIO3, SPI3, B, 2, D, 14, D, 30), 164 + PINGROUP(SDIO1, SDIO1, RSVD, UARTE, UARTA, A, 30, A, 30, E, 18), 165 + PINGROUP(SLXA, PCIE, SPI4, SDIO3, SPI2, B, 3, B, 6, B, 22), 166 + PINGROUP(SLXC, SPDIF, SPI4, SDIO3, SPI2, B, 5, B, 10, B, 26), 167 + PINGROUP(SLXD, SPDIF, SPI4, SDIO3, SPI2, B, 6, B, 12, B, 28), 168 + PINGROUP(SLXK, PCIE, SPI4, SDIO3, SPI2, B, 7, B, 14, B, 30), 169 + PINGROUP(SPDI, SPDIF, RSVD, I2C, SDIO2, B, 8, D, 8, B, 16), 170 + PINGROUP(SPDO, SPDIF, RSVD, I2C, SDIO2, B, 9, D, 6, B, 18), 171 + PINGROUP(SPIA, SPI1, SPI2, SPI3, GMI, B, 10, D, 30, C, 4), 172 + PINGROUP(SPIB, SPI1, SPI2, SPI3, GMI, B, 11, D, 28, C, 6), 173 + PINGROUP(SPIC, SPI1, SPI2, SPI3, GMI, B, 12, D, 26, C, 8), 174 + PINGROUP(SPID, SPI2, SPI1, SPI2_ALT, GMI, B, 13, D, 24, C, 10), 175 + PINGROUP(SPIE, SPI2, SPI1, SPI2_ALT, GMI, B, 14, D, 22, C, 12), 176 + PINGROUP(SPIF, SPI3, SPI1, SPI2, RSVD, B, 15, D, 20, C, 14), 177 + PINGROUP(SPIG, SPI3, SPI2, SPI2_ALT, I2C, B, 16, D, 18, C, 16), 178 + PINGROUP(SPIH, SPI3, SPI2, SPI2_ALT, I2C, B, 17, D, 16, C, 18), 179 + PINGROUP(UAA, SPI3, MIPI_HS, UARTA, ULPI, B, 18, A, 0, D, 0), 180 + PINGROUP(UAB, SPI2, MIPI_HS, UARTA, ULPI, B, 19, A, 2, D, 2), 181 + PINGROUP(UAC, OWR, RSVD, RSVD, RSVD, B, 20, A, 4, D, 4), 182 + PINGROUP(UAD, IRDA, SPDIF, UARTA, SPI4, B, 21, A, 6, D, 6), 183 + PINGROUP(UCA, UARTC, RSVD, GMI, RSVD, B, 22, B, 16, D, 8), 184 + PINGROUP(UCB, UARTC, PWM, GMI, RSVD, B, 23, B, 18, D, 10), 185 + PINGROUP(UDA, SPI1, RSVD, UARTD, ULPI, D, 13, A, 8, E, 16), 186 + /* these pin groups only have pullup and pull down control */ 187 + PINGROUP(CK32, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 14), 188 + PINGROUP(DDRC, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, D, 26), 189 + PINGROUP(PMCA, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 4), 190 + PINGROUP(PMCB, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 6), 191 + PINGROUP(PMCC, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 8), 192 + PINGROUP(PMCD, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 10), 193 + PINGROUP(PMCE, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, E, 12), 194 + PINGROUP(XM2C, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, C, 30), 195 + PINGROUP(XM2D, RSVD, RSVD, RSVD, RSVD, N, -1, N, -1, C, 28), 196 + }; 197 + 198 + static char *tegra_mux_names[TEGRA_MAX_MUX] = { 199 + [TEGRA_MUX_AHB_CLK] = "AHB_CLK", 200 + [TEGRA_MUX_APB_CLK] = "APB_CLK", 201 + [TEGRA_MUX_AUDIO_SYNC] = "AUDIO_SYNC", 202 + [TEGRA_MUX_CRT] = "CRT", 203 + [TEGRA_MUX_DAP1] = "DAP1", 204 + [TEGRA_MUX_DAP2] = "DAP2", 205 + [TEGRA_MUX_DAP3] = "DAP3", 206 + [TEGRA_MUX_DAP4] = "DAP4", 207 + [TEGRA_MUX_DAP5] = "DAP5", 208 + [TEGRA_MUX_DISPLAYA] = "DISPLAYA", 209 + [TEGRA_MUX_DISPLAYB] = "DISPLAYB", 210 + [TEGRA_MUX_EMC_TEST0_DLL] = "EMC_TEST0_DLL", 211 + [TEGRA_MUX_EMC_TEST1_DLL] = "EMC_TEST1_DLL", 212 + [TEGRA_MUX_GMI] = "GMI", 213 + [TEGRA_MUX_GMI_INT] = "GMI_INT", 214 + [TEGRA_MUX_HDMI] = "HDMI", 215 + [TEGRA_MUX_I2C] = "I2C", 216 + [TEGRA_MUX_I2C2] = "I2C2", 217 + [TEGRA_MUX_I2C3] = "I2C3", 218 + [TEGRA_MUX_IDE] = "IDE", 219 + [TEGRA_MUX_IRDA] = "IRDA", 220 + [TEGRA_MUX_KBC] = "KBC", 221 + [TEGRA_MUX_MIO] = "MIO", 222 + [TEGRA_MUX_MIPI_HS] = "MIPI_HS", 223 + [TEGRA_MUX_NAND] = "NAND", 224 + [TEGRA_MUX_OSC] = "OSC", 225 + [TEGRA_MUX_OWR] = "OWR", 226 + [TEGRA_MUX_PCIE] = "PCIE", 227 + [TEGRA_MUX_PLLA_OUT] = "PLLA_OUT", 228 + [TEGRA_MUX_PLLC_OUT1] = "PLLC_OUT1", 229 + [TEGRA_MUX_PLLM_OUT1] = "PLLM_OUT1", 230 + [TEGRA_MUX_PLLP_OUT2] = "PLLP_OUT2", 231 + [TEGRA_MUX_PLLP_OUT3] = "PLLP_OUT3", 232 + [TEGRA_MUX_PLLP_OUT4] = "PLLP_OUT4", 233 + [TEGRA_MUX_PWM] = "PWM", 234 + [TEGRA_MUX_PWR_INTR] = "PWR_INTR", 235 + [TEGRA_MUX_PWR_ON] = "PWR_ON", 236 + [TEGRA_MUX_RTCK] = "RTCK", 237 + [TEGRA_MUX_SDIO1] = "SDIO1", 238 + [TEGRA_MUX_SDIO2] = "SDIO2", 239 + [TEGRA_MUX_SDIO3] = "SDIO3", 240 + [TEGRA_MUX_SDIO4] = "SDIO4", 241 + [TEGRA_MUX_SFLASH] = "SFLASH", 242 + [TEGRA_MUX_SPDIF] = "SPDIF", 243 + [TEGRA_MUX_SPI1] = "SPI1", 244 + [TEGRA_MUX_SPI2] = "SPI2", 245 + [TEGRA_MUX_SPI2_ALT] = "SPI2_ALT", 246 + [TEGRA_MUX_SPI3] = "SPI3", 247 + [TEGRA_MUX_SPI4] = "SPI4", 248 + [TEGRA_MUX_TRACE] = "TRACE", 249 + [TEGRA_MUX_TWC] = "TWC", 250 + [TEGRA_MUX_UARTA] = "UARTA", 251 + [TEGRA_MUX_UARTB] = "UARTB", 252 + [TEGRA_MUX_UARTC] = "UARTC", 253 + [TEGRA_MUX_UARTD] = "UARTD", 254 + [TEGRA_MUX_UARTE] = "UARTE", 255 + [TEGRA_MUX_ULPI] = "ULPI", 256 + [TEGRA_MUX_VI] = "VI", 257 + [TEGRA_MUX_VI_SENSOR_CLK] = "VI_SENSOR_CLK", 258 + [TEGRA_MUX_XIO] = "XIO", 259 + }; 260 + 261 + struct tegra_drive_pingroup_desc { 262 + const char *name; 263 + s16 reg; 264 + }; 265 + 266 + #define DRIVE_PINGROUP(pg_name, r) \ 267 + [TEGRA_DRIVE_PINGROUP_ ## pg_name] = { \ 268 + .name = #pg_name, \ 269 + .reg = r \ 270 + } 271 + 272 + static const struct tegra_drive_pingroup_desc drive_pingroups[TEGRA_MAX_PINGROUP] = { 273 + DRIVE_PINGROUP(AO1, 0x868), 274 + DRIVE_PINGROUP(AO2, 0x86c), 275 + DRIVE_PINGROUP(AT1, 0x870), 276 + DRIVE_PINGROUP(AT2, 0x874), 277 + DRIVE_PINGROUP(CDEV1, 0x878), 278 + DRIVE_PINGROUP(CDEV2, 0x87c), 279 + DRIVE_PINGROUP(CSUS, 0x880), 280 + DRIVE_PINGROUP(DAP1, 0x884), 281 + DRIVE_PINGROUP(DAP2, 0x888), 282 + DRIVE_PINGROUP(DAP3, 0x88c), 283 + DRIVE_PINGROUP(DAP4, 0x890), 284 + DRIVE_PINGROUP(DBG, 0x894), 285 + DRIVE_PINGROUP(LCD1, 0x898), 286 + DRIVE_PINGROUP(LCD2, 0x89c), 287 + DRIVE_PINGROUP(SDMMC2, 0x8a0), 288 + DRIVE_PINGROUP(SDMMC3, 0x8a4), 289 + DRIVE_PINGROUP(SPI, 0x8a8), 290 + DRIVE_PINGROUP(UAA, 0x8ac), 291 + DRIVE_PINGROUP(UAB, 0x8b0), 292 + DRIVE_PINGROUP(UART2, 0x8b4), 293 + DRIVE_PINGROUP(UART3, 0x8b8), 294 + DRIVE_PINGROUP(VI1, 0x8bc), 295 + DRIVE_PINGROUP(VI2, 0x8c0), 296 + DRIVE_PINGROUP(XM2A, 0x8c4), 297 + DRIVE_PINGROUP(XM2C, 0x8c8), 298 + DRIVE_PINGROUP(XM2D, 0x8cc), 299 + DRIVE_PINGROUP(XM2CLK, 0x8d0), 300 + DRIVE_PINGROUP(MEMCOMP, 0x8d4), 301 + }; 302 + 303 + static const char *tegra_drive_names[TEGRA_MAX_DRIVE] = { 304 + [TEGRA_DRIVE_DIV_8] = "DIV_8", 305 + [TEGRA_DRIVE_DIV_4] = "DIV_4", 306 + [TEGRA_DRIVE_DIV_2] = "DIV_2", 307 + [TEGRA_DRIVE_DIV_1] = "DIV_1", 308 + }; 309 + 310 + static const char *tegra_slew_names[TEGRA_MAX_SLEW] = { 311 + [TEGRA_SLEW_FASTEST] = "FASTEST", 312 + [TEGRA_SLEW_FAST] = "FAST", 313 + [TEGRA_SLEW_SLOW] = "SLOW", 314 + [TEGRA_SLEW_SLOWEST] = "SLOWEST", 315 + }; 316 + 317 + static DEFINE_SPINLOCK(mux_lock); 318 + 319 + static const char *pingroup_name(enum tegra_pingroup pg) 320 + { 321 + if (pg < 0 || pg >= TEGRA_MAX_PINGROUP) 322 + return "<UNKNOWN>"; 323 + 324 + return pingroups[pg].name; 325 + } 326 + 327 + static const char *func_name(enum tegra_mux_func func) 328 + { 329 + if (func == TEGRA_MUX_RSVD1) 330 + return "RSVD1"; 331 + 332 + if (func == TEGRA_MUX_RSVD2) 333 + return "RSVD2"; 334 + 335 + if (func == TEGRA_MUX_RSVD3) 336 + return "RSVD3"; 337 + 338 + if (func == TEGRA_MUX_RSVD4) 339 + return "RSVD4"; 340 + 341 + if (func == TEGRA_MUX_NONE) 342 + return "NONE"; 343 + 344 + if (func < 0 || func >= TEGRA_MAX_MUX) 345 + return "<UNKNOWN>"; 346 + 347 + return tegra_mux_names[func]; 348 + } 349 + 350 + 351 + static const char *tri_name(unsigned long val) 352 + { 353 + return val ? "TRISTATE" : "NORMAL"; 354 + } 355 + 356 + static const char *pupd_name(unsigned long val) 357 + { 358 + switch (val) { 359 + case 0: 360 + return "NORMAL"; 361 + 362 + case 1: 363 + return "PULL_DOWN"; 364 + 365 + case 2: 366 + return "PULL_UP"; 367 + 368 + default: 369 + return "RSVD"; 370 + } 371 + } 372 + 373 + 374 + static inline unsigned long pg_readl(unsigned long offset) 375 + { 376 + return readl(IO_TO_VIRT(TEGRA_APB_MISC_BASE + offset)); 377 + } 378 + 379 + static inline void pg_writel(unsigned long value, unsigned long offset) 380 + { 381 + writel(value, IO_TO_VIRT(TEGRA_APB_MISC_BASE + offset)); 382 + } 383 + 384 + int tegra_pinmux_set_func(enum tegra_pingroup pg, enum tegra_mux_func func) 385 + { 386 + int mux = -1; 387 + int i; 388 + unsigned long reg; 389 + unsigned long flags; 390 + 391 + if (pg < 0 || pg >= TEGRA_MAX_PINGROUP) 392 + return -ERANGE; 393 + 394 + if (pingroups[pg].mux_reg == REG_N) 395 + return -EINVAL; 396 + 397 + if (func < 0) 398 + return -ERANGE; 399 + 400 + if (func & TEGRA_MUX_RSVD) { 401 + mux = func & 0x3; 402 + } else { 403 + for (i = 0; i < 4; i++) { 404 + if (pingroups[pg].funcs[i] == func) { 405 + mux = i; 406 + break; 407 + } 408 + } 409 + } 410 + 411 + if (mux < 0) 412 + return -EINVAL; 413 + 414 + spin_lock_irqsave(&mux_lock, flags); 415 + 416 + reg = pg_readl(TEGRA_PP_MUX_CTL(pingroups[pg].mux_reg)); 417 + reg &= ~(0x3 << pingroups[pg].mux_bit); 418 + reg |= mux << pingroups[pg].mux_bit; 419 + pg_writel(reg, TEGRA_PP_MUX_CTL(pingroups[pg].mux_reg)); 420 + 421 + spin_unlock_irqrestore(&mux_lock, flags); 422 + 423 + return 0; 424 + } 425 + 426 + int tegra_pinmux_set_tristate(enum tegra_pingroup pg, 427 + enum tegra_tristate tristate) 428 + { 429 + unsigned long reg; 430 + unsigned long flags; 431 + 432 + if (pg < 0 || pg >= TEGRA_MAX_PINGROUP) 433 + return -ERANGE; 434 + 435 + if (pingroups[pg].tri_reg == REG_N) 436 + return -EINVAL; 437 + 438 + spin_lock_irqsave(&mux_lock, flags); 439 + 440 + reg = pg_readl(TEGRA_TRI_STATE(pingroups[pg].tri_reg)); 441 + reg &= ~(0x1 << pingroups[pg].tri_bit); 442 + if (tristate) 443 + reg |= 1 << pingroups[pg].tri_bit; 444 + pg_writel(reg, TEGRA_TRI_STATE(pingroups[pg].tri_reg)); 445 + 446 + spin_unlock_irqrestore(&mux_lock, flags); 447 + 448 + return 0; 449 + } 450 + 451 + int tegra_pinmux_set_pullupdown(enum tegra_pingroup pg, 452 + enum tegra_pullupdown pupd) 453 + { 454 + unsigned long reg; 455 + unsigned long flags; 456 + 457 + if (pg < 0 || pg >= TEGRA_MAX_PINGROUP) 458 + return -ERANGE; 459 + 460 + if (pingroups[pg].pupd_reg == REG_N) 461 + return -EINVAL; 462 + 463 + if (pupd != TEGRA_PUPD_NORMAL && 464 + pupd != TEGRA_PUPD_PULL_DOWN && 465 + pupd != TEGRA_PUPD_PULL_UP) 466 + return -EINVAL; 467 + 468 + 469 + spin_lock_irqsave(&mux_lock, flags); 470 + 471 + reg = pg_readl(TEGRA_PP_PU_PD(pingroups[pg].pupd_reg)); 472 + reg &= ~(0x3 << pingroups[pg].pupd_bit); 473 + reg |= pupd << pingroups[pg].pupd_bit; 474 + pg_writel(reg, TEGRA_PP_PU_PD(pingroups[pg].pupd_reg)); 475 + 476 + spin_unlock_irqrestore(&mux_lock, flags); 477 + 478 + return 0; 479 + } 480 + 481 + void tegra_pinmux_config_pingroup(enum tegra_pingroup pingroup, 482 + enum tegra_mux_func func, 483 + enum tegra_pullupdown pupd, 484 + enum tegra_tristate tristate) 485 + { 486 + int err; 487 + 488 + if (pingroups[pingroup].mux_reg != REG_N) { 489 + err = tegra_pinmux_set_func(pingroup, func); 490 + if (err < 0) 491 + pr_err("pinmux: can't set pingroup %s func to %s: %d\n", 492 + pingroup_name(pingroup), func_name(func), err); 493 + } 494 + 495 + if (pingroups[pingroup].pupd_reg != REG_N) { 496 + err = tegra_pinmux_set_pullupdown(pingroup, pupd); 497 + if (err < 0) 498 + pr_err("pinmux: can't set pingroup %s pullupdown to %s: %d\n", 499 + pingroup_name(pingroup), pupd_name(pupd), err); 500 + } 501 + 502 + if (pingroups[pingroup].tri_reg != REG_N) { 503 + err = tegra_pinmux_set_tristate(pingroup, tristate); 504 + if (err < 0) 505 + pr_err("pinmux: can't set pingroup %s tristate to %s: %d\n", 506 + pingroup_name(pingroup), tri_name(func), err); 507 + } 508 + } 509 + 510 + 511 + 512 + void tegra_pinmux_config_table(struct tegra_pingroup_config *config, int len) 513 + { 514 + int i; 515 + 516 + for (i = 0; i < len; i++) 517 + tegra_pinmux_config_pingroup(config[i].pingroup, 518 + config[i].func, 519 + config[i].pupd, 520 + config[i].tristate); 521 + } 522 + 523 + static const char *drive_pinmux_name(enum tegra_drive_pingroup pg) 524 + { 525 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 526 + return "<UNKNOWN>"; 527 + 528 + return drive_pingroups[pg].name; 529 + } 530 + 531 + static const char *enable_name(unsigned long val) 532 + { 533 + return val ? "ENABLE" : "DISABLE"; 534 + } 535 + 536 + static const char *drive_name(unsigned long val) 537 + { 538 + if (val >= TEGRA_MAX_DRIVE) 539 + return "<UNKNOWN>"; 540 + 541 + return tegra_drive_names[val]; 542 + } 543 + 544 + static const char *slew_name(unsigned long val) 545 + { 546 + if (val >= TEGRA_MAX_SLEW) 547 + return "<UNKNOWN>"; 548 + 549 + return tegra_slew_names[val]; 550 + } 551 + 552 + static int tegra_drive_pinmux_set_hsm(enum tegra_drive_pingroup pg, 553 + enum tegra_hsm hsm) 554 + { 555 + unsigned long flags; 556 + u32 reg; 557 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 558 + return -ERANGE; 559 + 560 + if (hsm != TEGRA_HSM_ENABLE && hsm != TEGRA_HSM_DISABLE) 561 + return -EINVAL; 562 + 563 + spin_lock_irqsave(&mux_lock, flags); 564 + 565 + reg = pg_readl(drive_pingroups[pg].reg); 566 + if (hsm == TEGRA_HSM_ENABLE) 567 + reg |= (1 << 2); 568 + else 569 + reg &= ~(1 << 2); 570 + pg_writel(reg, drive_pingroups[pg].reg); 571 + 572 + spin_unlock_irqrestore(&mux_lock, flags); 573 + 574 + return 0; 575 + } 576 + 577 + static int tegra_drive_pinmux_set_schmitt(enum tegra_drive_pingroup pg, 578 + enum tegra_schmitt schmitt) 579 + { 580 + unsigned long flags; 581 + u32 reg; 582 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 583 + return -ERANGE; 584 + 585 + if (schmitt != TEGRA_SCHMITT_ENABLE && schmitt != TEGRA_SCHMITT_DISABLE) 586 + return -EINVAL; 587 + 588 + spin_lock_irqsave(&mux_lock, flags); 589 + 590 + reg = pg_readl(drive_pingroups[pg].reg); 591 + if (schmitt == TEGRA_SCHMITT_ENABLE) 592 + reg |= (1 << 3); 593 + else 594 + reg &= ~(1 << 3); 595 + pg_writel(reg, drive_pingroups[pg].reg); 596 + 597 + spin_unlock_irqrestore(&mux_lock, flags); 598 + 599 + return 0; 600 + } 601 + 602 + static int tegra_drive_pinmux_set_drive(enum tegra_drive_pingroup pg, 603 + enum tegra_drive drive) 604 + { 605 + unsigned long flags; 606 + u32 reg; 607 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 608 + return -ERANGE; 609 + 610 + if (drive < 0 || drive >= TEGRA_MAX_DRIVE) 611 + return -EINVAL; 612 + 613 + spin_lock_irqsave(&mux_lock, flags); 614 + 615 + reg = pg_readl(drive_pingroups[pg].reg); 616 + reg &= ~(0x3 << 4); 617 + reg |= drive << 4; 618 + pg_writel(reg, drive_pingroups[pg].reg); 619 + 620 + spin_unlock_irqrestore(&mux_lock, flags); 621 + 622 + return 0; 623 + } 624 + 625 + static int tegra_drive_pinmux_set_pull_down(enum tegra_drive_pingroup pg, 626 + enum tegra_pull_strength pull_down) 627 + { 628 + unsigned long flags; 629 + u32 reg; 630 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 631 + return -ERANGE; 632 + 633 + if (pull_down < 0 || pull_down >= TEGRA_MAX_PULL) 634 + return -EINVAL; 635 + 636 + spin_lock_irqsave(&mux_lock, flags); 637 + 638 + reg = pg_readl(drive_pingroups[pg].reg); 639 + reg &= ~(0x1f << 12); 640 + reg |= pull_down << 12; 641 + pg_writel(reg, drive_pingroups[pg].reg); 642 + 643 + spin_unlock_irqrestore(&mux_lock, flags); 644 + 645 + return 0; 646 + } 647 + 648 + static int tegra_drive_pinmux_set_pull_up(enum tegra_drive_pingroup pg, 649 + enum tegra_pull_strength pull_up) 650 + { 651 + unsigned long flags; 652 + u32 reg; 653 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 654 + return -ERANGE; 655 + 656 + if (pull_up < 0 || pull_up >= TEGRA_MAX_PULL) 657 + return -EINVAL; 658 + 659 + spin_lock_irqsave(&mux_lock, flags); 660 + 661 + reg = pg_readl(drive_pingroups[pg].reg); 662 + reg &= ~(0x1f << 12); 663 + reg |= pull_up << 12; 664 + pg_writel(reg, drive_pingroups[pg].reg); 665 + 666 + spin_unlock_irqrestore(&mux_lock, flags); 667 + 668 + return 0; 669 + } 670 + 671 + static int tegra_drive_pinmux_set_slew_rising(enum tegra_drive_pingroup pg, 672 + enum tegra_slew slew_rising) 673 + { 674 + unsigned long flags; 675 + u32 reg; 676 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 677 + return -ERANGE; 678 + 679 + if (slew_rising < 0 || slew_rising >= TEGRA_MAX_SLEW) 680 + return -EINVAL; 681 + 682 + spin_lock_irqsave(&mux_lock, flags); 683 + 684 + reg = pg_readl(drive_pingroups[pg].reg); 685 + reg &= ~(0x3 << 28); 686 + reg |= slew_rising << 28; 687 + pg_writel(reg, drive_pingroups[pg].reg); 688 + 689 + spin_unlock_irqrestore(&mux_lock, flags); 690 + 691 + return 0; 692 + } 693 + 694 + static int tegra_drive_pinmux_set_slew_falling(enum tegra_drive_pingroup pg, 695 + enum tegra_slew slew_falling) 696 + { 697 + unsigned long flags; 698 + u32 reg; 699 + if (pg < 0 || pg >= TEGRA_MAX_DRIVE_PINGROUP) 700 + return -ERANGE; 701 + 702 + if (slew_falling < 0 || slew_falling >= TEGRA_MAX_SLEW) 703 + return -EINVAL; 704 + 705 + spin_lock_irqsave(&mux_lock, flags); 706 + 707 + reg = pg_readl(drive_pingroups[pg].reg); 708 + reg &= ~(0x3 << 30); 709 + reg |= slew_falling << 30; 710 + pg_writel(reg, drive_pingroups[pg].reg); 711 + 712 + spin_unlock_irqrestore(&mux_lock, flags); 713 + 714 + return 0; 715 + } 716 + 717 + static void tegra_drive_pinmux_config_pingroup(enum tegra_drive_pingroup pingroup, 718 + enum tegra_hsm hsm, 719 + enum tegra_schmitt schmitt, 720 + enum tegra_drive drive, 721 + enum tegra_pull_strength pull_down, 722 + enum tegra_pull_strength pull_up, 723 + enum tegra_slew slew_rising, 724 + enum tegra_slew slew_falling) 725 + { 726 + int err; 727 + 728 + err = tegra_drive_pinmux_set_hsm(pingroup, hsm); 729 + if (err < 0) 730 + pr_err("pinmux: can't set pingroup %s hsm to %s: %d\n", 731 + drive_pinmux_name(pingroup), 732 + enable_name(hsm), err); 733 + 734 + err = tegra_drive_pinmux_set_schmitt(pingroup, schmitt); 735 + if (err < 0) 736 + pr_err("pinmux: can't set pingroup %s schmitt to %s: %d\n", 737 + drive_pinmux_name(pingroup), 738 + enable_name(schmitt), err); 739 + 740 + err = tegra_drive_pinmux_set_drive(pingroup, drive); 741 + if (err < 0) 742 + pr_err("pinmux: can't set pingroup %s drive to %s: %d\n", 743 + drive_pinmux_name(pingroup), 744 + drive_name(drive), err); 745 + 746 + err = tegra_drive_pinmux_set_pull_down(pingroup, pull_down); 747 + if (err < 0) 748 + pr_err("pinmux: can't set pingroup %s pull down to %d: %d\n", 749 + drive_pinmux_name(pingroup), 750 + pull_down, err); 751 + 752 + err = tegra_drive_pinmux_set_pull_up(pingroup, pull_up); 753 + if (err < 0) 754 + pr_err("pinmux: can't set pingroup %s pull up to %d: %d\n", 755 + drive_pinmux_name(pingroup), 756 + pull_up, err); 757 + 758 + err = tegra_drive_pinmux_set_slew_rising(pingroup, slew_rising); 759 + if (err < 0) 760 + pr_err("pinmux: can't set pingroup %s rising slew to %s: %d\n", 761 + drive_pinmux_name(pingroup), 762 + slew_name(slew_rising), err); 763 + 764 + err = tegra_drive_pinmux_set_slew_falling(pingroup, slew_falling); 765 + if (err < 0) 766 + pr_err("pinmux: can't set pingroup %s falling slew to %s: %d\n", 767 + drive_pinmux_name(pingroup), 768 + slew_name(slew_falling), err); 769 + } 770 + 771 + void tegra_drive_pinmux_config_table(struct tegra_drive_pingroup_config *config, 772 + int len) 773 + { 774 + int i; 775 + 776 + for (i = 0; i < len; i++) 777 + tegra_drive_pinmux_config_pingroup(config[i].pingroup, 778 + config[i].hsm, 779 + config[i].schmitt, 780 + config[i].drive, 781 + config[i].pull_down, 782 + config[i].pull_up, 783 + config[i].slew_rising, 784 + config[i].slew_falling); 785 + } 786 + 787 + 788 + #ifdef CONFIG_DEBUG_FS 789 + 790 + #include <linux/debugfs.h> 791 + #include <linux/seq_file.h> 792 + 793 + static void dbg_pad_field(struct seq_file *s, int len) 794 + { 795 + seq_putc(s, ','); 796 + 797 + while (len-- > -1) 798 + seq_putc(s, ' '); 799 + } 800 + 801 + static int dbg_pinmux_show(struct seq_file *s, void *unused) 802 + { 803 + int i; 804 + int len; 805 + 806 + for (i = 0; i < TEGRA_MAX_PINGROUP; i++) { 807 + unsigned long tri; 808 + unsigned long mux; 809 + unsigned long pupd; 810 + 811 + seq_printf(s, "\t{TEGRA_PINGROUP_%s", pingroups[i].name); 812 + len = strlen(pingroups[i].name); 813 + dbg_pad_field(s, 5 - len); 814 + 815 + if (pingroups[i].mux_reg == REG_N) { 816 + seq_printf(s, "TEGRA_MUX_NONE"); 817 + len = strlen("NONE"); 818 + } else { 819 + mux = (pg_readl(TEGRA_PP_MUX_CTL(pingroups[i].mux_reg)) >> 820 + pingroups[i].mux_bit) & 0x3; 821 + if (pingroups[i].funcs[mux] == TEGRA_MUX_RSVD) { 822 + seq_printf(s, "TEGRA_MUX_RSVD%1lu", mux+1); 823 + len = 5; 824 + } else { 825 + seq_printf(s, "TEGRA_MUX_%s", 826 + tegra_mux_names[pingroups[i].funcs[mux]]); 827 + len = strlen(tegra_mux_names[pingroups[i].funcs[mux]]); 828 + } 829 + } 830 + dbg_pad_field(s, 13-len); 831 + 832 + if (pingroups[i].mux_reg == REG_N) { 833 + seq_printf(s, "TEGRA_PUPD_NORMAL"); 834 + len = strlen("NORMAL"); 835 + } else { 836 + pupd = (pg_readl(TEGRA_PP_PU_PD(pingroups[i].pupd_reg)) >> 837 + pingroups[i].pupd_bit) & 0x3; 838 + seq_printf(s, "TEGRA_PUPD_%s", pupd_name(pupd)); 839 + len = strlen(pupd_name(pupd)); 840 + } 841 + dbg_pad_field(s, 9 - len); 842 + 843 + if (pingroups[i].tri_reg == REG_N) { 844 + seq_printf(s, "TEGRA_TRI_NORMAL"); 845 + } else { 846 + tri = (pg_readl(TEGRA_TRI_STATE(pingroups[i].tri_reg)) >> 847 + pingroups[i].tri_bit) & 0x1; 848 + 849 + seq_printf(s, "TEGRA_TRI_%s", tri_name(tri)); 850 + } 851 + seq_printf(s, "},\n"); 852 + } 853 + return 0; 854 + } 855 + 856 + static int dbg_pinmux_open(struct inode *inode, struct file *file) 857 + { 858 + return single_open(file, dbg_pinmux_show, &inode->i_private); 859 + } 860 + 861 + static const struct file_operations debug_fops = { 862 + .open = dbg_pinmux_open, 863 + .read = seq_read, 864 + .llseek = seq_lseek, 865 + .release = single_release, 866 + }; 867 + 868 + static int dbg_drive_pinmux_show(struct seq_file *s, void *unused) 869 + { 870 + int i; 871 + int len; 872 + 873 + for (i = 0; i < TEGRA_MAX_DRIVE_PINGROUP; i++) { 874 + u32 reg; 875 + 876 + seq_printf(s, "\t{TEGRA_DRIVE_PINGROUP_%s", 877 + drive_pingroups[i].name); 878 + len = strlen(drive_pingroups[i].name); 879 + dbg_pad_field(s, 7 - len); 880 + 881 + 882 + reg = pg_readl(drive_pingroups[i].reg); 883 + if (HSM_EN(reg)) { 884 + seq_printf(s, "TEGRA_HSM_ENABLE"); 885 + len = 16; 886 + } else { 887 + seq_printf(s, "TEGRA_HSM_DISABLE"); 888 + len = 17; 889 + } 890 + dbg_pad_field(s, 17 - len); 891 + 892 + if (SCHMT_EN(reg)) { 893 + seq_printf(s, "TEGRA_SCHMITT_ENABLE"); 894 + len = 21; 895 + } else { 896 + seq_printf(s, "TEGRA_SCHMITT_DISABLE"); 897 + len = 22; 898 + } 899 + dbg_pad_field(s, 22 - len); 900 + 901 + seq_printf(s, "TEGRA_DRIVE_%s", drive_name(LPMD(reg))); 902 + len = strlen(drive_name(LPMD(reg))); 903 + dbg_pad_field(s, 5 - len); 904 + 905 + seq_printf(s, "TEGRA_PULL_%d", DRVDN(reg)); 906 + len = DRVDN(reg) < 10 ? 1 : 2; 907 + dbg_pad_field(s, 2 - len); 908 + 909 + seq_printf(s, "TEGRA_PULL_%d", DRVUP(reg)); 910 + len = DRVUP(reg) < 10 ? 1 : 2; 911 + dbg_pad_field(s, 2 - len); 912 + 913 + seq_printf(s, "TEGRA_SLEW_%s", slew_name(SLWR(reg))); 914 + len = strlen(slew_name(SLWR(reg))); 915 + dbg_pad_field(s, 7 - len); 916 + 917 + seq_printf(s, "TEGRA_SLEW_%s", slew_name(SLWF(reg))); 918 + 919 + seq_printf(s, "},\n"); 920 + } 921 + return 0; 922 + } 923 + 924 + static int dbg_drive_pinmux_open(struct inode *inode, struct file *file) 925 + { 926 + return single_open(file, dbg_drive_pinmux_show, &inode->i_private); 927 + } 928 + 929 + static const struct file_operations debug_drive_fops = { 930 + .open = dbg_drive_pinmux_open, 931 + .read = seq_read, 932 + .llseek = seq_lseek, 933 + .release = single_release, 934 + }; 935 + 936 + static int __init tegra_pinmux_debuginit(void) 937 + { 938 + (void) debugfs_create_file("tegra_pinmux", S_IRUGO, 939 + NULL, NULL, &debug_fops); 940 + (void) debugfs_create_file("tegra_pinmux_drive", S_IRUGO, 941 + NULL, NULL, &debug_drive_fops); 942 + return 0; 943 + } 944 + late_initcall(tegra_pinmux_debuginit); 945 + #endif
+156
arch/arm/mach-tegra/platsmp.c
··· 1 + /* 2 + * linux/arch/arm/mach-tegra/platsmp.c 3 + * 4 + * Copyright (C) 2002 ARM Ltd. 5 + * All Rights Reserved 6 + * 7 + * Copyright (C) 2009 Palm 8 + * All Rights Reserved 9 + * 10 + * This program is free software; you can redistribute it and/or modify 11 + * it under the terms of the GNU General Public License version 2 as 12 + * published by the Free Software Foundation. 13 + */ 14 + #include <linux/init.h> 15 + #include <linux/errno.h> 16 + #include <linux/delay.h> 17 + #include <linux/device.h> 18 + #include <linux/jiffies.h> 19 + #include <linux/smp.h> 20 + #include <linux/io.h> 21 + 22 + #include <asm/cacheflush.h> 23 + #include <mach/hardware.h> 24 + #include <asm/mach-types.h> 25 + #include <asm/localtimer.h> 26 + #include <asm/smp_scu.h> 27 + 28 + #include <mach/iomap.h> 29 + 30 + extern void tegra_secondary_startup(void); 31 + 32 + static DEFINE_SPINLOCK(boot_lock); 33 + static void __iomem *scu_base = IO_ADDRESS(TEGRA_ARM_PERIF_BASE); 34 + 35 + #define EVP_CPU_RESET_VECTOR \ 36 + (IO_ADDRESS(TEGRA_EXCEPTION_VECTORS_BASE) + 0x100) 37 + #define CLK_RST_CONTROLLER_CLK_CPU_CMPLX \ 38 + (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x4c) 39 + #define CLK_RST_CONTROLLER_RST_CPU_CMPLX_CLR \ 40 + (IO_ADDRESS(TEGRA_CLK_RESET_BASE) + 0x344) 41 + 42 + void __cpuinit platform_secondary_init(unsigned int cpu) 43 + { 44 + trace_hardirqs_off(); 45 + 46 + /* 47 + * if any interrupts are already enabled for the primary 48 + * core (e.g. timer irq), then they will not have been enabled 49 + * for us: do so 50 + */ 51 + gic_cpu_init(0, IO_ADDRESS(TEGRA_ARM_PERIF_BASE) + 0x100); 52 + 53 + /* 54 + * Synchronise with the boot thread. 55 + */ 56 + spin_lock(&boot_lock); 57 + spin_unlock(&boot_lock); 58 + } 59 + 60 + int __cpuinit boot_secondary(unsigned int cpu, struct task_struct *idle) 61 + { 62 + unsigned long old_boot_vector; 63 + unsigned long boot_vector; 64 + unsigned long timeout; 65 + u32 reg; 66 + 67 + /* 68 + * set synchronisation state between this boot processor 69 + * and the secondary one 70 + */ 71 + spin_lock(&boot_lock); 72 + 73 + 74 + /* set the reset vector to point to the secondary_startup routine */ 75 + 76 + boot_vector = virt_to_phys(tegra_secondary_startup); 77 + old_boot_vector = readl(EVP_CPU_RESET_VECTOR); 78 + writel(boot_vector, EVP_CPU_RESET_VECTOR); 79 + 80 + /* enable cpu clock on cpu1 */ 81 + reg = readl(CLK_RST_CONTROLLER_CLK_CPU_CMPLX); 82 + writel(reg & ~(1<<9), CLK_RST_CONTROLLER_CLK_CPU_CMPLX); 83 + 84 + reg = (1<<13) | (1<<9) | (1<<5) | (1<<1); 85 + writel(reg, CLK_RST_CONTROLLER_RST_CPU_CMPLX_CLR); 86 + 87 + smp_wmb(); 88 + flush_cache_all(); 89 + 90 + /* unhalt the cpu */ 91 + writel(0, IO_ADDRESS(TEGRA_FLOW_CTRL_BASE) + 0x14); 92 + 93 + timeout = jiffies + (1 * HZ); 94 + while (time_before(jiffies, timeout)) { 95 + if (readl(EVP_CPU_RESET_VECTOR) != boot_vector) 96 + break; 97 + udelay(10); 98 + } 99 + 100 + /* put the old boot vector back */ 101 + writel(old_boot_vector, EVP_CPU_RESET_VECTOR); 102 + 103 + /* 104 + * now the secondary core is starting up let it run its 105 + * calibrations, then wait for it to finish 106 + */ 107 + spin_unlock(&boot_lock); 108 + 109 + return 0; 110 + } 111 + 112 + /* 113 + * Initialise the CPU possible map early - this describes the CPUs 114 + * which may be present or become present in the system. 115 + */ 116 + void __init smp_init_cpus(void) 117 + { 118 + unsigned int i, ncores = scu_get_core_count(scu_base); 119 + 120 + for (i = 0; i < ncores; i++) 121 + cpu_set(i, cpu_possible_map); 122 + } 123 + 124 + void __init smp_prepare_cpus(unsigned int max_cpus) 125 + { 126 + unsigned int ncores = scu_get_core_count(scu_base); 127 + unsigned int cpu = smp_processor_id(); 128 + int i; 129 + 130 + smp_store_cpu_info(cpu); 131 + 132 + /* 133 + * are we trying to boot more cores than exist? 134 + */ 135 + if (max_cpus > ncores) 136 + max_cpus = ncores; 137 + 138 + /* 139 + * Initialise the present map, which describes the set of CPUs 140 + * actually populated at the present time. 141 + */ 142 + for (i = 0; i < max_cpus; i++) 143 + set_cpu_present(i, true); 144 + 145 + /* 146 + * Initialise the SCU if there are more than one CPU and let 147 + * them know where to start. Note that, on modern versions of 148 + * MILO, the "poke" doesn't actually do anything until each 149 + * individual core is sent a soft interrupt to get it out of 150 + * WFI 151 + */ 152 + if (max_cpus > 1) { 153 + percpu_timer_setup(); 154 + scu_enable(scu_base); 155 + } 156 + }
+1359
arch/arm/mach-tegra/tegra2_clocks.c
··· 1 + /* 2 + * arch/arm/mach-tegra/tegra2_clocks.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #include <linux/kernel.h> 21 + #include <linux/module.h> 22 + #include <linux/list.h> 23 + #include <linux/spinlock.h> 24 + #include <linux/delay.h> 25 + #include <linux/io.h> 26 + #include <linux/hrtimer.h> 27 + 28 + #include <asm/clkdev.h> 29 + 30 + #include <mach/iomap.h> 31 + 32 + #include "clock.h" 33 + 34 + #define RST_DEVICES 0x004 35 + #define RST_DEVICES_SET 0x300 36 + #define RST_DEVICES_CLR 0x304 37 + 38 + #define CLK_OUT_ENB 0x010 39 + #define CLK_OUT_ENB_SET 0x320 40 + #define CLK_OUT_ENB_CLR 0x324 41 + 42 + #define OSC_CTRL 0x50 43 + #define OSC_CTRL_OSC_FREQ_MASK (3<<30) 44 + #define OSC_CTRL_OSC_FREQ_13MHZ (0<<30) 45 + #define OSC_CTRL_OSC_FREQ_19_2MHZ (1<<30) 46 + #define OSC_CTRL_OSC_FREQ_12MHZ (2<<30) 47 + #define OSC_CTRL_OSC_FREQ_26MHZ (3<<30) 48 + 49 + #define OSC_FREQ_DET 0x58 50 + #define OSC_FREQ_DET_TRIG (1<<31) 51 + 52 + #define OSC_FREQ_DET_STATUS 0x5C 53 + #define OSC_FREQ_DET_BUSY (1<<31) 54 + #define OSC_FREQ_DET_CNT_MASK 0xFFFF 55 + 56 + #define PERIPH_CLK_SOURCE_MASK (3<<30) 57 + #define PERIPH_CLK_SOURCE_SHIFT 30 58 + #define PERIPH_CLK_SOURCE_ENABLE (1<<28) 59 + #define PERIPH_CLK_SOURCE_DIV_MASK 0xFF 60 + #define PERIPH_CLK_SOURCE_DIV_SHIFT 0 61 + 62 + #define PLL_BASE 0x0 63 + #define PLL_BASE_BYPASS (1<<31) 64 + #define PLL_BASE_ENABLE (1<<30) 65 + #define PLL_BASE_REF_ENABLE (1<<29) 66 + #define PLL_BASE_OVERRIDE (1<<28) 67 + #define PLL_BASE_LOCK (1<<27) 68 + #define PLL_BASE_DIVP_MASK (0x7<<20) 69 + #define PLL_BASE_DIVP_SHIFT 20 70 + #define PLL_BASE_DIVN_MASK (0x3FF<<8) 71 + #define PLL_BASE_DIVN_SHIFT 8 72 + #define PLL_BASE_DIVM_MASK (0x1F) 73 + #define PLL_BASE_DIVM_SHIFT 0 74 + 75 + #define PLL_OUT_RATIO_MASK (0xFF<<8) 76 + #define PLL_OUT_RATIO_SHIFT 8 77 + #define PLL_OUT_OVERRIDE (1<<2) 78 + #define PLL_OUT_CLKEN (1<<1) 79 + #define PLL_OUT_RESET_DISABLE (1<<0) 80 + 81 + #define PLL_MISC(c) (((c)->flags & PLL_ALT_MISC_REG) ? 0x4 : 0xc) 82 + #define PLL_MISC_DCCON_SHIFT 20 83 + #define PLL_MISC_LOCK_ENABLE (1<<18) 84 + #define PLL_MISC_CPCON_SHIFT 8 85 + #define PLL_MISC_CPCON_MASK (0xF<<PLL_MISC_CPCON_SHIFT) 86 + #define PLL_MISC_LFCON_SHIFT 4 87 + #define PLL_MISC_LFCON_MASK (0xF<<PLL_MISC_LFCON_SHIFT) 88 + #define PLL_MISC_VCOCON_SHIFT 0 89 + #define PLL_MISC_VCOCON_MASK (0xF<<PLL_MISC_VCOCON_SHIFT) 90 + 91 + #define PLLD_MISC_CLKENABLE (1<<30) 92 + #define PLLD_MISC_DIV_RST (1<<23) 93 + #define PLLD_MISC_DCCON_SHIFT 12 94 + 95 + #define PERIPH_CLK_TO_ENB_REG(c) ((c->clk_num / 32) * 4) 96 + #define PERIPH_CLK_TO_ENB_SET_REG(c) ((c->clk_num / 32) * 8) 97 + #define PERIPH_CLK_TO_ENB_BIT(c) (1 << (c->clk_num % 32)) 98 + 99 + #define SUPER_CLK_MUX 0x00 100 + #define SUPER_STATE_SHIFT 28 101 + #define SUPER_STATE_MASK (0xF << SUPER_STATE_SHIFT) 102 + #define SUPER_STATE_STANDBY (0x0 << SUPER_STATE_SHIFT) 103 + #define SUPER_STATE_IDLE (0x1 << SUPER_STATE_SHIFT) 104 + #define SUPER_STATE_RUN (0x2 << SUPER_STATE_SHIFT) 105 + #define SUPER_STATE_IRQ (0x3 << SUPER_STATE_SHIFT) 106 + #define SUPER_STATE_FIQ (0x4 << SUPER_STATE_SHIFT) 107 + #define SUPER_SOURCE_MASK 0xF 108 + #define SUPER_FIQ_SOURCE_SHIFT 12 109 + #define SUPER_IRQ_SOURCE_SHIFT 8 110 + #define SUPER_RUN_SOURCE_SHIFT 4 111 + #define SUPER_IDLE_SOURCE_SHIFT 0 112 + 113 + #define SUPER_CLK_DIVIDER 0x04 114 + 115 + #define BUS_CLK_DISABLE (1<<3) 116 + #define BUS_CLK_DIV_MASK 0x3 117 + 118 + static void __iomem *reg_clk_base = IO_ADDRESS(TEGRA_CLK_RESET_BASE); 119 + 120 + #define clk_writel(value, reg) \ 121 + __raw_writel(value, (u32)reg_clk_base + (reg)) 122 + #define clk_readl(reg) \ 123 + __raw_readl((u32)reg_clk_base + (reg)) 124 + 125 + unsigned long clk_measure_input_freq(void) 126 + { 127 + u32 clock_autodetect; 128 + clk_writel(OSC_FREQ_DET_TRIG | 1, OSC_FREQ_DET); 129 + do {} while (clk_readl(OSC_FREQ_DET_STATUS) & OSC_FREQ_DET_BUSY); 130 + clock_autodetect = clk_readl(OSC_FREQ_DET_STATUS); 131 + if (clock_autodetect >= 732 - 3 && clock_autodetect <= 732 + 3) { 132 + return 12000000; 133 + } else if (clock_autodetect >= 794 - 3 && clock_autodetect <= 794 + 3) { 134 + return 13000000; 135 + } else if (clock_autodetect >= 1172 - 3 && clock_autodetect <= 1172 + 3) { 136 + return 19200000; 137 + } else if (clock_autodetect >= 1587 - 3 && clock_autodetect <= 1587 + 3) { 138 + return 26000000; 139 + } else { 140 + pr_err("%s: Unexpected clock autodetect value %d", __func__, clock_autodetect); 141 + BUG(); 142 + return 0; 143 + } 144 + } 145 + 146 + static int clk_div71_get_divider(struct clk *c, unsigned long rate) 147 + { 148 + unsigned long divider_u71; 149 + 150 + divider_u71 = DIV_ROUND_UP(c->rate * 2, rate); 151 + 152 + if (divider_u71 - 2 > 255 || divider_u71 - 2 < 0) 153 + return -EINVAL; 154 + 155 + return divider_u71 - 2; 156 + } 157 + 158 + static unsigned long tegra2_clk_recalculate_rate(struct clk *c) 159 + { 160 + unsigned long rate; 161 + rate = c->parent->rate; 162 + 163 + if (c->mul != 0 && c->div != 0) 164 + c->rate = rate * c->mul / c->div; 165 + else 166 + c->rate = rate; 167 + return c->rate; 168 + } 169 + 170 + 171 + /* clk_m functions */ 172 + static unsigned long tegra2_clk_m_autodetect_rate(struct clk *c) 173 + { 174 + u32 auto_clock_control = clk_readl(OSC_CTRL) & ~OSC_CTRL_OSC_FREQ_MASK; 175 + 176 + c->rate = clk_measure_input_freq(); 177 + switch (c->rate) { 178 + case 12000000: 179 + auto_clock_control |= OSC_CTRL_OSC_FREQ_12MHZ; 180 + break; 181 + case 13000000: 182 + auto_clock_control |= OSC_CTRL_OSC_FREQ_13MHZ; 183 + break; 184 + case 19200000: 185 + auto_clock_control |= OSC_CTRL_OSC_FREQ_19_2MHZ; 186 + break; 187 + case 26000000: 188 + auto_clock_control |= OSC_CTRL_OSC_FREQ_26MHZ; 189 + break; 190 + default: 191 + pr_err("%s: Unexpected clock rate %ld", __func__, c->rate); 192 + BUG(); 193 + } 194 + clk_writel(auto_clock_control, OSC_CTRL); 195 + return c->rate; 196 + } 197 + 198 + static void tegra2_clk_m_init(struct clk *c) 199 + { 200 + pr_debug("%s on clock %s\n", __func__, c->name); 201 + tegra2_clk_m_autodetect_rate(c); 202 + } 203 + 204 + static int tegra2_clk_m_enable(struct clk *c) 205 + { 206 + pr_debug("%s on clock %s\n", __func__, c->name); 207 + return 0; 208 + } 209 + 210 + static void tegra2_clk_m_disable(struct clk *c) 211 + { 212 + pr_debug("%s on clock %s\n", __func__, c->name); 213 + BUG(); 214 + } 215 + 216 + static struct clk_ops tegra_clk_m_ops = { 217 + .init = tegra2_clk_m_init, 218 + .enable = tegra2_clk_m_enable, 219 + .disable = tegra2_clk_m_disable, 220 + }; 221 + 222 + /* super clock functions */ 223 + /* "super clocks" on tegra have two-stage muxes and a clock skipping 224 + * super divider. We will ignore the clock skipping divider, since we 225 + * can't lower the voltage when using the clock skip, but we can if we 226 + * lower the PLL frequency. 227 + */ 228 + static void tegra2_super_clk_init(struct clk *c) 229 + { 230 + u32 val; 231 + int source; 232 + int shift; 233 + const struct clk_mux_sel *sel; 234 + val = clk_readl(c->reg + SUPER_CLK_MUX); 235 + c->state = ON; 236 + BUG_ON(((val & SUPER_STATE_MASK) != SUPER_STATE_RUN) && 237 + ((val & SUPER_STATE_MASK) != SUPER_STATE_IDLE)); 238 + shift = ((val & SUPER_STATE_MASK) == SUPER_STATE_IDLE) ? 239 + SUPER_IDLE_SOURCE_SHIFT : SUPER_RUN_SOURCE_SHIFT; 240 + source = (val >> shift) & SUPER_SOURCE_MASK; 241 + for (sel = c->inputs; sel->input != NULL; sel++) { 242 + if (sel->value == source) 243 + break; 244 + } 245 + BUG_ON(sel->input == NULL); 246 + c->parent = sel->input; 247 + tegra2_clk_recalculate_rate(c); 248 + } 249 + 250 + static int tegra2_super_clk_enable(struct clk *c) 251 + { 252 + clk_writel(0, c->reg + SUPER_CLK_DIVIDER); 253 + return 0; 254 + } 255 + 256 + static void tegra2_super_clk_disable(struct clk *c) 257 + { 258 + pr_debug("%s on clock %s\n", __func__, c->name); 259 + 260 + /* oops - don't disable the CPU clock! */ 261 + BUG(); 262 + } 263 + 264 + static int tegra2_super_clk_set_parent(struct clk *c, struct clk *p) 265 + { 266 + u32 val; 267 + const struct clk_mux_sel *sel; 268 + int shift; 269 + val = clk_readl(c->reg + SUPER_CLK_MUX);; 270 + BUG_ON(((val & SUPER_STATE_MASK) != SUPER_STATE_RUN) && 271 + ((val & SUPER_STATE_MASK) != SUPER_STATE_IDLE)); 272 + shift = ((val & SUPER_STATE_MASK) == SUPER_STATE_IDLE) ? 273 + SUPER_IDLE_SOURCE_SHIFT : SUPER_RUN_SOURCE_SHIFT; 274 + for (sel = c->inputs; sel->input != NULL; sel++) { 275 + if (sel->input == p) { 276 + clk_reparent(c, p); 277 + val &= ~(SUPER_SOURCE_MASK << shift); 278 + val |= sel->value << shift; 279 + clk_writel(val, c->reg); 280 + c->rate = c->parent->rate; 281 + return 0; 282 + } 283 + } 284 + return -EINVAL; 285 + } 286 + 287 + static struct clk_ops tegra_super_ops = { 288 + .init = tegra2_super_clk_init, 289 + .enable = tegra2_super_clk_enable, 290 + .disable = tegra2_super_clk_disable, 291 + .set_parent = tegra2_super_clk_set_parent, 292 + .recalculate_rate = tegra2_clk_recalculate_rate, 293 + }; 294 + 295 + /* bus clock functions */ 296 + static void tegra2_bus_clk_init(struct clk *c) 297 + { 298 + u32 val = clk_readl(c->reg); 299 + c->state = ((val >> c->reg_shift) & BUS_CLK_DISABLE) ? OFF : ON; 300 + c->div = ((val >> c->reg_shift) & BUS_CLK_DIV_MASK) + 1; 301 + c->mul = 1; 302 + tegra2_clk_recalculate_rate(c); 303 + } 304 + 305 + static int tegra2_bus_clk_enable(struct clk *c) 306 + { 307 + u32 val = clk_readl(c->reg); 308 + val &= ~(BUS_CLK_DISABLE << c->reg_shift); 309 + clk_writel(val, c->reg); 310 + return 0; 311 + } 312 + 313 + static void tegra2_bus_clk_disable(struct clk *c) 314 + { 315 + u32 val = clk_readl(c->reg); 316 + val |= BUS_CLK_DISABLE << c->reg_shift; 317 + clk_writel(val, c->reg); 318 + } 319 + 320 + static int tegra2_bus_clk_set_rate(struct clk *c, unsigned long rate) 321 + { 322 + u32 val = clk_readl(c->reg); 323 + unsigned long parent_rate = c->parent->rate; 324 + int i; 325 + for (i = 1; i <= 4; i++) { 326 + if (rate == parent_rate / i) { 327 + val &= ~(BUS_CLK_DIV_MASK << c->reg_shift); 328 + val |= (i - 1) << c->reg_shift; 329 + clk_writel(val, c->reg); 330 + c->div = i; 331 + c->mul = 1; 332 + return 0; 333 + } 334 + } 335 + return -EINVAL; 336 + } 337 + 338 + static struct clk_ops tegra_bus_ops = { 339 + .init = tegra2_bus_clk_init, 340 + .enable = tegra2_bus_clk_enable, 341 + .disable = tegra2_bus_clk_disable, 342 + .set_rate = tegra2_bus_clk_set_rate, 343 + .recalculate_rate = tegra2_clk_recalculate_rate, 344 + }; 345 + 346 + /* PLL Functions */ 347 + static unsigned long tegra2_pll_clk_recalculate_rate(struct clk *c) 348 + { 349 + u64 rate; 350 + rate = c->parent->rate; 351 + rate *= c->n; 352 + do_div(rate, c->m); 353 + if (c->p == 2) 354 + rate >>= 1; 355 + c->rate = rate; 356 + return c->rate; 357 + } 358 + 359 + static int tegra2_pll_clk_wait_for_lock(struct clk *c) 360 + { 361 + ktime_t before; 362 + 363 + before = ktime_get(); 364 + while (!(clk_readl(c->reg + PLL_BASE) & PLL_BASE_LOCK)) { 365 + if (ktime_us_delta(ktime_get(), before) > 5000) { 366 + pr_err("Timed out waiting for lock bit on pll %s", 367 + c->name); 368 + return -1; 369 + } 370 + } 371 + 372 + return 0; 373 + } 374 + 375 + static void tegra2_pll_clk_init(struct clk *c) 376 + { 377 + u32 val = clk_readl(c->reg + PLL_BASE); 378 + 379 + c->state = (val & PLL_BASE_ENABLE) ? ON : OFF; 380 + 381 + if (c->flags & PLL_FIXED && !(val & PLL_BASE_OVERRIDE)) { 382 + pr_warning("Clock %s has unknown fixed frequency\n", c->name); 383 + c->n = 1; 384 + c->m = 0; 385 + c->p = 1; 386 + } else if (val & PLL_BASE_BYPASS) { 387 + c->n = 1; 388 + c->m = 1; 389 + c->p = 1; 390 + } else { 391 + c->n = (val & PLL_BASE_DIVN_MASK) >> PLL_BASE_DIVN_SHIFT; 392 + c->m = (val & PLL_BASE_DIVM_MASK) >> PLL_BASE_DIVM_SHIFT; 393 + c->p = (val & PLL_BASE_DIVP_MASK) ? 2 : 1; 394 + } 395 + 396 + val = clk_readl(c->reg + PLL_MISC(c)); 397 + if (c->flags & PLL_HAS_CPCON) 398 + c->cpcon = (val & PLL_MISC_CPCON_MASK) >> PLL_MISC_CPCON_SHIFT; 399 + 400 + tegra2_pll_clk_recalculate_rate(c); 401 + } 402 + 403 + static int tegra2_pll_clk_enable(struct clk *c) 404 + { 405 + u32 val; 406 + pr_debug("%s on clock %s\n", __func__, c->name); 407 + 408 + val = clk_readl(c->reg + PLL_BASE); 409 + val &= ~PLL_BASE_BYPASS; 410 + val |= PLL_BASE_ENABLE; 411 + clk_writel(val, c->reg + PLL_BASE); 412 + 413 + val = clk_readl(c->reg + PLL_MISC(c)); 414 + val |= PLL_MISC_LOCK_ENABLE; 415 + clk_writel(val, c->reg + PLL_MISC(c)); 416 + 417 + tegra2_pll_clk_wait_for_lock(c); 418 + 419 + return 0; 420 + } 421 + 422 + static void tegra2_pll_clk_disable(struct clk *c) 423 + { 424 + u32 val; 425 + pr_debug("%s on clock %s\n", __func__, c->name); 426 + 427 + val = clk_readl(c->reg); 428 + val &= ~(PLL_BASE_BYPASS | PLL_BASE_ENABLE); 429 + clk_writel(val, c->reg); 430 + } 431 + 432 + static int tegra2_pll_clk_set_rate(struct clk *c, unsigned long rate) 433 + { 434 + u32 val; 435 + unsigned long input_rate; 436 + const struct clk_pll_table *sel; 437 + 438 + pr_debug("%s: %s %lu\n", __func__, c->name, rate); 439 + BUG_ON(c->refcnt != 0); 440 + 441 + input_rate = c->parent->rate; 442 + for (sel = c->pll_table; sel->input_rate != 0; sel++) { 443 + if (sel->input_rate == input_rate && sel->output_rate == rate) { 444 + c->n = sel->n; 445 + c->m = sel->m; 446 + c->p = sel->p; 447 + c->cpcon = sel->cpcon; 448 + 449 + val = clk_readl(c->reg + PLL_BASE); 450 + if (c->flags & PLL_FIXED) 451 + val |= PLL_BASE_OVERRIDE; 452 + val &= ~(PLL_BASE_DIVP_MASK | PLL_BASE_DIVN_MASK | 453 + PLL_BASE_DIVM_MASK); 454 + val |= (c->m << PLL_BASE_DIVM_SHIFT) | 455 + (c->n << PLL_BASE_DIVN_SHIFT); 456 + BUG_ON(c->p > 2); 457 + if (c->p == 2) 458 + val |= 1 << PLL_BASE_DIVP_SHIFT; 459 + clk_writel(val, c->reg + PLL_BASE); 460 + 461 + if (c->flags & PLL_HAS_CPCON) { 462 + val = c->cpcon << PLL_MISC_CPCON_SHIFT; 463 + val |= PLL_MISC_LOCK_ENABLE; 464 + clk_writel(val, c->reg + PLL_MISC(c)); 465 + } 466 + 467 + if (c->state == ON) 468 + tegra2_pll_clk_enable(c); 469 + 470 + c->rate = rate; 471 + return 0; 472 + } 473 + } 474 + return -EINVAL; 475 + } 476 + 477 + static struct clk_ops tegra_pll_ops = { 478 + .init = tegra2_pll_clk_init, 479 + .enable = tegra2_pll_clk_enable, 480 + .disable = tegra2_pll_clk_disable, 481 + .set_rate = tegra2_pll_clk_set_rate, 482 + .recalculate_rate = tegra2_pll_clk_recalculate_rate, 483 + }; 484 + 485 + /* Clock divider ops */ 486 + static void tegra2_pll_div_clk_init(struct clk *c) 487 + { 488 + u32 val = clk_readl(c->reg); 489 + u32 divu71; 490 + val >>= c->reg_shift; 491 + c->state = (val & PLL_OUT_CLKEN) ? ON : OFF; 492 + if (!(val & PLL_OUT_RESET_DISABLE)) 493 + c->state = OFF; 494 + 495 + if (c->flags & DIV_U71) { 496 + divu71 = (val & PLL_OUT_RATIO_MASK) >> PLL_OUT_RATIO_SHIFT; 497 + c->div = (divu71 + 2); 498 + c->mul = 2; 499 + } else if (c->flags & DIV_2) { 500 + c->div = 2; 501 + c->mul = 1; 502 + } else { 503 + c->div = 1; 504 + c->mul = 1; 505 + } 506 + 507 + tegra2_clk_recalculate_rate(c); 508 + } 509 + 510 + static int tegra2_pll_div_clk_enable(struct clk *c) 511 + { 512 + u32 val; 513 + u32 new_val; 514 + 515 + pr_debug("%s: %s\n", __func__, c->name); 516 + if (c->flags & DIV_U71) { 517 + val = clk_readl(c->reg); 518 + new_val = val >> c->reg_shift; 519 + new_val &= 0xFFFF; 520 + 521 + new_val |= PLL_OUT_CLKEN | PLL_OUT_RESET_DISABLE; 522 + 523 + val &= ~(0xFFFF << c->reg_shift); 524 + val |= new_val << c->reg_shift; 525 + clk_writel(val, c->reg); 526 + return 0; 527 + } else if (c->flags & DIV_2) { 528 + BUG_ON(!(c->flags & PLLD)); 529 + val = clk_readl(c->reg); 530 + val &= ~PLLD_MISC_DIV_RST; 531 + clk_writel(val, c->reg); 532 + return 0; 533 + } 534 + return -EINVAL; 535 + } 536 + 537 + static void tegra2_pll_div_clk_disable(struct clk *c) 538 + { 539 + u32 val; 540 + u32 new_val; 541 + 542 + pr_debug("%s: %s\n", __func__, c->name); 543 + if (c->flags & DIV_U71) { 544 + val = clk_readl(c->reg); 545 + new_val = val >> c->reg_shift; 546 + new_val &= 0xFFFF; 547 + 548 + new_val &= ~(PLL_OUT_CLKEN | PLL_OUT_RESET_DISABLE); 549 + 550 + val &= ~(0xFFFF << c->reg_shift); 551 + val |= new_val << c->reg_shift; 552 + clk_writel(val, c->reg); 553 + } else if (c->flags & DIV_2) { 554 + BUG_ON(!(c->flags & PLLD)); 555 + val = clk_readl(c->reg); 556 + val |= PLLD_MISC_DIV_RST; 557 + clk_writel(val, c->reg); 558 + } 559 + } 560 + 561 + static int tegra2_pll_div_clk_set_rate(struct clk *c, unsigned long rate) 562 + { 563 + u32 val; 564 + u32 new_val; 565 + int divider_u71; 566 + pr_debug("%s: %s %lu\n", __func__, c->name, rate); 567 + if (c->flags & DIV_U71) { 568 + divider_u71 = clk_div71_get_divider(c->parent, rate); 569 + if (divider_u71 >= 0) { 570 + val = clk_readl(c->reg); 571 + new_val = val >> c->reg_shift; 572 + new_val &= 0xFFFF; 573 + if (c->flags & DIV_U71_FIXED) 574 + new_val |= PLL_OUT_OVERRIDE; 575 + new_val &= ~PLL_OUT_RATIO_MASK; 576 + new_val |= divider_u71 << PLL_OUT_RATIO_SHIFT; 577 + 578 + val &= ~(0xFFFF << c->reg_shift); 579 + val |= new_val << c->reg_shift; 580 + clk_writel(val, c->reg); 581 + c->div = divider_u71 + 2; 582 + c->mul = 2; 583 + tegra2_clk_recalculate_rate(c); 584 + return 0; 585 + } 586 + } else if (c->flags & DIV_2) { 587 + if (c->parent->rate == rate * 2) { 588 + c->rate = rate; 589 + return 0; 590 + } 591 + } 592 + return -EINVAL; 593 + } 594 + 595 + 596 + static struct clk_ops tegra_pll_div_ops = { 597 + .init = tegra2_pll_div_clk_init, 598 + .enable = tegra2_pll_div_clk_enable, 599 + .disable = tegra2_pll_div_clk_disable, 600 + .set_rate = tegra2_pll_div_clk_set_rate, 601 + .recalculate_rate = tegra2_clk_recalculate_rate, 602 + }; 603 + 604 + /* Periph clk ops */ 605 + 606 + static void tegra2_periph_clk_init(struct clk *c) 607 + { 608 + u32 val = clk_readl(c->reg); 609 + const struct clk_mux_sel *mux = 0; 610 + const struct clk_mux_sel *sel; 611 + if (c->flags & MUX) { 612 + for (sel = c->inputs; sel->input != NULL; sel++) { 613 + if (val >> PERIPH_CLK_SOURCE_SHIFT == sel->value) 614 + mux = sel; 615 + } 616 + BUG_ON(!mux); 617 + 618 + c->parent = mux->input; 619 + } else { 620 + c->parent = c->inputs[0].input; 621 + } 622 + 623 + if (c->flags & DIV_U71) { 624 + u32 divu71 = val & PERIPH_CLK_SOURCE_DIV_MASK; 625 + c->div = divu71 + 2; 626 + c->mul = 2; 627 + } else { 628 + c->div = 1; 629 + c->mul = 1; 630 + } 631 + 632 + c->state = ON; 633 + if (!(clk_readl(CLK_OUT_ENB + PERIPH_CLK_TO_ENB_REG(c)) & 634 + PERIPH_CLK_TO_ENB_BIT(c))) 635 + c->state = OFF; 636 + if (!(c->flags & PERIPH_NO_RESET)) 637 + if (clk_readl(RST_DEVICES + PERIPH_CLK_TO_ENB_REG(c)) & 638 + PERIPH_CLK_TO_ENB_BIT(c)) 639 + c->state = OFF; 640 + tegra2_clk_recalculate_rate(c); 641 + } 642 + 643 + static int tegra2_periph_clk_enable(struct clk *c) 644 + { 645 + u32 val; 646 + pr_debug("%s on clock %s\n", __func__, c->name); 647 + 648 + clk_writel(PERIPH_CLK_TO_ENB_BIT(c), 649 + CLK_OUT_ENB_SET + PERIPH_CLK_TO_ENB_SET_REG(c)); 650 + if (!(c->flags & PERIPH_NO_RESET) && !(c->flags & PERIPH_MANUAL_RESET)) 651 + clk_writel(PERIPH_CLK_TO_ENB_BIT(c), 652 + RST_DEVICES_CLR + PERIPH_CLK_TO_ENB_SET_REG(c)); 653 + if (c->flags & PERIPH_EMC_ENB) { 654 + /* The EMC peripheral clock has 2 extra enable bits */ 655 + /* FIXME: Do they need to be disabled? */ 656 + val = clk_readl(c->reg); 657 + val |= 0x3 << 24; 658 + clk_writel(val, c->reg); 659 + } 660 + return 0; 661 + } 662 + 663 + static void tegra2_periph_clk_disable(struct clk *c) 664 + { 665 + pr_debug("%s on clock %s\n", __func__, c->name); 666 + 667 + clk_writel(PERIPH_CLK_TO_ENB_BIT(c), 668 + CLK_OUT_ENB_CLR + PERIPH_CLK_TO_ENB_SET_REG(c)); 669 + } 670 + 671 + void tegra2_periph_reset_deassert(struct clk *c) 672 + { 673 + pr_debug("%s on clock %s\n", __func__, c->name); 674 + if (!(c->flags & PERIPH_NO_RESET)) 675 + clk_writel(PERIPH_CLK_TO_ENB_BIT(c), 676 + RST_DEVICES_CLR + PERIPH_CLK_TO_ENB_SET_REG(c)); 677 + } 678 + 679 + void tegra2_periph_reset_assert(struct clk *c) 680 + { 681 + pr_debug("%s on clock %s\n", __func__, c->name); 682 + if (!(c->flags & PERIPH_NO_RESET)) 683 + clk_writel(PERIPH_CLK_TO_ENB_BIT(c), 684 + RST_DEVICES_SET + PERIPH_CLK_TO_ENB_SET_REG(c)); 685 + } 686 + 687 + 688 + static int tegra2_periph_clk_set_parent(struct clk *c, struct clk *p) 689 + { 690 + u32 val; 691 + const struct clk_mux_sel *sel; 692 + pr_debug("%s: %s %s\n", __func__, c->name, p->name); 693 + for (sel = c->inputs; sel->input != NULL; sel++) { 694 + if (sel->input == p) { 695 + clk_reparent(c, p); 696 + val = clk_readl(c->reg); 697 + val &= ~PERIPH_CLK_SOURCE_MASK; 698 + val |= (sel->value) << PERIPH_CLK_SOURCE_SHIFT; 699 + clk_writel(val, c->reg); 700 + c->rate = c->parent->rate; 701 + return 0; 702 + } 703 + } 704 + 705 + return -EINVAL; 706 + } 707 + 708 + static int tegra2_periph_clk_set_rate(struct clk *c, unsigned long rate) 709 + { 710 + u32 val; 711 + int divider_u71; 712 + pr_debug("%s: %lu\n", __func__, rate); 713 + if (c->flags & DIV_U71) { 714 + divider_u71 = clk_div71_get_divider(c->parent, rate); 715 + if (divider_u71 >= 0) { 716 + val = clk_readl(c->reg); 717 + val &= ~PERIPH_CLK_SOURCE_DIV_MASK; 718 + val |= divider_u71; 719 + clk_writel(val, c->reg); 720 + c->div = divider_u71 + 2; 721 + c->mul = 2; 722 + tegra2_clk_recalculate_rate(c); 723 + return 0; 724 + } 725 + } 726 + return -EINVAL; 727 + } 728 + 729 + static struct clk_ops tegra_periph_clk_ops = { 730 + .init = &tegra2_periph_clk_init, 731 + .enable = &tegra2_periph_clk_enable, 732 + .disable = &tegra2_periph_clk_disable, 733 + .set_parent = &tegra2_periph_clk_set_parent, 734 + .set_rate = &tegra2_periph_clk_set_rate, 735 + .recalculate_rate = &tegra2_clk_recalculate_rate, 736 + }; 737 + 738 + /* Clock doubler ops */ 739 + static void tegra2_clk_double_init(struct clk *c) 740 + { 741 + c->mul = 2; 742 + c->div = 1; 743 + c->state = ON; 744 + if (!(clk_readl(CLK_OUT_ENB + PERIPH_CLK_TO_ENB_REG(c)) & 745 + PERIPH_CLK_TO_ENB_BIT(c))) 746 + c->state = OFF; 747 + tegra2_clk_recalculate_rate(c); 748 + }; 749 + 750 + static struct clk_ops tegra_clk_double_ops = { 751 + .init = &tegra2_clk_double_init, 752 + .enable = &tegra2_periph_clk_enable, 753 + .disable = &tegra2_periph_clk_disable, 754 + .recalculate_rate = &tegra2_clk_recalculate_rate, 755 + }; 756 + 757 + /* Clock definitions */ 758 + static struct clk tegra_clk_32k = { 759 + .name = "clk_32k", 760 + .rate = 32678, 761 + .ops = NULL, 762 + }; 763 + 764 + static struct clk_pll_table tegra_pll_s_table[] = { 765 + {32768, 12000000, 366, 1, 1, 0}, 766 + {32768, 13000000, 397, 1, 1, 0}, 767 + {32768, 19200000, 586, 1, 1, 0}, 768 + {32768, 26000000, 793, 1, 1, 0}, 769 + {0, 0, 0, 0, 0, 0}, 770 + }; 771 + 772 + static struct clk tegra_pll_s = { 773 + .name = "pll_s", 774 + .flags = PLL_ALT_MISC_REG, 775 + .ops = &tegra_pll_ops, 776 + .reg = 0xf0, 777 + .input_min = 32768, 778 + .input_max = 32768, 779 + .parent = &tegra_clk_32k, 780 + .cf_min = 0, /* FIXME */ 781 + .cf_max = 0, /* FIXME */ 782 + .vco_min = 12000000, 783 + .vco_max = 26000000, 784 + .pll_table = tegra_pll_s_table, 785 + }; 786 + 787 + static struct clk_mux_sel tegra_clk_m_sel[] = { 788 + { .input = &tegra_clk_32k, .value = 0}, 789 + { .input = &tegra_pll_s, .value = 1}, 790 + { 0, 0}, 791 + }; 792 + static struct clk tegra_clk_m = { 793 + .name = "clk_m", 794 + .flags = ENABLE_ON_INIT, 795 + .ops = &tegra_clk_m_ops, 796 + .inputs = tegra_clk_m_sel, 797 + .reg = 0x1fc, 798 + .reg_mask = (1<<28), 799 + .reg_shift = 28, 800 + }; 801 + 802 + static struct clk_pll_table tegra_pll_c_table[] = { 803 + { 0, 0, 0, 0, 0, 0 }, 804 + }; 805 + 806 + static struct clk tegra_pll_c = { 807 + .name = "pll_c", 808 + .flags = PLL_HAS_CPCON, 809 + .ops = &tegra_pll_ops, 810 + .reg = 0x80, 811 + .input_min = 2000000, 812 + .input_max = 31000000, 813 + .parent = &tegra_clk_m, 814 + .cf_min = 1000000, 815 + .cf_max = 6000000, 816 + .vco_min = 20000000, 817 + .vco_max = 1400000000, 818 + .pll_table = tegra_pll_c_table, 819 + }; 820 + 821 + static struct clk tegra_pll_c_out1 = { 822 + .name = "pll_c_out1", 823 + .ops = &tegra_pll_div_ops, 824 + .flags = DIV_U71, 825 + .parent = &tegra_pll_c, 826 + .reg = 0x84, 827 + .reg_shift = 0, 828 + }; 829 + 830 + static struct clk_pll_table tegra_pll_m_table[] = { 831 + { 0, 0, 0, 0, 0, 0 }, 832 + }; 833 + 834 + static struct clk tegra_pll_m = { 835 + .name = "pll_m", 836 + .flags = PLL_HAS_CPCON, 837 + .ops = &tegra_pll_ops, 838 + .reg = 0x90, 839 + .input_min = 2000000, 840 + .input_max = 31000000, 841 + .parent = &tegra_clk_m, 842 + .cf_min = 1000000, 843 + .cf_max = 6000000, 844 + .vco_min = 20000000, 845 + .vco_max = 1200000000, 846 + .pll_table = tegra_pll_m_table, 847 + }; 848 + 849 + static struct clk tegra_pll_m_out1 = { 850 + .name = "pll_m_out1", 851 + .ops = &tegra_pll_div_ops, 852 + .flags = DIV_U71, 853 + .parent = &tegra_pll_m, 854 + .reg = 0x94, 855 + .reg_shift = 0, 856 + }; 857 + 858 + static struct clk_pll_table tegra_pll_p_table[] = { 859 + { 12000000, 216000000, 432, 12, 2, 8}, 860 + { 13000000, 216000000, 432, 13, 2, 8}, 861 + { 19200000, 216000000, 90, 4, 2, 1}, 862 + { 26000000, 216000000, 432, 26, 2, 8}, 863 + { 12000000, 432000000, 432, 12, 1, 8}, 864 + { 13000000, 432000000, 432, 13, 1, 8}, 865 + { 19200000, 432000000, 90, 4, 1, 1}, 866 + { 26000000, 432000000, 432, 26, 1, 8}, 867 + { 0, 0, 0, 0, 0, 0 }, 868 + }; 869 + 870 + static struct clk tegra_pll_p = { 871 + .name = "pll_p", 872 + .flags = ENABLE_ON_INIT | PLL_FIXED | PLL_HAS_CPCON, 873 + .ops = &tegra_pll_ops, 874 + .reg = 0xa0, 875 + .input_min = 2000000, 876 + .input_max = 31000000, 877 + .parent = &tegra_clk_m, 878 + .cf_min = 1000000, 879 + .cf_max = 6000000, 880 + .vco_min = 20000000, 881 + .vco_max = 1400000000, 882 + .pll_table = tegra_pll_p_table, 883 + }; 884 + 885 + static struct clk tegra_pll_p_out1 = { 886 + .name = "pll_p_out1", 887 + .ops = &tegra_pll_div_ops, 888 + .flags = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED, 889 + .parent = &tegra_pll_p, 890 + .reg = 0xa4, 891 + .reg_shift = 0, 892 + }; 893 + 894 + static struct clk tegra_pll_p_out2 = { 895 + .name = "pll_p_out2", 896 + .ops = &tegra_pll_div_ops, 897 + .flags = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED, 898 + .parent = &tegra_pll_p, 899 + .reg = 0xa4, 900 + .reg_shift = 16, 901 + }; 902 + 903 + static struct clk tegra_pll_p_out3 = { 904 + .name = "pll_p_out3", 905 + .ops = &tegra_pll_div_ops, 906 + .flags = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED, 907 + .parent = &tegra_pll_p, 908 + .reg = 0xa8, 909 + .reg_shift = 0, 910 + }; 911 + 912 + static struct clk tegra_pll_p_out4 = { 913 + .name = "pll_p_out4", 914 + .ops = &tegra_pll_div_ops, 915 + .flags = ENABLE_ON_INIT | DIV_U71 | DIV_U71_FIXED, 916 + .parent = &tegra_pll_p, 917 + .reg = 0xa8, 918 + .reg_shift = 16, 919 + }; 920 + 921 + static struct clk_pll_table tegra_pll_a_table[] = { 922 + { 28800000, 56448000, 49, 25, 1, 1}, 923 + { 28800000, 73728000, 64, 25, 1, 1}, 924 + { 28800000, 11289600, 49, 25, 1, 1}, 925 + { 28800000, 12288000, 64, 25, 1, 1}, 926 + { 0, 0, 0, 0, 0, 0 }, 927 + }; 928 + 929 + static struct clk tegra_pll_a = { 930 + .name = "pll_a", 931 + .flags = PLL_HAS_CPCON, 932 + .ops = &tegra_pll_ops, 933 + .reg = 0xb0, 934 + .input_min = 2000000, 935 + .input_max = 31000000, 936 + .parent = &tegra_pll_p_out1, 937 + .cf_min = 1000000, 938 + .cf_max = 6000000, 939 + .vco_min = 20000000, 940 + .vco_max = 1400000000, 941 + .pll_table = tegra_pll_a_table, 942 + }; 943 + 944 + static struct clk tegra_pll_a_out0 = { 945 + .name = "pll_a_out0", 946 + .ops = &tegra_pll_div_ops, 947 + .flags = DIV_U71, 948 + .parent = &tegra_pll_a, 949 + .reg = 0xb4, 950 + .reg_shift = 0, 951 + }; 952 + 953 + static struct clk_pll_table tegra_pll_d_table[] = { 954 + { 12000000, 1000000000, 1000, 12, 1, 12}, 955 + { 13000000, 1000000000, 1000, 13, 1, 12}, 956 + { 19200000, 1000000000, 625, 12, 1, 8}, 957 + { 26000000, 1000000000, 1000, 26, 1, 12}, 958 + { 0, 0, 0, 0, 0, 0 }, 959 + }; 960 + 961 + static struct clk tegra_pll_d = { 962 + .name = "pll_d", 963 + .flags = PLL_HAS_CPCON | PLLD, 964 + .ops = &tegra_pll_ops, 965 + .reg = 0xd0, 966 + .input_min = 2000000, 967 + .input_max = 40000000, 968 + .parent = &tegra_clk_m, 969 + .cf_min = 1000000, 970 + .cf_max = 6000000, 971 + .vco_min = 40000000, 972 + .vco_max = 1000000000, 973 + .pll_table = tegra_pll_d_table, 974 + }; 975 + 976 + static struct clk tegra_pll_d_out0 = { 977 + .name = "pll_d_out0", 978 + .ops = &tegra_pll_div_ops, 979 + .flags = DIV_2 | PLLD, 980 + .parent = &tegra_pll_d, 981 + }; 982 + 983 + static struct clk_pll_table tegra_pll_u_table[] = { 984 + { 12000000, 480000000, 960, 12, 1, 0}, 985 + { 13000000, 480000000, 960, 13, 1, 0}, 986 + { 19200000, 480000000, 200, 4, 1, 0}, 987 + { 26000000, 480000000, 960, 26, 1, 0}, 988 + { 0, 0, 0, 0, 0, 0 }, 989 + }; 990 + 991 + static struct clk tegra_pll_u = { 992 + .name = "pll_u", 993 + .flags = 0, 994 + .ops = &tegra_pll_ops, 995 + .reg = 0xc0, 996 + .input_min = 2000000, 997 + .input_max = 40000000, 998 + .parent = &tegra_clk_m, 999 + .cf_min = 1000000, 1000 + .cf_max = 6000000, 1001 + .vco_min = 480000000, 1002 + .vco_max = 960000000, 1003 + .pll_table = tegra_pll_u_table, 1004 + }; 1005 + 1006 + static struct clk_pll_table tegra_pll_x_table[] = { 1007 + { 12000000, 1000000000, 1000, 12, 1, 12}, 1008 + { 13000000, 1000000000, 1000, 13, 1, 12}, 1009 + { 19200000, 1000000000, 625, 12, 1, 8}, 1010 + { 26000000, 1000000000, 1000, 26, 1, 12}, 1011 + { 12000000, 750000000, 750, 12, 1, 12}, 1012 + { 13000000, 750000000, 750, 13, 1, 12}, 1013 + { 19200000, 750000000, 625, 16, 1, 8}, 1014 + { 26000000, 750000000, 750, 26, 1, 12}, 1015 + { 0, 0, 0, 0, 0, 0 }, 1016 + }; 1017 + 1018 + static struct clk tegra_pll_x = { 1019 + .name = "pll_x", 1020 + .flags = PLL_HAS_CPCON | PLL_ALT_MISC_REG, 1021 + .ops = &tegra_pll_ops, 1022 + .reg = 0xe0, 1023 + .input_min = 2000000, 1024 + .input_max = 31000000, 1025 + .parent = &tegra_clk_m, 1026 + .cf_min = 1000000, 1027 + .cf_max = 6000000, 1028 + .vco_min = 20000000, 1029 + .vco_max = 1200000000, 1030 + .pll_table = tegra_pll_x_table, 1031 + }; 1032 + 1033 + static struct clk tegra_clk_d = { 1034 + .name = "clk_d", 1035 + .flags = PERIPH_NO_RESET, 1036 + .ops = &tegra_clk_double_ops, 1037 + .clk_num = 90, 1038 + .reg = 0x34, 1039 + .reg_shift = 12, 1040 + .parent = &tegra_clk_m, 1041 + }; 1042 + 1043 + /* FIXME: need tegra_audio 1044 + static struct clk tegra_clk_audio_2x = { 1045 + .name = "clk_d", 1046 + .flags = PERIPH_NO_RESET, 1047 + .ops = &tegra_clk_double_ops, 1048 + .clk_num = 89, 1049 + .reg = 0x34, 1050 + .reg_shift = 8, 1051 + .parent = &tegra_audio, 1052 + } 1053 + */ 1054 + 1055 + static struct clk_mux_sel mux_cclk[] = { 1056 + { .input = &tegra_clk_m, .value = 0}, 1057 + { .input = &tegra_pll_c, .value = 1}, 1058 + { .input = &tegra_clk_32k, .value = 2}, 1059 + { .input = &tegra_pll_m, .value = 3}, 1060 + { .input = &tegra_pll_p, .value = 4}, 1061 + { .input = &tegra_pll_p_out4, .value = 5}, 1062 + { .input = &tegra_pll_p_out3, .value = 6}, 1063 + { .input = &tegra_clk_d, .value = 7}, 1064 + { .input = &tegra_pll_x, .value = 8}, 1065 + { 0, 0}, 1066 + }; 1067 + 1068 + static struct clk_mux_sel mux_sclk[] = { 1069 + { .input = &tegra_clk_m, .value = 0}, 1070 + { .input = &tegra_pll_c_out1, .value = 1}, 1071 + { .input = &tegra_pll_p_out4, .value = 2}, 1072 + { .input = &tegra_pll_p_out3, .value = 3}, 1073 + { .input = &tegra_pll_p_out2, .value = 4}, 1074 + { .input = &tegra_clk_d, .value = 5}, 1075 + { .input = &tegra_clk_32k, .value = 6}, 1076 + { .input = &tegra_pll_m_out1, .value = 7}, 1077 + { 0, 0}, 1078 + }; 1079 + 1080 + static struct clk tegra_clk_cpu = { 1081 + .name = "cpu", 1082 + .inputs = mux_cclk, 1083 + .reg = 0x20, 1084 + .ops = &tegra_super_ops, 1085 + }; 1086 + 1087 + static struct clk tegra_clk_sys = { 1088 + .name = "sys", 1089 + .inputs = mux_sclk, 1090 + .reg = 0x28, 1091 + .ops = &tegra_super_ops, 1092 + }; 1093 + 1094 + static struct clk tegra_clk_hclk = { 1095 + .name = "hclk", 1096 + .flags = DIV_BUS, 1097 + .parent = &tegra_clk_sys, 1098 + .reg = 0x30, 1099 + .reg_shift = 4, 1100 + .ops = &tegra_bus_ops, 1101 + }; 1102 + 1103 + static struct clk tegra_clk_pclk = { 1104 + .name = "pclk", 1105 + .flags = DIV_BUS, 1106 + .parent = &tegra_clk_hclk, 1107 + .reg = 0x30, 1108 + .reg_shift = 0, 1109 + .ops = &tegra_bus_ops, 1110 + }; 1111 + 1112 + static struct clk_mux_sel mux_pllm_pllc_pllp_plla[] = { 1113 + { .input = &tegra_pll_m, .value = 0}, 1114 + { .input = &tegra_pll_c, .value = 1}, 1115 + { .input = &tegra_pll_p, .value = 2}, 1116 + { .input = &tegra_pll_a_out0, .value = 3}, 1117 + { 0, 0}, 1118 + }; 1119 + 1120 + static struct clk_mux_sel mux_pllm_pllc_pllp_clkm[] = { 1121 + { .input = &tegra_pll_m, .value = 0}, 1122 + { .input = &tegra_pll_c, .value = 1}, 1123 + { .input = &tegra_pll_p, .value = 2}, 1124 + { .input = &tegra_clk_m, .value = 3}, 1125 + { 0, 0}, 1126 + }; 1127 + 1128 + static struct clk_mux_sel mux_pllp_pllc_pllm_clkm[] = { 1129 + { .input = &tegra_pll_p, .value = 0}, 1130 + { .input = &tegra_pll_c, .value = 1}, 1131 + { .input = &tegra_pll_m, .value = 2}, 1132 + { .input = &tegra_clk_m, .value = 3}, 1133 + { 0, 0}, 1134 + }; 1135 + 1136 + static struct clk_mux_sel mux_plla_audio_pllp_clkm[] = { 1137 + {.input = &tegra_pll_a, .value = 0}, 1138 + /* FIXME: no mux defined for tegra_audio 1139 + {.input = &tegra_audio, .value = 1},*/ 1140 + {.input = &tegra_pll_p, .value = 2}, 1141 + {.input = &tegra_clk_m, .value = 3}, 1142 + { 0, 0}, 1143 + }; 1144 + 1145 + static struct clk_mux_sel mux_pllp_plld_pllc_clkm[] = { 1146 + {.input = &tegra_pll_p, .value = 0}, 1147 + {.input = &tegra_pll_d_out0, .value = 1}, 1148 + {.input = &tegra_pll_c, .value = 2}, 1149 + {.input = &tegra_clk_m, .value = 3}, 1150 + { 0, 0}, 1151 + }; 1152 + 1153 + static struct clk_mux_sel mux_pllp_pllc_audio_clkm_clk32[] = { 1154 + {.input = &tegra_pll_p, .value = 0}, 1155 + {.input = &tegra_pll_c, .value = 1}, 1156 + /* FIXME: no mux defined for tegra_audio 1157 + {.input = &tegra_audio, .value = 2},*/ 1158 + {.input = &tegra_clk_m, .value = 3}, 1159 + {.input = &tegra_clk_32k, .value = 4}, 1160 + { 0, 0}, 1161 + }; 1162 + 1163 + static struct clk_mux_sel mux_pllp_pllc_pllm[] = { 1164 + {.input = &tegra_pll_p, .value = 0}, 1165 + {.input = &tegra_pll_c, .value = 1}, 1166 + {.input = &tegra_pll_m, .value = 2}, 1167 + { 0, 0}, 1168 + }; 1169 + 1170 + static struct clk_mux_sel mux_clk_m[] = { 1171 + { .input = &tegra_clk_m, .value = 0}, 1172 + { 0, 0}, 1173 + }; 1174 + 1175 + static struct clk_mux_sel mux_pllp_out3[] = { 1176 + { .input = &tegra_pll_p_out3, .value = 0}, 1177 + { 0, 0}, 1178 + }; 1179 + 1180 + static struct clk_mux_sel mux_plld[] = { 1181 + { .input = &tegra_pll_d, .value = 0}, 1182 + { 0, 0}, 1183 + }; 1184 + 1185 + static struct clk_mux_sel mux_clk_32k[] = { 1186 + { .input = &tegra_clk_32k, .value = 0}, 1187 + { 0, 0}, 1188 + }; 1189 + 1190 + #define PERIPH_CLK(_name, _dev, _con, _clk_num, _reg, _inputs, _flags) \ 1191 + { \ 1192 + .name = _name, \ 1193 + .lookup = { \ 1194 + .dev_id = _dev, \ 1195 + .con_id = _con, \ 1196 + }, \ 1197 + .ops = &tegra_periph_clk_ops, \ 1198 + .clk_num = _clk_num, \ 1199 + .reg = _reg, \ 1200 + .inputs = _inputs, \ 1201 + .flags = _flags, \ 1202 + } 1203 + 1204 + struct clk tegra_periph_clks[] = { 1205 + PERIPH_CLK("rtc", "rtc-tegra", NULL, 4, 0, mux_clk_32k, PERIPH_NO_RESET), 1206 + PERIPH_CLK("timer", "timer", NULL, 5, 0, mux_clk_m, 0), 1207 + PERIPH_CLK("i2s1", "i2s.0", NULL, 11, 0x100, mux_plla_audio_pllp_clkm, MUX | DIV_U71), 1208 + PERIPH_CLK("i2s2", "i2s.1", NULL, 18, 0x104, mux_plla_audio_pllp_clkm, MUX | DIV_U71), 1209 + /* FIXME: spdif has 2 clocks but 1 enable */ 1210 + PERIPH_CLK("spdif_out", "spdif_out", NULL, 10, 0x108, mux_plla_audio_pllp_clkm, MUX | DIV_U71), 1211 + PERIPH_CLK("spdif_in", "spdif_in", NULL, 10, 0x10c, mux_pllp_pllc_pllm, MUX | DIV_U71), 1212 + PERIPH_CLK("pwm", "pwm", NULL, 17, 0x110, mux_pllp_pllc_audio_clkm_clk32, MUX | DIV_U71), 1213 + PERIPH_CLK("spi", "spi", NULL, 43, 0x114, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1214 + PERIPH_CLK("xio", "xio", NULL, 45, 0x120, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1215 + PERIPH_CLK("twc", "twc", NULL, 16, 0x12c, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1216 + PERIPH_CLK("sbc1", "spi_tegra.0", NULL, 41, 0x134, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1217 + PERIPH_CLK("sbc2", "spi_tegra.1", NULL, 44, 0x118, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1218 + PERIPH_CLK("sbc3", "spi_tegra.2", NULL, 46, 0x11c, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1219 + PERIPH_CLK("sbc4", "spi_tegra.3", NULL, 68, 0x1b4, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1220 + PERIPH_CLK("ide", "ide", NULL, 25, 0x144, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1221 + PERIPH_CLK("ndflash", "tegra_nand", NULL, 13, 0x160, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1222 + /* FIXME: vfir shares an enable with uartb */ 1223 + PERIPH_CLK("vfir", "vfir", NULL, 7, 0x168, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1224 + PERIPH_CLK("sdmmc1", "sdhci-tegra.0", NULL, 14, 0x150, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1225 + PERIPH_CLK("sdmmc2", "sdhci-tegra.1", NULL, 9, 0x154, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1226 + PERIPH_CLK("sdmmc3", "sdhci-tegra.2", NULL, 69, 0x1bc, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1227 + PERIPH_CLK("sdmmc4", "sdhci-tegra.3", NULL, 15, 0x160, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1228 + PERIPH_CLK("vde", "vde", NULL, 61, 0x1c8, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1229 + PERIPH_CLK("csite", "csite", NULL, 73, 0x1d4, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1230 + /* FIXME: what is la? */ 1231 + PERIPH_CLK("la", "la", NULL, 76, 0x1f8, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1232 + PERIPH_CLK("owr", "owr", NULL, 71, 0x1cc, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1233 + PERIPH_CLK("nor", "nor", NULL, 42, 0x1d0, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1234 + PERIPH_CLK("mipi", "mipi", NULL, 50, 0x174, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1235 + PERIPH_CLK("i2c1", "tegra-i2c.0", NULL, 12, 0x124, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1236 + PERIPH_CLK("i2c2", "tegra-i2c.1", NULL, 54, 0x198, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1237 + PERIPH_CLK("i2c3", "tegra-i2c.2", NULL, 67, 0x1b8, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1238 + PERIPH_CLK("dvc", "tegra-i2c.3", NULL, 47, 0x128, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1239 + PERIPH_CLK("i2c1_i2c", "tegra-i2c.0", "i2c", 0, 0, mux_pllp_out3, 0), 1240 + PERIPH_CLK("i2c2_i2c", "tegra-i2c.1", "i2c", 0, 0, mux_pllp_out3, 0), 1241 + PERIPH_CLK("i2c3_i2c", "tegra-i2c.2", "i2c", 0, 0, mux_pllp_out3, 0), 1242 + PERIPH_CLK("dvc_i2c", "tegra-i2c.3", "i2c", 0, 0, mux_pllp_out3, 0), 1243 + PERIPH_CLK("uarta", "uart.0", NULL, 6, 0x178, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1244 + PERIPH_CLK("uartb", "uart.1", NULL, 7, 0x17c, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1245 + PERIPH_CLK("uartc", "uart.2", NULL, 55, 0x1a0, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1246 + PERIPH_CLK("uartd", "uart.3", NULL, 65, 0x1c0, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1247 + PERIPH_CLK("uarte", "uart.4", NULL, 66, 0x1c4, mux_pllp_pllc_pllm_clkm, MUX | DIV_U71), 1248 + PERIPH_CLK("3d", "3d", NULL, 24, 0x158, mux_pllm_pllc_pllp_plla, MUX | DIV_U71 | PERIPH_MANUAL_RESET), 1249 + PERIPH_CLK("2d", "2d", NULL, 21, 0x15c, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1250 + /* FIXME: vi and vi_sensor share an enable */ 1251 + PERIPH_CLK("vi", "vi", NULL, 20, 0x148, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1252 + PERIPH_CLK("vi_sensor", "vi_sensor", NULL, 20, 0x1a8, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1253 + PERIPH_CLK("epp", "epp", NULL, 19, 0x16c, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1254 + PERIPH_CLK("mpe", "mpe", NULL, 60, 0x170, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1255 + PERIPH_CLK("host1x", "host1x", NULL, 28, 0x180, mux_pllm_pllc_pllp_plla, MUX | DIV_U71), 1256 + /* FIXME: cve and tvo share an enable */ 1257 + PERIPH_CLK("cve", "cve", NULL, 49, 0x140, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1258 + PERIPH_CLK("tvo", "tvo", NULL, 49, 0x188, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1259 + PERIPH_CLK("hdmi", "hdmi", NULL, 51, 0x18c, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1260 + PERIPH_CLK("tvdac", "tvdac", NULL, 53, 0x194, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1261 + PERIPH_CLK("disp1", "tegrafb.0", NULL, 27, 0x138, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1262 + PERIPH_CLK("disp2", "tegrafb.1", NULL, 26, 0x13c, mux_pllp_plld_pllc_clkm, MUX | DIV_U71), 1263 + PERIPH_CLK("usbd", "fsl-tegra-udc", NULL, 22, 0, mux_clk_m, 0), 1264 + PERIPH_CLK("usb2", "usb.1", NULL, 58, 0, mux_clk_m, 0), 1265 + PERIPH_CLK("usb3", "usb.2", NULL, 59, 0, mux_clk_m, 0), 1266 + PERIPH_CLK("emc", "emc", NULL, 57, 0x19c, mux_pllm_pllc_pllp_clkm, MUX | DIV_U71 | PERIPH_EMC_ENB), 1267 + PERIPH_CLK("dsi", "dsi", NULL, 48, 0, mux_plld, 0), 1268 + }; 1269 + 1270 + #define CLK_DUPLICATE(_name, _dev, _con) \ 1271 + { \ 1272 + .name = _name, \ 1273 + .lookup = { \ 1274 + .dev_id = _dev, \ 1275 + .con_id = _con, \ 1276 + }, \ 1277 + } 1278 + 1279 + /* Some clocks may be used by different drivers depending on the board 1280 + * configuration. List those here to register them twice in the clock lookup 1281 + * table under two names. 1282 + */ 1283 + struct clk_duplicate tegra_clk_duplicates[] = { 1284 + CLK_DUPLICATE("uarta", "tegra_uart.0", NULL), 1285 + CLK_DUPLICATE("uartb", "tegra_uart.1", NULL), 1286 + CLK_DUPLICATE("uartc", "tegra_uart.2", NULL), 1287 + CLK_DUPLICATE("uartd", "tegra_uart.3", NULL), 1288 + CLK_DUPLICATE("uarte", "tegra_uart.4", NULL), 1289 + }; 1290 + 1291 + #define CLK(dev, con, ck) \ 1292 + { \ 1293 + .dev_id = dev, \ 1294 + .con_id = con, \ 1295 + .clk = ck, \ 1296 + } 1297 + 1298 + struct clk_lookup tegra_clk_lookups[] = { 1299 + /* external root sources */ 1300 + CLK(NULL, "32k_clk", &tegra_clk_32k), 1301 + CLK(NULL, "pll_s", &tegra_pll_s), 1302 + CLK(NULL, "clk_m", &tegra_clk_m), 1303 + CLK(NULL, "pll_m", &tegra_pll_m), 1304 + CLK(NULL, "pll_m_out1", &tegra_pll_m_out1), 1305 + CLK(NULL, "pll_c", &tegra_pll_c), 1306 + CLK(NULL, "pll_c_out1", &tegra_pll_c_out1), 1307 + CLK(NULL, "pll_p", &tegra_pll_p), 1308 + CLK(NULL, "pll_p_out1", &tegra_pll_p_out1), 1309 + CLK(NULL, "pll_p_out2", &tegra_pll_p_out2), 1310 + CLK(NULL, "pll_p_out3", &tegra_pll_p_out3), 1311 + CLK(NULL, "pll_p_out4", &tegra_pll_p_out4), 1312 + CLK(NULL, "pll_a", &tegra_pll_a), 1313 + CLK(NULL, "pll_a_out0", &tegra_pll_a_out0), 1314 + CLK(NULL, "pll_d", &tegra_pll_d), 1315 + CLK(NULL, "pll_d_out0", &tegra_pll_d_out0), 1316 + CLK(NULL, "pll_u", &tegra_pll_u), 1317 + CLK(NULL, "pll_x", &tegra_pll_x), 1318 + CLK(NULL, "cpu", &tegra_clk_cpu), 1319 + CLK(NULL, "sys", &tegra_clk_sys), 1320 + CLK(NULL, "hclk", &tegra_clk_hclk), 1321 + CLK(NULL, "pclk", &tegra_clk_pclk), 1322 + CLK(NULL, "clk_d", &tegra_clk_d), 1323 + }; 1324 + 1325 + void __init tegra2_init_clocks(void) 1326 + { 1327 + int i; 1328 + struct clk_lookup *cl; 1329 + struct clk *c; 1330 + struct clk_duplicate *cd; 1331 + 1332 + for (i = 0; i < ARRAY_SIZE(tegra_clk_lookups); i++) { 1333 + cl = &tegra_clk_lookups[i]; 1334 + clk_init(cl->clk); 1335 + clkdev_add(cl); 1336 + } 1337 + 1338 + for (i = 0; i < ARRAY_SIZE(tegra_periph_clks); i++) { 1339 + c = &tegra_periph_clks[i]; 1340 + cl = &c->lookup; 1341 + cl->clk = c; 1342 + 1343 + clk_init(cl->clk); 1344 + clkdev_add(cl); 1345 + } 1346 + 1347 + for (i = 0; i < ARRAY_SIZE(tegra_clk_duplicates); i++) { 1348 + cd = &tegra_clk_duplicates[i]; 1349 + c = tegra_get_clock_by_name(cd->name); 1350 + if (c) { 1351 + cl = &cd->lookup; 1352 + cl->clk = c; 1353 + clkdev_add(cl); 1354 + } else { 1355 + pr_err("%s: Unknown duplicate clock %s\n", __func__, 1356 + cd->name); 1357 + } 1358 + } 1359 + }
+187
arch/arm/mach-tegra/timer.c
··· 1 + /* 2 + * arch/arch/mach-tegra/timer.c 3 + * 4 + * Copyright (C) 2010 Google, Inc. 5 + * 6 + * Author: 7 + * Colin Cross <ccross@google.com> 8 + * 9 + * This software is licensed under the terms of the GNU General Public 10 + * License version 2, as published by the Free Software Foundation, and 11 + * may be copied, distributed, and modified under those terms. 12 + * 13 + * This program is distributed in the hope that it will be useful, 14 + * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 + * GNU General Public License for more details. 17 + * 18 + */ 19 + 20 + #include <linux/init.h> 21 + #include <linux/time.h> 22 + #include <linux/interrupt.h> 23 + #include <linux/irq.h> 24 + #include <linux/clockchips.h> 25 + #include <linux/clocksource.h> 26 + #include <linux/clk.h> 27 + #include <linux/io.h> 28 + #include <linux/cnt32_to_63.h> 29 + 30 + #include <asm/mach/time.h> 31 + #include <asm/mach/time.h> 32 + #include <asm/localtimer.h> 33 + 34 + #include <mach/iomap.h> 35 + #include <mach/irqs.h> 36 + 37 + #include "board.h" 38 + #include "clock.h" 39 + 40 + #define TIMERUS_CNTR_1US 0x10 41 + #define TIMERUS_USEC_CFG 0x14 42 + #define TIMERUS_CNTR_FREEZE 0x4c 43 + 44 + #define TIMER1_BASE 0x0 45 + #define TIMER2_BASE 0x8 46 + #define TIMER3_BASE 0x50 47 + #define TIMER4_BASE 0x58 48 + 49 + #define TIMER_PTV 0x0 50 + #define TIMER_PCR 0x4 51 + 52 + struct tegra_timer; 53 + 54 + static void __iomem *timer_reg_base = IO_ADDRESS(TEGRA_TMR1_BASE); 55 + 56 + #define timer_writel(value, reg) \ 57 + __raw_writel(value, (u32)timer_reg_base + (reg)) 58 + #define timer_readl(reg) \ 59 + __raw_readl((u32)timer_reg_base + (reg)) 60 + 61 + static int tegra_timer_set_next_event(unsigned long cycles, 62 + struct clock_event_device *evt) 63 + { 64 + u32 reg; 65 + 66 + reg = 0x80000000 | ((cycles > 1) ? (cycles-1) : 0); 67 + timer_writel(reg, TIMER3_BASE + TIMER_PTV); 68 + 69 + return 0; 70 + } 71 + 72 + static void tegra_timer_set_mode(enum clock_event_mode mode, 73 + struct clock_event_device *evt) 74 + { 75 + u32 reg; 76 + 77 + timer_writel(0, TIMER3_BASE + TIMER_PTV); 78 + 79 + switch (mode) { 80 + case CLOCK_EVT_MODE_PERIODIC: 81 + reg = 0xC0000000 | ((1000000/HZ)-1); 82 + timer_writel(reg, TIMER3_BASE + TIMER_PTV); 83 + break; 84 + case CLOCK_EVT_MODE_ONESHOT: 85 + break; 86 + case CLOCK_EVT_MODE_UNUSED: 87 + case CLOCK_EVT_MODE_SHUTDOWN: 88 + case CLOCK_EVT_MODE_RESUME: 89 + break; 90 + } 91 + } 92 + 93 + static cycle_t tegra_clocksource_read(struct clocksource *cs) 94 + { 95 + return cnt32_to_63(timer_readl(TIMERUS_CNTR_1US)); 96 + } 97 + 98 + static struct clock_event_device tegra_clockevent = { 99 + .name = "timer0", 100 + .rating = 300, 101 + .features = CLOCK_EVT_FEAT_ONESHOT | CLOCK_EVT_FEAT_PERIODIC, 102 + .set_next_event = tegra_timer_set_next_event, 103 + .set_mode = tegra_timer_set_mode, 104 + }; 105 + 106 + static struct clocksource tegra_clocksource = { 107 + .name = "timer_us", 108 + .rating = 300, 109 + .read = tegra_clocksource_read, 110 + .mask = 0x7FFFFFFFFFFFFFFFULL, 111 + .flags = CLOCK_SOURCE_IS_CONTINUOUS, 112 + }; 113 + 114 + unsigned long long sched_clock(void) 115 + { 116 + return clocksource_cyc2ns(tegra_clocksource.read(&tegra_clocksource), 117 + tegra_clocksource.mult, tegra_clocksource.shift); 118 + } 119 + 120 + static irqreturn_t tegra_timer_interrupt(int irq, void *dev_id) 121 + { 122 + struct clock_event_device *evt = (struct clock_event_device *)dev_id; 123 + timer_writel(1<<30, TIMER3_BASE + TIMER_PCR); 124 + evt->event_handler(evt); 125 + return IRQ_HANDLED; 126 + } 127 + 128 + static struct irqaction tegra_timer_irq = { 129 + .name = "timer0", 130 + .flags = IRQF_DISABLED | IRQF_TIMER | IRQF_TRIGGER_HIGH, 131 + .handler = tegra_timer_interrupt, 132 + .dev_id = &tegra_clockevent, 133 + .irq = INT_TMR3, 134 + }; 135 + 136 + static void __init tegra_init_timer(void) 137 + { 138 + unsigned long rate = clk_measure_input_freq(); 139 + int ret; 140 + 141 + #ifdef CONFIG_HAVE_ARM_TWD 142 + twd_base = IO_ADDRESS(TEGRA_ARM_PERIF_BASE + 0x600); 143 + #endif 144 + 145 + switch (rate) { 146 + case 12000000: 147 + timer_writel(0x000b, TIMERUS_USEC_CFG); 148 + break; 149 + case 13000000: 150 + timer_writel(0x000c, TIMERUS_USEC_CFG); 151 + break; 152 + case 19200000: 153 + timer_writel(0x045f, TIMERUS_USEC_CFG); 154 + break; 155 + case 26000000: 156 + timer_writel(0x0019, TIMERUS_USEC_CFG); 157 + break; 158 + default: 159 + WARN(1, "Unknown clock rate"); 160 + } 161 + 162 + if (clocksource_register_hz(&tegra_clocksource, 1000000)) { 163 + printk(KERN_ERR "Failed to register clocksource\n"); 164 + BUG(); 165 + } 166 + 167 + ret = setup_irq(tegra_timer_irq.irq, &tegra_timer_irq); 168 + if (ret) { 169 + printk(KERN_ERR "Failed to register timer IRQ: %d\n", ret); 170 + BUG(); 171 + } 172 + 173 + clockevents_calc_mult_shift(&tegra_clockevent, 1000000, 5); 174 + tegra_clockevent.max_delta_ns = 175 + clockevent_delta2ns(0x1fffffff, &tegra_clockevent); 176 + tegra_clockevent.min_delta_ns = 177 + clockevent_delta2ns(0x1, &tegra_clockevent); 178 + tegra_clockevent.cpumask = cpu_all_mask; 179 + tegra_clockevent.irq = tegra_timer_irq.irq; 180 + clockevents_register_device(&tegra_clockevent); 181 + 182 + return; 183 + } 184 + 185 + struct sys_timer tegra_timer = { 186 + .init = tegra_init_timer, 187 + };
+2 -1
arch/arm/mm/Kconfig
··· 771 771 bool "Enable the L2x0 outer cache controller" 772 772 depends on REALVIEW_EB_ARM11MP || MACH_REALVIEW_PB11MP || MACH_REALVIEW_PB1176 || \ 773 773 REALVIEW_EB_A9MP || ARCH_MX35 || ARCH_MX31 || MACH_REALVIEW_PBX || \ 774 - ARCH_NOMADIK || ARCH_OMAP4 || ARCH_U8500 || ARCH_VEXPRESS_CA9X4 774 + ARCH_NOMADIK || ARCH_OMAP4 || ARCH_U8500 || ARCH_VEXPRESS_CA9X4 || \ 775 + ARCH_TEGRA 775 776 default y 776 777 select OUTER_CACHE 777 778 select OUTER_CACHE_SYNC