LinuxPPC-Dev Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 2/7] Update mpic to use dcr_host_t.base
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

Now that dcr_host_t contains the base address, we can use that in the mpic
code, rather than storing it separately.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 arch/powerpc/sysdev/mpic.c |   28 +++++++++++-----------------
 include/asm-powerpc/mpic.h |    6 ------
 2 files changed, 11 insertions(+), 23 deletions(-)

diff --git a/arch/powerpc/sysdev/mpic.c b/arch/powerpc/sysdev/mpic.c
index 8de29f2..16b1f4b 100644
--- a/arch/powerpc/sysdev/mpic.c
+++ b/arch/powerpc/sysdev/mpic.c
@@ -156,8 +156,7 @@ static inline u32 _mpic_read(enum mpic_reg_type type,
 	switch(type) {
 #ifdef CONFIG_PPC_DCR
 	case mpic_access_dcr:
-		return dcr_read(rb->dhost,
-				rb->dbase + reg + rb->doff);
+		return dcr_read(rb->dhost, rb->dhost.base + reg);
 #endif
 	case mpic_access_mmio_be:
 		return in_be32(rb->base + (reg >> 2));
@@ -174,8 +173,7 @@ static inline void _mpic_write(enum mpic_reg_type type,
 	switch(type) {
 #ifdef CONFIG_PPC_DCR
 	case mpic_access_dcr:
-		return dcr_write(rb->dhost,
-				 rb->dbase + reg + rb->doff, value);
+		return dcr_write(rb->dhost, rb->dhost.base + reg, value);
 #endif
 	case mpic_access_mmio_be:
 		return out_be32(rb->base + (reg >> 2), value);
@@ -279,9 +277,11 @@ static void _mpic_map_mmio(struct mpic *mpic, unsigned long phys_addr,
 static void _mpic_map_dcr(struct mpic *mpic, struct mpic_reg_bank *rb,
 			  unsigned int offset, unsigned int size)
 {
-	rb->dbase = mpic->dcr_base;
-	rb->doff = offset;
-	rb->dhost = dcr_map(mpic->irqhost->of_node, rb->dbase + rb->doff, size);
+	const u32 *dbasep;
+
+	dbasep = of_get_property(mpic->irqhost->of_node, "dcr-reg", NULL);
+
+	rb->dhost = dcr_map(mpic->irqhost->of_node, *dbasep + offset, size);
 	BUG_ON(!DCR_MAP_OK(rb->dhost));
 }
 
@@ -1075,20 +1075,14 @@ struct mpic * __init mpic_alloc(struct device_node *node,
 	BUG_ON(paddr == 0 && node == NULL);
 
 	/* If no physical address passed in, check if it's dcr based */
-	if (paddr == 0 && of_get_property(node, "dcr-reg", NULL) != NULL)
-		mpic->flags |= MPIC_USES_DCR;
-
+	if (paddr == 0 && of_get_property(node, "dcr-reg", NULL) != NULL) {
 #ifdef CONFIG_PPC_DCR
-	if (mpic->flags & MPIC_USES_DCR) {
-		const u32 *dbasep;
-		dbasep = of_get_property(node, "dcr-reg", NULL);
-		BUG_ON(dbasep == NULL);
-		mpic->dcr_base = *dbasep;
+		mpic->flags |= MPIC_USES_DCR;
 		mpic->reg_type = mpic_access_dcr;
-	}
 #else
-	BUG_ON (mpic->flags & MPIC_USES_DCR);
+		BUG();
 #endif /* CONFIG_PPC_DCR */
+	}
 
 	/* If the MPIC is not DCR based, and no physical address was passed
 	 * in, try to obtain one
diff --git a/include/asm-powerpc/mpic.h b/include/asm-powerpc/mpic.h
index edb4a7c..ae84dde 100644
--- a/include/asm-powerpc/mpic.h
+++ b/include/asm-powerpc/mpic.h
@@ -224,8 +224,6 @@ struct mpic_reg_bank {
 	u32 __iomem	*base;
 #ifdef CONFIG_PPC_DCR
 	dcr_host_t	dhost;
-	unsigned int	dbase;
-	unsigned int	doff;
 #endif /* CONFIG_PPC_DCR */
 };
 
@@ -289,10 +287,6 @@ struct mpic
 	struct mpic_reg_bank	cpuregs[MPIC_MAX_CPUS];
 	struct mpic_reg_bank	isus[MPIC_MAX_ISU];
 
-#ifdef CONFIG_PPC_DCR
-	unsigned int		dcr_base;
-#endif
-
 	/* Protected sources */
 	unsigned long		*protected;
 
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* [PATCH 3/7] Use dcr_host_t.base in ibm_emac_mal
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

This requires us to do a sort-of fake dcr_map(), so that base is set
properly. This will be fixed/removed when the device-tree-aware emac driver
is merged.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 drivers/net/ibm_emac/ibm_emac_mal.c |    5 ++++-
 drivers/net/ibm_emac/ibm_emac_mal.h |    5 ++---
 2 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/drivers/net/ibm_emac/ibm_emac_mal.c b/drivers/net/ibm_emac/ibm_emac_mal.c
index cabd984..b08da96 100644
--- a/drivers/net/ibm_emac/ibm_emac_mal.c
+++ b/drivers/net/ibm_emac/ibm_emac_mal.c
@@ -421,7 +421,10 @@ static int __init mal_probe(struct ocp_device *ocpdev)
 		       ocpdev->def->index);
 		return -ENOMEM;
 	}
-	mal->dcrbase = maldata->dcr_base;
+
+	/* XXX This only works for native dcr for now */
+	mal->dcrhost = dcr_map(NULL, maldata->dcr_base, 0);
+
 	mal->def = ocpdev->def;
 
 	INIT_LIST_HEAD(&mal->poll_list);
diff --git a/drivers/net/ibm_emac/ibm_emac_mal.h b/drivers/net/ibm_emac/ibm_emac_mal.h
index 64bc338..6b1fbeb 100644
--- a/drivers/net/ibm_emac/ibm_emac_mal.h
+++ b/drivers/net/ibm_emac/ibm_emac_mal.h
@@ -191,7 +191,6 @@ struct mal_commac {
 };
 
 struct ibm_ocp_mal {
-	int			dcrbase;
 	dcr_host_t		dcrhost;
 
 	struct list_head	poll_list;
@@ -209,12 +208,12 @@ struct ibm_ocp_mal {
 
 static inline u32 get_mal_dcrn(struct ibm_ocp_mal *mal, int reg)
 {
-	return dcr_read(mal->dcrhost, mal->dcrbase + reg);
+	return dcr_read(mal->dcrhost, mal->dcrhost.base + reg);
 }
 
 static inline void set_mal_dcrn(struct ibm_ocp_mal *mal, int reg, u32 val)
 {
-	dcr_write(mal->dcrhost, mal->dcrbase + reg, val);
+	dcr_write(mal->dcrhost, mal->dcrhost.base + reg, val);
 }
 
 /* Register MAL devices */
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* [PATCH 4/7] Update axon_msi to use dcr_host_t.base
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

Now that dcr_host_t contains the base address, we can use that in the
axon_msi code, rather than storing it separately.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 arch/powerpc/platforms/cell/axon_msi.c |   13 ++++++-------
 1 files changed, 6 insertions(+), 7 deletions(-)

diff --git a/arch/powerpc/platforms/cell/axon_msi.c b/arch/powerpc/platforms/cell/axon_msi.c
index 74407af..23e039a 100644
--- a/arch/powerpc/platforms/cell/axon_msi.c
+++ b/arch/powerpc/platforms/cell/axon_msi.c
@@ -69,7 +69,6 @@ struct axon_msic {
 	dcr_host_t dcr_host;
 	struct list_head list;
 	u32 read_offset;
-	u32 dcr_base;
 };
 
 static LIST_HEAD(axon_msic_list);
@@ -78,12 +77,12 @@ static void msic_dcr_write(struct axon_msic *msic, unsigned int dcr_n, u32 val)
 {
 	pr_debug("axon_msi: dcr_write(0x%x, 0x%x)\n", val, dcr_n);
 
-	dcr_write(msic->dcr_host, msic->dcr_base + dcr_n, val);
+	dcr_write(msic->dcr_host, msic->dcr_host.base + dcr_n, val);
 }
 
 static u32 msic_dcr_read(struct axon_msic *msic, unsigned int dcr_n)
 {
-	return dcr_read(msic->dcr_host, msic->dcr_base + dcr_n);
+	return dcr_read(msic->dcr_host, msic->dcr_host.base + dcr_n);
 }
 
 static void axon_msi_cascade(unsigned int irq, struct irq_desc *desc)
@@ -324,7 +323,7 @@ static int axon_msi_setup_one(struct device_node *dn)
 	struct page *page;
 	struct axon_msic *msic;
 	unsigned int virq;
-	int dcr_len;
+	int dcr_base, dcr_len;
 
 	pr_debug("axon_msi: setting up dn %s\n", dn->full_name);
 
@@ -335,17 +334,17 @@ static int axon_msi_setup_one(struct device_node *dn)
 		goto out;
 	}
 
-	msic->dcr_base = dcr_resource_start(dn, 0);
+	dcr_base = dcr_resource_start(dn, 0);
 	dcr_len = dcr_resource_len(dn, 0);
 
-	if (msic->dcr_base == 0 || dcr_len == 0) {
+	if (dcr_base == 0 || dcr_len == 0) {
 		printk(KERN_ERR
 		       "axon_msi: couldn't parse dcr properties on %s\n",
 			dn->full_name);
 		goto out;
 	}
 
-	msic->dcr_host = dcr_map(dn, msic->dcr_base, dcr_len);
+	msic->dcr_host = dcr_map(dn, dcr_base, dcr_len);
 	if (!DCR_MAP_OK(msic->dcr_host)) {
 		printk(KERN_ERR "axon_msi: dcr_map failed for %s\n",
 		       dn->full_name);
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* [PATCH 5/7] Add dcr_host_t.base in dcr_read()/dcr_write()
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

Now that all users of dcr_read()/dcr_write() add the dcr_host_t.base, we can
save them the trouble and do it in dcr_read()/dcr_write().

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 arch/powerpc/platforms/cell/axon_msi.c |    4 ++--
 arch/powerpc/sysdev/mpic.c             |    4 ++--
 drivers/net/ibm_emac/ibm_emac_mal.h    |    4 ++--
 include/asm-powerpc/dcr-mmio.h         |    4 ++--
 include/asm-powerpc/dcr-native.h       |    4 ++--
 5 files changed, 10 insertions(+), 10 deletions(-)

diff --git a/arch/powerpc/platforms/cell/axon_msi.c b/arch/powerpc/platforms/cell/axon_msi.c
index 23e039a..26a5e88 100644
--- a/arch/powerpc/platforms/cell/axon_msi.c
+++ b/arch/powerpc/platforms/cell/axon_msi.c
@@ -77,12 +77,12 @@ static void msic_dcr_write(struct axon_msic *msic, unsigned int dcr_n, u32 val)
 {
 	pr_debug("axon_msi: dcr_write(0x%x, 0x%x)\n", val, dcr_n);
 
-	dcr_write(msic->dcr_host, msic->dcr_host.base + dcr_n, val);
+	dcr_write(msic->dcr_host, dcr_n, val);
 }
 
 static u32 msic_dcr_read(struct axon_msic *msic, unsigned int dcr_n)
 {
-	return dcr_read(msic->dcr_host, msic->dcr_host.base + dcr_n);
+	return dcr_read(msic->dcr_host, dcr_n);
 }
 
 static void axon_msi_cascade(unsigned int irq, struct irq_desc *desc)
diff --git a/arch/powerpc/sysdev/mpic.c b/arch/powerpc/sysdev/mpic.c
index 16b1f4b..61f5730 100644
--- a/arch/powerpc/sysdev/mpic.c
+++ b/arch/powerpc/sysdev/mpic.c
@@ -156,7 +156,7 @@ static inline u32 _mpic_read(enum mpic_reg_type type,
 	switch(type) {
 #ifdef CONFIG_PPC_DCR
 	case mpic_access_dcr:
-		return dcr_read(rb->dhost, rb->dhost.base + reg);
+		return dcr_read(rb->dhost, reg);
 #endif
 	case mpic_access_mmio_be:
 		return in_be32(rb->base + (reg >> 2));
@@ -173,7 +173,7 @@ static inline void _mpic_write(enum mpic_reg_type type,
 	switch(type) {
 #ifdef CONFIG_PPC_DCR
 	case mpic_access_dcr:
-		return dcr_write(rb->dhost, rb->dhost.base + reg, value);
+		return dcr_write(rb->dhost, reg, value);
 #endif
 	case mpic_access_mmio_be:
 		return out_be32(rb->base + (reg >> 2), value);
diff --git a/drivers/net/ibm_emac/ibm_emac_mal.h b/drivers/net/ibm_emac/ibm_emac_mal.h
index 6b1fbeb..10dc978 100644
--- a/drivers/net/ibm_emac/ibm_emac_mal.h
+++ b/drivers/net/ibm_emac/ibm_emac_mal.h
@@ -208,12 +208,12 @@ struct ibm_ocp_mal {
 
 static inline u32 get_mal_dcrn(struct ibm_ocp_mal *mal, int reg)
 {
-	return dcr_read(mal->dcrhost, mal->dcrhost.base + reg);
+	return dcr_read(mal->dcrhost, reg);
 }
 
 static inline void set_mal_dcrn(struct ibm_ocp_mal *mal, int reg, u32 val)
 {
-	dcr_write(mal->dcrhost, mal->dcrhost.base + reg, val);
+	dcr_write(mal->dcrhost, reg, val);
 }
 
 /* Register MAL devices */
diff --git a/include/asm-powerpc/dcr-mmio.h b/include/asm-powerpc/dcr-mmio.h
index 6b82c3b..a7d9eaf 100644
--- a/include/asm-powerpc/dcr-mmio.h
+++ b/include/asm-powerpc/dcr-mmio.h
@@ -37,12 +37,12 @@ extern void dcr_unmap(dcr_host_t host, unsigned int dcr_n, unsigned int dcr_c);
 
 static inline u32 dcr_read(dcr_host_t host, unsigned int dcr_n)
 {
-	return in_be32(host.token + dcr_n * host.stride);
+	return in_be32(host.token + ((host.base + dcr_n) * host.stride));
 }
 
 static inline void dcr_write(dcr_host_t host, unsigned int dcr_n, u32 value)
 {
-	out_be32(host.token + dcr_n * host.stride, value);
+	out_be32(host.token + ((host.base + dcr_n) * host.stride), value);
 }
 
 extern u64 of_translate_dcr_address(struct device_node *dev,
diff --git a/include/asm-powerpc/dcr-native.h b/include/asm-powerpc/dcr-native.h
index f41058c..3bc780f 100644
--- a/include/asm-powerpc/dcr-native.h
+++ b/include/asm-powerpc/dcr-native.h
@@ -30,8 +30,8 @@ typedef struct {
 
 #define dcr_map(dev, dcr_n, dcr_c)	((dcr_host_t){ .base = (dcr_n) })
 #define dcr_unmap(host, dcr_n, dcr_c)	do {} while (0)
-#define dcr_read(host, dcr_n)		mfdcr(dcr_n)
-#define dcr_write(host, dcr_n, value)	mtdcr(dcr_n, value)
+#define dcr_read(host, dcr_n)		mfdcr(dcr_n + host.base)
+#define dcr_write(host, dcr_n, value)	mtdcr(dcr_n + host.base, value)
 
 /* Device Control Registers */
 void __mtdcr(int reg, unsigned int val);
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* [PATCH 6/7] Add dcr_map_reg() helper
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

Add a helper routine to map dcr's based on the "dcr-reg" property of
a device node.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 arch/powerpc/sysdev/dcr.c |   17 +++++++++++++++++
 include/asm-powerpc/dcr.h |    1 +
 2 files changed, 18 insertions(+), 0 deletions(-)

diff --git a/arch/powerpc/sysdev/dcr.c b/arch/powerpc/sysdev/dcr.c
index ab11c0b..da4f9c6 100644
--- a/arch/powerpc/sysdev/dcr.c
+++ b/arch/powerpc/sysdev/dcr.c
@@ -126,6 +126,23 @@ dcr_host_t dcr_map(struct device_node *dev, unsigned int dcr_n,
 }
 EXPORT_SYMBOL_GPL(dcr_map);
 
+dcr_host_t dcr_map_reg(struct device_node *dev, unsigned int index)
+{
+	dcr_host_t ret = { .token = NULL };
+
+	unsigned int dcr_n, dcr_c;
+
+	dcr_n = dcr_resource_start(dev, index);
+	if (!dcr_n)
+		return ret;
+
+	dcr_c = dcr_resource_len(dev, index);
+	if (!dcr_c)
+		return ret;
+
+	return dcr_map(dev, dcr_n, dcr_c);
+}
+
 void dcr_unmap(dcr_host_t host, unsigned int dcr_n, unsigned int dcr_c)
 {
 	dcr_host_t h = host;
diff --git a/include/asm-powerpc/dcr.h b/include/asm-powerpc/dcr.h
index 9338d50..4d42f01 100644
--- a/include/asm-powerpc/dcr.h
+++ b/include/asm-powerpc/dcr.h
@@ -38,6 +38,7 @@ extern unsigned int dcr_resource_start(struct device_node *np,
 				       unsigned int index);
 extern unsigned int dcr_resource_len(struct device_node *np,
 				     unsigned int index);
+extern dcr_host_t dcr_map_reg(struct device_node *np, unsigned int index);
 #endif /* CONFIG_PPC_MERGE */
 
 #endif /* CONFIG_PPC_DCR */
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* [PATCH 7/7] Remove msic_dcr_read() and use dcr_map_reg() in axon_msi.c
From: Michael Ellerman @ 2007-09-17  6:05 UTC (permalink / raw)
  To: linuxppc-dev
In-Reply-To: <449a181e8169af98984bb2d61a759c23e55d19b4.1190009070.git.michael@ellerman.id.au>

msic_dcr_read() doesn't really do anything useful, just replace it with
direct calls to dcr_read().

Use dcr_map_reg() in the axon_msi setup code, rather than essentially doing
it by hand.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---
 arch/powerpc/platforms/cell/axon_msi.c |   22 +++-------------------
 1 files changed, 3 insertions(+), 19 deletions(-)

diff --git a/arch/powerpc/platforms/cell/axon_msi.c b/arch/powerpc/platforms/cell/axon_msi.c
index 26a5e88..57a6149 100644
--- a/arch/powerpc/platforms/cell/axon_msi.c
+++ b/arch/powerpc/platforms/cell/axon_msi.c
@@ -80,18 +80,13 @@ static void msic_dcr_write(struct axon_msic *msic, unsigned int dcr_n, u32 val)
 	dcr_write(msic->dcr_host, dcr_n, val);
 }
 
-static u32 msic_dcr_read(struct axon_msic *msic, unsigned int dcr_n)
-{
-	return dcr_read(msic->dcr_host, dcr_n);
-}
-
 static void axon_msi_cascade(unsigned int irq, struct irq_desc *desc)
 {
 	struct axon_msic *msic = get_irq_data(irq);
 	u32 write_offset, msi;
 	int idx;
 
-	write_offset = msic_dcr_read(msic, MSIC_WRITE_OFFSET_REG);
+	write_offset = dcr_read(msic->dcr_host, MSIC_WRITE_OFFSET_REG);
 	pr_debug("axon_msi: original write_offset 0x%x\n", write_offset);
 
 	/* write_offset doesn't wrap properly, so we have to mask it */
@@ -306,7 +301,7 @@ static int axon_msi_notify_reboot(struct notifier_block *nb,
 	list_for_each_entry(msic, &axon_msic_list, list) {
 		pr_debug("axon_msi: disabling %s\n",
 			  msic->irq_host->of_node->full_name);
-		tmp  = msic_dcr_read(msic, MSIC_CTRL_REG);
+		tmp  = dcr_read(msic->dcr_host, MSIC_CTRL_REG);
 		tmp &= ~MSIC_CTRL_ENABLE & ~MSIC_CTRL_IRQ_ENABLE;
 		msic_dcr_write(msic, MSIC_CTRL_REG, tmp);
 	}
@@ -323,7 +318,6 @@ static int axon_msi_setup_one(struct device_node *dn)
 	struct page *page;
 	struct axon_msic *msic;
 	unsigned int virq;
-	int dcr_base, dcr_len;
 
 	pr_debug("axon_msi: setting up dn %s\n", dn->full_name);
 
@@ -334,17 +328,7 @@ static int axon_msi_setup_one(struct device_node *dn)
 		goto out;
 	}
 
-	dcr_base = dcr_resource_start(dn, 0);
-	dcr_len = dcr_resource_len(dn, 0);
-
-	if (dcr_base == 0 || dcr_len == 0) {
-		printk(KERN_ERR
-		       "axon_msi: couldn't parse dcr properties on %s\n",
-			dn->full_name);
-		goto out;
-	}
-
-	msic->dcr_host = dcr_map(dn, dcr_base, dcr_len);
+	msic->dcr_host = dcr_map_reg(dn, 0);
 	if (!DCR_MAP_OK(msic->dcr_host)) {
 		printk(KERN_ERR "axon_msi: dcr_map failed for %s\n",
 		       dn->full_name);
-- 
1.5.1.3.g7a33b

^ permalink raw reply related

* Re: [PATCH] i2c: devtree-aware iic support for PPC4xx
From: Eugene Surovegin @ 2007-09-17  6:22 UTC (permalink / raw)
  To: Stefan Roese; +Cc: Jean Delvare, linuxppc-dev, i2c
In-Reply-To: <200709170734.09079.sr@denx.de>

On Mon, Sep 17, 2007 at 07:34:08AM +0200, Stefan Roese wrote:
> 
> My understanding was, that adding many #ifdef's into the code was not the 
> preferred way. 

But just making a copy seems to be a proffered one? Wow.

OCP and/or OF part is quite small part of the driver; another approach 
would been completely splitting OCP and OF specific part out 
(e.g. i2c-ibm_iic.c + i2c-ibm_iic_ocp.c / i2c_ibm_iic_of.c). I 
personally thing it's not worth the effort and just adding couple of 
ifdef'ed code is good enough, especially as a transitional thing.

> I could of course change this patch to not add an additional 
> driver but extend the existing driver with a bunch of #ifdef's to support 
> both versions.
> 
> This approach of multiple drivers seems to be common in the kernel right now:
> 
> drivers/mtd/maps/physmap.c
> drivers/mtd/maps/physmap_of.c
> 
> or
> 
> drivers/usb/host/ohci-ppc-soc.c
> drivers/usb/host/ohci-ppc-of.c

I don't think these are good examples, physmap.c seems to differ from 
physmap_of.c significantly. These drivers are mostly a glue, and it 
makes sense to have different versions, because there isn't much there 
except for platform/bus/glue specific code.

> Any other opinions on this? How should this be handled to get accepted 
> upstream? Two different drivers with removing the "old" one later when 
> arch/ppc is gone,

ppc has been going away for the last two years at least and still 
isn't gone. What makes you think this isn't gonna take another year or 
two :) ?

> 
> The "old" name "i2c-ibm_iic" is kind of redundant. Nearly all bus drivers are 
> named "i2c-platform". Perhaps a better name would be "i2c-ppc4xx" then. 

Sure, that'd be a much better choice.

-- 
Eugene

^ permalink raw reply

* Re: [PATCH 09/10] ppc64: Convert cpu_sibling_map to a per_cpu data array (v3)
From: Stephen Rothwell @ 2007-09-17  6:28 UTC (permalink / raw)
  To: travis
  Cc: linux-mm, Andi Kleen, linux-kernel, linuxppc-dev, sparclinux,
	Andrew Morton, Christoph Lameter
In-Reply-To: <20070912015647.486500682@sgi.com>

[-- Attachment #1: Type: text/plain, Size: 1319 bytes --]

On Tue, 11 Sep 2007 18:56:53 -0700 travis@sgi.com wrote:
>
> Convert cpu_sibling_map to a per_cpu cpumask_t array for the ppc64
> architecture.  This fixes build errors in block/blktrace.c and
> kernel/sched.c when CONFIG_SCHED_SMT is defined.
> 
> Note: these changes have not been built nor tested.

After applying all 10 patches, the ppc64_defconfig builds but:

	vmlinux is larger:

   text    data     bss     dec     hex filename
7705776 1756984  504624 9967384  981718 ppc64/vmlinux
7706228 1757120  504624 9967972  981964 trav.bld/vmlinux

	the topology (on my POWERPC5+ box) is not correct:

cpu0/topology/thread_siblings:0000000f
cpu1/topology/thread_siblings:0000000f
cpu2/topology/thread_siblings:0000000f
cpu3/topology/thread_siblings:0000000f

it used to be:

cpu0/topology/thread_siblings:00000003
cpu1/topology/thread_siblings:00000003
cpu2/topology/thread_siblings:0000000c
cpu3/topology/thread_siblings:0000000c

Similarly on my iSeries box, the topology is displayed as above
while it used to be:

cpu0/topology/thread_siblings:00000001
cpu1/topology/thread_siblings:00000002
cpu2/topology/thread_siblings:00000004
cpu3/topology/thread_siblings:00000008

-- 
Cheers,
Stephen Rothwell                    sfr@canb.auug.org.au
http://www.canb.auug.org.au/~sfr/

[-- Attachment #2: Type: application/pgp-signature, Size: 189 bytes --]

^ permalink raw reply

* Re: [PATCH 09/10] ppc64: Convert cpu_sibling_map to a per_cpu data array (v3)
From: Stephen Rothwell @ 2007-09-17  6:39 UTC (permalink / raw)
  To: travis
  Cc: linux-mm, Andi Kleen, linux-kernel, linuxppc-dev, sparclinux,
	Andrew Morton, Christoph Lameter
In-Reply-To: <20070917162831.b2a9d675.sfr@canb.auug.org.au>

[-- Attachment #1: Type: text/plain, Size: 718 bytes --]

On Mon, 17 Sep 2007 16:28:31 +1000 Stephen Rothwell <sfr@canb.auug.org.au> wrote:
>
> 	the topology (on my POWERPC5+ box) is not correct:
> 
> cpu0/topology/thread_siblings:0000000f
> cpu1/topology/thread_siblings:0000000f
> cpu2/topology/thread_siblings:0000000f
> cpu3/topology/thread_siblings:0000000f
> 
> it used to be:
> 
> cpu0/topology/thread_siblings:00000003
> cpu1/topology/thread_siblings:00000003
> cpu2/topology/thread_siblings:0000000c
> cpu3/topology/thread_siblings:0000000c

This would be because we are setting up the cpu_sibling map before we
call setup_per_cpu_areas().

-- 
Cheers,
Stephen Rothwell                    sfr@canb.auug.org.au
http://www.canb.auug.org.au/~sfr/

[-- Attachment #2: Type: application/pgp-signature, Size: 189 bytes --]

^ permalink raw reply

* Re: SYSFS: need a noncaching read
From: Tejun Heo @ 2007-09-17  5:22 UTC (permalink / raw)
  To: Greg KH; +Cc: linuxppc-dev, Heiko Schocher, linux-kernel, Detlev Zundel
In-Reply-To: <20070912100123.GA23182@kroah.com>

Greg KH wrote:
> On Wed, Sep 12, 2007 at 07:32:07AM +0200, Robert Schwebel wrote:
>> On Tue, Sep 11, 2007 at 11:43:17AM +0200, Heiko Schocher wrote:
>>> I have developed a device driver and use the sysFS to export some
>>> registers to userspace.
>> Uuuh, uggly. Don't do that. Device drivers are there to abstract things,
>> not to play around with registers from userspace.
>>
>>> I opened the sysFS File for one register and did some reads from this
>>> File, but I alwas becoming the same value from the register, whats not
>>> OK, because they are changing. So I found out that the sysFS caches
>>> the reads ... :-(
>> Yes, it does. What you can do is close()ing the file handle between
>> accesses, which makes it work but is slow.
> 
> Do an lseek back to 0 and then re-read, you will get called in your
> driver again.

There should be an intervening sysfs_notify() call from kernel side to
make sysfs re-populate its cache on read again.  sysfs bin files buffer
the result but don't cache the result but this again doesn't really fit
the usage case.

Thanks.

-- 
tejun

^ permalink raw reply

* DMA Generic Task
From: Pedro Luis D. L. @ 2007-09-17  8:39 UTC (permalink / raw)
  To: linuxppc-embedded


Hello,
I=B4m developing an small module to use the DMA API to copy some audio data=
 in a PSC wich has attached an digital to analog converter. It is only a pr=
oof of concept before I can use this information to develop an audio driver=
 for the SPI interface.=20
I=B4m using a 2.6.20 kernel patched with the bestcomm patches from http://w=
ww.246tnt.com/mpc52xx/dev_full/ at Sylvain's page.=20
My board is also a pcm030. I had the same problems with the Ethernet so I d=
ecided to keep the old fec driver with the old bestcomm driver also just fo=
r the Ethernet stuff until I could take a look over it.
I took a look into the code for the bestcomm API for the generic tasks and =
thought that this was the way to initialize the bestcomm task:

        struct bcom_task *tx_bcom;  =20
        struct bcom_task *rx_bcom;
=09
        switch(psc_num) {
		case 1:
			initiator_tx =3D SDMA_INITIATOR_PSC1_TX;
			initiator_rx =3D SDMA_INITIATOR_PSC1_RX;
			break;
		case 2:
			initiator_tx =3D SDMA_INITIATOR_PSC2_TX;
			initiator_rx =3D SDMA_INITIATOR_PSC2_RX;
			break;
		default:
			panic("snd-SPImgt.o: invalid value for psc_num (%i)\n",psc_num);
			break;
	};

	tx_bcom =3D bcom_gen_bd_tx_init(512, MPC52xx_PA(MPC52xx_PSCx_OFFSET(psc_nu=
m))+0x80, initiator_tx, 6);   //(1)

	rx_bcom =3D bcom_gen_bd_rx_init(512, MPC52xx_PA(MPC52xx_PSCx_OFFSET(psc_nu=
m))+0x60, initiator_rx, 6, 1024);


where MPC52xx_PA(MPC52xx_PSCx_OFFSET(psc_num)) =3D 0xf0002000, wich added t=
o 0x80 or 0x60 gives TXFIFO or RXFIFO's physical address.
However, when I insert the module, it crashes at (1) Line (bcom_gen_bd_tx_i=
nit...) with this output:

root@MPC5200B:~ insmod SPIspeaker
Inserting SPIspeaker module
Unable to handle kernel paging request for data at address 0x0000000c
Faulting instruction address: 0xc001525c
Oops: Kernel access of bad area, sig: 11 [#1]
PREEMPT
Modules linked in: SPIspeaker eeprom
NIP: C001525C LR: C0016458 CTR: 00000010
REGS: c3e7bd80 TRAP: 0300   Not tainted  (2.6.20)
MSR: 00009032   CR: 24008222  XER: 00000000
DAR: 0000000C, DSISR: 20000000
TASK =3D c3f2c7b0[447] 'insmod' THREAD: c3e7a000
GPR00: 00000010 C3E7BE30 C3F2C7B0 00000200 00000008 00000010 00000006 00004=
000
GPR08: C3E7A000 00000000 00000000 C0016430 24008222 1008B4E8 00000000 00000=
000
GPR16: 00000012 00000011 C5068C74 C3FD08C0 00000000 00000056 C024408C 00000=
000
GPR24: C01E28DC 00000008 C0260000 00000200 0000000E 00000010 00000006 C0244=
338
Call Trace:
[C3E7BE30] [C5060000]  (unreliable)
[C3E7BE60] [C0016458]
[C3E7BE80] [C506026C]
[C3E7BEA0] [C003F804]
[C3E7BF40] [C000F5C8]
--- Exception: c01Instruction dump:
7c7b1b78 90010034 7c992378 7cbd2b78 8128000c 39290001 9128000c 3f40c026
38000010 813a01a8 7c0903a6 39400000  7d695b78 396b0004 800b0000
 note: insmod[447] exited with preempt_count 1
BUG: scheduling while atomic: insmod/0x10000001/447
Call Trace:
[C3E7BB80] [C00081E0]  (unreliable)
[C3E7BBB0] [C01DDCB0]
[C3E7BC00] [C0017CD8]
[C3E7BC10] [C01DE924]
[C3E7BC20] [C00520C0]
[C3E7BCA0] [C0055B0C]
[C3E7BCD0] [C001A764]
[C3E7BCE0] [C001E8A0]
[C3E7BD00] [C0020428]
[C3E7BD40] [C000DB84]
[C3E7BD60] [C0011084]
[C3E7BD70] [C000FA64]
--- Exception: 300[C3E7BE30] [C5060000]  (unreliable)
[C3E7BE60] [C0016458]
[C3E7BE80] [C506026C]
[C3E7BEA0] [C003F804]
[C3E7BF40] [C000F5C8]
--- Exception: c01Segmentation fault

How should I use the API to initialize the Bestcomm task?


Regards,
Pedro Dominguez

_________________________________________________________________
Prueba algunos de los nuevos servicios en l=EDnea que te ofrece Windows Liv=
e Ideas: tan nuevos que ni siquiera se han publicado oficialmente todav=EDa=
.
http://ideas.live.com=

^ permalink raw reply

* Re: [PATCH 4/7] powerpc: BestComm core support for Freescale MPC5200
From: Matt Sealey @ 2007-09-17  8:57 UTC (permalink / raw)
  To: Sylvain Munaut; +Cc: Grant Likely, Paul Mackerras, PowerPC dev list
In-Reply-To: <1189940011134-git-send-email-tnt@246tNt.com>

My only nitpick is the function naming.

Why not bestcomm_blah() rather than bcom_blah()?

I also think, even though the SRAM functionality is dependant
on BestComm (it's hard to seperate into another driver because
of kernel driver init order being 'random'?) it should be named
after the chip and not the DMA unit - the SRAM can be used for
pretty much anything a developer wants.

For instance, you could allocate it for the power management
code, or simply as some kind of buffer between a PIO managed
port if you do not want to use main memory for some reason.
On the MPC5121E it looks like AXE (audio DSP) and certain other
components will be sharing SRAM with BestComm and there will
be a good deal more of it.

Just looking to the future on some code sharing, because of
the above.

On a lighter note (not something that should block these
patches), would it be a good idea perhaps to abstract SRAM
allocations into a driver class of it's own in this same
way? Nearly every SoC has some kind of built-in SRAM and
even some Northbridges (Marvell Discovery) - ostensibly for
peripheral buffers like ethernet and so on, they can still
be used for anything. Couldn't it be a library or driver
simply with a custom init/teardown function (platform
specific)? I suppose the fact that SRAM could be probed
after BestComm or other peripherals is the problem here,
but there is a platform device for Pegasos ethernet which
modifies Discovery SRAM parameters.. I suppose this is
what I am thinking of getting rid of and allowing code
to be shared and SRAM allocation and usage becoming more
of a tool for other devices and drivers to use, and not
simply something claimed/controlled by BestComm or Ethernet,
and occasionally hijacked by something else.

-- 
Matt Sealey <matt@genesi-usa.com>
Genesi, Manager, Developer Relations

Sylvain Munaut wrote:
> This patch adds support for the core of the BestComm API
> for the Freescale MPC5200(b). The BestComm engine is a
> microcode-controlled / tasks-based DMA used by several
> of the onchip devices.
> 
> Setting up the tasks / memory allocation and all common
> low level functions are handled by this patch.
> The specifics details of each tasks and their microcode
> are split-out in separate patches.
> 
> This is not the official API, but a much cleaner one.
> (hopefully)
> 
> Signed-off-by: Sylvain Munaut <tnt@246tNt.com>
> ---
>  arch/powerpc/platforms/Kconfig               |    2 +
>  arch/powerpc/sysdev/Makefile                 |    1 +
>  arch/powerpc/sysdev/bestcomm/Kconfig         |   18 +
>  arch/powerpc/sysdev/bestcomm/Makefile        |    8 +
>  arch/powerpc/sysdev/bestcomm/bestcomm.c      |  657 ++++++++++++++++++++++++++
>  arch/powerpc/sysdev/bestcomm/bestcomm.h      |  136 ++++++
>  arch/powerpc/sysdev/bestcomm/bestcomm_priv.h |  325 +++++++++++++
>  arch/powerpc/sysdev/bestcomm/sram.c          |  177 +++++++
>  arch/powerpc/sysdev/bestcomm/sram.h          |   54 +++
>  9 files changed, 1378 insertions(+), 0 deletions(-)
>  create mode 100644 arch/powerpc/sysdev/bestcomm/Kconfig
>  create mode 100644 arch/powerpc/sysdev/bestcomm/Makefile
>  create mode 100644 arch/powerpc/sysdev/bestcomm/bestcomm.c
>  create mode 100644 arch/powerpc/sysdev/bestcomm/bestcomm.h
>  create mode 100644 arch/powerpc/sysdev/bestcomm/bestcomm_priv.h
>  create mode 100644 arch/powerpc/sysdev/bestcomm/sram.c
>  create mode 100644 arch/powerpc/sysdev/bestcomm/sram.h
> 
> diff --git a/arch/powerpc/platforms/Kconfig b/arch/powerpc/platforms/Kconfig
> index 9189ba5..99d48be 100644
> --- a/arch/powerpc/platforms/Kconfig
> +++ b/arch/powerpc/platforms/Kconfig
> @@ -293,4 +293,6 @@ config FSL_ULI1575
>  	  Freescale reference boards. The boards all use the ULI in pretty
>  	  much the same way.
>  
> +source "arch/powerpc/sysdev/bestcomm/Kconfig"
> +
>  endmenu
> diff --git a/arch/powerpc/sysdev/Makefile b/arch/powerpc/sysdev/Makefile
> index 08ce31e..0c8a29d 100644
> --- a/arch/powerpc/sysdev/Makefile
> +++ b/arch/powerpc/sysdev/Makefile
> @@ -15,6 +15,7 @@ obj-$(CONFIG_FSL_SOC)		+= fsl_soc.o
>  obj-$(CONFIG_FSL_PCI)		+= fsl_pci.o
>  obj-$(CONFIG_TSI108_BRIDGE)	+= tsi108_pci.o tsi108_dev.o
>  obj-$(CONFIG_QUICC_ENGINE)	+= qe_lib/
> +obj-$(CONFIG_PPC_BESTCOMM)	+= bestcomm/
>  mv64x60-$(CONFIG_PCI)		+= mv64x60_pci.o
>  obj-$(CONFIG_MV64X60)		+= $(mv64x60-y) mv64x60_pic.o mv64x60_dev.o
>  obj-$(CONFIG_RTC_DRV_CMOS)	+= rtc_cmos_setup.o
> diff --git a/arch/powerpc/sysdev/bestcomm/Kconfig b/arch/powerpc/sysdev/bestcomm/Kconfig
> new file mode 100644
> index 0000000..3366e24
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/Kconfig
> @@ -0,0 +1,18 @@
> +#
> +# Kconfig options for Bestcomm
> +#
> +
> +config PPC_BESTCOMM
> +	tristate "Bestcomm DMA engine support"
> +	depends on PPC_MPC52xx
> +	default n
> +	select PPC_LIB_RHEAP
> +	help
> +	  BestComm is the name of the communication coprocessor found
> +	  on the Freescale MPC5200 family of processor. It's usage is
> +	  optionnal for some drivers (like ATA), but required for
> +	  others (like FEC).
> +
> +	  If you want to use drivers that require DMA operations,
> +	  answer Y or M. Otherwise say N.
> +
> diff --git a/arch/powerpc/sysdev/bestcomm/Makefile b/arch/powerpc/sysdev/bestcomm/Makefile
> new file mode 100644
> index 0000000..a24aa06
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/Makefile
> @@ -0,0 +1,8 @@
> +#
> +# Makefile for BestComm & co
> +#
> +
> +bestcomm-core-objs	:= bestcomm.o sram.o
> +
> +obj-$(CONFIG_PPC_BESTCOMM)		+= bestcomm-core.o
> + 
> diff --git a/arch/powerpc/sysdev/bestcomm/bestcomm.c b/arch/powerpc/sysdev/bestcomm/bestcomm.c
> new file mode 100644
> index 0000000..10fb476
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/bestcomm.c
> @@ -0,0 +1,657 @@
> +/*
> + * Driver for MPC52xx processor BestComm peripheral controller
> + *
> + *
> + * Copyright (C) 2006-2007 Sylvain Munaut <tnt@246tNt.com>
> + * Copyright (C) 2005      Varma Electronics Oy,
> + *                         ( by Andrey Volkov <avolkov@varma-el.com> )
> + * Copyright (C) 2003-2004 MontaVista, Software, Inc.
> + *                         ( by Dale Farnsworth <dfarnsworth@mvista.com> )
> + *
> + * This file is licensed under the terms of the GNU General Public License
> + * version 2. This program is licensed "as is" without any warranty of any
> + * kind, whether express or implied.
> + */
> +
> +#include <linux/module.h>
> +#include <linux/kernel.h>
> +#include <linux/slab.h>
> +
> +#include <asm/io.h>
> +#include <asm/irq.h>
> +#include <asm/prom.h>
> +#include <asm/mpc52xx.h>
> +#include <asm/of_device.h>
> +#include <asm/of_platform.h>
> +
> +#include "sram.h"
> +#include "bestcomm_priv.h"
> +#include "bestcomm.h"
> +
> +#define DRIVER_NAME "bestcomm-core"
> +
> +
> +struct bcom_engine *bcom_eng = NULL;
> +EXPORT_SYMBOL_GPL(bcom_eng);	/* needed for inline functions */
> +
> +
> +/* ======================================================================== */
> +/* Public and private API                                                   */
> +/* ======================================================================== */
> +
> +/* Debug Dump */
> +
> +#define BCOM_DPRINTK(a,b...) printk(KERN_DEBUG DRIVER_NAME ": " a, ## b)
> +
> +void
> +bcom_dump_status(void)
> +{
> +	int i;
> +	struct mpc52xx_sdma __iomem *r = bcom_eng->regs;
> +
> +	BCOM_DPRINTK("BestComm status dump (pa=%08lx, va=%p)\n",
> +			bcom_eng->regs_base, bcom_eng->regs);
> +	BCOM_DPRINTK(" taskBar         = %08x\n", in_be32(&r->taskBar));
> +	BCOM_DPRINTK(" currentPointer  = %08x\n", in_be32(&r->currentPointer));
> +	BCOM_DPRINTK(" endPointer      = %08x\n", in_be32(&r->endPointer));
> +	BCOM_DPRINTK(" variablePointer = %08x\n", in_be32(&r->variablePointer));
> +	BCOM_DPRINTK(" IntVect1        = %08x\n", (u32)in_8(&r->IntVect1));
> +	BCOM_DPRINTK(" IntVect2        = %08x\n", (u32)in_8(&r->IntVect2));
> +	BCOM_DPRINTK(" PtdCntrl        = %08hx\n", in_be16(&r->PtdCntrl));
> +	BCOM_DPRINTK(" IntPend         = %08x\n", in_be32(&r->IntPend));
> +	BCOM_DPRINTK(" IntMask         = %08x\n", in_be32(&r->IntMask));
> +
> +	BCOM_DPRINTK(" TCR dump :\n");
> +
> +	for (i=0; i<16; i++) {
> +		printk("%s%04hx%s",
> +			(i&0x7) == 0x0 ? KERN_DEBUG "\t" : "",
> +			in_be16(&r->tcr[i]),
> +			(i&0x7) == 0x7 ? "\n" : " ");
> +	}
> +
> +	BCOM_DPRINTK(" IPR dump :\n");
> +
> +	for (i=0; i<32; i++) {
> +		printk("%s%02x%s",
> +			(i&0x7) == 0x0 ? KERN_DEBUG "\t" : "",
> +			(u32)in_8(&r->ipr[i]),
> +			(i&0x7) == 0x7 ? "\n" : " ");
> +	}
> +
> +	BCOM_DPRINTK(" cReqSelect      = %08x\n", in_be32(&r->cReqSelect));
> +	BCOM_DPRINTK(" task_size0      = %08x\n", in_be32(&r->task_size0));
> +	BCOM_DPRINTK(" task_size1      = %08x\n", in_be32(&r->task_size1));
> +	BCOM_DPRINTK(" MDEDebug        = %08x\n", in_be32(&r->MDEDebug));
> +	BCOM_DPRINTK(" ADSDebug        = %08x\n", in_be32(&r->ADSDebug));
> +	BCOM_DPRINTK(" Value1          = %08x\n", in_be32(&r->Value1));
> +	BCOM_DPRINTK(" Value2          = %08x\n", in_be32(&r->Value2));
> +	BCOM_DPRINTK(" Control         = %08x\n", in_be32(&r->Control));
> +	BCOM_DPRINTK(" Status          = %08x\n", in_be32(&r->Status));
> +	BCOM_DPRINTK(" PTDDebug        = %08x\n", in_be32(&r->PTDDebug));
> +}
> +EXPORT_SYMBOL_GPL(bcom_dump_status);
> +
> +void
> +bcom_dump_task(int task)
> +{
> +	int i;
> +	u32 *p;
> +	struct bcom_tdt *tdt = &bcom_eng->tdt[task];
> +
> +	BCOM_DPRINTK("Task dump %d\n", task);
> +	BCOM_DPRINTK(" tcr          = %04hx\n", bcom_eng->regs->tcr[task]);
> +	BCOM_DPRINTK(" tdt          = %p\n", &bcom_eng->tdt[task]);
> +	BCOM_DPRINTK(" tdt->start   = %08x\n", tdt->start);
> +	BCOM_DPRINTK(" tdt->stop    = %08x\n", tdt->stop);
> +	BCOM_DPRINTK(" tdt->var     = %08x\n", tdt->var);
> +	BCOM_DPRINTK(" tdt->fdt     = %08x\n", tdt->fdt);
> +	BCOM_DPRINTK(" tdt->status  = %08x\n", tdt->exec_status);
> +	BCOM_DPRINTK(" tdt->mvtp    = %08x\n", tdt->mvtp);
> +	BCOM_DPRINTK(" tdt->context = %08x\n", tdt->context);
> +	BCOM_DPRINTK(" tdt->litbase = %08x\n", tdt->litbase);
> +
> +	BCOM_DPRINTK(" code    :\n");
> +
> +	p = bcom_task_desc(task);
> +	for (i=0; i<bcom_task_num_descs(task); i++)
> +		printk(KERN_DEBUG "\t%p %08x\n", &p[i], p[i]);
> +
> +	BCOM_DPRINTK(" var/inc :\n");
> +
> +	p = bcom_task_var(task);
> +	for (i=0; i<BCOM_MAX_VAR+BCOM_MAX_INC; i++)
> +		printk(KERN_DEBUG "\t%p %08x\n", &p[i], p[i]);
> +}
> +EXPORT_SYMBOL_GPL(bcom_dump_task);
> +
> +void
> +bcom_dump_bdring(struct bcom_task *tsk)
> +{
> +	int i, j;
> +
> +	BCOM_DPRINTK("BD ring dump %d\n", tsk->tasknum);
> +
> +	for (i=0; i<tsk->num_bd; i++) {
> +		BCOM_DPRINTK(" BD[%02d] :\n", i);
> +		BCOM_DPRINTK("  cookie   : %p\n", tsk->cookie[i]);
> +		BCOM_DPRINTK("  status   : %08x\n", tsk->bd[i].status);
> +		for (j=0; j<(tsk->bd_size/sizeof(u32))-1; j++)
> +			BCOM_DPRINTK("  data[%02d] : %08x\n",
> +				j, tsk->bd[i].data[j]);
> +	}
> +}
> +EXPORT_SYMBOL_GPL(bcom_dump_bdring);
> +
> +
> +/* Private API */
> +
> +struct bcom_task *
> +bcom_task_alloc(int bd_count, int bd_size, int priv_size)
> +{
> +	int i, tasknum = -1;
> +	struct bcom_task *tsk;
> +
> +	/* Get and reserve a task num */
> +	spin_lock(&bcom_eng->lock);
> +
> +	for (i=0; i<BCOM_MAX_TASKS; i++)
> +		if (!bcom_eng->tdt[i].stop) {	/* we use stop as a marker */
> +			bcom_eng->tdt[i].stop = 0xfffffffful; /* dummy addr */
> +			tasknum = i;
> +			break;
> +		}
> +
> +	spin_unlock(&bcom_eng->lock);
> +
> +	if (tasknum < 0)
> +		return NULL;
> +
> +	/* Allocate our structure */
> +	tsk = kzalloc(sizeof(struct bcom_task) + priv_size, GFP_KERNEL);
> +	if (!tsk)
> +		goto error;
> +
> +	tsk->tasknum = tasknum;
> +	if (priv_size)
> +		tsk->priv = (void*)tsk + sizeof(struct bcom_task);
> +
> +	/* Get IRQ of that task */
> +	tsk->irq = irq_of_parse_and_map(bcom_eng->ofnode, tsk->tasknum);
> +	if (tsk->irq == NO_IRQ)
> +		goto error;
> +
> +	/* Init the BDs, if needed */
> +	if (bd_count) {
> +		tsk->cookie = kmalloc(sizeof(void*) * bd_count, GFP_KERNEL);
> +		if (!tsk->cookie)
> +			goto error;
> +
> +		tsk->bd = bcom_sram_alloc(bd_count * bd_size, 4, &tsk->bd_pa);
> +		if (!tsk->bd)
> +			goto error;
> +		memset(tsk->bd, 0x00, bd_count * bd_size);
> +
> +		tsk->num_bd = bd_count;
> +		tsk->bd_size = bd_size;
> +	}
> +
> +	return tsk;
> +
> +error:
> +	if (tsk) {
> +		if (tsk->irq != NO_IRQ)
> +			irq_dispose_mapping(tsk->irq);
> +		bcom_sram_free(tsk->bd);
> +		kfree(tsk->cookie);
> +		kfree(tsk);
> +	}
> +
> +	bcom_eng->tdt[tasknum].stop = 0;
> +
> +	return NULL;
> +}
> +EXPORT_SYMBOL_GPL(bcom_task_alloc);
> +
> +void
> +bcom_task_release(struct bcom_task *tsk)
> +{
> +	/* Stop the task */
> +	bcom_disable_task(tsk->tasknum);
> +
> +	/* Clear TDT */
> +	bcom_eng->tdt[tsk->tasknum].start = 0;
> +	bcom_eng->tdt[tsk->tasknum].stop  = 0;
> +
> +	/* Free everything */
> +	irq_dispose_mapping(tsk->irq);
> +	bcom_sram_free(tsk->bd);
> +	kfree(tsk->cookie);
> +	kfree(tsk);
> +}
> +EXPORT_SYMBOL_GPL(bcom_task_release);
> +
> +int
> +bcom_load_image(int task, u32 *task_image)
> +{
> +	struct bcom_task_header *hdr = (struct bcom_task_header *)task_image;
> +	struct bcom_tdt *tdt;
> +	u32 *desc, *var, *inc;
> +	u32 *desc_src, *var_src, *inc_src;
> +
> +	/* Safety checks */
> +	if (hdr->magic != BCOM_TASK_MAGIC) {
> +		printk(KERN_ERR DRIVER_NAME
> +			": Trying to load invalid microcode\n");
> +		return -EINVAL;
> +	}
> +
> +	if ((task < 0) || (task >= BCOM_MAX_TASKS)) {
> +		printk(KERN_ERR DRIVER_NAME
> +			": Trying to load invalid task %d\n", task);
> +		return -EINVAL;
> +	}
> +
> +	/* Initial load or reload */
> +	tdt = &bcom_eng->tdt[task];
> +
> +	if (tdt->start) {
> +		desc = bcom_task_desc(task);
> +		if (hdr->desc_size != bcom_task_num_descs(task)) {
> +			printk(KERN_ERR DRIVER_NAME
> +				": Trying to reload wrong task image "
> +				"(%d size %d/%d)!\n",
> +				task,
> +				hdr->desc_size,
> +				bcom_task_num_descs(task));
> +			return -EINVAL;
> +		}
> +	} else {
> +		phys_addr_t start_pa;
> +
> +		desc = bcom_sram_alloc(hdr->desc_size * sizeof(u32), 4, &start_pa);
> +		if (!desc)
> +			return -ENOMEM;
> +
> +		tdt->start = start_pa;
> +		tdt->stop = start_pa + ((hdr->desc_size-1) * sizeof(u32));
> +	}
> +
> +	var = bcom_task_var(task);
> +	inc = bcom_task_inc(task);
> +
> +	/* Clear & copy */
> +	memset(var, 0x00, BCOM_VAR_SIZE);
> +	memset(inc, 0x00, BCOM_INC_SIZE);
> +
> +	desc_src = (u32 *)(hdr + 1);
> +	var_src = desc_src + hdr->desc_size;
> +	inc_src = var_src + hdr->var_size;
> +
> +	memcpy(desc, desc_src, hdr->desc_size * sizeof(u32));
> +	memcpy(var + hdr->first_var, var_src, hdr->var_size * sizeof(u32));
> +	memcpy(inc, inc_src, hdr->inc_size * sizeof(u32));
> +
> +	return 0;
> +}
> +EXPORT_SYMBOL_GPL(bcom_load_image);
> +
> +void
> +bcom_set_initiator(int task, int initiator)
> +{
> +	int i;
> +	int num_descs;
> +	u32 *desc;
> +	int next_drd_has_initiator;
> +
> +	bcom_set_tcr_initiator(task, initiator);
> +
> +	/* Just setting tcr is apparently not enough due to some problem */
> +	/* with it. So we just go thru all the microcode and replace in  */
> +	/* the DRD directly */
> +
> +	desc = bcom_task_desc(task);
> +	next_drd_has_initiator = 1;
> +	num_descs = bcom_task_num_descs(task);
> +
> +	for (i=0; i<num_descs; i++, desc++) {
> +		if (!bcom_desc_is_drd(*desc))
> +			continue;
> +		if (next_drd_has_initiator)
> +			if (bcom_desc_initiator(*desc) != BCOM_INITIATOR_ALWAYS)
> +				bcom_set_desc_initiator(desc, initiator);
> +		next_drd_has_initiator = !bcom_drd_is_extended(*desc);
> +	}
> +}
> +EXPORT_SYMBOL_GPL(bcom_set_initiator);
> +
> +
> +/* Public API */
> +
> +void
> +bcom_enable(struct bcom_task *tsk)
> +{
> +	bcom_enable_task(tsk->tasknum);
> +}
> +EXPORT_SYMBOL_GPL(bcom_enable);
> +
> +void
> +bcom_disable(struct bcom_task *tsk)
> +{
> +	bcom_disable_task(tsk->tasknum);
> +}
> +EXPORT_SYMBOL_GPL(bcom_disable);
> +
> +
> +/* ======================================================================== */
> +/* Engine init/cleanup                                                      */
> +/* ======================================================================== */
> +
> +/* Function Descriptor table */
> +/* this will need to be updated if Freescale changes their task code FDT */
> +static u32 fdt_ops[] = {
> +	0xa0045670,	/* FDT[48] - load_acc()	  */
> +	0x80045670,	/* FDT[49] - unload_acc() */
> +	0x21800000,	/* FDT[50] - and()        */
> +	0x21e00000,	/* FDT[51] - or()         */
> +	0x21500000,	/* FDT[52] - xor()        */
> +	0x21400000,	/* FDT[53] - andn()       */
> +	0x21500000,	/* FDT[54] - not()        */
> +	0x20400000,	/* FDT[55] - add()        */
> +	0x20500000,	/* FDT[56] - sub()        */
> +	0x20800000,	/* FDT[57] - lsh()        */
> +	0x20a00000,	/* FDT[58] - rsh()        */
> +	0xc0170000,	/* FDT[59] - crc8()       */
> +	0xc0145670,	/* FDT[60] - crc16()      */
> +	0xc0345670,	/* FDT[61] - crc32()      */
> +	0xa0076540,	/* FDT[62] - endian32()   */
> +	0xa0000760,	/* FDT[63] - endian16()   */
> +};
> +
> +
> +static int __devinit
> +bcom_engine_init(void)
> +{
> +	int task;
> +	phys_addr_t tdt_pa, ctx_pa, var_pa, fdt_pa;
> +	unsigned int tdt_size, ctx_size, var_size, fdt_size;
> +
> +	/* Allocate & clear SRAM zones for FDT, TDTs, contexts and vars/incs */
> +	tdt_size = BCOM_MAX_TASKS * sizeof(struct bcom_tdt);
> +	ctx_size = BCOM_MAX_TASKS * BCOM_CTX_SIZE;
> +	var_size = BCOM_MAX_TASKS * (BCOM_VAR_SIZE + BCOM_INC_SIZE);
> +	fdt_size = BCOM_FDT_SIZE;
> +
> +	bcom_eng->tdt = bcom_sram_alloc(tdt_size, sizeof(u32), &tdt_pa);
> +	bcom_eng->ctx = bcom_sram_alloc(ctx_size, BCOM_CTX_ALIGN, &ctx_pa);
> +	bcom_eng->var = bcom_sram_alloc(var_size, BCOM_VAR_ALIGN, &var_pa);
> +	bcom_eng->fdt = bcom_sram_alloc(fdt_size, BCOM_FDT_ALIGN, &fdt_pa);
> +
> +	if (!bcom_eng->tdt || !bcom_eng->ctx || !bcom_eng->var || !bcom_eng->fdt) {
> +		printk(KERN_ERR "DMA: SRAM alloc failed in engine init !\n");
> +
> +		bcom_sram_free(bcom_eng->tdt);
> +		bcom_sram_free(bcom_eng->ctx);
> +		bcom_sram_free(bcom_eng->var);
> +		bcom_sram_free(bcom_eng->fdt);
> +
> +		return -ENOMEM;
> +	}
> +
> +	memset(bcom_eng->tdt, 0x00, tdt_size);
> +	memset(bcom_eng->ctx, 0x00, ctx_size);
> +	memset(bcom_eng->var, 0x00, var_size);
> +	memset(bcom_eng->fdt, 0x00, fdt_size);
> +
> +	/* Copy the FDT for the EU#3 */
> +	memcpy(&bcom_eng->fdt[48], fdt_ops, sizeof(fdt_ops));
> +
> +	/* Initialize Task base structure */
> +	for (task=0; task<BCOM_MAX_TASKS; task++)
> +	{
> +		out_be16(&bcom_eng->regs->tcr[task], 0);
> +		out_8(&bcom_eng->regs->ipr[task], 0);
> +
> +		bcom_eng->tdt[task].context	= ctx_pa;
> +		bcom_eng->tdt[task].var	= var_pa;
> +		bcom_eng->tdt[task].fdt	= fdt_pa;
> +
> +		var_pa += BCOM_VAR_SIZE + BCOM_INC_SIZE;
> +		ctx_pa += BCOM_CTX_SIZE;
> +	}
> +
> +	out_be32(&bcom_eng->regs->taskBar, tdt_pa);
> +
> +	/* Init 'always' initiator */
> +	out_8(&bcom_eng->regs->ipr[BCOM_INITIATOR_ALWAYS], BCOM_IPR_ALWAYS);
> +
> +	/* Disable COMM Bus Prefetch, apparently it's not reliable yet */
> +	/* FIXME: This should be done on 5200 and not 5200B ... */
> +	out_be16(&bcom_eng->regs->PtdCntrl, in_be16(&bcom_eng->regs->PtdCntrl) | 1);
> +
> +	/* Init lock */
> +	spin_lock_init(&bcom_eng->lock);
> +
> +	return 0;
> +}
> +
> +static void
> +bcom_engine_cleanup(void)
> +{
> +	int task;
> +
> +	/* Stop all tasks */
> +	for (task=0; task<BCOM_MAX_TASKS; task++)
> +	{
> +		out_be16(&bcom_eng->regs->tcr[task], 0);
> +		out_8(&bcom_eng->regs->ipr[task], 0);
> +	}
> +
> +	out_be32(&bcom_eng->regs->taskBar, 0ul);
> +
> +	/* Release the SRAM zones */
> +	bcom_sram_free(bcom_eng->tdt);
> +	bcom_sram_free(bcom_eng->ctx);
> +	bcom_sram_free(bcom_eng->var);
> +	bcom_sram_free(bcom_eng->fdt);
> +}
> +
> +
> +/* ======================================================================== */
> +/* OF platform driver                                                       */
> +/* ======================================================================== */
> +
> +static int __devinit
> +mpc52xx_bcom_probe(struct of_device *op, const struct of_device_id *match)
> +{
> +	struct device_node *ofn_bcom, *ofn_sram;
> +	struct resource res_bcom;
> +
> +	int rv;
> +
> +	/* Inform user we're ok so far */
> +	printk(KERN_INFO "DMA: MPC52xx BestComm driver\n");
> +
> +	/* Get the bestcomm node */
> +	ofn_bcom = op->node;
> +	of_node_get(ofn_bcom);
> +
> +	/* Prepare SRAM */
> +	ofn_sram = of_find_compatible_node(NULL, "sram", "mpc5200-sram");
> +	if (!ofn_sram) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"No SRAM found in device tree\n");
> +		rv = -ENODEV;
> +		goto error_ofput;
> +	}
> +
> +	rv = bcom_sram_init(ofn_sram, DRIVER_NAME);
> +
> +	of_node_put(ofn_sram);
> +
> +	if (rv) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"Error in SRAM init\n");
> +		goto error_ofput;
> +	}
> +
> +	/* Get a clean struct */
> +	bcom_eng = kzalloc(sizeof(struct bcom_engine), GFP_KERNEL);
> +	if (!bcom_eng) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"Can't allocate state structure\n");
> +		rv = -ENOMEM;
> +		goto error_sramclean;
> +	}
> +
> +	/* Save the node */
> +	bcom_eng->ofnode = ofn_bcom;
> +
> +	/* Get, reserve & map io */
> +	if (of_address_to_resource(bcom_eng->ofnode, 0, &res_bcom)) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"Can't get resource\n");
> +		rv = -EINVAL;
> +		goto error_sramclean;
> +	}
> +
> +	if (!request_mem_region(res_bcom.start, sizeof(struct mpc52xx_sdma),
> +				DRIVER_NAME)) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"Can't request registers region\n");
> +		rv = -EBUSY;
> +		goto error_sramclean;
> +	}
> +
> +	bcom_eng->regs_base = res_bcom.start;
> +	bcom_eng->regs = ioremap(res_bcom.start, sizeof(struct mpc52xx_sdma));
> +	if (!bcom_eng->regs) {
> +		printk(KERN_ERR DRIVER_NAME ": "
> +			"Can't map registers\n");
> +		rv = -ENOMEM;
> +		goto error_release;
> +	}
> +
> +	/* Now, do the real init */
> +	rv = bcom_engine_init();
> +	if (rv)
> +		goto error_unmap;
> +
> +	/* Done ! */
> +	printk(KERN_INFO "DMA: MPC52xx BestComm engine @%08lx ok !\n",
> +		bcom_eng->regs_base);
> +
> +	return 0;
> +
> +	/* Error path */
> +error_unmap:
> +	iounmap(bcom_eng->regs);
> +error_release:
> +	release_mem_region(res_bcom.start, sizeof(struct mpc52xx_sdma));
> +error_sramclean:
> +	bcom_sram_cleanup();
> +error_ofput:
> +	of_node_put(bcom_eng->ofnode);
> +
> +	printk(KERN_ERR "DMA: MPC52xx BestComm init failed !\n");
> +
> +	return rv;
> +}
> +
> +
> +static int
> +mpc52xx_bcom_remove(struct of_device *op)
> +{
> +	/* Clean up the engine */
> +	bcom_engine_cleanup();
> +
> +	/* Cleanup SRAM */
> +	bcom_sram_cleanup();
> +
> +	/* Release regs */
> +	iounmap(bcom_eng->regs);
> +	release_mem_region(bcom_eng->regs_base, sizeof(struct mpc52xx_sdma));
> +
> +	/* Release the node */
> +	of_node_put(bcom_eng->ofnode);
> +
> +	/* Release memory */
> +	kfree(bcom_eng);
> +	bcom_eng = NULL;
> +
> +	return 0;
> +}
> +
> +
> +#ifdef CONFIG_PM
> +
> +static int
> +mpc52xx_bcom_suspend(struct of_device *op, pm_message_t state)
> +{
> +	return 0;	/* FIXME : What to do here ? */
> +}
> +
> +static int
> +mpc52xx_bcom_resume(struct of_device *op)
> +{
> +	return 0;
> +}
> +
> +#endif
> +
> +static struct of_device_id mpc52xx_bcom_of_match[] = {
> +	{
> +		.type		= "dma-controller",
> +		.compatible	= "mpc5200-bestcomm",
> +	},
> +	{},
> +};
> +
> +MODULE_DEVICE_TABLE(of, mpc52xx_bcom_of_match);
> +
> +
> +static struct of_platform_driver mpc52xx_bcom_of_platform_driver = {
> +	.owner		= THIS_MODULE,
> +	.name		= DRIVER_NAME,
> +	.match_table	= mpc52xx_bcom_of_match,
> +	.probe		= mpc52xx_bcom_probe,
> +	.remove		= mpc52xx_bcom_remove,
> +#ifdef CONFIG_PM
> +	.suspend	= mpc52xx_bcom_suspend,
> +	.resume		= mpc52xx_bcom_resume,
> +#endif
> +	.driver		= {
> +		.name	= DRIVER_NAME,
> +		.owner	= THIS_MODULE,
> +	},
> +};
> +
> +
> +/* ======================================================================== */
> +/* Module                                                                   */
> +/* ======================================================================== */
> +
> +static int __init
> +mpc52xx_bcom_init(void)
> +{
> +	return of_register_platform_driver(&mpc52xx_bcom_of_platform_driver);
> +}
> +
> +static void __exit
> +mpc52xx_bcom_exit(void)
> +{
> +	of_unregister_platform_driver(&mpc52xx_bcom_of_platform_driver);
> +}
> +
> +/* If we're not a module, we must make sure everything is setup before  */
> +/* anyone tries to use us ... that's why we use subsys_initcall instead */
> +/* of module_init. */
> +subsys_initcall(mpc52xx_bcom_init);
> +module_exit(mpc52xx_bcom_exit);
> +
> +MODULE_DESCRIPTION("Freescale MPC52xx BestComm DMA");
> +MODULE_AUTHOR("Sylvain Munaut <tnt@246tNt.com>");
> +MODULE_AUTHOR("Andrey Volkov <avolkov@varma-el.com>");
> +MODULE_AUTHOR("Dale Farnsworth <dfarnsworth@mvista.com>");
> +MODULE_LICENSE("GPL v2");
> +
> diff --git a/arch/powerpc/sysdev/bestcomm/bestcomm.h b/arch/powerpc/sysdev/bestcomm/bestcomm.h
> new file mode 100644
> index 0000000..eac3eec
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/bestcomm.h
> @@ -0,0 +1,136 @@
> +/*
> + * Public header for the MPC52xx processor BestComm driver
> + *
> + *
> + * Copyright (C) 2006      Sylvain Munaut <tnt@246tNt.com>
> + * Copyright (C) 2005      Varma Electronics Oy,
> + *                         ( by Andrey Volkov <avolkov@varma-el.com> )
> + * Copyright (C) 2003-2004 MontaVista, Software, Inc.
> + *                         ( by Dale Farnsworth <dfarnsworth@mvista.com> )
> + *
> + * This file is licensed under the terms of the GNU General Public License
> + * version 2. This program is licensed "as is" without any warranty of any
> + * kind, whether express or implied.
> + */
> +
> +#ifndef __BESTCOMM_H__
> +#define __BESTCOMM_H__
> +
> +struct bcom_bd; /* defined later on ... */
> +
> +
> +/* ======================================================================== */
> +/* Generic task managment                                                   */
> +/* ======================================================================== */
> +
> +struct bcom_task {
> +	unsigned int	tasknum;
> +	unsigned int	flags;
> +	int		irq;
> +
> +	struct bcom_bd	*bd;
> +	phys_addr_t	bd_pa;
> +	void		**cookie;
> +	unsigned short	index;
> +	unsigned short	outdex;
> +	unsigned int	num_bd;
> +	unsigned int	bd_size;
> +
> +	void*		priv;
> +};
> +
> +#define BCOM_FLAGS_NONE         0x00000000ul
> +#define BCOM_FLAGS_ENABLE_TASK  (1ul <<  0)
> +
> +
> +extern void bcom_enable(struct bcom_task *tsk);
> +extern void bcom_disable(struct bcom_task *tsk);
> +
> +static inline int
> +bcom_get_task_irq(struct bcom_task *tsk) {
> +	return tsk->irq;
> +}
> +
> +
> +/* Debug dumps */
> +extern void bcom_dump_status(void);
> +extern void bcom_dump_task(int task);
> +extern void bcom_dump_bdring(struct bcom_task *tsk);
> +
> +
> +/* ======================================================================== */
> +/* BD based tasks helpers                                                   */
> +/* ======================================================================== */
> +
> +struct bcom_bd {
> +	u32	status;
> +	u32	data[1];	/* variable, but at least 1 */
> +};
> +
> +#define BCOM_BD_READY	0x40000000ul
> +
> +static inline int	/* user shouldn't use this ! */
> +_bcom_next_index(struct bcom_task *tsk)
> +{
> +	return ((tsk->index + 1) == tsk->num_bd) ? 0 : tsk->index + 1;
> +}
> +
> +static inline int	/* user shouldn't use this ! */
> +_bcom_next_outdex(struct bcom_task *tsk)
> +{
> +	return ((tsk->outdex + 1) == tsk->num_bd) ? 0 : tsk->outdex + 1;
> +}
> +
> +static inline int
> +bcom_queue_empty(struct bcom_task *tsk)
> +{
> +	return tsk->index == tsk->outdex;
> +}
> +
> +static inline int
> +bcom_queue_full(struct bcom_task *tsk)
> +{
> +	return tsk->outdex == _bcom_next_index(tsk);
> +}
> +
> +static inline int
> +bcom_buffer_done(struct bcom_task *tsk)
> +{
> +	if (bcom_queue_empty(tsk))
> +		return 0;
> +	return !(tsk->bd[tsk->outdex].status & BCOM_BD_READY);
> +}
> +
> +static inline struct bcom_bd *
> +bcom_prepare_next_buffer(struct bcom_task *tsk)
> +{
> +	tsk->bd[tsk->index].status = 0;	/* cleanup last status */
> +	return &tsk->bd[tsk->index];
> +}
> +
> +static inline void
> +bcom_submit_next_buffer(struct bcom_task *tsk, void *cookie)
> +{
> +	tsk->cookie[tsk->index] = cookie;
> +	mb();	/* ensure the bd is really up-to-date */
> +	tsk->bd[tsk->index].status |= BCOM_BD_READY;
> +	tsk->index = _bcom_next_index(tsk);
> +	if (tsk->flags & BCOM_FLAGS_ENABLE_TASK)
> +		bcom_enable(tsk);
> +}
> +
> +static inline void *
> +bcom_retrieve_buffer(struct bcom_task *tsk, u32 *p_status, struct bcom_bd **p_bd)
> +{
> +	void *cookie = tsk->cookie[tsk->outdex];
> +	if (p_status)
> +		*p_status = tsk->bd[tsk->outdex].status;
> +	if (p_bd)
> +		*p_bd = &tsk->bd[tsk->outdex];
> +	tsk->outdex = _bcom_next_outdex(tsk);
> +	return cookie;
> +}
> +
> +
> +#endif /* __BESTCOMM_H__ */
> +
> diff --git a/arch/powerpc/sysdev/bestcomm/bestcomm_priv.h b/arch/powerpc/sysdev/bestcomm/bestcomm_priv.h
> new file mode 100644
> index 0000000..6f33f0c
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/bestcomm_priv.h
> @@ -0,0 +1,325 @@
> +/*
> + * Private header for the MPC52xx processor BestComm driver
> + *
> + *
> + * Copyright (C) 2006      Sylvain Munaut <tnt@246tNt.com>
> + * Copyright (C) 2005      Varma Electronics Oy,
> + *                         ( by Andrey Volkov <avolkov@varma-el.com> )
> + * Copyright (C) 2003-2004 MontaVista, Software, Inc.
> + *                         ( by Dale Farnsworth <dfarnsworth@mvista.com> )
> + *
> + * This file is licensed under the terms of the GNU General Public License
> + * version 2. This program is licensed "as is" without any warranty of any
> + * kind, whether express or implied.
> + */
> +
> +#ifndef __BESTCOMM_PRIV_H__
> +#define __BESTCOMM_PRIV_H__
> +
> +#include <linux/spinlock.h>
> +#include <asm/io.h>
> +#include <asm/prom.h>
> +#include <asm/mpc52xx.h>
> +
> +#include "sram.h"
> +
> +
> +/* ======================================================================== */
> +/* Engine related stuff                                                     */
> +/* ======================================================================== */
> +
> +/* Zones sizes and needed alignments */
> +#define BCOM_MAX_TASKS		16
> +#define BCOM_MAX_VAR		24
> +#define BCOM_MAX_INC		8
> +#define BCOM_MAX_FDT		64
> +#define BCOM_MAX_CTX		20
> +#define BCOM_CTX_SIZE		(BCOM_MAX_CTX * sizeof(u32))
> +#define BCOM_CTX_ALIGN		0x100
> +#define BCOM_VAR_SIZE		(BCOM_MAX_VAR * sizeof(u32))
> +#define BCOM_INC_SIZE		(BCOM_MAX_INC * sizeof(u32))
> +#define BCOM_VAR_ALIGN		0x80
> +#define BCOM_FDT_SIZE		(BCOM_MAX_FDT * sizeof(u32))
> +#define BCOM_FDT_ALIGN		0x100
> +
> +/* Task Descriptor Table Entry */
> +struct bcom_tdt {
> +	u32 start;
> +	u32 stop;
> +	u32 var;
> +	u32 fdt;
> +	u32 exec_status;	/* used internally by BestComm engine */
> +	u32 mvtp;		/* used internally by BestComm engine */
> +	u32 context;
> +	u32 litbase;
> +};
> +
> +/* This holds all info needed globaly to handle the engine */
> +struct bcom_engine {
> +	struct device_node		*ofnode;
> +	struct mpc52xx_sdma __iomem     *regs;
> +	phys_addr_t                      regs_base;
> +
> +	struct bcom_tdt			*tdt;
> +	u32				*ctx;
> +	u32				*var;
> +	u32				*fdt;
> +
> +	spinlock_t			lock;
> +};
> +
> +extern struct bcom_engine *bcom_eng;
> +
> +
> +/* ======================================================================== */
> +/* Tasks related stuff                                                      */
> +/* ======================================================================== */
> +
> +/* Tasks image header */
> +#define BCOM_TASK_MAGIC		0x4243544B	/* 'BCTK' */
> +
> +struct bcom_task_header {
> +	u32	magic;
> +	u8	desc_size;	/* the size fields     */
> +	u8	var_size;	/* are given in number */
> +	u8	inc_size;	/* of 32-bits words    */
> +	u8	first_var;
> +	u8	reserved[8];
> +};
> +
> +/* Descriptors stucture & co */
> +#define BCOM_DESC_NOP		0x000001f8
> +#define BCOM_LCD_MASK		0x80000000
> +#define BCOM_DRD_EXTENDED	0x40000000
> +#define BCOM_DRD_INITIATOR_SHIFT	21
> +
> +/* Tasks pragma */
> +#define BCOM_PRAGMA_BIT_RSV		7	/* reserved pragma bit */
> +#define BCOM_PRAGMA_BIT_PRECISE_INC	6	/* increment 0=when possible, */
> +						/*           1=iter end */
> +#define BCOM_PRAGMA_BIT_RST_ERROR_NO	5	/* don't reset errors on */
> +						/* task enable */
> +#define BCOM_PRAGMA_BIT_PACK		4	/* pack data enable */
> +#define BCOM_PRAGMA_BIT_INTEGER		3	/* data alignment */
> +						/* 0=frac(msb), 1=int(lsb) */
> +#define BCOM_PRAGMA_BIT_SPECREAD	2	/* XLB speculative read */
> +#define BCOM_PRAGMA_BIT_CW		1	/* write line buffer enable */
> +#define BCOM_PRAGMA_BIT_RL		0	/* read line buffer enable */
> +
> +	/* Looks like XLB speculative read generates XLB errors when a buffer
> +	 * is at the end of the physical memory. i.e. when accessing the
> +	 * lasts words, the engine tries to prefetch the next but there is no
> +	 * next ...
> +	 */
> +#define BCOM_STD_PRAGMA		((0 << BCOM_PRAGMA_BIT_RSV)		| \
> +				 (0 << BCOM_PRAGMA_BIT_PRECISE_INC)	| \
> +				 (0 << BCOM_PRAGMA_BIT_RST_ERROR_NO)	| \
> +				 (0 << BCOM_PRAGMA_BIT_PACK)		| \
> +				 (0 << BCOM_PRAGMA_BIT_INTEGER)		| \
> +				 (0 << BCOM_PRAGMA_BIT_SPECREAD)	| \
> +				 (1 << BCOM_PRAGMA_BIT_CW)		| \
> +				 (1 << BCOM_PRAGMA_BIT_RL))
> +
> +#define BCOM_PCI_PRAGMA		((0 << BCOM_PRAGMA_BIT_RSV)		| \
> +				 (0 << BCOM_PRAGMA_BIT_PRECISE_INC)	| \
> +				 (0 << BCOM_PRAGMA_BIT_RST_ERROR_NO)	| \
> +				 (0 << BCOM_PRAGMA_BIT_PACK)		| \
> +				 (1 << BCOM_PRAGMA_BIT_INTEGER)		| \
> +				 (0 << BCOM_PRAGMA_BIT_SPECREAD)	| \
> +				 (1 << BCOM_PRAGMA_BIT_CW)		| \
> +				 (1 << BCOM_PRAGMA_BIT_RL))
> +
> +#define BCOM_ATA_PRAGMA		BCOM_STD_PRAGMA
> +#define BCOM_CRC16_DP_0_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_CRC16_DP_1_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_FEC_RX_BD_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_FEC_TX_BD_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_0_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_1_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_2_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_3_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_BD_0_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_DP_BD_1_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_RX_BD_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_TX_BD_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_GEN_LPC_PRAGMA	BCOM_STD_PRAGMA
> +#define BCOM_PCI_RX_PRAGMA	BCOM_PCI_PRAGMA
> +#define BCOM_PCI_TX_PRAGMA	BCOM_PCI_PRAGMA
> +
> +/* Initiators number */
> +#define BCOM_INITIATOR_ALWAYS	 0
> +#define BCOM_INITIATOR_SCTMR_0	 1
> +#define BCOM_INITIATOR_SCTMR_1	 2
> +#define BCOM_INITIATOR_FEC_RX	 3
> +#define BCOM_INITIATOR_FEC_TX	 4
> +#define BCOM_INITIATOR_ATA_RX	 5
> +#define BCOM_INITIATOR_ATA_TX	 6
> +#define BCOM_INITIATOR_SCPCI_RX	 7
> +#define BCOM_INITIATOR_SCPCI_TX	 8
> +#define BCOM_INITIATOR_PSC3_RX	 9
> +#define BCOM_INITIATOR_PSC3_TX	10
> +#define BCOM_INITIATOR_PSC2_RX	11
> +#define BCOM_INITIATOR_PSC2_TX	12
> +#define BCOM_INITIATOR_PSC1_RX	13
> +#define BCOM_INITIATOR_PSC1_TX	14
> +#define BCOM_INITIATOR_SCTMR_2	15
> +#define BCOM_INITIATOR_SCLPC	16
> +#define BCOM_INITIATOR_PSC5_RX	17
> +#define BCOM_INITIATOR_PSC5_TX	18
> +#define BCOM_INITIATOR_PSC4_RX	19
> +#define BCOM_INITIATOR_PSC4_TX	20
> +#define BCOM_INITIATOR_I2C2_RX	21
> +#define BCOM_INITIATOR_I2C2_TX	22
> +#define BCOM_INITIATOR_I2C1_RX	23
> +#define BCOM_INITIATOR_I2C1_TX	24
> +#define BCOM_INITIATOR_PSC6_RX	25
> +#define BCOM_INITIATOR_PSC6_TX	26
> +#define BCOM_INITIATOR_IRDA_RX	25
> +#define BCOM_INITIATOR_IRDA_TX	26
> +#define BCOM_INITIATOR_SCTMR_3	27
> +#define BCOM_INITIATOR_SCTMR_4	28
> +#define BCOM_INITIATOR_SCTMR_5	29
> +#define BCOM_INITIATOR_SCTMR_6	30
> +#define BCOM_INITIATOR_SCTMR_7	31
> +
> +/* Initiators priorities */
> +#define BCOM_IPR_ALWAYS		7
> +#define BCOM_IPR_SCTMR_0	2
> +#define BCOM_IPR_SCTMR_1	2
> +#define BCOM_IPR_FEC_RX		6
> +#define BCOM_IPR_FEC_TX		5
> +#define BCOM_IPR_ATA_RX		4
> +#define BCOM_IPR_ATA_TX		3
> +#define BCOM_IPR_SCPCI_RX	2
> +#define BCOM_IPR_SCPCI_TX	2
> +#define BCOM_IPR_PSC3_RX	2
> +#define BCOM_IPR_PSC3_TX	2
> +#define BCOM_IPR_PSC2_RX	2
> +#define BCOM_IPR_PSC2_TX	2
> +#define BCOM_IPR_PSC1_RX	2
> +#define BCOM_IPR_PSC1_TX	2
> +#define BCOM_IPR_SCTMR_2	2
> +#define BCOM_IPR_SCLPC		2
> +#define BCOM_IPR_PSC5_RX	2
> +#define BCOM_IPR_PSC5_TX	2
> +#define BCOM_IPR_PSC4_RX	2
> +#define BCOM_IPR_PSC4_TX	2
> +#define BCOM_IPR_I2C2_RX	2
> +#define BCOM_IPR_I2C2_TX	2
> +#define BCOM_IPR_I2C1_RX	2
> +#define BCOM_IPR_I2C1_TX	2
> +#define BCOM_IPR_PSC6_RX	2
> +#define BCOM_IPR_PSC6_TX	2
> +#define BCOM_IPR_IRDA_RX	2
> +#define BCOM_IPR_IRDA_TX	2
> +#define BCOM_IPR_SCTMR_3	2
> +#define BCOM_IPR_SCTMR_4	2
> +#define BCOM_IPR_SCTMR_5	2
> +#define BCOM_IPR_SCTMR_6	2
> +#define BCOM_IPR_SCTMR_7	2
> +
> +
> +/* ======================================================================== */
> +/* API                                                                      */
> +/* ======================================================================== */
> +
> +extern struct bcom_task *bcom_task_alloc(int bd_count, int bd_size, int priv_size);
> +extern void bcom_task_release(struct bcom_task *tsk);
> +
> +extern int bcom_load_image(int task, u32 *task_image);
> +extern void bcom_set_initiator(int task, int initiator);
> +
> +
> +#define TASK_ENABLE             0x8000
> +
> +static inline void
> +bcom_enable_task(int task)
> +{
> +        u16 reg;
> +        reg = in_be16(&bcom_eng->regs->tcr[task]);
> +        out_be16(&bcom_eng->regs->tcr[task],  reg | TASK_ENABLE);
> +}
> +
> +static inline void
> +bcom_disable_task(int task)
> +{
> +        u16 reg = in_be16(&bcom_eng->regs->tcr[task]);
> +        out_be16(&bcom_eng->regs->tcr[task], reg & ~TASK_ENABLE);
> +}
> +
> +
> +static inline u32 *
> +bcom_task_desc(int task)
> +{
> +	return bcom_sram_pa2va(bcom_eng->tdt[task].start);
> +}
> +
> +static inline int
> +bcom_task_num_descs(int task)
> +{
> +	return (bcom_eng->tdt[task].stop - bcom_eng->tdt[task].start)/sizeof(u32) + 1;
> +}
> +
> +static inline u32 *
> +bcom_task_var(int task)
> +{
> +	return bcom_sram_pa2va(bcom_eng->tdt[task].var);
> +}
> +
> +static inline u32 *
> +bcom_task_inc(int task)
> +{
> +	return &bcom_task_var(task)[BCOM_MAX_VAR];
> +}
> +
> +
> +static inline int
> +bcom_drd_is_extended(u32 desc)
> +{
> +	return (desc) & BCOM_DRD_EXTENDED;
> +}
> +
> +static inline int
> +bcom_desc_is_drd(u32 desc)
> +{
> +	return !(desc & BCOM_LCD_MASK) && desc != BCOM_DESC_NOP;
> +}
> +
> +static inline int
> +bcom_desc_initiator(u32 desc)
> +{
> +	return (desc >> BCOM_DRD_INITIATOR_SHIFT) & 0x1f;
> +}
> +
> +static inline void
> +bcom_set_desc_initiator(u32 *desc, int initiator)
> +{
> +	*desc = (*desc & ~(0x1f << BCOM_DRD_INITIATOR_SHIFT)) |
> +			((initiator & 0x1f) << BCOM_DRD_INITIATOR_SHIFT);
> +}
> +
> +
> +static inline void
> +bcom_set_task_pragma(int task, int pragma)
> +{
> +	u32 *fdt = &bcom_eng->tdt[task].fdt;
> +	*fdt = (*fdt & ~0xff) | pragma;
> +}
> +
> +static inline void
> +bcom_set_task_auto_start(int task, int next_task)
> +{
> +	u16 __iomem *tcr = &bcom_eng->regs->tcr[task];
> +	out_be16(tcr, (in_be16(tcr) & ~0xff) | 0x00c0 | next_task);
> +}
> +
> +static inline void
> +bcom_set_tcr_initiator(int task, int initiator)
> +{
> +	u16 __iomem *tcr = &bcom_eng->regs->tcr[task];
> +	out_be16(tcr, (in_be16(tcr) & ~0x1f00) | ((initiator & 0x1f) << 8));
> +}
> +
> +
> +#endif /* __BESTCOMM_PRIV_H__ */
> +
> diff --git a/arch/powerpc/sysdev/bestcomm/sram.c b/arch/powerpc/sysdev/bestcomm/sram.c
> new file mode 100644
> index 0000000..a5094d6
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/sram.c
> @@ -0,0 +1,177 @@
> +/*
> + * Simple memory allocator for on-board SRAM
> + *
> + *
> + * Maintainer : Sylvain Munaut <tnt@246tNt.com>
> + *
> + * Copyright (C) 2005 Sylvain Munaut <tnt@246tNt.com>
> + *
> + * This file is licensed under the terms of the GNU General Public License
> + * version 2. This program is licensed "as is" without any warranty of any
> + * kind, whether express or implied.
> + */
> +
> +#include <linux/kernel.h>
> +#include <linux/module.h>
> +#include <linux/slab.h>
> +#include <linux/spinlock.h>
> +#include <linux/string.h>
> +#include <linux/ioport.h>
> +
> +#include <asm/io.h>
> +#include <asm/mmu.h>
> +#include <asm/prom.h>
> +
> +#include "sram.h"
> +
> +
> +/* Struct keeping our 'state' */
> +struct bcom_sram *bcom_sram = NULL;
> +EXPORT_SYMBOL_GPL(bcom_sram);	/* needed for inline functions */
> +
> +
> +/* ======================================================================== */
> +/* Public API                                                               */
> +/* ======================================================================== */
> +/* DO NOT USE in interrupts, if needed in irq handler, we should use the
> +   _irqsave version of the spin_locks */
> +
> +int bcom_sram_init(struct device_node *sram_node, char *owner)
> +{
> +	int rv;
> +	const u32 *regaddr_p;
> +	u64 regaddr64, size64;
> +	unsigned int psize;
> +
> +	/* Create our state struct */
> +	if (bcom_sram) {
> +		printk(KERN_ERR "%s: bcom_sram_init: "
> +			"Already initialiwed !\n", owner);
> +		return -EBUSY;
> +	}
> +
> +	bcom_sram = kmalloc(sizeof(struct bcom_sram), GFP_KERNEL);
> +	if (!bcom_sram) {
> +		printk(KERN_ERR "%s: bcom_sram_init: "
> +			"Couldn't allocate internal state !\n", owner);
> +		return -ENOMEM;
> +	}
> +
> +	/* Get address and size of the sram */
> +	regaddr_p = of_get_address(sram_node, 0, &size64, NULL);
> +	if (!regaddr_p) {
> +		printk(KERN_ERR "%s: bcom_sram_init: "
> +			"Invalid device node !\n", owner);
> +		rv = -EINVAL;
> +		goto error_free;
> +	}
> +
> +	regaddr64 = of_translate_address(sram_node, regaddr_p);
> +
> +	bcom_sram->base_phys = (phys_addr_t) regaddr64;
> +	bcom_sram->size = (unsigned int) size64;
> +
> +	/* Request region */
> +	if (!request_mem_region(bcom_sram->base_phys, bcom_sram->size, owner)) {
> +		printk(KERN_ERR "%s: bcom_sram_init: "
> +			"Couln't request region !\n", owner);
> +		rv = -EBUSY;
> +		goto error_free;
> +	}
> +
> +	/* Map SRAM */
> +		/* sram is not really __iomem */
> +	bcom_sram->base_virt = (void*) ioremap(bcom_sram->base_phys, bcom_sram->size);
> +
> +	if (!bcom_sram->base_virt) {
> +		printk(KERN_ERR "%s: bcom_sram_init: "
> +			"Map error SRAM zone 0x%08lx (0x%0x)!\n",
> +			owner, bcom_sram->base_phys, bcom_sram->size );
> +		rv = -ENOMEM;
> +		goto error_release;
> +	}
> +
> +	/* Create an rheap (defaults to 32 bits word alignment) */
> +	bcom_sram->rh = rh_create(4);
> +
> +	/* Attach the free zones */
> +#if 0
> +	/* Currently disabled ... for future use only */
> +	reg_addr_p = of_get_property(sram_node, "available", &psize);
> +#else
> +	regaddr_p = NULL;
> +	psize = 0;
> +#endif
> +
> +	if (!regaddr_p || !psize) {
> +		/* Attach the whole zone */
> +		rh_attach_region(bcom_sram->rh, 0, bcom_sram->size);
> +	} else {
> +		/* Attach each zone independently */
> +		while (psize >= 2 * sizeof(u32)) {
> +			phys_addr_t zbase = of_translate_address(sram_node, regaddr_p);
> +			rh_attach_region(bcom_sram->rh, zbase - bcom_sram->base_phys, regaddr_p[1]);
> +			regaddr_p += 2;
> +			psize -= 2 * sizeof(u32);
> +		}
> +	}
> +
> +	/* Init our spinlock */
> +	spin_lock_init(&bcom_sram->lock);
> +
> +	return 0;
> +
> +error_release:
> +	release_mem_region(bcom_sram->base_phys, bcom_sram->size);
> +error_free:
> +	kfree(bcom_sram);
> +	bcom_sram = NULL;
> +
> +	return rv;
> +}
> +EXPORT_SYMBOL_GPL(bcom_sram_init);
> +
> +void bcom_sram_cleanup(void)
> +{
> +	/* Free resources */
> +	if (bcom_sram) {
> +		rh_destroy(bcom_sram->rh);
> +		iounmap((void __iomem *)bcom_sram->base_virt);
> +		release_mem_region(bcom_sram->base_phys, bcom_sram->size);
> +		kfree(bcom_sram);
> +		bcom_sram = NULL;
> +	}
> +}
> +EXPORT_SYMBOL_GPL(bcom_sram_cleanup);
> +
> +void* bcom_sram_alloc(int size, int align, phys_addr_t *phys)
> +{
> +	unsigned long offset;
> +
> +	spin_lock(&bcom_sram->lock);
> +	offset = rh_alloc_align(bcom_sram->rh, size, align, NULL);
> +	spin_unlock(&bcom_sram->lock);
> +
> +	if (IS_ERR_VALUE(offset))
> +		return NULL;
> +
> +	*phys = bcom_sram->base_phys + offset;
> +	return bcom_sram->base_virt + offset;
> +}
> +EXPORT_SYMBOL_GPL(bcom_sram_alloc);
> +
> +void bcom_sram_free(void *ptr)
> +{
> +	unsigned long offset;
> +
> +	if (!ptr)
> +		return;
> +
> +	offset = ptr - bcom_sram->base_virt;
> +
> +	spin_lock(&bcom_sram->lock);
> +	rh_free(bcom_sram->rh, offset);
> +	spin_unlock(&bcom_sram->lock);
> +}
> +EXPORT_SYMBOL_GPL(bcom_sram_free);
> +
> diff --git a/arch/powerpc/sysdev/bestcomm/sram.h b/arch/powerpc/sysdev/bestcomm/sram.h
> new file mode 100644
> index 0000000..b6d6689
> --- /dev/null
> +++ b/arch/powerpc/sysdev/bestcomm/sram.h
> @@ -0,0 +1,54 @@
> +/*
> + * Handling of a sram zone for bestcomm
> + *
> + *
> + * Copyright (C) 2007 Sylvain Munaut <tnt@246tNt.com>
> + *
> + * This file is licensed under the terms of the GNU General Public License
> + * version 2. This program is licensed "as is" without any warranty of any
> + * kind, whether express or implied.
> + */
> +
> +#ifndef __BESTCOMM_SRAM_H__
> +#define __BESTCOMM_SRAM_H__
> +
> +#include <asm/rheap.h>
> +#include <asm/mmu.h>
> +#include <linux/spinlock.h>
> +
> +
> +/* Structure used internally */
> +	/* The internals are here for the inline functions
> +	 * sake, certainly not for the user to mess with !
> +	 */
> +struct bcom_sram {
> +	phys_addr_t		 base_phys;
> +	void 			*base_virt;
> +	unsigned int		 size;
> +	rh_info_t		*rh;
> +	spinlock_t		 lock;
> +};
> +
> +extern struct bcom_sram *bcom_sram;
> +
> +
> +/* Public API */
> +extern int  bcom_sram_init(struct device_node *sram_node, char *owner);
> +extern void bcom_sram_cleanup(void);
> +
> +extern void* bcom_sram_alloc(int size, int align, phys_addr_t *phys);
> +extern void  bcom_sram_free(void *ptr);
> +
> +static inline phys_addr_t bcom_sram_va2pa(void *va) {
> +	return bcom_sram->base_phys +
> +		(unsigned long)(va - bcom_sram->base_virt);
> +}
> +
> +static inline void *bcom_sram_pa2va(phys_addr_t pa) {
> +	return bcom_sram->base_virt +
> +		(unsigned long)(pa - bcom_sram->base_phys);
> +}
> +
> +
> +#endif  /* __BESTCOMM_SRAM_H__ */
> +

^ permalink raw reply

* Re: [RFC PATCH v0.2] net driver: mpc52xx fec
From: Sven Luther @ 2007-09-17  9:53 UTC (permalink / raw)
  To: Domen Puncer; +Cc: netdev, linuxppc-embedded
In-Reply-To: <20070915121444.GA19857@nd47.coderock.org>

On Sat, Sep 15, 2007 at 02:14:44PM +0200, Domen Puncer wrote:
> Updated and split version at:
> http://coderock.org/tmp/fec-v3rc1/
> 
> I'll repost to lists once I run-test them.

When applying those patches, the build did die with :


  ERROR: "phy_mii_ioctl" [drivers/net/fec_mpc52xx/fec_mpc52xx.ko] undefined!

Apparently, phy_mii_ioctl is not an exported symbol.

Domen, did you maybe forget a little snipplet when you cut the patches
in different pieces ? Or did i mess up applying them ?

Friendly,

Sven Luther

^ permalink raw reply

* Re: [PATCH] fix xmon input on 440
From: Josh Boyer @ 2007-09-17 10:58 UTC (permalink / raw)
  To: Hollis Blanchard; +Cc: Olof Johansson, linuxppc-dev, David Gibson
In-Reply-To: <1190002521.16747.1.camel@basalt>

On Sun, 2007-09-16 at 23:15 -0500, Hollis Blanchard wrote:
> On Sun, 2007-09-16 at 22:39 -0500, Olof Johansson wrote:
> > On Sun, Sep 16, 2007 at 10:26:37PM -0500, Josh Boyer wrote:
> > > On Mon, 2007-09-17 at 12:52 +1000, David Gibson wrote:
> > > > On Fri, Sep 14, 2007 at 03:44:47PM -0500, Hollis Blanchard wrote:
> > > > > Implement udbg_getc() for 440, which fixes xmon input.
> > > > > Signed-off-by: Hollis Blanchard <hollisb@us.ibm.com>
> > > > Acked-by: David Gibson <david@gibson.dropbear.id.au>
> > > > 
> > > 
> > > I fixed up the whitespace issues and applied it to my tree.  Oh, and
> > > comments don't need semi-colons ;)
> > 
> > Well, there's a big difference between:
> > 
> > 	while (foo)
> > 		/* moof */;
> > 	return bar;
> > 
> > and:
> > 	while (foo)
> > 		/* moof */
> > 	return bar;
> 
> Right, so this commit is broken:
> http://git.infradead.org/?p=users/jwboyer/powerpc.git;a=commitdiff;h=81ec428065c01e37fb143ad31dc04fea27fddcac

Yes, it is.  I realized that right as I was going to bed.  I've pushed a
new commit instead.

http://git.infradead.org/?p=users/jwboyer/powerpc.git;a=commitdiff;h=88305119ccab262897ddbbceeb5a1f725f2b60fa

josh

^ permalink raw reply

* Re: [PATCH] [POWERPC] Remove unused variabls from drivers/ide/ppc/pmac.c
From: Bartlomiej Zolnierkiewicz @ 2007-09-17 10:16 UTC (permalink / raw)
  To: Stephen Rothwell; +Cc: ppc-dev, paulus, linux-ide
In-Reply-To: <20070917140644.f62abe1e.sfr@canb.auug.org.au>

On Monday 17 September 2007, Stephen Rothwell wrote:
> Removes these warnings:
> 
> /home/sfr/kernels/linus/drivers/ide/ppc/pmac.c: In function 'pmac_ide_dma_check':
> /home/sfr/kernels/linus/drivers/ide/ppc/pmac.c:1807: warning: unused variable 'map'
> /home/sfr/kernels/linus/drivers/ide/ppc/pmac.c:1805: warning: unused variable 'pmif'
> 
> Signed-off-by: Stephen Rothwell <sfr@canb.auug.org.au>

applied

^ permalink raw reply

* Device tree compiler
From: Laurent Pinchart @ 2007-09-17 11:30 UTC (permalink / raw)
  To: Linux PPC Linux PPC

Hi everybody,

I'm trying to port a MPC8248-based board from ppc to powerpc.

While looking for example DTS files I found out that the Linux kernel sourc=
es=20
include a few of them in arch/powerpc/boot/dts. However, they don't compile=
=20
with the latest device-tree compiler available at=20
git://ozlabs.org/srv/projects/dtc/dtc.git.

One of the most common error comes from references to the PIC using a node=
=20
name instead of a linux,phandler value. As most DTS files in the kernel=20
sources fail to compile, I was wondering if there was another DTC I was not=
=20
aware of, or if those files have actually never been compiled.

Best regards,

=2D-=20
Laurent Pinchart
CSE Semaphore Belgium

Chauss=E9e de Bruxelles, 732A
B-1410 Waterloo
Belgium

T +32 (2) 387 42 59
=46 +32 (2) 387 42 75

^ permalink raw reply

* Re: Device tree compiler
From: Josh Boyer @ 2007-09-17 11:53 UTC (permalink / raw)
  To: Laurent Pinchart; +Cc: Linux PPC Linux PPC
In-Reply-To: <200709171330.37642.laurentp@cse-semaphore.com>

On Mon, 17 Sep 2007 13:30:37 +0200
Laurent Pinchart <laurentp@cse-semaphore.com> wrote:

> Hi everybody,
> 
> I'm trying to port a MPC8248-based board from ppc to powerpc.
> 
> While looking for example DTS files I found out that the Linux kernel sources 
> include a few of them in arch/powerpc/boot/dts. However, they don't compile 
> with the latest device-tree compiler available at 
> git://ozlabs.org/srv/projects/dtc/dtc.git.

Because that is ancient.  Use the one from:

git://www.jdl.com/software/dtc.git

Someone should really fix up the ozlabs page to stop pointing at
outdated versions of DTC.

josh

^ permalink raw reply

* Re: [PATCH] fix xmon input on 440
From: Milton Miller @ 2007-09-17 12:24 UTC (permalink / raw)
  To: Hollis Blanchard; +Cc: ppcdev
In-Reply-To: <1189802687.20625.74.camel@basalt>

On Sat Sep 15 06:44:47 EST 2007, Hollis Blanchard wrote:

> Implement udbg_getc() for 440, which fixes xmon input.
> Signed-off-by: Hollis Blanchard <hollisb at us.ibm.com>

>         udbg_putc = udbg_44x_as1_putc;
> +       udbg_getc = udbg_44x_as1_getc;

How about adding udbg_getc_poll as well?

While there are no in-tree users, we can use it for console input later.

milton

^ permalink raw reply

* [PATCH 0/3] usb: ehci ppc device-tree-aware driver
From: Valentine Barshak @ 2007-09-17 12:50 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: linux-usb-devel

Some PowerPC systems have a built-in EHCI controller.
This is a device tree aware version of the EHCI controller driver.
Currently it's been tested on the PowerPC 440EPx Sequoia board.
Other platforms can be added later.
The code is based on the ehci-ppc-soc driver by Stefan Roese <sr@denx.de>.

^ permalink raw reply

* [PATCH 1/3] usb: add device-tree-aware ehci driver
From: Valentine Barshak @ 2007-09-17 12:55 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: linux-usb-devel
In-Reply-To: <20070917125039.GA29525@ru.mvista.com>

This adds ehci-ppc-of driver. The code is based on the
ehci-ppc-soc driver by Stefan Roese <sr@denx.de>.

Signed-off-by: Stefan Roese <sr@denx.de>
Signed-off-by: Valentine Barshak <vbarshak@ru.mvista.com>
---
 drivers/usb/host/Kconfig       |    8 +
 drivers/usb/host/ehci-hcd.c    |   16 ++
 drivers/usb/host/ehci-ppc-of.c |  220 +++++++++++++++++++++++++++++++++++++++++
 drivers/usb/host/ehci.h        |    2 
 4 files changed, 244 insertions(+), 2 deletions(-)

diff -ruN linux-2.6.orig/drivers/usb/host/ehci.h linux-2.6/drivers/usb/host/ehci.h
--- linux-2.6.orig/drivers/usb/host/ehci.h	2007-09-15 14:28:42.000000000 +0400
+++ linux-2.6/drivers/usb/host/ehci.h	2007-09-15 15:12:04.000000000 +0400
@@ -725,7 +725,7 @@
  * definition below can die once the 4xx support is
  * finally ported over.
  */
-#if defined(CONFIG_PPC)
+#if defined(CONFIG_PPC) && !defined(CONFIG_PPC_MERGE)
 #define readl_be(addr)		in_be32((__force unsigned *)addr)
 #define writel_be(val, addr)	out_be32((__force unsigned *)addr, val)
 #endif
diff -ruN linux-2.6.orig/drivers/usb/host/ehci-hcd.c linux-2.6/drivers/usb/host/ehci-hcd.c
--- linux-2.6.orig/drivers/usb/host/ehci-hcd.c	2007-09-15 14:28:42.000000000 +0400
+++ linux-2.6/drivers/usb/host/ehci-hcd.c	2007-09-15 15:12:04.000000000 +0400
@@ -944,11 +944,16 @@
 #define	PS3_SYSTEM_BUS_DRIVER	ps3_ehci_driver
 #endif
 
-#ifdef CONFIG_440EPX
+#if defined(CONFIG_440EPX) && !defined(CONFIG_PPC_MERGE)
 #include "ehci-ppc-soc.c"
 #define	PLATFORM_DRIVER		ehci_ppc_soc_driver
 #endif
 
+#ifdef CONFIG_USB_EHCI_HCD_PPC_OF
+#include "ehci-ppc-of.c"
+#define OF_PLATFORM_DRIVER	ehci_hcd_ppc_of_driver
+#endif
+
 #if !defined(PCI_DRIVER) && !defined(PLATFORM_DRIVER) && \
     !defined(PS3_SYSTEM_BUS_DRIVER)
 #error "missing bus glue for ehci-hcd"
@@ -963,6 +968,12 @@
 		 sizeof(struct ehci_qh), sizeof(struct ehci_qtd),
 		 sizeof(struct ehci_itd), sizeof(struct ehci_sitd));
 
+#ifdef OF_PLATFORM_DRIVER
+	retval = of_register_platform_driver(&OF_PLATFORM_DRIVER);
+	if (retval < 0)
+		return retval;
+#endif
+
 #ifdef PLATFORM_DRIVER
 	retval = platform_driver_register(&PLATFORM_DRIVER);
 	if (retval < 0)
@@ -998,6 +1009,9 @@
 
 static void __exit ehci_hcd_cleanup(void)
 {
+#ifdef OF_PLATFORM_DRIVER
+	of_unregister_platform_driver(&OF_PLATFORM_DRIVER);
+#endif
 #ifdef PLATFORM_DRIVER
 	platform_driver_unregister(&PLATFORM_DRIVER);
 #endif
diff -ruN linux-2.6.orig/drivers/usb/host/ehci-ppc-of.c linux-2.6/drivers/usb/host/ehci-ppc-of.c
--- linux-2.6.orig/drivers/usb/host/ehci-ppc-of.c	1970-01-01 03:00:00.000000000 +0300
+++ linux-2.6/drivers/usb/host/ehci-ppc-of.c	2007-09-15 16:12:56.000000000 +0400
@@ -0,0 +1,220 @@
+/*
+ * EHCI HCD (Host Controller Driver) for USB.
+ *
+ * Bus Glue for PPC On-Chip EHCI driver on the of_platform bus
+ * Tested on AMCC PPC 440EPx
+ *
+ * Valentine Barshak <vbarshak@ru.mvista.com>
+ *
+ * Based on "ehci-ppc-soc.c" by Stefan Roese <sr@denx.de>
+ * and "ohci-ppc-of.c" by Sylvain Munaut <tnt@246tNt.com>
+ *
+ * This file is licenced under the GPL.
+ */
+
+#include <linux/signal.h>
+
+#include <asm/of_platform.h>
+#include <asm/prom.h>
+
+/* called during probe() after chip reset completes */
+static int ehci_ppc_of_setup(struct usb_hcd *hcd)
+{
+	struct ehci_hcd	*ehci = hcd_to_ehci(hcd);
+	int		retval;
+
+	retval = ehci_halt(ehci);
+	if (retval)
+		return retval;
+
+	retval = ehci_init(hcd);
+	if (retval)
+		return retval;
+
+	ehci->sbrn = 0x20;
+	return ehci_reset(ehci);
+}
+
+
+static const struct hc_driver ehci_ppc_of_hc_driver = {
+	.description = hcd_name,
+	.product_desc = "OF EHCI",
+	.hcd_priv_size = sizeof(struct ehci_hcd),
+
+	/*
+	 * generic hardware linkage
+	 */
+	.irq = ehci_irq,
+	.flags = HCD_MEMORY | HCD_USB2,
+
+	/*
+	 * basic lifecycle operations
+	 */
+	.reset = ehci_ppc_of_setup,
+	.start = ehci_run,
+	.stop = ehci_stop,
+	.shutdown = ehci_shutdown,
+
+	/*
+	 * managing i/o requests and associated device resources
+	 */
+	.urb_enqueue = ehci_urb_enqueue,
+	.urb_dequeue = ehci_urb_dequeue,
+	.endpoint_disable = ehci_endpoint_disable,
+
+	/*
+	 * scheduling support
+	 */
+	.get_frame_number = ehci_get_frame,
+
+	/*
+	 * root hub support
+	 */
+	.hub_status_data = ehci_hub_status_data,
+	.hub_control = ehci_hub_control,
+#ifdef	CONFIG_PM
+	.hub_suspend = ehci_hub_suspend,
+	.hub_resume = ehci_hub_resume,
+#endif
+};
+
+
+static int __devinit
+ehci_hcd_ppc_of_probe(struct of_device *op, const struct of_device_id *match)
+{
+	struct device_node *dn = op->node;
+	struct usb_hcd *hcd;
+	struct ehci_hcd	*ehci;
+	struct resource res;
+	int irq;
+	int rv;
+
+	if (usb_disabled())
+		return -ENODEV;
+
+	dev_dbg(&op->dev, "initializing PPC-OF USB Controller\n");
+
+	rv = of_address_to_resource(dn, 0, &res);
+	if (rv)
+		return rv;
+
+	hcd = usb_create_hcd(&ehci_ppc_of_hc_driver, &op->dev, "PPC-OF USB");
+	if (!hcd)
+		return -ENOMEM;
+
+	hcd->rsrc_start = res.start;
+	hcd->rsrc_len = res.end - res.start + 1;
+
+	if (!request_mem_region(hcd->rsrc_start, hcd->rsrc_len, hcd_name)) {
+		printk(KERN_ERR __FILE__ ": request_mem_region failed\n");
+		rv = -EBUSY;
+		goto err_rmr;
+	}
+
+	irq = irq_of_parse_and_map(dn, 0);
+	if (irq == NO_IRQ) {
+		printk(KERN_ERR __FILE__ ": irq_of_parse_and_map failed\n");
+		rv = -EBUSY;
+		goto err_irq;
+	}
+
+	hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len);
+	if (!hcd->regs) {
+		printk(KERN_ERR __FILE__ ": ioremap failed\n");
+		rv = -ENOMEM;
+		goto err_ioremap;
+	}
+
+	ehci = hcd_to_ehci(hcd);
+	if (of_device_is_compatible(dn, "ehci-be-desc"))
+		ehci->big_endian_desc = 1;
+	if (of_get_property(dn, "big-endian", NULL))
+		ehci->big_endian_mmio = 1;
+
+	ehci->caps = hcd->regs;
+	ehci->regs = hcd->regs + HC_LENGTH(ehci_readl(ehci, &ehci->caps->hc_capbase));
+
+	/* cache this readonly data; minimize chip reads */
+	ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params);
+
+	if (of_device_is_compatible(dn, "ibm,ehci-440epx")) {
+		/*
+		 * 440EPx Errata USBH_3
+		 * Fix: Enable Break Memory Transfer (BMT) in INSNREG3
+		 */
+		out_be32((void *)((ulong)(&ehci->regs->command) + 0x8c), (1 << 0));
+		ehci_dbg(ehci, "Break Memory Transfer (BMT) has beed enabled!\n");
+	}
+
+	rv = usb_add_hcd(hcd, irq, 0);
+	if (rv == 0)
+		return 0;
+
+	iounmap(hcd->regs);
+err_ioremap:
+	irq_dispose_mapping(irq);
+err_irq:
+	release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
+err_rmr:
+ 	usb_put_hcd(hcd);
+
+	return rv;
+}
+
+
+static int ehci_hcd_ppc_of_remove(struct of_device *op)
+{
+	struct usb_hcd *hcd = dev_get_drvdata(&op->dev);
+	dev_set_drvdata(&op->dev, NULL);
+
+	dev_dbg(&op->dev, "stopping PPC-OF USB Controller\n");
+
+	usb_remove_hcd(hcd);
+
+	iounmap(hcd->regs);
+	irq_dispose_mapping(hcd->irq);
+	release_mem_region(hcd->rsrc_start, hcd->rsrc_len);
+
+	usb_put_hcd(hcd);
+
+	return 0;
+}
+
+
+static int ehci_hcd_ppc_of_shutdown(struct of_device *op)
+{
+	struct usb_hcd *hcd = dev_get_drvdata(&op->dev);
+
+        if (hcd->driver->shutdown)
+                hcd->driver->shutdown(hcd);
+
+	return 0;
+}
+
+
+static struct of_device_id ehci_hcd_ppc_of_match[] = {
+	{
+		.type = "usb",
+		.compatible = "ehci",
+	},
+	{},
+};
+MODULE_DEVICE_TABLE(of, ehci_hcd_ppc_of_match);
+
+
+static struct of_platform_driver ehci_hcd_ppc_of_driver = {
+	.name		= "ppc-of-ehci",
+	.match_table	= ehci_hcd_ppc_of_match,
+	.probe		= ehci_hcd_ppc_of_probe,
+	.remove		= ehci_hcd_ppc_of_remove,
+	.shutdown 	= ehci_hcd_ppc_of_shutdown,
+#ifdef CONFIG_PM
+	/*.suspend	= ehci_hcd_ppc_of_drv_suspend,*/
+	/*.resume	= ehci_hcd_ppc_of_drv_resume,*/
+#endif
+	.driver		= {
+		.name	= "ppc-of-ehci",
+		.owner	= THIS_MODULE,
+	},
+};
+
diff -ruN linux-2.6.orig/drivers/usb/host/Kconfig linux-2.6/drivers/usb/host/Kconfig
--- linux-2.6.orig/drivers/usb/host/Kconfig	2007-09-15 14:28:42.000000000 +0400
+++ linux-2.6/drivers/usb/host/Kconfig	2007-09-15 15:12:04.000000000 +0400
@@ -84,6 +84,14 @@
 	---help---
 	  Variation of ARC USB block used in some Freescale chips.
 
+config USB_EHCI_HCD_PPC_OF
+	bool "EHCI support for PPC USB controller on OF platform bus"
+	depends on USB_EHCI_HCD && PPC_OF
+	default y
+	---help---
+	  Enables support for the USB controller PowerPC present on the
+	  OpenFirmware platform bus.
+
 config USB_ISP116X_HCD
 	tristate "ISP116X HCD support"
 	depends on USB

^ permalink raw reply

* [PATCH 2/3] usb: ehci-ppc-of dts bindings.
From: Valentine Barshak @ 2007-09-17 13:00 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: linux-usb-devel
In-Reply-To: <20070917125543.GA29584@ru.mvista.com>

Signed-off-by: Valentine Barshak <vbarshak@ru.mvista.com>
---
 Documentation/powerpc/booting-without-of.txt |   30 +++++++++++++++++++++++++++
 1 file changed, 30 insertions(+)

diff -ruN linux-2.6.orig/Documentation/powerpc/booting-without-of.txt linux-2.6.new/Documentation/powerpc/booting-without-of.txt
--- linux-2.6.orig/Documentation/powerpc/booting-without-of.txt	2007-09-15 14:27:57.000000000 +0400
+++ linux-2.6.new/Documentation/powerpc/booting-without-of.txt	2007-09-15 17:19:06.000000000 +0400
@@ -52,6 +52,7 @@
       i) Freescale QUICC Engine module (QE)
       j) CFI or JEDEC memory-mapped NOR flash
       k) Global Utilities Block
+      l) USB EHCI controllers
 
   VII - Specifying interrupt information for devices
     1) interrupts property
@@ -1848,6 +1849,35 @@
 		fsl,has-rstcr;
 	};
 
