2011-02-06 18:03:56

by Tardy, Pierre

[permalink] [raw]
Subject: [PATCH v2 0/3] introduce mmc per device quirks

This patchset is the resend and cleanup of
the mmc per device quirks patchset.

User of the quirks is attached, which allows
clock gating framework to be used for specific sdio
card that are known to work.

Pierre Tardy (3):
mmc: add per device quirk placeholder
mmc: add MMC_QUIRK_BROKEN_CLK_GATING
mmc: remove BROCKEN_CLK_GATING quirk for wl1271

drivers/mmc/core/Makefile | 3 +-
drivers/mmc/core/core.h | 2 +
drivers/mmc/core/host.c | 5 +--
drivers/mmc/core/quirks.c | 85 +++++++++++++++++++++++++++++++++++++++++++++
drivers/mmc/core/sdio.c | 1 +
include/linux/mmc/card.h | 3 ++
6 files changed, 94 insertions(+), 5 deletions(-)
create mode 100644 drivers/mmc/core/quirks.c

--
1.7.2.3

---------------------------------------------------------------------
Intel Corporation SAS (French simplified joint stock company)
Registered headquarters: "Les Montalets"- 2, rue de Paris,
92196 Meudon Cedex, France
Registration Number: 302 456 199 R.C.S. NANTERRE
Capital: 4,572,000 Euros

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.


2011-02-06 18:04:01

by Tardy, Pierre

[permalink] [raw]
Subject: [PATCH v2 1/3] mmc: add per device quirk placeholder

Some cards have quirks valid for every platforms
using current platform quirk hooks leads to a lot
of code and debug duplication.

So we inspire a bit from what exists in PCI subsystem
and do out own per vendorid/deviceid quirk
We still drop the complexity of the pci quirk system
(with special section tables, and so on)
That can be added later if needed.

Signed-off-by: Pierre Tardy <[email protected]>
Acked-by: Linus Walleij <[email protected]>
Acked-by: Ohad Ben-Cohen <[email protected]>
---
drivers/mmc/core/Makefile | 3 +-
drivers/mmc/core/core.h | 2 +
drivers/mmc/core/quirks.c | 62 +++++++++++++++++++++++++++++++++++++++++++++
drivers/mmc/core/sdio.c | 1 +
include/linux/mmc/card.h | 2 +
5 files changed, 69 insertions(+), 1 deletions(-)

diff --git a/drivers/mmc/core/Makefile b/drivers/mmc/core/Makefile
index 86b4791..6395019 100644
--- a/drivers/mmc/core/Makefile
+++ b/drivers/mmc/core/Makefile
@@ -6,6 +6,7 @@ obj-$(CONFIG_MMC) += mmc_core.o
mmc_core-y := core.o bus.o host.o \
mmc.o mmc_ops.o sd.o sd_ops.o \
sdio.o sdio_ops.o sdio_bus.o \
- sdio_cis.o sdio_io.o sdio_irq.o
+ sdio_cis.o sdio_io.o sdio_irq.o \
+ quirks.o

mmc_core-$(CONFIG_DEBUG_FS) += debugfs.o
diff --git a/drivers/mmc/core/core.h b/drivers/mmc/core/core.h
index ca1fdde..20b1c08 100644
--- a/drivers/mmc/core/core.h
+++ b/drivers/mmc/core/core.h
@@ -61,6 +61,8 @@ int mmc_attach_mmc(struct mmc_host *host);
int mmc_attach_sd(struct mmc_host *host);
int mmc_attach_sdio(struct mmc_host *host);

+void mmc_fixup_device(struct mmc_card *card);
+
/* Module parameters */
extern int use_spi_crc;

diff --git a/drivers/mmc/core/quirks.c b/drivers/mmc/core/quirks.c
new file mode 100644
index 0000000..aa811fc
--- /dev/null
+++ b/drivers/mmc/core/quirks.c
@@ -0,0 +1,62 @@
+/*
+ * This file contains work-arounds for many known sdio hardware
+ * bugs.
+ *
+ * Copyright (c) 2011 Pierre Tardy <[email protected]>
+ * Inspired from pci fixup code:
+ * Copyright (c) 1999 Martin Mares <[email protected]>
+ *
+ */
+
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <linux/mmc/card.h>
+#include <linux/mod_devicetable.h>
+
+/*
+ * The world is not perfect and supplies us with broken mmc/sdio devices.
+ * For at least a part of these bugs we need a work-around
+ */
+
+struct mmc_fixup {
+ u16 vendor, device; /* You can use SDIO_ANY_ID here of course */
+ void (*vendor_fixup)(struct mmc_card *card, int data);
+ int data;
+};
+
+/*
+ * This hook just adds a quirk unconditionnally
+ */
+static void __maybe_unused add_quirk(struct mmc_card *card, int data)
+{
+ card->quirks |= data;
+}
+
+/*
+ * This hook just removes a quirk unconditionnally
+ */
+static void __maybe_unused remove_quirk(struct mmc_card *card, int data)
+{
+ card->quirks &= ~data;
+}
+
+static const struct mmc_fixup mmc_fixup_methods[] = {
+ { 0 }
+};
+
+void mmc_fixup_device(struct mmc_card *card)
+{
+ const struct mmc_fixup *f;
+
+ for (f = mmc_fixup_methods; f->vendor_fixup; f++) {
+ if ((f->vendor == card->cis.vendor
+ || f->vendor == (u16) SDIO_ANY_ID) &&
+ (f->device == card->cis.device
+ || f->device == (u16) SDIO_ANY_ID)) {
+ dev_dbg(&card->dev, "calling %pF\n", f->vendor_fixup);
+ f->vendor_fixup(card, f->data);
+ }
+ }
+}
+EXPORT_SYMBOL(mmc_fixup_device);
+
diff --git a/drivers/mmc/core/sdio.c b/drivers/mmc/core/sdio.c
index 5c4a54d..617e9ad 100644
--- a/drivers/mmc/core/sdio.c
+++ b/drivers/mmc/core/sdio.c
@@ -458,6 +458,7 @@ static int mmc_sdio_init_card(struct mmc_host *host, u32 ocr,

card = oldcard;
}
+ mmc_fixup_device(card);

if (card->type == MMC_TYPE_SD_COMBO) {
err = mmc_sd_setup_card(host, card, oldcard != NULL);
diff --git a/include/linux/mmc/card.h b/include/linux/mmc/card.h
index 4652cf9..ad74138 100644
--- a/include/linux/mmc/card.h
+++ b/include/linux/mmc/card.h
@@ -151,6 +151,8 @@ struct mmc_card {
struct dentry *debugfs_root;
};

+void mmc_fixup_device(struct mmc_card *dev);
+
#define mmc_card_mmc(c) ((c)->type == MMC_TYPE_MMC)
#define mmc_card_sd(c) ((c)->type == MMC_TYPE_SD)
#define mmc_card_sdio(c) ((c)->type == MMC_TYPE_SDIO)
--
1.7.2.3

---------------------------------------------------------------------
Intel Corporation SAS (French simplified joint stock company)
Registered headquarters: "Les Montalets"- 2, rue de Paris,
92196 Meudon Cedex, France
Registration Number: 302 456 199 R.C.S. NANTERRE
Capital: 4,572,000 Euros

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.

2011-02-06 18:04:15

by Tardy, Pierre

[permalink] [raw]
Subject: [PATCH v2 2/3] mmc: add MMC_QUIRK_BROKEN_CLK_GATING

From: Pierre Tardy <[email protected]>

Some sdio card are not following sdio standard, and does not work
when the sdio bus's clock is gated

To keep functionnality for all legacy driver, we turn this quirk on
for every sdio card.
Drivers needs to disable the quirk manually when someone verified that their
supported card works with clock gating.

Signed-off-by: Pierre Tardy <[email protected]>
---
drivers/mmc/core/host.c | 5 +----
drivers/mmc/core/quirks.c | 13 +++++++++++++
include/linux/mmc/card.h | 1 +
3 files changed, 15 insertions(+), 4 deletions(-)

diff --git a/drivers/mmc/core/host.c b/drivers/mmc/core/host.c
index b3ac6c5..461e6a1 100644
--- a/drivers/mmc/core/host.c
+++ b/drivers/mmc/core/host.c
@@ -160,10 +160,7 @@ static bool mmc_host_may_gate_card(struct mmc_card *card)
* gate the clock, because there is somebody out there that may still
* be using it.
*/
- if (mmc_card_sdio(card))
- return false;
-
- return true;
+ return !(card->quirks & MMC_QUIRK_BROKEN_CLK_GATING);
}

/**
diff --git a/drivers/mmc/core/quirks.c b/drivers/mmc/core/quirks.c
index aa811fc..d004106 100644
--- a/drivers/mmc/core/quirks.c
+++ b/drivers/mmc/core/quirks.c
@@ -40,7 +40,20 @@ static void __maybe_unused remove_quirk(struct mmc_card *card, int data)
card->quirks &= ~data;
}

+/*
+ * This hook just adds a quirk for all sdio devices
+ */
+static void add_quirk_for_sdio_devices(struct mmc_card *card, int data)
+{
+ if (mmc_card_sdio(card))
+ card->quirks |= data;
+}
+
static const struct mmc_fixup mmc_fixup_methods[] = {
+ /* by default sdio devices are considered CLK_GATING broken */
+ /* good cards will be whitelisted as they are tested */
+ { SDIO_ANY_ID, SDIO_ANY_ID,
+ add_quirk_for_sdio_devices, MMC_QUIRK_BROKEN_CLK_GATING }
{ 0 }
};

