* [PATCH v5 2/2] powerpc: add support for new hcall H_BEST_ENERGY
From: Vaidyanathan Srinivasan @ 2010-10-06 18:37 UTC (permalink / raw)
To: Benjamin Herrenschmidt, Paul Mackerras, Anton Blanchard
Cc: Michael Neuling, linuxppc-dev
In-Reply-To: <20101006182948.7006.75088.stgit@drishya.in.ibm.com>
Create sysfs interface to export data from H_BEST_ENERGY hcall
that can be used by administrative tools on supported pseries
platforms for energy management optimizations.
/sys/device/system/cpu/pseries_(de)activate_hint_list and
/sys/device/system/cpu/cpuN/pseries_(de)activate_hint will provide
hints for activation and deactivation of cpus respectively.
These hints are abstract number given by the hypervisor based
on the extended knowledge the hypervisor has regarding the
current system topology and resource mappings.
The activate and the deactivate sysfs entry is for the two
distinct operations that we could do for energy savings. When
we have more capacity than required, we could deactivate few
core to save energy. The choice of the core to deactivate
will be based on /sys/devices/system/cpu/deactivate_hint_list.
The comma separated list of cpus (cores) will be the preferred
choice. If we have to activate some of the deactivated cores,
then /sys/devices/system/cpu/activate_hint_list will be used.
The per-cpu file
/sys/device/system/cpu/cpuN/pseries_(de)activate_hint further
provide more fine grain information by exporting the value of
the hint itself.
Added new driver module
arch/powerpc/platforms/pseries/pseries_energy.c
under new config option CONFIG_PSERIES_ENERGY
Signed-off-by: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
---
arch/powerpc/include/asm/hvcall.h | 3
arch/powerpc/platforms/pseries/Kconfig | 10 +
arch/powerpc/platforms/pseries/Makefile | 1
arch/powerpc/platforms/pseries/pseries_energy.c | 326 +++++++++++++++++++++++
4 files changed, 339 insertions(+), 1 deletions(-)
create mode 100644 arch/powerpc/platforms/pseries/pseries_energy.c
diff --git a/arch/powerpc/include/asm/hvcall.h b/arch/powerpc/include/asm/hvcall.h
index de03ca5..bf86b03 100644
--- a/arch/powerpc/include/asm/hvcall.h
+++ b/arch/powerpc/include/asm/hvcall.h
@@ -232,7 +232,8 @@
#define H_GET_EM_PARMS 0x2B8
#define H_SET_MPP 0x2D0
#define H_GET_MPP 0x2D4
-#define MAX_HCALL_OPCODE H_GET_MPP
+#define H_BEST_ENERGY 0x2F4
+#define MAX_HCALL_OPCODE H_BEST_ENERGY
#ifndef __ASSEMBLY__
diff --git a/arch/powerpc/platforms/pseries/Kconfig b/arch/powerpc/platforms/pseries/Kconfig
index c667f0f..8323622 100644
--- a/arch/powerpc/platforms/pseries/Kconfig
+++ b/arch/powerpc/platforms/pseries/Kconfig
@@ -33,6 +33,16 @@ config PSERIES_MSI
depends on PCI_MSI && EEH
default y
+config PSERIES_ENERGY
+ tristate "pSeries energy management capabilities driver"
+ depends on PPC_PSERIES
+ default y
+ help
+ Provides interface to platform energy management capabilities
+ on supported PSERIES platforms.
+ Provides: /sys/devices/system/cpu/pseries_(de)activation_hint_list
+ and /sys/devices/system/cpu/cpuN/pseries_(de)activation_hint
+
config SCANLOG
tristate "Scanlog dump interface"
depends on RTAS_PROC && PPC_PSERIES
diff --git a/arch/powerpc/platforms/pseries/Makefile b/arch/powerpc/platforms/pseries/Makefile
index 046ace9..50a7ea3 100644
--- a/arch/powerpc/platforms/pseries/Makefile
+++ b/arch/powerpc/platforms/pseries/Makefile
@@ -16,6 +16,7 @@ obj-$(CONFIG_EEH) += eeh.o eeh_cache.o eeh_driver.o eeh_event.o eeh_sysfs.o
obj-$(CONFIG_KEXEC) += kexec.o
obj-$(CONFIG_PCI) += pci.o pci_dlpar.o
obj-$(CONFIG_PSERIES_MSI) += msi.o
+obj-$(CONFIG_PSERIES_ENERGY) += pseries_energy.o
obj-$(CONFIG_HOTPLUG_CPU) += hotplug-cpu.o
obj-$(CONFIG_MEMORY_HOTPLUG) += hotplug-memory.o
diff --git a/arch/powerpc/platforms/pseries/pseries_energy.c b/arch/powerpc/platforms/pseries/pseries_energy.c
new file mode 100644
index 0000000..c8b3c69
--- /dev/null
+++ b/arch/powerpc/platforms/pseries/pseries_energy.c
@@ -0,0 +1,326 @@
+/*
+ * POWER platform energy management driver
+ * Copyright (C) 2010 IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * version 2 as published by the Free Software Foundation.
+ *
+ * This pseries platform device driver provides access to
+ * platform energy management capabilities.
+ */
+
+#include <linux/module.h>
+#include <linux/types.h>
+#include <linux/errno.h>
+#include <linux/init.h>
+#include <linux/seq_file.h>
+#include <linux/sysdev.h>
+#include <linux/cpu.h>
+#include <linux/of.h>
+#include <asm/cputhreads.h>
+#include <asm/page.h>
+#include <asm/hvcall.h>
+
+
+#define MODULE_VERS "1.0"
+#define MODULE_NAME "pseries_energy"
+
+/* Driver flags */
+
+static int sysfs_entries;
+
+/* Helper routines */
+
+/*
+ * Routine to detect firmware support for hcall
+ * return 1 if H_BEST_ENERGY is supported
+ * else return 0
+ */
+
+static int check_for_h_best_energy(void)
+{
+ struct device_node *rtas = NULL;
+ const char *hypertas, *s;
+ int length;
+ int rc = 0;
+
+ rtas = of_find_node_by_path("/rtas");
+ if (!rtas)
+ return 0;
+
+ hypertas = of_get_property(rtas, "ibm,hypertas-functions", &length);
+ if (!hypertas) {
+ of_node_put(rtas);
+ return 0;
+ }
+
+ /* hypertas will have list of strings with hcall names */
+ for (s = hypertas; s < hypertas + length; s += strlen(s) + 1) {
+ if (!strncmp("hcall-best-energy-1", s, 19)) {
+ rc = 1; /* Found the string */
+ break;
+ }
+ }
+ of_node_put(rtas);
+ return rc;
+}
+
+/* Helper Routines to convert between drc_index to cpu numbers */
+
+static u32 cpu_to_drc_index(int cpu)
+{
+ struct device_node *dn = NULL;
+ const int *indexes;
+ int i;
+ int rc = 1;
+ u32 ret = 0;
+
+ dn = of_find_node_by_path("/cpus");
+ if (dn == NULL)
+ goto err;
+ indexes = of_get_property(dn, "ibm,drc-indexes", NULL);
+ if (indexes == NULL)
+ goto err_of_node_put;
+ /* Convert logical cpu number to core number */
+ i = cpu_core_index_of_thread(cpu);
+ /*
+ * The first element indexes[0] is the number of drc_indexes
+ * returned in the list. Hence i+1 will get the drc_index
+ * corresponding to core number i.
+ */
+ WARN_ON(i > indexes[0]);
+ ret = indexes[i + 1];
+ rc = 0;
+
+err_of_node_put:
+ of_node_put(dn);
+err:
+ if (rc)
+ printk(KERN_WARNING "cpu_to_drc_index(%d) failed", cpu);
+ return ret;
+}
+
+static int drc_index_to_cpu(u32 drc_index)
+{
+ struct device_node *dn = NULL;
+ const int *indexes;
+ int i, cpu = 0;
+ int rc = 1;
+
+ dn = of_find_node_by_path("/cpus");
+ if (dn == NULL)
+ goto err;
+ indexes = of_get_property(dn, "ibm,drc-indexes", NULL);
+ if (indexes == NULL)
+ goto err_of_node_put;
+ /*
+ * First element in the array is the number of drc_indexes
+ * returned. Search through the list to find the matching
+ * drc_index and get the core number
+ */
+ for (i = 0; i < indexes[0]; i++) {
+ if (indexes[i + 1] == drc_index)
+ break;
+ }
+ /* Convert core number to logical cpu number */
+ cpu = cpu_first_thread_of_core(i);
+ rc = 0;
+
+err_of_node_put:
+ of_node_put(dn);
+err:
+ if (rc)
+ printk(KERN_WARNING "drc_index_to_cpu(%d) failed", drc_index);
+ return cpu;
+}
+
+/*
+ * pseries hypervisor call H_BEST_ENERGY provides hints to OS on
+ * preferred logical cpus to activate or deactivate for optimized
+ * energy consumption.
+ */
+
+#define FLAGS_MODE1 0x004E200000080E01
+#define FLAGS_MODE2 0x004E200000080401
+#define FLAGS_ACTIVATE 0x100
+
+static ssize_t get_best_energy_list(char *page, int activate)
+{
+ int rc, cnt, i, cpu;
+ unsigned long retbuf[PLPAR_HCALL9_BUFSIZE];
+ unsigned long flags = 0;
+ u32 *buf_page;
+ char *s = page;
+
+ buf_page = (u32 *) get_zeroed_page(GFP_KERNEL);
+ if (!buf_page)
+ return -ENOMEM;
+
+ flags = FLAGS_MODE1;
+ if (activate)
+ flags |= FLAGS_ACTIVATE;
+
+ rc = plpar_hcall9(H_BEST_ENERGY, retbuf, flags, 0, __pa(buf_page),
+ 0, 0, 0, 0, 0, 0);
+ if (rc != H_SUCCESS) {
+ free_page((unsigned long) buf_page);
+ return -EINVAL;
+ }
+
+ cnt = retbuf[0];
+ for (i = 0; i < cnt; i++) {
+ cpu = drc_index_to_cpu(buf_page[2*i+1]);
+ if ((cpu_online(cpu) && !activate) ||
+ (!cpu_online(cpu) && activate))
+ s += sprintf(s, "%d,", cpu);
+ }
+ if (s > page) { /* Something to show */
+ s--; /* Suppress last comma */
+ s += sprintf(s, "\n");
+ }
+
+ free_page((unsigned long) buf_page);
+ return s-page;
+}
+
+static ssize_t get_best_energy_data(struct sys_device *dev,
+ char *page, int activate)
+{
+ int rc;
+ unsigned long retbuf[PLPAR_HCALL9_BUFSIZE];
+ unsigned long flags = 0;
+
+ flags = FLAGS_MODE2;
+ if (activate)
+ flags |= FLAGS_ACTIVATE;
+
+ rc = plpar_hcall9(H_BEST_ENERGY, retbuf, flags,
+ cpu_to_drc_index(dev->id),
+ 0, 0, 0, 0, 0, 0, 0);
+
+ if (rc != H_SUCCESS)
+ return -EINVAL;
+
+ return sprintf(page, "%lu\n", retbuf[1] >> 32);
+}
+
+/* Wrapper functions */
+
+static ssize_t cpu_activate_hint_list_show(struct sysdev_class *class,
+ struct sysdev_class_attribute *attr, char *page)
+{
+ return get_best_energy_list(page, 1);
+}
+
+static ssize_t cpu_deactivate_hint_list_show(struct sysdev_class *class,
+ struct sysdev_class_attribute *attr, char *page)
+{
+ return get_best_energy_list(page, 0);
+}
+
+static ssize_t percpu_activate_hint_show(struct sys_device *dev,
+ struct sysdev_attribute *attr, char *page)
+{
+ return get_best_energy_data(dev, page, 1);
+}
+
+static ssize_t percpu_deactivate_hint_show(struct sys_device *dev,
+ struct sysdev_attribute *attr, char *page)
+{
+ return get_best_energy_data(dev, page, 0);
+}
+
+/*
+ * Create sysfs interface:
+ * /sys/devices/system/cpu/pseries_activate_hint_list
+ * /sys/devices/system/cpu/pseries_deactivate_hint_list
+ * Comma separated list of cpus to activate or deactivate
+ * /sys/devices/system/cpu/cpuN/pseries_activate_hint
+ * /sys/devices/system/cpu/cpuN/pseries_deactivate_hint
+ * Per-cpu value of the hint
+ */
+
+struct sysdev_class_attribute attr_cpu_activate_hint_list =
+ _SYSDEV_CLASS_ATTR(pseries_activate_hint_list, 0444,
+ cpu_activate_hint_list_show, NULL);
+
+struct sysdev_class_attribute attr_cpu_deactivate_hint_list =
+ _SYSDEV_CLASS_ATTR(pseries_deactivate_hint_list, 0444,
+ cpu_deactivate_hint_list_show, NULL);
+
+struct sysdev_attribute attr_percpu_activate_hint =
+ _SYSDEV_ATTR(pseries_activate_hint, 0444,
+ percpu_activate_hint_show, NULL);
+
+struct sysdev_attribute attr_percpu_deactivate_hint =
+ _SYSDEV_ATTR(pseries_deactivate_hint, 0444,
+ percpu_deactivate_hint_show, NULL);
+
+static int __init pseries_energy_init(void)
+{
+ int cpu, err;
+ struct sys_device *cpu_sys_dev;
+
+ if (!check_for_h_best_energy()) {
+ printk(KERN_INFO "Hypercall H_BEST_ENERGY not supported\n");
+ return 0;
+ }
+ /* Create the sysfs files */
+ err = sysfs_create_file(&cpu_sysdev_class.kset.kobj,
+ &attr_cpu_activate_hint_list.attr);
+ if (!err)
+ err = sysfs_create_file(&cpu_sysdev_class.kset.kobj,
+ &attr_cpu_deactivate_hint_list.attr);
+
+ if (err)
+ return err;
+ for_each_possible_cpu(cpu) {
+ cpu_sys_dev = get_cpu_sysdev(cpu);
+ err = sysfs_create_file(&cpu_sys_dev->kobj,
+ &attr_percpu_activate_hint.attr);
+ if (err)
+ break;
+ err = sysfs_create_file(&cpu_sys_dev->kobj,
+ &attr_percpu_deactivate_hint.attr);
+ if (err)
+ break;
+ }
+
+ if (err)
+ return err;
+
+ sysfs_entries = 1; /* Removed entries on cleanup */
+ return 0;
+
+}
+
+static void __exit pseries_energy_cleanup(void)
+{
+ int cpu;
+ struct sys_device *cpu_sys_dev;
+
+ if (!sysfs_entries)
+ return;
+
+ /* Remove the sysfs files */
+ sysfs_remove_file(&cpu_sysdev_class.kset.kobj,
+ &attr_cpu_activate_hint_list.attr);
+
+ sysfs_remove_file(&cpu_sysdev_class.kset.kobj,
+ &attr_cpu_deactivate_hint_list.attr);
+
+ for_each_possible_cpu(cpu) {
+ cpu_sys_dev = get_cpu_sysdev(cpu);
+ sysfs_remove_file(&cpu_sys_dev->kobj,
+ &attr_percpu_activate_hint.attr);
+ sysfs_remove_file(&cpu_sys_dev->kobj,
+ &attr_percpu_deactivate_hint.attr);
+ }
+}
+
+module_init(pseries_energy_init);
+module_exit(pseries_energy_cleanup);
+MODULE_DESCRIPTION("Driver for pSeries platform energy management");
+MODULE_AUTHOR("Vaidyanathan Srinivasan");
+MODULE_LICENSE("GPL");
^ permalink raw reply related
* [PATCH v5 1/2] powerpc: cleanup APIs for cpu/thread/core mappings
From: Vaidyanathan Srinivasan @ 2010-10-06 18:36 UTC (permalink / raw)
To: Benjamin Herrenschmidt, Paul Mackerras, Anton Blanchard
Cc: Michael Neuling, linuxppc-dev
In-Reply-To: <20101006182948.7006.75088.stgit@drishya.in.ibm.com>
These APIs take logical cpu number as input
Change cpu_first_thread_in_core() to cpu_first_thread_sibling()
Change cpu_last_thread_in_core() to cpu_last_thread_sibling()
These APIs convert core number (index) to logical cpu/thread numbers
Add cpu_first_thread_of_core(int core)
Changed cpu_thread_to_core() to cpu_core_index_of_thread(int cpu)
The goal is to make 'threads_per_core' accessible to the
pseries_energy module. Instead of making an API to read
threads_per_core, this is a higher level wrapper function to
convert from logical cpu number to core number.
The current APIs cpu_first_thread_in_core() and
cpu_last_thread_in_core() returns logical CPU number while
cpu_thread_to_core() returns core number or index which is
not a logical CPU number. The new APIs are now clearly named to
distinguish 'core number' versus first and last 'logical cpu
number' in that core.
The new APIs cpu_{first,last}_thread_sibling() work on
logical cpu numbers. While cpu_first_thread_of_core() and
cpu_core_index_of_thread() work on core index.
Example usage: (4 threads per core system)
cpu_first_thread_sibling(5) = 4
cpu_last_thread_sibling(5) = 7
cpu_core_index_of_thread(5) = 1
cpu_first_thread_of_core(1) = 4
cpu_core_index_of_thread() is used in cpu_to_drc_index() in the
module and cpu_first_thread_of_core() is used in
drc_index_to_cpu() in the module.
Make API changes to few callers. Export symbols for use in modules.
Signed-off-by: Vaidyanathan Srinivasan <svaidy@linux.vnet.ibm.com>
---
arch/powerpc/include/asm/cputhreads.h | 15 +++++++++------
arch/powerpc/kernel/smp.c | 19 ++++++++++++++++---
arch/powerpc/mm/mmu_context_nohash.c | 12 ++++++------
3 files changed, 31 insertions(+), 15 deletions(-)
diff --git a/arch/powerpc/include/asm/cputhreads.h b/arch/powerpc/include/asm/cputhreads.h
index a8e1844..f71bb4c 100644
--- a/arch/powerpc/include/asm/cputhreads.h
+++ b/arch/powerpc/include/asm/cputhreads.h
@@ -61,22 +61,25 @@ static inline cpumask_t cpu_online_cores_map(void)
return cpu_thread_mask_to_cores(cpu_online_map);
}
-static inline int cpu_thread_to_core(int cpu)
-{
- return cpu >> threads_shift;
-}
+#ifdef CONFIG_SMP
+int cpu_core_index_of_thread(int cpu);
+int cpu_first_thread_of_core(int core);
+#else
+static inline int cpu_core_index_of_thread(int cpu) { return cpu; }
+static inline int cpu_first_thread_of_core(int core) { return core; }
+#endif
static inline int cpu_thread_in_core(int cpu)
{
return cpu & (threads_per_core - 1);
}
-static inline int cpu_first_thread_in_core(int cpu)
+static inline int cpu_first_thread_sibling(int cpu)
{
return cpu & ~(threads_per_core - 1);
}
-static inline int cpu_last_thread_in_core(int cpu)
+static inline int cpu_last_thread_sibling(int cpu)
{
return cpu | (threads_per_core - 1);
}
diff --git a/arch/powerpc/kernel/smp.c b/arch/powerpc/kernel/smp.c
index 0008bc5..012d6e2 100644
--- a/arch/powerpc/kernel/smp.c
+++ b/arch/powerpc/kernel/smp.c
@@ -466,7 +466,20 @@ out:
return id;
}
-/* Must be called when no change can occur to cpu_present_mask,
+/* Helper routines for cpu to core mapping */
+int cpu_core_index_of_thread(int cpu)
+{
+ return cpu >> threads_shift;
+}
+EXPORT_SYMBOL_GPL(cpu_core_index_of_thread);
+
+int cpu_first_thread_of_core(int core)
+{
+ return core << threads_shift;
+}
+EXPORT_SYMBOL_GPL(cpu_first_thread_of_core);
+
+/* Must be called when no change can occur to cpu_present_map,
* i.e. during cpu online or offline.
*/
static struct device_node *cpu_to_l2cache(int cpu)
@@ -517,7 +530,7 @@ int __devinit start_secondary(void *unused)
notify_cpu_starting(cpu);
set_cpu_online(cpu, true);
/* Update sibling maps */
- base = cpu_first_thread_in_core(cpu);
+ base = cpu_first_thread_sibling(cpu);
for (i = 0; i < threads_per_core; i++) {
if (cpu_is_offline(base + i))
continue;
@@ -596,7 +609,7 @@ int __cpu_disable(void)
return err;
/* Update sibling maps */
- base = cpu_first_thread_in_core(cpu);
+ base = cpu_first_thread_sibling(cpu);
for (i = 0; i < threads_per_core; i++) {
cpumask_clear_cpu(cpu, cpu_sibling_mask(base + i));
cpumask_clear_cpu(base + i, cpu_sibling_mask(cpu));
diff --git a/arch/powerpc/mm/mmu_context_nohash.c b/arch/powerpc/mm/mmu_context_nohash.c
index ddfd7ad..9aa754c 100644
--- a/arch/powerpc/mm/mmu_context_nohash.c
+++ b/arch/powerpc/mm/mmu_context_nohash.c
@@ -111,8 +111,8 @@ static unsigned int steal_context_smp(unsigned int id)
* a core map instead but this will do for now.
*/
for_each_cpu(cpu, mm_cpumask(mm)) {
- for (i = cpu_first_thread_in_core(cpu);
- i <= cpu_last_thread_in_core(cpu); i++)
+ for (i = cpu_first_thread_sibling(cpu);
+ i <= cpu_last_thread_sibling(cpu); i++)
__set_bit(id, stale_map[i]);
cpu = i - 1;
}
@@ -264,14 +264,14 @@ void switch_mmu_context(struct mm_struct *prev, struct mm_struct *next)
*/
if (test_bit(id, stale_map[cpu])) {
pr_hardcont(" | stale flush %d [%d..%d]",
- id, cpu_first_thread_in_core(cpu),
- cpu_last_thread_in_core(cpu));
+ id, cpu_first_thread_sibling(cpu),
+ cpu_last_thread_sibling(cpu));
local_flush_tlb_mm(next);
/* XXX This clear should ultimately be part of local_flush_tlb_mm */
- for (i = cpu_first_thread_in_core(cpu);
- i <= cpu_last_thread_in_core(cpu); i++) {
+ for (i = cpu_first_thread_sibling(cpu);
+ i <= cpu_last_thread_sibling(cpu); i++) {
__clear_bit(id, stale_map[i]);
}
}
^ permalink raw reply related
* [PATCH v5 0/2] powerpc: add support for new hcall H_BEST_ENERGY
From: Vaidyanathan Srinivasan @ 2010-10-06 18:36 UTC (permalink / raw)
To: Benjamin Herrenschmidt, Paul Mackerras, Anton Blanchard
Cc: Michael Neuling, linuxppc-dev
Hi Ben,
The following series adds a new kernel module for powerpc pseries
platforms in order to export platform energy management capabilities.
The module exports data from a new hypervisor call H_BEST_ENERGY.
Comments and suggestions made on the previous iteration of the
patch related to function naming has been incorporated.
Changes in v5:
* Renamed cpu_{left,right}most_thread_sibling() to
cpu_{first,last}_thread_sibling()
* Renamed cpu_core_of_thread() to cpu_core_index_of_thread()
(these function work on core index)
* Rebased to 2.6.36-rc6 and tested on a supported platform
Changes in v4:
[4] [PATCH v4 0/2] powerpc: add support for new hcall H_BEST_ENERGY
http://lists.ozlabs.org/pipermail/linuxppc-dev/2010-July/084217.html
* Added more documentation
* Added check_for_h_best_energy() to look in ibm,hypertas-functions so
that sysfs entries are not created in an unsupported platform
* Added cleaner error checks and correct of_node_put()
* Rebased and tested on 2.6.35-rc5
Changed in v3:
[3] [PATCH v3 0/2] powerpc: add support for new hcall H_BEST_ENERGY
http://lists.ozlabs.org/pipermail/linuxppc-dev/2010-June/083414.html
* Added more documentation in the cleanup patch
* Removed RFC tag, rebased and tested on 2.6.35-rc3
* Ready for inclusion in powerpc/next tree for further testing
Changes in v2:
[2] [RFC PATCH v2 0/2] powerpc: add support for new hcall H_BEST_ENERGY
http://lists.ozlabs.org/pipermail/linuxppc-dev/2010-May/082246.html
* Cleanup cpu/thread/core APIs
* Export APIs to module instead of threads_per_core
* Use of_find_node_by_path() instead of of_find_node_by_name()
* Error checking and whitespace cleanups
First version:
[1] [RFC] powerpc: add support for new hcall H_BEST_ENERGY
http://lists.ozlabs.org/pipermail/linuxppc-dev/2010-March/080796.html
This patch series will apply on 2.6.36-rc6 as well as powerpc/next
tree. Please review and include in powerpc/next tree for further
testing.
I could incrementally reduce some of the error checks as suggested by
Michael Neuling as next steps. This patch series is conservative and
has more error checking in device tree parsing and drc index matching
code than what may be required.
Thanks,
Vaidy
---
Vaidyanathan Srinivasan (2):
powerpc: cleanup APIs for cpu/thread/core mappings
powerpc: add support for new hcall H_BEST_ENERGY
arch/powerpc/include/asm/cputhreads.h | 15 +
arch/powerpc/include/asm/hvcall.h | 3
arch/powerpc/kernel/smp.c | 19 +
arch/powerpc/mm/mmu_context_nohash.c | 12 -
arch/powerpc/platforms/pseries/Kconfig | 10 +
arch/powerpc/platforms/pseries/Makefile | 1
arch/powerpc/platforms/pseries/pseries_energy.c | 326 +++++++++++++++++++++++
7 files changed, 370 insertions(+), 16 deletions(-)
create mode 100644 arch/powerpc/platforms/pseries/pseries_energy.c
^ permalink raw reply
* RE: Serial RapidIO Maintaintance read causes lock up
From: Anderson, Trevor @ 2010-10-06 18:08 UTC (permalink / raw)
To: Bastiaan Nijkamp, John Traill
Cc: Bounine, Alexandre, linuxppc-dev@lists.ozlabs.org
In-Reply-To: <AANLkTik46NsiMhWo=GkHz4UbdDJeBLwFATJzhk-M3hSP@mail.gmail.com>
[-- Attachment #1: Type: text/plain, Size: 14335 bytes --]
I may have come across a similar problem, but I've never worked card-to-card without at least one switch in the way.
The problems I have encountered have been hang-ups during memory-mapped maintenance reads to devices that the switch reports as "up".
A workaround for the hang-up is to use a DMA transfer that bypasses the ATMU to perform a maintenance read (not all, just the first, a test read of a new discovery). If the DMA fails, as it does in those unusual circumstances, it will report a bus transfer error - but it will not hang up. You can recover, and avoid or re-try the connection later.
A real "fix" for your problem may be to ensure that both of your RapidIO interfaces are programmed to accept all incoming transactions (see "Accept All Configuration Register (AACR)" in Freescale reference manual). But no guarantees with that - it just seemed to clear up problems on my own rig.
From: linuxppc-dev-bounces+tanderson=curtisswright.com@lists.ozlabs.org [mailto:linuxppc-dev-bounces+tanderson=curtisswright.com@lists.ozlabs.org] On Behalf Of Bastiaan Nijkamp
Sent: Tuesday, October 05, 2010 7:28 AM
To: John Traill
Cc: Bounine, Alexandre; linuxppc-dev@lists.ozlabs.org
Subject: Re: Serial RapidIO Maintaintance read causes lock up
Hi John,
1. Yes, they are both running the exact same kernel and both are configured in the same way. With the exception that one is set as host and the other as a agent.
2. Accept All is set for both boards.
3. As i understand, the agent cannot send anything before it is enumerated, so it would be safe to first reset the agent and right after that the host. In either case, thats the way i am using. The full kernel log until the discovery times out after 30 seconds is shown below:
Using SBC8548 machine description
Memory CAM mapping: 256 Mb, residual: 0Mb
Linux version 2.6.35.6 (dl704@lxws006<mailto:dl704@lxws006>) (gcc version 4.4.1 (Wind River Linux Sour
cery G++ 4.4-250) ) #3 Tue Oct 5 13:24:45 CEST 2010
bootconsole [udbg0] enabled
setup_arch: bootmem
sbc8548_setup_arch()
arch: exit
Zone PFN ranges:
DMA 0x00000000 -> 0x00010000
Normal empty
Movable zone start PFN for each node
early_node_map[1] active PFN ranges
0: 0x00000000 -> 0x00010000
MMU: Allocated 1088 bytes of context maps for 255 contexts
Built 1 zonelists in Zone order, mobility grouping on. Total pages: 65024
Kernel command line: root=/dev/nfs rw nfsroot=192.168.100.21:/thales/target/rfs/
sbc8548_wrlinux4 ip=192.168.100.151:192.168.100.21:192.168.100.21:255.255.255.0:
sbc8548_1:eth0:off console=ttyS0,115200
PID hash table entries: 1024 (order: 0, 4096 bytes)
Dentry cache hash table entries: 32768 (order: 5, 131072 bytes)
Inode-cache hash table entries: 16384 (order: 4, 65536 bytes)
Memory: 256996k/262144k available (2644k kernel code, 5148k reserved, 108k data,
77k bss, 136k init)
Kernel virtual memory layout:
* 0xfffdf000..0xfffff000 : fixmap
* 0xfdffd000..0xfe000000 : early ioremap
* 0xd1000000..0xfdffd000 : vmalloc & ioremap
Hierarchical RCU implementation.
RCU-based detection of stalled CPUs is disabled.
Verbose stalled-CPUs detection is disabled.
NR_IRQS:512 nr_irqs:512
mpic: Setting up MPIC " OpenPIC " version 1.2 at e0040000, max 1 CPUs
mpic: ISU size: 80, shift: 7, mask: 7f
mpic: Initializing for 80 sources
clocksource: timebase mult[50cede6] shift[22] registered
pid_max: default: 32768 minimum: 301
Mount-cache hash table entries: 512
NET: Registered protocol family 16
PCI: Probing PCI hardware
bio: create slab <bio-0> at 0
vgaarb: loaded
Switching to clocksource timebase
NET: Registered protocol family 2
IP route cache hash table entries: 2048 (order: 1, 8192 bytes)
TCP established hash table entries: 8192 (order: 4, 65536 bytes)
TCP bind hash table entries: 8192 (order: 3, 32768 bytes)
TCP: Hash tables configured (established 8192 bind 8192)
TCP reno registered
UDP hash table entries: 256 (order: 0, 4096 bytes)
UDP-Lite hash table entries: 256 (order: 0, 4096 bytes)
NET: Registered protocol family 1
RPC: Registered udp transport module.
RPC: Registered tcp transport module.
RPC: Registered tcp NFSv4.1 backchannel transport module.
Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Of-device full name /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size 0x0000000020000000.
fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
fsl-of-rio e00c0000.rapidio: DeviceID is 0xffffffff
fsl-of-rio e00c0000.rapidio: Configured as AGENT
fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio e00c0000.rapidio: Hardware port width: 4
fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO Maintainance Window Size 0x400000,New Main Start: 0xd1080000
RIO: discover master port 0, RIO0 mport
A interesting thing that i found out is that when the agent is reset while the host is locked up (eg. it cannot be stopped nor can i read the registers and memory trough a JTAG Interface), the host comes back online and just continues booting linux with a RapidIO error. See the log below.
Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Of-device full name /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size 0x0000000020000000.
fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
fsl-of-rio e00c0000.rapidio: DeviceID is 0x0
fsl-of-rio e00c0000.rapidio: Configured as HOST
fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio e00c0000.rapidio: Hardware port width: 4
fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO Maintainance Window Size 0x400000,New Main Start: 0xd1080000
RIO: enumerate master port 0, RIO0 mport
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
RIO: master port 0 device has lost enumeration to a remote host
Regards,
Bastiaan
2010/10/5 John Traill <john.traill@freescale.com<mailto:john.traill@freescale.com>>
Bastiaan,
A few things to check.
1. Is the target board also set up for small common transport system size ie 256.
2. Make sure the target has "Accept All" set - in fsl_rio.c look for
/* Set to receive any dist ID for serial RapidIO controller. */
if (port->phy_type == RIO_PHY_SERIAL)
out_be32((priv->regs_win + RIO_ISR_AACR), RIO_ISR_AACR_AA);
3. How do you synchronise reset between both systems ? Both need to be reset to insure the inbound/outbound ackid's remain in sync. If you only reset one then you have the potential for the ackid's to get out of sync. Also what is the kernel log on the agent system ?
Cheers.
On 05/10/10 09:56, Bastiaan Nijkamp wrote:
Hi Alex,
Thanks for your advice. We are trying to make a board-to-board
connection without any additional hardware (eg. a switch). The boards
use a 50-pin, right-angle MEC8-125-02-L-D-RA1 connector from SAMTEC and
are connected trough a EEDP-016-12.00-RA1-RA2-2 cross cable from SAMTEC.
I hope this information is sufficient since there is not much one can
find about it on Google. In addition, you can see a picture of the board
including the connector in the datasheet located at
http://www.windriver.com/products/product-notes/SBC8548E-product-note.pdf.
It is the connector on the left side of the PCI-EX slot.
We have tried your suggestion but the situation does not change other
than the lane-mode being set to single lane 0, it still locks up when
trying to generate a maintenance transaction. I still think it is memory
related since the lock up occurs when accessing the maintenance window.
Although all memory related settings seems to be alright.
The kernel output is as follows:
Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Of-device full name
/soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size
0x0000000010000000.
fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
fsl-of-rio e00c0000.rapidio: DeviceID is 0x0
fsl-of-rio e00c0000.rapidio: Configured as HOST
fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio e00c0000.rapidio: Hardware port width: 4
fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO
Maintainance Window Size 0x400000,New Main Start: 0xd1080000
RIO: enumerate master port 0, RIO0 mport
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d108006
Regards,
Bastiaan
2010/10/4 Bounine, Alexandre <Alexandre.Bounine@idt.com<mailto:Alexandre.Bounine@idt.com>
<mailto:Alexandre.Bounine@idt.com<mailto:Alexandre.Bounine@idt.com>>>
Hi Bastiaan,
Are you trying board-to-board connection?
I am not familiar with WRS SBC8548 board - which type of connector they
use for SRIO?
Assuming that all configuration is correct,
I would recommend first to try setting up x1 link mode at the lowest
link speed.
The x4 mode may present challenges in some cases.
For quick test you may just add port width override into fsl_rio.c
like shown below (ugly but sometimes it helps ;) ):
@@ -1461,10 +1461,16 @@ int fsl_rio_setup(struct platform_device *dev)
rio_register_mport(port);
priv->regs_win = ioremap(regs.start, regs.end - regs.start + 1);
rio_regs_win = priv->regs_win;
+dev_info(&dev->dev, "Overriding RIO_PORT setting to single lane 0\n");
+out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
0x800000);
+out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
0x2000000);
+out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) &
~0x800000);
+msleep(100);
+
/* Probe the master port phy type */
ccsr = in_be32(priv->regs_win + RIO_CCSR);
port->phy_type = (ccsr & 1) ? RIO_PHY_SERIAL : RIO_PHY_PARALLEL;
dev_info(&dev->dev, "RapidIO PHY type: %s\n",
(port->phy_type == RIO_PHY_PARALLEL) ?
"parallel" :
Let me know what happens.
Please keep me in the CC: list next time when posting RapidIO questions
to the linuxppc-dev or kernel mailing lists.
Regards,
Alex.
_______________________________________________
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org<mailto:Linuxppc-dev@lists.ozlabs.org>
https://lists.ozlabs.org/listinfo/linuxppc-dev
--
John Traill
Systems Engineer
Network and Computing Systems Group
Freescale Semiconductor UK LTD
Colvilles Road
East Kilbride
Glasgow G75 0TG, Scotland
Tel: +44 (0) 1355 355494
Fax: +44 (0) 1355 261790
E-mail: john.traill@freescale.com<mailto:john.traill@freescale.com>
Registration Number: SC262720
VAT Number: GB831329053
[ ] General Business Use
[ ] Freescale Internal Use Only
[ ] Freescale Confidential Proprietary
_______________________________________________________________________
This e-mail and any files transmitted with it are proprietary and intended solely for the use of the individual or entity to whom they are addressed. If you have reason to believe that you have received this e-mail in error, please notify the sender and destroy this email and any attached files. Please note that any views or opinions presented in this e-mail are solely those of the author and do not necessarily represent those of the Curtiss-Wright Corporation or any of its subsidiaries. Documents attached hereto may contain technology subject to government export regulations. Recipient is solely responsible for ensuring that any re-export, transfer or disclosure of this information is in accordance with applicable government export regulations. The recipient should check this e-mail and any attachments for the presence of viruses. Curtiss-Wright Corporation and its subsidiaries accept no liability for any damage caused by any virus transmitted by this e-mail.
[-- Attachment #2: Type: text/html, Size: 24406 bytes --]
^ permalink raw reply
* Re: powerpc, fs_enet: scanning PHY after Linux is up
From: Grant Likely @ 2010-10-06 17:30 UTC (permalink / raw)
To: Holger brunck; +Cc: linuxppc-dev, devicetree-discuss, hs, Detlev Zundel, netdev
In-Reply-To: <4CAC7EB0.6080502@keymile.com>
On Wed, Oct 6, 2010 at 7:50 AM, Holger brunck <holger.brunck@keymile.com> w=
rote:
> Hello Heiko,
>
> On 10/06/2010 11:53 AM, Heiko Schocher wrote:
>>>> So, the question is, is there a possibility to solve this problem?
>>>>
>>>> If there is no standard option, what would be with adding a
>>>> "scan_phy" file in
>>>>
>>>> /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40
>>>> (or better destination?)
>>>>
>>>> which with we could rescan a PHY with
>>>> "echo addr > /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40/sc=
an_phy"
>>>> (so there is no need for using of_find_node_by_path(), as we should
>>>> =A0have the associated device node here, and can step through the chil=
d
>>>> =A0nodes with "for_each_child_of_node(np, child)" and check if reg =3D=
=3D addr)
>>>>
>>>> or shouldn;t be at least, if the phy couldn;t be found when opening
>>>> the port, retrigger a scanning, if the phy now is accessible?
>>>
>>> One option would be to still register a phy_device for each phy
>>> described in the device tree, but defer binding a driver to each phy
>>> that doesn't respond. =A0Then at of_phy_find_device() time, if it
>>
>> Maybe I din;t get the trick, but the problem is, that
>> you can;t register a phy_device in drivers/of/of_mdio.c
>> of_mdiobus_register(), if the phy didn;t respond with the
>> phy_id ... and of_phy_find_device() is not (yet) used in fs_enet
>>
>>> matches with a phy_device that isn't bound to a driver yet, then
>>> re-trigger the binding operation. =A0At which point the phy id can be
>>> probed and the correct driver can be chosen. =A0If binding succeeds,
>>> then return the phy_device handle. =A0If not, then fail as it currently
>>> does.
>>
>> Wouldn;t it be good, just if we need a PHY (on calling fs_enet_open)
>> to look if there is one?
>>
>> Something like that (not tested):
>>
>> in drivers/net/fs_enet/fs_enet-main.c in fs_init_phy()
>> called from fs_enet_open():
>>
>> Do first:
>> phydev =3D =A0of_phy_find_device(fep->fpi->phy_node);
>>
>> Look if there is a driver (phy_dev->drv =3D=3D NULL ?)
>>
>> If not, call new function
>> of_mdiobus_register_phy(mii_bus, fep->fpi->phy_node)
>> see below patch for it.
>>
>> If this succeeds, all is OK, and we can use this phy,
>> else ethernet not work.
>>
>> !!just no idea, how to get mii_bus pointer ...
>>
>
> in my understanding it should be posssible to get this pointer via the pa=
rent of
> the device_node you got via the private data of the fs_enet:
> fep->fpi->phy_node->parent should point you to the device_node for the md=
io_bus.
Yes, this will give you the mdio bus node pointer.
> In the next step you should be able to get the pointer of of_device for t=
he
> mdio_bus:
> ofdevice* ofdev =3D to_of_device(fep->fpi->phy_node->parent);
of_device is just an alias for platform_device now, and not all mdio
busses will be instantiated by a platform device. This method won't
always work. What is really needed is the pointer to the mii_bus
structure. That can be obtained by looping over the members of the
mdio_bus_class and comparing the mii_bus->device.parent->of_node to
the parent node from above.
g.
^ permalink raw reply
* Re: powerpc, fs_enet: scanning PHY after Linux is up
From: Grant Likely @ 2010-10-06 16:52 UTC (permalink / raw)
To: hs; +Cc: linuxppc-dev, devicetree-discuss, Holger Brunck, Detlev Zundel,
netdev
In-Reply-To: <4CAC472F.5070001@denx.de>
On Wed, Oct 6, 2010 at 3:53 AM, Heiko Schocher <hs@denx.de> wrote:
> Hello Grant,
>
> Thanks for your answer!
>
> Grant Likely wrote:
>> On Mon, Oct 4, 2010 at 1:32 AM, Heiko Schocher <hs@denx.de> wrote:
>>> Hello all,
>>>
>>> we have on the mgcoge arch/powerpc/boot/dts/mgcoge.dts 3 fs_enet
>>> devices. The first is accessible on boot, and so get correct
>>> probed and works fine. For the other two fs_enet devices the PHYs
>>> are on startup in reset, and gets later, through userapplikations,
>>> out of reset ... so, on bootup, this 2 fs_enet devices could
>>> not detect the PHY in drivers/of/of_mdio.c of_mdiobus_register(),
>>> and if we want to use them later, we get for example:
>>>
>>> -bash-3.2# ifconfig eth2 172.31.31.33
>>> net eth2: Could not attach to PHY
>>> SIOCSIFFLAGS: No such device
>>>
>>> So the problem is, that we cannot rescan the PHYs, if they are
>>> accessible. Also we could not load the fs_enet driver as a module,
>>> because the first port is used fix.
>>>
>>> So, first question which comes in my mind, is:
>>>
>>> Is detecting the phy in drivers/of/of_mdio.c of_mdiobus_register()
>>> the right place, or should it not better be done, when really
>>> using the port?
>>>
>>> But we found another way to solve this issue:
>>>
>>> After the PHYs are out of reset, we just have to rescan the PHYs
>>> with (for example PHY with addr 1)
>>>
>>> err =3D mdiobus_scan(bus, 1);
>>>
>>> and
>>>
>>> of_find_node_by_path("/soc@f0000000/cpm@119c0/mdio@10d40/ethernet-phy@1=
");
>>> of_node_get(np);
>>> dev_archdata_set_node(&err->dev.archdata, np);
>>>
>>> but thats just a hack ...
>>
>> Yeah, that's a hack. =A0It really needs to be done via the of_mdio
>> mechanisms so that dt <--> phy_device linkages remain consistent.
>
> Yep, I know, thats the reason why I ask ;-)
>
>>> So, the question is, is there a possibility to solve this problem?
>>>
>>> If there is no standard option, what would be with adding a
>>> "scan_phy" file in
>>>
>>> /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40
>>> (or better destination?)
>>>
>>> which with we could rescan a PHY with
>>> "echo addr > /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40/sca=
n_phy"
>>> (so there is no need for using of_find_node_by_path(), as we should
>>> =A0have the associated device node here, and can step through the child
>>> =A0nodes with "for_each_child_of_node(np, child)" and check if reg =3D=
=3D addr)
>>>
>>> or shouldn;t be at least, if the phy couldn;t be found when opening
>>> the port, retrigger a scanning, if the phy now is accessible?
>>
>> One option would be to still register a phy_device for each phy
>> described in the device tree, but defer binding a driver to each phy
>> that doesn't respond. =A0Then at of_phy_find_device() time, if it
>
> Maybe I din;t get the trick, but the problem is, that
> you can;t register a phy_device in drivers/of/of_mdio.c
> of_mdiobus_register(), if the phy didn;t respond with the
> phy_id ... and of_phy_find_device() is not (yet) used in fs_enet
I'm suggesting modifying the phy layer so that it is possible to
register a phy_device that doesn't (yet) respond.
>> matches with a phy_device that isn't bound to a driver yet, then
>> re-trigger the binding operation. =A0At which point the phy id can be
>> probed and the correct driver can be chosen. =A0If binding succeeds,
>> then return the phy_device handle. =A0If not, then fail as it currently
>> does.
>
> Wouldn;t it be good, just if we need a PHY (on calling fs_enet_open)
> to look if there is one?
>
> Something like that (not tested):
>
> in drivers/net/fs_enet/fs_enet-main.c in fs_init_phy()
> called from fs_enet_open():
>
> Do first:
> phydev =3D =A0of_phy_find_device(fep->fpi->phy_node);
>
> Look if there is a driver (phy_dev->drv =3D=3D NULL ?)
>
> If not, call new function
> of_mdiobus_register_phy(mii_bus, fep->fpi->phy_node)
> see below patch for it.
>
> If this succeeds, all is OK, and we can use this phy,
> else ethernet not work.
I don't like this approach because it muddies the concept of which
device is actually responsible for managing the phys on the bus. Is
it managed by the mdio bus device or the Ethernet device? It also has
a potential race condition. Whereas triggering a late driver bind
will be safe.
Alternately, I'd also be okay with a common method to trigger a
reprobe of a particular phy from userspace, but I fear that would be a
significantly more complex solution.
>
> !!just no idea, how to get mii_bus pointer ...
You'd have to get the parent of the phy node, and then loop over all
the registered mdio busses looking for a bus that uses that node.
>
> here the patch for the new function of_mdiobus_register_phy():
>
> diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c
> index b474833..7afbb0b 100644
> --- a/drivers/of/of_mdio.c
> +++ b/drivers/of/of_mdio.c
> @@ -21,6 +21,51 @@
> =A0MODULE_AUTHOR("Grant Likely <grant.likely@secretlab.ca>");
> =A0MODULE_LICENSE("GPL");
>
> +int of_mdiobus_register_phy(struct mii_bus *mdio, struct device_node *ch=
ild)
> +{
> + =A0 =A0 =A0 struct phy_device *phy;
> + =A0 =A0 =A0 const __be32 *addr;
> + =A0 =A0 =A0 int len;
> + =A0 =A0 =A0 int rc;
> +
> + =A0 =A0 =A0 /* A PHY must have a reg property in the range [0-31] */
> + =A0 =A0 =A0 addr =3D of_get_property(child, "reg", &len);
> + =A0 =A0 =A0 if (!addr || len < sizeof(*addr) || *addr >=3D 32 || *addr =
< 0) {
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_err(&mdio->dev, "%s has invalid PHY add=
ress\n",
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 child->full_name);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 return -1;
> + =A0 =A0 =A0 }
> +
> + =A0 =A0 =A0 if (mdio->irq) {
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 mdio->irq[*addr] =3D irq_of_parse_and_map(c=
hild, 0);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (!mdio->irq[*addr])
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 mdio->irq[*addr] =3D PHY_PO=
LL;
> + =A0 =A0 =A0 }
> +
> + =A0 =A0 =A0 phy =3D get_phy_device(mdio, be32_to_cpup(addr));
> + =A0 =A0 =A0 if (!phy || IS_ERR(phy)) {
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_err(&mdio->dev, "error probing PHY at a=
ddress %i\n",
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 *addr);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 return -2;
> + =A0 =A0 =A0 }
> + =A0 =A0 =A0 phy_scan_fixups(phy);
> + =A0 =A0 =A0 /* Associate the OF node with the device structure so it
> + =A0 =A0 =A0 =A0* can be looked up later */
> + =A0 =A0 =A0 of_node_get(child);
> + =A0 =A0 =A0 dev_archdata_set_node(&phy->dev.archdata, child);
> +
> + =A0 =A0 =A0 /* All data is now stored in the phy struct; register it */
> + =A0 =A0 =A0 rc =3D phy_device_register(phy);
> + =A0 =A0 =A0 if (rc) {
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 phy_device_free(phy);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 of_node_put(child);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 return -3;
> + =A0 =A0 =A0 }
> +
> + =A0 =A0 =A0 dev_dbg(&mdio->dev, "registered phy %s at address %i\n",
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 child->name, *addr);
> +}
> +
> =A0/**
> =A0* of_mdiobus_register - Register mii_bus and create PHYs from the devi=
ce tree
> =A0* @mdio: pointer to mii_bus structure
> @@ -31,7 +76,6 @@ MODULE_LICENSE("GPL");
> =A0*/
> =A0int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np)
> =A0{
> - =A0 =A0 =A0 struct phy_device *phy;
> =A0 =A0 =A0 =A0struct device_node *child;
> =A0 =A0 =A0 =A0int rc, i;
>
> @@ -51,46 +95,7 @@ int of_mdiobus_register(struct mii_bus *mdio, struct d=
evice_node *np)
>
> =A0 =A0 =A0 =A0/* Loop over the child nodes and register a phy_device for=
each one */
> =A0 =A0 =A0 =A0for_each_child_of_node(np, child) {
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 const __be32 *addr;
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 int len;
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 /* A PHY must have a reg property in the ra=
nge [0-31] */
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 addr =3D of_get_property(child, "reg", &len=
);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (!addr || len < sizeof(*addr) || *addr >=
=3D 32 || *addr < 0) {
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_err(&mdio->dev, "%s has=
invalid PHY address\n",
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 child->full=
_name);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 continue;
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 }
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (mdio->irq) {
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 mdio->irq[*addr] =3D irq_of=
_parse_and_map(child, 0);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (!mdio->irq[*addr])
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 mdio->irq[*=
addr] =3D PHY_POLL;
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 }
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 phy =3D get_phy_device(mdio, be32_to_cpup(a=
ddr));
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (!phy || IS_ERR(phy)) {
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_err(&mdio->dev, "error =
probing PHY at address %i\n",
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 *addr);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 continue;
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 }
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 phy_scan_fixups(phy);
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 /* Associate the OF node with the device st=
ructure so it
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0* can be looked up later */
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 of_node_get(child);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_archdata_set_node(&phy->dev.archdata, c=
hild);
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 /* All data is now stored in the phy struct=
; register it */
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 rc =3D phy_device_register(phy);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 if (rc) {
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 phy_device_free(phy);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 of_node_put(child);
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 continue;
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 }
> -
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 dev_dbg(&mdio->dev, "registered phy %s at a=
ddress %i\n",
> - =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 =A0 child->name, *addr);
> + =A0 =A0 =A0 =A0 =A0 =A0 =A0 of_mdiobus_register_phy(mdio, child);
> =A0 =A0 =A0 =A0}
>
> =A0 =A0 =A0 =A0return 0;
>
> With this change, it would work on boot as actual (phy_device_register()
> will fail for the PHYs who don;t work when booting).
>
> Later, when opening the ethernet device, fs_init_phy, will look, if
> we have a valid phy with driver, if not we try to register it again.
> If this is successfull, we can use the device, if not we will fail,
> as now ... what do you think?
As mentioned above, it has the potential for some nasty confusion
about where exactly phy devices get registered, not to mention an
unlikely but potential race condition between the mdio bus and the
ethernet device trying to register the same phy since the MDIO bus
gets registered first, and then the bus loops over the phy nodes while
the bus is 'live'.
g.
^ permalink raw reply
* MPC8641D PCI Endpoint incoming interrupts?
From: david.hagood @ 2010-10-06 16:20 UTC (permalink / raw)
To: linuxppc-dev
I'm trying to use an MPC8641D as a PCIe endpoint device, and I'm trying to
work out how the host root complex CPU can interrupt the PPC core. It's
not very clear how to do all of this, and I'd like some help fitting the
pieces together. If there's a good how-to online I've yet to find it.
As I read it, on the host side, I'd do one of:
1) a write to the PPC's BAR0, offset 0x41400 (MSGR0) with some message value
2) a write to BAR0 offset 0x41600 (MSIR0) and set a bit within it.
3) a write to 0x41740 (MSIIR) to set a bit in MSIR0
So question #1 is "which of those should I use?" (or should I use
something else?)
Then, as I read it, I'd have to somehow convert the interrupt vector the
PIC uses into a virtual interrupt number suitable for request_irq. I've
seen mentions of irq_of_parse_and_map(), but I've not found a good
description of how to use it. Does anybody have any (non-null) pointers on
this?
Once I get to request_irq I'm on familiar ground.
^ permalink raw reply
* Linux on ppc440gp
From: Gorelik, Jacob (335F) @ 2010-10-06 14:35 UTC (permalink / raw)
To: linuxppc-dev@lists.ozlabs.org
In-Reply-To: <75413B9E73E7F04B96503BC6DAF2C5D19054A3F20E@ALTPHYEMBEVSP30.RES.AD.JPL>
[-- Attachment #1.1: Type: text/plain, Size: 260 bytes --]
Hello,
I am trying to run linux on a custom PPC440GP board; however, something goes wrong early in the boot process. I am not sure if the problem is in the device tree or in the memory map.
I've attached the log and the config files.
Thank you,
Jacob
[-- Attachment #1.2: Type: text/html, Size: 468 bytes --]
[-- Attachment #2: log.txt --]
[-- Type: application/octet-stream, Size: 2720 bytes --]
Using Starter440 machine description
Linux version 2.6.36-rc5 (jacob@jacob-laptop) (gcc version 4.2.2) #6 Tue Oct 5 15:42:56 PDT 2010
Found initrd at 0xcee3a000:0xcefff155
bootconsole [udbg0] enabled
setup_arch: bootmem
arch: exit
Zone PFN ranges:
DMA 0x00000000 -> 0x0000f000
Normal empty
Movable zone start PFN for each node
early_node_map[1] active PFN ranges
0: 0x00000000 -> 0x0000f000
MMU: Allocated 1088 bytes of context maps for 255 contexts
Built 1 zonelists in Zone order, mobility grouping on. Total pages: 60960
Kernel command line: root=/dev/ram rw ip=137.79.31.87:137.79.31.21:137.79.31.1:255.255.255.0:starter440:eth0:off panic=1 console=ttyS0,57600
PID hash table entries: 1024 (order: 0, 4096 bytes)
Dentry cache hash table entries: 32768 (order: 5, 131072 bytes)
Inode-cache hash table entries: 16384 (order: 4, 65536 bytes)
Memory: 238492k/245760k available (3060k kernel code, 7268k reserved, 100k data, 107k bss, 136k init)
Kernel virtual memory layout:
* 0xfffdf000..0xfffff000 : fixmap
* 0x0ee00000..0x0f000000 : consistent mem
* 0x0edfe000..0x0ee00000 : early ioremap
* 0xd1000000..0x0edfe000 : vmalloc & ioremap
SLUB: Genslabs=11, HWalign=32, Order=0-3, MinObjects=0, CPUs=1, Nodes=1
Hierarchical RCU implementation.
RCU-based detection of stalled CPUs is disabled.
Verbose stalled-CPUs detection is disabled.
NR_IRQS:512 nr_irqs:512
UIC0 (32 IRQ sources) at DCR 0xc0
UIC1 (32 IRQ sources) at DCR 0xd0
clocksource: timebase mult[d55555] shift[22] registered
Data machine check in kernel mode.
Oops: Machine check, sig: 7 [#1]
Starter440
last sysfs file:
Modules linked in:
NIP: c0009320 LR: c000c9d4 CTR: c00088e8
REGS: cee35f10 TRAP: 0202 Not tainted (2.6.36-rc5)
MSR: 00021000 <ME,CE> CR: 42f22f22 XER: 00000000
TASK = c0300350[0] 'swapper' THREAD: c0310000
GPR00: 08000000 c0311f00 c0300350 c0311f10 c0301110 00000000 00000077 c0303be8
GPR08: c0301110 c000c9d4 00021002 c0009320 c0300530 00000000 00000000 00000000
GPR16: 0ffe2864 0ffe7600 00000000 00000000 00000000 00000000 c0000020 00000001
GPR24: 00000000 00000000 00000e60 c03174d8 c0310000 c02f7878 c02f7668 c0316320
NIP [c0009320] timer_interrupt+0x0/0x118
LR [c000c9d4] ret_from_except+0x0/0x18
Call Trace:
[c0311f00] [c0050130] notifier_call_chain+0x60/0xac (unreliable)
--- Exception: 901 at start_kernel+0x194/0x2a4
LR = start_kernel+0x184/0x2a4
[c0311ff0] [c0000060] _start+0x60/0xbc
Instruction dump:
409efff0 7d6a5b78 7d495378 39400000 7d404378 39600000 3d00c030 39081110
7d295b78 90080064 91280060 4e800020 <9421fff0> 7c0802a6 bfc10008 90010014
---[ end trace 31fd0ba7d8756001 ]---
Kernel panic - not syncing: Attempted to kill the idle task!
Call Trace:
Rebooting in 1 seconds..
[-- Attachment #3: auto.conf --]
[-- Type: application/octet-stream, Size: 7502 bytes --]
#
# Automatically generated make config: don't edit
# Linux kernel version: 2.6.36-rc5
# Tue Oct 5 14:23:31 2010
#
CONFIG_CRC32=y
CONFIG_SECCOMP=y
CONFIG_FLATMEM_MANUAL=y
CONFIG_INOTIFY_USER=y
CONFIG_NETWORK_FILESYSTEMS=y
CONFIG_NET_ETHERNET=y
CONFIG_EXPERIMENTAL=y
CONFIG_INLINE_WRITE_UNLOCK_IRQ=y
CONFIG_SSB_POSSIBLE=y
CONFIG_CHELSIO_T4_DEPENDS=y
CONFIG_FSNOTIFY=y
CONFIG_ARCH_FLATMEM_ENABLE=y
CONFIG_DEFAULT_SECURITY_DAC=y
CONFIG_NETDEV_1000=y
CONFIG_AUDIT_ARCH=y
CONFIG_DEFAULT_TCP_CONG="cubic"
CONFIG_IBM_NEW_EMAC=y
CONFIG_UEVENT_HELPER_PATH="/sbin/hotplug"
CONFIG_WLAN=y
CONFIG_CONNECTOR=y
CONFIG_LEGACY_PTYS=y
CONFIG_SERIAL_8250=y
CONFIG_OF_DEVICE=y
CONFIG_SCHED_OMIT_FRAME_POINTER=y
CONFIG_BRANCH_PROFILE_NONE=y
CONFIG_VGA_ARB=y
CONFIG_FORCE_MAX_ZONEORDER=11
CONFIG_MTD_PARTITIONS=y
CONFIG_PRINTK=y
CONFIG_TIMERFD=y
CONFIG_MTD_CFI_I2=y
CONFIG_BOUNCE=y
CONFIG_SHMEM=y
CONFIG_MTD=y
CONFIG_DNOTIFY=y
CONFIG_ENABLE_MUST_CHECK=y
CONFIG_NR_IRQS=512
CONFIG_BOOKE=y
CONFIG_BLK_DEV_INITRD=y
CONFIG_CHELSIO_T3_DEPENDS=y
CONFIG_ZLIB_INFLATE=y
CONFIG_IP_PNP=y
CONFIG_STACKTRACE_SUPPORT=y
CONFIG_ARCH_HAS_WALK_MEMORY=y
CONFIG_LOCKD=y
CONFIG_JFFS2_FS=y
CONFIG_PPC_OF=y
CONFIG_MTD_CFI_UTIL=y
CONFIG_PPC_ADV_DEBUG_DVCS=2
CONFIG_STANDALONE=y
CONFIG_BLOCK=y
CONFIG_HAVE_IDE=y
CONFIG_INIT_ENV_ARG_LIMIT=32
CONFIG_ROOT_NFS=y
CONFIG_BUG=y
CONFIG_OF_IRQ=y
CONFIG_DEVKMEM=y
CONFIG_BOOTPARAM_HUNG_TASK_PANIC_VALUE=0
CONFIG_PPC_ADV_DEBUG_DAC_RANGE=y
CONFIG_DTC=y
CONFIG_SPLIT_PTLOCK_CPUS=4
CONFIG_WORD_SIZE=32
CONFIG_MFD_SUPPORT=y
CONFIG_ZONE_DMA=y
CONFIG_IBM_NEW_EMAC_RX_COPY_THRESHOLD=256
CONFIG_ENABLE_WARN_DEPRECATED=y
CONFIG_VGA_ARB_MAX_GPUS=16
CONFIG_ARCH_WANT_OPTIONAL_GPIOLIB=y
CONFIG_PPC_MMU_NOHASH=y
CONFIG_EXTRA_TARGETS=""
CONFIG_NETDEVICES=y
CONFIG_IOSCHED_DEADLINE=y
CONFIG_EVENTFD=y
CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config"
CONFIG_SERIAL_8250_CONSOLE=y
CONFIG_PROC_PAGE_MONITOR=y
CONFIG_SERIAL_8250_EXTENDED=y
CONFIG_MTD_OF_PARTS=y
CONFIG_SELECT_MEMORY_MODEL=y
CONFIG_MTD_CFI=y
CONFIG_JFFS2_FS_DEBUG=0
CONFIG_HAVE_DYNAMIC_FTRACE=y
CONFIG_MAGIC_SYSRQ=y
CONFIG_SPARSE_IRQ=y
CONFIG_DEFAULT_CFQ=y
CONFIG_MAX_ACTIVE_REGIONS=32
CONFIG_DEBUG_BUGVERBOSE=y
CONFIG_GENERIC_CLOCKEVENTS=y
CONFIG_IOSCHED_CFQ=y
CONFIG_GENERIC_FIND_LAST_BIT=y
CONFIG_RWSEM_XCHGADD_ALGORITHM=y
CONFIG_PPC_UDBG_16550=y
CONFIG_TRACE_IRQFLAGS_SUPPORT=y
CONFIG_DETECT_HUNG_TASK=y
CONFIG_RD_GZIP=y
CONFIG_HAVE_REGS_AND_STACK_ACCESS_API=y
CONFIG_TREE_RCU=y
CONFIG_LBDAF=y
CONFIG_KERNEL_START=0xc0000000
CONFIG_PPC=y
CONFIG_BINFMT_ELF=y
CONFIG_HOTPLUG=y
CONFIG_SLABINFO=y
CONFIG_IBM_NEW_EMAC_RX_SKB_HEADROOM=0
CONFIG_JFFS2_FS_WRITEBUFFER=y
CONFIG_440GP=y
CONFIG_SERIAL_OF_PLATFORM=y
CONFIG_BROKEN_ON_SMP=y
CONFIG_TMPFS=y
CONFIG_ANON_INODES=y
CONFIG_FUTEX=y
CONFIG_IP_PNP_DHCP=y
CONFIG_PPC_ADV_DEBUG_IACS=4
CONFIG_SERIAL_CORE_CONSOLE=y
CONFIG_SLUB_DEBUG=y
CONFIG_SYSVIPC=y
CONFIG_MODULES=y
CONFIG_ARCH_HIBERNATION_POSSIBLE=y
CONFIG_UNIX=y
CONFIG_NETDEV_10000=y
CONFIG_NFS_FS=y
CONFIG_IBM_NEW_EMAC_POLL_WEIGHT=32
CONFIG_MISC_DEVICES=y
CONFIG_ARCH_SUPPORTS_MSI=y
CONFIG_MTD_CFI_I1=y
CONFIG_NFS_COMMON=y
CONFIG_PPC_WERROR=y
CONFIG_LOG_BUF_SHIFT=14
CONFIG_EXTRA_FIRMWARE=""
CONFIG_PROC_EVENTS=y
CONFIG_VIRT_TO_BUS=y
CONFIG_SERIAL_8250_RUNTIME_UARTS=4
CONFIG_HAVE_LATENCYTOP_SUPPORT=y
CONFIG_HAVE_FUNCTION_TRACER=y
CONFIG_IBM_NEW_EMAC_TXB=64
CONFIG_SLUB=y
CONFIG_JFFS2_ZLIB=y
CONFIG_VM_EVENT_COUNTERS=y
CONFIG_DEBUG_FS=y
CONFIG_BASE_FULL=y
CONFIG_ZLIB_DEFLATE=y
CONFIG_SUNRPC=y
CONFIG_FW_LOADER=y
CONFIG_KALLSYMS=y
CONFIG_PCI=y
CONFIG_GENERIC_ATOMIC64=y
CONFIG_PPC_INDIRECT_PCI=y
CONFIG_MATH_EMULATION=y
CONFIG_PCI_QUIRKS=y
CONFIG_SIGNALFD=y
CONFIG_LOCKD_V4=y
CONFIG_HAS_IOMEM=y
CONFIG_PROC_DEVICETREE=y
CONFIG_PPC_PCI_CHOICE=y
CONFIG_PROC_KCORE=y
CONFIG_MTD_MAP_BANK_WIDTH_1=y
CONFIG_CONSTRUCTORS=y
CONFIG_EPOLL=y
CONFIG_PPC_ADV_DEBUG_DACS=2
CONFIG_NET=y
CONFIG_EXT2_FS=y
CONFIG_MTD_GEN_PROBE=y
CONFIG_PACKET=y
CONFIG_NFS_V3=y
CONFIG_INET=y
CONFIG_IP_PNP_BOOTP=y
CONFIG_PREVENT_FIRMWARE_BUILD=y
CONFIG_PCI_DOMAINS=y
CONFIG_IRQ_PER_CPU=y
CONFIG_HAVE_KPROBES=y
CONFIG_PPC32=y
CONFIG_IBM_NEW_EMAC_RXB=128
CONFIG_BLK_DEV_RAM_COUNT=16
CONFIG_LOCKDEP_SUPPORT=y
CONFIG_POSIX_MQUEUE=y
CONFIG_GENERIC_HARDIRQS_NO__DO_IRQ=y
CONFIG_USB_ARCH_HAS_EHCI=y
CONFIG_MTD_BLKDEVS=y
CONFIG_SYSCTL_SYSCALL=y
CONFIG_NEED_DMA_MAP_STATE=y
CONFIG_GENERIC_FIND_NEXT_BIT=y
CONFIG_PAGE_OFFSET=0xc0000000
CONFIG_PREEMPT_NONE=y
CONFIG_KALLSYMS_ALL=y
CONFIG_GENERIC_BUG=y
CONFIG_HAVE_FTRACE_MCOUNT_RECORD=y
CONFIG_INET_TCP_DIAG=y
CONFIG_IOSCHED_NOOP=y
CONFIG_PTE_64BIT=y
CONFIG_HAVE_IOREMAP_PROT=y
CONFIG_DEBUG_KERNEL=y
CONFIG_COMPAT_BRK=y
CONFIG_LOCALVERSION=""
CONFIG_SCHED_DEBUG=y
CONFIG_DEFAULT_MMAP_MIN_ADDR=4096
CONFIG_HAVE_DMA_API_DEBUG=y
CONFIG_USB_ARCH_HAS_HCD=y
CONFIG_SCSI_MOD=y
CONFIG_SERIAL_CORE=y
CONFIG_EMBEDDED=y
CONFIG_ARCH_PHYS_ADDR_T_64BIT=y
CONFIG_HAVE_KRETPROBES=y
CONFIG_CHELSIO_T4VF_DEPENDS=y
CONFIG_INLINE_READ_UNLOCK=y
CONFIG_HAS_DMA=y
CONFIG_LOWMEM_SIZE=0x0f000000
CONFIG_LOCALVERSION_AUTO=y
CONFIG_JFFS2_RTIME=y
CONFIG_MISC_FILESYSTEMS=y
CONFIG_FTRACE=y
CONFIG_OF_DYNAMIC=y
CONFIG_INLINE_READ_UNLOCK_IRQ=y
CONFIG_NEED_SG_DMA_LENGTH=y
CONFIG_PPC_DCR_NATIVE=y
CONFIG_PHYS_64BIT=y
CONFIG_TASK_SIZE=0x00200000
CONFIG_RT_MUTEXES=y
CONFIG_PCI_SYSCALL=y
CONFIG_WIRELESS=y
CONFIG_HZ_250=y
CONFIG_ARCH_POPULATES_NODE_MAP=y
CONFIG_FRAME_WARN=1024
CONFIG_GENERIC_HWEIGHT=y
CONFIG_INITRAMFS_SOURCE=""
CONFIG_INLINE_SPIN_UNLOCK=y
CONFIG_ARCH_SUPPORTS_DEBUG_PAGEALLOC=y
CONFIG_HAS_IOPORT=y
CONFIG_HZ=250
CONFIG_SERIAL_8250_SHARE_IRQ=y
CONFIG_INLINE_SPIN_UNLOCK_IRQ=y
CONFIG_SERIAL_8250_NR_UARTS=4
CONFIG_DEFAULT_IOSCHED="cfq"
CONFIG_NLATTR=y
CONFIG_TCP_CONG_CUBIC=y
CONFIG_FIRMWARE_IN_KERNEL=y
CONFIG_IBM_NEW_EMAC_ZMII=y
CONFIG_SYSFS=y
CONFIG_MTD_PHYSMAP_OF=y
CONFIG_MSDOS_PARTITION=y
CONFIG_HAVE_OPROFILE=y
CONFIG_THERMAL=y
CONFIG_4xx=y
CONFIG_PPC_MMU_NOHASH_32=y
CONFIG_HAVE_ARCH_KGDB=y
CONFIG_IP_FIB_HASH=y
CONFIG_USB_ARCH_HAS_OHCI=y
CONFIG_ZONE_DMA_FLAG=1
CONFIG_CONSISTENT_SIZE=0x00200000
CONFIG_STARTER440=y
CONFIG_LEGACY_PTY_COUNT=256
CONFIG_MTD_MAP_BANK_WIDTH_2=y
CONFIG_GENERIC_CMOS_UPDATE=y
CONFIG_DEFAULT_SECURITY=""
CONFIG_HAVE_DMA_ATTRS=y
CONFIG_EARLY_PRINTK=y
CONFIG_PPC_ADV_DEBUG_REGS=y
CONFIG_HAVE_FUNCTION_GRAPH_TRACER=y
CONFIG_BASE_SMALL=0
CONFIG_PPC_4K_PAGES=y
CONFIG_PROC_FS=y
CONFIG_MTD_BLOCK=y
CONFIG_FLATMEM=y
CONFIG_PAGEFLAGS_EXTENDED=y
CONFIG_SYSCTL=y
CONFIG_PHYS_ADDR_T_64BIT=y
CONFIG_HAVE_ARCH_TRACEHOOK=y
CONFIG_HAVE_PERF_EVENTS=y
CONFIG_CRAMFS=y
CONFIG_PPC_DCR=y
CONFIG_NOT_COHERENT_CACHE=y
CONFIG_BLK_DEV=y
CONFIG_OF_FLATTREE=y
CONFIG_TRACING_SUPPORT=y
CONFIG_UNIX98_PTYS=y
CONFIG_4xx_SOC=y
CONFIG_ARCH_MAY_HAVE_PC_FDC=y
CONFIG_INET_DIAG=y
CONFIG_ELF_CORE=y
CONFIG_MTD_JEDECPROBE=y
CONFIG_USB_SUPPORT=y
CONFIG_MTD_CHAR=y
CONFIG_FLAT_NODE_MEM_MAP=y
CONFIG_BLK_DEV_RAM=y
CONFIG_POSIX_MQUEUE_SYSCTL=y
CONFIG_ARCH_HAS_ILOG2_U32=y
CONFIG_GENERIC_CLOCKEVENTS_BUILD=y
CONFIG_MTD_CFI_AMDSTD=y
CONFIG_SYSVIPC_SYSCTL=y
CONFIG_OF_ADDRESS=y
CONFIG_DECOMPRESS_GZIP=y
CONFIG_CROSS_COMPILE=""
CONFIG_44x=y
CONFIG_PRINT_STACK_DEPTH=64
CONFIG_SWAP=y
CONFIG_MODULE_UNLOAD=y
CONFIG_RCU_FANOUT=32
CONFIG_BITREVERSE=y
CONFIG_DEVPORT=y
CONFIG_STDBINUTILS=y
CONFIG_BLK_DEV_RAM_SIZE=35000
CONFIG_FILE_LOCKING=y
CONFIG_AIO=y
CONFIG_OF=y
CONFIG_GENERIC_TIME_VSYSCALL=y
CONFIG_GENERIC_HARDIRQS=y
CONFIG_SYSCTL_SYSCALL_CHECK=y
CONFIG_MTD_MAP_BANK_WIDTH_4=y
CONFIG_PHYSICAL_START=0x00000000
CONFIG_HAVE_MEMBLOCK=y
CONFIG_HAVE_EFFICIENT_UNALIGNED_ACCESS=y
CONFIG_KALLSYMS_EXTRA_PASS=y
CONFIG_PROC_SYSCTL=y
CONFIG_MMU=y
CONFIG_INLINE_WRITE_UNLOCK=y
[-- Attachment #4: starter440.dts --]
[-- Type: application/octet-stream, Size: 7845 bytes --]
/*
* Device Tree Source for BRE Starter440
*
* Copyright (c) 2006, 2007 IBM Corp.
* Josh Boyer <jwboyer@linux.vnet.ibm.com>, David Gibson <dwg@au1.ibm.com>
*
* 2010 JPL
*
* 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.
*/
/dts-v1/;
/ {
#address-cells = <2>;
#size-cells = <1>;
model = "ibm,starter440";
compatible = "ibm,starter440";
dcr-parent = <&{/cpus/cpu@0}>;
aliases {
ethernet0 = &EMAC0;
ethernet1 = &EMAC1;
serial0 = &UART0;
serial1 = &UART1;
};
cpus {
#address-cells = <1>;
#size-cells = <0>;
cpu@0 {
device_type = "cpu";
model = "PowerPC,440GP";
reg = <0x00000000>;
clock-frequency = <0>; // Filled in by zImage
timebase-frequency = <0>; // Filled in by zImage
i-cache-line-size = <32>;
d-cache-line-size = <32>;
i-cache-size = <32768>; /* 32 kB */
d-cache-size = <32768>; /* 32 kB */
dcr-controller;
dcr-access-method = "native";
};
};
memory {
device_type = "memory";
reg = <0x00000000 0x00000000 0x00000000>; // Filled in by zImage
};
UIC0: interrupt-controller0 {
compatible = "ibm,uic-440gp", "ibm,uic";
interrupt-controller;
cell-index = <0>;
dcr-reg = <0x0c0 0x009>;
#address-cells = <0>;
#size-cells = <0>;
#interrupt-cells = <2>;
};
UIC1: interrupt-controller1 {
compatible = "ibm,uic-440gp", "ibm,uic";
interrupt-controller;
cell-index = <1>;
dcr-reg = <0x0d0 0x009>;
#address-cells = <0>;
#size-cells = <0>;
#interrupt-cells = <2>;
interrupts = <0x1e 0x4 0x1f 0x4>; /* cascade */
interrupt-parent = <&UIC0>;
};
CPC0: cpc {
compatible = "ibm,cpc-440gp";
dcr-reg = <0x0b0 0x003 0x0e0 0x010>;
// FIXME: anything else?
};
plb {
compatible = "ibm,plb-440gp", "ibm,plb4";
#address-cells = <2>;
#size-cells = <1>;
ranges;
clock-frequency = <0>; // Filled in by zImage
SDRAM0: memory-controller {
compatible = "ibm,sdram-440gp";
dcr-reg = <0x010 0x002>;
// FIXME: anything else?
};
SRAM0: sram {
compatible = "ibm,sram-440gp";
dcr-reg = <0x020 0x008 0x00a 0x001>;
};
DMA0: dma {
// FIXME: ???
compatible = "ibm,dma-440gp";
dcr-reg = <0x100 0x027>;
};
MAL0: mcmal {
compatible = "ibm,mcmal-440gp", "ibm,mcmal";
dcr-reg = <0x180 0x062>;
num-tx-chans = <4>;
num-rx-chans = <4>;
interrupt-parent = <&MAL0>;
interrupts = <0x0 0x1 0x2 0x3 0x4>;
#interrupt-cells = <1>;
#address-cells = <0>;
#size-cells = <0>;
interrupt-map = </*TXEOB*/ 0x0 &UIC0 0xa 0x4
/*RXEOB*/ 0x1 &UIC0 0xb 0x4
/*SERR*/ 0x2 &UIC1 0x0 0x4
/*TXDE*/ 0x3 &UIC1 0x1 0x4
/*RXDE*/ 0x4 &UIC1 0x2 0x4>;
interrupt-map-mask = <0xffffffff>;
};
OPB0: opb {
compatible = "ibm,opb-440gp", "ibm,opb";
#address-cells = <1>;
#size-cells = <1>;
/* Wish there was a nicer way of specifying a full 32-bit
range */
ranges = <0x00000000 0x00000001 0x00000000 0x80000000
0x80000000 0x00000001 0x80000000 0x80000000>;
dcr-reg = <0x090 0x00b>;
interrupt-parent = <&UIC1>;
interrupts = <0x7 0x4>;
clock-frequency = <0>; // Filled in by zImage
EBC0: ebc {
compatible = "ibm,ebc-440gp", "ibm,ebc";
dcr-reg = <0x012 0x002>;
#address-cells = <2>;
#size-cells = <1>;
clock-frequency = <0>; // Filled in by zImage
// ranges property is supplied by zImage
// based on firmware's configuration of the
// EBC bridge
interrupts = <0x5 0x4>;
interrupt-parent = <&UIC1>;
flash@0,0 {
compatible = "jedec-flash";
bank-width = <1>;
reg = <0x00000000 0x00000000 0x00400000>;
#address-cells = <1>;
#size-cells = <1>;
partition@0 {
label = "bank1";
reg = <0x00000000 0x00200000>;
};
partition@200000 {
label = "bank2";
reg = <0x00200000 0x00200000>;
};
};
ir@1,0 {
reg = <0x00000001 0x00000000 0x00000010>;
};
};
UART0: serial@40000200 {
device_type = "serial";
compatible = "ns16550";
reg = <0x40000200 0x00000008>;
virtual-reg = <0xe0000200>;
clock-frequency = <0x388394>;
current-speed = <0xe100>;
interrupt-parent = <&UIC0>;
interrupts = <0x0 0x4>;
};
UART1: serial@40000300 {
device_type = "serial";
compatible = "ns16550";
reg = <0x40000300 0x00000008>;
virtual-reg = <0xe0000300>;
clock-frequency = <0x388394>;
current-speed = <0xe100>;
interrupt-parent = <&UIC0>;
interrupts = <0x1 0x4>;
};
IIC0: i2c@40000400 {
/* FIXME */
compatible = "ibm,iic-440gp", "ibm,iic";
reg = <0x40000400 0x00000014>;
interrupt-parent = <&UIC0>;
interrupts = <0x2 0x4>;
};
IIC1: i2c@40000500 {
/* FIXME */
compatible = "ibm,iic-440gp", "ibm,iic";
reg = <0x40000500 0x00000014>;
interrupt-parent = <&UIC0>;
interrupts = <0x3 0x4>;
};
GPIO0: gpio@40000700 {
/* FIXME */
compatible = "ibm,gpio-440gp";
reg = <0x40000700 0x00000020>;
};
ZMII0: emac-zmii@40000780 {
compatible = "ibm,zmii-440gp", "ibm,zmii";
reg = <0x40000780 0x0000000c>;
};
EMAC0: ethernet@40000800 {
device_type = "network";
compatible = "ibm,emac-440gp", "ibm,emac";
interrupt-parent = <&UIC1>;
interrupts = <0x1c 0x4 0x1d 0x4>;
reg = <0x40000800 0x00000070>;
local-mac-address = [000000000000]; // Filled in by zImage
mal-device = <&MAL0>;
mal-tx-channel = <0 1>;
mal-rx-channel = <0>;
cell-index = <0>;
max-frame-size = <1500>;
rx-fifo-size = <4096>;
tx-fifo-size = <2048>;
phy-mode = "rmii";
phy-map = <0x00000001>;
zmii-device = <&ZMII0>;
zmii-channel = <0>;
};
EMAC1: ethernet@40000900 {
device_type = "network";
compatible = "ibm,emac-440gp", "ibm,emac";
interrupt-parent = <&UIC1>;
interrupts = <0x1e 0x4 0x1f 0x4>;
reg = <0x40000900 0x00000070>;
local-mac-address = [000000000000]; // Filled in by zImage
mal-device = <&MAL0>;
mal-tx-channel = <2 3>;
mal-rx-channel = <1>;
cell-index = <1>;
max-frame-size = <1500>;
rx-fifo-size = <4096>;
tx-fifo-size = <2048>;
phy-mode = "rmii";
phy-map = <0x00000001>;
zmii-device = <&ZMII0>;
zmii-channel = <1>;
};
GPT0: gpt@40000a00 {
/* FIXME */
reg = <0x40000a00 0x000000d4>;
interrupt-parent = <&UIC0>;
interrupts = <0x12 0x4 0x13 0x4 0x14 0x4 0x15 0x4 0x16 0x4>;
};
};
PCIX0: pci@20ec00000 {
device_type = "pci";
#interrupt-cells = <1>;
#size-cells = <2>;
#address-cells = <3>;
compatible = "ibm,plb440gp-pcix", "ibm,plb-pcix";
primary;
reg = <0x00000002 0x0ec00000 0x00000008 /* Config space access */
0x00000000 0x00000000 0x00000000 /* no IACK cycles */
0x00000002 0x0ed00000 0x00000004 /* Special cycles */
0x00000002 0x0ec80000 0x000000f0 /* Internal registers */
0x00000002 0x0ec80100 0x000000fc>; /* Internal messaging registers */
/* Outbound ranges, one memory and one IO,
* later cannot be changed
*/
ranges = <0x02000000 0x00000000 0x80000000 0x00000003 0x80000000 0x00000000 0x80000000
0x01000000 0x00000000 0x00000000 0x00000002 0x08000000 0x00000000 0x00010000>;
/* Inbound 2GB range starting at 0 */
dma-ranges = <0x42000000 0x0 0x0 0x0 0x0 0x0 0x80000000>;
/* Ebony has all 4 IRQ pins tied together per slot */
interrupt-map-mask = <0xf800 0x0 0x0 0x0>;
interrupt-map = <
/* IDSEL 1 */
0x800 0x0 0x0 0x0 &UIC0 0x17 0x8
/* IDSEL 2 */
0x1000 0x0 0x0 0x0 &UIC0 0x18 0x8
/* IDSEL 3 */
0x1800 0x0 0x0 0x0 &UIC0 0x19 0x8
/* IDSEL 4 */
0x2000 0x0 0x0 0x0 &UIC0 0x1a 0x8
>;
};
};
chosen {
linux,stdout-path = "/plb/opb/serial@40000200";
};
};
^ permalink raw reply
* Re: powerpc, fs_enet: scanning PHY after Linux is up
From: Heiko Schocher @ 2010-10-06 9:53 UTC (permalink / raw)
To: Grant Likely
Cc: linuxppc-dev, devicetree-discuss, Holger Brunck, Detlev Zundel,
netdev
In-Reply-To: <AANLkTinSersREjDnvg=8Gvpa6YmLuzgF1H8eEXRyCpW0@mail.gmail.com>
Hello Grant,
Thanks for your answer!
Grant Likely wrote:
> On Mon, Oct 4, 2010 at 1:32 AM, Heiko Schocher <hs@denx.de> wrote:
>> Hello all,
>>
>> we have on the mgcoge arch/powerpc/boot/dts/mgcoge.dts 3 fs_enet
>> devices. The first is accessible on boot, and so get correct
>> probed and works fine. For the other two fs_enet devices the PHYs
>> are on startup in reset, and gets later, through userapplikations,
>> out of reset ... so, on bootup, this 2 fs_enet devices could
>> not detect the PHY in drivers/of/of_mdio.c of_mdiobus_register(),
>> and if we want to use them later, we get for example:
>>
>> -bash-3.2# ifconfig eth2 172.31.31.33
>> net eth2: Could not attach to PHY
>> SIOCSIFFLAGS: No such device
>>
>> So the problem is, that we cannot rescan the PHYs, if they are
>> accessible. Also we could not load the fs_enet driver as a module,
>> because the first port is used fix.
>>
>> So, first question which comes in my mind, is:
>>
>> Is detecting the phy in drivers/of/of_mdio.c of_mdiobus_register()
>> the right place, or should it not better be done, when really
>> using the port?
>>
>> But we found another way to solve this issue:
>>
>> After the PHYs are out of reset, we just have to rescan the PHYs
>> with (for example PHY with addr 1)
>>
>> err = mdiobus_scan(bus, 1);
>>
>> and
>>
>> of_find_node_by_path("/soc@f0000000/cpm@119c0/mdio@10d40/ethernet-phy@1");
>> of_node_get(np);
>> dev_archdata_set_node(&err->dev.archdata, np);
>>
>> but thats just a hack ...
>
> Yeah, that's a hack. It really needs to be done via the of_mdio
> mechanisms so that dt <--> phy_device linkages remain consistent.
Yep, I know, thats the reason why I ask ;-)
>> So, the question is, is there a possibility to solve this problem?
>>
>> If there is no standard option, what would be with adding a
>> "scan_phy" file in
>>
>> /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40
>> (or better destination?)
>>
>> which with we could rescan a PHY with
>> "echo addr > /proc/device-tree/soc\@f0000000/cpm\@119c0/mdio\@10d40/scan_phy"
>> (so there is no need for using of_find_node_by_path(), as we should
>> have the associated device node here, and can step through the child
>> nodes with "for_each_child_of_node(np, child)" and check if reg == addr)
>>
>> or shouldn;t be at least, if the phy couldn;t be found when opening
>> the port, retrigger a scanning, if the phy now is accessible?
>
> One option would be to still register a phy_device for each phy
> described in the device tree, but defer binding a driver to each phy
> that doesn't respond. Then at of_phy_find_device() time, if it
Maybe I din;t get the trick, but the problem is, that
you can;t register a phy_device in drivers/of/of_mdio.c
of_mdiobus_register(), if the phy didn;t respond with the
phy_id ... and of_phy_find_device() is not (yet) used in fs_enet
> matches with a phy_device that isn't bound to a driver yet, then
> re-trigger the binding operation. At which point the phy id can be
> probed and the correct driver can be chosen. If binding succeeds,
> then return the phy_device handle. If not, then fail as it currently
> does.
Wouldn;t it be good, just if we need a PHY (on calling fs_enet_open)
to look if there is one?
Something like that (not tested):
in drivers/net/fs_enet/fs_enet-main.c in fs_init_phy()
called from fs_enet_open():
Do first:
phydev = of_phy_find_device(fep->fpi->phy_node);
Look if there is a driver (phy_dev->drv == NULL ?)
If not, call new function
of_mdiobus_register_phy(mii_bus, fep->fpi->phy_node)
see below patch for it.
If this succeeds, all is OK, and we can use this phy,
else ethernet not work.
!!just no idea, how to get mii_bus pointer ...
here the patch for the new function of_mdiobus_register_phy():
diff --git a/drivers/of/of_mdio.c b/drivers/of/of_mdio.c
index b474833..7afbb0b 100644
--- a/drivers/of/of_mdio.c
+++ b/drivers/of/of_mdio.c
@@ -21,6 +21,51 @@
MODULE_AUTHOR("Grant Likely <grant.likely@secretlab.ca>");
MODULE_LICENSE("GPL");
+int of_mdiobus_register_phy(struct mii_bus *mdio, struct device_node *child)
+{
+ struct phy_device *phy;
+ const __be32 *addr;
+ int len;
+ int rc;
+
+ /* A PHY must have a reg property in the range [0-31] */
+ addr = of_get_property(child, "reg", &len);
+ if (!addr || len < sizeof(*addr) || *addr >= 32 || *addr < 0) {
+ dev_err(&mdio->dev, "%s has invalid PHY address\n",
+ child->full_name);
+ return -1;
+ }
+
+ if (mdio->irq) {
+ mdio->irq[*addr] = irq_of_parse_and_map(child, 0);
+ if (!mdio->irq[*addr])
+ mdio->irq[*addr] = PHY_POLL;
+ }
+
+ phy = get_phy_device(mdio, be32_to_cpup(addr));
+ if (!phy || IS_ERR(phy)) {
+ dev_err(&mdio->dev, "error probing PHY at address %i\n",
+ *addr);
+ return -2;
+ }
+ phy_scan_fixups(phy);
+ /* Associate the OF node with the device structure so it
+ * can be looked up later */
+ of_node_get(child);
+ dev_archdata_set_node(&phy->dev.archdata, child);
+
+ /* All data is now stored in the phy struct; register it */
+ rc = phy_device_register(phy);
+ if (rc) {
+ phy_device_free(phy);
+ of_node_put(child);
+ return -3;
+ }
+
+ dev_dbg(&mdio->dev, "registered phy %s at address %i\n",
+ child->name, *addr);
+}
+
/**
* of_mdiobus_register - Register mii_bus and create PHYs from the device tree
* @mdio: pointer to mii_bus structure
@@ -31,7 +76,6 @@ MODULE_LICENSE("GPL");
*/
int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np)
{
- struct phy_device *phy;
struct device_node *child;
int rc, i;
@@ -51,46 +95,7 @@ int of_mdiobus_register(struct mii_bus *mdio, struct device_node *np)
/* Loop over the child nodes and register a phy_device for each one */
for_each_child_of_node(np, child) {
- const __be32 *addr;
- int len;
-
- /* A PHY must have a reg property in the range [0-31] */
- addr = of_get_property(child, "reg", &len);
- if (!addr || len < sizeof(*addr) || *addr >= 32 || *addr < 0) {
- dev_err(&mdio->dev, "%s has invalid PHY address\n",
- child->full_name);
- continue;
- }
-
- if (mdio->irq) {
- mdio->irq[*addr] = irq_of_parse_and_map(child, 0);
- if (!mdio->irq[*addr])
- mdio->irq[*addr] = PHY_POLL;
- }
-
- phy = get_phy_device(mdio, be32_to_cpup(addr));
- if (!phy || IS_ERR(phy)) {
- dev_err(&mdio->dev, "error probing PHY at address %i\n",
- *addr);
- continue;
- }
- phy_scan_fixups(phy);
-
- /* Associate the OF node with the device structure so it
- * can be looked up later */
- of_node_get(child);
- dev_archdata_set_node(&phy->dev.archdata, child);
-
- /* All data is now stored in the phy struct; register it */
- rc = phy_device_register(phy);
- if (rc) {
- phy_device_free(phy);
- of_node_put(child);
- continue;
- }
-
- dev_dbg(&mdio->dev, "registered phy %s at address %i\n",
- child->name, *addr);
+ of_mdiobus_register_phy(mdio, child);
}
return 0;
With this change, it would work on boot as actual (phy_device_register()
will fail for the PHYs who don;t work when booting).
Later, when opening the ethernet device, fs_init_phy, will look, if
we have a valid phy with driver, if not we try to register it again.
If this is successfull, we can use the device, if not we will fail,
as now ... what do you think?
bye,
Heiko
--
DENX Software Engineering GmbH, MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
^ permalink raw reply related
* Re: [PATCH 05/18] powerpc: Wire up 44x little endian boot for remaining 44x targets
From: Sean MacLennan @ 2010-10-06 2:10 UTC (permalink / raw)
To: Josh Boyer; +Cc: linuxppc-dev, paulus, Ian Munsie, linux-kernel
In-Reply-To: <AANLkTimNeWEo5P0wXzszBiSYdh81=uhARA8KZPr7rcPf@mail.gmail.com>
On Tue, 5 Oct 2010 21:55:35 -0400
Josh Boyer <jwboyer@gmail.com> wrote:
> Well, Warp and Sam440EP are production boards for actual companies.
> The rest are all just eval boards. I don't know if the board
> maintainers care either way, I was just using them as examples of
> cases where someone might.
In the warp case, I basically don't care. I know LE would break some of
our telephony drivers since we assume PPC is BE. But on the other hand,
realistically, it will never get turned on by customers anyway.
We have to provide our own .config anyway, so it really don't hurt us
as long as it doesn't break BE support.
Cheers,
Sean
^ permalink raw reply
* Re: [PATCH 05/18] powerpc: Wire up 44x little endian boot for remaining 44x targets
From: Josh Boyer @ 2010-10-06 1:55 UTC (permalink / raw)
To: Ian Munsie; +Cc: paulus, linuxppc-dev, linux-kernel
In-Reply-To: <1286327715-sup-584@au1.ibm.com>
On Tue, Oct 5, 2010 at 9:28 PM, Ian Munsie <imunsie@au1.ibm.com> wrote:
> Excerpts from Josh Boyer's message of Fri Oct 01 21:27:37 +1000 2010:
>> > From: Ian Munsie <imunsie@au1.ibm.com>
>> >
>> > I haven't tested booting a little endian kernel on any of these target=
s,
>> > but they all claim to be 44x so my little endian trampoline should wor=
k
>> > on all of them, so wire it up on:
>> >
>> > bamboo
>> > katmai
>> > kilauea
>> > rainer
>> > sam440ep
>> > sequoia
>> > warp
>> > yosemite
>> > ebony
>>
>> I see no reason to do this at all. =A0If you haven't tested them and
>> there is no demand, there's no reason to wire them up. =A0Some might
>> actively want to disallow LE mode anyway, like the Warp or Sam440EP.
>
> I wasn't aware that the Warp and Sam440EP disallowed LE mode - I'll
> definitely unwire them and move the ARCH_SUPPORTS_LITTLE_ENDIAN to just
> the sub-arch's that support it.
Well, Warp and Sam440EP are production boards for actual companies.
The rest are all just eval boards. I don't know if the board
maintainers care either way, I was just using them as examples of
cases where someone might.
> As for the other boards, I would like to wire them up if they are able
> to support LE mode - If anyone has one handy I would love to hear if
> they are able to begin booting a LE kernel with these patches, or when &
> how they fail.
I'd avoid anything with an FPU until that gets tested. So no bamboo,
sequoia, canyonlands, etc.
I noticed that canyonlands isn't even covered. I'm guessing that's
because we don't need to create a wrapper for it because U-Boot does
direct loading of vmlinux and the DTB itself. Has anyone done any
work with getting U-Boot to work in LE mode or at least load LE
vmlinux images? The majority of new boards are going to be using
U-Boot and it's ability to load the DTB/FDT, so that would be
something that needs addressing.
josh
^ permalink raw reply
* Re: [PATCH 05/18] powerpc: Wire up 44x little endian boot for remaining 44x targets
From: Ian Munsie @ 2010-10-06 1:28 UTC (permalink / raw)
To: Josh Boyer; +Cc: paulus, linuxppc-dev, linux-kernel
In-Reply-To: <AANLkTins34TrEWj618_4XBRwGGFqRSehwWEp7jBubvsu@mail.gmail.com>
Excerpts from Josh Boyer's message of Fri Oct 01 21:27:37 +1000 2010:
> > From: Ian Munsie <imunsie@au1.ibm.com>
> >
> > I haven't tested booting a little endian kernel on any of these targets,
> > but they all claim to be 44x so my little endian trampoline should work
> > on all of them, so wire it up on:
> >
> > bamboo
> > katmai
> > kilauea
> > rainer
> > sam440ep
> > sequoia
> > warp
> > yosemite
> > ebony
>
> I see no reason to do this at all. If you haven't tested them and
> there is no demand, there's no reason to wire them up. Some might
> actively want to disallow LE mode anyway, like the Warp or Sam440EP.
I wasn't aware that the Warp and Sam440EP disallowed LE mode - I'll
definitely unwire them and move the ARCH_SUPPORTS_LITTLE_ENDIAN to just
the sub-arch's that support it.
As for the other boards, I would like to wire them up if they are able
to support LE mode - If anyone has one handy I would love to hear if
they are able to begin booting a LE kernel with these patches, or when &
how they fail.
Cheers,
-Ian
^ permalink raw reply
* Re: Introduce support for little endian PowerPC
From: Ian Munsie @ 2010-10-06 1:04 UTC (permalink / raw)
To: Josh Boyer; +Cc: paulus, linuxppc-dev, linux-kernel
In-Reply-To: <AANLkTikHcoccu-WGtSOSdkwU6Tw_An_VFkUcEoY==8=c@mail.gmail.com>
Hi Josh,
Excerpts from Josh Boyer's message of Fri Oct 01 21:36:35 +1000 2010:
> Aside from my general "uh, why?" stance, I'm very very hesitant to
> integrate anything in the kernel that doesn'.t have released patches
> on the toolchain side.
As I said the kernel can be built today with an unpatched toolchain
targetted at powerpcle-elf, the new powerpcle-linux target is mainly
required for userspace, but yes I want to get those patches out as soon
as possible.
> Also, which uClibc? The old and crusty uClibc that uses the horrible
> linuxthreads, or the somewhat less crusty that just switched to NPTL
> (which hasn't been verified on normal PowerPC that I recall). Why not
> use glibc...
As Ben said this was for a proof of concept and changing uClibc to
support it was quite literally a one line change.
I've been using stable packages as my base on the toolchain side of
things (gcc 4.4.4, binutils 2.20.1 and uClibc 0.9.31) so uClibc is still
using linuxthreads since they haven't released a version with NPTL yet.
> I'm not meeting to detract here, but the Kconfig should be dependent
> on && BROKEN until the above is fixed.
Good point.
Cheers,
-Ian
^ permalink raw reply
* linux-next: build failure in Linus' tree
From: Stephen Rothwell @ 2010-10-06 0:09 UTC (permalink / raw)
To: Linus; +Cc: linux-next, ppc-dev, linux-kernel
Hi Linus,
Today's linux-next initial build (powerpc ppc64_defconfig) failed like
this:
cc1: warnings being treated as errors
arch/powerpc/kernel/module.c: In function 'module_finalize':
arch/powerpc/kernel/module.c:66: error: unused variable 'err'
Caused by commit 5336377d6225959624146629ce3fc88ee8ecda3d ("modules: Fix
module_bug_list list corruption race").
I added the following patch for today:
From: Stephen Rothwell <sfr@canb.auug.org.au>
Date: Wed, 6 Oct 2010 11:06:44 +1100
Subject: [PATCH] powerpc: remove unused variable
Since powerpc uses -Werror on arch powerpc, the build was broken like
this:
cc1: warnings being treated as errors
arch/powerpc/kernel/module.c: In function 'module_finalize':
arch/powerpc/kernel/module.c:66: error: unused variable 'err'
Signed-off-by: Stephen Rothwell <sfr@canb.auug.org.au>
---
arch/powerpc/kernel/module.c | 1 -
1 files changed, 0 insertions(+), 1 deletions(-)
diff --git a/arch/powerpc/kernel/module.c b/arch/powerpc/kernel/module.c
index 4ef93ae..49cee9d 100644
--- a/arch/powerpc/kernel/module.c
+++ b/arch/powerpc/kernel/module.c
@@ -63,7 +63,6 @@ int module_finalize(const Elf_Ehdr *hdr,
const Elf_Shdr *sechdrs, struct module *me)
{
const Elf_Shdr *sect;
- int err;
/* Apply feature fixups */
sect = find_section(hdr, sechdrs, "__ftr_fixup");
--
1.7.1
--
Cheers,
Stephen Rothwell sfr@canb.auug.org.au
http://www.canb.auug.org.au/~sfr/
^ permalink raw reply related
* [PATCH] powerpc/module: Remove unused variable err
From: Matthew McClintock @ 2010-10-05 22:26 UTC (permalink / raw)
To: linuxppc-dev; +Cc: Matthew McClintock
Commit 5336377d6225959624146629ce3fc88ee8ecda3d removed
the need for err, remove the variable
Signed-off-by: Matthew McClintock <msm@freescale.com>
---
arch/powerpc/kernel/module.c | 1 -
1 files changed, 0 insertions(+), 1 deletions(-)
diff --git a/arch/powerpc/kernel/module.c b/arch/powerpc/kernel/module.c
index 4ef93ae..49cee9d 100644
--- a/arch/powerpc/kernel/module.c
+++ b/arch/powerpc/kernel/module.c
@@ -63,7 +63,6 @@ int module_finalize(const Elf_Ehdr *hdr,
const Elf_Shdr *sechdrs, struct module *me)
{
const Elf_Shdr *sect;
- int err;
/* Apply feature fixups */
sect = find_section(hdr, sechdrs, "__ftr_fixup");
--
1.6.6.1
^ permalink raw reply related
* MSI-X vector allocation failure in upstream kernel
From: Anirban Chakraborty @ 2010-10-05 17:18 UTC (permalink / raw)
To: linuxppc-dev@lists.ozlabs.org; +Cc: Ameen Rahman
Hi All,
I am trying to test qlcnic driver (for 10Gb QLogic network adapter) on a Po=
wer 6 system=20
(IBM P 520, System type 8203) with upstream kernel and I do see that the ke=
rnel is=20
not able to allocate any MSI-X vectors. The driver requests for 4 vectors i=
n pci_enable_msix,
which returns 2. The driver again attempts, this time for 2 vectors but the=
kernel can't allocate=20
and it returns a value of 0xfffffffd. I upgraded the system FW to 01EL350 (=
from 01EL340)
just to make sure if MSI-X is enabled in the system. Is there anything tha=
t I am missing?=20
Any pointers will be highly appreciated.
thanks,
Anirban Chakraborty=
^ permalink raw reply
* Re: use of BAT before taking over the MMU
From: Segher Boessenkool @ 2010-10-05 15:31 UTC (permalink / raw)
To: Albert Cahalan; +Cc: linuxppc-dev
In-Reply-To: <AANLkTik9KeVzc6T7U=TX1bSA934Wmtbt4cjHrWSgWtLn@mail.gmail.com>
>>> The PowerPC OF binding requires the firmware to save and restore
>>> the BATs on entry to / exit from the firmware.
>
> That would defeat the purpose of setting them.
> They are used to provide Linux with mappings.
The initial state the OS has for the BATs is what the firmware
provides it with, sure.
An OS shouldn't expect to have more than its own program image
RAM mapped, in general.
> Of course that faults immediately, so I have a handler that
> loads IBAT0 with a 128 KiB mapping. I treat the BAT like a
> direct-mapped software-loaded TLB. (like MIPS arch MMU)
Just map the first 256MB and don't worry about anything else?
Seems a lot simpler to me ;-)
> Note that Linux can fail even with a firmware that doesn't touch
> the BAT registers. The MMU is on,
You can boot Linux with the MMU off as well.
> and 0xc0000000 may be
> where the firmware expects to have... MMIO for the console,
> the client interface entry point, a forth stack, whatever.
> The BAT takes priority, and thus the firmware splatters stuff
> right onto the kernel or dies trying to read something it left there.
Like I said, you're supposed to swap OS BATs with firmware BATs
in your client interface entry and exit. You have to switch
a lot of other registers there as well already, so that's no
big deal.
Segher
^ permalink raw reply
* RE: Serial RapidIO Maintaintance read causes lock up
From: Bounine, Alexandre @ 2010-10-05 15:11 UTC (permalink / raw)
To: Bastiaan Nijkamp, John Traill; +Cc: linuxppc-dev
In-Reply-To: <AANLkTik46NsiMhWo=GkHz4UbdDJeBLwFATJzhk-M3hSP@mail.gmail.com>
Bastiaan Nijkamp <bastiaan.nijkamp@gmail.com> wrote:=20
=A0
>A interesting thing that i found out is that when the agent is reset =
while the host is >locked up (eg. it cannot be stopped nor can i read =
the registers and memory trough a JTAG >Interface), the host comes back =
online and just continues booting linux with a RapidIO >error. See the =
log below.
... skip ...=A0
>fsl_rio_config_read: going to request to read data at d1080068
>RIO: cfg_read error -14 for ff:0:68
... skip ...
>RIO: master port 0 device has lost enumeration to a remote host
Looks like during agent reset your SRIO link becomes good and host's =
requests go ahead.
After that you get a machine check (response time out): link is OK but =
agent is not configured.
Can you check/print 0xC_0148 and 0xC_0158 registers of SRIO block before =
the first maintenance read.
Alex.
=20
^ permalink raw reply
* Re: use of BAT before taking over the MMU
From: Segher Boessenkool @ 2010-10-05 15:22 UTC (permalink / raw)
To: Benjamin Herrenschmidt; +Cc: Albert Cahalan, linuxppc-dev
In-Reply-To: <1286266201.2463.336.camel@pasglop>
>> The PowerPC OF binding requires the firmware to save and restore
>> the BATs on entry to / exit from the firmware.
>
> I'm not sure he was talking about OF here...
Yeah, I thought I was on a different mailing list. It's still
sort-of relevant though.
> In any case, we don't muck
> around with BATs until after we're done with OF anyways.
"Lower than the lowest common divider", yeah ;-)
Segher
^ permalink raw reply
* Re: Serial RapidIO Maintaintance read causes lock up
From: John Traill @ 2010-10-05 14:45 UTC (permalink / raw)
To: Bastiaan Nijkamp; +Cc: Bounine, Alexandre, linuxppc-dev
In-Reply-To: <AANLkTik46NsiMhWo=GkHz4UbdDJeBLwFATJzhk-M3hSP@mail.gmail.com>
Bastiaan,
On 05/10/10 15:28, Bastiaan Nijkamp wrote:
> Hi John,
> 1. Yes, they are both running the exact same kernel and both are
> configured in the same way. With the exception that one is set as host
> and the other as a agent.
> 2. Accept All is set for both boards.
> 3. As i understand, the agent cannot send anything before it is
> enumerated, so it would be safe to first reset the agent and right after
> that the host. In either case, thats the way i am using. The full kernel
> log until the discovery times out after 30 seconds is shown below:
> Using SBC8548 machine description
<snip>
In which case could you check the lawbar initialisation in u-boot for conflicts.
Would you post a dump of the lawbar registers from uboot.
The TLB's aren't important in this case as linux will reprogram as required.
Cheers
--
John Traill
Systems Engineer
Network and Computing Systems Group
Freescale Semiconductor UK LTD
Colvilles Road
East Kilbride
Glasgow G75 0TG, Scotland
Tel: +44 (0) 1355 355494
Fax: +44 (0) 1355 261790
E-mail: john.traill@freescale.com
Registration Number: SC262720
VAT Number: GB831329053
[ ] General Business Use
[ ] Freescale Internal Use Only
[ ] Freescale Confidential Proprietary
^ permalink raw reply
* Re: Serial RapidIO Maintaintance read causes lock up
From: Bastiaan Nijkamp @ 2010-10-05 14:30 UTC (permalink / raw)
To: Bounine, Alexandre; +Cc: linuxppc-dev
In-Reply-To: <0CE8B6BE3C4AD74AB97D9D29BD24E552013B9A9D@CORPEXCH1.na.ads.idt.com>
[-- Attachment #1: Type: text/plain, Size: 899 bytes --]
Hi Alex,
Yes, Sorry, that was a typo. The correct address that is printed is
0xd1080068.
And i did not disable the error handler, CONFIG_E500 is set at compile time.
Regards,
Bastiaan
2010/10/5 Bounine, Alexandre <Alexandre.Bounine@idt.com>
> Hi Bastiaan,
>
>
> Bastiaan Nijkamp <bastiaan.nijkamp@gmail.com> wrote:
>
> >fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO
> Maintainance Window Size >0x400000,New Main Start: 0xd1080000
> >RIO: enumerate master port 0, RIO0 mport
> >fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len
> 4
> ... skip ....
> >fsl_rio_config_read: triggering '__fsl_read_rio_config'
> >fsl_rio_config_read: going to request to read data at d108006
>
> An address printed in the last line looks strange - is this typo or real
> value?
> I would expect to see d1080068 here if your maintenance window starts at
> 0xd1080000.
>
> Alex.
>
[-- Attachment #2: Type: text/html, Size: 1392 bytes --]
^ permalink raw reply
* Re: Serial RapidIO Maintaintance read causes lock up
From: Bastiaan Nijkamp @ 2010-10-05 14:28 UTC (permalink / raw)
To: John Traill; +Cc: Bounine, Alexandre, linuxppc-dev
In-Reply-To: <4CAB2729.6080402@freescale.com>
[-- Attachment #1: Type: text/plain, Size: 11945 bytes --]
Hi John,
1. Yes, they are both running the exact same kernel and both are configured
in the same way. With the exception that one is set as host and the other as
a agent.
2. Accept All is set for both boards.
3. As i understand, the agent cannot send anything before it is enumerated,
so it would be safe to first reset the agent and right after that the host.
In either case, thats the way i am using. The full kernel log until the
discovery times out after 30 seconds is shown below:
Using SBC8548 machine description
Memory CAM mapping: 256 Mb, residual: 0Mb
Linux version 2.6.35.6 (dl704@lxws006) (gcc version 4.4.1 (Wind River Linux
Sour
cery G++ 4.4-250) ) #3 Tue Oct 5 13:24:45 CEST 2010
bootconsole [udbg0] enabled
setup_arch: bootmem
sbc8548_setup_arch()
arch: exit
Zone PFN ranges:
DMA 0x00000000 -> 0x00010000
Normal empty
Movable zone start PFN for each node
early_node_map[1] active PFN ranges
0: 0x00000000 -> 0x00010000
MMU: Allocated 1088 bytes of context maps for 255 contexts
Built 1 zonelists in Zone order, mobility grouping on. Total pages: 65024
Kernel command line: root=/dev/nfs rw nfsroot=192.168.100.21:
/thales/target/rfs/
sbc8548_wrlinux4 ip=192.168.100.151:192.168.100.21:192.168.100.21:255
.255.255.0:
sbc8548_1:eth0:off console=ttyS0,115200
PID hash table entries: 1024 (order: 0, 4096 bytes)
Dentry cache hash table entries: 32768 (order: 5, 131072 bytes)
Inode-cache hash table entries: 16384 (order: 4, 65536 bytes)
Memory: 256996k/262144k available (2644k kernel code, 5148k reserved, 108k
data,
77k bss, 136k init)
Kernel virtual memory layout:
* 0xfffdf000..0xfffff000 : fixmap
* 0xfdffd000..0xfe000000 : early ioremap
* 0xd1000000..0xfdffd000 : vmalloc & ioremap
Hierarchical RCU implementation.
RCU-based detection of stalled CPUs is disabled.
Verbose stalled-CPUs detection is disabled.
NR_IRQS:512 nr_irqs:512
mpic: Setting up MPIC " OpenPIC " version 1.2 at e0040000, max 1 CPUs
mpic: ISU size: 80, shift: 7, mask: 7f
mpic: Initializing for 80 sources
clocksource: timebase mult[50cede6] shift[22] registered
pid_max: default: 32768 minimum: 301
Mount-cache hash table entries: 512
NET: Registered protocol family 16
PCI: Probing PCI hardware
bio: create slab <bio-0> at 0
vgaarb: loaded
Switching to clocksource timebase
NET: Registered protocol family 2
IP route cache hash table entries: 2048 (order: 1, 8192 bytes)
TCP established hash table entries: 8192 (order: 4, 65536 bytes)
TCP bind hash table entries: 8192 (order: 3, 32768 bytes)
TCP: Hash tables configured (established 8192 bind 8192)
TCP reno registered
UDP hash table entries: 256 (order: 0, 4096 bytes)
UDP-Lite hash table entries: 256 (order: 0, 4096 bytes)
NET: Registered protocol family 1
RPC: Registered udp transport module.
RPC: Registered tcp transport module.
RPC: Registered tcp NFSv4.1 backchannel transport module.
Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Of-device full name
/soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size
0x0000000020000000.
fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
fsl-of-rio e00c0000.rapidio: DeviceID is 0xffffffff
fsl-of-rio e00c0000.rapidio: Configured as AGENT
fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio e00c0000.rapidio: Hardware port width: 4
fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO Maintainance
Window Size 0x400000,New Main Start: 0xd1080000
RIO: discover master port 0, RIO0 mport
A interesting thing that i found out is that when the agent is reset while
the host is locked up (eg. it cannot be stopped nor can i read the registers
and memory trough a JTAG Interface), the host comes back online and just
continues booting linux with a RapidIO error. See the log below.
Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Of-device full name
/soc8548@e0000000/rapidio@c0000
fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size
0x0000000020000000.
fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
fsl-of-rio e00c0000.rapidio: DeviceID is 0x0
fsl-of-rio e00c0000.rapidio: Configured as HOST
fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio e00c0000.rapidio: Hardware port width: 4
fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO Maintainance
Window Size 0x400000,New Main Start: 0xd1080000
RIO: enumerate master port 0, RIO0 mport
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
fsl_rio_config_read: Passed IS_ALIGNED.
fsl_rio_config_read: Passed 'out_be32_1'
fsl_rio_config_read: Passed 'out_be32_2'
fsl_rio_config_read: len is 4
fsl_rio_config_read: triggering '__fsl_read_rio_config'
fsl_rio_config_read: going to request to read data at d1080068
RIO: cfg_read error -14 for ff:0:68
RIO: master port 0 device has lost enumeration to a remote host
Regards,
Bastiaan
2010/10/5 John Traill <john.traill@freescale.com>
> Bastiaan,
>
> A few things to check.
>
> 1. Is the target board also set up for small common transport system size
> ie 256.
>
> 2. Make sure the target has "Accept All" set - in fsl_rio.c look for
>
>> /* Set to receive any dist ID for serial RapidIO controller. */
>> if (port->phy_type == RIO_PHY_SERIAL)
>> out_be32((priv->regs_win + RIO_ISR_AACR), RIO_ISR_AACR_AA);
>>
>
> 3. How do you synchronise reset between both systems ? Both need to be
> reset to insure the inbound/outbound ackid's remain in sync. If you only
> reset one then you have the potential for the ackid's to get out of sync.
> Also what is the kernel log on the agent system ?
>
> Cheers.
>
>
>
> On 05/10/10 09:56, Bastiaan Nijkamp wrote:
>
>>
>> Hi Alex,
>>
>> Thanks for your advice. We are trying to make a board-to-board
>> connection without any additional hardware (eg. a switch). The boards
>> use a 50-pin, right-angle MEC8-125-02-L-D-RA1 connector from SAMTEC and
>> are connected trough a EEDP-016-12.00-RA1-RA2-2 cross cable from SAMTEC.
>> I hope this information is sufficient since there is not much one can
>> find about it on Google. In addition, you can see a picture of the board
>> including the connector in the datasheet located at
>> http://www.windriver.com/products/product-notes/SBC8548E-product-note.pdf
>> .
>> It is the connector on the left side of the PCI-EX slot.
>>
>> We have tried your suggestion but the situation does not change other
>> than the lane-mode being set to single lane 0, it still locks up when
>> trying to generate a maintenance transaction. I still think it is memory
>> related since the lock up occurs when accessing the maintenance window.
>> Although all memory related settings seems to be alright.
>>
>> The kernel output is as follows:
>>
>> Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
>> fsl-of-rio e00c0000.rapidio: Of-device full name
>> /soc8548@e0000000/rapidio@c0000
>> fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
>> fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size
>> 0x0000000010000000.
>> fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
>> fsl-of-rio e00c0000.rapidio: DeviceID is 0x0
>> fsl-of-rio e00c0000.rapidio: Configured as HOST
>> fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
>> fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
>> fsl-of-rio e00c0000.rapidio: Hardware port width: 4
>> fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
>> fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
>> fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO
>> Maintainance Window Size 0x400000,New Main Start: 0xd1080000
>> RIO: enumerate master port 0, RIO0 mport
>> fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
>> fsl_rio_config_read: Passed IS_ALIGNED.
>> fsl_rio_config_read: Passed 'out_be32_1'
>> fsl_rio_config_read: Passed 'out_be32_2'
>> fsl_rio_config_read: len is 4
>> fsl_rio_config_read: triggering '__fsl_read_rio_config'
>> fsl_rio_config_read: going to request to read data at d108006
>>
>> Regards,
>> Bastiaan
>>
>> 2010/10/4 Bounine, Alexandre <Alexandre.Bounine@idt.com
>> <mailto:Alexandre.Bounine@idt.com>>
>>
>>
>> Hi Bastiaan,
>>
>> Are you trying board-to-board connection?
>> I am not familiar with WRS SBC8548 board - which type of connector they
>> use for SRIO?
>>
>> Assuming that all configuration is correct,
>> I would recommend first to try setting up x1 link mode at the lowest
>> link speed.
>> The x4 mode may present challenges in some cases.
>>
>> For quick test you may just add port width override into fsl_rio.c
>> like shown below (ugly but sometimes it helps ;) ):
>>
>> @@ -1461,10 +1461,16 @@ int fsl_rio_setup(struct platform_device *dev)
>> rio_register_mport(port);
>>
>> priv->regs_win = ioremap(regs.start, regs.end - regs.start +
>> 1);
>> rio_regs_win = priv->regs_win;
>>
>> +dev_info(&dev->dev, "Overriding RIO_PORT setting to single lane 0\n");
>> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
>> 0x800000);
>> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
>> 0x2000000);
>> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) &
>> ~0x800000);
>> +msleep(100);
>> +
>> /* Probe the master port phy type */
>> ccsr = in_be32(priv->regs_win + RIO_CCSR);
>> port->phy_type = (ccsr & 1) ? RIO_PHY_SERIAL :
>> RIO_PHY_PARALLEL;
>> dev_info(&dev->dev, "RapidIO PHY type: %s\n",
>> (port->phy_type == RIO_PHY_PARALLEL) ?
>> "parallel" :
>>
>>
>> Let me know what happens.
>> Please keep me in the CC: list next time when posting RapidIO questions
>> to the linuxppc-dev or kernel mailing lists.
>>
>> Regards,
>>
>> Alex.
>>
>>
>>
>>
>> _______________________________________________
>> Linuxppc-dev mailing list
>> Linuxppc-dev@lists.ozlabs.org
>> https://lists.ozlabs.org/listinfo/linuxppc-dev
>>
>
> --
> John Traill
> Systems Engineer
> Network and Computing Systems Group
>
> Freescale Semiconductor UK LTD
> Colvilles Road
> East Kilbride
> Glasgow G75 0TG, Scotland
>
> Tel: +44 (0) 1355 355494
> Fax: +44 (0) 1355 261790
>
> E-mail: john.traill@freescale.com
>
> Registration Number: SC262720
> VAT Number: GB831329053
>
> [ ] General Business Use
> [ ] Freescale Internal Use Only
> [ ] Freescale Confidential Proprietary
>
>
[-- Attachment #2: Type: text/html, Size: 14103 bytes --]
^ permalink raw reply
* RE: Serial RapidIO Maintaintance read causes lock up
From: Bounine, Alexandre @ 2010-10-05 13:49 UTC (permalink / raw)
To: John Traill, Bastiaan Nijkamp; +Cc: linuxppc-dev
In-Reply-To: <4CAB2729.6080402@freescale.com>
Hi John,
John Traill <john.traill@freescale.com> wrote:
> 2. Make sure the target has "Accept All" set - in fsl_rio.c look for
> > /* Set to receive any dist ID for serial RapidIO controller.
*/
> > if (port->phy_type =3D=3D RIO_PHY_SERIAL)
> > out_be32((priv->regs_win + RIO_ISR_AACR),
RIO_ISR_AACR_AA);
>
Looks like in Bastiaan's case request cannot leave the SRIO controller.
Otherwise he would get a machine check if a response is timed out
(assuming that he did not disable it).
Alex.
=20
=20
^ permalink raw reply
* RE: Serial RapidIO Maintaintance read causes lock up
From: Bounine, Alexandre @ 2010-10-05 13:34 UTC (permalink / raw)
To: Bastiaan Nijkamp; +Cc: linuxppc-dev
In-Reply-To: <AANLkTimCiHWRR-kVuT0ift3CH63Xk_XcaXS22qmVh6fr@mail.gmail.com>
Hi Bastiaan,
=20
Bastiaan Nijkamp <bastiaan.nijkamp@gmail.com> wrote:=20
>fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO
Maintainance Window Size >0x400000,New Main Start: 0xd1080000
>RIO: enumerate master port 0, RIO0 mport
>fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len
4
... skip ....
>fsl_rio_config_read: triggering '__fsl_read_rio_config'
>fsl_rio_config_read: going to request to read data at d108006
An address printed in the last line looks strange - is this typo or real
value?
I would expect to see d1080068 here if your maintenance window starts at
0xd1080000.
Alex.
^ permalink raw reply
* Re: Serial RapidIO Maintaintance read causes lock up
From: John Traill @ 2010-10-05 13:24 UTC (permalink / raw)
To: Bastiaan Nijkamp; +Cc: Bounine, Alexandre, linuxppc-dev
In-Reply-To: <AANLkTimCiHWRR-kVuT0ift3CH63Xk_XcaXS22qmVh6fr@mail.gmail.com>
Bastiaan,
A few things to check.
1. Is the target board also set up for small common transport system size ie 256.
2. Make sure the target has "Accept All" set - in fsl_rio.c look for
> /* Set to receive any dist ID for serial RapidIO controller. */
> if (port->phy_type == RIO_PHY_SERIAL)
> out_be32((priv->regs_win + RIO_ISR_AACR), RIO_ISR_AACR_AA);
3. How do you synchronise reset between both systems ? Both need to be reset to
insure the inbound/outbound ackid's remain in sync. If you only reset one then
you have the potential for the ackid's to get out of sync. Also what is the
kernel log on the agent system ?
Cheers.
On 05/10/10 09:56, Bastiaan Nijkamp wrote:
>
> Hi Alex,
>
> Thanks for your advice. We are trying to make a board-to-board
> connection without any additional hardware (eg. a switch). The boards
> use a 50-pin, right-angle MEC8-125-02-L-D-RA1 connector from SAMTEC and
> are connected trough a EEDP-016-12.00-RA1-RA2-2 cross cable from SAMTEC.
> I hope this information is sufficient since there is not much one can
> find about it on Google. In addition, you can see a picture of the board
> including the connector in the datasheet located at
> http://www.windriver.com/products/product-notes/SBC8548E-product-note.pdf.
> It is the connector on the left side of the PCI-EX slot.
>
> We have tried your suggestion but the situation does not change other
> than the lane-mode being set to single lane 0, it still locks up when
> trying to generate a maintenance transaction. I still think it is memory
> related since the lock up occurs when accessing the maintenance window.
> Although all memory related settings seems to be alright.
>
> The kernel output is as follows:
>
> Setting up RapidIO peer-to-peer network /soc8548@e0000000/rapidio@c0000
> fsl-of-rio e00c0000.rapidio: Of-device full name
> /soc8548@e0000000/rapidio@c0000
> fsl-of-rio e00c0000.rapidio: Regs: [mem 0xe00c0000-0xe00dffff]
> fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, size
> 0x0000000010000000.
> fsl-of-rio e00c0000.rapidio: pwirq: 48, bellirq: 50, txirq: 53, rxirq 54
> fsl-of-rio e00c0000.rapidio: DeviceID is 0x0
> fsl-of-rio e00c0000.rapidio: Configured as HOST
> fsl-of-rio e00c0000.rapidio: Overriding RIO_PORT setting to single lane 0
> fsl-of-rio e00c0000.rapidio: RapidIO PHY type: serial
> fsl-of-rio e00c0000.rapidio: Hardware port width: 4
> fsl-of-rio e00c0000.rapidio: Training connection status: Single-lane 0
> fsl-of-rio e00c0000.rapidio: RapidIO Common Transport System size: 256
> fsl-of-rio e00c0000.rapidio: LAW start 0x00000000c0000000, RIO
> Maintainance Window Size 0x400000,New Main Start: 0xd1080000
> RIO: enumerate master port 0, RIO0 mport
> fsl_rio_config_read: index 0 destid 255 hopcount 0 offset 00000068 len 4
> fsl_rio_config_read: Passed IS_ALIGNED.
> fsl_rio_config_read: Passed 'out_be32_1'
> fsl_rio_config_read: Passed 'out_be32_2'
> fsl_rio_config_read: len is 4
> fsl_rio_config_read: triggering '__fsl_read_rio_config'
> fsl_rio_config_read: going to request to read data at d108006
>
> Regards,
> Bastiaan
>
> 2010/10/4 Bounine, Alexandre <Alexandre.Bounine@idt.com
> <mailto:Alexandre.Bounine@idt.com>>
>
> Hi Bastiaan,
>
> Are you trying board-to-board connection?
> I am not familiar with WRS SBC8548 board - which type of connector they
> use for SRIO?
>
> Assuming that all configuration is correct,
> I would recommend first to try setting up x1 link mode at the lowest
> link speed.
> The x4 mode may present challenges in some cases.
>
> For quick test you may just add port width override into fsl_rio.c
> like shown below (ugly but sometimes it helps ;) ):
>
> @@ -1461,10 +1461,16 @@ int fsl_rio_setup(struct platform_device *dev)
> rio_register_mport(port);
>
> priv->regs_win = ioremap(regs.start, regs.end - regs.start + 1);
> rio_regs_win = priv->regs_win;
>
> +dev_info(&dev->dev, "Overriding RIO_PORT setting to single lane 0\n");
> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
> 0x800000);
> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) |
> 0x2000000);
> +out_be32(priv->regs_win + 0x15C, in_be32(priv->regs_win + 0x15C) &
> ~0x800000);
> +msleep(100);
> +
> /* Probe the master port phy type */
> ccsr = in_be32(priv->regs_win + RIO_CCSR);
> port->phy_type = (ccsr & 1) ? RIO_PHY_SERIAL : RIO_PHY_PARALLEL;
> dev_info(&dev->dev, "RapidIO PHY type: %s\n",
> (port->phy_type == RIO_PHY_PARALLEL) ?
> "parallel" :
>
>
> Let me know what happens.
> Please keep me in the CC: list next time when posting RapidIO questions
> to the linuxppc-dev or kernel mailing lists.
>
> Regards,
>
> Alex.
>
>
>
>
> _______________________________________________
> Linuxppc-dev mailing list
> Linuxppc-dev@lists.ozlabs.org
> https://lists.ozlabs.org/listinfo/linuxppc-dev
--
John Traill
Systems Engineer
Network and Computing Systems Group
Freescale Semiconductor UK LTD
Colvilles Road
East Kilbride
Glasgow G75 0TG, Scotland
Tel: +44 (0) 1355 355494
Fax: +44 (0) 1355 261790
E-mail: john.traill@freescale.com
Registration Number: SC262720
VAT Number: GB831329053
[ ] General Business Use
[ ] Freescale Internal Use Only
[ ] Freescale Confidential Proprietary
^ 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