0003-add-mmc-support.patch 46 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664
  1. From bd36739e77669e8df45c38f6acfe2cea511534d9 Mon Sep 17 00:00:00 2001
  2. From: Xiangfu <xiangfu@openmobilefree.net>
  3. Date: Wed, 10 Oct 2012 18:19:41 +0800
  4. Subject: [PATCH 3/6] add mmc support
  5. ---
  6. arch/mips/include/asm/jz4740.h | 166 ++++++
  7. board/qi/qi_lb60/qi_lb60.c | 9 +-
  8. drivers/mmc/Makefile | 1 +
  9. drivers/mmc/jz_mmc.c | 1179 ++++++++++++++++++++++++++++++++++++++++
  10. drivers/mmc/jz_mmc.h | 176 ++++++
  11. include/configs/qi_lb60.h | 9 +
  12. include/mmc.h | 40 ++
  13. 7 files changed, 1578 insertions(+), 2 deletions(-)
  14. create mode 100644 drivers/mmc/jz_mmc.c
  15. create mode 100644 drivers/mmc/jz_mmc.h
  16. diff --git a/arch/mips/include/asm/jz4740.h b/arch/mips/include/asm/jz4740.h
  17. index 7a7cfff..68287fb 100644
  18. --- a/arch/mips/include/asm/jz4740.h
  19. +++ b/arch/mips/include/asm/jz4740.h
  20. @@ -1146,5 +1146,171 @@ extern void sdram_init(void);
  21. extern void calc_clocks(void);
  22. extern void rtc_init(void);
  23. +/*************************************************************************
  24. + * MSC
  25. + *************************************************************************/
  26. +#define REG8(addr) *((volatile u8 *)(addr))
  27. +#define REG16(addr) *((volatile u16 *)(addr))
  28. +#define REG32(addr) *((volatile u32 *)(addr))
  29. +
  30. +#define CPM_BASE 0xB0000000
  31. +#define CPM_CPCCR (CPM_BASE+0x00)
  32. +#define CPM_MSCCDR (CPM_BASE+0x68)
  33. +#define REG_CPM_MSCCDR REG32(CPM_MSCCDR)
  34. +#define REG_CPM_CPCCR REG32(CPM_CPCCR)
  35. +
  36. +#define MSC_BASE 0xB0021000
  37. +
  38. +#define MSC_STRPCL (MSC_BASE + 0x000)
  39. +#define MSC_STAT (MSC_BASE + 0x004)
  40. +#define MSC_CLKRT (MSC_BASE + 0x008)
  41. +#define MSC_CMDAT (MSC_BASE + 0x00C)
  42. +#define MSC_RESTO (MSC_BASE + 0x010)
  43. +#define MSC_RDTO (MSC_BASE + 0x014)
  44. +#define MSC_BLKLEN (MSC_BASE + 0x018)
  45. +#define MSC_NOB (MSC_BASE + 0x01C)
  46. +#define MSC_SNOB (MSC_BASE + 0x020)
  47. +#define MSC_IMASK (MSC_BASE + 0x024)
  48. +#define MSC_IREG (MSC_BASE + 0x028)
  49. +#define MSC_CMD (MSC_BASE + 0x02C)
  50. +#define MSC_ARG (MSC_BASE + 0x030)
  51. +#define MSC_RES (MSC_BASE + 0x034)
  52. +#define MSC_RXFIFO (MSC_BASE + 0x038)
  53. +#define MSC_TXFIFO (MSC_BASE + 0x03C)
  54. +
  55. +#define REG_MSC_STRPCL REG16(MSC_STRPCL)
  56. +#define REG_MSC_STAT REG32(MSC_STAT)
  57. +#define REG_MSC_CLKRT REG16(MSC_CLKRT)
  58. +#define REG_MSC_CMDAT REG32(MSC_CMDAT)
  59. +#define REG_MSC_RESTO REG16(MSC_RESTO)
  60. +#define REG_MSC_RDTO REG16(MSC_RDTO)
  61. +#define REG_MSC_BLKLEN REG16(MSC_BLKLEN)
  62. +#define REG_MSC_NOB REG16(MSC_NOB)
  63. +#define REG_MSC_SNOB REG16(MSC_SNOB)
  64. +#define REG_MSC_IMASK REG16(MSC_IMASK)
  65. +#define REG_MSC_IREG REG16(MSC_IREG)
  66. +#define REG_MSC_CMD REG8(MSC_CMD)
  67. +#define REG_MSC_ARG REG32(MSC_ARG)
  68. +#define REG_MSC_RES REG16(MSC_RES)
  69. +#define REG_MSC_RXFIFO REG32(MSC_RXFIFO)
  70. +#define REG_MSC_TXFIFO REG32(MSC_TXFIFO)
  71. +
  72. +/* MSC Clock and Control Register (MSC_STRPCL) */
  73. +
  74. +#define MSC_STRPCL_EXIT_MULTIPLE (1 << 7)
  75. +#define MSC_STRPCL_EXIT_TRANSFER (1 << 6)
  76. +#define MSC_STRPCL_START_READWAIT (1 << 5)
  77. +#define MSC_STRPCL_STOP_READWAIT (1 << 4)
  78. +#define MSC_STRPCL_RESET (1 << 3)
  79. +#define MSC_STRPCL_START_OP (1 << 2)
  80. +#define MSC_STRPCL_CLOCK_CONTROL_BIT 0
  81. +#define MSC_STRPCL_CLOCK_CONTROL_MASK (0x3 << MSC_STRPCL_CLOCK_CONTROL_BIT)
  82. + #define MSC_STRPCL_CLOCK_CONTROL_STOP (0x1 << MSC_STRPCL_CLOCK_CONTROL_BIT) /* Stop MMC/SD clock */
  83. + #define MSC_STRPCL_CLOCK_CONTROL_START (0x2 << MSC_STRPCL_CLOCK_CONTROL_BIT) /* Start MMC/SD clock */
  84. +
  85. +/* MSC Status Register (MSC_STAT) */
  86. +
  87. +#define MSC_STAT_IS_RESETTING (1 << 15)
  88. +#define MSC_STAT_SDIO_INT_ACTIVE (1 << 14)
  89. +#define MSC_STAT_PRG_DONE (1 << 13)
  90. +#define MSC_STAT_DATA_TRAN_DONE (1 << 12)
  91. +#define MSC_STAT_END_CMD_RES (1 << 11)
  92. +#define MSC_STAT_DATA_FIFO_AFULL (1 << 10)
  93. +#define MSC_STAT_IS_READWAIT (1 << 9)
  94. +#define MSC_STAT_CLK_EN (1 << 8)
  95. +#define MSC_STAT_DATA_FIFO_FULL (1 << 7)
  96. +#define MSC_STAT_DATA_FIFO_EMPTY (1 << 6)
  97. +#define MSC_STAT_CRC_RES_ERR (1 << 5)
  98. +#define MSC_STAT_CRC_READ_ERROR (1 << 4)
  99. +#define MSC_STAT_CRC_WRITE_ERROR_BIT 2
  100. +#define MSC_STAT_CRC_WRITE_ERROR_MASK (0x3 << MSC_STAT_CRC_WRITE_ERROR_BIT)
  101. + #define MSC_STAT_CRC_WRITE_ERROR_NO (0 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* No error on transmission of data */
  102. + #define MSC_STAT_CRC_WRITE_ERROR (1 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* Card observed erroneous transmission of data */
  103. + #define MSC_STAT_CRC_WRITE_ERROR_NOSTS (2 << MSC_STAT_CRC_WRITE_ERROR_BIT) /* No CRC status is sent back */
  104. +#define MSC_STAT_TIME_OUT_RES (1 << 1)
  105. +#define MSC_STAT_TIME_OUT_READ (1 << 0)
  106. +
  107. +/* MSC Bus Clock Control Register (MSC_CLKRT) */
  108. +
  109. +#define MSC_CLKRT_CLK_RATE_BIT 0
  110. +#define MSC_CLKRT_CLK_RATE_MASK (0x7 << MSC_CLKRT_CLK_RATE_BIT)
  111. + #define MSC_CLKRT_CLK_RATE_DIV_1 (0x0 << MSC_CLKRT_CLK_RATE_BIT) /* CLK_SRC */
  112. + #define MSC_CLKRT_CLK_RATE_DIV_2 (0x1 << MSC_CLKRT_CLK_RATE_BIT) /* 1/2 of CLK_SRC */
  113. + #define MSC_CLKRT_CLK_RATE_DIV_4 (0x2 << MSC_CLKRT_CLK_RATE_BIT) /* 1/4 of CLK_SRC */
  114. + #define MSC_CLKRT_CLK_RATE_DIV_8 (0x3 << MSC_CLKRT_CLK_RATE_BIT) /* 1/8 of CLK_SRC */
  115. + #define MSC_CLKRT_CLK_RATE_DIV_16 (0x4 << MSC_CLKRT_CLK_RATE_BIT) /* 1/16 of CLK_SRC */
  116. + #define MSC_CLKRT_CLK_RATE_DIV_32 (0x5 << MSC_CLKRT_CLK_RATE_BIT) /* 1/32 of CLK_SRC */
  117. + #define MSC_CLKRT_CLK_RATE_DIV_64 (0x6 << MSC_CLKRT_CLK_RATE_BIT) /* 1/64 of CLK_SRC */
  118. + #define MSC_CLKRT_CLK_RATE_DIV_128 (0x7 << MSC_CLKRT_CLK_RATE_BIT) /* 1/128 of CLK_SRC */
  119. +
  120. +/* MSC Command Sequence Control Register (MSC_CMDAT) */
  121. +
  122. +#define MSC_CMDAT_IO_ABORT (1 << 11)
  123. +#define MSC_CMDAT_BUS_WIDTH_BIT 9
  124. +#define MSC_CMDAT_BUS_WIDTH_MASK (0x3 << MSC_CMDAT_BUS_WIDTH_BIT)
  125. +#define MSC_CMDAT_BUS_WIDTH_1BIT (0x0 << MSC_CMDAT_BUS_WIDTH_BIT)
  126. +#define MSC_CMDAT_BUS_WIDTH_4BIT (0x2 << MSC_CMDAT_BUS_WIDTH_BIT)
  127. +#define MSC_CMDAT_DMA_EN (1 << 8)
  128. +#define MSC_CMDAT_INIT (1 << 7)
  129. +#define MSC_CMDAT_BUSY (1 << 6)
  130. +#define MSC_CMDAT_STREAM_BLOCK (1 << 5)
  131. +#define MSC_CMDAT_WRITE (1 << 4)
  132. +#define MSC_CMDAT_READ (0 << 4)
  133. +#define MSC_CMDAT_DATA_EN (1 << 3)
  134. +#define MSC_CMDAT_RESPONSE_BIT 0
  135. +#define MSC_CMDAT_RESPONSE_MASK (0x7 << MSC_CMDAT_RESPONSE_BIT)
  136. +#define MSC_CMDAT_RESPONSE_NONE (0x0 << MSC_CMDAT_RESPONSE_BIT)
  137. +#define MSC_CMDAT_RESPONSE_R1 (0x1 << MSC_CMDAT_RESPONSE_BIT)
  138. +#define MSC_CMDAT_RESPONSE_R2 (0x2 << MSC_CMDAT_RESPONSE_BIT)
  139. +#define MSC_CMDAT_RESPONSE_R3 (0x3 << MSC_CMDAT_RESPONSE_BIT)
  140. +#define MSC_CMDAT_RESPONSE_R4 (0x4 << MSC_CMDAT_RESPONSE_BIT)
  141. +#define MSC_CMDAT_RESPONSE_R5 (0x5 << MSC_CMDAT_RESPONSE_BIT)
  142. +#define MSC_CMDAT_RESPONSE_R6 (0x6 << MSC_CMDAT_RESPONSE_BIT)
  143. +
  144. +/* MSC Interrupts Mask Register (MSC_IMASK) */
  145. +#define MSC_IMASK_SDIO (1 << 7)
  146. +#define MSC_IMASK_TXFIFO_WR_REQ (1 << 6)
  147. +#define MSC_IMASK_RXFIFO_RD_REQ (1 << 5)
  148. +#define MSC_IMASK_END_CMD_RES (1 << 2)
  149. +#define MSC_IMASK_PRG_DONE (1 << 1)
  150. +#define MSC_IMASK_DATA_TRAN_DONE (1 << 0)
  151. +
  152. +
  153. +/* MSC Interrupts Status Register (MSC_IREG) */
  154. +#define MSC_IREG_SDIO (1 << 7)
  155. +#define MSC_IREG_TXFIFO_WR_REQ (1 << 6)
  156. +#define MSC_IREG_RXFIFO_RD_REQ (1 << 5)
  157. +#define MSC_IREG_END_CMD_RES (1 << 2)
  158. +#define MSC_IREG_PRG_DONE (1 << 1)
  159. +#define MSC_IREG_DATA_TRAN_DONE (1 << 0)
  160. +
  161. +static __inline__ unsigned int __cpm_get_pllout2(void)
  162. +{
  163. + if (REG_CPM_CPCCR & CPM_CPCCR_PCS)
  164. + return __cpm_get_pllout();
  165. + else
  166. + return __cpm_get_pllout()/2;
  167. +}
  168. +
  169. +static inline void __cpm_select_msc_clk(int sd)
  170. +{
  171. + unsigned int pllout2 = __cpm_get_pllout2();
  172. + unsigned int div = 0;
  173. +
  174. + if (sd) {
  175. + div = pllout2 / 24000000;
  176. + }
  177. + else {
  178. + div = pllout2 / 16000000;
  179. + }
  180. +
  181. + REG_CPM_MSCCDR = div - 1;
  182. +}
  183. +#define __msc_reset() \
  184. +do { \
  185. + REG_MSC_STRPCL = MSC_STRPCL_RESET; \
  186. + while (REG_MSC_STAT & MSC_STAT_IS_RESETTING); \
  187. +} while (0)
  188. +
  189. #endif /* !__ASSEMBLY__ */
  190. #endif /* __JZ4740_H__ */
  191. diff --git a/board/qi/qi_lb60/qi_lb60.c b/board/qi/qi_lb60/qi_lb60.c
  192. index 3bd4e2f..a2ba648 100644
  193. --- a/board/qi/qi_lb60/qi_lb60.c
  194. +++ b/board/qi/qi_lb60/qi_lb60.c
  195. @@ -40,8 +40,13 @@ static void gpio_init(void)
  196. __gpio_clear_pin(GPIO_KEYOUT_BASE + i);
  197. }
  198. - __gpio_as_input(GPIO_KEYIN_8);
  199. - __gpio_enable_pull(GPIO_KEYIN_8);
  200. + if (__gpio_get_pin(GPIO_KEYIN_BASE + 2) == 0){
  201. + printf("[S] pressed, enable UART0\n");
  202. + __gpio_as_uart0();
  203. + } else {
  204. + __gpio_as_input(GPIO_KEYIN_8);
  205. + __gpio_enable_pull(GPIO_KEYIN_8);
  206. + }
  207. /* enable the TP4, TP5 as UART0 */
  208. __gpio_jtag_to_uart0();
  209. diff --git a/drivers/mmc/Makefile b/drivers/mmc/Makefile
  210. index 565ba6a..3c717b1 100644
  211. --- a/drivers/mmc/Makefile
  212. +++ b/drivers/mmc/Makefile
  213. @@ -47,6 +47,7 @@ COBJS-$(CONFIG_SDHCI) += sdhci.o
  214. COBJS-$(CONFIG_S5P_SDHCI) += s5p_sdhci.o
  215. COBJS-$(CONFIG_SH_MMCIF) += sh_mmcif.o
  216. COBJS-$(CONFIG_TEGRA_MMC) += tegra_mmc.o
  217. +COBJS-$(CONFIG_JZ4740_MMC) += jz_mmc.o
  218. COBJS := $(COBJS-y)
  219. SRCS := $(COBJS:.o=.c)
  220. diff --git a/drivers/mmc/jz_mmc.c b/drivers/mmc/jz_mmc.c
  221. new file mode 100644
  222. index 0000000..642cecc
  223. --- /dev/null
  224. +++ b/drivers/mmc/jz_mmc.c
  225. @@ -0,0 +1,1179 @@
  226. +/*
  227. + * (C) Copyright 2003
  228. + * Kyle Harris, Nexus Technologies, Inc. kharris@nexus-tech.net
  229. + *
  230. + * See file CREDITS for list of people who contributed to this
  231. + * project.
  232. + *
  233. + * This program is free software; you can redistribute it and/or
  234. + * modify it under the terms of the GNU General Public License as
  235. + * published by the Free Software Foundation; either version 2 of
  236. + * the License, or (at your option) any later version.
  237. + *
  238. + * This program is distributed in the hope that it will be useful,
  239. + * but WITHOUT ANY WARRANTY; without even the implied warranty of
  240. + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  241. + * GNU General Public License for more details.
  242. + *
  243. + * You should have received a copy of the GNU General Public License
  244. + * along with this program; if not, write to the Free Software
  245. + * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
  246. + * MA 02111-1307 USA
  247. + */
  248. +
  249. +#include <config.h>
  250. +#include <common.h>
  251. +#include <part.h>
  252. +#include <mmc.h>
  253. +
  254. +#include <asm/io.h>
  255. +#include <asm/jz4740.h>
  256. +#include "jz_mmc.h"
  257. +
  258. +static int sd2_0 = 0;
  259. +static int mmc_ready = 0;
  260. +static int use_4bit; /* Use 4-bit data bus */
  261. +/*
  262. + * MMC Events
  263. + */
  264. +#define MMC_EVENT_NONE 0x00 /* No events */
  265. +#define MMC_EVENT_RX_DATA_DONE 0x01 /* Rx data done */
  266. +#define MMC_EVENT_TX_DATA_DONE 0x02 /* Tx data done */
  267. +#define MMC_EVENT_PROG_DONE 0x04 /* Programming is done */
  268. +
  269. +
  270. +#define MMC_IRQ_MASK() \
  271. +do { \
  272. + REG_MSC_IMASK = 0xffff; \
  273. + REG_MSC_IREG = 0xffff; \
  274. +} while (0)
  275. +
  276. +/*
  277. + * GPIO definition
  278. + */
  279. +#if defined(CONFIG_SAKC)
  280. +
  281. +#define __msc_init_io() \
  282. +do { \
  283. + __gpio_as_input(GPIO_SD_CD_N); \
  284. +} while (0)
  285. +
  286. +#else
  287. +#define __msc_init_io() \
  288. +do { \
  289. + __gpio_as_output(GPIO_SD_VCC_EN_N); \
  290. + __gpio_as_input(GPIO_SD_CD_N); \
  291. +} while (0)
  292. +
  293. +#define __msc_enable_power() \
  294. +do { \
  295. + __gpio_clear_pin(GPIO_SD_VCC_EN_N); \
  296. +} while (0)
  297. +
  298. +#define __msc_disable_power() \
  299. +do { \
  300. + __gpio_set_pin(GPIO_SD_VCC_EN_N); \
  301. +} while (0)
  302. +
  303. +#endif /* CONFIG_SAKE */
  304. +
  305. +#define __msc_card_detected() \
  306. +({ \
  307. + int detected = 1; \
  308. + __gpio_as_input(GPIO_SD_CD_N); \
  309. + __gpio_disable_pull(GPIO_SD_CD_N); \
  310. + if (!__gpio_get_pin(GPIO_SD_CD_N)) \
  311. + detected = 0; \
  312. + detected; \
  313. +})
  314. +
  315. +/*
  316. + * Local functions
  317. + */
  318. +
  319. +extern int
  320. +fat_register_device(block_dev_desc_t *dev_desc, int part_no);
  321. +
  322. +static block_dev_desc_t mmc_dev;
  323. +
  324. +block_dev_desc_t * mmc_get_dev(int dev)
  325. +{
  326. + return ((block_dev_desc_t *)&mmc_dev);
  327. +}
  328. +
  329. +/* Stop the MMC clock and wait while it happens */
  330. +static inline int jz_mmc_stop_clock(void)
  331. +{
  332. + int timeout = 1000;
  333. +
  334. + REG_MSC_STRPCL = MSC_STRPCL_CLOCK_CONTROL_STOP;
  335. +
  336. + while (timeout && (REG_MSC_STAT & MSC_STAT_CLK_EN)) {
  337. + timeout--;
  338. + if (timeout == 0)
  339. + return MMC_ERROR_TIMEOUT;
  340. + udelay(1);
  341. + }
  342. + return MMC_NO_ERROR;
  343. +}
  344. +
  345. +/* Start the MMC clock and operation */
  346. +static inline int jz_mmc_start_clock(void)
  347. +{
  348. + REG_MSC_STRPCL = MSC_STRPCL_CLOCK_CONTROL_START | MSC_STRPCL_START_OP;
  349. + return MMC_NO_ERROR;
  350. +}
  351. +
  352. +static inline u32 jz_mmc_calc_clkrt(int is_sd, u32 rate)
  353. +{
  354. + u32 clkrt = 0;
  355. + u32 clk_src = is_sd ? 24000000 : 16000000;
  356. +
  357. + while (rate < clk_src) {
  358. + clkrt ++;
  359. + clk_src >>= 1;
  360. + }
  361. +
  362. + return clkrt;
  363. +}
  364. +
  365. +/* Set the MMC clock frequency */
  366. +void jz_mmc_set_clock(int sd, u32 rate)
  367. +{
  368. + jz_mmc_stop_clock();
  369. +
  370. + /* Select clock source of MSC */
  371. + __cpm_select_msc_clk(sd);
  372. +
  373. + /* Set clock dividor of MSC */
  374. + REG_MSC_CLKRT = jz_mmc_calc_clkrt(sd, rate);
  375. +}
  376. +
  377. +static int jz_mmc_check_status(struct mmc_request *request)
  378. +{
  379. + u32 status = REG_MSC_STAT;
  380. +
  381. + /* Checking for response or data timeout */
  382. + if (status & (MSC_STAT_TIME_OUT_RES | MSC_STAT_TIME_OUT_READ)) {
  383. + printf("MMC/SD timeout, MMC_STAT 0x%x CMD %d\n", status, request->cmd);
  384. + return MMC_ERROR_TIMEOUT;
  385. + }
  386. +
  387. + /* Checking for CRC error */
  388. + if (status & (MSC_STAT_CRC_READ_ERROR | MSC_STAT_CRC_WRITE_ERROR | MSC_STAT_CRC_RES_ERR)) {
  389. + printf("MMC/CD CRC error, MMC_STAT 0x%x\n", status);
  390. + return MMC_ERROR_CRC;
  391. + }
  392. +
  393. + return MMC_NO_ERROR;
  394. +}
  395. +
  396. +/* Obtain response to the command and store it to response buffer */
  397. +static void jz_mmc_get_response(struct mmc_request *request)
  398. +{
  399. + int i;
  400. + u8 *buf;
  401. + u32 data;
  402. +
  403. + debug("fetch response for request %d, cmd %d\n",
  404. + request->rtype, request->cmd);
  405. +
  406. + buf = request->response;
  407. + request->result = MMC_NO_ERROR;
  408. +
  409. + switch (request->rtype) {
  410. + case RESPONSE_R1: case RESPONSE_R1B: case RESPONSE_R6:
  411. + case RESPONSE_R3: case RESPONSE_R4: case RESPONSE_R5:
  412. + {
  413. + data = REG_MSC_RES;
  414. + buf[0] = (data >> 8) & 0xff;
  415. + buf[1] = data & 0xff;
  416. + data = REG_MSC_RES;
  417. + buf[2] = (data >> 8) & 0xff;
  418. + buf[3] = data & 0xff;
  419. + data = REG_MSC_RES;
  420. + buf[4] = data & 0xff;
  421. +
  422. + debug("request %d, response [%02x %02x %02x %02x %02x]\n",
  423. + request->rtype, buf[0], buf[1], buf[2], buf[3], buf[4]);
  424. + break;
  425. + }
  426. + case RESPONSE_R2_CID: case RESPONSE_R2_CSD:
  427. + {
  428. + for (i = 0; i < 16; i += 2) {
  429. + data = REG_MSC_RES;
  430. + buf[i] = (data >> 8) & 0xff;
  431. + buf[i+1] = data & 0xff;
  432. + }
  433. + debug("request %d, response [", request->rtype);
  434. +#if CONFIG_MMC_DEBUG_VERBOSE > 2
  435. + if (g_mmc_debug >= 3) {
  436. + int n;
  437. + for (n = 0; n < 17; n++)
  438. + printk("%02x ", buf[n]);
  439. + printk("]\n");
  440. + }
  441. +#endif
  442. + break;
  443. + }
  444. + case RESPONSE_NONE:
  445. + debug("No response\n");
  446. + break;
  447. +
  448. + default:
  449. + debug("unhandled response type for request %d\n", request->rtype);
  450. + break;
  451. + }
  452. +}
  453. +
  454. +static int jz_mmc_receive_data(struct mmc_request *req)
  455. +{
  456. + u32 stat, timeout, data, cnt;
  457. + u8 *buf = req->buffer;
  458. + u32 wblocklen = (u32)(req->block_len + 3) >> 2; /* length in word */
  459. +
  460. + timeout = 0x3ffffff;
  461. +
  462. + while (timeout) {
  463. + timeout--;
  464. + stat = REG_MSC_STAT;
  465. +
  466. + if (stat & MSC_STAT_TIME_OUT_READ)
  467. + return MMC_ERROR_TIMEOUT;
  468. + else if (stat & MSC_STAT_CRC_READ_ERROR)
  469. + return MMC_ERROR_CRC;
  470. + else if (!(stat & MSC_STAT_DATA_FIFO_EMPTY)
  471. + || (stat & MSC_STAT_DATA_FIFO_AFULL)) {
  472. + /* Ready to read data */
  473. + break;
  474. + }
  475. + udelay(1);
  476. + }
  477. + if (!timeout)
  478. + return MMC_ERROR_TIMEOUT;
  479. +
  480. + /* Read data from RXFIFO. It could be FULL or PARTIAL FULL */
  481. + cnt = wblocklen;
  482. + while (cnt) {
  483. + data = REG_MSC_RXFIFO;
  484. + {
  485. + *buf++ = (u8)(data >> 0);
  486. + *buf++ = (u8)(data >> 8);
  487. + *buf++ = (u8)(data >> 16);
  488. + *buf++ = (u8)(data >> 24);
  489. + }
  490. + cnt --;
  491. + while (cnt && (REG_MSC_STAT & MSC_STAT_DATA_FIFO_EMPTY))
  492. + ;
  493. + }
  494. + return MMC_NO_ERROR;
  495. +}
  496. +
  497. +static int jz_mmc_transmit_data(struct mmc_request *req)
  498. +{
  499. +#if 0
  500. + u32 nob = req->nob;
  501. + u32 wblocklen = (u32)(req->block_len + 3) >> 2; /* length in word */
  502. + u8 *buf = req->buffer;
  503. + u32 *wbuf = (u32 *)buf;
  504. + u32 waligned = (((u32)buf & 0x3) == 0); /* word aligned ? */
  505. + u32 stat, timeout, data, cnt;
  506. +
  507. + for (nob; nob >= 1; nob--) {
  508. + timeout = 0x3FFFFFF;
  509. +
  510. + while (timeout) {
  511. + timeout--;
  512. + stat = REG_MSC_STAT;
  513. +
  514. + if (stat & (MSC_STAT_CRC_WRITE_ERROR | MSC_STAT_CRC_WRITE_ERROR_NOSTS))
  515. + return MMC_ERROR_CRC;
  516. + else if (!(stat & MSC_STAT_DATA_FIFO_FULL)) {
  517. + /* Ready to write data */
  518. + break;
  519. + }
  520. +
  521. + udelay(1);
  522. + }
  523. +
  524. + if (!timeout)
  525. + return MMC_ERROR_TIMEOUT;
  526. +
  527. + /* Write data to TXFIFO */
  528. + cnt = wblocklen;
  529. + while (cnt) {
  530. + while (REG_MSC_STAT & MSC_STAT_DATA_FIFO_FULL)
  531. + ;
  532. +
  533. + if (waligned) {
  534. + REG_MSC_TXFIFO = *wbuf++;
  535. + }
  536. + else {
  537. + data = *buf++ | (*buf++ << 8) | (*buf++ << 16) | (*buf++ << 24);
  538. + REG_MSC_TXFIFO = data;
  539. + }
  540. +
  541. + cnt--;
  542. + }
  543. + }
  544. +#endif
  545. + return MMC_NO_ERROR;
  546. +}
  547. +
  548. +
  549. +/*
  550. + * Name: int jz_mmc_exec_cmd()
  551. + * Function: send command to the card, and get a response
  552. + * Input: struct mmc_request *req : MMC/SD request
  553. + * Output: 0: right >0: error code
  554. + */
  555. +int jz_mmc_exec_cmd(struct mmc_request *request)
  556. +{
  557. + u32 cmdat = 0, events = 0;
  558. + int retval, timeout = 0x3fffff;
  559. +
  560. + /* Indicate we have no result yet */
  561. + request->result = MMC_NO_RESPONSE;
  562. + if (request->cmd == MMC_CIM_RESET) {
  563. + /* On reset, 1-bit bus width */
  564. + use_4bit = 0;
  565. +
  566. + /* Reset MMC/SD controller */
  567. + __msc_reset();
  568. +
  569. + /* On reset, drop MMC clock down */
  570. + jz_mmc_set_clock(0, MMC_CLOCK_SLOW);
  571. +
  572. + /* On reset, stop MMC clock */
  573. + jz_mmc_stop_clock();
  574. + }
  575. + if (request->cmd == MMC_CMD_SEND_OP_COND) {
  576. + debug("Have an MMC card\n");
  577. + /* always use 1bit for MMC */
  578. + use_4bit = 0;
  579. + }
  580. + if (request->cmd == SET_BUS_WIDTH) {
  581. + if (request->arg == 0x2) {
  582. + printf("Use 4-bit bus width\n");
  583. + use_4bit = 1;
  584. + } else {
  585. + printf("Use 1-bit bus width\n");
  586. + use_4bit = 0;
  587. + }
  588. + }
  589. +
  590. + /* stop clock */
  591. + jz_mmc_stop_clock();
  592. +
  593. + /* mask all interrupts */
  594. + REG_MSC_IMASK = 0xffff;
  595. +
  596. + /* clear status */
  597. + REG_MSC_IREG = 0xffff;
  598. +
  599. + /* use 4-bit bus width when possible */
  600. + if (use_4bit)
  601. + cmdat |= MSC_CMDAT_BUS_WIDTH_4BIT;
  602. +
  603. + /* Set command type and events */
  604. + switch (request->cmd) {
  605. + /* MMC core extra command */
  606. + case MMC_CIM_RESET:
  607. + cmdat |= MSC_CMDAT_INIT; /* Initialization sequence sent prior to command */
  608. + break;
  609. +
  610. + /* bc - broadcast - no response */
  611. + case MMC_CMD_GO_IDLE_STATE:
  612. + case MMC_CMD_SET_DSR:
  613. + break;
  614. +
  615. + /* bcr - broadcast with response */
  616. + case MMC_CMD_SEND_OP_COND:
  617. + case MMC_CMD_ALL_SEND_CID:
  618. + case MMC_GO_IRQ_STATE:
  619. + break;
  620. +
  621. + /* adtc - addressed with data transfer */
  622. + case MMC_READ_DAT_UNTIL_STOP:
  623. + case MMC_CMD_READ_SINGLE_BLOCK:
  624. + case MMC_CMD_READ_MULTIPLE_BLOCK:
  625. + case SD_CMD_APP_SEND_SCR:
  626. + cmdat |= MSC_CMDAT_DATA_EN | MSC_CMDAT_READ;
  627. + events = MMC_EVENT_RX_DATA_DONE;
  628. + break;
  629. +
  630. + case MMC_WRITE_DAT_UNTIL_STOP:
  631. + case MMC_CMD_WRITE_SINGLE_BLOCK:
  632. + case MMC_CMD_WRITE_MULTIPLE_BLOCK:
  633. + case MMC_PROGRAM_CID:
  634. + case MMC_PROGRAM_CSD:
  635. + case MMC_SEND_WRITE_PROT:
  636. + case MMC_GEN_CMD:
  637. + case MMC_LOCK_UNLOCK:
  638. + cmdat |= MSC_CMDAT_DATA_EN | MSC_CMDAT_WRITE;
  639. + events = MMC_EVENT_TX_DATA_DONE | MMC_EVENT_PROG_DONE;
  640. +
  641. + break;
  642. +
  643. + case MMC_CMD_STOP_TRANSMISSION:
  644. + events = MMC_EVENT_PROG_DONE;
  645. + break;
  646. +
  647. + /* ac - no data transfer */
  648. + default:
  649. + break;
  650. + }
  651. +
  652. + /* Set response type */
  653. + switch (request->rtype) {
  654. + case RESPONSE_NONE:
  655. + break;
  656. +
  657. + case RESPONSE_R1B:
  658. + cmdat |= MSC_CMDAT_BUSY;
  659. + /*FALLTHRU*/
  660. + case RESPONSE_R1:
  661. + cmdat |= MSC_CMDAT_RESPONSE_R1;
  662. + break;
  663. + case RESPONSE_R2_CID:
  664. + case RESPONSE_R2_CSD:
  665. + cmdat |= MSC_CMDAT_RESPONSE_R2;
  666. + break;
  667. + case RESPONSE_R3:
  668. + cmdat |= MSC_CMDAT_RESPONSE_R3;
  669. + break;
  670. + case RESPONSE_R4:
  671. + cmdat |= MSC_CMDAT_RESPONSE_R4;
  672. + break;
  673. + case RESPONSE_R5:
  674. + cmdat |= MSC_CMDAT_RESPONSE_R5;
  675. + break;
  676. + case RESPONSE_R6:
  677. + cmdat |= MSC_CMDAT_RESPONSE_R6;
  678. + break;
  679. + default:
  680. + break;
  681. + }
  682. +
  683. + /* Set command index */
  684. + if (request->cmd == MMC_CIM_RESET) {
  685. + REG_MSC_CMD = MMC_CMD_GO_IDLE_STATE;
  686. + } else {
  687. + REG_MSC_CMD = request->cmd;
  688. + }
  689. +
  690. + /* Set argument */
  691. + REG_MSC_ARG = request->arg;
  692. +
  693. + /* Set block length and nob */
  694. + if (request->cmd == SD_CMD_APP_SEND_SCR) { /* get SCR from DataFIFO */
  695. + REG_MSC_BLKLEN = 8;
  696. + REG_MSC_NOB = 1;
  697. + } else {
  698. + REG_MSC_BLKLEN = request->block_len;
  699. + REG_MSC_NOB = request->nob;
  700. + }
  701. +
  702. + /* Set command */
  703. + REG_MSC_CMDAT = cmdat;
  704. +
  705. + debug("Send cmd %d cmdat: %x arg: %x resp %d\n", request->cmd,
  706. + cmdat, request->arg, request->rtype);
  707. +
  708. + /* Start MMC/SD clock and send command to card */
  709. + jz_mmc_start_clock();
  710. +
  711. + /* Wait for command completion */
  712. + while (timeout-- && !(REG_MSC_STAT & MSC_STAT_END_CMD_RES))
  713. + ;
  714. +
  715. + if (timeout == 0)
  716. + return MMC_ERROR_TIMEOUT;
  717. +
  718. + REG_MSC_IREG = MSC_IREG_END_CMD_RES; /* clear flag */
  719. +
  720. + /* Check for status */
  721. + retval = jz_mmc_check_status(request);
  722. + if (retval) {
  723. + return retval;
  724. + }
  725. +
  726. + /* Complete command with no response */
  727. + if (request->rtype == RESPONSE_NONE) {
  728. + return MMC_NO_ERROR;
  729. + }
  730. +
  731. + /* Get response */
  732. + jz_mmc_get_response(request);
  733. +
  734. + /* Start data operation */
  735. + if (events & (MMC_EVENT_RX_DATA_DONE | MMC_EVENT_TX_DATA_DONE)) {
  736. + if (events & MMC_EVENT_RX_DATA_DONE) {
  737. + if (request->cmd == SD_CMD_APP_SEND_SCR) {
  738. + /* SD card returns SCR register as data.
  739. + MMC core expect it in the response buffer,
  740. + after normal response. */
  741. + request->buffer = (u8 *)((u32)request->response + 5);
  742. + }
  743. + jz_mmc_receive_data(request);
  744. + }
  745. +
  746. + if (events & MMC_EVENT_TX_DATA_DONE) {
  747. + jz_mmc_transmit_data(request);
  748. + }
  749. +
  750. + /* Wait for Data Done */
  751. + while (!(REG_MSC_IREG & MSC_IREG_DATA_TRAN_DONE))
  752. + ;
  753. + REG_MSC_IREG = MSC_IREG_DATA_TRAN_DONE; /* clear status */
  754. + }
  755. +
  756. + /* Wait for Prog Done event */
  757. + if (events & MMC_EVENT_PROG_DONE) {
  758. + while (!(REG_MSC_IREG & MSC_IREG_PRG_DONE))
  759. + ;
  760. + REG_MSC_IREG = MSC_IREG_PRG_DONE; /* clear status */
  761. + }
  762. +
  763. + /* Command completed */
  764. +
  765. + return MMC_NO_ERROR; /* return successfully */
  766. +}
  767. +
  768. +int mmc_block_read(u8 *dst, ulong src, ulong len)
  769. +{
  770. +
  771. + struct mmc_request request;
  772. + struct mmc_response_r1 r1;
  773. + int retval = 0;
  774. +
  775. + if (len == 0)
  776. + goto exit;
  777. +
  778. + mmc_simple_cmd(&request, MMC_CMD_SEND_STATUS, mmcinfo.rca, RESPONSE_R1);
  779. + retval = mmc_unpack_r1(&request, &r1, 0);
  780. + if (retval && (retval != MMC_ERROR_STATE_MISMATCH))
  781. + goto exit;
  782. +
  783. + mmc_simple_cmd(&request, MMC_CMD_SET_BLOCKLEN, len, RESPONSE_R1);
  784. + if (retval = mmc_unpack_r1(&request, &r1, 0))
  785. + goto exit;
  786. +
  787. + if (!sd2_0)
  788. + src *= mmcinfo.block_len;
  789. +
  790. + mmc_send_cmd(&request, MMC_CMD_READ_SINGLE_BLOCK, src, 1, len, RESPONSE_R1, dst);
  791. + if (retval = mmc_unpack_r1(&request, &r1, 0))
  792. + goto exit;
  793. +
  794. +exit:
  795. + return retval;
  796. +}
  797. +
  798. +ulong mmc_bread(int dev_num, ulong blkstart, ulong blkcnt, ulong *dst)
  799. +{
  800. + if (!mmc_ready) {
  801. + printf("Please initial the MMC first\n");
  802. + return -1;
  803. + }
  804. +
  805. + int i = 0;
  806. + ulong dst_tmp = dst;
  807. +
  808. + for (i = 0; i < blkcnt; i++) {
  809. + if ((mmc_block_read((uchar *)(dst_tmp), blkstart, mmcinfo.block_len)) < 0)
  810. + return -1;
  811. +
  812. + dst_tmp += mmcinfo.block_len;
  813. + blkstart++;
  814. + }
  815. +
  816. + return i;
  817. +}
  818. +
  819. +int mmc_select_card(void)
  820. +{
  821. + struct mmc_request request;
  822. + struct mmc_response_r1 r1;
  823. + int retval;
  824. +
  825. + mmc_simple_cmd(&request, MMC_CMD_SELECT_CARD, mmcinfo.rca, RESPONSE_R1B);
  826. + retval = mmc_unpack_r1(&request, &r1, 0);
  827. + if (retval) {
  828. + return retval;
  829. + }
  830. +
  831. + if (mmcinfo.sd) {
  832. + mmc_simple_cmd(&request, MMC_CMD_APP_CMD, mmcinfo.rca, RESPONSE_R1);
  833. + retval = mmc_unpack_r1(&request,&r1,0);
  834. + if (retval) {
  835. + return retval;
  836. + }
  837. +#if defined(MMC_BUS_WIDTH_1BIT)
  838. + mmc_simple_cmd(&request, SET_BUS_WIDTH, 1, RESPONSE_R1);
  839. +#else
  840. + mmc_simple_cmd(&request, SET_BUS_WIDTH, 2, RESPONSE_R1);
  841. +#endif
  842. + retval = mmc_unpack_r1(&request,&r1,0);
  843. + if (retval) {
  844. + return retval;
  845. + }
  846. + }
  847. + return 0;
  848. +}
  849. +
  850. +/*
  851. + * Configure card
  852. + */
  853. +static void mmc_configure_card(void)
  854. +{
  855. + u32 rate;
  856. +
  857. + /* Get card info */
  858. + if (sd2_0)
  859. + mmcinfo.block_num = (mmcinfo.csd.c_size + 1) << 10;
  860. + else
  861. + mmcinfo.block_num = (mmcinfo.csd.c_size + 1) * (1 << (mmcinfo.csd.c_size_mult + 2));
  862. +
  863. + mmcinfo.block_len = 1 << mmcinfo.csd.read_bl_len;
  864. +
  865. + mmc_dev.if_type = IF_TYPE_SD;
  866. + mmc_dev.part_type = PART_TYPE_DOS;
  867. + mmc_dev.dev = 0;
  868. + mmc_dev.lun = 0;
  869. + mmc_dev.type = 0;
  870. + mmc_dev.blksz = mmcinfo.block_len;
  871. + mmc_dev.lba = mmcinfo.block_num;
  872. + mmc_dev.removable = 0;
  873. +
  874. + printf("%s Detected: %lu blocks of %lu bytes\n",
  875. + sd2_0 == 1 ? "SDHC" : "SD",
  876. + mmc_dev.lba,
  877. + mmc_dev.blksz);
  878. +
  879. + /* Fix the clock rate */
  880. + rate = mmc_tran_speed(mmcinfo.csd.tran_speed);
  881. + if (rate < MMC_CLOCK_SLOW)
  882. + rate = MMC_CLOCK_SLOW;
  883. + if ((mmcinfo.sd == 0) && (rate > MMC_CLOCK_FAST))
  884. + rate = MMC_CLOCK_FAST;
  885. + if ((mmcinfo.sd) && (rate > SD_CLOCK_FAST))
  886. + rate = SD_CLOCK_FAST;
  887. +
  888. + debug("%s: block_len=%d block_num=%d rate=%d\n",
  889. + __func__, mmcinfo.block_len, mmcinfo.block_num, rate);
  890. +
  891. + jz_mmc_set_clock(mmcinfo.sd, rate);
  892. +}
  893. +
  894. +/*
  895. + * State machine routines to initialize card(s)
  896. + */
  897. +
  898. +/*
  899. + CIM_SINGLE_CARD_ACQ (frequency at 400 kHz)
  900. + --- Must enter from GO_IDLE_STATE ---
  901. + 1. SD_SEND_OP_COND (SD Card) [CMD55] + [CMD41]
  902. + 2. SEND_OP_COND (Full Range) [CMD1] {optional}
  903. + 3. SEND_OP_COND (Set Range ) [CMD1]
  904. + If busy, delay and repeat step 2
  905. + 4. ALL_SEND_CID [CMD2]
  906. + If timeout, set an error (no cards found)
  907. + 5. SET_RELATIVE_ADDR [CMD3]
  908. + 6. SEND_CSD [CMD9]
  909. + 7. SET_DSR [CMD4] Only call this if (csd.dsr_imp).
  910. + 8. Set clock frequency (check available in csd.tran_speed)
  911. + */
  912. +
  913. +#define MMC_INIT_DOING 0
  914. +#define MMC_INIT_PASSED 1
  915. +#define MMC_INIT_FAILED 2
  916. +
  917. +static int mmc_init_card_state(struct mmc_request *request)
  918. +{
  919. + struct mmc_response_r1 r1;
  920. + struct mmc_response_r3 r3;
  921. + int retval;
  922. + int ocr = 0x40300000;
  923. + int limit_41 = 0;
  924. +
  925. + switch (request->cmd) {
  926. + case MMC_CMD_GO_IDLE_STATE: /* No response to parse */
  927. + if (mmcinfo.sd)
  928. + mmc_simple_cmd(request, 8, 0x1aa, RESPONSE_R1);
  929. + else
  930. + mmc_simple_cmd(request, MMC_CMD_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3);
  931. + break;
  932. +
  933. + case 8:
  934. + retval = mmc_unpack_r1(request,&r1,mmcinfo.state);
  935. + mmc_simple_cmd(request, MMC_CMD_APP_CMD, 0, RESPONSE_R1);
  936. + break;
  937. +
  938. + case MMC_CMD_APP_CMD:
  939. + retval = mmc_unpack_r1(request,&r1,mmcinfo.state);
  940. + if (retval & (limit_41 < 100)) {
  941. + debug("%s: unable to MMC_APP_CMD error=%d (%s)\n",
  942. + __func__, retval, mmc_result_to_string(retval));
  943. + limit_41++;
  944. + mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, ocr, RESPONSE_R3);
  945. + } else if (limit_41 < 100) {
  946. + limit_41++;
  947. + mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, ocr, RESPONSE_R3);
  948. + } else{
  949. + /* reset the card to idle*/
  950. + mmc_simple_cmd(request, MMC_CMD_GO_IDLE_STATE, 0, RESPONSE_NONE);
  951. + mmcinfo.sd = 0;
  952. + }
  953. + break;
  954. +
  955. + case SD_CMD_APP_SEND_OP_COND:
  956. + retval = mmc_unpack_r3(request, &r3);
  957. + if (retval) {
  958. + debug("%s: try MMC card\n", __func__);
  959. + mmc_simple_cmd(request, SD_CMD_APP_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3);
  960. + break;
  961. + }
  962. +
  963. + debug("%s: read ocr value = 0x%08x\n", __func__, r3.ocr);
  964. +
  965. + if(!(r3.ocr & MMC_CARD_BUSY || ocr == 0)){
  966. + udelay(50000);
  967. + mmc_simple_cmd(request, MMC_CMD_APP_CMD, 0, RESPONSE_R1);
  968. + } else {
  969. + mmcinfo.sd = 1; /* SD Card ready */
  970. + mmcinfo.state = CARD_STATE_READY;
  971. + mmc_simple_cmd(request, MMC_CMD_ALL_SEND_CID, 0, RESPONSE_R2_CID);
  972. + }
  973. + break;
  974. +
  975. + case MMC_CMD_SEND_OP_COND:
  976. + retval = mmc_unpack_r3(request, &r3);
  977. + if (retval) {
  978. + debug("%s: failed SEND_OP_COND error=%d (%s)\n",
  979. + __func__, retval, mmc_result_to_string(retval));
  980. + return MMC_INIT_FAILED;
  981. + }
  982. +
  983. + debug("%s: read ocr value = 0x%08x\n", __func__, r3.ocr);
  984. + if (!(r3.ocr & MMC_CARD_BUSY)) {
  985. + mmc_simple_cmd(request, MMC_CMD_SEND_OP_COND, MMC_OCR_ARG, RESPONSE_R3);
  986. + } else {
  987. + mmcinfo.sd = 0; /* MMC Card ready */
  988. + mmcinfo.state = CARD_STATE_READY;
  989. + mmc_simple_cmd(request, MMC_CMD_ALL_SEND_CID, 0, RESPONSE_R2_CID);
  990. + }
  991. + break;
  992. +
  993. + case MMC_CMD_ALL_SEND_CID:
  994. + retval = mmc_unpack_cid( request, &mmcinfo.cid );
  995. + /*FIXME:ignore CRC error for CMD2/CMD9/CMD10 */
  996. + if ( retval && (retval != MMC_ERROR_CRC)) {
  997. + debug("mmc_init_card_state: unable to ALL_SEND_CID error=%d (%s)\n",
  998. + retval, mmc_result_to_string(retval));
  999. + return MMC_INIT_FAILED;
  1000. + }
  1001. + mmcinfo.state = CARD_STATE_IDENT;
  1002. + if(mmcinfo.sd)
  1003. + mmc_simple_cmd(request, MMC_CMD_SET_RELATIVE_ADDR, 0, RESPONSE_R6);
  1004. + else
  1005. + mmc_simple_cmd(request, MMC_CMD_SET_RELATIVE_ADDR, ID_TO_RCA(mmcinfo.id) << 16, RESPONSE_R1);
  1006. + break;
  1007. +
  1008. + case MMC_CMD_SET_RELATIVE_ADDR:
  1009. + if (mmcinfo.sd) {
  1010. + retval = mmc_unpack_r6(request, &r1, mmcinfo.state, &mmcinfo.rca);
  1011. + mmcinfo.rca = mmcinfo.rca << 16;
  1012. + debug("%s: Get RCA from SD: 0x%04x Status: %x\n",
  1013. + __func__, mmcinfo.rca, r1.status);
  1014. + } else {
  1015. + retval = mmc_unpack_r1(request,&r1,mmcinfo.state);
  1016. + mmcinfo.rca = ID_TO_RCA(mmcinfo.id) << 16;
  1017. + }
  1018. + if (retval) {
  1019. + debug("%s: unable to SET_RELATIVE_ADDR error=%d (%s)\n",
  1020. + __func__, retval, mmc_result_to_string(retval));
  1021. + return MMC_INIT_FAILED;
  1022. + }
  1023. +
  1024. + mmcinfo.state = CARD_STATE_STBY;
  1025. + mmc_simple_cmd(request, MMC_CMD_SEND_CSD, mmcinfo.rca, RESPONSE_R2_CSD);
  1026. +
  1027. + break;
  1028. +
  1029. + case MMC_CMD_SEND_CSD:
  1030. + retval = mmc_unpack_csd(request, &mmcinfo.csd);
  1031. + mmc_ready = 1;
  1032. + /*FIXME:ignore CRC error for CMD2/CMD9/CMD10 */
  1033. + if (retval && (retval != MMC_ERROR_CRC)) {
  1034. + debug("%s: unable to SEND_CSD error=%d (%s)\n",
  1035. + __func__, retval, mmc_result_to_string(retval));
  1036. + return MMC_INIT_FAILED;
  1037. + }
  1038. + if (mmcinfo.csd.dsr_imp) {
  1039. + debug("%s: driver doesn't support setting DSR\n", __func__);
  1040. + }
  1041. + mmc_configure_card();
  1042. + return MMC_INIT_PASSED;
  1043. +
  1044. + default:
  1045. + debug("%s: error! Illegal last cmd %d\n", __func__, request->cmd);
  1046. + return MMC_INIT_FAILED;
  1047. + }
  1048. +
  1049. + return MMC_INIT_DOING;
  1050. +}
  1051. +
  1052. +int mmc_init_card(void)
  1053. +{
  1054. + struct mmc_request request;
  1055. + int retval;
  1056. +
  1057. + mmc_simple_cmd(&request, MMC_CIM_RESET, 0, RESPONSE_NONE); /* reset card */
  1058. + mmc_simple_cmd(&request, MMC_CMD_GO_IDLE_STATE, 0, RESPONSE_NONE);
  1059. + mmcinfo.sd = 1; /* assuming a SD card */
  1060. +
  1061. + while ((retval = mmc_init_card_state(&request)) == MMC_INIT_DOING)
  1062. + ;
  1063. +
  1064. + if (retval == MMC_INIT_PASSED)
  1065. + return MMC_NO_ERROR;
  1066. + else
  1067. + return MMC_NO_RESPONSE;
  1068. +}
  1069. +
  1070. +int mmc_legacy_init(int verbose)
  1071. +{
  1072. + if (!__msc_card_detected())
  1073. + return 1;
  1074. +
  1075. + /* Step-1: init GPIO */
  1076. + __gpio_as_msc();
  1077. + __msc_init_io();
  1078. +
  1079. + /* Step-2: turn on power of card */
  1080. +#if !defined(CONFIG_SAKC)
  1081. + __msc_enable_power();
  1082. +#endif
  1083. +
  1084. + /* Step-3: Reset MSC Controller. */
  1085. + __msc_reset();
  1086. +
  1087. + /* Step-3: mask all IRQs. */
  1088. + MMC_IRQ_MASK();
  1089. +
  1090. + /* Step-4: stop MMC/SD clock */
  1091. + jz_mmc_stop_clock();
  1092. + mmc_init_card();
  1093. + mmc_select_card();
  1094. +
  1095. + mmc_dev.block_read = mmc_bread;
  1096. + fat_register_device(&mmc_dev,1); /* partitions start counting with 1 */
  1097. +
  1098. + return 0;
  1099. +}
  1100. +
  1101. +/*
  1102. + * Debugging functions
  1103. + */
  1104. +static char * mmc_result_strings[] = {
  1105. + "NO_RESPONSE",
  1106. + "NO_ERROR",
  1107. + "ERROR_OUT_OF_RANGE",
  1108. + "ERROR_ADDRESS",
  1109. + "ERROR_BLOCK_LEN",
  1110. + "ERROR_ERASE_SEQ",
  1111. + "ERROR_ERASE_PARAM",
  1112. + "ERROR_WP_VIOLATION",
  1113. + "ERROR_CARD_IS_LOCKED",
  1114. + "ERROR_LOCK_UNLOCK_FAILED",
  1115. + "ERROR_COM_CRC",
  1116. + "ERROR_ILLEGAL_COMMAND",
  1117. + "ERROR_CARD_ECC_FAILED",
  1118. + "ERROR_CC",
  1119. + "ERROR_GENERAL",
  1120. + "ERROR_UNDERRUN",
  1121. + "ERROR_OVERRUN",
  1122. + "ERROR_CID_CSD_OVERWRITE",
  1123. + "ERROR_STATE_MISMATCH",
  1124. + "ERROR_HEADER_MISMATCH",
  1125. + "ERROR_TIMEOUT",
  1126. + "ERROR_CRC",
  1127. + "ERROR_DRIVER_FAILURE",
  1128. +};
  1129. +
  1130. +char * mmc_result_to_string(int i)
  1131. +{
  1132. + return mmc_result_strings[i+1];
  1133. +}
  1134. +
  1135. +static char * card_state_strings[] = {
  1136. + "empty",
  1137. + "idle",
  1138. + "ready",
  1139. + "ident",
  1140. + "stby",
  1141. + "tran",
  1142. + "data",
  1143. + "rcv",
  1144. + "prg",
  1145. + "dis",
  1146. +};
  1147. +
  1148. +static inline char * card_state_to_string(int i)
  1149. +{
  1150. + return card_state_strings[i+1];
  1151. +}
  1152. +
  1153. +/*
  1154. + * Utility functions
  1155. + */
  1156. +
  1157. +#define PARSE_U32(_buf,_index) \
  1158. + (((u32)_buf[_index]) << 24) | (((u32)_buf[_index+1]) << 16) | \
  1159. + (((u32)_buf[_index+2]) << 8) | ((u32)_buf[_index+3]);
  1160. +
  1161. +#define PARSE_U16(_buf,_index) \
  1162. + (((u16)_buf[_index]) << 8) | ((u16)_buf[_index+1]);
  1163. +
  1164. +int mmc_unpack_csd(struct mmc_request *request, struct mmc_csd *csd)
  1165. +{
  1166. + u8 *buf = request->response;
  1167. + int num = 0;
  1168. +
  1169. + if (request->result)
  1170. + return request->result;
  1171. +
  1172. + if (buf[0] != 0x3f)
  1173. + return MMC_ERROR_HEADER_MISMATCH;
  1174. +
  1175. + csd->csd_structure = (buf[1] & 0xc0) >> 6;
  1176. + if (csd->csd_structure)
  1177. + sd2_0 = 1;
  1178. + else
  1179. + sd2_0 = 0;
  1180. +
  1181. + switch (csd->csd_structure) {
  1182. + case 0 :/* Version 1.01-1.10
  1183. + * Version 2.00/Standard Capacity */
  1184. + csd->taac = buf[2];
  1185. + csd->nsac = buf[3];
  1186. + csd->tran_speed = buf[4];
  1187. + csd->ccc = (((u16)buf[5]) << 4) | ((buf[6] & 0xf0) >> 4);
  1188. + csd->read_bl_len = buf[6] & 0x0f;
  1189. + /* for support 2GB card*/
  1190. + if (csd->read_bl_len >= 10)
  1191. + {
  1192. + num = csd->read_bl_len - 9;
  1193. + csd->read_bl_len = 9;
  1194. + }
  1195. +
  1196. + csd->read_bl_partial = (buf[7] & 0x80) ? 1 : 0;
  1197. + csd->write_blk_misalign = (buf[7] & 0x40) ? 1 : 0;
  1198. + csd->read_blk_misalign = (buf[7] & 0x20) ? 1 : 0;
  1199. + csd->dsr_imp = (buf[7] & 0x10) ? 1 : 0;
  1200. + csd->c_size = ((((u16)buf[7]) & 0x03) << 10) | (((u16)buf[8]) << 2) | (((u16)buf[9]) & 0xc0) >> 6;
  1201. +
  1202. + if (num)
  1203. + csd->c_size = csd->c_size << num;
  1204. +
  1205. +
  1206. + csd->vdd_r_curr_min = (buf[9] & 0x38) >> 3;
  1207. + csd->vdd_r_curr_max = buf[9] & 0x07;
  1208. + csd->vdd_w_curr_min = (buf[10] & 0xe0) >> 5;
  1209. + csd->vdd_w_curr_max = (buf[10] & 0x1c) >> 2;
  1210. + csd->c_size_mult = ((buf[10] & 0x03) << 1) | ((buf[11] & 0x80) >> 7);
  1211. + csd->sector_size = (buf[11] & 0x7c) >> 2;
  1212. + csd->erase_grp_size = ((buf[11] & 0x03) << 3) | ((buf[12] & 0xe0) >> 5);
  1213. + csd->wp_grp_size = buf[12] & 0x1f;
  1214. + csd->wp_grp_enable = (buf[13] & 0x80) ? 1 : 0;
  1215. + csd->default_ecc = (buf[13] & 0x60) >> 5;
  1216. + csd->r2w_factor = (buf[13] & 0x1c) >> 2;
  1217. + csd->write_bl_len = ((buf[13] & 0x03) << 2) | ((buf[14] & 0xc0) >> 6);
  1218. + if (csd->write_bl_len >= 10)
  1219. + csd->write_bl_len = 9;
  1220. +
  1221. + csd->write_bl_partial = (buf[14] & 0x20) ? 1 : 0;
  1222. + csd->file_format_grp = (buf[15] & 0x80) ? 1 : 0;
  1223. + csd->copy = (buf[15] & 0x40) ? 1 : 0;
  1224. + csd->perm_write_protect = (buf[15] & 0x20) ? 1 : 0;
  1225. + csd->tmp_write_protect = (buf[15] & 0x10) ? 1 : 0;
  1226. + csd->file_format = (buf[15] & 0x0c) >> 2;
  1227. + csd->ecc = buf[15] & 0x03;
  1228. + break;
  1229. + case 1 : /* Version 2.00/High Capacity */
  1230. + csd->taac = 0;
  1231. + csd->nsac = 0;
  1232. + csd->tran_speed = buf[4];
  1233. + csd->ccc = (((u16)buf[5]) << 4) | ((buf[6] & 0xf0) >> 4);
  1234. +
  1235. + csd->read_bl_len = 9;
  1236. + csd->read_bl_partial = 0;
  1237. + csd->write_blk_misalign = 0;
  1238. + csd->read_blk_misalign = 0;
  1239. + csd->dsr_imp = (buf[7] & 0x10) ? 1 : 0;
  1240. + csd->c_size = ((((u16)buf[8]) & 0x3f) << 16) | (((u16)buf[9]) << 8) | ((u16)buf[10]) ;
  1241. + csd->sector_size = 0x7f;
  1242. + csd->erase_grp_size = 0;
  1243. + csd->wp_grp_size = 0;
  1244. + csd->wp_grp_enable = 0;
  1245. + csd->default_ecc = (buf[13] & 0x60) >> 5;
  1246. + csd->r2w_factor = 4;/* Unused */
  1247. + csd->write_bl_len = 9;
  1248. +
  1249. + csd->write_bl_partial = 0;
  1250. + csd->file_format_grp = 0;
  1251. + csd->copy = (buf[15] & 0x40) ? 1 : 0;
  1252. + csd->perm_write_protect = (buf[15] & 0x20) ? 1 : 0;
  1253. + csd->tmp_write_protect = (buf[15] & 0x10) ? 1 : 0;
  1254. + csd->file_format = 0;
  1255. + csd->ecc = buf[15] & 0x03;
  1256. + }
  1257. +
  1258. + return 0;
  1259. +}
  1260. +
  1261. +int mmc_unpack_r1(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state)
  1262. +{
  1263. + u8 *buf = request->response;
  1264. +
  1265. + if (request->result)
  1266. + return request->result;
  1267. +
  1268. + r1->cmd = buf[0];
  1269. + r1->status = PARSE_U32(buf,1);
  1270. +
  1271. + debug("mmc_unpack_r1: cmd=%d status=%08x\n", r1->cmd, r1->status);
  1272. +
  1273. + if (R1_STATUS(r1->status)) {
  1274. + if (r1->status & R1_OUT_OF_RANGE) return MMC_ERROR_OUT_OF_RANGE;
  1275. + if (r1->status & R1_ADDRESS_ERROR) return MMC_ERROR_ADDRESS;
  1276. + if (r1->status & R1_BLOCK_LEN_ERROR) return MMC_ERROR_BLOCK_LEN;
  1277. + if (r1->status & R1_ERASE_SEQ_ERROR) return MMC_ERROR_ERASE_SEQ;
  1278. + if (r1->status & R1_ERASE_PARAM) return MMC_ERROR_ERASE_PARAM;
  1279. + if (r1->status & R1_WP_VIOLATION) return MMC_ERROR_WP_VIOLATION;
  1280. + /*if (r1->status & R1_CARD_IS_LOCKED) return MMC_ERROR_CARD_IS_LOCKED; */
  1281. + if (r1->status & R1_LOCK_UNLOCK_FAILED) return MMC_ERROR_LOCK_UNLOCK_FAILED;
  1282. + if (r1->status & R1_COM_CRC_ERROR) return MMC_ERROR_COM_CRC;
  1283. + if (r1->status & R1_ILLEGAL_COMMAND) return MMC_ERROR_ILLEGAL_COMMAND;
  1284. + if (r1->status & R1_CARD_ECC_FAILED) return MMC_ERROR_CARD_ECC_FAILED;
  1285. + if (r1->status & R1_CC_ERROR) return MMC_ERROR_CC;
  1286. + if (r1->status & R1_ERROR) return MMC_ERROR_GENERAL;
  1287. + if (r1->status & R1_UNDERRUN) return MMC_ERROR_UNDERRUN;
  1288. + if (r1->status & R1_OVERRUN) return MMC_ERROR_OVERRUN;
  1289. + if (r1->status & R1_CID_CSD_OVERWRITE) return MMC_ERROR_CID_CSD_OVERWRITE;
  1290. + }
  1291. +
  1292. + if (buf[0] != request->cmd)
  1293. + return MMC_ERROR_HEADER_MISMATCH;
  1294. +
  1295. + /* This should be last - it's the least dangerous error */
  1296. +
  1297. + return 0;
  1298. +}
  1299. +
  1300. +int mmc_unpack_scr(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, u32 *scr)
  1301. +{
  1302. + u8 *buf = request->response;
  1303. + if (request->result)
  1304. + return request->result;
  1305. +
  1306. + *scr = PARSE_U32(buf, 5); /* Save SCR returned by the SD Card */
  1307. + return mmc_unpack_r1(request, r1, state);
  1308. +
  1309. +}
  1310. +
  1311. +int mmc_unpack_r6(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, int *rca)
  1312. +{
  1313. + u8 *buf = request->response;
  1314. +
  1315. + if (request->result)
  1316. + return request->result;
  1317. +
  1318. + *rca = PARSE_U16(buf,1); /* Save RCA returned by the SD Card */
  1319. +
  1320. + *(buf+1) = 0;
  1321. + *(buf+2) = 0;
  1322. +
  1323. + return mmc_unpack_r1(request, r1, state);
  1324. +}
  1325. +
  1326. +int mmc_unpack_cid(struct mmc_request *request, struct mmc_cid *cid)
  1327. +{
  1328. + int i;
  1329. + u8 *buf = request->response;
  1330. +
  1331. + if (request->result)
  1332. + return request->result;
  1333. +
  1334. + cid->mid = buf[1];
  1335. + cid->oid = PARSE_U16(buf,2);
  1336. + for (i = 0 ; i < 5 ; i++)
  1337. + cid->pnm[i] = buf[4+i];
  1338. + cid->pnm[6] = 0;
  1339. + cid->prv = buf[10];
  1340. + cid->psn = PARSE_U32(buf,10);
  1341. + cid->mdt = buf[15];
  1342. +
  1343. + printf("Man %02x OEM 0x%04x \"%s\" %d.%d 0x%08x "
  1344. + "Date %02u/%04u\n",
  1345. + cid->mid,
  1346. + cid->oid,
  1347. + cid->pnm,
  1348. + cid->prv >> 4,
  1349. + cid->prv & 0xf,
  1350. + cid->psn,
  1351. + cid->mdt & 0xf,
  1352. + (cid->mdt >> 4) + 2000);
  1353. +
  1354. + if (buf[0] != 0x3f)
  1355. + return MMC_ERROR_HEADER_MISMATCH;
  1356. + return 0;
  1357. +}
  1358. +
  1359. +int mmc_unpack_r3(struct mmc_request *request, struct mmc_response_r3 *r3)
  1360. +{
  1361. + u8 *buf = request->response;
  1362. +
  1363. + if (request->result)
  1364. + return request->result;
  1365. +
  1366. + r3->ocr = PARSE_U32(buf,1);
  1367. + debug("mmc_unpack_r3: ocr=%08x\n", r3->ocr);
  1368. +
  1369. + if (buf[0] != 0x3f) return MMC_ERROR_HEADER_MISMATCH;
  1370. + return 0;
  1371. +}
  1372. +
  1373. +#define KBPS 1
  1374. +#define MBPS 1000
  1375. +
  1376. +static u32 ts_exp[] = { 100*KBPS, 1*MBPS, 10*MBPS, 100*MBPS, 0, 0, 0, 0 };
  1377. +static u32 ts_mul[] = { 0, 1000, 1200, 1300, 1500, 2000, 2500, 3000,
  1378. + 3500, 4000, 4500, 5000, 5500, 6000, 7000, 8000 };
  1379. +
  1380. +u32 mmc_tran_speed(u8 ts)
  1381. +{
  1382. + u32 rate = ts_exp[(ts & 0x7)] * ts_mul[(ts & 0x78) >> 3];
  1383. +
  1384. + if (rate <= 0) {
  1385. + debug("%s: error - unrecognized speed 0x%02x\n", __func__, ts);
  1386. + return 1;
  1387. + }
  1388. +
  1389. + return rate;
  1390. +}
  1391. +
  1392. +void mmc_send_cmd(struct mmc_request *request, int cmd, u32 arg,
  1393. + u16 nob, u16 block_len, enum mmc_rsp_t rtype, u8 *buffer)
  1394. +{
  1395. + request->cmd = cmd;
  1396. + request->arg = arg;
  1397. + request->rtype = rtype;
  1398. + request->nob = nob;
  1399. + request->block_len = block_len;
  1400. + request->buffer = buffer;
  1401. + request->cnt = nob * block_len;
  1402. +
  1403. + jz_mmc_exec_cmd(request);
  1404. +}
  1405. diff --git a/drivers/mmc/jz_mmc.h b/drivers/mmc/jz_mmc.h
  1406. new file mode 100644
  1407. index 0000000..936c514
  1408. --- /dev/null
  1409. +++ b/drivers/mmc/jz_mmc.h
  1410. @@ -0,0 +1,176 @@
  1411. +/*
  1412. + * linux/drivers/mmc/jz_mmc.h
  1413. + *
  1414. + * Author: Vladimir Shebordaev, Igor Oblakov
  1415. + * Copyright: MontaVista Software Inc.
  1416. + *
  1417. + * $Id: jz_mmc.h,v 1.3 2007-06-15 08:04:20 jlwei Exp $
  1418. + *
  1419. + * This program is free software; you can redistribute it and/or modify
  1420. + * it under the terms of the GNU General Public License version 2 as
  1421. + * published by the Free Software Foundation.
  1422. + */
  1423. +#ifndef __MMC_JZMMC_H__
  1424. +#define __MMC_JZMMC_H__
  1425. +
  1426. +#define ID_TO_RCA(x) ((x)+1)
  1427. +#define MMC_OCR_ARG 0x00ff8000 /* Argument of OCR */
  1428. +
  1429. +/* Standard MMC/SD clock speeds */
  1430. +#define MMC_CLOCK_SLOW 400000 /* 400 kHz for initial setup */
  1431. +#define MMC_CLOCK_FAST 20000000 /* 20 MHz for maximum for normal operation */
  1432. +#define SD_CLOCK_FAST 24000000 /* 24 MHz for SD Cards */
  1433. +
  1434. +/* Use negative numbers to disambiguate */
  1435. +#define MMC_CIM_RESET -1
  1436. +#define SET_BUS_WIDTH 6 /* ac [1:0] bus width R1 */
  1437. +
  1438. +#define R1_OUT_OF_RANGE (1 << 31) /* er, c */
  1439. +#define R1_ADDRESS_ERROR (1 << 30) /* erx, c */
  1440. +#define R1_BLOCK_LEN_ERROR (1 << 29) /* er, c */
  1441. +#define R1_ERASE_SEQ_ERROR (1 << 28) /* er, c */
  1442. +#define R1_ERASE_PARAM (1 << 27) /* ex, c */
  1443. +#define R1_WP_VIOLATION (1 << 26) /* erx, c */
  1444. +#define R1_CARD_IS_LOCKED (1 << 25) /* sx, a */
  1445. +#define R1_LOCK_UNLOCK_FAILED (1 << 24) /* erx, c */
  1446. +#define R1_COM_CRC_ERROR (1 << 23) /* er, b */
  1447. +#define R1_ILLEGAL_COMMAND (1 << 22) /* er, b */
  1448. +#define R1_CARD_ECC_FAILED (1 << 21) /* ex, c */
  1449. +#define R1_CC_ERROR (1 << 20) /* erx, c */
  1450. +#define R1_ERROR (1 << 19) /* erx, c */
  1451. +#define R1_UNDERRUN (1 << 18) /* ex, c */
  1452. +#define R1_OVERRUN (1 << 17) /* ex, c */
  1453. +#define R1_CID_CSD_OVERWRITE (1 << 16) /* erx, c, CID/CSD overwrite */
  1454. +#define R1_WP_ERASE_SKIP (1 << 15) /* sx, c */
  1455. +#define R1_CARD_ECC_DISABLED (1 << 14) /* sx, a */
  1456. +#define R1_ERASE_RESET (1 << 13) /* sr, c */
  1457. +#define R1_STATUS(x) (x & 0xFFFFE000)
  1458. +
  1459. +#define MMC_CARD_BUSY 0x80000000 /* Card Power up status bit */
  1460. +
  1461. +#define MMC_PROGRAM_CID 26 /* adtc R1 */
  1462. +#define MMC_PROGRAM_CSD 27 /* adtc R1 */
  1463. +
  1464. +#define MMC_GO_IRQ_STATE 40 /* bcr R5 */
  1465. +#define MMC_GEN_CMD 56 /* adtc [0] RD/WR R1b */
  1466. +#define MMC_LOCK_UNLOCK 42 /* adtc R1b */
  1467. +#define MMC_WRITE_DAT_UNTIL_STOP 20 /* adtc [31:0] data addr R1 */
  1468. +#define MMC_READ_DAT_UNTIL_STOP 11 /* adtc [31:0] dadr R1 */
  1469. +#define MMC_SEND_WRITE_PROT 30 /* adtc [31:0] wpdata addr R1 */
  1470. +
  1471. +
  1472. +enum mmc_result_t {
  1473. + MMC_NO_RESPONSE = -1,
  1474. + MMC_NO_ERROR = 0,
  1475. + MMC_ERROR_OUT_OF_RANGE,
  1476. + MMC_ERROR_ADDRESS,
  1477. + MMC_ERROR_BLOCK_LEN,
  1478. + MMC_ERROR_ERASE_SEQ,
  1479. + MMC_ERROR_ERASE_PARAM,
  1480. + MMC_ERROR_WP_VIOLATION,
  1481. + MMC_ERROR_CARD_IS_LOCKED,
  1482. + MMC_ERROR_LOCK_UNLOCK_FAILED,
  1483. + MMC_ERROR_COM_CRC,
  1484. + MMC_ERROR_ILLEGAL_COMMAND,
  1485. + MMC_ERROR_CARD_ECC_FAILED,
  1486. + MMC_ERROR_CC,
  1487. + MMC_ERROR_GENERAL,
  1488. + MMC_ERROR_UNDERRUN,
  1489. + MMC_ERROR_OVERRUN,
  1490. + MMC_ERROR_CID_CSD_OVERWRITE,
  1491. + MMC_ERROR_STATE_MISMATCH,
  1492. + MMC_ERROR_HEADER_MISMATCH,
  1493. + MMC_ERROR_TIMEOUT,
  1494. + MMC_ERROR_CRC,
  1495. + MMC_ERROR_DRIVER_FAILURE,
  1496. +};
  1497. +
  1498. +enum card_state {
  1499. + CARD_STATE_EMPTY = -1,
  1500. + CARD_STATE_IDLE = 0,
  1501. + CARD_STATE_READY = 1,
  1502. + CARD_STATE_IDENT = 2,
  1503. + CARD_STATE_STBY = 3,
  1504. + CARD_STATE_TRAN = 4,
  1505. + CARD_STATE_DATA = 5,
  1506. + CARD_STATE_RCV = 6,
  1507. + CARD_STATE_PRG = 7,
  1508. + CARD_STATE_DIS = 8,
  1509. +};
  1510. +
  1511. +enum mmc_rsp_t {
  1512. + RESPONSE_NONE = 0,
  1513. + RESPONSE_R1 = 1,
  1514. + RESPONSE_R1B = 2,
  1515. + RESPONSE_R2_CID = 3,
  1516. + RESPONSE_R2_CSD = 4,
  1517. + RESPONSE_R3 = 5,
  1518. + RESPONSE_R4 = 6,
  1519. + RESPONSE_R5 = 7,
  1520. + RESPONSE_R6 = 8,
  1521. +};
  1522. +
  1523. +struct mmc_response_r1 {
  1524. + u8 cmd;
  1525. + u32 status;
  1526. +};
  1527. +
  1528. +struct mmc_response_r3 {
  1529. + u32 ocr;
  1530. +};
  1531. +
  1532. +/* the information structure of MMC/SD Card */
  1533. +struct mmc_info {
  1534. + int id; /* Card index */
  1535. + int sd; /* MMC or SD card */
  1536. + int rca; /* RCA */
  1537. + u32 scr; /* SCR 63:32*/
  1538. + int flags; /* Ejected, inserted */
  1539. + enum card_state state; /* empty, ident, ready, whatever */
  1540. +
  1541. + /* Card specific information */
  1542. + struct mmc_cid cid;
  1543. + struct mmc_csd csd;
  1544. + u32 block_num;
  1545. + u32 block_len;
  1546. + u32 erase_unit;
  1547. +};
  1548. +
  1549. +struct mmc_info mmcinfo;
  1550. +
  1551. +struct mmc_request {
  1552. + int index; /* Slot index - used for CS lines */
  1553. + int cmd; /* Command to send */
  1554. + u32 arg; /* Argument to send */
  1555. + enum mmc_rsp_t rtype; /* Response type expected */
  1556. +
  1557. + /* Data transfer (these may be modified at the low level) */
  1558. + u16 nob; /* Number of blocks to transfer*/
  1559. + u16 block_len; /* Block length */
  1560. + u8 *buffer; /* Data buffer */
  1561. + u32 cnt; /* Data length, for PIO */
  1562. +
  1563. + /* Results */
  1564. + u8 response[18]; /* Buffer to store response - CRC is optional */
  1565. + enum mmc_result_t result;
  1566. +};
  1567. +
  1568. +char * mmc_result_to_string(int);
  1569. +int mmc_unpack_csd(struct mmc_request *request, struct mmc_csd *csd);
  1570. +int mmc_unpack_r1(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state);
  1571. +int mmc_unpack_r6(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, int *rca);
  1572. +int mmc_unpack_scr(struct mmc_request *request, struct mmc_response_r1 *r1, enum card_state state, u32 *scr);
  1573. +int mmc_unpack_cid(struct mmc_request *request, struct mmc_cid *cid);
  1574. +int mmc_unpack_r3(struct mmc_request *request, struct mmc_response_r3 *r3);
  1575. +
  1576. +void mmc_send_cmd(struct mmc_request *request, int cmd, u32 arg,
  1577. + u16 nob, u16 block_len, enum mmc_rsp_t rtype, u8 *buffer);
  1578. +u32 mmc_tran_speed(u8 ts);
  1579. +void jz_mmc_set_clock(int sd, u32 rate);
  1580. +
  1581. +static inline void mmc_simple_cmd(struct mmc_request *request, int cmd, u32 arg, enum mmc_rsp_t rtype)
  1582. +{
  1583. + mmc_send_cmd( request, cmd, arg, 0, 0, rtype, 0);
  1584. +}
  1585. +
  1586. +#endif /* __MMC_JZMMC_H__ */
  1587. diff --git a/include/configs/qi_lb60.h b/include/configs/qi_lb60.h
  1588. index 7bff444..7b33be0 100644
  1589. --- a/include/configs/qi_lb60.h
  1590. +++ b/include/configs/qi_lb60.h
  1591. @@ -31,6 +31,15 @@
  1592. /*
  1593. * Miscellaneous configurable options
  1594. */
  1595. +#define CONFIG_JZ4740_MMC
  1596. +#define CONFIG_MMC 1
  1597. +#define CONFIG_FAT 1
  1598. +#define CONFIG_DOS_PARTITION 1
  1599. +#define CONFIG_CMD_MMC
  1600. +#define CONFIG_CMD_FAT
  1601. +#define CONFIG_CMD_EXT2
  1602. +
  1603. +
  1604. #define CONFIG_SYS_SDRAM_BASE 0x80000000 /* Cached addr */
  1605. #define CONFIG_SYS_INIT_SP_OFFSET 0x400000
  1606. #define CONFIG_SYS_LOAD_ADDR 0x80600000
  1607. diff --git a/include/mmc.h b/include/mmc.h
  1608. index a13e2bd..3c4761c 100644
  1609. --- a/include/mmc.h
  1610. +++ b/include/mmc.h
  1611. @@ -283,4 +283,44 @@ struct mmc *mmc_spi_init(uint bus, uint cs, uint speed, uint mode);
  1612. int mmc_legacy_init(int verbose);
  1613. #endif
  1614. +struct mmc_csd
  1615. +{
  1616. + u8 csd_structure:2,
  1617. + spec_vers:4,
  1618. + rsvd1:2;
  1619. + u8 taac;
  1620. + u8 nsac;
  1621. + u8 tran_speed;
  1622. + u16 ccc:12,
  1623. + read_bl_len:4;
  1624. + u32 c_size:22;
  1625. + u64 read_bl_partial:1,
  1626. + write_blk_misalign:1,
  1627. + read_blk_misalign:1,
  1628. + dsr_imp:1,
  1629. + rsvd2:2,
  1630. + vdd_r_curr_min:3,
  1631. + vdd_r_curr_max:3,
  1632. + vdd_w_curr_min:3,
  1633. + vdd_w_curr_max:3,
  1634. + c_size_mult:3,
  1635. + sector_size:5,
  1636. + erase_grp_size:5,
  1637. + wp_grp_size:5,
  1638. + wp_grp_enable:1,
  1639. + default_ecc:2,
  1640. + r2w_factor:3,
  1641. + write_bl_len:4,
  1642. + write_bl_partial:1,
  1643. + rsvd3:5;
  1644. + u8 file_format_grp:1,
  1645. + copy:1,
  1646. + perm_write_protect:1,
  1647. + tmp_write_protect:1,
  1648. + file_format:2,
  1649. + ecc:2;
  1650. + u8 crc:7;
  1651. + u8 one:1;
  1652. +};
  1653. +
  1654. #endif /* _MMC_H_ */
  1655. --
  1656. 1.7.9.5