diff options
| -rw-r--r-- | drivers/pinctrl/Kconfig | 4 | ||||
| -rw-r--r-- | drivers/pinctrl/pinctrl-sirf.c | 48 |
2 files changed, 39 insertions, 13 deletions
diff --git a/drivers/pinctrl/Kconfig b/drivers/pinctrl/Kconfig index 011133772d2a..5f2f9dc43e3b 100644 --- a/drivers/pinctrl/Kconfig +++ b/drivers/pinctrl/Kconfig | |||
| @@ -143,8 +143,8 @@ config PINCTRL_SINGLE | |||
| 143 | This selects the device tree based generic pinctrl driver. | 143 | This selects the device tree based generic pinctrl driver. |
| 144 | 144 | ||
| 145 | config PINCTRL_SIRF | 145 | config PINCTRL_SIRF |
| 146 | bool "CSR SiRFprimaII pin controller driver" | 146 | bool "CSR SiRFprimaII/SiRFmarco pin controller driver" |
| 147 | depends on ARCH_PRIMA2 | 147 | depends on ARCH_SIRF |
| 148 | select PINMUX | 148 | select PINMUX |
| 149 | 149 | ||
| 150 | config PINCTRL_TEGRA | 150 | config PINCTRL_TEGRA |
diff --git a/drivers/pinctrl/pinctrl-sirf.c b/drivers/pinctrl/pinctrl-sirf.c index 9ecacf3d0a75..16ec7d4d81ee 100644 --- a/drivers/pinctrl/pinctrl-sirf.c +++ b/drivers/pinctrl/pinctrl-sirf.c | |||
| @@ -32,10 +32,10 @@ | |||
| 32 | #define SIRFSOC_NUM_PADS 622 | 32 | #define SIRFSOC_NUM_PADS 622 |
| 33 | #define SIRFSOC_RSC_PIN_MUX 0x4 | 33 | #define SIRFSOC_RSC_PIN_MUX 0x4 |
| 34 | 34 | ||
| 35 | #define SIRFSOC_GPIO_PAD_EN(g) ((g)*0x100 + 0x84) | 35 | #define SIRFSOC_GPIO_PAD_EN(g) ((g)*0x100 + 0x84) |
| 36 | #define SIRFSOC_GPIO_PAD_EN_CLR(g) ((g)*0x100 + 0x90) | ||
| 36 | #define SIRFSOC_GPIO_CTRL(g, i) ((g)*0x100 + (i)*4) | 37 | #define SIRFSOC_GPIO_CTRL(g, i) ((g)*0x100 + (i)*4) |
| 37 | #define SIRFSOC_GPIO_DSP_EN0 (0x80) | 38 | #define SIRFSOC_GPIO_DSP_EN0 (0x80) |
| 38 | #define SIRFSOC_GPIO_PAD_EN(g) ((g)*0x100 + 0x84) | ||
| 39 | #define SIRFSOC_GPIO_INT_STATUS(g) ((g)*0x100 + 0x8C) | 39 | #define SIRFSOC_GPIO_INT_STATUS(g) ((g)*0x100 + 0x8C) |
| 40 | 40 | ||
| 41 | #define SIRFSOC_GPIO_CTL_INTR_LOW_MASK 0x1 | 41 | #define SIRFSOC_GPIO_CTL_INTR_LOW_MASK 0x1 |
| @@ -60,6 +60,7 @@ struct sirfsoc_gpio_bank { | |||
| 60 | int id; | 60 | int id; |
| 61 | int parent_irq; | 61 | int parent_irq; |
| 62 | spinlock_t lock; | 62 | spinlock_t lock; |
| 63 | bool is_marco; /* for marco, some registers are different with prima2 */ | ||
| 63 | }; | 64 | }; |
| 64 | 65 | ||
| 65 | static struct sirfsoc_gpio_bank sgpio_bank[SIRFSOC_GPIO_NO_OF_BANKS]; | 66 | static struct sirfsoc_gpio_bank sgpio_bank[SIRFSOC_GPIO_NO_OF_BANKS]; |
| @@ -191,6 +192,7 @@ struct sirfsoc_pmx { | |||
| 191 | struct pinctrl_dev *pmx; | 192 | struct pinctrl_dev *pmx; |
| 192 | void __iomem *gpio_virtbase; | 193 | void __iomem *gpio_virtbase; |
| 193 | void __iomem *rsc_virtbase; | 194 | void __iomem *rsc_virtbase; |
| 195 | bool is_marco; | ||
| 194 | }; | 196 | }; |
| 195 | 197 | ||
| 196 | /* SIRFSOC_GPIO_PAD_EN set */ | 198 | /* SIRFSOC_GPIO_PAD_EN set */ |
| @@ -1088,12 +1090,21 @@ static void sirfsoc_pinmux_endisable(struct sirfsoc_pmx *spmx, unsigned selector | |||
| 1088 | 1090 | ||
| 1089 | for (i = 0; i < mux->muxmask_counts; i++) { | 1091 | for (i = 0; i < mux->muxmask_counts; i++) { |
| 1090 | u32 muxval; | 1092 | u32 muxval; |
| 1091 | muxval = readl(spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(mask[i].group)); | 1093 | if (!spmx->is_marco) { |
| 1092 | if (enable) | 1094 | muxval = readl(spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(mask[i].group)); |
| 1093 | muxval = muxval & ~mask[i].mask; | 1095 | if (enable) |
| 1094 | else | 1096 | muxval = muxval & ~mask[i].mask; |
| 1095 | muxval = muxval | mask[i].mask; | 1097 | else |
| 1096 | writel(muxval, spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(mask[i].group)); | 1098 | muxval = muxval | mask[i].mask; |
| 1099 | writel(muxval, spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(mask[i].group)); | ||
| 1100 | } else { | ||
| 1101 | if (enable) | ||
| 1102 | writel(mask[i].mask, spmx->gpio_virtbase + | ||
| 1103 | SIRFSOC_GPIO_PAD_EN_CLR(mask[i].group)); | ||
| 1104 | else | ||
| 1105 | writel(mask[i].mask, spmx->gpio_virtbase + | ||
| 1106 | SIRFSOC_GPIO_PAD_EN(mask[i].group)); | ||
| 1107 | } | ||
| 1097 | } | 1108 | } |
| 1098 | 1109 | ||
| 1099 | if (mux->funcmask && enable) { | 1110 | if (mux->funcmask && enable) { |
| @@ -1158,9 +1169,14 @@ static int sirfsoc_pinmux_request_gpio(struct pinctrl_dev *pmxdev, | |||
| 1158 | 1169 | ||
| 1159 | spmx = pinctrl_dev_get_drvdata(pmxdev); | 1170 | spmx = pinctrl_dev_get_drvdata(pmxdev); |
| 1160 | 1171 | ||
| 1161 | muxval = readl(spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(group)); | 1172 | if (!spmx->is_marco) { |
| 1162 | muxval = muxval | (1 << (offset - range->pin_base)); | 1173 | muxval = readl(spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(group)); |
| 1163 | writel(muxval, spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(group)); | 1174 | muxval = muxval | (1 << (offset - range->pin_base)); |
| 1175 | writel(muxval, spmx->gpio_virtbase + SIRFSOC_GPIO_PAD_EN(group)); | ||
| 1176 | } else { | ||
| 1177 | writel(1 << (offset - range->pin_base), spmx->gpio_virtbase + | ||
| 1178 | SIRFSOC_GPIO_PAD_EN(group)); | ||
| 1179 | } | ||
| 1164 | 1180 | ||
| 1165 | return 0; | 1181 | return 0; |
| 1166 | } | 1182 | } |
| @@ -1218,6 +1234,7 @@ static void __iomem *sirfsoc_rsc_of_iomap(void) | |||
| 1218 | { | 1234 | { |
| 1219 | const struct of_device_id rsc_ids[] = { | 1235 | const struct of_device_id rsc_ids[] = { |
| 1220 | { .compatible = "sirf,prima2-rsc" }, | 1236 | { .compatible = "sirf,prima2-rsc" }, |
| 1237 | { .compatible = "sirf,marco-rsc" }, | ||
| 1221 | {} | 1238 | {} |
| 1222 | }; | 1239 | }; |
| 1223 | struct device_node *np; | 1240 | struct device_node *np; |
| @@ -1259,6 +1276,9 @@ static int __devinit sirfsoc_pinmux_probe(struct platform_device *pdev) | |||
| 1259 | goto out_no_rsc_remap; | 1276 | goto out_no_rsc_remap; |
| 1260 | } | 1277 | } |
| 1261 | 1278 | ||
| 1279 | if (of_device_is_compatible(np, "sirf,marco-pinctrl")) | ||
| 1280 | spmx->is_marco = 1; | ||
| 1281 | |||
| 1262 | /* Now register the pin controller and all pins it handles */ | 1282 | /* Now register the pin controller and all pins it handles */ |
| 1263 | spmx->pmx = pinctrl_register(&sirfsoc_pinmux_desc, &pdev->dev, spmx); | 1283 | spmx->pmx = pinctrl_register(&sirfsoc_pinmux_desc, &pdev->dev, spmx); |
| 1264 | if (!spmx->pmx) { | 1284 | if (!spmx->pmx) { |
| @@ -1287,6 +1307,7 @@ out_no_gpio_remap: | |||
| 1287 | 1307 | ||
| 1288 | static const struct of_device_id pinmux_ids[] __devinitconst = { | 1308 | static const struct of_device_id pinmux_ids[] __devinitconst = { |
| 1289 | { .compatible = "sirf,prima2-pinctrl" }, | 1309 | { .compatible = "sirf,prima2-pinctrl" }, |
| 1310 | { .compatible = "sirf,marco-pinctrl" }, | ||
| 1290 | {} | 1311 | {} |
| 1291 | }; | 1312 | }; |
| 1292 | 1313 | ||
| @@ -1648,6 +1669,7 @@ static int __devinit sirfsoc_gpio_probe(struct device_node *np) | |||
| 1648 | struct sirfsoc_gpio_bank *bank; | 1669 | struct sirfsoc_gpio_bank *bank; |
| 1649 | void *regs; | 1670 | void *regs; |
| 1650 | struct platform_device *pdev; | 1671 | struct platform_device *pdev; |
| 1672 | bool is_marco = false; | ||
| 1651 | 1673 | ||
| 1652 | pdev = of_find_device_by_node(np); | 1674 | pdev = of_find_device_by_node(np); |
| 1653 | if (!pdev) | 1675 | if (!pdev) |
| @@ -1657,6 +1679,9 @@ static int __devinit sirfsoc_gpio_probe(struct device_node *np) | |||
| 1657 | if (!regs) | 1679 | if (!regs) |
| 1658 | return -ENOMEM; | 1680 | return -ENOMEM; |
| 1659 | 1681 | ||
| 1682 | if (of_device_is_compatible(np, "sirf,marco-pinctrl")) | ||
| 1683 | is_marco = 1; | ||
| 1684 | |||
| 1660 | for (i = 0; i < SIRFSOC_GPIO_NO_OF_BANKS; i++) { | 1685 | for (i = 0; i < SIRFSOC_GPIO_NO_OF_BANKS; i++) { |
| 1661 | bank = &sgpio_bank[i]; | 1686 | bank = &sgpio_bank[i]; |
| 1662 | spin_lock_init(&bank->lock); | 1687 | spin_lock_init(&bank->lock); |
| @@ -1673,6 +1698,7 @@ static int __devinit sirfsoc_gpio_probe(struct device_node *np) | |||
| 1673 | bank->chip.gc.of_node = np; | 1698 | bank->chip.gc.of_node = np; |
| 1674 | bank->chip.regs = regs; | 1699 | bank->chip.regs = regs; |
| 1675 | bank->id = i; | 1700 | bank->id = i; |
| 1701 | bank->is_marco = is_marco; | ||
| 1676 | bank->parent_irq = platform_get_irq(pdev, i); | 1702 | bank->parent_irq = platform_get_irq(pdev, i); |
| 1677 | if (bank->parent_irq < 0) { | 1703 | if (bank->parent_irq < 0) { |
| 1678 | err = bank->parent_irq; | 1704 | err = bank->parent_irq; |
