1. 25 2月, 2012 9 次提交
  2. 24 2月, 2012 15 次提交
    • B
      PCI: collapse pcibios_resource_to_bus · fb127cb9
      Bjorn Helgaas 提交于
      Everybody uses the generic pcibios_resource_to_bus() supplied by the core
      now, so remove the ARCH_HAS_GENERIC_PCI_OFFSETS used during conversion.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      fb127cb9
    • B
      PCI: add generic pcibios_resource_to_bus() · 36a66cd6
      Bjorn Helgaas 提交于
      This replaces the generic versions of pcibios_resource_to_bus() and
      pcibios_bus_to_resource() in asm-generic/pci.h with versions that use
      pci_resource_to_bus() and pci_bus_to_resource().
      
      The replacements are equivalent except that they can apply host
      bridge window offsets when the arch has supplied them by using
      pci_add_resource_offset().
      
      Each arch can convert to using pci_add_resource_offset() individually by
      removing its device resource fixups from pcibios_fixup_bus() and supplying
      ARCH_HAS_GENERIC_PCI_OFFSETS.  ARCH_HAS_GENERIC_PCI_OFFSETS can be removed
      after all have converted.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      36a66cd6
    • B
      PCI: convert bus addresses to resource when reading BARs · 5bfa14ed
      Bjorn Helgaas 提交于
      Some PCI host bridges translate CPU addresses to PCI bus addresses.
      Previously, we initialized pci_dev resources with PCI bus addresses,
      then converted them to CPU addresses later in arch-specific code
      (pcibios_fixup_resources()), which leaves a window of time where the
      pci_dev resources are incorrect.
      
      This patch adds support in the core for this address translation.
      When the arch creates the root bus, it can supply the host bridge
      address translation information, and the core can use it to set the
      pci_dev resources correctly from the beginning.
      
      This gives us a way to fix the problem that quirks that run between device
      discovery and pcibios_fixup_resources() fail because they use pci_dev
      resources that haven't been converted.  The reference below is to one
      such problem that affected ARM and ia64.
      
      Note that this patch has no effect until an arch starts using
      pci_add_resource_offset() with a non-zero offset: before that, all
      all host bridge windows have a zero offset and pci_bus_to_resource()
      copies the pci_bus_region directly to the struct resource.
      
      Reference: https://lkml.org/lkml/2009/10/12/405Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      5bfa14ed
    • B
      PCI: add struct pci_host_bridge_window with CPU/bus address offset · 0efd5aab
      Bjorn Helgaas 提交于
      Some PCI host bridges apply an address offset, so bus addresses on PCI are
      different from CPU addresses.  This patch adds a way for architectures to
      tell the PCI core about this offset.  For example:
      
          LIST_HEAD(resources);
          pci_add_resource_offset(&resources, host->io_space, host->io_offset);
          pci_add_resource_offset(&resources, host->mem_space, host->mem_offset);
          pci_scan_root_bus(parent, bus, ops, sysdata, &resources);
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      0efd5aab
    • B
      PCI: add struct pci_host_bridge and a list of all bridges found · 5a21d70d
      Bjorn Helgaas 提交于
      This adds a list of all PCI host bridges we find and a way to look up
      the host bridge from a pci_dev.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      5a21d70d
    • B
      PCI: don't publish new root bus until it's fully initialized · a5390aa6
      Bjorn Helgaas 提交于
      When pci_create_root_bus() adds the new struct pci_bus to the global
      pci_root_buses list, the bus becomes visible to other parts of the
      kernel, so it should be fully initialized.
      
      This patch delays adding the bus to the pci_root_buses list until after
      all the struct pci_bus initialization is finished.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      a5390aa6
    • B
      PCI: make pci_flags non-weak · 844393f4
      Bjorn Helgaas 提交于
      No architecture defines its own pci_flags, so the core symbol does not
      need to be weak.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      844393f4
    • B
      PCI: make pci_flags always available · 47087700
      Bjorn Helgaas 提交于
      If we move resource assignment functions into the core, we'll still
      need a way for architectures to prevent reassignment, e.g., the
      "pci_probe_only" functionality, and we'll need a generic, always
      available way the core can test for that.  The "pci_flags"
      arrangement used by several architectures seems like a convenient
      way to do this.
      Signed-off-by: NBjorn Helgaas <bhelgaas@google.com>
      47087700
    • M
      PCI: Add pcie_hp=nomsi to disable MSI/MSI-X for pciehp driver · 7570a333
      MUNEDA Takahiro 提交于
      Add a parameter to avoid using MSI/MSI-X for PCIe native hotplug; it's
      known to be buggy on some platforms.
      
      In my environment, while shutting down, following stack trace is shown
      sometimes.
      
        irq 16: nobody cared (try booting with the "irqpoll" option)
        Pid: 1081, comm: reboot Not tainted 3.2.0 #1
        Call Trace:
         <IRQ>  [<ffffffff810cec1d>] __report_bad_irq+0x3d/0xe0
         [<ffffffff810cee1c>] note_interrupt+0x15c/0x210
         [<ffffffff810cc485>] handle_irq_event_percpu+0xb5/0x210
         [<ffffffff810cc621>] handle_irq_event+0x41/0x70
         [<ffffffff810cf675>] handle_fasteoi_irq+0x55/0xc0
         [<ffffffff81015356>] handle_irq+0x46/0xb0
         [<ffffffff814fbe9d>] do_IRQ+0x5d/0xe0
         [<ffffffff814f146e>] common_interrupt+0x6e/0x6e
         [<ffffffff8106b040>] ? __do_softirq+0x60/0x210
         [<ffffffff8108aeb1>] ? hrtimer_interrupt+0x151/0x240
         [<ffffffff814fb5ec>] call_softirq+0x1c/0x30
         [<ffffffff810152d5>] do_softirq+0x65/0xa0
         [<ffffffff8106ae9d>] irq_exit+0xbd/0xe0
         [<ffffffff814fbf8e>] smp_apic_timer_interrupt+0x6e/0x99
         [<ffffffff814f9e5e>] apic_timer_interrupt+0x6e/0x80
         <EOI>  [<ffffffff814f0fb1>] ? _raw_spin_unlock_irqrestore+0x11/0x20
         [<ffffffff812629fc>] pci_bus_write_config_word+0x6c/0x80
         [<ffffffff81266fc2>] pci_intx+0x52/0xa0
         [<ffffffff8127de3d>] pci_intx_for_msi+0x1d/0x30
        [<ffffffff8127e4fb>] pci_msi_shutdown+0x7b/0x110
         [<ffffffff81269d34>] pci_device_shutdown+0x34/0x50
         [<ffffffff81326c4f>] device_shutdown+0x2f/0x140
         [<ffffffff8107b981>] kernel_restart_prepare+0x31/0x40
         [<ffffffff8107b9e6>] kernel_restart+0x16/0x60
         [<ffffffff8107bbfd>] sys_reboot+0x1ad/0x220
         [<ffffffff814f4b90>] ? do_page_fault+0x1e0/0x460
         [<ffffffff811942d0>] ? __sync_filesystem+0x90/0x90
         [<ffffffff8105c9aa>] ? __cond_resched+0x2a/0x40
         [<ffffffff814ef090>] ? _cond_resched+0x30/0x40
         [<ffffffff81169e17>] ? iterate_supers+0xb7/0xd0
         [<ffffffff814f9382>] system_call_fastpath+0x16/0x1b
        handlers:
        [<ffffffff8138a0f0>] usb_hcd_irq
        [<ffffffff8138a0f0>] usb_hcd_irq
        [<ffffffff8138a0f0>] usb_hcd_irq
        Disabling IRQ #16
      
      An un-wanted interrupt is generated when PCI driver switches from
      MSI/MSI-X to INTx while shutting down the device.  The interrupt does
      not happen if MSI/MSI-X is not used on the device.
      I confirmed that this problem does not happen if pcie_hp=nomsi was
      specified and hotplug operation worked fine as usual.
      
      v2: Automatically disable MSI/MSI-X against following device:
          PCI bridge: Integrated Device Technology, Inc. Device 807f (rev 02)
      v3: Based on the review comment, combile the if statements.
      v4: Removed module parameter.
          Move some code to build pciehp as a module.
          Move device specific code to driver/pci/quirks.c.
      v5: Drop a device specific code until getting a vendor statement.
      Reviewed-by: NKenji Kaneshige <kaneshige.kenji@jp.fujitsu.com>
      Signed-off-by: NMUNEDA Takahiro <muneda.takahiro@jp.fujitsu.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      7570a333
    • Y
      PCI: move pci_find_saved_cap out of linux/pci.h · 34a4876e
      Yinghai Lu 提交于
      Only one user in driver/pci/pci.c, so we don't need to put it in global
      pci.h
      Reviewed-by: NBjorn Helgaas <bhelgaas@google.com>
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      34a4876e
    • Y
      PCI: fix memleak for pci dev removing during hotplug · f796841e
      Yinghai Lu 提交于
      unreferenced object 0xffff880276d17700 (size 64):
        comm "swapper/0", pid 1, jiffies 4294897182 (age 3976.028s)
        hex dump (first 32 bytes):
          00 00 00 00 00 00 00 00 18 f9 de 76 02 88 ff ff  ...........v....
          10 00 00 00 0e 00 00 00 0f 28 40 00 00 00 00 00  .........(@.....
        backtrace:
          [<ffffffff81c8aede>] kmemleak_alloc+0x26/0x43
          [<ffffffff811385f0>] __kmalloc+0x121/0x183
          [<ffffffff813cf821>] pci_add_cap_save_buffer+0x35/0x7c
          [<ffffffff813d12b7>] pci_allocate_cap_save_buffers+0x1d/0x65
          [<ffffffff813cdb52>] pci_device_add+0x92/0xf1
          [<ffffffff81c8afe6>] pci_scan_single_device+0x9f/0xa1
          [<ffffffff813cdbd2>] pci_scan_slot.part.20+0x21/0x106
          [<ffffffff813cdce2>] pci_scan_slot+0x2b/0x35
          [<ffffffff81c8dae4>] __pci_scan_child_bus+0x51/0x107
          [<ffffffff81c8d75b>] pci_scan_bridge+0x376/0x6ae
          [<ffffffff81c8db60>] __pci_scan_child_bus+0xcd/0x107
          [<ffffffff81c8dbab>] pci_scan_child_bus+0x11/0x2a
          [<ffffffff81cca58c>] pci_acpi_scan_root+0x18b/0x21c
          [<ffffffff81c916be>] acpi_pci_root_add+0x1e1/0x42a
          [<ffffffff81406210>] acpi_device_probe+0x50/0x190
          [<ffffffff814a0227>] really_probe+0x99/0x126
      
      Need to free saved_buffer for capabilities.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      f796841e
    • Y
      PCI: Fix device class print out · 2dd8ba92
      Yinghai Lu 提交于
      Found debug print of class is shifted.
      
      | pci 0000:f8:15.2: [8086:2b56] type 0 class 0x000600
      
      Code is trying to print class with 6 digits, but use shifted class with
      4 digits valid value as variable.
      
      Change to original dev->class directly.
      
      Also remove not needed calculating of local variable class, because it
      will be updated after pci_fixup_device(pci_fixup_early...)
      
      Also unify type print out when class and header is not matched.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      2dd8ba92
    • Y
      PCI: Skip cardbus assigned resource reset during pci bus rescan · 3796f1e2
      Yinghai Lu 提交于
      Otherwise when rescan is used for cardbus, assigned resources will get
      cleared.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Tested-by: NDominik Brodowski <linux@dominikbrodowski.net>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      3796f1e2
    • Y
      PCI: Fix "cardbus bridge resources as optional" size handling · 11848934
      Yinghai Lu 提交于
      We should not set the requested size to -2; that will confuse the
      resource list sorting with align when SIZEALIGN is used.
      
      Change to STARTALIGN and pass align from start;  we are safe to do that
      just as we do that regular pci bridge.  In the long run, we should just
      treat cardbus like a regular pci bridge.
      
      Also fix the case when realloc_head is not passed: we should keep the
      requested size.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Tested-by: NDominik Brodowski <linux@dominikbrodowski.net>
      Acked-by: NRam Pai <linuxram@us.ibm.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      11848934
    • Y
      PCI: Disable cardbus bridge MEM1 prefetchable bit · dcef0d06
      Yinghai Lu 提交于
      Some BIOSes enable prefetch on both MEM0 and MEM1.  But the cardbus code
      assumes MEM1 is non-pref...
      
      Discussion could be found at:
      	https://lkml.org/lkml/2012/1/12/1
      	https://bugzilla.kernel.org/show_bug.cgi?id=41622#c23Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Tested-by: NDominik Brodowski <linux@dominikbrodowski.net>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      dcef0d06
  3. 18 2月, 2012 3 次提交
  4. 15 2月, 2012 13 次提交
    • T
      PCI: Add quirk for still enabled interrupts on Intel Sandy Bridge GPUs · f67fd55f
      Thomas Jarosch 提交于
      Some BIOS implementations leave the Intel GPU interrupts enabled,
      even though no one is handling them (f.e. i915 driver is never loaded).
      Additionally the interrupt destination is not set up properly
      and the interrupt ends up -somewhere-.
      
      These spurious interrupts are "sticky" and the kernel disables
      the (shared) interrupt line after 100.000+ generated interrupts.
      
      Fix it by disabling the still enabled interrupts.
      This resolves crashes often seen on monitor unplug.
      
      Tested on the following boards:
      - Intel DH61CR: Affected
      - Intel DH67BL: Affected
      - Intel S1200KP server board: Affected
      - Asus P8H61-M LE: Affected, but system does not crash.
        Probably the IRQ ends up somewhere unnoticed.
      
      According to reports on the net, the Intel DH61WW board is also affected.
      
      Many thanks to Jesse Barnes from Intel for helping
      with the register configuration and to Intel in general
      for providing public hardware documentation.
      Signed-off-by: NThomas Jarosch <thomas.jarosch@intra2net.com>
      Tested-by: NCharlie Suffin <charlie.suffin@stratus.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      f67fd55f
    • A
      PCI: Annotate PCI quirks in initcall_debug style · 3209874a
      Arjan van de Ven 提交于
      While diagnosing some boot time issues on a platform, all that I
      could see in the bootgraph/dmesg was that the system was spending
      a lot of time in applying one or more PCI quirks... which
      was virtually undebuggable.
      
      This patch adds printk's in "initcall_debug" style to the dmesg,
      which are added when the user asks for the initcall_debug
      (the nr one tool to use when debugging boot hangs or boot time issues)
      kernel command line option.
      
      v2: add #includes so quirks can build on non-x86
      Signed-off-by: NArjan van de Ven <arjan@linux.intel.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      3209874a
    • D
      PCI hotplug: cpcihp: fix debug module parameter to be bool · 309c6651
      Danny Kukawka 提交于
      Fix debug variable from module parameter to be really bool to
      fix 'warning: return from incompatible pointer type'.
      Acked-by: NScott Murray <scott@spiteful.org>
      Signed-off-by: NDanny Kukawka <danny.kukawka@bisect.de>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      309c6651
    • K
      PCI: check for pci bar restore completion and retry · 26f41062
      Kay, Allen M 提交于
      On some OEM systems, pci_restore_state() is called while FLR has not yet
      completed.  As a result, PCI BAR register restore is not successful.  This fix
      reads back the restored value and compares it with saved value and re-tries 10
      times before giving up.
      Signed-off-by: NJean Guyader <jean.guyader@eu.citrix.com>
      Signed-off-by: NEric Chanudet <eric.chanudet@citrix.com>
      Signed-off-by: NAllen Kay <allen.m.kay@intel.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      26f41062
    • Y
      PCI: pciehp: Disable/enable link during slot power off/on · 2debd928
      Yinghai Lu 提交于
      On a system with a repeater on the system board to support gen2 hotplug,
      we found that when an ExpressModule is removed from some slots,
      /var/log/messages will be full of "card present/not present" warnings.
      
      It turns out the root complex is continually trying to train the link to
      the repeater because the repeater has not been reset.
      
      This patch will disable the link at removal time to allow the repeater
      to be reset properly.  This also prevents a potential AER message at
      removal time.
      
      Also, when testing hotplug on a system under development, we found if we
      boot the system without an EM installed, and later hot-add an EM, it
      does not work with Linux, but another OS is ok.  The root cause is that
      BIOS left link disabled when slot was empty at boot time, and other OS
      is modifying the link disable bit in link ctrl during power on/off.
      
      So we should do the same thing to disable/enable link during power off/on.
      
      -v2: check link DLLA bit instead of 100ms waiting.
           Separate link disable/enable functions to another patch.
      Signed-off-by: NYinghai Lu <yinghai.lu@oracle.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      2debd928
    • Y
      PCI: pciehp: Add Disable/enable link functions · 7f822999
      Yinghai Lu 提交于
      Will use it during power off/on of slots
      Signed-off-by: NYinghai Lu <yinghai.lu@oracle.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      7f822999
    • Y
      PCI: pciehp: Add pcie_wait_link_not_active() · bffe4f72
      Yinghai Lu 提交于
      Will use it for link disable status checking.
      Signed-off-by: NYinghai Lu <yinghai.lu@oracle.com>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      bffe4f72
    • Y
      PCI: pciehp: make check_link_active more helpful · 4e2ce405
      Yinghai Lu 提交于
      A few changes:
        - remove the 'inline' and let the complier decide
        - return a bool to indicate whether the link was active
        - add a debug message to indicate link state when it beocmes active
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      4e2ce405
    • Y
      PCI: pciehp: replace unconditional sleep with config space access check · 2f5d8e4f
      Yinghai Lu 提交于
      During reviewing
      |	PCI: pciehp: wait 1000 ms before Link Training check
      Linus said:
      >...
      > That's a *long* time, and it's irritating to the user. It makes the
      > user think "the machine is slow".
      >...
      > And quite frankly, an unconditional one-second delay here seems bad.
      >Two seconds was unacceptable, one second is just bad.
      
      Try to access the pci conf of a pci device that is supposed to show up
      in 1s.  If we can read back a valid vendor/device id, we can return
      early.
      
      Related discussion could be found:
      	https://lkml.org/lkml/2011/12/6/339
      
      -v2: seperate code to pci_bus_read_dev_vendor_id() from pci_scan_device()
          and reuse it from pciehp code. Suggested by Matthew Wilcox.
      -v3: According to Kenj, don't use array in stack, and don't wait too long
          for crs, also return fail status if not found.
          Also separate pci_bus_dev_read_vendor_id() change to another patch.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      2f5d8e4f
    • Y
      PCI: Separate pci_bus_read_dev_vendor_id from pci_scan_device · efdc87da
      Yinghai Lu 提交于
      We can reuse it for pciehp probing.
      
      -v2: according to Kenji, fix crs timeout checking, and export the function
           for later use when pciehp is compiled as a module.
      Suggested-by: NMatthew Wilcox <matthew@wil.cx>
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      efdc87da
    • Y
      PCI: make sriov work with hotplug remove · ac205b7b
      Yinghai Lu 提交于
      When hot removing a pci express module that has a pcie switch and supports
      SRIOV, we got:
      
      [ 5918.610127] pciehp 0000:80:02.2:pcie04: pcie_isr: intr_loc 1
      [ 5918.615779] pciehp 0000:80:02.2:pcie04: Attention button interrupt received
      [ 5918.622730] pciehp 0000:80:02.2:pcie04: Button pressed on Slot(3)
      [ 5918.629002] pciehp 0000:80:02.2:pcie04: pciehp_get_power_status: SLOTCTRL a8 value read 1f9
      [ 5918.637416] pciehp 0000:80:02.2:pcie04: PCI slot #3 - powering off due to button press.
      [ 5918.647125] pciehp 0000:80:02.2:pcie04: pcie_isr: intr_loc 10
      [ 5918.653039] pciehp 0000:80:02.2:pcie04: pciehp_green_led_blink: SLOTCTRL a8 write cmd 200
      [ 5918.661229] pciehp 0000:80:02.2:pcie04: pciehp_set_attention_status: SLOTCTRL a8 write cmd c0
      [ 5924.667627] pciehp 0000:80:02.2:pcie04: Disabling domain:bus:device=0000:b0:00
      [ 5924.674909] pciehp 0000:80:02.2:pcie04: pciehp_get_power_status: SLOTCTRL a8 value read 2f9
      [ 5924.683262] pciehp 0000:80:02.2:pcie04: pciehp_unconfigure_device: domain:bus:dev = 0000:b0:00
      [ 5924.693976] libfcoe_device_notification: NETDEV_UNREGISTER eth6
      [ 5924.764979] libfcoe_device_notification: NETDEV_UNREGISTER eth14
      [ 5924.873539] libfcoe_device_notification: NETDEV_UNREGISTER eth15
      [ 5924.995209] libfcoe_device_notification: NETDEV_UNREGISTER eth16
      [ 5926.114407] sxge 0000:b2:00.0: PCI INT A disabled
      [ 5926.119342] BUG: unable to handle kernel NULL pointer dereference at (null)
      [ 5926.127189] IP: [<ffffffff81353a3b>] pci_stop_bus_device+0x33/0x83
      [ 5926.133377] PGD 0
      [ 5926.135402] Oops: 0000 [#1] SMP
      [ 5926.138659] CPU 2
      [ 5926.140499] Modules linked in:
      ...
      [ 5926.143754]
      [ 5926.275823] Call Trace:
      [ 5926.278267]  [<ffffffff81353a38>] pci_stop_bus_device+0x30/0x83
      [ 5926.284180]  [<ffffffff81353af4>] pci_remove_bus_device+0x1a/0xba
      [ 5926.290264]  [<ffffffff81366311>] pciehp_unconfigure_device+0x110/0x17b
      [ 5926.296866]  [<ffffffff81365dd9>] ? pciehp_disable_slot+0x188/0x188
      [ 5926.303123]  [<ffffffff81365d6f>] pciehp_disable_slot+0x11e/0x188
      [ 5926.309206]  [<ffffffff81365e68>] pciehp_power_thread+0x8f/0xe0
      ...
      
       +-[0000:80]-+-00.0-[81-8f]--
       |           +-01.0-[90-9f]--
       |           +-02.0-[a0-af]--
       |           +-02.2-[b0-bf]----00.0-[b1-b3]--+-02.0-[b2]--+-00.0 Device
       |           |                               |            +-00.1 Device
       |           |                               |            +-00.2 Device
       |           |                               |            \-00.3 Device
       |           |                               \-03.0-[b3]--+-00.0 Device
       |           |                                            +-00.1 Device
       |           |                                            +-00.2 Device
       |           |                                            \-00.3 Device
      
      root complex: 80:02.2
      pci express modules: have pcie switch and are listed as b0:00.0, b1:02.0 and b1:03.0.
      end devices  are b2:00.0 and b3.00.0.
      VFs are: b2:00.1,... b2:00.3, and b3:00.1,...,b3:00.3
      
      Root cause: when doing pci_stop_bus_device() with phys fn, it will stop
      virt fn and remove the fn, so
      	list_for_each_safe(l, n, &bus->devices)
      will have problem to refer freed n that is pointed to vf entry.
      
      Solution is just replacing list_for_each_safe() with
      list_for_each_prev_safe().  This will make sure we can get valid n pointer
      to PF instead of the freed VF pointer (because newly added devices are
      inserted to the bus->devices list tail).
      
      During reviewing the patch, Bjorn said:
      |   The PCI hot-remove path calls pci_stop_bus_devices() via
      |   pci_remove_bus_device().
      |
      |   pci_stop_bus_devices() traverses the bus->devices list (point A below),
      |   stopping each device in turn, which calls the driver remove() method.  When
      |   the device is an SR-IOV PF, the driver calls pci_disable_sriov(), which
      |   also uses pci_remove_bus_device() to remove the VF devices from the
      |   bus->devices list (point B).
      |
      |       pci_remove_bus_device
      |         pci_stop_bus_device
      |           pci_stop_bus_devices(subordinate)
      |             list_for_each(bus->devices)             <-- A
      |               pci_stop_bus_device(PF)
      |                 ...
      |                   driver->remove
      |                     pci_disable_sriov
      |                       ...
      |                         pci_remove_bus_device(VF)
      |                             <remove from bus_list>  <-- B
      |
      |   At B, we're changing the same list we're iterating through at A, so when
      |   the driver remove() method returns, the pci_stop_bus_devices() iterator has
      |   a pointer to a list entry that has already been freed.
      
      Discussion thread can be found : https://lkml.org/lkml/2011/10/15/141
      				 https://lkml.org/lkml/2012/1/23/360
      
      -v5: According to Linus to make remove more robust, Change to
           list_for_each_prev_safe instead. That is more reasonable, because
           those devices are added to tail of the list before.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      ac205b7b
    • Y
      PCI: remove add_to_failed_list() · 67cc7e26
      Yinghai Lu 提交于
      Only one user; just use add_to_list instead.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      67cc7e26
    • Y
      PCI: add debug print out for add_size · b592443d
      Yinghai Lu 提交于
      For use in debugging resource reallocation.
      Signed-off-by: NYinghai Lu <yinghai@kernel.org>
      Signed-off-by: NJesse Barnes <jbarnes@virtuousgeek.org>
      b592443d