Re: [PATCH] leds: Add options to have GPIO LEDs start on or keep their state

2009-05-13 Thread Trent Piepho
On Wed, 13 May 2009, Wolfram Sang wrote:
  diff --git a/include/linux/leds.h b/include/linux/leds.h
  index 376fe07..66e7d75 100644
  --- a/include/linux/leds.h
  +++ b/include/linux/leds.h
  @@ -141,9 +141,14 @@ struct gpio_led {
  const char *name;
  const char *default_trigger;
  unsignedgpio;
  -   u8  active_low : 1;
  -   u8  retain_state_suspended : 1;
  +   unsignedactive_low : 1;
  +   unsignedretain_state_suspended : 1;
  +   unsigneddefault_state : 2;
  +   /* default_state should be one of LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP) */

 Any specific reason for the change from u8 to unsigned? Could be
 mentioned in the patch description maybe. And what Sean mentioned :)

I should have mentioned that in the description.  It didn't make sense to
me to declare a bit field with u8.  An eight bit type that is one bit
wide?  The field width overrides the type width, but I think it's better to
just use unsigned and only specify a width once.


 Other than that:

 Acked-by: Wolfram Sang w.s...@pengutronix.de

 --
 Pengutronix e.K.   | Wolfram Sang|
 Industrial Linux Solutions | http://www.pengutronix.de/  |

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] leds: Add options to have GPIO LEDs start on or keep their state

2009-05-12 Thread Trent Piepho
There already is a default-on trigger but there are problems with it.

For one, it's a inefficient way to do it and requires led trigger support
to be compiled in.

But the real reason is that is produces a glitch on the LED.  The GPIO is
allocate with the LED *off*, then *later* when the trigger runs it is
turned back on.  If the LED was already on via the GPIO's reset default or
action of the firmware, this produces a glitch where the LED goes from on
to off to on.  While normally this is fast enough that it wouldn't be
noticeable to a human observer, there are still serious problems.

One is that there may be something else on the GPIO line, like a hardware
alarm or watchdog, that is fast enough to notice the glitch.

Another is that the kernel may panic before the LED is turned back on, thus
hanging with the LED in the wrong state.  This is not just speculation, but
actually happened to me with an embedded system that has an LED which
should turn off when the kernel finishes booting, which was left in the
incorrect state due to a bug in the OF LED binding code.

We also let GPIO LEDs get their initial value from whatever the current
state of the GPIO line is.  On some systems the LEDs are put into some
state by the firmware or hardware before Linux boots, and it is desired to
have them keep this state which is otherwise unknown to Linux.

This requires that the underlying GPIO driver support reading the value of
output GPIOs.  Some drivers support this and some do not.

The platform device binding gains a field in the platform data
default_state that controls this.  There are three constants defined to
select from on, off, or keeping the current state.  The OpenFirmware
binding uses a property named default-state that can be set to on,
off, or keep.  The default if the property isn't present is off.

Signed-off-by: Trent Piepho xy...@speakeasy.org
Acked-by: Grant Likely grant.lik...@secretlab.ca
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   17 -
 drivers/leds/leds-gpio.c|   21 ++---
 include/linux/leds.h|9 +++--
 3 files changed, 41 insertions(+), 6 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 4fe14de..064db92 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -16,10 +16,17 @@ LED sub-node properties:
   string defining the trigger assigned to the LED.  Current triggers are:
 backlight - LED will act as a back-light, controlled by the framebuffer
  system
-default-on - LED will turn on
+default-on - LED will turn on, but see default-state below
 heartbeat - LED double flashes at a load average based rate
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
+- default-state:  (optional) The initial state of the LED.  Valid
+  values are on, off, and keep.  If the LED is already on or off
+  and the default-state property is set the to same value, then no
+  glitch should be produced where the LED momentarily turns off (or
+  on).  The keep setting will keep the LED at whatever its current
+  state is, without producing a glitch.  The default is off if this
+  property is not present.
 
 Examples:
 
@@ -30,14 +37,22 @@ leds {
gpios = mcu_pio 0 1; /* Active low */
linux,default-trigger = ide-disk;
};
+
+   fault {
+   gpios = mcu_pio 1 0;
+   /* Keep LED on if BIOS detected hardware fault */
+   default-state = keep;
+   };
 };
 
 run-control {
compatible = gpio-leds;
red {
gpios = mpc8572 6 0;
+   default-state = off;
};
green {
gpios = mpc8572 7 0;
+   default-state = on;
};
 }
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index d210905..b5fd008 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -76,7 +76,7 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
struct gpio_led_data *led_dat, struct device *parent,
int (*blink_set)(unsigned, unsigned long *, unsigned long *))
 {
-   int ret;
+   int ret, state;
 
/* skip leds that aren't available */
if (!gpio_is_valid(template-gpio)) {
@@ -99,11 +99,15 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = LED_OFF;
+   if (template-default_state == LEDS_GPIO_DEFSTATE_KEEP)
+   state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
+   else
+   state = (template-default_state == LEDS_GPIO_DEFSTATE_ON);
+   led_dat-cdev.brightness = state

Re: [PATCH] powerpc: Update Warp to use leds-gpio driver

2009-04-17 Thread Trent Piepho
On Mon, 6 Apr 2009, Sean MacLennan wrote:
 Now that leds-gpio is a proper OF platform driver, the Warp can use
 the leds-gpio driver rather than the old out-of-kernel driver.

 One side-effect is the leds-gpio driver always turns the leds off
 while the old driver left them alone. So we have to set them back to
 the correct settings.

Originally, I had the OF bindings support this feature, see
http://article.gmane.org/gmane.linux.kernel/749094

Maybe this would be a better way to do it?  It avoids the glitch in the
leds, is less code overall, and can be use by other devices that might want
this same behavior.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [GIT PULL] LED updates for 2.6.29

2009-01-11 Thread Trent Piepho
On Sun, 11 Jan 2009, Richard Purdie wrote:
 On Sat, 2009-01-10 at 21:43 -0800, Trent Piepho wrote:
  On Sun, 11 Jan 2009, Richard Purdie wrote:
   On Sat, 2009-01-10 at 04:31 -0800, Trent Piepho wrote:
The LED tree makes more sense for what's left I think.  There was a
openfirmware gpio patch, but that's already gone in.  What's left only
touches led files and the device tree binding docs.
   
AFAIK, there were no objections to the patches left.
  
   Ok, these are now queued in the LED tree:
  
   http://git.o-hand.com/cgit.cgi/linux-rpurdie-leds/log/
  
   I did merge the last three patches in one and make some changes to deal
   with some other outstanding issues. Let me know ASAP if there are any
   problems.
 
  Since the last patch looks like it's just my three patches folded into one,
  shouldn't I be listed as the author and the primary signed off by?

 I made changes other than just merging the three together (the
 syspend/resume change and the bitfield parts in leds.h) so putting you
 as signed off by/authorship would not have been correct and I credited
 you in the commit message instead. I wanted to get the missing patches
 queued ASAP so I went with the way that does fit in the rules as you'd
 not have been happy if a modified patch was attributed to you. I'll put
 you as author and a signoff if you confirm thats acceptable.

It doesn't seem right to merge someone's patches together, make a very
small change, and then no longer credit them as the author.  Seems like it
defeats the purpose of the SOB lines for tracing the train of custody too.
If someone looks to see where the code came from, it will look like you
wrote it.  Maybe Freescale will say Intel stole our code?  Without the SOB,
what record is there in git that Freescale gave permission to put the code
in the kernel?

I also put some significant effort into writing informative commit
messages, which have been lost.  Along with Grant's acks for my patches.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [GIT PULL] LED updates for 2.6.29

2009-01-10 Thread Trent Piepho
On Fri, 9 Jan 2009, Richard Purdie wrote:
 On Fri, 2009-01-09 at 12:37 -0800, Trent Piepho wrote:
  On Fri, 9 Jan 2009, Richard Purdie wrote:
   for the LED tree updates for 2.6.29. This includes some new drivers,
   bugfixes and a core improvement resulting in nicer code.
  
 
  Any chance of these patches getting accepted?  They've been going back and
  forth for months now.
 
  [v2,1/4] leds: Support OpenFirmware led bindings
  http://patchwork.ozlabs.org/patch/13581/
 
  [v2,2/4] leds: Add option to have GPIO LEDs start on
  http://patchwork.ozlabs.org/patch/13580/
 
  [v2,3/4] leds: Let GPIO LEDs keep their current state
  http://patchwork.ozlabs.org/patch/13583/
 
  [v2,4/4] leds: Use tristate property in platform data
  http://patchwork.ozlabs.org/patch/13584/

 I think there was some confusion as to who was going to take them. Are
 the PPC people happy with them? If so I'll merge through the LED tree.
 There are these and a couple of other patches around which have got lost
 in the system. If there is time which I'm hoping there might be, I'll
 try and get a second LED tree merge in.

The LED tree makes more sense for what's left I think.  There was a
openfirmware gpio patch, but that's already gone in.  What's left only
touches led files and the device tree binding docs.

AFAIK, there were no objections to the patches left.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [GIT PULL] LED updates for 2.6.29

2009-01-10 Thread Trent Piepho
On Sun, 11 Jan 2009, Richard Purdie wrote:
 On Sat, 2009-01-10 at 04:31 -0800, Trent Piepho wrote:
  The LED tree makes more sense for what's left I think.  There was a
  openfirmware gpio patch, but that's already gone in.  What's left only
  touches led files and the device tree binding docs.
 
  AFAIK, there were no objections to the patches left.

 Ok, these are now queued in the LED tree:

 http://git.o-hand.com/cgit.cgi/linux-rpurdie-leds/log/

 I did merge the last three patches in one and make some changes to deal
 with some other outstanding issues. Let me know ASAP if there are any
 problems.

Since the last patch looks like it's just my three patches folded into one,
shouldn't I be listed as the author and the primary signed off by?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Status of fsl booke TLB and ATMU patches

2009-01-02 Thread Trent Piepho
2.6.28 is out, can my existing patches be accepted?

[2/2] POWERPC/fsl-pci: Set relaxed ordering on prefetchable ranges
http://patchwork.ozlabs.org/patch/14546/

[1/2] POWERPC/fsl-pci: Better ATMU setup
http://patchwork.ozlabs.org/patch/14544/

[5/5] powerpc: booke: Allow larger CAM sizes than 256 MB
http://patchwork.ozlabs.org/patch/12885/

[4/5] powerpc: booke: Make CAM entries used for lowmem configurable
http://patchwork.ozlabs.org/patch/12884/

[3/5] powerpc: booke: Remove code duplication in lowmem mapping
http://patchwork.ozlabs.org/patch/12883/

[2/5] powerpc: booke: Remove num_tlbcam_entries
http://patchwork.ozlabs.org/patch/12882/

[1/5] powerpc: booke: Don't hard-code size of struct tlbcam
http://patchwork.ozlabs.org/patch/12881/
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/2] POWERPC/fsl-pci: Better ATMU setup

2008-12-17 Thread Trent Piepho
The code that sets up the outbound ATMU windows, which is used to map CPU
physical addresses into PCI bus addresses where BARs will be mapped, didn't
work so well.

For one, it leaked the ioremap() of the ATMU registers.  Another small bug
was the high 20 bits of the PCI bus address were left as zero.  It's legal
for prefetchable memory regions to be above 32 bits, so the high 20 bits
might not be zero.

Mainly, it couldn't handle ranges that were not a power of two in size or
were not naturally aligned.  The ATMU windows have these requirements (size
 alignment), but the code didn't bother to check if the ranges it was
programming met them.  If they didn't, the windows would silently be
programmed incorrectly.

This new code can handle ranges which are not power of two sized nor
naturally aligned.  It simply splits the ranges into multiple valid ATMU
windows.  As there are only four windows, pooly aligned or sized ranges
(which didn't even work before) may run out of windows.  In this case an
error is printed and an effort is made to disable the unmapped resources.

An improvement that could be made would be to make use of the default
outbound window.  Iff hose-pci_mem_offset is zero, then it's possible that
some or all of the ranges might not need an outbound window and could just
use the default window.

The default ATMU window can support a pci_mem_offset less than zero too,
but pci_mem_offset is unsigned.  One could say the abilities allowed a
powerpc pci_controller is neither subset nor a superset of the abilities of
a Freescale PCIe controller.  Thankfully, the most useful bits are in the
intersection of the two abilities.

Signed-off-by: Trent Piepho tpie...@freescale.com
---
 arch/powerpc/sysdev/fsl_pci.c |  104 -
 1 files changed, 71 insertions(+), 33 deletions(-)

diff --git a/arch/powerpc/sysdev/fsl_pci.c b/arch/powerpc/sysdev/fsl_pci.c
index 5b264eb..656f914 100644
--- a/arch/powerpc/sysdev/fsl_pci.c
+++ b/arch/powerpc/sysdev/fsl_pci.c
@@ -28,62 +28,100 @@
 #include sysdev/fsl_pci.h
 
 #if defined(CONFIG_PPC_85xx) || defined(CONFIG_PPC_86xx)
+static int __init setup_one_atmu(struct ccsr_pci __iomem *pci,
+   unsigned int index, const struct resource *res,
+   resource_size_t offset)
+{
+   resource_size_t pci_addr = res-start - offset;
+   resource_size_t phys_addr = res-start;
+   resource_size_t size = res-end - res-start + 1;
+   u32 flags = 0x80044000; /* enable  mem R/W */
+   unsigned int i;
+
+   pr_debug(PCI MEM resource start 0x%016llx, size 0x%016llx.\n,
+   (u64)res-start, (u64)size);
+
+   for (i = 0; size  0; i++) {
+   unsigned int bits = min(__ilog2(size),
+   __ffs(pci_addr | phys_addr));
+
+   if (index + i = 5)
+   return -1;
+
+   out_be32(pci-pow[index + i].potar, pci_addr  12);
+   out_be32(pci-pow[index + i].potear, (u64)pci_addr  44);
+   out_be32(pci-pow[index + i].powbar, phys_addr  12);
+   out_be32(pci-pow[index + i].powar, flags | (bits - 1));
+
+   pci_addr += (resource_size_t)1U  bits;
+   phys_addr += (resource_size_t)1U  bits;
+   size -= (resource_size_t)1U  bits;
+   }
+
+   return i;
+}
+
 /* atmu setup for fsl pci/pcie controller */
 void __init setup_pci_atmu(struct pci_controller *hose, struct resource *rsrc)
 {
struct ccsr_pci __iomem *pci;
-   int i;
+   int i, j, n;
 
pr_debug(PCI memory map start 0x%016llx, size 0x%016llx\n,
(u64)rsrc-start, (u64)rsrc-end - (u64)rsrc-start + 1);
pci = ioremap(rsrc-start, rsrc-end - rsrc-start + 1);
+   if (!pci) {
+   dev_err(hose-parent, Unable to map ATMU registers\n);
+   return;
+   }
 
-   /* Disable all windows (except powar0 since its ignored) */
+   /* Disable all windows (except powar0 since it's ignored) */
for(i = 1; i  5; i++)
out_be32(pci-pow[i].powar, 0);
for(i = 0; i  3; i++)
out_be32(pci-piw[i].piwar, 0);
 
/* Setup outbound MEM window */
-   for(i = 0; i  3; i++)
-   if (hose-mem_resources[i].flags  IORESOURCE_MEM){
-   resource_size_t pci_addr_start =
-hose-mem_resources[i].start -
-hose-pci_mem_offset;
-   pr_debug(PCI MEM resource start 0x%016llx, size 
0x%016llx.\n,
-   (u64)hose-mem_resources[i].start,
-   (u64)hose-mem_resources[i].end
- - (u64)hose-mem_resources[i].start + 1);
-   out_be32(pci-pow[i+1].potar, (pci_addr_start  12));
-   out_be32(pci-pow[i+1].potear, 0);
-   out_be32(pci-pow[i+1].powbar,
-   (hose

[PATCH 2/2] POWERPC/fsl-pci: Set relaxed ordering on prefetchable ranges

2008-12-17 Thread Trent Piepho
Provides a small speedup when accessing pefetchable ranges.  To indicate
that a memory range is prefetchable, mark it in the dts file with 4200
instead of 0200.

A powepc pci_controller is allowed three memory ranges, any of which may be
prefetchable.  However, the PCI-PCI bridge configuration space only has one
field for non-prefetchable memory behind bridge, which has a 32 bit
address, and one field for prefetchable memory behind bridge, which may
have a 64 bit address.  These are PCI bus addresses, not CPU physical
addresses.

So really you're only allowed one memory range of each type.  And if you
want the range at a PCI address above 32 bits you must make it
prefetchable.

Signed-off-by: Trent Piepho tpie...@freescale.com
---
 arch/powerpc/sysdev/fsl_pci.c |3 +++
 1 files changed, 3 insertions(+), 0 deletions(-)

diff --git a/arch/powerpc/sysdev/fsl_pci.c b/arch/powerpc/sysdev/fsl_pci.c
index 656f914..af0d7e3 100644
--- a/arch/powerpc/sysdev/fsl_pci.c
+++ b/arch/powerpc/sysdev/fsl_pci.c
@@ -41,6 +41,9 @@ static int __init setup_one_atmu(struct ccsr_pci __iomem *pci,
pr_debug(PCI MEM resource start 0x%016llx, size 0x%016llx.\n,
(u64)res-start, (u64)size);
 
+   if (res-flags  IORESOURCE_PREFETCH)
+   flags |= 0x1000; /* enable relaxed ordering */
+
for (i = 0; size  0; i++) {
unsigned int bits = min(__ilog2(size),
__ffs(pci_addr | phys_addr));
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] POWERPC: MTD: Add cached map support to physmap_of MTD driver

2008-12-15 Thread Trent Piepho
The MTD system supports operation where a direct mapped flash chip is
mapped twice.  The normal mapping is a standard ioremap(), which is
non-cached and guarded on powerpc.  The second mapping is used only for
reads and can be cached and non-guarded.  Currently, only the pxa2xx
mapping driver makes use of this feature.  This patch adds support to the
physmap_of driver on PPC32 platforms for this cached mapping mode.

Because the flash chip doesn't participate in the cache coherency protocol,
it's necessary to invalidate the cache for parts of flash that are modified
with a program or erase operation.  This is platform specific, for instance
the pxa2xx driver uses an ARM specific function.  This patch adds
invalidate_dcache_icache_range() for PPC32 and uses it.  Because of XIP,
it's entirely possible that the flash might be in the icache(*), so the
existing invalidate_dcache_range() function isn't enough.

Of course, a cached mapping can increase performance if the data is read
from cache instead of flash.  But less obvious is that it can provide a
significant performance increase for cold-cache reads that still come from
flash.  It allows efficient back-to-back reads and if the flash chip 
controller support page burst mode, it allows that to be used as well.

The figures are for *cold-cache* read performance, measured on a Freescale
MPC8572 controlling a Spansion S29GL064N NOR flash chip.  With and without
the flash being mapped cached and with and without the localbus controller
being programmed to use page burst mode:

Non-cached, w/o bursts: 13.61 MB/s
Non-cached, w/ bursts:  13.61 MB/s
Cached, w/o bursts: 16.75 MB/s 23% increase
Cached, w/ bursts:  44.79 MB/s 229% increase!

Even without any cache hits, the cached mapping provides a significant
increase in performance via improved bus utilization.  Enabling burst
transfers is even more significant.

(*) The MTD device's -point() method, which is the mechanism for
supporting mmap and XIP, only allows for mmapping the uncached region.  So
you can't actually XIP anything in the cache.  But this could be fixed.

Signed-off-by: Trent Piepho tpie...@freescale.com
---
 arch/powerpc/include/asm/cacheflush.h |2 ++
 arch/powerpc/kernel/misc_32.S |   21 +
 drivers/mtd/maps/physmap_of.c |   20 
 3 files changed, 43 insertions(+), 0 deletions(-)

diff --git a/arch/powerpc/include/asm/cacheflush.h 
b/arch/powerpc/include/asm/cacheflush.h
index ba667a3..385c26c 100644
--- a/arch/powerpc/include/asm/cacheflush.h
+++ b/arch/powerpc/include/asm/cacheflush.h
@@ -49,6 +49,8 @@ extern void flush_dcache_range(unsigned long start, unsigned 
long stop);
 #ifdef CONFIG_PPC32
 extern void clean_dcache_range(unsigned long start, unsigned long stop);
 extern void invalidate_dcache_range(unsigned long start, unsigned long stop);
+extern void invalidate_dcache_icache_range(unsigned long start,
+  unsigned long stop);
 #endif /* CONFIG_PPC32 */
 #ifdef CONFIG_PPC64
 extern void flush_inval_dcache_range(unsigned long start, unsigned long stop);
diff --git a/arch/powerpc/kernel/misc_32.S b/arch/powerpc/kernel/misc_32.S
index d108715..5e6a154 100644
--- a/arch/powerpc/kernel/misc_32.S
+++ b/arch/powerpc/kernel/misc_32.S
@@ -639,6 +639,27 @@ _GLOBAL(invalidate_dcache_range)
blr
 
 /*
+ * Like above, but invalidate both the D-cache and I-cache.  Used when a cached
+ * region has been modified from a source that does not participate in the 
cache
+ * coherency protocol.
+ *
+ * invalidate_dcache_icache_range(unsigned long start, unsigned long stop)
+ */
+_GLOBAL(invalidate_dcache_icache_range)
+   clrrwi  r3, r3, L1_CACHE_SHIFT  /* start = ~((1SHIFT)-1) */
+   subfr4,r3,r4
+   addir4,r4,L1_CACHE_BYTES-1
+   srwi.   r4,r4,L1_CACHE_SHIFT/* count = (start-stop+BYTES-1)/BYTES */
+   beqlr   /* if (!count) return */
+   mtctr   r4
+1: dcbi0,r3
+   icbi0,r3
+   addir3,r3,L1_CACHE_BYTES
+   bdnz1b
+   sync/* wait for [id]cbi's to get to ram */
+   blr
+
+/*
  * Flush a particular page from the data cache to RAM.
  * Note: this is necessary because the instruction cache does *not*
  * snoop from the data cache.
diff --git a/drivers/mtd/maps/physmap_of.c b/drivers/mtd/maps/physmap_of.c
index 5fcfec0..e834298 100644
--- a/drivers/mtd/maps/physmap_of.c
+++ b/drivers/mtd/maps/physmap_of.c
@@ -32,6 +32,16 @@ struct of_flash {
 #endif
 };
 
+#ifdef CONFIG_PPC32
+#include asm/cacheflush.h
+static void ppc32_inval_cache(struct map_info *map, unsigned long from,
+ ssize_t len)
+{
+   invalidate_dcache_icache_range((unsigned long)map-cached + from,
+  (unsigned long)map-cached + from + len);
+}
+#endif
+
 #ifdef CONFIG_MTD_PARTITIONS
 #define OF_FLASH_PARTS(info)   ((info)-parts)
 
@@ -106,6 +116,8

Re: [PATCH] POWERPC: MTD: Add cached map support to physmap_of MTD driver

2008-12-15 Thread Trent Piepho
On Mon, 15 Dec 2008, Josh Boyer wrote:

 Did you actually change anything in this version when compared to the
 version you sent out last week?  If not, is there a reason you sent it
 again without flagging it as a resend?

I sent it out last week?  I'm trying to tie up loose ends before I leave
and thought this patch hadn't gone out yet.  No changes unless there was
some kind of last minute spelling fix in the patch comments.

At least this one has my non-Freescale address CCed so I'll get replies if
there are any.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] POWERPC: MTD: Add cached map support to physmap_of MTD driver

2008-12-15 Thread Trent Piepho
On Tue, 16 Dec 2008, Paul Mackerras wrote:
 Trent Piepho writes:
 The MTD system supports operation where a direct mapped flash chip is
 mapped twice.  The normal mapping is a standard ioremap(), which is
 non-cached and guarded on powerpc.  The second mapping is used only for
 reads and can be cached and non-guarded.  Currently, only the pxa2xx
 mapping driver makes use of this feature.  This patch adds support to the
 physmap_of driver on PPC32 platforms for this cached mapping mode.

 Note that having two mappings of the same physical address that differ
 in cacheability is a programming error according to the PowerPC
 architecture.

 Do you know that the processor implementations where you want to do
 this can cope with having two mappings with different cacheability?

Good question.  It worked for me, but I guess all powerpc32 can't handle
it.

Shame, as it provides a huge speed up.  I suppose an alternative would be
to map the chip twice at different physical addresses, by just configuring
the chip select to be twice the size it should be, and giving them
different cacheability.

Or changing the mapping for writes and then changing it back.  It wouldn't
be necessary to change the whole thing, just the page being written to.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: Re: How to support 3GB pci address?

2008-12-13 Thread Trent Piepho
On Sat, 13 Dec 2008, maillist.kernel wrote:
 Thanks for all the suggestions and Comments!
 In the system,  the total memory size is less than 4GB.   I want to know how 
 to map the 3GB pci address to the kernel ,
 and how can my driver access all the pci device. Usually we have only 1GB 
 kernel address, minus the 896MB
 for memory map, we can only use the 128M for ioremap. I can adjust the 
 PAGE_OFFSET to a lower value, but it's not enough.

My contract with Freescale is expiring very soon, so you will probably not
be able to reach me at this email address next week.

In order to ioremap() 3GB from the kernel, I think what you'll need to do
is reduce the user task size and low mem size to less than 1 GB.  Set the
custom user task to something like 512MB, set PAGE_OFFSET to whatever the
user task size is, and set maximum low memory to 384 MB.  That should give
you 3.25 GB for kernel ioremap()s.  If your BARs are 3GB total you'll
need a little more than that for other things the kernel will map.  Of
course, the user task size and lowmem size are now rather small

I've tested ioremap() of a 2GB PCI BAR and I know at least that much can
work.

Current kernels require that PAGE_OFFSET be 256 MB aligned, but I've posted
patches that reduce this requirement.  They've been ignored so far.

 One can mmap() a PCI BAR from userspace, in which case the mapping comes
 out of the max userspace size pool instead of the all ioremap()s pool.
 The userspace pool is per processes.  So while having four kernel drivers
 each call ioremap(..., 1GB) will never work, it is possible to have four
 userspace processes each call mmap(/sys/bus/pci.../resource, 1GB) and
 have it work.

 There are many pci devices in the system and every pci device has only 
 several tens of MB, so how can I call the mmap(/sys/bus/pci.../resource, 
 1GB)
 and how can I use it by my drivers ?

There are resource files in sysfs for each PCI BAR.  For example, say we
have this device:

00:00.0 Host bridge: Advanced Micro Devices [AMD] AMD-760 MP
 Flags: bus master, 66Mhz, medium devsel, latency 32
Memory at e800 (32-bit, prefetchable) [size=128M]
Memory at e700 (32-bit, prefetchable) [size=4K]
I/O ports at 1020 [disabled] [size=4]

Then in sysfs we will have these files:
-rw--- root 128M /sys/bus/pci/devices/:00:00.0/resource0
-rw--- root 4.0K /sys/bus/pci/devices/:00:00.0/resource1
-rw--- root4 /sys/bus/pci/devices/:00:00.0/resource2

A userspace process can use mmap() on them to map the PCI BAR into its
address space.  Because each process get it's own address space, you could
have multiple processes which have mapped a total of more than 4 GB.  But
this is for userspace processes, not the kernel.  The kernel only gets one
address space.

 On Fri, 12 Dec 2008, Kumar Gala wrote:
 On Dec 12, 2008, at 3:04 AM, Trent Piepho wrote:
 On Thu, 11 Dec 2008, Kumar Gala wrote:
  On Dec 11, 2008, at 10:07 PM, Trent Piepho wrote:
   On Thu, 11 Dec 2008, Kumar Gala wrote:
The 36-bit support is current (in tree) in complete.  Work is in
add swiotlb support to PPC which will generically enable what you
  
   Don't the ATMU windows in the pcie controller serve as a IOMMU, making
   swiotlb
   unnecessary and wasteful?
 
  Nope.  You have no way to tell when to switch a window as you have no
  idea
  when a device might DMA data.

 Isn't that what dma_alloc_coherent() and dma_map_single() are for?

 Nope.  How would manipulate the PCI ATMU?

 Umm, out_be32()?  Why would it be any different than other iommu
 implementations, like the pseries one for example?

 Just define set a of fsl dma ops that use an inbound ATMU window if they
 need to.  The only issue would be if you have a 32-bit device with multiple
 concurrent DMA buffers scattered over   32 bits of address space and run
 out of ATMU windows.  But other iommu implementations have that same
 limitation.  You just have to try harder to allocate GFP_DMA memory that
 doesn't need an ATMU window or create larger contiguous bounce buffer to
 replace scattered smaller buffers.

 It sounded like the original poster was talking about having 3GB of PCI
 BARs.  How does swiotlb even enter the picture for that?

 It wasn't clear how much system memory they wanted.  If they can fit their
 entire memory map for PCI addresses in 4G of address space (this includes all
 of system DRAM) than they don't need anything special.

 Why the need to fit the entire PCI memory map into the lower 4G?  What
 issue is there with mapping a PCI BAR above 4G if you have 36-bit support?

 Putting system memory below 4GB is only an issue if you're talking about
 DMA.  For mapping a PCI BAR, what does it doesn't matter?

 The problem I see with having large PCI BARs, is that the max userspace
 process size plus low memory plus all ioremap()s must be less than 4GB.  If
 one wants to call ioremap(..., 3GB), then only 1 GB is left for userspace
 plus low memory.  That's

Re: How to support 3GB pci address?

2008-12-12 Thread Trent Piepho
On Thu, 11 Dec 2008, Kumar Gala wrote:
 On Dec 11, 2008, at 10:07 PM, Trent Piepho wrote:
 On Thu, 11 Dec 2008, Kumar Gala wrote:
  On Dec 11, 2008, at 6:04 AM, maillist.kernel wrote:
   In the system, the total PCI address needed is about 3GB, so I want to 
   know
   how to support it in linux. mpc8548 has 36-bit real address, and can
   support 32GB PCIE address space, but in linux, there is only 1GB kernel
   space, how to map the 3GB pci address to kernel? Is the  36-bit real
   address only used to support large memory(4GB) for muti-threads?
  
  The 36-bit support is current (in tree) in complete.  Work is in progress 
  to
  add swiotlb support to PPC which will generically enable what you want to
  accomplish.
 
 Don't the ATMU windows in the pcie controller serve as a IOMMU, making 
 swiotlb
 unnecessary and wasteful?

 Nope.  You have no way to tell when to switch a window as you have no idea 
 when a device might DMA data.

Isn't that what dma_alloc_coherent() and dma_map_single() are for?

It sounded like the original poster was talking about having 3GB of PCI
BARs.  How does swiotlb even enter the picture for that?

From what I've read about swiotlb, it is a hack that allows one to do DMA
with 32-bit PCI devices on 64-bit systems that lack an IOMMU.  It reserves
a large block of RAM under 32-bits (technically it uses GFP_DMA) and doles
this out to drivers that allocate DMA memory.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: How to support 3GB pci address?

2008-12-12 Thread Trent Piepho
On Fri, 12 Dec 2008, Kumar Gala wrote:
 On Dec 12, 2008, at 3:04 AM, Trent Piepho wrote:
 On Thu, 11 Dec 2008, Kumar Gala wrote:
  On Dec 11, 2008, at 10:07 PM, Trent Piepho wrote:
   On Thu, 11 Dec 2008, Kumar Gala wrote:
The 36-bit support is current (in tree) in complete.  Work is in 
add swiotlb support to PPC which will generically enable what you 
   
   Don't the ATMU windows in the pcie controller serve as a IOMMU, making
   swiotlb
   unnecessary and wasteful?
  
  Nope.  You have no way to tell when to switch a window as you have no 
  idea
  when a device might DMA data.
 
 Isn't that what dma_alloc_coherent() and dma_map_single() are for?

 Nope.  How would manipulate the PCI ATMU?

Umm, out_be32()?  Why would it be any different than other iommu
implementations, like the pseries one for example?

Just define set a of fsl dma ops that use an inbound ATMU window if they
need to.  The only issue would be if you have a 32-bit device with multiple
concurrent DMA buffers scattered over  32 bits of address space and run
out of ATMU windows.  But other iommu implementations have that same
limitation.  You just have to try harder to allocate GFP_DMA memory that
doesn't need an ATMU window or create larger contiguous bounce buffer to
replace scattered smaller buffers.

 It sounded like the original poster was talking about having 3GB of PCI
 BARs.  How does swiotlb even enter the picture for that?

 It wasn't clear how much system memory they wanted.  If they can fit their 
 entire memory map for PCI addresses in 4G of address space (this includes all 
 of system DRAM) than they don't need anything special.

Why the need to fit the entire PCI memory map into the lower 4G?  What
issue is there with mapping a PCI BAR above 4G if you have 36-bit support?

Putting system memory below 4GB is only an issue if you're talking about
DMA.  For mapping a PCI BAR, what does it doesn't matter?

The problem I see with having large PCI BARs, is that the max userspace
process size plus low memory plus all ioremap()s must be less than 4GB.  If
one wants to call ioremap(..., 3GB), then only 1 GB is left for userspace
plus low memory.  That's not very much.

One can mmap() a PCI BAR from userspace, in which case the mapping comes
out of the max userspace size pool instead of the all ioremap()s pool. 
The userspace pool is per processes.  So while having four kernel drivers
each call ioremap(..., 1GB) will never work, it is possible to have four
userspace processes each call mmap(/sys/bus/pci.../resource, 1GB) and
have it work.

 From what I've read about swiotlb, it is a hack that allows one to do DMA
 with 32-bit PCI devices on 64-bit systems that lack an IOMMU.  It reserves
 a large block of RAM under 32-bits (technically it uses GFP_DMA) and doles
 this out to drivers that allocate DMA memory.

 correct.  It bounce buffers the DMAs to a 32-bit dma'ble region and copies 
 to/from the 32-bit address.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [RFC] Dummy GPIO driver for use with SPI

2008-12-12 Thread Trent Piepho
On Fri, 12 Dec 2008, Anton Vorontsov wrote:
 On Fri, Dec 12, 2008 at 11:59:13AM -0500, Steven A. Falco wrote:
 What do you think about having a mechanism to specify that some
 SPI slaves have a chip select, while others don't have to have a
 chip select managed by the SPI subsystem?

 Um.. do you know that you can pass '0' as a GPIO?

 For example,

 spi-controller {
   gpios = pio1 1 0  /* cs0 */
0  /* cs1, no GPIO */
pio2 2 0;/* cs2 */

It's ok the that middle specifier is only one word instead of three?  Seems
like 0 0 0 would be better, so all the specifiers are the same size.

   normal case;
   } else if (gpio == -EEXIST) {

Isn't EEXIST (pathname already exists) backward?  Seems like ENOENT would
be the right error code.  Except that's used for reading past the end...

Maybe a reading past the end should be EINVAL or EBADF?

Or return ENODEV for the 'hole' cell?  Or ENOLINK?

EEXIST is for trying to create something that already exists.  The 'hole'
is more like trying to follow a broken link or find something that doesn't
exist.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 1/4] leds: Support OpenFirmware led bindings

2008-12-11 Thread Trent Piepho
On Wed, 10 Dec 2008, Anton Vorontsov wrote:
 +gpio_direction_output(led_dat-gpio, led_dat-active_low);

 This can fail (yeah, the original code didn't check return value
 either).

I've added a check.

 +unsigned int flags;

 I think it would be better to use `enum of_gpio_flags' type here,
 just for clarity.

You're right, I forgot to change this after the of_get_gpio patch was
changed.

 +ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
 +  ofdev-dev, NULL);
 +if (ret  0)

 of_node_put(np); is missing here.

of_node_put(child) you mean.  It's easy to forget this when one exits one
of these iterators early, since there's no explicit get or put otherwise.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH v2 2/4] leds: Add option to have GPIO LEDs start on

2008-12-11 Thread Trent Piepho
Yes, there is the default-on trigger but there are problems with that.

For one, it's a inefficient way to do it and requires led trigger support
to be compiled in.

But the real reason is that is produces a glitch on the LED.  The GPIO is
allocate with the LED *off*, then *later* when then trigger runs it is
turned back on.  If the LED was already on via the GPIO's reset default or
action of the firmware, this produces a glitch where the LED goes from on
to off to on.  While normally this is fast enough that it wouldn't be
noticeable to a human observer, there are still serious problems.

One is that there may be something else on the GPIO line, like a hardware
alarm or watchdog, that is fast enough to notice the glitch.

Another is that the kernel may panic before the LED is turned back on, thus
hanging with the LED in the wrong state.  This is not just speculation, but
actually happened to me with an embedded system that has an LED which
should turn off when the kernel finishes booting, which was left in the
incorrect state due to a bug in the OF LED binding code.

The platform device binding gains a field in the platform data
default_state that controls this.  The OpenFirmware binding uses a
property named default-state that can be set to on or off.  The
default if the property isn't present is off.

Signed-off-by: Trent Piepho tpie...@freescale.com
Acked-by: Grant Likely grant.lik...@secretlab.ca
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |9 -
 drivers/leds/leds-gpio.c|8 ++--
 include/linux/leds.h|1 +
 3 files changed, 15 insertions(+), 3 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 4fe14de..5df384d 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -16,10 +16,15 @@ LED sub-node properties:
   string defining the trigger assigned to the LED.  Current triggers are:
 backlight - LED will act as a back-light, controlled by the framebuffer
  system
-default-on - LED will turn on
+default-on - LED will turn on, but see default-state below
 heartbeat - LED double flashes at a load average based rate
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
+- default-state:  (optional) The initial state of the LED.  Valid
+  values are on and off.  If the LED is already on or off and the
+  default-state property is set the to same value, then no glitch
+  should be produced where the LED momentarily turns off (or on).
+  The default is off if this property is not present.
 
 Examples:
 
@@ -36,8 +41,10 @@ run-control {
compatible = gpio-leds;
red {
gpios = mpc8572 6 0;
+   default-state = off;
};
green {
gpios = mpc8572 7 0;
+   default-state = on;
};
 }
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index be4d6aa..1ad96d2 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,9 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = LED_OFF;
+   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
 
-   ret = gpio_direction_output(led_dat-gpio, led_dat-active_low);
+   ret = gpio_direction_output(led_dat-gpio,
+   led_dat-active_low ^ template-default_state);
if (ret  0)
goto err;
 
@@ -261,12 +262,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
memset(led, 0, sizeof(led));
for_each_child_of_node(np, child) {
enum of_gpio_flags flags;
+   const char *state;
 
led.gpio = of_get_gpio_flags(child, 0, flags);
led.active_low = flags  OF_GPIO_ACTIVE_LOW;
led.name = of_get_property(child, label, NULL) ? : 
child-name;
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
+   state = of_get_property(child, default-state, NULL);
+   led.default_state = state  !strcmp(state, on);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index d3a73f5..caa3987 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,6 +138,7 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
+   u8  default_state;
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.1

[PATCH v2 1/4] leds: Support OpenFirmware led bindings

2008-12-11 Thread Trent Piepho
Add bindings to support LEDs defined as of_platform devices in addition to
the existing bindings for platform devices.

New options in Kconfig allow the platform binding code and/or the
of_platform code to be turned on.  The of_platform code is of course only
available on archs that have OF support.

The existing probe and remove methods are refactored to use new functions
create_gpio_led(), to create and register one led, and delete_gpio_led(),
to unregister and free one led.  The new probe and remove methods for the
of_platform driver can then share most of the common probe and remove code
with the platform driver.

The suspend and resume methods aren't shared, but they are very short.  The
actual led driving code is the same for LEDs created by either binding.

The OF bindings are based on patch by Anton Vorontsov
avoront...@ru.mvista.com.  They have been extended to allow multiple LEDs
per device.

Signed-off-by: Trent Piepho tpie...@freescale.com
Acked-by: Grant Likely grant.lik...@secretlab.ca
Acked-by: Sean MacLennan smaclen...@pikatech.com
CC: devicetree-disc...@ozlabs.org
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   46 -
 drivers/leds/Kconfig|   21 ++-
 drivers/leds/leds-gpio.c|  237 ++-
 3 files changed, 250 insertions(+), 54 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index ff51f4c..4fe14de 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -1,15 +1,43 @@
-LED connected to GPIO
+LEDs connected to GPIO lines
 
 Required properties:
-- compatible : should be gpio-led.
-- label : (optional) the label for this LED. If omitted, the label is
+- compatible : should be gpio-leds.
+
+Each LED is represented as a sub-node of the gpio-leds device.  Each
+node's name represents the name of the corresponding LED.
+
+LED sub-node properties:
+- gpios :  Should specify the LED's GPIO, see Specifying GPIO information
+  for devices in Documentation/powerpc/booting-without-of.txt.  Active
+  low LEDs should be indicated using flags in the GPIO specifier.
+- label :  (optional) The label for this LED.  If omitted, the label is
   taken from the node name (excluding the unit address).
-- gpios : should specify LED GPIO.
+- linux,default-trigger :  (optional) This parameter, if present, is a
+  string defining the trigger assigned to the LED.  Current triggers are:
+backlight - LED will act as a back-light, controlled by the framebuffer
+ system
+default-on - LED will turn on
+heartbeat - LED double flashes at a load average based rate
+ide-disk - LED indicates disk activity
+timer - LED flashes at a fixed, configurable rate
 
-Example:
+Examples:
 
-...@0 {
-   compatible = gpio-led;
-   label = hdd;
-   gpios = mcu_pio 0 1;
+leds {
+   compatible = gpio-leds;
+   hdd {
+   label = IDE Activity;
+   gpios = mcu_pio 0 1; /* Active low */
+   linux,default-trigger = ide-disk;
+   };
 };
+
+run-control {
+   compatible = gpio-leds;
+   red {
+   gpios = mpc8572 6 0;
+   };
+   green {
+   gpios = mpc8572 7 0;
+   };
+}
diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig
index e7fb7d2..6c6dc96 100644
--- a/drivers/leds/Kconfig
+++ b/drivers/leds/Kconfig
@@ -111,7 +111,26 @@ config LEDS_GPIO
help
  This option enables support for the LEDs connected to GPIO
  outputs. To be useful the particular board must have LEDs
- and they must be connected to the GPIO lines.
+ and they must be connected to the GPIO lines.  The LEDs must be
+ defined as platform devices and/or OpenFirmware platform devices.
+ The code to use these bindings can be selected below.
+
+config LEDS_GPIO_PLATFORM
+   bool Platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ platform devices.  If you don't know what this means, say yes.
+
+config LEDS_GPIO_OF
+   bool OpenFirmware platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO  OF_DEVICE
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ of_platform devices.  For instance, LEDs which are listed in a dts
+ file.
 
 config LEDS_HP_DISK
tristate LED Support for disk protection LED on HP notebooks
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index b13bd29..be4d6aa 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -3,6 +3,7 @@
  *
  * Copyright (C) 2007 8D Technologies inc.
  * Raphael Assenat r...@8d.com
+ * Copyright (C) 2008 Freescale Semiconductor, Inc.
  *
  * This program is free software; you can

[PATCH v2 3/4] leds: Let GPIO LEDs keep their current state

2008-12-11 Thread Trent Piepho
Let GPIO LEDs get their initial value from whatever the current state of
the GPIO line is.  On some systems the LEDs are put into some state by the
firmware or hardware before Linux boots, and it is desired to have them
keep this state which is otherwise unknown to Linux.

This requires that the underlying GPIO driver support reading the value of
output GPIOs.  Some drivers support this and some do not.

The platform data for the platform device binding gets a new field
'keep_state' which turns this on.  keep_state overrides default_state.

For the OpenFirmware bindings, the default-state property gains a new
allowable setting keep.

Signed-off-by: Trent Piepho tpie...@freescale.com
Acked-by: Grant Likely grant.lik...@secretlab.ca
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   16 
 drivers/leds/leds-gpio.c|   12 
 include/linux/leds.h|3 ++-
 3 files changed, 22 insertions(+), 9 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 5df384d..064db92 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -21,10 +21,12 @@ LED sub-node properties:
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
 - default-state:  (optional) The initial state of the LED.  Valid
-  values are on and off.  If the LED is already on or off and the
-  default-state property is set the to same value, then no glitch
-  should be produced where the LED momentarily turns off (or on).
-  The default is off if this property is not present.
+  values are on, off, and keep.  If the LED is already on or off
+  and the default-state property is set the to same value, then no
+  glitch should be produced where the LED momentarily turns off (or
+  on).  The keep setting will keep the LED at whatever its current
+  state is, without producing a glitch.  The default is off if this
+  property is not present.
 
 Examples:
 
@@ -35,6 +37,12 @@ leds {
gpios = mcu_pio 0 1; /* Active low */
linux,default-trigger = ide-disk;
};
+
+   fault {
+   gpios = mcu_pio 1 0;
+   /* Keep LED on if BIOS detected hardware fault */
+   default-state = keep;
+   };
 };
 
 run-control {
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index 1ad96d2..bb9d9ff 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -76,7 +76,7 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
struct gpio_led_data *led_dat, struct device *parent,
int (*blink_set)(unsigned, unsigned long *, unsigned long *))
 {
-   int ret;
+   int ret, state;
 
ret = gpio_request(template-gpio, template-name);
if (ret  0)
@@ -92,10 +92,13 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
+   if (template-keep_state)
+   state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
+   else
+   state = template-default_state;
+   led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;
 
-   ret = gpio_direction_output(led_dat-gpio,
-   led_dat-active_low ^ template-default_state);
+   ret = gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
if (ret  0)
goto err;
 
@@ -271,6 +274,7 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
led.default_state = state  !strcmp(state, on);
+   led.keep_state = state  !strcmp(state, keep);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index caa3987..c51b625 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,7 +138,8 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;
+   u8  default_state;  /* 0 = off, 1 = on */
+   u8  keep_state; /* overrides default_state */
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH v2 4/4] leds: Use tristate property in platform data

2008-12-11 Thread Trent Piepho
Replace the two boolean properties default_state and keep_state with a
single tristate property that can be set to
LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP).  This ends up being more complicated,
requires more code, and makes developers remember not just the name of the
field to set but also the symbolic constant to set it to.  Yet despite
these shortcomings it remains more popular.

Signed-off-by: Trent Piepho tpie...@freescale.com
---
 drivers/leds/leds-gpio.c |   15 +++
 include/linux/leds.h |7 +--
 2 files changed, 16 insertions(+), 6 deletions(-)

diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index bb9d9ff..2d1b71f 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,10 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   if (template-keep_state)
+   if (template-default_state == LEDS_GPIO_DEFSTATE_KEEP)
state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
else
-   state = template-default_state;
+   state = (template-default_state == LEDS_GPIO_DEFSTATE_ON);
led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;
 
ret = gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
@@ -273,8 +273,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
-   led.default_state = state  !strcmp(state, on);
-   led.keep_state = state  !strcmp(state, keep);
+   if (state) {
+   if (!strcmp(state, keep)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_KEEP;
+   } else if(!strcmp(state, on)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_ON;
+   } else {
+   led.default_state = LEDS_GPIO_DEFSTATE_OFF;
+   }
+   }
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index c51b625..f4a125c 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,9 +138,12 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;  /* 0 = off, 1 = on */
-   u8  keep_state; /* overrides default_state */
+   u8  default_state;
+   /* default_state should be one of LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP) */
 };
+#define LEDS_GPIO_DEFSTATE_OFF 0
+#define LEDS_GPIO_DEFSTATE_ON  1
+#define LEDS_GPIO_DEFSTATE_KEEP2
 
 struct gpio_led_platform_data {
int num_leds;
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: How to support 3GB pci address?

2008-12-11 Thread Trent Piepho
On Thu, 11 Dec 2008, Kumar Gala wrote:
 On Dec 11, 2008, at 6:04 AM, maillist.kernel wrote:
 In the system, the total PCI address needed is about 3GB, so I want to know 
 how to support it in linux. mpc8548 has 36-bit real address, and can 
 support 32GB PCIE address space, but in linux, there is only 1GB kernel 
 space, how to map the 3GB pci address to kernel? Is the  36-bit real 
 address only used to support large memory(4GB) for muti-threads?

 The 36-bit support is current (in tree) in complete.  Work is in progress to 
 add swiotlb support to PPC which will generically enable what you want to 
 accomplish.

Don't the ATMU windows in the pcie controller serve as a IOMMU, making swiotlb
unnecessary and wasteful?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] fsl-booke: declare tlbcam_index and num_tlbcam_entries for use in c file

2008-12-10 Thread Trent Piepho
On Wed, 10 Dec 2008, Liu Yu wrote:
 KVM on E500 platform currently utilize TLB1 entries without bothering host,
 that is using unused TLB1 entries.

 So, KVM needs to read tlbcam_index and num_tlbcam_entries to know exactly
 which TLB1 entry is unused.

Do you need really need num_tlbcam_entries?  It's completely unused and
I've already sent out a patch to remove it.  If you want to know how
big TLB1 is, just read it from SPRN_TLB1CFG.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 3/4] leds: Let GPIO LEDs keep their current state

2008-12-10 Thread Trent Piepho
Let GPIO LEDs get their initial value from whatever the current state of
the GPIO line is.  On some systems the LEDs are put into some state by the
firmware or hardware before Linux boots, and it is desired to have them
keep this state which is otherwise unknown to Linux.

This requires that the underlying GPIO driver support reading the value of
output GPIOs.  Some drivers support this and some do not.

The platform data for the platform device binding gets a new field
'keep_state' which turns this on.  keep_state overrides default_state.

For the OpenFirmware bindings, the default-state property gains a new
allowable setting keep.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Grant Likely [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   16 
 drivers/leds/leds-gpio.c|   12 
 include/linux/leds.h|3 ++-
 3 files changed, 22 insertions(+), 9 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 5df384d..064db92 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -21,10 +21,12 @@ LED sub-node properties:
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
 - default-state:  (optional) The initial state of the LED.  Valid
-  values are on and off.  If the LED is already on or off and the
-  default-state property is set the to same value, then no glitch
-  should be produced where the LED momentarily turns off (or on).
-  The default is off if this property is not present.
+  values are on, off, and keep.  If the LED is already on or off
+  and the default-state property is set the to same value, then no
+  glitch should be produced where the LED momentarily turns off (or
+  on).  The keep setting will keep the LED at whatever its current
+  state is, without producing a glitch.  The default is off if this
+  property is not present.
 
 Examples:
 
@@ -35,6 +37,12 @@ leds {
gpios = mcu_pio 0 1; /* Active low */
linux,default-trigger = ide-disk;
};
+
+   fault {
+   gpios = mcu_pio 1 0;
+   /* Keep LED on if BIOS detected hardware fault */
+   default-state = keep;
+   };
 };
 
 run-control {
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index 21084a3..e33cdd3 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -76,7 +76,7 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
struct gpio_led_data *led_dat, struct device *parent,
int (*blink_set)(unsigned, unsigned long *, unsigned long *))
 {
-   int ret;
+   int ret, state;
 
ret = gpio_request(template-gpio, template-name);
if (ret  0)
@@ -92,10 +92,13 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
+   if (template-keep_state)
+   state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
+   else
+   state = template-default_state;
+   led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;
 
-   gpio_direction_output(led_dat-gpio,
- led_dat-active_low ^ template-default_state);
+   gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
 
INIT_WORK(led_dat-work, gpio_led_work);
 
@@ -266,6 +269,7 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
led.default_state = state  !strcmp(state, on);
+   led.keep_state = state  !strcmp(state, keep);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index caa3987..c51b625 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,7 +138,8 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;
+   u8  default_state;  /* 0 = off, 1 = on */
+   u8  keep_state; /* overrides default_state */
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/4] leds: Support OpenFirmware led bindings

2008-12-10 Thread Trent Piepho
Add bindings to support LEDs defined as of_platform devices in addition to
the existing bindings for platform devices.

New options in Kconfig allow the platform binding code and/or the
of_platform code to be turned on.  The of_platform code is of course only
available on archs that have OF support.

The existing probe and remove methods are refactored to use new functions
create_gpio_led(), to create and register one led, and delete_gpio_led(),
to unregister and free one led.  The new probe and remove methods for the
of_platform driver can then share most of the common probe and remove code
with the platform driver.

The suspend and resume methods aren't shared, but they are very short.  The
actual led driving code is the same for LEDs created by either binding.

The OF bindings are based on patch by Anton Vorontsov
[EMAIL PROTECTED].  They have been extended to allow multiple LEDs
per device.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Grant Likely [EMAIL PROTECTED]
Acked-by: Sean MacLennan [EMAIL PROTECTED]
CC: [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   46 -
 drivers/leds/Kconfig|   21 ++-
 drivers/leds/leds-gpio.c|  230 ++-
 3 files changed, 243 insertions(+), 54 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index ff51f4c..4fe14de 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -1,15 +1,43 @@
-LED connected to GPIO
+LEDs connected to GPIO lines
 
 Required properties:
-- compatible : should be gpio-led.
-- label : (optional) the label for this LED. If omitted, the label is
+- compatible : should be gpio-leds.
+
+Each LED is represented as a sub-node of the gpio-leds device.  Each
+node's name represents the name of the corresponding LED.
+
+LED sub-node properties:
+- gpios :  Should specify the LED's GPIO, see Specifying GPIO information
+  for devices in Documentation/powerpc/booting-without-of.txt.  Active
+  low LEDs should be indicated using flags in the GPIO specifier.
+- label :  (optional) The label for this LED.  If omitted, the label is
   taken from the node name (excluding the unit address).
-- gpios : should specify LED GPIO.
+- linux,default-trigger :  (optional) This parameter, if present, is a
+  string defining the trigger assigned to the LED.  Current triggers are:
+backlight - LED will act as a back-light, controlled by the framebuffer
+ system
+default-on - LED will turn on
+heartbeat - LED double flashes at a load average based rate
+ide-disk - LED indicates disk activity
+timer - LED flashes at a fixed, configurable rate
 
-Example:
+Examples:
 
[EMAIL PROTECTED] {
-   compatible = gpio-led;
-   label = hdd;
-   gpios = mcu_pio 0 1;
+leds {
+   compatible = gpio-leds;
+   hdd {
+   label = IDE Activity;
+   gpios = mcu_pio 0 1; /* Active low */
+   linux,default-trigger = ide-disk;
+   };
 };
+
+run-control {
+   compatible = gpio-leds;
+   red {
+   gpios = mpc8572 6 0;
+   };
+   green {
+   gpios = mpc8572 7 0;
+   };
+}
diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig
index e7fb7d2..6c6dc96 100644
--- a/drivers/leds/Kconfig
+++ b/drivers/leds/Kconfig
@@ -111,7 +111,26 @@ config LEDS_GPIO
help
  This option enables support for the LEDs connected to GPIO
  outputs. To be useful the particular board must have LEDs
- and they must be connected to the GPIO lines.
+ and they must be connected to the GPIO lines.  The LEDs must be
+ defined as platform devices and/or OpenFirmware platform devices.
+ The code to use these bindings can be selected below.
+
+config LEDS_GPIO_PLATFORM
+   bool Platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ platform devices.  If you don't know what this means, say yes.
+
+config LEDS_GPIO_OF
+   bool OpenFirmware platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO  OF_DEVICE
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ of_platform devices.  For instance, LEDs which are listed in a dts
+ file.
 
 config LEDS_HP_DISK
tristate LED Support for disk protection LED on HP notebooks
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index b13bd29..107b958 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -3,6 +3,7 @@
  *
  * Copyright (C) 2007 8D Technologies inc.
  * Raphael Assenat [EMAIL PROTECTED]
+ * Copyright (C) 2008 Freescale Semiconductor, Inc.
  *
  * This program is free software; you can redistribute

[PATCH 4/4] leds: Use tristate property in platform data

2008-12-10 Thread Trent Piepho
Replace the two boolean properties default_state and keep_state with a
single tristate property that can be set to
LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP).  This ends up being more complicated,
requires more code, and makes developers remember not just the name of the
field to set but also the symbolic constant to set it to.  Yet despite
these shortcomings it remains more popular.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 drivers/leds/leds-gpio.c |   15 +++
 include/linux/leds.h |7 +--
 2 files changed, 16 insertions(+), 6 deletions(-)

diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index e33cdd3..47da332 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,10 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   if (template-keep_state)
+   if (template-default_state == LEDS_GPIO_DEFSTATE_KEEP)
state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
else
-   state = template-default_state;
+   state = (template-default_state == LEDS_GPIO_DEFSTATE_ON);
led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;
 
gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
@@ -268,8 +268,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
-   led.default_state = state  !strcmp(state, on);
-   led.keep_state = state  !strcmp(state, keep);
+   if (state) {
+   if (!strcmp(state, keep)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_KEEP;
+   } else if(!strcmp(state, on)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_ON;
+   } else {
+   led.default_state = LEDS_GPIO_DEFSTATE_OFF;
+   }
+   }
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index c51b625..f4a125c 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,9 +138,12 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;  /* 0 = off, 1 = on */
-   u8  keep_state; /* overrides default_state */
+   u8  default_state;
+   /* default_state should be one of LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP) */
 };
+#define LEDS_GPIO_DEFSTATE_OFF 0
+#define LEDS_GPIO_DEFSTATE_ON  1
+#define LEDS_GPIO_DEFSTATE_KEEP2
 
 struct gpio_led_platform_data {
int num_leds;
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 2/4] leds: Add option to have GPIO LEDs start on

2008-12-10 Thread Trent Piepho
Yes, there is the default-on trigger but there are problems with that.

For one, it's a inefficient way to do it and requires led trigger support
to be compiled in.

But the real reason is that is produces a glitch on the LED.  The GPIO is
allocate with the LED *off*, then *later* when then trigger runs it is
turned back on.  If the LED was already on via the GPIO's reset default or
action of the firmware, this produces a glitch where the LED goes from on
to off to on.  While normally this is fast enough that it wouldn't be
noticeable to a human observer, there are still serious problems.

One is that there may be something else on the GPIO line, like a hardware
alarm or watchdog, that is fast enough to notice the glitch.

Another is that the kernel may panic before the LED is turned back on, thus
hanging with the LED in the wrong state.  This is not just speculation, but
actually happened to me with an embedded system that has an LED which
should turn off when the kernel finishes booting, which was left in the
incorrect state due to a bug in the OF LED binding code.

The platform device binding gains a field in the platform data
default_state that controls this.  The OpenFirmware binding uses a
property named default-state that can be set to on or off.  The
default if the property isn't present is off.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Grant Likely [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |9 -
 drivers/leds/leds-gpio.c|8 ++--
 include/linux/leds.h|1 +
 3 files changed, 15 insertions(+), 3 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 4fe14de..5df384d 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -16,10 +16,15 @@ LED sub-node properties:
   string defining the trigger assigned to the LED.  Current triggers are:
 backlight - LED will act as a back-light, controlled by the framebuffer
  system
-default-on - LED will turn on
+default-on - LED will turn on, but see default-state below
 heartbeat - LED double flashes at a load average based rate
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
+- default-state:  (optional) The initial state of the LED.  Valid
+  values are on and off.  If the LED is already on or off and the
+  default-state property is set the to same value, then no glitch
+  should be produced where the LED momentarily turns off (or on).
+  The default is off if this property is not present.
 
 Examples:
 
@@ -36,8 +41,10 @@ run-control {
compatible = gpio-leds;
red {
gpios = mpc8572 6 0;
+   default-state = off;
};
green {
gpios = mpc8572 7 0;
+   default-state = on;
};
 }
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index 107b958..21084a3 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,9 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = LED_OFF;
+   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
 
-   gpio_direction_output(led_dat-gpio, led_dat-active_low);
+   gpio_direction_output(led_dat-gpio,
+ led_dat-active_low ^ template-default_state);
 
INIT_WORK(led_dat-work, gpio_led_work);
 
@@ -256,12 +257,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
memset(led, 0, sizeof(led));
for_each_child_of_node(np, child) {
unsigned int flags;
+   const char *state;
 
led.gpio = of_get_gpio_flags(child, 0, flags);
led.active_low = flags  OF_GPIO_ACTIVE_LOW;
led.name = of_get_property(child, label, NULL) ? : 
child-name;
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
+   state = of_get_property(child, default-state, NULL);
+   led.default_state = state  !strcmp(state, on);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index d3a73f5..caa3987 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,6 +138,7 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
+   u8  default_state;
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.1

___
Linuxppc-dev mailing list

Re: [RFC/PATCH 1/2] powerpc: Rework usage of _PAGE_COHERENT/NO_CACHE/GUARDED

2008-12-10 Thread Trent Piepho
On Wed, 10 Dec 2008, Benjamin Herrenschmidt wrote:
 This changes the logic so that instead, the PTE now contains
 _PAGE_COHERENT for all normal RAM pages tha have I = 0. The hash
 code clears it if the feature bit is not set.

Why not check the feature bit when the PTE is made and unset _PAGE_COHERENT
at that point?  In fact, could you do something like:

#if defined(CONFIG_SMP) || 
#define _PAGE_BASE  (_PAGE_PRESENT | _PAGE_ACCESSED | _PAGE_COHERENT)
#else
#define _PAGE_BASE  (_PAGE_PRESENT | _PAGE_ACCESSED)
#endif

 I haven't touched at the FSL BookE code yet. It may need to selectively
 clear M in the TLB miss handler ... or not. Depends what the impact of
 M on non-SMP E5xx setup is. I also didn't bother to clear it on 440 because
 it just has no effect (ie, it won't slow things down).

I've been told that setting M on non-SMP will slows things down.  But
couldn't you just change _PAGE_BASE on non-SMP instead of clearning it in
the miss handler?

   for_each_pci_dev(pdev) {
   for (i = 0; i = PCI_ROM_RESOURCE; i++) {
   struct resource *rp = pdev-resource[i];
 @@ -422,14 +417,14 @@ pgprot_t pci_phys_mem_access_prot(struct
   }
   if (found) {
   if (found-flags  IORESOURCE_PREFETCH)
 - prot = ~_PAGE_GUARDED;
 + prot = pgprot_noncached_wc(prot);
   pci_dev_put(pdev);
   }

I have a patch to remove this IORESOURCE_PREFETCH hack.  The current kernel
creates two files, resourceN and resourceN_wc, for prefetchable BARs to
allow the user to choose what mode to use.

Though I want to be able to map PCI resources as cached too.  I'm not sure
what a good way to add that is.  Yet another resource file?  The first
proposal for allowing WC mappings was to add support for ioctl() on sysfs
attributes.  Then one could use ioctl() after opening the resource file to
specify what mode to map it with.  No one liked ioctl(), but clearly the
current method doesn't scale well to all 32 combinations of the WIMGE bits.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [RFC/PATCH 1/2] powerpc: Rework usage of _PAGE_COHERENT/NO_CACHE/GUARDED

2008-12-10 Thread Trent Piepho
On Thu, 11 Dec 2008, Benjamin Herrenschmidt wrote:
 On Wed, 2008-12-10 at 11:33 -0800, Trent Piepho wrote:
 On Wed, 10 Dec 2008, Benjamin Herrenschmidt wrote:
 This changes the logic so that instead, the PTE now contains
 _PAGE_COHERENT for all normal RAM pages tha have I = 0. The hash
 code clears it if the feature bit is not set.

 Why not check the feature bit when the PTE is made and unset _PAGE_COHERENT
 at that point?  In fact, could you do something like:

 Not sure what you mean. Inside set_pte_at ? Well, the one line of asm is
 going to be in the noise in the hash code, I'm just flipping an existing
 condition. I like the PTE to represent whether it's supposed to be a
 coherent page.

In the code that does the mapping.  It's a lot cheaper to figure out if
_PAGE_COHERENT is needed once per mapping instead of per page per fault.

It sounds like getting it right is a lot more complicated than just one
instruction.  No M bit for non-SMP, except for some 74xx, or if a MPC107
bridge is used, which should be determined at runtime.  And does the MPC107
thing apply to all pages or just those PCI memory behind the bridge?  Or
DMA?

 I've been told that setting M on non-SMP will slows things down.  But
 couldn't you just change _PAGE_BASE on non-SMP instead of clearning it in
 the miss handler?

 Well, because we need it set on non SMP on some 74xx.. maybe we can
 have it set in PAGE_BASE only if CONFIG_SMP and CONFIG_6xx ?

That's what I was thinking, set it in page base for SMP and other instances
when we know it's necessary at compile time.  If/when there is a runtime
check, then it would be lot easier to put that check in the code that made
the mapping instead of the miss handler.

 I have a patch to remove this IORESOURCE_PREFETCH hack.  The current kernel
 creates two files, resourceN and resourceN_wc, for prefetchable BARs to
 allow the user to choose what mode to use.

 Ah ? That's new ? I missed it. Has X been updated to use them ? If not,
 keep the hack for a little while more :-)

It's rather new so I bet X servers that use it aren't widely deployed yet.

commit 45aec1ae72fc592f231e9e73ed9ed4d10cfbc0b5
Author: [EMAIL PROTECTED] [EMAIL PROTECTED]
Date:   Tue Mar 18 17:00:22 2008 -0700

 x86: PAT export resource_wc in pci sysfs

Patch title is somewhat misleading, as it doesn't touch any x86 specific
code.  And people complain when I used booke instead of fsl-booke...  like
I want to make it any easier to have patches ignored.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] Introduce ppc_pci_flags accessors

2008-12-10 Thread Trent Piepho
On Wed, 10 Dec 2008, Josh Boyer wrote:
 On Thu, 11 Dec 2008 10:46:28 +1100
 +#ifdef CONFIG_PCI
 +extern unsigned int ppc_pci_flags;
 +#define ppc_pci_set_flags(flags) ppc_pci_flags = (flags)
 +#define ppc_pci_add_flags(flags) ppc_pci_flags |= (flags)
 +#define ppc_pci_flag_is_set(flag) (ppc_pci_flags  (flag))
 +#else
 +#define ppc_pci_set_flags(flags) do {} while (0)
 +#define ppc_pci_add_flags(flags) do {} while (0)
 +#define ppc_pci_flag_is_set(flag) (0)
 +#endif

 I hate to be picky, but I don't see any reason why these shouldn't be
 static inlines.

 There's a perfectly good reason.  I AM LAZY.

 That aside, it doesn't matter to me either way.  If the general idea
 seems fine and the naming of the functions is acceptable, I'd be happy
 to respin.

If were allowed to be picky, I think ppc_pci_has_flag() is a better name
than ppc_pci_flag_is_set().  Matches the other function names better, and a
quick grep of the kernel source shows bar_has_foo() is much more common
than bar_foo_is_set().
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 4/4] leds: Let GPIO LEDs keep their current state

2008-12-09 Thread Trent Piepho
On Wed, 3 Dec 2008, Richard Purdie wrote:
 On Sun, 2008-11-23 at 13:31 +0100, Pavel Machek wrote:
 On Thu 2008-11-20 17:05:56, Trent Piepho wrote:
 I thought of that, but it ends up being more complex.  Instead of just
 using:
 static const struct gpio_led myled = {
 .name = something,
 .keep_state = 1,
 }

 You'd do something like this:
 .default_state = LEDS_GPIO_DEFSTATE_KEEP,

 Is that better?

 Yes.

 Yes, agreed, much better.

Oh very well, I'll change it.  But I reserve the right to make a sarcastic
commit message.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] powerpc/85xx: Add support for SMP initialization

2008-12-08 Thread Trent Piepho
On Tue, 2 Dec 2008, Kumar Gala wrote:
 Added 85xx specifc smp_ops structure.  We use ePAPR style boot release
 and the MPIC for IPIs at this point.

 Additionally added routines for secondary cpu entry and initializtion.

 @@ -740,6 +750,9 @@ finish_tlb_load:
 #else
   rlwimi  r12, r11, 26, 27, 31/* extract WIMGE from pte */
 #endif
 +#ifdef CONFIG_SMP
 + ori r12, r12, MAS2_M
 +#endif
   mtspr   SPRN_MAS2, r12

Wouldn't it be more efficient to set _PAGE_COHERENT when the pte is created
vs setting MAS2_M each time it's loaded?

Is it correct to set MAS2_M for all pages, even uncached ones?

The code for ioremap() has this:

 /* Non-cacheable page cannot be coherent */
 if (flags  _PAGE_NO_CACHE)
 flags = ~_PAGE_COHERENT;

It seems odd that ioremap would explictly unset _PAGE_COHERENT when the
code that sets the tlb will just force it back on.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/5] powerpc: booke: Don't hard-code size of struct tlbcam

2008-12-08 Thread Trent Piepho
Some assembly code in head_fsl_booke.S hard-coded the size of struct tlbcam
to 20 when it indexed the TLBCAM table.  Anyone changing the size of struct
tlbcam would not know to expect that.

The kernel already has a system to get the size of C structures into
assembly language files, asm-offsets, so let's use it.

The definition of the struct gets moved to a header, so that asm-offsets.c
can include it.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/kernel/asm-offsets.c|8 
 arch/powerpc/kernel/head_fsl_booke.S |2 +-
 arch/powerpc/mm/fsl_booke_mmu.c  |8 +---
 arch/powerpc/mm/mmu_decl.h   |9 +
 4 files changed, 19 insertions(+), 8 deletions(-)

diff --git a/arch/powerpc/kernel/asm-offsets.c 
b/arch/powerpc/kernel/asm-offsets.c
index 050abfd..4d62a8d 100644
--- a/arch/powerpc/kernel/asm-offsets.c
+++ b/arch/powerpc/kernel/asm-offsets.c
@@ -56,6 +56,10 @@
 #include head_booke.h
 #endif
 
+#if defined(CONFIG_FSL_BOOKE)
+#include ../mm/mmu_decl.h
+#endif
+
 int main(void)
 {
DEFINE(THREAD, offsetof(struct task_struct, thread));
@@ -271,6 +275,10 @@ int main(void)
DEFINE(SAVED_KSP_LIMIT, STACK_INT_FRAME_SIZE+offsetof(struct 
exception_regs, saved_ksp_limit));
 #endif
 
+#ifdef CONFIG_FSL_BOOKE
+   DEFINE(TLBCAM_SIZE, sizeof(struct tlbcam));
+#endif
+
DEFINE(CLONE_VM, CLONE_VM);
DEFINE(CLONE_UNTRACED, CLONE_UNTRACED);
 
diff --git a/arch/powerpc/kernel/head_fsl_booke.S 
b/arch/powerpc/kernel/head_fsl_booke.S
index 9a4639c..c591acb 100644
--- a/arch/powerpc/kernel/head_fsl_booke.S
+++ b/arch/powerpc/kernel/head_fsl_booke.S
@@ -909,7 +909,7 @@ KernelSPE:
 _GLOBAL(loadcam_entry)
lis r4,[EMAIL PROTECTED]
addir4,r4,[EMAIL PROTECTED]
-   mulli   r5,r3,20
+   mulli   r5,r3,TLBCAM_SIZE
add r3,r5,r4
lwz r4,0(r3)
mtspr   SPRN_MAS0,r4
diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index 23cee39..c9ee59a 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -61,13 +61,7 @@ static unsigned long __cam0, __cam1, __cam2;
 
 #define NUM_TLBCAMS(16)
 
-struct tlbcam {
-   u32 MAS0;
-   u32 MAS1;
-   u32 MAS2;
-   u32 MAS3;
-   u32 MAS7;
-} TLBCAM[NUM_TLBCAMS];
+struct tlbcam TLBCAM[NUM_TLBCAMS];
 
 struct tlbcamrange {
unsigned long start;
diff --git a/arch/powerpc/mm/mmu_decl.h b/arch/powerpc/mm/mmu_decl.h
index fab3cfa..f0d0aae 100644
--- a/arch/powerpc/mm/mmu_decl.h
+++ b/arch/powerpc/mm/mmu_decl.h
@@ -27,6 +27,15 @@ extern void hash_preload(struct mm_struct *mm, unsigned long 
ea,
 
 
 #ifdef CONFIG_PPC32
+
+struct tlbcam {
+   u32 MAS0;
+   u32 MAS1;
+   u32 MAS2;
+   u32 MAS3;
+   u32 MAS7;
+};
+
 extern void mapin_ram(void);
 extern int map_page(unsigned long va, phys_addr_t pa, int flags);
 extern void setbat(int index, unsigned long virt, phys_addr_t phys,
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 2/5] powerpc: booke: Remove num_tlbcam_entries

2008-12-08 Thread Trent Piepho
This is a global variable defined in fsl_booke_mmu.c with a value that gets
initialized in assembly code in head_fsl_booke.S.

It's never used.

If some code ever does want to know the number of entries in TLB1, then
numcams = mfspr(SPRN_TLB1CFG)  0xfff, is a whole lot simpler than a
global initialized during kernel boot from assembly.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/kernel/head_fsl_booke.S |4 
 arch/powerpc/mm/fsl_booke_mmu.c  |1 -
 arch/powerpc/mm/mmu_decl.h   |2 --
 3 files changed, 0 insertions(+), 7 deletions(-)

diff --git a/arch/powerpc/kernel/head_fsl_booke.S 
b/arch/powerpc/kernel/head_fsl_booke.S
index c591acb..e33021f 100644
--- a/arch/powerpc/kernel/head_fsl_booke.S
+++ b/arch/powerpc/kernel/head_fsl_booke.S
@@ -389,10 +389,6 @@ skpinv:addir6,r6,1 /* 
Increment */
 #endif
 #endif
 
-   mfspr   r3,SPRN_TLB1CFG
-   andi.   r3,r3,0xfff
-   lis r4,[EMAIL PROTECTED]
-   stw r3,[EMAIL PROTECTED](r4)
 /*
  * Decide what sort of machine this is and initialize the MMU.
  */
diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index c9ee59a..1971e4e 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -56,7 +56,6 @@
 
 extern void loadcam_entry(unsigned int index);
 unsigned int tlbcam_index;
-unsigned int num_tlbcam_entries;
 static unsigned long __cam0, __cam1, __cam2;
 
 #define NUM_TLBCAMS(16)
diff --git a/arch/powerpc/mm/mmu_decl.h b/arch/powerpc/mm/mmu_decl.h
index f0d0aae..1db3c67 100644
--- a/arch/powerpc/mm/mmu_decl.h
+++ b/arch/powerpc/mm/mmu_decl.h
@@ -51,8 +51,6 @@ extern unsigned int rtas_data, rtas_size;
 struct hash_pte;
 extern struct hash_pte *Hash, *Hash_end;
 extern unsigned long Hash_size, Hash_mask;
-
-extern unsigned int num_tlbcam_entries;
 #endif
 
 extern unsigned long ioremap_bot;
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 3/5] powerpc: booke: Remove code duplication in lowmem mapping

2008-12-08 Thread Trent Piepho
The code to map lowmem uses three CAM aka TLB[1] entries to cover it.  The
size of each is stored in three globals named __cam0, __cam1, and __cam2.
All the code that uses them is duplicated three times for each of the three
variables.

We have these things called arrays and loops

Once converted to use an array, it will be easier to make the number of
CAMs configurable.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/mm/fsl_booke_mmu.c |   79 +++---
 1 files changed, 31 insertions(+), 48 deletions(-)

diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index 1971e4e..1dabe1a 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -56,7 +56,7 @@
 
 extern void loadcam_entry(unsigned int index);
 unsigned int tlbcam_index;
-static unsigned long __cam0, __cam1, __cam2;
+static unsigned long cam[3];
 
 #define NUM_TLBCAMS(16)
 
@@ -152,19 +152,19 @@ void invalidate_tlbcam_entry(int index)
loadcam_entry(index);
 }
 
-void __init cam_mapin_ram(unsigned long cam0, unsigned long cam1,
-   unsigned long cam2)
+unsigned long __init mmu_mapin_ram(void)
 {
-   settlbcam(0, PAGE_OFFSET, memstart_addr, cam0, _PAGE_KERNEL, 0);
-   tlbcam_index++;
-   if (cam1) {
-   tlbcam_index++;
-   settlbcam(1, PAGE_OFFSET+cam0, memstart_addr+cam0, cam1, 
_PAGE_KERNEL, 0);
-   }
-   if (cam2) {
+   unsigned long virt = PAGE_OFFSET;
+   phys_addr_t phys = memstart_addr;
+
+   while (cam[tlbcam_index]  tlbcam_index  ARRAY_SIZE(cam)) {
+   settlbcam(tlbcam_index, virt, phys, cam[tlbcam_index], 
_PAGE_KERNEL, 0);
+   virt += cam[tlbcam_index];
+   phys += cam[tlbcam_index];
tlbcam_index++;
-   settlbcam(2, PAGE_OFFSET+cam0+cam1, memstart_addr+cam0+cam1, 
cam2, _PAGE_KERNEL, 0);
}
+
+   return virt - PAGE_OFFSET;
 }
 
 /*
@@ -175,51 +175,34 @@ void __init MMU_init_hw(void)
flush_instruction_cache();
 }
 
-unsigned long __init mmu_mapin_ram(void)
-{
-   cam_mapin_ram(__cam0, __cam1, __cam2);
-
-   return __cam0 + __cam1 + __cam2;
-}
-
-
 void __init
 adjust_total_lowmem(void)
 {
-   phys_addr_t max_lowmem_size = __max_low_memory;
-   phys_addr_t cam_max_size = 0x1000;
phys_addr_t ram;
+   unsigned int max_cam = 28;  /* 2^28 = 256 Mb */
+   char buf[ARRAY_SIZE(cam) * 5 + 1], *p = buf;
+   int i;
 
-   /* adjust CAM size to max_lowmem_size */
-   if (max_lowmem_size  cam_max_size)
-   cam_max_size = max_lowmem_size;
-
-   /* adjust lowmem size to max_lowmem_size */
-   ram = min(max_lowmem_size, total_lowmem);
+   /* adjust lowmem size to __max_low_memory */
+   ram = min((phys_addr_t)__max_low_memory, (phys_addr_t)total_lowmem);
 
/* Calculate CAM values */
-   __cam0 = 1UL  2 * (__ilog2(ram) / 2);
-   if (__cam0  cam_max_size)
-   __cam0 = cam_max_size;
-   ram -= __cam0;
-   if (ram) {
-   __cam1 = 1UL  2 * (__ilog2(ram) / 2);
-   if (__cam1  cam_max_size)
-   __cam1 = cam_max_size;
-   ram -= __cam1;
-   }
-   if (ram) {
-   __cam2 = 1UL  2 * (__ilog2(ram) / 2);
-   if (__cam2  cam_max_size)
-   __cam2 = cam_max_size;
-   ram -= __cam2;
+   __max_low_memory = 0;
+   for (i = 0; ram  i  ARRAY_SIZE(cam); i++) {
+   unsigned int camsize = __ilog2(ram)  ~1U;
+   if (camsize  max_cam)
+   camsize = max_cam;
+   cam[i] = 1UL  camsize;
+   ram -= cam[i];
+   __max_low_memory += cam[i];
+
+   p += sprintf(p, %lu/, cam[i]  20);
}
+   for (; i  ARRAY_SIZE(cam); i++)
+   p += sprintf(p, 0/);
+   p[-1] = '\0';
 
-   printk(KERN_INFO Memory CAM mapping: CAM0=%ldMb, CAM1=%ldMb,
-CAM2=%ldMb residual: %ldMb\n,
-   __cam0  20, __cam1  20, __cam2  20,
-   (long int)((total_lowmem - __cam0 - __cam1 - __cam2)
-   20));
-   __max_low_memory = __cam0 + __cam1 + __cam2;
+   pr_info(Memory CAM mapping: %s Mb, residual: %ldMb\n, buf,
+   (total_lowmem - __max_low_memory)  20);
__initial_memory_limit_addr = memstart_addr + __max_low_memory;
 }
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 4/5] powerpc: booke: Make CAM entries used for lowmem configurable

2008-12-08 Thread Trent Piepho
On booke processors, the code that maps low memory only uses up to three
CAM entries, even though there are sixteen and nothing else uses them.

Make this number configurable in the advanced options menu along with max
low memory size.  If one wants 1 GB of lowmem, then it's typically
necessary to have four CAM entries.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/Kconfig|   16 
 arch/powerpc/mm/fsl_booke_mmu.c |6 +-
 2 files changed, 21 insertions(+), 1 deletions(-)

diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
index be4f99b..2bb645c 100644
--- a/arch/powerpc/Kconfig
+++ b/arch/powerpc/Kconfig
@@ -696,6 +696,22 @@ config LOWMEM_SIZE
hex Maximum low memory size (in bytes) if LOWMEM_SIZE_BOOL
default 0x3000
 
+config LOWMEM_CAM_NUM_BOOL
+   bool Set number of CAMs to use to map low memory
+   depends on ADVANCED_OPTIONS  FSL_BOOKE
+   help
+ This option allows you to set the maximum number of CAM slots that
+ will be used to map low memory.  There are a limited number of slots
+ available and even more limited number that will fit in the L1 MMU.
+ However, using more entries will allow mapping more low memory.  This
+ can be useful in optimizing the layout of kernel virtual memory.
+
+ Say N here unless you know what you are doing.
+
+config LOWMEM_CAM_NUM
+   int Number of CAMs to use to map low memory if LOWMEM_CAM_NUM_BOOL
+   default 3
+
 config RELOCATABLE
bool Build a relocatable kernel (EXPERIMENTAL)
depends on EXPERIMENTAL  ADVANCED_OPTIONS  FLATMEM  FSL_BOOKE
diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index 1dabe1a..73aa9b7 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -56,10 +56,14 @@
 
 extern void loadcam_entry(unsigned int index);
 unsigned int tlbcam_index;
-static unsigned long cam[3];
+static unsigned long cam[CONFIG_LOWMEM_CAM_NUM];
 
 #define NUM_TLBCAMS(16)
 
+#if defined(CONFIG_LOWMEM_CAM_NUM_BOOL)  (CONFIG_LOWMEM_CAM_NUM = 
NUM_TLBCAMS)
+#error LOWMEM_CAM_NUM must be less than NUM_TLBCAMS
+#endif
+
 struct tlbcam TLBCAM[NUM_TLBCAMS];
 
 struct tlbcamrange {
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 5/5] powerpc: booke: Allow larger CAM sizes than 256 MB

2008-12-08 Thread Trent Piepho
The code that maps kernel low memory would only use page sizes up to 256
MB.  On E500v2 pages up to 4 GB are supported.

However, a page must be aligned to a multiple of the page's size.  I.e.
256 MB pages must aligned to a 256 MB boundary.  This was enforced by a
requirement that the physical and virtual addresses of the start of lowmem
be aligned to 256 MB.  Clearly requiring 1GB or 4GB alignment to allow
pages of that size isn't acceptable.

To solve this, I simply have adjust_total_lowmem() take alignment into
account when it decides what size pages to use.  Give it PAGE_OFFSET =
0x7000_, PHYSICAL_START = 0x3000_, and 2GB of RAM, and it will map
pages like this:
PA 0x3000_ VA 0x7000_ Size 256 MB
PA 0x4000_ VA 0x8000_ Size 1 GB
PA 0x8000_ VA 0xC000_ Size 256 MB
PA 0x9000_ VA 0xD000_ Size 256 MB
PA 0xA000_ VA 0xE000_ Size 256 MB

Because the lowmem mapping code now takes alignment into account,
PHYSICAL_ALIGN can be lowered from 256 MB to 64 MB.  Even lower might be
possible.  The lowmem code will work down to 4 kB but it's possible some of
the boot code will fail before then.  Poor alignment will force small pages
to be used, which combined with the limited number of TLB1 pages available,
will result in very little memory getting mapped.  So alignments less than
64 MB probably aren't very useful anyway.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/Kconfig|2 +-
 arch/powerpc/mm/fsl_booke_mmu.c |   14 +-
 2 files changed, 14 insertions(+), 2 deletions(-)

diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
index 2bb645c..a7b6b8f 100644
--- a/arch/powerpc/Kconfig
+++ b/arch/powerpc/Kconfig
@@ -776,7 +776,7 @@ config PHYSICAL_START
 
 config PHYSICAL_ALIGN
hex
-   default 0x1000 if FSL_BOOKE
+   default 0x0400 if FSL_BOOKE
help
  This value puts the alignment restrictions on physical address
  where kernel is loaded and run from. Kernel is compiled for an
diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index 73aa9b7..0b9ba6b 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -183,9 +183,14 @@ void __init
 adjust_total_lowmem(void)
 {
phys_addr_t ram;
-   unsigned int max_cam = 28;  /* 2^28 = 256 Mb */
+   unsigned int max_cam = (mfspr(SPRN_TLB1CFG)  16)  0xff;
char buf[ARRAY_SIZE(cam) * 5 + 1], *p = buf;
int i;
+   unsigned long virt = PAGE_OFFSET  0xUL;
+   unsigned long phys = memstart_addr  0xUL;
+
+   /* Convert (4^max) kB to (2^max) bytes */
+   max_cam = max_cam * 2 + 10;
 
/* adjust lowmem size to __max_low_memory */
ram = min((phys_addr_t)__max_low_memory, (phys_addr_t)total_lowmem);
@@ -194,11 +199,18 @@ adjust_total_lowmem(void)
__max_low_memory = 0;
for (i = 0; ram  i  ARRAY_SIZE(cam); i++) {
unsigned int camsize = __ilog2(ram)  ~1U;
+   unsigned int align = __ffs(virt | phys)  ~1U;
+
+   if (camsize  align)
+   camsize = align;
if (camsize  max_cam)
camsize = max_cam;
+
cam[i] = 1UL  camsize;
ram -= cam[i];
__max_low_memory += cam[i];
+   virt += cam[i];
+   phys += cam[i];
 
p += sprintf(p, %lu/, cam[i]  20);
}
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] POWERPC: Add cached region support to physmap_of MTD driver

2008-12-07 Thread Trent Piepho
The MTD system supports operation where a direct mapped flash chip is
mapped twice.  The normal mapping is a standard ioremap(), which is
non-cached and guarded on powerpc.  The second mapping is used only for
reads and can be cached and non-guarded.  Currently, only the pxa2xx
mapping driver makes use of this feature.  This patch adds support to the
physmap_of driver on PPC32 platforms for this cached mapping mode.

Because the flash chip doesn't participate in the cache coherency protocol,
it's necessary to invalidate the cache for parts of flash that are modified
with a program or erase operation.  This is platform specific, for instance
the pxa2xx driver uses an ARM specific function.  This patch adds
invalidate_dcache_icache_range() for PPC32 and uses it.  Because of XIP,
it's entirely possible that the flash might be in the icache(*), so the
existing invalidate_dcache_range() function isn't enough.

Of course, a cached mapping can increase performance if the data is read
from cache instead of flash.  But less obvious is that it can provide a
significant performance increase for cold-cache reads that still come from
flash.  It allows efficient back-to-back reads and if the flash chip 
controller support page burst mode, it allows that to be used as well.

The figures are for *cold-cache* read performance, measured on a Freescale
MPC8572 controlling a Spansion S29GL064N NOR flash chip.  With and without
the flash being mapped cached and with and without the localbus controller
being programmed to use page burst mode:

Non-cached, w/o bursts: 13.61 MB/s
Non-cached, w/ bursts:  13.61 MB/s
Cached, w/o bursts: 16.75 MB/s 23% increase
Cached, w/ bursts:  44.79 MB/s 229% increase!

Even without any cache hits, the cached mapping provides a significant
increase in performance via improved bus utilization.  Enabling burst
transfers is even more significant.

(*) The MTD device's -point() method, which is the mechanism for
supporting mmap and XIP, only allows for mmapping the uncached region.  So
you can't actually XIP anything in the cache.  But this could be fixed.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
Should this go in via powerpc tree or mtd?

 arch/powerpc/include/asm/cacheflush.h |2 ++
 arch/powerpc/kernel/misc_32.S |   21 +
 drivers/mtd/maps/physmap_of.c |   20 
 3 files changed, 43 insertions(+), 0 deletions(-)

diff --git a/arch/powerpc/include/asm/cacheflush.h 
b/arch/powerpc/include/asm/cacheflush.h
index ba667a3..385c26c 100644
--- a/arch/powerpc/include/asm/cacheflush.h
+++ b/arch/powerpc/include/asm/cacheflush.h
@@ -49,6 +49,8 @@ extern void flush_dcache_range(unsigned long start, unsigned 
long stop);
 #ifdef CONFIG_PPC32
 extern void clean_dcache_range(unsigned long start, unsigned long stop);
 extern void invalidate_dcache_range(unsigned long start, unsigned long stop);
+extern void invalidate_dcache_icache_range(unsigned long start,
+  unsigned long stop);
 #endif /* CONFIG_PPC32 */
 #ifdef CONFIG_PPC64
 extern void flush_inval_dcache_range(unsigned long start, unsigned long stop);
diff --git a/arch/powerpc/kernel/misc_32.S b/arch/powerpc/kernel/misc_32.S
index bdc8b0e..ad12c9a 100644
--- a/arch/powerpc/kernel/misc_32.S
+++ b/arch/powerpc/kernel/misc_32.S
@@ -636,6 +636,27 @@ _GLOBAL(invalidate_dcache_range)
blr
 
 /*
+ * Like above, but invalidate both the D-cache and I-cache.  Used when a cached
+ * region has been modified from a source that does not participate in the 
cache
+ * coherency protocol.
+ *
+ * invalidate_dcache_icache_range(unsigned long start, unsigned long stop)
+ */
+_GLOBAL(invalidate_dcache_icache_range)
+   clrrwi  r3, r3, L1_CACHE_SHIFT  /* start = ~((1SHIFT)-1) */
+   subfr4,r3,r4
+   addir4,r4,L1_CACHE_BYTES-1
+   srwi.   r4,r4,L1_CACHE_SHIFT/* count = (start-stop+BYTES-1)/BYTES */
+   beqlr   /* if (!count) return */
+   mtctr   r4
+1: dcbi0,r3
+   icbi0,r3
+   addir3,r3,L1_CACHE_BYTES
+   bdnz1b
+   sync/* wait for [id]cbi's to get to ram */
+   blr
+
+/*
  * Flush a particular page from the data cache to RAM.
  * Note: this is necessary because the instruction cache does *not*
  * snoop from the data cache.
diff --git a/drivers/mtd/maps/physmap_of.c b/drivers/mtd/maps/physmap_of.c
index 5fcfec0..e834298 100644
--- a/drivers/mtd/maps/physmap_of.c
+++ b/drivers/mtd/maps/physmap_of.c
@@ -32,6 +32,16 @@ struct of_flash {
 #endif
 };
 
+#ifdef CONFIG_PPC32
+#include asm/cacheflush.h
+static void ppc32_inval_cache(struct map_info *map, unsigned long from,
+ ssize_t len)
+{
+   invalidate_dcache_icache_range((unsigned long)map-cached + from,
+  (unsigned long)map-cached + from + len);
+}
+#endif
+
 #ifdef CONFIG_MTD_PARTITIONS
 #define OF_FLASH_PARTS

Re: [PATCH] powerpc: Fix bogus cache flushing on all 40x and BookE processors

2008-12-03 Thread Trent Piepho
On Tue, 2 Dec 2008, Benjamin Herrenschmidt wrote:
 On Tue, 2008-12-02 at 01:36 -0600, Kumar Gala wrote:

 #define CPU_FTRS_E200   (CPU_FTR_USE_TB | CPU_FTR_SPE_COMP | \
 CPU_FTR_NODSISRALIGN | CPU_FTR_COHERENT_ICACHE | \
 -   CPU_FTR_UNIFIED_ID_CACHE)
 +   CPU_FTR_UNIFIED_ID_CACHE | CPU_FTR_NOEXECUTE)
 #define CPU_FTRS_E500   (CPU_FTR_MAYBE_CAN_DOZE | CPU_FTR_USE_TB | \
 -   CPU_FTR_SPE_COMP | CPU_FTR_MAYBE_CAN_NAP | CPU_FTR_NODSISRALIGN)
 +   CPU_FTR_SPE_COMP | CPU_FTR_MAYBE_CAN_NAP |
 CPU_FTR_NODSISRALIGN \

 Added a '|' at the end of the line before the escape

 Right. Will send a new patch tomorrow. Appart from that, have you
 verified it doesn't have any adverse effects for you ? I did some quick
 tests on 440 and things seem to be fine.


#ifdef __powerpc64__
#define LONG_ASM_CONST(x)   ASM_CONST(x)
#else
#define LONG_ASM_CONST(x)   0
#endif

#define CPU_FTR_NOEXECUTE   LONG_ASM_CONST(0x0008)

Am I not looking at the right code?  Since e200 and e500 aren't powerpc64,
doesn't adding CPU_FTR_NOEXECUTE have no effect at all?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: __cpu_up vs. start_secondary race?

2008-12-02 Thread Trent Piepho
On Tue, 2 Dec 2008, Nathan Lynch wrote:
 Apart from barriers (or lack thereof), the fact that __cpu_up gives up
 after a more-or-less arbitrary period seems... well, arbitrary.  If we
 get to Processor X is stuck then something is seriously wrong:
 there's either a kernel bug or a platform issue, and the CPU just
 kicked is in an unknown state.  Polling indefinitely seems safer, no?

I recently fixed a bug that did this.  There was a bug in how the secondary
CPU's memory was mapped (in some non-mailine code, not fixed).  It was nice
to get the warning and have the kernel not hang.  On embedded systems with
only network access and no persistent storage for system logs, a kernel
hang is a lot more a pain.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [U-Boot] NAND only (no NOR)

2008-12-02 Thread Trent Piepho
On Wed, 3 Dec 2008, Sean MacLennan wrote:
 Yes, I would recommend to do it this way if possible. A small NOR for
 U-Boot and environment and everything else in NAND. This makes things
 much easier. But I understand that this is sometimes a problem with
 space (2 FLASH chips) and costs.

 Mainly cost. We didn't want to pay for a second chip.

I think for NAND the latches necessary to de-multiplex the localbus aren't
necessary like they are for NOR?  On our board the latches might even take
more space than the flash chip.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: i2c-mpc clocking scheme

2008-12-01 Thread Trent Piepho
On Mon, 1 Dec 2008, Andr? Schwarz wrote:
 Timur Tabi wrote:
  Trent Piepho wrote:

 
   Seems like it should keep the clock registers at what u-boot set them 
   too.
  

  Or we could have U-Boot put the i2c clock frequency into the I2C node, and
  let
  the driver program the hardware again.  That would keep the ugliness in
  U-Boot.

 
 Wouldn't it be easier to omit frequency re-programming at all ?
 Maybe configurable for non U-Boot users ...

That's what I'm thinking too.  Calculating the settings for a given bus
frequency, even with the system specific source clock provided by u-boot,
involves either a complex algorithm or a big ugly black box table that's
even larger than the algorithm.  I also think it's different for 8xxx and
52xx.

On the other hand just keeping the clock the same doesn't require any code
at all.

U-boot could pass in bus-frequency to let software know the speed of the
I2C bus from Linux.  Seems like a standard property for bus nodes.

There could be a current-speed property that tells linux to keep the
registers the same, in case we have to worry about u-boot not programming
the i2c clock.  I think the serial drivers have something like this.___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev

Re: i2c-mpc clocking scheme

2008-12-01 Thread Trent Piepho
On Mon, 1 Dec 2008, Scott Wood wrote:
 Trent Piepho wrote:
  U-boot could pass in bus-frequency to let software know the speed of the
  I2C bus from Linux.  Seems like a standard property for bus nodes.

 clock-frequency is standard, though it should probably be the input frequency 
 rather than the bus frequency, in case the OS really does want to change it 
 (maybe making the bus run faster when accessing faster devices).

For a bus device like an i2c controller, you really have two clocks.  The
input clock the controller runs from and the speed it runs the bus at.  One
could say that one clock is for the device node and the other clock is for
the device's sub-nodes.

Linux doesn't have an API for setting I2C bus speed.  If it did, then
adding support for it to i2c-mpc if there was demand would really be
another patch.  Right now the problem is that Linux programs the I2C
controller stupidly and undoes u-boot's (better) settings.

  There could be a current-speed property that tells linux to keep the
  registers the same,

 That would be a bit different from the way it's used in serial nodes, where 
 current-speed is simply a description of the baud rate that corresponds to 
 the current divider setting.  I'm not sure that it makes as much sense for 
 i2c, as you don't have the shared state on the other end that depends on 
 maintaining the exact same speed.

The Linux code could use current-speed to know if it should program the
registers.  I.e., if current-speed is present and non-zero, then leave the
frequency registers alone.  Otherwise u-boot or whatever might not have
programmed the I2C controller and the driver can do what it's doing now.

 When does the guest really care what the specific i2c bus frequency is, if 
 it's not going to change it?

I don't know of a real reason.  Maybe an I2C device where the clock speed
makes a difference?  Maximum polling rate or something?  Is there reason
the CPU clock and the CCB frequency need to be in the device tree?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] of/gpio: Implement of_get_gpio_flags()

2008-11-28 Thread Trent Piepho
On Thu, 27 Nov 2008, Anton Vorontsov wrote:
 This function is alike to the simple of_get_gpio(), but accepts new
 argument: flags. This new function will be used by the drivers that
 need to retrieve additional GPIO information, such as active-low flag.

 Signed-off-by: Anton Vorontsov [EMAIL PROTECTED]

So you want to do the clean up patch later?

 + /*
 +  * We're discouraging gpio_cells  2, since that way you'll have to
 +  * write your own xlate function (that will have to retrive the GPIO
 +  * number and the flags from a single gpio cell -- this is possible,
 +  * but not recommended).
 +  */
 + if (of_gc-gpio_cells  2) {
 + WARN_ON(1);
 + return -EINVAL;
 + }

If you're not going to allow 1 cell anymore (which should perhaps be
mentioned in the changelog), you could just check that when the of_gpio
chip is registered.  There's no need to see if of_gc-gpio_cells has
changed each time a driver maps a GPIO.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: i2c-mpc clocking scheme

2008-11-28 Thread Trent Piepho
On Thu, 27 Nov 2008, Andre Schwarz wrote:
 Timur Tabi schrieb:
 On Thu, Nov 27, 2008 at 9:00 AM, Andre Schwarz
 [EMAIL PROTECTED] wrote:

 All,

 is anybody working on some improvements regarding configurable I2C
 frequency inside the i2c-mpc driver ?

 If not - would anybody be intersted in getting this done, i.e.
 configurable via device tree ?


 Maybe I'm missing something, but U-Boot configures the I2C bus speed.
 It does this because the algorithm is specific to the SOC itself.  For
 example, the 8544 is different from the 8548.  It would be a mess to
 duplicate this code in the kernel.


 You're right regarding U-Boot, but the i2c-mpc driver overwrites the
 frequency divider register on all chips.

 I'm not happy with a fixed 0x3f @ MPC5200 which results in 65kHz ... :-(

 Have a look at line 163 in drivers/i2c/busses/i2c-mpc.c

Seems like it should keep the clock registers at what u-boot set them too.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v2] of_gpio: Return GPIO flags from of_get_gpio()

2008-11-26 Thread Trent Piepho
On Thu, 27 Nov 2008, Paul Mackerras wrote:
 Anton Vorontsov writes:

 Can we apply it? Paul, Benjamin?

 The patchwork url for this patch is:
 http://patchwork.ozlabs.org/patch/6650/


 Thanks!

  drivers/mtd/nand/fsl_upm.c  |2 +-
  drivers/net/fs_enet/fs_enet-main.c  |2 +-
  drivers/net/phy/mdio-ofgpio.c   |4 ++--
  drivers/of/gpio.c   |   13 ++---
  drivers/serial/cpm_uart/cpm_uart_core.c |2 +-
  include/linux/of_gpio.h |   21 +
  6 files changed, 32 insertions(+), 12 deletions(-)

 That would need acks from Jeff Garzik and David Woodhouse.

 Alternatively you could add a new function (called, for instance,
 of_get_gpio_flags) with the extra parameter to eliminate the need to
 change any drivers at this stage, since they all seem to pass NULL for
 the flags argument.

But if we did this every time any exported function needs to change, think
how bloated the API would be with cruft.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: 8572E - machine check pin (MCP0)

2008-11-24 Thread Trent Piepho
On Mon, 24 Nov 2008, Morrison, Tom wrote:
 Running 2.6.23.25 kernel...

 I have an external watchdog timer that is going off - and pulsing into
 the MCP0 of the 8572E. I get the printk indicating that the MCP0 went
 off - the problem is - how do I clear the condition that caused this
 because my hardware engineer swears that the pulse is ONLY 250ms - and
 after resetting several status registers (mcpsumr  rst
 (because my hardware engineer swears that the pulse is ONLY 250ms long
 (and I have a delay after my printk of 250ms)) - so I am pretty sure

 I am resetting the conditions mcpsumr (also, extra: the rstsr),
 but after writing mcpsumr - and reading back - it still has
 the mcp0 bit set?

 Where else do I need to reset the status - I think I am doing it
 right...
 but it isn't clearing the exception - and it 'dies' the next time
 through
 this (why is another problem - but first, I'd like to know why the
 condition
 is NOT being cleared...at all)...

SRESET# also sets MCP0 and MCP1, maybe that is on?

I'd also check the EMCP bit in SPRN_HID0 (on core 0 for MCP0).
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 4/4] leds: Let GPIO LEDs keep their current state

2008-11-20 Thread Trent Piepho
On Mon, 17 Nov 2008, Richard Purdie wrote:
 On Fri, 2008-10-24 at 16:09 -0700, Trent Piepho wrote:
 +if (template-keep_state)
 +state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
 +else
 +state = template-default_state;

  state = of_get_property(child, default-state, NULL);
  led.default_state = state  !strcmp(state, on);
 +led.keep_state = state  !strcmp(state, keep);

 +++ b/include/linux/leds.h
 @@ -138,7 +138,8 @@ struct gpio_led {
  const char *default_trigger;
  unsignedgpio;
  u8  active_low;
 -u8  default_state;
 +u8  default_state;  /* 0 = off, 1 = on */
 +u8  keep_state; /* overrides default_state */
  };

 How about something simpler here, just make default state have three
 different values - keep, on and off? I'm not keen on having two
 different state variables like this.

I thought of that, but it ends up being more complex.  Instead of just
using:
static const struct gpio_led myled = {
.name = something,
.keep_state = 1,
}

You'd do something like this:
.default_state = LEDS_GPIO_DEFSTATE_KEEP,

Is that better?  The constants for on/off/keep are one more thing you have
to look-up and remember when defining leds.  The code in the leds-gpio
driver ends up getting more complex to deal with one tristate vs two
booleans.

This is a patch to change to a tristate.  I don't think it's an
improvement.  More symbols defined, more code, extra stuff to remember
when defining leds, and removing the field from struct gpio_led doesn't
make it smaller due to padding.

diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index bb2a234..8a7303c 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,10 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   if (template-keep_state)
+   if (template-default_state == LEDS_GPIO_DEFSTATE_KEEP)
state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
else
-   state = template-default_state;
+   state = (template-default_state == LEDS_GPIO_DEFSTATE_ON);
led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;

gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
@@ -268,8 +268,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
-   led.default_state = state  !strcmp(state, on);
-   led.keep_state = state  !strcmp(state, keep);
+   if (state) {
+   if (!strcmp(state, keep)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_KEEP;
+   } else if(!strcmp(state, on)) {
+   led.default_state = LEDS_GPIO_DEFSTATE_ON;
+   } else {
+   led.default_state = LEDS_GPIO_DEFSTATE_OFF;
+   }
+   }

ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index c51b625..f4a125c 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,9 +138,12 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;  /* 0 = off, 1 = on */
-   u8  keep_state; /* overrides default_state */
+   u8  default_state;
+   /* default_state should be one of LEDS_GPIO_DEFSTATE_(ON|OFF|KEEP) */
  };
+#define LEDS_GPIO_DEFSTATE_OFF 0
+#define LEDS_GPIO_DEFSTATE_ON  1
+#define LEDS_GPIO_DEFSTATE_KEEP2

  struct gpio_led_platform_data {
int num_leds;
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] powerpc: L2 cache size wrong in 8572DS dts

2008-11-19 Thread Trent Piepho
It's 1MB, not 512KB.  Newer U-Boots will fix this entry, but that's no
reason to have the wrong value in the dts.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Kumar Gala [EMAIL PROTECTED]
---
 arch/powerpc/boot/dts/mpc8572ds.dts |2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/arch/powerpc/boot/dts/mpc8572ds.dts 
b/arch/powerpc/boot/dts/mpc8572ds.dts
index cadd465..5c69b2f 100644
--- a/arch/powerpc/boot/dts/mpc8572ds.dts
+++ b/arch/powerpc/boot/dts/mpc8572ds.dts
@@ -90,7 +90,7 @@
compatible = fsl,mpc8572-l2-cache-controller;
reg = 0x2 0x1000;
cache-line-size = 32; // 32 bytes
-   cache-size = 0x8; // L2, 512K
+   cache-size = 0x10; // L2, 1M
interrupt-parent = mpic;
interrupts = 16 2;
};
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] powerpc: Better setup of boot page TLB entry

2008-11-19 Thread Trent Piepho
The initial TLB mapping for the kernel boot didn't set the memory coherent
attribute, MAS2[M], in SMP mode.

If this code supported booting a secondary processor, which it doesn't yet,
but suppose it did, then when a secondary processor boots, it would have
probably signaled the primary processor by setting a variable called
something like __secondary_hold_acknowledge.  However, due to the lack of
the M bit, the primary processor would not have snooped the transaction
(even if a transaction were broadcast).  If primary CPU's L1 D-cache had a
copy, it would not have been flushed and the CPU would have never seen the
ack.  Which would have resulted in the primary CPU spinning for a long
time, perhaps a full second before it would have given up, while it would
have waited for the ack from the secondary CPU that it wouldn't have been
able to see because of the stale cache.

The value of MAS2 for the boot page TLB1 entry is a compile time constant,
so there is no need to calculate it in powerpc assembly language.

Also, from the MPC8572 manual section 6.12.5.3, Bits that represent
offsets within a page are ignored and should be cleared. Existing code
didn't clear them, this code does.

The same when the page of KERNELBASE is found; we don't need to use asm to
mask the lower 12 bits off.

In the code that computes the address to rfi from, don't hard code the
offset to 24 bytes, but have the assembler figure that out for us.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Kumar Gala [EMAIL PROTECTED]
---
 arch/powerpc/include/asm/mmu-fsl-booke.h |2 ++
 arch/powerpc/kernel/head_fsl_booke.S |   22 +-
 2 files changed, 15 insertions(+), 9 deletions(-)

diff --git a/arch/powerpc/include/asm/mmu-fsl-booke.h 
b/arch/powerpc/include/asm/mmu-fsl-booke.h
index 925d93c..5588a41 100644
--- a/arch/powerpc/include/asm/mmu-fsl-booke.h
+++ b/arch/powerpc/include/asm/mmu-fsl-booke.h
@@ -40,6 +40,8 @@
 #define MAS2_M 0x0004
 #define MAS2_G 0x0002
 #define MAS2_E 0x0001
+#define MAS2_EPN_MASK(size)(~0  (2*(size) + 10))
+#define MAS2_VAL(addr, size, flags)((addr)  MAS2_EPN_MASK(size) | (flags))
 
 #define MAS3_RPN   0xF000
 #define MAS3_U00x0200
diff --git a/arch/powerpc/kernel/head_fsl_booke.S 
b/arch/powerpc/kernel/head_fsl_booke.S
index 590304c..e621eac 100644
--- a/arch/powerpc/kernel/head_fsl_booke.S
+++ b/arch/powerpc/kernel/head_fsl_booke.S
@@ -235,36 +235,40 @@ skpinv:   addir6,r6,1 /* 
Increment */
tlbivax 0,r9
TLBSYNC
 
+/* The mapping only needs to be cache-coherent on SMP */
+#ifdef CONFIG_SMP
+#defineM_IF_SMPMAS2_M
+#else
+#define M_IF_SMP   0
+#endif
+
 /* 6. Setup KERNELBASE mapping in TLB1[0] */
lis r6,0x1000   /* Set MAS0(TLBSEL) = TLB1(1), ESEL = 0 
*/
mtspr   SPRN_MAS0,r6
lis r6,(MAS1_VALID|MAS1_IPROT)@h
ori r6,r6,(MAS1_TSIZE(BOOKE_PAGESZ_64M))@l
mtspr   SPRN_MAS1,r6
-   li  r7,0
-   lis r6,[EMAIL PROTECTED]
-   ori r6,r6,[EMAIL PROTECTED]
-   rlwimi  r6,r7,0,20,31
+   lis r6,MAS2_VAL(PAGE_OFFSET, BOOKE_PAGESZ_64M, M_IF_SMP)@h
+   ori r6,r6,MAS2_VAL(PAGE_OFFSET, BOOKE_PAGESZ_64M, M_IF_SMP)@l
mtspr   SPRN_MAS2,r6
mtspr   SPRN_MAS3,r8
tlbwe
 
 /* 7. Jump to KERNELBASE mapping */
-   lis r6,[EMAIL PROTECTED]
-   ori r6,r6,[EMAIL PROTECTED]
-   rlwimi  r6,r7,0,20,31
+   lis r6,(KERNELBASE  ~0xfff)@h
+   ori r6,r6,(KERNELBASE  ~0xfff)@l
lis r7,[EMAIL PROTECTED]
ori r7,r7,[EMAIL PROTECTED]
bl  1f  /* Find our address */
 1: mflrr9
rlwimi  r6,r9,0,20,31
-   addir6,r6,24
+   addir6,r6,(2f - 1b)
mtspr   SPRN_SRR0,r6
mtspr   SPRN_SRR1,r7
rfi /* start execution out of TLB1[0] entry 
*/
 
 /* 8. Clear out the temp mapping */
-   lis r7,0x1000   /* Set MAS0(TLBSEL) = 1 */
+2: lis r7,0x1000   /* Set MAS0(TLBSEL) = 1 */
rlwimi  r7,r5,16,4,15   /* Setup MAS0 = TLBSEL | ESEL(r5) */
mtspr   SPRN_MAS0,r7
tlbre
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] powerpc: Silence timebase sync code

2008-11-18 Thread Trent Piepho
On Tue, 18 Nov 2008, Michael Ellerman wrote:
 On Mon, 2008-11-17 at 14:22 -0800, Trent Piepho wrote:
 On Mon, 17 Nov 2008, Kumar Gala wrote:
 On Nov 17, 2008, at 3:58 PM, Trent Piepho wrote:

 It's over a dozen lines of output and doesn't appear to provide any useful
 information.  Even after looking at the code, I'm in the dark about what
 score 299, offset 250 means.

 Signed-off-by: Trent Piepho [EMAIL PROTECTED]
 ---
 +++ b/arch/powerpc/kernel/smp-tbsync.c
 @@ -113,7 +113,7 @@ void __devinit smp_generic_give_timebase(void)
 {
  int i, score, score2, old, min=0, max=5000, offset=1000;

 -  printk(Synchronizing timebase\n);
 +  pr_info(Synchronizing timebase\n);

 I think its useful to leave this as a printk.

 #define pr_info(fmt, arg...) \
  printk(KERN_INFO fmt, ##arg)

 Isn't printk with no level tag the same as KERN_INFO?

 Stuff like this should IMHO be printk(KERN_DEBUG ..)

 That way it will show up in the log as long as you boot with 'debug' on
 your command line, it doesn't require a kernel recompile to turn on. And
 at the same time it doesn't spam the boot log for a normal boot.

Originally my patched changed it to debug, but Kumar requested I keep it at
info level.  The timebase sync code might hang or be slow, so it's nice to
give a status output before doing it.  It seems just as good as most of the
info printks during boot.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] powerpc: Silence timebase sync code

2008-11-17 Thread Trent Piepho
It's over a dozen lines of output and doesn't appear to provide any useful
information.  Even after looking at the code, I'm in the dark about what
score 299, offset 250 means.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 arch/powerpc/kernel/smp-tbsync.c |   12 
 1 files changed, 4 insertions(+), 8 deletions(-)

diff --git a/arch/powerpc/kernel/smp-tbsync.c b/arch/powerpc/kernel/smp-tbsync.c
index bc892e6..b590135 100644
--- a/arch/powerpc/kernel/smp-tbsync.c
+++ b/arch/powerpc/kernel/smp-tbsync.c
@@ -113,7 +113,7 @@ void __devinit smp_generic_give_timebase(void)
 {
int i, score, score2, old, min=0, max=5000, offset=1000;
 
-   printk(Synchronizing timebase\n);
+   pr_info(Synchronizing timebase\n);
 
/* if this fails then this kernel won't work anyway... */
tbsync = kzalloc( sizeof(*tbsync), GFP_KERNEL );
@@ -123,14 +123,10 @@ void __devinit smp_generic_give_timebase(void)
while (!tbsync-ack)
barrier();
 
-   printk(Got ack\n);
-
/* binary search */
for (old = -1; old != offset ; offset = (min+max) / 2) {
score = start_contest(kSetAndTest, offset, NUM_ITER);
 
-   printk(score %d, offset %d\n, score, offset );
-
if( score  0 )
max = offset;
else
@@ -140,8 +136,8 @@ void __devinit smp_generic_give_timebase(void)
score = start_contest(kSetAndTest, min, NUM_ITER);
score2 = start_contest(kSetAndTest, max, NUM_ITER);
 
-   printk(Min %d (score %d), Max %d (score %d)\n,
-  min, score, max, score2);
+   pr_debug(Min %d (score %d), Max %d (score %d)\n,
+min, score, max, score2);
score = abs(score);
score2 = abs(score2);
offset = (score  score2) ? min : max;
@@ -155,7 +151,7 @@ void __devinit smp_generic_give_timebase(void)
if (score2 = score || score2  20)
break;
}
-   printk(Final offset: %d (%d/%d)\n, offset, score2, NUM_ITER );
+   pr_debug(Final offset: %d (%d/%d)\n, offset, score2, NUM_ITER);
 
/* exiting */
tbsync-cmd = kExit;
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] powerpc: Silence timebase sync code

2008-11-17 Thread Trent Piepho
On Mon, 17 Nov 2008, Kumar Gala wrote:
 On Nov 17, 2008, at 3:58 PM, Trent Piepho wrote:

 It's over a dozen lines of output and doesn't appear to provide any useful
 information.  Even after looking at the code, I'm in the dark about what
 score 299, offset 250 means.
 
 Signed-off-by: Trent Piepho [EMAIL PROTECTED]
 ---
 arch/powerpc/kernel/smp-tbsync.c |   12 
 1 files changed, 4 insertions(+), 8 deletions(-)
 
 diff --git a/arch/powerpc/kernel/smp-tbsync.c 
 b/arch/powerpc/kernel/smp-tbsync.c
 index bc892e6..b590135 100644
 --- a/arch/powerpc/kernel/smp-tbsync.c
 +++ b/arch/powerpc/kernel/smp-tbsync.c
 @@ -113,7 +113,7 @@ void __devinit smp_generic_give_timebase(void)
 {
  int i, score, score2, old, min=0, max=5000, offset=1000;
 
 -printk(Synchronizing timebase\n);
 +pr_info(Synchronizing timebase\n);

 I think its useful to leave this as a printk.

#define pr_info(fmt, arg...) \
 printk(KERN_INFO fmt, ##arg)

Isn't printk with no level tag the same as KERN_INFO?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH] powerpc: Repair device bindings documentation

2008-11-10 Thread Trent Piepho
Commit d0fc2eaaf4c56a95f5ed29b6bfb609e19714fc16 powerpc/fsl: Refactor
device bindings split out a number of device bindings from
booting-without-of.txt into separate files.  Having them all in one file
was a frequent source of merge conflicts.

However, in the next merge, 49997d75152b3d23c53b0fa730599f2f74c92c65, there
was another conflict.  Some of the bindings removed from
booting-without-of.txt were mistakenly added back in and the copies in
dts-bindings were kept as well.

This patch re-removes Freescale Display Interface and Freescale on board
FPGA and fixes the table of contents.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Kumar Gala [EMAIL PROTECTED]
---

Maybe this should go in 2.6.28, since it fixes a doc bug and before
anyone modifies the version of the docs that should have been deleted.

 Documentation/powerpc/booting-without-of.txt |   65 --
 1 files changed, 10 insertions(+), 55 deletions(-)

diff --git a/Documentation/powerpc/booting-without-of.txt 
b/Documentation/powerpc/booting-without-of.txt
index 02ea9a9..0ab0230 100644
--- a/Documentation/powerpc/booting-without-of.txt
+++ b/Documentation/powerpc/booting-without-of.txt
@@ -41,25 +41,14 @@ Table of Contents
   VI - System-on-a-chip devices and nodes
 1) Defining child nodes of an SOC
 2) Representing devices without a current OF specification
-  a) MDIO IO device
-  b) Gianfar-compatible ethernet nodes
-  c) PHY nodes
-  d) Interrupt controllers
-  e) I2C
-  f) Freescale SOC USB controllers
-  g) Freescale SOC SEC Security Engines
-  h) Board Control and Status (BCSR)
-  i) Freescale QUICC Engine module (QE)
-  j) CFI or JEDEC memory-mapped NOR flash
-  k) Global Utilities Block
-  l) Freescale Communications Processor Module
-  m) Chipselect/Local Bus
-  n) 4xx/Axon EMAC ethernet nodes
-  o) Xilinx IP cores
-  p) Freescale Synchronous Serial Interface
- q) USB EHCI controllers
-  r) MDIO on GPIOs
-  s) SPI busses
+  a) PHY nodes
+  b) Interrupt controllers
+  c) CFI or JEDEC memory-mapped NOR flash
+  d) 4xx/Axon EMAC ethernet nodes
+  e) Xilinx IP cores
+  f) USB EHCI controllers
+  g) MDIO on GPIOs
+  h) SPI busses
 
   VII - Marvell Discovery mv64[345]6x System Controller chips
 1) The /system-controller node
@@ -1830,41 +1819,7 @@ platforms are moved over to use the 
flattened-device-tree model.
   big-endian;
   };
 
-r) Freescale Display Interface Unit
-
-The Freescale DIU is a LCD controller, with proper hardware, it can also
-drive DVI monitors.
-
-Required properties:
-- compatible : should be fsl-diu.
-- reg : should contain at least address and length of the DIU register
-  set.
-- Interrupts : one DIU interrupt should be describe here.
-
-Example (MPC8610HPCD)
-   [EMAIL PROTECTED] {
-   compatible = fsl,diu;
-   reg = 0x2c000 100;
-   interrupts = 72 2;
-   interrupt-parent = mpic;
-   };
-
-s) Freescale on board FPGA
-
-This is the memory-mapped registers for on board FPGA.
-
-Required properities:
-- compatible : should be fsl,fpga-pixis.
-- reg : should contain the address and the lenght of the FPPGA register
-  set.
-
-Example (MPC8610HPCD)
-   [EMAIL PROTECTED] {
-   compatible = fsl,fpga-pixis;
-   reg = 0xe800 32;
-   };
-
-   r) MDIO on GPIOs
+   g) MDIO on GPIOs
 
Currently defined compatibles:
- virtual,gpio-mdio
@@ -1884,7 +1839,7 @@ platforms are moved over to use the flattened-device-tree 
model.
 qe_pio_c 6;
};
 
-s) SPI (Serial Peripheral Interface) busses
+h) SPI (Serial Peripheral Interface) busses
 
 SPI busses can be described with a node for the SPI master device
 and a set of child nodes for each SPI slave on the bus.  For this
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [v5] powerpc: gpio driver for mpc8349/8572/8610 and compatible

2008-10-30 Thread Trent Piepho
On Thu, 30 Oct 2008, Peter Korsgaard wrote:
 Trent == Trent Piepho [EMAIL PROTECTED] writes:
 Trent On Tue, 23 Sep 2008, Peter Korsgaard wrote:
  +- compatible : fsl,CHIP-gpio followed by fsl,mpc8349-gpio for
  +  83xx, fsl,mpc8572-gpio for 85xx and fsl,mpc8610-gpio for 86xx.

 Trent Why have the three different compatible settings when the code
 Trent doesn't do anything different?

 Purely for cosmetics / ease of use - As requested by Kumar:

 http://ozlabs.org/pipermail/linuxppc-dev/2008-September/062934.html

Though I see Scott didn't agree.

  +#define MPC8XXX_GPIO_PINS 32

 Trent 8572 has eight GPIOs.

 Doesn't matter - It's register interface is compatible. Most real
 world design with the other SoCs also don't have all 32 gpio pins
 available because of pin multiplexing.

Doesn't it seem flawed that 32 gpios will show up under debugfs and via the
sysfs interface, when it's known that there are only 8?

Since there is an 8572 compat property, it's not like it's not solvable.

 Trent I wrote an MPC8572 GPIO driver back in March, and posted it
 Trent internally at Freescale on June 2nd.  But it was just
 Trent ignored...  I wonder what your secret is to get Kumar to apply
 Trent your patches?  It's too bad this work keeps getting
 Trent duplicated.

 Did you try bribing? ;) No, seriously, why didn't you post it to
 linuxppc-dev, so the rest of the world would know about it?

Well, I get totally ignored posting to an internal Freescale list, it doesn't
seem like it will be any better posting to an external list.

 Trent But, I'm using the GPIOs to bit-bang a JTAG bus in the 20-30
 Trent MHz range.  The obvious GPIO driver is *much* too slow for
 Trent that.  I got less than 3 MHz, and your driver looks like it
 Trent might be slightly slower than my initial driver.

 I would write a dedicated driver for something like that instead of
 using gpiolib.

But the JTAG bus only uses four GPIOs, the other four get used for other
things with gpiolib, like gpio leds for example.  I also found it very handy
to be able to see and modify all the gpio lines, even the ones the JTAG driver
is using, via a sysfs interface to gpiolib.

 Gpiolib has quite some overhead compared to the actual work for
 changing a SoC gpio pin, but it also has some very nice

Certainly is does, but there are ways to make it faster.

 Trent So I went to a lot of effort to speed it up and managed to
 Trent increase GPIO performance by nearly a factor of 10.  Trying to
 Trent commit my driver at this point is probably hopeless and I
 Trent doubt anyone else cares about gpio speed.  But at least the
 Trent number of gpios for 8572 can be fixed.

 Sure, going dedicated always can improve performance. I recently did
 some work in u-boot talking directly to the mpc83xx spi controller and
 got ~5x throughput compared to the Linux driver.

It's not dedicated though.  The gpiolib interface is still used.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] gianfar: Omit TBI auto-negotiation based on device tree

2008-10-30 Thread Trent Piepho
On Tue, 28 Oct 2008, Nate Case wrote:
 Some SGMII PHYs don't auto-negotiate correctly with the TBI+SerDes
 interface on the mpc85xx processors.  Check for the sgmii-aneg-disable
 device tree flag and skip enabling auto-negotiation on the TBI
 side if present.  Full duplex 1000 Mbit/s will be assumed for the
 SGMII link to the PHY (note that this does not affect the link speed
 on the external side of the external PHY).

Note that there is a race in the tbi/serdes setup code.  The writes to the
TBI/SerDes with gfar_local_mdio_write() use the same MDIO bus registers as
phylib uses to talk to the real phy or phys.  There is no locking for
gfar_local_mdio vs phylib so they can (and will) clobber each other.

It doesn't usually happen, due to luck and general phylib slowness.  But I've
got some patches in 2.6.28 that speed up phylib and might makes this happen
more often...

But more relevant to your serdes problem, I also have a patch that prevents
restarting serdes auto-negotiation if the serdes link is already up.  My SGMII
PHY will auto-negotiate, but it takes about 3 seconds.  Avoiding an
unnecessary 3 second auto-negotiation when the gianfar device is opened lets
me cut my power-on to DHCP completion time in half.

I wonder if this would also fix your problem, without needing to add the extra
workaround?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/2] gianfar: Fix race in TBI/SerDes configuration

2008-10-30 Thread Trent Piepho
The init_phy() function attaches to the PHY, then configures the
SerDes-TBI link (in SGMII mode).  The TBI is on the MDIO bus with the PHY
(sort of) and is accessed via the gianfar's MDIO registers, using the
functions gfar_local_mdio_read/write(), which don't do any locking.

The previously attached PHY will start a work-queue on a timer, and
probably an irq handler as well, which will talk to the PHY and thus use
the MDIO bus.  This uses phy_read/write(), which have locking, but not
against the gfar_local_mdio versions.

The result is that PHY code will try to use the MDIO bus at the same time
as the SerDes setup code, corrupting the transfers.

Setting up the SerDes before attaching to the PHY will insure that there is
no race between the SerDes code and *our* PHY, but doesn't fix everything.
Typically the PHYs for all gianfar devices are on the same MDIO bus, which
is associated with the first gianfar device.  This means that the first
gianfar's SerDes code could corrupt the MDIO transfers for a different
gianfar's PHY.

The lock used by phy_read/write() is contained in the mii_bus structure,
which is pointed to by the PHY.  This is difficult to access from the
gianfar drivers, as there is no link between a gianfar device and the
mii_bus which shares the same MDIO registers.  As far as the device layer
and drivers are concerned they are two unrelated devices (which happen to
share registers).

Generally all gianfar devices' PHYs will be on the bus associated with the
first gianfar.  But this might not be the case, so simply locking the
gianfar's PHY's mii bus might not lock the mii bus that the SerDes setup
code is going to use.

We solve this by having the code that creates the gianfar platform device
look in the device tree for an mdio device that shares the gianfar's
registers.  If one is found the ID of its platform device is saved in the
gianfar's platform data.

A new function in the gianfar mii code, gfar_get_miibus(), can use the bus
ID to search through the platform devices for a gianfar_mdio device with
the right ID.  The platform device's driver data is the mii_bus structure,
which the SerDes setup code can use to lock the current bus.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
CC: Andy Fleming [EMAIL PROTECTED]
---
 arch/powerpc/sysdev/fsl_soc.c |   26 ++
 drivers/net/gianfar.c |7 +++
 drivers/net/gianfar_mii.c |   21 +
 drivers/net/gianfar_mii.h |3 +++
 include/linux/fsl_devices.h   |3 ++-
 5 files changed, 59 insertions(+), 1 deletions(-)

diff --git a/arch/powerpc/sysdev/fsl_soc.c b/arch/powerpc/sysdev/fsl_soc.c
index 01b884b..26ecb96 100644
--- a/arch/powerpc/sysdev/fsl_soc.c
+++ b/arch/powerpc/sysdev/fsl_soc.c
@@ -223,6 +223,8 @@ static int gfar_mdio_of_init_one(struct device_node *np)
if (ret)
return ret;
 
+   /* The gianfar device will try to use the same ID created below to find
+* this bus, to coordinate register access (since they share).  */
mdio_dev = platform_device_register_simple(fsl-gianfar_mdio,
res.start0xf, res, 1);
if (IS_ERR(mdio_dev))
@@ -394,6 +396,30 @@ static int __init gfar_of_init(void)
of_node_put(mdio);
}
 
+   /* Get MDIO bus controlled by this eTSEC, if any.  Normally only
+* eTSEC 1 will control an MDIO bus, not necessarily the same
+* bus that its PHY is on ('mdio' above), so we can't just use
+* that.  What we do is look for a gianfar mdio device that has
+* overlapping registers with this device.  That's really the
+* whole point, to find the device sharing our registers to
+* coordinate access with it.
+*/
+   for_each_compatible_node(mdio, NULL, fsl,gianfar-mdio) {
+   if (of_address_to_resource(mdio, 0, res))
+   continue;
+
+   if (res.start = r[0].start  res.end = r[0].end) {
+   /* Get the ID the mdio bus platform device was
+* registered with.  gfar_data.bus_id is
+* different because it's for finding a PHY,
+* while this is for finding a MII bus.
+*/
+   gfar_data.mdio_bus = res.start0xf;
+   of_node_put(mdio);
+   break;
+   }
+   }
+
ret =
platform_device_add_data(gfar_dev, gfar_data,
 sizeof(struct
diff --git a/drivers/net/gianfar.c b/drivers/net/gianfar.c
index 64b2011..249541a 100644
--- a/drivers/net/gianfar.c
+++ b/drivers/net/gianfar.c
@@ -586,6 +586,10 @@ static void gfar_configure_serdes

[PATCH 2/2] gianfar: Don't reset TBI-SerDes link if it's already up

2008-10-30 Thread Trent Piepho
The link may be up already via the chip's reset strapping, or though action
of U-Boot, or from the last time the interface was brought up.  Resetting
the link causes it to go down for several seconds.  This can significantly
increase the time from power-on to DHCP completion and a device being
accessible to the network.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Andy Fleming [EMAIL PROTECTED]
---
 drivers/net/gianfar.c |9 +
 1 files changed, 9 insertions(+), 0 deletions(-)

diff --git a/drivers/net/gianfar.c b/drivers/net/gianfar.c
index 249541a..83a5cb6 100644
--- a/drivers/net/gianfar.c
+++ b/drivers/net/gianfar.c
@@ -591,6 +591,14 @@ static void gfar_configure_serdes(struct net_device *dev)
if (bus)
mutex_lock(bus-mdio_lock);
 
+   /* If the link is already up, we must already be ok, and don't need to
+* configure and reset the TBI-SerDes link.  Maybe U-Boot configured
+* everything for us?  Resetting it takes the link down and requires
+* several seconds for it to come back.
+*/
+   if (gfar_local_mdio_read(regs, tbipa, MII_BMSR)  BMSR_LSTATUS)
+   goto done;
+
/* Single clk mode, mii mode off(for serdes communication) */
gfar_local_mdio_write(regs, tbipa, MII_TBICON, TBICON_CLK_SELECT);
 
@@ -601,6 +609,7 @@ static void gfar_configure_serdes(struct net_device *dev)
gfar_local_mdio_write(regs, tbipa, MII_BMCR, BMCR_ANENABLE |
BMCR_ANRESTART | BMCR_FULLDPLX | BMCR_SPEED1000);
 
+   done:
if (bus)
mutex_unlock(bus-mdio_lock);
 }
-- 
1.5.4.1

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH v2] of_gpio: Return GPIO flags from of_get_gpio()

2008-10-30 Thread Trent Piepho
The device binding spec for OF GPIOs defines a flags field, but there is
currently no way to get it.  This patch adds a parameter to of_get_gpio()
where the flags will be returned if non-NULL.  of_get_gpio() in turn passes
the parameter to the of_gpio_chip's xlate method, which can extract any
flags present from the gpio_spec.

The default (and currently only) of_gpio_chip xlate method,
of_gpio_simple_xlate(), is modified to do this.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
Acked-by: Grant Likely [EMAIL PROTECTED]
Acked-by: Anton Vorontsov [EMAIL PROTECTED]
---
Since this patch changes an API, it would be nice to get it into powerpc-next
soon so that people who have new patches that use this API, like Anton, can
base off it.

 drivers/mtd/nand/fsl_upm.c  |2 +-
 drivers/net/fs_enet/fs_enet-main.c  |2 +-
 drivers/net/phy/mdio-ofgpio.c   |4 ++--
 drivers/of/gpio.c   |   13 ++---
 drivers/serial/cpm_uart/cpm_uart_core.c |2 +-
 include/linux/of_gpio.h |   21 +
 6 files changed, 32 insertions(+), 12 deletions(-)

diff --git a/drivers/mtd/nand/fsl_upm.c b/drivers/mtd/nand/fsl_upm.c
index 024e3ff..a25d962 100644
--- a/drivers/mtd/nand/fsl_upm.c
+++ b/drivers/mtd/nand/fsl_upm.c
@@ -218,7 +218,7 @@ static int __devinit fun_probe(struct of_device *ofdev,
}
fun-upm_cmd_offset = *prop;
 
-   fun-rnb_gpio = of_get_gpio(ofdev-node, 0);
+   fun-rnb_gpio = of_get_gpio(ofdev-node, 0, NULL);
if (fun-rnb_gpio = 0) {
ret = gpio_request(fun-rnb_gpio, ofdev-dev.bus_id);
if (ret) {
diff --git a/drivers/net/fs_enet/fs_enet-main.c 
b/drivers/net/fs_enet/fs_enet-main.c
index cb51c1f..5a3c7ee 100644
--- a/drivers/net/fs_enet/fs_enet-main.c
+++ b/drivers/net/fs_enet/fs_enet-main.c
@@ -994,7 +994,7 @@ static int __devinit find_phy(struct device_node *np,
goto out_put_phy;
}
 
-   bus_id = of_get_gpio(mdionode, 0);
+   bus_id = of_get_gpio(mdionode, 0, NULL);
if (bus_id  0) {
struct resource res;
ret = of_address_to_resource(mdionode, 0, res);
diff --git a/drivers/net/phy/mdio-ofgpio.c b/drivers/net/phy/mdio-ofgpio.c
index 2ff9775..e3757c6 100644
--- a/drivers/net/phy/mdio-ofgpio.c
+++ b/drivers/net/phy/mdio-ofgpio.c
@@ -78,8 +78,8 @@ static int __devinit mdio_ofgpio_bitbang_init(struct mii_bus 
*bus,
 {
struct mdio_gpio_info *bitbang = bus-priv;
 
-   bitbang-mdc = of_get_gpio(np, 0);
-   bitbang-mdio = of_get_gpio(np, 1);
+   bitbang-mdc = of_get_gpio(np, 0, NULL);
+   bitbang-mdio = of_get_gpio(np, 1, NULL);
 
if (bitbang-mdc  0 || bitbang-mdio  0)
return -ENODEV;
diff --git a/drivers/of/gpio.c b/drivers/of/gpio.c
index 7cd7301..ae14215 100644
--- a/drivers/of/gpio.c
+++ b/drivers/of/gpio.c
@@ -22,11 +22,12 @@
  * of_get_gpio - Get a GPIO number from the device tree to use with GPIO API
  * @np:device node to get GPIO from
  * @index: index of the GPIO
+ * @flags: GPIO's flags are returned here if non-NULL
  *
  * Returns GPIO number to use with Linux generic GPIO API, or one of the errno
  * value on the error condition.
  */
-int of_get_gpio(struct device_node *np, int index)
+int of_get_gpio(struct device_node *np, int index, enum of_gpio_flags *flags)
 {
int ret;
struct device_node *gc;
@@ -59,7 +60,9 @@ int of_get_gpio(struct device_node *np, int index)
goto err1;
}
 
-   ret = of_gc-xlate(of_gc, np, gpio_spec);
+   if (flags)
+   *flags = 0;
+   ret = of_gc-xlate(of_gc, np, gpio_spec, flags);
if (ret  0)
goto err1;
 
@@ -77,19 +80,23 @@ EXPORT_SYMBOL(of_get_gpio);
  * @of_gc: pointer to the of_gpio_chip structure
  * @np:device node of the GPIO chip
  * @gpio_spec: gpio specifier as found in the device tree
+ * @flags: if non-NULL flags are returned here
  *
  * This is simple translation function, suitable for the most 1:1 mapped
  * gpio chips. This function performs only one sanity check: whether gpio
  * is less than ngpios (that is specified in the gpio_chip).
  */
 int of_gpio_simple_xlate(struct of_gpio_chip *of_gc, struct device_node *np,
-const void *gpio_spec)
+const void *gpio_spec, enum of_gpio_flags *flags)
 {
const u32 *gpio = gpio_spec;
 
if (*gpio  of_gc-gc.ngpio)
return -EINVAL;
 
+   if (flags  of_gc-gpio_cells  1)
+   *flags = gpio[1];
+
return *gpio;
 }
 EXPORT_SYMBOL(of_gpio_simple_xlate);
diff --git a/drivers/serial/cpm_uart/cpm_uart_core.c 
b/drivers/serial/cpm_uart/cpm_uart_core.c
index bde4b4b..7835cd4 100644
--- a/drivers/serial/cpm_uart/cpm_uart_core.c
+++ b/drivers/serial/cpm_uart/cpm_uart_core.c
@@ -1094,7 +1094,7 @@ static int cpm_uart_init_port(struct device_node *np

Re: [v5] powerpc: gpio driver for mpc8349/8572/8610 and compatible

2008-10-29 Thread Trent Piepho
On Tue, 23 Sep 2008, Peter Korsgaard wrote:
 +- compatible : fsl,CHIP-gpio followed by fsl,mpc8349-gpio for
 +  83xx, fsl,mpc8572-gpio for 85xx and fsl,mpc8610-gpio for 86xx.

Why have the three different compatible settings when the code doesn't do
anything different?

 +#define MPC8XXX_GPIO_PINS32

8572 has eight GPIOs.

I wrote an MPC8572 GPIO driver back in March, and posted it internally at
Freescale on June 2nd.  But it was just ignored...  I wonder what your secret
is to get Kumar to apply your patches?  It's too bad this work keeps getting
duplicated.

My patch started out *very* much like yours, except it pre-dated the OF gpio
controller stuff and of_mm_gpiochip so it didn't use that.

But, I'm using the GPIOs to bit-bang a JTAG bus in the 20-30 MHz range.  The
obvious GPIO driver is *much* too slow for that.  I got less than 3 MHz, and
your driver looks like it might be slightly slower than my initial driver.

So I went to a lot of effort to speed it up and managed to increase GPIO
performance by nearly a factor of 10.  Trying to commit my driver at this
point is probably hopeless and I doubt anyone else cares about gpio speed. 
But at least the number of gpios for 8572 can be fixed.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 1/4] of_gpio: Return GPIO flags from of_get_gpio()A

2008-10-29 Thread Trent Piepho
On Tue, 28 Oct 2008, Anton Vorontsov wrote:
 On Fri, Oct 24, 2008 at 04:08:58PM -0700, Trent Piepho wrote:
 + * @flags:  if non-NUll flags are returned here

 NULL, not NUll.

Thanks, fixed.

 + const void *gpio_spec, unsigned int *flags)

 Why you made it unsigned int? In my original patch, I used
 named enum, which is self-documenting type.

I started writing this patch before you posted yours, and I didn't think of
the enum.  But you have a good point so I'll switch to an enum.

 + * Flags as returned by OF GPIO chip's xlate function.
 + * These do not need to be the same as the flags in the GPIO specifier in 
 the
 + * OF device tree, but it's convenient if they are.  The mm chip OF GPIO
 + * driver works this way.

 This is not of_mm_gpio_chip specific.

of_mm_gpio_chip was just an example of a driver that uses the same flag format
for Linux and the OF binding.  I'll clarify the comment.

WRT changing the interface, Linux doesn't provide a stable kernel API. 
Functions that have been around far longer than of_get_gpio() and have far
more users have changed.  Yes, it is slightly annoying now.  But providing
backward compatibility for every single interface change will produce a
bloated and redundant API that will be around forever.

 Can you repost a fixed version with my Ack and Cc: Andrew Morton,
 Benjamin Herrenschmidt?

 I think this change should go into the 2.6.28, so that we can
 write new code on top of new API. Otherwise this change will cause
 issues in the next merge window.

If you can get your patch into Ben's -next tree before the high .28-RCs come
out, I can just rebase my patch to that tree and make the changes to any new
callers of of_get_gpio() that are there.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


OpenFirmware GPIO LED driver

2008-10-24 Thread Trent Piepho
This series of patches adds support for OpenFirmware bindings for GPIO based
LEDs.

I last posted a version of this in July but discussion of the OF binding
details didn't seem to be going anywhere.

I've since been contacted by some people who are actually using the previous
patches and have been motivated to try again.

All the users of this code are satisfied with the current version and it does
everything they need it to do.

The first patch extends the of_get_gpio() function to provide the gpio flags.

The way this already works (i.e., this is not something I'm adding, it's
what's already there) is that the OF gpio specifier is an opaque sequence of
words.  The GPIO controller driver (of which only one currently exists)
provides an -xlate() method that turns this into a Linux gpiolib gpio number. 
All current gpio controllers have flags in their gpio specifier, but there is
no way to get them.  So I extend the xlate method to also produce the flags in
a Linux format, the same way it produces a Linux gpio number.

The second patch adds OF bindings to the gpio-leds driver.  The existing code
is refactored so that almost all of the common code is shared between the two
binding methods.  Either or both bindings can be selected via Kconfig.  The
bindings do have one linux, property, but no one has been able to come up
with something close to workable that avoids this and still satisfies the
*requirement* that the default trigger be settable from the OF bindings.

The second and third patches add some additional capabilities for gpio leds
that some users need.

One is to have a LED start in the on state when it's made known to Linux. 
There is already a default-on trigger that does this, but it produces a
glitch where an LED that is already on will turn off then back on.  My (tiny)
patch avoids this problem.

The next lets an LED stay, without glitches, in whatever state it was already
in when it's made known to Linux.  It may have been put into this state by the
BIOS, firmware, bootloader, or the hardware itself.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/4] of_gpio: Return GPIO flags from of_get_gpio()

2008-10-24 Thread Trent Piepho
The device binding spec for OF GPIOs defines a flags field, but there is
currently no way to get it.  This patch adds a parameter to of_get_gpio()
where the flags will be returned if non-NULL.  of_get_gpio() in turn passes
the parameter to the of_gpio_chip's xlate method, which can extract any
flags present from the gpio_spec.

The default (and currently only) of_gpio_chip xlate method,
of_gpio_simple_xlate(), is modified to do this.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 drivers/mtd/nand/fsl_upm.c  |2 +-
 drivers/net/fs_enet/fs_enet-main.c  |2 +-
 drivers/net/phy/mdio-ofgpio.c   |4 ++--
 drivers/of/gpio.c   |   13 ++---
 drivers/serial/cpm_uart/cpm_uart_core.c |2 +-
 include/linux/of_gpio.h |   17 +
 6 files changed, 28 insertions(+), 12 deletions(-)

diff --git a/drivers/mtd/nand/fsl_upm.c b/drivers/mtd/nand/fsl_upm.c
index 024e3ff..a25d962 100644
--- a/drivers/mtd/nand/fsl_upm.c
+++ b/drivers/mtd/nand/fsl_upm.c
@@ -218,7 +218,7 @@ static int __devinit fun_probe(struct of_device *ofdev,
}
fun-upm_cmd_offset = *prop;
 
-   fun-rnb_gpio = of_get_gpio(ofdev-node, 0);
+   fun-rnb_gpio = of_get_gpio(ofdev-node, 0, NULL);
if (fun-rnb_gpio = 0) {
ret = gpio_request(fun-rnb_gpio, ofdev-dev.bus_id);
if (ret) {
diff --git a/drivers/net/fs_enet/fs_enet-main.c 
b/drivers/net/fs_enet/fs_enet-main.c
index cb51c1f..5a3c7ee 100644
--- a/drivers/net/fs_enet/fs_enet-main.c
+++ b/drivers/net/fs_enet/fs_enet-main.c
@@ -994,7 +994,7 @@ static int __devinit find_phy(struct device_node *np,
goto out_put_phy;
}
 
-   bus_id = of_get_gpio(mdionode, 0);
+   bus_id = of_get_gpio(mdionode, 0, NULL);
if (bus_id  0) {
struct resource res;
ret = of_address_to_resource(mdionode, 0, res);
diff --git a/drivers/net/phy/mdio-ofgpio.c b/drivers/net/phy/mdio-ofgpio.c
index 2ff9775..e3757c6 100644
--- a/drivers/net/phy/mdio-ofgpio.c
+++ b/drivers/net/phy/mdio-ofgpio.c
@@ -78,8 +78,8 @@ static int __devinit mdio_ofgpio_bitbang_init(struct mii_bus 
*bus,
 {
struct mdio_gpio_info *bitbang = bus-priv;
 
-   bitbang-mdc = of_get_gpio(np, 0);
-   bitbang-mdio = of_get_gpio(np, 1);
+   bitbang-mdc = of_get_gpio(np, 0, NULL);
+   bitbang-mdio = of_get_gpio(np, 1, NULL);
 
if (bitbang-mdc  0 || bitbang-mdio  0)
return -ENODEV;
diff --git a/drivers/of/gpio.c b/drivers/of/gpio.c
index 7cd7301..2123517 100644
--- a/drivers/of/gpio.c
+++ b/drivers/of/gpio.c
@@ -22,11 +22,12 @@
  * of_get_gpio - Get a GPIO number from the device tree to use with GPIO API
  * @np:device node to get GPIO from
  * @index: index of the GPIO
+ * @flags: GPIO's flags are returned here if non-NULL
  *
  * Returns GPIO number to use with Linux generic GPIO API, or one of the errno
  * value on the error condition.
  */
-int of_get_gpio(struct device_node *np, int index)
+int of_get_gpio(struct device_node *np, int index, unsigned int *flags)
 {
int ret;
struct device_node *gc;
@@ -59,7 +60,9 @@ int of_get_gpio(struct device_node *np, int index)
goto err1;
}
 
-   ret = of_gc-xlate(of_gc, np, gpio_spec);
+   if (flags)
+   *flags = 0;
+   ret = of_gc-xlate(of_gc, np, gpio_spec, flags);
if (ret  0)
goto err1;
 
@@ -77,19 +80,23 @@ EXPORT_SYMBOL(of_get_gpio);
  * @of_gc: pointer to the of_gpio_chip structure
  * @np:device node of the GPIO chip
  * @gpio_spec: gpio specifier as found in the device tree
+ * @flags: if non-NUll flags are returned here
  *
  * This is simple translation function, suitable for the most 1:1 mapped
  * gpio chips. This function performs only one sanity check: whether gpio
  * is less than ngpios (that is specified in the gpio_chip).
  */
 int of_gpio_simple_xlate(struct of_gpio_chip *of_gc, struct device_node *np,
-const void *gpio_spec)
+const void *gpio_spec, unsigned int *flags)
 {
const u32 *gpio = gpio_spec;
 
if (*gpio  of_gc-gc.ngpio)
return -EINVAL;
 
+   if (flags  of_gc-gpio_cells  1)
+   *flags = gpio[1];
+
return *gpio;
 }
 EXPORT_SYMBOL(of_gpio_simple_xlate);
diff --git a/drivers/serial/cpm_uart/cpm_uart_core.c 
b/drivers/serial/cpm_uart/cpm_uart_core.c
index bde4b4b..7835cd4 100644
--- a/drivers/serial/cpm_uart/cpm_uart_core.c
+++ b/drivers/serial/cpm_uart/cpm_uart_core.c
@@ -1094,7 +1094,7 @@ static int cpm_uart_init_port(struct device_node *np,
}
 
for (i = 0; i  NUM_GPIOS; i++)
-   pinfo-gpios[i] = of_get_gpio(np, i);
+   pinfo-gpios[i] = of_get_gpio(np, i, NULL);
 
return cpm_uart_request_port(pinfo-port);
 
diff --git a/include/linux/of_gpio.h b/include/linux

[PATCH 2/4] leds: Support OpenFirmware led bindings

2008-10-24 Thread Trent Piepho
Add bindings to support LEDs defined as of_platform devices in addition to
the existing bindings for platform devices.

New options in Kconfig allow the platform binding code and/or the
of_platform code to be turned on.  The of_platform code is of course only
available on archs that have OF support.

The existing probe and remove methods are refactored to use new functions
create_gpio_led(), to create and register one led, and delete_gpio_led(),
to unregister and free one led.  The new probe and remove methods for the
of_platform driver can then share most of the common probe and remove code
with the platform driver.

The suspend and resume methods aren't shared, but they are very short.  The
actual led driving code is the same for LEDs created by either binding.

The OF bindings are based on patch by Anton Vorontsov
[EMAIL PROTECTED].  They have been extended to allow multiple LEDs
per device.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   46 -
 drivers/leds/Kconfig|   21 ++-
 drivers/leds/leds-gpio.c|  230 ++-
 3 files changed, 243 insertions(+), 54 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index ff51f4c..9f969c2 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -1,15 +1,43 @@
-LED connected to GPIO
+LEDs connected to GPIO lines
 
 Required properties:
-- compatible : should be gpio-led.
-- label : (optional) the label for this LED. If omitted, the label is
+- compatible : should be gpio-leds.
+
+Each LED is represented as a sub-node of the gpio-leds device.  Each
+node's name represents the name of the corresponding LED.
+
+LED sub-node properties:
+- gpios :  Should specify the LED's GPIO, see Specifying GPIO information
+  for devices in Documentation/powerpc/booting-without-of.txt.  Active
+  low LEDs should be indicated using flags in the GPIO specifier. 
+- label :  (optional) The label for this LED.  If omitted, the label is
   taken from the node name (excluding the unit address).
-- gpios : should specify LED GPIO.
+- linux,default-trigger :  (optional) This parameter, if present, is a
+  string defining the trigger assigned to the LED.  Current triggers are:
+backlight - LED will act as a back-light, controlled by the framebuffer
+ system
+default-on - LED will turn on
+heartbeat - LED double flashes at a load average based rate
+ide-disk - LED indicates disk activity
+timer - LED flashes at a fixed, configurable rate
 
-Example:
+Examples:
 
[EMAIL PROTECTED] {
-   compatible = gpio-led;
-   label = hdd;
-   gpios = mcu_pio 0 1;
+leds {
+   compatible = gpio-leds;
+   hdd {
+   label = IDE Activity;
+   gpios = mcu_pio 0 1; /* Active low */
+   linux,default-trigger = ide-disk;
+   };
 };
+
+run-control {
+   compatible = gpio-leds;
+   red {
+   gpios = mpc8572 6 0;
+   };
+   green {
+   gpios = mpc8572 7 0;
+   };
+}
diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig
index e7fb7d2..6c6dc96 100644
--- a/drivers/leds/Kconfig
+++ b/drivers/leds/Kconfig
@@ -111,7 +111,26 @@ config LEDS_GPIO
help
  This option enables support for the LEDs connected to GPIO
  outputs. To be useful the particular board must have LEDs
- and they must be connected to the GPIO lines.
+ and they must be connected to the GPIO lines.  The LEDs must be
+ defined as platform devices and/or OpenFirmware platform devices.
+ The code to use these bindings can be selected below.
+
+config LEDS_GPIO_PLATFORM
+   bool Platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ platform devices.  If you don't know what this means, say yes.
+
+config LEDS_GPIO_OF
+   bool OpenFirmware platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO  OF_DEVICE
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ of_platform devices.  For instance, LEDs which are listed in a dts
+ file.
 
 config LEDS_HP_DISK
tristate LED Support for disk protection LED on HP notebooks
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index b13bd29..f41b841 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -3,6 +3,7 @@
  *
  * Copyright (C) 2007 8D Technologies inc.
  * Raphael Assenat [EMAIL PROTECTED]
+ * Copyright (C) 2008 Freescale Semiconductor, Inc.
  *
  * 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
@@ -71,50 +72,67 @@ static

[PATCH 3/4] leds: Add option to have GPIO LEDs start on

2008-10-24 Thread Trent Piepho
Yes, there is the default-on trigger but there are problems with that.

For one, it's a inefficient way to do it and requires led trigger support
to be compiled in.

But the real reason is that is produces a glitch on the LED.  The GPIO is
allocate with the LED *off*, then *later* when then trigger runs it is
turned back on.  If the LED was already on via the GPIO's reset default or
action of the firmware, this produces a glitch where the LED goes from on
to off to on.  While normally this is fast enough that it wouldn't be
noticeable to a human observer, there are still serious problems.

One is that there may be something else on the GPIO line, like a hardware
alarm or watchdog, that is fast enough to notice the glitch.

Another is that the kernel may panic before the LED is turned back on, thus
hanging with the LED in the wrong state.  This is not just speculation, but
actually happened to me with an embedded system that has an LED which
should turn off when the kernel finishes booting, which was left in the
incorrect state due to a bug in the OF LED binding code.

The platform device binding gains a field in the platform data default_state
that controls this.  The OpenFirmware binding uses a property named
default-state that can be set to on or off.  The default the property
isn't present is off.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |7 +++
 drivers/leds/leds-gpio.c|8 ++--
 include/linux/leds.h|1 +
 3 files changed, 14 insertions(+), 2 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 9f969c2..544ded7 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -20,6 +20,11 @@ LED sub-node properties:
 heartbeat - LED double flashes at a load average based rate
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
+- default-state:  (optional) The initial state of the LED.  Valid
+  values are on and off.  If the LED is already on or off and the
+  default-state property is set the to same value, then no glitch
+  should be produced where the LED momentarily turns off (or on).
+  The default is off if this property is not present.
 
 Examples:
 
@@ -36,8 +41,10 @@ run-control {
compatible = gpio-leds;
red {
gpios = mpc8572 6 0;
+   default-state = off;
};
green {
gpios = mpc8572 7 0;
+   default-state = on;
};
 }
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index f41b841..0dbad87 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -92,9 +92,10 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = LED_OFF;
+   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
 
-   gpio_direction_output(led_dat-gpio, led_dat-active_low);
+   gpio_direction_output(led_dat-gpio,
+ led_dat-active_low ^ template-default_state);
 
INIT_WORK(led_dat-work, gpio_led_work);
 
@@ -256,12 +257,15 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
memset(led, 0, sizeof(led));
for_each_child_of_node(np, child) {
unsigned int flags;
+   const char *state;
 
led.gpio = of_get_gpio(child, 0, flags);
led.active_low = flags  OF_GPIO_ACTIVE_LOW;
led.name = of_get_property(child, label, NULL) ? : 
child-name;
led.default_trigger =
of_get_property(child, linux,default-trigger, NULL);
+   state = of_get_property(child, default-state, NULL);
+   led.default_state = state  !strcmp(state, on);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index d3a73f5..caa3987 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,6 +138,7 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
+   u8  default_state;
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.3

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 4/4] leds: Let GPIO LEDs keep their current state

2008-10-24 Thread Trent Piepho
Let GPIO LEDs get their initial value from whatever the current state of
the GPIO line is.  On some systems the LEDs are put into some state by the
firmware or hardware before Linux boots, and it is desired to have them
keep this state which is otherwise unknown to Linux.

This requires that the underlying GPIO driver support reading the value of
output GPIOs.  Some drivers support this and some do not.

The platform data for the platform device binding gets a new field
'keep_state' which turns this on.  keep_state overrides default_state.

For the OpenFirmware bindings, the default-state property gains a new
allowable setting keep.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   16 
 drivers/leds/leds-gpio.c|   12 
 include/linux/leds.h|3 ++-
 3 files changed, 22 insertions(+), 9 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index 544ded7..918bf9f 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -21,10 +21,12 @@ LED sub-node properties:
 ide-disk - LED indicates disk activity
 timer - LED flashes at a fixed, configurable rate
 - default-state:  (optional) The initial state of the LED.  Valid
-  values are on and off.  If the LED is already on or off and the
-  default-state property is set the to same value, then no glitch
-  should be produced where the LED momentarily turns off (or on).
-  The default is off if this property is not present.
+  values are on, off, and keep.  If the LED is already on or off
+  and the default-state property is set the to same value, then no
+  glitch should be produced where the LED momentarily turns off (or
+  on).  The keep setting will keep the LED at whatever its current
+  state is, without producing a glitch.  The default is off if this
+  property is not present.
 
 Examples:
 
@@ -35,6 +37,12 @@ leds {
gpios = mcu_pio 0 1; /* Active low */
linux,default-trigger = ide-disk;
};
+
+   fault {
+   gpios = mcu_pio 1 0;
+   /* Keep LED on if BIOS detected hardware fault */
+   default-state = keep;
+   };
 };
 
 run-control {
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index 0dbad87..bb2a234 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -76,7 +76,7 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
struct gpio_led_data *led_dat, struct device *parent,
int (*blink_set)(unsigned, unsigned long *, unsigned long *))
 {
-   int ret;
+   int ret, state;
 
ret = gpio_request(template-gpio, template-name);
if (ret  0)
@@ -92,10 +92,13 @@ static int __devinit create_gpio_led(const struct gpio_led 
*template,
led_dat-cdev.blink_set = gpio_blink_set;
}
led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness = template-default_state ? LED_FULL : LED_OFF;
+   if (template-keep_state)
+   state = !!gpio_get_value(led_dat-gpio) ^ led_dat-active_low;
+   else
+   state = template-default_state;
+   led_dat-cdev.brightness = state ? LED_FULL : LED_OFF;
 
-   gpio_direction_output(led_dat-gpio,
- led_dat-active_low ^ template-default_state);
+   gpio_direction_output(led_dat-gpio, led_dat-active_low ^ state);
 
INIT_WORK(led_dat-work, gpio_led_work);
 
@@ -266,6 +269,7 @@ static int __devinit of_gpio_leds_probe(struct of_device 
*ofdev,
of_get_property(child, linux,default-trigger, NULL);
state = of_get_property(child, default-state, NULL);
led.default_state = state  !strcmp(state, on);
+   led.keep_state = state  !strcmp(state, keep);
 
ret = create_gpio_led(led, pdata-led_data[pdata-num_leds++],
  ofdev-dev, NULL);
diff --git a/include/linux/leds.h b/include/linux/leds.h
index caa3987..c51b625 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -138,7 +138,8 @@ struct gpio_led {
const char *default_trigger;
unsignedgpio;
u8  active_low;
-   u8  default_state;
+   u8  default_state;  /* 0 = off, 1 = on */
+   u8  keep_state; /* overrides default_state */
 };
 
 struct gpio_led_platform_data {
-- 
1.5.4.3

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH] powerpc/fsl: Refactor device bindings

2008-09-21 Thread Trent Piepho
On Wed, 9 Jul 2008, Kumar Gala wrote:
 Moved Freescale SoC related bindings out of booting-without-of.txt and into
 their own files.

 Signed-off-by: Kumar Gala galak at kernel.crashing.org
 ---

 We need to resolve some conflicts in cpm.txt and qe.txt but that will be a
 followup patch.
 
 - k

  Documentation/powerpc/booting-without-of.txt   | 1218 
 +---

It looks like the part of the this patch that deleted all the bindings from
booting-without-of.txt was paritially reverted in a subsequent merge.  The
table of contents still lists all the sections that were removed and sections
r) and s) were added back in.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 1/2] leds: make the default trigger name const

2008-08-28 Thread Trent Piepho
The default_trigger fields of struct gpio_led and thus struct led_classdev
are pretty much always assigned from a string literal, which means the
string can't be modified.  Which is fine, since there is no reason to
modify the string and in fact it never is.

But they should be marked const to prevent such code from being added, to
prevent warnings if -Wwrite-strings is used and when assigned from a
constant string other than a string literal (which produces a warning under
current kernel compiler flags), and for general good coding practices.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
Reposting this again.  It still applies to powerpc-next as of Aug 28 and I
don't think anyone had any problems with it.

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

diff --git a/include/linux/leds.h b/include/linux/leds.h
index d41ccb5..d3a73f5 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -123,7 +123,7 @@ extern void ledtrig_ide_activity(void);
   */
  struct led_info {
const char  *name;
-   char*default_trigger;
+   const char  *default_trigger;
int flags;
  };

@@ -135,7 +135,7 @@ struct led_platform_data {
  /* For the leds-gpio driver */
  struct gpio_led {
const char *name;
-   char *default_trigger;
+   const char *default_trigger;
unsignedgpio;
u8  active_low;
  };
-- 
1.5.4.3

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-08-01 Thread Trent Piepho
On Fri, 1 Aug 2008, Timur Tabi wrote:
 On Thu, Jul 31, 2008 at 6:32 PM, Trent Piepho [EMAIL PROTECTED] wrote:

  The real problem, which kept me from making a patch to do this months ago,
  is that the source clock that the I2C freq divider applies to is different
  for just about every MPC8xxx platform.  Not just a different value, but a
  totally different internal clock.  Sometimes is CCB, sometimes CCB/2,
  sometimes tsec2's clock, etc.

 On which SOC is it the tesc2 clock?

834x


   Sometimes the two i2c controllers don't even
  have the same clock.

 On which platform is that the case?  I thought I had all 8[356]xx
 boards covered.  Did I miss some?

All 83xx other than 832x.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-08-01 Thread Trent Piepho
On Fri, 1 Aug 2008, Jon Smirl wrote:
 I don't like the third choice. Keep a simple Linux driver for i2c and
 the platform, and then move all of the messy code into uboot.  BTW,
 the messy code is about 10 lines. It's going to take more than 10
 lines to hide those 10 lines.

It's not being _moved_ to u-boot, it's already there.  U-boot needs it
because u-boot uses i2c.

It would need to be duplicated in linux, and then both u-boot and linux
would need to be updated each time a new platform is added.

It's pretty much a given that a u-boot binary will only work on one
platform.  The same is not true with a compiled kernel.  That makes it
harder to all the platform specific stuff in linux.  It's a little more
than 10 lines too.  Keep in mind that accessing all these devices registers
isn't as easy in linux as u-boot.  In linux you have to look up the
register location in device tree and map the registers.  All this code uses
a system clock as a starting point, which u-boot already passes to linux.

#if defined(CONFIG_MPC83XX)
volatile immap_t *im = (immap_t *) CFG_IMMR;
sccr = im-clk.sccr;
#if defined(CONFIG_MPC834X) || defined(CONFIG_MPC831X) || 
defined(CONFIG_MPC837X)
switch ((sccr  SCCR_TSEC1CM)  SCCR_TSEC1CM_SHIFT) {
case 0:
tsec1_clk = 0;
break;
case 1:
tsec1_clk = csb_clk;
break;
case 2:
tsec1_clk = csb_clk / 2;
break;
case 3:
tsec1_clk = csb_clk / 3;
break;
default:
/* unkown SCCR_TSEC1CM value */
return -2;
}
#endif
#if defined(CONFIG_MPC834X) || defined(CONFIG_MPC837X) || 
defined(CONFIG_MPC8315)
switch ((sccr  SCCR_TSEC2CM)  SCCR_TSEC2CM_SHIFT) {
case 0:
tsec2_clk = 0;
break;
case 1:
tsec2_clk = csb_clk;
break;
case 2:
tsec2_clk = csb_clk / 2;
break;
case 3:
tsec2_clk = csb_clk / 3;
break;
default:
/* unkown SCCR_TSEC2CM value */
return -4;
}
#elif defined(CONFIG_MPC8313)
tsec2_clk = tsec1_clk;

if (!(sccr  SCCR_TSEC1ON))
tsec1_clk = 0;
if (!(sccr  SCCR_TSEC2ON))
tsec2_clk = 0;
#endif
switch ((sccr  SCCR_ENCCM)  SCCR_ENCCM_SHIFT) {
case 0:
enc_clk = 0;
break;
case 1:
enc_clk = csb_clk;
break;
case 2:
enc_clk = csb_clk / 2;
break;
case 3:
enc_clk = csb_clk / 3;
break;
default:
/* unkown SCCR_ENCCM value */
return -7;
}
#if defined(CONFIG_MPC837X)
switch ((sccr  SCCR_SDHCCM)  SCCR_SDHCCM_SHIFT) {
case 0:
sdhc_clk = 0;
break;
case 1:
sdhc_clk = csb_clk;
break;
case 2:
sdhc_clk = csb_clk / 2;
break;
case 3:
sdhc_clk = csb_clk / 3;
break;
default:
/* unkown SCCR_SDHCCM value */
return -8;
}
#endif
#if defined(CONFIG_MPC834X)
i2c1_clk = tsec2_clk;
#elif defined(CONFIG_MPC8360)
i2c1_clk = csb_clk;
#elif defined(CONFIG_MPC832X)
i2c1_clk = enc_clk;
#elif defined(CONFIG_MPC831X)
i2c1_clk = enc_clk;
#elif defined(CONFIG_MPC837X)
i2c1_clk = sdhc_clk;
#endif
#if !defined(CONFIG_MPC832X)
i2c2_clk = csb_clk; /* i2c-2 clk is equal to csb clk */
#endif

#elif defined (CONFIG_MPC85XX)

#if defined(CONFIG_MPC8540) || defined(CONFIG_MPC8541) || \
defined(CONFIG_MPC8560) || defined(CONFIG_MPC8555)
gd-i2c1_clk = sys_info.freqSystemBus;
#elif defined(CONFIG_MPC8544)
volatile ccsr_gur_t *gur = (void *) CFG_MPC85xx_GUTS_ADDR;
/*
 * On the 8544, the I2C clock is the same as the SEC clock.  This can be
 * either CCB/2 or CCB/3, depending on the value of cfg_sec_freq. See
 * 4.4.3.3 of the 8544 RM.  Note that this might actually work for all
 * 85xx, but only the 8544 has cfg_sec_freq, so it's unknown if the
 * PORDEVSR2_SEC_CFG bit is 0 on all 85xx boards that are not an 8544.
 */
if (gur-pordevsr2  MPC85xx_PORDEVSR2_SEC_CFG)
gd-i2c1_clk = sys_info.freqSystemBus / 3;
else
gd-i2c1_clk = sys_info.freqSystemBus / 2;
#else
/* Most 85xx SOCs use CCB/2, so this is the default behavior. */
gd-i2c1_clk = sys_info.freqSystemBus / 2;
#endif
gd-i2c2_clk = gd-i2c1_clk;

#elif defined(CONFIG_MPC86XX)

#ifdef CONFIG_MPC8610
gd-i2c1_clk = sys_info.freqSystemBus;
#else
gd-i2c1_clk = sys_info.freqSystemBus / 

Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Timur Tabi wrote:
 Jon Smirl wrote:

  Aren't the tables in the manual there just to make it easy for a human
  to pick out the line they want? For a computer you'd program the
  formula that was used to create the tables.

 Actually, the tables in the manuals are just an example of what can be
 programmed.  They don't cover all cases.  The tables assume a specific value 
 of
 DFSR.

 For 8xxx, you want to use AN2919 to figure out how to really program the 
 device.

 The table I generated for U-Boot is based on the calculations outlined in
 AN2919.  I debated trying to implement the actual algorithm, but decided that
 pre-calculating the values was better.  The algorithm is very convoluted.

And I decided to program the algorithm.  It's not that complex and overall
compiles to less total size than the table method.  It doesn't involve some
black box table either.

The real problem, which kept me from making a patch to do this months ago,
is that the source clock that the I2C freq divider applies to is different
for just about every MPC8xxx platform.  Not just a different value, but a
totally different internal clock.  Sometimes is CCB, sometimes CCB/2,
sometimes tsec2's clock, etc.  Sometimes the two i2c controllers don't even
have the same clock.  I didn't see any easy way to get this information.
In U-Boot I get it from the global board info struct, but I didn't see
anything like this in Linux.

  I agree that it took me half an hour to figure out the formula that
  was needed to compute the i2s clocks, but once you figure out the
  formula it solves all of the cases and no one needs to read the manual
  any more. The i2c formula may even need a small loop which compares
  different solutions looking for the smallest error term. But it's a
  small space to search.

Yes, I needed a loop.  The divider ends up having the form (a + c)  b,
where a is from some set of eight integers between 2 and 15, b has a range
of like 5 to 12, and c is usually zero.

So, I find the divider I want to get, loop over each b, shift the divider
right by b and find the closest (a+c) to that, calculate the error, and
then use the best one.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Jon Smirl wrote:
 As for the source clock, how about creating a new global like
 ppc_proc_freq called ppc_ipb_freq. The platform code can then set the
 right clock value into the variable. For mpc8 get it from uboot.
 mpc5200 can easily compute it from ppc_proc_freq and checking how the
 ipb divider is set. That will move the clock problem out of the i2c
 driver.

There is a huge variation in where the I2C source clock comes from.
Sometimes it's the system bus, sometimes ethernet, sometimes SEC, etc.  If
I look at u-boot (which might not be entirely correct or complete), I see:

83xx:  5 different clock sources
85xx:  3 different clock sources
86xx:  2 different clock sources

But there's more.  Sometimes the two I2C controllers don't use the same
clock!  So even if you add 10 globals with different clocks, and then add
code to the mpc i2c driver so if can figure out which one to use given the
platform, it's still not enough because you need to know which controller
the device node is for.

IMHO, what Timur suggested of having u-boot put the source clock into the
i2c node makes the most sense.  U-boot has to figure this out, so why
duplicate the work?

Here's my idea:

[EMAIL PROTECTED] {
compatible = fsl-i2c;
bus-frequency = 10;

/* Either */
source-clock-frequency = 0;
/* OR */
source-clock = ccb;
};

bus-frequency is the desired frequency of the i2c bus, i.e. 100 kHz or 400
kHz usually.  source-clock-frequency is the the source clock to this i2c
controller.  U-Boot can fill this in since it already knows it anyway.  Or,
instead of source-clock-frequency, source-clock can be specified as a
phandle to a device which has the clock to use.  This could be useful if
Linux can change the clock frequency.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Grant Likely wrote:
 On Thu, Jul 31, 2008 at 09:54:48PM +0200, Wolfgang Grandegger wrote:
  Thinking more about it, it would be best to add the property
  i2c-clock-divider to the soc node and implement fsl_get_i2c_freq() in
  a similar way:
 
  [EMAIL PROTECTED] {
  #address-cells = 1;
  #size-cells = 1;
  device_type = soc;
  ranges = 0x0 0xe000 0x10;
  reg = 0xe000 0x1000;  // CCSRBAR 1M
  bus-frequency = 0;
  i2c-clock-divider = 2;
 
  U-Boot could then fixup that value like bus-frequency() and the i2c-mpc
  driver simply calls fsl_get_i2c_freq().

Except the i2c clock isn't always a based on an interger divider of the CCB
frequency.  What's more, it's not always the same for both i2c controllers.
Suppose i2c #1 uses CCB times 2/3 and i2c #2 uses CCB/2, how would
fsl_get_i2c_freq() figure that out from bus-frequency and
i2c-clock-divider?

 Ugh.  This is specifically related to the i2c device, so please place
 the property in the i2c device.  Remember, device tree design is not
 about what will make the implementation simplest, but rather about what
 describes the hardware in the best way.

 Now, if you can argue that i2c-clock-frequency is actually a separate
 clock domain defined at the SoC level, not the i2c device level, then I
 will change my opinion.

The i2c controller just uses some system clock that was handy.  For each
chip, the designers consult tea leaves to choose a system clock at random
to connect to the i2c controller.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Grant Likely wrote:
   I'm a bit confused. The frequency of the I2C source clock and the real I2C
  clock frequency are two different things. The first one is common for all
  I2C devices, the second can be different. What properties would you like to
  use for defining both?

 How is the divider controlled?  Is it a fixed property of the SoC?

Usually.

 a shared register setting?

Sometimes.

 or a register setting within the i2c device?

Never.


Thinking of it as the CCB divided by 1, 2, 3 isn't really right.  It's just
some internal clock that I2C was connected to.  Sometimes it's the clock
for the ethernet block of the SoC.  Sometimes it comes from some other
block.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Timur Tabi wrote:
 Wolfgang Grandegger wrote:

  U-Boot does not (yet) use the FDT and it has therefore to use that ugly
  code to derive the I2C input clock frequency. I think its completely
  legal to put that hardware specific information into the FDT and get rid
  of such code.

 Huh?  U-Boot initializes several fields and creates several properties in the
 FDT today, so what's wrong with adding another one?  The clock frequencies 
 have
 always been calculated by U-Boot, because putting them in the device tree is a
 bad idea.

I think Wolfgang means u-boot doesn't _read_ information from the device
tree.  Put the I2C source clock into the device tree and have u-boot read it
in.

But that simply doesn't work at all.  The i2c source clock isn't constant.
It's not a constant divider from the core clock either.  Flip a dip switch,
and the divider changes.

But that's irrelevant.  U-boot needs to configure the i2c controller to
read SPD data from the DIMM's EPROM, which is necessary to get DRAM
working.  That happens long long before the FDT is loaded via TFTP,
y-modem, NFS, or from disk or flash.  Might as well have u-boot get the i2c
source clock via Linux's sysfs.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [i2c] [PATCH] powerpc: i2c-mpc: make speed registers configurable via FDT

2008-07-31 Thread Trent Piepho
On Thu, 31 Jul 2008, Jon Smirl wrote:
   Here's my idea:
 
  [EMAIL PROTECTED] {
  compatible = fsl-i2c;
  bus-frequency = 10;
 
  /* Either */
  source-clock-frequency = 0;
  /* OR */
  source-clock = ccb;
  };

 Can't we hide a lot of this on platforms where the source clock is not
 messed up? For example the mpc5200 doesn't need any of this, the
 needed frequency is already available in mpc52xx_find_ipb_freq().
 mpc5200 doesn't need any uboot change.

 Next would be normal mpc8xxx platforms where i2c is driven by a single
 clock, add a uboot filled in parameter in the root node (or I think it
 can be computed off of the ones uboot is already filling in). make a
 mpc8xxx_find_i2c_freq() function. May not need to change device tree
 and uboot.

 Finally use this for those days when the tea leaves were especially
 bad. Both a device tree and uboot change.

If you have to support clock speed in the i2c node anyway, what's the point
of the other options?

  Except the i2c clock isn't always a based on an integer divider of the CCB
   frequency.  What's more, it's not always the same for both i2c controllers.
   Suppose i2c #1 uses CCB times 2/3 and i2c #2 uses CCB/2, how would
   fsl_get_i2c_freq() figure that out from bus-frequency and
   i2c-clock-divider?

 If you get the CCB frequency from uboot and know the chip model, can't
 you compute these in the platform code? Then make a
 mpc8xxx_find_i2c_freq(cell_index).

You need a bunch of random other device registers (SEC, ethernet, sdhc,
etc.) too.

 I don't see why we want to go through the trouble of having uboot tell
 us things about a chip that are fixed in stone. Obviously something
 like the frequency of the external crystal needs to be passed up, but
 why pass up stuff that can be computed (or recovered by reading a
 register)?

One could also say that if U-boot has to have the code and already
calculated the value, why duplicate the code and the calculation in Linux?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 2/2] leds: Support OpenFirmware led bindings

2008-07-28 Thread Trent Piepho
On Sat, 26 Jul 2008, Grant Likely wrote:
 On Fri, Jul 25, 2008 at 02:01:45PM -0700, Trent Piepho wrote:
 Add bindings to support LEDs defined as of_platform devices in addition to
 the existing bindings for platform devices.

 +- gpios :  Should specify the LED GPIO.

 Question: it is possible/desirable for a single LED to be assigned
 multiple GPIO pins?  Say, for a tri-color LED?  (I'm fishing for
 opinions; I really don't know if it would be a good idea or not)

Good question.  The Linux LED layer has no concept of multi-color LEDs, so
it's more difficult that just adding support to the gpio led driver.  I have
a device with a tri-color red/green/orange LED and this posed some
difficulty.  It's defined as independent red and greed LEDs, which is mostly
fine, except I wanted it to flash orange.  I can make both the red LED and
green LED flash, but there is nothing to insure their flashing remains in
sync.

Other OF bindings allow multiple GPIOs to be listed in a gpios property, so
that's not a problem if someone wants to do that.  There would need to be a
way to define what the gpios mean.  I don't think it's worthwhile to come up
with a binding for that until there is a real user.

 +- function :  (optional) This parameter, if present, is a string
 +  defining the function of the LED.  It can be used to put the LED
 +  under software control, e.g. Linux LED triggers like heartbeat,
 +  ide-disk, and timer.  Or it could be used to attach a hardware
 +  signal to the LED, e.g. a SoC that can configured to put a SATA
 +  activity signal on a GPIO line.

 This makes me nervous.  It exposes Linux internal implementation details
 into the device tree data.  If you want to have a property that
 describes the LED usage, then the possible values and meanings should be
 documented here.

Should it be a linux specific property then?  I could list all the current
linux triggers, but enumerating every possible function someone might want
to assign to an LED seems hopeless.

 +led.default_trigger =
 +of_get_property(child, linux,default-trigger, NULL);

 This isn't in the documented binding.  I assume that you mean 'function'
 here?

Looks like I emailed the wrong patch file.  That should be changed to
function and there are a few cosmetic changes that are missing.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 2/2] leds: Support OpenFirmware led bindings

2008-07-28 Thread Trent Piepho
On Mon, 28 Jul 2008, Anton Vorontsov wrote:
 On Mon, Jul 28, 2008 at 11:09:14AM -0600, Grant Likely wrote:
 [...]
 +- function :  (optional) This parameter, if present, is a string
 +  defining the function of the LED.  It can be used to put the LED
 +  under software control, e.g. Linux LED triggers like heartbeat,
 +  ide-disk, and timer.  Or it could be used to attach a hardware
 +  signal to the LED, e.g. a SoC that can configured to put a SATA
 +  activity signal on a GPIO line.

 This makes me nervous.  It exposes Linux internal implementation details
 into the device tree data.  If you want to have a property that
 describes the LED usage, then the possible values and meanings should be
 documented here.

 Should it be a linux specific property then?  I could list all the current
 linux triggers, but enumerating every possible function someone might want
 to assign to an LED seems hopeless.

 I'd rather see the device tree provide 'hints' toward the expected usage
 and if a platform needs something specific, then the platform specific
 code should setup the trigger.

 Maybe we can encode leds into devices themselves, via phandles?

How will this work for anything besides ide activity?  For example, flashing,
heartbeat, default on, overheat, fan failed, kernel panic, etc.

 And then the OF GPIO LEDs driver could do something like:

 char *ide_disk_trigger_compatibles[] = {
   fsl,sata,
   ide-generic,
   ...
 };

Everytime someone added a new ide driver, this table would have to be updated.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 2/2] leds: Support OpenFirmware led bindings

2008-07-28 Thread Trent Piepho
On Mon, 28 Jul 2008, Anton Vorontsov wrote:
 On Mon, Jul 28, 2008 at 11:26:28AM -0700, Trent Piepho wrote:
 On Mon, 28 Jul 2008, Anton Vorontsov wrote:
 On Mon, Jul 28, 2008 at 11:09:14AM -0600, Grant Likely wrote:
 [...]
 +- function :  (optional) This parameter, if present, is a string
 +  defining the function of the LED.  It can be used to put the LED
 +  under software control, e.g. Linux LED triggers like heartbeat,
 +  ide-disk, and timer.  Or it could be used to attach a hardware
 +  signal to the LED, e.g. a SoC that can configured to put a SATA
 +  activity signal on a GPIO line.

 This makes me nervous.  It exposes Linux internal implementation details
 into the device tree data.  If you want to have a property that
 describes the LED usage, then the possible values and meanings should be
 documented here.

 Should it be a linux specific property then?  I could list all the current
 linux triggers, but enumerating every possible function someone might want
 to assign to an LED seems hopeless.

 I'd rather see the device tree provide 'hints' toward the expected usage
 and if a platform needs something specific, then the platform specific
 code should setup the trigger.

 Maybe we can encode leds into devices themselves, via phandles?

 How will this work for anything besides ide activity?  For example, flashing,
 heartbeat, default on, overheat, fan failed, kernel panic, etc.

 Everything is possible, but will look weird. For example,

 Default on (power led) could be encoded in the root node.
 fan and overheat in a PM controller's node.
 Kernel panic in the chosen node.

What about flashing?  What if the sensor chip isn't an OF device?

 And then the OF GPIO LEDs driver could do something like:

 char *ide_disk_trigger_compatibles[] = {
 fsl,sata,
 ide-generic,
 ...
 };

 Everytime someone added a new ide driver, this table would have to be 
 updated.

 Yes. device_type would be helpful here. :-)


 Well, otherwise, we could provide a trigger map in the chosen node:

 chosen {
   /* leds map: default-on, ide-disk, nand-disk, panic */
   linux,leds = green_led red_led 0 0;
 };

What if you have multiple leds that you want to be default on?  What happens
when new functions are added?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH 1/2] leds: make the default trigger name const

2008-07-27 Thread Trent Piepho
On Sun, 27 Jul 2008, Stephen Rothwell wrote:
 On Sat, 26 Jul 2008 20:08:57 -0600 Grant Likely [EMAIL PROTECTED] wrote:
 On Fri, Jul 25, 2008 at 02:01:44PM -0700, Trent Piepho wrote:
 The default_trigger fields of struct gpio_led and thus struct led_classdev
 are pretty much always assigned from a string literal, which means the
 string can't be modified.  Which is fine, since there is no reason to
 modify the string and in fact it never is.

 But they should be marked const to prevent such code from being added, to
 prevent warnings if -Wwrite-strings is used and when assigned from a
 constant string other than a string literal (which produces a warning under
 current kernel compiler flags), and for general good coding practices.

 Signed-off-by: Trent Piepho [EMAIL PROTECTED]
 Acked-by: Grant Likely [EMAIL PROTECTED]

 I would ack this as well, except I am not sure what tree this patch is
 against.  In the current powerpc next tree,

It was against powerpc next from Jul 22nd, current at the time I made the
patch.  It looks like that file has changed in the last few days.  There is a
patch from Anton Vorontsov, leds:  mark led_classdev.default_trigger as
const, which adds const to one of the structs I modified, but doesn't get the
other one (struct gpio_led).

Then another patch from Nate Case added a new LED chip driver, and the
platform data for this driver was added as generic led platform data, which
I don't entirely agree with.  And this new struct didn't make default_trigger
const, probably because it was just copied from the gpio led platform data
with some fields removed (so it's not really that generic then, is it?).

I'll send an updated patch for current powerpc next.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH v2] leds: make the default trigger name const

2008-07-27 Thread Trent Piepho
The default_trigger fields of struct gpio_led and thus struct led_classdev
are pretty much always assigned from a string literal, which means the
string can't be modified.  Which is fine, since there is no reason to
modify the string and in fact it never is.

But they should be marked const to prevent such code from being added, to
prevent warnings if -Wwrite-strings is used and when assigned from a
constant string other than a string literal (which produces a warning under
current kernel compiler flags), and for general good coding practices.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 include/linux/leds.h |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/include/linux/leds.h b/include/linux/leds.h
index 519df72..defe693 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -48,7 +48,7 @@ struct led_classdev {
 
struct device   *dev;
struct list_head node;  /* LED Device list */
-   char*default_trigger;   /* Trigger to use */
+   const char  *default_trigger;   /* Trigger to use */
 
 #ifdef CONFIG_LEDS_TRIGGERS
/* Protects the trigger data below */
@@ -121,7 +121,7 @@ extern void ledtrig_ide_activity(void);
 /* For the leds-gpio driver */
 struct gpio_led {
const char *name;
-   char *default_trigger;
+   const char *default_trigger;
unsignedgpio;
u8  active_low;
 };
-- 
1.5.4.3

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [RFC PATCH] of_gpio: implement of_get_gpio_flags()

2008-07-26 Thread Trent Piepho
On Fri, 25 Jul 2008, Anton Vorontsov wrote:

 The name seems a bit unfortunate though, because one could read the
 function as it gets gpio flags only (though, we might implement
 this instead, but this way average driver will end up with parsing
 gpios =  twice).

It is kind of a confusing name.  I'd be tempted to just change of_get_gpio,
it's a new function and it's only called from four places so it's not that
hard to change.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-25 Thread Trent Piepho
Here are my patches for the OF bindings.  The first is just a tiny change to
the leds code to silence a warning.  The second is the real patch.

The leds-gpio driver gets two sub-options in Kconfig, one for platform
device support and one for openfirmware platform device support.

There is support for setting an LED trigger.  I didn't include support for
active-low or initial brightness, but I think those would be good features
to add.  See below for more on that.

Since each device node can describe multiple leds, I used gpio-leds
instead of gpio-led for the compatible property.

Examples of the dts syntax:

leds {
 compatible = gpio-leds;
 hdd {
 label = IDE activity;
 gpios = mcu_pio 0 0;
 function = ide-disk;
 };
};

run-control {
 compatible = gpio-leds;
 red {
 gpios = mpc8572 6 0;
 };
 green {
 gpios = mpc8572 7 0;
 };
}


On Fri, 18 Jul 2008, Anton Vorontsov wrote:
 Later I tried to use aliases for default-trigger.

 http://ozlabs.org/pipermail/linuxppc-dev/2008-June/057244.html

I doesn't seem to me that the alias method will work very well.  If I want
an LED that starts on, I need to add code to the kernel to support an
led-on-while-kernel-boots alias?  And if I want red  green leds to flash
while booting, I need to add aliases led-flashing-while-kernel-boots-1 and
led-flashing-while-kernel-boots-2, since you can't assign two leds to the
same alias?

 As for linux,default-brightness... we don't need this since now we
 have default-on trigger.

Except we can't use triggers

There is an issue with the default-on trigger, besides requiring led
triggers be turned on and the extra code that needs.  It causes the led to
have a glitch in it.  Suppose the LED is already on from reset or the boot
loader.  When the gpio is allocated, it's allocated with an initial value of
off.  Then, later, it's turned back on when the trigger runs.  But say the
trigger doesn't run?

Here's a real example.  I have an LED that comes on the board powers on.  It
was supposed to turn off when the kernel has finished booting.  But suppose
the kernel panics between the gpio getting lowered when the led is added and
the trigger turning it back on?  Now the LED is off and it appears the
problem happened after the kernel finished booting, but really it happened
during the kernel boot.  In an embedded system with no console, that's quite
a bit of misinformation.  It can be entirely avoided by changing just three
lines of code with the leds-gpio driver to add an option to start the led
on.

It could also be the case that the gpio the led is on also triggers some
other piece of hardware.  An alarm that's on the same line as a fault led
for example.  The glitch created by the default-on trigger could be
unacceptable in that case.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 1/2] leds: make the default trigger name const

2008-07-25 Thread Trent Piepho
The default_trigger fields of struct gpio_led and thus struct led_classdev
are pretty much always assigned from a string literal, which means the
string can't be modified.  Which is fine, since there is no reason to
modify the string and in fact it never is.

But they should be marked const to prevent such code from being added, to
prevent warnings if -Wwrite-strings is used and when assigned from a
constant string other than a string literal (which produces a warning under
current kernel compiler flags), and for general good coding practices.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 include/linux/leds.h |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/include/linux/leds.h b/include/linux/leds.h
index 519df72..defe693 100644
--- a/include/linux/leds.h
+++ b/include/linux/leds.h
@@ -48,7 +48,7 @@ struct led_classdev {
 
struct device   *dev;
struct list_head node;  /* LED Device list */
-   char*default_trigger;   /* Trigger to use */
+   const char  *default_trigger;   /* Trigger to use */
 
 #ifdef CONFIG_LEDS_TRIGGERS
/* Protects the trigger data below */
@@ -121,7 +121,7 @@ extern void ledtrig_ide_activity(void);
 /* For the leds-gpio driver */
 struct gpio_led {
const char *name;
-   char *default_trigger;
+   const char *default_trigger;
unsignedgpio;
u8  active_low;
 };
-- 
1.5.4.3

___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


[PATCH 2/2] leds: Support OpenFirmware led bindings

2008-07-25 Thread Trent Piepho
Add bindings to support LEDs defined as of_platform devices in addition to
the existing bindings for platform devices.

New options in Kconfig allow the platform binding code and/or the
of_platform code to be turned on.  The of_platform code is of course only
available on archs that have OF support.

The existing probe and remove methods are refactored to use new functions
create_gpio_led(), to create and register one led, and delete_gpio_led(),
to unregister and free one led.  The new probe and remove methods for the
of_platform driver can then share most of the common probe and remove code
with the platform driver.

The suspend and resume methods aren't shared, but they are very short.  The
actual led driving code is the same for LEDs created by either binding.

The OF bindings are based on patch by Anton Vorontsov
[EMAIL PROTECTED].  They have been extended to allow multiple LEDs
per device.

Signed-off-by: Trent Piepho [EMAIL PROTECTED]
---
 Documentation/powerpc/dts-bindings/gpio/led.txt |   44 -
 drivers/leds/Kconfig|   21 ++-
 drivers/leds/leds-gpio.c|  225 ++-
 3 files changed, 236 insertions(+), 54 deletions(-)

diff --git a/Documentation/powerpc/dts-bindings/gpio/led.txt 
b/Documentation/powerpc/dts-bindings/gpio/led.txt
index ff51f4c..ed01297 100644
--- a/Documentation/powerpc/dts-bindings/gpio/led.txt
+++ b/Documentation/powerpc/dts-bindings/gpio/led.txt
@@ -1,15 +1,39 @@
-LED connected to GPIO
+LEDs connected to GPIO lines
 
 Required properties:
-- compatible : should be gpio-led.
-- label : (optional) the label for this LED. If omitted, the label is
-  taken from the node name (excluding the unit address).
-- gpios : should specify LED GPIO.
+- compatible : should be gpio-leds.
 
-Example:
+Each LED is represented as a sub-node of the gpio-leds device.  Each
+node's name represents the name of the corresponding LED.
 
[EMAIL PROTECTED] {
-   compatible = gpio-led;
-   label = hdd;
-   gpios = mcu_pio 0 1;
+LED node properties:
+- gpios :  Should specify the LED GPIO.
+- label :  (optional) The label for this LED.  If omitted, the label
+  is taken from the node name (excluding the unit address).
+- function :  (optional) This parameter, if present, is a string
+  defining the function of the LED.  It can be used to put the LED
+  under software control, e.g. Linux LED triggers like heartbeat,
+  ide-disk, and timer.  Or it could be used to attach a hardware
+  signal to the LED, e.g. a SoC that can configured to put a SATA
+  activity signal on a GPIO line.
+
+Examples:
+
+leds {
+   compatible = gpio-leds;
+   hdd {
+   label = IDE activity;
+   gpios = mcu_pio 0 0;
+   function = ide-disk;
+   };
 };
+
+run-control {
+   compatible = gpio-leds;
+   red {
+   gpios = mpc8572 6 0;
+   };
+   green {
+   gpios = mpc8572 7 0;
+   };
+}
diff --git a/drivers/leds/Kconfig b/drivers/leds/Kconfig
index 86a369b..8344256 100644
--- a/drivers/leds/Kconfig
+++ b/drivers/leds/Kconfig
@@ -109,7 +109,26 @@ config LEDS_GPIO
help
  This option enables support for the LEDs connected to GPIO
  outputs. To be useful the particular board must have LEDs
- and they must be connected to the GPIO lines.
+ and they must be connected to the GPIO lines.  The LEDs must be
+ defined as platform devices and/or OpenFirmware platform devices.
+ The code to use these bindings can be selected below.
+
+config LEDS_GPIO_PLATFORM
+   bool Platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ platform devices.  If you don't know what this means, say yes.
+
+config LEDS_GPIO_OF
+   bool OpenFirmware platform device bindings for GPIO LEDs
+   depends on LEDS_GPIO  OF_DEVICE
+   default y
+   help
+ Let the leds-gpio driver drive LEDs which have been defined as
+ of_platform devices.  For instance, LEDs which are listed in a dts
+ file.
 
 config LEDS_CM_X270
tristate LED Support for the CM-X270 LEDs
diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index b13bd29..f10f123 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -71,11 +71,52 @@ static int gpio_blink_set(struct led_classdev *led_cdev,
return led_dat-platform_gpio_blink_set(led_dat-gpio, delay_on, 
delay_off);
 }
 
-static int gpio_led_probe(struct platform_device *pdev)
+static int __devinit create_gpio_led(const struct gpio_led *template,
+   struct gpio_led_data *led_dat, struct device *parent,
+   int (*blink_set)(unsigned, unsigned long *, unsigned long *))
+{
+   int ret;
+
+   ret = gpio_request(template-gpio, template-name);
+   if (ret  0)
+   return ret;
+
+   led_dat

Re: PIXIS gpio controller and gpio flags

2008-07-23 Thread Trent Piepho
On Wed, 23 Jul 2008, Anton Vorontsov wrote:
 On Mon, Jul 21, 2008 at 02:12:20PM -0700, Trent Piepho wrote:
 On Mon, 21 Jul 2008, Anton Vorontsov wrote:
 On Sat, Jul 19, 2008 at 02:08:01PM -0700, Trent Piepho wrote:
 It doesn't look like you have any way to unset the active low flag.  What 
 if
 I unload the leds-gpio driver (or another gpio user) and then try to use 
 the
 gpio with something else?  The active low flag is stuck on!

 Why would you want to unset the flags? It is specified in the device
 tree, and can't be changed. Specifying different flags for the same GPIO
 would be an error (plus, Linux forbids shared gpios, so you simply can't
 specify one gpio for several devices).

 You can't use the same gpio for two different things at the same time, but 
 you
 can load a driver, unload it, and then load another.

 Hm.. yeah, this might happen. Now I tend to think that transparent
 active-low handling wasn't that good idea after all. So, something like
 of_gpio_is_active_low(device_node, gpioidx) should be implemented
 instead. This function will parse the gpio's =  flags. Please speak up
 if you have any better ideas though.

The flags could be provided via of_get_gpio.  E.g., something like
of_get_gpio(, u32 *flags), and if flags is non-NULL the gpio flags are
left there.  of_get_gpio already has the flags and some other of_get_*
functions return multiple things like this.

Or just have an active low property for the led:
led.active_low = !!of_get_property(np, active-low, NULL);

Pretty simple, just one line of code.  At least if one looks just at
leds-gpio, that's obviously the simplest way.  Is active low a property of
the led or a property of the gpio?  I guess one could argue either way.

It seems like putting one line of code leds-gpio driver is better than
putting much more complex code into the gpio controller driver.  And each
gpio controller has to have that code too.

Now you could say that each gpio user needing to support inverting gpios is
a lot of code too, but I don't think it's necessary.  Active low LEDs are
common since gpios can usually sink more current than they can source.  But
other gpio users, like the I2C, SPI, MDIO drivers etc., haven't had a need
to support inverting each signal.

I'm also loathe to add software gpio inverting to my mpc8572 gpio driver. 
In addition to some LEDs there is also a bit-banged JTAG bus on the CPU
GPIOs.  I had to go to great lengths to get it fast enough and each
instruction added to a gpio operation is going to cost me MHz.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: PIXIS gpio controller and gpio flags

2008-07-21 Thread Trent Piepho
On Mon, 21 Jul 2008, Anton Vorontsov wrote:
 On Sat, Jul 19, 2008 at 02:08:01PM -0700, Trent Piepho wrote:
 It doesn't look like you have any way to unset the active low flag.  What if
 I unload the leds-gpio driver (or another gpio user) and then try to use the
 gpio with something else?  The active low flag is stuck on!

 Why would you want to unset the flags? It is specified in the device
 tree, and can't be changed. Specifying different flags for the same GPIO
 would be an error (plus, Linux forbids shared gpios, so you simply can't
 specify one gpio for several devices).

You can't use the same gpio for two different things at the same time, but you
can load a driver, unload it, and then load another.

 Most gpio users, including leds-gpio, can handle gpios being busy.  If
 leds-gpio can't get one of the gpios, it rolls back all the leds it did
 create, doesn't drive the device and returns EBUSY.  Except with
 of_get_gpio() setting the flags, it will change the flags out from under
 whatever had the gpio already allocated!

 You're still assuming that something was allocated. It wasn't. The flag
 was set, and it should not change. It is irrelevant if request() failed
 or not.

Another driver has requested the gpio with active low NOT set.  Then the led
driver looks up the property with active low set, which changes the flags. 
When it tries to request the gpio it fails since the gpio is already in use. 
The led driver handles this failure.  Except the active low flag is now set
and the driver that was using the gpio before will now mysteriously stop
working.  Perhaps by erasing flash instead of reading it or something nasty
like that.

Is this the proper way to handle a dts mistake that has two drivers trying to
use the same gpio?  Without the gpio flags getting set when looking up the
gpio, this situation is handled without any difficulty.

And is having a gpio used twice in the device tree really a mistake?  What if
there are two different devices that can be attached to the gpios?  For
example, an LED bank that can be unplugged and a serial console attached in
its place, sharing the same connector and gpios.  Other than gpio flags
getting set when looking up a gpio, it works fine to list both devices in the
device tree as long as userspace has the correct driver loaded first.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: PIXIS gpio controller and gpio flags

2008-07-19 Thread Trent Piepho
On Fri, 18 Jul 2008, Anton Vorontsov wrote:
 +int px_gpio_xlate(struct of_gpio_chip *of_gc, struct device_node *np,
 +   const void *gpio_spec)
 +{
 + if (gpio[1]  PX_GPIO_FLAG_ACTIVE_LOW)
 + px_gc-active_low |= pin2mask(*gpio);

You have a race here.  What if px_gpio_xlate() is called at the same time
for different gpios?  This is an easy one to fix, since you can use the
atomic bitops.

It doesn't look like you have any way to unset the active low flag.  What if
I unload the leds-gpio driver (or another gpio user) and then try to use the
gpio with something else?  The active low flag is stuck on!  It doesn't show
in sysfs or debugfs either.  That could be very confusing.

I also wonder if it's ok to have the xlate function do flag setting?

of_get_property() just gets the property, it doesn't allocate it.  Same with
of_get_address() and of_get_pci_address(), they don't actually allocate or
map an address, they just get the value.  of_get_gpio() doesn't allocate the
gpio, that gets done later with gpio_request().  It seems like what it's
supposed to do is just get the translated value of the gpio property.

Except, your pixis gpio xlate function sets the gpio's flags.  What if one
wants to just look up a gpio number, but not allocate it?  The flags will
still get set.

Most gpio users, including leds-gpio, can handle gpios being busy.  If
leds-gpio can't get one of the gpios, it rolls back all the leds it did
create, doesn't drive the device and returns EBUSY.  Except with
of_get_gpio() setting the flags, it will change the flags out from under
whatever had the gpio already allocated!
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-18 Thread Trent Piepho
On Fri, 18 Jul 2008, Anton Vorontsov wrote:
 On Thu, Jul 17, 2008 at 01:18:18PM -0700, Trent Piepho wrote:
 Basically what I did then in my patch then, refactor leds-gpio so most of
 it is shared and there is a block of code that does platform binding and
 another block that does of_platform binding.

 Ok. I must admit I'm quite burned out with OF gpio-leds. I was posting the
 bindings since April, probably four or five times. Last time a week ago,
 IIRC.

 During the months I received just a few replies, one from Grant (Looks
 good to me.), few from Segher (with a lot of criticism, that I much
 appreciated and tried to fix all spotted issues), and one from Laurent
 (about active-low LEDs).

I'm sorry, I never saw those emails.  Were they all to linuxppc-dev?  I hate
reading that list, gmane, marc, and lkml.org don't archive it and
mail-archive.com isn't nearly as nice.

Is this the last version?
http://www.mail-archive.com/linuxppc-dev@ozlabs.org/msg18355.html

Why did you get rid of linux,default-trigger and the active-low property? 
I couldn't find any discussion about this.  When I first saw your current
patch I was going to add them, but I see you already had them and then
removed them.

I'd like to replace my led-hack stg patch with this, but I need
default-trigger to do that.  I don't need active-low or default-brightness,
but they seem like a good idea.  Actually, if you look closely at the patch
I posted, you'll see I had modified the existing leds-gpio driver to add a
default-brightness feature, though I don't need it anymore.  The requirement
changed from having an led on during kernel boot to having it flash.  I
have another hack for that, since there is no way to pass parameters to a
trigger.

 leds {
  compatible = gpio-led;
  [EMAIL PROTECTED] {
  gpios = mpc8572 6 0;
  label = red;
  };
  [EMAIL PROTECTED] {
  gpios = mpc8572 7 0;
  label = green;
  };
 };

 I like this. Or better what Grant suggested, i.e. move label to node
 name.

Ok, I used that.  It's like the new way partitions are defined in NOR flash
OF bindings.  My first example was more like the old way.  The led name can
come from a label property or if there is none then the node name is used. 
I don't think you can have colons or spaces in node names.  I don't have a
default trigger property, but I'd really like to have that.  I could add an
active low flag too.  Maybe compatible should be gpio-leds, since you can
define more than one?

The patch is done and works for me.  One can select platform device and/or
of_platform device support via Kconfig.  I'll port it to the git kernel and
post it soon.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-17 Thread Trent Piepho
On Thu, 17 Jul 2008, Anton Vorontsov wrote:
 On Wed, Jul 16, 2008 at 10:13:06PM -0700, Trent Piepho wrote:
 Ok, how about adding code the existing leds-gpio driver so that it can 
 creates
 LEDs from of_platform devices too?

 Few comments below.

 I've made a patch to do this and it works ok.  The code added to leds-gpio is
 about half what was involved in Anton's new driver.

 This isn't true.

Your new driver was 194 lines, not counting docs or Kconfig.  My patch
added about 104 lines to the existing leds-gpio driver.  So yes, about half
the code.

 There is still one of_platform device per led because of how the bindings 
 work
 (but that could be changed with new bindings), but there are zero extra
 platform devices created.

 You didn't count extra platform driver. You can't #ifdef it. The only way
 you can avoid this is creating leds-gpio-base.c or something, and place the
 helper functions there.

I guess, in terms of compiled size, the combined platform + of_platform
driver is bigger than the of_platform only driver.  Though it's much
smaller than having both the platform only and of_platform only drivers. 
In terms of source code, there's less with the combined driver.

I don't see why the combined leds-gpio driver can't have an ifdef for the
platform part.  All the platform driver specific code is already in one
contiguous block.  In fact, I just did it and it works fine.  My LEDs from
the dts were created and the LED I have as a platform device wasn't, as
expected.  Here's the patch, pretty simple:

diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -108,2 +108,3 @@ static int create_gpio_led(struct gpio_led *cur_led,

+#ifdef CONFIG_LEDS_GPIO_PLATFORM
  static int gpio_led_probe(struct platform_device *pdev)
@@ -222,2 +223,3 @@ module_init(gpio_led_init);
  module_exit(gpio_led_exit);
+#endif /* CONFIG_LEDS_GPIO_PLATFORM */


 +static int create_gpio_led(struct gpio_led *cur_led,

 The create_gpio_led() interface is also quite weird, since it implies that
 we have to pass two GPIO LED handles: struct gpio_led_data (that we
 allocated) and temporary struct gpio_led. And this helper function will
 just assign things from one struct to another, and then will register the
 led.

It creates a thing from a template passed a pointer to a struct.  This is
very common, there must be hundreds of functions in the kernel that work
this way.  The difference is instead of allocating and returning the
created thing, you pass it a blank pre-allocated thing to fill in and
register.  I know there is other code that works this way too.  It's
usually used, like it is here, so you can allocate a bunch of things at
once and then register them one at a time.

 With OF driver I don't need struct gpio_led. Only the platform driver
 need this so platforms could pass gpio led info through it, while with OF
 we're getting all information from the device tree.

The struct gpio_led is just used to pass the stats to the led creation
function.  It doesn't stick around.  You could use local variables for the
gpio and name and pass them to the create led function.  Bundling them into
a struct is an tiny change that lets more code be shared.

 +/* #ifdef CONFIG_LEDS_GPIO_OF */

 Heh.

Obviously the OF binding code should be conditional, selectable from
kconfig if the platform has OF support.  It's all in one contiguous block
and that shows where the ifdef would go.  I didn't think it was necessary
to include the obvious kconfig patch.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-17 Thread Trent Piepho
On Thu, 17 Jul 2008, Grant Likely wrote:
 Alternately, I would also be okay with a scheme where all LED nodes
 have a common parent and an of_platform driver would bind against the
 parent node; not the individual children.  Then the leds-gpio driver
 could be refactored to have both platform and of_platform bus
 bindings.

Basically what I did then in my patch then, refactor leds-gpio so most of
it is shared and there is a block of code that does platform binding and
another block that does of_platform binding.

I didn't change the OF platform binding syntax so as not to complicate the
example, but that's easy to do.  Something like:

leds {
compatible = gpio-led;
gpios = mpc8572 6 0
 mpc8572 7 0;
labels = red, green;
};

Or like this, which needs a little more code to parse:

leds {
compatible = gpio-led;
[EMAIL PROTECTED] {
gpios = mpc8572 6 0;
label = red;
};
[EMAIL PROTECTED] {
gpios = mpc8572 7 0;
label = green;
};
};

I like the first better.  It follows the example from the docs about how
devices with multiple gpios should work too.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-16 Thread Trent Piepho
On Tue, 15 Jul 2008, Anton Vorontsov wrote:
 Despite leds-gpio and leds-openfirmware-gpio similar purposes, there
 is not much code can be shared between the two drivers (both are mostly
 driver bindings anyway).

Why can't this driver use the existing gpio-led driver?  Basically, do
something like this:

of_gpio_leds_probe(...)
{
gpio = of_get_gpio(np, 0);
label = of_get_property(np, label, NULL);

struct gpio_led led = {
.name = label,
.gpio = gpio,
};

pdev = platform_device_register_simple(leds-gpio, 0, NULL, 0);
platform_device_add_data(pdev, led, sizeof(led));
}
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v2] leds: implement OpenFirmare GPIO LED driver

2008-07-16 Thread Trent Piepho
On Tue, 15 Jul 2008, Richard Purdie wrote:
 On Tue, 2008-07-15 at 18:23 +0400, Anton Vorontsov wrote:
 Spell out openfirmware :). I initially had no idea of == openfirmware
 and I suspect others won't either...

 This would be unusually long name, that is

 $ find . -iname '*openfirmware*' | wc -l
 0

 And in contrast:

 drivers/video/offb.c
 drivers/video/nvidia/nv_of.c
 drivers/usb/host/ohci-ppc-of.c
 drivers/usb/host/ehci-ppc-of.c
 drivers/serial/of_serial.c
 drivers/mtd/maps/physmap_of.c
 ...

 So, I think we should stick with the of for consistency, while
 confused users may consult with Kconfig for disambiguation.

 The other cases don't have a gpio driver to confuse this new driver
 with. Lets spell it out please, the filesystems can handle the extra
 letters :).

There's drivers/mtd/maps/physmap.c and drivers/mtd/maps/physmap_of.c,
drivers/serial/of_serial.c and drivers/serial/serial_core.c,
drivers/usb/host/ehci-ppc-soc.c and drivers/usb/host/ehci-ppc-of.c, etc.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: [PATCH v3] leds: implement OpenFirmare GPIO LED driver

2008-07-16 Thread Trent Piepho
on Wed, 16 Jul 2008, Grant Likely wrote:
 On Wed, Jul 16, 2008 at 04:18:52PM -0700, Trent Piepho wrote:
 On Tue, 15 Jul 2008, Anton Vorontsov wrote:
 Despite leds-gpio and leds-openfirmware-gpio similar purposes, there
 is not much code can be shared between the two drivers (both are mostly
 driver bindings anyway).

 Why can't this driver use the existing gpio-led driver?  Basically, do
 something like this:


 Ugh; that means registering *2* 'struct device' with the kernel instead of
 one.  One as a platform device and one as an of_platform device.
 It's bad enough that the LED scheme we're using for OF bindings has a
 separate registration for every single LED.

Ok, how about adding code the existing leds-gpio driver so that it can creates
LEDs from of_platform devices too?

I've made a patch to do this and it works ok.  The code added to leds-gpio is
about half what was involved in Anton's new driver.  What I did was re-factor
the existing platform device probe function to use a new function that creates
a single led.  Then a new of_platform probe function can use it too.  That way
most of the probe code is shared.  remove, suspend and resume aren't shared,
but they're short.  And the existing code to actually drive the led gets
reused as is.

There is still one of_platform device per led because of how the bindings work
(but that could be changed with new bindings), but there are zero extra
platform devices created.

Here's an example patch.  It won't apply to the git kernel as is, but should
make it clear how this works.

diff --git a/drivers/leds/leds-gpio.c b/drivers/leds/leds-gpio.c
index a4a2838..12e681e 100644
--- a/drivers/leds/leds-gpio.c
+++ b/drivers/leds/leds-gpio.c
@@ -71,11 +71,45 @@ static int gpio_blink_set(struct led_classdev *led_cdev,
return led_dat-platform_gpio_blink_set(led_dat-gpio, delay_on, 
delay_off);
  }

+static int create_gpio_led(struct gpio_led *cur_led,
+   struct gpio_led_data *led_dat, struct device *parent,
+   int (*blink_set)(unsigned, unsigned long *, unsigned long *))
+
+{
+   int ret;
+
+   ret = gpio_request(cur_led-gpio, cur_led-name);
+   if (ret  0)
+   return ret;
+
+   led_dat-cdev.name = cur_led-name;
+   led_dat-cdev.default_trigger = cur_led-default_trigger;
+   led_dat-gpio = cur_led-gpio;
+   led_dat-can_sleep = gpio_cansleep(cur_led-gpio);
+   led_dat-active_low = cur_led-active_low;
+   if (blink_set) {
+   led_dat-platform_gpio_blink_set = blink_set;
+   led_dat-cdev.blink_set = gpio_blink_set;
+   }
+   led_dat-cdev.brightness_set = gpio_led_set;
+   led_dat-cdev.brightness = cur_led-start_on ? LED_FULL : LED_OFF;
+
+   gpio_direction_output(led_dat-gpio,
+ led_dat-active_low ^ cur_led-start_on);
+
+   INIT_WORK(led_dat-work, gpio_led_work);
+
+   ret = led_classdev_register(parent, led_dat-cdev);
+   if (ret  0)
+   gpio_free(led_dat-gpio);
+
+   return ret;
+}
+
  static int gpio_led_probe(struct platform_device *pdev)
  {
struct gpio_led_platform_data *pdata = pdev-dev.platform_data;
-   struct gpio_led *cur_led;
-   struct gpio_led_data *leds_data, *led_dat;
+   struct gpio_led_data *leds_data;
int i, ret = 0;

if (!pdata)
@@ -87,36 +121,10 @@ static int gpio_led_probe(struct platform_device *pdev)
return -ENOMEM;

for (i = 0; i  pdata-num_leds; i++) {
-   cur_led = pdata-leds[i];
-   led_dat = leds_data[i];
-
-   ret = gpio_request(cur_led-gpio, cur_led-name);
+   ret = create_gpio_led(pdata-leds[i], leds_data[i],
+ pdev-dev, pdata-gpio_blink_set);
if (ret  0)
goto err;
-
-   led_dat-cdev.name = cur_led-name;
-   led_dat-cdev.default_trigger = cur_led-default_trigger;
-   led_dat-gpio = cur_led-gpio;
-   led_dat-can_sleep = gpio_cansleep(cur_led-gpio);
-   led_dat-active_low = cur_led-active_low;
-   if (pdata-gpio_blink_set) {
-   led_dat-platform_gpio_blink_set = 
pdata-gpio_blink_set;
-   led_dat-cdev.blink_set = gpio_blink_set;
-   }
-   led_dat-cdev.brightness_set = gpio_led_set;
-   led_dat-cdev.brightness =
-   cur_led-start_on ? LED_FULL : LED_OFF;
-
-   gpio_direction_output(led_dat-gpio,
- led_dat-active_low ^ cur_led-start_on);
-
-   INIT_WORK(led_dat-work, gpio_led_work);
-
-   ret = led_classdev_register(pdev-dev, led_dat-cdev);
-   if (ret  0) {
-   gpio_free(led_dat-gpio);
-   goto err;
-   }
}

platform_set_drvdata(pdev, leds_data);
@@ -217,3 +225,105 @@ MODULE_AUTHOR

Re: [PATCH] [Rev2] MPC5121 FEC support

2008-06-17 Thread Trent Piepho

On Tue, 17 Jun 2008, Scott Wood wrote:

Sam Ravnborg wrote:

 In general when you select a symbol that has dependencies you are almost
 always on the wrong track.


more specific options should make sure that they never select it when the 
dependencies aren't met.


Sure, in theory that would work, but in practice this ends up being a constant
source of broken builds.


 Use a dependency here with a sane default - then people can set it to 'n'
 if they really do not want this driver.

 Spreading selects too much is just causing you pain in the long run.


I'm not sure I understand what you're looking for, but I don't see anything 
wrong with something like this (apart from missing help text):


config FS_ENET
 bool
 select MII
 select PHYLIB

config FS_ENET_HAS_SCC
 bool Freescale CPM SCC Ethernet
 depends on CPM1 || CPM2
 select FS_ENET


What prevents me from turning on FS_ENET_HAS_SCC without MII or PHYLIB?  Why
is FS_ENET_HAS_SCC a bool, and not tristate?
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: MMIO and gcc re-ordering issue

2008-06-03 Thread Trent Piepho

On Tue, 3 Jun 2008, Linus Torvalds wrote:

On Tue, 3 Jun 2008, Nick Piggin wrote:


Linus: on x86, memory operations to wc and wc+ memory are not ordered
with one another, or operations to other memory types (ie. load/load
and store/store reordering is allowed). Also, as you know, store/load
reordering is explicitly allowed as well, which covers all memory
types. So perhaps it is not quite true to say readl/writel is strongly
ordered by default even on x86. You would have to put in some
mfence instructions in them to make it so.


So on x86, these could be re-ordered?

writel(START_OPERATION, CONTROL_REGISTER);
status = readl(STATUS_REGISTER);


Well, you have to ask for WC/WC+ anyway, so it's immaterial. A driver that
does that needs to be aware of it. IOW, it's a non-issue, imnsho.


You need to ask for coherent DMA memory too.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: MMIO and gcc re-ordering issue

2008-06-03 Thread Trent Piepho

On Tue, 3 Jun 2008, Matthew Wilcox wrote:

On Tue, Jun 03, 2008 at 11:47:00AM -0700, Trent Piepho wrote:

On Tue, 3 Jun 2008, Linus Torvalds wrote:

On Tue, 3 Jun 2008, Nick Piggin wrote:


Linus: on x86, memory operations to wc and wc+ memory are not ordered
with one another, or operations to other memory types (ie. load/load
and store/store reordering is allowed). Also, as you know, store/load
reordering is explicitly allowed as well, which covers all memory
types. So perhaps it is not quite true to say readl/writel is strongly
ordered by default even on x86. You would have to put in some
mfence instructions in them to make it so.


So on x86, these could be re-ordered?

writel(START_OPERATION, CONTROL_REGISTER);
status = readl(STATUS_REGISTER);


You wouldn't ask for write-combining memory mapping for control or
status registers.


But Nick said, store/load reordering is explicitly allowed as well, which
covers *all* memory types.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: MMIO and gcc re-ordering issue

2008-06-03 Thread Trent Piepho

On Tue, 3 Jun 2008, Nick Piggin wrote:

On Monday 02 June 2008 17:24, Russell King wrote:

So, can the semantics of what's expected from these IO accessor
functions be documented somewhere.  Please?  Before this thread gets
lost in the depths of time?


This whole thread also ties in with my posts about mmiowb (which IMO
should go away).

readl/writel:  strongly ordered wrt one another and other stores
  to cacheable RAM, byteswapping
__readl/__writel:  not ordered (needs mb/rmb/wmb to order with
  other readl/writel and cacheable operations, or
  io_*mb to order with one another)
raw_readl/raw_writel:  strongly ordered, no byteswapping
__raw_readl/__raw_writel:  not ordered, no byteswapping


Byte-swapping vs not byte-swapping is not usually what the programmer wants. 
Usually your device's registers are defined as being big-endian or

little-endian and you want whatever is needed to give you that.

I believe that on some archs that can be either byte order, some built-in
devices will change their registers to match, and so you want native endian
or no swapping for these.  Though that's definitely in the minority.

An accessors that always byte-swaps regardless of the endianness of the host
is never something I've seen a driver want.

IOW, there are four ways one can defined endianness/swapping:
1) Little-endian
2) Big-endian
3) Native-endian aka non-byte-swapping
4) Foreign-endian aka byte-swapping

1 and 2 are by far the most used.  Some code wants 3.  No one wants 4.  Yet
our API is providing 3  4, the two which are the least useful.

Is it enough to provide only all or none for ordering strictness?  For
instance on powerpc, one can get a speedup by dropping strict ordering for IO
vs cacheable memory, but still keeping ordering for IO vs IO and IO vs locks. 
This is much easier to program for than no ordering at all.  In fact, if one

doesn't use coherent DMA, it's basically the same as fully strict ordering.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: MMIO and gcc re-ordering issue

2008-06-03 Thread Trent Piepho

On Tue, 3 Jun 2008, Matthew Wilcox wrote:

On Tue, Jun 03, 2008 at 12:43:21PM -0700, Trent Piepho wrote:

IOW, there are four ways one can defined endianness/swapping:
1) Little-endian
2) Big-endian
3) Native-endian aka non-byte-swapping
4) Foreign-endian aka byte-swapping

1 and 2 are by far the most used.  Some code wants 3.  No one wants 4.  Yet
our API is providing 3  4, the two which are the least useful.


You've fundamentally misunderstood.

readX/writeX and __readX/__writeX provide little-endian access.
__raw_readX provide native-endian.

If you want 2 or 4, define your own accessors.  Some architectures define
other accessors (eg gsc_readX on parisc is native (big) endian, and


How about providing 1 and 2, and if you want 3 or 4 define your own accessors?


Is it enough to provide only all or none for ordering strictness?  For
instance on powerpc, one can get a speedup by dropping strict ordering for
IO
vs cacheable memory, but still keeping ordering for IO vs IO and IO vs
locks. This is much easier to program for than no ordering at all.  In
fact, if one
doesn't use coherent DMA, it's basically the same as fully strict ordering.


I don't understand why you keep talking about DMA.  Are you talking
about ordering between readX() and DMA?  PCI proides those guarantees.


I guess you haven't been reading the whole thread.  The reason it started was
because gcc can re-order powerpc (and everyone else's too) IO accesses vs
accesses to cachable memory (but not spin-locks), which ends up only being a
problem with coherent DMA.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


Re: MMIO and gcc re-ordering issue

2008-06-03 Thread Trent Piepho

On Tue, 3 Jun 2008, Matthew Wilcox wrote:

On Tue, Jun 03, 2008 at 12:57:56PM -0700, Trent Piepho wrote:

On Tue, 3 Jun 2008, Matthew Wilcox wrote:

On Tue, Jun 03, 2008 at 11:47:00AM -0700, Trent Piepho wrote:

On Tue, 3 Jun 2008, Linus Torvalds wrote:

On Tue, 3 Jun 2008, Nick Piggin wrote:


Linus: on x86, memory operations to wc and wc+ memory are not ordered
with one another, or operations to other memory types (ie. load/load
and store/store reordering is allowed). Also, as you know, store/load
reordering is explicitly allowed as well, which covers all memory
types. So perhaps it is not quite true to say readl/writel is strongly
ordered by default even on x86. You would have to put in some
mfence instructions in them to make it so.


So on x86, these could be re-ordered?

writel(START_OPERATION, CONTROL_REGISTER);
status = readl(STATUS_REGISTER);


You wouldn't ask for write-combining memory mapping for control or
status registers.


But Nick said, store/load reordering is explicitly allowed as well, which
covers *all* memory types.


Then Nick is confused.  PCI only defines one way to flush posted writes
to a device -- doing a read from it.  There's no way that reads can
be allowed to pass writes (unless you've asked for it, like with write
combining).


But that requirement is for the PCI bridge, isn't it?  It doesn't matter if
the bridge will flush all posted writes before allowing a read if the CPU
decides to give the bridge the read before the write.  A powerpc CPU will
certainly do this if you don't take any steps like telling it the memory is
uncachable and guarded.  I didn't think it was allowed on x86 (except with
WC), but Nick seemed to say it was.
___
Linuxppc-dev mailing list
Linuxppc-dev@ozlabs.org
https://ozlabs.org/mailman/listinfo/linuxppc-dev


  1   2   >