diff options
author | Russell King <rmk@dyn-67.arm.linux.org.uk> | 2008-01-28 08:21:38 -0500 |
---|---|---|
committer | Russell King <rmk+kernel@arm.linux.org.uk> | 2008-01-28 08:21:38 -0500 |
commit | 0ff66f0c7a5f1f4f5a0d91341b6f71fd2a49f0fa (patch) | |
tree | 7c4d74a76bf4f49e87d769c236fdd2db77fb241d /drivers | |
parent | c00d4ffdbace1bdc9fdd888e4ba6d207ffa3b679 (diff) | |
parent | 4e4fc05a2b6e7bd2e0facd96e0c18dceb34d9349 (diff) |
Merge branch 'pxa-plat' into devel
* pxa-plat: (53 commits)
[ARM] 4762/1: Basic support for Toradex Colibri module
[ARM] pxa: fix mci_init functions returning -1
[ARM] 4737/1: Refactor corgi_lcd to improve readability + bugfix
[ARM] 4747/1: pcm027: support for pcm990 baseboard for phyCORE-PXA270
[ARM] 4746/1: pcm027: network support for phyCORE-PXA270
[ARM] 4745/1: pcm027: default configuration
[ARM] 4744/1: pcm027: add support for phyCORE-PXA270 CPU module
[NET] smc91x: Make smc91x use IRQ resource trigger flags
[ARM] pxa: add default config for littleton
[ARM] pxa: add basic support for Littleton (PXA3xx Form Factor Platform)
[ARM] 4664/1: Add basic support for HTC Magician PDA phones
[ARM] 4649/1: Base support for pxa-based Toshiba e-series PDAs.
[ARM] pxa: skip registers saving/restoring if entering standby mode
[ARM] pxa: fix PXA27x resume
[ARM] pxa: Avoid fiddling with CKEN register on suspend
[ARM] pxa: Add PXA3 standby code hooked into the IRQ wake scheme
[ARM] pxa: Add zylonite MFP wakeup configurations
[ARM] pxa: program MFPs for low power mode when suspending
[ARM] pxa: make MFP configuration processor independent
[ARM] pxa: remove un-used pxa3xx_mfp_set_xxx() functions
...
Conflicts:
arch/arm/mach-pxa/ssp.c
Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/input/touchscreen/corgi_ts.c | 8 | ||||
-rw-r--r-- | drivers/mmc/host/pxamci.c | 61 | ||||
-rw-r--r-- | drivers/mmc/host/pxamci.h | 2 | ||||
-rw-r--r-- | drivers/net/dm9000.c | 3 | ||||
-rw-r--r-- | drivers/net/smc91x.c | 19 | ||||
-rw-r--r-- | drivers/net/smc91x.h | 24 | ||||
-rw-r--r-- | drivers/pcmcia/pxa2xx_base.c | 1 | ||||
-rw-r--r-- | drivers/rtc/rtc-sa1100.c | 31 | ||||
-rw-r--r-- | drivers/spi/Kconfig | 1 | ||||
-rw-r--r-- | drivers/spi/pxa2xx_spi.c | 139 | ||||
-rw-r--r-- | drivers/usb/Kconfig | 1 | ||||
-rw-r--r-- | drivers/usb/host/ohci-hcd.c | 2 | ||||
-rw-r--r-- | drivers/usb/host/ohci-pxa27x.c | 13 |
13 files changed, 173 insertions, 132 deletions
diff --git a/drivers/input/touchscreen/corgi_ts.c b/drivers/input/touchscreen/corgi_ts.c index b1b2e07bf080..99d92f5c93d6 100644 --- a/drivers/input/touchscreen/corgi_ts.c +++ b/drivers/input/touchscreen/corgi_ts.c | |||
@@ -74,10 +74,10 @@ extern unsigned int get_clk_frequency_khz(int info); | |||
74 | 74 | ||
75 | static unsigned long calc_waittime(struct corgi_ts *corgi_ts) | 75 | static unsigned long calc_waittime(struct corgi_ts *corgi_ts) |
76 | { | 76 | { |
77 | unsigned long hsync_len = corgi_ts->machinfo->get_hsync_len(); | 77 | unsigned long hsync_invperiod = corgi_ts->machinfo->get_hsync_invperiod(); |
78 | 78 | ||
79 | if (hsync_len) | 79 | if (hsync_invperiod) |
80 | return get_clk_frequency_khz(0)*1000/hsync_len; | 80 | return get_clk_frequency_khz(0)*1000/hsync_invperiod; |
81 | else | 81 | else |
82 | return 0; | 82 | return 0; |
83 | } | 83 | } |
@@ -114,7 +114,7 @@ static int sync_receive_data_send_cmd(struct corgi_ts *corgi_ts, int doRecive, i | |||
114 | if (timer2-timer1 > wait_time) { | 114 | if (timer2-timer1 > wait_time) { |
115 | /* too slow - timeout, try again */ | 115 | /* too slow - timeout, try again */ |
116 | corgi_ts->machinfo->wait_hsync(); | 116 | corgi_ts->machinfo->wait_hsync(); |
117 | /* get OSCR */ | 117 | /* get CCNT */ |
118 | CCNT(timer1); | 118 | CCNT(timer1); |
119 | /* Wait after HSync */ | 119 | /* Wait after HSync */ |
120 | CCNT(timer2); | 120 | CCNT(timer2); |
diff --git a/drivers/mmc/host/pxamci.c b/drivers/mmc/host/pxamci.c index 1654a3330340..1ea8482037bb 100644 --- a/drivers/mmc/host/pxamci.c +++ b/drivers/mmc/host/pxamci.c | |||
@@ -65,6 +65,8 @@ struct pxamci_host { | |||
65 | unsigned int dma_len; | 65 | unsigned int dma_len; |
66 | 66 | ||
67 | unsigned int dma_dir; | 67 | unsigned int dma_dir; |
68 | unsigned int dma_drcmrrx; | ||
69 | unsigned int dma_drcmrtx; | ||
68 | }; | 70 | }; |
69 | 71 | ||
70 | static void pxamci_stop_clock(struct pxamci_host *host) | 72 | static void pxamci_stop_clock(struct pxamci_host *host) |
@@ -131,13 +133,13 @@ static void pxamci_setup_data(struct pxamci_host *host, struct mmc_data *data) | |||
131 | if (data->flags & MMC_DATA_READ) { | 133 | if (data->flags & MMC_DATA_READ) { |
132 | host->dma_dir = DMA_FROM_DEVICE; | 134 | host->dma_dir = DMA_FROM_DEVICE; |
133 | dcmd = DCMD_INCTRGADDR | DCMD_FLOWTRG; | 135 | dcmd = DCMD_INCTRGADDR | DCMD_FLOWTRG; |
134 | DRCMRTXMMC = 0; | 136 | DRCMR(host->dma_drcmrtx) = 0; |
135 | DRCMRRXMMC = host->dma | DRCMR_MAPVLD; | 137 | DRCMR(host->dma_drcmrrx) = host->dma | DRCMR_MAPVLD; |
136 | } else { | 138 | } else { |
137 | host->dma_dir = DMA_TO_DEVICE; | 139 | host->dma_dir = DMA_TO_DEVICE; |
138 | dcmd = DCMD_INCSRCADDR | DCMD_FLOWSRC; | 140 | dcmd = DCMD_INCSRCADDR | DCMD_FLOWSRC; |
139 | DRCMRRXMMC = 0; | 141 | DRCMR(host->dma_drcmrrx) = 0; |
140 | DRCMRTXMMC = host->dma | DRCMR_MAPVLD; | 142 | DRCMR(host->dma_drcmrtx) = host->dma | DRCMR_MAPVLD; |
141 | } | 143 | } |
142 | 144 | ||
143 | dcmd |= DCMD_BURST32 | DCMD_WIDTH1; | 145 | dcmd |= DCMD_BURST32 | DCMD_WIDTH1; |
@@ -375,14 +377,23 @@ static void pxamci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
375 | if (host->clkrt == CLKRT_OFF) | 377 | if (host->clkrt == CLKRT_OFF) |
376 | clk_enable(host->clk); | 378 | clk_enable(host->clk); |
377 | 379 | ||
378 | /* | 380 | if (ios->clock == 26000000) { |
379 | * clk might result in a lower divisor than we | 381 | /* to support 26MHz on pxa300/pxa310 */ |
380 | * desire. check for that condition and adjust | 382 | host->clkrt = 7; |
381 | * as appropriate. | 383 | } else { |
382 | */ | 384 | /* to handle (19.5MHz, 26MHz) */ |
383 | if (rate / clk > ios->clock) | 385 | if (!clk) |
384 | clk <<= 1; | 386 | clk = 1; |
385 | host->clkrt = fls(clk) - 1; | 387 | |
388 | /* | ||
389 | * clk might result in a lower divisor than we | ||
390 | * desire. check for that condition and adjust | ||
391 | * as appropriate. | ||
392 | */ | ||
393 | if (rate / clk > ios->clock) | ||
394 | clk <<= 1; | ||
395 | host->clkrt = fls(clk) - 1; | ||
396 | } | ||
386 | 397 | ||
387 | /* | 398 | /* |
388 | * we write clkrt on the next command | 399 | * we write clkrt on the next command |
@@ -459,7 +470,7 @@ static int pxamci_probe(struct platform_device *pdev) | |||
459 | { | 470 | { |
460 | struct mmc_host *mmc; | 471 | struct mmc_host *mmc; |
461 | struct pxamci_host *host = NULL; | 472 | struct pxamci_host *host = NULL; |
462 | struct resource *r; | 473 | struct resource *r, *dmarx, *dmatx; |
463 | int ret, irq; | 474 | int ret, irq; |
464 | 475 | ||
465 | r = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 476 | r = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
@@ -519,7 +530,8 @@ static int pxamci_probe(struct platform_device *pdev) | |||
519 | * Calculate minimum clock rate, rounding up. | 530 | * Calculate minimum clock rate, rounding up. |
520 | */ | 531 | */ |
521 | mmc->f_min = (host->clkrate + 63) / 64; | 532 | mmc->f_min = (host->clkrate + 63) / 64; |
522 | mmc->f_max = host->clkrate; | 533 | mmc->f_max = (cpu_is_pxa300() || cpu_is_pxa310()) ? 26000000 |
534 | : host->clkrate; | ||
523 | 535 | ||
524 | mmc->ocr_avail = host->pdata ? | 536 | mmc->ocr_avail = host->pdata ? |
525 | host->pdata->ocr_mask : | 537 | host->pdata->ocr_mask : |
@@ -529,6 +541,9 @@ static int pxamci_probe(struct platform_device *pdev) | |||
529 | if (!cpu_is_pxa21x() && !cpu_is_pxa25x()) { | 541 | if (!cpu_is_pxa21x() && !cpu_is_pxa25x()) { |
530 | mmc->caps |= MMC_CAP_4_BIT_DATA | MMC_CAP_SDIO_IRQ; | 542 | mmc->caps |= MMC_CAP_4_BIT_DATA | MMC_CAP_SDIO_IRQ; |
531 | host->cmdat |= CMDAT_SDIO_INT_EN; | 543 | host->cmdat |= CMDAT_SDIO_INT_EN; |
544 | if (cpu_is_pxa300() || cpu_is_pxa310()) | ||
545 | mmc->caps |= MMC_CAP_MMC_HIGHSPEED | | ||
546 | MMC_CAP_SD_HIGHSPEED; | ||
532 | } | 547 | } |
533 | 548 | ||
534 | host->sg_cpu = dma_alloc_coherent(&pdev->dev, PAGE_SIZE, &host->sg_dma, GFP_KERNEL); | 549 | host->sg_cpu = dma_alloc_coherent(&pdev->dev, PAGE_SIZE, &host->sg_dma, GFP_KERNEL); |
@@ -570,6 +585,20 @@ static int pxamci_probe(struct platform_device *pdev) | |||
570 | 585 | ||
571 | platform_set_drvdata(pdev, mmc); | 586 | platform_set_drvdata(pdev, mmc); |
572 | 587 | ||
588 | dmarx = platform_get_resource(pdev, IORESOURCE_DMA, 0); | ||
589 | if (!dmarx) { | ||
590 | ret = -ENXIO; | ||
591 | goto out; | ||
592 | } | ||
593 | host->dma_drcmrrx = dmarx->start; | ||
594 | |||
595 | dmatx = platform_get_resource(pdev, IORESOURCE_DMA, 1); | ||
596 | if (!dmatx) { | ||
597 | ret = -ENXIO; | ||
598 | goto out; | ||
599 | } | ||
600 | host->dma_drcmrtx = dmatx->start; | ||
601 | |||
573 | if (host->pdata && host->pdata->init) | 602 | if (host->pdata && host->pdata->init) |
574 | host->pdata->init(&pdev->dev, pxamci_detect_irq, mmc); | 603 | host->pdata->init(&pdev->dev, pxamci_detect_irq, mmc); |
575 | 604 | ||
@@ -613,8 +642,8 @@ static int pxamci_remove(struct platform_device *pdev) | |||
613 | END_CMD_RES|PRG_DONE|DATA_TRAN_DONE, | 642 | END_CMD_RES|PRG_DONE|DATA_TRAN_DONE, |
614 | host->base + MMC_I_MASK); | 643 | host->base + MMC_I_MASK); |
615 | 644 | ||
616 | DRCMRRXMMC = 0; | 645 | DRCMR(host->dma_drcmrrx) = 0; |
617 | DRCMRTXMMC = 0; | 646 | DRCMR(host->dma_drcmrtx) = 0; |
618 | 647 | ||
619 | free_irq(host->irq, host); | 648 | free_irq(host->irq, host); |
620 | pxa_free_dma(host->dma); | 649 | pxa_free_dma(host->dma); |
diff --git a/drivers/mmc/host/pxamci.h b/drivers/mmc/host/pxamci.h index 748c7706f237..f6c2e2fcce37 100644 --- a/drivers/mmc/host/pxamci.h +++ b/drivers/mmc/host/pxamci.h | |||
@@ -68,7 +68,7 @@ | |||
68 | #define PRG_DONE (1 << 1) | 68 | #define PRG_DONE (1 << 1) |
69 | #define DATA_TRAN_DONE (1 << 0) | 69 | #define DATA_TRAN_DONE (1 << 0) |
70 | 70 | ||
71 | #ifdef CONFIG_PXA27x | 71 | #if defined(CONFIG_PXA27x) || defined(CONFIG_PXA3xx) |
72 | #define MMC_I_MASK_ALL 0x00001fff | 72 | #define MMC_I_MASK_ALL 0x00001fff |
73 | #else | 73 | #else |
74 | #define MMC_I_MASK_ALL 0x0000007f | 74 | #define MMC_I_MASK_ALL 0x0000007f |
diff --git a/drivers/net/dm9000.c b/drivers/net/dm9000.c index 3286d2a0a870..6a20a5491a96 100644 --- a/drivers/net/dm9000.c +++ b/drivers/net/dm9000.c | |||
@@ -66,6 +66,7 @@ | |||
66 | #include <linux/dm9000.h> | 66 | #include <linux/dm9000.h> |
67 | #include <linux/delay.h> | 67 | #include <linux/delay.h> |
68 | #include <linux/platform_device.h> | 68 | #include <linux/platform_device.h> |
69 | #include <linux/irq.h> | ||
69 | 70 | ||
70 | #include <asm/delay.h> | 71 | #include <asm/delay.h> |
71 | #include <asm/irq.h> | 72 | #include <asm/irq.h> |
@@ -113,7 +114,7 @@ | |||
113 | #define writesl outsl | 114 | #define writesl outsl |
114 | #define DM9000_IRQ_FLAGS (IRQF_SHARED | IRQF_TRIGGER_HIGH) | 115 | #define DM9000_IRQ_FLAGS (IRQF_SHARED | IRQF_TRIGGER_HIGH) |
115 | #else | 116 | #else |
116 | #define DM9000_IRQ_FLAGS IRQF_SHARED | 117 | #define DM9000_IRQ_FLAGS (IRQF_SHARED | IRQT_RISING) |
117 | #endif | 118 | #endif |
118 | 119 | ||
119 | /* | 120 | /* |
diff --git a/drivers/net/smc91x.c b/drivers/net/smc91x.c index 7da7589d45dd..4020e9e955b3 100644 --- a/drivers/net/smc91x.c +++ b/drivers/net/smc91x.c | |||
@@ -1775,7 +1775,8 @@ static int __init smc_findirq(void __iomem *ioaddr) | |||
1775 | * o actually GRAB the irq. | 1775 | * o actually GRAB the irq. |
1776 | * o GRAB the region | 1776 | * o GRAB the region |
1777 | */ | 1777 | */ |
1778 | static int __init smc_probe(struct net_device *dev, void __iomem *ioaddr) | 1778 | static int __init smc_probe(struct net_device *dev, void __iomem *ioaddr, |
1779 | unsigned long irq_flags) | ||
1779 | { | 1780 | { |
1780 | struct smc_local *lp = netdev_priv(dev); | 1781 | struct smc_local *lp = netdev_priv(dev); |
1781 | static int version_printed = 0; | 1782 | static int version_printed = 0; |
@@ -1941,7 +1942,7 @@ static int __init smc_probe(struct net_device *dev, void __iomem *ioaddr) | |||
1941 | } | 1942 | } |
1942 | 1943 | ||
1943 | /* Grab the IRQ */ | 1944 | /* Grab the IRQ */ |
1944 | retval = request_irq(dev->irq, &smc_interrupt, SMC_IRQ_FLAGS, dev->name, dev); | 1945 | retval = request_irq(dev->irq, &smc_interrupt, irq_flags, dev->name, dev); |
1945 | if (retval) | 1946 | if (retval) |
1946 | goto err_out; | 1947 | goto err_out; |
1947 | 1948 | ||
@@ -2123,8 +2124,9 @@ static void smc_release_datacs(struct platform_device *pdev, struct net_device * | |||
2123 | static int smc_drv_probe(struct platform_device *pdev) | 2124 | static int smc_drv_probe(struct platform_device *pdev) |
2124 | { | 2125 | { |
2125 | struct net_device *ndev; | 2126 | struct net_device *ndev; |
2126 | struct resource *res; | 2127 | struct resource *res, *ires; |
2127 | unsigned int __iomem *addr; | 2128 | unsigned int __iomem *addr; |
2129 | unsigned long irq_flags = SMC_IRQ_FLAGS; | ||
2128 | int ret; | 2130 | int ret; |
2129 | 2131 | ||
2130 | res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "smc91x-regs"); | 2132 | res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "smc91x-regs"); |
@@ -2150,12 +2152,17 @@ static int smc_drv_probe(struct platform_device *pdev) | |||
2150 | SET_NETDEV_DEV(ndev, &pdev->dev); | 2152 | SET_NETDEV_DEV(ndev, &pdev->dev); |
2151 | 2153 | ||
2152 | ndev->dma = (unsigned char)-1; | 2154 | ndev->dma = (unsigned char)-1; |
2153 | ndev->irq = platform_get_irq(pdev, 0); | 2155 | |
2154 | if (ndev->irq < 0) { | 2156 | ires = platform_get_resource(pdev, IORESOURCE_IRQ, 0); |
2157 | if (!ires) { | ||
2155 | ret = -ENODEV; | 2158 | ret = -ENODEV; |
2156 | goto out_free_netdev; | 2159 | goto out_free_netdev; |
2157 | } | 2160 | } |
2158 | 2161 | ||
2162 | ndev->irq = ires->start; | ||
2163 | if (SMC_IRQ_FLAGS == -1) | ||
2164 | irq_flags = ires->flags & IRQF_TRIGGER_MASK; | ||
2165 | |||
2159 | ret = smc_request_attrib(pdev); | 2166 | ret = smc_request_attrib(pdev); |
2160 | if (ret) | 2167 | if (ret) |
2161 | goto out_free_netdev; | 2168 | goto out_free_netdev; |
@@ -2181,7 +2188,7 @@ static int smc_drv_probe(struct platform_device *pdev) | |||
2181 | #endif | 2188 | #endif |
2182 | 2189 | ||
2183 | platform_set_drvdata(pdev, ndev); | 2190 | platform_set_drvdata(pdev, ndev); |
2184 | ret = smc_probe(ndev, addr); | 2191 | ret = smc_probe(ndev, addr, irq_flags); |
2185 | if (ret != 0) | 2192 | if (ret != 0) |
2186 | goto out_iounmap; | 2193 | goto out_iounmap; |
2187 | 2194 | ||
diff --git a/drivers/net/smc91x.h b/drivers/net/smc91x.h index 07b7f7120e37..271c28dc9baa 100644 --- a/drivers/net/smc91x.h +++ b/drivers/net/smc91x.h | |||
@@ -54,6 +54,7 @@ | |||
54 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) | 54 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) |
55 | #define SMC_insw(a, r, p, l) readsw((a) + (r), p, l) | 55 | #define SMC_insw(a, r, p, l) readsw((a) + (r), p, l) |
56 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) | 56 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) |
57 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | ||
57 | 58 | ||
58 | #elif defined(CONFIG_BLACKFIN) | 59 | #elif defined(CONFIG_BLACKFIN) |
59 | 60 | ||
@@ -158,7 +159,7 @@ | |||
158 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) | 159 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) |
159 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) | 160 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) |
160 | 161 | ||
161 | #define SMC_IRQ_FLAGS (0) | 162 | #define SMC_IRQ_FLAGS (-1) |
162 | 163 | ||
163 | #elif defined(CONFIG_SA1100_ASSABET) | 164 | #elif defined(CONFIG_SA1100_ASSABET) |
164 | 165 | ||
@@ -177,6 +178,7 @@ | |||
177 | #define SMC_outb(v, a, r) writeb(v, (a) + (r)) | 178 | #define SMC_outb(v, a, r) writeb(v, (a) + (r)) |
178 | #define SMC_insb(a, r, p, l) readsb((a) + (r), p, (l)) | 179 | #define SMC_insb(a, r, p, l) readsb((a) + (r), p, (l)) |
179 | #define SMC_outsb(a, r, p, l) writesb((a) + (r), p, (l)) | 180 | #define SMC_outsb(a, r, p, l) writesb((a) + (r), p, (l)) |
181 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | ||
180 | 182 | ||
181 | #elif defined(CONFIG_MACH_LOGICPD_PXA270) | 183 | #elif defined(CONFIG_MACH_LOGICPD_PXA270) |
182 | 184 | ||
@@ -194,7 +196,8 @@ | |||
194 | #elif defined(CONFIG_ARCH_INNOKOM) || \ | 196 | #elif defined(CONFIG_ARCH_INNOKOM) || \ |
195 | defined(CONFIG_MACH_MAINSTONE) || \ | 197 | defined(CONFIG_MACH_MAINSTONE) || \ |
196 | defined(CONFIG_ARCH_PXA_IDP) || \ | 198 | defined(CONFIG_ARCH_PXA_IDP) || \ |
197 | defined(CONFIG_ARCH_RAMSES) | 199 | defined(CONFIG_ARCH_RAMSES) || \ |
200 | defined(CONFIG_ARCH_PCM027) | ||
198 | 201 | ||
199 | #define SMC_CAN_USE_8BIT 1 | 202 | #define SMC_CAN_USE_8BIT 1 |
200 | #define SMC_CAN_USE_16BIT 1 | 203 | #define SMC_CAN_USE_16BIT 1 |
@@ -210,6 +213,7 @@ | |||
210 | #define SMC_outl(v, a, r) writel(v, (a) + (r)) | 213 | #define SMC_outl(v, a, r) writel(v, (a) + (r)) |
211 | #define SMC_insl(a, r, p, l) readsl((a) + (r), p, l) | 214 | #define SMC_insl(a, r, p, l) readsl((a) + (r), p, l) |
212 | #define SMC_outsl(a, r, p, l) writesl((a) + (r), p, l) | 215 | #define SMC_outsl(a, r, p, l) writesl((a) + (r), p, l) |
216 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | ||
213 | 217 | ||
214 | /* We actually can't write halfwords properly if not word aligned */ | 218 | /* We actually can't write halfwords properly if not word aligned */ |
215 | static inline void | 219 | static inline void |
@@ -238,6 +242,7 @@ SMC_outw(u16 val, void __iomem *ioaddr, int reg) | |||
238 | #define SMC_outsw(a, r, p, l) outsw((a) + (r), p, l) | 242 | #define SMC_outsw(a, r, p, l) outsw((a) + (r), p, l) |
239 | #define SMC_outb(v, a, r) writeb(v, (a) + (r)) | 243 | #define SMC_outb(v, a, r) writeb(v, (a) + (r)) |
240 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) | 244 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) |
245 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | ||
241 | 246 | ||
242 | #elif defined(CONFIG_ARCH_OMAP) | 247 | #elif defined(CONFIG_ARCH_OMAP) |
243 | 248 | ||
@@ -252,17 +257,7 @@ SMC_outw(u16 val, void __iomem *ioaddr, int reg) | |||
252 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) | 257 | #define SMC_outw(v, a, r) writew(v, (a) + (r)) |
253 | #define SMC_insw(a, r, p, l) readsw((a) + (r), p, l) | 258 | #define SMC_insw(a, r, p, l) readsw((a) + (r), p, l) |
254 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) | 259 | #define SMC_outsw(a, r, p, l) writesw((a) + (r), p, l) |
255 | 260 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | |
256 | #include <asm/mach-types.h> | ||
257 | #include <asm/arch/cpu.h> | ||
258 | |||
259 | #define SMC_IRQ_FLAGS (( \ | ||
260 | machine_is_omap_h2() \ | ||
261 | || machine_is_omap_h3() \ | ||
262 | || machine_is_omap_h4() \ | ||
263 | || (machine_is_omap_innovator() && !cpu_is_omap1510()) \ | ||
264 | ) ? IRQF_TRIGGER_FALLING : IRQF_TRIGGER_RISING) | ||
265 | |||
266 | 261 | ||
267 | #elif defined(CONFIG_SH_SH4202_MICRODEV) | 262 | #elif defined(CONFIG_SH_SH4202_MICRODEV) |
268 | 263 | ||
@@ -453,8 +448,7 @@ static inline void LPD7_SMC_outsw (unsigned char* a, int r, | |||
453 | #define SMC_outl(v, a, r) writel(v, (a) + (r)) | 448 | #define SMC_outl(v, a, r) writel(v, (a) + (r)) |
454 | #define SMC_insl(a, r, p, l) readsl((a) + (r), p, l) | 449 | #define SMC_insl(a, r, p, l) readsl((a) + (r), p, l) |
455 | #define SMC_outsl(a, r, p, l) writesl((a) + (r), p, l) | 450 | #define SMC_outsl(a, r, p, l) writesl((a) + (r), p, l) |
456 | 451 | #define SMC_IRQ_FLAGS (-1) /* from resource */ | |
457 | #define SMC_IRQ_FLAGS (0) | ||
458 | 452 | ||
459 | #else | 453 | #else |
460 | 454 | ||
diff --git a/drivers/pcmcia/pxa2xx_base.c b/drivers/pcmcia/pxa2xx_base.c index 874923fcb2f9..e439044d88f2 100644 --- a/drivers/pcmcia/pxa2xx_base.c +++ b/drivers/pcmcia/pxa2xx_base.c | |||
@@ -29,6 +29,7 @@ | |||
29 | #include <asm/irq.h> | 29 | #include <asm/irq.h> |
30 | #include <asm/system.h> | 30 | #include <asm/system.h> |
31 | #include <asm/arch/pxa-regs.h> | 31 | #include <asm/arch/pxa-regs.h> |
32 | #include <asm/arch/pxa2xx-regs.h> | ||
32 | 33 | ||
33 | #include <pcmcia/cs_types.h> | 34 | #include <pcmcia/cs_types.h> |
34 | #include <pcmcia/ss.h> | 35 | #include <pcmcia/ss.h> |
diff --git a/drivers/rtc/rtc-sa1100.c b/drivers/rtc/rtc-sa1100.c index 6f1e9a9804bc..2eb38520f0c8 100644 --- a/drivers/rtc/rtc-sa1100.c +++ b/drivers/rtc/rtc-sa1100.c | |||
@@ -337,6 +337,8 @@ static int sa1100_rtc_probe(struct platform_device *pdev) | |||
337 | if (IS_ERR(rtc)) | 337 | if (IS_ERR(rtc)) |
338 | return PTR_ERR(rtc); | 338 | return PTR_ERR(rtc); |
339 | 339 | ||
340 | device_init_wakeup(&pdev->dev, 1); | ||
341 | |||
340 | platform_set_drvdata(pdev, rtc); | 342 | platform_set_drvdata(pdev, rtc); |
341 | 343 | ||
342 | return 0; | 344 | return 0; |
@@ -352,9 +354,38 @@ static int sa1100_rtc_remove(struct platform_device *pdev) | |||
352 | return 0; | 354 | return 0; |
353 | } | 355 | } |
354 | 356 | ||
357 | #ifdef CONFIG_PM | ||
358 | static int sa1100_rtc_suspend(struct platform_device *pdev, pm_message_t state) | ||
359 | { | ||
360 | if (pdev->dev.power.power_state.event != state.event) { | ||
361 | if (state.event == PM_EVENT_SUSPEND && | ||
362 | device_may_wakeup(&pdev->dev)) | ||
363 | enable_irq_wake(IRQ_RTCAlrm); | ||
364 | |||
365 | pdev->dev.power.power_state = state; | ||
366 | } | ||
367 | return 0; | ||
368 | } | ||
369 | |||
370 | static int sa1100_rtc_resume(struct platform_device *pdev) | ||
371 | { | ||
372 | if (pdev->dev.power.power_state.event != PM_EVENT_ON) { | ||
373 | if (device_may_wakeup(&pdev->dev)) | ||
374 | disable_irq_wake(IRQ_RTCAlrm); | ||
375 | pdev->dev.power.power_state = PMSG_ON; | ||
376 | } | ||
377 | return 0; | ||
378 | } | ||
379 | #else | ||
380 | #define sa1100_rtc_suspend NULL | ||
381 | #define sa1100_rtc_resume NULL | ||
382 | #endif | ||
383 | |||
355 | static struct platform_driver sa1100_rtc_driver = { | 384 | static struct platform_driver sa1100_rtc_driver = { |
356 | .probe = sa1100_rtc_probe, | 385 | .probe = sa1100_rtc_probe, |
357 | .remove = sa1100_rtc_remove, | 386 | .remove = sa1100_rtc_remove, |
387 | .suspend = sa1100_rtc_suspend, | ||
388 | .resume = sa1100_rtc_resume, | ||
358 | .driver = { | 389 | .driver = { |
359 | .name = "sa1100-rtc", | 390 | .name = "sa1100-rtc", |
360 | }, | 391 | }, |
diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig index abf05048c638..aaaea81e412a 100644 --- a/drivers/spi/Kconfig +++ b/drivers/spi/Kconfig | |||
@@ -153,6 +153,7 @@ config SPI_OMAP24XX | |||
153 | config SPI_PXA2XX | 153 | config SPI_PXA2XX |
154 | tristate "PXA2xx SSP SPI master" | 154 | tristate "PXA2xx SSP SPI master" |
155 | depends on SPI_MASTER && ARCH_PXA && EXPERIMENTAL | 155 | depends on SPI_MASTER && ARCH_PXA && EXPERIMENTAL |
156 | select PXA_SSP | ||
156 | help | 157 | help |
157 | This enables using a PXA2xx SSP port as a SPI master controller. | 158 | This enables using a PXA2xx SSP port as a SPI master controller. |
158 | The driver can be configured to use any SSP port and additional | 159 | The driver can be configured to use any SSP port and additional |
diff --git a/drivers/spi/pxa2xx_spi.c b/drivers/spi/pxa2xx_spi.c index 1c2ab541d37d..eb817b8eb024 100644 --- a/drivers/spi/pxa2xx_spi.c +++ b/drivers/spi/pxa2xx_spi.c | |||
@@ -27,6 +27,7 @@ | |||
27 | #include <linux/spi/spi.h> | 27 | #include <linux/spi/spi.h> |
28 | #include <linux/workqueue.h> | 28 | #include <linux/workqueue.h> |
29 | #include <linux/delay.h> | 29 | #include <linux/delay.h> |
30 | #include <linux/clk.h> | ||
30 | 31 | ||
31 | #include <asm/io.h> | 32 | #include <asm/io.h> |
32 | #include <asm/irq.h> | 33 | #include <asm/irq.h> |
@@ -36,6 +37,8 @@ | |||
36 | 37 | ||
37 | #include <asm/arch/hardware.h> | 38 | #include <asm/arch/hardware.h> |
38 | #include <asm/arch/pxa-regs.h> | 39 | #include <asm/arch/pxa-regs.h> |
40 | #include <asm/arch/regs-ssp.h> | ||
41 | #include <asm/arch/ssp.h> | ||
39 | #include <asm/arch/pxa2xx_spi.h> | 42 | #include <asm/arch/pxa2xx_spi.h> |
40 | 43 | ||
41 | MODULE_AUTHOR("Stephen Street"); | 44 | MODULE_AUTHOR("Stephen Street"); |
@@ -80,6 +83,9 @@ struct driver_data { | |||
80 | /* Driver model hookup */ | 83 | /* Driver model hookup */ |
81 | struct platform_device *pdev; | 84 | struct platform_device *pdev; |
82 | 85 | ||
86 | /* SSP Info */ | ||
87 | struct ssp_device *ssp; | ||
88 | |||
83 | /* SPI framework hookup */ | 89 | /* SPI framework hookup */ |
84 | enum pxa_ssp_type ssp_type; | 90 | enum pxa_ssp_type ssp_type; |
85 | struct spi_master *master; | 91 | struct spi_master *master; |
@@ -778,6 +784,16 @@ int set_dma_burst_and_threshold(struct chip_data *chip, struct spi_device *spi, | |||
778 | return retval; | 784 | return retval; |
779 | } | 785 | } |
780 | 786 | ||
787 | static unsigned int ssp_get_clk_div(struct ssp_device *ssp, int rate) | ||
788 | { | ||
789 | unsigned long ssp_clk = clk_get_rate(ssp->clk); | ||
790 | |||
791 | if (ssp->type == PXA25x_SSP) | ||
792 | return ((ssp_clk / (2 * rate) - 1) & 0xff) << 8; | ||
793 | else | ||
794 | return ((ssp_clk / rate - 1) & 0xfff) << 8; | ||
795 | } | ||
796 | |||
781 | static void pump_transfers(unsigned long data) | 797 | static void pump_transfers(unsigned long data) |
782 | { | 798 | { |
783 | struct driver_data *drv_data = (struct driver_data *)data; | 799 | struct driver_data *drv_data = (struct driver_data *)data; |
@@ -785,6 +801,7 @@ static void pump_transfers(unsigned long data) | |||
785 | struct spi_transfer *transfer = NULL; | 801 | struct spi_transfer *transfer = NULL; |
786 | struct spi_transfer *previous = NULL; | 802 | struct spi_transfer *previous = NULL; |
787 | struct chip_data *chip = NULL; | 803 | struct chip_data *chip = NULL; |
804 | struct ssp_device *ssp = drv_data->ssp; | ||
788 | void *reg = drv_data->ioaddr; | 805 | void *reg = drv_data->ioaddr; |
789 | u32 clk_div = 0; | 806 | u32 clk_div = 0; |
790 | u8 bits = 0; | 807 | u8 bits = 0; |
@@ -866,12 +883,7 @@ static void pump_transfers(unsigned long data) | |||
866 | if (transfer->bits_per_word) | 883 | if (transfer->bits_per_word) |
867 | bits = transfer->bits_per_word; | 884 | bits = transfer->bits_per_word; |
868 | 885 | ||
869 | if (reg == SSP1_VIRT) | 886 | clk_div = ssp_get_clk_div(ssp, speed); |
870 | clk_div = SSP1_SerClkDiv(speed); | ||
871 | else if (reg == SSP2_VIRT) | ||
872 | clk_div = SSP2_SerClkDiv(speed); | ||
873 | else if (reg == SSP3_VIRT) | ||
874 | clk_div = SSP3_SerClkDiv(speed); | ||
875 | 887 | ||
876 | if (bits <= 8) { | 888 | if (bits <= 8) { |
877 | drv_data->n_bytes = 1; | 889 | drv_data->n_bytes = 1; |
@@ -1074,6 +1086,7 @@ static int setup(struct spi_device *spi) | |||
1074 | struct pxa2xx_spi_chip *chip_info = NULL; | 1086 | struct pxa2xx_spi_chip *chip_info = NULL; |
1075 | struct chip_data *chip; | 1087 | struct chip_data *chip; |
1076 | struct driver_data *drv_data = spi_master_get_devdata(spi->master); | 1088 | struct driver_data *drv_data = spi_master_get_devdata(spi->master); |
1089 | struct ssp_device *ssp = drv_data->ssp; | ||
1077 | unsigned int clk_div; | 1090 | unsigned int clk_div; |
1078 | 1091 | ||
1079 | if (!spi->bits_per_word) | 1092 | if (!spi->bits_per_word) |
@@ -1157,18 +1170,7 @@ static int setup(struct spi_device *spi) | |||
1157 | } | 1170 | } |
1158 | } | 1171 | } |
1159 | 1172 | ||
1160 | if (drv_data->ioaddr == SSP1_VIRT) | 1173 | clk_div = ssp_get_clk_div(ssp, spi->max_speed_hz); |
1161 | clk_div = SSP1_SerClkDiv(spi->max_speed_hz); | ||
1162 | else if (drv_data->ioaddr == SSP2_VIRT) | ||
1163 | clk_div = SSP2_SerClkDiv(spi->max_speed_hz); | ||
1164 | else if (drv_data->ioaddr == SSP3_VIRT) | ||
1165 | clk_div = SSP3_SerClkDiv(spi->max_speed_hz); | ||
1166 | else | ||
1167 | { | ||
1168 | dev_err(&spi->dev, "failed setup: unknown IO address=0x%p\n", | ||
1169 | drv_data->ioaddr); | ||
1170 | return -ENODEV; | ||
1171 | } | ||
1172 | chip->speed_hz = spi->max_speed_hz; | 1174 | chip->speed_hz = spi->max_speed_hz; |
1173 | 1175 | ||
1174 | chip->cr0 = clk_div | 1176 | chip->cr0 = clk_div |
@@ -1183,15 +1185,15 @@ static int setup(struct spi_device *spi) | |||
1183 | 1185 | ||
1184 | /* NOTE: PXA25x_SSP _could_ use external clocking ... */ | 1186 | /* NOTE: PXA25x_SSP _could_ use external clocking ... */ |
1185 | if (drv_data->ssp_type != PXA25x_SSP) | 1187 | if (drv_data->ssp_type != PXA25x_SSP) |
1186 | dev_dbg(&spi->dev, "%d bits/word, %d Hz, mode %d\n", | 1188 | dev_dbg(&spi->dev, "%d bits/word, %ld Hz, mode %d\n", |
1187 | spi->bits_per_word, | 1189 | spi->bits_per_word, |
1188 | (CLOCK_SPEED_HZ) | 1190 | clk_get_rate(ssp->clk) |
1189 | / (1 + ((chip->cr0 & SSCR0_SCR) >> 8)), | 1191 | / (1 + ((chip->cr0 & SSCR0_SCR) >> 8)), |
1190 | spi->mode & 0x3); | 1192 | spi->mode & 0x3); |
1191 | else | 1193 | else |
1192 | dev_dbg(&spi->dev, "%d bits/word, %d Hz, mode %d\n", | 1194 | dev_dbg(&spi->dev, "%d bits/word, %ld Hz, mode %d\n", |
1193 | spi->bits_per_word, | 1195 | spi->bits_per_word, |
1194 | (CLOCK_SPEED_HZ/2) | 1196 | clk_get_rate(ssp->clk) |
1195 | / (1 + ((chip->cr0 & SSCR0_SCR) >> 8)), | 1197 | / (1 + ((chip->cr0 & SSCR0_SCR) >> 8)), |
1196 | spi->mode & 0x3); | 1198 | spi->mode & 0x3); |
1197 | 1199 | ||
@@ -1323,14 +1325,14 @@ static int __init pxa2xx_spi_probe(struct platform_device *pdev) | |||
1323 | struct pxa2xx_spi_master *platform_info; | 1325 | struct pxa2xx_spi_master *platform_info; |
1324 | struct spi_master *master; | 1326 | struct spi_master *master; |
1325 | struct driver_data *drv_data = 0; | 1327 | struct driver_data *drv_data = 0; |
1326 | struct resource *memory_resource; | 1328 | struct ssp_device *ssp; |
1327 | int irq; | ||
1328 | int status = 0; | 1329 | int status = 0; |
1329 | 1330 | ||
1330 | platform_info = dev->platform_data; | 1331 | platform_info = dev->platform_data; |
1331 | 1332 | ||
1332 | if (platform_info->ssp_type == SSP_UNDEFINED) { | 1333 | ssp = ssp_request(pdev->id, pdev->name); |
1333 | dev_err(&pdev->dev, "undefined SSP\n"); | 1334 | if (ssp == NULL) { |
1335 | dev_err(&pdev->dev, "failed to request SSP%d\n", pdev->id); | ||
1334 | return -ENODEV; | 1336 | return -ENODEV; |
1335 | } | 1337 | } |
1336 | 1338 | ||
@@ -1338,12 +1340,14 @@ static int __init pxa2xx_spi_probe(struct platform_device *pdev) | |||
1338 | master = spi_alloc_master(dev, sizeof(struct driver_data) + 16); | 1340 | master = spi_alloc_master(dev, sizeof(struct driver_data) + 16); |
1339 | if (!master) { | 1341 | if (!master) { |
1340 | dev_err(&pdev->dev, "can not alloc spi_master\n"); | 1342 | dev_err(&pdev->dev, "can not alloc spi_master\n"); |
1343 | ssp_free(ssp); | ||
1341 | return -ENOMEM; | 1344 | return -ENOMEM; |
1342 | } | 1345 | } |
1343 | drv_data = spi_master_get_devdata(master); | 1346 | drv_data = spi_master_get_devdata(master); |
1344 | drv_data->master = master; | 1347 | drv_data->master = master; |
1345 | drv_data->master_info = platform_info; | 1348 | drv_data->master_info = platform_info; |
1346 | drv_data->pdev = pdev; | 1349 | drv_data->pdev = pdev; |
1350 | drv_data->ssp = ssp; | ||
1347 | 1351 | ||
1348 | master->bus_num = pdev->id; | 1352 | master->bus_num = pdev->id; |
1349 | master->num_chipselect = platform_info->num_chipselect; | 1353 | master->num_chipselect = platform_info->num_chipselect; |
@@ -1351,21 +1355,13 @@ static int __init pxa2xx_spi_probe(struct platform_device *pdev) | |||
1351 | master->setup = setup; | 1355 | master->setup = setup; |
1352 | master->transfer = transfer; | 1356 | master->transfer = transfer; |
1353 | 1357 | ||
1354 | drv_data->ssp_type = platform_info->ssp_type; | 1358 | drv_data->ssp_type = ssp->type; |
1355 | drv_data->null_dma_buf = (u32 *)ALIGN((u32)(drv_data + | 1359 | drv_data->null_dma_buf = (u32 *)ALIGN((u32)(drv_data + |
1356 | sizeof(struct driver_data)), 8); | 1360 | sizeof(struct driver_data)), 8); |
1357 | 1361 | ||
1358 | /* Setup register addresses */ | 1362 | drv_data->ioaddr = ssp->mmio_base; |
1359 | memory_resource = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 1363 | drv_data->ssdr_physical = ssp->phys_base + SSDR; |
1360 | if (!memory_resource) { | 1364 | if (ssp->type == PXA25x_SSP) { |
1361 | dev_err(&pdev->dev, "memory resources not defined\n"); | ||
1362 | status = -ENODEV; | ||
1363 | goto out_error_master_alloc; | ||
1364 | } | ||
1365 | |||
1366 | drv_data->ioaddr = (void *)io_p2v((unsigned long)(memory_resource->start)); | ||
1367 | drv_data->ssdr_physical = memory_resource->start + 0x00000010; | ||
1368 | if (platform_info->ssp_type == PXA25x_SSP) { | ||
1369 | drv_data->int_cr1 = SSCR1_TIE | SSCR1_RIE; | 1365 | drv_data->int_cr1 = SSCR1_TIE | SSCR1_RIE; |
1370 | drv_data->dma_cr1 = 0; | 1366 | drv_data->dma_cr1 = 0; |
1371 | drv_data->clear_sr = SSSR_ROR; | 1367 | drv_data->clear_sr = SSSR_ROR; |
@@ -1377,15 +1373,7 @@ static int __init pxa2xx_spi_probe(struct platform_device *pdev) | |||
1377 | drv_data->mask_sr = SSSR_TINT | SSSR_RFS | SSSR_TFS | SSSR_ROR; | 1373 | drv_data->mask_sr = SSSR_TINT | SSSR_RFS | SSSR_TFS | SSSR_ROR; |
1378 | } | 1374 | } |
1379 | 1375 | ||
1380 | /* Attach to IRQ */ | 1376 | status = request_irq(ssp->irq, ssp_int, 0, dev->bus_id, drv_data); |
1381 | irq = platform_get_irq(pdev, 0); | ||
1382 | if (irq < 0) { | ||
1383 | dev_err(&pdev->dev, "irq resource not defined\n"); | ||
1384 | status = -ENODEV; | ||
1385 | goto out_error_master_alloc; | ||
1386 | } | ||
1387 | |||
1388 | status = request_irq(irq, ssp_int, 0, dev->bus_id, drv_data); | ||
1389 | if (status < 0) { | 1377 | if (status < 0) { |
1390 | dev_err(&pdev->dev, "can not get IRQ\n"); | 1378 | dev_err(&pdev->dev, "can not get IRQ\n"); |
1391 | goto out_error_master_alloc; | 1379 | goto out_error_master_alloc; |
@@ -1418,29 +1406,12 @@ static int __init pxa2xx_spi_probe(struct platform_device *pdev) | |||
1418 | goto out_error_dma_alloc; | 1406 | goto out_error_dma_alloc; |
1419 | } | 1407 | } |
1420 | 1408 | ||
1421 | if (drv_data->ioaddr == SSP1_VIRT) { | 1409 | DRCMR(ssp->drcmr_rx) = DRCMR_MAPVLD | drv_data->rx_channel; |
1422 | DRCMRRXSSDR = DRCMR_MAPVLD | 1410 | DRCMR(ssp->drcmr_tx) = DRCMR_MAPVLD | drv_data->tx_channel; |
1423 | | drv_data->rx_channel; | ||
1424 | DRCMRTXSSDR = DRCMR_MAPVLD | ||
1425 | | drv_data->tx_channel; | ||
1426 | } else if (drv_data->ioaddr == SSP2_VIRT) { | ||
1427 | DRCMRRXSS2DR = DRCMR_MAPVLD | ||
1428 | | drv_data->rx_channel; | ||
1429 | DRCMRTXSS2DR = DRCMR_MAPVLD | ||
1430 | | drv_data->tx_channel; | ||
1431 | } else if (drv_data->ioaddr == SSP3_VIRT) { | ||
1432 | DRCMRRXSS3DR = DRCMR_MAPVLD | ||
1433 | | drv_data->rx_channel; | ||
1434 | DRCMRTXSS3DR = DRCMR_MAPVLD | ||
1435 | | drv_data->tx_channel; | ||
1436 | } else { | ||
1437 | dev_err(dev, "bad SSP type\n"); | ||
1438 | goto out_error_dma_alloc; | ||
1439 | } | ||
1440 | } | 1411 | } |
1441 | 1412 | ||
1442 | /* Enable SOC clock */ | 1413 | /* Enable SOC clock */ |
1443 | pxa_set_cken(platform_info->clock_enable, 1); | 1414 | clk_enable(ssp->clk); |
1444 | 1415 | ||
1445 | /* Load default SSP configuration */ | 1416 | /* Load default SSP configuration */ |
1446 | write_SSCR0(0, drv_data->ioaddr); | 1417 | write_SSCR0(0, drv_data->ioaddr); |
@@ -1479,7 +1450,7 @@ out_error_queue_alloc: | |||
1479 | destroy_queue(drv_data); | 1450 | destroy_queue(drv_data); |
1480 | 1451 | ||
1481 | out_error_clock_enabled: | 1452 | out_error_clock_enabled: |
1482 | pxa_set_cken(platform_info->clock_enable, 0); | 1453 | clk_disable(ssp->clk); |
1483 | 1454 | ||
1484 | out_error_dma_alloc: | 1455 | out_error_dma_alloc: |
1485 | if (drv_data->tx_channel != -1) | 1456 | if (drv_data->tx_channel != -1) |
@@ -1488,17 +1459,18 @@ out_error_dma_alloc: | |||
1488 | pxa_free_dma(drv_data->rx_channel); | 1459 | pxa_free_dma(drv_data->rx_channel); |
1489 | 1460 | ||
1490 | out_error_irq_alloc: | 1461 | out_error_irq_alloc: |
1491 | free_irq(irq, drv_data); | 1462 | free_irq(ssp->irq, drv_data); |
1492 | 1463 | ||
1493 | out_error_master_alloc: | 1464 | out_error_master_alloc: |
1494 | spi_master_put(master); | 1465 | spi_master_put(master); |
1466 | ssp_free(ssp); | ||
1495 | return status; | 1467 | return status; |
1496 | } | 1468 | } |
1497 | 1469 | ||
1498 | static int pxa2xx_spi_remove(struct platform_device *pdev) | 1470 | static int pxa2xx_spi_remove(struct platform_device *pdev) |
1499 | { | 1471 | { |
1500 | struct driver_data *drv_data = platform_get_drvdata(pdev); | 1472 | struct driver_data *drv_data = platform_get_drvdata(pdev); |
1501 | int irq; | 1473 | struct ssp_device *ssp = drv_data->ssp; |
1502 | int status = 0; | 1474 | int status = 0; |
1503 | 1475 | ||
1504 | if (!drv_data) | 1476 | if (!drv_data) |
@@ -1520,28 +1492,21 @@ static int pxa2xx_spi_remove(struct platform_device *pdev) | |||
1520 | 1492 | ||
1521 | /* Disable the SSP at the peripheral and SOC level */ | 1493 | /* Disable the SSP at the peripheral and SOC level */ |
1522 | write_SSCR0(0, drv_data->ioaddr); | 1494 | write_SSCR0(0, drv_data->ioaddr); |
1523 | pxa_set_cken(drv_data->master_info->clock_enable, 0); | 1495 | clk_disable(ssp->clk); |
1524 | 1496 | ||
1525 | /* Release DMA */ | 1497 | /* Release DMA */ |
1526 | if (drv_data->master_info->enable_dma) { | 1498 | if (drv_data->master_info->enable_dma) { |
1527 | if (drv_data->ioaddr == SSP1_VIRT) { | 1499 | DRCMR(ssp->drcmr_rx) = 0; |
1528 | DRCMRRXSSDR = 0; | 1500 | DRCMR(ssp->drcmr_tx) = 0; |
1529 | DRCMRTXSSDR = 0; | ||
1530 | } else if (drv_data->ioaddr == SSP2_VIRT) { | ||
1531 | DRCMRRXSS2DR = 0; | ||
1532 | DRCMRTXSS2DR = 0; | ||
1533 | } else if (drv_data->ioaddr == SSP3_VIRT) { | ||
1534 | DRCMRRXSS3DR = 0; | ||
1535 | DRCMRTXSS3DR = 0; | ||
1536 | } | ||
1537 | pxa_free_dma(drv_data->tx_channel); | 1501 | pxa_free_dma(drv_data->tx_channel); |
1538 | pxa_free_dma(drv_data->rx_channel); | 1502 | pxa_free_dma(drv_data->rx_channel); |
1539 | } | 1503 | } |
1540 | 1504 | ||
1541 | /* Release IRQ */ | 1505 | /* Release IRQ */ |
1542 | irq = platform_get_irq(pdev, 0); | 1506 | free_irq(ssp->irq, drv_data); |
1543 | if (irq >= 0) | 1507 | |
1544 | free_irq(irq, drv_data); | 1508 | /* Release SSP */ |
1509 | ssp_free(ssp); | ||
1545 | 1510 | ||
1546 | /* Disconnect from the SPI framework */ | 1511 | /* Disconnect from the SPI framework */ |
1547 | spi_unregister_master(drv_data->master); | 1512 | spi_unregister_master(drv_data->master); |
@@ -1576,6 +1541,7 @@ static int suspend_devices(struct device *dev, void *pm_message) | |||
1576 | static int pxa2xx_spi_suspend(struct platform_device *pdev, pm_message_t state) | 1541 | static int pxa2xx_spi_suspend(struct platform_device *pdev, pm_message_t state) |
1577 | { | 1542 | { |
1578 | struct driver_data *drv_data = platform_get_drvdata(pdev); | 1543 | struct driver_data *drv_data = platform_get_drvdata(pdev); |
1544 | struct ssp_device *ssp = drv_data->ssp; | ||
1579 | int status = 0; | 1545 | int status = 0; |
1580 | 1546 | ||
1581 | /* Check all childern for current power state */ | 1547 | /* Check all childern for current power state */ |
@@ -1588,7 +1554,7 @@ static int pxa2xx_spi_suspend(struct platform_device *pdev, pm_message_t state) | |||
1588 | if (status != 0) | 1554 | if (status != 0) |
1589 | return status; | 1555 | return status; |
1590 | write_SSCR0(0, drv_data->ioaddr); | 1556 | write_SSCR0(0, drv_data->ioaddr); |
1591 | pxa_set_cken(drv_data->master_info->clock_enable, 0); | 1557 | clk_disable(ssp->clk); |
1592 | 1558 | ||
1593 | return 0; | 1559 | return 0; |
1594 | } | 1560 | } |
@@ -1596,10 +1562,11 @@ static int pxa2xx_spi_suspend(struct platform_device *pdev, pm_message_t state) | |||
1596 | static int pxa2xx_spi_resume(struct platform_device *pdev) | 1562 | static int pxa2xx_spi_resume(struct platform_device *pdev) |
1597 | { | 1563 | { |
1598 | struct driver_data *drv_data = platform_get_drvdata(pdev); | 1564 | struct driver_data *drv_data = platform_get_drvdata(pdev); |
1565 | struct ssp_device *ssp = drv_data->ssp; | ||
1599 | int status = 0; | 1566 | int status = 0; |
1600 | 1567 | ||
1601 | /* Enable the SSP clock */ | 1568 | /* Enable the SSP clock */ |
1602 | pxa_set_cken(drv_data->master_info->clock_enable, 1); | 1569 | clk_disable(ssp->clk); |
1603 | 1570 | ||
1604 | /* Start the queue running */ | 1571 | /* Start the queue running */ |
1605 | status = start_queue(drv_data); | 1572 | status = start_queue(drv_data); |
diff --git a/drivers/usb/Kconfig b/drivers/usb/Kconfig index 7580aa5da0f8..7a6499008b89 100644 --- a/drivers/usb/Kconfig +++ b/drivers/usb/Kconfig | |||
@@ -33,6 +33,7 @@ config USB_ARCH_HAS_OHCI | |||
33 | default y if ARCH_LH7A404 | 33 | default y if ARCH_LH7A404 |
34 | default y if ARCH_S3C2410 | 34 | default y if ARCH_S3C2410 |
35 | default y if PXA27x | 35 | default y if PXA27x |
36 | default y if PXA3xx | ||
36 | default y if ARCH_EP93XX | 37 | default y if ARCH_EP93XX |
37 | default y if ARCH_AT91 | 38 | default y if ARCH_AT91 |
38 | default y if ARCH_PNX4008 | 39 | default y if ARCH_PNX4008 |
diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c index ecfe800fd720..ddd4ee1f2413 100644 --- a/drivers/usb/host/ohci-hcd.c +++ b/drivers/usb/host/ohci-hcd.c | |||
@@ -997,7 +997,7 @@ MODULE_LICENSE ("GPL"); | |||
997 | #define PLATFORM_DRIVER ohci_hcd_lh7a404_driver | 997 | #define PLATFORM_DRIVER ohci_hcd_lh7a404_driver |
998 | #endif | 998 | #endif |
999 | 999 | ||
1000 | #ifdef CONFIG_PXA27x | 1000 | #if defined(CONFIG_PXA27x) || defined(CONFIG_PXA3xx) |
1001 | #include "ohci-pxa27x.c" | 1001 | #include "ohci-pxa27x.c" |
1002 | #define PLATFORM_DRIVER ohci_hcd_pxa27x_driver | 1002 | #define PLATFORM_DRIVER ohci_hcd_pxa27x_driver |
1003 | #endif | 1003 | #endif |
diff --git a/drivers/usb/host/ohci-pxa27x.c b/drivers/usb/host/ohci-pxa27x.c index 23d2fe5a62f4..ff9a79843471 100644 --- a/drivers/usb/host/ohci-pxa27x.c +++ b/drivers/usb/host/ohci-pxa27x.c | |||
@@ -22,6 +22,7 @@ | |||
22 | #include <linux/device.h> | 22 | #include <linux/device.h> |
23 | #include <linux/signal.h> | 23 | #include <linux/signal.h> |
24 | #include <linux/platform_device.h> | 24 | #include <linux/platform_device.h> |
25 | #include <linux/clk.h> | ||
25 | 26 | ||
26 | #include <asm/mach-types.h> | 27 | #include <asm/mach-types.h> |
27 | #include <asm/hardware.h> | 28 | #include <asm/hardware.h> |
@@ -32,6 +33,8 @@ | |||
32 | 33 | ||
33 | #define UHCRHPS(x) __REG2( 0x4C000050, (x)<<2 ) | 34 | #define UHCRHPS(x) __REG2( 0x4C000050, (x)<<2 ) |
34 | 35 | ||
36 | static struct clk *usb_clk; | ||
37 | |||
35 | /* | 38 | /* |
36 | PMM_NPS_MODE -- PMM Non-power switching mode | 39 | PMM_NPS_MODE -- PMM Non-power switching mode |
37 | Ports are powered continuously. | 40 | Ports are powered continuously. |
@@ -80,7 +83,7 @@ static int pxa27x_start_hc(struct device *dev) | |||
80 | 83 | ||
81 | inf = dev->platform_data; | 84 | inf = dev->platform_data; |
82 | 85 | ||
83 | pxa_set_cken(CKEN_USBHOST, 1); | 86 | clk_enable(usb_clk); |
84 | 87 | ||
85 | UHCHR |= UHCHR_FHR; | 88 | UHCHR |= UHCHR_FHR; |
86 | udelay(11); | 89 | udelay(11); |
@@ -123,7 +126,7 @@ static void pxa27x_stop_hc(struct device *dev) | |||
123 | UHCCOMS |= 1; | 126 | UHCCOMS |= 1; |
124 | udelay(10); | 127 | udelay(10); |
125 | 128 | ||
126 | pxa_set_cken(CKEN_USBHOST, 0); | 129 | clk_disable(usb_clk); |
127 | } | 130 | } |
128 | 131 | ||
129 | 132 | ||
@@ -158,6 +161,10 @@ int usb_hcd_pxa27x_probe (const struct hc_driver *driver, struct platform_device | |||
158 | return -ENOMEM; | 161 | return -ENOMEM; |
159 | } | 162 | } |
160 | 163 | ||
164 | usb_clk = clk_get(&pdev->dev, "USBCLK"); | ||
165 | if (IS_ERR(usb_clk)) | ||
166 | return PTR_ERR(usb_clk); | ||
167 | |||
161 | hcd = usb_create_hcd (driver, &pdev->dev, "pxa27x"); | 168 | hcd = usb_create_hcd (driver, &pdev->dev, "pxa27x"); |
162 | if (!hcd) | 169 | if (!hcd) |
163 | return -ENOMEM; | 170 | return -ENOMEM; |
@@ -201,6 +208,7 @@ int usb_hcd_pxa27x_probe (const struct hc_driver *driver, struct platform_device | |||
201 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); | 208 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); |
202 | err1: | 209 | err1: |
203 | usb_put_hcd(hcd); | 210 | usb_put_hcd(hcd); |
211 | clk_put(usb_clk); | ||
204 | return retval; | 212 | return retval; |
205 | } | 213 | } |
206 | 214 | ||
@@ -225,6 +233,7 @@ void usb_hcd_pxa27x_remove (struct usb_hcd *hcd, struct platform_device *pdev) | |||
225 | iounmap(hcd->regs); | 233 | iounmap(hcd->regs); |
226 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); | 234 | release_mem_region(hcd->rsrc_start, hcd->rsrc_len); |
227 | usb_put_hcd(hcd); | 235 | usb_put_hcd(hcd); |
236 | clk_put(usb_clk); | ||
228 | } | 237 | } |
229 | 238 | ||
230 | /*-------------------------------------------------------------------------*/ | 239 | /*-------------------------------------------------------------------------*/ |