[U-Boot] [PATCH] omap3: mmc: mmc2 support

There are 3 MMC/SD/SDIO host controllers inside the device. This patch will support mmc2 and mmc3(mmc3 have not tested)
Signed-off-by: Minkyu Kang mk7.kang@samsung.com --- drivers/mmc/omap3_mmc.c | 74 ++++++++++++++++++++++++----- include/asm-arm/arch-omap3/mmc_host_def.h | 10 +++- include/asm-arm/arch-omap3/omap3.h | 3 + 3 files changed, 73 insertions(+), 14 deletions(-)
diff --git a/drivers/mmc/omap3_mmc.c b/drivers/mmc/omap3_mmc.c index e90db7e..934caff 100644 --- a/drivers/mmc/omap3_mmc.c +++ b/drivers/mmc/omap3_mmc.c @@ -51,7 +51,8 @@ const unsigned short mmc_transspeed_val[15][4] = {
mmc_card_data cur_card_data; static block_dev_desc_t mmc_blk_dev; -static hsmmc_t *mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE; +static hsmmc_t *mmc_base; +static int curr_device = -1;
block_dev_desc_t *mmc_get_dev(int dev) { @@ -62,10 +63,21 @@ void twl4030_mmc_config(void) { unsigned char data;
- data = DEV_GRP_P1; - i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEV_GRP, 1, &data, 1); - data = VMMC1_VSEL_30; - i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEDICATED, 1, &data, 1); + switch (curr_device) { + case 1: + data = DEV_GRP_P1; + i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEV_GRP, 1, &data, 1); + data = VMMC1_VSEL_30; + i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEDICATED, 1, &data, 1); + break; + case 2: + case 3: + data = DEV_GRP_P1; + i2c_write(PWRMGT_ADDR_ID4, VMMC2_DEV_GRP, 1, &data, 1); + data = VMMC2_VSEL_185; + i2c_write(PWRMGT_ADDR_ID4, VMMC2_DEDICATED, 1, &data, 1); + break; + } }
unsigned char mmc_board_init(void) @@ -74,12 +86,21 @@ unsigned char mmc_board_init(void)
twl4030_mmc_config();
- writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 | - PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0, - &t2_base->pbias_lite); + switch (curr_device) { + case 1: + writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 | + PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0, + &t2_base->pbias_lite);
- writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL, - &t2_base->devconf0); + writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL, + &t2_base->devconf0); + break; + case 2: + case 3: + writel(readl(&t2_base->devconf1) | MMCSDIO2ADPCLKISEL, + &t2_base->devconf1); + break; + }
return 1; } @@ -525,8 +546,37 @@ unsigned long mmc_bread(int dev_num, unsigned long blknr, lbaint_t blkcnt, return 1; }
-int mmc_legacy_init(int verbose) +int mmc_set_dev(int dev) +{ + if (dev < 0) { + printf("unknwon device\n"); + return 1; + } else { + switch (dev) { + case 1: + mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC1; + break; + case 2: + mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC2; + break; + case 3: + mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC3; + break; + default: + printf("unknwon device\n"); + return 1; + } + curr_device = dev; + } + + return 0; +} + +int mmc_legacy_init(int dev) { + if (mmc_set_dev(dev) != 0) + return 1; + if (configure_mmc(&cur_card_data) != 1) return 1;
@@ -538,7 +588,7 @@ int mmc_legacy_init(int verbose)
/* FIXME fill in the correct size (is set to 32MByte) */ mmc_blk_dev.blksz = MMCSD_SECTOR_SIZE; - mmc_blk_dev.lba = 0x10000; + mmc_blk_dev.lba = cur_card_data.size; mmc_blk_dev.removable = 0; mmc_blk_dev.block_read = mmc_bread;
diff --git a/include/asm-arm/arch-omap3/mmc_host_def.h b/include/asm-arm/arch-omap3/mmc_host_def.h index aa751c9..8b234ef 100644 --- a/include/asm-arm/arch-omap3/mmc_host_def.h +++ b/include/asm-arm/arch-omap3/mmc_host_def.h @@ -31,7 +31,9 @@ typedef struct t2 { unsigned char res1[0x274]; unsigned int devconf0; /* 0x274 */ - unsigned char res2[0x2A8]; + unsigned char res2[0x60]; + unsigned int devconf1; /* 0x2D8 */ + unsigned char res3[0x244]; unsigned int pbias_lite; /* 0x520 */ } t2_t;
@@ -41,10 +43,14 @@ typedef struct t2 { #define PBIASSPEEDCTRL0 (1 << 2) #define PBIASLITEPWRDNZ1 (1 << 9)
+#define MMCSDIO2ADPCLKISEL (1 << 6) + /* * OMAP HSMMC register definitions */ -#define OMAP_HSMMC_BASE 0x4809C000 +#define OMAP_HSMMC_BASE_MMC1 0x4809C000 +#define OMAP_HSMMC_BASE_MMC2 0x480B4000 +#define OMAP_HSMMC_BASE_MMC3 0x480AD000
typedef struct hsmmc { unsigned char res1[0x10]; diff --git a/include/asm-arm/arch-omap3/omap3.h b/include/asm-arm/arch-omap3/omap3.h index 8c9656f..b5b5def 100644 --- a/include/asm-arm/arch-omap3/omap3.h +++ b/include/asm-arm/arch-omap3/omap3.h @@ -206,6 +206,8 @@ typedef struct gpio { #define VAUX3_DEDICATED 0x7D #define VMMC1_DEV_GRP 0x82 #define VMMC1_DEDICATED 0x85 +#define VMMC2_DEV_GRP 0x86 +#define VMMC2_DEDICATED 0x89 #define VPLL2_DEV_GRP 0x8E #define VPLL2_DEDICATED 0x91 #define VDAC_DEV_GRP 0x96 @@ -219,5 +221,6 @@ typedef struct gpio { #define VPLL2_VSEL_18 0x05 #define VDAC_VSEL_18 0x03 #define VMMC1_VSEL_30 0x02 +#define VMMC2_VSEL_185 0x06
#endif

On 14:07 Sat 28 Mar , Minkyu Kang wrote:
There are 3 MMC/SD/SDIO host controllers inside the device. This patch will support mmc2 and mmc3(mmc3 have not tested)
Signed-off-by: Minkyu Kang mk7.kang@samsung.com
drivers/mmc/omap3_mmc.c | 74 ++++++++++++++++++++++++----- include/asm-arm/arch-omap3/mmc_host_def.h | 10 +++- include/asm-arm/arch-omap3/omap3.h | 3 + 3 files changed, 73 insertions(+), 14 deletions(-)
diff --git a/drivers/mmc/omap3_mmc.c b/drivers/mmc/omap3_mmc.c index e90db7e..934caff 100644 --- a/drivers/mmc/omap3_mmc.c +++ b/drivers/mmc/omap3_mmc.c @@ -51,7 +51,8 @@ const unsigned short mmc_transspeed_val[15][4] = {
mmc_card_data cur_card_data; static block_dev_desc_t mmc_blk_dev; -static hsmmc_t *mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE; +static hsmmc_t *mmc_base; +static int curr_device = -1;
block_dev_desc_t *mmc_get_dev(int dev) { @@ -62,10 +63,21 @@ void twl4030_mmc_config(void) { unsigned char data;
- data = DEV_GRP_P1;
- i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEV_GRP, 1, &data, 1);
- data = VMMC1_VSEL_30;
- i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEDICATED, 1, &data, 1);
- switch (curr_device) {
- case 1:
data = DEV_GRP_P1;
i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEV_GRP, 1, &data, 1);
data = VMMC1_VSEL_30;
i2c_write(PWRMGT_ADDR_ID4, VMMC1_DEDICATED, 1, &data, 1);
break;
- case 2:
- case 3:
data = DEV_GRP_P1;
i2c_write(PWRMGT_ADDR_ID4, VMMC2_DEV_GRP, 1, &data, 1);
data = VMMC2_VSEL_185;
i2c_write(PWRMGT_ADDR_ID4, VMMC2_DEDICATED, 1, &data, 1);
break;
- }
}
unsigned char mmc_board_init(void)
unsigned char? why
@@ -74,12 +86,21 @@ unsigned char mmc_board_init(void)
twl4030_mmc_config();
- writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 |
PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0,
&t2_base->pbias_lite);
- switch (curr_device) {
- case 1:
writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 |
PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0,
&t2_base->pbias_lite);
- writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL,
&t2_base->devconf0);
writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL,
&t2_base->devconf0);
break;
- case 2:
- case 3:
writel(readl(&t2_base->devconf1) | MMCSDIO2ADPCLKISEL,
&t2_base->devconf1);
break;
- }
please only active code when the user activate the mmcx support
how your driver will work it I want to have two mmc support at the sametime??
return 1; } @@ -525,8 +546,37 @@ unsigned long mmc_bread(int dev_num, unsigned long blknr, lbaint_t blkcnt, return 1; }
-int mmc_legacy_init(int verbose) +int mmc_set_dev(int dev) +{
- if (dev < 0) {
printf("unknwon device\n");
return 1;
no need already done in the switch please remove
- } else {
switch (dev) {
case 1:
mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC1;
break;
case 2:
mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC2;
break;
case 3:
mmc_base = (hsmmc_t *)OMAP_HSMMC_BASE_MMC3;
break;
has precedently please activate it only when it's need for each MMC slot
default:
printf("unknwon device\n");
return 1;
}
curr_device = dev;
- }
- return 0;
+}
+int mmc_legacy_init(int dev) {
- if (mmc_set_dev(dev) != 0)
return 1;
btw it will better to move to the new Framework
if (configure_mmc(&cur_card_data) != 1) return 1;
@@ -538,7 +588,7 @@ int mmc_legacy_init(int verbose)
/* FIXME fill in the correct size (is set to 32MByte) */ mmc_blk_dev.blksz = MMCSD_SECTOR_SIZE;
- mmc_blk_dev.lba = 0x10000;
- mmc_blk_dev.lba = cur_card_data.size; mmc_blk_dev.removable = 0; mmc_blk_dev.block_read = mmc_bread;
diff --git a/include/asm-arm/arch-omap3/mmc_host_def.h b/include/asm-arm/arch-omap3/mmc_host_def.h index aa751c9..8b234ef 100644 --- a/include/asm-arm/arch-omap3/mmc_host_def.h +++ b/include/asm-arm/arch-omap3/mmc_host_def.h @@ -31,7 +31,9 @@ typedef struct t2 { unsigned char res1[0x274]; unsigned int devconf0; /* 0x274 */
- unsigned char res2[0x2A8];
- unsigned char res2[0x60];
- unsigned int devconf1; /* 0x2D8 */
- unsigned char res3[0x244]; unsigned int pbias_lite; /* 0x520 */
} t2_t;
@@ -41,10 +43,14 @@ typedef struct t2 { #define PBIASSPEEDCTRL0 (1 << 2) #define PBIASLITEPWRDNZ1 (1 << 9)
+#define MMCSDIO2ADPCLKISEL (1 << 6)
/*
- OMAP HSMMC register definitions
*/ -#define OMAP_HSMMC_BASE 0x4809C000 +#define OMAP_HSMMC_BASE_MMC1 0x4809C000 +#define OMAP_HSMMC_BASE_MMC2 0x480B4000 +#define OMAP_HSMMC_BASE_MMC3 0x480AD000
it's really a shame that TI does not make it in order and at the same shift so we could do this #define OMAP_HSMMC_BASE(x) (0x4809C000 + (shift << x))
Best Regards, J.

Hi,
}
unsigned char mmc_board_init(void)
unsigned char? why
in omap3_mmc.c, many functions return the unsigned char. I don't know why too :( but if we need it can be changed.
- switch (curr_device) {
- case 1:
writel(readl(&t2_base->pbias_lite) | PBIASLITEPWRDNZ1 |
PBIASSPEEDCTRL0 | PBIASLITEPWRDNZ0,
&t2_base->pbias_lite);
- writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL,
&t2_base->devconf0);
writel(readl(&t2_base->devconf0) | MMCSDIO1ADPCLKISEL,
&t2_base->devconf0);
break;
- case 2:
- case 3:
writel(readl(&t2_base->devconf1) | MMCSDIO2ADPCLKISEL,
&t2_base->devconf1);
break;
- }
please only active code when the user activate the mmcx support
how your driver will work it I want to have two mmc support at the sametime??
I announced the patch for mmc command (but not applied yet) please check it http://lists.denx.de/pipermail/u-boot/2009-March/049835.html
+int mmc_legacy_init(int dev) {
- if (mmc_set_dev(dev) != 0)
return 1;
btw it will better to move to the new Framework
new Framework is what? do you mean generic mmc?
/*
- OMAP HSMMC register definitions
*/ -#define OMAP_HSMMC_BASE 0x4809C000 +#define OMAP_HSMMC_BASE_MMC1 0x4809C000 +#define OMAP_HSMMC_BASE_MMC2 0x480B4000 +#define OMAP_HSMMC_BASE_MMC3 0x480AD000
it's really a shame that TI does not make it in order and at the same shift so we could do this #define OMAP_HSMMC_BASE(x) (0x4809C000 + (shift << x))
right but.. I can't find any patterns for OMAP's HSMMC register. also HSMMC register is defined separately at linux kernel code (please see arch/arm/plat-omap/include/mach/mmc.h)
Many thanks Minkyu Kang
participants (2)
-
Jean-Christophe PLAGNIOL-VILLARD
-
Minkyu Kang