aboutsummaryrefslogtreecommitdiffstats
path: root/target/linux/s3c24xx/patches/0218-debug-add-glamo-drive-strength-module-param.patch.patch
blob: dd0fcff816ba188a2b7d5d8a800d3584e7462277 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
From e1bc0be9f95559ae154d24b353e404c781798da1 Mon Sep 17 00:00:00 2001
From: Andy Green <andy@openmoko.com>
Date: Fri, 25 Jul 2008 23:06:20 +0100
Subject: [PATCH] debug-add-glamo-drive-strength-module-param.patch
 Suggested-by: Werner Almesberger <werner@openmoko.org>

This patch allows users to control two additional settings
in Glamo MCI driver from kernel commandline or module
parameters.


First is Glamo drive strength on SD IOs including CLK.
This ranges from 0 (weakest) to 3 (strongest).

echo 0 > /sys/module/glamo_mci/parameters/sd_drive

(Changes to this take effect on next SD Card transaction)

or, from kernel commandline

glamo_mci.sd_drive=0

On tests here with 0 strength, communication to SD card
(shipped 512MB Sandisk) seemed fine, and a dd of 10MB
urandom had the same md5 when written to cache as after
a reboot.  I set the default to 2.


Second is whether we allow SD_CLK when the SD interface
is idle.

# stop the clock when we are idle (default)
echo 0 > /sys/module/glamo_mci/parameters/sd_idleclk

# run the SD clock all the time
echo 1 > /sys/module/glamo_mci/parameters/sd_idleclk

(changes take effect on next SD Card transaction)

From kernel commandline, eg:

glamo_mci.sd_idleclk=1

Normally you don't want to run the SD Clock all the time.


Signed-off-by: Andy Green <andy@openmoko.com>
---
 drivers/mfd/glamo/glamo-mci.c |   59 +++++++++++++++++++++++++++++++---------
 1 files changed, 45 insertions(+), 14 deletions(-)

diff --git a/drivers/mfd/glamo/glamo-mci.c b/drivers/mfd/glamo/glamo-mci.c
index 93f4074..4615033 100644
--- a/drivers/mfd/glamo/glamo-mci.c
+++ b/drivers/mfd/glamo/glamo-mci.c
@@ -56,6 +56,32 @@ static void glamo_mci_send_request(struct mmc_host *mmc);
 static int sd_max_clk = 50000000 / 3;
 module_param(sd_max_clk, int, 0644);
 
+/*
+ * SD Signal drive strength
+ *
+ * you can override this on kernel commandline using
+ *
+ *   glamo_mci.sd_drive=0
+ *
+ * for example
+ */
+
+static int sd_drive = 2;
+module_param(sd_drive, int, 0644);
+
+/*
+ * SD allow SD clock to run while idle
+ *
+ * you can override this on kernel commandline using
+ *
+ *   glamo_mci.sd_idleclk=0
+ *
+ * for example
+ */
+
+static int sd_idleclk = 0; /* disallow idle clock by default */
+module_param(sd_idleclk, int, 0644);
+
 
 
 unsigned char CRC7(u8 * pu8, int cnt)
@@ -239,7 +265,9 @@ static int __glamo_mci_set_card_clock(struct glamo_mci_host *host, int freq,
 		if (division)
 			*division = 0xff;
 
-		__glamo_mci_fix_card_div(host, -1); /* clock off */
+		if (!sd_idleclk)
+			/* clock off */
+			__glamo_mci_fix_card_div(host, -1);
 	}
 
 	return real_rate;
@@ -294,8 +322,9 @@ static void glamo_mci_irq(unsigned int irq, struct irq_desc *desc)
 		host->cmd_is_stop = 0;
 	}
 
-	/* clock off */
-	__glamo_mci_fix_card_div(host, -1);
+	if (!sd_idleclk)
+		/* clock off */
+		__glamo_mci_fix_card_div(host, -1);
 
 done:
 	host->complete_what = COMPLETION_NONE;
@@ -428,12 +457,10 @@ static int glamo_mci_send_command(struct glamo_mci_host *host,
 	} else
 		writew(0xfff, host->base + GLAMO_REG_MMC_TIMEOUT);
 
-	/* Generate interrupt on txfer; drive strength max */
-	writew_dly((readw_dly(host->base + GLAMO_REG_MMC_BASIC) & 0xfe) |
+	/* Generate interrupt on txfer */
+	writew_dly((readw_dly(host->base + GLAMO_REG_MMC_BASIC) & 0x3e) |
 		   0x0800 | GLAMO_BASIC_MMC_NO_CLK_RD_WAIT |
-		   GLAMO_BASIC_MMC_EN_COMPL_INT |
-		   GLAMO_BASIC_MMC_EN_DR_STR0 |
-		   GLAMO_BASIC_MMC_EN_DR_STR1,
+		   GLAMO_BASIC_MMC_EN_COMPL_INT | (sd_drive << 6),
 		   host->base + GLAMO_REG_MMC_BASIC);
 
 	/* send the command out on the wire */
@@ -620,8 +647,9 @@ done:
 	host->mrq = NULL;
 	mmc_request_done(host->mmc, cmd->mrq);
 bail:
-	/* stop the clock to card */
-	__glamo_mci_fix_card_div(host, -1);
+	if (!sd_idleclk)
+		/* stop the clock to card */
+		__glamo_mci_fix_card_div(host, -1);
 }
 
 static void glamo_mci_request(struct mmc_host *mmc, struct mmc_request *mrq)
@@ -687,8 +715,9 @@ static void glamo_mci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
 	host->real_rate = __glamo_mci_set_card_clock(host, ios->clock, &div);
 	host->clk_div = div;
 
-	/* stop the clock to card, because we are idle until transfer */
-	__glamo_mci_fix_card_div(host, -1);
+	if (!sd_idleclk)
+		/* stop the clock to card, because we are idle until transfer */
+		__glamo_mci_fix_card_div(host, -1);
 
 	if ((ios->power_mode == MMC_POWER_ON) ||
 	    (ios->power_mode == MMC_POWER_UP)) {
@@ -705,8 +734,10 @@ static void glamo_mci_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
 	if (host->bus_width == MMC_BUS_WIDTH_4)
 		n = GLAMO_BASIC_MMC_EN_4BIT_DATA;
 	writew_dly((readw_dly(host->base + GLAMO_REG_MMC_BASIC) &
-					  (~GLAMO_BASIC_MMC_EN_4BIT_DATA)) | n,
-					      host->base + GLAMO_REG_MMC_BASIC);
+					  (~(GLAMO_BASIC_MMC_EN_4BIT_DATA |
+					     GLAMO_BASIC_MMC_EN_DR_STR0 |
+					     GLAMO_BASIC_MMC_EN_DR_STR1))) | n |
+			       sd_drive << 6, host->base + GLAMO_REG_MMC_BASIC);
 }
 
 
-- 
1.5.6.3