linux/arch/mips/bcm63xx/reset.c
<<
>>
Prefs
   1/*
   2 * This file is subject to the terms and conditions of the GNU General Public
   3 * License.  See the file "COPYING" in the main directory of this archive
   4 * for more details.
   5 *
   6 * Copyright (C) 2012 Jonas Gorski <jonas.gorski@gmail.com>
   7 */
   8
   9#include <linux/module.h>
  10#include <linux/mutex.h>
  11#include <linux/err.h>
  12#include <linux/clk.h>
  13#include <linux/delay.h>
  14#include <bcm63xx_cpu.h>
  15#include <bcm63xx_io.h>
  16#include <bcm63xx_regs.h>
  17#include <bcm63xx_reset.h>
  18
  19#define __GEN_RESET_BITS_TABLE(__cpu)                                   \
  20        [BCM63XX_RESET_SPI]             = BCM## __cpu ##_RESET_SPI,     \
  21        [BCM63XX_RESET_ENET]            = BCM## __cpu ##_RESET_ENET,    \
  22        [BCM63XX_RESET_USBH]            = BCM## __cpu ##_RESET_USBH,    \
  23        [BCM63XX_RESET_USBD]            = BCM## __cpu ##_RESET_USBD,    \
  24        [BCM63XX_RESET_DSL]             = BCM## __cpu ##_RESET_DSL,     \
  25        [BCM63XX_RESET_SAR]             = BCM## __cpu ##_RESET_SAR,     \
  26        [BCM63XX_RESET_EPHY]            = BCM## __cpu ##_RESET_EPHY,    \
  27        [BCM63XX_RESET_ENETSW]          = BCM## __cpu ##_RESET_ENETSW,  \
  28        [BCM63XX_RESET_PCM]             = BCM## __cpu ##_RESET_PCM,     \
  29        [BCM63XX_RESET_MPI]             = BCM## __cpu ##_RESET_MPI,     \
  30        [BCM63XX_RESET_PCIE]            = BCM## __cpu ##_RESET_PCIE,    \
  31        [BCM63XX_RESET_PCIE_EXT]        = BCM## __cpu ##_RESET_PCIE_EXT,
  32
  33#define BCM3368_RESET_SPI       SOFTRESET_3368_SPI_MASK
  34#define BCM3368_RESET_ENET      SOFTRESET_3368_ENET_MASK
  35#define BCM3368_RESET_USBH      0
  36#define BCM3368_RESET_USBD      SOFTRESET_3368_USBS_MASK
  37#define BCM3368_RESET_DSL       0
  38#define BCM3368_RESET_SAR       0
  39#define BCM3368_RESET_EPHY      SOFTRESET_3368_EPHY_MASK
  40#define BCM3368_RESET_ENETSW    0
  41#define BCM3368_RESET_PCM       SOFTRESET_3368_PCM_MASK
  42#define BCM3368_RESET_MPI       SOFTRESET_3368_MPI_MASK
  43#define BCM3368_RESET_PCIE      0
  44#define BCM3368_RESET_PCIE_EXT  0
  45
  46#define BCM6328_RESET_SPI       SOFTRESET_6328_SPI_MASK
  47#define BCM6328_RESET_ENET      0
  48#define BCM6328_RESET_USBH      SOFTRESET_6328_USBH_MASK
  49#define BCM6328_RESET_USBD      SOFTRESET_6328_USBS_MASK
  50#define BCM6328_RESET_DSL       0
  51#define BCM6328_RESET_SAR       SOFTRESET_6328_SAR_MASK
  52#define BCM6328_RESET_EPHY      SOFTRESET_6328_EPHY_MASK
  53#define BCM6328_RESET_ENETSW    SOFTRESET_6328_ENETSW_MASK
  54#define BCM6328_RESET_PCM       SOFTRESET_6328_PCM_MASK
  55#define BCM6328_RESET_MPI       0
  56#define BCM6328_RESET_PCIE      \
  57                                (SOFTRESET_6328_PCIE_MASK |             \
  58                                 SOFTRESET_6328_PCIE_CORE_MASK |        \
  59                                 SOFTRESET_6328_PCIE_HARD_MASK)
  60#define BCM6328_RESET_PCIE_EXT  SOFTRESET_6328_PCIE_EXT_MASK
  61
  62#define BCM6338_RESET_SPI       SOFTRESET_6338_SPI_MASK
  63#define BCM6338_RESET_ENET      SOFTRESET_6338_ENET_MASK
  64#define BCM6338_RESET_USBH      SOFTRESET_6338_USBH_MASK
  65#define BCM6338_RESET_USBD      SOFTRESET_6338_USBS_MASK
  66#define BCM6338_RESET_DSL       SOFTRESET_6338_ADSL_MASK
  67#define BCM6338_RESET_SAR       SOFTRESET_6338_SAR_MASK
  68#define BCM6338_RESET_EPHY      0
  69#define BCM6338_RESET_ENETSW    0
  70#define BCM6338_RESET_PCM       0
  71#define BCM6338_RESET_MPI       0
  72#define BCM6338_RESET_PCIE      0
  73#define BCM6338_RESET_PCIE_EXT  0
  74
  75#define BCM6348_RESET_SPI       SOFTRESET_6348_SPI_MASK
  76#define BCM6348_RESET_ENET      SOFTRESET_6348_ENET_MASK
  77#define BCM6348_RESET_USBH      SOFTRESET_6348_USBH_MASK
  78#define BCM6348_RESET_USBD      SOFTRESET_6348_USBS_MASK
  79#define BCM6348_RESET_DSL       SOFTRESET_6348_ADSL_MASK
  80#define BCM6348_RESET_SAR       SOFTRESET_6348_SAR_MASK
  81#define BCM6348_RESET_EPHY      0
  82#define BCM6348_RESET_ENETSW    0
  83#define BCM6348_RESET_PCM       0
  84#define BCM6348_RESET_MPI       0
  85#define BCM6348_RESET_PCIE      0
  86#define BCM6348_RESET_PCIE_EXT  0
  87
  88#define BCM6358_RESET_SPI       SOFTRESET_6358_SPI_MASK
  89#define BCM6358_RESET_ENET      SOFTRESET_6358_ENET_MASK
  90#define BCM6358_RESET_USBH      SOFTRESET_6358_USBH_MASK
  91#define BCM6358_RESET_USBD      0
  92#define BCM6358_RESET_DSL       SOFTRESET_6358_ADSL_MASK
  93#define BCM6358_RESET_SAR       SOFTRESET_6358_SAR_MASK
  94#define BCM6358_RESET_EPHY      SOFTRESET_6358_EPHY_MASK
  95#define BCM6358_RESET_ENETSW    0
  96#define BCM6358_RESET_PCM       SOFTRESET_6358_PCM_MASK
  97#define BCM6358_RESET_MPI       SOFTRESET_6358_MPI_MASK
  98#define BCM6358_RESET_PCIE      0
  99#define BCM6358_RESET_PCIE_EXT  0
 100
 101#define BCM6362_RESET_SPI       SOFTRESET_6362_SPI_MASK
 102#define BCM6362_RESET_ENET      0
 103#define BCM6362_RESET_USBH      SOFTRESET_6362_USBH_MASK
 104#define BCM6362_RESET_USBD      SOFTRESET_6362_USBS_MASK
 105#define BCM6362_RESET_DSL       0
 106#define BCM6362_RESET_SAR       SOFTRESET_6362_SAR_MASK
 107#define BCM6362_RESET_EPHY      SOFTRESET_6362_EPHY_MASK
 108#define BCM6362_RESET_ENETSW    SOFTRESET_6362_ENETSW_MASK
 109#define BCM6362_RESET_PCM       SOFTRESET_6362_PCM_MASK
 110#define BCM6362_RESET_MPI       0
 111#define BCM6362_RESET_PCIE      (SOFTRESET_6362_PCIE_MASK | \
 112                                 SOFTRESET_6362_PCIE_CORE_MASK)
 113#define BCM6362_RESET_PCIE_EXT  SOFTRESET_6362_PCIE_EXT_MASK
 114
 115#define BCM6368_RESET_SPI       SOFTRESET_6368_SPI_MASK
 116#define BCM6368_RESET_ENET      0
 117#define BCM6368_RESET_USBH      SOFTRESET_6368_USBH_MASK
 118#define BCM6368_RESET_USBD      SOFTRESET_6368_USBS_MASK
 119#define BCM6368_RESET_DSL       0
 120#define BCM6368_RESET_SAR       SOFTRESET_6368_SAR_MASK
 121#define BCM6368_RESET_EPHY      SOFTRESET_6368_EPHY_MASK
 122#define BCM6368_RESET_ENETSW    0
 123#define BCM6368_RESET_PCM       SOFTRESET_6368_PCM_MASK
 124#define BCM6368_RESET_MPI       SOFTRESET_6368_MPI_MASK
 125#define BCM6368_RESET_PCIE      0
 126#define BCM6368_RESET_PCIE_EXT  0
 127
 128/*
 129 * core reset bits
 130 */
 131static const u32 bcm3368_reset_bits[] = {
 132        __GEN_RESET_BITS_TABLE(3368)
 133};
 134
 135static const u32 bcm6328_reset_bits[] = {
 136        __GEN_RESET_BITS_TABLE(6328)
 137};
 138
 139static const u32 bcm6338_reset_bits[] = {
 140        __GEN_RESET_BITS_TABLE(6338)
 141};
 142
 143static const u32 bcm6348_reset_bits[] = {
 144        __GEN_RESET_BITS_TABLE(6348)
 145};
 146
 147static const u32 bcm6358_reset_bits[] = {
 148        __GEN_RESET_BITS_TABLE(6358)
 149};
 150
 151static const u32 bcm6362_reset_bits[] = {
 152        __GEN_RESET_BITS_TABLE(6362)
 153};
 154
 155static const u32 bcm6368_reset_bits[] = {
 156        __GEN_RESET_BITS_TABLE(6368)
 157};
 158
 159const u32 *bcm63xx_reset_bits;
 160static int reset_reg;
 161
 162static int __init bcm63xx_reset_bits_init(void)
 163{
 164        if (BCMCPU_IS_3368()) {
 165                reset_reg = PERF_SOFTRESET_6358_REG;
 166                bcm63xx_reset_bits = bcm3368_reset_bits;
 167        } else if (BCMCPU_IS_6328()) {
 168                reset_reg = PERF_SOFTRESET_6328_REG;
 169                bcm63xx_reset_bits = bcm6328_reset_bits;
 170        } else if (BCMCPU_IS_6338()) {
 171                reset_reg = PERF_SOFTRESET_REG;
 172                bcm63xx_reset_bits = bcm6338_reset_bits;
 173        } else if (BCMCPU_IS_6348()) {
 174                reset_reg = PERF_SOFTRESET_REG;
 175                bcm63xx_reset_bits = bcm6348_reset_bits;
 176        } else if (BCMCPU_IS_6358()) {
 177                reset_reg = PERF_SOFTRESET_6358_REG;
 178                bcm63xx_reset_bits = bcm6358_reset_bits;
 179        } else if (BCMCPU_IS_6362()) {
 180                reset_reg = PERF_SOFTRESET_6362_REG;
 181                bcm63xx_reset_bits = bcm6362_reset_bits;
 182        } else if (BCMCPU_IS_6368()) {
 183                reset_reg = PERF_SOFTRESET_6368_REG;
 184                bcm63xx_reset_bits = bcm6368_reset_bits;
 185        }
 186
 187        return 0;
 188}
 189
 190static DEFINE_SPINLOCK(reset_mutex);
 191
 192static void __bcm63xx_core_set_reset(u32 mask, int enable)
 193{
 194        unsigned long flags;
 195        u32 val;
 196
 197        if (!mask)
 198                return;
 199
 200        spin_lock_irqsave(&reset_mutex, flags);
 201        val = bcm_perf_readl(reset_reg);
 202
 203        if (enable)
 204                val &= ~mask;
 205        else
 206                val |= mask;
 207
 208        bcm_perf_writel(val, reset_reg);
 209        spin_unlock_irqrestore(&reset_mutex, flags);
 210}
 211
 212void bcm63xx_core_set_reset(enum bcm63xx_core_reset core, int reset)
 213{
 214        __bcm63xx_core_set_reset(bcm63xx_reset_bits[core], reset);
 215}
 216EXPORT_SYMBOL(bcm63xx_core_set_reset);
 217
 218postcore_initcall(bcm63xx_reset_bits_init);
 219