diff options
Diffstat (limited to 'include/linux/mmc')
-rw-r--r-- | include/linux/mmc/card.h | 24 | ||||
-rw-r--r-- | include/linux/mmc/core.h | 19 | ||||
-rw-r--r-- | include/linux/mmc/host.h | 9 | ||||
-rw-r--r-- | include/linux/mmc/mmc.h | 25 | ||||
-rw-r--r-- | include/linux/mmc/sd.h | 5 | ||||
-rw-r--r-- | include/linux/mmc/sdhci-spear.h | 42 | ||||
-rw-r--r-- | include/linux/mmc/sdio.h | 4 | ||||
-rw-r--r-- | include/linux/mmc/sdio_func.h | 3 | ||||
-rw-r--r-- | include/linux/mmc/sh_mmcif.h | 200 |
9 files changed, 324 insertions, 7 deletions
diff --git a/include/linux/mmc/card.h b/include/linux/mmc/card.h index d02d2c6e0cfe..6b7525099e56 100644 --- a/include/linux/mmc/card.h +++ b/include/linux/mmc/card.h | |||
@@ -24,12 +24,14 @@ struct mmc_cid { | |||
24 | }; | 24 | }; |
25 | 25 | ||
26 | struct mmc_csd { | 26 | struct mmc_csd { |
27 | unsigned char structure; | ||
27 | unsigned char mmca_vsn; | 28 | unsigned char mmca_vsn; |
28 | unsigned short cmdclass; | 29 | unsigned short cmdclass; |
29 | unsigned short tacc_clks; | 30 | unsigned short tacc_clks; |
30 | unsigned int tacc_ns; | 31 | unsigned int tacc_ns; |
31 | unsigned int r2w_factor; | 32 | unsigned int r2w_factor; |
32 | unsigned int max_dtr; | 33 | unsigned int max_dtr; |
34 | unsigned int erase_size; /* In sectors */ | ||
33 | unsigned int read_blkbits; | 35 | unsigned int read_blkbits; |
34 | unsigned int write_blkbits; | 36 | unsigned int write_blkbits; |
35 | unsigned int capacity; | 37 | unsigned int capacity; |
@@ -41,9 +43,16 @@ struct mmc_csd { | |||
41 | 43 | ||
42 | struct mmc_ext_csd { | 44 | struct mmc_ext_csd { |
43 | u8 rev; | 45 | u8 rev; |
46 | u8 erase_group_def; | ||
47 | u8 sec_feature_support; | ||
44 | unsigned int sa_timeout; /* Units: 100ns */ | 48 | unsigned int sa_timeout; /* Units: 100ns */ |
45 | unsigned int hs_max_dtr; | 49 | unsigned int hs_max_dtr; |
46 | unsigned int sectors; | 50 | unsigned int sectors; |
51 | unsigned int hc_erase_size; /* In sectors */ | ||
52 | unsigned int hc_erase_timeout; /* In milliseconds */ | ||
53 | unsigned int sec_trim_mult; /* Secure trim multiplier */ | ||
54 | unsigned int sec_erase_mult; /* Secure erase multiplier */ | ||
55 | unsigned int trim_timeout; /* In milliseconds */ | ||
47 | }; | 56 | }; |
48 | 57 | ||
49 | struct sd_scr { | 58 | struct sd_scr { |
@@ -53,6 +62,12 @@ struct sd_scr { | |||
53 | #define SD_SCR_BUS_WIDTH_4 (1<<2) | 62 | #define SD_SCR_BUS_WIDTH_4 (1<<2) |
54 | }; | 63 | }; |
55 | 64 | ||
65 | struct sd_ssr { | ||
66 | unsigned int au; /* In sectors */ | ||
67 | unsigned int erase_timeout; /* In milliseconds */ | ||
68 | unsigned int erase_offset; /* In milliseconds */ | ||
69 | }; | ||
70 | |||
56 | struct sd_switch_caps { | 71 | struct sd_switch_caps { |
57 | unsigned int hs_max_dtr; | 72 | unsigned int hs_max_dtr; |
58 | }; | 73 | }; |
@@ -92,6 +107,7 @@ struct mmc_card { | |||
92 | #define MMC_TYPE_MMC 0 /* MMC card */ | 107 | #define MMC_TYPE_MMC 0 /* MMC card */ |
93 | #define MMC_TYPE_SD 1 /* SD card */ | 108 | #define MMC_TYPE_SD 1 /* SD card */ |
94 | #define MMC_TYPE_SDIO 2 /* SDIO card */ | 109 | #define MMC_TYPE_SDIO 2 /* SDIO card */ |
110 | #define MMC_TYPE_SD_COMBO 3 /* SD combo (IO+mem) card */ | ||
95 | unsigned int state; /* (our) card state */ | 111 | unsigned int state; /* (our) card state */ |
96 | #define MMC_STATE_PRESENT (1<<0) /* present in sysfs */ | 112 | #define MMC_STATE_PRESENT (1<<0) /* present in sysfs */ |
97 | #define MMC_STATE_READONLY (1<<1) /* card is read-only */ | 113 | #define MMC_STATE_READONLY (1<<1) /* card is read-only */ |
@@ -101,6 +117,13 @@ struct mmc_card { | |||
101 | #define MMC_QUIRK_LENIENT_FN0 (1<<0) /* allow SDIO FN0 writes outside of the VS CCCR range */ | 117 | #define MMC_QUIRK_LENIENT_FN0 (1<<0) /* allow SDIO FN0 writes outside of the VS CCCR range */ |
102 | #define MMC_QUIRK_BLKSZ_FOR_BYTE_MODE (1<<1) /* use func->cur_blksize */ | 118 | #define MMC_QUIRK_BLKSZ_FOR_BYTE_MODE (1<<1) /* use func->cur_blksize */ |
103 | /* for byte mode */ | 119 | /* for byte mode */ |
120 | #define MMC_QUIRK_NONSTD_SDIO (1<<2) /* non-standard SDIO card attached */ | ||
121 | /* (missing CIA registers) */ | ||
122 | |||
123 | unsigned int erase_size; /* erase size in sectors */ | ||
124 | unsigned int erase_shift; /* if erase unit is power 2 */ | ||
125 | unsigned int pref_erase; /* in sectors */ | ||
126 | u8 erased_byte; /* value of erased bytes */ | ||
104 | 127 | ||
105 | u32 raw_cid[4]; /* raw card CID */ | 128 | u32 raw_cid[4]; /* raw card CID */ |
106 | u32 raw_csd[4]; /* raw card CSD */ | 129 | u32 raw_csd[4]; /* raw card CSD */ |
@@ -109,6 +132,7 @@ struct mmc_card { | |||
109 | struct mmc_csd csd; /* card specific */ | 132 | struct mmc_csd csd; /* card specific */ |
110 | struct mmc_ext_csd ext_csd; /* mmc v4 extended card specific */ | 133 | struct mmc_ext_csd ext_csd; /* mmc v4 extended card specific */ |
111 | struct sd_scr scr; /* extra SD information */ | 134 | struct sd_scr scr; /* extra SD information */ |
135 | struct sd_ssr ssr; /* yet more SD information */ | ||
112 | struct sd_switch_caps sw_caps; /* switch (CMD6) caps */ | 136 | struct sd_switch_caps sw_caps; /* switch (CMD6) caps */ |
113 | 137 | ||
114 | unsigned int sdio_funcs; /* number of SDIO functions */ | 138 | unsigned int sdio_funcs; /* number of SDIO functions */ |
diff --git a/include/linux/mmc/core.h b/include/linux/mmc/core.h index e4898e9eeb59..7429033acb66 100644 --- a/include/linux/mmc/core.h +++ b/include/linux/mmc/core.h | |||
@@ -92,6 +92,8 @@ struct mmc_command { | |||
92 | * actively failing requests | 92 | * actively failing requests |
93 | */ | 93 | */ |
94 | 94 | ||
95 | unsigned int erase_timeout; /* in milliseconds */ | ||
96 | |||
95 | struct mmc_data *data; /* data segment associated with cmd */ | 97 | struct mmc_data *data; /* data segment associated with cmd */ |
96 | struct mmc_request *mrq; /* associated request */ | 98 | struct mmc_request *mrq; /* associated request */ |
97 | }; | 99 | }; |
@@ -134,6 +136,23 @@ extern int mmc_wait_for_cmd(struct mmc_host *, struct mmc_command *, int); | |||
134 | extern int mmc_wait_for_app_cmd(struct mmc_host *, struct mmc_card *, | 136 | extern int mmc_wait_for_app_cmd(struct mmc_host *, struct mmc_card *, |
135 | struct mmc_command *, int); | 137 | struct mmc_command *, int); |
136 | 138 | ||
139 | #define MMC_ERASE_ARG 0x00000000 | ||
140 | #define MMC_SECURE_ERASE_ARG 0x80000000 | ||
141 | #define MMC_TRIM_ARG 0x00000001 | ||
142 | #define MMC_SECURE_TRIM1_ARG 0x80000001 | ||
143 | #define MMC_SECURE_TRIM2_ARG 0x80008000 | ||
144 | |||
145 | #define MMC_SECURE_ARGS 0x80000000 | ||
146 | #define MMC_TRIM_ARGS 0x00008001 | ||
147 | |||
148 | extern int mmc_erase(struct mmc_card *card, unsigned int from, unsigned int nr, | ||
149 | unsigned int arg); | ||
150 | extern int mmc_can_erase(struct mmc_card *card); | ||
151 | extern int mmc_can_trim(struct mmc_card *card); | ||
152 | extern int mmc_can_secure_erase_trim(struct mmc_card *card); | ||
153 | extern int mmc_erase_group_aligned(struct mmc_card *card, unsigned int from, | ||
154 | unsigned int nr); | ||
155 | |||
137 | extern void mmc_set_data_timeout(struct mmc_data *, const struct mmc_card *); | 156 | extern void mmc_set_data_timeout(struct mmc_data *, const struct mmc_card *); |
138 | extern unsigned int mmc_align_data_size(struct mmc_card *, unsigned int); | 157 | extern unsigned int mmc_align_data_size(struct mmc_card *, unsigned int); |
139 | 158 | ||
diff --git a/include/linux/mmc/host.h b/include/linux/mmc/host.h index 43eaf5ca5848..1575b52c3bfa 100644 --- a/include/linux/mmc/host.h +++ b/include/linux/mmc/host.h | |||
@@ -108,6 +108,9 @@ struct mmc_host_ops { | |||
108 | int (*get_cd)(struct mmc_host *host); | 108 | int (*get_cd)(struct mmc_host *host); |
109 | 109 | ||
110 | void (*enable_sdio_irq)(struct mmc_host *host, int enable); | 110 | void (*enable_sdio_irq)(struct mmc_host *host, int enable); |
111 | |||
112 | /* optional callback for HC quirks */ | ||
113 | void (*init_card)(struct mmc_host *host, struct mmc_card *card); | ||
111 | }; | 114 | }; |
112 | 115 | ||
113 | struct mmc_card; | 116 | struct mmc_card; |
@@ -121,6 +124,7 @@ struct mmc_host { | |||
121 | unsigned int f_min; | 124 | unsigned int f_min; |
122 | unsigned int f_max; | 125 | unsigned int f_max; |
123 | u32 ocr_avail; | 126 | u32 ocr_avail; |
127 | struct notifier_block pm_notify; | ||
124 | 128 | ||
125 | #define MMC_VDD_165_195 0x00000080 /* VDD voltage 1.65 - 1.95 */ | 129 | #define MMC_VDD_165_195 0x00000080 /* VDD voltage 1.65 - 1.95 */ |
126 | #define MMC_VDD_20_21 0x00000100 /* VDD voltage 2.0 ~ 2.1 */ | 130 | #define MMC_VDD_20_21 0x00000100 /* VDD voltage 2.0 ~ 2.1 */ |
@@ -152,6 +156,7 @@ struct mmc_host { | |||
152 | #define MMC_CAP_DISABLE (1 << 7) /* Can the host be disabled */ | 156 | #define MMC_CAP_DISABLE (1 << 7) /* Can the host be disabled */ |
153 | #define MMC_CAP_NONREMOVABLE (1 << 8) /* Nonremovable e.g. eMMC */ | 157 | #define MMC_CAP_NONREMOVABLE (1 << 8) /* Nonremovable e.g. eMMC */ |
154 | #define MMC_CAP_WAIT_WHILE_BUSY (1 << 9) /* Waits while card is busy */ | 158 | #define MMC_CAP_WAIT_WHILE_BUSY (1 << 9) /* Waits while card is busy */ |
159 | #define MMC_CAP_ERASE (1 << 10) /* Allow erase/trim commands */ | ||
155 | 160 | ||
156 | mmc_pm_flag_t pm_caps; /* supported pm features */ | 161 | mmc_pm_flag_t pm_caps; /* supported pm features */ |
157 | 162 | ||
@@ -180,6 +185,7 @@ struct mmc_host { | |||
180 | 185 | ||
181 | /* Only used with MMC_CAP_DISABLE */ | 186 | /* Only used with MMC_CAP_DISABLE */ |
182 | int enabled; /* host is enabled */ | 187 | int enabled; /* host is enabled */ |
188 | int rescan_disable; /* disable card detection */ | ||
183 | int nesting_cnt; /* "enable" nesting count */ | 189 | int nesting_cnt; /* "enable" nesting count */ |
184 | int en_dis_recurs; /* detect recursion */ | 190 | int en_dis_recurs; /* detect recursion */ |
185 | unsigned int disable_delay; /* disable delay in msecs */ | 191 | unsigned int disable_delay; /* disable delay in msecs */ |
@@ -227,7 +233,7 @@ static inline void *mmc_priv(struct mmc_host *host) | |||
227 | #define mmc_classdev(x) (&(x)->class_dev) | 233 | #define mmc_classdev(x) (&(x)->class_dev) |
228 | #define mmc_hostname(x) (dev_name(&(x)->class_dev)) | 234 | #define mmc_hostname(x) (dev_name(&(x)->class_dev)) |
229 | 235 | ||
230 | extern int mmc_suspend_host(struct mmc_host *, pm_message_t); | 236 | extern int mmc_suspend_host(struct mmc_host *); |
231 | extern int mmc_resume_host(struct mmc_host *); | 237 | extern int mmc_resume_host(struct mmc_host *); |
232 | 238 | ||
233 | extern void mmc_power_save_host(struct mmc_host *host); | 239 | extern void mmc_power_save_host(struct mmc_host *host); |
@@ -254,6 +260,7 @@ int mmc_card_can_sleep(struct mmc_host *host); | |||
254 | int mmc_host_enable(struct mmc_host *host); | 260 | int mmc_host_enable(struct mmc_host *host); |
255 | int mmc_host_disable(struct mmc_host *host); | 261 | int mmc_host_disable(struct mmc_host *host); |
256 | int mmc_host_lazy_disable(struct mmc_host *host); | 262 | int mmc_host_lazy_disable(struct mmc_host *host); |
263 | int mmc_pm_notify(struct notifier_block *notify_block, unsigned long, void *); | ||
257 | 264 | ||
258 | static inline void mmc_set_disable_delay(struct mmc_host *host, | 265 | static inline void mmc_set_disable_delay(struct mmc_host *host, |
259 | unsigned int disable_delay) | 266 | unsigned int disable_delay) |
diff --git a/include/linux/mmc/mmc.h b/include/linux/mmc/mmc.h index 8a49cbf0376d..dd11ae51fb68 100644 --- a/include/linux/mmc/mmc.h +++ b/include/linux/mmc/mmc.h | |||
@@ -251,12 +251,21 @@ struct _mmc_csd { | |||
251 | * EXT_CSD fields | 251 | * EXT_CSD fields |
252 | */ | 252 | */ |
253 | 253 | ||
254 | #define EXT_CSD_BUS_WIDTH 183 /* R/W */ | 254 | #define EXT_CSD_ERASE_GROUP_DEF 175 /* R/W */ |
255 | #define EXT_CSD_HS_TIMING 185 /* R/W */ | 255 | #define EXT_CSD_ERASED_MEM_CONT 181 /* RO */ |
256 | #define EXT_CSD_CARD_TYPE 196 /* RO */ | 256 | #define EXT_CSD_BUS_WIDTH 183 /* R/W */ |
257 | #define EXT_CSD_REV 192 /* RO */ | 257 | #define EXT_CSD_HS_TIMING 185 /* R/W */ |
258 | #define EXT_CSD_SEC_CNT 212 /* RO, 4 bytes */ | 258 | #define EXT_CSD_REV 192 /* RO */ |
259 | #define EXT_CSD_S_A_TIMEOUT 217 | 259 | #define EXT_CSD_STRUCTURE 194 /* RO */ |
260 | #define EXT_CSD_CARD_TYPE 196 /* RO */ | ||
261 | #define EXT_CSD_SEC_CNT 212 /* RO, 4 bytes */ | ||
262 | #define EXT_CSD_S_A_TIMEOUT 217 /* RO */ | ||
263 | #define EXT_CSD_ERASE_TIMEOUT_MULT 223 /* RO */ | ||
264 | #define EXT_CSD_HC_ERASE_GRP_SIZE 224 /* RO */ | ||
265 | #define EXT_CSD_SEC_TRIM_MULT 229 /* RO */ | ||
266 | #define EXT_CSD_SEC_ERASE_MULT 230 /* RO */ | ||
267 | #define EXT_CSD_SEC_FEATURE_SUPPORT 231 /* RO */ | ||
268 | #define EXT_CSD_TRIM_MULT 232 /* RO */ | ||
260 | 269 | ||
261 | /* | 270 | /* |
262 | * EXT_CSD field definitions | 271 | * EXT_CSD field definitions |
@@ -274,6 +283,10 @@ struct _mmc_csd { | |||
274 | #define EXT_CSD_BUS_WIDTH_4 1 /* Card is in 4 bit mode */ | 283 | #define EXT_CSD_BUS_WIDTH_4 1 /* Card is in 4 bit mode */ |
275 | #define EXT_CSD_BUS_WIDTH_8 2 /* Card is in 8 bit mode */ | 284 | #define EXT_CSD_BUS_WIDTH_8 2 /* Card is in 8 bit mode */ |
276 | 285 | ||
286 | #define EXT_CSD_SEC_ER_EN BIT(0) | ||
287 | #define EXT_CSD_SEC_BD_BLK_EN BIT(2) | ||
288 | #define EXT_CSD_SEC_GB_CL_EN BIT(4) | ||
289 | |||
277 | /* | 290 | /* |
278 | * MMC_SWITCH access modes | 291 | * MMC_SWITCH access modes |
279 | */ | 292 | */ |
diff --git a/include/linux/mmc/sd.h b/include/linux/mmc/sd.h index f310062cffb4..3fd85e088cc3 100644 --- a/include/linux/mmc/sd.h +++ b/include/linux/mmc/sd.h | |||
@@ -21,8 +21,13 @@ | |||
21 | /* class 10 */ | 21 | /* class 10 */ |
22 | #define SD_SWITCH 6 /* adtc [31:0] See below R1 */ | 22 | #define SD_SWITCH 6 /* adtc [31:0] See below R1 */ |
23 | 23 | ||
24 | /* class 5 */ | ||
25 | #define SD_ERASE_WR_BLK_START 32 /* ac [31:0] data addr R1 */ | ||
26 | #define SD_ERASE_WR_BLK_END 33 /* ac [31:0] data addr R1 */ | ||
27 | |||
24 | /* Application commands */ | 28 | /* Application commands */ |
25 | #define SD_APP_SET_BUS_WIDTH 6 /* ac [1:0] bus width R1 */ | 29 | #define SD_APP_SET_BUS_WIDTH 6 /* ac [1:0] bus width R1 */ |
30 | #define SD_APP_SD_STATUS 13 /* adtc R1 */ | ||
26 | #define SD_APP_SEND_NUM_WR_BLKS 22 /* adtc R1 */ | 31 | #define SD_APP_SEND_NUM_WR_BLKS 22 /* adtc R1 */ |
27 | #define SD_APP_OP_COND 41 /* bcr [31:0] OCR R3 */ | 32 | #define SD_APP_OP_COND 41 /* bcr [31:0] OCR R3 */ |
28 | #define SD_APP_SEND_SCR 51 /* adtc R1 */ | 33 | #define SD_APP_SEND_SCR 51 /* adtc R1 */ |
diff --git a/include/linux/mmc/sdhci-spear.h b/include/linux/mmc/sdhci-spear.h new file mode 100644 index 000000000000..9188c973f3e1 --- /dev/null +++ b/include/linux/mmc/sdhci-spear.h | |||
@@ -0,0 +1,42 @@ | |||
1 | /* | ||
2 | * include/linux/mmc/sdhci-spear.h | ||
3 | * | ||
4 | * SDHCI declarations specific to ST SPEAr platform | ||
5 | * | ||
6 | * Copyright (C) 2010 ST Microelectronics | ||
7 | * Viresh Kumar<viresh.kumar@st.com> | ||
8 | * | ||
9 | * This file is licensed under the terms of the GNU General Public | ||
10 | * License version 2. This program is licensed "as is" without any | ||
11 | * warranty of any kind, whether express or implied. | ||
12 | */ | ||
13 | |||
14 | #ifndef MMC_SDHCI_SPEAR_H | ||
15 | #define MMC_SDHCI_SPEAR_H | ||
16 | |||
17 | #include <linux/platform_device.h> | ||
18 | /* | ||
19 | * struct sdhci_plat_data: spear sdhci platform data structure | ||
20 | * | ||
21 | * @card_power_gpio: gpio pin for enabling/disabling power to sdhci socket | ||
22 | * @power_active_high: if set, enable power to sdhci socket by setting | ||
23 | * card_power_gpio | ||
24 | * @power_always_enb: If set, then enable power on probe, otherwise enable only | ||
25 | * on card insertion and disable on card removal. | ||
26 | * card_int_gpio: gpio pin used for card detection | ||
27 | */ | ||
28 | struct sdhci_plat_data { | ||
29 | int card_power_gpio; | ||
30 | int power_active_high; | ||
31 | int power_always_enb; | ||
32 | int card_int_gpio; | ||
33 | }; | ||
34 | |||
35 | /* This function is used to set platform_data field of pdev->dev */ | ||
36 | static inline void | ||
37 | sdhci_set_plat_data(struct platform_device *pdev, struct sdhci_plat_data *data) | ||
38 | { | ||
39 | pdev->dev.platform_data = data; | ||
40 | } | ||
41 | |||
42 | #endif /* MMC_SDHCI_SPEAR_H */ | ||
diff --git a/include/linux/mmc/sdio.h b/include/linux/mmc/sdio.h index 0ebaef577ff5..245cdacee544 100644 --- a/include/linux/mmc/sdio.h +++ b/include/linux/mmc/sdio.h | |||
@@ -38,6 +38,8 @@ | |||
38 | * [8:0] Byte/block count | 38 | * [8:0] Byte/block count |
39 | */ | 39 | */ |
40 | 40 | ||
41 | #define R4_MEMORY_PRESENT (1 << 27) | ||
42 | |||
41 | /* | 43 | /* |
42 | SDIO status in R5 | 44 | SDIO status in R5 |
43 | Type | 45 | Type |
@@ -94,6 +96,8 @@ | |||
94 | 96 | ||
95 | #define SDIO_BUS_WIDTH_1BIT 0x00 | 97 | #define SDIO_BUS_WIDTH_1BIT 0x00 |
96 | #define SDIO_BUS_WIDTH_4BIT 0x02 | 98 | #define SDIO_BUS_WIDTH_4BIT 0x02 |
99 | #define SDIO_BUS_ECSI 0x20 /* Enable continuous SPI interrupt */ | ||
100 | #define SDIO_BUS_SCSI 0x40 /* Support continuous SPI interrupt */ | ||
97 | 101 | ||
98 | #define SDIO_BUS_ASYNC_INT 0x20 | 102 | #define SDIO_BUS_ASYNC_INT 0x20 |
99 | 103 | ||
diff --git a/include/linux/mmc/sdio_func.h b/include/linux/mmc/sdio_func.h index c6c0cceba5fe..31baaf82f458 100644 --- a/include/linux/mmc/sdio_func.h +++ b/include/linux/mmc/sdio_func.h | |||
@@ -145,6 +145,9 @@ extern void sdio_writew(struct sdio_func *func, u16 b, | |||
145 | extern void sdio_writel(struct sdio_func *func, u32 b, | 145 | extern void sdio_writel(struct sdio_func *func, u32 b, |
146 | unsigned int addr, int *err_ret); | 146 | unsigned int addr, int *err_ret); |
147 | 147 | ||
148 | extern u8 sdio_writeb_readb(struct sdio_func *func, u8 write_byte, | ||
149 | unsigned int addr, int *err_ret); | ||
150 | |||
148 | extern int sdio_memcpy_toio(struct sdio_func *func, unsigned int addr, | 151 | extern int sdio_memcpy_toio(struct sdio_func *func, unsigned int addr, |
149 | void *src, int count); | 152 | void *src, int count); |
150 | extern int sdio_writesb(struct sdio_func *func, unsigned int addr, | 153 | extern int sdio_writesb(struct sdio_func *func, unsigned int addr, |
diff --git a/include/linux/mmc/sh_mmcif.h b/include/linux/mmc/sh_mmcif.h new file mode 100644 index 000000000000..d4a2ebbdab4b --- /dev/null +++ b/include/linux/mmc/sh_mmcif.h | |||
@@ -0,0 +1,200 @@ | |||
1 | /* | ||
2 | * include/linux/mmc/sh_mmcif.h | ||
3 | * | ||
4 | * platform data for eMMC driver | ||
5 | * | ||
6 | * Copyright (C) 2010 Renesas Solutions Corp. | ||
7 | * | ||
8 | * This program is free software; you can redistribute it and/or modify | ||
9 | * it under the terms of the GNU General Public License as published by | ||
10 | * the Free Software Foundation; either version 2 of the License. | ||
11 | * | ||
12 | */ | ||
13 | |||
14 | #ifndef __SH_MMCIF_H__ | ||
15 | #define __SH_MMCIF_H__ | ||
16 | |||
17 | #include <linux/platform_device.h> | ||
18 | #include <linux/io.h> | ||
19 | |||
20 | /* | ||
21 | * MMCIF : CE_CLK_CTRL [19:16] | ||
22 | * 1000 : Peripheral clock / 512 | ||
23 | * 0111 : Peripheral clock / 256 | ||
24 | * 0110 : Peripheral clock / 128 | ||
25 | * 0101 : Peripheral clock / 64 | ||
26 | * 0100 : Peripheral clock / 32 | ||
27 | * 0011 : Peripheral clock / 16 | ||
28 | * 0010 : Peripheral clock / 8 | ||
29 | * 0001 : Peripheral clock / 4 | ||
30 | * 0000 : Peripheral clock / 2 | ||
31 | * 1111 : Peripheral clock (sup_pclk set '1') | ||
32 | */ | ||
33 | |||
34 | struct sh_mmcif_plat_data { | ||
35 | void (*set_pwr)(struct platform_device *pdev, int state); | ||
36 | void (*down_pwr)(struct platform_device *pdev); | ||
37 | u8 sup_pclk; /* 1 :SH7757, 0: SH7724/SH7372 */ | ||
38 | unsigned long caps; | ||
39 | u32 ocr; | ||
40 | }; | ||
41 | |||
42 | #define MMCIF_CE_CMD_SET 0x00000000 | ||
43 | #define MMCIF_CE_ARG 0x00000008 | ||
44 | #define MMCIF_CE_ARG_CMD12 0x0000000C | ||
45 | #define MMCIF_CE_CMD_CTRL 0x00000010 | ||
46 | #define MMCIF_CE_BLOCK_SET 0x00000014 | ||
47 | #define MMCIF_CE_CLK_CTRL 0x00000018 | ||
48 | #define MMCIF_CE_BUF_ACC 0x0000001C | ||
49 | #define MMCIF_CE_RESP3 0x00000020 | ||
50 | #define MMCIF_CE_RESP2 0x00000024 | ||
51 | #define MMCIF_CE_RESP1 0x00000028 | ||
52 | #define MMCIF_CE_RESP0 0x0000002C | ||
53 | #define MMCIF_CE_RESP_CMD12 0x00000030 | ||
54 | #define MMCIF_CE_DATA 0x00000034 | ||
55 | #define MMCIF_CE_INT 0x00000040 | ||
56 | #define MMCIF_CE_INT_MASK 0x00000044 | ||
57 | #define MMCIF_CE_HOST_STS1 0x00000048 | ||
58 | #define MMCIF_CE_HOST_STS2 0x0000004C | ||
59 | #define MMCIF_CE_VERSION 0x0000007C | ||
60 | |||
61 | extern inline u32 sh_mmcif_readl(void __iomem *addr, int reg) | ||
62 | { | ||
63 | return readl(addr + reg); | ||
64 | } | ||
65 | |||
66 | extern inline void sh_mmcif_writel(void __iomem *addr, int reg, u32 val) | ||
67 | { | ||
68 | writel(val, addr + reg); | ||
69 | } | ||
70 | |||
71 | #define SH_MMCIF_BBS 512 /* boot block size */ | ||
72 | |||
73 | extern inline void sh_mmcif_boot_cmd_send(void __iomem *base, | ||
74 | unsigned long cmd, unsigned long arg) | ||
75 | { | ||
76 | sh_mmcif_writel(base, MMCIF_CE_INT, 0); | ||
77 | sh_mmcif_writel(base, MMCIF_CE_ARG, arg); | ||
78 | sh_mmcif_writel(base, MMCIF_CE_CMD_SET, cmd); | ||
79 | } | ||
80 | |||
81 | extern inline int sh_mmcif_boot_cmd_poll(void __iomem *base, unsigned long mask) | ||
82 | { | ||
83 | unsigned long tmp; | ||
84 | int cnt; | ||
85 | |||
86 | for (cnt = 0; cnt < 1000000; cnt++) { | ||
87 | tmp = sh_mmcif_readl(base, MMCIF_CE_INT); | ||
88 | if (tmp & mask) { | ||
89 | sh_mmcif_writel(base, MMCIF_CE_INT, tmp & ~mask); | ||
90 | return 0; | ||
91 | } | ||
92 | } | ||
93 | |||
94 | return -1; | ||
95 | } | ||
96 | |||
97 | extern inline int sh_mmcif_boot_cmd(void __iomem *base, | ||
98 | unsigned long cmd, unsigned long arg) | ||
99 | { | ||
100 | sh_mmcif_boot_cmd_send(base, cmd, arg); | ||
101 | return sh_mmcif_boot_cmd_poll(base, 0x00010000); | ||
102 | } | ||
103 | |||
104 | extern inline int sh_mmcif_boot_do_read_single(void __iomem *base, | ||
105 | unsigned int block_nr, | ||
106 | unsigned long *buf) | ||
107 | { | ||
108 | int k; | ||
109 | |||
110 | /* CMD13 - Status */ | ||
111 | sh_mmcif_boot_cmd(base, 0x0d400000, 0x00010000); | ||
112 | |||
113 | if (sh_mmcif_readl(base, MMCIF_CE_RESP0) != 0x0900) | ||
114 | return -1; | ||
115 | |||
116 | /* CMD17 - Read */ | ||
117 | sh_mmcif_boot_cmd(base, 0x11480000, block_nr * SH_MMCIF_BBS); | ||
118 | if (sh_mmcif_boot_cmd_poll(base, 0x00100000) < 0) | ||
119 | return -1; | ||
120 | |||
121 | for (k = 0; k < (SH_MMCIF_BBS / 4); k++) | ||
122 | buf[k] = sh_mmcif_readl(base, MMCIF_CE_DATA); | ||
123 | |||
124 | return 0; | ||
125 | } | ||
126 | |||
127 | extern inline int sh_mmcif_boot_do_read(void __iomem *base, | ||
128 | unsigned long first_block, | ||
129 | unsigned long nr_blocks, | ||
130 | void *buf) | ||
131 | { | ||
132 | unsigned long k; | ||
133 | int ret = 0; | ||
134 | |||
135 | /* CMD16 - Set the block size */ | ||
136 | sh_mmcif_boot_cmd(base, 0x10400000, SH_MMCIF_BBS); | ||
137 | |||
138 | for (k = 0; !ret && k < nr_blocks; k++) | ||
139 | ret = sh_mmcif_boot_do_read_single(base, first_block + k, | ||
140 | buf + (k * SH_MMCIF_BBS)); | ||
141 | |||
142 | return ret; | ||
143 | } | ||
144 | |||
145 | extern inline void sh_mmcif_boot_init(void __iomem *base) | ||
146 | { | ||
147 | unsigned long tmp; | ||
148 | |||
149 | /* reset */ | ||
150 | tmp = sh_mmcif_readl(base, MMCIF_CE_VERSION); | ||
151 | sh_mmcif_writel(base, MMCIF_CE_VERSION, tmp | 0x80000000); | ||
152 | sh_mmcif_writel(base, MMCIF_CE_VERSION, tmp & ~0x80000000); | ||
153 | |||
154 | /* byte swap */ | ||
155 | sh_mmcif_writel(base, MMCIF_CE_BUF_ACC, 0x00010000); | ||
156 | |||
157 | /* Set block size in MMCIF hardware */ | ||
158 | sh_mmcif_writel(base, MMCIF_CE_BLOCK_SET, SH_MMCIF_BBS); | ||
159 | |||
160 | /* Enable the clock, set it to Bus clock/256 (about 325Khz)*/ | ||
161 | sh_mmcif_writel(base, MMCIF_CE_CLK_CTRL, 0x01072fff); | ||
162 | |||
163 | /* CMD0 */ | ||
164 | sh_mmcif_boot_cmd(base, 0x00000040, 0); | ||
165 | |||
166 | /* CMD1 - Get OCR */ | ||
167 | do { | ||
168 | sh_mmcif_boot_cmd(base, 0x01405040, 0x40300000); /* CMD1 */ | ||
169 | } while ((sh_mmcif_readl(base, MMCIF_CE_RESP0) & 0x80000000) | ||
170 | != 0x80000000); | ||
171 | |||
172 | /* CMD2 - Get CID */ | ||
173 | sh_mmcif_boot_cmd(base, 0x02806040, 0); | ||
174 | |||
175 | /* CMD3 - Set card relative address */ | ||
176 | sh_mmcif_boot_cmd(base, 0x03400040, 0x00010000); | ||
177 | } | ||
178 | |||
179 | extern inline void sh_mmcif_boot_slurp(void __iomem *base, | ||
180 | unsigned char *buf, | ||
181 | unsigned long no_bytes) | ||
182 | { | ||
183 | unsigned long tmp; | ||
184 | |||
185 | /* In data transfer mode: Set clock to Bus clock/4 (about 20Mhz) */ | ||
186 | sh_mmcif_writel(base, MMCIF_CE_CLK_CTRL, 0x01012fff); | ||
187 | |||
188 | /* CMD9 - Get CSD */ | ||
189 | sh_mmcif_boot_cmd(base, 0x09806000, 0x00010000); | ||
190 | |||
191 | /* CMD7 - Select the card */ | ||
192 | sh_mmcif_boot_cmd(base, 0x07400000, 0x00010000); | ||
193 | |||
194 | tmp = no_bytes / SH_MMCIF_BBS; | ||
195 | tmp += (no_bytes % SH_MMCIF_BBS) ? 1 : 0; | ||
196 | |||
197 | sh_mmcif_boot_do_read(base, 512, tmp, buf); | ||
198 | } | ||
199 | |||
200 | #endif /* __SH_MMCIF_H__ */ | ||