diff options
| author | Linus Torvalds <torvalds@g5.osdl.org> | 2006-06-29 14:32:34 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@g5.osdl.org> | 2006-06-29 14:32:34 -0400 |
| commit | 3aa590c6b7c89d844f81c2e96f295cf2c6967773 (patch) | |
| tree | 6f18b295b1ff4cd7fd1880db6f56721599d64439 | |
| parent | 4d3ce21fa9d2eaeda113aa2f9c2da80d972bef64 (diff) | |
| parent | 339d76c54336443f5050b00172beb675f35e3be0 (diff) | |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc
* git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc: (43 commits)
[POWERPC] Use little-endian bit from firmware ibm,pa-features property
[POWERPC] Make sure smp_processor_id works very early in boot
[POWERPC] U4 DART improvements
[POWERPC] todc: add support for Time-Of-Day-Clock
[POWERPC] Make lparcfg.c work when both iseries and pseries are selected
[POWERPC] Fix idr locking in init_new_context
[POWERPC] mpc7448hpc2 (taiga) board config file
[POWERPC] Add tsi108 pci and platform device data register function
[POWERPC] Add general support for mpc7448hpc2 (Taiga) platform
[POWERPC] Correct the MAX_CONTEXT definition
powerpc: minor cleanups for mpc86xx
[POWERPC] Make sure we select CONFIG_NEW_LEDS if ADB_PMU_LED is set
[POWERPC] Simplify the code defining the 64-bit CPU features
[POWERPC] powerpc: kconfig warning fix
[POWERPC] Consolidate some of kernel/misc*.S
[POWERPC] Remove unused function call_with_mmu_off
[POWERPC] update asm-powerpc/time.h
[POWERPC] Clean up it_lp_queue.h
[POWERPC] Skip the "copy down" of the kernel if it is already at zero.
[POWERPC] Add the use of the firmware soft-reset-nmi to kdump.
...
77 files changed, 4086 insertions, 1110 deletions
diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index d43e4521abf2..b9a40a35a9ed 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig | |||
| @@ -340,7 +340,7 @@ config PPC_ISERIES | |||
| 340 | 340 | ||
| 341 | config EMBEDDED6xx | 341 | config EMBEDDED6xx |
| 342 | bool "Embedded 6xx/7xx/7xxx-based board" | 342 | bool "Embedded 6xx/7xx/7xxx-based board" |
| 343 | depends on PPC32 && BROKEN | 343 | depends on PPC32 && (BROKEN||BROKEN_ON_SMP) |
| 344 | 344 | ||
| 345 | config APUS | 345 | config APUS |
| 346 | bool "Amiga-APUS" | 346 | bool "Amiga-APUS" |
| @@ -417,12 +417,17 @@ config PPC_CELL_NATIVE | |||
| 417 | default n | 417 | default n |
| 418 | 418 | ||
| 419 | config PPC_IBM_CELL_BLADE | 419 | config PPC_IBM_CELL_BLADE |
| 420 | bool " IBM Cell Blade" | 420 | bool "IBM Cell Blade" |
| 421 | depends on PPC_MULTIPLATFORM && PPC64 | 421 | depends on PPC_MULTIPLATFORM && PPC64 |
| 422 | select PPC_CELL_NATIVE | 422 | select PPC_CELL_NATIVE |
| 423 | select PPC_RTAS | 423 | select PPC_RTAS |
| 424 | select MMIO_NVRAM | 424 | select MMIO_NVRAM |
| 425 | select PPC_UDBG_16550 | 425 | select PPC_UDBG_16550 |
| 426 | select UDBG_RTAS_CONSOLE | ||
| 427 | |||
| 428 | config UDBG_RTAS_CONSOLE | ||
| 429 | bool | ||
| 430 | default n | ||
| 426 | 431 | ||
| 427 | config XICS | 432 | config XICS |
| 428 | depends on PPC_PSERIES | 433 | depends on PPC_PSERIES |
| @@ -435,7 +440,8 @@ config U3_DART | |||
| 435 | default n | 440 | default n |
| 436 | 441 | ||
| 437 | config MPIC | 442 | config MPIC |
| 438 | depends on PPC_PSERIES || PPC_PMAC || PPC_MAPLE || PPC_CHRP | 443 | depends on PPC_PSERIES || PPC_PMAC || PPC_MAPLE || PPC_CHRP \ |
| 444 | || MPC7448HPC2 | ||
| 439 | bool | 445 | bool |
| 440 | default y | 446 | default y |
| 441 | 447 | ||
| @@ -561,6 +567,13 @@ config TAU_AVERAGE | |||
| 561 | /proc/cpuinfo. | 567 | /proc/cpuinfo. |
| 562 | 568 | ||
| 563 | If in doubt, say N here. | 569 | If in doubt, say N here. |
| 570 | |||
| 571 | config PPC_TODC | ||
| 572 | depends on EMBEDDED6xx | ||
| 573 | bool "Generic Time-of-day Clock (TODC) support" | ||
| 574 | ---help--- | ||
| 575 | This adds support for many TODC/RTC chips. | ||
| 576 | |||
| 564 | endmenu | 577 | endmenu |
| 565 | 578 | ||
| 566 | source arch/powerpc/platforms/embedded6xx/Kconfig | 579 | source arch/powerpc/platforms/embedded6xx/Kconfig |
| @@ -801,7 +814,6 @@ config GENERIC_ISA_DMA | |||
| 801 | 814 | ||
| 802 | config PPC_I8259 | 815 | config PPC_I8259 |
| 803 | bool | 816 | bool |
| 804 | default y if MPC8641_HPCN | ||
| 805 | default n | 817 | default n |
| 806 | 818 | ||
| 807 | config PPC_INDIRECT_PCI | 819 | config PPC_INDIRECT_PCI |
| @@ -824,7 +836,8 @@ config MCA | |||
| 824 | bool | 836 | bool |
| 825 | 837 | ||
| 826 | config PCI | 838 | config PCI |
| 827 | bool "PCI support" if 40x || CPM2 || PPC_83xx || PPC_85xx || PPC_86xx || PPC_MPC52xx || (EMBEDDED && PPC_ISERIES) | 839 | bool "PCI support" if 40x || CPM2 || PPC_83xx || PPC_85xx || PPC_MPC52xx || (EMBEDDED && PPC_ISERIES) \ |
| 840 | || MPC7448HPC2 | ||
| 828 | default y if !40x && !CPM2 && !8xx && !APUS && !PPC_83xx && !PPC_85xx && !PPC_86xx | 841 | default y if !40x && !CPM2 && !8xx && !APUS && !PPC_83xx && !PPC_85xx && !PPC_86xx |
| 829 | default PCI_PERMEDIA if !4xx && !CPM2 && !8xx && APUS | 842 | default PCI_PERMEDIA if !4xx && !CPM2 && !8xx && APUS |
| 830 | default PCI_QSPAN if !4xx && !CPM2 && 8xx | 843 | default PCI_QSPAN if !4xx && !CPM2 && 8xx |
diff --git a/arch/powerpc/Kconfig.debug b/arch/powerpc/Kconfig.debug index c69006ae8246..e29ef77d3b00 100644 --- a/arch/powerpc/Kconfig.debug +++ b/arch/powerpc/Kconfig.debug | |||
| @@ -134,12 +134,19 @@ config PPC_EARLY_DEBUG_G5 | |||
| 134 | help | 134 | help |
| 135 | Select this to enable early debugging for Apple G5 machines. | 135 | Select this to enable early debugging for Apple G5 machines. |
| 136 | 136 | ||
| 137 | config PPC_EARLY_DEBUG_RTAS | 137 | config PPC_EARLY_DEBUG_RTAS_PANEL |
| 138 | bool "RTAS Panel" | 138 | bool "RTAS Panel" |
| 139 | depends on PPC_RTAS | 139 | depends on PPC_RTAS |
| 140 | help | 140 | help |
| 141 | Select this to enable early debugging via the RTAS panel. | 141 | Select this to enable early debugging via the RTAS panel. |
| 142 | 142 | ||
| 143 | config PPC_EARLY_DEBUG_RTAS_CONSOLE | ||
| 144 | bool "RTAS Console" | ||
| 145 | depends on PPC_RTAS | ||
| 146 | select UDBG_RTAS_CONSOLE | ||
| 147 | help | ||
| 148 | Select this to enable early debugging via the RTAS console. | ||
| 149 | |||
| 143 | config PPC_EARLY_DEBUG_MAPLE | 150 | config PPC_EARLY_DEBUG_MAPLE |
| 144 | bool "Maple real mode" | 151 | bool "Maple real mode" |
| 145 | depends on PPC_MAPLE | 152 | depends on PPC_MAPLE |
diff --git a/arch/powerpc/configs/cell_defconfig b/arch/powerpc/configs/cell_defconfig index b8b8d4675dc0..e028a2ecb8a3 100644 --- a/arch/powerpc/configs/cell_defconfig +++ b/arch/powerpc/configs/cell_defconfig | |||
| @@ -1,7 +1,7 @@ | |||
| 1 | # | 1 | # |
| 2 | # Automatically generated make config: don't edit | 2 | # Automatically generated make config: don't edit |
| 3 | # Linux kernel version: 2.6.17 | 3 | # Linux kernel version: 2.6.17-rc6 |
| 4 | # Mon Jun 19 17:23:03 2006 | 4 | # Thu Jun 22 15:28:36 2006 |
| 5 | # | 5 | # |
| 6 | CONFIG_PPC64=y | 6 | CONFIG_PPC64=y |
| 7 | CONFIG_64BIT=y | 7 | CONFIG_64BIT=y |
| @@ -1063,7 +1063,8 @@ CONFIG_DEBUG_FS=y | |||
| 1063 | # CONFIG_DEBUG_STACKOVERFLOW is not set | 1063 | # CONFIG_DEBUG_STACKOVERFLOW is not set |
| 1064 | # CONFIG_DEBUG_STACK_USAGE is not set | 1064 | # CONFIG_DEBUG_STACK_USAGE is not set |
| 1065 | CONFIG_DEBUGGER=y | 1065 | CONFIG_DEBUGGER=y |
| 1066 | # CONFIG_XMON is not set | 1066 | CONFIG_XMON=y |
| 1067 | CONFIG_XMON_DEFAULT=y | ||
| 1067 | CONFIG_IRQSTACKS=y | 1068 | CONFIG_IRQSTACKS=y |
| 1068 | # CONFIG_BOOTX_TEXT is not set | 1069 | # CONFIG_BOOTX_TEXT is not set |
| 1069 | # CONFIG_PPC_EARLY_DEBUG is not set | 1070 | # CONFIG_PPC_EARLY_DEBUG is not set |
diff --git a/arch/powerpc/configs/mpc7448_hpc2_defconfig b/arch/powerpc/configs/mpc7448_hpc2_defconfig new file mode 100644 index 000000000000..15a50f4ceb1f --- /dev/null +++ b/arch/powerpc/configs/mpc7448_hpc2_defconfig | |||
| @@ -0,0 +1,923 @@ | |||
| 1 | # | ||
| 2 | # Automatically generated make config: don't edit | ||
| 3 | # Linux kernel version: 2.6.17-rc4 | ||
| 4 | # Sat May 27 18:45:55 2006 | ||
| 5 | # | ||
| 6 | # CONFIG_PPC64 is not set | ||
| 7 | CONFIG_PPC32=y | ||
| 8 | CONFIG_PPC_MERGE=y | ||
| 9 | CONFIG_MMU=y | ||
| 10 | CONFIG_GENERIC_HARDIRQS=y | ||
| 11 | CONFIG_RWSEM_XCHGADD_ALGORITHM=y | ||
| 12 | CONFIG_GENERIC_HWEIGHT=y | ||
| 13 | CONFIG_GENERIC_CALIBRATE_DELAY=y | ||
| 14 | CONFIG_PPC=y | ||
| 15 | CONFIG_EARLY_PRINTK=y | ||
| 16 | CONFIG_GENERIC_NVRAM=y | ||
| 17 | CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y | ||
| 18 | CONFIG_ARCH_MAY_HAVE_PC_FDC=y | ||
| 19 | CONFIG_PPC_OF=y | ||
| 20 | CONFIG_PPC_UDBG_16550=y | ||
| 21 | # CONFIG_GENERIC_TBSYNC is not set | ||
| 22 | CONFIG_DEFAULT_UIMAGE=y | ||
| 23 | |||
| 24 | # | ||
| 25 | # Processor support | ||
| 26 | # | ||
| 27 | CONFIG_CLASSIC32=y | ||
| 28 | # CONFIG_PPC_52xx is not set | ||
| 29 | # CONFIG_PPC_82xx is not set | ||
| 30 | # CONFIG_PPC_83xx is not set | ||
| 31 | # CONFIG_PPC_85xx is not set | ||
| 32 | # CONFIG_40x is not set | ||
| 33 | # CONFIG_44x is not set | ||
| 34 | # CONFIG_8xx is not set | ||
| 35 | # CONFIG_E200 is not set | ||
| 36 | CONFIG_6xx=y | ||
| 37 | CONFIG_PPC_FPU=y | ||
| 38 | # CONFIG_ALTIVEC is not set | ||
| 39 | CONFIG_PPC_STD_MMU=y | ||
| 40 | CONFIG_PPC_STD_MMU_32=y | ||
| 41 | # CONFIG_SMP is not set | ||
| 42 | |||
| 43 | # | ||
| 44 | # Code maturity level options | ||
| 45 | # | ||
| 46 | CONFIG_EXPERIMENTAL=y | ||
| 47 | CONFIG_BROKEN_ON_SMP=y | ||
| 48 | CONFIG_INIT_ENV_ARG_LIMIT=32 | ||
| 49 | |||
| 50 | # | ||
| 51 | # General setup | ||
| 52 | # | ||
| 53 | CONFIG_LOCALVERSION="" | ||
| 54 | CONFIG_LOCALVERSION_AUTO=y | ||
| 55 | CONFIG_SWAP=y | ||
| 56 | CONFIG_SYSVIPC=y | ||
| 57 | # CONFIG_POSIX_MQUEUE is not set | ||
| 58 | # CONFIG_BSD_PROCESS_ACCT is not set | ||
| 59 | CONFIG_SYSCTL=y | ||
| 60 | # CONFIG_AUDIT is not set | ||
| 61 | # CONFIG_IKCONFIG is not set | ||
| 62 | # CONFIG_RELAY is not set | ||
| 63 | CONFIG_INITRAMFS_SOURCE="" | ||
| 64 | # CONFIG_CC_OPTIMIZE_FOR_SIZE is not set | ||
| 65 | CONFIG_EMBEDDED=y | ||
| 66 | CONFIG_KALLSYMS=y | ||
| 67 | # CONFIG_KALLSYMS_EXTRA_PASS is not set | ||
| 68 | CONFIG_HOTPLUG=y | ||
| 69 | CONFIG_PRINTK=y | ||
| 70 | CONFIG_BUG=y | ||
| 71 | CONFIG_ELF_CORE=y | ||
| 72 | CONFIG_BASE_FULL=y | ||
| 73 | CONFIG_FUTEX=y | ||
| 74 | CONFIG_EPOLL=y | ||
| 75 | CONFIG_SHMEM=y | ||
| 76 | CONFIG_SLAB=y | ||
| 77 | # CONFIG_TINY_SHMEM is not set | ||
| 78 | CONFIG_BASE_SMALL=0 | ||
| 79 | # CONFIG_SLOB is not set | ||
| 80 | |||
| 81 | # | ||
| 82 | # Loadable module support | ||
| 83 | # | ||
| 84 | # CONFIG_MODULES is not set | ||
| 85 | |||
| 86 | # | ||
| 87 | # Block layer | ||
| 88 | # | ||
| 89 | CONFIG_LBD=y | ||
| 90 | # CONFIG_BLK_DEV_IO_TRACE is not set | ||
| 91 | # CONFIG_LSF is not set | ||
| 92 | |||
| 93 | # | ||
| 94 | # IO Schedulers | ||
| 95 | # | ||
| 96 | CONFIG_IOSCHED_NOOP=y | ||
| 97 | CONFIG_IOSCHED_AS=y | ||
| 98 | CONFIG_IOSCHED_DEADLINE=y | ||
| 99 | CONFIG_IOSCHED_CFQ=y | ||
| 100 | CONFIG_DEFAULT_AS=y | ||
| 101 | # CONFIG_DEFAULT_DEADLINE is not set | ||
| 102 | # CONFIG_DEFAULT_CFQ is not set | ||
| 103 | # CONFIG_DEFAULT_NOOP is not set | ||
| 104 | CONFIG_DEFAULT_IOSCHED="anticipatory" | ||
| 105 | |||
| 106 | # | ||
| 107 | # Platform support | ||
| 108 | # | ||
| 109 | # CONFIG_PPC_MULTIPLATFORM is not set | ||
| 110 | # CONFIG_PPC_ISERIES is not set | ||
| 111 | CONFIG_EMBEDDED6xx=y | ||
| 112 | # CONFIG_APUS is not set | ||
| 113 | CONFIG_MPIC=y | ||
| 114 | # CONFIG_PPC_RTAS is not set | ||
| 115 | # CONFIG_MMIO_NVRAM is not set | ||
| 116 | # CONFIG_PPC_MPC106 is not set | ||
| 117 | # CONFIG_PPC_970_NAP is not set | ||
| 118 | # CONFIG_CPU_FREQ is not set | ||
| 119 | # CONFIG_TAU is not set | ||
| 120 | # CONFIG_KATANA is not set | ||
| 121 | # CONFIG_WILLOW is not set | ||
| 122 | # CONFIG_CPCI690 is not set | ||
| 123 | # CONFIG_POWERPMC250 is not set | ||
| 124 | # CONFIG_CHESTNUT is not set | ||
| 125 | # CONFIG_SPRUCE is not set | ||
| 126 | # CONFIG_HDPU is not set | ||
| 127 | # CONFIG_EV64260 is not set | ||
| 128 | # CONFIG_LOPEC is not set | ||
| 129 | # CONFIG_MVME5100 is not set | ||
| 130 | # CONFIG_PPLUS is not set | ||
| 131 | # CONFIG_PRPMC750 is not set | ||
| 132 | # CONFIG_PRPMC800 is not set | ||
| 133 | # CONFIG_SANDPOINT is not set | ||
| 134 | CONFIG_MPC7448HPC2=y | ||
| 135 | # CONFIG_RADSTONE_PPC7D is not set | ||
| 136 | # CONFIG_PAL4 is not set | ||
| 137 | # CONFIG_GEMINI is not set | ||
| 138 | # CONFIG_EST8260 is not set | ||
| 139 | # CONFIG_SBC82xx is not set | ||
| 140 | # CONFIG_SBS8260 is not set | ||
| 141 | # CONFIG_RPX8260 is not set | ||
| 142 | # CONFIG_TQM8260 is not set | ||
| 143 | # CONFIG_ADS8272 is not set | ||
| 144 | # CONFIG_PQ2FADS is not set | ||
| 145 | # CONFIG_LITE5200 is not set | ||
| 146 | # CONFIG_EV64360 is not set | ||
| 147 | CONFIG_TSI108_BRIDGE=y | ||
| 148 | # CONFIG_WANT_EARLY_SERIAL is not set | ||
| 149 | |||
| 150 | # | ||
| 151 | # Kernel options | ||
| 152 | # | ||
| 153 | # CONFIG_HIGHMEM is not set | ||
| 154 | # CONFIG_HZ_100 is not set | ||
| 155 | CONFIG_HZ_250=y | ||
| 156 | # CONFIG_HZ_1000 is not set | ||
| 157 | CONFIG_HZ=250 | ||
| 158 | CONFIG_PREEMPT_NONE=y | ||
| 159 | # CONFIG_PREEMPT_VOLUNTARY is not set | ||
| 160 | # CONFIG_PREEMPT is not set | ||
| 161 | CONFIG_BINFMT_ELF=y | ||
| 162 | CONFIG_BINFMT_MISC=y | ||
| 163 | CONFIG_ARCH_FLATMEM_ENABLE=y | ||
| 164 | CONFIG_SELECT_MEMORY_MODEL=y | ||
| 165 | CONFIG_FLATMEM_MANUAL=y | ||
| 166 | # CONFIG_DISCONTIGMEM_MANUAL is not set | ||
| 167 | # CONFIG_SPARSEMEM_MANUAL is not set | ||
| 168 | CONFIG_FLATMEM=y | ||
| 169 | CONFIG_FLAT_NODE_MEM_MAP=y | ||
| 170 | # CONFIG_SPARSEMEM_STATIC is not set | ||
| 171 | CONFIG_SPLIT_PTLOCK_CPUS=4 | ||
| 172 | CONFIG_PROC_DEVICETREE=y | ||
| 173 | # CONFIG_CMDLINE_BOOL is not set | ||
| 174 | # CONFIG_PM is not set | ||
| 175 | # CONFIG_SOFTWARE_SUSPEND is not set | ||
| 176 | # CONFIG_SECCOMP is not set | ||
| 177 | CONFIG_ISA_DMA_API=y | ||
| 178 | |||
| 179 | # | ||
| 180 | # Bus options | ||
| 181 | # | ||
| 182 | CONFIG_GENERIC_ISA_DMA=y | ||
| 183 | # CONFIG_PPC_I8259 is not set | ||
| 184 | # CONFIG_PPC_INDIRECT_PCI is not set | ||
| 185 | CONFIG_PCI=y | ||
| 186 | CONFIG_PCI_DOMAINS=y | ||
| 187 | |||
| 188 | # | ||
| 189 | # PCCARD (PCMCIA/CardBus) support | ||
| 190 | # | ||
| 191 | # CONFIG_PCCARD is not set | ||
| 192 | |||
| 193 | # | ||
| 194 | # PCI Hotplug Support | ||
| 195 | # | ||
| 196 | # CONFIG_HOTPLUG_PCI is not set | ||
| 197 | |||
| 198 | # | ||
| 199 | # Advanced setup | ||
| 200 | # | ||
| 201 | # CONFIG_ADVANCED_OPTIONS is not set | ||
| 202 | |||
| 203 | # | ||
| 204 | # Default settings for advanced configuration options are used | ||
| 205 | # | ||
| 206 | CONFIG_HIGHMEM_START=0xfe000000 | ||
| 207 | CONFIG_LOWMEM_SIZE=0x30000000 | ||
| 208 | CONFIG_KERNEL_START=0xc0000000 | ||
| 209 | CONFIG_TASK_SIZE=0x80000000 | ||
| 210 | CONFIG_BOOT_LOAD=0x00800000 | ||
| 211 | |||
| 212 | # | ||
| 213 | # Networking | ||
| 214 | # | ||
| 215 | CONFIG_NET=y | ||
| 216 | |||
| 217 | # | ||
| 218 | # Networking options | ||
| 219 | # | ||
| 220 | # CONFIG_NETDEBUG is not set | ||
| 221 | CONFIG_PACKET=y | ||
| 222 | # CONFIG_PACKET_MMAP is not set | ||
| 223 | CONFIG_UNIX=y | ||
| 224 | # CONFIG_NET_KEY is not set | ||
| 225 | CONFIG_INET=y | ||
| 226 | CONFIG_IP_MULTICAST=y | ||
| 227 | # CONFIG_IP_ADVANCED_ROUTER is not set | ||
| 228 | CONFIG_IP_FIB_HASH=y | ||
| 229 | CONFIG_IP_PNP=y | ||
| 230 | CONFIG_IP_PNP_DHCP=y | ||
| 231 | CONFIG_IP_PNP_BOOTP=y | ||
| 232 | # CONFIG_IP_PNP_RARP is not set | ||
| 233 | # CONFIG_NET_IPIP is not set | ||
| 234 | # CONFIG_NET_IPGRE is not set | ||
| 235 | # CONFIG_IP_MROUTE is not set | ||
| 236 | # CONFIG_ARPD is not set | ||
| 237 | CONFIG_SYN_COOKIES=y | ||
| 238 | # CONFIG_INET_AH is not set | ||
| 239 | # CONFIG_INET_ESP is not set | ||
| 240 | # CONFIG_INET_IPCOMP is not set | ||
| 241 | # CONFIG_INET_XFRM_TUNNEL is not set | ||
| 242 | # CONFIG_INET_TUNNEL is not set | ||
| 243 | CONFIG_INET_DIAG=y | ||
| 244 | CONFIG_INET_TCP_DIAG=y | ||
| 245 | # CONFIG_TCP_CONG_ADVANCED is not set | ||
| 246 | CONFIG_TCP_CONG_BIC=y | ||
| 247 | # CONFIG_IPV6 is not set | ||
| 248 | # CONFIG_INET6_XFRM_TUNNEL is not set | ||
| 249 | # CONFIG_INET6_TUNNEL is not set | ||
| 250 | # CONFIG_NETFILTER is not set | ||
| 251 | |||
| 252 | # | ||
| 253 | # DCCP Configuration (EXPERIMENTAL) | ||
| 254 | # | ||
| 255 | # CONFIG_IP_DCCP is not set | ||
| 256 | |||
| 257 | # | ||
| 258 | # SCTP Configuration (EXPERIMENTAL) | ||
| 259 | # | ||
| 260 | # CONFIG_IP_SCTP is not set | ||
| 261 | |||
| 262 | # | ||
| 263 | # TIPC Configuration (EXPERIMENTAL) | ||
| 264 | # | ||
| 265 | # CONFIG_TIPC is not set | ||
| 266 | # CONFIG_ATM is not set | ||
| 267 | # CONFIG_BRIDGE is not set | ||
| 268 | # CONFIG_VLAN_8021Q is not set | ||
| 269 | # CONFIG_DECNET is not set | ||
| 270 | # CONFIG_LLC2 is not set | ||
| 271 | # CONFIG_IPX is not set | ||
| 272 | # CONFIG_ATALK is not set | ||
| 273 | # CONFIG_X25 is not set | ||
| 274 | # CONFIG_LAPB is not set | ||
| 275 | # CONFIG_NET_DIVERT is not set | ||
| 276 | # CONFIG_ECONET is not set | ||
| 277 | # CONFIG_WAN_ROUTER is not set | ||
| 278 | |||
| 279 | # | ||
| 280 | # QoS and/or fair queueing | ||
| 281 | # | ||
| 282 | # CONFIG_NET_SCHED is not set | ||
| 283 | |||
| 284 | # | ||
| 285 | # Network testing | ||
| 286 | # | ||
| 287 | # CONFIG_NET_PKTGEN is not set | ||
| 288 | # CONFIG_HAMRADIO is not set | ||
| 289 | # CONFIG_IRDA is not set | ||
| 290 | # CONFIG_BT is not set | ||
| 291 | # CONFIG_IEEE80211 is not set | ||
| 292 | |||
| 293 | # | ||
| 294 | # Device Drivers | ||
| 295 | # | ||
| 296 | |||
| 297 | # | ||
| 298 | # Generic Driver Options | ||
| 299 | # | ||
| 300 | CONFIG_STANDALONE=y | ||
| 301 | CONFIG_PREVENT_FIRMWARE_BUILD=y | ||
| 302 | # CONFIG_FW_LOADER is not set | ||
| 303 | |||
| 304 | # | ||
| 305 | # Connector - unified userspace <-> kernelspace linker | ||
| 306 | # | ||
| 307 | # CONFIG_CONNECTOR is not set | ||
| 308 | |||
| 309 | # | ||
| 310 | # Memory Technology Devices (MTD) | ||
| 311 | # | ||
| 312 | # CONFIG_MTD is not set | ||
| 313 | |||
| 314 | # | ||
| 315 | # Parallel port support | ||
| 316 | # | ||
| 317 | # CONFIG_PARPORT is not set | ||
| 318 | |||
| 319 | # | ||
| 320 | # Plug and Play support | ||
| 321 | # | ||
| 322 | |||
| 323 | # | ||
| 324 | # Block devices | ||
| 325 | # | ||
| 326 | # CONFIG_BLK_DEV_FD is not set | ||
| 327 | # CONFIG_BLK_CPQ_DA is not set | ||
| 328 | # CONFIG_BLK_CPQ_CISS_DA is not set | ||
| 329 | # CONFIG_BLK_DEV_DAC960 is not set | ||
| 330 | # CONFIG_BLK_DEV_UMEM is not set | ||
| 331 | # CONFIG_BLK_DEV_COW_COMMON is not set | ||
| 332 | CONFIG_BLK_DEV_LOOP=y | ||
| 333 | # CONFIG_BLK_DEV_CRYPTOLOOP is not set | ||
| 334 | # CONFIG_BLK_DEV_NBD is not set | ||
| 335 | # CONFIG_BLK_DEV_SX8 is not set | ||
| 336 | CONFIG_BLK_DEV_RAM=y | ||
| 337 | CONFIG_BLK_DEV_RAM_COUNT=16 | ||
| 338 | CONFIG_BLK_DEV_RAM_SIZE=131072 | ||
| 339 | CONFIG_BLK_DEV_INITRD=y | ||
| 340 | # CONFIG_CDROM_PKTCDVD is not set | ||
| 341 | # CONFIG_ATA_OVER_ETH is not set | ||
| 342 | |||
| 343 | # | ||
| 344 | # ATA/ATAPI/MFM/RLL support | ||
| 345 | # | ||
| 346 | # CONFIG_IDE is not set | ||
| 347 | |||
| 348 | # | ||
| 349 | # SCSI device support | ||
| 350 | # | ||
| 351 | # CONFIG_RAID_ATTRS is not set | ||
| 352 | CONFIG_SCSI=y | ||
| 353 | CONFIG_SCSI_PROC_FS=y | ||
| 354 | |||
| 355 | # | ||
| 356 | # SCSI support type (disk, tape, CD-ROM) | ||
| 357 | # | ||
| 358 | CONFIG_BLK_DEV_SD=y | ||
| 359 | # CONFIG_CHR_DEV_ST is not set | ||
| 360 | # CONFIG_CHR_DEV_OSST is not set | ||
| 361 | # CONFIG_BLK_DEV_SR is not set | ||
| 362 | # CONFIG_CHR_DEV_SG is not set | ||
| 363 | # CONFIG_CHR_DEV_SCH is not set | ||
| 364 | |||
| 365 | # | ||
| 366 | # Some SCSI devices (e.g. CD jukebox) support multiple LUNs | ||
| 367 | # | ||
| 368 | # CONFIG_SCSI_MULTI_LUN is not set | ||
| 369 | # CONFIG_SCSI_CONSTANTS is not set | ||
| 370 | # CONFIG_SCSI_LOGGING is not set | ||
| 371 | |||
| 372 | # | ||
| 373 | # SCSI Transport Attributes | ||
| 374 | # | ||
| 375 | # CONFIG_SCSI_SPI_ATTRS is not set | ||
| 376 | # CONFIG_SCSI_FC_ATTRS is not set | ||
| 377 | # CONFIG_SCSI_ISCSI_ATTRS is not set | ||
| 378 | # CONFIG_SCSI_SAS_ATTRS is not set | ||
| 379 | |||
| 380 | # | ||
| 381 | # SCSI low-level drivers | ||
| 382 | # | ||
| 383 | # CONFIG_ISCSI_TCP is not set | ||
| 384 | # CONFIG_BLK_DEV_3W_XXXX_RAID is not set | ||
| 385 | # CONFIG_SCSI_3W_9XXX is not set | ||
| 386 | # CONFIG_SCSI_ACARD is not set | ||
| 387 | # CONFIG_SCSI_AACRAID is not set | ||
| 388 | # CONFIG_SCSI_AIC7XXX is not set | ||
| 389 | # CONFIG_SCSI_AIC7XXX_OLD is not set | ||
| 390 | # CONFIG_SCSI_AIC79XX is not set | ||
| 391 | # CONFIG_SCSI_DPT_I2O is not set | ||
| 392 | # CONFIG_MEGARAID_NEWGEN is not set | ||
| 393 | # CONFIG_MEGARAID_LEGACY is not set | ||
| 394 | # CONFIG_MEGARAID_SAS is not set | ||
| 395 | CONFIG_SCSI_SATA=y | ||
| 396 | # CONFIG_SCSI_SATA_AHCI is not set | ||
| 397 | # CONFIG_SCSI_SATA_SVW is not set | ||
| 398 | # CONFIG_SCSI_ATA_PIIX is not set | ||
| 399 | CONFIG_SCSI_SATA_MV=y | ||
| 400 | # CONFIG_SCSI_SATA_NV is not set | ||
| 401 | # CONFIG_SCSI_PDC_ADMA is not set | ||
| 402 | # CONFIG_SCSI_SATA_QSTOR is not set | ||
| 403 | # CONFIG_SCSI_SATA_PROMISE is not set | ||
| 404 | # CONFIG_SCSI_SATA_SX4 is not set | ||
| 405 | # CONFIG_SCSI_SATA_SIL is not set | ||
| 406 | # CONFIG_SCSI_SATA_SIL24 is not set | ||
| 407 | # CONFIG_SCSI_SATA_SIS is not set | ||
| 408 | # CONFIG_SCSI_SATA_ULI is not set | ||
| 409 | # CONFIG_SCSI_SATA_VIA is not set | ||
| 410 | # CONFIG_SCSI_SATA_VITESSE is not set | ||
| 411 | # CONFIG_SCSI_BUSLOGIC is not set | ||
| 412 | # CONFIG_SCSI_DMX3191D is not set | ||
| 413 | # CONFIG_SCSI_EATA is not set | ||
| 414 | # CONFIG_SCSI_FUTURE_DOMAIN is not set | ||
| 415 | # CONFIG_SCSI_GDTH is not set | ||
| 416 | # CONFIG_SCSI_IPS is not set | ||
| 417 | # CONFIG_SCSI_INITIO is not set | ||
| 418 | # CONFIG_SCSI_INIA100 is not set | ||
| 419 | # CONFIG_SCSI_SYM53C8XX_2 is not set | ||
| 420 | # CONFIG_SCSI_IPR is not set | ||
| 421 | # CONFIG_SCSI_QLOGIC_1280 is not set | ||
| 422 | # CONFIG_SCSI_QLA_FC is not set | ||
| 423 | # CONFIG_SCSI_LPFC is not set | ||
| 424 | # CONFIG_SCSI_DC395x is not set | ||
| 425 | # CONFIG_SCSI_DC390T is not set | ||
| 426 | # CONFIG_SCSI_NSP32 is not set | ||
| 427 | # CONFIG_SCSI_DEBUG is not set | ||
| 428 | |||
| 429 | # | ||
| 430 | # Multi-device support (RAID and LVM) | ||
| 431 | # | ||
| 432 | # CONFIG_MD is not set | ||
| 433 | |||
| 434 | # | ||
| 435 | # Fusion MPT device support | ||
| 436 | # | ||
| 437 | # CONFIG_FUSION is not set | ||
| 438 | # CONFIG_FUSION_SPI is not set | ||
| 439 | # CONFIG_FUSION_FC is not set | ||
| 440 | # CONFIG_FUSION_SAS is not set | ||
| 441 | |||
| 442 | # | ||
| 443 | # IEEE 1394 (FireWire) support | ||
| 444 | # | ||
| 445 | # CONFIG_IEEE1394 is not set | ||
| 446 | |||
| 447 | # | ||
| 448 | # I2O device support | ||
| 449 | # | ||
| 450 | # CONFIG_I2O is not set | ||
| 451 | |||
| 452 | # | ||
| 453 | # Macintosh device drivers | ||
| 454 | # | ||
| 455 | # CONFIG_WINDFARM is not set | ||
| 456 | |||
| 457 | # | ||
| 458 | # Network device support | ||
| 459 | # | ||
| 460 | CONFIG_NETDEVICES=y | ||
| 461 | # CONFIG_DUMMY is not set | ||
| 462 | # CONFIG_BONDING is not set | ||
| 463 | # CONFIG_EQUALIZER is not set | ||
| 464 | # CONFIG_TUN is not set | ||
| 465 | |||
| 466 | # | ||
| 467 | # ARCnet devices | ||
| 468 | # | ||
| 469 | # CONFIG_ARCNET is not set | ||
| 470 | |||
| 471 | # | ||
| 472 | # PHY device support | ||
| 473 | # | ||
| 474 | CONFIG_PHYLIB=y | ||
| 475 | |||
| 476 | # | ||
| 477 | # MII PHY device drivers | ||
| 478 | # | ||
| 479 | # CONFIG_MARVELL_PHY is not set | ||
| 480 | # CONFIG_DAVICOM_PHY is not set | ||
| 481 | # CONFIG_QSEMI_PHY is not set | ||
| 482 | # CONFIG_LXT_PHY is not set | ||
| 483 | # CONFIG_CICADA_PHY is not set | ||
| 484 | |||
| 485 | # | ||
| 486 | # Ethernet (10 or 100Mbit) | ||
| 487 | # | ||
| 488 | CONFIG_NET_ETHERNET=y | ||
| 489 | CONFIG_MII=y | ||
| 490 | # CONFIG_HAPPYMEAL is not set | ||
| 491 | # CONFIG_SUNGEM is not set | ||
| 492 | # CONFIG_CASSINI is not set | ||
| 493 | # CONFIG_NET_VENDOR_3COM is not set | ||
| 494 | |||
| 495 | # | ||
| 496 | # Tulip family network device support | ||
| 497 | # | ||
| 498 | # CONFIG_NET_TULIP is not set | ||
| 499 | # CONFIG_HP100 is not set | ||
| 500 | CONFIG_NET_PCI=y | ||
| 501 | # CONFIG_PCNET32 is not set | ||
| 502 | # CONFIG_AMD8111_ETH is not set | ||
| 503 | # CONFIG_ADAPTEC_STARFIRE is not set | ||
| 504 | # CONFIG_B44 is not set | ||
| 505 | # CONFIG_FORCEDETH is not set | ||
| 506 | # CONFIG_DGRS is not set | ||
| 507 | # CONFIG_EEPRO100 is not set | ||
| 508 | CONFIG_E100=y | ||
| 509 | # CONFIG_FEALNX is not set | ||
| 510 | # CONFIG_NATSEMI is not set | ||
| 511 | # CONFIG_NE2K_PCI is not set | ||
| 512 | # CONFIG_8139CP is not set | ||
| 513 | CONFIG_8139TOO=y | ||
| 514 | # CONFIG_8139TOO_PIO is not set | ||
| 515 | # CONFIG_8139TOO_TUNE_TWISTER is not set | ||
| 516 | # CONFIG_8139TOO_8129 is not set | ||
| 517 | # CONFIG_8139_OLD_RX_RESET is not set | ||
| 518 | # CONFIG_SIS900 is not set | ||
| 519 | # CONFIG_EPIC100 is not set | ||
| 520 | # CONFIG_SUNDANCE is not set | ||
| 521 | # CONFIG_TLAN is not set | ||
| 522 | # CONFIG_VIA_RHINE is not set | ||
| 523 | |||
| 524 | # | ||
| 525 | # Ethernet (1000 Mbit) | ||
| 526 | # | ||
| 527 | # CONFIG_ACENIC is not set | ||
| 528 | # CONFIG_DL2K is not set | ||
| 529 | # CONFIG_E1000 is not set | ||
| 530 | # CONFIG_NS83820 is not set | ||
| 531 | # CONFIG_HAMACHI is not set | ||
| 532 | # CONFIG_YELLOWFIN is not set | ||
| 533 | # CONFIG_R8169 is not set | ||
| 534 | # CONFIG_SIS190 is not set | ||
| 535 | # CONFIG_SKGE is not set | ||
| 536 | # CONFIG_SKY2 is not set | ||
| 537 | # CONFIG_SK98LIN is not set | ||
| 538 | # CONFIG_VIA_VELOCITY is not set | ||
| 539 | # CONFIG_TIGON3 is not set | ||
| 540 | # CONFIG_BNX2 is not set | ||
| 541 | CONFIG_TSI108_ETH=y | ||
| 542 | |||
| 543 | # | ||
| 544 | # Ethernet (10000 Mbit) | ||
| 545 | # | ||
| 546 | # CONFIG_CHELSIO_T1 is not set | ||
| 547 | # CONFIG_IXGB is not set | ||
| 548 | # CONFIG_S2IO is not set | ||
| 549 | |||
| 550 | # | ||
| 551 | # Token Ring devices | ||
| 552 | # | ||
| 553 | # CONFIG_TR is not set | ||
| 554 | |||
| 555 | # | ||
| 556 | # Wireless LAN (non-hamradio) | ||
| 557 | # | ||
| 558 | # CONFIG_NET_RADIO is not set | ||
| 559 | |||
| 560 | # | ||
| 561 | # Wan interfaces | ||
| 562 | # | ||
| 563 | # CONFIG_WAN is not set | ||
| 564 | # CONFIG_FDDI is not set | ||
| 565 | # CONFIG_HIPPI is not set | ||
| 566 | # CONFIG_PPP is not set | ||
| 567 | # CONFIG_SLIP is not set | ||
| 568 | # CONFIG_NET_FC is not set | ||
| 569 | # CONFIG_SHAPER is not set | ||
| 570 | # CONFIG_NETCONSOLE is not set | ||
| 571 | # CONFIG_NETPOLL is not set | ||
| 572 | # CONFIG_NET_POLL_CONTROLLER is not set | ||
| 573 | |||
| 574 | # | ||
| 575 | # ISDN subsystem | ||
| 576 | # | ||
| 577 | # CONFIG_ISDN is not set | ||
| 578 | |||
| 579 | # | ||
| 580 | # Telephony Support | ||
| 581 | # | ||
| 582 | # CONFIG_PHONE is not set | ||
| 583 | |||
| 584 | # | ||
| 585 | # Input device support | ||
| 586 | # | ||
| 587 | CONFIG_INPUT=y | ||
| 588 | |||
| 589 | # | ||
| 590 | # Userland interfaces | ||
| 591 | # | ||
| 592 | # CONFIG_INPUT_MOUSEDEV is not set | ||
| 593 | # CONFIG_INPUT_JOYDEV is not set | ||
| 594 | # CONFIG_INPUT_TSDEV is not set | ||
| 595 | # CONFIG_INPUT_EVDEV is not set | ||
| 596 | # CONFIG_INPUT_EVBUG is not set | ||
| 597 | |||
| 598 | # | ||
| 599 | # Input Device Drivers | ||
| 600 | # | ||
| 601 | # CONFIG_INPUT_KEYBOARD is not set | ||
| 602 | # CONFIG_INPUT_MOUSE is not set | ||
| 603 | # CONFIG_INPUT_JOYSTICK is not set | ||
| 604 | # CONFIG_INPUT_TOUCHSCREEN is not set | ||
| 605 | # CONFIG_INPUT_MISC is not set | ||
| 606 | |||
| 607 | # | ||
| 608 | # Hardware I/O ports | ||
| 609 | # | ||
| 610 | # CONFIG_SERIO is not set | ||
| 611 | # CONFIG_GAMEPORT is not set | ||
| 612 | |||
| 613 | # | ||
| 614 | # Character devices | ||
| 615 | # | ||
| 616 | # CONFIG_VT is not set | ||
| 617 | # CONFIG_SERIAL_NONSTANDARD is not set | ||
| 618 | |||
| 619 | # | ||
| 620 | # Serial drivers | ||
| 621 | # | ||
| 622 | CONFIG_SERIAL_8250=y | ||
| 623 | CONFIG_SERIAL_8250_CONSOLE=y | ||
| 624 | CONFIG_SERIAL_8250_PCI=y | ||
| 625 | CONFIG_SERIAL_8250_NR_UARTS=4 | ||
| 626 | CONFIG_SERIAL_8250_RUNTIME_UARTS=4 | ||
| 627 | # CONFIG_SERIAL_8250_EXTENDED is not set | ||
| 628 | |||
| 629 | # | ||
| 630 | # Non-8250 serial port support | ||
| 631 | # | ||
| 632 | CONFIG_SERIAL_CORE=y | ||
| 633 | CONFIG_SERIAL_CORE_CONSOLE=y | ||
| 634 | # CONFIG_SERIAL_JSM is not set | ||
| 635 | CONFIG_UNIX98_PTYS=y | ||
| 636 | CONFIG_LEGACY_PTYS=y | ||
| 637 | CONFIG_LEGACY_PTY_COUNT=256 | ||
| 638 | |||
| 639 | # | ||
| 640 | # IPMI | ||
| 641 | # | ||
| 642 | # CONFIG_IPMI_HANDLER is not set | ||
| 643 | |||
| 644 | # | ||
| 645 | # Watchdog Cards | ||
| 646 | # | ||
| 647 | # CONFIG_WATCHDOG is not set | ||
| 648 | # CONFIG_NVRAM is not set | ||
| 649 | CONFIG_GEN_RTC=y | ||
| 650 | # CONFIG_GEN_RTC_X is not set | ||
| 651 | # CONFIG_DTLK is not set | ||
| 652 | # CONFIG_R3964 is not set | ||
| 653 | # CONFIG_APPLICOM is not set | ||
| 654 | |||
| 655 | # | ||
| 656 | # Ftape, the floppy tape device driver | ||
| 657 | # | ||
| 658 | # CONFIG_AGP is not set | ||
| 659 | # CONFIG_DRM is not set | ||
| 660 | # CONFIG_RAW_DRIVER is not set | ||
| 661 | |||
| 662 | # | ||
| 663 | # TPM devices | ||
| 664 | # | ||
| 665 | # CONFIG_TCG_TPM is not set | ||
| 666 | # CONFIG_TELCLOCK is not set | ||
| 667 | |||
| 668 | # | ||
| 669 | # I2C support | ||
| 670 | # | ||
| 671 | # CONFIG_I2C is not set | ||
| 672 | |||
| 673 | # | ||
| 674 | # SPI support | ||
| 675 | # | ||
| 676 | # CONFIG_SPI is not set | ||
| 677 | # CONFIG_SPI_MASTER is not set | ||
| 678 | |||
| 679 | # | ||
| 680 | # Dallas's 1-wire bus | ||
| 681 | # | ||
| 682 | # CONFIG_W1 is not set | ||
| 683 | |||
| 684 | # | ||
| 685 | # Hardware Monitoring support | ||
| 686 | # | ||
| 687 | CONFIG_HWMON=y | ||
| 688 | # CONFIG_HWMON_VID is not set | ||
| 689 | # CONFIG_SENSORS_F71805F is not set | ||
| 690 | # CONFIG_HWMON_DEBUG_CHIP is not set | ||
| 691 | |||
| 692 | # | ||
| 693 | # Misc devices | ||
| 694 | # | ||
| 695 | |||
| 696 | # | ||
| 697 | # Multimedia devices | ||
| 698 | # | ||
| 699 | # CONFIG_VIDEO_DEV is not set | ||
| 700 | |||
| 701 | # | ||
| 702 | # Digital Video Broadcasting Devices | ||
| 703 | # | ||
| 704 | # CONFIG_DVB is not set | ||
| 705 | |||
| 706 | # | ||
| 707 | # Graphics support | ||
| 708 | # | ||
| 709 | # CONFIG_FB is not set | ||
| 710 | |||
| 711 | # | ||
| 712 | # Sound | ||
| 713 | # | ||
| 714 | # CONFIG_SOUND is not set | ||
| 715 | |||
| 716 | # | ||
| 717 | # USB support | ||
| 718 | # | ||
| 719 | CONFIG_USB_ARCH_HAS_HCD=y | ||
| 720 | CONFIG_USB_ARCH_HAS_OHCI=y | ||
| 721 | CONFIG_USB_ARCH_HAS_EHCI=y | ||
| 722 | # CONFIG_USB is not set | ||
| 723 | |||
| 724 | # | ||
| 725 | # NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support' | ||
| 726 | # | ||
| 727 | |||
| 728 | # | ||
| 729 | # USB Gadget Support | ||
| 730 | # | ||
| 731 | # CONFIG_USB_GADGET is not set | ||
| 732 | |||
| 733 | # | ||
| 734 | # MMC/SD Card support | ||
| 735 | # | ||
| 736 | # CONFIG_MMC is not set | ||
| 737 | |||
| 738 | # | ||
| 739 | # LED devices | ||
| 740 | # | ||
| 741 | # CONFIG_NEW_LEDS is not set | ||
| 742 | |||
| 743 | # | ||
| 744 | # LED drivers | ||
| 745 | # | ||
| 746 | |||
| 747 | # | ||
| 748 | # LED Triggers | ||
| 749 | # | ||
| 750 | |||
| 751 | # | ||
| 752 | # InfiniBand support | ||
| 753 | # | ||
| 754 | # CONFIG_INFINIBAND is not set | ||
| 755 | |||
| 756 | # | ||
| 757 | # EDAC - error detection and reporting (RAS) (EXPERIMENTAL) | ||
| 758 | # | ||
| 759 | |||
| 760 | # | ||
| 761 | # Real Time Clock | ||
| 762 | # | ||
| 763 | # CONFIG_RTC_CLASS is not set | ||
| 764 | |||
| 765 | # | ||
| 766 | # File systems | ||
| 767 | # | ||
| 768 | CONFIG_EXT2_FS=y | ||
| 769 | # CONFIG_EXT2_FS_XATTR is not set | ||
| 770 | # CONFIG_EXT2_FS_XIP is not set | ||
| 771 | CONFIG_EXT3_FS=y | ||
| 772 | CONFIG_EXT3_FS_XATTR=y | ||
| 773 | # CONFIG_EXT3_FS_POSIX_ACL is not set | ||
| 774 | # CONFIG_EXT3_FS_SECURITY is not set | ||
| 775 | CONFIG_JBD=y | ||
| 776 | # CONFIG_JBD_DEBUG is not set | ||
| 777 | CONFIG_FS_MBCACHE=y | ||
| 778 | # CONFIG_REISERFS_FS is not set | ||
| 779 | # CONFIG_JFS_FS is not set | ||
| 780 | # CONFIG_FS_POSIX_ACL is not set | ||
| 781 | # CONFIG_XFS_FS is not set | ||
| 782 | # CONFIG_OCFS2_FS is not set | ||
| 783 | # CONFIG_MINIX_FS is not set | ||
| 784 | # CONFIG_ROMFS_FS is not set | ||
| 785 | CONFIG_INOTIFY=y | ||
| 786 | # CONFIG_QUOTA is not set | ||
| 787 | CONFIG_DNOTIFY=y | ||
| 788 | # CONFIG_AUTOFS_FS is not set | ||
| 789 | # CONFIG_AUTOFS4_FS is not set | ||
| 790 | # CONFIG_FUSE_FS is not set | ||
| 791 | |||
| 792 | # | ||
| 793 | # CD-ROM/DVD Filesystems | ||
| 794 | # | ||
| 795 | # CONFIG_ISO9660_FS is not set | ||
| 796 | # CONFIG_UDF_FS is not set | ||
| 797 | |||
| 798 | # | ||
| 799 | # DOS/FAT/NT Filesystems | ||
| 800 | # | ||
| 801 | # CONFIG_MSDOS_FS is not set | ||
| 802 | # CONFIG_VFAT_FS is not set | ||
| 803 | # CONFIG_NTFS_FS is not set | ||
| 804 | |||
| 805 | # | ||
| 806 | # Pseudo filesystems | ||
| 807 | # | ||
| 808 | CONFIG_PROC_FS=y | ||
| 809 | CONFIG_PROC_KCORE=y | ||
| 810 | CONFIG_SYSFS=y | ||
| 811 | CONFIG_TMPFS=y | ||
| 812 | # CONFIG_HUGETLB_PAGE is not set | ||
| 813 | CONFIG_RAMFS=y | ||
| 814 | # CONFIG_CONFIGFS_FS is not set | ||
| 815 | |||
| 816 | # | ||
| 817 | # Miscellaneous filesystems | ||
| 818 | # | ||
| 819 | # CONFIG_ADFS_FS is not set | ||
| 820 | # CONFIG_AFFS_FS is not set | ||
| 821 | # CONFIG_HFS_FS is not set | ||
| 822 | # CONFIG_HFSPLUS_FS is not set | ||
| 823 | # CONFIG_BEFS_FS is not set | ||
| 824 | # CONFIG_BFS_FS is not set | ||
| 825 | # CONFIG_EFS_FS is not set | ||
| 826 | # CONFIG_CRAMFS is not set | ||
| 827 | # CONFIG_VXFS_FS is not set | ||
| 828 | # CONFIG_HPFS_FS is not set | ||
| 829 | # CONFIG_QNX4FS_FS is not set | ||
| 830 | # CONFIG_SYSV_FS is not set | ||
| 831 | # CONFIG_UFS_FS is not set | ||
| 832 | |||
| 833 | # | ||
| 834 | # Network File Systems | ||
| 835 | # | ||
| 836 | CONFIG_NFS_FS=y | ||
| 837 | # CONFIG_NFS_V3 is not set | ||
| 838 | # CONFIG_NFS_V4 is not set | ||
| 839 | # CONFIG_NFS_DIRECTIO is not set | ||
| 840 | # CONFIG_NFSD is not set | ||
| 841 | CONFIG_ROOT_NFS=y | ||
| 842 | CONFIG_LOCKD=y | ||
| 843 | CONFIG_NFS_COMMON=y | ||
| 844 | CONFIG_SUNRPC=y | ||
| 845 | # CONFIG_RPCSEC_GSS_KRB5 is not set | ||
| 846 | # CONFIG_RPCSEC_GSS_SPKM3 is not set | ||
| 847 | # CONFIG_SMB_FS is not set | ||
| 848 | # CONFIG_CIFS is not set | ||
| 849 | # CONFIG_NCP_FS is not set | ||
| 850 | # CONFIG_CODA_FS is not set | ||
| 851 | # CONFIG_AFS_FS is not set | ||
| 852 | # CONFIG_9P_FS is not set | ||
| 853 | |||
| 854 | # | ||
| 855 | # Partition Types | ||
| 856 | # | ||
| 857 | CONFIG_PARTITION_ADVANCED=y | ||
| 858 | # CONFIG_ACORN_PARTITION is not set | ||
| 859 | # CONFIG_OSF_PARTITION is not set | ||
| 860 | # CONFIG_AMIGA_PARTITION is not set | ||
| 861 | # CONFIG_ATARI_PARTITION is not set | ||
| 862 | # CONFIG_MAC_PARTITION is not set | ||
| 863 | CONFIG_MSDOS_PARTITION=y | ||
| 864 | # CONFIG_BSD_DISKLABEL is not set | ||
| 865 | # CONFIG_MINIX_SUBPARTITION is not set | ||
| 866 | # CONFIG_SOLARIS_X86_PARTITION is not set | ||
| 867 | # CONFIG_UNIXWARE_DISKLABEL is not set | ||
| 868 | # CONFIG_LDM_PARTITION is not set | ||
| 869 | # CONFIG_SGI_PARTITION is not set | ||
| 870 | # CONFIG_ULTRIX_PARTITION is not set | ||
| 871 | # CONFIG_SUN_PARTITION is not set | ||
| 872 | # CONFIG_KARMA_PARTITION is not set | ||
| 873 | # CONFIG_EFI_PARTITION is not set | ||
| 874 | |||
| 875 | # | ||
| 876 | # Native Language Support | ||
| 877 | # | ||
| 878 | # CONFIG_NLS is not set | ||
| 879 | |||
| 880 | # | ||
| 881 | # Library routines | ||
| 882 | # | ||
| 883 | # CONFIG_CRC_CCITT is not set | ||
| 884 | # CONFIG_CRC16 is not set | ||
| 885 | CONFIG_CRC32=y | ||
| 886 | # CONFIG_LIBCRC32C is not set | ||
| 887 | |||
| 888 | # | ||
| 889 | # Instrumentation Support | ||
| 890 | # | ||
| 891 | # CONFIG_PROFILING is not set | ||
| 892 | |||
| 893 | # | ||
| 894 | # Kernel hacking | ||
| 895 | # | ||
| 896 | # CONFIG_PRINTK_TIME is not set | ||
| 897 | # CONFIG_MAGIC_SYSRQ is not set | ||
| 898 | # CONFIG_DEBUG_KERNEL is not set | ||
| 899 | CONFIG_LOG_BUF_SHIFT=14 | ||
| 900 | # CONFIG_DEBUG_FS is not set | ||
| 901 | # CONFIG_UNWIND_INFO is not set | ||
| 902 | # CONFIG_BOOTX_TEXT is not set | ||
| 903 | # CONFIG_SERIAL_TEXT_DEBUG is not set | ||
| 904 | # CONFIG_PPC_EARLY_DEBUG_LPAR is not set | ||
| 905 | # CONFIG_PPC_EARLY_DEBUG_G5 is not set | ||
| 906 | # CONFIG_PPC_EARLY_DEBUG_RTAS is not set | ||
| 907 | # CONFIG_PPC_EARLY_DEBUG_MAPLE is not set | ||
| 908 | # CONFIG_PPC_EARLY_DEBUG_ISERIES is not set | ||
| 909 | |||
| 910 | # | ||
| 911 | # Security options | ||
| 912 | # | ||
| 913 | # CONFIG_KEYS is not set | ||
| 914 | # CONFIG_SECURITY is not set | ||
| 915 | |||
| 916 | # | ||
| 917 | # Cryptographic options | ||
| 918 | # | ||
| 919 | # CONFIG_CRYPTO is not set | ||
| 920 | |||
| 921 | # | ||
| 922 | # Hardware crypto devices | ||
| 923 | # | ||
diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile index 803858e86160..814f242aeb8c 100644 --- a/arch/powerpc/kernel/Makefile +++ b/arch/powerpc/kernel/Makefile | |||
| @@ -50,7 +50,8 @@ extra-$(CONFIG_FSL_BOOKE) := head_fsl_booke.o | |||
| 50 | extra-$(CONFIG_8xx) := head_8xx.o | 50 | extra-$(CONFIG_8xx) := head_8xx.o |
| 51 | extra-y += vmlinux.lds | 51 | extra-y += vmlinux.lds |
| 52 | 52 | ||
| 53 | obj-y += time.o prom.o traps.o setup-common.o udbg.o | 53 | obj-y += time.o prom.o traps.o setup-common.o \ |
| 54 | udbg.o misc.o | ||
| 54 | obj-$(CONFIG_PPC32) += entry_32.o setup_32.o misc_32.o | 55 | obj-$(CONFIG_PPC32) += entry_32.o setup_32.o misc_32.o |
| 55 | obj-$(CONFIG_PPC64) += misc_64.o dma_64.o iommu.o | 56 | obj-$(CONFIG_PPC64) += misc_64.o dma_64.o iommu.o |
| 56 | obj-$(CONFIG_PPC_MULTIPLATFORM) += prom_init.o | 57 | obj-$(CONFIG_PPC_MULTIPLATFORM) += prom_init.o |
diff --git a/arch/powerpc/kernel/cpu_setup_power4.S b/arch/powerpc/kernel/cpu_setup_power4.S index 271418308d53..1fc863261003 100644 --- a/arch/powerpc/kernel/cpu_setup_power4.S +++ b/arch/powerpc/kernel/cpu_setup_power4.S | |||
| @@ -125,7 +125,12 @@ _GLOBAL(__save_cpu_setup) | |||
| 125 | cmpwi r0,0x44 | 125 | cmpwi r0,0x44 |
| 126 | bne 2f | 126 | bne 2f |
| 127 | 127 | ||
| 128 | 1: /* Save HID0,1,4 and 5 */ | 128 | 1: /* skip if not running in HV mode */ |
| 129 | mfmsr r0 | ||
| 130 | rldicl. r0,r0,4,63 | ||
| 131 | beq 2f | ||
| 132 | |||
| 133 | /* Save HID0,1,4 and 5 */ | ||
| 129 | mfspr r3,SPRN_HID0 | 134 | mfspr r3,SPRN_HID0 |
| 130 | std r3,CS_HID0(r5) | 135 | std r3,CS_HID0(r5) |
| 131 | mfspr r3,SPRN_HID1 | 136 | mfspr r3,SPRN_HID1 |
| @@ -159,7 +164,12 @@ _GLOBAL(__restore_cpu_setup) | |||
| 159 | cmpwi r0,0x44 | 164 | cmpwi r0,0x44 |
| 160 | bnelr | 165 | bnelr |
| 161 | 166 | ||
| 162 | 1: /* Before accessing memory, we make sure rm_ci is clear */ | 167 | 1: /* skip if not running in HV mode */ |
| 168 | mfmsr r0 | ||
| 169 | rldicl. r0,r0,4,63 | ||
| 170 | beqlr | ||
| 171 | |||
| 172 | /* Before accessing memory, we make sure rm_ci is clear */ | ||
| 163 | li r0,0 | 173 | li r0,0 |
| 164 | mfspr r3,SPRN_HID4 | 174 | mfspr r3,SPRN_HID4 |
| 165 | rldimi r3,r0,40,23 /* clear bit 23 (rm_ci) */ | 175 | rldimi r3,r0,40,23 /* clear bit 23 (rm_ci) */ |
diff --git a/arch/powerpc/kernel/cputable.c b/arch/powerpc/kernel/cputable.c index 1c114880dc05..abf7d42a8b07 100644 --- a/arch/powerpc/kernel/cputable.c +++ b/arch/powerpc/kernel/cputable.c | |||
| @@ -722,18 +722,6 @@ struct cpu_spec cpu_specs[] = { | |||
| 722 | .oprofile_type = PPC_OPROFILE_G4, | 722 | .oprofile_type = PPC_OPROFILE_G4, |
| 723 | .platform = "ppc7450", | 723 | .platform = "ppc7450", |
| 724 | }, | 724 | }, |
| 725 | { /* 8641 */ | ||
| 726 | .pvr_mask = 0xffffffff, | ||
| 727 | .pvr_value = 0x80040010, | ||
| 728 | .cpu_name = "8641", | ||
| 729 | .cpu_features = CPU_FTRS_7447A, | ||
| 730 | .cpu_user_features = COMMON_USER | PPC_FEATURE_HAS_ALTIVEC_COMP, | ||
| 731 | .icache_bsize = 32, | ||
| 732 | .dcache_bsize = 32, | ||
| 733 | .num_pmcs = 6, | ||
| 734 | .cpu_setup = __setup_cpu_745x | ||
| 735 | }, | ||
| 736 | |||
| 737 | { /* 82xx (8240, 8245, 8260 are all 603e cores) */ | 725 | { /* 82xx (8240, 8245, 8260 are all 603e cores) */ |
| 738 | .pvr_mask = 0x7fff0000, | 726 | .pvr_mask = 0x7fff0000, |
| 739 | .pvr_value = 0x00810000, | 727 | .pvr_value = 0x00810000, |
diff --git a/arch/powerpc/kernel/crash.c b/arch/powerpc/kernel/crash.c index 22ceba844bf4..358cecdc6aef 100644 --- a/arch/powerpc/kernel/crash.c +++ b/arch/powerpc/kernel/crash.c | |||
| @@ -24,9 +24,11 @@ | |||
| 24 | #include <linux/init.h> | 24 | #include <linux/init.h> |
| 25 | #include <linux/irq.h> | 25 | #include <linux/irq.h> |
| 26 | #include <linux/types.h> | 26 | #include <linux/types.h> |
| 27 | #include <linux/irq.h> | ||
| 27 | 28 | ||
| 28 | #include <asm/processor.h> | 29 | #include <asm/processor.h> |
| 29 | #include <asm/machdep.h> | 30 | #include <asm/machdep.h> |
| 31 | #include <asm/kexec.h> | ||
| 30 | #include <asm/kdump.h> | 32 | #include <asm/kdump.h> |
| 31 | #include <asm/lmb.h> | 33 | #include <asm/lmb.h> |
| 32 | #include <asm/firmware.h> | 34 | #include <asm/firmware.h> |
| @@ -41,6 +43,7 @@ | |||
| 41 | 43 | ||
| 42 | /* This keeps a track of which one is crashing cpu. */ | 44 | /* This keeps a track of which one is crashing cpu. */ |
| 43 | int crashing_cpu = -1; | 45 | int crashing_cpu = -1; |
| 46 | static cpumask_t cpus_in_crash = CPU_MASK_NONE; | ||
| 44 | 47 | ||
| 45 | static u32 *append_elf_note(u32 *buf, char *name, unsigned type, void *data, | 48 | static u32 *append_elf_note(u32 *buf, char *name, unsigned type, void *data, |
| 46 | size_t data_len) | 49 | size_t data_len) |
| @@ -98,34 +101,66 @@ static void crash_save_this_cpu(struct pt_regs *regs, int cpu) | |||
| 98 | } | 101 | } |
| 99 | 102 | ||
| 100 | #ifdef CONFIG_SMP | 103 | #ifdef CONFIG_SMP |
| 101 | static atomic_t waiting_for_crash_ipi; | 104 | static atomic_t enter_on_soft_reset = ATOMIC_INIT(0); |
| 102 | 105 | ||
| 103 | void crash_ipi_callback(struct pt_regs *regs) | 106 | void crash_ipi_callback(struct pt_regs *regs) |
| 104 | { | 107 | { |
| 105 | int cpu = smp_processor_id(); | 108 | int cpu = smp_processor_id(); |
| 106 | 109 | ||
| 107 | if (cpu == crashing_cpu) | ||
| 108 | return; | ||
| 109 | |||
| 110 | if (!cpu_online(cpu)) | 110 | if (!cpu_online(cpu)) |
| 111 | return; | 111 | return; |
| 112 | 112 | ||
| 113 | if (ppc_md.kexec_cpu_down) | ||
| 114 | ppc_md.kexec_cpu_down(1, 1); | ||
| 115 | |||
| 116 | local_irq_disable(); | 113 | local_irq_disable(); |
| 114 | if (!cpu_isset(cpu, cpus_in_crash)) | ||
| 115 | crash_save_this_cpu(regs, cpu); | ||
| 116 | cpu_set(cpu, cpus_in_crash); | ||
| 117 | 117 | ||
| 118 | crash_save_this_cpu(regs, cpu); | 118 | /* |
| 119 | atomic_dec(&waiting_for_crash_ipi); | 119 | * Entered via soft-reset - could be the kdump |
| 120 | * process is invoked using soft-reset or user activated | ||
| 121 | * it if some CPU did not respond to an IPI. | ||
| 122 | * For soft-reset, the secondary CPU can enter this func | ||
| 123 | * twice. 1 - using IPI, and 2. soft-reset. | ||
| 124 | * Tell the kexec CPU that entered via soft-reset and ready | ||
| 125 | * to go down. | ||
| 126 | */ | ||
| 127 | if (cpu_isset(cpu, cpus_in_sr)) { | ||
| 128 | cpu_clear(cpu, cpus_in_sr); | ||
| 129 | atomic_inc(&enter_on_soft_reset); | ||
| 130 | } | ||
| 131 | |||
| 132 | /* | ||
| 133 | * Starting the kdump boot. | ||
| 134 | * This barrier is needed to make sure that all CPUs are stopped. | ||
| 135 | * If not, soft-reset will be invoked to bring other CPUs. | ||
| 136 | */ | ||
| 137 | while (!cpu_isset(crashing_cpu, cpus_in_crash)) | ||
| 138 | cpu_relax(); | ||
| 139 | |||
| 140 | if (ppc_md.kexec_cpu_down) | ||
| 141 | ppc_md.kexec_cpu_down(1, 1); | ||
| 120 | kexec_smp_wait(); | 142 | kexec_smp_wait(); |
| 121 | /* NOTREACHED */ | 143 | /* NOTREACHED */ |
| 122 | } | 144 | } |
| 123 | 145 | ||
| 124 | static void crash_kexec_prepare_cpus(void) | 146 | /* |
| 147 | * Wait until all CPUs are entered via soft-reset. | ||
| 148 | */ | ||
| 149 | static void crash_soft_reset_check(int cpu) | ||
| 150 | { | ||
| 151 | unsigned int ncpus = num_online_cpus() - 1;/* Excluding the panic cpu */ | ||
| 152 | |||
| 153 | cpu_clear(cpu, cpus_in_sr); | ||
| 154 | while (atomic_read(&enter_on_soft_reset) != ncpus) | ||
| 155 | cpu_relax(); | ||
| 156 | } | ||
| 157 | |||
| 158 | |||
| 159 | static void crash_kexec_prepare_cpus(int cpu) | ||
| 125 | { | 160 | { |
| 126 | unsigned int msecs; | 161 | unsigned int msecs; |
| 127 | 162 | ||
| 128 | atomic_set(&waiting_for_crash_ipi, num_online_cpus() - 1); | 163 | unsigned int ncpus = num_online_cpus() - 1;/* Excluding the panic cpu */ |
| 129 | 164 | ||
| 130 | crash_send_ipi(crash_ipi_callback); | 165 | crash_send_ipi(crash_ipi_callback); |
| 131 | smp_wmb(); | 166 | smp_wmb(); |
| @@ -133,14 +168,13 @@ static void crash_kexec_prepare_cpus(void) | |||
| 133 | /* | 168 | /* |
| 134 | * FIXME: Until we will have the way to stop other CPUSs reliabally, | 169 | * FIXME: Until we will have the way to stop other CPUSs reliabally, |
| 135 | * the crash CPU will send an IPI and wait for other CPUs to | 170 | * the crash CPU will send an IPI and wait for other CPUs to |
| 136 | * respond. If not, proceed the kexec boot even though we failed to | 171 | * respond. |
| 137 | * capture other CPU states. | ||
| 138 | * Delay of at least 10 seconds. | 172 | * Delay of at least 10 seconds. |
| 139 | */ | 173 | */ |
| 140 | printk(KERN_ALERT "Sending IPI to other cpus...\n"); | 174 | printk(KERN_EMERG "Sending IPI to other cpus...\n"); |
| 141 | msecs = 10000; | 175 | msecs = 10000; |
| 142 | while ((atomic_read(&waiting_for_crash_ipi) > 0) && (--msecs > 0)) { | 176 | while ((cpus_weight(cpus_in_crash) < ncpus) && (--msecs > 0)) { |
| 143 | barrier(); | 177 | cpu_relax(); |
| 144 | mdelay(1); | 178 | mdelay(1); |
| 145 | } | 179 | } |
| 146 | 180 | ||
| @@ -149,18 +183,71 @@ static void crash_kexec_prepare_cpus(void) | |||
| 149 | /* | 183 | /* |
| 150 | * FIXME: In case if we do not get all CPUs, one possibility: ask the | 184 | * FIXME: In case if we do not get all CPUs, one possibility: ask the |
| 151 | * user to do soft reset such that we get all. | 185 | * user to do soft reset such that we get all. |
| 152 | * IPI handler is already set by the panic cpu initially. Therefore, | 186 | * Soft-reset will be used until better mechanism is implemented. |
| 153 | * all cpus could invoke this handler from die() and the panic CPU | 187 | */ |
| 154 | * will call machine_kexec() directly from this handler to do | 188 | if (cpus_weight(cpus_in_crash) < ncpus) { |
| 155 | * kexec boot. | 189 | printk(KERN_EMERG "done waiting: %d cpu(s) not responding\n", |
| 190 | ncpus - cpus_weight(cpus_in_crash)); | ||
| 191 | printk(KERN_EMERG "Activate soft-reset to stop other cpu(s)\n"); | ||
| 192 | cpus_in_sr = CPU_MASK_NONE; | ||
| 193 | atomic_set(&enter_on_soft_reset, 0); | ||
| 194 | while (cpus_weight(cpus_in_crash) < ncpus) | ||
| 195 | cpu_relax(); | ||
| 196 | } | ||
| 197 | /* | ||
| 198 | * Make sure all CPUs are entered via soft-reset if the kdump is | ||
| 199 | * invoked using soft-reset. | ||
| 156 | */ | 200 | */ |
| 157 | if (atomic_read(&waiting_for_crash_ipi)) | 201 | if (cpu_isset(cpu, cpus_in_sr)) |
| 158 | printk(KERN_ALERT "done waiting: %d cpus not responding\n", | 202 | crash_soft_reset_check(cpu); |
| 159 | atomic_read(&waiting_for_crash_ipi)); | ||
| 160 | /* Leave the IPI callback set */ | 203 | /* Leave the IPI callback set */ |
| 161 | } | 204 | } |
| 205 | |||
| 206 | /* | ||
| 207 | * This function will be called by secondary cpus or by kexec cpu | ||
| 208 | * if soft-reset is activated to stop some CPUs. | ||
| 209 | */ | ||
| 210 | void crash_kexec_secondary(struct pt_regs *regs) | ||
| 211 | { | ||
| 212 | int cpu = smp_processor_id(); | ||
| 213 | unsigned long flags; | ||
| 214 | int msecs = 5; | ||
| 215 | |||
| 216 | local_irq_save(flags); | ||
| 217 | /* Wait 5ms if the kexec CPU is not entered yet. */ | ||
| 218 | while (crashing_cpu < 0) { | ||
| 219 | if (--msecs < 0) { | ||
| 220 | /* | ||
| 221 | * Either kdump image is not loaded or | ||
| 222 | * kdump process is not started - Probably xmon | ||
| 223 | * exited using 'x'(exit and recover) or | ||
| 224 | * kexec_should_crash() failed for all running tasks. | ||
| 225 | */ | ||
| 226 | cpu_clear(cpu, cpus_in_sr); | ||
| 227 | local_irq_restore(flags); | ||
| 228 | return; | ||
| 229 | } | ||
| 230 | mdelay(1); | ||
| 231 | cpu_relax(); | ||
| 232 | } | ||
| 233 | if (cpu == crashing_cpu) { | ||
| 234 | /* | ||
| 235 | * Panic CPU will enter this func only via soft-reset. | ||
| 236 | * Wait until all secondary CPUs entered and | ||
| 237 | * then start kexec boot. | ||
| 238 | */ | ||
| 239 | crash_soft_reset_check(cpu); | ||
| 240 | cpu_set(crashing_cpu, cpus_in_crash); | ||
| 241 | if (ppc_md.kexec_cpu_down) | ||
| 242 | ppc_md.kexec_cpu_down(1, 0); | ||
| 243 | machine_kexec(kexec_crash_image); | ||
| 244 | /* NOTREACHED */ | ||
| 245 | } | ||
| 246 | crash_ipi_callback(regs); | ||
| 247 | } | ||
| 248 | |||
| 162 | #else | 249 | #else |
| 163 | static void crash_kexec_prepare_cpus(void) | 250 | static void crash_kexec_prepare_cpus(int cpu) |
| 164 | { | 251 | { |
| 165 | /* | 252 | /* |
| 166 | * move the secondarys to us so that we can copy | 253 | * move the secondarys to us so that we can copy |
| @@ -171,6 +258,10 @@ static void crash_kexec_prepare_cpus(void) | |||
| 171 | smp_release_cpus(); | 258 | smp_release_cpus(); |
| 172 | } | 259 | } |
| 173 | 260 | ||
| 261 | void crash_kexec_secondary(struct pt_regs *regs) | ||
| 262 | { | ||
| 263 | cpus_in_sr = CPU_MASK_NONE; | ||
| 264 | } | ||
| 174 | #endif | 265 | #endif |
| 175 | 266 | ||
| 176 | void default_machine_crash_shutdown(struct pt_regs *regs) | 267 | void default_machine_crash_shutdown(struct pt_regs *regs) |
| @@ -199,14 +290,14 @@ void default_machine_crash_shutdown(struct pt_regs *regs) | |||
| 199 | desc->chip->disable(irq); | 290 | desc->chip->disable(irq); |
| 200 | } | 291 | } |
| 201 | 292 | ||
| 202 | if (ppc_md.kexec_cpu_down) | ||
| 203 | ppc_md.kexec_cpu_down(1, 0); | ||
| 204 | |||
| 205 | /* | 293 | /* |
| 206 | * Make a note of crashing cpu. Will be used in machine_kexec | 294 | * Make a note of crashing cpu. Will be used in machine_kexec |
| 207 | * such that another IPI will not be sent. | 295 | * such that another IPI will not be sent. |
| 208 | */ | 296 | */ |
| 209 | crashing_cpu = smp_processor_id(); | 297 | crashing_cpu = smp_processor_id(); |
| 210 | crash_kexec_prepare_cpus(); | ||
| 211 | crash_save_this_cpu(regs, crashing_cpu); | 298 | crash_save_this_cpu(regs, crashing_cpu); |
| 299 | crash_kexec_prepare_cpus(crashing_cpu); | ||
| 300 | cpu_set(crashing_cpu, cpus_in_crash); | ||
| 301 | if (ppc_md.kexec_cpu_down) | ||
| 302 | ppc_md.kexec_cpu_down(1, 0); | ||
| 212 | } | 303 | } |
diff --git a/arch/powerpc/kernel/head_64.S b/arch/powerpc/kernel/head_64.S index 831acbdf2592..8cfd040d1f50 100644 --- a/arch/powerpc/kernel/head_64.S +++ b/arch/powerpc/kernel/head_64.S | |||
| @@ -85,34 +85,6 @@ END_FTR_SECTION(0, 1) | |||
| 85 | /* Catch branch to 0 in real mode */ | 85 | /* Catch branch to 0 in real mode */ |
| 86 | trap | 86 | trap |
| 87 | 87 | ||
| 88 | #ifdef CONFIG_PPC_ISERIES | ||
| 89 | /* | ||
| 90 | * At offset 0x20, there is a pointer to iSeries LPAR data. | ||
| 91 | * This is required by the hypervisor | ||
| 92 | */ | ||
| 93 | . = 0x20 | ||
| 94 | .llong hvReleaseData-KERNELBASE | ||
| 95 | |||
| 96 | /* | ||
| 97 | * At offset 0x28 and 0x30 are offsets to the mschunks_map | ||
| 98 | * array (used by the iSeries LPAR debugger to do translation | ||
| 99 | * between physical addresses and absolute addresses) and | ||
| 100 | * to the pidhash table (also used by the debugger) | ||
| 101 | */ | ||
| 102 | .llong mschunks_map-KERNELBASE | ||
| 103 | .llong 0 /* pidhash-KERNELBASE SFRXXX */ | ||
| 104 | |||
| 105 | /* Offset 0x38 - Pointer to start of embedded System.map */ | ||
| 106 | .globl embedded_sysmap_start | ||
| 107 | embedded_sysmap_start: | ||
| 108 | .llong 0 | ||
| 109 | /* Offset 0x40 - Pointer to end of embedded System.map */ | ||
| 110 | .globl embedded_sysmap_end | ||
| 111 | embedded_sysmap_end: | ||
| 112 | .llong 0 | ||
| 113 | |||
| 114 | #endif /* CONFIG_PPC_ISERIES */ | ||
| 115 | |||
| 116 | /* Secondary processors spin on this value until it goes to 1. */ | 88 | /* Secondary processors spin on this value until it goes to 1. */ |
| 117 | .globl __secondary_hold_spinloop | 89 | .globl __secondary_hold_spinloop |
| 118 | __secondary_hold_spinloop: | 90 | __secondary_hold_spinloop: |
| @@ -124,6 +96,15 @@ __secondary_hold_spinloop: | |||
| 124 | __secondary_hold_acknowledge: | 96 | __secondary_hold_acknowledge: |
| 125 | .llong 0x0 | 97 | .llong 0x0 |
| 126 | 98 | ||
| 99 | #ifdef CONFIG_PPC_ISERIES | ||
| 100 | /* | ||
| 101 | * At offset 0x20, there is a pointer to iSeries LPAR data. | ||
| 102 | * This is required by the hypervisor | ||
| 103 | */ | ||
| 104 | . = 0x20 | ||
| 105 | .llong hvReleaseData-KERNELBASE | ||
| 106 | #endif /* CONFIG_PPC_ISERIES */ | ||
| 107 | |||
| 127 | . = 0x60 | 108 | . = 0x60 |
| 128 | /* | 109 | /* |
| 129 | * The following code is used on pSeries to hold secondary processors | 110 | * The following code is used on pSeries to hold secondary processors |
| @@ -1602,9 +1583,6 @@ _GLOBAL(__start_initialization_multiplatform) | |||
| 1602 | /* Setup some critical 970 SPRs before switching MMU off */ | 1583 | /* Setup some critical 970 SPRs before switching MMU off */ |
| 1603 | bl .__970_cpu_preinit | 1584 | bl .__970_cpu_preinit |
| 1604 | 1585 | ||
| 1605 | /* cpu # */ | ||
| 1606 | li r24,0 | ||
| 1607 | |||
| 1608 | /* Switch off MMU if not already */ | 1586 | /* Switch off MMU if not already */ |
| 1609 | LOAD_REG_IMMEDIATE(r4, .__after_prom_start - KERNELBASE) | 1587 | LOAD_REG_IMMEDIATE(r4, .__after_prom_start - KERNELBASE) |
| 1610 | add r4,r4,r30 | 1588 | add r4,r4,r30 |
| @@ -1683,6 +1661,9 @@ _STATIC(__after_prom_start) | |||
| 1683 | /* i.e. where we are running */ | 1661 | /* i.e. where we are running */ |
| 1684 | /* the source addr */ | 1662 | /* the source addr */ |
| 1685 | 1663 | ||
| 1664 | cmpdi r4,0 /* In some cases the loader may */ | ||
| 1665 | beq .start_here_multiplatform /* have already put us at zero */ | ||
| 1666 | /* so we can skip the copy. */ | ||
| 1686 | LOAD_REG_IMMEDIATE(r5,copy_to_here) /* # bytes of memory to copy */ | 1667 | LOAD_REG_IMMEDIATE(r5,copy_to_here) /* # bytes of memory to copy */ |
| 1687 | sub r5,r5,r27 | 1668 | sub r5,r5,r27 |
| 1688 | 1669 | ||
| @@ -1962,14 +1943,6 @@ _STATIC(start_here_common) | |||
| 1962 | li r3,0 | 1943 | li r3,0 |
| 1963 | bl .do_cpu_ftr_fixups | 1944 | bl .do_cpu_ftr_fixups |
| 1964 | 1945 | ||
| 1965 | LOAD_REG_IMMEDIATE(r26, boot_cpuid) | ||
| 1966 | lwz r26,0(r26) | ||
| 1967 | |||
| 1968 | LOAD_REG_IMMEDIATE(r24, paca) /* Get base vaddr of paca array */ | ||
| 1969 | mulli r13,r26,PACA_SIZE /* Calculate vaddr of right paca */ | ||
| 1970 | add r13,r13,r24 /* for this processor. */ | ||
| 1971 | mtspr SPRN_SPRG3,r13 | ||
| 1972 | |||
| 1973 | /* ptr to current */ | 1946 | /* ptr to current */ |
| 1974 | LOAD_REG_IMMEDIATE(r4, init_task) | 1947 | LOAD_REG_IMMEDIATE(r4, init_task) |
| 1975 | std r4,PACACURRENT(r13) | 1948 | std r4,PACACURRENT(r13) |
| @@ -1995,17 +1968,6 @@ _STATIC(start_here_common) | |||
| 1995 | /* Not reached */ | 1968 | /* Not reached */ |
| 1996 | BUG_OPCODE | 1969 | BUG_OPCODE |
| 1997 | 1970 | ||
| 1998 | /* Put the paca pointer into r13 and SPRG3 */ | ||
| 1999 | _GLOBAL(setup_boot_paca) | ||
| 2000 | LOAD_REG_IMMEDIATE(r3, boot_cpuid) | ||
| 2001 | lwz r3,0(r3) | ||
| 2002 | LOAD_REG_IMMEDIATE(r4, paca) /* Get base vaddr of paca array */ | ||
| 2003 | mulli r3,r3,PACA_SIZE /* Calculate vaddr of right paca */ | ||
| 2004 | add r13,r3,r4 /* for this processor. */ | ||
| 2005 | mtspr SPRN_SPRG3,r13 | ||
| 2006 | |||
| 2007 | blr | ||
| 2008 | |||
| 2009 | /* | 1971 | /* |
| 2010 | * We put a few things here that have to be page-aligned. | 1972 | * We put a few things here that have to be page-aligned. |
| 2011 | * This stuff goes at the beginning of the bss, which is page-aligned. | 1973 | * This stuff goes at the beginning of the bss, which is page-aligned. |
diff --git a/arch/powerpc/kernel/iommu.c b/arch/powerpc/kernel/iommu.c index 7cb77c20fc5d..3d677ac99659 100644 --- a/arch/powerpc/kernel/iommu.c +++ b/arch/powerpc/kernel/iommu.c | |||
| @@ -38,6 +38,7 @@ | |||
| 38 | #include <asm/iommu.h> | 38 | #include <asm/iommu.h> |
| 39 | #include <asm/pci-bridge.h> | 39 | #include <asm/pci-bridge.h> |
| 40 | #include <asm/machdep.h> | 40 | #include <asm/machdep.h> |
| 41 | #include <asm/kdump.h> | ||
| 41 | 42 | ||
| 42 | #define DBG(...) | 43 | #define DBG(...) |
| 43 | 44 | ||
| @@ -440,8 +441,37 @@ struct iommu_table *iommu_init_table(struct iommu_table *tbl, int nid) | |||
| 440 | tbl->it_largehint = tbl->it_halfpoint; | 441 | tbl->it_largehint = tbl->it_halfpoint; |
| 441 | spin_lock_init(&tbl->it_lock); | 442 | spin_lock_init(&tbl->it_lock); |
| 442 | 443 | ||
| 444 | #ifdef CONFIG_CRASH_DUMP | ||
| 445 | if (ppc_md.tce_get) { | ||
| 446 | unsigned long index, tceval; | ||
| 447 | unsigned long tcecount = 0; | ||
| 448 | |||
| 449 | /* | ||
| 450 | * Reserve the existing mappings left by the first kernel. | ||
| 451 | */ | ||
| 452 | for (index = 0; index < tbl->it_size; index++) { | ||
| 453 | tceval = ppc_md.tce_get(tbl, index + tbl->it_offset); | ||
| 454 | /* | ||
| 455 | * Freed TCE entry contains 0x7fffffffffffffff on JS20 | ||
| 456 | */ | ||
| 457 | if (tceval && (tceval != 0x7fffffffffffffffUL)) { | ||
| 458 | __set_bit(index, tbl->it_map); | ||
| 459 | tcecount++; | ||
| 460 | } | ||
| 461 | } | ||
| 462 | if ((tbl->it_size - tcecount) < KDUMP_MIN_TCE_ENTRIES) { | ||
| 463 | printk(KERN_WARNING "TCE table is full; "); | ||
| 464 | printk(KERN_WARNING "freeing %d entries for the kdump boot\n", | ||
| 465 | KDUMP_MIN_TCE_ENTRIES); | ||
| 466 | for (index = tbl->it_size - KDUMP_MIN_TCE_ENTRIES; | ||
| 467 | index < tbl->it_size; index++) | ||
| 468 | __clear_bit(index, tbl->it_map); | ||
| 469 | } | ||
| 470 | } | ||
| 471 | #else | ||
| 443 | /* Clear the hardware table in case firmware left allocations in it */ | 472 | /* Clear the hardware table in case firmware left allocations in it */ |
| 444 | ppc_md.tce_free(tbl, tbl->it_offset, tbl->it_size); | 473 | ppc_md.tce_free(tbl, tbl->it_offset, tbl->it_size); |
| 474 | #endif | ||
| 445 | 475 | ||
| 446 | if (!welcomed) { | 476 | if (!welcomed) { |
| 447 | printk(KERN_INFO "IOMMU table initialized, virtual merging %s\n", | 477 | printk(KERN_INFO "IOMMU table initialized, virtual merging %s\n", |
diff --git a/arch/powerpc/kernel/legacy_serial.c b/arch/powerpc/kernel/legacy_serial.c index 6e67b5b49ba1..3a9b78d03542 100644 --- a/arch/powerpc/kernel/legacy_serial.c +++ b/arch/powerpc/kernel/legacy_serial.c | |||
| @@ -302,6 +302,17 @@ void __init find_legacy_serial_ports(void) | |||
| 302 | of_node_put(isa); | 302 | of_node_put(isa); |
| 303 | } | 303 | } |
| 304 | 304 | ||
| 305 | /* First fill our array with tsi-bridge ports */ | ||
| 306 | for (np = NULL; (np = of_find_compatible_node(np, "serial", "ns16550")) != NULL;) { | ||
| 307 | struct device_node *tsi = of_get_parent(np); | ||
| 308 | if (tsi && !strcmp(tsi->type, "tsi-bridge")) { | ||
| 309 | index = add_legacy_soc_port(np, np); | ||
| 310 | if (index >= 0 && np == stdout) | ||
| 311 | legacy_serial_console = index; | ||
| 312 | } | ||
| 313 | of_node_put(tsi); | ||
| 314 | } | ||
| 315 | |||
| 305 | #ifdef CONFIG_PCI | 316 | #ifdef CONFIG_PCI |
| 306 | /* Next, try to locate PCI ports */ | 317 | /* Next, try to locate PCI ports */ |
| 307 | for (np = NULL; (np = of_find_all_nodes(np));) { | 318 | for (np = NULL; (np = of_find_all_nodes(np));) { |
diff --git a/arch/powerpc/kernel/lparcfg.c b/arch/powerpc/kernel/lparcfg.c index c02deaab26c7..73edc3c16137 100644 --- a/arch/powerpc/kernel/lparcfg.c +++ b/arch/powerpc/kernel/lparcfg.c | |||
| @@ -45,11 +45,9 @@ | |||
| 45 | static struct proc_dir_entry *proc_ppc64_lparcfg; | 45 | static struct proc_dir_entry *proc_ppc64_lparcfg; |
| 46 | #define LPARCFG_BUFF_SIZE 4096 | 46 | #define LPARCFG_BUFF_SIZE 4096 |
| 47 | 47 | ||
| 48 | #ifdef CONFIG_PPC_ISERIES | ||
| 49 | |||
| 50 | /* | 48 | /* |
| 51 | * For iSeries legacy systems, the PPA purr function is available from the | 49 | * Track sum of all purrs across all processors. This is used to further |
| 52 | * emulated_time_base field in the paca. | 50 | * calculate usage values by different applications |
| 53 | */ | 51 | */ |
| 54 | static unsigned long get_purr(void) | 52 | static unsigned long get_purr(void) |
| 55 | { | 53 | { |
| @@ -57,48 +55,31 @@ static unsigned long get_purr(void) | |||
| 57 | int cpu; | 55 | int cpu; |
| 58 | 56 | ||
| 59 | for_each_possible_cpu(cpu) { | 57 | for_each_possible_cpu(cpu) { |
| 60 | sum_purr += lppaca[cpu].emulated_time_base; | 58 | if (firmware_has_feature(FW_FEATURE_ISERIES)) |
| 59 | sum_purr += lppaca[cpu].emulated_time_base; | ||
| 60 | else { | ||
| 61 | struct cpu_usage *cu; | ||
| 61 | 62 | ||
| 62 | #ifdef PURR_DEBUG | 63 | cu = &per_cpu(cpu_usage_array, cpu); |
| 63 | printk(KERN_INFO "get_purr for cpu (%d) has value (%ld) \n", | 64 | sum_purr += cu->current_tb; |
| 64 | cpu, lppaca[cpu].emulated_time_base); | 65 | } |
| 65 | #endif | ||
| 66 | } | 66 | } |
| 67 | return sum_purr; | 67 | return sum_purr; |
| 68 | } | 68 | } |
| 69 | 69 | ||
| 70 | #define lparcfg_write NULL | 70 | #ifdef CONFIG_PPC_ISERIES |
| 71 | 71 | ||
| 72 | /* | 72 | /* |
| 73 | * Methods used to fetch LPAR data when running on an iSeries platform. | 73 | * Methods used to fetch LPAR data when running on an iSeries platform. |
| 74 | */ | 74 | */ |
| 75 | static int lparcfg_data(struct seq_file *m, void *v) | 75 | static int iseries_lparcfg_data(struct seq_file *m, void *v) |
| 76 | { | 76 | { |
| 77 | unsigned long pool_id, lp_index; | 77 | unsigned long pool_id; |
| 78 | int shared, entitled_capacity, max_entitled_capacity; | 78 | int shared, entitled_capacity, max_entitled_capacity; |
| 79 | int processors, max_processors; | 79 | int processors, max_processors; |
| 80 | unsigned long purr = get_purr(); | 80 | unsigned long purr = get_purr(); |
| 81 | 81 | ||
| 82 | seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS); | ||
| 83 | |||
| 84 | shared = (int)(get_lppaca()->shared_proc); | 82 | shared = (int)(get_lppaca()->shared_proc); |
| 85 | seq_printf(m, "serial_number=%c%c%c%c%c%c%c\n", | ||
| 86 | e2a(xItExtVpdPanel.mfgID[2]), | ||
| 87 | e2a(xItExtVpdPanel.mfgID[3]), | ||
| 88 | e2a(xItExtVpdPanel.systemSerial[1]), | ||
| 89 | e2a(xItExtVpdPanel.systemSerial[2]), | ||
| 90 | e2a(xItExtVpdPanel.systemSerial[3]), | ||
| 91 | e2a(xItExtVpdPanel.systemSerial[4]), | ||
| 92 | e2a(xItExtVpdPanel.systemSerial[5])); | ||
| 93 | |||
| 94 | seq_printf(m, "system_type=%c%c%c%c\n", | ||
| 95 | e2a(xItExtVpdPanel.machineType[0]), | ||
| 96 | e2a(xItExtVpdPanel.machineType[1]), | ||
| 97 | e2a(xItExtVpdPanel.machineType[2]), | ||
| 98 | e2a(xItExtVpdPanel.machineType[3])); | ||
| 99 | |||
| 100 | lp_index = HvLpConfig_getLpIndex(); | ||
| 101 | seq_printf(m, "partition_id=%d\n", (int)lp_index); | ||
| 102 | 83 | ||
| 103 | seq_printf(m, "system_active_processors=%d\n", | 84 | seq_printf(m, "system_active_processors=%d\n", |
| 104 | (int)HvLpConfig_getSystemPhysicalProcessors()); | 85 | (int)HvLpConfig_getSystemPhysicalProcessors()); |
| @@ -137,6 +118,14 @@ static int lparcfg_data(struct seq_file *m, void *v) | |||
| 137 | 118 | ||
| 138 | return 0; | 119 | return 0; |
| 139 | } | 120 | } |
| 121 | |||
| 122 | #else /* CONFIG_PPC_ISERIES */ | ||
| 123 | |||
| 124 | static int iseries_lparcfg_data(struct seq_file *m, void *v) | ||
| 125 | { | ||
| 126 | return 0; | ||
| 127 | } | ||
| 128 | |||
| 140 | #endif /* CONFIG_PPC_ISERIES */ | 129 | #endif /* CONFIG_PPC_ISERIES */ |
| 141 | 130 | ||
| 142 | #ifdef CONFIG_PPC_PSERIES | 131 | #ifdef CONFIG_PPC_PSERIES |
| @@ -213,22 +202,6 @@ static void h_pic(unsigned long *pool_idle_time, unsigned long *num_procs) | |||
| 213 | log_plpar_hcall_return(rc, "H_PIC"); | 202 | log_plpar_hcall_return(rc, "H_PIC"); |
| 214 | } | 203 | } |
| 215 | 204 | ||
| 216 | /* Track sum of all purrs across all processors. This is used to further */ | ||
| 217 | /* calculate usage values by different applications */ | ||
| 218 | |||
| 219 | static unsigned long get_purr(void) | ||
| 220 | { | ||
| 221 | unsigned long sum_purr = 0; | ||
| 222 | int cpu; | ||
| 223 | struct cpu_usage *cu; | ||
| 224 | |||
| 225 | for_each_possible_cpu(cpu) { | ||
| 226 | cu = &per_cpu(cpu_usage_array, cpu); | ||
| 227 | sum_purr += cu->current_tb; | ||
| 228 | } | ||
| 229 | return sum_purr; | ||
| 230 | } | ||
| 231 | |||
| 232 | #define SPLPAR_CHARACTERISTICS_TOKEN 20 | 205 | #define SPLPAR_CHARACTERISTICS_TOKEN 20 |
| 233 | #define SPLPAR_MAXLENGTH 1026*(sizeof(char)) | 206 | #define SPLPAR_MAXLENGTH 1026*(sizeof(char)) |
| 234 | 207 | ||
| @@ -333,35 +306,13 @@ static int lparcfg_count_active_processors(void) | |||
| 333 | return count; | 306 | return count; |
| 334 | } | 307 | } |
| 335 | 308 | ||
| 336 | static int lparcfg_data(struct seq_file *m, void *v) | 309 | static int pseries_lparcfg_data(struct seq_file *m, void *v) |
| 337 | { | 310 | { |
| 338 | int partition_potential_processors; | 311 | int partition_potential_processors; |
| 339 | int partition_active_processors; | 312 | int partition_active_processors; |
| 340 | struct device_node *rootdn; | ||
| 341 | const char *model = ""; | ||
| 342 | const char *system_id = ""; | ||
| 343 | unsigned int *lp_index_ptr, lp_index = 0; | ||
| 344 | struct device_node *rtas_node; | 313 | struct device_node *rtas_node; |
| 345 | int *lrdrp = NULL; | 314 | int *lrdrp = NULL; |
| 346 | 315 | ||
| 347 | rootdn = find_path_device("/"); | ||
| 348 | if (rootdn) { | ||
| 349 | model = get_property(rootdn, "model", NULL); | ||
| 350 | system_id = get_property(rootdn, "system-id", NULL); | ||
| 351 | lp_index_ptr = (unsigned int *) | ||
| 352 | get_property(rootdn, "ibm,partition-no", NULL); | ||
| 353 | if (lp_index_ptr) | ||
| 354 | lp_index = *lp_index_ptr; | ||
| 355 | } | ||
| 356 | |||
| 357 | seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS); | ||
| 358 | |||
| 359 | seq_printf(m, "serial_number=%s\n", system_id); | ||
| 360 | |||
| 361 | seq_printf(m, "system_type=%s\n", model); | ||
| 362 | |||
| 363 | seq_printf(m, "partition_id=%d\n", (int)lp_index); | ||
| 364 | |||
| 365 | rtas_node = find_path_device("/rtas"); | 316 | rtas_node = find_path_device("/rtas"); |
| 366 | if (rtas_node) | 317 | if (rtas_node) |
| 367 | lrdrp = (int *)get_property(rtas_node, "ibm,lrdr-capacity", | 318 | lrdrp = (int *)get_property(rtas_node, "ibm,lrdr-capacity", |
| @@ -549,8 +500,61 @@ out: | |||
| 549 | return retval; | 500 | return retval; |
| 550 | } | 501 | } |
| 551 | 502 | ||
| 503 | #else /* CONFIG_PPC_PSERIES */ | ||
| 504 | |||
| 505 | static int pseries_lparcfg_data(struct seq_file *m, void *v) | ||
| 506 | { | ||
| 507 | return 0; | ||
| 508 | } | ||
| 509 | |||
| 510 | static ssize_t lparcfg_write(struct file *file, const char __user * buf, | ||
| 511 | size_t count, loff_t * off) | ||
| 512 | { | ||
| 513 | return count; | ||
| 514 | } | ||
| 515 | |||
| 552 | #endif /* CONFIG_PPC_PSERIES */ | 516 | #endif /* CONFIG_PPC_PSERIES */ |
| 553 | 517 | ||
| 518 | static int lparcfg_data(struct seq_file *m, void *v) | ||
| 519 | { | ||
| 520 | struct device_node *rootdn; | ||
| 521 | const char *model = ""; | ||
| 522 | const char *system_id = ""; | ||
| 523 | const char *tmp; | ||
| 524 | unsigned int *lp_index_ptr, lp_index = 0; | ||
| 525 | |||
| 526 | seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS); | ||
| 527 | |||
| 528 | rootdn = find_path_device("/"); | ||
| 529 | if (rootdn) { | ||
| 530 | tmp = get_property(rootdn, "model", NULL); | ||
| 531 | if (tmp) { | ||
| 532 | model = tmp; | ||
| 533 | /* Skip "IBM," - see platforms/iseries/dt.c */ | ||
| 534 | if (firmware_has_feature(FW_FEATURE_ISERIES)) | ||
| 535 | model += 4; | ||
| 536 | } | ||
| 537 | tmp = get_property(rootdn, "system-id", NULL); | ||
| 538 | if (tmp) { | ||
| 539 | system_id = tmp; | ||
| 540 | /* Skip "IBM," - see platforms/iseries/dt.c */ | ||
| 541 | if (firmware_has_feature(FW_FEATURE_ISERIES)) | ||
| 542 | system_id += 4; | ||
| 543 | } | ||
| 544 | lp_index_ptr = (unsigned int *) | ||
| 545 | get_property(rootdn, "ibm,partition-no", NULL); | ||
| 546 | if (lp_index_ptr) | ||
| 547 | lp_index = *lp_index_ptr; | ||
| 548 | } | ||
| 549 | seq_printf(m, "serial_number=%s\n", system_id); | ||
| 550 | seq_printf(m, "system_type=%s\n", model); | ||
| 551 | seq_printf(m, "partition_id=%d\n", (int)lp_index); | ||
| 552 | |||
| 553 | if (firmware_has_feature(FW_FEATURE_ISERIES)) | ||
| 554 | return iseries_lparcfg_data(m, v); | ||
| 555 | return pseries_lparcfg_data(m, v); | ||
| 556 | } | ||
| 557 | |||
| 554 | static int lparcfg_open(struct inode *inode, struct file *file) | 558 | static int lparcfg_open(struct inode *inode, struct file *file) |
| 555 | { | 559 | { |
| 556 | return single_open(file, lparcfg_data, NULL); | 560 | return single_open(file, lparcfg_data, NULL); |
| @@ -569,7 +573,8 @@ int __init lparcfg_init(void) | |||
| 569 | mode_t mode = S_IRUSR | S_IRGRP | S_IROTH; | 573 | mode_t mode = S_IRUSR | S_IRGRP | S_IROTH; |
| 570 | 574 | ||
| 571 | /* Allow writing if we have FW_FEATURE_SPLPAR */ | 575 | /* Allow writing if we have FW_FEATURE_SPLPAR */ |
| 572 | if (firmware_has_feature(FW_FEATURE_SPLPAR)) { | 576 | if (firmware_has_feature(FW_FEATURE_SPLPAR) && |
| 577 | !firmware_has_feature(FW_FEATURE_ISERIES)) { | ||
| 573 | lparcfg_fops.write = lparcfg_write; | 578 | lparcfg_fops.write = lparcfg_write; |
| 574 | mode |= S_IWUSR; | 579 | mode |= S_IWUSR; |
| 575 | } | 580 | } |
diff --git a/arch/powerpc/kernel/machine_kexec_64.c b/arch/powerpc/kernel/machine_kexec_64.c index a8fa04ef27cd..b438d45a068c 100644 --- a/arch/powerpc/kernel/machine_kexec_64.c +++ b/arch/powerpc/kernel/machine_kexec_64.c | |||
| @@ -378,11 +378,13 @@ static void __init export_crashk_values(void) | |||
| 378 | of_node_put(node); | 378 | of_node_put(node); |
| 379 | } | 379 | } |
| 380 | 380 | ||
| 381 | void __init kexec_setup(void) | 381 | static int __init kexec_setup(void) |
| 382 | { | 382 | { |
| 383 | export_htab_values(); | 383 | export_htab_values(); |
| 384 | export_crashk_values(); | 384 | export_crashk_values(); |
| 385 | return 0; | ||
| 385 | } | 386 | } |
| 387 | __initcall(kexec_setup); | ||
| 386 | 388 | ||
| 387 | static int __init early_parse_crashk(char *p) | 389 | static int __init early_parse_crashk(char *p) |
| 388 | { | 390 | { |
diff --git a/arch/powerpc/kernel/misc.S b/arch/powerpc/kernel/misc.S new file mode 100644 index 000000000000..fc23040d5a26 --- /dev/null +++ b/arch/powerpc/kernel/misc.S | |||
| @@ -0,0 +1,203 @@ | |||
| 1 | /* | ||
| 2 | * This file contains miscellaneous low-level functions. | ||
| 3 | * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) | ||
| 4 | * | ||
| 5 | * Largely rewritten by Cort Dougan (cort@cs.nmt.edu) | ||
| 6 | * and Paul Mackerras. | ||
| 7 | * | ||
| 8 | * Adapted for iSeries by Mike Corrigan (mikejc@us.ibm.com) | ||
| 9 | * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com) | ||
| 10 | * | ||
| 11 | * This program is free software; you can redistribute it and/or | ||
| 12 | * modify it under the terms of the GNU General Public License | ||
| 13 | * as published by the Free Software Foundation; either version | ||
| 14 | * 2 of the License, or (at your option) any later version. | ||
| 15 | */ | ||
| 16 | #include <asm/ppc_asm.h> | ||
| 17 | |||
| 18 | .text | ||
| 19 | |||
| 20 | #ifdef CONFIG_PPC64 | ||
| 21 | #define IN_SYNC twi 0,r5,0; isync | ||
| 22 | #define EIEIO_32 | ||
| 23 | #define SYNC_64 sync | ||
| 24 | #else /* CONFIG_PPC32 */ | ||
| 25 | #define IN_SYNC | ||
| 26 | #define EIEIO_32 eieio | ||
| 27 | #define SYNC_64 | ||
| 28 | #endif | ||
| 29 | /* | ||
| 30 | * Returns (address we are running at) - (address we were linked at) | ||
| 31 | * for use before the text and data are mapped to KERNELBASE. | ||
| 32 | */ | ||
| 33 | |||
| 34 | _GLOBAL(reloc_offset) | ||
| 35 | mflr r0 | ||
| 36 | bl 1f | ||
| 37 | 1: mflr r3 | ||
| 38 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 39 | subf r3,r4,r3 | ||
| 40 | mtlr r0 | ||
| 41 | blr | ||
| 42 | |||
| 43 | /* | ||
| 44 | * add_reloc_offset(x) returns x + reloc_offset(). | ||
| 45 | */ | ||
| 46 | _GLOBAL(add_reloc_offset) | ||
| 47 | mflr r0 | ||
| 48 | bl 1f | ||
| 49 | 1: mflr r5 | ||
| 50 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 51 | subf r5,r4,r5 | ||
| 52 | add r3,r3,r5 | ||
| 53 | mtlr r0 | ||
| 54 | blr | ||
| 55 | |||
| 56 | /* | ||
| 57 | * I/O string operations | ||
| 58 | * | ||
| 59 | * insb(port, buf, len) | ||
| 60 | * outsb(port, buf, len) | ||
| 61 | * insw(port, buf, len) | ||
| 62 | * outsw(port, buf, len) | ||
| 63 | * insl(port, buf, len) | ||
| 64 | * outsl(port, buf, len) | ||
| 65 | * insw_ns(port, buf, len) | ||
| 66 | * outsw_ns(port, buf, len) | ||
| 67 | * insl_ns(port, buf, len) | ||
| 68 | * outsl_ns(port, buf, len) | ||
| 69 | * | ||
| 70 | * The *_ns versions don't do byte-swapping. | ||
| 71 | */ | ||
| 72 | _GLOBAL(_insb) | ||
| 73 | cmpwi 0,r5,0 | ||
| 74 | mtctr r5 | ||
| 75 | subi r4,r4,1 | ||
| 76 | blelr- | ||
| 77 | 00: lbz r5,0(r3) | ||
| 78 | eieio | ||
| 79 | stbu r5,1(r4) | ||
| 80 | bdnz 00b | ||
| 81 | IN_SYNC | ||
| 82 | blr | ||
| 83 | |||
| 84 | _GLOBAL(_outsb) | ||
| 85 | cmpwi 0,r5,0 | ||
| 86 | mtctr r5 | ||
| 87 | subi r4,r4,1 | ||
| 88 | blelr- | ||
| 89 | 00: lbzu r5,1(r4) | ||
| 90 | stb r5,0(r3) | ||
| 91 | EIEIO_32 | ||
| 92 | bdnz 00b | ||
| 93 | SYNC_64 | ||
| 94 | blr | ||
| 95 | |||
| 96 | _GLOBAL(_insw) | ||
| 97 | cmpwi 0,r5,0 | ||
| 98 | mtctr r5 | ||
| 99 | subi r4,r4,2 | ||
| 100 | blelr- | ||
| 101 | 00: lhbrx r5,0,r3 | ||
| 102 | eieio | ||
| 103 | sthu r5,2(r4) | ||
| 104 | bdnz 00b | ||
| 105 | IN_SYNC | ||
| 106 | blr | ||
| 107 | |||
| 108 | _GLOBAL(_outsw) | ||
| 109 | cmpwi 0,r5,0 | ||
| 110 | mtctr r5 | ||
| 111 | subi r4,r4,2 | ||
| 112 | blelr- | ||
| 113 | 00: lhzu r5,2(r4) | ||
| 114 | EIEIO_32 | ||
| 115 | sthbrx r5,0,r3 | ||
| 116 | bdnz 00b | ||
| 117 | SYNC_64 | ||
| 118 | blr | ||
| 119 | |||
| 120 | _GLOBAL(_insl) | ||
| 121 | cmpwi 0,r5,0 | ||
| 122 | mtctr r5 | ||
| 123 | subi r4,r4,4 | ||
| 124 | blelr- | ||
| 125 | 00: lwbrx r5,0,r3 | ||
| 126 | eieio | ||
| 127 | stwu r5,4(r4) | ||
| 128 | bdnz 00b | ||
| 129 | IN_SYNC | ||
| 130 | blr | ||
| 131 | |||
| 132 | _GLOBAL(_outsl) | ||
| 133 | cmpwi 0,r5,0 | ||
| 134 | mtctr r5 | ||
| 135 | subi r4,r4,4 | ||
| 136 | blelr- | ||
| 137 | 00: lwzu r5,4(r4) | ||
| 138 | stwbrx r5,0,r3 | ||
| 139 | EIEIO_32 | ||
| 140 | bdnz 00b | ||
| 141 | SYNC_64 | ||
| 142 | blr | ||
| 143 | |||
| 144 | #ifdef CONFIG_PPC32 | ||
| 145 | _GLOBAL(__ide_mm_insw) | ||
| 146 | #endif | ||
| 147 | _GLOBAL(_insw_ns) | ||
| 148 | cmpwi 0,r5,0 | ||
| 149 | mtctr r5 | ||
| 150 | subi r4,r4,2 | ||
| 151 | blelr- | ||
| 152 | 00: lhz r5,0(r3) | ||
| 153 | eieio | ||
| 154 | sthu r5,2(r4) | ||
| 155 | bdnz 00b | ||
| 156 | IN_SYNC | ||
| 157 | blr | ||
| 158 | |||
| 159 | #ifdef CONFIG_PPC32 | ||
| 160 | _GLOBAL(__ide_mm_outsw) | ||
| 161 | #endif | ||
| 162 | _GLOBAL(_outsw_ns) | ||
| 163 | cmpwi 0,r5,0 | ||
| 164 | mtctr r5 | ||
| 165 | subi r4,r4,2 | ||
| 166 | blelr- | ||
| 167 | 00: lhzu r5,2(r4) | ||
| 168 | sth r5,0(r3) | ||
| 169 | EIEIO_32 | ||
| 170 | bdnz 00b | ||
| 171 | SYNC_64 | ||
| 172 | blr | ||
| 173 | |||
| 174 | #ifdef CONFIG_PPC32 | ||
| 175 | _GLOBAL(__ide_mm_insl) | ||
| 176 | #endif | ||
| 177 | _GLOBAL(_insl_ns) | ||
| 178 | cmpwi 0,r5,0 | ||
| 179 | mtctr r5 | ||
| 180 | subi r4,r4,4 | ||
| 181 | blelr- | ||
| 182 | 00: lwz r5,0(r3) | ||
| 183 | eieio | ||
| 184 | stwu r5,4(r4) | ||
| 185 | bdnz 00b | ||
| 186 | IN_SYNC | ||
| 187 | blr | ||
| 188 | |||
| 189 | #ifdef CONFIG_PPC32 | ||
| 190 | _GLOBAL(__ide_mm_outsl) | ||
| 191 | #endif | ||
| 192 | _GLOBAL(_outsl_ns) | ||
| 193 | cmpwi 0,r5,0 | ||
| 194 | mtctr r5 | ||
| 195 | subi r4,r4,4 | ||
| 196 | blelr- | ||
| 197 | 00: lwzu r5,4(r4) | ||
| 198 | stw r5,0(r3) | ||
| 199 | EIEIO_32 | ||
| 200 | bdnz 00b | ||
| 201 | SYNC_64 | ||
| 202 | blr | ||
| 203 | |||
diff --git a/arch/powerpc/kernel/misc_32.S b/arch/powerpc/kernel/misc_32.S index 01d3916c4cb1..c74774e2175d 100644 --- a/arch/powerpc/kernel/misc_32.S +++ b/arch/powerpc/kernel/misc_32.S | |||
| @@ -61,32 +61,6 @@ _GLOBAL(mulhdu) | |||
| 61 | blr | 61 | blr |
| 62 | 62 | ||
| 63 | /* | 63 | /* |
| 64 | * Returns (address we're running at) - (address we were linked at) | ||
| 65 | * for use before the text and data are mapped to KERNELBASE. | ||
| 66 | */ | ||
| 67 | _GLOBAL(reloc_offset) | ||
| 68 | mflr r0 | ||
| 69 | bl 1f | ||
| 70 | 1: mflr r3 | ||
| 71 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 72 | subf r3,r4,r3 | ||
| 73 | mtlr r0 | ||
| 74 | blr | ||
| 75 | |||
| 76 | /* | ||
| 77 | * add_reloc_offset(x) returns x + reloc_offset(). | ||
| 78 | */ | ||
| 79 | _GLOBAL(add_reloc_offset) | ||
| 80 | mflr r0 | ||
| 81 | bl 1f | ||
| 82 | 1: mflr r5 | ||
| 83 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 84 | subf r5,r4,r5 | ||
| 85 | add r3,r3,r5 | ||
| 86 | mtlr r0 | ||
| 87 | blr | ||
| 88 | |||
| 89 | /* | ||
| 90 | * sub_reloc_offset(x) returns x - reloc_offset(). | 64 | * sub_reloc_offset(x) returns x - reloc_offset(). |
| 91 | */ | 65 | */ |
| 92 | _GLOBAL(sub_reloc_offset) | 66 | _GLOBAL(sub_reloc_offset) |
| @@ -781,136 +755,6 @@ _GLOBAL(atomic_set_mask) | |||
| 781 | blr | 755 | blr |
| 782 | 756 | ||
| 783 | /* | 757 | /* |
| 784 | * I/O string operations | ||
| 785 | * | ||
| 786 | * insb(port, buf, len) | ||
| 787 | * outsb(port, buf, len) | ||
| 788 | * insw(port, buf, len) | ||
| 789 | * outsw(port, buf, len) | ||
| 790 | * insl(port, buf, len) | ||
| 791 | * outsl(port, buf, len) | ||
| 792 | * insw_ns(port, buf, len) | ||
| 793 | * outsw_ns(port, buf, len) | ||
| 794 | * insl_ns(port, buf, len) | ||
| 795 | * outsl_ns(port, buf, len) | ||
| 796 | * | ||
| 797 | * The *_ns versions don't do byte-swapping. | ||
| 798 | */ | ||
| 799 | _GLOBAL(_insb) | ||
| 800 | cmpwi 0,r5,0 | ||
| 801 | mtctr r5 | ||
| 802 | subi r4,r4,1 | ||
| 803 | blelr- | ||
| 804 | 00: lbz r5,0(r3) | ||
| 805 | eieio | ||
| 806 | stbu r5,1(r4) | ||
| 807 | bdnz 00b | ||
| 808 | blr | ||
| 809 | |||
| 810 | _GLOBAL(_outsb) | ||
| 811 | cmpwi 0,r5,0 | ||
| 812 | mtctr r5 | ||
| 813 | subi r4,r4,1 | ||
| 814 | blelr- | ||
| 815 | 00: lbzu r5,1(r4) | ||
| 816 | stb r5,0(r3) | ||
| 817 | eieio | ||
| 818 | bdnz 00b | ||
| 819 | blr | ||
| 820 | |||
| 821 | _GLOBAL(_insw) | ||
| 822 | cmpwi 0,r5,0 | ||
| 823 | mtctr r5 | ||
| 824 | subi r4,r4,2 | ||
| 825 | blelr- | ||
| 826 | 00: lhbrx r5,0,r3 | ||
| 827 | eieio | ||
| 828 | sthu r5,2(r4) | ||
| 829 | bdnz 00b | ||
| 830 | blr | ||
| 831 | |||
| 832 | _GLOBAL(_outsw) | ||
| 833 | cmpwi 0,r5,0 | ||
| 834 | mtctr r5 | ||
| 835 | subi r4,r4,2 | ||
| 836 | blelr- | ||
| 837 | 00: lhzu r5,2(r4) | ||
| 838 | eieio | ||
| 839 | sthbrx r5,0,r3 | ||
| 840 | bdnz 00b | ||
| 841 | blr | ||
| 842 | |||
| 843 | _GLOBAL(_insl) | ||
| 844 | cmpwi 0,r5,0 | ||
| 845 | mtctr r5 | ||
| 846 | subi r4,r4,4 | ||
| 847 | blelr- | ||
| 848 | 00: lwbrx r5,0,r3 | ||
| 849 | eieio | ||
| 850 | stwu r5,4(r4) | ||
| 851 | bdnz 00b | ||
| 852 | blr | ||
| 853 | |||
| 854 | _GLOBAL(_outsl) | ||
| 855 | cmpwi 0,r5,0 | ||
| 856 | mtctr r5 | ||
| 857 | subi r4,r4,4 | ||
| 858 | blelr- | ||
| 859 | 00: lwzu r5,4(r4) | ||
| 860 | stwbrx r5,0,r3 | ||
| 861 | eieio | ||
| 862 | bdnz 00b | ||
| 863 | blr | ||
| 864 | |||
| 865 | _GLOBAL(__ide_mm_insw) | ||
| 866 | _GLOBAL(_insw_ns) | ||
| 867 | cmpwi 0,r5,0 | ||
| 868 | mtctr r5 | ||
| 869 | subi r4,r4,2 | ||
| 870 | blelr- | ||
| 871 | 00: lhz r5,0(r3) | ||
| 872 | eieio | ||
| 873 | sthu r5,2(r4) | ||
| 874 | bdnz 00b | ||
| 875 | blr | ||
| 876 | |||
| 877 | _GLOBAL(__ide_mm_outsw) | ||
| 878 | _GLOBAL(_outsw_ns) | ||
| 879 | cmpwi 0,r5,0 | ||
| 880 | mtctr r5 | ||
| 881 | subi r4,r4,2 | ||
| 882 | blelr- | ||
| 883 | 00: lhzu r5,2(r4) | ||
| 884 | sth r5,0(r3) | ||
| 885 | eieio | ||
| 886 | bdnz 00b | ||
| 887 | blr | ||
| 888 | |||
| 889 | _GLOBAL(__ide_mm_insl) | ||
| 890 | _GLOBAL(_insl_ns) | ||
| 891 | cmpwi 0,r5,0 | ||
| 892 | mtctr r5 | ||
| 893 | subi r4,r4,4 | ||
| 894 | blelr- | ||
| 895 | 00: lwz r5,0(r3) | ||
| 896 | eieio | ||
| 897 | stwu r5,4(r4) | ||
| 898 | bdnz 00b | ||
| 899 | blr | ||
| 900 | |||
| 901 | _GLOBAL(__ide_mm_outsl) | ||
| 902 | _GLOBAL(_outsl_ns) | ||
| 903 | cmpwi 0,r5,0 | ||
| 904 | mtctr r5 | ||
| 905 | subi r4,r4,4 | ||
| 906 | blelr- | ||
| 907 | 00: lwzu r5,4(r4) | ||
| 908 | stw r5,0(r3) | ||
| 909 | eieio | ||
| 910 | bdnz 00b | ||
| 911 | blr | ||
| 912 | |||
| 913 | /* | ||
| 914 | * Extended precision shifts. | 758 | * Extended precision shifts. |
| 915 | * | 759 | * |
| 916 | * Updated to be valid for shift counts from 0 to 63 inclusive. | 760 | * Updated to be valid for shift counts from 0 to 63 inclusive. |
diff --git a/arch/powerpc/kernel/misc_64.S b/arch/powerpc/kernel/misc_64.S index e8883d42c43c..580891cb8ccb 100644 --- a/arch/powerpc/kernel/misc_64.S +++ b/arch/powerpc/kernel/misc_64.S | |||
| @@ -1,14 +1,12 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * arch/powerpc/kernel/misc64.S | ||
| 3 | * | ||
| 4 | * This file contains miscellaneous low-level functions. | 2 | * This file contains miscellaneous low-level functions. |
| 5 | * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) | 3 | * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) |
| 6 | * | 4 | * |
| 7 | * Largely rewritten by Cort Dougan (cort@cs.nmt.edu) | 5 | * Largely rewritten by Cort Dougan (cort@cs.nmt.edu) |
| 8 | * and Paul Mackerras. | 6 | * and Paul Mackerras. |
| 9 | * Adapted for iSeries by Mike Corrigan (mikejc@us.ibm.com) | 7 | * Adapted for iSeries by Mike Corrigan (mikejc@us.ibm.com) |
| 10 | * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com) | 8 | * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com) |
| 11 | * | 9 | * |
| 12 | * This program is free software; you can redistribute it and/or | 10 | * This program is free software; you can redistribute it and/or |
| 13 | * modify it under the terms of the GNU General Public License | 11 | * modify it under the terms of the GNU General Public License |
| 14 | * as published by the Free Software Foundation; either version | 12 | * as published by the Free Software Foundation; either version |
| @@ -30,41 +28,10 @@ | |||
| 30 | 28 | ||
| 31 | .text | 29 | .text |
| 32 | 30 | ||
| 33 | /* | ||
| 34 | * Returns (address we are running at) - (address we were linked at) | ||
| 35 | * for use before the text and data are mapped to KERNELBASE. | ||
| 36 | */ | ||
| 37 | |||
| 38 | _GLOBAL(reloc_offset) | ||
| 39 | mflr r0 | ||
| 40 | bl 1f | ||
| 41 | 1: mflr r3 | ||
| 42 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 43 | subf r3,r4,r3 | ||
| 44 | mtlr r0 | ||
| 45 | blr | ||
| 46 | |||
| 47 | /* | ||
| 48 | * add_reloc_offset(x) returns x + reloc_offset(). | ||
| 49 | */ | ||
| 50 | _GLOBAL(add_reloc_offset) | ||
| 51 | mflr r0 | ||
| 52 | bl 1f | ||
| 53 | 1: mflr r5 | ||
| 54 | LOAD_REG_IMMEDIATE(r4,1b) | ||
| 55 | subf r5,r4,r5 | ||
| 56 | add r3,r3,r5 | ||
| 57 | mtlr r0 | ||
| 58 | blr | ||
| 59 | |||
| 60 | _GLOBAL(get_msr) | 31 | _GLOBAL(get_msr) |
| 61 | mfmsr r3 | 32 | mfmsr r3 |
| 62 | blr | 33 | blr |
| 63 | 34 | ||
| 64 | _GLOBAL(get_dar) | ||
| 65 | mfdar r3 | ||
| 66 | blr | ||
| 67 | |||
| 68 | _GLOBAL(get_srr0) | 35 | _GLOBAL(get_srr0) |
| 69 | mfsrr0 r3 | 36 | mfsrr0 r3 |
| 70 | blr | 37 | blr |
| @@ -72,10 +39,6 @@ _GLOBAL(get_srr0) | |||
| 72 | _GLOBAL(get_srr1) | 39 | _GLOBAL(get_srr1) |
| 73 | mfsrr1 r3 | 40 | mfsrr1 r3 |
| 74 | blr | 41 | blr |
| 75 | |||
| 76 | _GLOBAL(get_sp) | ||
| 77 | mr r3,r1 | ||
| 78 | blr | ||
| 79 | 42 | ||
| 80 | #ifdef CONFIG_IRQSTACKS | 43 | #ifdef CONFIG_IRQSTACKS |
| 81 | _GLOBAL(call_do_softirq) | 44 | _GLOBAL(call_do_softirq) |
| @@ -101,48 +64,6 @@ _GLOBAL(call___do_IRQ) | |||
| 101 | blr | 64 | blr |
| 102 | #endif /* CONFIG_IRQSTACKS */ | 65 | #endif /* CONFIG_IRQSTACKS */ |
| 103 | 66 | ||
| 104 | /* | ||
| 105 | * To be called by C code which needs to do some operations with MMU | ||
| 106 | * disabled. Note that interrupts have to be disabled by the caller | ||
| 107 | * prior to calling us. The code called _MUST_ be in the RMO of course | ||
| 108 | * and part of the linear mapping as we don't attempt to translate the | ||
| 109 | * stack pointer at all. The function is called with the stack switched | ||
| 110 | * to this CPU emergency stack | ||
| 111 | * | ||
| 112 | * prototype is void *call_with_mmu_off(void *func, void *data); | ||
| 113 | * | ||
| 114 | * the called function is expected to be of the form | ||
| 115 | * | ||
| 116 | * void *called(void *data); | ||
| 117 | */ | ||
| 118 | _GLOBAL(call_with_mmu_off) | ||
| 119 | mflr r0 /* get link, save it on stackframe */ | ||
| 120 | std r0,16(r1) | ||
| 121 | mr r1,r5 /* save old stack ptr */ | ||
| 122 | ld r1,PACAEMERGSP(r13) /* get emerg. stack */ | ||
| 123 | subi r1,r1,STACK_FRAME_OVERHEAD | ||
| 124 | std r0,16(r1) /* save link on emerg. stack */ | ||
| 125 | std r5,0(r1) /* save old stack ptr in backchain */ | ||
| 126 | ld r3,0(r3) /* get to real function ptr (assume same TOC) */ | ||
| 127 | bl 2f /* we need LR to return, continue at label 2 */ | ||
| 128 | |||
| 129 | ld r0,16(r1) /* we return here from the call, get LR and */ | ||
| 130 | ld r1,0(r1) /* .. old stack ptr */ | ||
| 131 | mtspr SPRN_SRR0,r0 /* and get back to virtual mode with these */ | ||
| 132 | mfmsr r4 | ||
| 133 | ori r4,r4,MSR_IR|MSR_DR | ||
| 134 | mtspr SPRN_SRR1,r4 | ||
| 135 | rfid | ||
| 136 | |||
| 137 | 2: mtspr SPRN_SRR0,r3 /* coming from above, enter real mode */ | ||
| 138 | mr r3,r4 /* get parameter */ | ||
| 139 | mfmsr r0 | ||
| 140 | ori r0,r0,MSR_IR|MSR_DR | ||
| 141 | xori r0,r0,MSR_IR|MSR_DR | ||
| 142 | mtspr SPRN_SRR1,r0 | ||
| 143 | rfid | ||
| 144 | |||
| 145 | |||
| 146 | .section ".toc","aw" | 67 | .section ".toc","aw" |
| 147 | PPC64_CACHES: | 68 | PPC64_CACHES: |
| 148 | .tc ppc64_caches[TC],ppc64_caches | 69 | .tc ppc64_caches[TC],ppc64_caches |
| @@ -323,144 +244,6 @@ _GLOBAL(__flush_dcache_icache) | |||
| 323 | bdnz 1b | 244 | bdnz 1b |
| 324 | isync | 245 | isync |
| 325 | blr | 246 | blr |
| 326 | |||
| 327 | /* | ||
| 328 | * I/O string operations | ||
| 329 | * | ||
| 330 | * insb(port, buf, len) | ||
| 331 | * outsb(port, buf, len) | ||
| 332 | * insw(port, buf, len) | ||
| 333 | * outsw(port, buf, len) | ||
| 334 | * insl(port, buf, len) | ||
| 335 | * outsl(port, buf, len) | ||
| 336 | * insw_ns(port, buf, len) | ||
| 337 | * outsw_ns(port, buf, len) | ||
| 338 | * insl_ns(port, buf, len) | ||
| 339 | * outsl_ns(port, buf, len) | ||
| 340 | * | ||
| 341 | * The *_ns versions don't do byte-swapping. | ||
| 342 | */ | ||
| 343 | _GLOBAL(_insb) | ||
| 344 | cmpwi 0,r5,0 | ||
| 345 | mtctr r5 | ||
| 346 | subi r4,r4,1 | ||
| 347 | blelr- | ||
| 348 | 00: lbz r5,0(r3) | ||
| 349 | eieio | ||
| 350 | stbu r5,1(r4) | ||
| 351 | bdnz 00b | ||
| 352 | twi 0,r5,0 | ||
| 353 | isync | ||
| 354 | blr | ||
| 355 | |||
| 356 | _GLOBAL(_outsb) | ||
| 357 | cmpwi 0,r5,0 | ||
| 358 | mtctr r5 | ||
| 359 | subi r4,r4,1 | ||
| 360 | blelr- | ||
| 361 | 00: lbzu r5,1(r4) | ||
| 362 | stb r5,0(r3) | ||
| 363 | bdnz 00b | ||
| 364 | sync | ||
| 365 | blr | ||
| 366 | |||
| 367 | _GLOBAL(_insw) | ||
| 368 | cmpwi 0,r5,0 | ||
| 369 | mtctr r5 | ||
| 370 | subi r4,r4,2 | ||
| 371 | blelr- | ||
| 372 | 00: lhbrx r5,0,r3 | ||
| 373 | eieio | ||
| 374 | sthu r5,2(r4) | ||
| 375 | bdnz 00b | ||
| 376 | twi 0,r5,0 | ||
| 377 | isync | ||
| 378 | blr | ||
| 379 | |||
| 380 | _GLOBAL(_outsw) | ||
| 381 | cmpwi 0,r5,0 | ||
| 382 | mtctr r5 | ||
| 383 | subi r4,r4,2 | ||
| 384 | blelr- | ||
| 385 | 00: lhzu r5,2(r4) | ||
| 386 | sthbrx r5,0,r3 | ||
| 387 | bdnz 00b | ||
| 388 | sync | ||
| 389 | blr | ||
| 390 | |||
| 391 | _GLOBAL(_insl) | ||
| 392 | cmpwi 0,r5,0 | ||
| 393 | mtctr r5 | ||
| 394 | subi r4,r4,4 | ||
| 395 | blelr- | ||
| 396 | 00: lwbrx r5,0,r3 | ||
| 397 | eieio | ||
| 398 | stwu r5,4(r4) | ||
| 399 | bdnz 00b | ||
| 400 | twi 0,r5,0 | ||
| 401 | isync | ||
| 402 | blr | ||
| 403 | |||
| 404 | _GLOBAL(_outsl) | ||
| 405 | cmpwi 0,r5,0 | ||
| 406 | mtctr r5 | ||
| 407 | subi r4,r4,4 | ||
| 408 | blelr- | ||
| 409 | 00: lwzu r5,4(r4) | ||
| 410 | stwbrx r5,0,r3 | ||
| 411 | bdnz 00b | ||
| 412 | sync | ||
| 413 | blr | ||
| 414 | |||
| 415 | /* _GLOBAL(ide_insw) now in drivers/ide/ide-iops.c */ | ||
| 416 | _GLOBAL(_insw_ns) | ||
| 417 | cmpwi 0,r5,0 | ||
| 418 | mtctr r5 | ||
| 419 | subi r4,r4,2 | ||
| 420 | blelr- | ||
| 421 | 00: lhz r5,0(r3) | ||
| 422 | eieio | ||
| 423 | sthu r5,2(r4) | ||
| 424 | bdnz 00b | ||
| 425 | twi 0,r5,0 | ||
| 426 | isync | ||
| 427 | blr | ||
| 428 | |||
| 429 | /* _GLOBAL(ide_outsw) now in drivers/ide/ide-iops.c */ | ||
| 430 | _GLOBAL(_outsw_ns) | ||
| 431 | cmpwi 0,r5,0 | ||
| 432 | mtctr r5 | ||
| 433 | subi r4,r4,2 | ||
| 434 | blelr- | ||
| 435 | 00: lhzu r5,2(r4) | ||
| 436 | sth r5,0(r3) | ||
| 437 | bdnz 00b | ||
| 438 | sync | ||
| 439 | blr | ||
| 440 | |||
| 441 | _GLOBAL(_insl_ns) | ||
| 442 | cmpwi 0,r5,0 | ||
| 443 | mtctr r5 | ||
| 444 | subi r4,r4,4 | ||
| 445 | blelr- | ||
| 446 | 00: lwz r5,0(r3) | ||
| 447 | eieio | ||
| 448 | stwu r5,4(r4) | ||
| 449 | bdnz 00b | ||
| 450 | twi 0,r5,0 | ||
| 451 | isync | ||
| 452 | blr | ||
| 453 | |||
| 454 | _GLOBAL(_outsl_ns) | ||
| 455 | cmpwi 0,r5,0 | ||
| 456 | mtctr r5 | ||
| 457 | subi r4,r4,4 | ||
| 458 | blelr- | ||
| 459 | 00: lwzu r5,4(r4) | ||
| 460 | stw r5,0(r3) | ||
| 461 | bdnz 00b | ||
| 462 | sync | ||
| 463 | blr | ||
| 464 | 247 | ||
| 465 | /* | 248 | /* |
| 466 | * identify_cpu and calls setup_cpu | 249 | * identify_cpu and calls setup_cpu |
| @@ -605,6 +388,7 @@ _GLOBAL(real_writeb) | |||
| 605 | blr | 388 | blr |
| 606 | #endif /* defined(CONFIG_PPC_PMAC) || defined(CONFIG_PPC_MAPLE) */ | 389 | #endif /* defined(CONFIG_PPC_PMAC) || defined(CONFIG_PPC_MAPLE) */ |
| 607 | 390 | ||
| 391 | #ifdef CONFIG_CPU_FREQ_PMAC64 | ||
| 608 | /* | 392 | /* |
| 609 | * SCOM access functions for 970 (FX only for now) | 393 | * SCOM access functions for 970 (FX only for now) |
| 610 | * | 394 | * |
| @@ -673,6 +457,7 @@ _GLOBAL(scom970_write) | |||
| 673 | /* restore interrupts */ | 457 | /* restore interrupts */ |
| 674 | mtmsrd r5,1 | 458 | mtmsrd r5,1 |
| 675 | blr | 459 | blr |
| 460 | #endif /* CONFIG_CPU_FREQ_PMAC64 */ | ||
| 676 | 461 | ||
| 677 | 462 | ||
| 678 | /* | 463 | /* |
diff --git a/arch/powerpc/kernel/paca.c b/arch/powerpc/kernel/paca.c index f505a8827e3e..a0bb354c1c08 100644 --- a/arch/powerpc/kernel/paca.c +++ b/arch/powerpc/kernel/paca.c | |||
| @@ -16,7 +16,6 @@ | |||
| 16 | #include <asm/ptrace.h> | 16 | #include <asm/ptrace.h> |
| 17 | #include <asm/page.h> | 17 | #include <asm/page.h> |
| 18 | #include <asm/lppaca.h> | 18 | #include <asm/lppaca.h> |
| 19 | #include <asm/iseries/it_lp_queue.h> | ||
| 20 | #include <asm/iseries/it_lp_reg_save.h> | 19 | #include <asm/iseries/it_lp_reg_save.h> |
| 21 | #include <asm/paca.h> | 20 | #include <asm/paca.h> |
| 22 | 21 | ||
diff --git a/arch/powerpc/kernel/prom.c b/arch/powerpc/kernel/prom.c index 483455c5bb02..320c913435cd 100644 --- a/arch/powerpc/kernel/prom.c +++ b/arch/powerpc/kernel/prom.c | |||
| @@ -30,6 +30,7 @@ | |||
| 30 | #include <linux/bitops.h> | 30 | #include <linux/bitops.h> |
| 31 | #include <linux/module.h> | 31 | #include <linux/module.h> |
| 32 | #include <linux/kexec.h> | 32 | #include <linux/kexec.h> |
| 33 | #include <linux/debugfs.h> | ||
| 33 | 34 | ||
| 34 | #include <asm/prom.h> | 35 | #include <asm/prom.h> |
| 35 | #include <asm/rtas.h> | 36 | #include <asm/rtas.h> |
| @@ -952,6 +953,7 @@ static struct ibm_pa_feature { | |||
| 952 | /* put this back once we know how to test if firmware does 64k IO */ | 953 | /* put this back once we know how to test if firmware does 64k IO */ |
| 953 | {CPU_FTR_CI_LARGE_PAGE, 0, 1, 2, 0}, | 954 | {CPU_FTR_CI_LARGE_PAGE, 0, 1, 2, 0}, |
| 954 | #endif | 955 | #endif |
| 956 | {CPU_FTR_REAL_LE, PPC_FEATURE_TRUE_LE, 5, 0, 0}, | ||
| 955 | }; | 957 | }; |
| 956 | 958 | ||
| 957 | static void __init check_cpu_pa_features(unsigned long node) | 959 | static void __init check_cpu_pa_features(unsigned long node) |
| @@ -1124,24 +1126,6 @@ static int __init early_init_dt_scan_chosen(unsigned long node, | |||
| 1124 | tce_alloc_end = *lprop; | 1126 | tce_alloc_end = *lprop; |
| 1125 | #endif | 1127 | #endif |
| 1126 | 1128 | ||
| 1127 | #ifdef CONFIG_PPC_RTAS | ||
| 1128 | /* To help early debugging via the front panel, we retrieve a minimal | ||
| 1129 | * set of RTAS infos now if available | ||
| 1130 | */ | ||
| 1131 | { | ||
| 1132 | u64 *basep, *entryp, *sizep; | ||
| 1133 | |||
| 1134 | basep = of_get_flat_dt_prop(node, "linux,rtas-base", NULL); | ||
| 1135 | entryp = of_get_flat_dt_prop(node, "linux,rtas-entry", NULL); | ||
| 1136 | sizep = of_get_flat_dt_prop(node, "linux,rtas-size", NULL); | ||
| 1137 | if (basep && entryp && sizep) { | ||
| 1138 | rtas.base = *basep; | ||
| 1139 | rtas.entry = *entryp; | ||
| 1140 | rtas.size = *sizep; | ||
| 1141 | } | ||
| 1142 | } | ||
| 1143 | #endif /* CONFIG_PPC_RTAS */ | ||
| 1144 | |||
| 1145 | #ifdef CONFIG_KEXEC | 1129 | #ifdef CONFIG_KEXEC |
| 1146 | lprop = (u64*)of_get_flat_dt_prop(node, "linux,crashkernel-base", NULL); | 1130 | lprop = (u64*)of_get_flat_dt_prop(node, "linux,crashkernel-base", NULL); |
| 1147 | if (lprop) | 1131 | if (lprop) |
| @@ -1326,6 +1310,11 @@ void __init early_init_devtree(void *params) | |||
| 1326 | /* Setup flat device-tree pointer */ | 1310 | /* Setup flat device-tree pointer */ |
| 1327 | initial_boot_params = params; | 1311 | initial_boot_params = params; |
| 1328 | 1312 | ||
| 1313 | #ifdef CONFIG_PPC_RTAS | ||
| 1314 | /* Some machines might need RTAS info for debugging, grab it now. */ | ||
| 1315 | of_scan_flat_dt(early_init_dt_scan_rtas, NULL); | ||
| 1316 | #endif | ||
| 1317 | |||
| 1329 | /* Retrieve various informations from the /chosen node of the | 1318 | /* Retrieve various informations from the /chosen node of the |
| 1330 | * device-tree, including the platform type, initrd location and | 1319 | * device-tree, including the platform type, initrd location and |
| 1331 | * size, TCE reserve, and more ... | 1320 | * size, TCE reserve, and more ... |
| @@ -2148,3 +2137,27 @@ struct device_node *of_get_cpu_node(int cpu, unsigned int *thread) | |||
| 2148 | } | 2137 | } |
| 2149 | return NULL; | 2138 | return NULL; |
| 2150 | } | 2139 | } |
| 2140 | |||
| 2141 | #ifdef DEBUG | ||
| 2142 | static struct debugfs_blob_wrapper flat_dt_blob; | ||
| 2143 | |||
| 2144 | static int __init export_flat_device_tree(void) | ||
| 2145 | { | ||
| 2146 | struct dentry *d; | ||
| 2147 | |||
| 2148 | d = debugfs_create_dir("powerpc", NULL); | ||
| 2149 | if (!d) | ||
| 2150 | return 1; | ||
| 2151 | |||
| 2152 | flat_dt_blob.data = initial_boot_params; | ||
| 2153 | flat_dt_blob.size = initial_boot_params->totalsize; | ||
| 2154 | |||
| 2155 | d = debugfs_create_blob("flat-device-tree", S_IFREG | S_IRUSR, | ||
| 2156 | d, &flat_dt_blob); | ||
| 2157 | if (!d) | ||
| 2158 | return 1; | ||
| 2159 | |||
| 2160 | return 0; | ||
| 2161 | } | ||
| 2162 | __initcall(export_flat_device_tree); | ||
| 2163 | #endif | ||
diff --git a/arch/powerpc/kernel/rtas.c b/arch/powerpc/kernel/rtas.c index 17dc79198515..4a4cb5598402 100644 --- a/arch/powerpc/kernel/rtas.c +++ b/arch/powerpc/kernel/rtas.c | |||
| @@ -38,16 +38,19 @@ | |||
| 38 | struct rtas_t rtas = { | 38 | struct rtas_t rtas = { |
| 39 | .lock = SPIN_LOCK_UNLOCKED | 39 | .lock = SPIN_LOCK_UNLOCKED |
| 40 | }; | 40 | }; |
| 41 | EXPORT_SYMBOL(rtas); | ||
| 41 | 42 | ||
| 42 | struct rtas_suspend_me_data { | 43 | struct rtas_suspend_me_data { |
| 43 | long waiting; | 44 | long waiting; |
| 44 | struct rtas_args *args; | 45 | struct rtas_args *args; |
| 45 | }; | 46 | }; |
| 46 | 47 | ||
| 47 | EXPORT_SYMBOL(rtas); | ||
| 48 | |||
| 49 | DEFINE_SPINLOCK(rtas_data_buf_lock); | 48 | DEFINE_SPINLOCK(rtas_data_buf_lock); |
| 49 | EXPORT_SYMBOL(rtas_data_buf_lock); | ||
| 50 | |||
| 50 | char rtas_data_buf[RTAS_DATA_BUF_SIZE] __cacheline_aligned; | 51 | char rtas_data_buf[RTAS_DATA_BUF_SIZE] __cacheline_aligned; |
| 52 | EXPORT_SYMBOL(rtas_data_buf); | ||
| 53 | |||
| 51 | unsigned long rtas_rmo_buf; | 54 | unsigned long rtas_rmo_buf; |
| 52 | 55 | ||
| 53 | /* | 56 | /* |
| @@ -106,11 +109,71 @@ static void call_rtas_display_status_delay(char c) | |||
| 106 | } | 109 | } |
| 107 | } | 110 | } |
| 108 | 111 | ||
| 109 | void __init udbg_init_rtas(void) | 112 | void __init udbg_init_rtas_panel(void) |
| 110 | { | 113 | { |
| 111 | udbg_putc = call_rtas_display_status_delay; | 114 | udbg_putc = call_rtas_display_status_delay; |
| 112 | } | 115 | } |
| 113 | 116 | ||
| 117 | #ifdef CONFIG_UDBG_RTAS_CONSOLE | ||
| 118 | |||
| 119 | /* If you think you're dying before early_init_dt_scan_rtas() does its | ||
| 120 | * work, you can hard code the token values for your firmware here and | ||
| 121 | * hardcode rtas.base/entry etc. | ||
| 122 | */ | ||
| 123 | static unsigned int rtas_putchar_token = RTAS_UNKNOWN_SERVICE; | ||
| 124 | static unsigned int rtas_getchar_token = RTAS_UNKNOWN_SERVICE; | ||
| 125 | |||
| 126 | static void udbg_rtascon_putc(char c) | ||
| 127 | { | ||
| 128 | int tries; | ||
| 129 | |||
| 130 | if (!rtas.base) | ||
| 131 | return; | ||
| 132 | |||
| 133 | /* Add CRs before LFs */ | ||
| 134 | if (c == '\n') | ||
| 135 | udbg_rtascon_putc('\r'); | ||
| 136 | |||
| 137 | /* if there is more than one character to be displayed, wait a bit */ | ||
| 138 | for (tries = 0; tries < 16; tries++) { | ||
| 139 | if (rtas_call(rtas_putchar_token, 1, 1, NULL, c) == 0) | ||
| 140 | break; | ||
| 141 | udelay(1000); | ||
| 142 | } | ||
| 143 | } | ||
| 144 | |||
| 145 | static int udbg_rtascon_getc_poll(void) | ||
| 146 | { | ||
| 147 | int c; | ||
| 148 | |||
| 149 | if (!rtas.base) | ||
| 150 | return -1; | ||
| 151 | |||
| 152 | if (rtas_call(rtas_getchar_token, 0, 2, &c)) | ||
| 153 | return -1; | ||
| 154 | |||
| 155 | return c; | ||
| 156 | } | ||
| 157 | |||
| 158 | static int udbg_rtascon_getc(void) | ||
| 159 | { | ||
| 160 | int c; | ||
| 161 | |||
| 162 | while ((c = udbg_rtascon_getc_poll()) == -1) | ||
| 163 | ; | ||
| 164 | |||
| 165 | return c; | ||
| 166 | } | ||
| 167 | |||
| 168 | |||
| 169 | void __init udbg_init_rtas_console(void) | ||
| 170 | { | ||
| 171 | udbg_putc = udbg_rtascon_putc; | ||
| 172 | udbg_getc = udbg_rtascon_getc; | ||
| 173 | udbg_getc_poll = udbg_rtascon_getc_poll; | ||
| 174 | } | ||
| 175 | #endif /* CONFIG_UDBG_RTAS_CONSOLE */ | ||
| 176 | |||
| 114 | void rtas_progress(char *s, unsigned short hex) | 177 | void rtas_progress(char *s, unsigned short hex) |
| 115 | { | 178 | { |
| 116 | struct device_node *root; | 179 | struct device_node *root; |
| @@ -236,6 +299,7 @@ int rtas_token(const char *service) | |||
| 236 | tokp = (int *) get_property(rtas.dev, service, NULL); | 299 | tokp = (int *) get_property(rtas.dev, service, NULL); |
| 237 | return tokp ? *tokp : RTAS_UNKNOWN_SERVICE; | 300 | return tokp ? *tokp : RTAS_UNKNOWN_SERVICE; |
| 238 | } | 301 | } |
| 302 | EXPORT_SYMBOL(rtas_token); | ||
| 239 | 303 | ||
| 240 | #ifdef CONFIG_RTAS_ERROR_LOGGING | 304 | #ifdef CONFIG_RTAS_ERROR_LOGGING |
| 241 | /* | 305 | /* |
| @@ -328,7 +392,7 @@ int rtas_call(int token, int nargs, int nret, int *outputs, ...) | |||
| 328 | char *buff_copy = NULL; | 392 | char *buff_copy = NULL; |
| 329 | int ret; | 393 | int ret; |
| 330 | 394 | ||
| 331 | if (token == RTAS_UNKNOWN_SERVICE) | 395 | if (!rtas.entry || token == RTAS_UNKNOWN_SERVICE) |
| 332 | return -1; | 396 | return -1; |
| 333 | 397 | ||
| 334 | /* Gotta do something different here, use global lock for now... */ | 398 | /* Gotta do something different here, use global lock for now... */ |
| @@ -369,6 +433,7 @@ int rtas_call(int token, int nargs, int nret, int *outputs, ...) | |||
| 369 | } | 433 | } |
| 370 | return ret; | 434 | return ret; |
| 371 | } | 435 | } |
| 436 | EXPORT_SYMBOL(rtas_call); | ||
| 372 | 437 | ||
| 373 | /* For RTAS_BUSY (-2), delay for 1 millisecond. For an extended busy status | 438 | /* For RTAS_BUSY (-2), delay for 1 millisecond. For an extended busy status |
| 374 | * code of 990n, perform the hinted delay of 10^n (last digit) milliseconds. | 439 | * code of 990n, perform the hinted delay of 10^n (last digit) milliseconds. |
| @@ -388,6 +453,7 @@ unsigned int rtas_busy_delay_time(int status) | |||
| 388 | 453 | ||
| 389 | return ms; | 454 | return ms; |
| 390 | } | 455 | } |
| 456 | EXPORT_SYMBOL(rtas_busy_delay_time); | ||
| 391 | 457 | ||
| 392 | /* For an RTAS busy status code, perform the hinted delay. */ | 458 | /* For an RTAS busy status code, perform the hinted delay. */ |
| 393 | unsigned int rtas_busy_delay(int status) | 459 | unsigned int rtas_busy_delay(int status) |
| @@ -401,6 +467,7 @@ unsigned int rtas_busy_delay(int status) | |||
| 401 | 467 | ||
| 402 | return ms; | 468 | return ms; |
| 403 | } | 469 | } |
| 470 | EXPORT_SYMBOL(rtas_busy_delay); | ||
| 404 | 471 | ||
| 405 | int rtas_error_rc(int rtas_rc) | 472 | int rtas_error_rc(int rtas_rc) |
| 406 | { | 473 | { |
| @@ -446,6 +513,7 @@ int rtas_get_power_level(int powerdomain, int *level) | |||
| 446 | return rtas_error_rc(rc); | 513 | return rtas_error_rc(rc); |
| 447 | return rc; | 514 | return rc; |
| 448 | } | 515 | } |
| 516 | EXPORT_SYMBOL(rtas_get_power_level); | ||
| 449 | 517 | ||
| 450 | int rtas_set_power_level(int powerdomain, int level, int *setlevel) | 518 | int rtas_set_power_level(int powerdomain, int level, int *setlevel) |
| 451 | { | 519 | { |
| @@ -463,6 +531,7 @@ int rtas_set_power_level(int powerdomain, int level, int *setlevel) | |||
| 463 | return rtas_error_rc(rc); | 531 | return rtas_error_rc(rc); |
| 464 | return rc; | 532 | return rc; |
| 465 | } | 533 | } |
| 534 | EXPORT_SYMBOL(rtas_set_power_level); | ||
| 466 | 535 | ||
| 467 | int rtas_get_sensor(int sensor, int index, int *state) | 536 | int rtas_get_sensor(int sensor, int index, int *state) |
| 468 | { | 537 | { |
| @@ -480,6 +549,7 @@ int rtas_get_sensor(int sensor, int index, int *state) | |||
| 480 | return rtas_error_rc(rc); | 549 | return rtas_error_rc(rc); |
| 481 | return rc; | 550 | return rc; |
| 482 | } | 551 | } |
| 552 | EXPORT_SYMBOL(rtas_get_sensor); | ||
| 483 | 553 | ||
| 484 | int rtas_set_indicator(int indicator, int index, int new_value) | 554 | int rtas_set_indicator(int indicator, int index, int new_value) |
| 485 | { | 555 | { |
| @@ -497,6 +567,7 @@ int rtas_set_indicator(int indicator, int index, int new_value) | |||
| 497 | return rtas_error_rc(rc); | 567 | return rtas_error_rc(rc); |
| 498 | return rc; | 568 | return rc; |
| 499 | } | 569 | } |
| 570 | EXPORT_SYMBOL(rtas_set_indicator); | ||
| 500 | 571 | ||
| 501 | void rtas_restart(char *cmd) | 572 | void rtas_restart(char *cmd) |
| 502 | { | 573 | { |
| @@ -791,14 +862,34 @@ void __init rtas_initialize(void) | |||
| 791 | #endif | 862 | #endif |
| 792 | } | 863 | } |
| 793 | 864 | ||
| 865 | int __init early_init_dt_scan_rtas(unsigned long node, | ||
| 866 | const char *uname, int depth, void *data) | ||
| 867 | { | ||
| 868 | u32 *basep, *entryp, *sizep; | ||
| 794 | 869 | ||
| 795 | EXPORT_SYMBOL(rtas_token); | 870 | if (depth != 1 || strcmp(uname, "rtas") != 0) |
| 796 | EXPORT_SYMBOL(rtas_call); | 871 | return 0; |
| 797 | EXPORT_SYMBOL(rtas_data_buf); | 872 | |
| 798 | EXPORT_SYMBOL(rtas_data_buf_lock); | 873 | basep = of_get_flat_dt_prop(node, "linux,rtas-base", NULL); |
| 799 | EXPORT_SYMBOL(rtas_busy_delay_time); | 874 | entryp = of_get_flat_dt_prop(node, "linux,rtas-entry", NULL); |
| 800 | EXPORT_SYMBOL(rtas_busy_delay); | 875 | sizep = of_get_flat_dt_prop(node, "rtas-size", NULL); |
| 801 | EXPORT_SYMBOL(rtas_get_sensor); | 876 | |
| 802 | EXPORT_SYMBOL(rtas_get_power_level); | 877 | if (basep && entryp && sizep) { |
| 803 | EXPORT_SYMBOL(rtas_set_power_level); | 878 | rtas.base = *basep; |
| 804 | EXPORT_SYMBOL(rtas_set_indicator); | 879 | rtas.entry = *entryp; |
| 880 | rtas.size = *sizep; | ||
| 881 | } | ||
| 882 | |||
| 883 | #ifdef CONFIG_UDBG_RTAS_CONSOLE | ||
| 884 | basep = of_get_flat_dt_prop(node, "put-term-char", NULL); | ||
| 885 | if (basep) | ||
| 886 | rtas_putchar_token = *basep; | ||
| 887 | |||
| 888 | basep = of_get_flat_dt_prop(node, "get-term-char", NULL); | ||
| 889 | if (basep) | ||
| 890 | rtas_getchar_token = *basep; | ||
| 891 | #endif | ||
| 892 | |||
| 893 | /* break now */ | ||
| 894 | return 1; | ||
| 895 | } | ||
diff --git a/arch/powerpc/kernel/setup_64.c b/arch/powerpc/kernel/setup_64.c index 78f3a5fd43f6..175539c9afa0 100644 --- a/arch/powerpc/kernel/setup_64.c +++ b/arch/powerpc/kernel/setup_64.c | |||
| @@ -149,6 +149,13 @@ early_param("smt-enabled", early_smt_enabled); | |||
| 149 | #define check_smt_enabled() | 149 | #define check_smt_enabled() |
| 150 | #endif /* CONFIG_SMP */ | 150 | #endif /* CONFIG_SMP */ |
| 151 | 151 | ||
| 152 | /* Put the paca pointer into r13 and SPRG3 */ | ||
| 153 | void __init setup_paca(int cpu) | ||
| 154 | { | ||
| 155 | local_paca = &paca[cpu]; | ||
| 156 | mtspr(SPRN_SPRG3, local_paca); | ||
| 157 | } | ||
| 158 | |||
| 152 | /* | 159 | /* |
| 153 | * Early initialization entry point. This is called by head.S | 160 | * Early initialization entry point. This is called by head.S |
| 154 | * with MMU translation disabled. We rely on the "feature" of | 161 | * with MMU translation disabled. We rely on the "feature" of |
| @@ -170,6 +177,9 @@ early_param("smt-enabled", early_smt_enabled); | |||
| 170 | 177 | ||
| 171 | void __init early_setup(unsigned long dt_ptr) | 178 | void __init early_setup(unsigned long dt_ptr) |
| 172 | { | 179 | { |
| 180 | /* Assume we're on cpu 0 for now. Don't write to the paca yet! */ | ||
| 181 | setup_paca(0); | ||
| 182 | |||
| 173 | /* Enable early debugging if any specified (see udbg.h) */ | 183 | /* Enable early debugging if any specified (see udbg.h) */ |
| 174 | udbg_early_init(); | 184 | udbg_early_init(); |
| 175 | 185 | ||
| @@ -183,7 +193,7 @@ void __init early_setup(unsigned long dt_ptr) | |||
| 183 | early_init_devtree(__va(dt_ptr)); | 193 | early_init_devtree(__va(dt_ptr)); |
| 184 | 194 | ||
| 185 | /* Now we know the logical id of our boot cpu, setup the paca. */ | 195 | /* Now we know the logical id of our boot cpu, setup the paca. */ |
| 186 | setup_boot_paca(); | 196 | setup_paca(boot_cpuid); |
| 187 | 197 | ||
| 188 | /* Fix up paca fields required for the boot cpu */ | 198 | /* Fix up paca fields required for the boot cpu */ |
| 189 | get_paca()->cpu_start = 1; | 199 | get_paca()->cpu_start = 1; |
| @@ -350,19 +360,11 @@ void __init setup_system(void) | |||
| 350 | */ | 360 | */ |
| 351 | unflatten_device_tree(); | 361 | unflatten_device_tree(); |
| 352 | 362 | ||
| 353 | #ifdef CONFIG_KEXEC | ||
| 354 | kexec_setup(); /* requires unflattened device tree. */ | ||
| 355 | #endif | ||
| 356 | |||
| 357 | /* | 363 | /* |
| 358 | * Fill the ppc64_caches & systemcfg structures with informations | 364 | * Fill the ppc64_caches & systemcfg structures with informations |
| 359 | * retrieved from the device-tree. Need to be called before | 365 | * retrieved from the device-tree. Need to be called before |
| 360 | * finish_device_tree() since the later requires some of the | 366 | * finish_device_tree() since the later requires some of the |
| 361 | * informations filled up here to properly parse the interrupt | 367 | * informations filled up here to properly parse the interrupt tree. |
| 362 | * tree. | ||
| 363 | * It also sets up the cache line sizes which allows to call | ||
| 364 | * routines like flush_icache_range (used by the hash init | ||
| 365 | * later on). | ||
| 366 | */ | 368 | */ |
| 367 | initialize_cache_info(); | 369 | initialize_cache_info(); |
| 368 | 370 | ||
diff --git a/arch/powerpc/kernel/traps.c b/arch/powerpc/kernel/traps.c index 52f5659534f4..fa6bd97b6b9d 100644 --- a/arch/powerpc/kernel/traps.c +++ b/arch/powerpc/kernel/traps.c | |||
| @@ -52,9 +52,13 @@ | |||
| 52 | #include <asm/firmware.h> | 52 | #include <asm/firmware.h> |
| 53 | #include <asm/processor.h> | 53 | #include <asm/processor.h> |
| 54 | #endif | 54 | #endif |
| 55 | #include <asm/kexec.h> | ||
| 55 | 56 | ||
| 56 | #ifdef CONFIG_PPC64 /* XXX */ | 57 | #ifdef CONFIG_PPC64 /* XXX */ |
| 57 | #define _IO_BASE pci_io_base | 58 | #define _IO_BASE pci_io_base |
| 59 | #ifdef CONFIG_KEXEC | ||
| 60 | cpumask_t cpus_in_sr = CPU_MASK_NONE; | ||
| 61 | #endif | ||
| 58 | #endif | 62 | #endif |
| 59 | 63 | ||
| 60 | #ifdef CONFIG_DEBUGGER | 64 | #ifdef CONFIG_DEBUGGER |
| @@ -97,7 +101,7 @@ static DEFINE_SPINLOCK(die_lock); | |||
| 97 | 101 | ||
| 98 | int die(const char *str, struct pt_regs *regs, long err) | 102 | int die(const char *str, struct pt_regs *regs, long err) |
| 99 | { | 103 | { |
| 100 | static int die_counter, crash_dump_start = 0; | 104 | static int die_counter; |
| 101 | 105 | ||
| 102 | if (debugger(regs)) | 106 | if (debugger(regs)) |
| 103 | return 1; | 107 | return 1; |
| @@ -137,21 +141,12 @@ int die(const char *str, struct pt_regs *regs, long err) | |||
| 137 | print_modules(); | 141 | print_modules(); |
| 138 | show_regs(regs); | 142 | show_regs(regs); |
| 139 | bust_spinlocks(0); | 143 | bust_spinlocks(0); |
| 144 | spin_unlock_irq(&die_lock); | ||
| 140 | 145 | ||
| 141 | if (!crash_dump_start && kexec_should_crash(current)) { | 146 | if (kexec_should_crash(current) || |
| 142 | crash_dump_start = 1; | 147 | kexec_sr_activated(smp_processor_id())) |
| 143 | spin_unlock_irq(&die_lock); | ||
| 144 | crash_kexec(regs); | 148 | crash_kexec(regs); |
| 145 | /* NOTREACHED */ | 149 | crash_kexec_secondary(regs); |
| 146 | } | ||
| 147 | spin_unlock_irq(&die_lock); | ||
| 148 | if (crash_dump_start) | ||
| 149 | /* | ||
| 150 | * Only for soft-reset: Other CPUs will be responded to an IPI | ||
| 151 | * sent by first kexec CPU. | ||
| 152 | */ | ||
| 153 | for(;;) | ||
| 154 | ; | ||
| 155 | 150 | ||
| 156 | if (in_interrupt()) | 151 | if (in_interrupt()) |
| 157 | panic("Fatal exception in interrupt"); | 152 | panic("Fatal exception in interrupt"); |
| @@ -215,6 +210,10 @@ void system_reset_exception(struct pt_regs *regs) | |||
| 215 | return; | 210 | return; |
| 216 | } | 211 | } |
| 217 | 212 | ||
| 213 | #ifdef CONFIG_KEXEC | ||
| 214 | cpu_set(smp_processor_id(), cpus_in_sr); | ||
| 215 | #endif | ||
| 216 | |||
| 218 | die("System Reset", regs, SIGABRT); | 217 | die("System Reset", regs, SIGABRT); |
| 219 | 218 | ||
| 220 | /* Must die if the interrupt is not recoverable */ | 219 | /* Must die if the interrupt is not recoverable */ |
diff --git a/arch/powerpc/kernel/udbg.c b/arch/powerpc/kernel/udbg.c index 67d9fd9ae2b5..759afd5e0d8a 100644 --- a/arch/powerpc/kernel/udbg.c +++ b/arch/powerpc/kernel/udbg.c | |||
| @@ -34,9 +34,12 @@ void __init udbg_early_init(void) | |||
| 34 | #elif defined(CONFIG_PPC_EARLY_DEBUG_G5) | 34 | #elif defined(CONFIG_PPC_EARLY_DEBUG_G5) |
| 35 | /* For use on Apple G5 machines */ | 35 | /* For use on Apple G5 machines */ |
| 36 | udbg_init_pmac_realmode(); | 36 | udbg_init_pmac_realmode(); |
| 37 | #elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS) | 37 | #elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS_PANEL) |
| 38 | /* RTAS panel debug */ | 38 | /* RTAS panel debug */ |
| 39 | udbg_init_rtas(); | 39 | udbg_init_rtas_panel(); |
| 40 | #elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS_CONSOLE) | ||
| 41 | /* RTAS console debug */ | ||
| 42 | udbg_init_rtas_console(); | ||
| 40 | #elif defined(CONFIG_PPC_EARLY_DEBUG_MAPLE) | 43 | #elif defined(CONFIG_PPC_EARLY_DEBUG_MAPLE) |
| 41 | /* Maple real mode debug */ | 44 | /* Maple real mode debug */ |
| 42 | udbg_init_maple_realmode(); | 45 | udbg_init_maple_realmode(); |
diff --git a/arch/powerpc/mm/hash_native_64.c b/arch/powerpc/mm/hash_native_64.c index a0f3cbd00d39..c90f124f3c71 100644 --- a/arch/powerpc/mm/hash_native_64.c +++ b/arch/powerpc/mm/hash_native_64.c | |||
| @@ -520,7 +520,7 @@ static inline int tlb_batching_enabled(void) | |||
| 520 | } | 520 | } |
| 521 | #endif | 521 | #endif |
| 522 | 522 | ||
| 523 | void hpte_init_native(void) | 523 | void __init hpte_init_native(void) |
| 524 | { | 524 | { |
| 525 | ppc_md.hpte_invalidate = native_hpte_invalidate; | 525 | ppc_md.hpte_invalidate = native_hpte_invalidate; |
| 526 | ppc_md.hpte_updatepp = native_hpte_updatepp; | 526 | ppc_md.hpte_updatepp = native_hpte_updatepp; |
| @@ -530,5 +530,4 @@ void hpte_init_native(void) | |||
| 530 | ppc_md.hpte_clear_all = native_hpte_clear; | 530 | ppc_md.hpte_clear_all = native_hpte_clear; |
| 531 | if (tlb_batching_enabled()) | 531 | if (tlb_batching_enabled()) |
| 532 | ppc_md.flush_hash_range = native_flush_hash_range; | 532 | ppc_md.flush_hash_range = native_flush_hash_range; |
| 533 | htab_finish_init(); | ||
| 534 | } | 533 | } |
diff --git a/arch/powerpc/mm/hash_utils_64.c b/arch/powerpc/mm/hash_utils_64.c index d03fd2b4445e..3cc6d68f7117 100644 --- a/arch/powerpc/mm/hash_utils_64.c +++ b/arch/powerpc/mm/hash_utils_64.c | |||
| @@ -167,34 +167,12 @@ int htab_bolt_mapping(unsigned long vstart, unsigned long vend, | |||
| 167 | hash = hpt_hash(va, shift); | 167 | hash = hpt_hash(va, shift); |
| 168 | hpteg = ((hash & htab_hash_mask) * HPTES_PER_GROUP); | 168 | hpteg = ((hash & htab_hash_mask) * HPTES_PER_GROUP); |
| 169 | 169 | ||
| 170 | /* The crap below can be cleaned once ppd_md.probe() can | 170 | DBG("htab_bolt_mapping: calling %p\n", ppc_md.hpte_insert); |
| 171 | * set up the hash callbacks, thus we can just used the | 171 | |
| 172 | * normal insert callback here. | 172 | BUG_ON(!ppc_md.hpte_insert); |
| 173 | */ | 173 | ret = ppc_md.hpte_insert(hpteg, va, paddr, |
| 174 | #ifdef CONFIG_PPC_ISERIES | 174 | tmp_mode, HPTE_V_BOLTED, psize); |
| 175 | if (machine_is(iseries)) | 175 | |
| 176 | ret = iSeries_hpte_insert(hpteg, va, | ||
| 177 | paddr, | ||
| 178 | tmp_mode, | ||
| 179 | HPTE_V_BOLTED, | ||
| 180 | psize); | ||
| 181 | else | ||
| 182 | #endif | ||
| 183 | #ifdef CONFIG_PPC_PSERIES | ||
| 184 | if (machine_is(pseries) && firmware_has_feature(FW_FEATURE_LPAR)) | ||
| 185 | ret = pSeries_lpar_hpte_insert(hpteg, va, | ||
| 186 | paddr, | ||
| 187 | tmp_mode, | ||
| 188 | HPTE_V_BOLTED, | ||
| 189 | psize); | ||
| 190 | else | ||
| 191 | #endif | ||
| 192 | #ifdef CONFIG_PPC_MULTIPLATFORM | ||
| 193 | ret = native_hpte_insert(hpteg, va, | ||
| 194 | paddr, | ||
| 195 | tmp_mode, HPTE_V_BOLTED, | ||
| 196 | psize); | ||
| 197 | #endif | ||
| 198 | if (ret < 0) | 176 | if (ret < 0) |
| 199 | break; | 177 | break; |
| 200 | } | 178 | } |
| @@ -413,6 +391,41 @@ void create_section_mapping(unsigned long start, unsigned long end) | |||
| 413 | } | 391 | } |
| 414 | #endif /* CONFIG_MEMORY_HOTPLUG */ | 392 | #endif /* CONFIG_MEMORY_HOTPLUG */ |
| 415 | 393 | ||
| 394 | static inline void make_bl(unsigned int *insn_addr, void *func) | ||
| 395 | { | ||
| 396 | unsigned long funcp = *((unsigned long *)func); | ||
| 397 | int offset = funcp - (unsigned long)insn_addr; | ||
| 398 | |||
| 399 | *insn_addr = (unsigned int)(0x48000001 | (offset & 0x03fffffc)); | ||
| 400 | flush_icache_range((unsigned long)insn_addr, 4+ | ||
| 401 | (unsigned long)insn_addr); | ||
| 402 | } | ||
| 403 | |||
| 404 | static void __init htab_finish_init(void) | ||
| 405 | { | ||
| 406 | extern unsigned int *htab_call_hpte_insert1; | ||
| 407 | extern unsigned int *htab_call_hpte_insert2; | ||
| 408 | extern unsigned int *htab_call_hpte_remove; | ||
| 409 | extern unsigned int *htab_call_hpte_updatepp; | ||
| 410 | |||
| 411 | #ifdef CONFIG_PPC_64K_PAGES | ||
| 412 | extern unsigned int *ht64_call_hpte_insert1; | ||
| 413 | extern unsigned int *ht64_call_hpte_insert2; | ||
| 414 | extern unsigned int *ht64_call_hpte_remove; | ||
| 415 | extern unsigned int *ht64_call_hpte_updatepp; | ||
| 416 | |||
| 417 | make_bl(ht64_call_hpte_insert1, ppc_md.hpte_insert); | ||
| 418 | make_bl(ht64_call_hpte_insert2, ppc_md.hpte_insert); | ||
| 419 | make_bl(ht64_call_hpte_remove, ppc_md.hpte_remove); | ||
| 420 | make_bl(ht64_call_hpte_updatepp, ppc_md.hpte_updatepp); | ||
| 421 | #endif /* CONFIG_PPC_64K_PAGES */ | ||
| 422 | |||
| 423 | make_bl(htab_call_hpte_insert1, ppc_md.hpte_insert); | ||
| 424 | make_bl(htab_call_hpte_insert2, ppc_md.hpte_insert); | ||
| 425 | make_bl(htab_call_hpte_remove, ppc_md.hpte_remove); | ||
| 426 | make_bl(htab_call_hpte_updatepp, ppc_md.hpte_updatepp); | ||
| 427 | } | ||
| 428 | |||
| 416 | void __init htab_initialize(void) | 429 | void __init htab_initialize(void) |
| 417 | { | 430 | { |
| 418 | unsigned long table; | 431 | unsigned long table; |
| @@ -525,6 +538,8 @@ void __init htab_initialize(void) | |||
| 525 | mmu_linear_psize)); | 538 | mmu_linear_psize)); |
| 526 | } | 539 | } |
| 527 | 540 | ||
| 541 | htab_finish_init(); | ||
| 542 | |||
| 528 | DBG(" <- htab_initialize()\n"); | 543 | DBG(" <- htab_initialize()\n"); |
| 529 | } | 544 | } |
| 530 | #undef KB | 545 | #undef KB |
| @@ -787,16 +802,6 @@ void flush_hash_range(unsigned long number, int local) | |||
| 787 | } | 802 | } |
| 788 | } | 803 | } |
| 789 | 804 | ||
| 790 | static inline void make_bl(unsigned int *insn_addr, void *func) | ||
| 791 | { | ||
| 792 | unsigned long funcp = *((unsigned long *)func); | ||
| 793 | int offset = funcp - (unsigned long)insn_addr; | ||
| 794 | |||
| 795 | *insn_addr = (unsigned int)(0x48000001 | (offset & 0x03fffffc)); | ||
| 796 | flush_icache_range((unsigned long)insn_addr, 4+ | ||
| 797 | (unsigned long)insn_addr); | ||
| 798 | } | ||
| 799 | |||
| 800 | /* | 805 | /* |
| 801 | * low_hash_fault is called when we the low level hash code failed | 806 | * low_hash_fault is called when we the low level hash code failed |
| 802 | * to instert a PTE due to an hypervisor error | 807 | * to instert a PTE due to an hypervisor error |
| @@ -815,28 +820,3 @@ void low_hash_fault(struct pt_regs *regs, unsigned long address) | |||
| 815 | } | 820 | } |
| 816 | bad_page_fault(regs, address, SIGBUS); | 821 | bad_page_fault(regs, address, SIGBUS); |
| 817 | } | 822 | } |
| 818 | |||
| 819 | void __init htab_finish_init(void) | ||
| 820 | { | ||
| 821 | extern unsigned int *htab_call_hpte_insert1; | ||
| 822 | extern unsigned int *htab_call_hpte_insert2; | ||
| 823 | extern unsigned int *htab_call_hpte_remove; | ||
| 824 | extern unsigned int *htab_call_hpte_updatepp; | ||
| 825 | |||
| 826 | #ifdef CONFIG_PPC_64K_PAGES | ||
| 827 | extern unsigned int *ht64_call_hpte_insert1; | ||
| 828 | extern unsigned int *ht64_call_hpte_insert2; | ||
| 829 | extern unsigned int *ht64_call_hpte_remove; | ||
| 830 | extern unsigned int *ht64_call_hpte_updatepp; | ||
| 831 | |||
| 832 | make_bl(ht64_call_hpte_insert1, ppc_md.hpte_insert); | ||
| 833 | make_bl(ht64_call_hpte_insert2, ppc_md.hpte_insert); | ||
| 834 | make_bl(ht64_call_hpte_remove, ppc_md.hpte_remove); | ||
| 835 | make_bl(ht64_call_hpte_updatepp, ppc_md.hpte_updatepp); | ||
| 836 | #endif /* CONFIG_PPC_64K_PAGES */ | ||
| 837 | |||
| 838 | make_bl(htab_call_hpte_insert1, ppc_md.hpte_insert); | ||
| 839 | make_bl(htab_call_hpte_insert2, ppc_md.hpte_insert); | ||
| 840 | make_bl(htab_call_hpte_remove, ppc_md.hpte_remove); | ||
| 841 | make_bl(htab_call_hpte_updatepp, ppc_md.hpte_updatepp); | ||
| 842 | } | ||
diff --git a/arch/powerpc/mm/mmu_context_64.c b/arch/powerpc/mm/mmu_context_64.c index 65d18dca266f..e2051efa09c5 100644 --- a/arch/powerpc/mm/mmu_context_64.c +++ b/arch/powerpc/mm/mmu_context_64.c | |||
| @@ -44,7 +44,9 @@ again: | |||
| 44 | return err; | 44 | return err; |
| 45 | 45 | ||
| 46 | if (index > MAX_CONTEXT) { | 46 | if (index > MAX_CONTEXT) { |
| 47 | spin_lock(&mmu_context_lock); | ||
| 47 | idr_remove(&mmu_context_idr, index); | 48 | idr_remove(&mmu_context_idr, index); |
| 49 | spin_unlock(&mmu_context_lock); | ||
| 48 | return -ENOMEM; | 50 | return -ENOMEM; |
| 49 | } | 51 | } |
| 50 | 52 | ||
diff --git a/arch/powerpc/platforms/86xx/Kconfig b/arch/powerpc/platforms/86xx/Kconfig index 3a87863d2876..d1ecc0f9ab58 100644 --- a/arch/powerpc/platforms/86xx/Kconfig +++ b/arch/powerpc/platforms/86xx/Kconfig | |||
| @@ -7,6 +7,7 @@ choice | |||
| 7 | 7 | ||
| 8 | config MPC8641_HPCN | 8 | config MPC8641_HPCN |
| 9 | bool "Freescale MPC8641 HPCN" | 9 | bool "Freescale MPC8641 HPCN" |
| 10 | select PPC_I8259 | ||
| 10 | help | 11 | help |
| 11 | This option enables support for the MPC8641 HPCN board. | 12 | This option enables support for the MPC8641 HPCN board. |
| 12 | 13 | ||
| @@ -28,9 +29,4 @@ config PPC_INDIRECT_PCI_BE | |||
| 28 | depends on PPC_86xx | 29 | depends on PPC_86xx |
| 29 | default y | 30 | default y |
| 30 | 31 | ||
| 31 | config PPC_STD_MMU | ||
| 32 | bool | ||
| 33 | depends on PPC_86xx | ||
| 34 | default y | ||
| 35 | |||
| 36 | endmenu | 32 | endmenu |
diff --git a/arch/powerpc/platforms/86xx/Makefile b/arch/powerpc/platforms/86xx/Makefile index 7be796c5d5c9..476a6eeee710 100644 --- a/arch/powerpc/platforms/86xx/Makefile +++ b/arch/powerpc/platforms/86xx/Makefile | |||
| @@ -2,9 +2,6 @@ | |||
| 2 | # Makefile for the PowerPC 86xx linux kernel. | 2 | # Makefile for the PowerPC 86xx linux kernel. |
| 3 | # | 3 | # |
| 4 | 4 | ||
| 5 | |||
| 6 | ifeq ($(CONFIG_PPC_86xx),y) | ||
| 7 | obj-$(CONFIG_SMP) += mpc86xx_smp.o | 5 | obj-$(CONFIG_SMP) += mpc86xx_smp.o |
| 8 | endif | ||
| 9 | obj-$(CONFIG_MPC8641_HPCN) += mpc86xx_hpcn.o | 6 | obj-$(CONFIG_MPC8641_HPCN) += mpc86xx_hpcn.o |
| 10 | obj-$(CONFIG_PCI) += pci.o mpc86xx_pcie.o | 7 | obj-$(CONFIG_PCI) += pci.o mpc86xx_pcie.o |
diff --git a/arch/powerpc/platforms/86xx/mpc8641_hpcn.h b/arch/powerpc/platforms/86xx/mpc8641_hpcn.h index 5042253758b7..5d2bcf78cef7 100644 --- a/arch/powerpc/platforms/86xx/mpc8641_hpcn.h +++ b/arch/powerpc/platforms/86xx/mpc8641_hpcn.h | |||
| @@ -14,7 +14,6 @@ | |||
| 14 | #ifndef __MPC8641_HPCN_H__ | 14 | #ifndef __MPC8641_HPCN_H__ |
| 15 | #define __MPC8641_HPCN_H__ | 15 | #define __MPC8641_HPCN_H__ |
| 16 | 16 | ||
| 17 | #include <linux/config.h> | ||
| 18 | #include <linux/init.h> | 17 | #include <linux/init.h> |
| 19 | 18 | ||
| 20 | /* PCI interrupt controller */ | 19 | /* PCI interrupt controller */ |
diff --git a/arch/powerpc/platforms/86xx/mpc86xx.h b/arch/powerpc/platforms/86xx/mpc86xx.h index e3c9e4f417d3..2834462590b8 100644 --- a/arch/powerpc/platforms/86xx/mpc86xx.h +++ b/arch/powerpc/platforms/86xx/mpc86xx.h | |||
| @@ -15,11 +15,13 @@ | |||
| 15 | * mpc86xx_* files. Mostly for use by mpc86xx_setup(). | 15 | * mpc86xx_* files. Mostly for use by mpc86xx_setup(). |
| 16 | */ | 16 | */ |
| 17 | 17 | ||
| 18 | extern int __init add_bridge(struct device_node *dev); | 18 | extern int add_bridge(struct device_node *dev); |
| 19 | 19 | ||
| 20 | extern void __init setup_indirect_pcie(struct pci_controller *hose, | 20 | extern int mpc86xx_exclude_device(u_char bus, u_char devfn); |
| 21 | |||
| 22 | extern void setup_indirect_pcie(struct pci_controller *hose, | ||
| 21 | u32 cfg_addr, u32 cfg_data); | 23 | u32 cfg_addr, u32 cfg_data); |
| 22 | extern void __init setup_indirect_pcie_nomap(struct pci_controller *hose, | 24 | extern void setup_indirect_pcie_nomap(struct pci_controller *hose, |
| 23 | void __iomem *cfg_addr, | 25 | void __iomem *cfg_addr, |
| 24 | void __iomem *cfg_data); | 26 | void __iomem *cfg_data); |
| 25 | 27 | ||
diff --git a/arch/powerpc/platforms/86xx/mpc86xx_hpcn.c b/arch/powerpc/platforms/86xx/mpc86xx_hpcn.c index 483c21df181e..ebae73eb0063 100644 --- a/arch/powerpc/platforms/86xx/mpc86xx_hpcn.c +++ b/arch/powerpc/platforms/86xx/mpc86xx_hpcn.c | |||
| @@ -12,7 +12,6 @@ | |||
| 12 | * option) any later version. | 12 | * option) any later version. |
| 13 | */ | 13 | */ |
| 14 | 14 | ||
| 15 | #include <linux/config.h> | ||
| 16 | #include <linux/stddef.h> | 15 | #include <linux/stddef.h> |
| 17 | #include <linux/kernel.h> | 16 | #include <linux/kernel.h> |
| 18 | #include <linux/pci.h> | 17 | #include <linux/pci.h> |
| @@ -36,6 +35,7 @@ | |||
| 36 | #include <sysdev/fsl_soc.h> | 35 | #include <sysdev/fsl_soc.h> |
| 37 | 36 | ||
| 38 | #include "mpc86xx.h" | 37 | #include "mpc86xx.h" |
| 38 | #include "mpc8641_hpcn.h" | ||
| 39 | 39 | ||
| 40 | #ifndef CONFIG_PCI | 40 | #ifndef CONFIG_PCI |
| 41 | unsigned long isa_io_base = 0; | 41 | unsigned long isa_io_base = 0; |
| @@ -186,17 +186,130 @@ mpc86xx_map_irq(struct pci_dev *dev, unsigned char idsel, unsigned char pin) | |||
| 186 | return PCI_IRQ_TABLE_LOOKUP + I8259_OFFSET; | 186 | return PCI_IRQ_TABLE_LOOKUP + I8259_OFFSET; |
| 187 | } | 187 | } |
| 188 | 188 | ||
| 189 | static void __devinit quirk_ali1575(struct pci_dev *dev) | ||
| 190 | { | ||
| 191 | unsigned short temp; | ||
| 192 | |||
| 193 | /* | ||
| 194 | * ALI1575 interrupts route table setup: | ||
| 195 | * | ||
| 196 | * IRQ pin IRQ# | ||
| 197 | * PIRQA ---- 3 | ||
| 198 | * PIRQB ---- 4 | ||
| 199 | * PIRQC ---- 5 | ||
| 200 | * PIRQD ---- 6 | ||
| 201 | * PIRQE ---- 9 | ||
| 202 | * PIRQF ---- 10 | ||
| 203 | * PIRQG ---- 11 | ||
| 204 | * PIRQH ---- 12 | ||
| 205 | * | ||
| 206 | * interrupts for PCI slot0 -- PIRQA / PIRQB / PIRQC / PIRQD | ||
| 207 | * PCI slot1 -- PIRQB / PIRQC / PIRQD / PIRQA | ||
| 208 | */ | ||
| 209 | pci_write_config_dword(dev, 0x48, 0xb9317542); | ||
| 210 | |||
| 211 | /* USB 1.1 OHCI controller 1, interrupt: PIRQE */ | ||
| 212 | pci_write_config_byte(dev, 0x86, 0x0c); | ||
| 213 | |||
| 214 | /* USB 1.1 OHCI controller 2, interrupt: PIRQF */ | ||
| 215 | pci_write_config_byte(dev, 0x87, 0x0d); | ||
| 216 | |||
| 217 | /* USB 1.1 OHCI controller 3, interrupt: PIRQH */ | ||
| 218 | pci_write_config_byte(dev, 0x88, 0x0f); | ||
| 219 | |||
| 220 | /* USB 2.0 controller, interrupt: PIRQ7 */ | ||
| 221 | pci_write_config_byte(dev, 0x74, 0x06); | ||
| 222 | |||
| 223 | /* Audio controller, interrupt: PIRQE */ | ||
| 224 | pci_write_config_byte(dev, 0x8a, 0x0c); | ||
| 225 | |||
| 226 | /* Modem controller, interrupt: PIRQF */ | ||
| 227 | pci_write_config_byte(dev, 0x8b, 0x0d); | ||
| 228 | |||
| 229 | /* HD audio controller, interrupt: PIRQG */ | ||
| 230 | pci_write_config_byte(dev, 0x8c, 0x0e); | ||
| 231 | |||
| 232 | /* Serial ATA interrupt: PIRQD */ | ||
| 233 | pci_write_config_byte(dev, 0x8d, 0x0b); | ||
| 234 | |||
| 235 | /* SMB interrupt: PIRQH */ | ||
| 236 | pci_write_config_byte(dev, 0x8e, 0x0f); | ||
| 237 | |||
| 238 | /* PMU ACPI SCI interrupt: PIRQH */ | ||
| 239 | pci_write_config_byte(dev, 0x8f, 0x0f); | ||
| 240 | |||
| 241 | /* Primary PATA IDE IRQ: 14 | ||
| 242 | * Secondary PATA IDE IRQ: 15 | ||
| 243 | */ | ||
| 244 | pci_write_config_byte(dev, 0x44, 0x3d); | ||
| 245 | pci_write_config_byte(dev, 0x75, 0x0f); | ||
| 246 | |||
| 247 | /* Set IRQ14 and IRQ15 to legacy IRQs */ | ||
| 248 | pci_read_config_word(dev, 0x46, &temp); | ||
| 249 | temp |= 0xc000; | ||
| 250 | pci_write_config_word(dev, 0x46, temp); | ||
| 251 | |||
| 252 | /* Set i8259 interrupt trigger | ||
| 253 | * IRQ 3: Level | ||
| 254 | * IRQ 4: Level | ||
| 255 | * IRQ 5: Level | ||
| 256 | * IRQ 6: Level | ||
| 257 | * IRQ 7: Level | ||
| 258 | * IRQ 9: Level | ||
| 259 | * IRQ 10: Level | ||
| 260 | * IRQ 11: Level | ||
| 261 | * IRQ 12: Level | ||
| 262 | * IRQ 14: Edge | ||
| 263 | * IRQ 15: Edge | ||
| 264 | */ | ||
| 265 | outb(0xfa, 0x4d0); | ||
| 266 | outb(0x1e, 0x4d1); | ||
| 267 | } | ||
| 189 | 268 | ||
| 190 | int | 269 | static void __devinit quirk_uli5288(struct pci_dev *dev) |
| 191 | mpc86xx_exclude_device(u_char bus, u_char devfn) | ||
| 192 | { | 270 | { |
| 193 | #if !defined(CONFIG_PCI) | 271 | unsigned char c; |
| 194 | if (bus == 0 && PCI_SLOT(devfn) == 0) | 272 | |
| 195 | return PCIBIOS_DEVICE_NOT_FOUND; | 273 | pci_read_config_byte(dev,0x83,&c); |
| 196 | #endif | 274 | c |= 0x80; |
| 275 | pci_write_config_byte(dev, 0x83, c); | ||
| 276 | |||
| 277 | pci_write_config_byte(dev, 0x09, 0x01); | ||
| 278 | pci_write_config_byte(dev, 0x0a, 0x06); | ||
| 279 | |||
| 280 | pci_read_config_byte(dev,0x83,&c); | ||
| 281 | c &= 0x7f; | ||
| 282 | pci_write_config_byte(dev, 0x83, c); | ||
| 197 | 283 | ||
| 198 | return PCIBIOS_SUCCESSFUL; | 284 | pci_read_config_byte(dev,0x84,&c); |
| 285 | c |= 0x01; | ||
| 286 | pci_write_config_byte(dev, 0x84, c); | ||
| 199 | } | 287 | } |
| 288 | |||
| 289 | static void __devinit quirk_uli5229(struct pci_dev *dev) | ||
| 290 | { | ||
| 291 | unsigned short temp; | ||
| 292 | pci_write_config_word(dev, 0x04, 0x0405); | ||
| 293 | pci_read_config_word(dev, 0x4a, &temp); | ||
| 294 | temp |= 0x1000; | ||
| 295 | pci_write_config_word(dev, 0x4a, temp); | ||
| 296 | } | ||
| 297 | |||
| 298 | static void __devinit early_uli5249(struct pci_dev *dev) | ||
| 299 | { | ||
| 300 | unsigned char temp; | ||
| 301 | pci_write_config_word(dev, 0x04, 0x0007); | ||
| 302 | pci_read_config_byte(dev, 0x7c, &temp); | ||
| 303 | pci_write_config_byte(dev, 0x7c, 0x80); | ||
| 304 | pci_write_config_byte(dev, 0x09, 0x01); | ||
| 305 | pci_write_config_byte(dev, 0x7c, temp); | ||
| 306 | dev->class |= 0x1; | ||
| 307 | } | ||
| 308 | |||
| 309 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x1575, quirk_ali1575); | ||
| 310 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5288, quirk_uli5288); | ||
| 311 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5229, quirk_uli5229); | ||
| 312 | DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_AL, 0x5249, early_uli5249); | ||
| 200 | #endif /* CONFIG_PCI */ | 313 | #endif /* CONFIG_PCI */ |
| 201 | 314 | ||
| 202 | 315 | ||
diff --git a/arch/powerpc/platforms/86xx/mpc86xx_smp.c b/arch/powerpc/platforms/86xx/mpc86xx_smp.c index 944ec4b71416..bb7fb41933ad 100644 --- a/arch/powerpc/platforms/86xx/mpc86xx_smp.c +++ b/arch/powerpc/platforms/86xx/mpc86xx_smp.c | |||
| @@ -10,7 +10,6 @@ | |||
| 10 | * option) any later version. | 10 | * option) any later version. |
| 11 | */ | 11 | */ |
| 12 | 12 | ||
| 13 | #include <linux/config.h> | ||
| 14 | #include <linux/stddef.h> | 13 | #include <linux/stddef.h> |
| 15 | #include <linux/kernel.h> | 14 | #include <linux/kernel.h> |
| 16 | #include <linux/init.h> | 15 | #include <linux/init.h> |
| @@ -34,8 +33,8 @@ extern unsigned long __secondary_hold_acknowledge; | |||
| 34 | static void __init | 33 | static void __init |
| 35 | smp_86xx_release_core(int nr) | 34 | smp_86xx_release_core(int nr) |
| 36 | { | 35 | { |
| 37 | void *mcm_vaddr; | 36 | __be32 __iomem *mcm_vaddr; |
| 38 | unsigned long vaddr, pcr; | 37 | unsigned long pcr; |
| 39 | 38 | ||
| 40 | if (nr < 0 || nr >= NR_CPUS) | 39 | if (nr < 0 || nr >= NR_CPUS) |
| 41 | return; | 40 | return; |
| @@ -45,10 +44,9 @@ smp_86xx_release_core(int nr) | |||
| 45 | */ | 44 | */ |
| 46 | mcm_vaddr = ioremap(get_immrbase() + MPC86xx_MCM_OFFSET, | 45 | mcm_vaddr = ioremap(get_immrbase() + MPC86xx_MCM_OFFSET, |
| 47 | MPC86xx_MCM_SIZE); | 46 | MPC86xx_MCM_SIZE); |
| 48 | vaddr = (unsigned long)mcm_vaddr + MCM_PORT_CONFIG_OFFSET; | 47 | pcr = in_be32(mcm_vaddr + (MCM_PORT_CONFIG_OFFSET >> 2)); |
| 49 | pcr = in_be32((volatile unsigned *)vaddr); | ||
| 50 | pcr |= 1 << (nr + 24); | 48 | pcr |= 1 << (nr + 24); |
| 51 | out_be32((volatile unsigned *)vaddr, pcr); | 49 | out_be32(mcm_vaddr + (MCM_PORT_CONFIG_OFFSET >> 2), pcr); |
| 52 | } | 50 | } |
| 53 | 51 | ||
| 54 | 52 | ||
diff --git a/arch/powerpc/platforms/86xx/pci.c b/arch/powerpc/platforms/86xx/pci.c index 5180df7c75bc..bc5139043112 100644 --- a/arch/powerpc/platforms/86xx/pci.c +++ b/arch/powerpc/platforms/86xx/pci.c | |||
| @@ -12,7 +12,6 @@ | |||
| 12 | * option) any later version. | 12 | * option) any later version. |
| 13 | */ | 13 | */ |
| 14 | 14 | ||
| 15 | #include <linux/config.h> | ||
| 16 | #include <linux/types.h> | 15 | #include <linux/types.h> |
| 17 | #include <linux/module.h> | 16 | #include <linux/module.h> |
| 18 | #include <linux/init.h> | 17 | #include <linux/init.h> |
| @@ -122,15 +121,12 @@ static void __init setup_pcie_atmu(struct pci_controller *hose, struct resource | |||
| 122 | static void __init | 121 | static void __init |
| 123 | mpc86xx_setup_pcie(struct pci_controller *hose, u32 pcie_offset, u32 pcie_size) | 122 | mpc86xx_setup_pcie(struct pci_controller *hose, u32 pcie_offset, u32 pcie_size) |
| 124 | { | 123 | { |
| 125 | volatile struct ccsr_pex *pcie; | ||
| 126 | u16 cmd; | 124 | u16 cmd; |
| 127 | unsigned int temps; | 125 | unsigned int temps; |
| 128 | 126 | ||
| 129 | DBG("PCIE host controller register offset 0x%08x, size 0x%08x.\n", | 127 | DBG("PCIE host controller register offset 0x%08x, size 0x%08x.\n", |
| 130 | pcie_offset, pcie_size); | 128 | pcie_offset, pcie_size); |
| 131 | 129 | ||
| 132 | pcie = ioremap(pcie_offset, pcie_size); | ||
| 133 | |||
| 134 | early_read_config_word(hose, 0, 0, PCI_COMMAND, &cmd); | 130 | early_read_config_word(hose, 0, 0, PCI_COMMAND, &cmd); |
| 135 | cmd |= PCI_COMMAND_SERR | PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY | 131 | cmd |= PCI_COMMAND_SERR | PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY |
| 136 | | PCI_COMMAND_IO; | 132 | | PCI_COMMAND_IO; |
| @@ -144,6 +140,14 @@ mpc86xx_setup_pcie(struct pci_controller *hose, u32 pcie_offset, u32 pcie_size) | |||
| 144 | early_write_config_dword(hose, 0, 0, PCI_PRIMARY_BUS, temps); | 140 | early_write_config_dword(hose, 0, 0, PCI_PRIMARY_BUS, temps); |
| 145 | } | 141 | } |
| 146 | 142 | ||
| 143 | int mpc86xx_exclude_device(u_char bus, u_char devfn) | ||
| 144 | { | ||
| 145 | if (bus == 0 && PCI_SLOT(devfn) == 0) | ||
| 146 | return PCIBIOS_DEVICE_NOT_FOUND; | ||
| 147 | |||
| 148 | return PCIBIOS_SUCCESSFUL; | ||
| 149 | } | ||
| 150 | |||
| 147 | int __init add_bridge(struct device_node *dev) | 151 | int __init add_bridge(struct device_node *dev) |
| 148 | { | 152 | { |
| 149 | int len; | 153 | int len; |
| @@ -198,128 +202,3 @@ int __init add_bridge(struct device_node *dev) | |||
| 198 | 202 | ||
| 199 | return 0; | 203 | return 0; |
| 200 | } | 204 | } |
| 201 | |||
| 202 | static void __devinit quirk_ali1575(struct pci_dev *dev) | ||
| 203 | { | ||
| 204 | unsigned short temp; | ||
| 205 | |||
| 206 | /* | ||
| 207 | * ALI1575 interrupts route table setup: | ||
| 208 | * | ||
| 209 | * IRQ pin IRQ# | ||
| 210 | * PIRQA ---- 3 | ||
| 211 | * PIRQB ---- 4 | ||
| 212 | * PIRQC ---- 5 | ||
| 213 | * PIRQD ---- 6 | ||
| 214 | * PIRQE ---- 9 | ||
| 215 | * PIRQF ---- 10 | ||
| 216 | * PIRQG ---- 11 | ||
| 217 | * PIRQH ---- 12 | ||
| 218 | * | ||
| 219 | * interrupts for PCI slot0 -- PIRQA / PIRQB / PIRQC / PIRQD | ||
| 220 | * PCI slot1 -- PIRQB / PIRQC / PIRQD / PIRQA | ||
| 221 | */ | ||
| 222 | pci_write_config_dword(dev, 0x48, 0xb9317542); | ||
| 223 | |||
| 224 | /* USB 1.1 OHCI controller 1, interrupt: PIRQE */ | ||
| 225 | pci_write_config_byte(dev, 0x86, 0x0c); | ||
| 226 | |||
| 227 | /* USB 1.1 OHCI controller 2, interrupt: PIRQF */ | ||
| 228 | pci_write_config_byte(dev, 0x87, 0x0d); | ||
| 229 | |||
| 230 | /* USB 1.1 OHCI controller 3, interrupt: PIRQH */ | ||
| 231 | pci_write_config_byte(dev, 0x88, 0x0f); | ||
| 232 | |||
| 233 | /* USB 2.0 controller, interrupt: PIRQ7 */ | ||
| 234 | pci_write_config_byte(dev, 0x74, 0x06); | ||
| 235 | |||
| 236 | /* Audio controller, interrupt: PIRQE */ | ||
| 237 | pci_write_config_byte(dev, 0x8a, 0x0c); | ||
| 238 | |||
| 239 | /* Modem controller, interrupt: PIRQF */ | ||
| 240 | pci_write_config_byte(dev, 0x8b, 0x0d); | ||
| 241 | |||
| 242 | /* HD audio controller, interrupt: PIRQG */ | ||
| 243 | pci_write_config_byte(dev, 0x8c, 0x0e); | ||
| 244 | |||
| 245 | /* Serial ATA interrupt: PIRQD */ | ||
| 246 | pci_write_config_byte(dev, 0x8d, 0x0b); | ||
| 247 | |||
| 248 | /* SMB interrupt: PIRQH */ | ||
| 249 | pci_write_config_byte(dev, 0x8e, 0x0f); | ||
| 250 | |||
| 251 | /* PMU ACPI SCI interrupt: PIRQH */ | ||
| 252 | pci_write_config_byte(dev, 0x8f, 0x0f); | ||
| 253 | |||
| 254 | /* Primary PATA IDE IRQ: 14 | ||
| 255 | * Secondary PATA IDE IRQ: 15 | ||
| 256 | */ | ||
| 257 | pci_write_config_byte(dev, 0x44, 0x3d); | ||
| 258 | pci_write_config_byte(dev, 0x75, 0x0f); | ||
| 259 | |||
| 260 | /* Set IRQ14 and IRQ15 to legacy IRQs */ | ||
| 261 | pci_read_config_word(dev, 0x46, &temp); | ||
| 262 | temp |= 0xc000; | ||
| 263 | pci_write_config_word(dev, 0x46, temp); | ||
| 264 | |||
| 265 | /* Set i8259 interrupt trigger | ||
| 266 | * IRQ 3: Level | ||
| 267 | * IRQ 4: Level | ||
| 268 | * IRQ 5: Level | ||
| 269 | * IRQ 6: Level | ||
| 270 | * IRQ 7: Level | ||
| 271 | * IRQ 9: Level | ||
| 272 | * IRQ 10: Level | ||
| 273 | * IRQ 11: Level | ||
| 274 | * IRQ 12: Level | ||
| 275 | * IRQ 14: Edge | ||
| 276 | * IRQ 15: Edge | ||
| 277 | */ | ||
| 278 | outb(0xfa, 0x4d0); | ||
| 279 | outb(0x1e, 0x4d1); | ||
| 280 | } | ||
| 281 | |||
| 282 | static void __devinit quirk_uli5288(struct pci_dev *dev) | ||
| 283 | { | ||
| 284 | unsigned char c; | ||
| 285 | |||
| 286 | pci_read_config_byte(dev,0x83,&c); | ||
| 287 | c |= 0x80; | ||
| 288 | pci_write_config_byte(dev, 0x83, c); | ||
| 289 | |||
| 290 | pci_write_config_byte(dev, 0x09, 0x01); | ||
| 291 | pci_write_config_byte(dev, 0x0a, 0x06); | ||
| 292 | |||
| 293 | pci_read_config_byte(dev,0x83,&c); | ||
| 294 | c &= 0x7f; | ||
| 295 | pci_write_config_byte(dev, 0x83, c); | ||
| 296 | |||
| 297 | pci_read_config_byte(dev,0x84,&c); | ||
| 298 | c |= 0x01; | ||
| 299 | pci_write_config_byte(dev, 0x84, c); | ||
| 300 | } | ||
| 301 | |||
| 302 | static void __devinit quirk_uli5229(struct pci_dev *dev) | ||
| 303 | { | ||
| 304 | unsigned short temp; | ||
| 305 | pci_write_config_word(dev, 0x04, 0x0405); | ||
| 306 | pci_read_config_word(dev, 0x4a, &temp); | ||
| 307 | temp |= 0x1000; | ||
| 308 | pci_write_config_word(dev, 0x4a, temp); | ||
| 309 | } | ||
| 310 | |||
| 311 | static void __devinit early_uli5249(struct pci_dev *dev) | ||
| 312 | { | ||
| 313 | unsigned char temp; | ||
| 314 | pci_write_config_word(dev, 0x04, 0x0007); | ||
| 315 | pci_read_config_byte(dev, 0x7c, &temp); | ||
| 316 | pci_write_config_byte(dev, 0x7c, 0x80); | ||
| 317 | pci_write_config_byte(dev, 0x09, 0x01); | ||
| 318 | pci_write_config_byte(dev, 0x7c, temp); | ||
| 319 | dev->class |= 0x1; | ||
| 320 | } | ||
| 321 | |||
| 322 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x1575, quirk_ali1575); | ||
| 323 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5288, quirk_uli5288); | ||
| 324 | DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5229, quirk_uli5229); | ||
| 325 | DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_AL, 0x5249, early_uli5249); | ||
diff --git a/arch/powerpc/platforms/Makefile b/arch/powerpc/platforms/Makefile index 292863694562..5cf46dc57895 100644 --- a/arch/powerpc/platforms/Makefile +++ b/arch/powerpc/platforms/Makefile | |||
| @@ -14,3 +14,4 @@ obj-$(CONFIG_PPC_PSERIES) += pseries/ | |||
| 14 | obj-$(CONFIG_PPC_ISERIES) += iseries/ | 14 | obj-$(CONFIG_PPC_ISERIES) += iseries/ |
| 15 | obj-$(CONFIG_PPC_MAPLE) += maple/ | 15 | obj-$(CONFIG_PPC_MAPLE) += maple/ |
| 16 | obj-$(CONFIG_PPC_CELL) += cell/ | 16 | obj-$(CONFIG_PPC_CELL) += cell/ |
| 17 | obj-$(CONFIG_EMBEDDED6xx) += embedded6xx/ | ||
diff --git a/arch/powerpc/platforms/cell/Kconfig b/arch/powerpc/platforms/cell/Kconfig index 352bbbacde9a..0c8c7b6ab897 100644 --- a/arch/powerpc/platforms/cell/Kconfig +++ b/arch/powerpc/platforms/cell/Kconfig | |||
| @@ -6,6 +6,7 @@ config SPU_FS | |||
| 6 | default m | 6 | default m |
| 7 | depends on PPC_CELL | 7 | depends on PPC_CELL |
| 8 | select SPU_BASE | 8 | select SPU_BASE |
| 9 | select MEMORY_HOTPLUG | ||
| 9 | help | 10 | help |
| 10 | The SPU file system is used to access Synergistic Processing | 11 | The SPU file system is used to access Synergistic Processing |
| 11 | Units on machines implementing the Broadband Processor | 12 | Units on machines implementing the Broadband Processor |
| @@ -18,7 +19,6 @@ config SPU_BASE | |||
| 18 | config SPUFS_MMAP | 19 | config SPUFS_MMAP |
| 19 | bool | 20 | bool |
| 20 | depends on SPU_FS && SPARSEMEM | 21 | depends on SPU_FS && SPARSEMEM |
| 21 | select MEMORY_HOTPLUG | ||
| 22 | default y | 22 | default y |
| 23 | 23 | ||
| 24 | config CBE_RAS | 24 | config CBE_RAS |
diff --git a/arch/powerpc/platforms/cell/setup.c b/arch/powerpc/platforms/cell/setup.c index 3d1831d331e5..00d112f92272 100644 --- a/arch/powerpc/platforms/cell/setup.c +++ b/arch/powerpc/platforms/cell/setup.c | |||
| @@ -125,8 +125,6 @@ static void __init cell_init_early(void) | |||
| 125 | { | 125 | { |
| 126 | DBG(" -> cell_init_early()\n"); | 126 | DBG(" -> cell_init_early()\n"); |
| 127 | 127 | ||
| 128 | hpte_init_native(); | ||
| 129 | |||
| 130 | cell_init_iommu(); | 128 | cell_init_iommu(); |
| 131 | 129 | ||
| 132 | ppc64_interrupt_controller = IC_CELL_PIC; | 130 | ppc64_interrupt_controller = IC_CELL_PIC; |
| @@ -139,11 +137,17 @@ static int __init cell_probe(void) | |||
| 139 | { | 137 | { |
| 140 | unsigned long root = of_get_flat_dt_root(); | 138 | unsigned long root = of_get_flat_dt_root(); |
| 141 | 139 | ||
| 142 | if (of_flat_dt_is_compatible(root, "IBM,CBEA") || | 140 | if (!of_flat_dt_is_compatible(root, "IBM,CBEA") && |
| 143 | of_flat_dt_is_compatible(root, "IBM,CPBW-1.0")) | 141 | !of_flat_dt_is_compatible(root, "IBM,CPBW-1.0")) |
| 144 | return 1; | 142 | return 0; |
| 143 | |||
| 144 | #ifdef CONFIG_UDBG_RTAS_CONSOLE | ||
| 145 | udbg_init_rtas_console(); | ||
| 146 | #endif | ||
| 147 | |||
| 148 | hpte_init_native(); | ||
| 145 | 149 | ||
| 146 | return 0; | 150 | return 1; |
| 147 | } | 151 | } |
| 148 | 152 | ||
| 149 | /* | 153 | /* |
diff --git a/arch/powerpc/platforms/cell/spu_base.c b/arch/powerpc/platforms/cell/spu_base.c index db82f503ba2c..b306723abb87 100644 --- a/arch/powerpc/platforms/cell/spu_base.c +++ b/arch/powerpc/platforms/cell/spu_base.c | |||
| @@ -168,12 +168,12 @@ spu_irq_class_0_bottom(struct spu *spu) | |||
| 168 | 168 | ||
| 169 | stat &= mask; | 169 | stat &= mask; |
| 170 | 170 | ||
| 171 | if (stat & 1) /* invalid MFC DMA */ | 171 | if (stat & 1) /* invalid DMA alignment */ |
| 172 | __spu_trap_invalid_dma(spu); | ||
| 173 | |||
| 174 | if (stat & 2) /* invalid DMA alignment */ | ||
| 175 | __spu_trap_dma_align(spu); | 172 | __spu_trap_dma_align(spu); |
| 176 | 173 | ||
| 174 | if (stat & 2) /* invalid MFC DMA */ | ||
| 175 | __spu_trap_invalid_dma(spu); | ||
| 176 | |||
| 177 | if (stat & 4) /* error on SPU */ | 177 | if (stat & 4) /* error on SPU */ |
| 178 | __spu_trap_error(spu); | 178 | __spu_trap_error(spu); |
| 179 | 179 | ||
diff --git a/arch/powerpc/platforms/cell/spufs/file.c b/arch/powerpc/platforms/cell/spufs/file.c index 7854a380dce2..58e794f9da1b 100644 --- a/arch/powerpc/platforms/cell/spufs/file.c +++ b/arch/powerpc/platforms/cell/spufs/file.c | |||
| @@ -204,7 +204,7 @@ static int spufs_cntl_mmap(struct file *file, struct vm_area_struct *vma) | |||
| 204 | 204 | ||
| 205 | vma->vm_flags |= VM_RESERVED; | 205 | vma->vm_flags |= VM_RESERVED; |
| 206 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) | 206 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) |
| 207 | | _PAGE_NO_CACHE); | 207 | | _PAGE_NO_CACHE | _PAGE_GUARDED); |
| 208 | 208 | ||
| 209 | vma->vm_ops = &spufs_cntl_mmap_vmops; | 209 | vma->vm_ops = &spufs_cntl_mmap_vmops; |
| 210 | return 0; | 210 | return 0; |
| @@ -675,7 +675,7 @@ static int spufs_signal1_mmap(struct file *file, struct vm_area_struct *vma) | |||
| 675 | 675 | ||
| 676 | vma->vm_flags |= VM_RESERVED; | 676 | vma->vm_flags |= VM_RESERVED; |
| 677 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) | 677 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) |
| 678 | | _PAGE_NO_CACHE); | 678 | | _PAGE_NO_CACHE | _PAGE_GUARDED); |
| 679 | 679 | ||
| 680 | vma->vm_ops = &spufs_signal1_mmap_vmops; | 680 | vma->vm_ops = &spufs_signal1_mmap_vmops; |
| 681 | return 0; | 681 | return 0; |
| @@ -762,7 +762,7 @@ static int spufs_signal2_mmap(struct file *file, struct vm_area_struct *vma) | |||
| 762 | /* FIXME: */ | 762 | /* FIXME: */ |
| 763 | vma->vm_flags |= VM_RESERVED; | 763 | vma->vm_flags |= VM_RESERVED; |
| 764 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) | 764 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) |
| 765 | | _PAGE_NO_CACHE); | 765 | | _PAGE_NO_CACHE | _PAGE_GUARDED); |
| 766 | 766 | ||
| 767 | vma->vm_ops = &spufs_signal2_mmap_vmops; | 767 | vma->vm_ops = &spufs_signal2_mmap_vmops; |
| 768 | return 0; | 768 | return 0; |
| @@ -850,7 +850,7 @@ static int spufs_mss_mmap(struct file *file, struct vm_area_struct *vma) | |||
| 850 | 850 | ||
| 851 | vma->vm_flags |= VM_RESERVED; | 851 | vma->vm_flags |= VM_RESERVED; |
| 852 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) | 852 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) |
| 853 | | _PAGE_NO_CACHE); | 853 | | _PAGE_NO_CACHE | _PAGE_GUARDED); |
| 854 | 854 | ||
| 855 | vma->vm_ops = &spufs_mss_mmap_vmops; | 855 | vma->vm_ops = &spufs_mss_mmap_vmops; |
| 856 | return 0; | 856 | return 0; |
| @@ -899,7 +899,7 @@ static int spufs_mfc_mmap(struct file *file, struct vm_area_struct *vma) | |||
| 899 | 899 | ||
| 900 | vma->vm_flags |= VM_RESERVED; | 900 | vma->vm_flags |= VM_RESERVED; |
| 901 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) | 901 | vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot) |
| 902 | | _PAGE_NO_CACHE); | 902 | | _PAGE_NO_CACHE | _PAGE_GUARDED); |
| 903 | 903 | ||
| 904 | vma->vm_ops = &spufs_mfc_mmap_vmops; | 904 | vma->vm_ops = &spufs_mfc_mmap_vmops; |
| 905 | return 0; | 905 | return 0; |
diff --git a/arch/powerpc/platforms/cell/spufs/switch.c b/arch/powerpc/platforms/cell/spufs/switch.c index a656d810a44a..c7fea2cca534 100644 --- a/arch/powerpc/platforms/cell/spufs/switch.c +++ b/arch/powerpc/platforms/cell/spufs/switch.c | |||
| @@ -464,7 +464,8 @@ static inline void wait_purge_complete(struct spu_state *csa, struct spu *spu) | |||
| 464 | * Poll MFC_CNTL[Ps] until value '11' is read | 464 | * Poll MFC_CNTL[Ps] until value '11' is read |
| 465 | * (purge complete). | 465 | * (purge complete). |
| 466 | */ | 466 | */ |
| 467 | POLL_WHILE_FALSE(in_be64(&priv2->mfc_control_RW) & | 467 | POLL_WHILE_FALSE((in_be64(&priv2->mfc_control_RW) & |
| 468 | MFC_CNTL_PURGE_DMA_STATUS_MASK) == | ||
| 468 | MFC_CNTL_PURGE_DMA_COMPLETE); | 469 | MFC_CNTL_PURGE_DMA_COMPLETE); |
| 469 | } | 470 | } |
| 470 | 471 | ||
| @@ -1028,7 +1029,8 @@ static inline void wait_suspend_mfc_complete(struct spu_state *csa, | |||
| 1028 | * Restore, Step 47. | 1029 | * Restore, Step 47. |
| 1029 | * Poll MFC_CNTL[Ss] until 11 is returned. | 1030 | * Poll MFC_CNTL[Ss] until 11 is returned. |
| 1030 | */ | 1031 | */ |
| 1031 | POLL_WHILE_FALSE(in_be64(&priv2->mfc_control_RW) & | 1032 | POLL_WHILE_FALSE((in_be64(&priv2->mfc_control_RW) & |
| 1033 | MFC_CNTL_SUSPEND_DMA_STATUS_MASK) == | ||
| 1032 | MFC_CNTL_SUSPEND_COMPLETE); | 1034 | MFC_CNTL_SUSPEND_COMPLETE); |
| 1033 | } | 1035 | } |
| 1034 | 1036 | ||
diff --git a/arch/powerpc/platforms/embedded6xx/Kconfig b/arch/powerpc/platforms/embedded6xx/Kconfig index 4fdbc9ae876b..ba07a9a7c039 100644 --- a/arch/powerpc/platforms/embedded6xx/Kconfig +++ b/arch/powerpc/platforms/embedded6xx/Kconfig | |||
| @@ -74,6 +74,16 @@ config SANDPOINT | |||
| 74 | Select SANDPOINT if configuring for a Motorola Sandpoint X3 | 74 | Select SANDPOINT if configuring for a Motorola Sandpoint X3 |
| 75 | (any flavor). | 75 | (any flavor). |
| 76 | 76 | ||
| 77 | config MPC7448HPC2 | ||
| 78 | bool "Freescale MPC7448HPC2(Taiga)" | ||
| 79 | select TSI108_BRIDGE | ||
| 80 | select DEFAULT_UIMAGE | ||
| 81 | select PPC_UDBG_16550 | ||
| 82 | select MPIC | ||
| 83 | help | ||
| 84 | Select MPC7448HPC2 if configuring for Freescale MPC7448HPC2 (Taiga) | ||
| 85 | platform | ||
| 86 | |||
| 77 | config RADSTONE_PPC7D | 87 | config RADSTONE_PPC7D |
| 78 | bool "Radstone Technology PPC7D board" | 88 | bool "Radstone Technology PPC7D board" |
| 79 | select PPC_I8259 | 89 | select PPC_I8259 |
| @@ -221,6 +231,11 @@ config MV64X60 | |||
| 221 | select PPC_INDIRECT_PCI | 231 | select PPC_INDIRECT_PCI |
| 222 | default y | 232 | default y |
| 223 | 233 | ||
| 234 | config TSI108_BRIDGE | ||
| 235 | bool | ||
| 236 | depends on MPC7448HPC2 | ||
| 237 | default y | ||
| 238 | |||
| 224 | menu "Set bridge options" | 239 | menu "Set bridge options" |
| 225 | depends on MV64X60 | 240 | depends on MV64X60 |
| 226 | 241 | ||
diff --git a/arch/powerpc/platforms/embedded6xx/Makefile b/arch/powerpc/platforms/embedded6xx/Makefile new file mode 100644 index 000000000000..fa499fe59291 --- /dev/null +++ b/arch/powerpc/platforms/embedded6xx/Makefile | |||
| @@ -0,0 +1,4 @@ | |||
| 1 | # | ||
| 2 | # Makefile for the 6xx/7xx/7xxxx linux kernel. | ||
| 3 | # | ||
| 4 | obj-$(CONFIG_MPC7448HPC2) += mpc7448_hpc2.o | ||
diff --git a/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c new file mode 100644 index 000000000000..d7a4fc7ca238 --- /dev/null +++ b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c | |||
| @@ -0,0 +1,335 @@ | |||
| 1 | /* | ||
| 2 | * mpc7448_hpc2.c | ||
| 3 | * | ||
| 4 | * Board setup routines for the Freescale Taiga platform | ||
| 5 | * | ||
| 6 | * Author: Jacob Pan | ||
| 7 | * jacob.pan@freescale.com | ||
| 8 | * Author: Xianghua Xiao | ||
| 9 | * x.xiao@freescale.com | ||
| 10 | * Maintainer: Roy Zang <tie-fei.zang@freescale.com> | ||
| 11 | * Add Flat Device Tree support fot mpc7448hpc2 board | ||
| 12 | * | ||
| 13 | * Copyright 2004-2006 Freescale Semiconductor, Inc. | ||
| 14 | * | ||
| 15 | * This file is licensed under | ||
| 16 | * the terms of the GNU General Public License version 2. This program | ||
| 17 | * is licensed "as is" without any warranty of any kind, whether express | ||
| 18 | * or implied. | ||
| 19 | */ | ||
| 20 | |||
| 21 | #include <linux/config.h> | ||
| 22 | #include <linux/stddef.h> | ||
| 23 | #include <linux/kernel.h> | ||
| 24 | #include <linux/pci.h> | ||
| 25 | #include <linux/kdev_t.h> | ||
| 26 | #include <linux/console.h> | ||
| 27 | #include <linux/delay.h> | ||
| 28 | #include <linux/irq.h> | ||
| 29 | #include <linux/ide.h> | ||
| 30 | #include <linux/seq_file.h> | ||
| 31 | #include <linux/root_dev.h> | ||
| 32 | #include <linux/serial.h> | ||
| 33 | #include <linux/tty.h> | ||
| 34 | #include <linux/serial_core.h> | ||
| 35 | |||
| 36 | #include <asm/system.h> | ||
| 37 | #include <asm/time.h> | ||
| 38 | #include <asm/machdep.h> | ||
| 39 | #include <asm/prom.h> | ||
| 40 | #include <asm/udbg.h> | ||
| 41 | #include <asm/tsi108.h> | ||
| 42 | #include <asm/pci-bridge.h> | ||
| 43 | #include <asm/reg.h> | ||
| 44 | #include <mm/mmu_decl.h> | ||
| 45 | #include "mpc7448_hpc2.h" | ||
| 46 | #include <asm/tsi108_irq.h> | ||
| 47 | #include <asm/mpic.h> | ||
| 48 | |||
| 49 | #undef DEBUG | ||
| 50 | #ifdef DEBUG | ||
| 51 | #define DBG(fmt...) do { printk(fmt); } while(0) | ||
| 52 | #else | ||
| 53 | #define DBG(fmt...) do { } while(0) | ||
| 54 | #endif | ||
| 55 | |||
| 56 | #ifndef CONFIG_PCI | ||
| 57 | isa_io_base = MPC7448_HPC2_ISA_IO_BASE; | ||
| 58 | isa_mem_base = MPC7448_HPC2_ISA_MEM_BASE; | ||
| 59 | pci_dram_offset = MPC7448_HPC2_PCI_MEM_OFFSET; | ||
| 60 | #endif | ||
| 61 | |||
| 62 | extern int tsi108_setup_pci(struct device_node *dev); | ||
| 63 | extern void _nmask_and_or_msr(unsigned long nmask, unsigned long or_val); | ||
| 64 | extern void tsi108_pci_int_init(void); | ||
| 65 | extern int tsi108_irq_cascade(struct pt_regs *regs, void *unused); | ||
| 66 | |||
| 67 | /* | ||
| 68 | * Define all of the IRQ senses and polarities. Taken from the | ||
| 69 | * mpc7448hpc manual. | ||
| 70 | * Note: Likely, this table and the following function should be | ||
| 71 | * obtained and derived from the OF Device Tree. | ||
| 72 | */ | ||
| 73 | |||
| 74 | static u_char mpc7448_hpc2_pic_initsenses[] __initdata = { | ||
| 75 | /* External on-board sources */ | ||
| 76 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE), /* INT[0] XINT0 from FPGA */ | ||
| 77 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE), /* INT[1] XINT1 from FPGA */ | ||
| 78 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE), /* INT[2] PHY_INT from both GIGE */ | ||
| 79 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE), /* INT[3] RESERVED */ | ||
| 80 | /* Internal Tsi108/109 interrupt sources */ | ||
| 81 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 82 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 83 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 84 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 85 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* DMA0 */ | ||
| 86 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* DMA1 */ | ||
| 87 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* DMA2 */ | ||
| 88 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* DMA3 */ | ||
| 89 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* UART0 */ | ||
| 90 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* UART1 */ | ||
| 91 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* I2C */ | ||
| 92 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* GPIO */ | ||
| 93 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE), /* GIGE0 */ | ||
| 94 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE), /* GIGE1 */ | ||
| 95 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 96 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* HLP */ | ||
| 97 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* SDC */ | ||
| 98 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Processor IF */ | ||
| 99 | (IRQ_SENSE_EDGE | IRQ_POLARITY_POSITIVE), /* Reserved IRQ */ | ||
| 100 | (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE), /* PCI/X block */ | ||
| 101 | }; | ||
| 102 | |||
| 103 | int mpc7448_hpc2_exclude_device(u_char bus, u_char devfn) | ||
| 104 | { | ||
| 105 | if (bus == 0 && PCI_SLOT(devfn) == 0) | ||
| 106 | return PCIBIOS_DEVICE_NOT_FOUND; | ||
| 107 | else | ||
| 108 | return PCIBIOS_SUCCESSFUL; | ||
| 109 | } | ||
| 110 | |||
| 111 | /* | ||
| 112 | * find pci slot by devfn in interrupt map of OF tree | ||
| 113 | */ | ||
| 114 | u8 find_slot_by_devfn(unsigned int *interrupt_map, unsigned int devfn) | ||
| 115 | { | ||
| 116 | int i; | ||
| 117 | unsigned int tmp; | ||
| 118 | for (i = 0; i < 4; i++){ | ||
| 119 | tmp = interrupt_map[i*4*7]; | ||
| 120 | if ((tmp >> 11) == (devfn >> 3)) | ||
| 121 | return i; | ||
| 122 | } | ||
| 123 | return i; | ||
| 124 | } | ||
| 125 | |||
| 126 | /* | ||
| 127 | * Scans the interrupt map for pci device | ||
| 128 | */ | ||
| 129 | void mpc7448_hpc2_fixup_irq(struct pci_dev *dev) | ||
| 130 | { | ||
| 131 | struct pci_controller *hose; | ||
| 132 | struct device_node *node; | ||
| 133 | unsigned int *interrupt; | ||
| 134 | int busnr; | ||
| 135 | int len; | ||
| 136 | u8 slot; | ||
| 137 | u8 pin; | ||
| 138 | |||
| 139 | /* Lookup the hose */ | ||
| 140 | busnr = dev->bus->number; | ||
| 141 | hose = pci_bus_to_hose(busnr); | ||
| 142 | if (!hose) | ||
| 143 | printk(KERN_ERR "No pci hose found\n"); | ||
| 144 | |||
| 145 | /* Check it has an OF node associated */ | ||
| 146 | node = (struct device_node *) hose->arch_data; | ||
| 147 | if (!node) | ||
| 148 | printk(KERN_ERR "No pci node found\n"); | ||
| 149 | |||
| 150 | interrupt = (unsigned int *) get_property(node, "interrupt-map", &len); | ||
| 151 | slot = find_slot_by_devfn(interrupt, dev->devfn); | ||
| 152 | pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &pin); | ||
| 153 | if (pin == 0 || pin > 4) | ||
| 154 | pin = 1; | ||
| 155 | pin--; | ||
| 156 | dev->irq = interrupt[slot*4*7 + pin*7 + 5]; | ||
| 157 | DBG("TSI_PCI: dev->irq = 0x%x\n", dev->irq); | ||
| 158 | } | ||
| 159 | /* temporary pci irq map fixup*/ | ||
| 160 | |||
| 161 | void __init mpc7448_hpc2_pcibios_fixup(void) | ||
| 162 | { | ||
| 163 | struct pci_dev *dev = NULL; | ||
| 164 | for_each_pci_dev(dev) { | ||
| 165 | mpc7448_hpc2_fixup_irq(dev); | ||
| 166 | pci_write_config_byte(dev, PCI_INTERRUPT_LINE, dev->irq); | ||
| 167 | } | ||
| 168 | } | ||
| 169 | |||
| 170 | static void __init mpc7448_hpc2_setup_arch(void) | ||
| 171 | { | ||
| 172 | struct device_node *cpu; | ||
| 173 | struct device_node *np; | ||
| 174 | if (ppc_md.progress) | ||
| 175 | ppc_md.progress("mpc7448_hpc2_setup_arch():set_bridge", 0); | ||
| 176 | |||
| 177 | cpu = of_find_node_by_type(NULL, "cpu"); | ||
| 178 | if (cpu != 0) { | ||
| 179 | unsigned int *fp; | ||
| 180 | |||
| 181 | fp = (int *)get_property(cpu, "clock-frequency", NULL); | ||
| 182 | if (fp != 0) | ||
| 183 | loops_per_jiffy = *fp / HZ; | ||
| 184 | else | ||
| 185 | loops_per_jiffy = 50000000 / HZ; | ||
| 186 | of_node_put(cpu); | ||
| 187 | } | ||
| 188 | tsi108_csr_vir_base = get_vir_csrbase(); | ||
| 189 | |||
| 190 | #ifdef CONFIG_ROOT_NFS | ||
| 191 | ROOT_DEV = Root_NFS; | ||
| 192 | #else | ||
| 193 | ROOT_DEV = Root_HDA1; | ||
| 194 | #endif | ||
| 195 | |||
| 196 | #ifdef CONFIG_BLK_DEV_INITRD | ||
| 197 | ROOT_DEV = Root_RAM0; | ||
| 198 | #endif | ||
| 199 | |||
| 200 | /* setup PCI host bridge */ | ||
| 201 | #ifdef CONFIG_PCI | ||
| 202 | for (np = NULL; (np = of_find_node_by_type(np, "pci")) != NULL;) | ||
| 203 | tsi108_setup_pci(np); | ||
| 204 | |||
| 205 | ppc_md.pci_exclude_device = mpc7448_hpc2_exclude_device; | ||
| 206 | if (ppc_md.progress) | ||
| 207 | ppc_md.progress("tsi108: resources set", 0x100); | ||
| 208 | #endif | ||
| 209 | |||
| 210 | printk(KERN_INFO "MPC7448HPC2 (TAIGA) Platform\n"); | ||
| 211 | printk(KERN_INFO | ||
| 212 | "Jointly ported by Freescale and Tundra Semiconductor\n"); | ||
| 213 | printk(KERN_INFO | ||
| 214 | "Enabling L2 cache then enabling the HID0 prefetch engine.\n"); | ||
| 215 | } | ||
| 216 | |||
| 217 | /* | ||
| 218 | * Interrupt setup and service. Interrrupts on the mpc7448_hpc2 come | ||
| 219 | * from the four external INT pins, PCI interrupts are routed via | ||
| 220 | * PCI interrupt control registers, it generates internal IRQ23 | ||
| 221 | * | ||
| 222 | * Interrupt routing on the Taiga Board: | ||
| 223 | * TSI108:PB_INT[0] -> CPU0:INT# | ||
| 224 | * TSI108:PB_INT[1] -> CPU0:MCP# | ||
| 225 | * TSI108:PB_INT[2] -> N/C | ||
| 226 | * TSI108:PB_INT[3] -> N/C | ||
| 227 | */ | ||
| 228 | static void __init mpc7448_hpc2_init_IRQ(void) | ||
| 229 | { | ||
| 230 | struct mpic *mpic; | ||
| 231 | phys_addr_t mpic_paddr = 0; | ||
| 232 | struct device_node *tsi_pic; | ||
| 233 | |||
| 234 | tsi_pic = of_find_node_by_type(NULL, "open-pic"); | ||
| 235 | if (tsi_pic) { | ||
| 236 | unsigned int size; | ||
| 237 | void *prop = get_property(tsi_pic, "reg", &size); | ||
| 238 | mpic_paddr = of_translate_address(tsi_pic, prop); | ||
| 239 | } | ||
| 240 | |||
| 241 | if (mpic_paddr == 0) { | ||
| 242 | printk("%s: No tsi108 PIC found !\n", __FUNCTION__); | ||
| 243 | return; | ||
| 244 | } | ||
| 245 | |||
| 246 | DBG("%s: tsi108pic phys_addr = 0x%x\n", __FUNCTION__, | ||
| 247 | (u32) mpic_paddr); | ||
| 248 | |||
| 249 | mpic = mpic_alloc(mpic_paddr, | ||
| 250 | MPIC_PRIMARY | MPIC_BIG_ENDIAN | MPIC_WANTS_RESET | | ||
| 251 | MPIC_SPV_EOI | MPIC_MOD_ID(MPIC_ID_TSI108), | ||
| 252 | 0, /* num_sources used */ | ||
| 253 | TSI108_IRQ_BASE, | ||
| 254 | 0, /* num_sources used */ | ||
| 255 | NR_IRQS - 4 /* XXXX */, | ||
| 256 | mpc7448_hpc2_pic_initsenses, | ||
| 257 | sizeof(mpc7448_hpc2_pic_initsenses), "Tsi108_PIC"); | ||
| 258 | |||
| 259 | BUG_ON(mpic == NULL); /* XXXX */ | ||
| 260 | |||
| 261 | mpic_init(mpic); | ||
| 262 | mpic_setup_cascade(IRQ_TSI108_PCI, tsi108_irq_cascade, mpic); | ||
| 263 | tsi108_pci_int_init(); | ||
| 264 | |||
| 265 | /* Configure MPIC outputs to CPU0 */ | ||
| 266 | tsi108_write_reg(TSI108_MPIC_OFFSET + 0x30c, 0); | ||
| 267 | } | ||
| 268 | |||
| 269 | void mpc7448_hpc2_show_cpuinfo(struct seq_file *m) | ||
| 270 | { | ||
| 271 | seq_printf(m, "vendor\t\t: Freescale Semiconductor\n"); | ||
| 272 | seq_printf(m, "machine\t\t: MPC7448hpc2\n"); | ||
| 273 | } | ||
| 274 | |||
| 275 | void mpc7448_hpc2_restart(char *cmd) | ||
| 276 | { | ||
| 277 | local_irq_disable(); | ||
| 278 | |||
| 279 | /* Set exception prefix high - to the firmware */ | ||
| 280 | _nmask_and_or_msr(0, MSR_IP); | ||
| 281 | |||
| 282 | for (;;) ; /* Spin until reset happens */ | ||
| 283 | } | ||
| 284 | |||
| 285 | void mpc7448_hpc2_power_off(void) | ||
| 286 | { | ||
| 287 | local_irq_disable(); | ||
| 288 | for (;;) ; /* No way to shut power off with software */ | ||
| 289 | } | ||
| 290 | |||
| 291 | void mpc7448_hpc2_halt(void) | ||
| 292 | { | ||
| 293 | mpc7448_hpc2_power_off(); | ||
| 294 | } | ||
| 295 | |||
| 296 | /* | ||
| 297 | * Called very early, device-tree isn't unflattened | ||
| 298 | */ | ||
| 299 | static int __init mpc7448_hpc2_probe(void) | ||
| 300 | { | ||
| 301 | unsigned long root = of_get_flat_dt_root(); | ||
| 302 | |||
| 303 | if (!of_flat_dt_is_compatible(root, "mpc74xx")) | ||
| 304 | return 0; | ||
| 305 | return 1; | ||
| 306 | } | ||
| 307 | |||
| 308 | static int mpc7448_machine_check_exception(struct pt_regs *regs) | ||
| 309 | { | ||
| 310 | extern void tsi108_clear_pci_cfg_error(void); | ||
| 311 | const struct exception_table_entry *entry; | ||
| 312 | |||
| 313 | /* Are we prepared to handle this fault */ | ||
| 314 | if ((entry = search_exception_tables(regs->nip)) != NULL) { | ||
| 315 | tsi108_clear_pci_cfg_error(); | ||
| 316 | regs->msr |= MSR_RI; | ||
| 317 | regs->nip = entry->fixup; | ||
| 318 | return 1; | ||
| 319 | } | ||
| 320 | return 0; | ||
| 321 | |||
| 322 | } | ||
| 323 | define_machine(mpc7448_hpc2){ | ||
| 324 | .name = "MPC7448 HPC2", | ||
| 325 | .probe = mpc7448_hpc2_probe, | ||
| 326 | .setup_arch = mpc7448_hpc2_setup_arch, | ||
| 327 | .init_IRQ = mpc7448_hpc2_init_IRQ, | ||
| 328 | .show_cpuinfo = mpc7448_hpc2_show_cpuinfo, | ||
| 329 | .get_irq = mpic_get_irq, | ||
| 330 | .pcibios_fixup = mpc7448_hpc2_pcibios_fixup, | ||
| 331 | .restart = mpc7448_hpc2_restart, | ||
| 332 | .calibrate_decr = generic_calibrate_decr, | ||
| 333 | .machine_check_exception= mpc7448_machine_check_exception, | ||
| 334 | .progress = udbg_progress, | ||
| 335 | }; | ||
diff --git a/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h new file mode 100644 index 000000000000..a543a5242e34 --- /dev/null +++ b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h | |||
| @@ -0,0 +1,26 @@ | |||
| 1 | /* | ||
| 2 | * mpc7448_hpc2.h | ||
| 3 | * | ||
| 4 | * Definitions for Freescale MPC7448_HPC2 platform | ||
| 5 | * | ||
| 6 | * Author: Jacob Pan | ||
| 7 | * jacob.pan@freescale.com | ||
| 8 | * Maintainer: Roy Zang <roy.zang@freescale.com> | ||
| 9 | * | ||
| 10 | * 2006 (c) Freescale Semiconductor, Inc. This file is licensed under | ||
| 11 | * the terms of the GNU General Public License version 2. This program | ||
| 12 | * is licensed "as is" without any warranty of any kind, whether express | ||
| 13 | * or implied. | ||
| 14 | */ | ||
| 15 | |||
| 16 | #ifndef __PPC_PLATFORMS_MPC7448_HPC2_H | ||
| 17 | #define __PPC_PLATFORMS_MPC7448_HPC2_H | ||
| 18 | |||
| 19 | #include <asm/ppcboot.h> | ||
| 20 | |||
| 21 | /* Base Addresses for the PCI bus | ||
| 22 | */ | ||
| 23 | #define MPC7448_HPC2_PCI_MEM_OFFSET (0x00000000) | ||
| 24 | #define MPC7448_HPC2_ISA_IO_BASE (0x00000000) | ||
| 25 | #define MPC7448_HPC2_ISA_MEM_BASE (0x00000000) | ||
| 26 | #endif /* __PPC_PLATFORMS_MPC7448_HPC2_H */ | ||
diff --git a/arch/powerpc/platforms/iseries/dt.c b/arch/powerpc/platforms/iseries/dt.c index d3444aabe76e..d194140c1ebf 100644 --- a/arch/powerpc/platforms/iseries/dt.c +++ b/arch/powerpc/platforms/iseries/dt.c | |||
| @@ -252,6 +252,7 @@ static void __init dt_model(struct iseries_flat_dt *dt) | |||
| 252 | { | 252 | { |
| 253 | char buf[16] = "IBM,"; | 253 | char buf[16] = "IBM,"; |
| 254 | 254 | ||
| 255 | /* N.B. lparcfg.c knows about the "IBM," prefixes ... */ | ||
| 255 | /* "IBM," + mfgId[2:3] + systemSerial[1:5] */ | 256 | /* "IBM," + mfgId[2:3] + systemSerial[1:5] */ |
| 256 | strne2a(buf + 4, xItExtVpdPanel.mfgID + 2, 2); | 257 | strne2a(buf + 4, xItExtVpdPanel.mfgID + 2, 2); |
| 257 | strne2a(buf + 6, xItExtVpdPanel.systemSerial + 1, 5); | 258 | strne2a(buf + 6, xItExtVpdPanel.systemSerial + 1, 5); |
| @@ -264,6 +265,7 @@ static void __init dt_model(struct iseries_flat_dt *dt) | |||
| 264 | dt_prop_str(dt, "model", buf); | 265 | dt_prop_str(dt, "model", buf); |
| 265 | 266 | ||
| 266 | dt_prop_str(dt, "compatible", "IBM,iSeries"); | 267 | dt_prop_str(dt, "compatible", "IBM,iSeries"); |
| 268 | dt_prop_u32(dt, "ibm,partition-no", HvLpConfig_getLpIndex()); | ||
| 267 | } | 269 | } |
| 268 | 270 | ||
| 269 | static void __init dt_do_vdevice(struct iseries_flat_dt *dt, | 271 | static void __init dt_do_vdevice(struct iseries_flat_dt *dt, |
diff --git a/arch/powerpc/platforms/iseries/htab.c b/arch/powerpc/platforms/iseries/htab.c index 30bdcf3925d9..ed44dfceaa45 100644 --- a/arch/powerpc/platforms/iseries/htab.c +++ b/arch/powerpc/platforms/iseries/htab.c | |||
| @@ -242,13 +242,11 @@ static void iSeries_hpte_invalidate(unsigned long slot, unsigned long va, | |||
| 242 | local_irq_restore(flags); | 242 | local_irq_restore(flags); |
| 243 | } | 243 | } |
| 244 | 244 | ||
| 245 | void hpte_init_iSeries(void) | 245 | void __init hpte_init_iSeries(void) |
| 246 | { | 246 | { |
| 247 | ppc_md.hpte_invalidate = iSeries_hpte_invalidate; | 247 | ppc_md.hpte_invalidate = iSeries_hpte_invalidate; |
| 248 | ppc_md.hpte_updatepp = iSeries_hpte_updatepp; | 248 | ppc_md.hpte_updatepp = iSeries_hpte_updatepp; |
| 249 | ppc_md.hpte_updateboltedpp = iSeries_hpte_updateboltedpp; | 249 | ppc_md.hpte_updateboltedpp = iSeries_hpte_updateboltedpp; |
| 250 | ppc_md.hpte_insert = iSeries_hpte_insert; | 250 | ppc_md.hpte_insert = iSeries_hpte_insert; |
| 251 | ppc_md.hpte_remove = iSeries_hpte_remove; | 251 | ppc_md.hpte_remove = iSeries_hpte_remove; |
| 252 | |||
| 253 | htab_finish_init(); | ||
| 254 | } | 252 | } |
diff --git a/arch/powerpc/platforms/iseries/lpevents.c b/arch/powerpc/platforms/iseries/lpevents.c index 8ca7b9396355..2a9f81ea27d6 100644 --- a/arch/powerpc/platforms/iseries/lpevents.c +++ b/arch/powerpc/platforms/iseries/lpevents.c | |||
| @@ -51,20 +51,21 @@ static unsigned lpEventHandlerPaths[HvLpEvent_Type_NumTypes]; | |||
| 51 | static struct HvLpEvent * get_next_hvlpevent(void) | 51 | static struct HvLpEvent * get_next_hvlpevent(void) |
| 52 | { | 52 | { |
| 53 | struct HvLpEvent * event; | 53 | struct HvLpEvent * event; |
| 54 | event = (struct HvLpEvent *)hvlpevent_queue.xSlicCurEventPtr; | 54 | event = (struct HvLpEvent *)hvlpevent_queue.hq_current_event; |
| 55 | 55 | ||
| 56 | if (hvlpevent_is_valid(event)) { | 56 | if (hvlpevent_is_valid(event)) { |
| 57 | /* rmb() needed only for weakly consistent machines (regatta) */ | 57 | /* rmb() needed only for weakly consistent machines (regatta) */ |
| 58 | rmb(); | 58 | rmb(); |
| 59 | /* Set pointer to next potential event */ | 59 | /* Set pointer to next potential event */ |
| 60 | hvlpevent_queue.xSlicCurEventPtr += ((event->xSizeMinus1 + | 60 | hvlpevent_queue.hq_current_event += ((event->xSizeMinus1 + |
| 61 | LpEventAlign) / LpEventAlign) * LpEventAlign; | 61 | IT_LP_EVENT_ALIGN) / IT_LP_EVENT_ALIGN) * |
| 62 | IT_LP_EVENT_ALIGN; | ||
| 62 | 63 | ||
| 63 | /* Wrap to beginning if no room at end */ | 64 | /* Wrap to beginning if no room at end */ |
| 64 | if (hvlpevent_queue.xSlicCurEventPtr > | 65 | if (hvlpevent_queue.hq_current_event > |
| 65 | hvlpevent_queue.xSlicLastValidEventPtr) { | 66 | hvlpevent_queue.hq_last_event) { |
| 66 | hvlpevent_queue.xSlicCurEventPtr = | 67 | hvlpevent_queue.hq_current_event = |
| 67 | hvlpevent_queue.xSlicEventStackPtr; | 68 | hvlpevent_queue.hq_event_stack; |
| 68 | } | 69 | } |
| 69 | } else { | 70 | } else { |
| 70 | event = NULL; | 71 | event = NULL; |
| @@ -82,10 +83,10 @@ int hvlpevent_is_pending(void) | |||
| 82 | if (smp_processor_id() >= spread_lpevents) | 83 | if (smp_processor_id() >= spread_lpevents) |
| 83 | return 0; | 84 | return 0; |
| 84 | 85 | ||
| 85 | next_event = (struct HvLpEvent *)hvlpevent_queue.xSlicCurEventPtr; | 86 | next_event = (struct HvLpEvent *)hvlpevent_queue.hq_current_event; |
| 86 | 87 | ||
| 87 | return hvlpevent_is_valid(next_event) || | 88 | return hvlpevent_is_valid(next_event) || |
| 88 | hvlpevent_queue.xPlicOverflowIntPending; | 89 | hvlpevent_queue.hq_overflow_pending; |
| 89 | } | 90 | } |
| 90 | 91 | ||
| 91 | static void hvlpevent_clear_valid(struct HvLpEvent * event) | 92 | static void hvlpevent_clear_valid(struct HvLpEvent * event) |
| @@ -95,18 +96,18 @@ static void hvlpevent_clear_valid(struct HvLpEvent * event) | |||
| 95 | * ie. on 64-byte boundaries. | 96 | * ie. on 64-byte boundaries. |
| 96 | */ | 97 | */ |
| 97 | struct HvLpEvent *tmp; | 98 | struct HvLpEvent *tmp; |
| 98 | unsigned extra = ((event->xSizeMinus1 + LpEventAlign) / | 99 | unsigned extra = ((event->xSizeMinus1 + IT_LP_EVENT_ALIGN) / |
| 99 | LpEventAlign) - 1; | 100 | IT_LP_EVENT_ALIGN) - 1; |
| 100 | 101 | ||
| 101 | switch (extra) { | 102 | switch (extra) { |
| 102 | case 3: | 103 | case 3: |
| 103 | tmp = (struct HvLpEvent*)((char*)event + 3 * LpEventAlign); | 104 | tmp = (struct HvLpEvent*)((char*)event + 3 * IT_LP_EVENT_ALIGN); |
| 104 | hvlpevent_invalidate(tmp); | 105 | hvlpevent_invalidate(tmp); |
| 105 | case 2: | 106 | case 2: |
| 106 | tmp = (struct HvLpEvent*)((char*)event + 2 * LpEventAlign); | 107 | tmp = (struct HvLpEvent*)((char*)event + 2 * IT_LP_EVENT_ALIGN); |
| 107 | hvlpevent_invalidate(tmp); | 108 | hvlpevent_invalidate(tmp); |
| 108 | case 1: | 109 | case 1: |
| 109 | tmp = (struct HvLpEvent*)((char*)event + 1 * LpEventAlign); | 110 | tmp = (struct HvLpEvent*)((char*)event + 1 * IT_LP_EVENT_ALIGN); |
| 110 | hvlpevent_invalidate(tmp); | 111 | hvlpevent_invalidate(tmp); |
| 111 | } | 112 | } |
| 112 | 113 | ||
| @@ -120,7 +121,7 @@ void process_hvlpevents(struct pt_regs *regs) | |||
| 120 | struct HvLpEvent * event; | 121 | struct HvLpEvent * event; |
| 121 | 122 | ||
| 122 | /* If we have recursed, just return */ | 123 | /* If we have recursed, just return */ |
| 123 | if (!spin_trylock(&hvlpevent_queue.lock)) | 124 | if (!spin_trylock(&hvlpevent_queue.hq_lock)) |
| 124 | return; | 125 | return; |
| 125 | 126 | ||
| 126 | for (;;) { | 127 | for (;;) { |
| @@ -148,17 +149,17 @@ void process_hvlpevents(struct pt_regs *regs) | |||
| 148 | printk(KERN_INFO "Unexpected Lp Event type=%d\n", event->xType ); | 149 | printk(KERN_INFO "Unexpected Lp Event type=%d\n", event->xType ); |
| 149 | 150 | ||
| 150 | hvlpevent_clear_valid(event); | 151 | hvlpevent_clear_valid(event); |
| 151 | } else if (hvlpevent_queue.xPlicOverflowIntPending) | 152 | } else if (hvlpevent_queue.hq_overflow_pending) |
| 152 | /* | 153 | /* |
| 153 | * No more valid events. If overflow events are | 154 | * No more valid events. If overflow events are |
| 154 | * pending process them | 155 | * pending process them |
| 155 | */ | 156 | */ |
| 156 | HvCallEvent_getOverflowLpEvents(hvlpevent_queue.xIndex); | 157 | HvCallEvent_getOverflowLpEvents(hvlpevent_queue.hq_index); |
| 157 | else | 158 | else |
| 158 | break; | 159 | break; |
| 159 | } | 160 | } |
| 160 | 161 | ||
| 161 | spin_unlock(&hvlpevent_queue.lock); | 162 | spin_unlock(&hvlpevent_queue.hq_lock); |
| 162 | } | 163 | } |
| 163 | 164 | ||
| 164 | static int set_spread_lpevents(char *str) | 165 | static int set_spread_lpevents(char *str) |
| @@ -184,20 +185,20 @@ void setup_hvlpevent_queue(void) | |||
| 184 | { | 185 | { |
| 185 | void *eventStack; | 186 | void *eventStack; |
| 186 | 187 | ||
| 187 | spin_lock_init(&hvlpevent_queue.lock); | 188 | spin_lock_init(&hvlpevent_queue.hq_lock); |
| 188 | 189 | ||
| 189 | /* Allocate a page for the Event Stack. */ | 190 | /* Allocate a page for the Event Stack. */ |
| 190 | eventStack = alloc_bootmem_pages(LpEventStackSize); | 191 | eventStack = alloc_bootmem_pages(IT_LP_EVENT_STACK_SIZE); |
| 191 | memset(eventStack, 0, LpEventStackSize); | 192 | memset(eventStack, 0, IT_LP_EVENT_STACK_SIZE); |
| 192 | 193 | ||
| 193 | /* Invoke the hypervisor to initialize the event stack */ | 194 | /* Invoke the hypervisor to initialize the event stack */ |
| 194 | HvCallEvent_setLpEventStack(0, eventStack, LpEventStackSize); | 195 | HvCallEvent_setLpEventStack(0, eventStack, IT_LP_EVENT_STACK_SIZE); |
| 195 | 196 | ||
| 196 | hvlpevent_queue.xSlicEventStackPtr = (char *)eventStack; | 197 | hvlpevent_queue.hq_event_stack = eventStack; |
| 197 | hvlpevent_queue.xSlicCurEventPtr = (char *)eventStack; | 198 | hvlpevent_queue.hq_current_event = eventStack; |
| 198 | hvlpevent_queue.xSlicLastValidEventPtr = (char *)eventStack + | 199 | hvlpevent_queue.hq_last_event = (char *)eventStack + |
| 199 | (LpEventStackSize - LpEventMaxSize); | 200 | (IT_LP_EVENT_STACK_SIZE - IT_LP_EVENT_MAX_SIZE); |
| 200 | hvlpevent_queue.xIndex = 0; | 201 | hvlpevent_queue.hq_index = 0; |
| 201 | } | 202 | } |
| 202 | 203 | ||
| 203 | /* Register a handler for an LpEvent type */ | 204 | /* Register a handler for an LpEvent type */ |
diff --git a/arch/powerpc/platforms/iseries/proc.c b/arch/powerpc/platforms/iseries/proc.c index e68b6b5fa89f..c241413629ac 100644 --- a/arch/powerpc/platforms/iseries/proc.c +++ b/arch/powerpc/platforms/iseries/proc.c | |||
| @@ -24,7 +24,6 @@ | |||
| 24 | #include <asm/processor.h> | 24 | #include <asm/processor.h> |
| 25 | #include <asm/time.h> | 25 | #include <asm/time.h> |
| 26 | #include <asm/lppaca.h> | 26 | #include <asm/lppaca.h> |
| 27 | #include <asm/iseries/it_lp_queue.h> | ||
| 28 | #include <asm/iseries/hv_call_xm.h> | 27 | #include <asm/iseries/hv_call_xm.h> |
| 29 | 28 | ||
| 30 | #include "processor_vpd.h" | 29 | #include "processor_vpd.h" |
diff --git a/arch/powerpc/platforms/iseries/setup.c b/arch/powerpc/platforms/iseries/setup.c index 617c724c4590..66c77e4f8ec2 100644 --- a/arch/powerpc/platforms/iseries/setup.c +++ b/arch/powerpc/platforms/iseries/setup.c | |||
| @@ -81,8 +81,6 @@ static void iSeries_pci_final_fixup(void) { } | |||
| 81 | #endif | 81 | #endif |
| 82 | 82 | ||
| 83 | extern int rd_size; /* Defined in drivers/block/rd.c */ | 83 | extern int rd_size; /* Defined in drivers/block/rd.c */ |
| 84 | extern unsigned long embedded_sysmap_start; | ||
| 85 | extern unsigned long embedded_sysmap_end; | ||
| 86 | 84 | ||
| 87 | extern unsigned long iSeries_recal_tb; | 85 | extern unsigned long iSeries_recal_tb; |
| 88 | extern unsigned long iSeries_recal_titan; | 86 | extern unsigned long iSeries_recal_titan; |
| @@ -321,11 +319,6 @@ static void __init iSeries_init_early(void) | |||
| 321 | iSeries_recal_titan = HvCallXm_loadTod(); | 319 | iSeries_recal_titan = HvCallXm_loadTod(); |
| 322 | 320 | ||
| 323 | /* | 321 | /* |
| 324 | * Initialize the hash table management pointers | ||
| 325 | */ | ||
| 326 | hpte_init_iSeries(); | ||
| 327 | |||
| 328 | /* | ||
| 329 | * Initialize the DMA/TCE management | 322 | * Initialize the DMA/TCE management |
| 330 | */ | 323 | */ |
| 331 | iommu_init_early_iSeries(); | 324 | iommu_init_early_iSeries(); |
| @@ -563,16 +556,6 @@ static void __init iSeries_fixup_klimit(void) | |||
| 563 | if (naca.xRamDisk) | 556 | if (naca.xRamDisk) |
| 564 | klimit = KERNELBASE + (u64)naca.xRamDisk + | 557 | klimit = KERNELBASE + (u64)naca.xRamDisk + |
| 565 | (naca.xRamDiskSize * HW_PAGE_SIZE); | 558 | (naca.xRamDiskSize * HW_PAGE_SIZE); |
| 566 | else { | ||
| 567 | /* | ||
| 568 | * No ram disk was included - check and see if there | ||
| 569 | * was an embedded system map. Change klimit to take | ||
| 570 | * into account any embedded system map | ||
| 571 | */ | ||
| 572 | if (embedded_sysmap_end) | ||
| 573 | klimit = KERNELBASE + ((embedded_sysmap_end + 4095) & | ||
| 574 | 0xfffffffffffff000); | ||
| 575 | } | ||
| 576 | } | 559 | } |
| 577 | 560 | ||
| 578 | static int __init iSeries_src_init(void) | 561 | static int __init iSeries_src_init(void) |
| @@ -683,6 +666,8 @@ static int __init iseries_probe(void) | |||
| 683 | */ | 666 | */ |
| 684 | virt_irq_max = 255; | 667 | virt_irq_max = 255; |
| 685 | 668 | ||
| 669 | hpte_init_iSeries(); | ||
| 670 | |||
| 686 | return 1; | 671 | return 1; |
| 687 | } | 672 | } |
| 688 | 673 | ||
diff --git a/arch/powerpc/platforms/maple/setup.c b/arch/powerpc/platforms/maple/setup.c index a0505ea48a86..4e32a5417fd1 100644 --- a/arch/powerpc/platforms/maple/setup.c +++ b/arch/powerpc/platforms/maple/setup.c | |||
| @@ -199,11 +199,6 @@ static void __init maple_init_early(void) | |||
| 199 | { | 199 | { |
| 200 | DBG(" -> maple_init_early\n"); | 200 | DBG(" -> maple_init_early\n"); |
| 201 | 201 | ||
| 202 | /* Initialize hash table, from now on, we can take hash faults | ||
| 203 | * and call ioremap | ||
| 204 | */ | ||
| 205 | hpte_init_native(); | ||
| 206 | |||
| 207 | /* Setup interrupt mapping options */ | 202 | /* Setup interrupt mapping options */ |
| 208 | ppc64_interrupt_controller = IC_OPEN_PIC; | 203 | ppc64_interrupt_controller = IC_OPEN_PIC; |
| 209 | 204 | ||
| @@ -272,6 +267,8 @@ static int __init maple_probe(void) | |||
| 272 | */ | 267 | */ |
| 273 | alloc_dart_table(); | 268 | alloc_dart_table(); |
| 274 | 269 | ||
| 270 | hpte_init_native(); | ||
| 271 | |||
| 275 | return 1; | 272 | return 1; |
| 276 | } | 273 | } |
| 277 | 274 | ||
diff --git a/arch/powerpc/platforms/powermac/setup.c b/arch/powerpc/platforms/powermac/setup.c index 9cc7db7a8bdc..89c5775f83be 100644 --- a/arch/powerpc/platforms/powermac/setup.c +++ b/arch/powerpc/platforms/powermac/setup.c | |||
| @@ -600,13 +600,6 @@ pmac_halt(void) | |||
| 600 | */ | 600 | */ |
| 601 | static void __init pmac_init_early(void) | 601 | static void __init pmac_init_early(void) |
| 602 | { | 602 | { |
| 603 | #ifdef CONFIG_PPC64 | ||
| 604 | /* Initialize hash table, from now on, we can take hash faults | ||
| 605 | * and call ioremap | ||
| 606 | */ | ||
| 607 | hpte_init_native(); | ||
| 608 | #endif | ||
| 609 | |||
| 610 | /* Enable early btext debug if requested */ | 603 | /* Enable early btext debug if requested */ |
| 611 | if (strstr(cmd_line, "btextdbg")) { | 604 | if (strstr(cmd_line, "btextdbg")) { |
| 612 | udbg_adb_init_early(); | 605 | udbg_adb_init_early(); |
| @@ -683,6 +676,8 @@ static int __init pmac_probe(void) | |||
| 683 | * part of the cacheable linar mapping | 676 | * part of the cacheable linar mapping |
| 684 | */ | 677 | */ |
| 685 | alloc_dart_table(); | 678 | alloc_dart_table(); |
| 679 | |||
| 680 | hpte_init_native(); | ||
| 686 | #endif | 681 | #endif |
| 687 | 682 | ||
| 688 | #ifdef CONFIG_PPC32 | 683 | #ifdef CONFIG_PPC32 |
diff --git a/arch/powerpc/platforms/pseries/iommu.c b/arch/powerpc/platforms/pseries/iommu.c index d03a8b078f9d..8cfb5706790e 100644 --- a/arch/powerpc/platforms/pseries/iommu.c +++ b/arch/powerpc/platforms/pseries/iommu.c | |||
| @@ -92,6 +92,15 @@ static void tce_free_pSeries(struct iommu_table *tbl, long index, long npages) | |||
| 92 | *(tcep++) = 0; | 92 | *(tcep++) = 0; |
| 93 | } | 93 | } |
| 94 | 94 | ||
| 95 | static unsigned long tce_get_pseries(struct iommu_table *tbl, long index) | ||
| 96 | { | ||
| 97 | u64 *tcep; | ||
| 98 | |||
| 99 | index <<= TCE_PAGE_FACTOR; | ||
| 100 | tcep = ((u64 *)tbl->it_base) + index; | ||
| 101 | |||
| 102 | return *tcep; | ||
| 103 | } | ||
| 95 | 104 | ||
| 96 | static void tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum, | 105 | static void tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum, |
| 97 | long npages, unsigned long uaddr, | 106 | long npages, unsigned long uaddr, |
| @@ -235,6 +244,25 @@ static void tce_freemulti_pSeriesLP(struct iommu_table *tbl, long tcenum, long n | |||
| 235 | } | 244 | } |
| 236 | } | 245 | } |
| 237 | 246 | ||
| 247 | static unsigned long tce_get_pSeriesLP(struct iommu_table *tbl, long tcenum) | ||
| 248 | { | ||
| 249 | u64 rc; | ||
| 250 | unsigned long tce_ret; | ||
| 251 | |||
| 252 | tcenum <<= TCE_PAGE_FACTOR; | ||
| 253 | rc = plpar_tce_get((u64)tbl->it_index, (u64)tcenum << 12, &tce_ret); | ||
| 254 | |||
| 255 | if (rc && printk_ratelimit()) { | ||
| 256 | printk("tce_get_pSeriesLP: plpar_tce_get failed. rc=%ld\n", | ||
| 257 | rc); | ||
| 258 | printk("\tindex = 0x%lx\n", (u64)tbl->it_index); | ||
| 259 | printk("\ttcenum = 0x%lx\n", (u64)tcenum); | ||
| 260 | show_stack(current, (unsigned long *)__get_SP()); | ||
| 261 | } | ||
| 262 | |||
| 263 | return tce_ret; | ||
| 264 | } | ||
| 265 | |||
| 238 | static void iommu_table_setparms(struct pci_controller *phb, | 266 | static void iommu_table_setparms(struct pci_controller *phb, |
| 239 | struct device_node *dn, | 267 | struct device_node *dn, |
| 240 | struct iommu_table *tbl) | 268 | struct iommu_table *tbl) |
| @@ -254,7 +282,10 @@ static void iommu_table_setparms(struct pci_controller *phb, | |||
| 254 | } | 282 | } |
| 255 | 283 | ||
| 256 | tbl->it_base = (unsigned long)__va(*basep); | 284 | tbl->it_base = (unsigned long)__va(*basep); |
| 285 | |||
| 286 | #ifndef CONFIG_CRASH_DUMP | ||
| 257 | memset((void *)tbl->it_base, 0, *sizep); | 287 | memset((void *)tbl->it_base, 0, *sizep); |
| 288 | #endif | ||
| 258 | 289 | ||
| 259 | tbl->it_busno = phb->bus->number; | 290 | tbl->it_busno = phb->bus->number; |
| 260 | 291 | ||
| @@ -560,11 +591,13 @@ void iommu_init_early_pSeries(void) | |||
| 560 | ppc_md.tce_build = tce_build_pSeriesLP; | 591 | ppc_md.tce_build = tce_build_pSeriesLP; |
| 561 | ppc_md.tce_free = tce_free_pSeriesLP; | 592 | ppc_md.tce_free = tce_free_pSeriesLP; |
| 562 | } | 593 | } |
| 594 | ppc_md.tce_get = tce_get_pSeriesLP; | ||
| 563 | ppc_md.iommu_bus_setup = iommu_bus_setup_pSeriesLP; | 595 | ppc_md.iommu_bus_setup = iommu_bus_setup_pSeriesLP; |
| 564 | ppc_md.iommu_dev_setup = iommu_dev_setup_pSeriesLP; | 596 | ppc_md.iommu_dev_setup = iommu_dev_setup_pSeriesLP; |
| 565 | } else { | 597 | } else { |
| 566 | ppc_md.tce_build = tce_build_pSeries; | 598 | ppc_md.tce_build = tce_build_pSeries; |
| 567 | ppc_md.tce_free = tce_free_pSeries; | 599 | ppc_md.tce_free = tce_free_pSeries; |
| 600 | ppc_md.tce_get = tce_get_pseries; | ||
| 568 | ppc_md.iommu_bus_setup = iommu_bus_setup_pSeries; | 601 | ppc_md.iommu_bus_setup = iommu_bus_setup_pSeries; |
| 569 | ppc_md.iommu_dev_setup = iommu_dev_setup_pSeries; | 602 | ppc_md.iommu_dev_setup = iommu_dev_setup_pSeries; |
| 570 | } | 603 | } |
diff --git a/arch/powerpc/platforms/pseries/lpar.c b/arch/powerpc/platforms/pseries/lpar.c index 634b7d06d3cc..27480705996f 100644 --- a/arch/powerpc/platforms/pseries/lpar.c +++ b/arch/powerpc/platforms/pseries/lpar.c | |||
| @@ -513,7 +513,7 @@ void pSeries_lpar_flush_hash_range(unsigned long number, int local) | |||
| 513 | spin_unlock_irqrestore(&pSeries_lpar_tlbie_lock, flags); | 513 | spin_unlock_irqrestore(&pSeries_lpar_tlbie_lock, flags); |
| 514 | } | 514 | } |
| 515 | 515 | ||
| 516 | void hpte_init_lpar(void) | 516 | void __init hpte_init_lpar(void) |
| 517 | { | 517 | { |
| 518 | ppc_md.hpte_invalidate = pSeries_lpar_hpte_invalidate; | 518 | ppc_md.hpte_invalidate = pSeries_lpar_hpte_invalidate; |
| 519 | ppc_md.hpte_updatepp = pSeries_lpar_hpte_updatepp; | 519 | ppc_md.hpte_updatepp = pSeries_lpar_hpte_updatepp; |
| @@ -522,6 +522,4 @@ void hpte_init_lpar(void) | |||
| 522 | ppc_md.hpte_remove = pSeries_lpar_hpte_remove; | 522 | ppc_md.hpte_remove = pSeries_lpar_hpte_remove; |
| 523 | ppc_md.flush_hash_range = pSeries_lpar_flush_hash_range; | 523 | ppc_md.flush_hash_range = pSeries_lpar_flush_hash_range; |
| 524 | ppc_md.hpte_clear_all = pSeries_lpar_hptab_clear; | 524 | ppc_md.hpte_clear_all = pSeries_lpar_hptab_clear; |
| 525 | |||
| 526 | htab_finish_init(); | ||
| 527 | } | 525 | } |
diff --git a/arch/powerpc/platforms/pseries/setup.c b/arch/powerpc/platforms/pseries/setup.c index 1e28518c6121..b3197ff156c6 100644 --- a/arch/powerpc/platforms/pseries/setup.c +++ b/arch/powerpc/platforms/pseries/setup.c | |||
| @@ -322,11 +322,6 @@ static void __init pSeries_init_early(void) | |||
| 322 | DBG(" -> pSeries_init_early()\n"); | 322 | DBG(" -> pSeries_init_early()\n"); |
| 323 | 323 | ||
| 324 | fw_feature_init(); | 324 | fw_feature_init(); |
| 325 | |||
| 326 | if (firmware_has_feature(FW_FEATURE_LPAR)) | ||
| 327 | hpte_init_lpar(); | ||
| 328 | else | ||
| 329 | hpte_init_native(); | ||
| 330 | 325 | ||
| 331 | if (firmware_has_feature(FW_FEATURE_LPAR)) | 326 | if (firmware_has_feature(FW_FEATURE_LPAR)) |
| 332 | find_udbg_vterm(); | 327 | find_udbg_vterm(); |
| @@ -384,6 +379,11 @@ static int __init pSeries_probe_hypertas(unsigned long node, | |||
| 384 | if (of_get_flat_dt_prop(node, "ibm,hypertas-functions", NULL) != NULL) | 379 | if (of_get_flat_dt_prop(node, "ibm,hypertas-functions", NULL) != NULL) |
| 385 | powerpc_firmware_features |= FW_FEATURE_LPAR; | 380 | powerpc_firmware_features |= FW_FEATURE_LPAR; |
| 386 | 381 | ||
| 382 | if (firmware_has_feature(FW_FEATURE_LPAR)) | ||
| 383 | hpte_init_lpar(); | ||
| 384 | else | ||
| 385 | hpte_init_native(); | ||
| 386 | |||
| 387 | return 1; | 387 | return 1; |
| 388 | } | 388 | } |
| 389 | 389 | ||
diff --git a/arch/powerpc/sysdev/Makefile b/arch/powerpc/sysdev/Makefile index cef95b023730..054bd8b41ef5 100644 --- a/arch/powerpc/sysdev/Makefile +++ b/arch/powerpc/sysdev/Makefile | |||
| @@ -12,3 +12,5 @@ obj-$(CONFIG_U3_DART) += dart_iommu.o | |||
| 12 | obj-$(CONFIG_MMIO_NVRAM) += mmio_nvram.o | 12 | obj-$(CONFIG_MMIO_NVRAM) += mmio_nvram.o |
| 13 | obj-$(CONFIG_PPC_83xx) += ipic.o | 13 | obj-$(CONFIG_PPC_83xx) += ipic.o |
| 14 | obj-$(CONFIG_FSL_SOC) += fsl_soc.o | 14 | obj-$(CONFIG_FSL_SOC) += fsl_soc.o |
| 15 | obj-$(CONFIG_PPC_TODC) += todc.o | ||
| 16 | obj-$(CONFIG_TSI108_BRIDGE) += tsi108_pci.o tsi108_dev.o | ||
diff --git a/arch/powerpc/sysdev/dart.h b/arch/powerpc/sysdev/dart.h index c2d05763ccbe..1c8817c4835e 100644 --- a/arch/powerpc/sysdev/dart.h +++ b/arch/powerpc/sysdev/dart.h | |||
| @@ -47,8 +47,12 @@ | |||
| 47 | /* U4 registers */ | 47 | /* U4 registers */ |
| 48 | #define DART_BASE_U4_BASE_MASK 0xffffff | 48 | #define DART_BASE_U4_BASE_MASK 0xffffff |
| 49 | #define DART_BASE_U4_BASE_SHIFT 0 | 49 | #define DART_BASE_U4_BASE_SHIFT 0 |
| 50 | #define DART_CNTL_U4_FLUSHTLB 0x20000000 | ||
| 51 | #define DART_CNTL_U4_ENABLE 0x80000000 | 50 | #define DART_CNTL_U4_ENABLE 0x80000000 |
| 51 | #define DART_CNTL_U4_IONE 0x40000000 | ||
| 52 | #define DART_CNTL_U4_FLUSHTLB 0x20000000 | ||
| 53 | #define DART_CNTL_U4_IDLE 0x10000000 | ||
| 54 | #define DART_CNTL_U4_PAR_EN 0x08000000 | ||
| 55 | #define DART_CNTL_U4_IONE_MASK 0x07ffffff | ||
| 52 | #define DART_SIZE_U4_SIZE_MASK 0x1fff | 56 | #define DART_SIZE_U4_SIZE_MASK 0x1fff |
| 53 | #define DART_SIZE_U4_SIZE_SHIFT 0 | 57 | #define DART_SIZE_U4_SIZE_SHIFT 0 |
| 54 | 58 | ||
diff --git a/arch/powerpc/sysdev/dart_iommu.c b/arch/powerpc/sysdev/dart_iommu.c index 6232091cc72b..7c7f34ce4986 100644 --- a/arch/powerpc/sysdev/dart_iommu.c +++ b/arch/powerpc/sysdev/dart_iommu.c | |||
| @@ -101,8 +101,8 @@ retry: | |||
| 101 | if (l == (1L << limit)) { | 101 | if (l == (1L << limit)) { |
| 102 | if (limit < 4) { | 102 | if (limit < 4) { |
| 103 | limit++; | 103 | limit++; |
| 104 | reg = DART_IN(DART_CNTL); | 104 | reg = DART_IN(DART_CNTL); |
| 105 | reg &= ~inv_bit; | 105 | reg &= ~inv_bit; |
| 106 | DART_OUT(DART_CNTL, reg); | 106 | DART_OUT(DART_CNTL, reg); |
| 107 | goto retry; | 107 | goto retry; |
| 108 | } else | 108 | } else |
| @@ -111,11 +111,39 @@ retry: | |||
| 111 | } | 111 | } |
| 112 | } | 112 | } |
| 113 | 113 | ||
| 114 | static inline void dart_tlb_invalidate_one(unsigned long bus_rpn) | ||
| 115 | { | ||
| 116 | unsigned int reg; | ||
| 117 | unsigned int l, limit; | ||
| 118 | |||
| 119 | reg = DART_CNTL_U4_ENABLE | DART_CNTL_U4_IONE | | ||
| 120 | (bus_rpn & DART_CNTL_U4_IONE_MASK); | ||
| 121 | DART_OUT(DART_CNTL, reg); | ||
| 122 | |||
| 123 | limit = 0; | ||
| 124 | wait_more: | ||
| 125 | l = 0; | ||
| 126 | while ((DART_IN(DART_CNTL) & DART_CNTL_U4_IONE) && l < (1L << limit)) { | ||
| 127 | rmb(); | ||
| 128 | l++; | ||
| 129 | } | ||
| 130 | |||
| 131 | if (l == (1L << limit)) { | ||
| 132 | if (limit < 4) { | ||
| 133 | limit++; | ||
| 134 | goto wait_more; | ||
| 135 | } else | ||
| 136 | panic("DART: TLB did not flush after waiting a long " | ||
| 137 | "time. Buggy U4 ?"); | ||
| 138 | } | ||
| 139 | } | ||
| 140 | |||
| 114 | static void dart_flush(struct iommu_table *tbl) | 141 | static void dart_flush(struct iommu_table *tbl) |
| 115 | { | 142 | { |
| 116 | if (dart_dirty) | 143 | if (dart_dirty) { |
| 117 | dart_tlb_invalidate_all(); | 144 | dart_tlb_invalidate_all(); |
| 118 | dart_dirty = 0; | 145 | dart_dirty = 0; |
| 146 | } | ||
| 119 | } | 147 | } |
| 120 | 148 | ||
| 121 | static void dart_build(struct iommu_table *tbl, long index, | 149 | static void dart_build(struct iommu_table *tbl, long index, |
| @@ -124,6 +152,7 @@ static void dart_build(struct iommu_table *tbl, long index, | |||
| 124 | { | 152 | { |
| 125 | unsigned int *dp; | 153 | unsigned int *dp; |
| 126 | unsigned int rpn; | 154 | unsigned int rpn; |
| 155 | long l; | ||
| 127 | 156 | ||
| 128 | DBG("dart: build at: %lx, %lx, addr: %x\n", index, npages, uaddr); | 157 | DBG("dart: build at: %lx, %lx, addr: %x\n", index, npages, uaddr); |
| 129 | 158 | ||
| @@ -135,7 +164,8 @@ static void dart_build(struct iommu_table *tbl, long index, | |||
| 135 | /* On U3, all memory is contigous, so we can move this | 164 | /* On U3, all memory is contigous, so we can move this |
| 136 | * out of the loop. | 165 | * out of the loop. |
| 137 | */ | 166 | */ |
| 138 | while (npages--) { | 167 | l = npages; |
| 168 | while (l--) { | ||
| 139 | rpn = virt_to_abs(uaddr) >> DART_PAGE_SHIFT; | 169 | rpn = virt_to_abs(uaddr) >> DART_PAGE_SHIFT; |
| 140 | 170 | ||
| 141 | *(dp++) = DARTMAP_VALID | (rpn & DARTMAP_RPNMASK); | 171 | *(dp++) = DARTMAP_VALID | (rpn & DARTMAP_RPNMASK); |
| @@ -143,7 +173,14 @@ static void dart_build(struct iommu_table *tbl, long index, | |||
| 143 | uaddr += DART_PAGE_SIZE; | 173 | uaddr += DART_PAGE_SIZE; |
| 144 | } | 174 | } |
| 145 | 175 | ||
| 146 | dart_dirty = 1; | 176 | if (dart_is_u4) { |
| 177 | rpn = index; | ||
| 178 | mb(); /* make sure all updates have reached memory */ | ||
| 179 | while (npages--) | ||
| 180 | dart_tlb_invalidate_one(rpn++); | ||
| 181 | } else { | ||
| 182 | dart_dirty = 1; | ||
| 183 | } | ||
| 147 | } | 184 | } |
| 148 | 185 | ||
| 149 | 186 | ||
diff --git a/arch/powerpc/sysdev/todc.c b/arch/powerpc/sysdev/todc.c new file mode 100644 index 000000000000..0a65980efb50 --- /dev/null +++ b/arch/powerpc/sysdev/todc.c | |||
| @@ -0,0 +1,392 @@ | |||
| 1 | /* | ||
| 2 | * Time of Day Clock support for the M48T35, M48T37, M48T59, and MC146818 | ||
| 3 | * Real Time Clocks/Timekeepers. | ||
| 4 | * | ||
| 5 | * Author: Mark A. Greer <mgreer@mvista.com> | ||
| 6 | * | ||
| 7 | * 2001-2004 (c) MontaVista, Software, Inc. This file is licensed under | ||
| 8 | * the terms of the GNU General Public License version 2. This program | ||
| 9 | * is licensed "as is" without any warranty of any kind, whether express | ||
| 10 | * or implied. | ||
| 11 | */ | ||
| 12 | #include <linux/errno.h> | ||
| 13 | #include <linux/init.h> | ||
| 14 | #include <linux/kernel.h> | ||
| 15 | #include <linux/time.h> | ||
| 16 | #include <linux/timex.h> | ||
| 17 | #include <linux/bcd.h> | ||
| 18 | #include <linux/mc146818rtc.h> | ||
| 19 | |||
| 20 | #include <asm/machdep.h> | ||
| 21 | #include <asm/io.h> | ||
| 22 | #include <asm/time.h> | ||
| 23 | #include <asm/todc.h> | ||
| 24 | |||
| 25 | /* | ||
| 26 | * Depending on the hardware on your board and your board design, the | ||
| 27 | * RTC/NVRAM may be accessed either directly (like normal memory) or via | ||
| 28 | * address/data registers. If your board uses the direct method, set | ||
| 29 | * 'nvram_data' to the base address of your nvram and leave 'nvram_as0' and | ||
| 30 | * 'nvram_as1' NULL. If your board uses address/data regs to access nvram, | ||
| 31 | * set 'nvram_as0' to the address of the lower byte, set 'nvram_as1' to the | ||
| 32 | * address of the upper byte (leave NULL if using mc146818), and set | ||
| 33 | * 'nvram_data' to the address of the 8-bit data register. | ||
| 34 | * | ||
| 35 | * Note: Even though the documentation for the various RTC chips say that it | ||
| 36 | * take up to a second before it starts updating once the 'R' bit is | ||
| 37 | * cleared, they always seem to update even though we bang on it many | ||
| 38 | * times a second. This is true, except for the Dallas Semi 1746/1747 | ||
| 39 | * (possibly others). Those chips seem to have a real problem whenever | ||
| 40 | * we set the 'R' bit before reading them, they basically stop counting. | ||
| 41 | * --MAG | ||
| 42 | */ | ||
| 43 | |||
| 44 | /* | ||
| 45 | * 'todc_info' should be initialized in your *_setup.c file to | ||
| 46 | * point to a fully initialized 'todc_info_t' structure. | ||
| 47 | * This structure holds all the register offsets for your particular | ||
| 48 | * TODC/RTC chip. | ||
| 49 | * TODC_ALLOC()/TODC_INIT() will allocate and initialize this table for you. | ||
| 50 | */ | ||
| 51 | |||
| 52 | #ifdef RTC_FREQ_SELECT | ||
| 53 | #undef RTC_FREQ_SELECT | ||
| 54 | #define RTC_FREQ_SELECT control_b /* Register A */ | ||
| 55 | #endif | ||
| 56 | |||
| 57 | #ifdef RTC_CONTROL | ||
| 58 | #undef RTC_CONTROL | ||
| 59 | #define RTC_CONTROL control_a /* Register B */ | ||
| 60 | #endif | ||
| 61 | |||
| 62 | #ifdef RTC_INTR_FLAGS | ||
| 63 | #undef RTC_INTR_FLAGS | ||
| 64 | #define RTC_INTR_FLAGS watchdog /* Register C */ | ||
| 65 | #endif | ||
| 66 | |||
| 67 | #ifdef RTC_VALID | ||
| 68 | #undef RTC_VALID | ||
| 69 | #define RTC_VALID interrupts /* Register D */ | ||
| 70 | #endif | ||
| 71 | |||
| 72 | /* Access routines when RTC accessed directly (like normal memory) */ | ||
| 73 | u_char | ||
| 74 | todc_direct_read_val(int addr) | ||
| 75 | { | ||
| 76 | return readb((void __iomem *)(todc_info->nvram_data + addr)); | ||
| 77 | } | ||
| 78 | |||
| 79 | void | ||
| 80 | todc_direct_write_val(int addr, unsigned char val) | ||
| 81 | { | ||
| 82 | writeb(val, (void __iomem *)(todc_info->nvram_data + addr)); | ||
| 83 | return; | ||
| 84 | } | ||
| 85 | |||
| 86 | /* Access routines for accessing m48txx type chips via addr/data regs */ | ||
| 87 | u_char | ||
| 88 | todc_m48txx_read_val(int addr) | ||
| 89 | { | ||
| 90 | outb(addr, todc_info->nvram_as0); | ||
| 91 | outb(addr>>todc_info->as0_bits, todc_info->nvram_as1); | ||
| 92 | return inb(todc_info->nvram_data); | ||
| 93 | } | ||
| 94 | |||
| 95 | void | ||
| 96 | todc_m48txx_write_val(int addr, unsigned char val) | ||
| 97 | { | ||
| 98 | outb(addr, todc_info->nvram_as0); | ||
| 99 | outb(addr>>todc_info->as0_bits, todc_info->nvram_as1); | ||
| 100 | outb(val, todc_info->nvram_data); | ||
| 101 | return; | ||
| 102 | } | ||
| 103 | |||
| 104 | /* Access routines for accessing mc146818 type chips via addr/data regs */ | ||
| 105 | u_char | ||
| 106 | todc_mc146818_read_val(int addr) | ||
| 107 | { | ||
| 108 | outb_p(addr, todc_info->nvram_as0); | ||
| 109 | return inb_p(todc_info->nvram_data); | ||
| 110 | } | ||
| 111 | |||
| 112 | void | ||
| 113 | todc_mc146818_write_val(int addr, unsigned char val) | ||
| 114 | { | ||
| 115 | outb_p(addr, todc_info->nvram_as0); | ||
| 116 | outb_p(val, todc_info->nvram_data); | ||
| 117 | } | ||
| 118 | |||
| 119 | |||
| 120 | /* | ||
| 121 | * Routines to make RTC chips with NVRAM buried behind an addr/data pair | ||
| 122 | * have the NVRAM and clock regs appear at the same level. | ||
| 123 | * The NVRAM will appear to start at addr 0 and the clock regs will appear | ||
| 124 | * to start immediately after the NVRAM (actually, start at offset | ||
| 125 | * todc_info->nvram_size). | ||
| 126 | */ | ||
| 127 | static inline u_char | ||
| 128 | todc_read_val(int addr) | ||
| 129 | { | ||
| 130 | u_char val; | ||
| 131 | |||
| 132 | if (todc_info->sw_flags & TODC_FLAG_2_LEVEL_NVRAM) { | ||
| 133 | if (addr < todc_info->nvram_size) { /* NVRAM */ | ||
| 134 | ppc_md.rtc_write_val(todc_info->nvram_addr_reg, addr); | ||
| 135 | val = ppc_md.rtc_read_val(todc_info->nvram_data_reg); | ||
| 136 | } else { /* Clock Reg */ | ||
| 137 | addr -= todc_info->nvram_size; | ||
| 138 | val = ppc_md.rtc_read_val(addr); | ||
| 139 | } | ||
| 140 | } else | ||
| 141 | val = ppc_md.rtc_read_val(addr); | ||
| 142 | |||
| 143 | return val; | ||
| 144 | } | ||
| 145 | |||
| 146 | static inline void | ||
| 147 | todc_write_val(int addr, u_char val) | ||
| 148 | { | ||
| 149 | if (todc_info->sw_flags & TODC_FLAG_2_LEVEL_NVRAM) { | ||
| 150 | if (addr < todc_info->nvram_size) { /* NVRAM */ | ||
| 151 | ppc_md.rtc_write_val(todc_info->nvram_addr_reg, addr); | ||
| 152 | ppc_md.rtc_write_val(todc_info->nvram_data_reg, val); | ||
| 153 | } else { /* Clock Reg */ | ||
| 154 | addr -= todc_info->nvram_size; | ||
| 155 | ppc_md.rtc_write_val(addr, val); | ||
| 156 | } | ||
| 157 | } else | ||
| 158 | ppc_md.rtc_write_val(addr, val); | ||
| 159 | } | ||
| 160 | |||
| 161 | /* | ||
| 162 | * TODC routines | ||
| 163 | * | ||
| 164 | * There is some ugly stuff in that there are assumptions for the mc146818. | ||
| 165 | * | ||
| 166 | * Assumptions: | ||
| 167 | * - todc_info->control_a has the offset as mc146818 Register B reg | ||
| 168 | * - todc_info->control_b has the offset as mc146818 Register A reg | ||
| 169 | * - m48txx control reg's write enable or 'W' bit is same as | ||
| 170 | * mc146818 Register B 'SET' bit (i.e., 0x80) | ||
| 171 | * | ||
| 172 | * These assumptions were made to make the code simpler. | ||
| 173 | */ | ||
| 174 | long __init | ||
| 175 | todc_time_init(void) | ||
| 176 | { | ||
| 177 | u_char cntl_b; | ||
| 178 | |||
| 179 | if (!ppc_md.rtc_read_val) | ||
| 180 | ppc_md.rtc_read_val = ppc_md.nvram_read_val; | ||
| 181 | if (!ppc_md.rtc_write_val) | ||
| 182 | ppc_md.rtc_write_val = ppc_md.nvram_write_val; | ||
| 183 | |||
| 184 | cntl_b = todc_read_val(todc_info->control_b); | ||
| 185 | |||
| 186 | if (todc_info->rtc_type == TODC_TYPE_MC146818) { | ||
| 187 | if ((cntl_b & 0x70) != 0x20) { | ||
| 188 | printk(KERN_INFO "TODC real-time-clock was stopped." | ||
| 189 | " Now starting..."); | ||
| 190 | cntl_b &= ~0x70; | ||
| 191 | cntl_b |= 0x20; | ||
| 192 | } | ||
| 193 | |||
| 194 | todc_write_val(todc_info->control_b, cntl_b); | ||
| 195 | } else if (todc_info->rtc_type == TODC_TYPE_DS17285) { | ||
| 196 | u_char mode; | ||
| 197 | |||
| 198 | mode = todc_read_val(TODC_TYPE_DS17285_CNTL_A); | ||
| 199 | /* Make sure countdown clear is not set */ | ||
| 200 | mode &= ~0x40; | ||
| 201 | /* Enable oscillator, extended register set */ | ||
| 202 | mode |= 0x30; | ||
| 203 | todc_write_val(TODC_TYPE_DS17285_CNTL_A, mode); | ||
| 204 | |||
| 205 | } else if (todc_info->rtc_type == TODC_TYPE_DS1501) { | ||
| 206 | u_char month; | ||
| 207 | |||
| 208 | todc_info->enable_read = TODC_DS1501_CNTL_B_TE; | ||
| 209 | todc_info->enable_write = TODC_DS1501_CNTL_B_TE; | ||
| 210 | |||
| 211 | month = todc_read_val(todc_info->month); | ||
| 212 | |||
| 213 | if ((month & 0x80) == 0x80) { | ||
| 214 | printk(KERN_INFO "TODC %s %s\n", | ||
| 215 | "real-time-clock was stopped.", | ||
| 216 | "Now starting..."); | ||
| 217 | month &= ~0x80; | ||
| 218 | todc_write_val(todc_info->month, month); | ||
| 219 | } | ||
| 220 | |||
| 221 | cntl_b &= ~TODC_DS1501_CNTL_B_TE; | ||
| 222 | todc_write_val(todc_info->control_b, cntl_b); | ||
| 223 | } else { /* must be a m48txx type */ | ||
| 224 | u_char cntl_a; | ||
| 225 | |||
| 226 | todc_info->enable_read = TODC_MK48TXX_CNTL_A_R; | ||
| 227 | todc_info->enable_write = TODC_MK48TXX_CNTL_A_W; | ||
| 228 | |||
| 229 | cntl_a = todc_read_val(todc_info->control_a); | ||
| 230 | |||
| 231 | /* Check & clear STOP bit in control B register */ | ||
| 232 | if (cntl_b & TODC_MK48TXX_DAY_CB) { | ||
| 233 | printk(KERN_INFO "TODC %s %s\n", | ||
| 234 | "real-time-clock was stopped.", | ||
| 235 | "Now starting..."); | ||
| 236 | |||
| 237 | cntl_a |= todc_info->enable_write; | ||
| 238 | cntl_b &= ~TODC_MK48TXX_DAY_CB;/* Start Oscil */ | ||
| 239 | |||
| 240 | todc_write_val(todc_info->control_a, cntl_a); | ||
| 241 | todc_write_val(todc_info->control_b, cntl_b); | ||
| 242 | } | ||
| 243 | |||
| 244 | /* Make sure READ & WRITE bits are cleared. */ | ||
| 245 | cntl_a &= ~(todc_info->enable_write | todc_info->enable_read); | ||
| 246 | todc_write_val(todc_info->control_a, cntl_a); | ||
| 247 | } | ||
| 248 | |||
| 249 | return 0; | ||
| 250 | } | ||
| 251 | |||
| 252 | /* | ||
| 253 | * There is some ugly stuff in that there are assumptions that for a mc146818, | ||
| 254 | * the todc_info->control_a has the offset of the mc146818 Register B reg and | ||
| 255 | * that the register'ss 'SET' bit is the same as the m48txx's write enable | ||
| 256 | * bit in the control register of the m48txx (i.e., 0x80). | ||
| 257 | * | ||
| 258 | * It was done to make the code look simpler. | ||
| 259 | */ | ||
| 260 | void | ||
| 261 | todc_get_rtc_time(struct rtc_time *tm) | ||
| 262 | { | ||
| 263 | uint year = 0, mon = 0, mday = 0, hour = 0, min = 0, sec = 0; | ||
| 264 | uint limit, i; | ||
| 265 | u_char save_control, uip = 0; | ||
| 266 | extern void GregorianDay(struct rtc_time *); | ||
| 267 | |||
| 268 | spin_lock(&rtc_lock); | ||
| 269 | save_control = todc_read_val(todc_info->control_a); | ||
| 270 | |||
| 271 | if (todc_info->rtc_type != TODC_TYPE_MC146818) { | ||
| 272 | limit = 1; | ||
| 273 | |||
| 274 | switch (todc_info->rtc_type) { | ||
| 275 | case TODC_TYPE_DS1553: | ||
| 276 | case TODC_TYPE_DS1557: | ||
| 277 | case TODC_TYPE_DS1743: | ||
| 278 | case TODC_TYPE_DS1746: /* XXXX BAD HACK -> FIX */ | ||
| 279 | case TODC_TYPE_DS1747: | ||
| 280 | case TODC_TYPE_DS17285: | ||
| 281 | break; | ||
| 282 | default: | ||
| 283 | todc_write_val(todc_info->control_a, | ||
| 284 | (save_control | todc_info->enable_read)); | ||
| 285 | } | ||
| 286 | } else | ||
| 287 | limit = 100000000; | ||
| 288 | |||
| 289 | for (i=0; i<limit; i++) { | ||
| 290 | if (todc_info->rtc_type == TODC_TYPE_MC146818) | ||
| 291 | uip = todc_read_val(todc_info->RTC_FREQ_SELECT); | ||
| 292 | |||
| 293 | sec = todc_read_val(todc_info->seconds) & 0x7f; | ||
| 294 | min = todc_read_val(todc_info->minutes) & 0x7f; | ||
| 295 | hour = todc_read_val(todc_info->hours) & 0x3f; | ||
| 296 | mday = todc_read_val(todc_info->day_of_month) & 0x3f; | ||
| 297 | mon = todc_read_val(todc_info->month) & 0x1f; | ||
| 298 | year = todc_read_val(todc_info->year) & 0xff; | ||
| 299 | |||
| 300 | if (todc_info->rtc_type == TODC_TYPE_MC146818) { | ||
| 301 | uip |= todc_read_val(todc_info->RTC_FREQ_SELECT); | ||
| 302 | if ((uip & RTC_UIP) == 0) | ||
| 303 | break; | ||
| 304 | } | ||
| 305 | } | ||
| 306 | |||
| 307 | if (todc_info->rtc_type != TODC_TYPE_MC146818) { | ||
| 308 | switch (todc_info->rtc_type) { | ||
| 309 | case TODC_TYPE_DS1553: | ||
| 310 | case TODC_TYPE_DS1557: | ||
| 311 | case TODC_TYPE_DS1743: | ||
| 312 | case TODC_TYPE_DS1746: /* XXXX BAD HACK -> FIX */ | ||
| 313 | case TODC_TYPE_DS1747: | ||
| 314 | case TODC_TYPE_DS17285: | ||
| 315 | break; | ||
| 316 | default: | ||
| 317 | save_control &= ~(todc_info->enable_read); | ||
| 318 | todc_write_val(todc_info->control_a, save_control); | ||
| 319 | } | ||
| 320 | } | ||
| 321 | spin_unlock(&rtc_lock); | ||
| 322 | |||
| 323 | if ((todc_info->rtc_type != TODC_TYPE_MC146818) | ||
| 324 | || ((save_control & RTC_DM_BINARY) == 0) | ||
| 325 | || RTC_ALWAYS_BCD) { | ||
| 326 | BCD_TO_BIN(sec); | ||
| 327 | BCD_TO_BIN(min); | ||
| 328 | BCD_TO_BIN(hour); | ||
| 329 | BCD_TO_BIN(mday); | ||
| 330 | BCD_TO_BIN(mon); | ||
| 331 | BCD_TO_BIN(year); | ||
| 332 | } | ||
| 333 | |||
| 334 | if ((year + 1900) < 1970) { | ||
| 335 | year += 100; | ||
| 336 | } | ||
| 337 | |||
| 338 | tm->tm_sec = sec; | ||
| 339 | tm->tm_min = min; | ||
| 340 | tm->tm_hour = hour; | ||
| 341 | tm->tm_mday = mday; | ||
| 342 | tm->tm_mon = mon; | ||
| 343 | tm->tm_year = year; | ||
| 344 | |||
| 345 | GregorianDay(tm); | ||
| 346 | } | ||
| 347 | |||
| 348 | int | ||
| 349 | todc_set_rtc_time(struct rtc_time *tm) | ||
| 350 | { | ||
| 351 | u_char save_control, save_freq_select = 0; | ||
| 352 | |||
| 353 | spin_lock(&rtc_lock); | ||
| 354 | save_control = todc_read_val(todc_info->control_a); | ||
| 355 | |||
| 356 | /* Assuming MK48T59_RTC_CA_WRITE & RTC_SET are equal */ | ||
| 357 | todc_write_val(todc_info->control_a, | ||
| 358 | (save_control | todc_info->enable_write)); | ||
| 359 | save_control &= ~(todc_info->enable_write); /* in case it was set */ | ||
| 360 | |||
| 361 | if (todc_info->rtc_type == TODC_TYPE_MC146818) { | ||
| 362 | save_freq_select = todc_read_val(todc_info->RTC_FREQ_SELECT); | ||
| 363 | todc_write_val(todc_info->RTC_FREQ_SELECT, | ||
| 364 | save_freq_select | RTC_DIV_RESET2); | ||
| 365 | } | ||
| 366 | |||
| 367 | if ((todc_info->rtc_type != TODC_TYPE_MC146818) | ||
| 368 | || ((save_control & RTC_DM_BINARY) == 0) | ||
| 369 | || RTC_ALWAYS_BCD) { | ||
| 370 | BIN_TO_BCD(tm->tm_sec); | ||
| 371 | BIN_TO_BCD(tm->tm_min); | ||
| 372 | BIN_TO_BCD(tm->tm_hour); | ||
| 373 | BIN_TO_BCD(tm->tm_mon); | ||
| 374 | BIN_TO_BCD(tm->tm_mday); | ||
| 375 | BIN_TO_BCD(tm->tm_year); | ||
| 376 | } | ||
| 377 | |||
| 378 | todc_write_val(todc_info->seconds, tm->tm_sec); | ||
| 379 | todc_write_val(todc_info->minutes, tm->tm_min); | ||
| 380 | todc_write_val(todc_info->hours, tm->tm_hour); | ||
| 381 | todc_write_val(todc_info->month, tm->tm_mon); | ||
| 382 | todc_write_val(todc_info->day_of_month, tm->tm_mday); | ||
| 383 | todc_write_val(todc_info->year, tm->tm_year); | ||
| 384 | |||
| 385 | todc_write_val(todc_info->control_a, save_control); | ||
| 386 | |||
| 387 | if (todc_info->rtc_type == TODC_TYPE_MC146818) | ||
| 388 | todc_write_val(todc_info->RTC_FREQ_SELECT, save_freq_select); | ||
| 389 | |||
| 390 | spin_unlock(&rtc_lock); | ||
| 391 | return 0; | ||
| 392 | } | ||
diff --git a/arch/powerpc/sysdev/tsi108_dev.c b/arch/powerpc/sysdev/tsi108_dev.c new file mode 100644 index 000000000000..26a0cc820cde --- /dev/null +++ b/arch/powerpc/sysdev/tsi108_dev.c | |||
| @@ -0,0 +1,145 @@ | |||
| 1 | /* | ||
| 2 | * tsi108/109 device setup code | ||
| 3 | * | ||
| 4 | * Maintained by Roy Zang < tie-fei.zang@freescale.com > | ||
| 5 | * | ||
| 6 | * This program is free software; you can redistribute it and/or modify it | ||
| 7 | * under the terms of the GNU General Public License as published by the | ||
| 8 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 9 | * option) any later version. | ||
| 10 | */ | ||
| 11 | |||
| 12 | #include <linux/config.h> | ||
| 13 | #include <linux/stddef.h> | ||
| 14 | #include <linux/kernel.h> | ||
| 15 | #include <linux/init.h> | ||
| 16 | #include <linux/errno.h> | ||
| 17 | #include <linux/major.h> | ||
| 18 | #include <linux/delay.h> | ||
| 19 | #include <linux/irq.h> | ||
| 20 | #include <linux/module.h> | ||
| 21 | #include <linux/device.h> | ||
| 22 | #include <linux/platform_device.h> | ||
| 23 | #include <asm/tsi108.h> | ||
| 24 | |||
| 25 | #include <asm/system.h> | ||
| 26 | #include <asm/atomic.h> | ||
| 27 | #include <asm/io.h> | ||
| 28 | #include <asm/irq.h> | ||
| 29 | #include <asm/prom.h> | ||
| 30 | #include <mm/mmu_decl.h> | ||
| 31 | |||
| 32 | #undef DEBUG | ||
| 33 | |||
| 34 | #ifdef DEBUG | ||
| 35 | #define DBG(fmt...) do { printk(fmt); } while(0) | ||
| 36 | #else | ||
| 37 | #define DBG(fmt...) do { } while(0) | ||
| 38 | #endif | ||
| 39 | |||
| 40 | static phys_addr_t tsi108_csr_base = -1; | ||
| 41 | |||
| 42 | phys_addr_t get_csrbase(void) | ||
| 43 | { | ||
| 44 | struct device_node *tsi; | ||
| 45 | |||
| 46 | if (tsi108_csr_base != -1) | ||
| 47 | return tsi108_csr_base; | ||
| 48 | |||
| 49 | tsi = of_find_node_by_type(NULL, "tsi-bridge"); | ||
| 50 | if (tsi) { | ||
| 51 | unsigned int size; | ||
| 52 | void *prop = get_property(tsi, "reg", &size); | ||
| 53 | tsi108_csr_base = of_translate_address(tsi, prop); | ||
| 54 | of_node_put(tsi); | ||
| 55 | }; | ||
| 56 | return tsi108_csr_base; | ||
| 57 | } | ||
| 58 | |||
| 59 | u32 get_vir_csrbase(void) | ||
| 60 | { | ||
| 61 | return (u32) (ioremap(get_csrbase(), 0x10000)); | ||
| 62 | } | ||
| 63 | |||
| 64 | EXPORT_SYMBOL(get_csrbase); | ||
| 65 | EXPORT_SYMBOL(get_vir_csrbase); | ||
| 66 | |||
| 67 | static int __init tsi108_eth_of_init(void) | ||
| 68 | { | ||
| 69 | struct device_node *np; | ||
| 70 | unsigned int i; | ||
| 71 | struct platform_device *tsi_eth_dev; | ||
| 72 | struct resource res; | ||
| 73 | int ret; | ||
| 74 | |||
| 75 | for (np = NULL, i = 0; | ||
| 76 | (np = of_find_compatible_node(np, "network", "tsi-ethernet")) != NULL; | ||
| 77 | i++) { | ||
| 78 | struct resource r[2]; | ||
| 79 | struct device_node *phy; | ||
| 80 | hw_info tsi_eth_data; | ||
| 81 | unsigned int *id; | ||
| 82 | unsigned int *phy_id; | ||
| 83 | void *mac_addr; | ||
| 84 | phandle *ph; | ||
| 85 | |||
| 86 | memset(r, 0, sizeof(r)); | ||
| 87 | memset(&tsi_eth_data, 0, sizeof(tsi_eth_data)); | ||
| 88 | |||
| 89 | ret = of_address_to_resource(np, 0, &r[0]); | ||
| 90 | DBG("%s: name:start->end = %s:0x%lx-> 0x%lx\n", | ||
| 91 | __FUNCTION__,r[0].name, r[0].start, r[0].end); | ||
| 92 | if (ret) | ||
| 93 | goto err; | ||
| 94 | |||
| 95 | r[1].name = "tx"; | ||
| 96 | r[1].start = np->intrs[0].line; | ||
| 97 | r[1].end = np->intrs[0].line; | ||
| 98 | r[1].flags = IORESOURCE_IRQ; | ||
| 99 | |||
| 100 | tsi_eth_dev = | ||
| 101 | platform_device_register_simple("tsi-ethernet", i, &r[0], | ||
| 102 | np->n_intrs + 1); | ||
| 103 | |||
| 104 | if (IS_ERR(tsi_eth_dev)) { | ||
| 105 | ret = PTR_ERR(tsi_eth_dev); | ||
| 106 | goto err; | ||
| 107 | } | ||
| 108 | |||
| 109 | mac_addr = get_property(np, "address", NULL); | ||
| 110 | memcpy(tsi_eth_data.mac_addr, mac_addr, 6); | ||
| 111 | |||
| 112 | ph = (phandle *) get_property(np, "phy-handle", NULL); | ||
| 113 | phy = of_find_node_by_phandle(*ph); | ||
| 114 | |||
| 115 | if (phy == NULL) { | ||
| 116 | ret = -ENODEV; | ||
| 117 | goto unreg; | ||
| 118 | } | ||
| 119 | |||
| 120 | id = (u32 *) get_property(phy, "reg", NULL); | ||
| 121 | phy_id = (u32 *) get_property(phy, "phy-id", NULL); | ||
| 122 | ret = of_address_to_resource(phy, 0, &res); | ||
| 123 | if (ret) { | ||
| 124 | of_node_put(phy); | ||
| 125 | goto unreg; | ||
| 126 | } | ||
| 127 | tsi_eth_data.regs = r[0].start; | ||
| 128 | tsi_eth_data.phyregs = res.start; | ||
| 129 | tsi_eth_data.phy = *phy_id; | ||
| 130 | tsi_eth_data.irq_num = np->intrs[0].line; | ||
| 131 | of_node_put(phy); | ||
| 132 | ret = | ||
| 133 | platform_device_add_data(tsi_eth_dev, &tsi_eth_data, | ||
| 134 | sizeof(hw_info)); | ||
| 135 | if (ret) | ||
| 136 | goto unreg; | ||
| 137 | } | ||
| 138 | return 0; | ||
| 139 | unreg: | ||
| 140 | platform_device_unregister(tsi_eth_dev); | ||
| 141 | err: | ||
| 142 | return ret; | ||
| 143 | } | ||
| 144 | |||
| 145 | arch_initcall(tsi108_eth_of_init); | ||
diff --git a/arch/powerpc/sysdev/tsi108_pci.c b/arch/powerpc/sysdev/tsi108_pci.c new file mode 100644 index 000000000000..3265d54c82ed --- /dev/null +++ b/arch/powerpc/sysdev/tsi108_pci.c | |||
| @@ -0,0 +1,412 @@ | |||
| 1 | /* | ||
| 2 | * Common routines for Tundra Semiconductor TSI108 host bridge. | ||
| 3 | * | ||
| 4 | * 2004-2005 (c) Tundra Semiconductor Corp. | ||
| 5 | * Author: Alex Bounine (alexandreb@tundra.com) | ||
| 6 | * | ||
| 7 | * This program is free software; you can redistribute it and/or modify it | ||
| 8 | * under the terms of the GNU General Public License as published by the Free | ||
| 9 | * Software Foundation; either version 2 of the License, or (at your option) | ||
| 10 | * any later version. | ||
| 11 | * | ||
| 12 | * This program is distributed in the hope that it will be useful, but WITHOUT | ||
| 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
| 14 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
| 15 | * more details. | ||
| 16 | * | ||
| 17 | * You should have received a copy of the GNU General Public License along with | ||
| 18 | * this program; if not, write to the Free Software Foundation, Inc., 59 | ||
| 19 | * Temple Place - Suite 330, Boston, MA 02111-1307, USA. | ||
| 20 | */ | ||
| 21 | |||
| 22 | #include <linux/kernel.h> | ||
| 23 | #include <linux/init.h> | ||
| 24 | #include <linux/pci.h> | ||
| 25 | #include <linux/slab.h> | ||
| 26 | #include <linux/irq.h> | ||
| 27 | #include <linux/interrupt.h> | ||
| 28 | |||
| 29 | |||
| 30 | #include <asm/byteorder.h> | ||
| 31 | #include <asm/io.h> | ||
| 32 | #include <asm/irq.h> | ||
| 33 | #include <asm/uaccess.h> | ||
| 34 | #include <asm/machdep.h> | ||
| 35 | #include <asm/pci-bridge.h> | ||
| 36 | #include <asm/tsi108.h> | ||
| 37 | #include <asm/tsi108_irq.h> | ||
| 38 | #include <asm/prom.h> | ||
| 39 | |||
| 40 | #undef DEBUG | ||
| 41 | #ifdef DEBUG | ||
| 42 | #define DBG(x...) printk(x) | ||
| 43 | #else | ||
| 44 | #define DBG(x...) | ||
| 45 | #endif | ||
| 46 | |||
| 47 | #define tsi_mk_config_addr(bus, devfunc, offset) \ | ||
| 48 | ((((bus)<<16) | ((devfunc)<<8) | (offset & 0xfc)) + tsi108_pci_cfg_base) | ||
| 49 | |||
| 50 | u32 tsi108_pci_cfg_base; | ||
| 51 | u32 tsi108_csr_vir_base; | ||
| 52 | |||
| 53 | extern u32 get_vir_csrbase(void); | ||
| 54 | extern u32 tsi108_read_reg(u32 reg_offset); | ||
| 55 | extern void tsi108_write_reg(u32 reg_offset, u32 val); | ||
| 56 | |||
| 57 | int | ||
| 58 | tsi108_direct_write_config(struct pci_bus *bus, unsigned int devfunc, | ||
| 59 | int offset, int len, u32 val) | ||
| 60 | { | ||
| 61 | volatile unsigned char *cfg_addr; | ||
| 62 | |||
| 63 | if (ppc_md.pci_exclude_device) | ||
| 64 | if (ppc_md.pci_exclude_device(bus->number, devfunc)) | ||
| 65 | return PCIBIOS_DEVICE_NOT_FOUND; | ||
| 66 | |||
| 67 | cfg_addr = (unsigned char *)(tsi_mk_config_addr(bus->number, | ||
| 68 | devfunc, offset) | | ||
| 69 | (offset & 0x03)); | ||
| 70 | |||
| 71 | #ifdef DEBUG | ||
| 72 | printk("PCI CFG write : "); | ||
| 73 | printk("%d:0x%x:0x%x ", bus->number, devfunc, offset); | ||
| 74 | printk("%d ADDR=0x%08x ", len, (uint) cfg_addr); | ||
| 75 | printk("data = 0x%08x\n", val); | ||
| 76 | #endif | ||
| 77 | |||
| 78 | switch (len) { | ||
| 79 | case 1: | ||
| 80 | out_8((u8 *) cfg_addr, val); | ||
| 81 | break; | ||
| 82 | case 2: | ||
| 83 | out_le16((u16 *) cfg_addr, val); | ||
| 84 | break; | ||
| 85 | default: | ||
| 86 | out_le32((u32 *) cfg_addr, val); | ||
| 87 | break; | ||
| 88 | } | ||
| 89 | |||
| 90 | return PCIBIOS_SUCCESSFUL; | ||
| 91 | } | ||
| 92 | |||
| 93 | void tsi108_clear_pci_error(u32 pci_cfg_base) | ||
| 94 | { | ||
| 95 | u32 err_stat, err_addr, pci_stat; | ||
| 96 | |||
| 97 | /* | ||
| 98 | * Quietly clear PB and PCI error flags set as result | ||
| 99 | * of PCI/X configuration read requests. | ||
| 100 | */ | ||
| 101 | |||
| 102 | /* Read PB Error Log Registers */ | ||
| 103 | |||
| 104 | err_stat = tsi108_read_reg(TSI108_PB_OFFSET + TSI108_PB_ERRCS); | ||
| 105 | err_addr = tsi108_read_reg(TSI108_PB_OFFSET + TSI108_PB_AERR); | ||
| 106 | |||
| 107 | if (err_stat & TSI108_PB_ERRCS_ES) { | ||
| 108 | /* Clear error flag */ | ||
| 109 | tsi108_write_reg(TSI108_PB_OFFSET + TSI108_PB_ERRCS, | ||
| 110 | TSI108_PB_ERRCS_ES); | ||
| 111 | |||
| 112 | /* Clear read error reported in PB_ISR */ | ||
| 113 | tsi108_write_reg(TSI108_PB_OFFSET + TSI108_PB_ISR, | ||
| 114 | TSI108_PB_ISR_PBS_RD_ERR); | ||
| 115 | |||
| 116 | /* Clear PCI/X bus cfg errors if applicable */ | ||
| 117 | if ((err_addr & 0xFF000000) == pci_cfg_base) { | ||
| 118 | pci_stat = | ||
| 119 | tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_CSR); | ||
| 120 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_CSR, | ||
| 121 | pci_stat); | ||
| 122 | } | ||
| 123 | } | ||
| 124 | |||
| 125 | return; | ||
| 126 | } | ||
| 127 | |||
| 128 | #define __tsi108_read_pci_config(x, addr, op) \ | ||
| 129 | __asm__ __volatile__( \ | ||
| 130 | " "op" %0,0,%1\n" \ | ||
| 131 | "1: eieio\n" \ | ||
| 132 | "2:\n" \ | ||
| 133 | ".section .fixup,\"ax\"\n" \ | ||
| 134 | "3: li %0,-1\n" \ | ||
| 135 | " b 2b\n" \ | ||
| 136 | ".section __ex_table,\"a\"\n" \ | ||
| 137 | " .align 2\n" \ | ||
| 138 | " .long 1b,3b\n" \ | ||
| 139 | ".text" \ | ||
| 140 | : "=r"(x) : "r"(addr)) | ||
| 141 | |||
| 142 | int | ||
| 143 | tsi108_direct_read_config(struct pci_bus *bus, unsigned int devfn, int offset, | ||
| 144 | int len, u32 * val) | ||
| 145 | { | ||
| 146 | volatile unsigned char *cfg_addr; | ||
| 147 | u32 temp; | ||
| 148 | |||
| 149 | if (ppc_md.pci_exclude_device) | ||
| 150 | if (ppc_md.pci_exclude_device(bus->number, devfn)) | ||
| 151 | return PCIBIOS_DEVICE_NOT_FOUND; | ||
| 152 | |||
| 153 | cfg_addr = (unsigned char *)(tsi_mk_config_addr(bus->number, | ||
| 154 | devfn, | ||
| 155 | offset) | (offset & | ||
| 156 | 0x03)); | ||
| 157 | |||
| 158 | switch (len) { | ||
| 159 | case 1: | ||
| 160 | __tsi108_read_pci_config(temp, cfg_addr, "lbzx"); | ||
| 161 | break; | ||
| 162 | case 2: | ||
| 163 | __tsi108_read_pci_config(temp, cfg_addr, "lhbrx"); | ||
| 164 | break; | ||
| 165 | default: | ||
| 166 | __tsi108_read_pci_config(temp, cfg_addr, "lwbrx"); | ||
| 167 | break; | ||
| 168 | } | ||
| 169 | |||
| 170 | *val = temp; | ||
| 171 | |||
| 172 | #ifdef DEBUG | ||
| 173 | if ((0xFFFFFFFF != temp) && (0xFFFF != temp) && (0xFF != temp)) { | ||
| 174 | printk("PCI CFG read : "); | ||
| 175 | printk("%d:0x%x:0x%x ", bus->number, devfn, offset); | ||
| 176 | printk("%d ADDR=0x%08x ", len, (uint) cfg_addr); | ||
| 177 | printk("data = 0x%x\n", *val); | ||
| 178 | } | ||
| 179 | #endif | ||
| 180 | return PCIBIOS_SUCCESSFUL; | ||
| 181 | } | ||
| 182 | |||
| 183 | void tsi108_clear_pci_cfg_error(void) | ||
| 184 | { | ||
| 185 | tsi108_clear_pci_error(TSI108_PCI_CFG_BASE_PHYS); | ||
| 186 | } | ||
| 187 | |||
| 188 | static struct pci_ops tsi108_direct_pci_ops = { | ||
| 189 | tsi108_direct_read_config, | ||
| 190 | tsi108_direct_write_config | ||
| 191 | }; | ||
| 192 | |||
| 193 | int __init tsi108_setup_pci(struct device_node *dev) | ||
| 194 | { | ||
| 195 | int len; | ||
| 196 | struct pci_controller *hose; | ||
| 197 | struct resource rsrc; | ||
| 198 | int *bus_range; | ||
| 199 | int primary = 0, has_address = 0; | ||
| 200 | |||
| 201 | /* PCI Config mapping */ | ||
| 202 | tsi108_pci_cfg_base = (u32)ioremap(TSI108_PCI_CFG_BASE_PHYS, | ||
| 203 | TSI108_PCI_CFG_SIZE); | ||
| 204 | DBG("TSI_PCI: %s tsi108_pci_cfg_base=0x%x\n", __FUNCTION__, | ||
| 205 | tsi108_pci_cfg_base); | ||
| 206 | |||
| 207 | /* Fetch host bridge registers address */ | ||
| 208 | has_address = (of_address_to_resource(dev, 0, &rsrc) == 0); | ||
| 209 | |||
| 210 | /* Get bus range if any */ | ||
| 211 | bus_range = (int *)get_property(dev, "bus-range", &len); | ||
| 212 | if (bus_range == NULL || len < 2 * sizeof(int)) { | ||
| 213 | printk(KERN_WARNING "Can't get bus-range for %s, assume" | ||
| 214 | " bus 0\n", dev->full_name); | ||
| 215 | } | ||
| 216 | |||
| 217 | hose = pcibios_alloc_controller(); | ||
| 218 | |||
| 219 | if (!hose) { | ||
| 220 | printk("PCI Host bridge init failed\n"); | ||
| 221 | return -ENOMEM; | ||
| 222 | } | ||
| 223 | hose->arch_data = dev; | ||
| 224 | hose->set_cfg_type = 1; | ||
| 225 | |||
| 226 | hose->first_busno = bus_range ? bus_range[0] : 0; | ||
| 227 | hose->last_busno = bus_range ? bus_range[1] : 0xff; | ||
| 228 | |||
| 229 | (hose)->ops = &tsi108_direct_pci_ops; | ||
| 230 | |||
| 231 | printk(KERN_INFO "Found tsi108 PCI host bridge at 0x%08lx. " | ||
| 232 | "Firmware bus number: %d->%d\n", | ||
| 233 | rsrc.start, hose->first_busno, hose->last_busno); | ||
| 234 | |||
| 235 | /* Interpret the "ranges" property */ | ||
| 236 | /* This also maps the I/O region and sets isa_io/mem_base */ | ||
| 237 | pci_process_bridge_OF_ranges(hose, dev, primary); | ||
| 238 | return 0; | ||
| 239 | } | ||
| 240 | |||
| 241 | /* | ||
| 242 | * Low level utility functions | ||
| 243 | */ | ||
| 244 | |||
| 245 | static void tsi108_pci_int_mask(u_int irq) | ||
| 246 | { | ||
| 247 | u_int irp_cfg; | ||
| 248 | int int_line = (irq - IRQ_PCI_INTAD_BASE); | ||
| 249 | |||
| 250 | irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL); | ||
| 251 | mb(); | ||
| 252 | irp_cfg |= (1 << int_line); /* INTx_DIR = output */ | ||
| 253 | irp_cfg &= ~(3 << (8 + (int_line * 2))); /* INTx_TYPE = unused */ | ||
| 254 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL, irp_cfg); | ||
| 255 | mb(); | ||
| 256 | irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL); | ||
| 257 | } | ||
| 258 | |||
| 259 | static void tsi108_pci_int_unmask(u_int irq) | ||
| 260 | { | ||
| 261 | u_int irp_cfg; | ||
| 262 | int int_line = (irq - IRQ_PCI_INTAD_BASE); | ||
| 263 | |||
| 264 | irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL); | ||
| 265 | mb(); | ||
| 266 | irp_cfg &= ~(1 << int_line); | ||
| 267 | irp_cfg |= (3 << (8 + (int_line * 2))); | ||
| 268 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL, irp_cfg); | ||
| 269 | mb(); | ||
| 270 | } | ||
| 271 | |||
| 272 | static void init_pci_source(void) | ||
| 273 | { | ||
| 274 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL, | ||
| 275 | 0x0000ff00); | ||
| 276 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE, | ||
| 277 | TSI108_PCI_IRP_ENABLE_P_INT); | ||
| 278 | mb(); | ||
| 279 | } | ||
| 280 | |||
| 281 | static inline int get_pci_source(void) | ||
| 282 | { | ||
| 283 | u_int temp = 0; | ||
| 284 | int irq = -1; | ||
| 285 | int i; | ||
| 286 | u_int pci_irp_stat; | ||
| 287 | static int mask = 0; | ||
| 288 | |||
| 289 | /* Read PCI/X block interrupt status register */ | ||
| 290 | pci_irp_stat = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_STAT); | ||
| 291 | mb(); | ||
| 292 | |||
| 293 | if (pci_irp_stat & TSI108_PCI_IRP_STAT_P_INT) { | ||
| 294 | /* Process Interrupt from PCI bus INTA# - INTD# lines */ | ||
| 295 | temp = | ||
| 296 | tsi108_read_reg(TSI108_PCI_OFFSET + | ||
| 297 | TSI108_PCI_IRP_INTAD) & 0xf; | ||
| 298 | mb(); | ||
| 299 | for (i = 0; i < 4; i++, mask++) { | ||
| 300 | if (temp & (1 << mask % 4)) { | ||
| 301 | irq = IRQ_PCI_INTA + mask % 4; | ||
| 302 | mask++; | ||
| 303 | break; | ||
| 304 | } | ||
| 305 | } | ||
| 306 | |||
| 307 | /* Disable interrupts from PCI block */ | ||
| 308 | temp = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE); | ||
| 309 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE, | ||
| 310 | temp & ~TSI108_PCI_IRP_ENABLE_P_INT); | ||
| 311 | mb(); | ||
| 312 | (void)tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE); | ||
| 313 | mb(); | ||
| 314 | } | ||
| 315 | #ifdef DEBUG | ||
| 316 | else { | ||
| 317 | printk("TSI108_PIC: error in TSI108_PCI_IRP_STAT\n"); | ||
| 318 | pci_irp_stat = | ||
| 319 | tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_STAT); | ||
| 320 | temp = | ||
| 321 | tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_INTAD); | ||
| 322 | mb(); | ||
| 323 | printk(">> stat=0x%08x intad=0x%08x ", pci_irp_stat, temp); | ||
| 324 | temp = | ||
| 325 | tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL); | ||
| 326 | mb(); | ||
| 327 | printk("cfg_ctl=0x%08x ", temp); | ||
| 328 | temp = | ||
| 329 | tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE); | ||
| 330 | mb(); | ||
| 331 | printk("irp_enable=0x%08x\n", temp); | ||
| 332 | } | ||
| 333 | #endif /* end of DEBUG */ | ||
| 334 | |||
| 335 | return irq; | ||
| 336 | } | ||
| 337 | |||
| 338 | |||
| 339 | /* | ||
| 340 | * Linux descriptor level callbacks | ||
| 341 | */ | ||
| 342 | |||
| 343 | static void tsi108_pci_irq_enable(u_int irq) | ||
| 344 | { | ||
| 345 | tsi108_pci_int_unmask(irq); | ||
| 346 | } | ||
| 347 | |||
| 348 | static void tsi108_pci_irq_disable(u_int irq) | ||
| 349 | { | ||
| 350 | tsi108_pci_int_mask(irq); | ||
| 351 | } | ||
| 352 | |||
| 353 | static void tsi108_pci_irq_ack(u_int irq) | ||
| 354 | { | ||
| 355 | tsi108_pci_int_mask(irq); | ||
| 356 | } | ||
| 357 | |||
| 358 | static void tsi108_pci_irq_end(u_int irq) | ||
| 359 | { | ||
| 360 | tsi108_pci_int_unmask(irq); | ||
| 361 | |||
| 362 | /* Enable interrupts from PCI block */ | ||
| 363 | tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE, | ||
| 364 | tsi108_read_reg(TSI108_PCI_OFFSET + | ||
| 365 | TSI108_PCI_IRP_ENABLE) | | ||
| 366 | TSI108_PCI_IRP_ENABLE_P_INT); | ||
| 367 | mb(); | ||
| 368 | } | ||
| 369 | |||
| 370 | /* | ||
| 371 | * Interrupt controller descriptor for cascaded PCI interrupt controller. | ||
| 372 | */ | ||
| 373 | |||
| 374 | struct hw_interrupt_type tsi108_pci_irq = { | ||
| 375 | .typename = "tsi108_PCI_int", | ||
| 376 | .enable = tsi108_pci_irq_enable, | ||
| 377 | .disable = tsi108_pci_irq_disable, | ||
| 378 | .ack = tsi108_pci_irq_ack, | ||
| 379 | .end = tsi108_pci_irq_end, | ||
| 380 | }; | ||
| 381 | |||
| 382 | /* | ||
| 383 | * Exported functions | ||
| 384 | */ | ||
| 385 | |||
| 386 | /* | ||
| 387 | * The Tsi108 PCI interrupts initialization routine. | ||
| 388 | * | ||
| 389 | * The INTA# - INTD# interrupts on the PCI bus are reported by the PCI block | ||
| 390 | * to the MPIC using single interrupt source (IRQ_TSI108_PCI). Therefore the | ||
| 391 | * PCI block has to be treated as a cascaded interrupt controller connected | ||
| 392 | * to the MPIC. | ||
| 393 | */ | ||
| 394 | |||
| 395 | void __init tsi108_pci_int_init(void) | ||
| 396 | { | ||
| 397 | u_int i; | ||
| 398 | |||
| 399 | DBG("Tsi108_pci_int_init: initializing PCI interrupts\n"); | ||
| 400 | |||
| 401 | for (i = 0; i < NUM_PCI_IRQS; i++) { | ||
| 402 | irq_desc[i + IRQ_PCI_INTAD_BASE].handler = &tsi108_pci_irq; | ||
| 403 | irq_desc[i + IRQ_PCI_INTAD_BASE].status |= IRQ_LEVEL; | ||
| 404 | } | ||
| 405 | |||
| 406 | init_pci_source(); | ||
| 407 | } | ||
| 408 | |||
| 409 | int tsi108_irq_cascade(struct pt_regs *regs, void *unused) | ||
| 410 | { | ||
| 411 | return get_pci_source(); | ||
| 412 | } | ||
diff --git a/drivers/ide/Kconfig b/drivers/ide/Kconfig index d633081fa4c5..d1266fe2d1ab 100644 --- a/drivers/ide/Kconfig +++ b/drivers/ide/Kconfig | |||
| @@ -774,11 +774,18 @@ config BLK_DEV_IDEDMA_PMAC | |||
| 774 | performance. | 774 | performance. |
| 775 | 775 | ||
| 776 | config BLK_DEV_IDE_PMAC_BLINK | 776 | config BLK_DEV_IDE_PMAC_BLINK |
| 777 | bool "Blink laptop LED on drive activity" | 777 | bool "Blink laptop LED on drive activity (DEPRECATED)" |
| 778 | depends on BLK_DEV_IDE_PMAC && ADB_PMU | 778 | depends on BLK_DEV_IDE_PMAC && ADB_PMU |
| 779 | select ADB_PMU_LED | ||
| 780 | select LEDS_TRIGGERS | ||
| 781 | select LEDS_TRIGGER_IDE_DISK | ||
| 779 | help | 782 | help |
| 780 | This option enables the use of the sleep LED as a hard drive | 783 | This option enables the use of the sleep LED as a hard drive |
| 781 | activity LED. | 784 | activity LED. |
| 785 | This option is deprecated, it only selects ADB_PMU_LED and | ||
| 786 | LEDS_TRIGGER_IDE_DISK and changes the code in the new led class | ||
| 787 | device to default to the ide-disk trigger (which should be set | ||
| 788 | from userspace via sysfs). | ||
| 782 | 789 | ||
| 783 | config BLK_DEV_IDE_SWARM | 790 | config BLK_DEV_IDE_SWARM |
| 784 | tristate "IDE for Sibyte evaluation boards" | 791 | tristate "IDE for Sibyte evaluation boards" |
diff --git a/drivers/ide/ppc/pmac.c b/drivers/ide/ppc/pmac.c index ffca8b63ee79..e8ef3455ec35 100644 --- a/drivers/ide/ppc/pmac.c +++ b/drivers/ide/ppc/pmac.c | |||
| @@ -421,107 +421,6 @@ static void pmac_ide_kauai_selectproc(ide_drive_t *drive); | |||
| 421 | #endif /* CONFIG_BLK_DEV_IDEDMA_PMAC */ | 421 | #endif /* CONFIG_BLK_DEV_IDEDMA_PMAC */ |
| 422 | 422 | ||
| 423 | /* | 423 | /* |
| 424 | * Below is the code for blinking the laptop LED along with hard | ||
| 425 | * disk activity. | ||
| 426 | */ | ||
| 427 | |||
| 428 | #ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK | ||
| 429 | |||
| 430 | /* Set to 50ms minimum led-on time (also used to limit frequency | ||
| 431 | * of requests sent to the PMU | ||
| 432 | */ | ||
| 433 | #define PMU_HD_BLINK_TIME (HZ/50) | ||
| 434 | |||
| 435 | static struct adb_request pmu_blink_on, pmu_blink_off; | ||
| 436 | static spinlock_t pmu_blink_lock; | ||
| 437 | static unsigned long pmu_blink_stoptime; | ||
| 438 | static int pmu_blink_ledstate; | ||
| 439 | static struct timer_list pmu_blink_timer; | ||
| 440 | static int pmu_ide_blink_enabled; | ||
| 441 | |||
| 442 | |||
| 443 | static void | ||
| 444 | pmu_hd_blink_timeout(unsigned long data) | ||
| 445 | { | ||
| 446 | unsigned long flags; | ||
| 447 | |||
| 448 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 449 | |||
| 450 | /* We may have been triggered again in a racy way, check | ||
| 451 | * that we really want to switch it off | ||
| 452 | */ | ||
| 453 | if (time_after(pmu_blink_stoptime, jiffies)) | ||
| 454 | goto done; | ||
| 455 | |||
| 456 | /* Previous req. not complete, try 100ms more */ | ||
| 457 | if (pmu_blink_off.complete == 0) | ||
| 458 | mod_timer(&pmu_blink_timer, jiffies + PMU_HD_BLINK_TIME); | ||
| 459 | else if (pmu_blink_ledstate) { | ||
| 460 | pmu_request(&pmu_blink_off, NULL, 4, 0xee, 4, 0, 0); | ||
| 461 | pmu_blink_ledstate = 0; | ||
| 462 | } | ||
| 463 | done: | ||
| 464 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 465 | } | ||
| 466 | |||
| 467 | static void | ||
| 468 | pmu_hd_kick_blink(void *data, int rw) | ||
| 469 | { | ||
| 470 | unsigned long flags; | ||
| 471 | |||
| 472 | pmu_blink_stoptime = jiffies + PMU_HD_BLINK_TIME; | ||
| 473 | wmb(); | ||
| 474 | mod_timer(&pmu_blink_timer, pmu_blink_stoptime); | ||
| 475 | /* Fast path when LED is already ON */ | ||
| 476 | if (pmu_blink_ledstate == 1) | ||
| 477 | return; | ||
| 478 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 479 | if (pmu_blink_on.complete && !pmu_blink_ledstate) { | ||
| 480 | pmu_request(&pmu_blink_on, NULL, 4, 0xee, 4, 0, 1); | ||
| 481 | pmu_blink_ledstate = 1; | ||
| 482 | } | ||
| 483 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 484 | } | ||
| 485 | |||
| 486 | static int | ||
| 487 | pmu_hd_blink_init(void) | ||
| 488 | { | ||
| 489 | struct device_node *dt; | ||
| 490 | const char *model; | ||
| 491 | |||
| 492 | /* Currently, I only enable this feature on KeyLargo based laptops, | ||
| 493 | * older laptops may support it (at least heathrow/paddington) but | ||
| 494 | * I don't feel like loading those venerable old machines with so | ||
| 495 | * much additional interrupt & PMU activity... | ||
| 496 | */ | ||
| 497 | if (pmu_get_model() != PMU_KEYLARGO_BASED) | ||
| 498 | return 0; | ||
| 499 | |||
| 500 | dt = of_find_node_by_path("/"); | ||
| 501 | if (dt == NULL) | ||
| 502 | return 0; | ||
| 503 | model = (const char *)get_property(dt, "model", NULL); | ||
| 504 | if (model == NULL) | ||
| 505 | return 0; | ||
| 506 | if (strncmp(model, "PowerBook", strlen("PowerBook")) != 0 && | ||
| 507 | strncmp(model, "iBook", strlen("iBook")) != 0) { | ||
| 508 | of_node_put(dt); | ||
| 509 | return 0; | ||
| 510 | } | ||
| 511 | of_node_put(dt); | ||
| 512 | |||
| 513 | pmu_blink_on.complete = 1; | ||
| 514 | pmu_blink_off.complete = 1; | ||
| 515 | spin_lock_init(&pmu_blink_lock); | ||
| 516 | init_timer(&pmu_blink_timer); | ||
| 517 | pmu_blink_timer.function = pmu_hd_blink_timeout; | ||
| 518 | |||
| 519 | return 1; | ||
| 520 | } | ||
| 521 | |||
| 522 | #endif /* CONFIG_BLK_DEV_IDE_PMAC_BLINK */ | ||
| 523 | |||
| 524 | /* | ||
| 525 | * N.B. this can't be an initfunc, because the media-bay task can | 424 | * N.B. this can't be an initfunc, because the media-bay task can |
| 526 | * call ide_[un]register at any time. | 425 | * call ide_[un]register at any time. |
| 527 | */ | 426 | */ |
| @@ -1192,23 +1091,6 @@ pmac_ide_do_suspend(ide_hwif_t *hwif) | |||
| 1192 | pmif->timings[0] = 0; | 1091 | pmif->timings[0] = 0; |
| 1193 | pmif->timings[1] = 0; | 1092 | pmif->timings[1] = 0; |
| 1194 | 1093 | ||
| 1195 | #ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK | ||
| 1196 | /* Note: This code will be called for every hwif, thus we'll | ||
| 1197 | * try several time to stop the LED blinker timer, but that | ||
| 1198 | * should be harmless | ||
| 1199 | */ | ||
| 1200 | if (pmu_ide_blink_enabled) { | ||
| 1201 | unsigned long flags; | ||
| 1202 | |||
| 1203 | /* Make sure we don't hit the PMU blink */ | ||
| 1204 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 1205 | if (pmu_blink_ledstate) | ||
| 1206 | del_timer(&pmu_blink_timer); | ||
| 1207 | pmu_blink_ledstate = 0; | ||
| 1208 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 1209 | } | ||
| 1210 | #endif /* CONFIG_BLK_DEV_IDE_PMAC_BLINK */ | ||
| 1211 | |||
| 1212 | disable_irq(pmif->irq); | 1094 | disable_irq(pmif->irq); |
| 1213 | 1095 | ||
| 1214 | /* The media bay will handle itself just fine */ | 1096 | /* The media bay will handle itself just fine */ |
| @@ -1376,13 +1258,6 @@ pmac_ide_setup_device(pmac_ide_hwif_t *pmif, ide_hwif_t *hwif) | |||
| 1376 | hwif->selectproc = pmac_ide_selectproc; | 1258 | hwif->selectproc = pmac_ide_selectproc; |
| 1377 | hwif->speedproc = pmac_ide_tune_chipset; | 1259 | hwif->speedproc = pmac_ide_tune_chipset; |
| 1378 | 1260 | ||
| 1379 | #ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK | ||
| 1380 | pmu_ide_blink_enabled = pmu_hd_blink_init(); | ||
| 1381 | |||
| 1382 | if (pmu_ide_blink_enabled) | ||
| 1383 | hwif->led_act = pmu_hd_kick_blink; | ||
| 1384 | #endif | ||
| 1385 | |||
| 1386 | printk(KERN_INFO "ide%d: Found Apple %s controller, bus ID %d%s, irq %d\n", | 1261 | printk(KERN_INFO "ide%d: Found Apple %s controller, bus ID %d%s, irq %d\n", |
| 1387 | hwif->index, model_name[pmif->kind], pmif->aapl_bus_id, | 1262 | hwif->index, model_name[pmif->kind], pmif->aapl_bus_id, |
| 1388 | pmif->mediabay ? " (mediabay)" : "", hwif->irq); | 1263 | pmif->mediabay ? " (mediabay)" : "", hwif->irq); |
diff --git a/drivers/macintosh/Kconfig b/drivers/macintosh/Kconfig index 37cd6ee4586b..54f3f6b94efc 100644 --- a/drivers/macintosh/Kconfig +++ b/drivers/macintosh/Kconfig | |||
| @@ -78,6 +78,18 @@ config ADB_PMU | |||
| 78 | this device; you should do so if your machine is one of those | 78 | this device; you should do so if your machine is one of those |
| 79 | mentioned above. | 79 | mentioned above. |
| 80 | 80 | ||
| 81 | config ADB_PMU_LED | ||
| 82 | bool "Support for the Power/iBook front LED" | ||
| 83 | depends on ADB_PMU | ||
| 84 | select NEW_LEDS | ||
| 85 | select LEDS_CLASS | ||
| 86 | help | ||
| 87 | Support the front LED on Power/iBooks as a generic LED that can | ||
| 88 | be triggered by any of the supported triggers. To get the | ||
| 89 | behaviour of the old CONFIG_BLK_DEV_IDE_PMAC_BLINK, select this | ||
| 90 | and the ide-disk LED trigger and configure appropriately through | ||
| 91 | sysfs. | ||
| 92 | |||
| 81 | config PMAC_SMU | 93 | config PMAC_SMU |
| 82 | bool "Support for SMU based PowerMacs" | 94 | bool "Support for SMU based PowerMacs" |
| 83 | depends on PPC_PMAC64 | 95 | depends on PPC_PMAC64 |
diff --git a/drivers/macintosh/Makefile b/drivers/macintosh/Makefile index 45a268f8047e..b53d45f87b0b 100644 --- a/drivers/macintosh/Makefile +++ b/drivers/macintosh/Makefile | |||
| @@ -12,6 +12,7 @@ obj-$(CONFIG_INPUT_ADBHID) += adbhid.o | |||
| 12 | obj-$(CONFIG_ANSLCD) += ans-lcd.o | 12 | obj-$(CONFIG_ANSLCD) += ans-lcd.o |
| 13 | 13 | ||
| 14 | obj-$(CONFIG_ADB_PMU) += via-pmu.o via-pmu-event.o | 14 | obj-$(CONFIG_ADB_PMU) += via-pmu.o via-pmu-event.o |
| 15 | obj-$(CONFIG_ADB_PMU_LED) += via-pmu-led.o | ||
| 15 | obj-$(CONFIG_PMAC_BACKLIGHT) += via-pmu-backlight.o | 16 | obj-$(CONFIG_PMAC_BACKLIGHT) += via-pmu-backlight.o |
| 16 | obj-$(CONFIG_ADB_CUDA) += via-cuda.o | 17 | obj-$(CONFIG_ADB_CUDA) += via-cuda.o |
| 17 | obj-$(CONFIG_PMAC_APM_EMU) += apm_emu.o | 18 | obj-$(CONFIG_PMAC_APM_EMU) += apm_emu.o |
diff --git a/drivers/macintosh/via-pmu-led.c b/drivers/macintosh/via-pmu-led.c new file mode 100644 index 000000000000..af8375ed0f5e --- /dev/null +++ b/drivers/macintosh/via-pmu-led.c | |||
| @@ -0,0 +1,144 @@ | |||
| 1 | /* | ||
| 2 | * via-pmu LED class device | ||
| 3 | * | ||
| 4 | * Copyright 2006 Johannes Berg <johannes@sipsolutions.net> | ||
| 5 | * | ||
| 6 | * This program is free software; you can redistribute it and/or modify | ||
| 7 | * it under the terms of the GNU General Public License as published by | ||
| 8 | * the Free Software Foundation; either version 2 of the License, or | ||
| 9 | * (at your option) any later version. | ||
| 10 | * | ||
| 11 | * This program is distributed in the hope that it will be useful, but | ||
| 12 | * WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 13 | * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or | ||
| 14 | * NON INFRINGEMENT. See the GNU General Public License for more | ||
| 15 | * details. | ||
| 16 | * | ||
| 17 | * You should have received a copy of the GNU General Public License | ||
| 18 | * along with this program; if not, write to the Free Software | ||
| 19 | * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA | ||
| 20 | * | ||
| 21 | */ | ||
| 22 | #include <linux/types.h> | ||
| 23 | #include <linux/kernel.h> | ||
| 24 | #include <linux/device.h> | ||
| 25 | #include <linux/leds.h> | ||
| 26 | #include <linux/adb.h> | ||
| 27 | #include <linux/pmu.h> | ||
| 28 | #include <asm/prom.h> | ||
| 29 | |||
| 30 | static spinlock_t pmu_blink_lock; | ||
| 31 | static struct adb_request pmu_blink_req; | ||
| 32 | /* -1: no change, 0: request off, 1: request on */ | ||
| 33 | static int requested_change; | ||
| 34 | static int sleeping; | ||
| 35 | |||
| 36 | static void pmu_req_done(struct adb_request * req) | ||
| 37 | { | ||
| 38 | unsigned long flags; | ||
| 39 | |||
| 40 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 41 | /* if someone requested a change in the meantime | ||
| 42 | * (we only see the last one which is fine) | ||
| 43 | * then apply it now */ | ||
| 44 | if (requested_change != -1 && !sleeping) | ||
| 45 | pmu_request(&pmu_blink_req, NULL, 4, 0xee, 4, 0, requested_change); | ||
| 46 | /* reset requested change */ | ||
| 47 | requested_change = -1; | ||
| 48 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 49 | } | ||
| 50 | |||
| 51 | static void pmu_led_set(struct led_classdev *led_cdev, | ||
| 52 | enum led_brightness brightness) | ||
| 53 | { | ||
| 54 | unsigned long flags; | ||
| 55 | |||
| 56 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 57 | switch (brightness) { | ||
| 58 | case LED_OFF: | ||
| 59 | requested_change = 0; | ||
| 60 | break; | ||
| 61 | case LED_FULL: | ||
| 62 | requested_change = 1; | ||
| 63 | break; | ||
| 64 | default: | ||
| 65 | goto out; | ||
| 66 | break; | ||
| 67 | } | ||
| 68 | /* if request isn't done, then don't do anything */ | ||
| 69 | if (pmu_blink_req.complete && !sleeping) | ||
| 70 | pmu_request(&pmu_blink_req, NULL, 4, 0xee, 4, 0, requested_change); | ||
| 71 | out: | ||
| 72 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 73 | } | ||
| 74 | |||
| 75 | static struct led_classdev pmu_led = { | ||
| 76 | .name = "pmu-front-led", | ||
| 77 | #ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK | ||
| 78 | .default_trigger = "ide-disk", | ||
| 79 | #endif | ||
| 80 | .brightness_set = pmu_led_set, | ||
| 81 | }; | ||
| 82 | |||
| 83 | #ifdef CONFIG_PM | ||
| 84 | static int pmu_led_sleep_call(struct pmu_sleep_notifier *self, int when) | ||
| 85 | { | ||
| 86 | unsigned long flags; | ||
| 87 | |||
| 88 | spin_lock_irqsave(&pmu_blink_lock, flags); | ||
| 89 | |||
| 90 | switch (when) { | ||
| 91 | case PBOOK_SLEEP_REQUEST: | ||
| 92 | sleeping = 1; | ||
| 93 | break; | ||
| 94 | case PBOOK_WAKE: | ||
| 95 | sleeping = 0; | ||
| 96 | break; | ||
| 97 | default: | ||
| 98 | /* do nothing */ | ||
| 99 | break; | ||
| 100 | } | ||
| 101 | spin_unlock_irqrestore(&pmu_blink_lock, flags); | ||
| 102 | |||
| 103 | return PBOOK_SLEEP_OK; | ||
| 104 | } | ||
| 105 | |||
| 106 | static struct pmu_sleep_notifier via_pmu_led_sleep_notif = { | ||
| 107 | .notifier_call = pmu_led_sleep_call, | ||
| 108 | }; | ||
| 109 | #endif | ||
| 110 | |||
| 111 | static int __init via_pmu_led_init(void) | ||
| 112 | { | ||
| 113 | struct device_node *dt; | ||
| 114 | const char *model; | ||
| 115 | |||
| 116 | /* only do this on keylargo based models */ | ||
| 117 | if (pmu_get_model() != PMU_KEYLARGO_BASED) | ||
| 118 | return -ENODEV; | ||
| 119 | |||
| 120 | dt = of_find_node_by_path("/"); | ||
| 121 | if (dt == NULL) | ||
| 122 | return -ENODEV; | ||
| 123 | model = (const char *)get_property(dt, "model", NULL); | ||
| 124 | if (model == NULL) | ||
| 125 | return -ENODEV; | ||
| 126 | if (strncmp(model, "PowerBook", strlen("PowerBook")) != 0 && | ||
| 127 | strncmp(model, "iBook", strlen("iBook")) != 0) { | ||
| 128 | of_node_put(dt); | ||
| 129 | /* ignore */ | ||
| 130 | return -ENODEV; | ||
| 131 | } | ||
| 132 | of_node_put(dt); | ||
| 133 | |||
| 134 | spin_lock_init(&pmu_blink_lock); | ||
| 135 | /* no outstanding req */ | ||
| 136 | pmu_blink_req.complete = 1; | ||
| 137 | pmu_blink_req.done = pmu_req_done; | ||
| 138 | #ifdef CONFIG_PM | ||
| 139 | pmu_register_sleep_notifier(&via_pmu_led_sleep_notif); | ||
| 140 | #endif | ||
| 141 | return led_classdev_register(NULL, &pmu_led); | ||
| 142 | } | ||
| 143 | |||
| 144 | late_initcall(via_pmu_led_init); | ||
diff --git a/include/asm-powerpc/cputable.h b/include/asm-powerpc/cputable.h index fab41c280aa1..1ba3c9983614 100644 --- a/include/asm-powerpc/cputable.h +++ b/include/asm-powerpc/cputable.h | |||
| @@ -117,38 +117,30 @@ extern void do_cpu_ftr_fixups(unsigned long offset); | |||
| 117 | #define CPU_FTR_PPC_LE ASM_CONST(0x0000000000200000) | 117 | #define CPU_FTR_PPC_LE ASM_CONST(0x0000000000200000) |
| 118 | #define CPU_FTR_REAL_LE ASM_CONST(0x0000000000400000) | 118 | #define CPU_FTR_REAL_LE ASM_CONST(0x0000000000400000) |
| 119 | 119 | ||
| 120 | /* | ||
| 121 | * Add the 64-bit processor unique features in the top half of the word; | ||
| 122 | * on 32-bit, make the names available but defined to be 0. | ||
| 123 | */ | ||
| 120 | #ifdef __powerpc64__ | 124 | #ifdef __powerpc64__ |
| 121 | /* Add the 64b processor unique features in the top half of the word */ | 125 | #define LONG_ASM_CONST(x) ASM_CONST(x) |
| 122 | #define CPU_FTR_SLB ASM_CONST(0x0000000100000000) | ||
| 123 | #define CPU_FTR_16M_PAGE ASM_CONST(0x0000000200000000) | ||
| 124 | #define CPU_FTR_TLBIEL ASM_CONST(0x0000000400000000) | ||
| 125 | #define CPU_FTR_NOEXECUTE ASM_CONST(0x0000000800000000) | ||
| 126 | #define CPU_FTR_IABR ASM_CONST(0x0000002000000000) | ||
| 127 | #define CPU_FTR_MMCRA ASM_CONST(0x0000004000000000) | ||
| 128 | #define CPU_FTR_CTRL ASM_CONST(0x0000008000000000) | ||
| 129 | #define CPU_FTR_SMT ASM_CONST(0x0000010000000000) | ||
| 130 | #define CPU_FTR_COHERENT_ICACHE ASM_CONST(0x0000020000000000) | ||
| 131 | #define CPU_FTR_LOCKLESS_TLBIE ASM_CONST(0x0000040000000000) | ||
| 132 | #define CPU_FTR_CI_LARGE_PAGE ASM_CONST(0x0000100000000000) | ||
| 133 | #define CPU_FTR_PAUSE_ZERO ASM_CONST(0x0000200000000000) | ||
| 134 | #define CPU_FTR_PURR ASM_CONST(0x0000400000000000) | ||
| 135 | #else | 126 | #else |
| 136 | /* ensure on 32b processors the flags are available for compiling but | 127 | #define LONG_ASM_CONST(x) 0 |
| 137 | * don't do anything */ | ||
| 138 | #define CPU_FTR_SLB ASM_CONST(0x0) | ||
| 139 | #define CPU_FTR_16M_PAGE ASM_CONST(0x0) | ||
| 140 | #define CPU_FTR_TLBIEL ASM_CONST(0x0) | ||
| 141 | #define CPU_FTR_NOEXECUTE ASM_CONST(0x0) | ||
| 142 | #define CPU_FTR_IABR ASM_CONST(0x0) | ||
| 143 | #define CPU_FTR_MMCRA ASM_CONST(0x0) | ||
| 144 | #define CPU_FTR_CTRL ASM_CONST(0x0) | ||
| 145 | #define CPU_FTR_SMT ASM_CONST(0x0) | ||
| 146 | #define CPU_FTR_COHERENT_ICACHE ASM_CONST(0x0) | ||
| 147 | #define CPU_FTR_LOCKLESS_TLBIE ASM_CONST(0x0) | ||
| 148 | #define CPU_FTR_CI_LARGE_PAGE ASM_CONST(0x0) | ||
| 149 | #define CPU_FTR_PURR ASM_CONST(0x0) | ||
| 150 | #endif | 128 | #endif |
| 151 | 129 | ||
| 130 | #define CPU_FTR_SLB LONG_ASM_CONST(0x0000000100000000) | ||
| 131 | #define CPU_FTR_16M_PAGE LONG_ASM_CONST(0x0000000200000000) | ||
| 132 | #define CPU_FTR_TLBIEL LONG_ASM_CONST(0x0000000400000000) | ||
| 133 | #define CPU_FTR_NOEXECUTE LONG_ASM_CONST(0x0000000800000000) | ||
| 134 | #define CPU_FTR_IABR LONG_ASM_CONST(0x0000002000000000) | ||
| 135 | #define CPU_FTR_MMCRA LONG_ASM_CONST(0x0000004000000000) | ||
| 136 | #define CPU_FTR_CTRL LONG_ASM_CONST(0x0000008000000000) | ||
| 137 | #define CPU_FTR_SMT LONG_ASM_CONST(0x0000010000000000) | ||
| 138 | #define CPU_FTR_COHERENT_ICACHE LONG_ASM_CONST(0x0000020000000000) | ||
| 139 | #define CPU_FTR_LOCKLESS_TLBIE LONG_ASM_CONST(0x0000040000000000) | ||
| 140 | #define CPU_FTR_CI_LARGE_PAGE LONG_ASM_CONST(0x0000100000000000) | ||
| 141 | #define CPU_FTR_PAUSE_ZERO LONG_ASM_CONST(0x0000200000000000) | ||
| 142 | #define CPU_FTR_PURR LONG_ASM_CONST(0x0000400000000000) | ||
| 143 | |||
| 152 | #ifndef __ASSEMBLY__ | 144 | #ifndef __ASSEMBLY__ |
| 153 | 145 | ||
| 154 | #define CPU_FTR_PPCAS_ARCH_V2_BASE (CPU_FTR_SLB | \ | 146 | #define CPU_FTR_PPCAS_ARCH_V2_BASE (CPU_FTR_SLB | \ |
diff --git a/include/asm-powerpc/iseries/it_lp_queue.h b/include/asm-powerpc/iseries/it_lp_queue.h index b7c6fc12cce2..284c5a7db3ac 100644 --- a/include/asm-powerpc/iseries/it_lp_queue.h +++ b/include/asm-powerpc/iseries/it_lp_queue.h | |||
| @@ -29,20 +29,20 @@ | |||
| 29 | 29 | ||
| 30 | struct HvLpEvent; | 30 | struct HvLpEvent; |
| 31 | 31 | ||
| 32 | #define ITMaxLpQueues 8 | 32 | #define IT_LP_MAX_QUEUES 8 |
| 33 | 33 | ||
| 34 | #define NotUsed 0 // Queue will not be used by PLIC | 34 | #define IT_LP_NOT_USED 0 /* Queue will not be used by PLIC */ |
| 35 | #define DedicatedIo 1 // Queue dedicated to IO processor specified | 35 | #define IT_LP_DEDICATED_IO 1 /* Queue dedicated to IO processor specified */ |
| 36 | #define DedicatedLp 2 // Queue dedicated to LP specified | 36 | #define IT_LP_DEDICATED_LP 2 /* Queue dedicated to LP specified */ |
| 37 | #define Shared 3 // Queue shared for both IO and LP | 37 | #define IT_LP_SHARED 3 /* Queue shared for both IO and LP */ |
| 38 | 38 | ||
| 39 | #define LpEventStackSize 4096 | 39 | #define IT_LP_EVENT_STACK_SIZE 4096 |
| 40 | #define LpEventMaxSize 256 | 40 | #define IT_LP_EVENT_MAX_SIZE 256 |
| 41 | #define LpEventAlign 64 | 41 | #define IT_LP_EVENT_ALIGN 64 |
| 42 | 42 | ||
| 43 | struct hvlpevent_queue { | 43 | struct hvlpevent_queue { |
| 44 | /* | 44 | /* |
| 45 | * The xSlicCurEventPtr is the pointer to the next event stack entry | 45 | * The hq_current_event is the pointer to the next event stack entry |
| 46 | * that will become valid. The OS must peek at this entry to determine | 46 | * that will become valid. The OS must peek at this entry to determine |
| 47 | * if it is valid. PLIC will set the valid indicator as the very last | 47 | * if it is valid. PLIC will set the valid indicator as the very last |
| 48 | * store into that entry. | 48 | * store into that entry. |
| @@ -52,23 +52,23 @@ struct hvlpevent_queue { | |||
| 52 | * location again. | 52 | * location again. |
| 53 | * | 53 | * |
| 54 | * If the event stack fills and there are overflow events, then PLIC | 54 | * If the event stack fills and there are overflow events, then PLIC |
| 55 | * will set the xPlicOverflowIntPending flag in which case the OS will | 55 | * will set the hq_overflow_pending flag in which case the OS will |
| 56 | * have to fetch the additional LP events once they have drained the | 56 | * have to fetch the additional LP events once they have drained the |
| 57 | * event stack. | 57 | * event stack. |
| 58 | * | 58 | * |
| 59 | * The first 16-bytes are known by both the OS and PLIC. The remainder | 59 | * The first 16-bytes are known by both the OS and PLIC. The remainder |
| 60 | * of the cache line is for use by the OS. | 60 | * of the cache line is for use by the OS. |
| 61 | */ | 61 | */ |
| 62 | u8 xPlicOverflowIntPending;// 0x00 Overflow events are pending | 62 | u8 hq_overflow_pending; /* 0x00 Overflow events are pending */ |
| 63 | u8 xPlicStatus; // 0x01 DedicatedIo or DedicatedLp or NotUsed | 63 | u8 hq_status; /* 0x01 DedicatedIo or DedicatedLp or NotUsed */ |
| 64 | u16 xSlicLogicalProcIndex; // 0x02 Logical Proc Index for correlation | 64 | u16 hq_proc_index; /* 0x02 Logical Proc Index for correlation */ |
| 65 | u8 xPlicRsvd[12]; // 0x04 | 65 | u8 hq_reserved1[12]; /* 0x04 */ |
| 66 | char *xSlicCurEventPtr; // 0x10 | 66 | char *hq_current_event; /* 0x10 */ |
| 67 | char *xSlicLastValidEventPtr; // 0x18 | 67 | char *hq_last_event; /* 0x18 */ |
| 68 | char *xSlicEventStackPtr; // 0x20 | 68 | char *hq_event_stack; /* 0x20 */ |
| 69 | u8 xIndex; // 0x28 unique sequential index. | 69 | u8 hq_index; /* 0x28 unique sequential index. */ |
| 70 | u8 xSlicRsvd[3]; // 0x29-2b | 70 | u8 hq_reserved2[3]; /* 0x29-2b */ |
| 71 | spinlock_t lock; | 71 | spinlock_t hq_lock; |
| 72 | }; | 72 | }; |
| 73 | 73 | ||
| 74 | extern struct hvlpevent_queue hvlpevent_queue; | 74 | extern struct hvlpevent_queue hvlpevent_queue; |
diff --git a/include/asm-powerpc/kdump.h b/include/asm-powerpc/kdump.h index 5a5c3b5ab1e0..dc1574c945f8 100644 --- a/include/asm-powerpc/kdump.h +++ b/include/asm-powerpc/kdump.h | |||
| @@ -15,6 +15,8 @@ | |||
| 15 | #define KDUMP_TRAMPOLINE_START 0x0100 | 15 | #define KDUMP_TRAMPOLINE_START 0x0100 |
| 16 | #define KDUMP_TRAMPOLINE_END 0x3000 | 16 | #define KDUMP_TRAMPOLINE_END 0x3000 |
| 17 | 17 | ||
| 18 | #define KDUMP_MIN_TCE_ENTRIES 2048 | ||
| 19 | |||
| 18 | #else /* !CONFIG_CRASH_DUMP */ | 20 | #else /* !CONFIG_CRASH_DUMP */ |
| 19 | 21 | ||
| 20 | #define PHYSICAL_START 0x0 | 22 | #define PHYSICAL_START 0x0 |
diff --git a/include/asm-powerpc/kexec.h b/include/asm-powerpc/kexec.h index efe8872ec583..8f7fd5cfec34 100644 --- a/include/asm-powerpc/kexec.h +++ b/include/asm-powerpc/kexec.h | |||
| @@ -112,9 +112,13 @@ static inline void crash_setup_regs(struct pt_regs *newregs, | |||
| 112 | #ifdef __powerpc64__ | 112 | #ifdef __powerpc64__ |
| 113 | extern void kexec_smp_wait(void); /* get and clear naca physid, wait for | 113 | extern void kexec_smp_wait(void); /* get and clear naca physid, wait for |
| 114 | master to copy new code to 0 */ | 114 | master to copy new code to 0 */ |
| 115 | extern void __init kexec_setup(void); | ||
| 116 | extern int crashing_cpu; | 115 | extern int crashing_cpu; |
| 117 | extern void crash_send_ipi(void (*crash_ipi_callback)(struct pt_regs *)); | 116 | extern void crash_send_ipi(void (*crash_ipi_callback)(struct pt_regs *)); |
| 117 | extern cpumask_t cpus_in_sr; | ||
| 118 | static inline int kexec_sr_activated(int cpu) | ||
| 119 | { | ||
| 120 | return cpu_isset(cpu,cpus_in_sr); | ||
| 121 | } | ||
| 118 | #endif /* __powerpc64 __ */ | 122 | #endif /* __powerpc64 __ */ |
| 119 | 123 | ||
| 120 | struct kimage; | 124 | struct kimage; |
| @@ -124,10 +128,13 @@ extern int default_machine_kexec_prepare(struct kimage *image); | |||
| 124 | extern void default_machine_crash_shutdown(struct pt_regs *regs); | 128 | extern void default_machine_crash_shutdown(struct pt_regs *regs); |
| 125 | 129 | ||
| 126 | extern void machine_kexec_simple(struct kimage *image); | 130 | extern void machine_kexec_simple(struct kimage *image); |
| 131 | extern void crash_kexec_secondary(struct pt_regs *regs); | ||
| 127 | extern int overlaps_crashkernel(unsigned long start, unsigned long size); | 132 | extern int overlaps_crashkernel(unsigned long start, unsigned long size); |
| 128 | extern void reserve_crashkernel(void); | 133 | extern void reserve_crashkernel(void); |
| 129 | 134 | ||
| 130 | #else /* !CONFIG_KEXEC */ | 135 | #else /* !CONFIG_KEXEC */ |
| 136 | static inline int kexec_sr_activated(int cpu) { return 0; } | ||
| 137 | static inline void crash_kexec_secondary(struct pt_regs *regs) { } | ||
| 131 | 138 | ||
| 132 | static inline int overlaps_crashkernel(unsigned long start, unsigned long size) | 139 | static inline int overlaps_crashkernel(unsigned long start, unsigned long size) |
| 133 | { | 140 | { |
diff --git a/include/asm-powerpc/machdep.h b/include/asm-powerpc/machdep.h index 73db1f71329d..eba133d149a7 100644 --- a/include/asm-powerpc/machdep.h +++ b/include/asm-powerpc/machdep.h | |||
| @@ -81,6 +81,8 @@ struct machdep_calls { | |||
| 81 | void (*tce_free)(struct iommu_table *tbl, | 81 | void (*tce_free)(struct iommu_table *tbl, |
| 82 | long index, | 82 | long index, |
| 83 | long npages); | 83 | long npages); |
| 84 | unsigned long (*tce_get)(struct iommu_table *tbl, | ||
| 85 | long index); | ||
| 84 | void (*tce_flush)(struct iommu_table *tbl); | 86 | void (*tce_flush)(struct iommu_table *tbl); |
| 85 | void (*iommu_dev_setup)(struct pci_dev *dev); | 87 | void (*iommu_dev_setup)(struct pci_dev *dev); |
| 86 | void (*iommu_bus_setup)(struct pci_bus *bus); | 88 | void (*iommu_bus_setup)(struct pci_bus *bus); |
diff --git a/include/asm-powerpc/mmu.h b/include/asm-powerpc/mmu.h index 3a5ebe229af5..c3fc7a28e3cd 100644 --- a/include/asm-powerpc/mmu.h +++ b/include/asm-powerpc/mmu.h | |||
| @@ -238,7 +238,6 @@ extern int hash_huge_page(struct mm_struct *mm, unsigned long access, | |||
| 238 | unsigned long ea, unsigned long vsid, int local, | 238 | unsigned long ea, unsigned long vsid, int local, |
| 239 | unsigned long trap); | 239 | unsigned long trap); |
| 240 | 240 | ||
| 241 | extern void htab_finish_init(void); | ||
| 242 | extern int htab_bolt_mapping(unsigned long vstart, unsigned long vend, | 241 | extern int htab_bolt_mapping(unsigned long vstart, unsigned long vend, |
| 243 | unsigned long pstart, unsigned long mode, | 242 | unsigned long pstart, unsigned long mode, |
| 244 | int psize); | 243 | int psize); |
diff --git a/include/asm-powerpc/mmu_context.h b/include/asm-powerpc/mmu_context.h index 8c6b1a6d944f..083ac917bd29 100644 --- a/include/asm-powerpc/mmu_context.h +++ b/include/asm-powerpc/mmu_context.h | |||
| @@ -25,8 +25,13 @@ static inline void enter_lazy_tlb(struct mm_struct *mm, | |||
| 25 | { | 25 | { |
| 26 | } | 26 | } |
| 27 | 27 | ||
| 28 | /* | ||
| 29 | * The proto-VSID space has 2^35 - 1 segments available for user mappings. | ||
| 30 | * Each segment contains 2^28 bytes. Each context maps 2^44 bytes, | ||
| 31 | * so we can support 2^19-1 contexts (19 == 35 + 28 - 44). | ||
| 32 | */ | ||
| 28 | #define NO_CONTEXT 0 | 33 | #define NO_CONTEXT 0 |
| 29 | #define MAX_CONTEXT (0x100000-1) | 34 | #define MAX_CONTEXT ((1UL << 19) - 1) |
| 30 | 35 | ||
| 31 | extern int init_new_context(struct task_struct *tsk, struct mm_struct *mm); | 36 | extern int init_new_context(struct task_struct *tsk, struct mm_struct *mm); |
| 32 | extern void destroy_context(struct mm_struct *mm); | 37 | extern void destroy_context(struct mm_struct *mm); |
diff --git a/include/asm-powerpc/mpc86xx.h b/include/asm-powerpc/mpc86xx.h index d0a6718d188b..f260382739fa 100644 --- a/include/asm-powerpc/mpc86xx.h +++ b/include/asm-powerpc/mpc86xx.h | |||
| @@ -15,15 +15,10 @@ | |||
| 15 | #ifndef __ASM_POWERPC_MPC86xx_H__ | 15 | #ifndef __ASM_POWERPC_MPC86xx_H__ |
| 16 | #define __ASM_POWERPC_MPC86xx_H__ | 16 | #define __ASM_POWERPC_MPC86xx_H__ |
| 17 | 17 | ||
| 18 | #include <linux/config.h> | ||
| 19 | #include <asm/mmu.h> | 18 | #include <asm/mmu.h> |
| 20 | 19 | ||
| 21 | #ifdef CONFIG_PPC_86xx | 20 | #ifdef CONFIG_PPC_86xx |
| 22 | 21 | ||
| 23 | #ifdef CONFIG_MPC8641_HPCN | ||
| 24 | #include <platforms/86xx/mpc8641_hpcn.h> | ||
| 25 | #endif | ||
| 26 | |||
| 27 | #define _IO_BASE isa_io_base | 22 | #define _IO_BASE isa_io_base |
| 28 | #define _ISA_MEM_BASE isa_mem_base | 23 | #define _ISA_MEM_BASE isa_mem_base |
| 29 | #ifdef CONFIG_PCI | 24 | #ifdef CONFIG_PCI |
diff --git a/include/asm-powerpc/rtas.h b/include/asm-powerpc/rtas.h index 02e213e3d69f..a33c6acffa61 100644 --- a/include/asm-powerpc/rtas.h +++ b/include/asm-powerpc/rtas.h | |||
| @@ -181,6 +181,9 @@ extern int rtas_set_rtc_time(struct rtc_time *rtc_time); | |||
| 181 | extern unsigned int rtas_busy_delay_time(int status); | 181 | extern unsigned int rtas_busy_delay_time(int status); |
| 182 | extern unsigned int rtas_busy_delay(int status); | 182 | extern unsigned int rtas_busy_delay(int status); |
| 183 | 183 | ||
| 184 | extern int early_init_dt_scan_rtas(unsigned long node, | ||
| 185 | const char *uname, int depth, void *data); | ||
| 186 | |||
| 184 | extern void pSeries_log_error(char *buf, unsigned int err_type, int fatal); | 187 | extern void pSeries_log_error(char *buf, unsigned int err_type, int fatal); |
| 185 | 188 | ||
| 186 | /* Error types logged. */ | 189 | /* Error types logged. */ |
diff --git a/include/asm-powerpc/time.h b/include/asm-powerpc/time.h index 4463148c659f..dcde4410348d 100644 --- a/include/asm-powerpc/time.h +++ b/include/asm-powerpc/time.h | |||
| @@ -18,8 +18,9 @@ | |||
| 18 | #include <linux/percpu.h> | 18 | #include <linux/percpu.h> |
| 19 | 19 | ||
| 20 | #include <asm/processor.h> | 20 | #include <asm/processor.h> |
| 21 | #ifdef CONFIG_PPC64 | 21 | #ifdef CONFIG_PPC_ISERIES |
| 22 | #include <asm/paca.h> | 22 | #include <asm/paca.h> |
| 23 | #include <asm/firmware.h> | ||
| 23 | #include <asm/iseries/hv_call.h> | 24 | #include <asm/iseries/hv_call.h> |
| 24 | #endif | 25 | #endif |
| 25 | 26 | ||
| @@ -177,7 +178,8 @@ static inline void set_dec(int val) | |||
| 177 | #ifdef CONFIG_PPC_ISERIES | 178 | #ifdef CONFIG_PPC_ISERIES |
| 178 | int cur_dec; | 179 | int cur_dec; |
| 179 | 180 | ||
| 180 | if (get_lppaca()->shared_proc) { | 181 | if (firmware_has_feature(FW_FEATURE_ISERIES) && |
| 182 | get_lppaca()->shared_proc) { | ||
| 181 | get_lppaca()->virtual_decr = val; | 183 | get_lppaca()->virtual_decr = val; |
| 182 | cur_dec = get_dec(); | 184 | cur_dec = get_dec(); |
| 183 | if (cur_dec > val) | 185 | if (cur_dec > val) |
diff --git a/include/asm-powerpc/todc.h b/include/asm-powerpc/todc.h new file mode 100644 index 000000000000..60a8c39b8c11 --- /dev/null +++ b/include/asm-powerpc/todc.h | |||
| @@ -0,0 +1,487 @@ | |||
| 1 | /* | ||
| 2 | * Definitions for the M48Txx and mc146818 series of Time of day/Real Time | ||
| 3 | * Clock chips. | ||
| 4 | * | ||
| 5 | * Author: Mark A. Greer <mgreer@mvista.com> | ||
| 6 | * | ||
| 7 | * 2001 (c) MontaVista, Software, Inc. This file is licensed under | ||
| 8 | * the terms of the GNU General Public License version 2. This program | ||
| 9 | * is licensed "as is" without any warranty of any kind, whether express | ||
| 10 | * or implied. | ||
| 11 | */ | ||
| 12 | |||
| 13 | /* | ||
| 14 | * Support for the M48T37/M48T59/.../mc146818 Real Time Clock chips. | ||
| 15 | * Purpose is to make one generic file that handles all of these chips instead | ||
| 16 | * of every platform implementing the same code over & over again. | ||
| 17 | */ | ||
| 18 | |||
| 19 | #ifndef __PPC_KERNEL_TODC_H | ||
| 20 | #define __PPC_KERNEL_TODC_H | ||
| 21 | |||
| 22 | typedef struct { | ||
| 23 | uint rtc_type; /* your particular chip */ | ||
| 24 | |||
| 25 | /* | ||
| 26 | * Following are the addresses of the AS0, AS1, and DATA registers | ||
| 27 | * of these chips. Note that these are board-specific. | ||
| 28 | */ | ||
| 29 | unsigned int nvram_as0; | ||
| 30 | unsigned int nvram_as1; | ||
| 31 | unsigned int nvram_data; | ||
| 32 | |||
| 33 | /* | ||
| 34 | * Define bits to stop external set of regs from changing so | ||
| 35 | * the chip can be read/written reliably. | ||
| 36 | */ | ||
| 37 | unsigned char enable_read; | ||
| 38 | unsigned char enable_write; | ||
| 39 | |||
| 40 | /* | ||
| 41 | * Following is the number of AS0 address bits. This is normally | ||
| 42 | * 8 but some bad hardware routes address lines incorrectly. | ||
| 43 | */ | ||
| 44 | int as0_bits; | ||
| 45 | |||
| 46 | int nvram_size; /* Size of NVRAM on chip */ | ||
| 47 | int sw_flags; /* Software control flags */ | ||
| 48 | |||
| 49 | /* Following are the register offsets for the particular chip */ | ||
| 50 | int year; | ||
| 51 | int month; | ||
| 52 | int day_of_month; | ||
| 53 | int day_of_week; | ||
| 54 | int hours; | ||
| 55 | int minutes; | ||
| 56 | int seconds; | ||
| 57 | int control_b; | ||
| 58 | int control_a; | ||
| 59 | int watchdog; | ||
| 60 | int interrupts; | ||
| 61 | int alarm_date; | ||
| 62 | int alarm_hour; | ||
| 63 | int alarm_minutes; | ||
| 64 | int alarm_seconds; | ||
| 65 | int century; | ||
| 66 | int flags; | ||
| 67 | |||
| 68 | /* | ||
| 69 | * Some RTC chips have their NVRAM buried behind a addr/data pair of | ||
| 70 | * regs on the first level/clock registers. The following fields | ||
| 71 | * are the addresses for those addr/data regs. | ||
| 72 | */ | ||
| 73 | int nvram_addr_reg; | ||
| 74 | int nvram_data_reg; | ||
| 75 | } todc_info_t; | ||
| 76 | |||
| 77 | /* | ||
| 78 | * Define the types of TODC/RTC variants that are supported in | ||
| 79 | * arch/ppc/kernel/todc_time.c | ||
| 80 | * Make a new one of these for any chip somehow differs from what's already | ||
| 81 | * defined. That way, if you ever need to put in code to touch those | ||
| 82 | * bits/registers in todc_time.c, you can put it inside an | ||
| 83 | * 'if (todc_info->rtc_type == TODC_TYPE_XXX)' so you won't break | ||
| 84 | * anyone else. | ||
| 85 | */ | ||
| 86 | #define TODC_TYPE_MK48T35 1 | ||
| 87 | #define TODC_TYPE_MK48T37 2 | ||
| 88 | #define TODC_TYPE_MK48T59 3 | ||
| 89 | #define TODC_TYPE_DS1693 4 /* Dallas DS1693 RTC */ | ||
| 90 | #define TODC_TYPE_DS1743 5 /* Dallas DS1743 RTC */ | ||
| 91 | #define TODC_TYPE_DS1746 6 /* Dallas DS1746 RTC */ | ||
| 92 | #define TODC_TYPE_DS1747 7 /* Dallas DS1747 RTC */ | ||
| 93 | #define TODC_TYPE_DS1501 8 /* Dallas DS1501 RTC */ | ||
| 94 | #define TODC_TYPE_DS1643 9 /* Dallas DS1643 RTC */ | ||
| 95 | #define TODC_TYPE_PC97307 10 /* PC97307 internal RTC */ | ||
| 96 | #define TODC_TYPE_DS1557 11 /* Dallas DS1557 RTC */ | ||
| 97 | #define TODC_TYPE_DS17285 12 /* Dallas DS17285 RTC */ | ||
| 98 | #define TODC_TYPE_DS1553 13 /* Dallas DS1553 RTC */ | ||
| 99 | #define TODC_TYPE_MC146818 100 /* Leave room for m48txx's */ | ||
| 100 | |||
| 101 | /* | ||
| 102 | * Bit to clear/set to enable reads/writes to the chip | ||
| 103 | */ | ||
| 104 | #define TODC_MK48TXX_CNTL_A_R 0x40 | ||
| 105 | #define TODC_MK48TXX_CNTL_A_W 0x80 | ||
| 106 | #define TODC_MK48TXX_DAY_CB 0x80 | ||
| 107 | |||
| 108 | #define TODC_DS1501_CNTL_B_TE 0x80 | ||
| 109 | |||
| 110 | /* | ||
| 111 | * Define flag bits used by todc routines. | ||
| 112 | */ | ||
| 113 | #define TODC_FLAG_2_LEVEL_NVRAM 0x00000001 | ||
| 114 | |||
| 115 | /* | ||
| 116 | * Define the values for the various RTC's that should to into the todc_info | ||
| 117 | * table. | ||
| 118 | * Note: The XXX_NVRAM_SIZE, XXX_NVRAM_ADDR_REG, and XXX_NVRAM_DATA_REG only | ||
| 119 | * matter if XXX_SW_FLAGS has TODC_FLAG_2_LEVEL_NVRAM set. | ||
| 120 | */ | ||
| 121 | #define TODC_TYPE_MK48T35_NVRAM_SIZE 0x7ff8 | ||
| 122 | #define TODC_TYPE_MK48T35_SW_FLAGS 0 | ||
| 123 | #define TODC_TYPE_MK48T35_YEAR 0x7fff | ||
| 124 | #define TODC_TYPE_MK48T35_MONTH 0x7ffe | ||
| 125 | #define TODC_TYPE_MK48T35_DOM 0x7ffd /* Day of Month */ | ||
| 126 | #define TODC_TYPE_MK48T35_DOW 0x7ffc /* Day of Week */ | ||
| 127 | #define TODC_TYPE_MK48T35_HOURS 0x7ffb | ||
| 128 | #define TODC_TYPE_MK48T35_MINUTES 0x7ffa | ||
| 129 | #define TODC_TYPE_MK48T35_SECONDS 0x7ff9 | ||
| 130 | #define TODC_TYPE_MK48T35_CNTL_B 0x7ff9 | ||
| 131 | #define TODC_TYPE_MK48T35_CNTL_A 0x7ff8 | ||
| 132 | #define TODC_TYPE_MK48T35_WATCHDOG 0x0000 | ||
| 133 | #define TODC_TYPE_MK48T35_INTERRUPTS 0x0000 | ||
| 134 | #define TODC_TYPE_MK48T35_ALARM_DATE 0x0000 | ||
| 135 | #define TODC_TYPE_MK48T35_ALARM_HOUR 0x0000 | ||
| 136 | #define TODC_TYPE_MK48T35_ALARM_MINUTES 0x0000 | ||
| 137 | #define TODC_TYPE_MK48T35_ALARM_SECONDS 0x0000 | ||
| 138 | #define TODC_TYPE_MK48T35_CENTURY 0x0000 | ||
| 139 | #define TODC_TYPE_MK48T35_FLAGS 0x0000 | ||
| 140 | #define TODC_TYPE_MK48T35_NVRAM_ADDR_REG 0 | ||
| 141 | #define TODC_TYPE_MK48T35_NVRAM_DATA_REG 0 | ||
| 142 | |||
| 143 | #define TODC_TYPE_MK48T37_NVRAM_SIZE 0x7ff0 | ||
| 144 | #define TODC_TYPE_MK48T37_SW_FLAGS 0 | ||
| 145 | #define TODC_TYPE_MK48T37_YEAR 0x7fff | ||
| 146 | #define TODC_TYPE_MK48T37_MONTH 0x7ffe | ||
| 147 | #define TODC_TYPE_MK48T37_DOM 0x7ffd /* Day of Month */ | ||
| 148 | #define TODC_TYPE_MK48T37_DOW 0x7ffc /* Day of Week */ | ||
| 149 | #define TODC_TYPE_MK48T37_HOURS 0x7ffb | ||
| 150 | #define TODC_TYPE_MK48T37_MINUTES 0x7ffa | ||
| 151 | #define TODC_TYPE_MK48T37_SECONDS 0x7ff9 | ||
| 152 | #define TODC_TYPE_MK48T37_CNTL_B 0x7ff9 | ||
| 153 | #define TODC_TYPE_MK48T37_CNTL_A 0x7ff8 | ||
| 154 | #define TODC_TYPE_MK48T37_WATCHDOG 0x7ff7 | ||
| 155 | #define TODC_TYPE_MK48T37_INTERRUPTS 0x7ff6 | ||
| 156 | #define TODC_TYPE_MK48T37_ALARM_DATE 0x7ff5 | ||
| 157 | #define TODC_TYPE_MK48T37_ALARM_HOUR 0x7ff4 | ||
| 158 | #define TODC_TYPE_MK48T37_ALARM_MINUTES 0x7ff3 | ||
| 159 | #define TODC_TYPE_MK48T37_ALARM_SECONDS 0x7ff2 | ||
| 160 | #define TODC_TYPE_MK48T37_CENTURY 0x7ff1 | ||
| 161 | #define TODC_TYPE_MK48T37_FLAGS 0x7ff0 | ||
| 162 | #define TODC_TYPE_MK48T37_NVRAM_ADDR_REG 0 | ||
| 163 | #define TODC_TYPE_MK48T37_NVRAM_DATA_REG 0 | ||
| 164 | |||
| 165 | #define TODC_TYPE_MK48T59_NVRAM_SIZE 0x1ff0 | ||
| 166 | #define TODC_TYPE_MK48T59_SW_FLAGS 0 | ||
| 167 | #define TODC_TYPE_MK48T59_YEAR 0x1fff | ||
| 168 | #define TODC_TYPE_MK48T59_MONTH 0x1ffe | ||
| 169 | #define TODC_TYPE_MK48T59_DOM 0x1ffd /* Day of Month */ | ||
| 170 | #define TODC_TYPE_MK48T59_DOW 0x1ffc /* Day of Week */ | ||
| 171 | #define TODC_TYPE_MK48T59_HOURS 0x1ffb | ||
| 172 | #define TODC_TYPE_MK48T59_MINUTES 0x1ffa | ||
| 173 | #define TODC_TYPE_MK48T59_SECONDS 0x1ff9 | ||
| 174 | #define TODC_TYPE_MK48T59_CNTL_B 0x1ff9 | ||
| 175 | #define TODC_TYPE_MK48T59_CNTL_A 0x1ff8 | ||
| 176 | #define TODC_TYPE_MK48T59_WATCHDOG 0x1fff | ||
| 177 | #define TODC_TYPE_MK48T59_INTERRUPTS 0x1fff | ||
| 178 | #define TODC_TYPE_MK48T59_ALARM_DATE 0x1fff | ||
| 179 | #define TODC_TYPE_MK48T59_ALARM_HOUR 0x1fff | ||
| 180 | #define TODC_TYPE_MK48T59_ALARM_MINUTES 0x1fff | ||
| 181 | #define TODC_TYPE_MK48T59_ALARM_SECONDS 0x1fff | ||
| 182 | #define TODC_TYPE_MK48T59_CENTURY 0x1fff | ||
| 183 | #define TODC_TYPE_MK48T59_FLAGS 0x1fff | ||
| 184 | #define TODC_TYPE_MK48T59_NVRAM_ADDR_REG 0 | ||
| 185 | #define TODC_TYPE_MK48T59_NVRAM_DATA_REG 0 | ||
| 186 | |||
| 187 | #define TODC_TYPE_DS1501_NVRAM_SIZE 0x100 | ||
| 188 | #define TODC_TYPE_DS1501_SW_FLAGS TODC_FLAG_2_LEVEL_NVRAM | ||
| 189 | #define TODC_TYPE_DS1501_YEAR (TODC_TYPE_DS1501_NVRAM_SIZE + 0x06) | ||
| 190 | #define TODC_TYPE_DS1501_MONTH (TODC_TYPE_DS1501_NVRAM_SIZE + 0x05) | ||
| 191 | #define TODC_TYPE_DS1501_DOM (TODC_TYPE_DS1501_NVRAM_SIZE + 0x04) | ||
| 192 | #define TODC_TYPE_DS1501_DOW (TODC_TYPE_DS1501_NVRAM_SIZE + 0x03) | ||
| 193 | #define TODC_TYPE_DS1501_HOURS (TODC_TYPE_DS1501_NVRAM_SIZE + 0x02) | ||
| 194 | #define TODC_TYPE_DS1501_MINUTES (TODC_TYPE_DS1501_NVRAM_SIZE + 0x01) | ||
| 195 | #define TODC_TYPE_DS1501_SECONDS (TODC_TYPE_DS1501_NVRAM_SIZE + 0x00) | ||
| 196 | #define TODC_TYPE_DS1501_CNTL_B (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0f) | ||
| 197 | #define TODC_TYPE_DS1501_CNTL_A (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0f) | ||
| 198 | #define TODC_TYPE_DS1501_WATCHDOG (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff) | ||
| 199 | #define TODC_TYPE_DS1501_INTERRUPTS (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff) | ||
| 200 | #define TODC_TYPE_DS1501_ALARM_DATE (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0b) | ||
| 201 | #define TODC_TYPE_DS1501_ALARM_HOUR (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0a) | ||
| 202 | #define TODC_TYPE_DS1501_ALARM_MINUTES (TODC_TYPE_DS1501_NVRAM_SIZE + 0x09) | ||
| 203 | #define TODC_TYPE_DS1501_ALARM_SECONDS (TODC_TYPE_DS1501_NVRAM_SIZE + 0x08) | ||
| 204 | #define TODC_TYPE_DS1501_CENTURY (TODC_TYPE_DS1501_NVRAM_SIZE + 0x07) | ||
| 205 | #define TODC_TYPE_DS1501_FLAGS (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff) | ||
| 206 | #define TODC_TYPE_DS1501_NVRAM_ADDR_REG 0x10 | ||
| 207 | #define TODC_TYPE_DS1501_NVRAM_DATA_REG 0x13 | ||
| 208 | |||
| 209 | #define TODC_TYPE_DS1553_NVRAM_SIZE 0x1ff0 | ||
| 210 | #define TODC_TYPE_DS1553_SW_FLAGS 0 | ||
| 211 | #define TODC_TYPE_DS1553_YEAR 0x1fff | ||
| 212 | #define TODC_TYPE_DS1553_MONTH 0x1ffe | ||
| 213 | #define TODC_TYPE_DS1553_DOM 0x1ffd /* Day of Month */ | ||
| 214 | #define TODC_TYPE_DS1553_DOW 0x1ffc /* Day of Week */ | ||
| 215 | #define TODC_TYPE_DS1553_HOURS 0x1ffb | ||
| 216 | #define TODC_TYPE_DS1553_MINUTES 0x1ffa | ||
| 217 | #define TODC_TYPE_DS1553_SECONDS 0x1ff9 | ||
| 218 | #define TODC_TYPE_DS1553_CNTL_B 0x1ff9 | ||
| 219 | #define TODC_TYPE_DS1553_CNTL_A 0x1ff8 /* control_a R/W regs */ | ||
| 220 | #define TODC_TYPE_DS1553_WATCHDOG 0x1ff7 | ||
| 221 | #define TODC_TYPE_DS1553_INTERRUPTS 0x1ff6 | ||
| 222 | #define TODC_TYPE_DS1553_ALARM_DATE 0x1ff5 | ||
| 223 | #define TODC_TYPE_DS1553_ALARM_HOUR 0x1ff4 | ||
| 224 | #define TODC_TYPE_DS1553_ALARM_MINUTES 0x1ff3 | ||
| 225 | #define TODC_TYPE_DS1553_ALARM_SECONDS 0x1ff2 | ||
| 226 | #define TODC_TYPE_DS1553_CENTURY 0x1ff8 | ||
| 227 | #define TODC_TYPE_DS1553_FLAGS 0x1ff0 | ||
| 228 | #define TODC_TYPE_DS1553_NVRAM_ADDR_REG 0 | ||
| 229 | #define TODC_TYPE_DS1553_NVRAM_DATA_REG 0 | ||
| 230 | |||
| 231 | #define TODC_TYPE_DS1557_NVRAM_SIZE 0x7fff0 | ||
| 232 | #define TODC_TYPE_DS1557_SW_FLAGS 0 | ||
| 233 | #define TODC_TYPE_DS1557_YEAR 0x7ffff | ||
| 234 | #define TODC_TYPE_DS1557_MONTH 0x7fffe | ||
| 235 | #define TODC_TYPE_DS1557_DOM 0x7fffd /* Day of Month */ | ||
| 236 | #define TODC_TYPE_DS1557_DOW 0x7fffc /* Day of Week */ | ||
| 237 | #define TODC_TYPE_DS1557_HOURS 0x7fffb | ||
| 238 | #define TODC_TYPE_DS1557_MINUTES 0x7fffa | ||
| 239 | #define TODC_TYPE_DS1557_SECONDS 0x7fff9 | ||
| 240 | #define TODC_TYPE_DS1557_CNTL_B 0x7fff9 | ||
| 241 | #define TODC_TYPE_DS1557_CNTL_A 0x7fff8 /* control_a R/W regs */ | ||
| 242 | #define TODC_TYPE_DS1557_WATCHDOG 0x7fff7 | ||
| 243 | #define TODC_TYPE_DS1557_INTERRUPTS 0x7fff6 | ||
| 244 | #define TODC_TYPE_DS1557_ALARM_DATE 0x7fff5 | ||
| 245 | #define TODC_TYPE_DS1557_ALARM_HOUR 0x7fff4 | ||
| 246 | #define TODC_TYPE_DS1557_ALARM_MINUTES 0x7fff3 | ||
| 247 | #define TODC_TYPE_DS1557_ALARM_SECONDS 0x7fff2 | ||
| 248 | #define TODC_TYPE_DS1557_CENTURY 0x7fff8 | ||
| 249 | #define TODC_TYPE_DS1557_FLAGS 0x7fff0 | ||
| 250 | #define TODC_TYPE_DS1557_NVRAM_ADDR_REG 0 | ||
| 251 | #define TODC_TYPE_DS1557_NVRAM_DATA_REG 0 | ||
| 252 | |||
| 253 | #define TODC_TYPE_DS1643_NVRAM_SIZE 0x1ff8 | ||
| 254 | #define TODC_TYPE_DS1643_SW_FLAGS 0 | ||
| 255 | #define TODC_TYPE_DS1643_YEAR 0x1fff | ||
| 256 | #define TODC_TYPE_DS1643_MONTH 0x1ffe | ||
| 257 | #define TODC_TYPE_DS1643_DOM 0x1ffd /* Day of Month */ | ||
| 258 | #define TODC_TYPE_DS1643_DOW 0x1ffc /* Day of Week */ | ||
| 259 | #define TODC_TYPE_DS1643_HOURS 0x1ffb | ||
| 260 | #define TODC_TYPE_DS1643_MINUTES 0x1ffa | ||
| 261 | #define TODC_TYPE_DS1643_SECONDS 0x1ff9 | ||
| 262 | #define TODC_TYPE_DS1643_CNTL_B 0x1ff9 | ||
| 263 | #define TODC_TYPE_DS1643_CNTL_A 0x1ff8 /* control_a R/W regs */ | ||
| 264 | #define TODC_TYPE_DS1643_WATCHDOG 0x1fff | ||
| 265 | #define TODC_TYPE_DS1643_INTERRUPTS 0x1fff | ||
| 266 | #define TODC_TYPE_DS1643_ALARM_DATE 0x1fff | ||
| 267 | #define TODC_TYPE_DS1643_ALARM_HOUR 0x1fff | ||
| 268 | #define TODC_TYPE_DS1643_ALARM_MINUTES 0x1fff | ||
| 269 | #define TODC_TYPE_DS1643_ALARM_SECONDS 0x1fff | ||
| 270 | #define TODC_TYPE_DS1643_CENTURY 0x1ff8 | ||
| 271 | #define TODC_TYPE_DS1643_FLAGS 0x1fff | ||
| 272 | #define TODC_TYPE_DS1643_NVRAM_ADDR_REG 0 | ||
| 273 | #define TODC_TYPE_DS1643_NVRAM_DATA_REG 0 | ||
| 274 | |||
| 275 | #define TODC_TYPE_DS1693_NVRAM_SIZE 0 /* Not handled yet */ | ||
| 276 | #define TODC_TYPE_DS1693_SW_FLAGS 0 | ||
| 277 | #define TODC_TYPE_DS1693_YEAR 0x09 | ||
| 278 | #define TODC_TYPE_DS1693_MONTH 0x08 | ||
| 279 | #define TODC_TYPE_DS1693_DOM 0x07 /* Day of Month */ | ||
| 280 | #define TODC_TYPE_DS1693_DOW 0x06 /* Day of Week */ | ||
| 281 | #define TODC_TYPE_DS1693_HOURS 0x04 | ||
| 282 | #define TODC_TYPE_DS1693_MINUTES 0x02 | ||
| 283 | #define TODC_TYPE_DS1693_SECONDS 0x00 | ||
| 284 | #define TODC_TYPE_DS1693_CNTL_B 0x0b | ||
| 285 | #define TODC_TYPE_DS1693_CNTL_A 0x0a | ||
| 286 | #define TODC_TYPE_DS1693_WATCHDOG 0xff | ||
| 287 | #define TODC_TYPE_DS1693_INTERRUPTS 0xff | ||
| 288 | #define TODC_TYPE_DS1693_ALARM_DATE 0x49 | ||
| 289 | #define TODC_TYPE_DS1693_ALARM_HOUR 0x05 | ||
| 290 | #define TODC_TYPE_DS1693_ALARM_MINUTES 0x03 | ||
| 291 | #define TODC_TYPE_DS1693_ALARM_SECONDS 0x01 | ||
| 292 | #define TODC_TYPE_DS1693_CENTURY 0x48 | ||
| 293 | #define TODC_TYPE_DS1693_FLAGS 0xff | ||
| 294 | #define TODC_TYPE_DS1693_NVRAM_ADDR_REG 0 | ||
| 295 | #define TODC_TYPE_DS1693_NVRAM_DATA_REG 0 | ||
| 296 | |||
| 297 | #define TODC_TYPE_DS1743_NVRAM_SIZE 0x1ff8 | ||
| 298 | #define TODC_TYPE_DS1743_SW_FLAGS 0 | ||
| 299 | #define TODC_TYPE_DS1743_YEAR 0x1fff | ||
| 300 | #define TODC_TYPE_DS1743_MONTH 0x1ffe | ||
| 301 | #define TODC_TYPE_DS1743_DOM 0x1ffd /* Day of Month */ | ||
| 302 | #define TODC_TYPE_DS1743_DOW 0x1ffc /* Day of Week */ | ||
| 303 | #define TODC_TYPE_DS1743_HOURS 0x1ffb | ||
| 304 | #define TODC_TYPE_DS1743_MINUTES 0x1ffa | ||
| 305 | #define TODC_TYPE_DS1743_SECONDS 0x1ff9 | ||
| 306 | #define TODC_TYPE_DS1743_CNTL_B 0x1ff9 | ||
| 307 | #define TODC_TYPE_DS1743_CNTL_A 0x1ff8 /* control_a R/W regs */ | ||
| 308 | #define TODC_TYPE_DS1743_WATCHDOG 0x1fff | ||
| 309 | #define TODC_TYPE_DS1743_INTERRUPTS 0x1fff | ||
| 310 | #define TODC_TYPE_DS1743_ALARM_DATE 0x1fff | ||
| 311 | #define TODC_TYPE_DS1743_ALARM_HOUR 0x1fff | ||
| 312 | #define TODC_TYPE_DS1743_ALARM_MINUTES 0x1fff | ||
| 313 | #define TODC_TYPE_DS1743_ALARM_SECONDS 0x1fff | ||
| 314 | #define TODC_TYPE_DS1743_CENTURY 0x1ff8 | ||
| 315 | #define TODC_TYPE_DS1743_FLAGS 0x1fff | ||
| 316 | #define TODC_TYPE_DS1743_NVRAM_ADDR_REG 0 | ||
| 317 | #define TODC_TYPE_DS1743_NVRAM_DATA_REG 0 | ||
| 318 | |||
| 319 | #define TODC_TYPE_DS1746_NVRAM_SIZE 0x1fff8 | ||
| 320 | #define TODC_TYPE_DS1746_SW_FLAGS 0 | ||
| 321 | #define TODC_TYPE_DS1746_YEAR 0x1ffff | ||
| 322 | #define TODC_TYPE_DS1746_MONTH 0x1fffe | ||
| 323 | #define TODC_TYPE_DS1746_DOM 0x1fffd /* Day of Month */ | ||
| 324 | #define TODC_TYPE_DS1746_DOW 0x1fffc /* Day of Week */ | ||
| 325 | #define TODC_TYPE_DS1746_HOURS 0x1fffb | ||
| 326 | #define TODC_TYPE_DS1746_MINUTES 0x1fffa | ||
| 327 | #define TODC_TYPE_DS1746_SECONDS 0x1fff9 | ||
| 328 | #define TODC_TYPE_DS1746_CNTL_B 0x1fff9 | ||
| 329 | #define TODC_TYPE_DS1746_CNTL_A 0x1fff8 /* control_a R/W regs */ | ||
| 330 | #define TODC_TYPE_DS1746_WATCHDOG 0x00000 | ||
| 331 | #define TODC_TYPE_DS1746_INTERRUPTS 0x00000 | ||
| 332 | #define TODC_TYPE_DS1746_ALARM_DATE 0x00000 | ||
| 333 | #define TODC_TYPE_DS1746_ALARM_HOUR 0x00000 | ||
| 334 | #define TODC_TYPE_DS1746_ALARM_MINUTES 0x00000 | ||
| 335 | #define TODC_TYPE_DS1746_ALARM_SECONDS 0x00000 | ||
| 336 | #define TODC_TYPE_DS1746_CENTURY 0x00000 | ||
| 337 | #define TODC_TYPE_DS1746_FLAGS 0x00000 | ||
| 338 | #define TODC_TYPE_DS1746_NVRAM_ADDR_REG 0 | ||
| 339 | #define TODC_TYPE_DS1746_NVRAM_DATA_REG 0 | ||
| 340 | |||
| 341 | #define TODC_TYPE_DS1747_NVRAM_SIZE 0x7fff8 | ||
| 342 | #define TODC_TYPE_DS1747_SW_FLAGS 0 | ||
| 343 | #define TODC_TYPE_DS1747_YEAR 0x7ffff | ||
| 344 | #define TODC_TYPE_DS1747_MONTH 0x7fffe | ||
| 345 | #define TODC_TYPE_DS1747_DOM 0x7fffd /* Day of Month */ | ||
| 346 | #define TODC_TYPE_DS1747_DOW 0x7fffc /* Day of Week */ | ||
| 347 | #define TODC_TYPE_DS1747_HOURS 0x7fffb | ||
| 348 | #define TODC_TYPE_DS1747_MINUTES 0x7fffa | ||
| 349 | #define TODC_TYPE_DS1747_SECONDS 0x7fff9 | ||
| 350 | #define TODC_TYPE_DS1747_CNTL_B 0x7fff9 | ||
| 351 | #define TODC_TYPE_DS1747_CNTL_A 0x7fff8 /* control_a R/W regs */ | ||
| 352 | #define TODC_TYPE_DS1747_WATCHDOG 0x00000 | ||
| 353 | #define TODC_TYPE_DS1747_INTERRUPTS 0x00000 | ||
| 354 | #define TODC_TYPE_DS1747_ALARM_DATE 0x00000 | ||
| 355 | #define TODC_TYPE_DS1747_ALARM_HOUR 0x00000 | ||
| 356 | #define TODC_TYPE_DS1747_ALARM_MINUTES 0x00000 | ||
| 357 | #define TODC_TYPE_DS1747_ALARM_SECONDS 0x00000 | ||
| 358 | #define TODC_TYPE_DS1747_CENTURY 0x00000 | ||
| 359 | #define TODC_TYPE_DS1747_FLAGS 0x00000 | ||
| 360 | #define TODC_TYPE_DS1747_NVRAM_ADDR_REG 0 | ||
| 361 | #define TODC_TYPE_DS1747_NVRAM_DATA_REG 0 | ||
| 362 | |||
| 363 | #define TODC_TYPE_DS17285_NVRAM_SIZE (0x1000-0x80) /* 4Kx8 NVRAM (minus RTC regs) */ | ||
| 364 | #define TODC_TYPE_DS17285_SW_FLAGS TODC_FLAG_2_LEVEL_NVRAM | ||
| 365 | #define TODC_TYPE_DS17285_SECONDS (TODC_TYPE_DS17285_NVRAM_SIZE + 0x00) | ||
| 366 | #define TODC_TYPE_DS17285_ALARM_SECONDS (TODC_TYPE_DS17285_NVRAM_SIZE + 0x01) | ||
| 367 | #define TODC_TYPE_DS17285_MINUTES (TODC_TYPE_DS17285_NVRAM_SIZE + 0x02) | ||
| 368 | #define TODC_TYPE_DS17285_ALARM_MINUTES (TODC_TYPE_DS17285_NVRAM_SIZE + 0x03) | ||
| 369 | #define TODC_TYPE_DS17285_HOURS (TODC_TYPE_DS17285_NVRAM_SIZE + 0x04) | ||
| 370 | #define TODC_TYPE_DS17285_ALARM_HOUR (TODC_TYPE_DS17285_NVRAM_SIZE + 0x05) | ||
| 371 | #define TODC_TYPE_DS17285_DOW (TODC_TYPE_DS17285_NVRAM_SIZE + 0x06) | ||
| 372 | #define TODC_TYPE_DS17285_DOM (TODC_TYPE_DS17285_NVRAM_SIZE + 0x07) | ||
| 373 | #define TODC_TYPE_DS17285_MONTH (TODC_TYPE_DS17285_NVRAM_SIZE + 0x08) | ||
| 374 | #define TODC_TYPE_DS17285_YEAR (TODC_TYPE_DS17285_NVRAM_SIZE + 0x09) | ||
| 375 | #define TODC_TYPE_DS17285_CNTL_A (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0A) | ||
| 376 | #define TODC_TYPE_DS17285_CNTL_B (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0B) | ||
| 377 | #define TODC_TYPE_DS17285_CNTL_C (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0C) | ||
| 378 | #define TODC_TYPE_DS17285_CNTL_D (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0D) | ||
| 379 | #define TODC_TYPE_DS17285_WATCHDOG 0 | ||
| 380 | #define TODC_TYPE_DS17285_INTERRUPTS 0 | ||
| 381 | #define TODC_TYPE_DS17285_ALARM_DATE 0 | ||
| 382 | #define TODC_TYPE_DS17285_CENTURY 0 | ||
| 383 | #define TODC_TYPE_DS17285_FLAGS 0 | ||
| 384 | #define TODC_TYPE_DS17285_NVRAM_ADDR_REG 0x50 | ||
| 385 | #define TODC_TYPE_DS17285_NVRAM_DATA_REG 0x53 | ||
| 386 | |||
| 387 | #define TODC_TYPE_MC146818_NVRAM_SIZE 0 /* XXXX */ | ||
| 388 | #define TODC_TYPE_MC146818_SW_FLAGS 0 | ||
| 389 | #define TODC_TYPE_MC146818_YEAR 0x09 | ||
| 390 | #define TODC_TYPE_MC146818_MONTH 0x08 | ||
| 391 | #define TODC_TYPE_MC146818_DOM 0x07 /* Day of Month */ | ||
| 392 | #define TODC_TYPE_MC146818_DOW 0x06 /* Day of Week */ | ||
| 393 | #define TODC_TYPE_MC146818_HOURS 0x04 | ||
| 394 | #define TODC_TYPE_MC146818_MINUTES 0x02 | ||
| 395 | #define TODC_TYPE_MC146818_SECONDS 0x00 | ||
| 396 | #define TODC_TYPE_MC146818_CNTL_B 0x0a | ||
| 397 | #define TODC_TYPE_MC146818_CNTL_A 0x0b /* control_a R/W regs */ | ||
| 398 | #define TODC_TYPE_MC146818_WATCHDOG 0 | ||
| 399 | #define TODC_TYPE_MC146818_INTERRUPTS 0x0c | ||
| 400 | #define TODC_TYPE_MC146818_ALARM_DATE 0xff | ||
| 401 | #define TODC_TYPE_MC146818_ALARM_HOUR 0x05 | ||
| 402 | #define TODC_TYPE_MC146818_ALARM_MINUTES 0x03 | ||
| 403 | #define TODC_TYPE_MC146818_ALARM_SECONDS 0x01 | ||
| 404 | #define TODC_TYPE_MC146818_CENTURY 0xff | ||
| 405 | #define TODC_TYPE_MC146818_FLAGS 0xff | ||
| 406 | #define TODC_TYPE_MC146818_NVRAM_ADDR_REG 0 | ||
| 407 | #define TODC_TYPE_MC146818_NVRAM_DATA_REG 0 | ||
| 408 | |||
| 409 | #define TODC_TYPE_PC97307_NVRAM_SIZE 0 /* No NVRAM? */ | ||
| 410 | #define TODC_TYPE_PC97307_SW_FLAGS 0 | ||
| 411 | #define TODC_TYPE_PC97307_YEAR 0x09 | ||
| 412 | #define TODC_TYPE_PC97307_MONTH 0x08 | ||
| 413 | #define TODC_TYPE_PC97307_DOM 0x07 /* Day of Month */ | ||
| 414 | #define TODC_TYPE_PC97307_DOW 0x06 /* Day of Week */ | ||
| 415 | #define TODC_TYPE_PC97307_HOURS 0x04 | ||
| 416 | #define TODC_TYPE_PC97307_MINUTES 0x02 | ||
| 417 | #define TODC_TYPE_PC97307_SECONDS 0x00 | ||
| 418 | #define TODC_TYPE_PC97307_CNTL_B 0x0a | ||
| 419 | #define TODC_TYPE_PC97307_CNTL_A 0x0b /* control_a R/W regs */ | ||
| 420 | #define TODC_TYPE_PC97307_WATCHDOG 0x0c | ||
| 421 | #define TODC_TYPE_PC97307_INTERRUPTS 0x0d | ||
| 422 | #define TODC_TYPE_PC97307_ALARM_DATE 0xff | ||
| 423 | #define TODC_TYPE_PC97307_ALARM_HOUR 0x05 | ||
| 424 | #define TODC_TYPE_PC97307_ALARM_MINUTES 0x03 | ||
| 425 | #define TODC_TYPE_PC97307_ALARM_SECONDS 0x01 | ||
| 426 | #define TODC_TYPE_PC97307_CENTURY 0xff | ||
| 427 | #define TODC_TYPE_PC97307_FLAGS 0xff | ||
| 428 | #define TODC_TYPE_PC97307_NVRAM_ADDR_REG 0 | ||
| 429 | #define TODC_TYPE_PC97307_NVRAM_DATA_REG 0 | ||
| 430 | |||
| 431 | /* | ||
| 432 | * Define macros to allocate and init the todc_info_t table that will | ||
| 433 | * be used by the todc_time.c routines. | ||
| 434 | */ | ||
| 435 | #define TODC_ALLOC() \ | ||
| 436 | static todc_info_t todc_info_alloc; \ | ||
| 437 | todc_info_t *todc_info = &todc_info_alloc; | ||
| 438 | |||
| 439 | #define TODC_INIT(clock_type, as0, as1, data, bits) { \ | ||
| 440 | todc_info->rtc_type = clock_type; \ | ||
| 441 | \ | ||
| 442 | todc_info->nvram_as0 = (unsigned int)(as0); \ | ||
| 443 | todc_info->nvram_as1 = (unsigned int)(as1); \ | ||
| 444 | todc_info->nvram_data = (unsigned int)(data); \ | ||
| 445 | \ | ||
| 446 | todc_info->as0_bits = (bits); \ | ||
| 447 | \ | ||
| 448 | todc_info->nvram_size = clock_type ##_NVRAM_SIZE; \ | ||
| 449 | todc_info->sw_flags = clock_type ##_SW_FLAGS; \ | ||
| 450 | \ | ||
| 451 | todc_info->year = clock_type ##_YEAR; \ | ||
| 452 | todc_info->month = clock_type ##_MONTH; \ | ||
| 453 | todc_info->day_of_month = clock_type ##_DOM; \ | ||
| 454 | todc_info->day_of_week = clock_type ##_DOW; \ | ||
| 455 | todc_info->hours = clock_type ##_HOURS; \ | ||
| 456 | todc_info->minutes = clock_type ##_MINUTES; \ | ||
| 457 | todc_info->seconds = clock_type ##_SECONDS; \ | ||
| 458 | todc_info->control_b = clock_type ##_CNTL_B; \ | ||
| 459 | todc_info->control_a = clock_type ##_CNTL_A; \ | ||
| 460 | todc_info->watchdog = clock_type ##_WATCHDOG; \ | ||
| 461 | todc_info->interrupts = clock_type ##_INTERRUPTS; \ | ||
| 462 | todc_info->alarm_date = clock_type ##_ALARM_DATE; \ | ||
| 463 | todc_info->alarm_hour = clock_type ##_ALARM_HOUR; \ | ||
| 464 | todc_info->alarm_minutes = clock_type ##_ALARM_MINUTES; \ | ||
| 465 | todc_info->alarm_seconds = clock_type ##_ALARM_SECONDS; \ | ||
| 466 | todc_info->century = clock_type ##_CENTURY; \ | ||
| 467 | todc_info->flags = clock_type ##_FLAGS; \ | ||
| 468 | \ | ||
| 469 | todc_info->nvram_addr_reg = clock_type ##_NVRAM_ADDR_REG; \ | ||
| 470 | todc_info->nvram_data_reg = clock_type ##_NVRAM_DATA_REG; \ | ||
| 471 | } | ||
| 472 | |||
| 473 | extern todc_info_t *todc_info; | ||
| 474 | |||
| 475 | unsigned char todc_direct_read_val(int addr); | ||
| 476 | void todc_direct_write_val(int addr, unsigned char val); | ||
| 477 | unsigned char todc_m48txx_read_val(int addr); | ||
| 478 | void todc_m48txx_write_val(int addr, unsigned char val); | ||
| 479 | unsigned char todc_mc146818_read_val(int addr); | ||
| 480 | void todc_mc146818_write_val(int addr, unsigned char val); | ||
| 481 | |||
| 482 | long todc_time_init(void); | ||
| 483 | void todc_get_rtc_time(struct rtc_time *); | ||
| 484 | int todc_set_rtc_time(struct rtc_time *); | ||
| 485 | void todc_calibrate_decr(void); | ||
| 486 | |||
| 487 | #endif /* __PPC_KERNEL_TODC_H */ | ||
diff --git a/include/asm-powerpc/tsi108.h b/include/asm-powerpc/tsi108.h new file mode 100644 index 000000000000..c4c278d72f71 --- /dev/null +++ b/include/asm-powerpc/tsi108.h | |||
| @@ -0,0 +1,109 @@ | |||
| 1 | /* | ||
| 2 | * include/asm-ppc/tsi108.h | ||
| 3 | * | ||
| 4 | * common routine and memory layout for Tundra TSI108(Grendel) host bridge | ||
| 5 | * memory controller. | ||
| 6 | * | ||
| 7 | * Author: Jacob Pan (jacob.pan@freescale.com) | ||
| 8 | * Alex Bounine (alexandreb@tundra.com) | ||
| 9 | * 2004 (c) Freescale Semiconductor Inc. This file is licensed under | ||
| 10 | * the terms of the GNU General Public License version 2. This program | ||
| 11 | * is licensed "as is" without any warranty of any kind, whether express | ||
| 12 | * or implied. | ||
| 13 | */ | ||
| 14 | #ifndef __PPC_KERNEL_TSI108_H | ||
| 15 | #define __PPC_KERNEL_TSI108_H | ||
| 16 | |||
| 17 | #include <asm/pci-bridge.h> | ||
| 18 | |||
| 19 | /* Size of entire register space */ | ||
| 20 | #define TSI108_REG_SIZE (0x10000) | ||
| 21 | |||
| 22 | /* Sizes of register spaces for individual blocks */ | ||
| 23 | #define TSI108_HLP_SIZE 0x1000 | ||
| 24 | #define TSI108_PCI_SIZE 0x1000 | ||
| 25 | #define TSI108_CLK_SIZE 0x1000 | ||
| 26 | #define TSI108_PB_SIZE 0x1000 | ||
| 27 | #define TSI108_SD_SIZE 0x1000 | ||
| 28 | #define TSI108_DMA_SIZE 0x1000 | ||
| 29 | #define TSI108_ETH_SIZE 0x1000 | ||
| 30 | #define TSI108_I2C_SIZE 0x400 | ||
| 31 | #define TSI108_MPIC_SIZE 0x400 | ||
| 32 | #define TSI108_UART0_SIZE 0x200 | ||
| 33 | #define TSI108_GPIO_SIZE 0x200 | ||
| 34 | #define TSI108_UART1_SIZE 0x200 | ||
| 35 | |||
| 36 | /* Offsets within Tsi108(A) CSR space for individual blocks */ | ||
| 37 | #define TSI108_HLP_OFFSET 0x0000 | ||
| 38 | #define TSI108_PCI_OFFSET 0x1000 | ||
| 39 | #define TSI108_CLK_OFFSET 0x2000 | ||
| 40 | #define TSI108_PB_OFFSET 0x3000 | ||
| 41 | #define TSI108_SD_OFFSET 0x4000 | ||
| 42 | #define TSI108_DMA_OFFSET 0x5000 | ||
| 43 | #define TSI108_ETH_OFFSET 0x6000 | ||
| 44 | #define TSI108_I2C_OFFSET 0x7000 | ||
| 45 | #define TSI108_MPIC_OFFSET 0x7400 | ||
| 46 | #define TSI108_UART0_OFFSET 0x7800 | ||
| 47 | #define TSI108_GPIO_OFFSET 0x7A00 | ||
| 48 | #define TSI108_UART1_OFFSET 0x7C00 | ||
| 49 | |||
| 50 | /* Tsi108 registers used by common code components */ | ||
| 51 | #define TSI108_PCI_CSR (0x004) | ||
| 52 | #define TSI108_PCI_IRP_CFG_CTL (0x180) | ||
| 53 | #define TSI108_PCI_IRP_STAT (0x184) | ||
| 54 | #define TSI108_PCI_IRP_ENABLE (0x188) | ||
| 55 | #define TSI108_PCI_IRP_INTAD (0x18C) | ||
| 56 | |||
| 57 | #define TSI108_PCI_IRP_STAT_P_INT (0x00400000) | ||
| 58 | #define TSI108_PCI_IRP_ENABLE_P_INT (0x00400000) | ||
| 59 | |||
| 60 | #define TSI108_CG_PWRUP_STATUS (0x234) | ||
| 61 | |||
| 62 | #define TSI108_PB_ISR (0x00C) | ||
| 63 | #define TSI108_PB_ERRCS (0x404) | ||
| 64 | #define TSI108_PB_AERR (0x408) | ||
| 65 | |||
| 66 | #define TSI108_PB_ERRCS_ES (1 << 1) | ||
| 67 | #define TSI108_PB_ISR_PBS_RD_ERR (1 << 8) | ||
| 68 | |||
| 69 | #define TSI108_PCI_CFG_BASE_PHYS (0xfb000000) | ||
| 70 | #define TSI108_PCI_CFG_SIZE (0x01000000) | ||
| 71 | /* Global variables */ | ||
| 72 | |||
| 73 | extern u32 tsi108_pci_cfg_base; | ||
| 74 | /* Exported functions */ | ||
| 75 | |||
| 76 | extern int tsi108_bridge_init(struct pci_controller *hose, uint phys_csr_base); | ||
| 77 | extern unsigned long tsi108_get_mem_size(void); | ||
| 78 | extern unsigned long tsi108_get_cpu_clk(void); | ||
| 79 | extern unsigned long tsi108_get_sdc_clk(void); | ||
| 80 | extern int tsi108_direct_write_config(struct pci_bus *bus, unsigned int devfn, | ||
| 81 | int offset, int len, u32 val); | ||
| 82 | extern int tsi108_direct_read_config(struct pci_bus *bus, unsigned int devfn, | ||
| 83 | int offset, int len, u32 * val); | ||
| 84 | extern void tsi108_clear_pci_error(u32 pci_cfg_base); | ||
| 85 | |||
| 86 | extern phys_addr_t get_csrbase(void); | ||
| 87 | |||
| 88 | typedef struct { | ||
| 89 | u32 regs; /* hw registers base address */ | ||
| 90 | u32 phyregs; /* phy registers base address */ | ||
| 91 | u16 phy; /* phy address */ | ||
| 92 | u16 irq_num; /* irq number */ | ||
| 93 | u8 mac_addr[6]; /* phy mac address */ | ||
| 94 | } hw_info; | ||
| 95 | |||
| 96 | extern u32 get_vir_csrbase(void); | ||
| 97 | extern u32 tsi108_csr_vir_base; | ||
| 98 | |||
| 99 | extern inline u32 tsi108_read_reg(u32 reg_offset) | ||
| 100 | { | ||
| 101 | return in_be32((volatile u32 *)(tsi108_csr_vir_base + reg_offset)); | ||
| 102 | } | ||
| 103 | |||
| 104 | extern inline void tsi108_write_reg(u32 reg_offset, u32 val) | ||
| 105 | { | ||
| 106 | out_be32((volatile u32 *)(tsi108_csr_vir_base + reg_offset), val); | ||
| 107 | } | ||
| 108 | |||
| 109 | #endif /* __PPC_KERNEL_TSI108_H */ | ||
diff --git a/include/asm-powerpc/udbg.h b/include/asm-powerpc/udbg.h index 19a1517ac43b..55e57844fa78 100644 --- a/include/asm-powerpc/udbg.h +++ b/include/asm-powerpc/udbg.h | |||
| @@ -42,7 +42,8 @@ extern void __init udbg_init_debug_lpar(void); | |||
| 42 | extern void __init udbg_init_pmac_realmode(void); | 42 | extern void __init udbg_init_pmac_realmode(void); |
| 43 | extern void __init udbg_init_maple_realmode(void); | 43 | extern void __init udbg_init_maple_realmode(void); |
| 44 | extern void __init udbg_init_iseries(void); | 44 | extern void __init udbg_init_iseries(void); |
| 45 | extern void __init udbg_init_rtas(void); | 45 | extern void __init udbg_init_rtas_panel(void); |
| 46 | extern void __init udbg_init_rtas_console(void); | ||
| 46 | 47 | ||
| 47 | #endif /* __KERNEL__ */ | 48 | #endif /* __KERNEL__ */ |
| 48 | #endif /* _ASM_POWERPC_UDBG_H */ | 49 | #endif /* _ASM_POWERPC_UDBG_H */ |
diff --git a/kernel/kexec.c b/kernel/kexec.c index 58f0f382597c..50087ecf337e 100644 --- a/kernel/kexec.c +++ b/kernel/kexec.c | |||
| @@ -1042,7 +1042,6 @@ asmlinkage long compat_sys_kexec_load(unsigned long entry, | |||
| 1042 | 1042 | ||
| 1043 | void crash_kexec(struct pt_regs *regs) | 1043 | void crash_kexec(struct pt_regs *regs) |
| 1044 | { | 1044 | { |
| 1045 | struct kimage *image; | ||
| 1046 | int locked; | 1045 | int locked; |
| 1047 | 1046 | ||
| 1048 | 1047 | ||
| @@ -1056,12 +1055,11 @@ void crash_kexec(struct pt_regs *regs) | |||
| 1056 | */ | 1055 | */ |
| 1057 | locked = xchg(&kexec_lock, 1); | 1056 | locked = xchg(&kexec_lock, 1); |
| 1058 | if (!locked) { | 1057 | if (!locked) { |
| 1059 | image = xchg(&kexec_crash_image, NULL); | 1058 | if (kexec_crash_image) { |
| 1060 | if (image) { | ||
| 1061 | struct pt_regs fixed_regs; | 1059 | struct pt_regs fixed_regs; |
| 1062 | crash_setup_regs(&fixed_regs, regs); | 1060 | crash_setup_regs(&fixed_regs, regs); |
| 1063 | machine_crash_shutdown(&fixed_regs); | 1061 | machine_crash_shutdown(&fixed_regs); |
| 1064 | machine_kexec(image); | 1062 | machine_kexec(kexec_crash_image); |
| 1065 | } | 1063 | } |
| 1066 | xchg(&kexec_lock, 0); | 1064 | xchg(&kexec_lock, 0); |
| 1067 | } | 1065 | } |