+  l) USB EHCI controllers
+
+  Required properties:
+  - device_type : should be "usb".
+  - compatible : should be "ehci".
+  - reg : Offset and length of the register set for the device
+  - interrupts : <a b> where a is the interrupt number and b is a
+    field that represents an encoding of the sense and level
+    information for the interrupt.  This should be encoded based on
+    the information in section 2) depending on the type of interrupt
+    controller you have.
+  - interrupt-parent : the phandle for the interrupt controller that
+    services interrupts for this device.
+  If device registers are implemented in big endian mode, the device
+  node should have "big-endian" property.
+  If controller implementation operates with big endian descriptors,
+  compatible should also have "ehci-be-desc"
+
+   Example (Sequoia 440EPx):
+	ehci@e0000300 {
+		device_type = "usb";
+		compatible = "ibm,ehci-440epx", "ehci-be-desc", "ehci";
+		interrupts = <1a 4>;
+		interrupt-parent = <&UIC0>;
+		reg = <0 e0000300 ff>;
+		big-endian;
+	};
+
+
    More devices will be defined as this spec matures.
 
 VII - Specifying interrupt information for devices

^ permalink raw reply

* [PATCH 3/3] Add PowerPC 440EPx Sequoia ehci dts entry.
From: Valentine Barshak @ 2007-09-17 13:02 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: linux-usb-devel
In-Reply-To: <20070917125039.GA29525@ru.mvista.com>