diff --git a/include/linux/mmc/card.h b/include/linux/mmc/card.h
index ad74138..adb4888 100644
--- a/include/linux/mmc/card.h
+++ b/include/linux/mmc/card.h
@@ -124,6 +124,7 @@ struct mmc_card {
/* for byte mode */
#define MMC_QUIRK_NONSTD_SDIO (1<<2) /* non-standard SDIO card attached */
/* (missing CIA registers) */
+#define MMC_QUIRK_BROKEN_CLK_GATING (1<<3) /* clock gating the sdio bus will make card fail */

unsigned int erase_size; /* erase size in sectors */
unsigned int erase_shift; /* if erase unit is power 2 */
--
1.7.2.3

---------------------------------------------------------------------
Intel Corporation SAS (French simplified joint stock company)
Registered headquarters: "Les Montalets"- 2, rue de Paris,
92196 Meudon Cedex, France
Registration Number: 302 456 199 R.C.S. NANTERRE
Capital: 4,572,000 Euros

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.

2011-02-06 18:04:34

by Tardy, Pierre

[permalink] [raw]
Subject: [PATCH v2 3/3] mmc: remove BROCKEN_CLK_GATING quirk for wl1271

This sdio card is supporting having its sdio clock shutdown
It is also not using the SDIO IRQ, but rather uses
a side gpio irq.

Signed-off-by: Pierre Tardy <[email protected]>
---
drivers/mmc/core/quirks.c | 12 +++++++++++-
1 files changed, 11 insertions(+), 1 deletions(-)

diff --git a/drivers/mmc/core/quirks.c b/drivers/mmc/core/quirks.c
index d004106..4fb16ac 100644
--- a/drivers/mmc/core/quirks.c
+++ b/drivers/mmc/core/quirks.c
@@ -49,11 +49,21 @@ static void add_quirk_for_sdio_devices(struct mmc_card *card, int data)
card->quirks |= data;
}

+#ifndef SDIO_VENDOR_ID_TI
+#define SDIO_VENDOR_ID_TI 0x0097
+#endif
+
+#ifndef SDIO_DEVICE_ID_TI_WL1271
+#define SDIO_DEVICE_ID_TI_WL1271 0x4076
+#endif
+
static const struct mmc_fixup mmc_fixup_methods[] = {
/* by default sdio devices are considered CLK_GATING broken */
/* good cards will be whitelisted as they are tested */
{ SDIO_ANY_ID, SDIO_ANY_ID,
- add_quirk_for_sdio_devices, MMC_QUIRK_BROKEN_CLK_GATING }
+ add_quirk_for_sdio_devices, MMC_QUIRK_BROKEN_CLK_GATING },
+ { SDIO_VENDOR_ID_TI, SDIO_DEVICE_ID_TI_WL1271,
+ remove_quirk, MMC_QUIRK_BROKEN_CLK_GATING },
{ 0 }
};

--
1.7.2.3

---------------------------------------------------------------------
Intel Corporation SAS (French simplified joint stock company)
Registered headquarters: "Les Montalets"- 2, rue de Paris,
92196 Meudon Cedex, France
Registration Number: 302 456 199 R.C.S. NANTERRE
Capital: 4,572,000 Euros

This e-mail and any attachments may contain confidential material for
the sole use of the intended recipient(s). Any review or distribution
by others is strictly prohibited. If you are not the intended
recipient, please contact the sender and delete all copies.

2011-02-06 20:37:08

by Chris Ball

[permalink] [raw]
Subject: Re: [PATCH v2 0/3] introduce mmc per device quirks

On Sun, Feb 06, 2011 at 07:03:45PM +0100, Pierre Tardy wrote:
> This patchset is the resend and cleanup of
> the mmc per device quirks patchset.
>
> User of the quirks is attached, which allows
> clock gating framework to be used for specific sdio
> card that are known to work.
>
> Pierre Tardy (3):
> mmc: add per device quirk placeholder
> mmc: add MMC_QUIRK_BROKEN_CLK_GATING
> mmc: remove BROCKEN_CLK_GATING quirk for wl1271

Looks good, pushed to mmc-next, thanks!

--
Chris Ball <[email protected]> <http://printf.net/>
One Laptop Per Child