diff options
author | Bjorn Helgaas <bhelgaas@google.com> | 2013-08-29 19:23:33 -0400 |
---|---|---|
committer | Bjorn Helgaas <bhelgaas@google.com> | 2013-08-29 19:23:33 -0400 |
commit | e89c33168aad32436da842ddda307dcc31c0c4e2 (patch) | |
tree | 831668bbda77e4b5ff463b26a75c8f88819436aa /drivers/acpi/pci_root.c | |
parent | 2e8b5f621dbe29425906852c6079afb6b28720cb (diff) | |
parent | 3dc48af310709b85d07c8b0d3aa8f1ead02829d3 (diff) |
Merge branch 'pci/misc' into next
* pci/misc:
PCI/ACPI: Fix _OSC ordering to allow PCIe hotplug use when available
PCI: exynos: Add I/O access wrappers
PCI: designware: Drop "addr" arg from dw_pcie_readl_rc()/dw_pcie_writel_rc()
Diffstat (limited to 'drivers/acpi/pci_root.c')
-rw-r--r-- | drivers/acpi/pci_root.c | 62 |
1 files changed, 38 insertions, 24 deletions
diff --git a/drivers/acpi/pci_root.c b/drivers/acpi/pci_root.c index ce04eb28e029..d3874f425653 100644 --- a/drivers/acpi/pci_root.c +++ b/drivers/acpi/pci_root.c | |||
@@ -378,6 +378,7 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
378 | struct acpi_pci_root *root; | 378 | struct acpi_pci_root *root; |
379 | u32 flags, base_flags; | 379 | u32 flags, base_flags; |
380 | acpi_handle handle = device->handle; | 380 | acpi_handle handle = device->handle; |
381 | bool no_aspm = false, clear_aspm = false; | ||
381 | 382 | ||
382 | root = kzalloc(sizeof(struct acpi_pci_root), GFP_KERNEL); | 383 | root = kzalloc(sizeof(struct acpi_pci_root), GFP_KERNEL); |
383 | if (!root) | 384 | if (!root) |
@@ -437,27 +438,6 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
437 | flags = base_flags = OSC_PCI_SEGMENT_GROUPS_SUPPORT; | 438 | flags = base_flags = OSC_PCI_SEGMENT_GROUPS_SUPPORT; |
438 | acpi_pci_osc_support(root, flags); | 439 | acpi_pci_osc_support(root, flags); |
439 | 440 | ||
440 | /* | ||
441 | * TBD: Need PCI interface for enumeration/configuration of roots. | ||
442 | */ | ||
443 | |||
444 | /* | ||
445 | * Scan the Root Bridge | ||
446 | * -------------------- | ||
447 | * Must do this prior to any attempt to bind the root device, as the | ||
448 | * PCI namespace does not get created until this call is made (and | ||
449 | * thus the root bridge's pci_dev does not exist). | ||
450 | */ | ||
451 | root->bus = pci_acpi_scan_root(root); | ||
452 | if (!root->bus) { | ||
453 | dev_err(&device->dev, | ||
454 | "Bus %04x:%02x not present in PCI namespace\n", | ||
455 | root->segment, (unsigned int)root->secondary.start); | ||
456 | result = -ENODEV; | ||
457 | goto end; | ||
458 | } | ||
459 | |||
460 | /* Indicate support for various _OSC capabilities. */ | ||
461 | if (pci_ext_cfg_avail()) | 441 | if (pci_ext_cfg_avail()) |
462 | flags |= OSC_EXT_PCI_CONFIG_SUPPORT; | 442 | flags |= OSC_EXT_PCI_CONFIG_SUPPORT; |
463 | if (pcie_aspm_support_enabled()) { | 443 | if (pcie_aspm_support_enabled()) { |
@@ -471,7 +451,7 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
471 | if (ACPI_FAILURE(status)) { | 451 | if (ACPI_FAILURE(status)) { |
472 | dev_info(&device->dev, "ACPI _OSC support " | 452 | dev_info(&device->dev, "ACPI _OSC support " |
473 | "notification failed, disabling PCIe ASPM\n"); | 453 | "notification failed, disabling PCIe ASPM\n"); |
474 | pcie_no_aspm(); | 454 | no_aspm = true; |
475 | flags = base_flags; | 455 | flags = base_flags; |
476 | } | 456 | } |
477 | } | 457 | } |
@@ -503,7 +483,7 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
503 | * We have ASPM control, but the FADT indicates | 483 | * We have ASPM control, but the FADT indicates |
504 | * that it's unsupported. Clear it. | 484 | * that it's unsupported. Clear it. |
505 | */ | 485 | */ |
506 | pcie_clear_aspm(root->bus); | 486 | clear_aspm = true; |
507 | } | 487 | } |
508 | } else { | 488 | } else { |
509 | dev_info(&device->dev, | 489 | dev_info(&device->dev, |
@@ -512,7 +492,14 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
512 | acpi_format_exception(status), flags); | 492 | acpi_format_exception(status), flags); |
513 | dev_info(&device->dev, | 493 | dev_info(&device->dev, |
514 | "ACPI _OSC control for PCIe not granted, disabling ASPM\n"); | 494 | "ACPI _OSC control for PCIe not granted, disabling ASPM\n"); |
515 | pcie_no_aspm(); | 495 | /* |
496 | * We want to disable ASPM here, but aspm_disabled | ||
497 | * needs to remain in its state from boot so that we | ||
498 | * properly handle PCIe 1.1 devices. So we set this | ||
499 | * flag here, to defer the action until after the ACPI | ||
500 | * root scan. | ||
501 | */ | ||
502 | no_aspm = true; | ||
516 | } | 503 | } |
517 | } else { | 504 | } else { |
518 | dev_info(&device->dev, | 505 | dev_info(&device->dev, |
@@ -520,6 +507,33 @@ static int acpi_pci_root_add(struct acpi_device *device, | |||
520 | "(_OSC support mask: 0x%02x)\n", flags); | 507 | "(_OSC support mask: 0x%02x)\n", flags); |
521 | } | 508 | } |
522 | 509 | ||
510 | /* | ||
511 | * TBD: Need PCI interface for enumeration/configuration of roots. | ||
512 | */ | ||
513 | |||
514 | /* | ||
515 | * Scan the Root Bridge | ||
516 | * -------------------- | ||
517 | * Must do this prior to any attempt to bind the root device, as the | ||
518 | * PCI namespace does not get created until this call is made (and | ||
519 | * thus the root bridge's pci_dev does not exist). | ||
520 | */ | ||
521 | root->bus = pci_acpi_scan_root(root); | ||
522 | if (!root->bus) { | ||
523 | dev_err(&device->dev, | ||
524 | "Bus %04x:%02x not present in PCI namespace\n", | ||
525 | root->segment, (unsigned int)root->secondary.start); | ||
526 | result = -ENODEV; | ||
527 | goto end; | ||
528 | } | ||
529 | |||
530 | if (clear_aspm) { | ||
531 | dev_info(&device->dev, "Disabling ASPM (FADT indicates it is unsupported)\n"); | ||
532 | pcie_clear_aspm(root->bus); | ||
533 | } | ||
534 | if (no_aspm) | ||
535 | pcie_no_aspm(); | ||
536 | |||
523 | pci_acpi_add_bus_pm_notifier(device, root->bus); | 537 | pci_acpi_add_bus_pm_notifier(device, root->bus); |
524 | if (device->wakeup.flags.run_wake) | 538 | if (device->wakeup.flags.run_wake) |
525 | device_set_run_wake(root->bus->bridge, true); | 539 | device_set_run_wake(root->bus->bridge, true); |