~ubuntu-branches/debian/wheezy/linux-2.6/wheezy

« back to all changes in this revision

Viewing changes to arch/arm/mach-s5pc100/dev-spi.c

  • Committer: Bazaar Package Importer
  • Author(s): Ben Hutchings, Ben Hutchings, Aurelien Jarno, Martin Michlmayr
  • Date: 2011-04-06 13:53:30 UTC
  • mfrom: (43.1.5 sid)
  • Revision ID: james.westby@ubuntu.com-20110406135330-wjufxhd0tvn3zx4z
Tags: 2.6.38-3
[ Ben Hutchings ]
* [ppc64] Add to linux-tools package architectures (Closes: #620124)
* [amd64] Save cr4 to mmu_cr4_features at boot time (Closes: #620284)
* appletalk: Fix bugs introduced when removing use of BKL
* ALSA: Fix yet another race in disconnection
* cciss: Fix lost command issue
* ath9k: Fix kernel panic in AR2427
* ses: Avoid kernel panic when lun 0 is not mapped
* PCI/ACPI: Report ASPM support to BIOS if not disabled from command line

[ Aurelien Jarno ]
* rtlwifi: fix build when PCI is not enabled.

[ Martin Michlmayr ]
* rtlwifi: Eliminate udelay calls with too large values (Closes: #620204)

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* linux/arch/arm/mach-s5pc100/dev-spi.c
 
2
 *
 
3
 * Copyright (C) 2010 Samsung Electronics Co. Ltd.
 
4
 *      Jaswinder Singh <jassi.brar@samsung.com>
 
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 version 2 as
 
8
 * published by the Free Software Foundation.
 
9
 */
 
10
 
 
11
#include <linux/platform_device.h>
 
12
#include <linux/dma-mapping.h>
 
13
#include <linux/gpio.h>
 
14
 
 
15
#include <mach/dma.h>
 
16
#include <mach/map.h>
 
17
#include <mach/spi-clocks.h>
 
18
 
 
19
#include <plat/s3c64xx-spi.h>
 
20
#include <plat/gpio-cfg.h>
 
21
#include <plat/irqs.h>
 
22
 
 
23
static char *spi_src_clks[] = {
 
24
        [S5PC100_SPI_SRCCLK_PCLK] = "pclk",
 
25
        [S5PC100_SPI_SRCCLK_48M] = "spi_48m",
 
26
        [S5PC100_SPI_SRCCLK_SPIBUS] = "spi_bus",
 
27
};
 
28
 
 
29
/* SPI Controller platform_devices */
 
30
 
 
31
/* Since we emulate multi-cs capability, we do not touch the CS.
 
32
 * The emulated CS is toggled by board specific mechanism, as it can
 
33
 * be either some immediate GPIO or some signal out of some other
 
34
 * chip in between ... or some yet another way.
 
35
 * We simply do not assume anything about CS.
 
36
 */
 
37
static int s5pc100_spi_cfg_gpio(struct platform_device *pdev)
 
38
{
 
39
        switch (pdev->id) {
 
40
        case 0:
 
41
                s3c_gpio_cfgall_range(S5PC100_GPB(0), 3,
 
42
                                      S3C_GPIO_SFN(2), S3C_GPIO_PULL_UP);
 
43
                break;
 
44
 
 
45
        case 1:
 
46
                s3c_gpio_cfgall_range(S5PC100_GPB(4), 3,
 
47
                                      S3C_GPIO_SFN(2), S3C_GPIO_PULL_UP);
 
48
                break;
 
49
 
 
50
        case 2:
 
51
                s3c_gpio_cfgpin(S5PC100_GPG3(0), S3C_GPIO_SFN(3));
 
52
                s3c_gpio_setpull(S5PC100_GPG3(0), S3C_GPIO_PULL_UP);
 
53
                s3c_gpio_cfgall_range(S5PC100_GPB(2), 2,
 
54
                                      S3C_GPIO_SFN(3), S3C_GPIO_PULL_UP);
 
55
                break;
 
56
 
 
57
        default:
 
58
                dev_err(&pdev->dev, "Invalid SPI Controller number!");
 
59
                return -EINVAL;
 
60
        }
 
61
 
 
62
        return 0;
 
63
}
 
64
 
 
65
static struct resource s5pc100_spi0_resource[] = {
 
66
        [0] = {
 
67
                .start = S5PC100_PA_SPI0,
 
68
                .end   = S5PC100_PA_SPI0 + 0x100 - 1,
 
69
                .flags = IORESOURCE_MEM,
 
70
        },
 
71
        [1] = {
 
72
                .start = DMACH_SPI0_TX,
 
73
                .end   = DMACH_SPI0_TX,
 
74
                .flags = IORESOURCE_DMA,
 
75
        },
 
76
        [2] = {
 
77
                .start = DMACH_SPI0_RX,
 
78
                .end   = DMACH_SPI0_RX,
 
79
                .flags = IORESOURCE_DMA,
 
80
        },
 
81
        [3] = {
 
82
                .start = IRQ_SPI0,
 
83
                .end   = IRQ_SPI0,
 
84
                .flags = IORESOURCE_IRQ,
 
85
        },
 
86
};
 
87
 
 
88
static struct s3c64xx_spi_info s5pc100_spi0_pdata = {
 
89
        .cfg_gpio = s5pc100_spi_cfg_gpio,
 
90
        .fifo_lvl_mask = 0x7f,
 
91
        .rx_lvl_offset = 13,
 
92
        .high_speed = 1,
 
93
};
 
94
 
 
95
static u64 spi_dmamask = DMA_BIT_MASK(32);
 
96
 
 
97
struct platform_device s5pc100_device_spi0 = {
 
98
        .name             = "s3c64xx-spi",
 
99
        .id               = 0,
 
100
        .num_resources    = ARRAY_SIZE(s5pc100_spi0_resource),
 
101
        .resource         = s5pc100_spi0_resource,
 
102
        .dev = {
 
103
                .dma_mask               = &spi_dmamask,
 
104
                .coherent_dma_mask      = DMA_BIT_MASK(32),
 
105
                .platform_data = &s5pc100_spi0_pdata,
 
106
        },
 
107
};
 
108
 
 
109
static struct resource s5pc100_spi1_resource[] = {
 
110
        [0] = {
 
111
                .start = S5PC100_PA_SPI1,
 
112
                .end   = S5PC100_PA_SPI1 + 0x100 - 1,
 
113
                .flags = IORESOURCE_MEM,
 
114
        },
 
115
        [1] = {
 
116
                .start = DMACH_SPI1_TX,
 
117
                .end   = DMACH_SPI1_TX,
 
118
                .flags = IORESOURCE_DMA,
 
119
        },
 
120
        [2] = {
 
121
                .start = DMACH_SPI1_RX,
 
122
                .end   = DMACH_SPI1_RX,
 
123
                .flags = IORESOURCE_DMA,
 
124
        },
 
125
        [3] = {
 
126
                .start = IRQ_SPI1,
 
127
                .end   = IRQ_SPI1,
 
128
                .flags = IORESOURCE_IRQ,
 
129
        },
 
130
};
 
131
 
 
132
static struct s3c64xx_spi_info s5pc100_spi1_pdata = {
 
133
        .cfg_gpio = s5pc100_spi_cfg_gpio,
 
134
        .fifo_lvl_mask = 0x7f,
 
135
        .rx_lvl_offset = 13,
 
136
        .high_speed = 1,
 
137
};
 
138
 
 
139
struct platform_device s5pc100_device_spi1 = {
 
140
        .name             = "s3c64xx-spi",
 
141
        .id               = 1,
 
142
        .num_resources    = ARRAY_SIZE(s5pc100_spi1_resource),
 
143
        .resource         = s5pc100_spi1_resource,
 
144
        .dev = {
 
145
                .dma_mask               = &spi_dmamask,
 
146
                .coherent_dma_mask      = DMA_BIT_MASK(32),
 
147
                .platform_data = &s5pc100_spi1_pdata,
 
148
        },
 
149
};
 
150
 
 
151
static struct resource s5pc100_spi2_resource[] = {
 
152
        [0] = {
 
153
                .start = S5PC100_PA_SPI2,
 
154
                .end   = S5PC100_PA_SPI2 + 0x100 - 1,
 
155
                .flags = IORESOURCE_MEM,
 
156
        },
 
157
        [1] = {
 
158
                .start = DMACH_SPI2_TX,
 
159
                .end   = DMACH_SPI2_TX,
 
160
                .flags = IORESOURCE_DMA,
 
161
        },
 
162
        [2] = {
 
163
                .start = DMACH_SPI2_RX,
 
164
                .end   = DMACH_SPI2_RX,
 
165
                .flags = IORESOURCE_DMA,
 
166
        },
 
167
        [3] = {
 
168
                .start = IRQ_SPI2,
 
169
                .end   = IRQ_SPI2,
 
170
                .flags = IORESOURCE_IRQ,
 
171
        },
 
172
};
 
173
 
 
174
static struct s3c64xx_spi_info s5pc100_spi2_pdata = {
 
175
        .cfg_gpio = s5pc100_spi_cfg_gpio,
 
176
        .fifo_lvl_mask = 0x7f,
 
177
        .rx_lvl_offset = 13,
 
178
        .high_speed = 1,
 
179
};
 
180
 
 
181
struct platform_device s5pc100_device_spi2 = {
 
182
        .name             = "s3c64xx-spi",
 
183
        .id               = 2,
 
184
        .num_resources    = ARRAY_SIZE(s5pc100_spi2_resource),
 
185
        .resource         = s5pc100_spi2_resource,
 
186
        .dev = {
 
187
                .dma_mask               = &spi_dmamask,
 
188
                .coherent_dma_mask      = DMA_BIT_MASK(32),
 
189
                .platform_data = &s5pc100_spi2_pdata,
 
190
        },
 
191
};
 
192
 
 
193
void __init s5pc100_spi_set_info(int cntrlr, int src_clk_nr, int num_cs)
 
194
{
 
195
        struct s3c64xx_spi_info *pd;
 
196
 
 
197
        /* Reject invalid configuration */
 
198
        if (!num_cs || src_clk_nr < 0
 
199
                        || src_clk_nr > S5PC100_SPI_SRCCLK_SPIBUS) {
 
200
                printk(KERN_ERR "%s: Invalid SPI configuration\n", __func__);
 
201
                return;
 
202
        }
 
203
 
 
204
        switch (cntrlr) {
 
205
        case 0:
 
206
                pd = &s5pc100_spi0_pdata;
 
207
                break;
 
208
        case 1:
 
209
                pd = &s5pc100_spi1_pdata;
 
210
                break;
 
211
        case 2:
 
212
                pd = &s5pc100_spi2_pdata;
 
213
                break;
 
214
        default:
 
215
                printk(KERN_ERR "%s: Invalid SPI controller(%d)\n",
 
216
                                                        __func__, cntrlr);
 
217
                return;
 
218
        }
 
219
 
 
220
        pd->num_cs = num_cs;
 
221
        pd->src_clk_nr = src_clk_nr;
 
222
        pd->src_clk_name = spi_src_clks[src_clk_nr];
 
223
}