blob: 5cdb7c80b1f10017ee9fc32ef56417f71444c53f [file] [log] [blame]
// Copyright 2022 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SRC_GRAPHICS_DISPLAY_DRIVERS_INTEL_I915_FIRMWARE_BRIDGE_H_
#define SRC_GRAPHICS_DISPLAY_DRIVERS_INTEL_I915_FIRMWARE_BRIDGE_H_
// This file implements Intel's ACPI (Advanced Configuration and
// Power Interface) IGD (Integrated Graphics Device) OpRegion Specification.
//
// See the .cc file for full documentation references.
#include <lib/device-protocol/pci.h>
#include <lib/zx/result.h>
#include <zircon/types.h>
#include <cstddef>
namespace i915 {
// The GMCH (Graphics Memory Controller Hub) PCI configuration space OpRegion.
//
// First release: Section 2.3 "OpRegion Initialization", pages 27-30
// 728117: Section 2.2 "GMCH PCI Config OpRegion", pages 8-9
// 621530: Section 2.3 "GMCH PCI Config OpRegion", page 10
class PciConfigOpRegion {
public:
explicit PciConfigOpRegion(ddk::Pci& pci);
PciConfigOpRegion(const PciConfigOpRegion&) = delete;
PciConfigOpRegion& operator=(const PciConfigOpRegion&) = delete;
~PciConfigOpRegion();
// Reads the Memory OpRegion address from the PCI configuration space.
zx::result<zx_paddr_t> ReadMemoryOpRegionAddress();
// Invokes the system firmware using the OpRegion SWSCI mechanism.
//
// SWSCI (Software System Control Interrupt) is a mechanism for the display
// driver to invoke the system firmware (BIOS). This mechanism was introduced
// in the OpRegion spec, with the goal of removing the need to grant drivers
// the capability of invoking SMM interrupts and video BIOS interrupts.
//
// SWSCI is relegated to fringe functionality that is not covered by the ACPI
// specification and by the VBT (Video BIOS Table). Document 621530 suggests
// that SWSCI has been removed from recent OpRegion versions, as all
// references to it (Mailbox 2, private ACPI calls) were removed.
//
// Returns ZX_ERR_BAD_STATE if the SWSCI mechanism is in use at the time of
// the call, or ZX_ERR_NOT_SUPPORTED if the firmware doesn't appear to support
// the OpRegion protocol. If any PCI operation fails, returns the underlying
// zx_status_t error.
//
// The caller must set up Mailbox 2 correctly in the Memory OpRegion before
// invoking the system firmware.
//
// The caller should ensure that SWSCI mechanism is not in use before the
// call. This can be accomplished by calling IsSystemControlInterruptInUse()
// and/or additional synchronization in the layer above PciConfigOpRegion.
//
// After the call, the caller should track when the system firmware completes
// the request, by polling IsSystemControlInterruptInUse() together with the
// "SCI issued" field in the SCIC (Software SCI Entry/Exit parameter) member
// of Mailbox 2 in the Memory OpRegion.
zx::result<> TriggerSystemControlInterrupt();
// Checks if the OpRegion SWSCI mechanism is currently in use.
//
// See TriggerSystemControlInterrupt() for a description of SWSCI.
//
// This check involves reading the SWSCI register from the PCI configuration
// space. If the PCI operation fails, returns the underlying zx_status_t
// error. Returns ZX_ERR_NOT_SUPPORTED if the SWSCI register state indicates
// that the firmware does not support the OpRegion protocol.
//
// If the system firmware supports the OpRegion protocol, this method should
// succeed and return false (indicating that SWSCI is not currently in use)
// when the display driver starts up.
zx::result<bool> IsSystemControlInterruptInUse();
private:
ddk::Pci& pci_;
};
} // namespace i915
#endif // SRC_GRAPHICS_DISPLAY_DRIVERS_INTEL_I915_FIRMWARE_BRIDGE_H_