* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Bartlomiej Zolnierkiewicz @ 2007-07-26 19:28 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165318.5331.23795.stgit@localhost.localdomain>
Hi,
On Wednesday 25 July 2007, Vitaly Bordug wrote:
>
> This is now very similar to pata_platform.c, they both use
> same platform data structure and same resources.
>
> To achieve that, byte_lanes_swapping platform data variable
> and platform specified iops removed from that driver. It's fine,
> since those were never used anyway.
>
> pata_platform and ide_platform are carrying same driver names,
> to easily switch between these drivers, without need to touch
> platform code.
Looks really good, thanks for working on this.
> Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
> Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
applied but it would be also nice to fix minor issues found by Sergei
(please just send a new version of the patch and I will replace this
version with the newer one in my tree)
patch #2/2 also looks fine and when issues raised by Sergei gets
addressed it will be merged
Thanks,
Bart
^ permalink raw reply
* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Bartlomiej Zolnierkiewicz @ 2007-07-26 19:28 UTC (permalink / raw)
To: Alan Cox; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <20070725184312.44ca7a8c@the-village.bc.nu>
On Wednesday 25 July 2007, Alan Cox wrote:
> > pata_platform and ide_platform are carrying same driver names,
> > to easily switch between these drivers, without need to touch
> > platform code.
> >
> > Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
> > Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
>
> Acked-by: Alan Cox <alan@redhat.com>
added
^ permalink raw reply
* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Bartlomiej Zolnierkiewicz @ 2007-07-26 20:11 UTC (permalink / raw)
To: Guennadi Liakhovetski; +Cc: linuxppc-dev, linux-kernel, Alan Cox, linux-ide
In-Reply-To: <Pine.LNX.4.60.0707262136530.6614@poirot.grange>
Hi,
On Thursday 26 July 2007, Guennadi Liakhovetski wrote:
> On Wed, 25 Jul 2007, Alan Cox wrote:
>
> > > driver to using platform-device. I got a reply, that it's not worth it now
> > > that IDE is slowly becoming obsolete, and the pata_platform serves the
> > > perpose perfectly well. I found this argument reasonable, I had the same
> > > doubt, just wanted to double-check. So, why do we now need a new legacy
> > > (a/drivers/ide/legacy/ide_platform.c) driver when a "modern" driver
> > > exists?
> >
> > We don't *need* it but some people still want to use old IDE and the
> > author was willing to make it neatly compatible so that anything that
> > works with the pata_platform should be able to use the ide_platform
> > driver and vice versa. For the shorter term that can only be a good thing
> > - arch code doesn't need to care about which driver is used, end users
> > can pick and it doesn't end up adding new ties between code and old IDE.
>
> Ok, thanks for the explanation Alan. So, there's no technical argument,
> just "being nice to the users", and add a new driver, which we know we'll
There are some rough edges (especially older and/or rare hardware,
this goes for both cotrollers and devices) that SCSI/libata don't
handle and IDE subsystem do.
> have to remove soon, thus having to persuade its users, who by that time
Well, we've been hearing "soon" for two years now...
> will get used to it and will not want to invest money into switching to
> another one...
PS wrt ide_arm.c changes, you really should have cc:ed the author... ;)
Thanks,
Bart
^ permalink raw reply
* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Guennadi Liakhovetski @ 2007-07-26 20:13 UTC (permalink / raw)
To: Sergei Shtylyov; +Cc: linuxppc-dev, linux-kernel, Alan Cox, linux-ide
In-Reply-To: <46A8FB86.2010907@ru.mvista.com>
On Thu, 26 Jul 2007, Sergei Shtylyov wrote:
> Guennadi Liakhovetski wrote:
>
> > Ok, thanks for the explanation Alan. So, there's no technical argument,
> > just "being nice to the users", and add a new driver, which we know we'll
> > have to remove soon, thus having to persuade its users, who by that time
>
> Define "soon". :-)
"Soon" in this case means, we NOW have a replacement driver and we aim at
deprecating the IDE driver in its favour.
> > will get used to it and will not want to invest money into switching to
> > another one...
>
> Invest into what if the drivers are functionally identical?
For example, into porting user space (replace hdx with sdx). And even
switching to a "functionally identical" driver requires a new complete
testing cycle... No, I won't be in that situation, so, it's not my money
I'm worrying about. But I know there are companies for whom releasing a
new version of /etc/fstab is a considerable expense... Not that I cared
about them anyway.
Thanks
Guennadi
---
Guennadi Liakhovetski
^ permalink raw reply
* Re: [patch 07/35] pasemi_mac: stop using the pci config space accessors for register read/writes
From: Marian Balakowicz @ 2007-07-26 21:25 UTC (permalink / raw)
To: Olof Johansson; +Cc: linuxppc-dev
In-Reply-To: <20070705170235.314700000@lixom.net>
Olof,
Olof Johansson wrote:
> Move away from using the pci config access functions for simple register
> access. Our device has all of the registers in the config space (hey,
> from the hardware point of view it looks reasonable :-), so we need to
> somehow get to it. Newer firmwares have it in the device tree such that
> we can just get it and ioremap it there (in case it ever moves in future
> products). For now, provide a hardcoded fallback for older firmwares.
I have recently tried to apply a group of your MAC patches that includes the one from this email. Strangely, I got a pretty random kernel panics (or kernel freezes) when this patch is included. Panics happen in a random, places and have random causes. What I observed is that replacing newly introduced mac->iob_regs with the corresponding offset from (already ioremapped) hose->cfg_data removed the problem. So, it seems that dereferencing pointers based on a second ioremap on a subset of 0xe000_0000 addresses is problematic.
Here are the questions that come to my mind:
- I am testing on a A2 hw, what what your testing setup, anything newer than this (something closer B0 maybe), did you have a chance to try that on a A2 board?
- Is there any particular patch or set of patches/updates that this patch may depend on?
Switching from pci accessors to direct in_* out_* calls drops the guard pci spinlock. Initially, I thought that this may be the reason, but it's not, adding the spinlock is not solving the problem. But anyway, shouldn't we be using it to coordinate access?
Thanks,
Marian
^ permalink raw reply
* Re: [PATCH] Re: 2.6.22-git hangs during boot on PowerBook G3 in 0.0 seconds
From: Kim Phillips @ 2007-07-26 21:29 UTC (permalink / raw)
To: Paul Mackerras; +Cc: Rutger Nijlunsing, linuxppc-dev
In-Reply-To: <18088.6185.491082.875891@cargo.ozlabs.ibm.com>
On Thu, 26 Jul 2007 13:42:33 +1000
Paul Mackerras <paulus@samba.org> wrote:
> Kim Phillips writes:
>
> > > In which circumstances are you trying to translate an address with no
> > > size cell ?
> >
> > for the enumerated PHYs. As the original commit comment states, I was
> > getting these messages:
> >
> > prom_parse: Bad cell count for /qe@e0100000/mdio@2120/ethernet-phy@00
> > prom_parse: Bad cell count for /qe@e0100000/mdio@2120/ethernet-phy@01
>
> Specifically, which of_address_to_resource or other call is producing
> these error messages?
>
Turns out I mistakenly added an mdio type to the platform
of_platform_bus_probe scan list early on in my ucc phylib migration
work, and it went unnoticed. Please do a:
git-revert 3baee955953957be5496cd28e9c544d9db214262
to remove "[POWERPC] Add 'mdio' to bus scan id list for platforms with
QE UEC" (in addition to the one you've already reverted). Reverting
both these commits eliminates the prom_parse badness messages on the
MPC8360.
Thanks, and sorry,
Kim
p.s. should the stable team be notified to fix 2.6.22 for
Lombard-nvram-style machines?
^ permalink raw reply
* Re: [PATCH] Re: 2.6.22-git hangs during boot on PowerBook G3 in 0.0 seconds
From: Benjamin Herrenschmidt @ 2007-07-26 21:53 UTC (permalink / raw)
To: Kim Phillips; +Cc: linuxppc-dev, Paul Mackerras, Rutger Nijlunsing
In-Reply-To: <20070726162921.a60c76ae.kim.phillips@freescale.com>
On Thu, 2007-07-26 at 16:29 -0500, Kim Phillips wrote:
>
> p.s. should the stable team be notified to fix 2.6.22 for
> Lombard-nvram-style machines?
Yes, definitely.
Cheers,
Ben.
^ permalink raw reply
* Re: dlopen source
From: Linas Vepstas @ 2007-07-26 21:59 UTC (permalink / raw)
To: Siva Prasad; +Cc: linuxppc-dev
In-Reply-To: <D83235F0F3C86D4D889D8B9A0DA8C6D78D86C2@corpexc01.corp.networkrobots.com>
On Thu, Jul 26, 2007 at 12:47:57PM -0700, Siva Prasad wrote:
> Hi,
>
> Can some one point to where I can find the source code for dlopen()
> function.
? Should be in glibc, right? I don't remember f it requires binutils
pieces or not.
(Yes, glibc is a rats nest, so understanding how it works is a whole
nuther thing.)
--linas
^ permalink raw reply
* [PATCH 1/2] powerpc: publish 85xx soc dts entries as of_device on cds and ads platforms
From: Dave Jiang @ 2007-07-26 22:20 UTC (permalink / raw)
To: galak; +Cc: linuxppc-dev, bluesmoke-devel, norsk5
Publish the devices listed in dts under SOC as of_device just like what
mpc85xx_mds platforms do. The 85xx cds and ads platforms currently do not
export the devices in dts as of_device.
I need the memory controller, L2 cache-controller, and the PCI controller
published as of_device so the mpc85xx EDAC driver can claim them for usage.
Signed-off-by: Dave Jiang <djiang@mvista.com>
---
commit 8a80b43ddd3a4f7694df75869e13c3fc6e6c89f6
tree 772b956da2f4a1a55564519ececaf2e54be32248
parent 46b2835771ad8ef19b8e081e8c90439408c7645f
author Dave Jiang <djiang@mvista.com> Thu, 26 Jul 2007 10:59:00 -0700
committer Dave Jiang <djiang@blade.(none)> Thu, 26 Jul 2007 10:59:00 -0700
arch/powerpc/platforms/85xx/mpc85xx_ads.c | 19 +++++++++++++++++++
arch/powerpc/platforms/85xx/mpc85xx_cds.c | 19 +++++++++++++++++++
2 files changed, 38 insertions(+), 0 deletions(-)
diff --git a/arch/powerpc/platforms/85xx/mpc85xx_ads.c b/arch/powerpc/platforms/85xx/mpc85xx_ads.c
index 40a8286..599d7f7 100644
--- a/arch/powerpc/platforms/85xx/mpc85xx_ads.c
+++ b/arch/powerpc/platforms/85xx/mpc85xx_ads.c
@@ -18,6 +18,8 @@
#include <linux/delay.h>
#include <linux/seq_file.h>
+#include <asm/of_device.h>
+#include <asm/of_platform.h>
#include <asm/system.h>
#include <asm/time.h>
#include <asm/machdep.h>
@@ -254,6 +256,23 @@ static int __init mpc85xx_ads_probe(void)
return of_flat_dt_is_compatible(root, "MPC85xxADS");
}
+static struct of_device_id mpc85xx_ids[] = {
+ { .type = "soc", },
+ { .compatible = "soc", },
+ {},
+};
+
+static int __init mpc85xx_publish_devices(void)
+{
+ if (!machine_is(mpc85xx_ads))
+ return 0;
+
+ of_platform_bus_probe(NULL, mpc85xx_ids, NULL);
+
+ return 0;
+}
+device_initcall(mpc85xx_publish_devices);
+
define_machine(mpc85xx_ads) {
.name = "MPC85xx ADS",
.probe = mpc85xx_ads_probe,
diff --git a/arch/powerpc/platforms/85xx/mpc85xx_cds.c b/arch/powerpc/platforms/85xx/mpc85xx_cds.c
index 6a171e9..5294884 100644
--- a/arch/powerpc/platforms/85xx/mpc85xx_cds.c
+++ b/arch/powerpc/platforms/85xx/mpc85xx_cds.c
@@ -27,6 +27,8 @@
#include <linux/interrupt.h>
#include <linux/fsl_devices.h>
+#include <asm/of_device.h>
+#include <asm/of_platform.h>
#include <asm/system.h>
#include <asm/pgtable.h>
#include <asm/page.h>
@@ -342,6 +344,23 @@ static int __init mpc85xx_cds_probe(void)
return of_flat_dt_is_compatible(root, "MPC85xxCDS");
}
+static struct of_device_id mpc85xx_ids[] = {
+ { .type = "soc", },
+ { .compatible = "soc", },
+ {},
+};
+
+static int __init mpc85xx_publish_devices(void)
+{
+ if (!machine_is(mpc85xx_cds))
+ return 0;
+
+ of_platform_bus_probe(NULL, mpc85xx_ids, NULL);
+
+ return 0;
+}
+device_initcall(mpc85xx_publish_devices);
+
define_machine(mpc85xx_cds) {
.name = "MPC85xx CDS",
.probe = mpc85xx_cds_probe,
^ permalink raw reply related
* [PATCH 2/2] powerpc: MPC85xx EDAC device driver
From: Dave Jiang @ 2007-07-26 22:22 UTC (permalink / raw)
To: galak; +Cc: linuxppc-dev, bluesmoke-devel, norsk5
Freescale MPC85xx SoC support for EDAC. Used on PPC platforms. Development
and testing done on PPC Freescale MPC8548CDS.
The driver provides error reporting for L2 cache error registers, the
memory controller error registers, and the PCI error registers. The error
reporting can be done two ways, via interrupts or polling.
Signed-off-by: Dave Jiang <djiang@mvista.com>
Signed-off-by: Douglas Thompson <dougthompson@xmission.com>
---
commit 8ab17eba61575673d4e6a637a3987253cad9adaa
tree 1280fcac7b336cae61cd1e4a6dc9a82741b766ec
parent 8a80b43ddd3a4f7694df75869e13c3fc6e6c89f6
author Dave Jiang <djiang@mvista.com> Thu, 26 Jul 2007 14:53:20 -0700
committer Dave Jiang <djiang@blade.(none)> Thu, 26 Jul 2007 14:53:20 -0700
drivers/edac/Kconfig | 6
drivers/edac/Makefile | 1
drivers/edac/mpc85xx_edac.c | 1048 +++++++++++++++++++++++++++++++++++++++++++
drivers/edac/mpc85xx_edac.h | 162 +++++++
4 files changed, 1217 insertions(+), 0 deletions(-)
diff --git a/drivers/edac/Kconfig b/drivers/edac/Kconfig
index 1724c41..cc50ab6 100644
--- a/drivers/edac/Kconfig
+++ b/drivers/edac/Kconfig
@@ -131,5 +131,11 @@ config EDAC_PASEMI
Support for error detection and correction on PA Semi
PWRficient.
+config EDAC_MPC85XX
+ tristate "Freescale MPC85xx"
+ depends on EDAC_MM_EDAC && FSL_SOC && MPC85xx
+ help
+ Support for error detection and correction on the Freescale
+ MPC8560, MPC8540, MPC8548
endif # EDAC
diff --git a/drivers/edac/Makefile b/drivers/edac/Makefile
index 02c09f0..62696aa 100644
--- a/drivers/edac/Makefile
+++ b/drivers/edac/Makefile
@@ -28,4 +28,5 @@ obj-$(CONFIG_EDAC_I3000) += i3000_edac.o
obj-$(CONFIG_EDAC_I82860) += i82860_edac.o
obj-$(CONFIG_EDAC_R82600) += r82600_edac.o
obj-$(CONFIG_EDAC_PASEMI) += pasemi_edac.o
+obj-$(CONFIG_EDAC_MPC85XX) += mpc85xx_edac.o
diff --git a/drivers/edac/mpc85xx_edac.c b/drivers/edac/mpc85xx_edac.c
new file mode 100644
index 0000000..8078d53
--- /dev/null
+++ b/drivers/edac/mpc85xx_edac.c
@@ -0,0 +1,1048 @@
+/*
+ * Freescale MPC85xx Memory Controller kenel module
+ *
+ * Author: Dave Jiang <djiang@mvista.com>
+ *
+ * 2006-2007 (c) MontaVista Software, Inc. 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/init.h>
+#include <linux/slab.h>
+#include <linux/interrupt.h>
+#include <linux/ctype.h>
+#include <linux/io.h>
+#include <linux/mod_devicetable.h>
+#include <linux/edac.h>
+#include <linux/of_device.h>
+#include <linux/of_platform.h>
+
+#include <asm/mpc85xx.h>
+#include "edac_module.h"
+#include "edac_core.h"
+#include "mpc85xx_edac.h"
+
+static int edac_dev_idx;
+static int edac_pci_idx;
+static int edac_mc_idx;
+
+static u32 orig_ddr_err_disable;
+static u32 orig_ddr_err_sbe;
+
+/*
+ * PCI Err defines
+ */
+#ifdef CONFIG_PCI
+static u32 orig_pci_err_cap_dr;
+static u32 orig_pci_err_en;
+#endif
+
+static u32 orig_l2_err_disable;
+static u32 orig_hid1;
+
+const char *mpc85xx_ctl_name = "MPC85xx";
+
+/************************ MC SYSFS parts ***********************************/
+
+static ssize_t mpc85xx_mc_inject_data_hi_show(struct mem_ctl_info *mci,
+ char *data)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->mc_vbase +
+ MPC85XX_MC_DATA_ERR_INJECT_HI));
+}
+
+static ssize_t mpc85xx_mc_inject_data_lo_show(struct mem_ctl_info *mci,
+ char *data)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->mc_vbase +
+ MPC85XX_MC_DATA_ERR_INJECT_LO));
+}
+
+static ssize_t mpc85xx_mc_inject_ctrl_show(struct mem_ctl_info *mci, char *data)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->mc_vbase + MPC85XX_MC_ECC_ERR_INJECT));
+}
+
+static ssize_t mpc85xx_mc_inject_data_hi_store(struct mem_ctl_info *mci,
+ const char *data, size_t count)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_DATA_ERR_INJECT_HI,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static ssize_t mpc85xx_mc_inject_data_lo_store(struct mem_ctl_info *mci,
+ const char *data, size_t count)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_DATA_ERR_INJECT_LO,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static ssize_t mpc85xx_mc_inject_ctrl_store(struct mem_ctl_info *mci,
+ const char *data, size_t count)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ECC_ERR_INJECT,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static struct mcidev_sysfs_attribute mpc85xx_mc_sysfs_attributes[] = {
+ {
+ .attr = {
+ .name = "inject_data_hi",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_mc_inject_data_hi_show,
+ .store = mpc85xx_mc_inject_data_hi_store},
+ {
+ .attr = {
+ .name = "inject_data_lo",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_mc_inject_data_lo_show,
+ .store = mpc85xx_mc_inject_data_lo_store},
+ {
+ .attr = {
+ .name = "inject_ctrl",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_mc_inject_ctrl_show,
+ .store = mpc85xx_mc_inject_ctrl_store},
+
+ /* End of list */
+ {
+ .attr = {.name = NULL}
+ }
+};
+
+static void mpc85xx_set_mc_sysfs_attributes(struct mem_ctl_info *mci)
+{
+ mci->mc_driver_sysfs_attributes = mpc85xx_mc_sysfs_attributes;
+}
+
+/**************************** PCI Err device ***************************/
+#ifdef CONFIG_PCI
+
+static void mpc85xx_pci_check(struct edac_pci_ctl_info *pci)
+{
+ struct mpc85xx_pci_pdata *pdata = pci->pvt_info;
+ u32 err_detect;
+
+ err_detect = in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DR);
+
+ /* master aborts can happen during PCI config cycles */
+ if (!(err_detect & ~(PCI_EDE_MULTI_ERR | PCI_EDE_MST_ABRT))) {
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DR, err_detect);
+ return;
+ }
+
+ printk(KERN_ERR "PCI error(s) detected\n");
+ printk(KERN_ERR "PCI/X ERR_DR register: %#08x\n", err_detect);
+
+ printk(KERN_ERR "PCI/X ERR_ATTRIB register: %#08x\n",
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_ATTRIB));
+ printk(KERN_ERR "PCI/X ERR_ADDR register: %#08x\n",
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_ADDR));
+ printk(KERN_ERR "PCI/X ERR_EXT_ADDR register: %#08x\n",
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_EXT_ADDR));
+ printk(KERN_ERR "PCI/X ERR_DL register: %#08x\n",
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DL));
+ printk(KERN_ERR "PCI/X ERR_DH register: %#08x\n",
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DH));
+
+ /* clear error bits */
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DR, err_detect);
+
+ if (err_detect & PCI_EDE_PERR_MASK)
+ edac_pci_handle_pe(pci, pci->ctl_name);
+
+ if ((err_detect & ~PCI_EDE_MULTI_ERR) & ~PCI_EDE_PERR_MASK)
+ edac_pci_handle_npe(pci, pci->ctl_name);
+}
+
+static irqreturn_t mpc85xx_pci_isr(int irq, void *dev_id)
+{
+ struct edac_pci_ctl_info *pci = dev_id;
+ struct mpc85xx_pci_pdata *pdata = pci->pvt_info;
+ u32 err_detect;
+
+ err_detect = in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DR);
+
+ if (!err_detect)
+ return IRQ_NONE;
+
+ return IRQ_HANDLED;
+}
+
+static int __devinit mpc85xx_pci_err_probe(struct of_device *op,
+ const struct of_device_id *match)
+{
+ struct edac_pci_ctl_info *pci;
+ struct mpc85xx_pci_pdata *pdata;
+ struct resource r;
+ int res;
+
+ if (!devres_open_group(&op->dev, mpc85xx_pci_err_probe, GFP_KERNEL))
+ return -ENOMEM;
+
+ pci = edac_pci_alloc_ctl_info(sizeof(*pdata), "mpc85xx_pci_err");
+ if (!pci)
+ return -ENOMEM;
+
+ pdata = pci->pvt_info;
+ pdata->name = "mpc85xx_pci_err";
+ pdata->irq = NO_IRQ;
+ dev_set_drvdata(&op->dev, pci);
+ pci->dev = &op->dev;
+ pci->dev_name = op->dev.bus_id;
+ pci->mod_name = EDAC_MOD_STR;
+
+ if (edac_op_state == EDAC_OPSTATE_POLL)
+ pci->edac_check = mpc85xx_pci_check;
+
+ pdata->edac_idx = edac_pci_idx++;
+
+ res = of_address_to_resource(op->node, 0, &r);
+ if (res) {
+ printk(KERN_ERR "%s: Unable to get resource for "
+ "PCI err regs\n", __func__);
+ goto err;
+ }
+
+ /* we only need the error registers */
+ r.start += 0xe00;
+
+ if (!devm_request_mem_region(&op->dev, r.start,
+ r.end - r.start + 1, pdata->name)) {
+ printk(KERN_ERR "%s: Error while requesting mem region\n",
+ __func__);
+ res = -EBUSY;
+ goto err;
+ }
+
+ pdata->pci_vbase = devm_ioremap(&op->dev, r.start, r.end - r.start + 1);
+ if (!pdata->pci_vbase) {
+ printk(KERN_ERR "%s: Unable to setup PCI err regs\n", __func__);
+ res = -ENOMEM;
+ goto err;
+ }
+
+ orig_pci_err_cap_dr =
+ in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_CAP_DR);
+
+ /* PCI master abort is expected during config cycles */
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_CAP_DR, 0x40);
+
+ orig_pci_err_en = in_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_EN);
+
+ /* disable master abort reporting */
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_EN, ~0x40);
+
+ /* clear error bits */
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_DR, ~0);
+
+ if (edac_pci_add_device(pci, pdata->edac_idx) > 0) {
+ debugf3("%s(): failed edac_pci_add_device()\n", __func__);
+ goto err;
+ }
+
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ pdata->irq = irq_of_parse_and_map(op->node, 0);
+ res = devm_request_irq(&op->dev, pdata->irq,
+ mpc85xx_pci_isr, IRQF_DISABLED,
+ "[EDAC] PCI err", pci);
+ if (res < 0) {
+ printk(KERN_ERR
+ "%s: Unable to requiest irq %d for "
+ "MPC85xx PCI err\n", __func__, pdata->irq);
+ irq_dispose_mapping(pdata->irq);
+ res = -ENODEV;
+ goto err2;
+ }
+
+ printk(KERN_INFO EDAC_MOD_STR " acquired irq %d for PCI Err\n",
+ pdata->irq);
+ }
+
+ devres_remove_group(&op->dev, mpc85xx_pci_err_probe);
+ debugf3("%s(): success\n", __func__);
+ printk(KERN_INFO EDAC_MOD_STR " PCI err registered\n");
+
+ return 0;
+
+err2:
+ edac_pci_del_device(&op->dev);
+err:
+ edac_pci_free_ctl_info(pci);
+ devres_release_group(&op->dev, mpc85xx_pci_err_probe);
+ return res;
+}
+
+static int mpc85xx_pci_err_remove(struct of_device *op)
+{
+ struct edac_pci_ctl_info *pci = dev_get_drvdata(&op->dev);
+ struct mpc85xx_pci_pdata *pdata = pci->pvt_info;
+
+ debugf0("%s()\n", __func__);
+
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_CAP_DR,
+ orig_pci_err_cap_dr);
+
+ out_be32(pdata->pci_vbase + MPC85XX_PCI_ERR_EN, orig_pci_err_en);
+
+ edac_pci_del_device(pci->dev);
+
+ if (edac_op_state == EDAC_OPSTATE_INT)
+ irq_dispose_mapping(pdata->irq);
+
+ edac_pci_free_ctl_info(pci);
+
+ return 0;
+}
+
+static struct of_device_id mpc85xx_pci_err_of_match[] = {
+ {
+ .type = "pci",
+ .compatible = "fsl,mpc8540-pci",
+ },
+ {},
+};
+
+static struct of_platform_driver mpc85xx_pci_err_driver = {
+ .owner = THIS_MODULE,
+ .name = "mpc85xx_pci_err",
+ .match_table = mpc85xx_pci_err_of_match,
+ .probe = mpc85xx_pci_err_probe,
+ .remove = mpc85xx_pci_err_remove,
+ .driver = {
+ .name = "mpc85xx_pci_err",
+ .owner = THIS_MODULE,
+ },
+};
+
+#endif /* CONFIG_PCI */
+
+/**************************** L2 Err device ***************************/
+
+/************************ L2 SYSFS parts ***********************************/
+
+static ssize_t mpc85xx_l2_inject_data_hi_show(struct edac_device_ctl_info
+ *edac_dev, char *data)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJHI));
+}
+
+static ssize_t mpc85xx_l2_inject_data_lo_show(struct edac_device_ctl_info
+ *edac_dev, char *data)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJLO));
+}
+
+static ssize_t mpc85xx_l2_inject_ctrl_show(struct edac_device_ctl_info
+ *edac_dev, char *data)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ return sprintf(data, "0x%08x",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJCTL));
+}
+
+static ssize_t mpc85xx_l2_inject_data_hi_store(struct edac_device_ctl_info
+ *edac_dev, const char *data,
+ size_t count)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJHI,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static ssize_t mpc85xx_l2_inject_data_lo_store(struct edac_device_ctl_info
+ *edac_dev, const char *data,
+ size_t count)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJLO,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static ssize_t mpc85xx_l2_inject_ctrl_store(struct edac_device_ctl_info
+ *edac_dev, const char *data,
+ size_t count)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ if (isdigit(*data)) {
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINJCTL,
+ simple_strtoul(data, NULL, 0));
+ return count;
+ }
+ return 0;
+}
+
+static struct edac_dev_sysfs_attribute mpc85xx_l2_sysfs_attributes[] = {
+ {
+ .attr = {
+ .name = "inject_data_hi",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_l2_inject_data_hi_show,
+ .store = mpc85xx_l2_inject_data_hi_store},
+ {
+ .attr = {
+ .name = "inject_data_lo",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_l2_inject_data_lo_show,
+ .store = mpc85xx_l2_inject_data_lo_store},
+ {
+ .attr = {
+ .name = "inject_ctrl",
+ .mode = (S_IRUGO | S_IWUSR)
+ },
+ .show = mpc85xx_l2_inject_ctrl_show,
+ .store = mpc85xx_l2_inject_ctrl_store},
+
+ /* End of list */
+ {
+ .attr = {.name = NULL}
+ }
+};
+
+static void mpc85xx_set_l2_sysfs_attributes(struct edac_device_ctl_info
+ *edac_dev)
+{
+ edac_dev->sysfs_attributes = mpc85xx_l2_sysfs_attributes;
+}
+
+/***************************** L2 ops ***********************************/
+
+static void mpc85xx_l2_check(struct edac_device_ctl_info *edac_dev)
+{
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ u32 err_detect;
+
+ err_detect = in_be32(pdata->l2_vbase + MPC85XX_L2_ERRDET);
+
+ if (!(err_detect & L2_EDE_MASK))
+ return;
+
+ printk(KERN_ERR "ECC Error in CPU L2 cache\n");
+ printk(KERN_ERR "L2 Error Detect Register: 0x%08x\n", err_detect);
+ printk(KERN_ERR "L2 Error Capture Data High Register: 0x%08x\n",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_CAPTDATAHI));
+ printk(KERN_ERR "L2 Error Capture Data Lo Register: 0x%08x\n",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_CAPTDATALO));
+ printk(KERN_ERR "L2 Error Syndrome Register: 0x%08x\n",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_CAPTECC));
+ printk(KERN_ERR "L2 Error Attributes Capture Register: 0x%08x\n",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_ERRATTR));
+ printk(KERN_ERR "L2 Error Address Capture Register: 0x%08x\n",
+ in_be32(pdata->l2_vbase + MPC85XX_L2_ERRADDR));
+
+ /* clear error detect register */
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDET, err_detect);
+
+ if (err_detect & L2_EDE_CE_MASK)
+ edac_device_handle_ce(edac_dev, 0, 0, edac_dev->ctl_name);
+
+ if (err_detect & L2_EDE_UE_MASK)
+ edac_device_handle_ue(edac_dev, 0, 0, edac_dev->ctl_name);
+}
+
+static irqreturn_t mpc85xx_l2_isr(int irq, void *dev_id)
+{
+ struct edac_device_ctl_info *edac_dev = dev_id;
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+ u32 err_detect;
+
+ err_detect = in_be32(pdata->l2_vbase + MPC85XX_L2_ERRDET);
+
+ if (!(err_detect & L2_EDE_MASK))
+ return IRQ_NONE;
+
+ mpc85xx_l2_check(edac_dev);
+ return IRQ_HANDLED;
+}
+
+static int __devinit mpc85xx_l2_err_probe(struct of_device *op,
+ const struct of_device_id *match)
+{
+ struct edac_device_ctl_info *edac_dev;
+ struct mpc85xx_l2_pdata *pdata;
+ struct resource r;
+ int res;
+
+ if (!devres_open_group(&op->dev, mpc85xx_l2_err_probe, GFP_KERNEL))
+ return -ENOMEM;
+
+ edac_dev = edac_device_alloc_ctl_info(sizeof(*pdata),
+ "cpu", 1, "L", 1, 2, NULL, 0,
+ edac_dev_idx);
+ if (!edac_dev) {
+ devres_release_group(&op->dev, mpc85xx_l2_err_probe);
+ return -ENOMEM;
+ }
+
+ pdata = edac_dev->pvt_info;
+ pdata->name = "mpc85xx_l2_err";
+ pdata->irq = NO_IRQ;
+ edac_dev->dev = &op->dev;
+ dev_set_drvdata(edac_dev->dev, edac_dev);
+
+ res = of_address_to_resource(op->node, 0, &r);
+ if (res) {
+ printk(KERN_ERR "%s: Unable to get resource for "
+ "L2 err regs\n", __func__);
+ goto err;
+ }
+
+ /* we only need the error registers */
+ r.start += 0xe00;
+
+ if (!devm_request_mem_region(&op->dev, r.start,
+ r.end - r.start + 1, pdata->name)) {
+ printk(KERN_ERR "%s: Error while requesting mem region\n",
+ __func__);
+ res = -EBUSY;
+ goto err;
+ }
+
+ pdata->l2_vbase = devm_ioremap(&op->dev, r.start, r.end - r.start + 1);
+ if (!pdata->l2_vbase) {
+ printk(KERN_ERR "%s: Unable to setup L2 err regs\n", __func__);
+ res = -ENOMEM;
+ goto err;
+ }
+
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDET, ~0);
+
+ orig_l2_err_disable = in_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS);
+
+ /* clear the err_dis */
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS, 0);
+
+ edac_dev->mod_name = EDAC_MOD_STR;
+ edac_dev->ctl_name = pdata->name;
+
+ if (edac_op_state == EDAC_OPSTATE_POLL)
+ edac_dev->edac_check = mpc85xx_l2_check;
+
+ mpc85xx_set_l2_sysfs_attributes(edac_dev);
+
+ pdata->edac_idx = edac_dev_idx++;
+
+ if (edac_device_add_device(edac_dev) > 0) {
+ debugf3("%s(): failed edac_device_add_device()\n", __func__);
+ goto err;
+ }
+
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ pdata->irq = irq_of_parse_and_map(op->node, 0);
+ res = devm_request_irq(&op->dev, pdata->irq,
+ mpc85xx_l2_isr, IRQF_DISABLED,
+ "[EDAC] L2 err", edac_dev);
+ if (res < 0) {
+ printk(KERN_ERR
+ "%s: Unable to requiest irq %d for "
+ "MPC85xx L2 err\n", __func__, pdata->irq);
+ irq_dispose_mapping(pdata->irq);
+ res = -ENODEV;
+ goto err2;
+ }
+
+ printk(KERN_INFO EDAC_MOD_STR " acquired irq %d for L2 Err\n",
+ pdata->irq);
+
+ edac_dev->op_state = OP_RUNNING_INTERRUPT;
+
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINTEN, L2_EIE_MASK);
+ }
+
+ devres_remove_group(&op->dev, mpc85xx_l2_err_probe);
+
+ debugf3("%s(): success\n", __func__);
+ printk(KERN_INFO EDAC_MOD_STR " L2 err registered\n");
+
+ return 0;
+
+err2:
+ edac_device_del_device(&op->dev);
+err:
+ devres_release_group(&op->dev, mpc85xx_l2_err_probe);
+ edac_device_free_ctl_info(edac_dev);
+ return res;
+}
+
+static int mpc85xx_l2_err_remove(struct of_device *op)
+{
+ struct edac_device_ctl_info *edac_dev = dev_get_drvdata(&op->dev);
+ struct mpc85xx_l2_pdata *pdata = edac_dev->pvt_info;
+
+ debugf0("%s()\n", __func__);
+
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRINTEN, 0);
+ irq_dispose_mapping(pdata->irq);
+ }
+
+ out_be32(pdata->l2_vbase + MPC85XX_L2_ERRDIS, orig_l2_err_disable);
+ edac_device_del_device(&op->dev);
+ edac_device_free_ctl_info(edac_dev);
+ return 0;
+}
+
+static struct of_device_id mpc85xx_l2_err_of_match[] = {
+ {
+ .compatible = "fsl,8540-l2-cache-controller",
+ },
+ {
+ .compatible = "fsl,8541-l2-cache-controller",
+ },
+ {
+ .compatible = "fsl,8544-l2-cache-controller",
+ },
+ {
+ .compatible = "fsl,8548-l2-cache-controller",
+ },
+ {
+ .compatible = "fsl,8555-l2-cache-controller",
+ },
+ {
+ .compatible = "fsl,8568-l2-cache-controller",
+ },
+ {},
+};
+
+static struct of_platform_driver mpc85xx_l2_err_driver = {
+ .owner = THIS_MODULE,
+ .name = "mpc85xx_l2_err",
+ .match_table = mpc85xx_l2_err_of_match,
+ .probe = mpc85xx_l2_err_probe,
+ .remove = mpc85xx_l2_err_remove,
+ .driver = {
+ .name = "mpc85xx_l2_err",
+ .owner = THIS_MODULE,
+ },
+};
+
+/**************************** MC Err device ***************************/
+
+static void mpc85xx_mc_check(struct mem_ctl_info *mci)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ struct csrow_info *csrow;
+ u32 err_detect;
+ u32 syndrome;
+ u32 err_addr;
+ u32 pfn;
+ int row_index;
+
+ err_detect = in_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT);
+ if (!unlikely(err_detect))
+ return;
+
+ mpc85xx_mc_printk(mci, KERN_ERR, "Err Detect Register: %#8.8x\n",
+ err_detect);
+
+ /* no more processing if not ECC bit errors */
+ if (!(err_detect & (DDR_EDE_SBE | DDR_EDE_MBE))) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT, err_detect);
+ return;
+ }
+
+ syndrome = in_be32(pdata->mc_vbase + MPC85XX_MC_CAPTURE_ECC);
+ err_addr = in_be32(pdata->mc_vbase + MPC85XX_MC_CAPTURE_ADDRESS);
+ pfn = err_addr >> PAGE_SHIFT;
+
+ for (row_index = 0; row_index < mci->nr_csrows; row_index++) {
+ csrow = &mci->csrows[row_index];
+ if ((pfn >= csrow->first_page) && (pfn <= csrow->last_page))
+ break;
+ }
+
+ mpc85xx_mc_printk(mci, KERN_ERR, "Capture Data High: %#8.8x\n",
+ in_be32(pdata->mc_vbase +
+ MPC85XX_MC_CAPTURE_DATA_HI));
+ mpc85xx_mc_printk(mci, KERN_ERR, "Capture Data Low: %#8.8x\n",
+ in_be32(pdata->mc_vbase +
+ MPC85XX_MC_CAPTURE_DATA_LO));
+ mpc85xx_mc_printk(mci, KERN_ERR, "syndrome: %#8.8x\n", syndrome);
+ mpc85xx_mc_printk(mci, KERN_ERR, "err addr: %#8.8x\n", err_addr);
+ mpc85xx_mc_printk(mci, KERN_ERR, "PFN: %#8.8x\n", pfn);
+
+ /* we are out of range */
+ if (row_index == mci->nr_csrows)
+ mpc85xx_mc_printk(mci, KERN_ERR, "PFN out of range!\n");
+
+ if (err_detect & DDR_EDE_SBE)
+ edac_mc_handle_ce(mci, pfn, err_addr & PAGE_MASK,
+ syndrome, row_index, 0, mci->ctl_name);
+
+ if (err_detect & DDR_EDE_MBE)
+ edac_mc_handle_ue(mci, pfn, err_addr & PAGE_MASK,
+ row_index, mci->ctl_name);
+
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT, err_detect);
+}
+
+static irqreturn_t mpc85xx_mc_isr(int irq, void *dev_id)
+{
+ struct mem_ctl_info *mci = dev_id;
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ u32 err_detect;
+
+ err_detect = in_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT);
+ if (unlikely(!err_detect))
+ return IRQ_NONE;
+
+ mpc85xx_mc_check(mci);
+
+ return IRQ_HANDLED;
+}
+
+static void __devinit mpc85xx_init_csrows(struct mem_ctl_info *mci)
+{
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+ struct csrow_info *csrow;
+ u32 sdram_ctl;
+ u32 sdtype;
+ enum mem_type mtype;
+ u32 cs_bnds;
+ int index;
+
+ sdram_ctl = in_be32(pdata->mc_vbase + MPC85XX_MC_DDR_SDRAM_CFG);
+
+ sdtype = sdram_ctl & DSC_SDTYPE_MASK;
+ if (sdram_ctl & DSC_RD_EN) {
+ switch (sdtype) {
+ case DSC_SDTYPE_DDR:
+ mtype = MEM_RDDR;
+ break;
+ case DSC_SDTYPE_DDR2:
+ mtype = MEM_RDDR2;
+ break;
+ default:
+ mtype = MEM_UNKNOWN;
+ break;
+ }
+ } else {
+ switch (sdtype) {
+ case DSC_SDTYPE_DDR:
+ mtype = MEM_DDR;
+ break;
+ case DSC_SDTYPE_DDR2:
+ mtype = MEM_DDR2;
+ break;
+ default:
+ mtype = MEM_UNKNOWN;
+ break;
+ }
+ }
+
+ for (index = 0; index < mci->nr_csrows; index++) {
+ u32 start;
+ u32 end;
+
+ csrow = &mci->csrows[index];
+ cs_bnds = in_be32(pdata->mc_vbase + MPC85XX_MC_CS_BNDS_0 +
+ (index * MPC85XX_MC_CS_BNDS_OFS));
+ start = (cs_bnds & 0xfff0000) << 4;
+ end = ((cs_bnds & 0xfff) << 20);
+ if (start)
+ start |= 0xfffff;
+ if (end)
+ end |= 0xfffff;
+
+ if (start == end)
+ continue; /* not populated */
+
+ csrow->first_page = start >> PAGE_SHIFT;
+ csrow->last_page = end >> PAGE_SHIFT;
+ csrow->nr_pages = csrow->last_page + 1 - csrow->first_page;
+ csrow->grain = 8;
+ csrow->mtype = mtype;
+ csrow->dtype = DEV_UNKNOWN;
+ if (sdram_ctl & DSC_X32_EN)
+ csrow->dtype = DEV_X32;
+ csrow->edac_mode = EDAC_SECDED;
+ }
+}
+
+static int __devinit mpc85xx_mc_err_probe(struct of_device *op,
+ const struct of_device_id *match)
+{
+ struct mem_ctl_info *mci;
+ struct mpc85xx_mc_pdata *pdata;
+ struct resource r;
+ u32 sdram_ctl;
+ int res;
+
+ if (!devres_open_group(&op->dev, mpc85xx_mc_err_probe, GFP_KERNEL))
+ return -ENOMEM;
+
+ mci = edac_mc_alloc(sizeof(*pdata), 4, 1, edac_mc_idx);
+ if (!mci) {
+ devres_release_group(&op->dev, mpc85xx_mc_err_probe);
+ return -ENOMEM;
+ }
+
+ pdata = mci->pvt_info;
+ pdata->name = "mpc85xx_mc_err";
+ pdata->irq = NO_IRQ;
+ mci->dev = &op->dev;
+ pdata->edac_idx = edac_mc_idx++;
+ dev_set_drvdata(mci->dev, mci);
+
+ res = of_address_to_resource(op->node, 0, &r);
+ if (res) {
+ printk(KERN_ERR "%s: Unable to get resource for MC err regs\n",
+ __func__);
+ goto err;
+ }
+
+ if (!devm_request_mem_region(&op->dev, r.start,
+ r.end - r.start + 1, pdata->name)) {
+ printk(KERN_ERR "%s: Error while requesting mem region\n",
+ __func__);
+ res = -EBUSY;
+ goto err;
+ }
+
+ pdata->mc_vbase = devm_ioremap(&op->dev, r.start, r.end - r.start + 1);
+ if (!pdata->mc_vbase) {
+ printk(KERN_ERR "%s: Unable to setup MC err regs\n", __func__);
+ res = -ENOMEM;
+ goto err;
+ }
+
+ sdram_ctl = in_be32(pdata->mc_vbase + MPC85XX_MC_DDR_SDRAM_CFG);
+ if (!(sdram_ctl & DSC_ECC_EN)) {
+ /* no ECC */
+ printk(KERN_WARNING "%s: No ECC DIMMs discovered\n", __func__);
+ res = -ENODEV;
+ goto err;
+ }
+
+ debugf3("%s(): init mci\n", __func__);
+ mci->mtype_cap = MEM_FLAG_RDDR | MEM_FLAG_RDDR2 |
+ MEM_FLAG_DDR | MEM_FLAG_DDR2;
+ mci->edac_ctl_cap = EDAC_FLAG_NONE | EDAC_FLAG_SECDED;
+ mci->edac_cap = EDAC_FLAG_SECDED;
+ mci->mod_name = EDAC_MOD_STR;
+ mci->mod_ver = MPC85XX_REVISION;
+ mci->ctl_name = mpc85xx_ctl_name;
+
+ if (edac_op_state == EDAC_OPSTATE_POLL)
+ mci->edac_check = mpc85xx_mc_check;
+
+ mci->ctl_page_to_phys = NULL;
+
+ mci->scrub_mode = SCRUB_SW_SRC;
+
+ mpc85xx_set_mc_sysfs_attributes(mci);
+
+ mpc85xx_init_csrows(mci);
+
+#ifdef CONFIG_EDAC_DEBUG
+ edac_mc_register_mcidev_debug((struct attribute **)debug_attr);
+#endif
+
+ /* store the original error disable bits */
+ orig_ddr_err_disable =
+ in_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DISABLE);
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DISABLE, 0);
+
+ /* clear all error bits */
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DETECT, ~0);
+
+ if (edac_mc_add_mc(mci)) {
+ debugf3("%s(): failed edac_mc_add_mc()\n", __func__);
+ goto err;
+ }
+
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_INT_EN,
+ DDR_EIE_MBEE | DDR_EIE_SBEE);
+
+ /* store the original error management threshold */
+ orig_ddr_err_sbe = in_be32(pdata->mc_vbase +
+ MPC85XX_MC_ERR_SBE) & 0xff0000;
+
+ /* set threshold to 1 error per interrupt */
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_SBE, 0x10000);
+
+ /* register interrupts */
+ pdata->irq = irq_of_parse_and_map(op->node, 0);
+ res = devm_request_irq(&op->dev, pdata->irq,
+ mpc85xx_mc_isr, IRQF_DISABLED,
+ "[EDAC] MC err", mci);
+ if (res < 0) {
+ printk(KERN_ERR "%s: Unable to request irq %d for "
+ "MPC85xx DRAM ERR\n", __func__, pdata->irq);
+ irq_dispose_mapping(pdata->irq);
+ res = -ENODEV;
+ goto err2;
+ }
+
+ printk(KERN_INFO EDAC_MOD_STR " acquired irq %d for MC\n",
+ pdata->irq);
+ }
+
+ devres_remove_group(&op->dev, mpc85xx_mc_err_probe);
+ debugf3("%s(): success\n", __func__);
+ printk(KERN_INFO EDAC_MOD_STR " MC err registered\n");
+
+ return 0;
+
+err2:
+ edac_mc_del_mc(&op->dev);
+err:
+ devres_release_group(&op->dev, mpc85xx_mc_err_probe);
+ edac_mc_free(mci);
+ return res;
+}
+
+static int mpc85xx_mc_err_remove(struct of_device *op)
+{
+ struct mem_ctl_info *mci = dev_get_drvdata(&op->dev);
+ struct mpc85xx_mc_pdata *pdata = mci->pvt_info;
+
+ debugf0("%s()\n", __func__);
+
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_INT_EN, 0);
+ irq_dispose_mapping(pdata->irq);
+ }
+
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_DISABLE,
+ orig_ddr_err_disable);
+ out_be32(pdata->mc_vbase + MPC85XX_MC_ERR_SBE, orig_ddr_err_sbe);
+
+ edac_mc_del_mc(&op->dev);
+ edac_mc_free(mci);
+ return 0;
+}
+
+static struct of_device_id mpc85xx_mc_err_of_match[] = {
+ {
+ .compatible = "fsl,8540-memory-controller",
+ },
+ {
+ .compatible = "fsl,8541-memory-controller",
+ },
+ {
+ .compatible = "fsl,8544-memory-controller",
+ },
+ {
+ .compatible = "fsl,8548-memory-controller",
+ },
+ {
+ .compatible = "fsl,8555-memory-controller",
+ },
+ {
+ .compatible = "fsl,8568-memory-controller",
+ },
+ {},
+};
+
+static struct of_platform_driver mpc85xx_mc_err_driver = {
+ .owner = THIS_MODULE,
+ .name = "mpc85xx_mc_err",
+ .match_table = mpc85xx_mc_err_of_match,
+ .probe = mpc85xx_mc_err_probe,
+ .remove = mpc85xx_mc_err_remove,
+ .driver = {
+ .name = "mpc85xx_mc_err",
+ .owner = THIS_MODULE,
+ },
+};
+
+static int __init mpc85xx_mc_init(void)
+{
+ int res = 0;
+
+ printk(KERN_INFO "Freescale(R) MPC85xx EDAC driver, "
+ "(C) 2006 Montavista Software\n");
+
+ /* make sure error reporting method is sane */
+ switch (edac_op_state) {
+ case EDAC_OPSTATE_POLL:
+ case EDAC_OPSTATE_INT:
+ break;
+ default:
+ edac_op_state = EDAC_OPSTATE_INT;
+ break;
+ }
+
+ res = of_register_platform_driver(&mpc85xx_mc_err_driver) ? : res;
+
+ res = of_register_platform_driver(&mpc85xx_l2_err_driver) ? : res;
+
+#ifdef CONFIG_PCI
+ res = of_register_platform_driver(&mpc85xx_pci_err_driver) ? : res;
+#endif
+
+ /*
+ * need to clear HID1[RFXE] to disable machine check int
+ * so we can catch it
+ */
+ if (edac_op_state == EDAC_OPSTATE_INT) {
+ orig_hid1 = mfspr(SPRN_HID1);
+
+ mtspr(SPRN_HID1, (orig_hid1 & ~0x20000));
+ }
+
+ return res;
+}
+
+module_init(mpc85xx_mc_init);
+
+static void __exit mpc85xx_mc_exit(void)
+{
+ mtspr(SPRN_HID1, orig_hid1);
+#ifdef CONFIG_PCI
+ of_unregister_platform_driver(&mpc85xx_pci_err_driver);
+#endif
+ of_unregister_platform_driver(&mpc85xx_l2_err_driver);
+ of_unregister_platform_driver(&mpc85xx_mc_err_driver);
+}
+
+module_exit(mpc85xx_mc_exit);
+
+MODULE_LICENSE("GPL");
+MODULE_AUTHOR("Montavista Software, Inc.");
+module_param(edac_op_state, int, 0444);
+MODULE_PARM_DESC(edac_op_state,
+ "EDAC Error Reporting state: 0=Poll, 2=Interrupt");
diff --git a/drivers/edac/mpc85xx_edac.h b/drivers/edac/mpc85xx_edac.h
new file mode 100644
index 0000000..135b353
--- /dev/null
+++ b/drivers/edac/mpc85xx_edac.h
@@ -0,0 +1,162 @@
+/*
+ * Freescale MPC85xx Memory Controller kenel module
+ * Author: Dave Jiang <djiang@mvista.com>
+ *
+ * 2006-2007 (c) MontaVista Software, Inc. 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 _MPC85XX_EDAC_H_
+#define _MPC85XX_EDAC_H_
+
+#define MPC85XX_REVISION " Ver: 2.0.0 " __DATE__
+#define EDAC_MOD_STR "MPC85xx_edac"
+
+#define mpc85xx_printk(level, fmt, arg...) \
+ edac_printk(level, "MPC85xx", fmt, ##arg)
+
+#define mpc85xx_mc_printk(mci, level, fmt, arg...) \
+ edac_mc_chipset_printk(mci, level, "MPC85xx", fmt, ##arg)
+
+/*
+ * DRAM error defines
+ */
+
+/* DDR_SDRAM_CFG */
+#define MPC85XX_MC_DDR_SDRAM_CFG 0x0110
+#define MPC85XX_MC_CS_BNDS_0 0x0000
+#define MPC85XX_MC_CS_BNDS_1 0x0008
+#define MPC85XX_MC_CS_BNDS_2 0x0010
+#define MPC85XX_MC_CS_BNDS_3 0x0018
+#define MPC85XX_MC_CS_BNDS_OFS 0x0008
+
+#define MPC85XX_MC_DATA_ERR_INJECT_HI 0x0e00
+#define MPC85XX_MC_DATA_ERR_INJECT_LO 0x0e04
+#define MPC85XX_MC_ECC_ERR_INJECT 0x0e08
+#define MPC85XX_MC_CAPTURE_DATA_HI 0x0e20
+#define MPC85XX_MC_CAPTURE_DATA_LO 0x0e24
+#define MPC85XX_MC_CAPTURE_ECC 0x0e28
+#define MPC85XX_MC_ERR_DETECT 0x0e40
+#define MPC85XX_MC_ERR_DISABLE 0x0e44
+#define MPC85XX_MC_ERR_INT_EN 0x0e48
+#define MPC85XX_MC_CAPTURE_ATRIBUTES 0x0e4c
+#define MPC85XX_MC_CAPTURE_ADDRESS 0x0e50
+#define MPC85XX_MC_ERR_SBE 0x0e58
+
+#define DSC_MEM_EN 0x80000000
+#define DSC_ECC_EN 0x20000000
+#define DSC_RD_EN 0x10000000
+
+#define DSC_SDTYPE_MASK 0x07000000
+
+#define DSC_SDTYPE_DDR 0x02000000
+#define DSC_SDTYPE_DDR2 0x03000000
+#define DSC_X32_EN 0x00000020
+
+/* Err_Int_En */
+#define DDR_EIE_MSEE 0x1 /* memory select */
+#define DDR_EIE_SBEE 0x4 /* single-bit ECC error */
+#define DDR_EIE_MBEE 0x8 /* multi-bit ECC error */
+
+/* Err_Detect */
+#define DDR_EDE_MSE 0x1 /* memory select */
+#define DDR_EDE_SBE 0x4 /* single-bit ECC error */
+#define DDR_EDE_MBE 0x8 /* multi-bit ECC error */
+#define DDR_EDE_MME 0x80000000 /* multiple memory errors */
+
+/* Err_Disable */
+#define DDR_EDI_MSED 0x1 /* memory select disable */
+#define DDR_EDI_SBED 0x4 /* single-bit ECC error disable */
+#define DDR_EDI_MBED 0x8 /* multi-bit ECC error disable */
+
+/*
+ * L2 Err defines
+ */
+#define MPC85XX_L2_ERRINJHI 0x0000
+#define MPC85XX_L2_ERRINJLO 0x0004
+#define MPC85XX_L2_ERRINJCTL 0x0008
+#define MPC85XX_L2_CAPTDATAHI 0x0020
+#define MPC85XX_L2_CAPTDATALO 0x0024
+#define MPC85XX_L2_CAPTECC 0x0028
+#define MPC85XX_L2_ERRDET 0x0040
+#define MPC85XX_L2_ERRDIS 0x0044
+#define MPC85XX_L2_ERRINTEN 0x0048
+#define MPC85XX_L2_ERRATTR 0x004c
+#define MPC85XX_L2_ERRADDR 0x0050
+#define MPC85XX_L2_ERRCTL 0x0058
+
+/* Error Interrupt Enable */
+#define L2_EIE_L2CFGINTEN 0x1
+#define L2_EIE_SBECCINTEN 0x4
+#define L2_EIE_MBECCINTEN 0x8
+#define L2_EIE_TPARINTEN 0x10
+#define L2_EIE_MASK (L2_EIE_L2CFGINTEN | L2_EIE_SBECCINTEN | \
+ L2_EIE_MBECCINTEN | L2_EIE_TPARINTEN)
+
+/* Error Detect */
+#define L2_EDE_L2CFGERR 0x1
+#define L2_EDE_SBECCERR 0x4
+#define L2_EDE_MBECCERR 0x8
+#define L2_EDE_TPARERR 0x10
+#define L2_EDE_MULL2ERR 0x80000000
+
+#define L2_EDE_CE_MASK L2_EDE_SBECCERR
+#define L2_EDE_UE_MASK (L2_EDE_L2CFGERR | L2_EDE_MBECCERR | \
+ L2_EDE_TPARERR)
+#define L2_EDE_MASK (L2_EDE_L2CFGERR | L2_EDE_SBECCERR | \
+ L2_EDE_MBECCERR | L2_EDE_TPARERR | L2_EDE_MULL2ERR)
+
+/*
+ * PCI Err defines
+ */
+#define PCI_EDE_TOE 0x00000001
+#define PCI_EDE_SCM 0x00000002
+#define PCI_EDE_IRMSV 0x00000004
+#define PCI_EDE_ORMSV 0x00000008
+#define PCI_EDE_OWMSV 0x00000010
+#define PCI_EDE_TGT_ABRT 0x00000020
+#define PCI_EDE_MST_ABRT 0x00000040
+#define PCI_EDE_TGT_PERR 0x00000080
+#define PCI_EDE_MST_PERR 0x00000100
+#define PCI_EDE_RCVD_SERR 0x00000200
+#define PCI_EDE_ADDR_PERR 0x00000400
+#define PCI_EDE_MULTI_ERR 0x80000000
+
+#define PCI_EDE_PERR_MASK (PCI_EDE_TGT_PERR | PCI_EDE_MST_PERR | \
+ PCI_EDE_ADDR_PERR)
+
+#define MPC85XX_PCI_ERR_DR 0x0000
+#define MPC85XX_PCI_ERR_CAP_DR 0x0004
+#define MPC85XX_PCI_ERR_EN 0x0008
+#define MPC85XX_PCI_ERR_ATTRIB 0x000c
+#define MPC85XX_PCI_ERR_ADDR 0x0010
+#define MPC85XX_PCI_ERR_EXT_ADDR 0x0014
+#define MPC85XX_PCI_ERR_DL 0x0018
+#define MPC85XX_PCI_ERR_DH 0x001c
+#define MPC85XX_PCI_GAS_TIMR 0x0020
+#define MPC85XX_PCI_PCIX_TIMR 0x0024
+
+struct mpc85xx_mc_pdata {
+ char *name;
+ int edac_idx;
+ void __iomem *mc_vbase;
+ int irq;
+};
+
+struct mpc85xx_l2_pdata {
+ char *name;
+ int edac_idx;
+ void __iomem *l2_vbase;
+ int irq;
+};
+
+struct mpc85xx_pci_pdata {
+ char *name;
+ int edac_idx;
+ void __iomem *pci_vbase;
+ int irq;
+};
+
+#endif
^ permalink raw reply related
* [PATCH 0/3] powerpc/eeh: for 2.6.23: a fix for bridges, and tweaks
From: Linas Vepstas @ 2007-07-26 22:29 UTC (permalink / raw)
To: Paul Mackerras; +Cc: linuxppc-dev
Paul,
The following three patches should be low impact, and I think they could
go into 2.6.23 if its not too late.
-- two are formating/printing fixes/enhancements
-- one fixes the way PCI cards with bridges are handled;
in particular, it avoids a nll pointer deref, so is a serious bugfix.
Linas.
^ permalink raw reply
* [PATCH 1/3] powerpc/eeh: tweak printk message.
From: Linas Vepstas @ 2007-07-26 22:30 UTC (permalink / raw)
To: Paul Mackerras; +Cc: linuxppc-dev
In-Reply-To: <20070726222935.GJ9876@austin.ibm.com>
Print return code to print message. Also fix whitespace.
Signed-off-by: Linas Vepstas <linas@austin.ibm.com>
----
arch/powerpc/platforms/pseries/eeh.c | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
Index: linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh.c
===================================================================
--- linux-2.6.22-git2.orig/arch/powerpc/platforms/pseries/eeh.c 2007-07-24 16:14:22.000000000 -0500
+++ linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh.c 2007-07-25 13:11:09.000000000 -0500
@@ -750,12 +750,12 @@ int rtas_set_slot_reset(struct pci_dn *p
return 0;
if (rc < 0) {
- printk (KERN_ERR "EEH: unrecoverable slot failure %s\n",
- pdn->node->full_name);
+ printk(KERN_ERR "EEH: unrecoverable slot failure %s\n",
+ pdn->node->full_name);
return -1;
}
- printk (KERN_ERR "EEH: bus reset %d failed on slot %s\n",
- i+1, pdn->node->full_name);
+ printk(KERN_ERR "EEH: bus reset %d failed on slot %s, rc=%d\n",
+ i+1, pdn->node->full_name, rc);
}
return -1;
^ permalink raw reply
* [PATCH 2/3] powerpc/eeh: Fix pci bridge handling bug
From: Linas Vepstas @ 2007-07-26 22:33 UTC (permalink / raw)
To: Paul Mackerras; +Cc: linuxppc-dev
In-Reply-To: <20070726223026.GA21552@austin.ibm.com>
The EEH code needs to ignore PCI bridges; sort-of. It was ignoring
them in the wrong place, and thus failing to set up the
PCI_DN(dn)->pcidev pointer. Imprudent dereferencing of this pointer
would lead to a crash on cards with bridges.
Signed-off-by: Linas Vepstas <linas@austin.ibm.com>
----
arch/powerpc/platforms/pseries/eeh_cache.c | 9 +++++----
1 file changed, 5 insertions(+), 4 deletions(-)
Index: linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh_cache.c
===================================================================
--- linux-2.6.22-git2.orig/arch/powerpc/platforms/pseries/eeh_cache.c 2007-07-25 13:10:03.000000000 -0500
+++ linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh_cache.c 2007-07-25 13:13:41.000000000 -0500
@@ -225,6 +225,10 @@ void pci_addr_cache_insert_device(struct
{
unsigned long flags;
+ /* Ignore PCI bridges */
+ if ((dev->class >> 16) == PCI_BASE_CLASS_BRIDGE)
+ return;
+
spin_lock_irqsave(&pci_io_addr_cache_root.piar_lock, flags);
__pci_addr_cache_insert_device(dev);
spin_unlock_irqrestore(&pci_io_addr_cache_root.piar_lock, flags);
@@ -285,16 +289,13 @@ void __init pci_addr_cache_build(void)
spin_lock_init(&pci_io_addr_cache_root.piar_lock);
while ((dev = pci_get_device(PCI_ANY_ID, PCI_ANY_ID, dev)) != NULL) {
- /* Ignore PCI bridges */
- if ((dev->class >> 16) == PCI_BASE_CLASS_BRIDGE)
- continue;
pci_addr_cache_insert_device(dev);
dn = pci_device_to_OF_node(dev);
if (!dn)
continue;
- pci_dev_get (dev); /* matching put is in eeh_remove_device() */
+ pci_dev_get(dev); /* matching put is in eeh_remove_device() */
PCI_DN(dn)->pcidev = dev;
eeh_sysfs_add_device(dev);
^ permalink raw reply
* [PATCH 3/3] powerpc/eeh: dump pci bridge status on event
From: Linas Vepstas @ 2007-07-26 22:35 UTC (permalink / raw)
To: Paul Mackerras; +Cc: linuxppc-dev
In-Reply-To: <20070726223358.GB21552@austin.ibm.com>
Gather bridge-specific data on EEH events.
Signed-off-by: Linas Vepstas <linas@austin.ibm.com>
----
arch/powerpc/platforms/pseries/eeh.c | 27 ++++++++++++++++++++++++++-
1 file changed, 26 insertions(+), 1 deletion(-)
Index: linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh.c
===================================================================
--- linux-2.6.22-git2.orig/arch/powerpc/platforms/pseries/eeh.c 2007-07-25 16:41:42.000000000 -0500
+++ linux-2.6.22-git2/arch/powerpc/platforms/pseries/eeh.c 2007-07-25 16:42:20.000000000 -0500
@@ -169,6 +169,8 @@ static void rtas_slot_error_detail(struc
*/
static size_t gather_pci_data(struct pci_dn *pdn, char * buf, size_t len)
{
+ struct device_node *dn;
+ struct pci_dev *dev = pdn->pcidev;
u32 cfg;
int cap, i;
int n = 0;
@@ -184,6 +186,17 @@ static size_t gather_pci_data(struct pci
n += scnprintf(buf+n, len-n, "cmd/stat:%x\n", cfg);
printk(KERN_WARNING "EEH: PCI cmd/status register: %08x\n", cfg);
+ /* Gather bridge-specific registers */
+ if (dev->class >> 16 == PCI_BASE_CLASS_BRIDGE) {
+ rtas_read_config(pdn, PCI_SEC_STATUS, 2, &cfg);
+ n += scnprintf(buf+n, len-n, "sec stat:%x\n", cfg);
+ printk(KERN_WARNING "EEH: Bridge secondary status: %04x\n", cfg);
+
+ rtas_read_config(pdn, PCI_BRIDGE_CONTROL, 2, &cfg);
+ n += scnprintf(buf+n, len-n, "brdg ctl:%x\n", cfg);
+ printk(KERN_WARNING "EEH: Bridge control: %04x\n", cfg);
+ }
+
/* Dump out the PCI-X command and status regs */
cap = pci_find_capability(pdn->pcidev, PCI_CAP_ID_PCIX);
if (cap) {
@@ -209,7 +222,7 @@ static size_t gather_pci_data(struct pci
printk(KERN_WARNING "EEH: PCI-E %02x: %08x\n", i, cfg);
}
- cap = pci_find_ext_capability(pdn->pcidev,PCI_EXT_CAP_ID_ERR);
+ cap = pci_find_ext_capability(pdn->pcidev, PCI_EXT_CAP_ID_ERR);
if (cap) {
n += scnprintf(buf+n, len-n, "pci-e AER:\n");
printk(KERN_WARNING
@@ -222,6 +235,18 @@ static size_t gather_pci_data(struct pci
}
}
}
+
+ /* Gather status on devices under the bridge */
+ if (dev->class >> 16 == PCI_BASE_CLASS_BRIDGE) {
+ dn = pdn->node->child;
+ while (dn) {
+ pdn = PCI_DN(dn);
+ if (pdn)
+ n += gather_pci_data(pdn, buf+n, len-n);
+ dn = dn->sibling;
+ }
+ }
+
return n;
}
^ permalink raw reply
* Re: [PATCH] make powerpc BUG_ON() OK with pointers and bitwise
From: Paul Mackerras @ 2007-07-26 23:30 UTC (permalink / raw)
To: Al Viro; +Cc: linuxppc-dev, torvalds, linux-kernel
In-Reply-To: <E1IE6JZ-0005QA-R8@ZenIV.linux.org.uk>
Al Viro writes:
> Since powerpc insists on printing the _value_ of condition
We don't _print_ the value of the condition, we give it to a
conditional-trap instruction which will trap if it is non-zero.
> and on casting it to long... At least let's make it a force-cast.
The long cast is to make sure it's sign-extended to the full register
width. Adding __force looks fine.
> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Acked-by: Paul Mackerras <paulus@samba.org>
^ permalink raw reply
* Re: [PATCH 1/2] [POWERPC] Add support of platforms without PHY to gianfar driver
From: Kim Phillips @ 2007-07-27 0:04 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linuxppc-dev, Jeff Garzik
In-Reply-To: <20070725174312.5818.61155.stgit@localhost.localdomain>
On Wed, 25 Jul 2007 21:43:12 +0400
Vitaly Bordug <vitb@kernel.crashing.org> wrote:
>
> Gianfar driver is now able to work without real phy subnode,
> that is necessary to cope with fixed-link situation, when
> SoC is connected to the Ethernet inteface or embedded switch
> without any PHY. In this case, fixed-speed property will
> describe such a situation for gianfar driver.
>
> The property is in form <duplexity speed>
>
> Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
>
> ---
>
> arch/powerpc/sysdev/fsl_soc.c | 39 +++++++++++++++++++++++----------------
> drivers/net/gianfar.c | 17 ++++++++++++++---
please run this through checkpatch.pl until it passes.
<snip>
> + bus_id = of_get_property(np, "fixed_speed",NULL);
hyphens are preferred for new properties. Plus, isn't fixed-link a
better name? unless you instead want to put speed first and make
duplexity an optional second, or possibly even a string.
Also, can we get this new property documented in b-w-of in a separate
patch?
Kim
^ permalink raw reply
* Re: dlopen source
From: David Gibson @ 2007-07-27 0:52 UTC (permalink / raw)
To: Linas Vepstas; +Cc: linuxppc-dev, Siva Prasad
In-Reply-To: <20070726215928.GG9876@austin.ibm.com>
On Thu, Jul 26, 2007 at 04:59:28PM -0500, Linas Vepstas wrote:
> On Thu, Jul 26, 2007 at 12:47:57PM -0700, Siva Prasad wrote:
> > Hi,
> >
> > Can some one point to where I can find the source code for dlopen()
> > function.
>
> ? Should be in glibc, right? I don't remember f it requires binutils
> pieces or not.
Yes, it's in glibc.
> (Yes, glibc is a rats nest, so understanding how it works is a whole
> nuther thing.)
Quite so. The dynamic linking code in particular is
highly... impenetrable :(
--
David Gibson | I'll have my music baroque, and my code
david AT gibson.dropbear.id.au | minimalist, thank you. NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson
^ permalink raw reply
* Re: DTC 1.0.0 Release Coming?
From: David Gibson @ 2007-07-27 1:33 UTC (permalink / raw)
To: Jon Loeliger; +Cc: linuxppc-dev
In-Reply-To: <E1IE59h-0001tt-JE@jdl.com>
On Thu, Jul 26, 2007 at 10:21:33AM -0500, Jon Loeliger wrote:
> So, like, the other day David Gibson mumbled:
>
> > > > Only thing I'm not really happy with in the current release is the
> > > > versioning stuff. For starters, it always reports my builds as
> > > > -dirty, even when they're not.
> > >
> > > I think it won't do that once there is a tag available.
> >
> > Your 1.0.0-rc1 tag is there, still showing as dirty.
>
> Hmmm.. Seems to work here. Is your working directory really clean?
Yes, it really is. I have quilt control directories, but it still
shows as dirty with no patches applied. Exttra files which don't
affect the build shouldn't count as being dirty.
> jdl.com 872 % make clean
> CLEAN (libfdt)
> CLEAN (tests)
> CLEAN
> jdl.com 873 % make
> LEX lex.yy.c
> BISON dtc-parser.tab.c
> ---- Expect 2 s/r and 2 r/r. ----
> dtc-parser.y: conflicts: 2 shift/reduce, 2 reduce/reduce
> CHK version_gen.h
> UPD version_gen.h
> CC dtc.o
> CC flattree.o
> [ snip ]
> CC tests/del_node.o
> CC tests/truncated_property.o
> AS tests/trees.o
> DUMPTREES
> jdl.com 874 % ./dtc -v
> Version: DTC 1.0.0-rc1
sneetch:~/ibm/dtc$ git-ls-files -m
sneetch:~/ibm/dtc$ make clean
CLEAN (libfdt)
CLEAN (tests)
CLEAN
sneetch:~/ibm/dtc$ make
BISON dtc-parser.tab.c
LEX lex.yy.c
---- Expect 2 s/r and 2 r/r. ----
dtc-parser.y: conflicts: 2 shift/reduce, 2 reduce/reduce
[snip]
DUMPTREES
sneetch:~/ibm/dtc$ ./dtc -v
Version: DTC 1.0.0-rc1-dirty
> I hve also verified that at least one other independent build
> using this approach produces a correct version string for them
> as well.
Yes, well, this is the other trouble - the current system is so
complex it's very hard to debug and figure out why it's claiming my
build is dirty but not yours.
> > > That is essentially what is there now. We just need a tag!
> >
> > Um... no. The base version comes from the numbers specified in the
> > Makefile, not from the git tag.
>
> Ah, ok. I understand what you mean now. That part.
> So run it the other way instead. So perhaps have the
> Makefile generate the tag using those versioning parts
> instead using some "make tagged_release" target?
Hrm... I really think the other way is both easier and less fragile.
> > > I would like to keep the current version mechanism as it
> > > is really quite similar to what is in the Kernel now.
> >
> > First, I don't think it really is - except in superficial aspect of
> > how the version number is partitioned
>
> I lifted the code from the Kernel's Makefile directly, and tweaked
> it slightly for lack of Kconfig aspects.
Ah, yes, ok, I see. Frankly I really don't think a lot of that stuff
makes much sense outside the context of Kbuild. The whole complex
filechk macro, for example - for which there's only one used parameter
in dtc's case.
> I don't want to tie the code and build mechanism to git too much.
> Specifically, we need to be able to support stand-alone tarball
> based builds. For example, I've spoken to the Debian package
> maintainer on this issue, and he likes this approach as well as
> he says it will make packaging it much easier.
Have a look at the patch I posted. I haven't sufficiently tested it
yet, but it should be able to generated version info for a tarball too
(provided the .git-manifest file is included, and I'm intending that
will be build by a make dist target). It will give both the
git-derived based version, and a file content derived hash so we can
robustly tell different builds apart, all with less code than the
current system.
--
David Gibson | I'll have my music baroque, and my code
david AT gibson.dropbear.id.au | minimalist, thank you. NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson
^ permalink raw reply
* Re: [PATCH] powerpc: Pegasos keyboard detection
From: Andrew Morton @ 2007-07-27 1:48 UTC (permalink / raw)
To: Benjamin Herrenschmidt; +Cc: linuxppc-dev, Alan Curry, linux-kernel
In-Reply-To: <1185347565.5439.310.camel@localhost.localdomain>
On Wed, 25 Jul 2007 17:12:45 +1000 Benjamin Herrenschmidt <benh@kernel.crashing.org> wrote:
> On Tue, 2007-07-24 at 21:28 -0400, Alan Curry wrote:
> > As of 2.6.22 the kernel doesn't recognize the i8042 keyboard/mouse controller
> > on the PegasosPPC. This is because of a feature/bug in the OF device tree:
> > the "device_type" attribute is an empty string instead of "8042" as the
> > kernel expects. This patch (against 2.6.22.1) adds a secondary detection
> > which looks for a device whose *name* is "8042" if there is no device whose
> > *type* is "8042".
> >
> > Signed-off-by: Alan Curry <pacman@world.std.com>
>
> Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
>
> Note, if there's a volunteer, we could probably turn that code into a
> nice table lookup.
Did this get merged, or otherwise fixed? Even though the code in there has
changed quite a bit, it looks to my untrained eye like the fix is still
applicable?
From: Alan Curry <pacman@TheWorld.com>
As of 2.6.22 the kernel doesn't recognize the i8042 keyboard/mouse
controller on the PegasosPPC. This is because of a feature/bug in the OF
device tree: the "device_type" attribute is an empty string instead of
"8042" as the kernel expects. This patch (against 2.6.22.1) adds a
secondary detection which looks for a device whose *name* is "8042" if
there is no device whose *type* is "8042".
Signed-off-by: Alan Curry <pacman@world.std.com>
Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
arch/powerpc/kernel/setup-common.c | 6 ++++++
1 file changed, 6 insertions(+)
diff -puN /dev/null /dev/null
diff -puN arch/powerpc/kernel/setup-common.c~powerpc-pegasos-keyboard-detection arch/powerpc/kernel/setup-common.c
--- a/arch/powerpc/kernel/setup-common.c~powerpc-pegasos-keyboard-detection
+++ a/arch/powerpc/kernel/setup-common.c
@@ -496,6 +496,12 @@ int check_legacy_ioport(unsigned long ba
break;
}
np = of_find_node_by_type(NULL, "8042");
+ /*
+ * Pegasos has no device_type on its 8042 node, look for the
+ * name instead
+ */
+ if (!np)
+ np = of_find_node_by_name(NULL, "8042");
break;
case FDC_BASE: /* FDC1 */
np = of_find_node_by_type(NULL, "fdc");
_
And ALan says that 2.6.22 is bust, but this patch no won't apply there so
if we want to fix 2.6.22.x then Alan's original patch would be needed.
^ permalink raw reply
* Re: DTC 1.0.0 Release Coming?
From: David Gibson @ 2007-07-27 2:00 UTC (permalink / raw)
To: Jon Loeliger, linuxppc-dev
In-Reply-To: <20070727013331.GB1561@localhost.localdomain>
On Fri, Jul 27, 2007 at 11:33:31AM +1000, David Gibson wrote:
> On Thu, Jul 26, 2007 at 10:21:33AM -0500, Jon Loeliger wrote:
[snip]
> > I hve also verified that at least one other independent build
> > using this approach produces a correct version string for them
> > as well.
>
> Yes, well, this is the other trouble - the current system is so
> complex it's very hard to debug and figure out why it's claiming my
> build is dirty but not yours.
Ok, figured out why. When I push, then pop a quilt patch some of the
files end up with their original contents, but changed timestamps.
That altered stat information causes git-diff-index to give false
indications of changed files, so setlocalversion adds the -dirty.
Running git status, or gitool or various other things causes git to
notice that the files aren't really changed, updates the index and
then the version is generated correctly again.
Not very robust though.
--
David Gibson | I'll have my music baroque, and my code
david AT gibson.dropbear.id.au | minimalist, thank you. NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson
^ permalink raw reply
* Re: [spi-devel-general] [PATCH 0/4] Few spi_mpc83xx.c fixes and improvements
From: David Brownell @ 2007-07-27 2:58 UTC (permalink / raw)
To: linuxppc-dev; +Cc: spi-devel-general
In-Reply-To: <20070726131134.GA3309@localhost.localdomain>
On Thursday 26 July 2007, Anton Vorontsov wrote:
> Hi all,
>
> These patches based on Linus' tree, as of today.
I don't know mpc83xx ... are there any PPC folk who can see
any reason not to just merge these patches? They look OK
to me, but in this case that doesn't mean much. :)
If I don't hear otherwise, I'll forward all four of these
patches upstream on Monday.
(Anton, thanks for these updates!)
- Dave
^ permalink raw reply
* Re: [PATCH] powerpc: Pegasos keyboard detection
From: Benjamin Herrenschmidt @ 2007-07-27 3:00 UTC (permalink / raw)
To: Andrew Morton; +Cc: linuxppc-dev, Alan Curry, linux-kernel
In-Reply-To: <20070726184800.0bb3b9fb.akpm@linux-foundation.org>
On Thu, 2007-07-26 at 18:48 -0700, Andrew Morton wrote:
> On Wed, 25 Jul 2007 17:12:45 +1000 Benjamin Herrenschmidt <benh@kernel.crashing.org> wrote:
>
> > On Tue, 2007-07-24 at 21:28 -0400, Alan Curry wrote:
> > > As of 2.6.22 the kernel doesn't recognize the i8042 keyboard/mouse controller
> > > on the PegasosPPC. This is because of a feature/bug in the OF device tree:
> > > the "device_type" attribute is an empty string instead of "8042" as the
> > > kernel expects. This patch (against 2.6.22.1) adds a secondary detection
> > > which looks for a device whose *name* is "8042" if there is no device whose
> > > *type* is "8042".
> > >
> > > Signed-off-by: Alan Curry <pacman@world.std.com>
> >
> > Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
> >
> > Note, if there's a volunteer, we could probably turn that code into a
> > nice table lookup.
>
> Did this get merged, or otherwise fixed? Even though the code in there has
> changed quite a bit, it looks to my untrained eye like the fix is still
> applicable?
Merged a fixed version:
f5d834fc34e61f1a40435981062000e5d2b2baa8
(In linus tree as of now)
Cheers,
Ben.
>
> From: Alan Curry <pacman@TheWorld.com>
>
> As of 2.6.22 the kernel doesn't recognize the i8042 keyboard/mouse
> controller on the PegasosPPC. This is because of a feature/bug in the OF
> device tree: the "device_type" attribute is an empty string instead of
> "8042" as the kernel expects. This patch (against 2.6.22.1) adds a
> secondary detection which looks for a device whose *name* is "8042" if
> there is no device whose *type* is "8042".
>
> Signed-off-by: Alan Curry <pacman@world.std.com>
> Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
> Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
> ---
>
> arch/powerpc/kernel/setup-common.c | 6 ++++++
> 1 file changed, 6 insertions(+)
>
> diff -puN /dev/null /dev/null
> diff -puN arch/powerpc/kernel/setup-common.c~powerpc-pegasos-keyboard-detection arch/powerpc/kernel/setup-common.c
> --- a/arch/powerpc/kernel/setup-common.c~powerpc-pegasos-keyboard-detection
> +++ a/arch/powerpc/kernel/setup-common.c
> @@ -496,6 +496,12 @@ int check_legacy_ioport(unsigned long ba
> break;
> }
> np = of_find_node_by_type(NULL, "8042");
> + /*
> + * Pegasos has no device_type on its 8042 node, look for the
> + * name instead
> + */
> + if (!np)
> + np = of_find_node_by_name(NULL, "8042");
> break;
> case FDC_BASE: /* FDC1 */
> np = of_find_node_by_type(NULL, "fdc");
> _
>
>
> And ALan says that 2.6.22 is bust, but this patch no won't apply there so
> if we want to fix 2.6.22.x then Alan's original patch would be needed.
>
> -
> To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at http://vger.kernel.org/majordomo-info.html
> Please read the FAQ at http://www.tux.org/lkml/
^ permalink raw reply
* Re: [spi-devel-general] [PATCH 1/3] [SPI] Sync spidev.{h, c} with spi.h
From: David Brownell @ 2007-07-27 3:02 UTC (permalink / raw)
To: spi-devel-general; +Cc: linuxppc-dev
In-Reply-To: <20070726135041.GA5550@localhost.localdomain>
On Thursday 26 July 2007, Anton Vorontsov wrote:
> --- a/drivers/spi/spidev.c
> +++ b/drivers/spi/spidev.c
> @@ -56,8 +56,8 @@ static unsigned long minors[N_SPI_MINORS / BITS_PER_LONG];
>
>
> /* Bit masks for spi_device.mode management */
> -#define SPI_MODE_MASK (SPI_CPHA | SPI_CPOL)
> -
> +#define SPI_MODE_MASK (SPI_CPHA | SPI_CPOL | SPI_CS_HIGH | \
> + SPI_LSB_FIRST | SPI_3WIRE)
Hmm, I seem to recall explicitly leaving out CS_HIGH on the grounds
that getting it wrong could corrupt the whole bus; Not Good (tm).
And the same argument can apply to 3WIRE mode ...
On the other hand, that's not necessarily a good reason, since there
are other ways to trash hardware too.
Comments anyone?
- Dave
^ permalink raw reply
* Re: [spi-devel-general] [PATCH 2/3] [SPI] Add new mode: SPI_LOOP
From: David Brownell @ 2007-07-27 3:07 UTC (permalink / raw)
To: spi-devel-general; +Cc: linuxppc-dev, Stephen Street
In-Reply-To: <20070726135051.GB5550@localhost.localdomain>
On Thursday 26 July 2007, Anton Vorontsov wrote:
> Loopback mode is supported by various controllers, this mode
> is useful for testing, especially in conjunction with spidev
> driver.
ISTR that Stephen Street provided a loopback mode for debug
in his pxa2xx_spi code. And I know you're fight that this
mode shows up in a lot of hardware.
Comments, anyone? This seems like a fair way to expose this
mechanism. And I tend to agree that it'd mostly be useful in
conjunction with "spidev".
Anton -- assuming this goes in, it'd be nice if you could
contribute a simple test program using this, which we could
keep in Documentation/spi somewhere. (Maybe with other testing
notes, if anyone comes up with such.)
- Dave
> ...
>
> --- a/include/linux/spi/spi.h
> +++ b/include/linux/spi/spi.h
> @@ -77,6 +77,7 @@ struct spi_device {
> #define SPI_CS_HIGH 0x04 /* chipselect active high? */
> #define SPI_LSB_FIRST 0x08 /* per-word bits-on-wire */
> #define SPI_3WIRE 0x10 /* SI/SO signals shared */
> +#define SPI_LOOP 0x20 /* loopback mode */
> u8 bits_per_word;
> int irq;
> void *controller_state;
^ permalink raw reply
* Re: [spi-devel-general] [PATCH 2/3] [SPI] Add new mode: SPI_LOOP
From: Ned Forrester @ 2007-07-27 3:34 UTC (permalink / raw)
To: David Brownell; +Cc: spi-devel-general, Stephen Street, linuxppc-dev
In-Reply-To: <200707262007.07537.david-b@pacbell.net>
David Brownell wrote:
> On Thursday 26 July 2007, Anton Vorontsov wrote:
>> Loopback mode is supported by various controllers, this mode
>> is useful for testing, especially in conjunction with spidev
>> driver.
>
> ISTR that Stephen Street provided a loopback mode for debug
> in his pxa2xx_spi code. And I know you're fight that this
> mode shows up in a lot of hardware.
>
> Comments, anyone? This seems like a fair way to expose this
> mechanism. And I tend to agree that it'd mostly be useful in
> conjunction with "spidev".
Yes, it is in pxa2xx_spi. It is passed in a structure that is attached
to spi_board_info.controller_data. I have used it to great effect to
test data modes in the driver for which I have no external hardware
support: various bits/word, clock frequencies, fifo thresholds, dma
burst sizes, etc.
It works for me if this is moved to struct spi_device.
I don't think I have any code that could be readily turned into a
generic test program.
--
Ned Forrester nforrester@whoi.edu
Oceanographic Systems Lab 508-289-2226
Applied Ocean Physics and Engineering Dept.
Woods Hole Oceanographic Institution Woods Hole, MA 02543, USA
http://www.whoi.edu/sbl/liteSite.do?litesiteid=7212
http://www.whoi.edu/hpb/Site.do?id=1532
http://www.whoi.edu/page.do?pid=10079
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox