Skip to content

Commit

Permalink
sky2: irqname based on pci address
Browse files Browse the repository at this point in the history
This is based on Michal Schmidt fix for skge.

Most network drivers request their IRQ when the interface is activated.
sky2 does it in ->probe() instead, because it can work with two-port
cards where the two net_devices use the same IRQ. This works fine most
of the time, except in some situations when the interface gets renamed.
Consider this example:

1. modprobe sky2
   The card is detected as eth0 and requests IRQ 17. Directory
   /proc/irq/17/eth0 is created.
2. There is an udev rule which says this interface should be called
   eth1, so udev renames eth0 -> eth1.
3. modprobe 8139too
   The Realtek card is detected as eth0. It will be using IRQ 17 too.
4. ip link set eth0 up
   Now 8139too requests IRQ 17.

The result is:
WARNING: at fs/proc/generic.c:590 proc_register ...
proc_dir_entry '17/eth0' already registered

The fix is for sky2 to name the irq based on the pci device, as is done
by some other devices DRM, infiniband, ...  ie. sky2@pci:0000:00:00

Signed-off-by: Stephen Hemminger <shemminger@vyatta.com>
Reviewed-by: Michal Schmidt <mschmidt@redhat.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
Stephen Hemminger authored and David S. Miller committed Oct 1, 2009
1 parent 415e69e commit 6646679
Show file tree
Hide file tree
Showing 2 changed files with 7 additions and 2 deletions.
7 changes: 5 additions & 2 deletions drivers/net/sky2.c
Original file line number Diff line number Diff line change
Expand Up @@ -4487,13 +4487,16 @@ static int __devinit sky2_probe(struct pci_dev *pdev,
wol_default = device_may_wakeup(&pdev->dev) ? WAKE_MAGIC : 0;

err = -ENOMEM;
hw = kzalloc(sizeof(*hw), GFP_KERNEL);

hw = kzalloc(sizeof(*hw) + strlen(DRV_NAME "@pci:")
+ strlen(pci_name(pdev)) + 1, GFP_KERNEL);
if (!hw) {
dev_err(&pdev->dev, "cannot allocate hardware struct\n");
goto err_out_free_regions;
}

hw->pdev = pdev;
sprintf(hw->irq_name, DRV_NAME "@pci:%s", pci_name(pdev));

hw->regs = ioremap_nocache(pci_resource_start(pdev, 0), 0x4000);
if (!hw->regs) {
Expand Down Expand Up @@ -4539,7 +4542,7 @@ static int __devinit sky2_probe(struct pci_dev *pdev,

err = request_irq(pdev->irq, sky2_intr,
(hw->flags & SKY2_HW_USE_MSI) ? 0 : IRQF_SHARED,
dev->name, hw);
hw->irq_name, hw);
if (err) {
dev_err(&pdev->dev, "cannot assign irq %d\n", pdev->irq);
goto err_out_unregister;
Expand Down
2 changes: 2 additions & 0 deletions drivers/net/sky2.h
Original file line number Diff line number Diff line change
Expand Up @@ -2085,6 +2085,8 @@ struct sky2_hw {
struct timer_list watchdog_timer;
struct work_struct restart_work;
wait_queue_head_t msi_wait;

char irq_name[0];
};

static inline int sky2_is_copper(const struct sky2_hw *hw)
Expand Down

0 comments on commit 6646679

Please sign in to comment.