omap_hsmmc.c 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415
  1. /*
  2. * (C) Copyright 2008
  3. * Texas Instruments, <www.ti.com>
  4. * Sukumar Ghorai <s-ghorai@ti.com>
  5. *
  6. * See file CREDITS for list of people who contributed to this
  7. * project.
  8. *
  9. * This program is free software; you can redistribute it and/or
  10. * modify it under the terms of the GNU General Public License as
  11. * published by the Free Software Foundation's version 2 of
  12. * the License.
  13. *
  14. * This program is distributed in the hope that it will be useful,
  15. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  17. * GNU General Public License for more details.
  18. *
  19. * You should have received a copy of the GNU General Public License
  20. * along with this program; if not, write to the Free Software
  21. * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  22. * MA 02111-1307 USA
  23. */
  24. #include <config.h>
  25. #include <common.h>
  26. #include <mmc.h>
  27. #include <part.h>
  28. #include <i2c.h>
  29. #include <twl4030.h>
  30. #include <asm/io.h>
  31. #include <asm/arch/mmc_host_def.h>
  32. static int mmc_read_data(hsmmc_t *mmc_base, char *buf, unsigned int size);
  33. static int mmc_write_data(hsmmc_t *mmc_base, const char *buf, unsigned int siz);
  34. static struct mmc hsmmc_dev[2];
  35. unsigned char mmc_board_init(hsmmc_t *mmc_base)
  36. {
  37. #if defined(CONFIG_TWL4030_POWER)
  38. twl4030_power_mmc_init();
  39. #endif
  40. #if defined(CONFIG_OMAP34XX)
  41. t2_t *t2_base = (t2_t *)T2_BASE;
  42. struct prcm *prcm_base = (struct prcm *)PRCM_BASE;
  43. writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 |
  44. PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0,
  45. &t2_base->pbias_lite);
  46. writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL,
  47. &t2_base->devconf0);
  48. writel(readl(&t2_base->devconf1) | MMCSDIO2ADPCLKISEL,
  49. &t2_base->devconf1);
  50. writel(readl(&prcm_base->fclken1_core) |
  51. EN_MMC1 | EN_MMC2 | EN_MMC3,
  52. &prcm_base->fclken1_core);
  53. writel(readl(&prcm_base->iclken1_core) |
  54. EN_MMC1 | EN_MMC2 | EN_MMC3,
  55. &prcm_base->iclken1_core);
  56. #endif
  57. /* TODO add appropriate OMAP4 init - none currently necessary */
  58. return 0;
  59. }
  60. void mmc_init_stream(hsmmc_t *mmc_base)
  61. {
  62. writel(readl(&mmc_base->con) | INIT_INITSTREAM, &mmc_base->con);
  63. writel(MMC_CMD0, &mmc_base->cmd);
  64. while (!(readl(&mmc_base->stat) & CC_MASK))
  65. ;
  66. writel(CC_MASK, &mmc_base->stat)
  67. ;
  68. writel(MMC_CMD0, &mmc_base->cmd)
  69. ;
  70. while (!(readl(&mmc_base->stat) & CC_MASK))
  71. ;
  72. writel(readl(&mmc_base->con) & ~INIT_INITSTREAM, &mmc_base->con);
  73. }
  74. static int mmc_init_setup(struct mmc *mmc)
  75. {
  76. hsmmc_t *mmc_base = (hsmmc_t *)mmc->priv;
  77. unsigned int reg_val;
  78. unsigned int dsor;
  79. mmc_board_init(mmc_base);
  80. writel(readl(&mmc_base->sysconfig) | MMC_SOFTRESET,
  81. &mmc_base->sysconfig);
  82. while ((readl(&mmc_base->sysstatus) & RESETDONE) == 0)
  83. ;
  84. writel(readl(&mmc_base->sysctl) | SOFTRESETALL, &mmc_base->sysctl);
  85. while ((readl(&mmc_base->sysctl) & SOFTRESETALL) != 0x0)
  86. ;
  87. writel(DTW_1_BITMODE | SDBP_PWROFF | SDVS_3V0, &mmc_base->hctl);
  88. writel(readl(&mmc_base->capa) | VS30_3V0SUP | VS18_1V8SUP,
  89. &mmc_base->capa);
  90. reg_val = readl(&mmc_base->con) & RESERVED_MASK;
  91. writel(CTPL_MMC_SD | reg_val | WPP_ACTIVEHIGH | CDP_ACTIVEHIGH |
  92. MIT_CTO | DW8_1_4BITMODE | MODE_FUNC | STR_BLOCK |
  93. HR_NOHOSTRESP | INIT_NOINIT | NOOPENDRAIN, &mmc_base->con);
  94. dsor = 240;
  95. mmc_reg_out(&mmc_base->sysctl, (ICE_MASK | DTO_MASK | CEN_MASK),
  96. (ICE_STOP | DTO_15THDTO | CEN_DISABLE));
  97. mmc_reg_out(&mmc_base->sysctl, ICE_MASK | CLKD_MASK,
  98. (dsor << CLKD_OFFSET) | ICE_OSCILLATE);
  99. while ((readl(&mmc_base->sysctl) & ICS_MASK) == ICS_NOTREADY)
  100. ;
  101. writel(readl(&mmc_base->sysctl) | CEN_ENABLE, &mmc_base->sysctl);
  102. writel(readl(&mmc_base->hctl) | SDBP_PWRON, &mmc_base->hctl);
  103. writel(IE_BADA | IE_CERR | IE_DEB | IE_DCRC | IE_DTO | IE_CIE |
  104. IE_CEB | IE_CCRC | IE_CTO | IE_BRR | IE_BWR | IE_TC | IE_CC,
  105. &mmc_base->ie);
  106. mmc_init_stream(mmc_base);
  107. return 0;
  108. }
  109. static int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd,
  110. struct mmc_data *data)
  111. {
  112. hsmmc_t *mmc_base = (hsmmc_t *)mmc->priv;
  113. unsigned int flags, mmc_stat;
  114. unsigned int retry = 0x100000;
  115. while ((readl(&mmc_base->pstate) & DATI_MASK) == DATI_CMDDIS)
  116. ;
  117. writel(0xFFFFFFFF, &mmc_base->stat);
  118. while (readl(&mmc_base->stat))
  119. ;
  120. /*
  121. * CMDREG
  122. * CMDIDX[13:8] : Command index
  123. * DATAPRNT[5] : Data Present Select
  124. * ENCMDIDX[4] : Command Index Check Enable
  125. * ENCMDCRC[3] : Command CRC Check Enable
  126. * RSPTYP[1:0]
  127. * 00 = No Response
  128. * 01 = Length 136
  129. * 10 = Length 48
  130. * 11 = Length 48 Check busy after response
  131. */
  132. /* Delay added before checking the status of frq change
  133. * retry not supported by mmc.c(core file)
  134. */
  135. if (cmd->cmdidx == SD_CMD_APP_SEND_SCR)
  136. udelay(50000); /* wait 50 ms */
  137. if (!(cmd->resp_type & MMC_RSP_PRESENT))
  138. flags = 0;
  139. else if (cmd->resp_type & MMC_RSP_136)
  140. flags = RSP_TYPE_LGHT136 | CICE_NOCHECK;
  141. else if (cmd->resp_type & MMC_RSP_BUSY)
  142. flags = RSP_TYPE_LGHT48B;
  143. else
  144. flags = RSP_TYPE_LGHT48;
  145. /* enable default flags */
  146. flags = flags | (CMD_TYPE_NORMAL | CICE_NOCHECK | CCCE_NOCHECK |
  147. MSBS_SGLEBLK | ACEN_DISABLE | BCE_DISABLE | DE_DISABLE);
  148. if (cmd->resp_type & MMC_RSP_CRC)
  149. flags |= CCCE_CHECK;
  150. if (cmd->resp_type & MMC_RSP_OPCODE)
  151. flags |= CICE_CHECK;
  152. if (data) {
  153. if ((cmd->cmdidx == MMC_CMD_READ_MULTIPLE_BLOCK) ||
  154. (cmd->cmdidx == MMC_CMD_WRITE_MULTIPLE_BLOCK)) {
  155. flags |= (MSBS_MULTIBLK | BCE_ENABLE);
  156. data->blocksize = 512;
  157. writel(data->blocksize | (data->blocks << 16),
  158. &mmc_base->blk);
  159. } else
  160. writel(data->blocksize | NBLK_STPCNT, &mmc_base->blk);
  161. if (data->flags & MMC_DATA_READ)
  162. flags |= (DP_DATA | DDIR_READ);
  163. else
  164. flags |= (DP_DATA | DDIR_WRITE);
  165. }
  166. writel(cmd->cmdarg, &mmc_base->arg);
  167. writel((cmd->cmdidx << 24) | flags, &mmc_base->cmd);
  168. do {
  169. mmc_stat = readl(&mmc_base->stat);
  170. retry--;
  171. } while ((mmc_stat == 0) && (retry > 0));
  172. if (retry == 0) {
  173. printf("%s : timeout: No status update\n", __func__);
  174. return TIMEOUT;
  175. }
  176. if ((mmc_stat & IE_CTO) != 0)
  177. return TIMEOUT;
  178. else if ((mmc_stat & ERRI_MASK) != 0)
  179. return -1;
  180. if (mmc_stat & CC_MASK) {
  181. writel(CC_MASK, &mmc_base->stat);
  182. if (cmd->resp_type & MMC_RSP_PRESENT) {
  183. if (cmd->resp_type & MMC_RSP_136) {
  184. /* response type 2 */
  185. cmd->response[3] = readl(&mmc_base->rsp10);
  186. cmd->response[2] = readl(&mmc_base->rsp32);
  187. cmd->response[1] = readl(&mmc_base->rsp54);
  188. cmd->response[0] = readl(&mmc_base->rsp76);
  189. } else
  190. /* response types 1, 1b, 3, 4, 5, 6 */
  191. cmd->response[0] = readl(&mmc_base->rsp10);
  192. }
  193. }
  194. if (data && (data->flags & MMC_DATA_READ)) {
  195. mmc_read_data(mmc_base, data->dest,
  196. data->blocksize * data->blocks);
  197. } else if (data && (data->flags & MMC_DATA_WRITE)) {
  198. mmc_write_data(mmc_base, data->src,
  199. data->blocksize * data->blocks);
  200. }
  201. return 0;
  202. }
  203. static int mmc_read_data(hsmmc_t *mmc_base, char *buf, unsigned int size)
  204. {
  205. unsigned int *output_buf = (unsigned int *)buf;
  206. unsigned int mmc_stat;
  207. unsigned int count;
  208. /*
  209. * Start Polled Read
  210. */
  211. count = (size > MMCSD_SECTOR_SIZE) ? MMCSD_SECTOR_SIZE : size;
  212. count /= 4;
  213. while (size) {
  214. do {
  215. mmc_stat = readl(&mmc_base->stat);
  216. } while (mmc_stat == 0);
  217. if ((mmc_stat & ERRI_MASK) != 0)
  218. return 1;
  219. if (mmc_stat & BRR_MASK) {
  220. unsigned int k;
  221. writel(readl(&mmc_base->stat) | BRR_MASK,
  222. &mmc_base->stat);
  223. for (k = 0; k < count; k++) {
  224. *output_buf = readl(&mmc_base->data);
  225. output_buf++;
  226. }
  227. size -= (count*4);
  228. }
  229. if (mmc_stat & BWR_MASK)
  230. writel(readl(&mmc_base->stat) | BWR_MASK,
  231. &mmc_base->stat);
  232. if (mmc_stat & TC_MASK) {
  233. writel(readl(&mmc_base->stat) | TC_MASK,
  234. &mmc_base->stat);
  235. break;
  236. }
  237. }
  238. return 0;
  239. }
  240. static int mmc_write_data(hsmmc_t *mmc_base, const char *buf, unsigned int size)
  241. {
  242. unsigned int *input_buf = (unsigned int *)buf;
  243. unsigned int mmc_stat;
  244. unsigned int count;
  245. /*
  246. * Start Polled Read
  247. */
  248. count = (size > MMCSD_SECTOR_SIZE) ? MMCSD_SECTOR_SIZE : size;
  249. count /= 4;
  250. while (size) {
  251. do {
  252. mmc_stat = readl(&mmc_base->stat);
  253. } while (mmc_stat == 0);
  254. if ((mmc_stat & ERRI_MASK) != 0)
  255. return 1;
  256. if (mmc_stat & BWR_MASK) {
  257. unsigned int k;
  258. writel(readl(&mmc_base->stat) | BWR_MASK,
  259. &mmc_base->stat);
  260. for (k = 0; k < count; k++) {
  261. writel(*input_buf, &mmc_base->data);
  262. input_buf++;
  263. }
  264. size -= (count*4);
  265. }
  266. if (mmc_stat & BRR_MASK)
  267. writel(readl(&mmc_base->stat) | BRR_MASK,
  268. &mmc_base->stat);
  269. if (mmc_stat & TC_MASK) {
  270. writel(readl(&mmc_base->stat) | TC_MASK,
  271. &mmc_base->stat);
  272. break;
  273. }
  274. }
  275. return 0;
  276. }
  277. static void mmc_set_ios(struct mmc *mmc)
  278. {
  279. hsmmc_t *mmc_base = (hsmmc_t *)mmc->priv;
  280. unsigned int dsor = 0;
  281. /* configue bus width */
  282. switch (mmc->bus_width) {
  283. case 8:
  284. writel(readl(&mmc_base->con) | DTW_8_BITMODE,
  285. &mmc_base->con);
  286. break;
  287. case 4:
  288. writel(readl(&mmc_base->con) & ~DTW_8_BITMODE,
  289. &mmc_base->con);
  290. writel(readl(&mmc_base->hctl) | DTW_4_BITMODE,
  291. &mmc_base->hctl);
  292. break;
  293. case 1:
  294. default:
  295. writel(readl(&mmc_base->con) & ~DTW_8_BITMODE,
  296. &mmc_base->con);
  297. writel(readl(&mmc_base->hctl) & ~DTW_4_BITMODE,
  298. &mmc_base->hctl);
  299. break;
  300. }
  301. /* configure clock with 96Mhz system clock.
  302. */
  303. if (mmc->clock != 0) {
  304. dsor = (MMC_CLOCK_REFERENCE * 1000000 / mmc->clock);
  305. if ((MMC_CLOCK_REFERENCE * 1000000) / dsor > mmc->clock)
  306. dsor++;
  307. }
  308. mmc_reg_out(&mmc_base->sysctl, (ICE_MASK | DTO_MASK | CEN_MASK),
  309. (ICE_STOP | DTO_15THDTO | CEN_DISABLE));
  310. mmc_reg_out(&mmc_base->sysctl, ICE_MASK | CLKD_MASK,
  311. (dsor << CLKD_OFFSET) | ICE_OSCILLATE);
  312. while ((readl(&mmc_base->sysctl) & ICS_MASK) == ICS_NOTREADY)
  313. ;
  314. writel(readl(&mmc_base->sysctl) | CEN_ENABLE, &mmc_base->sysctl);
  315. }
  316. int omap_mmc_init(int dev_index)
  317. {
  318. struct mmc *mmc;
  319. mmc = &hsmmc_dev[dev_index];
  320. sprintf(mmc->name, "OMAP SD/MMC");
  321. mmc->send_cmd = mmc_send_cmd;
  322. mmc->set_ios = mmc_set_ios;
  323. mmc->init = mmc_init_setup;
  324. switch (dev_index) {
  325. case 0:
  326. mmc->priv = (hsmmc_t *)OMAP_HSMMC1_BASE;
  327. break;
  328. case 1:
  329. mmc->priv = (hsmmc_t *)OMAP_HSMMC2_BASE;
  330. break;
  331. case 2:
  332. mmc->priv = (hsmmc_t *)OMAP_HSMMC3_BASE;
  333. break;
  334. default:
  335. mmc->priv = (hsmmc_t *)OMAP_HSMMC1_BASE;
  336. return 1;
  337. }
  338. mmc->voltages = MMC_VDD_32_33 | MMC_VDD_33_34 | MMC_VDD_165_195;
  339. mmc->host_caps = MMC_MODE_4BIT | MMC_MODE_HS_52MHz | MMC_MODE_HS;
  340. mmc->f_min = 400000;
  341. mmc->f_max = 52000000;
  342. mmc_register(mmc);
  343. return 0;
  344. }