/** * DOC: LPE Audio integration for HDMI or DP playback * * Motivation: * Atom platforms (e.g. valleyview and cherryTrail) integrates a DMA-based * interface as an alternative to the traditional HDaudio path. While this * mode is unrelated to the LPE aka SST audio engine, the documentation refers * to this mode as LPE so we keep this notation for the sake of consistency. * * The interface is handled by a separate standalone driver maintained in the * ALSA subsystem for simplicity. To minimize the interaction between the two * subsystems, a bridge is setup between the hdmi-lpe-audio and i915: * 1. Create a platform device to share MMIO/IRQ resources * 2. Make the platform device child of i915 device for runtime PM. * 3. Create IRQ chip to forward the LPE audio irqs. * the hdmi-lpe-audio driver probes the lpe audio device and creates a new * sound card * * Threats: * Due to the restriction in Linux platform device model, user need manually * uninstall the hdmi-lpe-audio driver before uninstalling i915 module, * otherwise we might run into use-after-free issues after i915 removes the * platform device: even though hdmi-lpe-audio driver is released, the modules * is still in "installed" status. * * Implementation: * The MMIO/REG platform resources are created according to the registers * specification. * When forwarding LPE audio irqs, the flow control handler selection depends * on the platform, for example on valleyview handle_simple_irq is enough. *
*/
if (IS_ERR(platdev)) {
drm_err(display->drm, "Failed to allocate LPE audio platform device\n"); return platdev;
}
pm_runtime_no_callbacks(&platdev->dev);
return platdev;
}
staticvoid lpe_audio_platdev_destroy(struct intel_display *display)
{ /* XXX Note that platform_device_register_full() allocates a dma_mask * and never frees it. We can't free it here as we cannot guarantee * this is the last reference (i.e. that the dma_mask will not be * used after our unregister). So ee choose to leak the sizeof(u64) * allocation here - it should be fixed in the platform_device rather * than us fiddle with its internals.
*/
if (IS_ERR(display->audio.lpe.platdev)) {
ret = PTR_ERR(display->audio.lpe.platdev);
drm_err(display->drm, "Failed to create lpe audio platform device: %d\n",
ret); goto err_free_irq;
}
/* enable chicken bit; at least this is required for Dell Wyse 3040 * with DP outputs (but only sometimes by some reason!)
*/
intel_de_write(display, VLV_AUD_CHICKEN_BIT_REG,
VLV_CHICKEN_BIT_DBG_ENABLE);
/** * intel_lpe_audio_irq_handler() - forwards the LPE audio irq * @display: display device * * the LPE Audio irq is forwarded to the irq handler registered by LPE audio * driver.
*/ void intel_lpe_audio_irq_handler(struct intel_display *display)
{ int ret;
if (!HAS_LPE_AUDIO(display)) return;
ret = generic_handle_irq(display->audio.lpe.irq); if (ret)
drm_err_ratelimited(display->drm, "error handling LPE audio irq: %d\n", ret);
}
/** * intel_lpe_audio_init() - detect and setup the bridge between HDMI LPE Audio * driver and i915 * @display: display device * * Return: 0 if successful. non-zero if detection or * llocation/initialization fails
*/ int intel_lpe_audio_init(struct intel_display *display)
{ int ret = -ENODEV;
if (lpe_audio_detect(display)) {
ret = lpe_audio_setup(display); if (ret < 0)
drm_err(display->drm, "failed to setup LPE Audio bridge\n");
} return ret;
}
/** * intel_lpe_audio_teardown() - destroy the bridge between HDMI LPE * audio driver and i915 * @display: display device * * release all the resources for LPE audio <-> i915 bridge.
*/ void intel_lpe_audio_teardown(struct intel_display *display)
{ if (!HAS_LPE_AUDIO(display)) return;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.