The patch adds usb ehci entry to PowerPC440EPx Sequoia DTS.

Signed-off-by: Valentine Barshak <vbarshak@ru.mvista.com>
---
 arch/powerpc/boot/dts/sequoia.dts |    9 +++++++++
 1 file changed, 9 insertions(+)

diff -ruN linux-2.6.orig/arch/powerpc/boot/dts/sequoia.dts linux-2.6/arch/powerpc/boot/dts/sequoia.dts
--- linux-2.6.orig/arch/powerpc/boot/dts/sequoia.dts	2007-09-15 14:28:06.000000000 +0400
+++ linux-2.6/arch/powerpc/boot/dts/sequoia.dts	2007-09-15 16:20:19.000000000 +0400
@@ -122,6 +122,15 @@
 			interrupt-map-mask = <ffffffff>;
 		};
 
+		USB0: ehci@e0000300 {
+			device_type = "usb";
+			compatible = "ibm,ehci-440epx", "ehci-be-desc", "ehci";
+			interrupt-parent = <&UIC0>;
+			interrupts = <1a 4>;
+			reg = <0 e0000300 ff>;
+			big-endian;
+		};
+
 		POB0: opb {
 		  	compatible = "ibm,opb-440epx", "ibm,opb";
 			#address-cells = <1>;

^ permalink raw reply

* Re: [PATCH 1/3] usb: add device-tree-aware ehci driver
From: Stephen Rothwell @ 2007-09-17 13:28 UTC (permalink / raw)
  To: Valentine Barshak; +Cc: linuxppc-dev, linux-usb-devel
In-Reply-To: <20070917125543.GA29584@ru.mvista.com>

[-- Attachment #1: Type: text/plain, Size: 683 bytes --]

On Mon, 17 Sep 2007 16:55:43 +0400 Valentine Barshak <vbarshak@ru.mvista.com> wrote:
>
> +++ linux-2.6/drivers/usb/host/ehci-ppc-of.c	2007-09-15 16:12:56.000000000 +0400
> @@ -0,0 +1,220 @@
> +
> +#include <asm/of_platform.h>
> +#include <asm/prom.h>

Please use linux/of.h and linux/of_platform.h instead.

> +static int ehci_hcd_ppc_of_shutdown(struct of_device *op)
> +{
> +	struct usb_hcd *hcd = dev_get_drvdata(&op->dev);
> +
> +        if (hcd->driver->shutdown)
> +                hcd->driver->shutdown(hcd);

White space has gone a bit funny here.

-- 
Cheers,
Stephen Rothwell                    sfr@canb.auug.org.au
http://www.canb.auug.org.au/~sfr/

[-- Attachment #2: Type: application/pgp-signature, Size: 189 bytes --]

^ permalink raw reply

* Re: [PATCH 1/3] usb: add device-tree-aware ehci driver
From: Josh Boyer @ 2007-09-17 14:00 UTC (permalink / raw)
  To: Stephen Rothwell; +Cc: linuxppc-dev, linux-usb-devel
In-Reply-To: <20070917232809.1221acd9.sfr@canb.auug.org.au>

On Mon, 17 Sep 2007 23:28:09 +1000
Stephen Rothwell <sfr@canb.auug.org.au> wrote:

> On Mon, 17 Sep 2007 16:55:43 +0400 Valentine Barshak <vbarshak@ru.mvista.com> wrote:
> >
> > +++ linux-2.6/drivers/usb/host/ehci-ppc-of.c	2007-09-15 16:12:56.000000000 +0400
> > @@ -0,0 +1,220 @@
> > +
> > +#include <asm/of_platform.h>
> > +#include <asm/prom.h>
> 
> Please use linux/of.h and linux/of_platform.h instead.

This seems to be a common error these days.  Perhaps a #warning in the
asm/ files if _LINUX_OF_PLATFORM_H and _LINUX_OF_H aren't defined would
be helpful.

josh

^ permalink raw reply

* Re: CONFIG_BLK_DEV_BSG=n
From: David Howells @ 2007-09-17 14:46 UTC (permalink / raw)
  To: James Bottomley, akpm, jens.axboe
  Cc: fujita.tomonori, linux-scsi, Gala Kumar-B11780, linuxppc-dev,
	paulus
In-Reply-To: <1189800008.3343.21.camel@localhost.localdomain>


James Bottomley <James.Bottomley@SteelEye.com> wrote:

> > Which solution would you be more comfortable with?
> 
> The one which is currently in -mm is this one:
> 
> http://git.kernel.org/?p=linux/kernel/git/jejb/scsi-misc-2.6.git;a=commit;h=49892223f7d3a2333ef9e6cbdd526676e1fc517a

In my opinion, this is the wrong fix.  There shouldn't be anything in the
kernel using stuff from bsg.h if CONFIG_BLOCK=n, so there should be an error if
anything tries to.  The correct fix is to exclude the non-userspace-visible
contents of bsg.h with #ifdef CONFIG_BLOCK, not to declare things that we've
tried to make sure specifically aren't declared.

David
---

[PATCH] VFS: Make BSG declarations dependent on CONFIG_BLOCK

From: David Howells <dhowells@redhat.com>

Make BSG function declarations dependent on CONFIG_BLOCK as they are not
compilable if the block layer is compiled out.

Signed-off-by: David Howells <dhowells@redhat.com>
---

 include/linux/bsg.h |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/include/linux/bsg.h b/include/linux/bsg.h
index 60e377b..28f5d44 100644
--- a/include/linux/bsg.h
+++ b/include/linux/bsg.h
@@ -52,6 +52,7 @@ struct sg_io_v4 {
 };
 
 #ifdef __KERNEL__
+#ifdef CONFIG_BLOCK
 
 #if defined(CONFIG_BLK_DEV_BSG)
 struct bsg_class_device {
@@ -73,6 +74,7 @@ static inline void bsg_unregister_queue(struct request_queue *rq)
 }
 #endif
 
+#endif /* CONFIG_BLOCK */
 #endif /* __KERNEL__ */
 
 #endif

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox