* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Sergei Shtylyov @ 2007-07-25 19:00 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165318.5331.23795.stgit@localhost.localdomain>
Vitaly Bordug wrote:
> This is now very similar to pata_platform.c, they both use
> same platform data structure and same resources.
> To achieve that, byte_lanes_swapping platform data variable
> and platform specified iops removed from that driver. It's fine,
> since those were never used anyway.
Hopefully, PPC will never need them.
> pata_platform and ide_platform are carrying same driver names,
> to easily switch between these drivers, without need to touch
> platform code.
> diff --git a/drivers/ide/legacy/ide_platform.c b/drivers/ide/legacy/ide_platform.c
> new file mode 100644
> index 0000000..0b3f5b5
> --- /dev/null
> +++ b/drivers/ide/legacy/ide_platform.c
> @@ -0,0 +1,181 @@
> +/*
> + * Platform IDE driver
> + *
> + * Copyright (C) 2007 MontaVista Software
> + *
> + * Maintainer: Kumar Gala <galak@kernel.crashing.org>
Poor Kumar, I guess he was surprised be being assigned a maintainer of the
driver he didn't write (well, even if it borrowed some code from his earlier
one ;-)...
> + *
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms of the GNU General Public License as published by the
> + * Free Software Foundation; either version 2 of the License, or (at your
> + * option) any later version.
> + */
> +
> +#include <linux/types.h>
> +#include <linux/init.h>
> +#include <linux/kernel.h>
> +#include <linux/ide.h>
> +#include <linux/ioport.h>
> +#include <linux/module.h>
> +#include <linux/pata_platform.h>
> +#include <linux/io.h>
> +
> +static struct {
> + void __iomem *plat_ide_mapbase;
> + void __iomem *plat_ide_alt_mapbase;
> + ide_hwif_t *hwif;
> + int index;
> +} hwif_prop;
> +
> +static ide_hwif_t *__devinit plat_ide_locate_hwif(void __iomem *base,
> + void __iomem *ctrl, struct pata_platform_info *pdata, int irq,
> + int mmio)
> +{
> + unsigned long port = (unsigned long)base;
> + ide_hwif_t *hwif;
> + int index, i;
> +
> + for (index = 0; index < MAX_HWIFS; ++index) {
> + hwif = ide_hwifs + index;
> + if (hwif->io_ports[IDE_DATA_OFFSET] == port)
> + goto found;
> + }
> +
> + for (index = 0; index < MAX_HWIFS; ++index) {
> + hwif = ide_hwifs + index;
> + if (hwif->io_ports[IDE_DATA_OFFSET] == 0)
> + goto found;
> + }
> +
> + return NULL;
> +
> +found:
> +
> + hwif->hw.io_ports[IDE_DATA_OFFSET] = port;
> +
> + port += (1 << pdata->ioport_shift);
> + for (i = IDE_ERROR_OFFSET; i <= IDE_STATUS_OFFSET;
> + i++, port += (1 << pdata->ioport_shift))
Looks like shift doesn't buy as anything, why not just use stride?
> + hwif->hw.io_ports[i] = port;
> +
> + hwif->hw.io_ports[IDE_CONTROL_OFFSET] = (unsigned long)ctrl;
> +
> + memcpy(hwif->io_ports, hwif->hw.io_ports, sizeof(hwif->hw.io_ports));
> + hwif->hw.irq = hwif->irq = irq;
> +
> + hwif->hw.dma = NO_DMA;
> + hwif->hw.chipset = ide_generic;
> +
> + if (mmio) {
> + hwif->mmio = 1;
> + default_hwif_mmiops(hwif);
> + }
And why default_hwif_iops(hwif) is not called else?
And I remember the previos variant was overriding INSW()/OUTSW() methods
-- turned out to be unnecessary? :-)
> +
> + hwif_prop.hwif = hwif;
> + hwif_prop.index = index;
> +
> + return hwif;
> +}
> +
> +static int __devinit plat_ide_probe(struct platform_device *pdev)
> +{
> + struct resource *res_base, *res_alt, *res_irq;
> + ide_hwif_t *hwif;
> + struct pata_platform_info *pdata;
> + int ret = 0;
> + int mmio = 0;
> +
> + pdata = pdev->dev.platform_data;
> +
> + /* get a pointer to the register memory */
> + res_base = platform_get_resource(pdev, IORESOURCE_IO, 0);
> + res_alt = platform_get_resource(pdev, IORESOURCE_IO, 1);
> +
> + if (!res_base || !res_alt) {
> + res_base = platform_get_resource(pdev, IORESOURCE_MEM, 0);
> + res_alt = platform_get_resource(pdev, IORESOURCE_MEM, 1);
> + if (!res_base || !res_alt) {
> + ret = -ENOMEM;
ENODEV or EINVAL you mean? :-)
> + goto out;
Bleh... just return please.
> + }
> + mmio = 1;
> + }
> +
> + res_irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
> + if (!res_irq) {
> + ret = -EINVAL;
> + goto out;
Bleh... return -EINVAL, please. Or maybe -ENODEV.
> + }
> +
[...]
> + hwif = plat_ide_locate_hwif(hwif_prop.plat_ide_mapbase,
> + hwif_prop.plat_ide_alt_mapbase, pdata, res_irq->start, mmio);
> +
> + if (!hwif) {
> + ret = -ENODEV;
> + goto out;
Bleh... please just
return -ENODEV.
> + }
> + hwif->gendev.parent = &pdev->dev;
> + hwif->noprobe = 0;
> +
> + probe_hwif_init(hwif);
> +
> + platform_set_drvdata(pdev, hwif);
> + ide_proc_register_port(hwif);
> +
> + return 0;
> +
> +out:
No need to abuse the function cleanup style when you have nothing to
cleanup. :-/
> + return ret;
> +}
> +
> +static int __devexit plat_ide_remove(struct platform_device *pdev)
> +{
> + ide_hwif_t *hwif = pdev->dev.driver_data;
> +
> + if (hwif != hwif_prop.hwif) {
> + dev_printk(KERN_DEBUG, &pdev->dev, "%s: hwif value error",
> + pdev->name);
> + } else {
> + ide_unregister(hwif_prop.index);
> + hwif_prop.index = 0;
> + hwif_prop.hwif = NULL;
> + }
> +
I'd have interchanged the success/failure branches...
> + return 0;
> +}
> +
> +static struct platform_driver platform_ide_driver = {
> + .driver {
> + .name = "pata_platform",
> + },
> + .probe = plat_ide_probe,
> + .remove = __devexit_p(plat_ide_remove),
> +};
> +
> +static int __init platform_ide_init(void)
> +{
> + return platform_driver_register(&platform_ide_driver);
> +}
> +
> +static void __exit platform_ide_exit(void)
> +{
> + platform_driver_unregister(&platform_ide_driver);
> +}
> +
> +MODULE_DESCRIPTION("Platform IDE driver");
> +MODULE_LICENSE("GPL");
> +
> +module_init(platform_ide_init);
> +module_exit(platform_ide_exit);
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Scott Wood @ 2007-07-25 18:46 UTC (permalink / raw)
To: Sergei Shtylyov; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <46A7968D.3070707@ru.mvista.com>
Sergei Shtylyov wrote:
> I acn undertand your complaint in the context of an OF driver (which
> we don't have yet) but "mmio-ide" just means nothing to the current
> driver, and it doesn't convery enough info on the programming interface
> for the conceivable OF driver, it also does need to know at least
> "reg-stride" (and maybe "reg-size" in case only 16/32-bit accesses can
> be used). Well, if such driver will be written, I/O mapping support
> will probably be dropped from it, so indeed, calling it mmio-ide.c would
> make sense. But that can be added when this driver is done, and for now
I don't think the details of what Linux code currently exists should
drive the device tree binding. That the current patches use
platform_device glue code is an implementation detail (and one I'd
rather see go away, in favor of a driver that supports both
platform_device and of_device).
> I'd really prefer the board name to appear in the "compatible" prop (to
> which "mmio-ide" can be appended)...
Sure, that's always good... it was the "instead" that I objected to.
-Scott
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Scott Wood @ 2007-07-25 18:39 UTC (permalink / raw)
To: Sergei Shtylyov; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <46A7941F.2050300@ru.mvista.com>
Sergei Shtylyov wrote:
> Hello.
>
> Scott Wood wrote:
>
>>> Also, what mmio-ide in the compat properly means in the context of
>>> ide_platform which is able to handle both port and memory mapped IDE.
>
>
>> I/O-space is only valid in the context of PCI, ISA, or similar buses, and
>> the bus-specific reg format indicates whether it's mmio-space or
>> io-space.
>
> You could save time on lecturing me (and use it to look on the driver
> ;-).
Sorry, I misread the question as being a mismatch between the
capabilities of the device binding and the driver, not about the
specific compatible name. Something like "generic-ide" would probably
be better.
>> What is board specific about a set of standard IDE registers at a given
>
> The regisrer mapping used is highly non-standard.
The gap between registers is nonstandard, but that's a fairly common
type of noncompliance in embedded-land, and probably merits being
supported in a generic way. I wouldn't call it "highly" nonstandard.
Is there some other non-standardness that I'm missing?
> We're already in board specific code, so why the heck not? :-)
>
>> various ns16550-compatibles out there as well?
>
> I never suggested that -- what I did suggest was make of_serial.c
> recognize certain chip types and register them with 8250 driver.
What would be the advantage of maintaining a list of chips whose only
difference is register spacing, rather than just using reg-shift and
being done with it?
-Scott
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Sergei Shtylyov @ 2007-07-25 18:29 UTC (permalink / raw)
To: Scott Wood; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <20070725180145.GA29689@ld0162-tx32.am.freescale.net>
Scott Wood wrote:
>> Also, what mmio-ide in the compat properly means in the context of
>>ide_platform which is able to handle both port and memory mapped IDE.
>>I think we must get rid with this crap, and since this IDE register
>>mapping is pretty much board specific, call it something like
>>"mpc8349emitx-ide" instead.
> What is board specific about a set of standard IDE registers at a given
> address? Do we need to make board-specific glue code for all of the
> various ns16550-compatibles out there as well?
I acn undertand your complaint in the context of an OF driver (which we
don't have yet) but "mmio-ide" just means nothing to the current driver, and
it doesn't convery enough info on the programming interface for the
conceivable OF driver, it also does need to know at least "reg-stride" (and
maybe "reg-size" in case only 16/32-bit accesses can be used). Well, if such
driver will be written, I/O mapping support will probably be dropped from it,
so indeed, calling it mmio-ide.c would make sense. But that can be added when
this driver is done, and for now I'd really prefer the board name to appear in
the "compatible" prop (to which "mmio-ide" can be appended)...
> -Scott
WBR, Sergei
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Sergei Shtylyov @ 2007-07-25 18:19 UTC (permalink / raw)
To: Scott Wood; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <20070725180145.GA29689@ld0162-tx32.am.freescale.net>
Hello.
Scott Wood wrote:
>> Also, what mmio-ide in the compat properly means in the context of
>>ide_platform which is able to handle both port and memory mapped IDE.
> I/O-space is only valid in the context of PCI, ISA, or similar buses, and
> the bus-specific reg format indicates whether it's mmio-space or
> io-space.
You could save time on lecturing me (and use it to look on the driver ;-).
>>I think we must get rid with this crap, and since this IDE register
>>mapping is pretty much board specific, call it something like
>>"mpc8349emitx-ide" instead.
> What is board specific about a set of standard IDE registers at a given
The regisrer mapping used is highly non-standard.
> address? Do we need to make board-specific glue code for all of the
We're already in board specific code, so why the heck not? :-)
> various ns16550-compatibles out there as well?
I never suggested that -- what I did suggest was make of_serial.c
recognize certain chip types and register them with 8250 driver.
> -Scott
MBR, Sergei
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Scott Wood @ 2007-07-25 18:01 UTC (permalink / raw)
To: Sergei Shtylyov; +Cc: linuxppc-dev, linux-kernel, linux-ide
In-Reply-To: <46A78E3F.1030904@ru.mvista.com>
On Wed, Jul 25, 2007 at 09:54:07PM +0400, Sergei Shtylyov wrote:
> Also, what mmio-ide in the compat properly means in the context of
> ide_platform which is able to handle both port and memory mapped IDE.
I/O-space is only valid in the context of PCI, ISA, or similar buses, and
the bus-specific reg format indicates whether it's mmio-space or
io-space.
> I think we must get rid with this crap, and since this IDE register
> mapping is pretty much board specific, call it something like
> "mpc8349emitx-ide" instead.
What is board specific about a set of standard IDE registers at a given
address? Do we need to make board-specific glue code for all of the
various ns16550-compatibles out there as well?
-Scott
^ permalink raw reply
* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Kumar Gala @ 2007-07-25 17:59 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165318.5331.23795.stgit@localhost.localdomain>
On Jul 25, 2007, at 11:53 AM, Vitaly Bordug wrote:
>
> This is now very similar to pata_platform.c, they both use
> same platform data structure and same resources.
>
> To achieve that, byte_lanes_swapping platform data variable
> and platform specified iops removed from that driver. It's fine,
> since those were never used anyway.
>
> pata_platform and ide_platform are carrying same driver names,
> to easily switch between these drivers, without need to touch
> platform code.
>
> Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
> Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
Out of interest is this something that could exist in pata land? I
haven't really been following legacy/ide vs pata lately.
- k
^ permalink raw reply
* Re: [RFC 0/1] lro: Generic Large Receive Offload for TCP traffic
From: Andrew Gallatin @ 2007-07-25 17:17 UTC (permalink / raw)
To: Jan-Bernd Themann
Cc: Thomas Klein, Jeff Garzik, Jan-Bernd Themann, netdev,
linux-kernel, linux-ppc, Christoph Raisch, Marcus Eder,
Stefan Roscher, David Miller
In-Reply-To: <200707201741.45079.ossthema@de.ibm.com>
[-- Attachment #1: Type: text/plain, Size: 6259 bytes --]
Hi,
I've ported myri10ge to use the new LRO interface. I have attached a
preliminary patch to myri10ge. I'm very pleased to note that the
performance is on-par with my own LRO used by our out-of-tree driver.
(except when using mixed MTUS, see performance data below).
As I expected, actually porting our driver to use the LRO interface
gave me a far better understanding of the interface, and allowed for
better feedback. I have attached a patch to the LRO code which
addresses some of the issues I mention below.
Please find below a performance summary, as well as my comments
on the LRO code, and patches to myri10ge and inet_lro. Both patches
are Signed-off-by: Andrew J. Gallatin <gallatin@myri.com>
Cheers,
Drew
===================
Performance:
===================
Here is a performance summary taken on my very low-end 2.0GHz AMD
Athlon(tm) 64 X2 Dual Core Processor 3800+ running 2.6.23-rc1 and
receiving a netperf TCP_SENDFILE test from an identical sender (which
was running 2.6.22 and our 1.3.1 "out of tree" driver). The netserver
process was bound to a different core than the interrupt handler. The
data reported is from the median of 5 60 second netperf tests. The
following settings were in /etc/sysctl.conf on both machines:
net.core.rmem_max = 16777216
net.core.wmem_max = 16777216
net.ipv4.tcp_rmem = 4096 87380 16777216
net.ipv4.tcp_wmem = 4096 65536 16777216
net.core.netdev_max_backlog = 2500
net.ipv4.tcp_timestamps = 0
RX Performance for Sender MTU=1500, Receiver MTU=1500 expressed as
"x Gb/s, y %CPU receiver utilization":
rxbuf(1) 1.3.1(2) inet_lro no LRO
----- ------- ------- --------
4K pg 8.9 78% 8.8 77% 3.7 89%
8K pg 9.2 77% 9.1 77% 3.7 89%
16Kpg 9.4 73% 9.4 73% 3.8 89%
32Kpg 9.4 72% 9.4 72% 3.9 89%
skb N/A N/A 5.5 90% 4.1 92%
RX Performance for Sender MTU=1500, Receiver MTU=9000 expressed as
"x Gb/s, y %CPU receiver utilization":
rxbuf(1) 1.3.1(2) inet_lro no LRO
----- ------- ------- --------
4K pg 8.9 78% 7.3 79% 3.7 89%
8K pg 9.2 77% 7.6 79% 3.7 89%
16Kpg 9.4 73% 8.0 78% 3.8 89%
32Kpg 9.4 72% 8.2 79% 3.9 89%
skb N/A N/A 4.9 92% 4.1 92%
RX Performance for Sender MTU=9000, Receiver MTU=9000 expressed as
"x Gb/s, y %CPU receiver utilization":
rxbuf(1) 1.3.1(2) inet_lro no LRO
----- ------- ------- --------
4K pg 9.9 63% 9.6 66% 8.3 71%
8K pg 9.9 60% 9.9 63% 8.4 72%
16Kpg 9.9 55% 9.9 55% 8.7 70%
32Kpg 9.9 53% 9.9 53% 8.9 67%
skb N/A N/A 9.9 68% 8.7 72%
(1) "xK pg" means the driver was configured to adjust the receive page
size using MYRI10GE_ALLOC_ORDER. "skb" means an internal variant
of our driver which receives into skbs rather than pages was used.
(2) "1.3.1" is our latest out of tree driver which uses the myri10ge
specific frags-based LRO code previously submitted and rejected.
===================
Code review / comments:
===================
1) Checksum information for CHECKSUM_COMPLETE drivers.
Our NIC passes partial checksums to our driver. In the current code,
it seems impossible for page based CHECKSUM_COMPLETE drivers to behave
correctly in the case of "rejected" frames. Eg, there is no way
to pass the partial checksum to the LRO module so that it gets
set in the skb header and passed up the stack.
Further, there seems to be no (easy) way to use CHECKSUM_COMPLETE
on an aggregated packet at LRO flush time. By the time a packet
is aggregated, the partial checksum from the first segment is
out of date.
I think it would make sense to require that a CHECKSUM_COMPLETE style
driver verify the checksum in its get_frag_header / get_skb_header
callback. This allows the LRO code to unconditionally set
CHECKSUM_UNNECESSARY.
The attached a patch modifies the code to do this.
2) Non-accelerated VLAN tags
Our firmware currently does not do vlan tag insertion
and removal. This causes a problem in __lro_proc_segment()
where the tcp and ip headers are setup to point into the
newly created skb. A frame containing an unstripped vlan
tag will cause the headers to be garbage.
The attached patch modifies __lro_proc_segment() to offset
those pointers by VLAN_HLEN when required.
3) Padded frames.
I may be missing something, but I don't see where you
either strip padding from frames or reject padded frames.
(see the pskb_trim_rcsum() in net/ipv4/ip_input.c:ip_rcv()
I did not add such a feature as I was confused about the intended
use of len/true_size.
Also, trimming is a pain when dealing with pure frags (without a
containing skb). We have code in our out-of-kernel driver to deal
with it which you are welcome to use.
4) LRO_MIN_PG_HLEN (== 80)
This confuses me. Can you please explain what you're trying to do?
Because of this, I kept getting crashes in the skb_pull() done by
eth_type_trans() because I was passing segments which were 60 bytes
and the skb->data_len of the skb constructed by lro_gen_skb() was -20.
I added my own code to bump the length to a magic 80 bytes, and the
panics disappeared. This may cause data corruption because of
#3 above!
5) NAPI/non-NAPI
The LRO code assumes the underlying driver uses NAPI, and calls
netif_receive_skb() rather than netif_rx(). Perhaps there should be a
field in the lro_mgr struct to specify napi / non-napi.
6) The checks for when to stop aggregating and flush in
__lro_proc_{segment|skb} need some improvement.
The skb variant currently uses a pure count (max_aggr). In order to
keep the resulting aggregated frame below 64KB, the underlying driver
computes max_aggr as 0xffff / MTU. This reduces the effectiveness of
LRO on mixed MTU networks. Eg, this causes packets coming from a
source with a 1500b MTU to be aggregated after 7 frames when using a
9000b MTU on the receiver, rather than after 43 frames. As you can
see from the differences in inet_lro's performance in the table
above, this is a real problem.
I believe that a hybrid byte / max_aggr model should be used. The
__lro_proc_segment takes this approach. Note that there is a subtle
bug in that the maximum aggregated bytes should not be be 0xffff.
Rather, one must leave room for the next frame to arrive by setting
the max aggregated bytes to 0xffff - dev->mtu. This is masked
by the driver computing max_aggr as above.
[-- Attachment #2: inet_lro.diff --]
[-- Type: text/plain, Size: 3544 bytes --]
--- linux-2.6.23-rc1.orig/include/linux/inet_lro.h 2007-07-25 12:48:48.000000000 -0400
+++ linux-2.6.23-rc1/include/linux/inet_lro.h 2007-07-24 15:07:28.000000000 -0400
@@ -132,7 +132,7 @@ void lro_vlan_hwaccel_receive_skb(struct
void lro_receive_frags(struct net_lro_mgr *lro_mgr,
struct skb_frag_struct *frags,
- int len, int true_size, void *priv);
+ int len, int true_size, void *priv, __wsum sum);
void lro_vlan_hwaccel_receive_frags(struct net_lro_mgr *lro_mgr,
struct skb_frag_struct *frags,
@@ -140,7 +140,8 @@ void lro_vlan_hwaccel_receive_frags(stru
int true_size,
struct vlan_group *vgrp,
u16 vlan_tag,
- void *priv);
+ void *priv,
+ __wsum sum);
/*
* Forward all aggregated SKBs held by lro_mgr to network stack
--- linux-2.6.23-rc1.orig/net/ipv4/inet_lro.c 2007-07-25 12:48:48.000000000 -0400
+++ linux-2.6.23-rc1/net/ipv4/inet_lro.c 2007-07-25 10:23:31.000000000 -0400
@@ -341,6 +341,10 @@ int __lro_proc_skb(struct net_lro_mgr *l
if (!(flags & LRO_IPV4) || !(flags & LRO_TCP))
goto out;
+ /* checksum has been verified by get_frag_header() */
+ skb->ip_summed = CHECKSUM_UNNECESSARY;
+ skb->csum = 0;
+
lro_desc = lro_get_desc(lro_mgr, lro_mgr->lro_arr, iph, tcph);
if (!lro_desc)
goto out;
@@ -437,7 +441,8 @@ struct sk_buff *__lro_proc_segment(struc
struct skb_frag_struct *frags,
int len, int true_size,
struct vlan_group *vgrp,
- u16 vlan_tag, void *priv)
+ u16 vlan_tag, void *priv,
+ __wsum sum)
{
struct net_lro_desc *lro_desc;
struct iphdr *iph;
@@ -446,6 +451,7 @@ struct sk_buff *__lro_proc_segment(struc
void *mac_hdr;
u64 flags;
int hdr_len = 0;
+ int vlan_hdr_len;
if (!lro_mgr->get_frag_header
|| lro_mgr->get_frag_header(frags, (void *)&mac_hdr, (void *)&iph,
@@ -473,8 +479,17 @@ struct sk_buff *__lro_proc_segment(struc
if (!skb)
goto out;
- iph = (void *)(skb->data);
- tcph = (void *)((u8 *)skb->data + IP_HDR_LEN(iph));
+ /* checksum has been verified by get_frag_header() */
+ skb->ip_summed = CHECKSUM_UNNECESSARY;
+ skb->csum = 0;
+
+ if (skb->protocol == htons(ETH_P_8021Q))
+ vlan_hdr_len = VLAN_HLEN;
+ else
+ vlan_hdr_len = 0;
+
+ iph = (void *)(skb->data + vlan_hdr_len);
+ tcph = (void *)((u8 *)skb->data + vlan_hdr_len + IP_HDR_LEN(iph));
lro_init_desc(lro_desc, skb, iph, tcph, 0, NULL);
return 0;
@@ -501,17 +516,20 @@ out1: /* Original packet has to be post
skb = lro_gen_skb(lro_mgr, frags,
len, true_size, mac_hdr,
max(hdr_len, LRO_MIN_PG_HLEN));
+ skb->ip_summed = lro_mgr->ip_summed;
+ skb->csum = sum;
out:
return skb;
}
void lro_receive_frags(struct net_lro_mgr *lro_mgr,
struct skb_frag_struct *frags,
- int len, int true_size, void *priv)
+ int len, int true_size, void *priv, __wsum sum)
{
struct sk_buff *skb;
- skb = __lro_proc_segment(lro_mgr, frags, len, true_size, NULL, 0, priv);
+ skb = __lro_proc_segment(lro_mgr, frags, len, true_size, NULL, 0,
+ priv, sum);
if(skb)
netif_receive_skb(skb);
}
@@ -524,12 +542,13 @@ void lro_vlan_hwaccel_receive_frags(stru
int true_size,
struct vlan_group *vgrp,
u16 vlan_tag,
- void *priv)
+ void *priv,
+ __wsum sum)
{
struct sk_buff *skb;
skb = __lro_proc_segment(lro_mgr, frags, len, true_size, vgrp,
- vlan_tag, priv);
+ vlan_tag, priv, sum);
if(skb)
vlan_hwaccel_receive_skb(skb, vgrp, vlan_tag);
}
[-- Attachment #3: myri10ge_lro.diff --]
[-- Type: text/plain, Size: 5467 bytes --]
diff -urNp a/drivers/net/myri10ge/myri10ge.c b/drivers/net/myri10ge/myri10ge.c
--- a/drivers/net/myri10ge/myri10ge.c 2007-07-24 15:57:12.000000000 -0400
+++ b/drivers/net/myri10ge/myri10ge.c 2007-07-25 13:10:54.000000000 -0400
@@ -48,6 +48,7 @@
#include <linux/etherdevice.h>
#include <linux/if_ether.h>
#include <linux/if_vlan.h>
+#include <linux/inet_lro.h>
#include <linux/ip.h>
#include <linux/inet.h>
#include <linux/in.h>
@@ -62,6 +63,8 @@
#include <linux/io.h>
#include <linux/log2.h>
#include <net/checksum.h>
+#include <net/ip.h>
+#include <net/tcp.h>
#include <asm/byteorder.h>
#include <asm/io.h>
#include <asm/processor.h>
@@ -89,6 +92,7 @@ MODULE_LICENSE("Dual BSD/GPL");
#define MYRI10GE_EEPROM_STRINGS_SIZE 256
#define MYRI10GE_MAX_SEND_DESC_TSO ((65536 / 2048) * 2)
+#define MYRI10GE_MAX_LRO_DESCRIPTORS 8
#define MYRI10GE_NO_CONFIRM_DATA htonl(0xffffffff)
#define MYRI10GE_NO_RESPONSE_RESULT 0xffffffff
@@ -151,6 +155,8 @@ struct myri10ge_rx_done {
dma_addr_t bus;
int cnt;
int idx;
+ struct net_lro_mgr lro_mgr;
+ struct net_lro_desc lro_desc[MYRI10GE_MAX_LRO_DESCRIPTORS];
};
struct myri10ge_priv {
@@ -276,6 +282,14 @@ static int myri10ge_debug = -1; /* defau
module_param(myri10ge_debug, int, 0);
MODULE_PARM_DESC(myri10ge_debug, "Debug level (0=none,...,16=all)");
+static int myri10ge_lro = 1;
+module_param(myri10ge_lro, int, S_IRUGO);
+MODULE_PARM_DESC(myri10ge_lro, "Enable large receive offload\n");
+
+static int myri10ge_lro_max_pkts = MYRI10GE_LRO_MAX_PKTS;
+module_param(myri10ge_lro_max_pkts, int, S_IRUGO);
+MODULE_PARM_DESC(myri10ge_lro, "Number of LRO packets to be aggregated\n");
+
static int myri10ge_fill_thresh = 256;
module_param(myri10ge_fill_thresh, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(myri10ge_fill_thresh, "Number of empty rx slots allowed\n");
@@ -1001,6 +1015,8 @@ myri10ge_rx_done(struct myri10ge_priv *m
struct net_device *dev = mgp->dev;
u8 *va;
+ if (len < 80)
+ len = 80; /* XXX LRO hack XXX */
len += MXGEFW_PAD;
idx = rx->cnt & rx->mask;
va = page_address(rx->info[idx].page) + rx->info[idx].page_offset;
@@ -1019,6 +1035,15 @@ myri10ge_rx_done(struct myri10ge_priv *m
remainder -= MYRI10GE_ALLOC_SIZE;
}
+ if (mgp->csum_flag && myri10ge_lro) {
+ rx_frags[0].page_offset += MXGEFW_PAD;
+ rx_frags[0].size -= MXGEFW_PAD;
+ len -= MXGEFW_PAD;
+ lro_receive_frags(&mgp->rx_done.lro_mgr, rx_frags,
+ len, len, (void *)(unsigned long)csum, csum);
+ return 1;
+ }
+
hlen = MYRI10GE_HLEN > len ? len : MYRI10GE_HLEN;
/* allocate an skb to attach the page(s) to. */
@@ -1137,6 +1162,9 @@ static inline void myri10ge_clean_rx_don
mgp->stats.rx_packets += rx_packets;
mgp->stats.rx_bytes += rx_bytes;
+ if (myri10ge_lro)
+ lro_flush_all(&rx_done->lro_mgr);
+
/* restock receive rings if needed */
if (mgp->rx_small.fill_cnt - mgp->rx_small.cnt < myri10ge_fill_thresh)
myri10ge_alloc_rx_pages(mgp, &mgp->rx_small,
@@ -1717,10 +1745,69 @@ static void myri10ge_free_irq(struct myr
pci_disable_msi(pdev);
}
+static int
+myri10ge_get_frag_header(struct skb_frag_struct *frag, void **mac_hdr,
+ void **ip_hdr, void **tcpudp_hdr,
+ u64 * hdr_flags, void *priv)
+{
+ struct ethhdr *eh;
+ struct vlan_ethhdr *veh;
+ struct iphdr *iph;
+ u8 *va = page_address(frag->page) + frag->page_offset;
+ unsigned long ll_hlen;
+ __wsum csum = (__wsum) (unsigned long)priv;
+
+ /* find the mac header, aborting if not IPv4 */
+
+ eh = (struct ethhdr *)va;
+ *mac_hdr = eh;
+ ll_hlen = ETH_HLEN;
+ if (eh->h_proto != htons(ETH_P_IP)) {
+ if (eh->h_proto == htons(ETH_P_8021Q)) {
+ veh = (struct vlan_ethhdr *)va;
+ if (veh->h_vlan_encapsulated_proto != htons(ETH_P_IP))
+ return -1;
+
+ ll_hlen += VLAN_HLEN;
+
+ /*
+ * HW checksum starts ETH_HLEN bytes into
+ * frame, so we must subtract off the VLAN
+ * header's checksum before csum can be used
+ */
+ csum = csum_sub(csum, csum_partial(va + ETH_HLEN,
+ VLAN_HLEN, 0));
+ } else {
+ return -1;
+ }
+ }
+ *hdr_flags = LRO_IPV4;
+
+ iph = (struct iphdr *)(va + ll_hlen);
+ *ip_hdr = iph;
+ if (iph->protocol != IPPROTO_TCP)
+ return -1;
+ *hdr_flags |= LRO_TCP;
+ *tcpudp_hdr = (u8 *) (*ip_hdr) + (iph->ihl << 2);
+
+ /* verify the IP checksum */
+ if (unlikely(ip_fast_csum((u8 *) iph, iph->ihl)))
+ return -1;
+
+ /* verify the checksum */
+ if (unlikely(csum_tcpudp_magic(iph->saddr, iph->daddr,
+ ntohs(iph->tot_len) - (iph->ihl << 2),
+ IPPROTO_TCP, csum)))
+ return -1;
+
+ return 0;
+}
+
static int myri10ge_open(struct net_device *dev)
{
struct myri10ge_priv *mgp;
struct myri10ge_cmd cmd;
+ struct net_lro_mgr *lro_mgr;
int status, big_pow2;
mgp = netdev_priv(dev);
@@ -1852,6 +1939,18 @@ static int myri10ge_open(struct net_devi
mgp->link_state = htonl(~0U);
mgp->rdma_tags_available = 15;
+ lro_mgr = &mgp->rx_done.lro_mgr;
+ lro_mgr->dev = dev;
+ lro_mgr->ip_summed = CHECKSUM_COMPLETE;
+ lro_mgr->max_desc = MYRI10GE_MAX_LRO_DESCRIPTORS;
+ lro_mgr->lro_arr = mgp->rx_done.lro_desc;
+ lro_mgr->get_frag_header = myri10ge_get_frag_header;
+ lro_mgr->max_aggr = 0xffff / dev->mtu;
+ if (lro_mgr->max_aggr > myri10ge_lro_max_pkts)
+ lro_mgr->max_aggr = myri10ge_lro_max_pkts;
+ if (lro_mgr->max_aggr > MAX_SKB_FRAGS)
+ lro_mgr->max_aggr = MAX_SKB_FRAGS;
+
netif_poll_enable(mgp->dev); /* must happen prior to any irq */
status = myri10ge_send_cmd(mgp, MXGEFW_CMD_ETHERNET_UP, &cmd, 0);
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Sergei Shtylyov @ 2007-07-25 17:54 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <46A78322.3080607@ru.mvista.com>
Hello, I wrote:
>>diff --git a/arch/powerpc/boot/dts/mpc8349emitx.dts b/arch/powerpc/boot/dts/mpc8349emitx.dts
>>index db0d003..f8f0e8a 100644
>>--- a/arch/powerpc/boot/dts/mpc8349emitx.dts
>>+++ b/arch/powerpc/boot/dts/mpc8349emitx.dts
>>@@ -37,6 +37,15 @@
>> reg = <00000000 10000000>;
>> };
>>
>>+ ide@f0000000 {
>>+ compatible = "mmio-ide";
>>+ device_type = "ide";
> Why not "ata"?
Also, what mmio-ide in the compat properly means in the context of
ide_platform which is able to handle both port and memory mapped IDE. I think
we must get rid with this crap, and since this IDE register mapping is pretty
much board specific, call it something like "mpc8349emitx-ide" instead.
MBR, Sergei
^ permalink raw reply
* [PATCH 2/2] [POWERPC] Remove dummy network phy from MPC8313E-RDB
From: Vitaly Bordug @ 2007-07-25 17:43 UTC (permalink / raw)
To: Jeff Garzik; +Cc: linuxppc-dev, linux-kernel, netdev
In-Reply-To: <20070725174312.5818.61155.stgit@localhost.localdomain>
Cleaned up inexistent network phy from the target dts, added
necessary property to gianfar node there.
Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
---
arch/powerpc/boot/dts/mpc8313erdb.dts | 8 +-------
1 files changed, 1 insertions(+), 7 deletions(-)
diff --git a/arch/powerpc/boot/dts/mpc8313erdb.dts b/arch/powerpc/boot/dts/mpc8313erdb.dts
index a1533cc..b602a8b 100644
--- a/arch/powerpc/boot/dts/mpc8313erdb.dts
+++ b/arch/powerpc/boot/dts/mpc8313erdb.dts
@@ -98,12 +98,6 @@
reg = <24520 20>;
#address-cells = <1>;
#size-cells = <0>;
- phy1: ethernet-phy@1 {
- interrupt-parent = < &ipic >;
- interrupts = <13 8>;
- reg = <1>;
- device_type = "ethernet-phy";
- };
phy4: ethernet-phy@4 {
interrupt-parent = < &ipic >;
interrupts = <14 8>;
@@ -120,7 +114,7 @@
local-mac-address = [ 00 00 00 00 00 00 ];
interrupts = <25 8 24 8 23 8>;
interrupt-parent = < &ipic >;
- phy-handle = < &phy1 >;
+ fixed_speed = <1 1000>;
};
ethernet@25000 {
^ permalink raw reply related
* [PATCH 1/2] [POWERPC] Add support of platforms without PHY to gianfar driver
From: Vitaly Bordug @ 2007-07-25 17:43 UTC (permalink / raw)
To: Jeff Garzik; +Cc: linuxppc-dev, linux-kernel, netdev
Gianfar driver is now able to work without real phy subnode,
that is necessary to cope with fixed-link situation, when
SoC is connected to the Ethernet inteface or embedded switch
without any PHY. In this case, fixed-speed property will
describe such a situation for gianfar driver.
The property is in form <duplexity speed>
Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
---
arch/powerpc/sysdev/fsl_soc.c | 39 +++++++++++++++++++++++----------------
drivers/net/gianfar.c | 17 ++++++++++++++---
2 files changed, 37 insertions(+), 19 deletions(-)
diff --git a/arch/powerpc/sysdev/fsl_soc.c b/arch/powerpc/sysdev/fsl_soc.c
index cad1757..6864534 100644
--- a/arch/powerpc/sysdev/fsl_soc.c
+++ b/arch/powerpc/sysdev/fsl_soc.c
@@ -255,29 +255,36 @@ static int __init gfar_of_init(void)
FSL_GIANFAR_DEV_HAS_EXTENDED_HASH;
ph = of_get_property(np, "phy-handle", NULL);
- phy = of_find_node_by_phandle(*ph);
+ if (ph == NULL) {
+ unsigned int *bus_id;
- if (phy == NULL) {
- ret = -ENODEV;
- goto unreg;
- }
+ bus_id = of_get_property(np, "fixed_speed",NULL);
+ gfar_data.bus_id = (bus_id[0]<<16) | bus_id[1];
+ } else {
+ phy = of_find_node_by_phandle(*ph);
- mdio = of_get_parent(phy);
+ if (phy == NULL) {
+ ret = -ENODEV;
+ goto unreg;
+ }
+
+ mdio = of_get_parent(phy);
+
+ id = of_get_property(phy, "reg", NULL);
+ ret = of_address_to_resource(mdio, 0, &res);
+ if (ret) {
+ of_node_put(phy);
+ of_node_put(mdio);
+ goto unreg;
+ }
+
+ gfar_data.phy_id = *id;
+ gfar_data.bus_id = res.start;
- id = of_get_property(phy, "reg", NULL);
- ret = of_address_to_resource(mdio, 0, &res);
- if (ret) {
of_node_put(phy);
of_node_put(mdio);
- goto unreg;
}
- gfar_data.phy_id = *id;
- gfar_data.bus_id = res.start;
-
- of_node_put(phy);
- of_node_put(mdio);
-
ret =
platform_device_add_data(gfar_dev, &gfar_data,
sizeof(struct
diff --git a/drivers/net/gianfar.c b/drivers/net/gianfar.c
index 1b854bf..cf08ced 100644
--- a/drivers/net/gianfar.c
+++ b/drivers/net/gianfar.c
@@ -93,6 +93,7 @@
#include <linux/crc32.h>
#include <linux/mii.h>
#include <linux/phy.h>
+#include <linux/phy_fixed.h>
#include "gianfar.h"
#include "gianfar_mii.h"
@@ -445,11 +446,21 @@ static int init_phy(struct net_device *dev)
priv->oldspeed = 0;
priv->oldduplex = -1;
- snprintf(phy_id, BUS_ID_SIZE, PHY_ID_FMT, priv->einfo->bus_id, priv->einfo->phy_id);
-
interface = gfar_get_interface(dev);
- phydev = phy_connect(dev, phy_id, &adjust_link, 0, interface);
+ if (priv->einfo->phy_id) {
+ snprintf(phy_id, BUS_ID_SIZE, PHY_ID_FMT, priv->einfo->bus_id, priv->einfo->phy_id);
+ phydev = phy_connect(dev, phy_id, &adjust_link, 0, interface);
+ } else {
+ struct fixed_info *phyinfo;
+ int phy_addr = (priv->einfo->bus_id >> 16);
+
+ phyinfo = fixed_mdio_get_phydev(phy_addr-1);
+ phydev = phyinfo->phydev;
+ snprintf(phydev->dev.bus_id, BUS_ID_SIZE, PHY_ID_FMT,
+ (priv->einfo->bus_id & 0xffff) , phy_addr);
+ memset(phyinfo->regs,0xff,sizeof(phyinfo->regs[0])*phyinfo->regs_num);
+ }
if (IS_ERR(phydev)) {
printk(KERN_ERR "%s: Could not attach to PHY\n", dev->name);
^ permalink raw reply related
* Re: [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Alan Cox @ 2007-07-25 17:43 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165318.5331.23795.stgit@localhost.localdomain>
> pata_platform and ide_platform are carrying same driver names,
> to easily switch between these drivers, without need to touch
> platform code.
>
> Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
> Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
Acked-by: Alan Cox <alan@redhat.com>
^ permalink raw reply
* [PATCH] POWERPC: Fix definition of global-utilites structure for 86xx
From: Timur Tabi @ 2007-07-25 17:30 UTC (permalink / raw)
To: linuxppc-dev; +Cc: Timur Tabi
The current definition of struct ccsr_guts in immap_86xx.h was for 85xx.
This patch fixes that and replaces the vague integer types with sized types
of the correct endianness. The unused struct ccsr_pci is also deleted.
Signed-off-by: Timur Tabi <timur@freescale.com>
---
include/asm-powerpc/immap_86xx.h | 151 ++++++++++++--------------------------
1 files changed, 46 insertions(+), 105 deletions(-)
diff --git a/include/asm-powerpc/immap_86xx.h b/include/asm-powerpc/immap_86xx.h
index 59b9e07..c83d7ad 100644
--- a/include/asm-powerpc/immap_86xx.h
+++ b/include/asm-powerpc/immap_86xx.h
@@ -1,124 +1,65 @@
-/*
+/**
* MPC86xx Internal Memory Map
*
- * Author: Jeff Brown
+ * Authors: Jeff Brown
+ * Timur Tabi <timur@freescale.com>
*
- * Copyright 2004 Freescale Semiconductor, Inc
+ * Copyright 2004,2007 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 as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
+ * This header file defines structures for various 86xx SOC devices that are
+ * used by multiple source files.
*/
#ifndef __ASM_POWERPC_IMMAP_86XX_H__
#define __ASM_POWERPC_IMMAP_86XX_H__
#ifdef __KERNEL__
-/* Eventually this should define all the IO block registers in 86xx */
-
-/* PCI Registers */
-typedef struct ccsr_pci {
- uint cfg_addr; /* 0x.000 - PCI Configuration Address Register */
- uint cfg_data; /* 0x.004 - PCI Configuration Data Register */
- uint int_ack; /* 0x.008 - PCI Interrupt Acknowledge Register */
- char res1[3060];
- uint potar0; /* 0x.c00 - PCI Outbound Transaction Address Register 0 */
- uint potear0; /* 0x.c04 - PCI Outbound Translation Extended Address Register 0 */
- uint powbar0; /* 0x.c08 - PCI Outbound Window Base Address Register 0 */
- char res2[4];
- uint powar0; /* 0x.c10 - PCI Outbound Window Attributes Register 0 */
- char res3[12];
- uint potar1; /* 0x.c20 - PCI Outbound Transaction Address Register 1 */
- uint potear1; /* 0x.c24 - PCI Outbound Translation Extended Address Register 1 */
- uint powbar1; /* 0x.c28 - PCI Outbound Window Base Address Register 1 */
- char res4[4];
- uint powar1; /* 0x.c30 - PCI Outbound Window Attributes Register 1 */
- char res5[12];
- uint potar2; /* 0x.c40 - PCI Outbound Transaction Address Register 2 */
- uint potear2; /* 0x.c44 - PCI Outbound Translation Extended Address Register 2 */
- uint powbar2; /* 0x.c48 - PCI Outbound Window Base Address Register 2 */
- char res6[4];
- uint powar2; /* 0x.c50 - PCI Outbound Window Attributes Register 2 */
- char res7[12];
- uint potar3; /* 0x.c60 - PCI Outbound Transaction Address Register 3 */
- uint potear3; /* 0x.c64 - PCI Outbound Translation Extended Address Register 3 */
- uint powbar3; /* 0x.c68 - PCI Outbound Window Base Address Register 3 */
- char res8[4];
- uint powar3; /* 0x.c70 - PCI Outbound Window Attributes Register 3 */
- char res9[12];
- uint potar4; /* 0x.c80 - PCI Outbound Transaction Address Register 4 */
- uint potear4; /* 0x.c84 - PCI Outbound Translation Extended Address Register 4 */
- uint powbar4; /* 0x.c88 - PCI Outbound Window Base Address Register 4 */
- char res10[4];
- uint powar4; /* 0x.c90 - PCI Outbound Window Attributes Register 4 */
- char res11[268];
- uint pitar3; /* 0x.da0 - PCI Inbound Translation Address Register 3 */
- char res12[4];
- uint piwbar3; /* 0x.da8 - PCI Inbound Window Base Address Register 3 */
- uint piwbear3; /* 0x.dac - PCI Inbound Window Base Extended Address Register 3 */
- uint piwar3; /* 0x.db0 - PCI Inbound Window Attributes Register 3 */
- char res13[12];
- uint pitar2; /* 0x.dc0 - PCI Inbound Translation Address Register 2 */
- char res14[4];
- uint piwbar2; /* 0x.dc8 - PCI Inbound Window Base Address Register 2 */
- uint piwbear2; /* 0x.dcc - PCI Inbound Window Base Extended Address Register 2 */
- uint piwar2; /* 0x.dd0 - PCI Inbound Window Attributes Register 2 */
- char res15[12];
- uint pitar1; /* 0x.de0 - PCI Inbound Translation Address Register 1 */
- char res16[4];
- uint piwbar1; /* 0x.de8 - PCI Inbound Window Base Address Register 1 */
- char res17[4];
- uint piwar1; /* 0x.df0 - PCI Inbound Window Attributes Register 1 */
- char res18[12];
- uint err_dr; /* 0x.e00 - PCI Error Detect Register */
- uint err_cap_dr; /* 0x.e04 - PCI Error Capture Disable Register */
- uint err_en; /* 0x.e08 - PCI Error Enable Register */
- uint err_attrib; /* 0x.e0c - PCI Error Attributes Capture Register */
- uint err_addr; /* 0x.e10 - PCI Error Address Capture Register */
- uint err_ext_addr; /* 0x.e14 - PCI Error Extended Address Capture Register */
- uint err_dl; /* 0x.e18 - PCI Error Data Low Capture Register */
- uint err_dh; /* 0x.e1c - PCI Error Data High Capture Register */
- uint gas_timr; /* 0x.e20 - PCI Gasket Timer Register */
- uint pci_timr; /* 0x.e24 - PCI Timer Register */
- char res19[472];
-} ccsr_pci_t;
-
/* Global Utility Registers */
-typedef struct ccsr_guts {
- uint porpllsr; /* 0x.0000 - POR PLL Ratio Status Register */
- uint porbmsr; /* 0x.0004 - POR Boot Mode Status Register */
- uint porimpscr; /* 0x.0008 - POR I/O Impedance Status and Control Register */
- uint pordevsr; /* 0x.000c - POR I/O Device Status Register */
- uint pordbgmsr; /* 0x.0010 - POR Debug Mode Status Register */
- char res1[12];
- uint gpporcr; /* 0x.0020 - General-Purpose POR Configuration Register */
- char res2[12];
- uint gpiocr; /* 0x.0030 - GPIO Control Register */
- char res3[12];
- uint gpoutdr; /* 0x.0040 - General-Purpose Output Data Register */
- char res4[12];
- uint gpindr; /* 0x.0050 - General-Purpose Input Data Register */
- char res5[12];
- uint pmuxcr; /* 0x.0060 - Alternate Function Signal Multiplex Control */
- char res6[12];
- uint devdisr; /* 0x.0070 - Device Disable Control */
- char res7[12];
- uint powmgtcsr; /* 0x.0080 - Power Management Status and Control Register */
- char res8[12];
- uint mcpsumr; /* 0x.0090 - Machine Check Summary Register */
- char res9[12];
- uint pvr; /* 0x.00a0 - Processor Version Register */
- uint svr; /* 0x.00a4 - System Version Register */
- char res10[3416];
- uint clkocr; /* 0x.0e00 - Clock Out Select Register */
- char res11[12];
- uint ddrdllcr; /* 0x.0e10 - DDR DLL Control Register */
- char res12[12];
- uint lbcdllcr; /* 0x.0e20 - LBC DLL Control Register */
- char res13[61916];
-} ccsr_guts_t;
+struct ccsr_guts {
+ __be32 porpllsr; /* 0x.0000 - POR PLL Ratio Status Register */
+ __be32 porbmsr; /* 0x.0004 - POR Boot Mode Status Register */
+ __be32 porimpscr; /* 0x.0008 - POR I/O Impedance Status and Control Register */
+ __be32 pordevsr; /* 0x.000c - POR I/O Device Status Register */
+ __be32 pordbgmsr; /* 0x.0010 - POR Debug Mode Status Register */
+ u8 res1[0x20 - 0x14];
+ __be32 porcir; /* 0x.0020 - POR Configuration Information Register */
+ u8 res2[0x30 - 0x24];
+ __be32 gpiocr; /* 0x.0030 - GPIO Control Register */
+ u8 res3[0x40 - 0x34];
+ __be32 gpoutdr; /* 0x.0040 - General-Purpose Output Data Register */
+ u8 res4[0x50 - 0x44];
+ __be32 gpindr; /* 0x.0050 - General-Purpose Input Data Register */
+ u8 res5[0x60 - 0x54];
+ __be32 pmuxcr; /* 0x.0060 - Alternate Function Signal Multiplex Control */
+ u8 res6[0x70 - 0x64];
+ __be32 devdisr; /* 0x.0070 - Device Disable Control */
+ u8 res7[0x80 - 0x74];
+ __be32 powmgtcsr; /* 0x.0080 - Power Management Status and Control Register */
+ u8 res8[0x90 - 0x84];
+ __be32 mcpsumr; /* 0x.0090 - Machine Check Summary Register */
+ __be32 rstrscr; /* 0x.0094 - Reset Request Status and Control Register */
+ u8 res9[0xA0 - 0x98];
+ __be32 pvr; /* 0x.00a0 - Processor Version Register */
+ __be32 svr; /* 0x.00a4 - System Version Register */
+ u8 res10[0xB0 - 0xA8];
+ __be32 rstcr; /* 0x.00b0 - Reset Control Register */
+ u8 res11[0xB20 - 0xB4];
+ __be32 ddr1clkdr; /* 0x.0b20 - DDRC1 Clock Disable Register */
+ __be32 ddr2clkdr; /* 0x.0b24 - DDRC2 Clock Disable Register */
+ u8 res12[0xE00 - 0xB28];
+ __be32 clkocr; /* 0x.0e00 - Clock Out Select Register */
+ u8 res13[0xF04 - 0xE04];
+ __be32 srds1cr0; /* 0x.0f04 - SerDes1 Control Register 0 */
+ __be32 srds1cr1; /* 0x.0f08 - SerDes1 Control Register 0 */
+ u8 res14[0xF40 - 0xF0C];
+ __be32 srds2cr0; /* 0x.0f40 - SerDes1 Control Register 0 */
+ __be32 srds2cr1; /* 0x.0f44 - SerDes1 Control Register 0 */
+};
#endif /* __ASM_POWERPC_IMMAP_86XX_H__ */
#endif /* __KERNEL__ */
--
1.5.2.4
^ permalink raw reply related
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Scott Wood @ 2007-07-25 17:29 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165326.5331.19920.stgit@localhost.localdomain>
Vitaly Bordug wrote:
> diff --git a/arch/powerpc/boot/dts/mpc8349emitx.dts b/arch/powerpc/boot/dts/mpc8349emitx.dts
> index db0d003..f8f0e8a 100644
> --- a/arch/powerpc/boot/dts/mpc8349emitx.dts
> +++ b/arch/powerpc/boot/dts/mpc8349emitx.dts
> @@ -37,6 +37,15 @@
> reg = <00000000 10000000>;
> };
>
> + ide@f0000000 {
> + compatible = "mmio-ide";
> + device_type = "ide";
> + reg = <f0000000 10 f000020c 4>;
> + ioport_shift = <1>;
> + interrupts = <17 8>;
> + interrupt-parent = < &ipic >;
> + };
> +
Is this binding documented anywhere? If it's a new binding, could we
use reg-shift instead of ioport_shift? This is what ns16550 uses, and
in general dashes are preferable to underscores in device trees
(device_type is an ugly, historical exception).
> diff --git a/arch/powerpc/platforms/83xx/mpc834x_itx.c b/arch/powerpc/platforms/83xx/mpc834x_itx.c
> index 40a0194..d63a104 100644
> --- a/arch/powerpc/platforms/83xx/mpc834x_itx.c
> +++ b/arch/powerpc/platforms/83xx/mpc834x_itx.c
> @@ -23,6 +23,7 @@
> #include <linux/delay.h>
> #include <linux/seq_file.h>
> #include <linux/root_dev.h>
> +#include <linux/pata_platform.h>
>
> #include <asm/system.h>
> #include <asm/atomic.h>
> @@ -43,6 +44,75 @@ unsigned long isa_io_base = 0;
> unsigned long isa_mem_base = 0;
> #endif
>
> +static int __init mmio_ide_of_init(void)
> +{
> + struct device_node *np;
> + unsigned int i;
> +
> + for (np = NULL, i = 0;
> + (np = of_find_compatible_node(np, "ide", "mmio-ide")) != NULL;
> + i++) {
> + int ret = 0;
> + struct resource res[3];
> + struct platform_device *pdev = NULL;
> + static struct pata_platform_info pdata;
We really don't want code like this for every board with an MMIO IDE
controller. At the very least, make it a generic function in sysdev;
better would be to make the driver also support of_platform devices.
-Scott
^ permalink raw reply
* Re: [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Sergei Shtylyov @ 2007-07-25 17:06 UTC (permalink / raw)
To: Vitaly Bordug; +Cc: linux-ide, linux-kernel, linuxppc-dev
In-Reply-To: <20070725165326.5331.19920.stgit@localhost.localdomain>
Hello.
Vitaly Bordug wrote:
> This updates relevant platform code (freescale mpc8349itx target)
> to make the CompactFlash work in TrueIDE mode.
Erm, I'm not sure it's worth submitting the platform device driver for
PowerPC at this point, but well...
> Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
> Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
> arch/powerpc/boot/dts/mpc8349emitx.dts | 9 ++++
> arch/powerpc/platforms/83xx/mpc834x_itx.c | 70 +++++++++++++++++++++++++++++
> 2 files changed, 79 insertions(+), 0 deletions(-)
> diff --git a/arch/powerpc/boot/dts/mpc8349emitx.dts b/arch/powerpc/boot/dts/mpc8349emitx.dts
> index db0d003..f8f0e8a 100644
> --- a/arch/powerpc/boot/dts/mpc8349emitx.dts
> +++ b/arch/powerpc/boot/dts/mpc8349emitx.dts
> @@ -37,6 +37,15 @@
> reg = <00000000 10000000>;
> };
>
> + ide@f0000000 {
> + compatible = "mmio-ide";
> + device_type = "ide";
Why not "ata"?
> + reg = <f0000000 10 f000020c 4>;
> + ioport_shift = <1>;
Please use hyphen, not underscore in the property names ("device_type"
seems an only exception from this rule).
And since using shift instead of size buys you nothing is this case, I'd
prefer this property to be called reg-size or reg-stride.
[...]
> diff --git a/arch/powerpc/platforms/83xx/mpc834x_itx.c b/arch/powerpc/platforms/83xx/mpc834x_itx.c
> index 40a0194..d63a104 100644
> --- a/arch/powerpc/platforms/83xx/mpc834x_itx.c
> +++ b/arch/powerpc/platforms/83xx/mpc834x_itx.c
[...]
> @@ -43,6 +44,75 @@ unsigned long isa_io_base = 0;
> unsigned long isa_mem_base = 0;
> #endif
>
> +static int __init mmio_ide_of_init(void)
> +{
> + struct device_node *np;
> + unsigned int i;
> +
> + for (np = NULL, i = 0;
> + (np = of_find_compatible_node(np, "ide", "mmio-ide")) != NULL;
> + i++) {
> + int ret = 0;
Unneeded initialization.
> + struct resource res[3];
> + struct platform_device *pdev = NULL;
Another one.
> + static struct pata_platform_info pdata;
> +
> + memset(res, 0, sizeof(res));
> +
> + ret = of_address_to_resource(np, 0, &res[0]);
> + if (ret) {
> + printk(KERN_ERR "mmio-ide.%d: unable to get "
> + "resource from OF\n", i);
> + goto err0;
> + }
> +
> + ret = of_address_to_resource(np, 1, &res[1]);
> + if (ret) {
> + printk(KERN_ERR "mmio-ide.%d: unable to get "
> + "resource from OF\n", i);
> + goto err0;
Erm, these printk's are repetitive, isn't it better to put them under err0
label?
> + }
> +
> + res[2].start = res[2].end = irq_of_parse_and_map(np, 0);
> + if (res[2].start == NO_IRQ) {
> + printk(KERN_ERR "mmio-ide.%d: no IRQ\n", i);
> + goto err0;
> + }
> + res[2].name = "pata_platform";
> + res[2].flags = IORESOURCE_IRQ;
> +
> + pdata.ioport_shift = *((u32 *)of_get_property(np,
> + "ioport_shift", NULL));
> +
> + pdev = platform_device_alloc("pata_platform", i);
> + if (!pdev)
> + goto err1;
Hm, not err0?
> +
> + ret = platform_device_add_data(pdev, &pdata, sizeof(pdata));
> + if (ret)
> + goto err1;
> +
> + ret = platform_device_add_resources(pdev, res, ARRAY_SIZE(res));
> + if (ret)
> + goto err1;
> +
> + ret = platform_device_register(pdev);
> + if (ret)
> + goto err1;
> +
> + continue;
> +err1:
> + printk(KERN_ERR "mmio-ide.%d: registration failed\n", i);
> + platform_device_del(pdev); /* it will free everything */
> +err0:
> + /* Even if some device failed, try others */
> + continue;
> + }
> +
> + return 0;
> +}
> +device_initcall(mmio_ide_of_init);
> +
> /* ************************************************************************
> *
> * Setup the architecture
MBR, Sergei
^ permalink raw reply
* Re: [PATCH] [POWERPC] iSeries: fix section mismatch warnings
From: Will Schmidt @ 2007-07-25 16:55 UTC (permalink / raw)
To: Stephen Rothwell; +Cc: ppc-dev, paulus
In-Reply-To: <20070725092735.0a5a1c52.sfr@canb.auug.org.au>
> diff --git a/arch/powerpc/kernel/head_64.S b/arch/powerpc/kernel/head_64.S
> index 8cdd48e..1448af9 100644
> --- a/arch/powerpc/kernel/head_64.S
> +++ b/arch/powerpc/kernel/head_64.S
> @@ -809,8 +809,9 @@ system_reset_iSeries:
> mtmsrd r24 /* RI on */
> lhz r24,PACAPACAINDEX(r13) /* Get processor # */
> cmpwi 0,r24,0 /* Are we processor 0? */
> - beq .__start_initialization_iSeries /* Start up the first processor */
> - mfspr r4,SPRN_CTRLF
> + bne 1f
> + b .__start_initialization_iSeries /* Start up the first processor */
> +1: mfspr r4,SPRN_CTRLF
> li r5,CTRL_RUNLATCH /* Turn off the run light */
> andc r4,r4,r5
> mtspr SPRN_CTRLT,r4
This part isnt clicking for me..
How does changing a "beq" to a "bne" over a "b" fit into changing
__start_initialization_iSeries static?
-Will
^ permalink raw reply
* [PATCH 2/2] [POWERPC] MPC8349E-mITX: use platform IDE driver for CF interface
From: Vitaly Bordug @ 2007-07-25 16:53 UTC (permalink / raw)
To: linux-ide; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <20070725165318.5331.23795.stgit@localhost.localdomain>
This updates relevant platform code (freescale mpc8349itx target)
to make the CompactFlash work in TrueIDE mode.
Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
---
arch/powerpc/boot/dts/mpc8349emitx.dts | 9 ++++
arch/powerpc/platforms/83xx/mpc834x_itx.c | 70 +++++++++++++++++++++++++++++
2 files changed, 79 insertions(+), 0 deletions(-)
diff --git a/arch/powerpc/boot/dts/mpc8349emitx.dts b/arch/powerpc/boot/dts/mpc8349emitx.dts
index db0d003..f8f0e8a 100644
--- a/arch/powerpc/boot/dts/mpc8349emitx.dts
+++ b/arch/powerpc/boot/dts/mpc8349emitx.dts
@@ -37,6 +37,15 @@
reg = <00000000 10000000>;
};
+ ide@f0000000 {
+ compatible = "mmio-ide";
+ device_type = "ide";
+ reg = <f0000000 10 f000020c 4>;
+ ioport_shift = <1>;
+ interrupts = <17 8>;
+ interrupt-parent = < &ipic >;
+ };
+
soc8349@e0000000 {
#address-cells = <1>;
#size-cells = <1>;
diff --git a/arch/powerpc/platforms/83xx/mpc834x_itx.c b/arch/powerpc/platforms/83xx/mpc834x_itx.c
index 40a0194..d63a104 100644
--- a/arch/powerpc/platforms/83xx/mpc834x_itx.c
+++ b/arch/powerpc/platforms/83xx/mpc834x_itx.c
@@ -23,6 +23,7 @@
#include <linux/delay.h>
#include <linux/seq_file.h>
#include <linux/root_dev.h>
+#include <linux/pata_platform.h>
#include <asm/system.h>
#include <asm/atomic.h>
@@ -43,6 +44,75 @@ unsigned long isa_io_base = 0;
unsigned long isa_mem_base = 0;
#endif
+static int __init mmio_ide_of_init(void)
+{
+ struct device_node *np;
+ unsigned int i;
+
+ for (np = NULL, i = 0;
+ (np = of_find_compatible_node(np, "ide", "mmio-ide")) != NULL;
+ i++) {
+ int ret = 0;
+ struct resource res[3];
+ struct platform_device *pdev = NULL;
+ static struct pata_platform_info pdata;
+
+ memset(res, 0, sizeof(res));
+
+ ret = of_address_to_resource(np, 0, &res[0]);
+ if (ret) {
+ printk(KERN_ERR "mmio-ide.%d: unable to get "
+ "resource from OF\n", i);
+ goto err0;
+ }
+
+ ret = of_address_to_resource(np, 1, &res[1]);
+ if (ret) {
+ printk(KERN_ERR "mmio-ide.%d: unable to get "
+ "resource from OF\n", i);
+ goto err0;
+ }
+
+ res[2].start = res[2].end = irq_of_parse_and_map(np, 0);
+ if (res[2].start == NO_IRQ) {
+ printk(KERN_ERR "mmio-ide.%d: no IRQ\n", i);
+ goto err0;
+ }
+ res[2].name = "pata_platform";
+ res[2].flags = IORESOURCE_IRQ;
+
+ pdata.ioport_shift = *((u32 *)of_get_property(np,
+ "ioport_shift", NULL));
+
+ pdev = platform_device_alloc("pata_platform", i);
+ if (!pdev)
+ goto err1;
+
+ ret = platform_device_add_data(pdev, &pdata, sizeof(pdata));
+ if (ret)
+ goto err1;
+
+ ret = platform_device_add_resources(pdev, res, ARRAY_SIZE(res));
+ if (ret)
+ goto err1;
+
+ ret = platform_device_register(pdev);
+ if (ret)
+ goto err1;
+
+ continue;
+err1:
+ printk(KERN_ERR "mmio-ide.%d: registration failed\n", i);
+ platform_device_del(pdev); /* it will free everything */
+err0:
+ /* Even if some device failed, try others */
+ continue;
+ }
+
+ return 0;
+}
+device_initcall(mmio_ide_of_init);
+
/* ************************************************************************
*
* Setup the architecture
^ permalink raw reply related
* [PATCH 1/2] [IDE] Platform IDE driver (was: MMIO IDE driver)
From: Vitaly Bordug @ 2007-07-25 16:53 UTC (permalink / raw)
To: linux-ide; +Cc: linuxppc-dev, linux-kernel
This is now very similar to pata_platform.c, they both use
same platform data structure and same resources.
To achieve that, byte_lanes_swapping platform data variable
and platform specified iops removed from that driver. It's fine,
since those were never used anyway.
pata_platform and ide_platform are carrying same driver names,
to easily switch between these drivers, without need to touch
platform code.
Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
Signed-off-by: Vitaly Bordug <vitb@kernel.crashing.org>
---
drivers/ide/Kconfig | 8 ++
drivers/ide/legacy/Makefile | 2
drivers/ide/legacy/ide_platform.c | 181 +++++++++++++++++++++++++++++++++++++
3 files changed, 191 insertions(+), 0 deletions(-)
diff --git a/drivers/ide/Kconfig b/drivers/ide/Kconfig
index b1a9b81..b5a44da 100644
--- a/drivers/ide/Kconfig
+++ b/drivers/ide/Kconfig
@@ -308,6 +308,14 @@ config IDE_GENERIC
help
If unsure, say Y.
+config BLK_DEV_PLATFORM
+ tristate "Platform driver for IDE interfaces"
+ help
+ This is the platform IDE driver, used mostly for Memory Mapped
+ IDE devices, like Compact Flashes running in True IDE mode.
+
+ If unsure, say N.
+
config BLK_DEV_CMD640
bool "CMD640 chipset bugfix/support"
depends on X86
diff --git a/drivers/ide/legacy/Makefile b/drivers/ide/legacy/Makefile
index c797106..4098223 100644
--- a/drivers/ide/legacy/Makefile
+++ b/drivers/ide/legacy/Makefile
@@ -7,6 +7,8 @@ obj-$(CONFIG_BLK_DEV_UMC8672) += umc8672.o
obj-$(CONFIG_BLK_DEV_IDECS) += ide-cs.o
+obj-$(CONFIG_BLK_DEV_PLATFORM) += ide_platform.o
+
# Last of all
obj-$(CONFIG_BLK_DEV_HD) += hd.o
diff --git a/drivers/ide/legacy/ide_platform.c b/drivers/ide/legacy/ide_platform.c
new file mode 100644
index 0000000..0b3f5b5
--- /dev/null
+++ b/drivers/ide/legacy/ide_platform.c
@@ -0,0 +1,181 @@
+/*
+ * Platform IDE driver
+ *
+ * Copyright (C) 2007 MontaVista Software
+ *
+ * Maintainer: Kumar Gala <galak@kernel.crashing.org>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version.
+ */
+
+#include <linux/types.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/ide.h>
+#include <linux/ioport.h>
+#include <linux/module.h>
+#include <linux/pata_platform.h>
+#include <linux/io.h>
+
+static struct {
+ void __iomem *plat_ide_mapbase;
+ void __iomem *plat_ide_alt_mapbase;
+ ide_hwif_t *hwif;
+ int index;
+} hwif_prop;
+
+static ide_hwif_t *__devinit plat_ide_locate_hwif(void __iomem *base,
+ void __iomem *ctrl, struct pata_platform_info *pdata, int irq,
+ int mmio)
+{
+ unsigned long port = (unsigned long)base;
+ ide_hwif_t *hwif;
+ int index, i;
+
+ for (index = 0; index < MAX_HWIFS; ++index) {
+ hwif = ide_hwifs + index;
+ if (hwif->io_ports[IDE_DATA_OFFSET] == port)
+ goto found;
+ }
+
+ for (index = 0; index < MAX_HWIFS; ++index) {
+ hwif = ide_hwifs + index;
+ if (hwif->io_ports[IDE_DATA_OFFSET] == 0)
+ goto found;
+ }
+
+ return NULL;
+
+found:
+
+ hwif->hw.io_ports[IDE_DATA_OFFSET] = port;
+
+ port += (1 << pdata->ioport_shift);
+ for (i = IDE_ERROR_OFFSET; i <= IDE_STATUS_OFFSET;
+ i++, port += (1 << pdata->ioport_shift))
+ hwif->hw.io_ports[i] = port;
+
+ hwif->hw.io_ports[IDE_CONTROL_OFFSET] = (unsigned long)ctrl;
+
+ memcpy(hwif->io_ports, hwif->hw.io_ports, sizeof(hwif->hw.io_ports));
+ hwif->hw.irq = hwif->irq = irq;
+
+ hwif->hw.dma = NO_DMA;
+ hwif->hw.chipset = ide_generic;
+
+ if (mmio) {
+ hwif->mmio = 1;
+ default_hwif_mmiops(hwif);
+ }
+
+ hwif_prop.hwif = hwif;
+ hwif_prop.index = index;
+
+ return hwif;
+}
+
+static int __devinit plat_ide_probe(struct platform_device *pdev)
+{
+ struct resource *res_base, *res_alt, *res_irq;
+ ide_hwif_t *hwif;
+ struct pata_platform_info *pdata;
+ int ret = 0;
+ int mmio = 0;
+
+ pdata = pdev->dev.platform_data;
+
+ /* get a pointer to the register memory */
+ res_base = platform_get_resource(pdev, IORESOURCE_IO, 0);
+ res_alt = platform_get_resource(pdev, IORESOURCE_IO, 1);
+
+ if (!res_base || !res_alt) {
+ res_base = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+ res_alt = platform_get_resource(pdev, IORESOURCE_MEM, 1);
+ if (!res_base || !res_alt) {
+ ret = -ENOMEM;
+ goto out;
+ }
+ mmio = 1;
+ }
+
+ res_irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
+ if (!res_irq) {
+ ret = -EINVAL;
+ goto out;
+ }
+
+ if (mmio) {
+ hwif_prop.plat_ide_mapbase = devm_ioremap(&pdev->dev,
+ res_base->start, res_base->end - res_base->start + 1);
+ hwif_prop.plat_ide_alt_mapbase = devm_ioremap(&pdev->dev,
+ res_alt->start, res_alt->end - res_alt->start + 1);
+ } else {
+ hwif_prop.plat_ide_mapbase = devm_ioport_map(&pdev->dev,
+ res_base->start, res_base->end - res_base->start + 1);
+ hwif_prop.plat_ide_alt_mapbase = devm_ioport_map(&pdev->dev,
+ res_alt->start, res_alt->end - res_alt->start + 1);
+ }
+
+ hwif = plat_ide_locate_hwif(hwif_prop.plat_ide_mapbase,
+ hwif_prop.plat_ide_alt_mapbase, pdata, res_irq->start, mmio);
+
+ if (!hwif) {
+ ret = -ENODEV;
+ goto out;
+ }
+ hwif->gendev.parent = &pdev->dev;
+ hwif->noprobe = 0;
+
+ probe_hwif_init(hwif);
+
+ platform_set_drvdata(pdev, hwif);
+ ide_proc_register_port(hwif);
+
+ return 0;
+
+out:
+ return ret;
+}
+
+static int __devexit plat_ide_remove(struct platform_device *pdev)
+{
+ ide_hwif_t *hwif = pdev->dev.driver_data;
+
+ if (hwif != hwif_prop.hwif) {
+ dev_printk(KERN_DEBUG, &pdev->dev, "%s: hwif value error",
+ pdev->name);
+ } else {
+ ide_unregister(hwif_prop.index);
+ hwif_prop.index = 0;
+ hwif_prop.hwif = NULL;
+ }
+
+ return 0;
+}
+
+static struct platform_driver platform_ide_driver = {
+ .driver {
+ .name = "pata_platform",
+ },
+ .probe = plat_ide_probe,
+ .remove = __devexit_p(plat_ide_remove),
+};
+
+static int __init platform_ide_init(void)
+{
+ return platform_driver_register(&platform_ide_driver);
+}
+
+static void __exit platform_ide_exit(void)
+{
+ platform_driver_unregister(&platform_ide_driver);
+}
+
+MODULE_DESCRIPTION("Platform IDE driver");
+MODULE_LICENSE("GPL");
+
+module_init(platform_ide_init);
+module_exit(platform_ide_exit);
^ permalink raw reply related
* Re: About mdio_bus for 82xx based board
From: Scott Wood @ 2007-07-25 16:23 UTC (permalink / raw)
To: Alexandros Kostopoulos; +Cc: linuxppc-dev
In-Reply-To: <op.tv0x7yvmnhx3hy@phoenix>
On Wed, Jul 25, 2007 at 05:22:40PM +0300, Alexandros Kostopoulos wrote:
> 1) When mdiobus_register() called from mii-bitbang.c (fs_enet_mdio_probe()
> function) attemps to do a device_register for the mdio bus, it actually
> registers the device with a bus_id in the form [0|1|...]:<phy_addr>, that
> is the first part a simple integer. This, of course, happens because
> fs_enet_of_init() (fsl_soc.c) does a
> platform_device_register_simple("fsl-bb-mdio", i, NULL, 0); with i being
> the first part of the bus, starting from 0. Unfortunately, when
> fs_init_phy() (fs_enet_main.c) calls phy_connect() and therefore
> phy_attach() (phy_device.c), the latter attempts to find the device in the
> mdio bus, but it searches using the bus_id registered in the net_device
> struct, which is in the form of <resource address>:<phy_addr>, eg.
> f0000000:0, and therefore it fails... I don't know if I am doing something
> wrong here, so any hint would be greatly appreciated.
The code is broken. Try applying the set of 61 patches I posted a week
or so ago (you'll need to apply them to Paul's tree from around the same
time, not the current tree).
> 2) Since there are two ethernet@<address> nodes in my device tree,
> fs_of_enet_init() calls platform_device_register_simple("fsl-bb-mdio",...)
> twice, therefore creating two mdio busses, 0 and 1, each having the same
> two devices. For example, if I have two PHYs with addresses 1 and 5, I
> will get two mdio busses and 4 devices, 0:1, 0:5, 1:1 and 1:5. Well, this
> doesn't sound right to me, although I am not sure if this is a fatal
> issue. Any comments?
It's not right -- my patchset gets rid of all of this mess.
> 3) Also, if I don't want to enter the phy interrupt in the device tree
> (there is not one or I want to use PHY_POLL), what should I do? dtc seems
> to not allow -1 as a value in the reg property.
Leave the property out altogether.
-Scott
^ permalink raw reply
* DTC 1.0.0 Release Coming?
From: Jon Loeliger @ 2007-07-25 16:12 UTC (permalink / raw)
To: linuxppc-dev
Folks,
I'd like to make an official DTC Version 1.0.0 release soon!
To that end, I've published a repo on jdl.com with a v1.0.0-rc1
tag on it. I anticipate some updates to the Documentation before
a final 1.0.0 release still. However, if you have something
you would like to have be in The Real 1.0.0 release, please
let me know soon!
Thanks,
jdl
^ permalink raw reply
* Re: dtc: Improve the make install target
From: Jon Loeliger @ 2007-07-25 15:29 UTC (permalink / raw)
To: David Gibson; +Cc: linuxppc-dev
In-Reply-To: <20070724051452.GA28851@localhost.localdomain>
So, like, the other day David Gibson mumbled:
> This patch makes various improvements to dtc's make install target:
> - libfdt is also installed. Specifically, libfdt.a and the
> two export relevant header files, fdt.h and libfdt.h are installed.
> - ftdump is no longer installed. It was only ever a
> development debugging tool and may well go away at some point.
> - In keeping with normal conventions, there is now a PREFIX
> variable, allowing control of where things are installed (in /usr,
> /usr/local, /opt, etc.).
> - By default, installed into the user's home directory,
> instead of /usr. This is friendlier for self-installers, package
> builders can easily override PREFIX to restore the old behaviour.
>
> Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
Applied.
Thanks,
jdl
^ permalink raw reply
* [PATCH] Fix ibmvscsi client for multiplatform iSeries+pSeries kernel.
From: David Woodhouse @ 2007-07-25 14:41 UTC (permalink / raw)
To: Stephen Rothwell, Paul Mackerras; +Cc: linuxppc-dev
If you build a multiplatform kernel for iSeries and pSeries, with
ibmvscsic support, the resulting client doesn't work on iSeries.
This patch should fix that, using the appropriate low-level operations
for the machine detected at runtime.
Signed-off-by: David Woodhouse <dwmw2@infradead.org>
--- linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/rpa_vscsi.c~ 2006-11-29 21:57:37.000000000 +0000
+++ linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/rpa_vscsi.c 2006-12-19 15:42:57.000000000 +0000
@@ -42,14 +42,14 @@ static unsigned int partition_number = -
* Routines for managing the command/response queue
*/
/**
- * ibmvscsi_handle_event: - Interrupt handler for crq events
+ * rpavscsi_handle_event: - Interrupt handler for crq events
* @irq: number of irq to handle, not used
* @dev_instance: ibmvscsi_host_data of host that received interrupt
*
* Disables interrupts and schedules srp_task
* Always returns IRQ_HANDLED
*/
-static irqreturn_t ibmvscsi_handle_event(int irq, void *dev_instance)
+static irqreturn_t rpavscsi_handle_event(int irq, void *dev_instance)
{
struct ibmvscsi_host_data *hostdata =
(struct ibmvscsi_host_data *)dev_instance;
@@ -66,9 +66,9 @@ static irqreturn_t ibmvscsi_handle_event
* Frees irq, deallocates a page for messages, unmaps dma, and unregisters
* the crq with the hypervisor.
*/
-void ibmvscsi_release_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests)
+static void rpavscsi_release_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests)
{
long rc;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
@@ -108,12 +108,13 @@ static struct viosrp_crq *crq_queue_next
}
/**
- * ibmvscsi_send_crq: - Send a CRQ
+ * rpavscsi_send_crq: - Send a CRQ
* @hostdata: the adapter
* @word1: the first 64 bits of the data
* @word2: the second 64 bits of the data
*/
-int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata, u64 word1, u64 word2)
+static int rpavscsi_send_crq(struct ibmvscsi_host_data *hostdata,
+ u64 word1, u64 word2)
{
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
@@ -121,10 +122,10 @@ int ibmvscsi_send_crq(struct ibmvscsi_ho
}
/**
- * ibmvscsi_task: - Process srps asynchronously
+ * rpavscsi_task: - Process srps asynchronously
* @data: ibmvscsi_host_data of host
*/
-static void ibmvscsi_task(void *data)
+static void rpavscsi_task(void *data)
{
struct ibmvscsi_host_data *hostdata = (struct ibmvscsi_host_data *)data;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
@@ -189,6 +190,42 @@ static void set_adapter_info(struct ibmv
}
/**
+ * reset_crq_queue: - resets a crq after a failure
+ * @queue: crq_queue to initialize and register
+ * @hostdata: ibmvscsi_host_data of host
+ *
+ */
+static int rpavscsi_reset_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata)
+{
+ int rc;
+ struct vio_dev *vdev = to_vio_dev(hostdata->dev);
+
+ /* Close the CRQ */
+ do {
+ rc = plpar_hcall_norets(H_FREE_CRQ, vdev->unit_address);
+ } while ((rc == H_BUSY) || (H_IS_LONG_BUSY(rc)));
+
+ /* Clean out the queue */
+ memset(queue->msgs, 0x00, PAGE_SIZE);
+ queue->cur = 0;
+
+ set_adapter_info(hostdata);
+
+ /* And re-open it again */
+ rc = plpar_hcall_norets(H_REG_CRQ,
+ vdev->unit_address,
+ queue->msg_token, PAGE_SIZE);
+ if (rc == 2) {
+ /* Adapter is good, but other end is not ready */
+ printk(KERN_WARNING "ibmvscsi: Partner adapter not ready\n");
+ } else if (rc != 0) {
+ printk(KERN_WARNING
+ "ibmvscsi: couldn't register crq--rc 0x%x\n", rc);
+ }
+ return rc;
+}
+/**
* initialize_crq_queue: - Initializes and registers CRQ with hypervisor
* @queue: crq_queue to initialize and register
* @hostdata: ibmvscsi_host_data of host
@@ -197,9 +234,9 @@ static void set_adapter_info(struct ibmv
* the crq with the hypervisor.
* Returns zero on success.
*/
-int ibmvscsi_init_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests)
+static int rpavscsi_init_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests)
{
int rc;
int retrc;
@@ -226,7 +263,7 @@ int ibmvscsi_init_crq_queue(struct crq_q
queue->msg_token, PAGE_SIZE);
if (rc == H_RESOURCE)
/* maybe kexecing and resource is busy. try a reset */
- rc = ibmvscsi_reset_crq_queue(queue,
+ rc = rpavscsi_reset_crq_queue(queue,
hostdata);
if (rc == 2) {
@@ -239,7 +276,7 @@ int ibmvscsi_init_crq_queue(struct crq_q
}
if (request_irq(vdev->irq,
- ibmvscsi_handle_event,
+ rpavscsi_handle_event,
0, "ibmvscsi", (void *)hostdata) != 0) {
printk(KERN_ERR "ibmvscsi: couldn't register irq 0x%x\n",
vdev->irq);
@@ -256,7 +293,7 @@ int ibmvscsi_init_crq_queue(struct crq_q
queue->cur = 0;
spin_lock_init(&queue->lock);
- tasklet_init(&hostdata->srp_task, (void *)ibmvscsi_task,
+ tasklet_init(&hostdata->srp_task, (void *)rpavscsi_task,
(unsigned long)hostdata);
return retrc;
@@ -281,8 +318,8 @@ int ibmvscsi_init_crq_queue(struct crq_q
* @hostdata: ibmvscsi_host_data of host
*
*/
-int ibmvscsi_reenable_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata)
+static int rpavscsi_reenable_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata)
{
int rc;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
@@ -297,39 +334,10 @@ int ibmvscsi_reenable_crq_queue(struct c
return rc;
}
-/**
- * reset_crq_queue: - resets a crq after a failure
- * @queue: crq_queue to initialize and register
- * @hostdata: ibmvscsi_host_data of host
- *
- */
-int ibmvscsi_reset_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata)
-{
- int rc;
- struct vio_dev *vdev = to_vio_dev(hostdata->dev);
-
- /* Close the CRQ */
- do {
- rc = plpar_hcall_norets(H_FREE_CRQ, vdev->unit_address);
- } while ((rc == H_BUSY) || (H_IS_LONG_BUSY(rc)));
-
- /* Clean out the queue */
- memset(queue->msgs, 0x00, PAGE_SIZE);
- queue->cur = 0;
-
- set_adapter_info(hostdata);
-
- /* And re-open it again */
- rc = plpar_hcall_norets(H_REG_CRQ,
- vdev->unit_address,
- queue->msg_token, PAGE_SIZE);
- if (rc == 2) {
- /* Adapter is good, but other end is not ready */
- printk(KERN_WARNING "ibmvscsi: Partner adapter not ready\n");
- } else if (rc != 0) {
- printk(KERN_WARNING
- "ibmvscsi: couldn't register crq--rc 0x%x\n", rc);
- }
- return rc;
-}
+struct ibmvscsi_ops rpavscsi_ops = {
+ .init_crq_queue = rpavscsi_init_crq_queue,
+ .release_crq_queue = rpavscsi_release_crq_queue,
+ .reset_crq_queue = rpavscsi_reset_crq_queue,
+ .reenable_crq_queue = rpavscsi_reenable_crq_queue,
+ .send_crq = rpavscsi_send_crq,
+};
--- linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/ibmvscsi.c~ 2006-11-29 21:57:37.000000000 +0000
+++ linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/ibmvscsi.c 2006-12-19 15:53:59.000000000 +0000
@@ -89,6 +89,8 @@ static int max_requests = 50;
#define IBMVSCSI_VERSION "1.5.8"
+static struct ibmvscsi_ops *ibmvscsi_ops;
+
MODULE_DESCRIPTION("IBM Virtual SCSI");
MODULE_AUTHOR("Dave Boutcher");
MODULE_LICENSE("GPL");
@@ -567,7 +569,7 @@ static int ibmvscsi_send_srp_event(struc
list_add_tail(&evt_struct->list, &hostdata->sent);
if ((rc =
- ibmvscsi_send_crq(hostdata, crq_as_u64[0], crq_as_u64[1])) != 0) {
+ ibmvscsi_ops->send_crq(hostdata, crq_as_u64[0], crq_as_u64[1])) != 0) {
list_del(&evt_struct->list);
printk(KERN_ERR "ibmvscsi: send error %d\n",
@@ -1183,8 +1185,8 @@ void ibmvscsi_handle_crq(struct viosrp_c
case 0x01: /* Initialization message */
printk(KERN_INFO "ibmvscsi: partner initialized\n");
/* Send back a response */
- if (ibmvscsi_send_crq(hostdata,
- 0xC002000000000000LL, 0) == 0) {
+ if (ibmvscsi_ops->send_crq(hostdata,
+ 0xC002000000000000LL, 0) == 0) {
/* Now login */
send_srp_login(hostdata);
} else {
@@ -1212,10 +1214,10 @@ void ibmvscsi_handle_crq(struct viosrp_c
printk(KERN_INFO
"ibmvscsi: Re-enabling adapter!\n");
purge_requests(hostdata, DID_REQUEUE);
- if ((ibmvscsi_reenable_crq_queue(&hostdata->queue,
- hostdata)) ||
- (ibmvscsi_send_crq(hostdata,
- 0xC001000000000000LL, 0))) {
+ if ((ibmvscsi_ops->reenable_crq_queue(&hostdata->queue,
+ hostdata)) ||
+ (ibmvscsi_ops->send_crq(hostdata,
+ 0xC001000000000000LL, 0))) {
atomic_set(&hostdata->request_limit,
-1);
printk(KERN_ERR
@@ -1228,10 +1230,10 @@ void ibmvscsi_handle_crq(struct viosrp_c
crq->format);
purge_requests(hostdata, DID_ERROR);
- if ((ibmvscsi_reset_crq_queue(&hostdata->queue,
- hostdata)) ||
- (ibmvscsi_send_crq(hostdata,
- 0xC001000000000000LL, 0))) {
+ if ((ibmvscsi_ops->reset_crq_queue(&hostdata->queue,
+ hostdata)) ||
+ (ibmvscsi_ops->send_crq(hostdata,
+ 0xC001000000000000LL, 0))) {
atomic_set(&hostdata->request_limit,
-1);
printk(KERN_ERR
@@ -1517,7 +1519,7 @@ static int ibmvscsi_probe(struct vio_dev
atomic_set(&hostdata->request_limit, -1);
hostdata->host->max_sectors = 32 * 8; /* default max I/O 32 pages */
- rc = ibmvscsi_init_crq_queue(&hostdata->queue, hostdata, max_requests);
+ rc = ibmvscsi_ops->init_crq_queue(&hostdata->queue, hostdata, max_requests);
if (rc != 0 && rc != H_RESOURCE) {
printk(KERN_ERR "ibmvscsi: couldn't initialize crq\n");
goto init_crq_failed;
@@ -1538,7 +1540,7 @@ static int ibmvscsi_probe(struct vio_dev
* to fail if the other end is not acive. In that case we don't
* want to scan
*/
- if (ibmvscsi_send_crq(hostdata, 0xC001000000000000LL, 0) == 0
+ if (ibmvscsi_ops->send_crq(hostdata, 0xC001000000000000LL, 0) == 0
|| rc == H_RESOURCE) {
/*
* Wait around max init_timeout secs for the adapter to finish
@@ -1564,7 +1566,7 @@ static int ibmvscsi_probe(struct vio_dev
add_host_failed:
release_event_pool(&hostdata->pool, hostdata);
init_pool_failed:
- ibmvscsi_release_crq_queue(&hostdata->queue, hostdata, max_requests);
+ ibmvscsi_ops->release_crq_queue(&hostdata->queue, hostdata, max_requests);
init_crq_failed:
scsi_host_put(host);
scsi_host_alloc_failed:
@@ -1575,8 +1577,8 @@ static int ibmvscsi_remove(struct vio_de
{
struct ibmvscsi_host_data *hostdata = vdev->dev.driver_data;
release_event_pool(&hostdata->pool, hostdata);
- ibmvscsi_release_crq_queue(&hostdata->queue, hostdata,
- max_requests);
+ ibmvscsi_ops->release_crq_queue(&hostdata->queue, hostdata,
+ max_requests);
scsi_remove_host(hostdata->host);
scsi_host_put(hostdata->host);
@@ -1606,6 +1608,13 @@ static struct vio_driver ibmvscsi_driver
int __init ibmvscsi_module_init(void)
{
+ if (firmware_has_feature(FW_FEATURE_ISERIES))
+ ibmvscsi_ops = &iseriesvscsi_ops;
+ else if (firmware_has_feature(FW_FEATURE_VIO))
+ ibmvscsi_ops = &rpavscsi_ops;
+ else
+ return -ENODEV;
+
return vio_register_driver(&ibmvscsi_driver);
}
--- linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/ibmvscsi.h~ 2006-11-29 21:57:37.000000000 +0000
+++ linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/ibmvscsi.h 2006-12-19 15:54:18.000000000 +0000
@@ -94,21 +94,25 @@ struct ibmvscsi_host_data {
};
/* routines for managing a command/response queue */
-int ibmvscsi_init_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests);
-void ibmvscsi_release_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests);
-int ibmvscsi_reset_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata);
-
-int ibmvscsi_reenable_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata);
-
void ibmvscsi_handle_crq(struct viosrp_crq *crq,
struct ibmvscsi_host_data *hostdata);
-int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata,
- u64 word1, u64 word2);
+
+struct ibmvscsi_ops {
+ int (*init_crq_queue)(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests);
+ void (*release_crq_queue)(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests);
+ int (*reset_crq_queue)(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata);
+ int (*reenable_crq_queue)(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata);
+ int (*send_crq)(struct ibmvscsi_host_data *hostdata,
+ u64 word1, u64 word2);
+};
+
+extern struct ibmvscsi_ops iseriesvscsi_ops;
+extern struct ibmvscsi_ops rpavscsi_ops;
#endif /* IBMVSCSI_H */
--- linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/iseries_vscsi.c~ 2006-11-29 21:57:37.000000000 +0000
+++ linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/iseries_vscsi.c 2006-12-19 15:47:03.000000000 +0000
@@ -53,7 +53,7 @@ struct srp_lp_event {
/**
* standard interface for handling logical partition events.
*/
-static void ibmvscsi_handle_event(struct HvLpEvent *lpevt)
+static void iseriesvscsi_handle_event(struct HvLpEvent *lpevt)
{
struct srp_lp_event *evt = (struct srp_lp_event *)lpevt;
@@ -74,9 +74,9 @@ static void ibmvscsi_handle_event(struct
/* ------------------------------------------------------------
* Routines for driver initialization
*/
-int ibmvscsi_init_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests)
+static int iseriesvscsi_init_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests)
{
int rc;
@@ -88,7 +88,7 @@ int ibmvscsi_init_crq_queue(struct crq_q
goto viopath_open_failed;
}
- rc = vio_setHandler(viomajorsubtype_scsi, ibmvscsi_handle_event);
+ rc = vio_setHandler(viomajorsubtype_scsi, iseriesvscsi_handle_event);
if (rc < 0) {
printk("vio_setHandler failed with rc %d in open_event_path\n",
rc);
@@ -102,9 +102,9 @@ int ibmvscsi_init_crq_queue(struct crq_q
return -1;
}
-void ibmvscsi_release_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata,
- int max_requests)
+static void iseriesvscsi_release_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata,
+ int max_requests)
{
vio_clearHandler(viomajorsubtype_scsi);
viopath_close(viopath_hostLp, viomajorsubtype_scsi, max_requests);
@@ -117,8 +117,8 @@ void ibmvscsi_release_crq_queue(struct c
*
* no-op for iSeries
*/
-int ibmvscsi_reset_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata)
+static int iseriesvscsi_reset_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata)
{
return 0;
}
@@ -130,19 +130,20 @@ int ibmvscsi_reset_crq_queue(struct crq_
*
* no-op for iSeries
*/
-int ibmvscsi_reenable_crq_queue(struct crq_queue *queue,
- struct ibmvscsi_host_data *hostdata)
+static int iseriesvscsi_reenable_crq_queue(struct crq_queue *queue,
+ struct ibmvscsi_host_data *hostdata)
{
return 0;
}
/**
- * ibmvscsi_send_crq: - Send a CRQ
+ * iseriesvscsi_send_crq: - Send a CRQ
* @hostdata: the adapter
* @word1: the first 64 bits of the data
* @word2: the second 64 bits of the data
*/
-int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata, u64 word1, u64 word2)
+static int iseriesvscsi_send_crq(struct ibmvscsi_host_data *hostdata,
+ u64 word1, u64 word2)
{
single_host_data = hostdata;
return HvCallEvent_signalLpEventFast(viopath_hostLp,
@@ -156,3 +157,11 @@ int ibmvscsi_send_crq(struct ibmvscsi_ho
VIOVERSION << 16, word1, word2, 0,
0);
}
+
+struct ibmvscsi_ops iseriesvscsi_ops = {
+ .init_crq_queue = iseriesvscsi_init_crq_queue,
+ .release_crq_queue = iseriesvscsi_release_crq_queue,
+ .reset_crq_queue = iseriesvscsi_reset_crq_queue,
+ .reenable_crq_queue = iseriesvscsi_reenable_crq_queue,
+ .send_crq = iseriesvscsi_send_crq,
+};
--- linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/Makefile.orig 2007-01-01 20:06:26.000000000 +0000
+++ linux-2.6.19.ppc64/drivers/scsi/ibmvscsi/Makefile 2007-01-01 20:06:35.000000000 +0000
@@ -1,9 +1,7 @@
obj-$(CONFIG_SCSI_IBMVSCSI) += ibmvscsic.o
ibmvscsic-y += ibmvscsi.o
-ifndef CONFIG_PPC_PSERIES
ibmvscsic-$(CONFIG_PPC_ISERIES) += iseries_vscsi.o
-endif
ibmvscsic-$(CONFIG_PPC_PSERIES) += rpa_vscsi.o
obj-$(CONFIG_SCSI_IBMVSCSIS) += ibmvstgt.o
--
dwmw2
^ permalink raw reply
* Re: [PATCH] xmon consistency clean up
From: Grant Likely @ 2007-07-25 14:25 UTC (permalink / raw)
To: michael; +Cc: paulus, linuxppc-dev
In-Reply-To: <1185365630.21877.4.camel@concordia.ozlabs.ibm.com>
On 7/25/07, Michael Ellerman <michael@ellerman.id.au> wrote:
> On Wed, 2007-07-25 at 16:21 +1000, Benjamin Herrenschmidt wrote:
> > Nah, keep it xmon_puts, since it doesn't take a stream argument and
> > define a "puts" for use by xmon core.
>
> But then it needs to add a newline .. and we've gone around in a circle
> again. Funny how the trivialest of patches gets the most review.
And the bike shed needs to be green.
http://www.freebsd.org/doc/en_US.ISO8859-1/books/faq/misc.html#BIKESHED-PAINTING
:-)
g.
--
Grant Likely, B.Sc., P.Eng.
Secret Lab Technologies Ltd.
grant.likely@secretlab.ca
(403) 399-0195
^ permalink raw reply
* About mdio_bus for 82xx based board
From: Alexandros Kostopoulos @ 2007-07-25 14:22 UTC (permalink / raw)
To: linuxppc-dev
Hi all,
I'm trying to make FCC ethernet work with my board, based on an MPC8275
processor. I'm using kernel 2.6.22.1
I have the following problems:
1) When mdiobus_register() called from mii-bitbang.c (fs_enet_mdio_probe()
function) attemps to do a device_register for the mdio bus, it actually
registers the device with a bus_id in the form [0|1|...]:<phy_addr>, that
is the first part a simple integer. This, of course, happens because
fs_enet_of_init() (fsl_soc.c) does a
platform_device_register_simple("fsl-bb-mdio", i, NULL, 0); with i being
the first part of the bus, starting from 0. Unfortunately, when
fs_init_phy() (fs_enet_main.c) calls phy_connect() and therefore
phy_attach() (phy_device.c), the latter attempts to find the device in the
mdio bus, but it searches using the bus_id registered in the net_device
struct, which is in the form of <resource address>:<phy_addr>, eg.
f0000000:0, and therefore it fails... I don't know if I am doing something
wrong here, so any hint would be greatly appreciated.
2) Since there are two ethernet@<address> nodes in my device tree,
fs_of_enet_init() calls platform_device_register_simple("fsl-bb-mdio",...)
twice, therefore creating two mdio busses, 0 and 1, each having the same
two devices. For example, if I have two PHYs with addresses 1 and 5, I
will get two mdio busses and 4 devices, 0:1, 0:5, 1:1 and 1:5. Well, this
doesn't sound right to me, although I am not sure if this is a fatal
issue. Any comments?
3) Also, if I don't want to enter the phy interrupt in the device tree
(there is not one or I want to use PHY_POLL), what should I do? dtc seems
to not allow -1 as a value in the reg property.
thank you in advance for your responses
Alex
^ permalink raw reply
* [PATCH] fix ppc kernels after build-id addition
From: Meelis Roos @ 2007-07-25 12:17 UTC (permalink / raw)
To: linuxppc-dev, Linux Kernel list
This patch fixes arch/ppc kernels, at least for prep subarch, after
build-id addition. Without the patch, kernels were 3 times the size and
bootloader refused to load them. Now they are back to normal again.
The patch is very similar to David Millers sparc patch, just applied to
ppc architecture.
Tested only with Roland McGrath's "Use LDFLAGS_MODULE only for .ko
links" patch applied - boots and works fine.
Signed-off-by: Meelis Roos <mroos@linux.ee>
diff --git a/arch/ppc/kernel/vmlinux.lds.S b/arch/ppc/kernel/vmlinux.lds.S
index c0aac3f..98c1212 100644
--- a/arch/ppc/kernel/vmlinux.lds.S
+++ b/arch/ppc/kernel/vmlinux.lds.S
@@ -91,6 +91,8 @@ SECTIONS
. = ALIGN(8192);
.data.init_task : { *(.data.init_task) }
+ NOTES
+
. = ALIGN(4096);
__init_begin = .;
.init.text : {
--
Meelis Roos (mroos@linux.ee)
^ permalink raw reply related
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox